Unity3D学习资源:委托和lambda表达式二

本文通过Unity游戏开发实例,详细介绍了委托的概念及其在处理碰撞事件和方法调用方面的应用,包括如何将方法作为参数传递,以及委托绑定多个方法在设计模式中的使用。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

 

四.把一个方法赋值给一个委托变量的这种机制,可以实现把方法当做参数进行传递,如果一个方法,其参数是一个委托,则调用该方法时,就可以把与该委托格式一样的方法传给形参.下面的代码以List集合类型里面的RemoveAll方法为例:

[C] 纯文本查看 复制代码

List<int> list = new List<int>();
                        list.Add(123);
                        list.Add(123);
                        list.Add(234);
                        list.Add(123);
                        list.RemoveAll((int a) =>
                                {
                                        if (a == 123)
                                        {
                                                return true;
                                        }
                                        return false;
                                });
                        foreach (int s in list)
                        {
                                Console.WriteLine(s);
                        }

先看一下RemoveAll方法的原型,public int RemoveAll(Predicate<T> match);进入到API里面,看到其形参是一个委托类型,原型为:public delegate bool Predicate<in T>(T obj);T为泛型类型占位符,上面的代码中list中用的是int类型,故此委托里面的T也为int,委托的原型为返回值为bool类型,参数为int类型,在调用方法时,用的是lambda表达式,参数是int类型的a,方法体里面的返回值类型为bool类型,a会遍历集合里面的所有元素,只要等于123,返回为true,就会把123从集合里面删除掉,遍历完一遍后,把集合里面的123全部删除了,输出的结果只有234了.




五.委托可以绑定多个方法这种特性,可以用在设计模式上面,下面有个Unity的一个Demo,先看一下截图:

屏幕快照 2015-09-15 下午10.13.47.png (100.63 KB, 下载次数: 0)

下载附件

前天 22:45 上传


工程运行前,场景中有四个带颜色的物体,中间是一个小球,然后移动小球,与四个物体中的任何一个碰撞后,再按下空格键,则把碰撞过的物体颜色改为蓝色.效果图如下:

屏幕快照 2015-09-15 下午10.14.11.png (19.95 KB, 下载次数: 0)

下载附件

前天 22:45 上传


其主要的思想就是:在移动的小球的脚本里面,定义了一个接口类型的变量,在其它四个物体的脚本都继承接口,接口类里面有一个委托属性,只有get方法,然后四个物体的脚本都继承该接口,实现接口里面的属性,委托属性的返回值是其脚本里面的方法,其格式和定义的委托格式一样,当移动的小球与四个物体碰撞后,就把所碰撞物体脚本组件赋值给移动小球脚本组件里面的接口变量,然后再调用相对应的委托变量所返回的方法,把相对应的物体的颜色改变即可.下面是代码:
脚本一是绑定在四个带有颜色物体上的脚本组件

[C] 纯文本查看 复制代码

using UnityEngine;
using System.Collections;

public class EnemyHurt : MonoBehaviour,IEventInterface
{

                public HurtDelegate hurtdelegate { 
                                get {
                                                return Hurt; 
                                } 
                }

                public void Hurt ()
                {
                                //把物体材质的颜色变成黑色,代表已死亡
                                transform.renderer.material.color = Color.blue;
                }
}
下面两个脚本是加到移动小球上面的:
脚本二.

[C] 纯文本查看 复制代码

using UnityEngine;
using System.Collections;

//此脚本是用来控制小球移动的
public class Move : MonoBehaviour
{
                //小球移动的速度
                public float speed = 3.0f;

                void Update ()
                {
                                //得到横竖虚拟轴的值
                                float hor = Input.GetAxis ("Horizontal");
                                float vec = Input.GetAxis ("Vertical");
                                //小球的移动
                                transform.position += new Vector3 (hor, 0, vec) * Time.deltaTime * speed;
                }
}
脚本三:

[C] 纯文本查看 复制代码

using UnityEngine;
using System.Collections;

public class Boom : MonoBehaviour
{
                //定义一个接口的属性,由于敌人继承了该接口,只需要把子类的对象赋值给该接口变量即可执行子类里面的方法
                public IEventInterface eventInterface{ get; set; }
                //碰撞检测,当小球与四个物体发生碰撞时,
                void OnCollisionEnter (Collision other)
                {
                                //如果碰撞物体的父物体不为空并且父物体的名字是Enemies时
                                if (other.transform.parent != null && other.transform.parent.name == "Enemies") {
                                //接口变量指向子类的对象,就会调用所指向的子类里面的委托.
                                                this.eventInterface = other.transform.GetComponent<EnemyHurt> ();
                                }
                }
                // Update is called once per frame
                void Update ()
                {
                                //当按下空格键时,调用委托,实际上调用的就是接口变量所指向的子类里面的委托,而
                                //其委托又返回的是子类里面的方法
                                if (Input.GetKeyDown (KeyCode.Space)) {
                                                this.eventInterface.hurtdelegate ();
                                }
                }
}

脚本四:是一个公有的文件其它脚本组件可以引用该文件里面的接口

[C] 纯文本查看 复制代码

using UnityEngine;
using System.Collections;

//声明一个委托
public delegate void HurtDelegate ();
//创建一个接口
public interface IEventInterface
{
                //声明一个委托属性
                HurtDelegate hurtdelegate{ get; }
}

以下是Unity场景里面的各物体之间的父子关系图:

屏幕快照 2015-09-15 下午10.27.44.png (12.33 KB, 下载次数: 0)

下载附件

前天 22:45 上传


以上就是关于委托的应用,由于书写时间仓促,有什么问题还请各位大神多多指教.



转载于:https://my.oschina.net/u/2438875/blog/507539

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值