Search Unity

  1. Welcome to the Unity Forums! Please take the time to read our Code of Conduct to familiarize yourself with the forum rules and how to post constructively.
  2. Dismiss Notice

Drag and drop UnityEngine.Object references

Discussion in 'Editor & General Support' started by abegue, Nov 29, 2021.

  1. abegue

    abegue

    Joined:
    Jan 28, 2019
    Posts:
    24
    Hi,

    I've got an issue with custom drag and drop UnityEngine.Object references from one component to another.
    I am actually creating a kind of behaviors holder (like Cinemachine with its modules) and I have the need to drag and drop these behaviors (inheriting from ScriptableObject) to other object fields (so a UI.Button, for example, can have an event with the behavior as a target to call a function).

    The drag and drop works correctly while it occurs in the same component but not when the target field is in another component.

    Capture.JPG

    *The header is a box that can be dragged with a custom script.*

    Here is my drag and drop code:
    Code (CSharp):
    1. switch (evt.type)
    2. {
    3.     case EventType.MouseDrag:
    4.         {
    5.             DragAndDrop.PrepareStartDrag();
    6.            // Bind my custom behavior, that is a specialized ScriptableObject, created with
    7.            // CreateInstance and no HideFlag is set.
    8.             DragAndDrop.objectReferences = new UnityEngine.Object[] { behaviorSP.objectReferenceValue };
    9.             evt.Use();
    10.         }
    11.         break;
    12. }
    Note that I also tried to do
    Selection.activeObject = behaviorSP.objectReferenceValue;
    during the drag operation. The focus is now set on my behavior object when starting to drag, however, if I lock the Inspector, then the drag and drop works correctly! So, I think Selection.activeObject probably triggers something internally (that I should set) that make the drag and drop working, and I may succeed to make my system works by doing the same thing.
    For now, the system is not really reliable since the user have to lock the Inspector to make it work...

    Update 1:
    After trying to reproduce code from the ObjectField's dropping system (based on Unity C# sources), I could notice that the drop logic is not called at all. I think it may occurs because the Inspector/property drawer is not recalled and the opportunity to manage the drop is not called at all. I will continue to investigate this way.

    Update 2:
    I can confirm that event are not called anymore during dropping on another component. I made the drop zone (the blue/red one) switch color each time there is a repaint. We can see that the area drop blinks correctly as I drag my object in the same component, but when I go for another component, the logic is not called anymore, so the code to receive the drop logic is not called at all.
    Temp.gif

    Any help will be appreciated!
     
    Last edited: Nov 29, 2021
  2. abegue

    abegue

    Joined:
    Jan 28, 2019
    Posts:
    24
    Okay, issue fixed.

    Seems that my example code was wrong and the correct event type for my drag initialization was
    case EventType.MouseDown
    . Thus, it works with this:
    Code (CSharp):
    1. switch (evt.type)
    2. {
    3.     case EventType.MouseUp:
    4.     case EventType.DragExited:
    5.         DragAndDrop.PrepareStartDrag();
    6.         break;
    7.     case EventType.MouseDown:
    8.         {
    9.             DragAndDrop.PrepareStartDrag();
    10.             DragAndDrop.objectReferences = new UnityEngine.Object[] { behaviorSP.objectReferenceValue };
    11.             DragAndDrop.StartDrag($"Drag {behaviorSP.objectReferenceValue.name}");
    12.             evt.Use();
    13.         }
    14.         break;
    15. }