Author Topic: MODULE: [UI] DragDrop 1.0.0: helps to drag things around your AGS game!  (Read 6537 times)

DOWNLOAD DragDrop 1.0.0 MODULE
DOWNLOAD DragDropCommon 1.0.1 MODULE
DOWNLOAD Demo game (needs AGS 3.2.1 or higher)

Latest source code may be found here
Git cloning address: https://ivan-mogilko@bitbucket.org/ivan-mogilko/ags-script-modules.git
Demo Game(s) cloning address: https://ivan-mogilko@bitbucket.org/ivan-mogilko/ags-script-demos.git

Module supports AGS 3.2.1 and higher.



DragDrop module implements abstract drag-and-drop functionality. It does not drag and drop any particular item on its own, but it provides means for easily scripting such actions inside your game, or write advanced d'n'd script modules for which it serves as a functional base.

Here it is accompanied by DragDropCommon module, which lets you drag and drop built-in AGS objects, such as: characters, room objects, guis and gui controls, and inventory items. DragDropCommon module requires DragDrop, and may serve a good example of its use.


DragDrop API may be confusing at first, and requires expanded explanation. For those who want a quick test of its ability, here is a quick example of using DragDropCommon in your game:

1. Add both DragDrop and DragDropCommon modules to your game. DragDrop should be higher in the module list, or your game won't compile.
2. In one of the rooms add following code to the "After Fade-in" event handler:
Code: Adventure Game Studio
  1.   DragDrop.Enabled = true;
  2.   DragDropCommon.ModeEnabled[eDragDropCharacter] = true;
  3.   DragDropCommon.ModeEnabled[eDragDropRoomObject] = true;
  4.   DragDropCommon.DragMove = eDDCmnMoveSelf;
  5.  
3. Just in case, add following code to the "Leave room" event handler:
Code: Adventure Game Studio
  1.   DragDropCommon.DisableAllModes();
  2.   DragDrop.Enabled = false;
  3.  
4. That's it! Now you can drag and drop characters and objects with your mouse in that room. Have fun :).



Using DragDrop

DragDrop is an abstract functionality module, which means that it does not drag any objects by itself. Instead, it tracks mouse movement and related button state, and tells you when the important events take place. It is up to you to handle such events correspondingly: provide description of a custom draggable object, update custom object's position as it is being dragged around, etc.
A number of things in DragDrop may be automated, but almost everything may also be customized and overriden. You will need a good understanding of the concepts to make it work best for your game.


Basic terms
Draggable object - this is something that can be dragged to another position.
Hooking - is an event of "grappling up" the draggable object to move it somewhere.
Hook Key - is the key or mouse button that should be pressed down to hook an object.
Dragging - is the process of moving hooked object around while the hook key is down; NOTE: it does not have to literally move an actual object on screen, it may be a "pseudo-object", an object link, etc.
Drop - the event of putting an object onto new position; usually occurs when the hook key was released, but may also be triggered by script command.



Signal properties
Since AGS does not support custom callbacks (calling your own functions when something happened in script module), DragDrop tells you about immediate events by setting certain signal properties. These properties are easily distinguished by "Evt*" prefix.
The positive values on signal properties only set for 1 game tick (update), and are reset immediately afterwards. They literally mean that the event has just occured, and you should react to that. The next tick they will be reset until some event occurs again.
You will have to check these properties periodically, in the "repeatedly_execute" or "repeatedly_execute_always" functions of GlobalScript or your own custom script to know when the related events occur.


Drag-and-drop phases
Module distinguishes several phases (steps) in drag-n-drop action. Changing from one phase to another is followed by signalling an event (as explained in Signal properties section). The phase may be changed automatically, when certain conditions are met, or by calling particular module function. Latter lets user to customize and control DragDrop behavior.

The following table lists all phases, as well as corresponding events. "Automation" column names properties that regulate default/automatic passing of the phase, while "User command" column lists the functions that must be called to manually pass to the next phase, skipping or overriding automation.
Note that some of the commands won't work unless the module is in particular phase. For example, you cannot order module to drop an object if no object is dragged yet.


PhaseExplanationEventAutomationUser command
IdleAt this phase module waits until the hook key is pressed down.---DefaultHookKey, DefaultHookMouseButton, AutoTrackHookKey propertiesHookKeyDown()
Hooking objectModule expects to grapple an object under mouse cursor.EvtWantObject---HookObject()
Waiting for dragAfter object was hooked, module expects certain conditions to complete before dragging may start, such as minimal mouse move distance or time hook key was pressed down.EvtObjectHookedDragMinDistance, DragMinTime propertiesHookKeyUp(), Drop(), DropAt(), Revert()
DraggingThe object is being dragged around. It takes releasing hook key or explicit command for a dragging to stop.EvtDragStartedAutoTrackHookKey propertyHookKeyUp(), Drop(), DropAt(), Revert()
DroppingWhen the hook key is released, module notifies user that the object is about to be dropped. User may rely on default action, or call a related command.EvtWantDropDefaultUnhookAction propertyDrop(), DropAt(), Revert()
After droppedThis is one extra tick before returning to idle mode, when the user script may still access information on dropped object and perform some final processing on its side.EvtDropped------


Practical use in detail

Whether to automate or manually control particular phases - this depends on what effect you are trying to achieve.

Letting module trigger object hook and dragging is done by assigning a hook key using either DragDrop.DefaultHookKey or DragDrop.DefaultHookMouseButton properties. DragDrop.AutoTrackHookKey property should also be set as 'true'.

If you want to use several hook keys, for example - each key determining its own custom drag'n'drop mode - then you should probably disable default hook key by setting both properties (DefaultHookKey and DefaultHookMouseButton) to zero. In your own script call DragDrop.HookKeyDown() function, providing key code or mouse button code.

You may still keep AutoTrackHookKey enabled so that the module was automatically detecting when the hook key you defined is released.

If you just do not want the module to be affected by actual key/mouse clicks at all, then you should set AutoTrackHookKey to 'false'.
Also, HookKeyDown() does not need to get a real key code. You may pass some imaginary key code. Since the module writes that key code down and lets you read it while the object is being dragged, that code could later be used in your own script as a reference.
If AutoTrackHookKey is disabled, you will have to call DragDrop.HookKeyUp() in time to tell the module that the hook key was released (whether that was a real or not real key).

In any case you must provide your own object data upon EvtWantObject signal. You do so by calling DragDrop.HookObject() function. This function basically tells the module some abstract information about the dragged object:
Code: Adventure Game Studio
  1. static void  HookObject(int user_mode, int obj_x, int obj_y, int tag = 0, String stag = 0);
  2.  
