Unity3D仿写Button面板事件绑定功能

本文实例为大家分享了Unity3D仿写Button面板事件绑定功能的具体代码,供大家参考,具体内容如下

最近在做一个情节引导得项目。其中一个需求特点是:每一步都要显示类似的信息,不同的是,每一次要去引导玩家玩的东西不同。比如:第一步需要显示物体1,第二步需要显示物体2,区别就是在相同的脚本调用不同的函数。我们不可能为了每一次不同的设置写不同的脚本,如果一千多步,难道要写一千多个脚本?突然想要unity 的UGUI中button事件的绑定是一个好的解决方案。于是我上网搜索了button的源代码。如下:

using System;
using System.Collections;
using UnityEngine.Events;
using UnityEngine.EventSystems;
using UnityEngine.Serialization;

namespace UnityEngine.UI
{
 // Button that's meant to work with mouse or touch-based devices.
 [AddComponentMenu("UI/Button", 30)]
 public class Button : Selectable, IPointerClickHandler, ISubmitHandler
 {
  [Serializable]
  /// <summary>
  /// Function definition for a button click event.
  /// </summary>
  public class ButtonClickedEvent : UnityEvent {}

  // Event delegates triggered on click.
  [FormerlySerializedAs("onClick")]
  [SerializeField]
  private ButtonClickedEvent m_OnClick = new ButtonClickedEvent();

  protected Button()
  {}

  /// <summary>
  /// UnityEvent that is triggered when the button is pressed.
  /// Note: Triggered on MouseUp after MouseDown on the same object.
  /// </summary>
  ///<example>
  ///<code>
  /// using UnityEngine;
  /// using UnityEngine.UI;
  /// using System.Collections;
  ///
  /// public class ClickExample : MonoBehaviour
  /// {
  ///  public Button yourButton;
  ///
  ///  void Start()
  ///  {
  ///   Button btn = yourButton.GetComponent<Button>();
  ///   btn.onClick.AddListener(TaskOnClick);
  ///  }
  ///
  ///  void TaskOnClick()
  ///  {
  ///   Debug.Log("You have clicked the button!");
  ///  }
  /// }
  ///</code>
  ///</example>
  public ButtonClickedEvent onClick
  {
   get { return m_OnClick; }
   set { m_OnClick = value; }
  }

  private void Press()
  {
   if (!IsActive() || !IsInteractable())
    return;

   UISystemProfilerApi.AddMarker("Button.onClick", this);
   m_OnClick.Invoke();
  }

  /// <summary>
  /// Call all registered IPointerClickHandlers.
  /// Register button presses using the IPointerClickHandler. You can also use it to tell what type of click happened (left, right etc.).
  /// Make sure your Scene has an EventSystem.
  /// </summary>
  /// <param name="eventData">Pointer Data associated with the event. Typically by the event system.</param>
  /// <example>
  /// <code>
  /// //Attatch this script to a Button GameObject
  /// using UnityEngine;
  /// using UnityEngine.EventSystems;
  ///
  /// public class Example : MonoBehaviour, IPointerClickHandler
  /// {
  ///  //Detect if a click occurs
  ///  public void OnPointerClick(PointerEventData pointerEventData)
  ///  {
  ///    //Use this to tell when the user right-clicks on the Button
  ///   if (pointerEventData.button == PointerEventData.InputButton.Right)
  ///   {
  ///    //Output to console the clicked GameObject's name and the following message. You can replace this with your own actions for when clicking the GameObject.
  ///    Debug.Log(name + " Game Object Right Clicked!");
  ///   }
  ///
  ///   //Use this to tell when the user left-clicks on the Button
  ///   if (pointerEventData.button == PointerEventData.InputButton.Left)
  ///   {
  ///    Debug.Log(name + " Game Object Left Clicked!");
  ///   }
  ///  }
  /// }
  /// </code>
  /// </example>

  public virtual void OnPointerClick(PointerEventData eventData)
  {
   if (eventData.button != PointerEventData.InputButton.Left)
    return;

   Press();
  }

  /// <summary>
  /// Call all registered ISubmitHandler.
  /// </summary>
  /// <param name="eventData">Associated data with the event. Typically by the event system.</param>
  /// <remarks>
  /// This detects when a Button has been selected via a "submit" key you specify (default is the return key).
  ///
  /// To change the submit key, either:
  ///
  /// 1. Go to Edit->Project Settings->Input.
  ///
  /// 2. Next, expand the Axes section and go to the Submit section if it exists.
  ///
  /// 3. If Submit doesn't exist, add 1 number to the Size field. This creates a new section at the bottom. Expand the new section and change the Name field to “Submit”.
  ///
  /// 4. Change the Positive Button field to the key you want (e.g. space).
  ///
  ///
  /// Or:
  ///
  /// 1. Go to your EventSystem in your Project
  ///
  /// 2. Go to the Inspector window and change the Submit Button field to one of the sections in the Input Manager (e.g. "Submit"), or create your own by naming it what you like, then following the next few steps.
  ///
  /// 3. Go to Edit->Project Settings->Input to get to the Input Manager.
  ///
  /// 4. Expand the Axes section in the Inspector window. Add 1 to the number in the Size field. This creates a new section at the bottom.
  ///
  /// 5. Expand the new section and name it the same as the name you inserted in the Submit Button field in the EventSystem. Set the Positive Button field to the key you want (e.g. space)
  /// </remarks>

