2014-09-13 59 views
0

在Unity 4.6中尝试新的uGUI,编写按钮脚本...遍历一个目录并为每个文件创建一个按钮... AddListener位中f.Name的值应该为每个按钮独立设置。相反,每个按钮都具有要处理的最后一个f.Name的值(目录中按字母顺序排列的最后一个文件)。有任何想法吗?Unity 4.6,如何阻止共享侦听器的克隆?

foreach (FileInfo f in fileInfo) { 
    Button btnCurrLvl = (Button) Instantiate(btnLvl); 

    btnCurrLvl.GetComponentInChildren<Text>().text = f.Name.Remove(f.Name.Length-5); 

    Debug.Log(f.Name); // f.Name is different every time 
    btnCurrLvl.name = f.Name; // renaming the btns works 
    btnCurrLvl.GetComponent<Button>().onClick.AddListener(() => LoadLocalLvl(f.Name)); // all the listeners on all created buttons are set to the last value of f.Name!? 
} 
+0

普莱斯使用unity3d这样的问题。 – 2014-09-13 03:21:14

回答

1

在foreach循环中使用lambda表达式时要小心。以下代码:

var someList = new List<int> {1, 2, 3, 4}; 
var listOfClosures = new List<Func<int>>(); 
foreach (int v in someList) 
{ 
    listOfClosures.Add(() => v); 
} 

是(或多或少)等效于:该v声明出for循环的范围,然后仅重新分配在每个通

var someList = new List<int> {1, 2, 3, 4}; 
var listOfClosures = new List<Func<int>>(); 
int v; 
for (int i = 0; i < someList.Count; i++) 
{ 
    v = someList[i]; 
    listOfClosures.Add(() => v); 
} 

的通知。另请注意,闭包只保留对变量v的引用。因此,listOfClosures中的每个闭包在被调用时将返回4(最后一个赋值v被赋值)。

同样的情况,你的情况:

foreach (FileInfo f in fileInfo) { 
    btnCurrLvl.GetComponent<Button>().onClick.AddListener(() => LoadLocalLvl(f.Name)); 
} 

全部关闭将举行参照同F。 尝试在每个回路通创造新的变量,而不是:

foreach (FileInfo f in fileInfo) { 
    var name = f.Name; 
    btnCurrLvl.GetComponent<Button>().onClick.AddListener(() => LoadLocalLvl(name)); 
} 
0
string captured; 
foreach (FileInfo f in fileInfo) { 
    Button btnCurrLvl = (Button) Instantiate(btnLvl); 
    btnCurrLvl.GetComponentInChildren<Text>().text = f.Name.Remove(f.Name.Length-5); 
    btnCurrLvl.name = f.Name; 
    captured = f.Name; 
    btnCurrLvl.GetComponent<Button>().onClick.AddListener(() => LoadLocalLvl(captured)); 
} 

:)

相关问题