'User_mode' is a custom value that determines a drag'n'drop mode. Pass the value you want - since you will be the one who needs it - or just any random number, except for 0, which means "no mode" for the module.
'Obj_x' and 'obj_y' are object's coordinates that define its position. These should be the values that you may rely upon in your own script. As for the module itself, it does not care if these are sensible or related to an actual item on screen at all. However the module remembers a distance between mouse cursor and provided object coordinates, and keeps this distance same when calculating new object position after mouse drag starts. This calculated position may be read using DragDrop.ObjectX and DragDrop.ObjectY properties.
The 'tag' and 'stag' parameters are user-defined values that could be useful if you need to identify the dragged object somehow. They are readable using DragDrop.ObjectTag and DragDrop.ObjectSTag properties as long as the object is being dragged, and right after it was dropped.

Remember, that although the dragged object's position is updated properly by the module, it does not move anything itself. You should do that in your own script, using ObjectX and ObjectY values as a reference. Whether you actually move something on screen, or just check where object was supposed to move, is completely up to you.

When getting EvtWantDrop signal you have a chance to decide whether to let object drop at its current position, drop somewhere else, or completely revert back to initial position. This can be done by calling DragDrop.Drop(), DragDrop.DropAt() or DragDrop.Revert().
If you do not call anything at this time, the module will drop or revert depending on the DragDrop.DefaultUnhookAction setting.

In either case, module will update ObjectX and ObjectY values last time, and set EvtDropped signal, which means that the object is not going anywhere anymore (at least not until next drag). You may use this moment as a last chance to update your real object. For example, you may finally assign its position to ObjectX and ObjectY values.



DragDrop API

Following are properties and functions of the DragDrop class, that are exposed for use in your scripts:

Code: Adventure Game Studio
  1. enum DragDropMode
  2. {
  3.   eDragDropNone = 0
  4. };
  5.  
  6. // An action to do when the hook key is released
  7. enum DragDropUnhookAction
  8. {
  9.   eDDUnhookDrop,  // drop the dragged object at current cursor position
  10.   eDDUnhookRevert // revert the dragged object to its initial position
  11. };
  12.  
  13. struct DragDrop
  14. {
  15.   ///////////////////////////////////////////////////////////////////////////
  16.   //
  17.   // Setting up
  18.   // ------------------------------------------------------------------------
  19.   // Functions and properties meant to configure the drag'n'drop behavior.
  20.   //
  21.   ///////////////////////////////////////////////////////////////////////////
  22.  
  23.   /// Enables or disables DragDrop work, without cancelling any settings
  24.   import static attribute bool        Enabled;
  25.  
  26.   /// Get/set default hook key
  27.   import static attribute eKeyCode    DefaultHookKey;
  28.   /// Get/set default hook mouse button
  29.   import static attribute MouseButton DefaultHookMouseButton;
  30.   /// Get/set minimal number of pixels the mouse should move before it is considered to be dragging
  31.   import static attribute int         DragMinDistance;
  32.   /// Get/set minimal time (in milliseconds) the mouse should move before it is considered to be dragging
  33.   import static attribute int         DragMinTime;
  34.  
  35.   /// Get/set if the module should automatically track hook key press and release
  36.   import static attribute bool        AutoTrackHookKey;
  37.   /// Get/set the default action that should be done to dragged object when the hook key is released;
  38.   /// this action may be overriden by user by explicitly calling Drop() or Revert()
  39.   import static attribute DragDropUnhookAction DefaultUnhookAction;
  40.  
  41.  
  42.   ///////////////////////////////////////////////////////////////////////////
  43.   //
  44.   // Event signals
  45.   // ------------------------------------------------------------------------
  46.   // Properties meant to signal user about drag'n'drop events.
  47.   //
  48.   ///////////////////////////////////////////////////////////////////////////
  49.  
  50.   /// Gets if the hook key was pushed down and the module is looking for the actual
  51.   /// draggable object under the cursor; this is when the user should supply module
  52.   /// with draggable object
  53.   readonly import static attribute bool EvtWantObject;
  54.   /// Gets if the draggable object was just hooked; this is when the user may take
  55.   /// some action right before the object will be actually dragged around
  56.   readonly import static attribute bool EvtObjectHooked;
  57.   /// Gets if mouse drag just started; this event takes place if the draggable object
  58.   /// was found and drag conditions were met (minimal drag time and/or distance)
  59.   readonly import static attribute bool EvtDragStarted;
  60.   /// Gets if the mouse drag was just released; the event takes place just a tick
  61.   /// before object is actually dropped on a new place, letting user to choose a drop
  62.   /// coordinates or revert the drag
  63.   readonly import static attribute bool EvtWantDrop;
  64.   /// Gets if the object was just dropped on a new position
  65.   readonly import static attribute bool EvtDropped;
  66.  
  67.  
  68.   ///////////////////////////////////////////////////////////////////////////
  69.   //
  70.   // State control
  71.   // ------------------------------------------------------------------------
  72.   // Properties and functions meant to tell about current drag'n'drop process
  73.   // and control its state.
  74.   //
  75.   ///////////////////////////////////////////////////////////////////////////
  76.  
  77.   /// Gets if the module is currently doing nothing
  78.   readonly import static attribute bool         IsIdle;
  79.   /// Gets if the module has an object hooked (during pre-dragging, dragging or dropping states)
  80.   readonly import static attribute bool         HasObjectHooked;
  81.   /// Gets if the mouse is currently being dragged (drag button held down and mouse moved)
  82.   readonly import static attribute bool         IsDragging;
  83.   /// Gets the current hook key
  84.   readonly import static attribute int          CurrentKey;
  85.   /// Gets the current drag mouse button
  86.   readonly import static attribute MouseButton  CurrentMouseButton;
  87.   /// Gets the current drag mode (this hints the type of object being dragged)
  88.   readonly import static attribute int          CurrentMode;
  89.   /// Gets the user-defined dragged object integer tag
  90.   readonly import static attribute int          ObjectTag;
  91.   /// Gets the user-defined dragged object String tag
  92.   readonly import static attribute String       ObjectSTag;
  93.   /// Gets X coordinate of cursor position at which the hook key was pushed down
  94.   readonly import static attribute int          DragStartX;
  95.   /// Gets Y coordinate of cursor position at which the hook key was pushed down
  96.   readonly import static attribute int          DragStartY;
  97.   /// Gets X coordinate of initial object's position
  98.   readonly import static attribute int          ObjectStartX;
  99.   /// Gets Y coordinate of initial object's position
  100.   readonly import static attribute int          ObjectStartY;
  101.   /// Gets X coordinate of the dragged object's position
  102.   readonly import static attribute int          ObjectX;
  103.   /// Gets Y coordinate of the dragged object's position
  104.   readonly import static attribute int          ObjectY;
  105.  
  106.   /// Notify hook key push down; this does not have to be real keycode
  107.   import static void  HookKeyDown(int user_key = 0, MouseButton mbtn = 0);
  108.   /// Assign a draggable object for the module when it expects to find one under the mouse cursor
  109.   import static void  HookObject(int user_mode, int obj_x, int obj_y, int tag = 0, String stag = 0);
  110.   /// Notify hook key release
  111.   import static void  HookKeyUp();
  112.  
  113.   /// Drop the object now
  114.   import static void  Drop();
  115.   /// Drop the object now and position it at the given coordinates
  116.   import static void  DropAt(int x, int y);
  117.   /// Reset drag; if an AGS object was dragged, return it to original position
  118.   import static void  Revert();
  119. };
  120.  


