Unity中button事件监听的四种方式

本文介绍Unity中UGUI按钮的多种事件绑定方法,包括可视化创建、脚本绑定、EventTrigger和事件类接口实现等,帮助开发者高效处理用户交互。
ACE-Step

ACE-Step

音乐合成
ACE-Step

ACE-Step是由中国团队阶跃星辰(StepFun)与ACE Studio联手打造的开源音乐生成模型。 它拥有3.5B参数量,支持快速高质量生成、强可控性和易于拓展的特点。 最厉害的是,它可以生成多种语言的歌曲,包括但不限于中文、英文、日文等19种语言

UGUI 可视化创建以及关联事件很方便, 动态创建可以利用创建好的 Prefab 进行实例化, 只是在关联事件上有些复杂, 本文总结了几种给按钮绑定事件的关联方式.

1. 可视化创建及事件绑定 #
Step 1 : 通过 Hierarchy 面板创建 UI > Button.

这里写图片描述

Step 2 : 创建一个脚本 TestClick.cs, 定义了一个 Click 的 public 方法.

Step 3 : 选中 Hierarchy 中的 Button, Add Component 脚本 TestClick.cs

Step 4 : 在 Button(Script) 关联 TestClick 脚本里的 Click 方法.

这里写图片描述

Step 5 : Done.

TestClick.cs

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

public class TestClick : MonoBehaviour {

public void Click(){
    Debug.Log ("Button Clicked. TestClick.");
}

}
2. 通过直接绑定脚本来绑定事件 #
Step 1 : 通过 Hierarchy 面板创建 UI > Button.

Step 2 : 创建一个 ClickHandler.cs 脚本, 定义了一个私有方法 OnClick(), 并在 Start() 方法里为 Button 添加点击事件的监听,作为参数传入 OnClick 方法.
这里写图片描述
Step 3 : 将 ClickHandler 绑定在 Button 对象上.

Step 4 : Done.

ClickHandler.cs

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

public class ClickHandler : MonoBehaviour {

void Start () {
    Button btn = this.GetComponent<Button> ();
    btn.onClick.AddListener (OnClick);
}

private void OnClick(){
    Debug.Log ("Button Clicked. ClickHandler.");
}

}
3. 通过 EventTrigger 实现按钮点击事件 #
UGUI 系统中 Button 默认只提供了 OnClick 的调用方法, 有时候我们还需要监听鼠标进入事件 (MouseIn) 和鼠标滑出事件 (MouseOut). 就需要借助 UI 系统中的 EventTrigger 脚本来实现.

Step 1 : 通过 Hierarchy 面板创建 UI > Button.

Step 2 : 创建一个 EventTriggerHandler.cs 脚本, 利用 UnityEngine.EventSystems.EventTrigger 添加监听事件.
这里写图片描述
Step 3 : 绑定 EventTriggerHandler.cs 脚本到 Button 上.

Step 4 : Done.

EventTriggerHandler.cs

using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using UnityEngine.UI;
using UnityEngine.EventSystems;

// 需要 EventTrigger 脚本的支援
[RequireComponent(typeof(UnityEngine.EventSystems.EventTrigger))]
public class EventTriggerHandler : MonoBehaviour {

// Use this for initialization
void Start () {
    Button btn = this.GetComponent<Button> ();
    EventTrigger trigger = btn.gameObject.GetComponent<EventTrigger> ();
    EventTrigger.Entry entry = new EventTrigger.Entry ();
    // 鼠标点击事件
    entry.eventID = EventTriggerType.PointerClick;
    // 鼠标进入事件 entry.eventID = EventTriggerType.PointerEnter;
    // 鼠标滑出事件 entry.eventID = EventTriggerType.PointerExit;
    entry.callback = new EventTrigger.TriggerEvent ();
    entry.callback.AddListener (OnClick);
    // entry.callback.AddListener (OnMouseEnter);
    trigger.triggers.Add (entry);
}

private void OnClick(BaseEventData pointData){
    Debug.Log ("Button Clicked. EventTrigger..");
}

private void OnMouseEnter(BaseEventData pointData){
    Debug.Log ("Button Enter. EventTrigger..");
}

}
4. 通过 MonoBehaviour 实现事件类接口来实现事件的监听 #
Step 1 : 通过 Hierarchy 面板创建 UI > Button.

