Forum rules - please read before posting.

Enable interaction menus by holding down mouse button

Hi Chris,
I am trying to change the way in which the interaction menu is activated. I want it to activate it by holding down mouse button for one second, just like someone asked in this post:
https://adventurecreator.org/forum/discussion/6388/beginner-question-how-to-modify-the-mouse-controls
I know I have to change the 'see interactions' setting to 'via script only', but after that I don't know what to do exactly. After writting my piece of code, where should I attach it? And what should I write exactly?
I am sorry for the beginner question, I know it is explained on the manual but I still can't figure it out on my own. Some indications would be really appreciated.
Thanks!

Comments

  • A message box should appear underneath the See Interactions with field once is set to Script Only, explaining that Interaction menus can be opened through script with the EnableInteractionMenus function.

    As I said in the linked thread, this function has two parameter variants, allowing you to open it for both Hotspots and inventory items:

    AC.KickStarter.playerMenus.EnableInteractionMenus (myHotspot);
    AC.KickStarter.playerMenus.EnableInteractionMenus (myInventoryItem);


    Working with just Hotspots for the moment, the top line of code would be called after checking that the mouse has been held down for a second, e.g.:

    void Update ()
    {
      bool heldForOneSecond = IsHeldForOneSecond (); // Example function that does the checking
      if (heldForOneSecond)
      {
        AC.KickStarter.playerMenus.EnableInteractionMenus (myHotspot);
      }
    }


    Such code could all live in a single C# script that's placed on an empty GameObject in the scene.  The actual code to determine if the mouse has been held (IsHeldForOneSecond in the above example) is not AC related but standard Unity code.  You should be able to find something on the Unity forums if you need help with that.

    In terms of what the "myHotspot" Hotspot variable is, you should start out by testing a pre-defined Hotspot in your script, e.g.:

    public Hotspot myHotspot;
    // void Update () etc

    That will then expose the "My Hotspot" field in the Inspector which you can then test with.  It'll open the menu for the same Hotspot each time, but I'd recommend getting to that point first.

    You'd presumable then want the myHotspot variable to be set to whatever the mouse pointer is currently (or just was) over.  This can be read with:

    myHotspot = AC.KickStarter.playerInteraction.GetLastOrActiveHotspot ();

    Therefore, provided your IsHeldForOneSecond () function also exists, your code would look something like (inside the "public class" brackets):

    public Hotspot myHotspot;

    void Update ()
    {
      bool heldForOneSecond = IsHeldForOneSecond (); // Example function that does the checking
      if (heldForOneSecond)
      {
        myHotspot = AC.KickStarter.playerInteraction.GetLastOrActiveHotspot ();
        if (myHotspot)
        {
          AC.KickStarter.playerMenus.EnableInteractionMenus (myHotspot);
        }
      }
    }
  • edited October 2017
    Hello Chris! Thanks for the answer. After lots of research and help from a friend I managed to do it. Let me show the code:

    using System.Collections;
    using System.Collections.Generic;
    using UnityEngine;

    namespace AC
    {
        public class MouseHold : MonoBehaviour {
           
            //FIELDS
            public double chopTime = 0.0;    
            public Hotspot myHotspot;

            // Use this for initialization
            void Start () {
                Debug.Log("Hello start MOUSEHOLD");
            }
           
            bool IsHeldForOneSecond ()
             {
                 if (Input.GetMouseButton(0))
                 {
                     chopTime += Time.deltaTime;
                 }
                 else{
                     chopTime = 0;
                     isMenuOpen = false;
                 }
                 Debug.Log(chopTime.ToString("R"));
                 if(chopTime > 0.5){
                     chopTime = 0;
                     return true;
                 }
                 else{
                     return false;
                 }
             }
           
            // Update is called once per frame
            void Update () {
                   
                bool heldForOneSecond = IsHeldForOneSecond (); // Example function that does the checking
                if (heldForOneSecond)
                {
                    myHotspot = AC.KickStarter.playerInteraction.GetLastOrActiveHotspot ();
                    if (myHotspot)
                    {
                      AC.KickStarter.playerMenus.EnableInteractionMenus (myHotspot);
                    }
               }
            }
        }
    }




    The script works perfectly, the interaction menu opens after holding the mouse for 0.5 seconds, great. The problem I found now is that the player won't walk towards the hotspots when clicking on it. I guess that has something to do with my currently interaction method (choose hotspot then interaction). Any idea on how to solve this?
  • What do you mean - that Interactions trigger but the player doesn't move, or that Interactions don't trigger at all?

    Other than the "isMenuOpen" bool needing to be declared, the script works fine for me when used in the 2D Demo (after changing the See Interactions with field to Via Script Only) - Hotspots included.

    Try it in the 2D Demo as well (with the 2D Demo Managers loaded) to see if the same occurs for you.  If so, it could be some other setting you've set - in which case compare them with the 2D Demo's to see which one is causing the difference.  You can post screens of your Settings Manager's Interaction settings here if you'd like me to look as well.
  • The interactions work just fine. What I would like to do now is be able to left-click once (not holding mouse button) on top of a hotspot and have the character walk to that specific point, just as if I was clicking straight onto the navmesh walkable area.

    https://ibb.co/dpOOMR

    As you can see in the picture, I've got hotspots that mark the exits of the scene. I also have triggers in the same place that activate when the player walks over them, making the player move to a marker out of the camera view and switching scenes. That is because I want the player to be able to notice the scene different exits by hovering the mouse over those hotspots, but I also would like the player to be able to click once on the hotspot and have the character move there.
    That is why I wanted the interaction menu to activate after holding the mouse for half a second, because I thought that single clicking on a hotspot would make the player walk to that position and totally ignore the hotspot.

    Thanks again Chris!

  • Be aware that Hotspots also have a "Single-use interaction" checkbox that overrides their behaviour to single-click (no Interaction menus).  The 2D Demo uses these for its own scene exits as well.

    But to make the player walk somewhere at the same time as the interaction menu opens, use the following code:

    Vector2 mousePosition = KickStarter.playerInput.GetMousePosition ();
    Vector3 worldMousePosition = Camera.main.ScreenToWorldPoint (mousePosition);
    KickStarter.player.MoveToPoint (mousePosition, false, true);

Sign In or Register to comment.

Howdy, Stranger!

It looks like you're new here. If you want to get involved, click one of these buttons!

Welcome to the official forum for Adventure Creator.