Examples of use

The possibly simpliest example of using DragDrop is this:
Code: Adventure Game Studio
  1. function game_start()
  2. {
  3.   DragDrop.Enabled = true;
  4. }
  5.  
  6. #define MY_DRAGDROP_MODE 1
  7.  
  8. function repeatedly_execute()
  9. {
  10.   if (DragDrop.EvtWantObject)
  11.   {
  12.     DragDrop.HookObject(MY_DRAGDROP_MODE, mouse.x, mouse.y);
  13.   }
  14.   else if (DragDrop.EvtDropped)
  15.   {
  16.     // cannot use blocking functions in repeatedly_execute, so use SayBackground
  17.     player.SayBackground(String.Format("An object was moved from (%d,%d) to (%d,%d)", DragDrop.ObjectStartX, DragDrop.ObjectStartY, DragDrop.ObjectX, DragDrop.ObjectY));
  18.   }
  19. }
  20.  

Real working examples may be larger, and I recommend to refer to the Demo game for better code:
https://bitbucket.org/ivan-mogilko/ags-script-modules/downloads/DragDropDemo_1.0.0.zip

Also, the DragDropCommon module itself may be a good example, because it uses DragDrop features to move actual AGS objects around.



Using DragDropCommon

DragDropCommon module uses DragDrop interface in same way as a regular user will, to drag the built-in AGS object types, such as Characters, Room objects, GUIs and GUI controls, and Inventory Items. It is pretty simple to setup and use. As with base DragDrop module there is default behavior and ways to override one.


DragDropCommon API

Following are properties and functions of the DragDropCommon class, that are exposed for use in your scripts:

Code: Adventure Game Studio
  1.  
  2. enum DragDropCommonMode
  3. {
  4.   eDragDropCharacter = 1,
  5.   eDragDropGUI,
  6.   eDragDropGUIControl,
  7.   eDragDropRoomObject,
  8.   eDragDropInvItem,
  9.   NUM_DRAGDROPCOMMON_MODES
  10. };
  11.  
  12. // DragDropCommonMove enumeration determines the way hooked object is being dragged around
  13. enum DragDropCommonMove
  14. {
  15.   // drag actual object itself (position updates real-time)
  16.   eDDCmnMoveSelf,
  17.   // drag overlay with object's image, while object stays in place until drag ends;
  18.   // this currently works only for characters and room objects!
  19.   eDDCmnMoveGhostOverlay,
  20.   // drag GUI with object's image; this is currently only way to drag inventory items
  21.   eDDCmnMoveGhostGUI
  22. };
  23.  
  24. struct DragDropCommon
  25. {
  26.   ///////////////////////////////////////////////////////////////////////////
  27.   //
  28.   // Setting up
  29.   // ------------------------------------------------------------------------
  30.   // Functions and properties meant to configure the drag'n'drop behavior.
  31.   //
  32.   ///////////////////////////////////////////////////////////////////////////
  33.  
  34.   /// Get/set whether particular drag'n'drop mode is enabled
  35.   import static attribute bool  ModeEnabled[];
  36.   /// Disable drag'n'drop for all the modes
  37.   import static void            DisableAllModes();
  38.  
  39.   /// Get/set whether click on AGS object should be tested using pixel-perfect detection
  40.   /// (alternatively only hit inside bounding rectangle is tested)
  41.   import static attribute bool  PixelPerfect;
  42.   /// Get/set whether only Clickable AGS objects should be draggable
  43.   import static attribute bool  TestClickable;
  44.  
  45.   /// Get/set the way object's drag around is represented
  46.   import static attribute DragDropCommonMove DragMove;
  47.   /// Get/set transparency of a representation used when DragStyle is NOT eDragDropMoveSelf
  48.   import static attribute int   GhostTransparency;
  49.   /// Get/set whether representation should keep sprite's alpha channel
  50.   import static attribute bool  GhostAlpha;
  51.   /// Get/set the GUI used to represent dragged object
  52.   import static attribute GUI*  GhostGUI;
  53.  
  54.  
  55.   ///////////////////////////////////////////////////////////////////////////
  56.   //
  57.   // State control
  58.   // ------------------------------------------------------------------------
  59.   // Properties and functions meant to tell about current drag'n'drop process
  60.   // and control its state.
  61.   //
  62.   ///////////////////////////////////////////////////////////////////////////
  63.  
  64.   /// Gets current dragged character
  65.   readonly import static attribute Character*   _Character;
  66.   /// Gets current dragged GUI
  67.   readonly import static attribute GUI*         _GUI;
  68.   /// Gets current dragged GUIControl
  69.   readonly import static attribute GUIControl*  _GUIControl;
  70.   /// Gets current dragged room Object
  71.   readonly import static attribute Object*      _RoomObject;
  72.   /// Gets current dragged Inventory Item
  73.   readonly import static attribute InventoryItem* _InvItem;
  74.   /// Gets current dragged object's or its representation width
  75.   readonly import static attribute int          ObjectWidth;
  76.   /// Gets current dragged object's or its representation height
  77.   readonly import static attribute int          ObjectHeight;
  78.   /// Gets current dragged overlay's graphic (only if drag style is NOT eDragDropMoveSelf)
  79.   readonly import static attribute int          UsedGhostGraphic;
  80.  
  81.   /// Start dragging a character under cursor
  82.   import static bool  TryHookCharacter();
  83.   /// Start dragging a GUI under cursor
  84.   import static bool  TryHookGUI();
  85.   /// Start dragging a GUI Control under cursor
  86.   import static bool  TryHookGUIControl();
  87.   /// Start dragging a room Object under cursor
  88.   import static bool  TryHookRoomObject();
  89.   /// Start dragging an Inventory Item under cursor
  90.   import static bool  TryHookInventoryItem();
  91.   /// Try to find an applicable object to drag under cursor, based on currently enabled modes
  92.   import static bool  TryHookDraggableObject();
  93. };
  94.  

Enabling particular modes is needed for automatic object hookup. If you are going to hook objects manually (calling functions like TryHookCharacter(), etc), you do not need to enable these.

Depending on DragMove property value, this module either moves the actual object on screen at real-time (eDDCmnMoveSelf mode), or moves its "ghost" clone image on overlay (eDDCmnMoveGhostOverlay mode) or custom GUI (eDDCmnMoveGhostGUI mode). Overlay is created automatically, but you must assign GhostGUI if you want to use GUI mode.
In the first case you do not need to move object yourself, but in the last two cases you will have to script actual object repositioning yourself, presumably on receiving EvtWantDrop signal.