Step 2 : 创建一个 EventHandler.cs 脚本.

Step 3 : 将脚本绑定在 Button 对象上.
这里写图片描述

Step 4 : Done.

EventHandler.cs

using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using UnityEngine.UI;
using UnityEngine.EventSystems;

public class EventHandler : MonoBehaviour, IPointerClickHandler, IPointerEnterHandler, IPointerExitHandler, IPointerDownHandler, IDragHandler {

public void OnPointerClick(PointerEventData eventData){
    if(eventData.pointerId == -1){
        Debug.Log ("Left Mouse Clicked.");
    } else if(eventData.pointerId == -2){
        Debug.Log ("Right Mouse Clicked.");
    }
}

public void OnPointerEnter(PointerEventData eventData){
    Debug.Log ("Pointer Enter..");
}

public void OnPointerExit(PointerEventData eventData){
    Debug.Log ("Pointer Exit..");
}

public void OnPointerDown(PointerEventData eventData){
    Debug.Log ("Pointer Down..");
}

public void OnDrag(PointerEventData eventData){
    Debug.Log ("Dragged..");
}

}
UGUI 如何判断 UI 元素被点击时是鼠标的哪个按键, 上面的代码中我们可以根据 eventData.pointerId 来监听是鼠标左键还是右键. 但是每个 UI 元素都创建一个 MonoBehaviour 来监听各个事件显然不好, 下面是通过利用 Delegate 和 Event 来做一个通用类 UIEventListener 来处理事件 (观察者模式).

UIEventListener.cs

using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using UnityEngine.UI;
using UnityEngine.EventSystems;

public class UIEventListener : MonoBehaviour, IPointerClickHandler, IPointerEnterHandler, IPointerExitHandler {

// 定义事件代理
public delegate void UIEventProxy(GameObject gb);

// 鼠标点击事件
public event UIEventProxy OnClick;

// 鼠标进入事件
public event UIEventProxy OnMouseEnter;

// 鼠标滑出事件
public event UIEventProxy OnMouseExit;

public void OnPointerClick(PointerEventData eventData){
    if (OnClick != null)
        OnClick (this.gameObject);
}

public void OnPointerEnter(PointerEventData eventData){
    if (OnMouseEnter != null)
        OnMouseEnter (this.gameObject);
}

public void OnPointerExit(PointerEventData eventData){
    if (OnMouseExit != null)
        OnMouseExit (this.gameObject);
}

}
TestEvent.cs

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

public class TestEvent : MonoBehaviour {

void Start () {
    Button btn = this.GetComponent<Button> ();
    UIEventListener btnListener = btn.gameObject.AddComponent<UIEventListener> ();

    btnListener.OnClick += delegate(GameObject gb) {
        Debug.Log(gb.name + " OnClick");
    };

    btnListener.OnMouseEnter += delegate(GameObject gb) {
        Debug.Log(gb.name + " OnMouseEnter");
    };

    btnListener.OnMouseExit += delegate(GameObject gb) {
        Debug.Log(gb.name + " OnMOuseExit");
    };
}

}
TestEvent 脚本绑定在 Button 上即可.

您可能感兴趣的与本文相关的镜像

ACE-Step

ACE-Step

音乐合成
ACE-Step

ACE-Step是由中国团队阶跃星辰(StepFun)与ACE Studio联手打造的开源音乐生成模型。 它拥有3.5B参数量,支持快速高质量生成、强可控性和易于拓展的特点。 最厉害的是,它可以生成多种语言的歌曲,包括但不限于中文、英文、日文等19种语言