  public virtual void OnSubmit(BaseEventData eventData)
  {
   Press();

   // if we get set disabled during the press
   // don't run the coroutine.
   if (!IsActive() || !IsInteractable())
    return;

   DoStateTransition(SelectionState.Pressed, false);
   StartCoroutine(OnFinishSubmit());
  }

  private IEnumerator OnFinishSubmit()
  {
   var fadeTime = colors.fadeDuration;
   var elapsedTime = 0f;

   while (elapsedTime < fadeTime)
   {
    elapsedTime += Time.unscaledDeltaTime;
    yield return null;
   }

   DoStateTransition(currentSelectionState, false);
  }
 }
}

代码其实挺简单的,主要是自己new 一个新的unityEvent,然后我们在外界调用。这个UnityEvent通过序列化显示在面板上。我们可以通过两种方式绑定事件。第一种就是在面板绑定,第二种就是AddListener添加事件。于是我们可以照猫画虎择取我们自己需要的部份写我们自己需要的事件绑定。代码如下:

using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using UnityEngine.Events;
using UnityEngine.EventSystems;
using UnityEngine.Serialization;
using System;

namespace MyEvent
{
 public class MyCompotent : MonoBehaviour {

  [Serializable]
  public class MyCompontentEvent:UnityEvent{ }

  [FormerlySerializedAs("MyEvent")]
  [SerializeField]
  private MyCompontentEvent myEvent = new MyCompontentEvent();

  public MyCompontentEvent MyEvent { get { return myEvent; }set { myEvent = value; } }

  //执行绑定的事件
  public void ExcuteEvent()
  {
   MyEvent.Invoke();
  }
 }
}

我们将脚本挂到空物体上,效果如下:

使用方法如下例子:

我们自己写一个步骤设置器,代码如下:

namespace MyEvent
{
 public class StepControl : MyCompotent
 {
  public string Name;
  public int Index;

  private void Start()
  {
   //设置名字
   //设置Index
   //去做每一步应该设置得事情
   ExcuteEvent();
  }
 }
}

我们在StepControl里设置相同的操作。不同的操作通过面板绑定让ExcuteEvent()去执行。使用unity自带的消息事件会让我们开发轻松很多。如果不使用UnityEvent,我们也可以在StepControl声明一个我们自己的委托,但是去调用小的操作的时候会需要多写一点代码。比如 我们想让某个物体隐藏,需要单独写一个脚本设置物体隐藏并且将函数绑定到此StepControl的委托上。而在UnityEvent里可以直接通过面板操作实现。

以上为我的博客内容。有错误欢迎指点!

今年一定要学会代码重新建模+shader效果的初级编写。

以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持我们。

(0)