NOTE: it is possible to have DragDropCommon and your own custom drag modes in the same game, and even at the same time. But you should make sure that you choose a new mode IDs that do not mess up with DragDropCommon's mode numbers.


NOTE: DragDropCommon has a pixel perfect detection option, but it works only for characters and room objects now.



The modules are working in general, but still need more public testing.
Comments, critism, suggestions and bug reports are welcome.
« Last Edit: 18 Jul 2021, 22:02 by Crimson Wizard »

selmiak

  • ǝsıɔɹǝxǝ ʞɔǝu puɐ uıɐɹq
    • I can help with play testing
    • I can help with proof reading
    • I can help with translating
    • I can help with web design
    • selmiak worked on one or more games that won an AGS Award!
    •  
    • selmiak worked on one or more games that was nominated for an AGS Award!
Now this sounds really useful! Especially for mobile games and even cooler ingame computerscreens with hacking!

And hereby I release Drag & Drop module v1.0.0.
DOWNLOAD DragDrop 1.0.0 MODULE
DOWNLOAD DragDropCommon 1.0.0 MODULE
DOWNLOAD Demo game (needs AGS 3.2.1 or higher)
(Also updated first post)

Not sure how much this was popular, since I got only 1 response and no questions about module usage, but I keep hopes that it will be useful to some.

What's new in 1.0.0

This update was focused on making DragDropCommon module capable of dragging object images instead of objects themselves, which also let me implement dragging of InventoryItems.

1. Added DragDropCommon.DragMove property, which determines the way dragging is done. It can be:
- eDDCmnMoveSelf - drags the object itself at real time (does not work for Inventory Items);
- eDDCmnMoveGhostOverlay - drags overlay with object's image on it (won't work for GUI and Controls);
- eDDCmnMoveGhostGUI - drags supplied custom GUI with object's image on it (currently does not work for GUI and Controls, but this is ONLY way to make inventory items drag & drop);

