PDA

View Full Version : Correct use of ActionObject_ID and UseObject_ID



xelanoimis
19-11-07, 07:12 AM
While working on my game, I found a situation worth mentioning here too.
It's about correct use of the ActionObject_ID and UseObject_ID callbacks.
Obviously, it's for those who work on their DizzyAGE games and have knowledge about the script.

Here is the situation:
You have a closed door (or a trigger), as an action object, and you want Dizzy to say something about it when he presses action in front of it, for the first time.
After that, you want him to be able to use objects on it, to finally open it with a key item.

So, you could do it all, using the ActionObject_ID callback. Something like this:



func ActionObject_1000()
{
idxdoor = ObjFind(1000);
status = ObjGet(idxdoor,O_STATUS);
if(status==0)
{
Message1(2,2,"IT'S LOCKED!");
ObjSet(idxdoor,O_STATUS,1);
}
else
{
idx = OpenDialogInventory();
if(idx==ObjFind(5000)) // the id of the key
{
// unlock it, message, show or hide tile, remove the key from inventory etc.
ObjSet(idxdoor,O_DISABLE,1); // puzzle solved, disable the action object
}
else
if(idx!=-1)
UseObject(idx);
}
}


The above method is fine, but there is a small issue about it:

If you have an item in front of the door, pressing action will pick it up and open the Inventory Dialog.
There you can choose the key object and use it on the door.
If the door is already in status 1, accepting objects, you might expect this to work, since you are using the key on the door, as you shoud.

But the game does not that,
because, when used from inventory, the UseObject_1000(idx) would be called with the index of the key object.
However, we don't have this callback implemented, since we did the key test inside the ActionObject callback.

So in these situation it's correct to implement both callbacks, like this:



func ActionObject_1000()
{
idxdoor = ObjFind(1000);
status = ObjGet(idxdoor,O_STATUS);
if(status==0)
{
Message1(2,2,"IT'S LOCKED!");
ObjSet(idxdoor,O_STATUS,1);
}
else
{
idx = OpenDialogInventory();
if(idx!=-1)
UseObject(idx); // will call UseObject_1000 callback
}
}

func UseObject_1000(idx)
{
if(idx==ObjFind(5000)) // the id of the key
{
// unlock it, message, show or hide tile, remove the key from inventory etc.
ObjSet(ObjFind(1000),O_DISABLE,1); // puzzle solved, disable the action object
}
else
DropObject(idx);
}


So, in conclusion:
1. When using an item from the Inventory Dialog, after another was just picked up, the UseObject_ID is called, not the ActionObject_ID.
2. So this would skip the ActionObject_ID, if there is a pickable object, in front of the action object.
3. You can end with a pickable object in front of the action object, by picking and dropping it while you move closer to the action object.
4. If you fail implementing the above code, you will have no result when using the key in front of the door, after you picked other item that was in front of it.
Of course it will work if you press action button again, and select the key again.

If more is needed on the subject, let me know.

delta
19-11-07, 11:46 AM
That's almost exactly the way i do it.

if the status is 0, then you get a message saying something like 'the door is locked', then it sets the status to 5. the next time you action it, it opens the inventory and calls the useobject function, where it decides if you've selected the correct object or not.

once the door is open, it can then either disable the door trigger, or set the status as something else to allow it to be actioned again.

never seen it done the top way before, and correct me if i'm wrong, but i don't think you'd get to choose which object to use if coding it the top way...

xelanoimis
19-11-07, 05:10 PM
In the first version, the inventory dialog is opened with OpenDialogInventory() that allows you to choose one item and the result (index of selected item) is tested for matching the key object (id=5000). If so, specific action is performed right there, on the spot.

It is not really incorrect, but it doesn't deal with the case I mentioned before.

delta
19-11-07, 07:49 PM
ahh yes i see the problem with it.

i was at work earlier, concentrating on other things. :)