### Unity Button 添加事件监听教程 在 Unity 中,为 Button 添加事件监听有多种方式。以下是几种常见的方法及其详细说明: #### 方法一:通过 `onClick.AddListener` 添加监听器 这是最常见的方式之一,直接使用 Button 的 `onClick` 属性来添加监听函数[^1]。例如,创建一个脚本并将其附加到包含 Button 的游戏对象上: ```csharp using UnityEngine; using UnityEngine.UI; public class ClickExample : MonoBehaviour { public Button start; void Start() { Button btn = start.GetComponent<Button>(); btn.onClick.AddListener(TaskOnClick); } void TaskOnClick() { Debug.Log("You have clicked the button!"); } } ``` 此代码会在点击按钮时输出日志信息。 --- #### 方法二:动态添加持久化监听器 如果需要动态地向 Button 添加持久化监听器(即即使场景重新加载,监听器仍然有效),可以使用 `UnityEventTools` 和 `UnityAction`[^2]。以下是一个示例: ```csharp using UnityEngine; using UnityEngine.Events; using UnityEditor; public class PersistentListenerExample : MonoBehaviour { void AddPersistentListener(GameObject selectObj, GameObject anchorController) { SpeechInputHandler speechInput = selectObj.AddComponent<SpeechInputHandler>(); speechInput.IsFocusRequired = false; UnityEvent editEvent = new UnityEvent(); UnityEvent cancleEditEvent = new UnityEvent(); speechInput.Keywords = new KeywordAndResponse[] { new KeywordAndResponse("编辑", editEvent), new KeywordAndResponse("取消编辑", cancleEditEvent), }; UnityAction<bool> editDelegate = System.Delegate.CreateDelegate(typeof(UnityAction<bool>), anchorController.gameObject, "SetActive") as UnityAction<bool>; UnityEventTools.AddBoolPersistentListener(editEvent, editDelegate, true); UnityAction<bool> cancleDelegate = System.Delegate.CreateDelegate(typeof(UnityAction<bool>), anchorController.gameObject, "SetActive") as UnityAction<bool>; UnityEventTools.AddBoolPersistentListener(cancleEditEvent, cancleDelegate, false); } } ``` 此代码展示了如何通过关键字触发不同的事件,并将这些事件绑定到特定的回调函数上。 --- #### 方法三:使用 `UIEventListener` 组件 对于更复杂的交互需求,可以使用自定义的 `UIEventListener` 类来处理多个事件(如鼠标进入、离开等)[^3]。以下是一个示例: ```csharp using UnityEngine; using UnityEngine.UI; public class TestEvent : MonoBehaviour { void Start() { Button btn = this.GetComponent<Button>(); UIEventListener btnListener = btn.gameObject.AddComponent<UIEventListener>(); btnListener.OnClick += delegate(GameObject gb) { Debug.Log(gb.name + " OnClick"); }; btnListener.OnMouseEnter += delegate(GameObject gb) { Debug.Log(gb.name + " OnMouseEnter"); }; btnListener.OnMouseExit += delegate(GameObject gb) { Debug.Log(gb.name + " OnMouseExit"); }; } } ``` 此代码允许同时监听按钮的点击、鼠标进入和离开事件。 --- #### 方法四:利用观察者模式实现通用事件监听 为了减少重复代码,可以通过观察者模式实现一个通用的事件监听类[^4]。以下是一个简单的实现: ```csharp using UnityEngine; using UnityEngine.UI; public class EventObserver : MonoBehaviour { public void RegisterButton(Button button, System.Action callback) { button.onClick.AddListener(() => callback?.Invoke()); } public void UnregisterButton(Button button, System.Action callback) { button.onClick.RemoveListener(() => callback?.Invoke()); } } ``` 使用时,只需调用 `RegisterButton` 方法即可为指定按钮注册监听器。 --- #### 注意事项 - 如果同一个按钮被多次注册相同的监听器,可能会导致事件重复执行。因此,在注销监听器时,应确保调用 `RemoveListener` 方法[^5]。 - 在某些情况下,可能需要根据鼠标按键类型(如左键或右键)进行区分。可以通过 `eventData.pointerId` 来判断具体是哪个按键触发了事件。 --- ### 示例总结 上述四种方法分别适用于不同的场景: 1. **`onClick.AddListener`**:适合简单且常用的按钮点击事件。 2. **动态持久化监听器**:适合需要保存状态的复杂场景。 3. **`UIEventListener`**:适合需要监听多种交互事件的情况。 4. **观察者模式**:适合减少代码冗余,实现更灵活的事件管理。 ---
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值