2. Additionally to DragMove, following properties can be set:
- DragDropCommon.GhostTransparency - determines ghost mode image transparency;
- DragDropCommon.GhostAlpha - determines whether ghost mode uses images with alpha channel;
- DragDropCommon.GhostGUI - sets custom GUI to be used for eDDCmnMoveGhostGUI mode (this MUST be set, otherwise it won't work);

3. Following new properties are meant for reading current state:
- DragDropCommon._InvItem - pointer to inventory item (if one is being dragged);
- DragDropCommon.ObjectWidth - returns dragged object/representation width, either taken from its properties, or deduced from the image;
- DragDropCommon.ObjectHeight - returns dragged object/representation height, either taken from its properties, or deduced from the image;
- DragDropCommon.UsedGhostGraphic - returns actual graphic index used in ghost modes (or 0);

4. Added DragDropCommon.TryHookInventoryItem() function, which, naturally, tries to start dragging inventory item under DragDrop.DragStartX / DragStartY coordinates.


Extended and improved Demo Game. I was actually worried if those who downloaded it noticed there are more than 1 room. So this time I provided slightly better help messages and a kind of "startup menu".
Also, now there are 4 demo rooms.
« Last Edit: 29 Jul 2016, 01:02 by Crimson Wizard »

thank you, but I can edit it like the deduction room, like Sherlock Holmes: Crimes & Punishments?

thank you, but I can edit it like the deduction room, like Sherlock Holmes: Crimes & Punishments?

Yes of course. The module was created having extension in mind, that allows you to script dragging of both built-in AGS objects and also any kind of custom "entities" in your game, that you define yourself.

Before using it I recommend to first find out how do you set up the deduction room itself. After you know what kind of objects you will have there, and which AGS features will represent them, then I may be able to give more detailed advice for the use of this module.

Cassiebsg

  • Cavefish
  • Fleeing the Cylon tyrrany...
    • Cassiebsg worked on one or more games that won an AGS Award!
    •  
    • Cassiebsg worked on one or more games that was nominated for an AGS Award!
Okay, I just installed this module as I got an idea where this will be perfect.
But after following your instrucs from the first post:
Quote
1. Add both DragDrop and DragDropCommon modules to your game. DragDrop should be higher in the module list, or your game won't compile.
2. In one of the rooms add following code to the "After Fade-in" event handler:
Code: Adventure Game Studio

      DragDrop.Enabled = true;
      DragDropCommon.ModeEnabled[eDragDropCharacter] = true;
      DragDropCommon.ModeEnabled[eDragDropRoomObject] = true;
     

3. Just in case, add following code to the "Leave room" event handler:
Code: Adventure Game Studio

      DragDropCommon.DisableAllModes();
      DragDrop.Enabled = false;
     

4. That's it! Now you can drag and drop characters and objects with your mouse in that room. Have fun :).

I immediately get a crash when trying to click on a character or object.
It fails on line 67, 147, 270 & 632 of DragDropCommon.asc with "Error running function 'repeatedly_execute_always': Error: Null pointer refenced

I'm using the latest AGS, 3.5.0.24

I haven't tried anything else or look at the demo yet... but since you wrote that was all that was needed to try it...  (roll)
I'll check the demo now.
There are those who believe that life here began out there...

@Cassiebsg, looks like it works in "Ghost GUI" mode by default (don't know why :/), which requires you to set a GUI object to the module.

Change to another mode as
Code: Adventure Game Studio
  1. DragDropCommon.DragMove = eDDCmnMoveSelf;
  2.    OR
  3. DragDropCommon.DragMove = eDDCmnMoveGhostOverlay;
  4.  

I must update this module when I get spare time, with fixes and maybe also better tutorial.
« Last Edit: 20 Mar 2020, 14:16 by Crimson Wizard »

Cassiebsg

  • Cavefish
  • Fleeing the Cylon tyrrany...
    • Cassiebsg worked on one or more games that won an AGS Award!
    •  
    • Cassiebsg worked on one or more games that was nominated for an AGS Award!
Thanks, I'll give a try later on, but will add the lines already before the forum crashes again.  :)

Edit: Works now! :) So guess I can now play with programming the game.  :-D
« Last Edit: 20 Mar 2020, 17:09 by Cassiebsg »
There are those who believe that life here began out there...

Can u drop and drag inventory items with the module and let them interact with other inventory items, hotspots, objects and characters?

I tried but I couldn't get it. Codes or modules for drop and drag of inventory items in other threads would also help although I couldn't find any.
Truly, truly, i say to you, blessed are those who play adventure games, for theirs is the kingdom of heaven.

Can u drop and drag inventory items with the module and let them interact with other inventory items, hotspots, objects and characters?

I tried but I couldn't get it. Codes or modules for drop and drag of inventory items in other threads would also help although I couldn't find any.

Inventory items themselves cannot be dragged, because they are not real on-screen objects. You need something that would represent them in game.

DragDropCommon module implements this using either a GUI or Overlay, but for items only feasible solution is GUI. If I remember correctly, Overlays don't work well because they are always appear behind GUI, which means they will be behind InventoryWindow too. Which is ugly. So best use GUI mode.

You may check how this is done in the Demo game's room 4 script (download link in the first post).

PS. For a brief example, here's how you set a GUI for representing item drag:
Code: Adventure Game Studio
  1. DragDropCommon.DragMove = eDDCmnMoveGhostGUI;
  2. DragDropCommon.GhostGUI = MyGUI; // where MyGUI is the GUI you create yourself for this purpose
  3.  

That may be enough for starters.
« Last Edit: 01 Jul 2021, 18:38 by Crimson Wizard »

eri0o

 @Amir, are you trying to use this module on Android? It doesn't work with the allegro4 based engine with touchscreen devices.

Amir, are you trying to use this module on Android? It doesn't work with the allegro4 based engine.

What do you mean, why?

eri0o

There's no click and hold in allegro4 port - you can't check if a "mouse" button is down in the old allegro 4 Android port. This is the main thing I want to change with the new Android port (besides soon adding proper crossplatform multi-touch)

Edit: CW, I will not answer here to avoid complicating the topic, I just mentioned because Amir was asking about Android the other day. But in short we need proper way to support touch devices, including devices that have both, like laptop tablet hybrids. It's possible code wise with SDL, it's more about figuring the right design on how to handle this in AGS, I plan to open a ticket about this when I have at least a sketch of something.
« Last Edit: 01 Jul 2021, 18:47 by eri0o »

There's no click and hold in allegro4 port. This is the main thing I want to change with the new Android port (besides soon adding proper crossplatform multi-touch)

If it's about controls and default ones don't work, this module allows to create custom ones. For example, if you check the demo game, there's one room where you press a key to start drag, and then press it again to stop drag.

I'd imagine there might be a way to figure out a solution on touch devices as well.

EDIT: I mean, that won't be literal "drag" anymore :), but rather click/touch to move, click/touch to drop workaround, or something similar.
« Last Edit: 01 Jul 2021, 18:52 by Crimson Wizard »

@Crimson Wizard,  I checked room 4 script and created a gui like in ur module and I could drag the inventory items, but I couldn't let them interact with other inventory items, hotspots, objects and characters.

@eri0o  Oh, that's right. I'm trying to change a few things in my game so that it can be played on Android devices. All that remains is to drag the inventory items like other AGS games on Android, Whispers of a Machine, Blackwell series, etc.

if you are sure eri0o that this this module doesnt work on Android, is there some other code or method anywhere to do that?
Truly, truly, i say to you, blessed are those who play adventure games, for theirs is the kingdom of heaven.

eri0o

WoaM and Kathy Rain use a different code that works with the old android port - I actually have the script code because I asked by mail the dev, but I think you should just ask them yourself. If you want to use this module and use the same behavior for mouse and fingers, you need to use the Android SDL Port.

I have a little game that uses this module too here: https://github.com/ericoporto/dungeonhands

It has touch on the webport, but I don't know how well it runs on old devices. :/

@Crimson Wizard,  I checked room 4 script and created a gui like in ur module and I could drag the inventory items, but I couldn't let them interact with other inventory items, hotspots, objects and characters.

You need to handle the "DragDrop.EvtWantDrop" event. For example, if you look into the room 4 script, there will be this piece of the code:
Code: Adventure Game Studio
  1. function room_RepExec()
  2. {
  3.   <...>
  4.   else if (DragDrop.EvtWantDrop)
  5.   {
  6.     InvWindow* drop_to = GetInvWindowUnderObject(o_x, o_y, o_w, o_h);
  7.     if (drop_to != null && ItemOrigin != null && drop_to != ItemOrigin)
  8.     {
  9.       ItemOrigin.CharacterToUse.LoseInventory(DragDropCommon._InvItem);
  10.       drop_to.CharacterToUse.AddInventory(DragDropCommon._InvItem);
  11.     }
  12.   }
  13. }
  14.  

You write something similar in your "repeatedly_execute" function (e.g. in global script), and replace this with checking if there's a character, object, etc under the dragged item (or under the mouse x,y if you prefer), and if there's then, for example, call RunInteraction(eModeUseinv) for that object below.


if you are sure eri0o that this this module doesnt work on Android, is there some other code or method anywhere to do that?

This module is not strictly specific to desktop controls, it lets you customize itself to any control scheme you like. The problem is only in finding out what works with Android port, and applying here.

If the new Android port works better, 3.6.0 engine should be running games from previous versions well, you don't even have to recompile them in 3.6.0 (but you may).


I'd propose to separate this in two problems:
1. Making this interact with other objects after you drop the item;
2. Solving the Android controls.

Perhaps its best to test the first problem on desktop (like Windows) to make sure first part works.
« Last Edit: 01 Jul 2021, 19:33 by Crimson Wizard »

I might need to add another room to this demo showing how to script this kind interaction...

There's no click and hold in allegro4 port - you can't check if a "mouse" button is down in the old allegro 4 Android port.

What happens when you press the finger and hold on Android, what kind of events does it send to AGS, if any?
« Last Edit: 01 Jul 2021, 19:40 by Crimson Wizard »

Ahaaaa, I see.

I've tried something similar but not exactly as you described it. I will try it. Many Thanks.

Quote
I might need to add another room to this demo showing how to script this kind interaction

This is the best idea I ever heard  ;-D

Quote
I have a little game that uses this module too here: https://github.com/ericoporto/dungeonhands

I will check it out.

« Last Edit: 01 Jul 2021, 19:50 by Amir »
Truly, truly, i say to you, blessed are those who play adventure games, for theirs is the kingdom of heaven.

Quote
You write something similar in your "repeatedly_execute" function (e.g. in global script), and replace this with checking if there's a character, object, etc under the dragged item (or under the mouse x,y if you prefer), and if there's then, for example, call RunInteraction(eModeUseinv) for that object below.

Hi, I wrote something and I can now interact with hotspots,objects and characters but wrong interaction and inventory items don't interact with other inventory items. Do u know what's wrong?

Code: Adventure Game Studio
  1. function game_start()
  2. {
  3.  
  4.   DragDrop.Enabled = true;
  5.  
  6.   DragDropCommon.ModeEnabled[eDragDropInvItem] = true;
  7.   DragDropCommon.DragMove = eDDCmnMoveGhostGUI;
  8.   DragDropCommon.GhostGUI = gInvItemGhost;
  9.   DragDropCommon.GhostTransparency = 0;
  10.   DragDropCommon.GhostAlpha = false;
  11.   DragDrop.DefaultHookKey = 0;
  12.   DragDrop.DefaultHookMouseButton = eMouseLeft;
  13.   DragDrop.DragMinDistance = 0;
  14.   DragDrop.DragMinTime = 0;
  15.   DragDrop.AutoTrackHookKey = true;
  16.   DragDrop.DefaultUnhookAction = eDDUnhookRevert;
  17.   }
  18.  



Code: Adventure Game Studio
  1.  
  2. function repeatedly_execute()
  3. {
  4. Character *chara = Character.GetAtScreenXY(mouse.x, mouse.y);
  5. Object *obj = Object.GetAtScreenXY(mouse.x, mouse.y);
  6. Hotspot *hot = Hotspot.GetAtScreenXY(mouse.x, mouse.y);
  7. InventoryItem *inv = InventoryItem.GetAtScreenXY(mouse.x, mouse.y);
  8.  
  9. if (DragDrop.EvtWantDrop)
  10. {
  11.   if ((chara != null) || (obj != null) || (hot != null) || (inv !=null))
  12.   {
  13.    Room.ProcessClick(mouse.x, mouse.y, eModeUseinv);
  14.   }
  15. }
  16. }
  17.  


« Last Edit: 04 Jul 2021, 19:25 by Amir »
Truly, truly, i say to you, blessed are those who play adventure games, for theirs is the kingdom of heaven.

Hi, I wrote something and I can now interact with hotspots,objects and characters but wrong interaction and inventory items don't interact with other inventory items. Do u know what's wrong?

First of all, I imagine the code above is not your real code, because there are commands outside of a function?

Regarding the problem, Room.ProcessClick does not interact with the inventory items, because they are not inside the room. For them you got to do GUI.ProcessClick, or just call inv.RunInteraction(eModeUseinv);

I did not understand the part about "wrong interaction", could you explain more?
« Last Edit: 04 Jul 2021, 16:34 by Crimson Wizard »

Oh, sorry, I made a mistake when I was trying to design my post here. I edited it.

GUI.ProcessClick is new to me but it dosn't work, I tried inv.RunInteraction(eModeUseinv); before but I'm getting an error "Null pointer referenced"
I tried
Code: Adventure Game Studio
  1.   if ((chara != null) || (obj != null) || (hot != null) || (inv !=null))
  2.   {
  3.    //Room.ProcessClick(mouse.x, mouse.y, eModeUseinv);
  4.    //inv.RunInteraction(eModeUseinv);
  5.    //ProcessClick(mouse.x, mouse.y, eModeUseinv);
  6.    //cJesus.RunInteraction(eModeUseinv);
  7.    //GUI.ProcessClick(mouse.x, mouse.y, eModeUseinv);
  8.   }
  9.  

Room.ProcessClick, ProcessClick, cJesus.RunInteraction work but wrong interaction I mean, when I have if, else if and else, it ignores the commands in if and else if and prints the commands in else, I mean it only sees "els" and  inventory items still don't interact with other inventory items.  ???
Truly, truly, i say to you, blessed are those who play adventure games, for theirs is the kingdom of heaven.

GUI.ProcessClick is new to me but it dosn't work, I tried inv.RunInteraction(eModeUseinv); before but I'm getting an error "Null pointer referenced"

I think at this point it's more a general question of scripting, rather than the use of this module.

You cannot call inv.RunInteraction(eModeUseinv) always, but only if "inv" is valid (inv !=null). You likely will need more if/elseif blocks to handle everything.


Code: Adventure Game Studio
  1.   if ((chara != null) || (obj != null) || (hot != null))
  2.   {
  3.     Room.ProcessClick(mouse.x, mouse.y, eModeUseinv);
  4.   }
  5.   else if (inv !=null)
  6.   {
  7.     inv.RunInteraction(eModeUseinv);
  8.   }
  9.  

Room.ProcessClick, ProcessClick, cJesus.RunInteraction work but wrong interaction I mean, when I have if, else if and else, it ignores the commands in if and else if and prints the commands in else

Wrong interactions, as in wrong verb, or wrong inventory item?

If last, how do you normally check for the used item? For example, if you check "player.ActiveInventory", then you simply may set it before running process click to whatever item is being dropped.
Code: Adventure Game Studio
  1. player.ActiveInventory = DragDropCommon._InvItem;
  2.  
« Last Edit: 04 Jul 2021, 20:10 by Crimson Wizard »

Quote
Wrong interactions, as in wrong verb, or wrong inventory item?

Wrong verb.

But with player.ActiveInventory = DragDropCommon._InvItem; it works, cool  :)  inventory items still don't want to interact with other inventory items.