相关推荐

  • 在Unity中捕捉Android的常用按钮返回事件

    在Unity开发中捕捉Android的常用事件其实很简单 Input.GetKey(KeyCode.Escape) Input.GetKeyDown(KeyCode.Home) // 返回键 if ( Application.platform == RuntimePlatform.Android &&(Input.GetKeyDown(KeyCode.Escape))) { //.... } // Home键 if ( Application.platform == RuntimePlat

  • Unity实现轮盘方式的按钮滚动效果

    近期在项目中,策划给出了一个需求就是,让按钮按照一个轮盘的轨迹进行滑动的效果,经过一番测试,实现了初步的效果. 我这里区分了横向滑动和纵向滑动,这里以纵向滑动为例子进行示范,实现按钮的滑动效果. 首先就是先进行位置初始化: /// <summary> ///从大到小排序,Y轴 /// </summary> private Comparison<CircleScrollRectItemBase> ComparisionY = delegate (CircleScrollR

  • Unity3D仿写Button面板事件绑定功能

    本文实例为大家分享了Unity3D仿写Button面板事件绑定功能的具体代码,供大家参考,具体内容如下 最近在做一个情节引导得项目.其中一个需求特点是:每一步都要显示类似的信息,不同的是,每一次要去引导玩家玩的东西不同.比如:第一步需要显示物体1,第二步需要显示物体2,区别就是在相同的脚本调用不同的函数.我们不可能为了每一次不同的设置写不同的脚本,如果一千多步,难道要写一千多个脚本?突然想要unity 的UGUI中button事件的绑定是一个好的解决方案.于是我上网搜索了button的源代码.如

  • jQuery实现的事件绑定功能基本示例

    本文实例讲述了jQuery实现的事件绑定功能.分享给大家供大家参考,具体如下: HTML正文: 用户名:<input type="text" value="邮箱/用户名/手机号" id="login"/><br> 密 码:<input type="password" id="passwd"><br> <input type="button&qu

  • ES6中javascript实现函数绑定及类的事件绑定功能详解

    本文实例讲述了ES6中javascript实现函数绑定及类的事件绑定功能的方法.分享给大家供大家参考,具体如下: 函数绑定 箭头函数可以绑定this对象,大大减少了显式绑定this对象的写法(call.apply.bind).但是,箭头函数并不适用于所有场合,所以 ES7 提出了 " 函数绑定 " ( function bind )运算符,用来取代call.apply.bind调用.虽然该语法还是 ES7 的一个提案,但是 Babel 转码器已经支持. 函数绑定运算符是并排的两个双冒号

  • vue 使用饿了么UI仿写teambition的筛选功能

    问题描述 teambition软件是企业办公协同软件,相信部分朋友的公司应该用过这款软件.里面的筛选功能挺有意思,本篇文章,就是仿写其功能.我们先看一下最终做出来的效果图 大致的功能效果有如下 需求一:常用筛选条件放在上面直接看到,不常用筛选条件放在添加筛选条件里面 需求二:筛选的方式有输入框筛选.下拉框筛选.时间选择器筛选等 需求三:如果觉得常用筛选条件比较多的话,可以鼠标移入点击删除,使之进入不常用的筛选条件里 需求四:也可以从不常用的筛选条件里面点击对应筛选条件使之"蹦到"常用筛

  • iOS bounds学习笔记以及仿写UIScrollView部分功能详解

    经常看到这种说法,frame是基于父控件的,bounds是基于自身坐标的.然而,这个自身坐标是什么?bounds这个属性存在的意义是什么呢?bounds的x和y值真的永远是0吗? 经过查阅资料,我看到这样一种说法:一个控件,拥有其展示部分和内容部分.其展示部分是有限大的,固定坐标固定大小,而其内容部分是无限大的.就像一个电视机以及其播放的电影(这个比喻不太恰当,是我强行比喻的),电视机用于放映电影的屏幕(控件的展示部分)是固定位置固定大小的,然而电影的世界(控件的内容部分)是无限大的,我们只能展

  • jQuery事件绑定on()、bind()与delegate() 方法详解

    啃了一段日子的js相关了,学的过程中发现在jQuery中绑定事件时,有人用bind(),有人用on(),有人用delegate(),还有人用live(),看代码的时候觉得都实现功能了也就掀过去了,只是一直没完全弄懂之间的区别,于是今天查了下资料,自己做个总结. 之所以有这么多类型的绑定方法,是因为jQuery的版本更新的原因,如on()方法就是1.7以后出现的. jQuery的事件绑定api页面上,提到live()方法已经过时,不建议使用.所以这里我们主要就看下以下三个方法:bind().del

  • Android开发实现仿京东商品搜索选项卡弹窗功能

    本文实例讲述了Android开发实现仿京东商品搜索选项卡弹窗功能.分享给大家供大家参考,具体如下: 一.效果图: 二.思路: (1)首先顶部布局由通过LinearLayout水平按比重平均分配各个item宽度. (2)每个item设置两种状态,点击状态与未点击状态 (3)弹窗由PopupWindow实现 三.布局 (1)item布局 <!-- 优先筛选条件布局 --> <RelativeLayout android:id="@+id/rl_priority_filter&quo

  • 简单仿写Android控件SlidingMenu的实例代码

    SlidingMenu (侧滑菜单形式)在android开发过程中,经常用到,这次我们通过一个简单案例来仿写SlidingMenu 的大体功能,下面 是主要实现的代码: java代码:(重写onTouchEvent方法 处理侧滑菜单处的事件分发机制) public class SlidingMenu extends ViewGroup implements OnClickListener { private View menu; private View main; private int me

  • C#仿QQ实现简单的截图功能

    目录 实现功能 开发环境 实现代码 实现效果 接上一篇写的截取电脑屏幕,我们在原来的基础上加一个选择区域的功能,实现自定义选择截图. 个人比较懒,上一篇的代码就不重新设计了,就简单改一下呈现方式. 不得不吐槽一下,在windows10系统上设置了放大比例的话,用这种方式来实现截图功能的话需要去计算比例.后面有机会的话,用第三方DLL再实现一次. 实现功能 屏幕选择区域截图 开发环境 开发工具:Visual Studio 2013 .NET Framework版本:4.5 实现代码 //将上一篇的

  • elementui源码学习仿写el-link示例详解

    目录 正文 组件思考 组件的需求 组件的效果图 组件实现分析 给link组件加上链接样式 给link组件加上鼠标悬浮时下划线 通过传参控制是否加上下划线(即:是否加上这个下划线类名) 使用v-bind="$attrs"兜底a标签的其他的未在props中声明的参数 代码 使用代码 封装组件代码 正文 本篇文章记录仿写一个el-link组件细节,从而有助于大家更好理解饿了么ui对应组件具体工作细节.本文是elementui源码学习仿写系列的又一篇文章,后续空闲了会不断更新并仿写其他组件.源

随机推荐