使用EventSystem进行按键事件 [英] Use EventSystem for key-pressing events

查看:283
本文介绍了使用EventSystem进行按键事件的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

上下文:说您正在检查是否在键盘上按下了"W",最常见的检查方法是通过以下代码:

Context: say you're checking whether "W" is pressed on the keyboard, the most common way to check this is through the following code:

void Update(){
    if (Input.GetKeyDown("W"))
        DoSomething();
}

是否可以使用Unity的EventSystem执行以下操作?换句话说,是否存在例如 IPointerClickHandler 之类的接口的实现,以检查是否按下了按钮,而没有在 Update()函数中这样做?/p>

Is there a way to do the following, using Unity's EventSystem? In other words, is there an implementation of an interface like IPointerClickHandler, for example, to check whether a button is pressed, without doing so in an Update() function?

推荐答案

是否可以使用Unity的EventSystem执行以下操作?换句话说,是否有IPointerClickHandler之类的接口的实现,

Is there a way to do the following, using Unity's EventSystem? In other words, is there an implementation of an interface like IPointerClickHandler,

不. EventSystem主要用于光线广播和调度事件.这不用于检测键盘事件. EventSystem中唯一可以检测键盘事件的组件是InputField组件.就是这样,它不能用于其他任何用途.

No. The EventSystem is mostly used for raycasting and dispatching events. This is not used to detect keyboard events. The only component from the EventSystem that can detect keyboard events is the InputField component. That's it and it can't be used for anything else.

检查是否按下了按钮,而没有在Update()中这样做 功能?

Check whether a button is pressed, without doing so in an Update() function?

是的,有一种使用Event.KeyboardEvent的方法,这需要 OnGUI 函数.

Yes, there is a way with Event.KeyboardEvent and this requires the OnGUI function.

void OnGUI()
{
    if (Event.current.Equals(Event.KeyboardEvent("W")))
    {
        print("W pressed!");
    }
}

这比将Input.GetKeyDown功能与Update功能一起使用要差.我鼓励您坚持使用Input.GetKeyDown.没问题.

This is worse than using the Input.GetKeyDown function with the Update function. I encourage you to stick with Input.GetKeyDown. There is nothing wrong with it.

如果您要查找没有Input.GetKeyDown的事件类型 InputSystem ,请使用Unity的新Input API并订阅InputSystem.onEvent事件.

If you are looking for event type InputSystem without Input.GetKeyDown then use Unity's new Input API and subscribe to the InputSystem.onEvent event.

如果您正在寻找类似于IPointerClickHandler界面的功能,则可以在Input.GetKeyDown之上实现它.

If you are looking for feature similar to the IPointerClickHandler interface you can implement it on top of Input.GetKeyDown.

1 .首先,用System.Enum.GetValues(typeof(KeyCode));获取所有KeyCode枚举并将其存储在数组中.

1.First, get all the KeyCode enum with System.Enum.GetValues(typeof(KeyCode)); and store it in an array.

2 .创建一个接口"IKeyboardEvent"并添加OnKeyDown之类的功能,就像在IPointerClickHandler界面中的OnPointerClick一样.

2.Create an interface "IKeyboardEvent" and add functions such as OnKeyDown just like OnPointerClick in the IPointerClickHandler interface.

3 .从#1 中遍历KeyCode,并检查是否按下,释放或按住了阵列中的每个键.

3.Loop through the KeyCode from #1 and check if each key in the array is pressed, released or held down.

4 .获取场景中的所有组件,并检查它们是否实现了IKeyboardEvent界面.如果是这样,则根据#3 的键状态在界面中调用适当的功能.

4.Get all the components in the scene and check if they implemented the IKeyboardEvent interface. If they do, invoke the proper function in the interface based on the key status from #3.

这是一个仍可以扩展或改进的功能示例:

Here is a functional example that can still be extended or improved:

附加到一个空的GameObject.

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

public class KeyboardEventSystem : MonoBehaviour
{
    Array allKeyCodes;

    private static List<Transform> allTransforms = new List<Transform>();
    private static List<GameObject> rootGameObjects = new List<GameObject>();

    void Awake()
    {
        allKeyCodes = System.Enum.GetValues(typeof(KeyCode));
    }

    void Update()
    {
        //Loop over all the keycodes
        foreach (KeyCode tempKey in allKeyCodes)
        {
            //Send event to key down
            if (Input.GetKeyDown(tempKey))
                senEvent(tempKey, KeybrdEventType.keyDown);

            //Send event to key up
            if (Input.GetKeyUp(tempKey))
                senEvent(tempKey, KeybrdEventType.KeyUp);

            //Send event to while key is held down
            if (Input.GetKey(tempKey))
                senEvent(tempKey, KeybrdEventType.down);

        }
    }


    void senEvent(KeyCode keycode, KeybrdEventType evType)
    {
        GetAllRootObject();
        GetAllComponents();

        //Loop over all the interfaces and callthe appropriate function
        for (int i = 0; i < allTransforms.Count; i++)
        {
            GameObject obj = allTransforms[i].gameObject;

            //Invoke the appropriate interface function if not null
            IKeyboardEvent itfc = obj.GetComponent<IKeyboardEvent>();
            if (itfc != null)
            {
                if (evType == KeybrdEventType.keyDown)
                    itfc.OnKeyDown(keycode);
                if (evType == KeybrdEventType.KeyUp)
                    itfc.OnKeyUP(keycode);
                if (evType == KeybrdEventType.down)
                    itfc.OnKey(keycode);
            }
        }
    }

    private static void GetAllRootObject()
    {
        rootGameObjects.Clear();

        Scene activeScene = SceneManager.GetActiveScene();
        activeScene.GetRootGameObjects(rootGameObjects);
    }


    private static void GetAllComponents()
    {
        allTransforms.Clear();

        for (int i = 0; i < rootGameObjects.Count; ++i)
        {
            GameObject obj = rootGameObjects[i];

            //Get all child Transforms attached to this GameObject
            obj.GetComponentsInChildren<Transform>(true, allTransforms);
        }
    }

}

public enum KeybrdEventType
{
    keyDown,
    KeyUp,
    down
}

public interface IKeyboardEvent
{
    void OnKeyDown(KeyCode keycode);
    void OnKeyUP(KeyCode keycode);
    void OnKey(KeyCode keycode);
}

用法:

在脚本中实现IKeyboardEvent接口及其功能,就像使用IPointerClickHandler一样.

Implement the IKeyboardEvent interface and the functions from it in your script just like you would with IPointerClickHandler.

public class test : MonoBehaviour, IKeyboardEvent
{
    public void OnKey(KeyCode keycode)
    {
        Debug.Log("Key held down: " + keycode);
    }

    public void OnKeyDown(KeyCode keycode)
    {
        Debug.Log("Key pressed: " + keycode);
    }

    public void OnKeyUP(KeyCode keycode)
    {
        Debug.Log("Key released: " + keycode);
    }
}

这篇关于使用EventSystem进行按键事件的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