Code: Adventure Game Studio
  1. if (DragDrop.EvtWantDrop)
  2. {
  3.   cJesus.ActiveInventory = DragDropCommon._InvItem;
  4.  
  5.   if ((chara != null) || (obj != null) || (hot != null))
  6.   {
  7.    ProcessClick(mouse.x, mouse.y, eModeUseinv);
  8.   }
  9.  
  10.   else if (inv != null)
  11.   {
  12.     inv.RunInteraction(eModeUseinv);
  13.   }
  14. }
  15.  

I made a video of whats happening. I've tried a lot of things but it still doesn't work. I think something is still missing in the code.


« Last Edit: 05 Jul 2021, 10:52 by Amir »
Truly, truly, i say to you, blessed are those who play adventure games, for theirs is the kingdom of heaven.

  inventory items still don't want to interact with other inventory items.

More information is needed.
Does the code ever pass under "else if (inv != null)" ? You may test that either by placing a breakpoint there or "Display" command with some message.
You are running eModeUseinv interaction. Do you have event of that type ("use inventory item on") created for your items?
What is inside these event functions, are there more conditions? Can you post an example of your script?

Quote
Does the code ever pass under "else if (inv != null)" ? You may test that either by placing a breakpoint there or "Display" command with some message.

Good question. I tried Display command, nothing happened, the Display message didn't appear.

Quote
You are running eModeUseinv interaction. Do you have event of that type ("use inventory item on") created for your items?
What is inside these event functions, are there more conditions? Can you post an example of your script?

Yes, most of them have "use inventory item on" I tried many items with each other with an event and it happens the same as in the video. I'm not just trying money with carrot  ;-D
An example for useing an inventory item with another item: honey with bread.

Code: Adventure Game Studio
  1. function iBrot_UseInv()
  2. {
  3. if (cJesus.ActiveInventory == iHonig)
  4. {
  5.   aBrotmithonig.Play(eAudioPriorityNormal, eOnce);
  6.   Wait(80);
  7.   cJesus.LoseInventory(iBrot);
  8.   cJesus.LoseInventory(iHonig);
  9.   cJesus.AddInventory(iBrotmithonig);
  10.  
  11. }  
  12. else
  13. {
  14.      int i;
  15.     i = Random(3);
  16.     if (i == 0) cJesus.Say("Das ist eine bizarre, teuflische Idee.");
  17.     if (i == 1) cJesus.Say("Wahrlich, wahrlich, ich sage dir: Das geht nicht.");
  18.     if (i == 2) cJesus.Say("Versuche das nicht, sonst landest du in der Hölle.");
  19.     if (i == 3) cJesus.Say("Du sollst den Herrn, deinen Gott nicht versuchen. Das geht doch nicht.");  
  20. }  
  21. }
  22.  

