我的例子是动态添加“按钮”,并给“按钮”添加监听——难点出在了,用代码给按钮添加监听上——如果用Lambda表达式,作为监听方法【图1】,它不允许有参数(比如“gameObject.GetComponent < Button > ().onClick.AddListener()”中的AddListener(),官方规定,它括号内,得是个无参委托)【通过F12追溯按钮点击事件的AddListener()方法和此方法中的UnityAction类可得知】
using UnityEngine;
using UnityEngine.UI;
public class TestUGUIbtnAddListener : MonoBehaviour
{
public Button myBtn;
void Start()
{
myBtn.onClick.AddListener(
()=>
{
Debug.Log("我是要求空参的,UnityAction委托");
}
);
}
}
具体例子:准备一个按钮prefab
,叫“item-musicScrollView”,在滑动视图中,生成6个按钮prefab
的实例,并给这六个按钮添加监听
点击第一个按钮,调用PlaySelect(0)
点击第二个按钮,调用PlaySelect(1)
点击第三个按钮,调用PlaySelect(2)
点击第四个按钮,调用PlaySelect(3)
点击第五个按钮,调用PlaySelect(4)
点击第六个按钮,调用PlaySelect(5)
原先代码及更正后的代码,如下
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using UnityEngine.UI;
public class TestBtnItemAddListener : MonoBehaviour
{
private Transform content;
public GameObject item_musicScrollView;
void Start()
{
content = transform.Find("/Canvas/Scroll View/Viewport/Content");
for (int i = 0; i < 6; i++)
{
GameObject musicItem = Instantiate(item_musicScrollView);
musicItem.transform.SetParent(content);
musicItem.GetComponent<Button>().onClick.AddListener(
() => {
PlaySelect(i);
});
}
}
public void PlaySelect(int x)
{
Debug.Log("监听方法" + x);
}
}
结果是:点击每一个按钮,都输出“监听方法6”
改进:在预设体实例的名字上,动手脚,让名字和所调用方法的参数对应起来(至于为什么这样做管用,自己暂时也没搞清楚,听同事说是“栈”和“堆”的问题)
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using UnityEngine.UI;
public class TestBtnItemAddListener : MonoBehaviour
{
private Transform content;
public GameObject item_musicScrollView;
void Start()
{
content = transform.Find("/Canvas/Scroll View/Viewport/Content");
for (int i = 0; i < 6; i++)
{
GameObject musicItem = Instantiate(item_musicScrollView);
//重点语句
musicItem.name=i.ToString();
musicItem.transform.SetParent(content);
musicItem.GetComponent<Button>().onClick.AddListener(
() => {
//重点语句
PlaySelect(System.Int32.Parse(musicItem.name));
});
}
}
public void PlaySelect(int x)
{
Debug.Log("监听方法" + x);
}
}