I think it's up to the module. something is still missing something like player.ActiveInventory = DragDropCommon._InvItem; I read through ur module, tried to understand it, I got half of it but I couldn't find out why the inventory items don't interact with other inventory items.

Truly, truly, i say to you, blessed are those who play adventure games, for theirs is the kingdom of heaven.

Quote
Does the code ever pass under "else if (inv != null)" ? You may test that either by placing a breakpoint there or "Display" command with some message.

Good question. I tried Display command, nothing happened, the Display message didn't appear.

So, inv is always null, or condition does not work.
The question is why your script does not detect an inventory item at the place of the drop.
Maybe the detection is not correct. Or there's some extra code that prevents this to work.



I made a quick test with the existing Demo game, and added few lines in the 4th room script:
Code: Adventure Game Studio
  1.   else if (DragDrop.EvtWantDrop)
  2.   {
  3.     InventoryItem* item = InventoryItem.GetAtScreenXY(mouse.x, mouse.y); // <-------------
  4.     if (item != null) // <-----------------------------------------------------------------------------
  5.       Display("item under: %s",item.Name); // <-------------------------------------------------
  6.  
  7.     InvWindow* drop_to = GetInvWindowUnderObject(o_x, o_y, o_w, o_h);
  8.     if (drop_to != null && ItemOrigin != null && drop_to != ItemOrigin)
  9.     {
  10.       ItemOrigin.CharacterToUse.LoseInventory(DragDropCommon._InvItem);
  11.       drop_to.CharacterToUse.AddInventory(DragDropCommon._InvItem);
  12.     }
  13.   }
  14.  

This displays inventory item's name under the mouse cursor every time you drop something on it.
« Last Edit: 05 Jul 2021, 20:30 by Crimson Wizard »

Hmm, I have got one idea.

Try changing the order of tests. Test inventory item first, then everything else:

Code: Adventure Game Studio
  1.   if (inv != null)
  2.   {
  3.     inv.RunInteraction(eModeUseinv);
  4.   }
  5.   else if ((chara != null) || (obj != null) || (hot != null))
  6.   {
  7.    ProcessClick(mouse.x, mouse.y, eModeUseinv);
  8.   }
  9.  


EDIT Also I've just realized that the hotspot test is wrong. You should not compare hot with null, because Hotspot.GetAtScreenXY always returns something.
You got to compare it with hotspot[0], which is "no hotspot"/eraser:
Code: Adventure Game Studio
  1.   else if ((chara != null) || (obj != null) || (hot != hotspot[0]))
  2.  
« Last Edit: 05 Jul 2021, 20:37 by Crimson Wizard »

It's a good thing that I refreshed here and saw your edit. I almost wanted to try something complicated. Now it works  (laugh) ur right about hot != null, I have often read it here in the forum but forgot it. Such a little thing can cause disaster like a butterfly effect.

There are a few problems but it has nothing to do with the module. I think I can solve them on my own or I would create a new thread. the biggest problem would be the Android port but it doesn't matter if it doesn't work. Programming with AGS is fun.

Thank u so much for ur patience and help.
Truly, truly, i say to you, blessed are those who play adventure games, for theirs is the kingdom of heaven.

Sorry for bothering again. I'm trying something but it dosn't work. I want the selected inventory item to disappear after the interaction or dropping, both in the inventory with inventory items and outside with objects.

I used if (DragDrop.EvtDragStarted) player.ActiveInventory = null; so that it's not chosen twice like in the video. This works fine.

in repeatedly execute
Code: Adventure Game Studio
  1. if ((DragDrop.EvtDragStarted) || (DragDrop.EvtDropped))
  2.   {
  3.     player.ActiveInventory = null;
  4.   }
  5.  

or alone

Code: Adventure Game Studio
  1. if (DragDrop.EvtDropped)
  2.   {
  3.    player.ActiveInventory = null;  
  4.   }
  5.  

The inventory item doesn't go away.

Truly, truly, i say to you, blessed are those who play adventure games, for theirs is the kingdom of heaven.

I want the selected inventory item to disappear after the interaction or dropping, both in the inventory with inventory items and outside with objects

When you say "dissapear" do you mean dissapear from cursor, or dissapear from player's inventory?

I want the selected inventory item to disappear after the interaction or dropping, both in the inventory with inventory items and outside with objects

When you say "dissapear" do you mean dissapear from cursor, or dissapear from player's inventory?

From cursor  ;-D
Truly, truly, i say to you, blessed are those who play adventure games, for theirs is the kingdom of heaven.

I cannot tell without seeing full code of rep exec.

I cannot tell without seeing full code of rep exec.

Ok.

Code: Adventure Game Studio
  1.  
  2. Hotspot* prevH;
  3.  
  4. function repeatedly_execute()
  5. {  
  6.  
  7.  int x = mouse.x -280;
  8.  int y = mouse.y -115;
  9.   InventoryItem*ii = InventoryItem.GetAtScreenXY(mouse.x, mouse.y);
  10.   Label*lbl = gGui1.Controls[0].AsLabel;
  11.   String text;
  12.   if (ii) text = ii.Name;
  13.   else text = Game.GetLocationName(mouse.x, mouse.y);
  14.  
  15.  gGui1.SetPosition(x, y);  // name over verbcoins
  16.  
  17.  
  18.  
  19. Character *chara = Character.GetAtScreenXY(mouse.x, mouse.y);
  20. Object *obj = Object.GetAtScreenXY(mouse.x, mouse.y);
  21. Hotspot *hot = Hotspot.GetAtScreenXY(mouse.x, mouse.y);
  22. InventoryItem *inv = InventoryItem.GetAtScreenXY(mouse.x, mouse.y);
  23.  
  24. if (DragDrop.EvtWantDrop)
  25. {
  26.  
  27.   cJesus.ActiveInventory = DragDropCommon._InvItem;
  28.  
  29.   if ((chara != null) || (obj != null) || (hot != hotspot[0]))
  30.   {
  31.    ProcessClick(mouse.x, mouse.y, eModeUseinv);
  32.  
  33.   }
  34.  
  35.     else if (inv != null)
  36.   {
  37.    
  38.     inv.RunInteraction(eModeUseinv);
  39.    
  40.   }
  41. }
  42.  
  43.  
  44. else if (DragDrop.EvtDragStarted) // || (DragDrop.EvtDropped))
  45.   {
  46.     player.ActiveInventory = null;
  47.   }
  48.  
  49.  /*
  50. else
  51. {
  52. player.ActiveInventory = null;  // it works but not a good idea coz the name of objects over the verbcoins doesn't appear any more
  53. }
  54. */
  55.  
  56.  
  57.  
  58.  
  59.  
  60. /////////// Pfeile an Hotspots
  61.  
  62.  
  63. Hotspot* currentH = Hotspot.GetAtScreenXY(mouse.x, mouse.y);
  64. if (currentH != prevH) {
  65. int pfeil = currentH.GetProperty("Pfeil");
  66. if (pfeil == 1)
  67. {
  68. mouse.ChangeModeGraphic(eModeWalkto, 236);  
  69. mouse.ChangeModeView(eModeWalkto, 24);
  70. cJesus.Clickable = false;
  71. }  
  72. if (pfeil == 2)
  73. {
  74. mouse.ChangeModeGraphic(eModeWalkto, 232);  
  75. mouse.ChangeModeView(eModeWalkto, 23);  
  76. cJesus.Clickable = false;
  77. }  
  78. if (pfeil == 3)
  79. {
  80. mouse.ChangeModeGraphic(eModeWalkto, 240);  
  81. mouse.ChangeModeView(eModeWalkto, 25);
  82. cJesus.Clickable = false;
  83. }
  84. if (pfeil == 4)
  85. {
  86. mouse.ChangeModeGraphic(eModeWalkto, 228);  
  87. mouse.ChangeModeView(eModeWalkto, 22);
  88. cJesus.Clickable = false;
  89. }
  90.  
  91. if (pfeil == 0 || currentH.ID == 0)
  92. {
  93.  
  94. mouse.ChangeModeGraphic(eModeWalkto, 217);
  95. mouse.ChangeModeView(eModeWalkto, 21);
  96. cJesus.Clickable = true;
  97. }
  98. if ((gMainmenu2.Transparency == 0) && (pfeil == currentH.GetProperty("Pfeil")))
  99. {
  100. mouse.ChangeModeGraphic(eModeWalkto, 217);
  101. }  
  102.  
  103. }
  104. prevH = currentH;
  105.  
  106. }  
  107.  
  108.  
  109.  
Truly, truly, i say to you, blessed are those who play adventure games, for theirs is the kingdom of heaven.

It works there.

Code: Adventure Game Studio
  1. function repeatedly_execute_always()
  2. {  
  3. if (DragDrop.EvtDropped)
  4. {
  5.   player.ActiveInventory = null;
  6. }
  7.  
  8. }
  9.  

But I don't know if this is its right place.
Truly, truly, i say to you, blessed are those who play adventure games, for theirs is the kingdom of heaven.

Amir, sorry for not responding earlier.

I don't think the repeatedly_execute_always is a "wrong" place, with that it may work all the time regardless of other things you do in rep-exec.

Looking at the big repeatedly_execute() function, my first thought is that you could place it under the "if (DragDrop.EvtWantDrop)" section, after calling all the ProcessClick/RunInteraction:
Code: Adventure Game Studio
  1. if (DragDrop.EvtWantDrop)
  2. {
  3.   cJesus.ActiveInventory = DragDropCommon._InvItem;
  4.  
  5.   if ((chara != null) || (obj != null) || (hot != hotspot[0]))
  6.   {
  7.    ProcessClick(mouse.x, mouse.y, eModeUseinv);
  8.   }  
  9.   else if (inv != null)
  10.   {
  11.     inv.RunInteraction(eModeUseinv);
  12.   }
  13.  
  14.   cJesus.ActiveInventory = null; // <---------------------
  15. }
  16.  

But maybe you tried that already and it did not work?

Thanks for ur returning and answer. I thought you gave up  ;-D

I think I've tried this before because what's happening with this method has happened to me before, and what's happening is that it's wrong interaction again. It goes in the function directly to ELSE again and ignores IF and ELSE IF. Our example: Bread with honey, Jesus says: it doesn't work, instead of combining them together.

Quote
I don't think the repeatedly_execute_always is a "wrong" place, with that it may work all the time regardless of other things you do in rep-exec.

Okay. I will leave it there then. It doesn't cause any problems so far. I think that is the only solution. I don't know why but that is what it looks like.
Truly, truly, i say to you, blessed are those who play adventure games, for theirs is the kingdom of heaven.

There is also a problem that I didn't notice before. The inventory items interact with themselves (laugh) especially if you click on it once. I can't find where to check if an inventory item is on itself so that nothing happens.

I have this solution:

Code: Adventure Game Studio
  1. function ihoney_UseInv()
  2. {
  3. if (cJesus.ActiveInventory == ihoney)
  4. {
  5.  // do nothing  
  6. }
  7. }
  8.  

But I have 60 inventory items. Do you have a quicker solution?
« Last Edit: 11 Jul 2021, 17:10 by Amir »
Truly, truly, i say to you, blessed are those who play adventure games, for theirs is the kingdom of heaven.

There is also a problem that I didn't notice before. The inventory items interact with themselves (laugh) especially if you click on it once. I can't find where to check if an inventory item is on itself so that nothing happens.

Ah right, so, you have this code above, under condition "if (DragDrop.EvtWantDrop)":
Code: Adventure Game Studio
  1.   else if (inv != null)
  2.   {
  3.     inv.RunInteraction(eModeUseinv);
  4.   }
  5.  
so you could probably also test
Code: Adventure Game Studio
  1.   else if (inv != null && inv != cJesus.ActiveInventory)
  2.   {
  3.     inv.RunInteraction(eModeUseinv);
  4.   }
  5.  

Oh, I'm stupid. Thank u so much.
Truly, truly, i say to you, blessed are those who play adventure games, for theirs is the kingdom of heaven.

The module works as in the video with AGS engine Android port (the app). Not quite drag and drop ;-D  by pressing and holding an inventory item, but I like it that way. It's practical too. I made the mouse cursor transparent so that it looks like it does on smartphones or iPads.



WoaM and Kathy Rain use a different code that works with the old android port - I actually have the script code because I asked by mail the dev, but I think you should just ask them yourself. If you want to use this module and use the same behavior for mouse and fingers, you need to use the Android SDL Port.

I have a little game that uses this module too here: https://github.com/ericoporto/dungeonhands

It has touch on the webport, but I don't know how well it runs on old devices. :/

What do you mean exactly by Android SDL Port? Do you mean by creating an APK with monkeys plugin or your way with Android Studio? I wanted to try that anyway.
Truly, truly, i say to you, blessed are those who play adventure games, for theirs is the kingdom of heaven.

Updated DragDropCommon module to 1.0.1, fixing default settings, to avoid people stumbling into a missing GUI crash if they forgot to explicitly set a drag mode.

Updated DragDropCommon module to 1.0.1, fixing default settings, to avoid people stumbling into a missing GUI crash if they forgot to explicitly set a drag mode.

Thank u.
Truly, truly, i say to you, blessed are those who play adventure games, for theirs is the kingdom of heaven.