Monotouch.Dialog StyledStringElement委托总是为最后添加的元素触发

时间:2012-10-29 22:37:27

标签: xamarin.ios dialogviewcontroller

给出以下代码,单击每个元素时遇到问题。如果我们假设我有5个练习,因此在foreach()循环中创建了5个元素,当表格被渲染并且我点击任何元素时,委托总是得到第5个(最后一个)元素的练习。

正确显示元素,每个元素都显示相关练习的名称。只是代表没有按预期工作。

如果我不使用foreach循环并对每个元素进行硬编码,则它会按预期工作。但是如果我不能动态填充dialogViewController并为每个使用元素tapped事件,那就不好了。

private void CreateExerciseTable()
{
Section section = new Section();

foreach (var exercise in exercises)
{
    var element = new StyledStringElement(exercise.ExerciseName, 
        delegate { AddExercise(exercise); }) 
        {
            Font = Fonts.H3,
            TextColor = UIColor.White,
            BackgroundColor = RGBColors.LightBlue,
            Accessory = UITableViewCellAccessory.DisclosureIndicator
        };

    section.Elements.Add(element);
}

var root = new RootElement("Selection") {
    section
};

 var dv = new DialogViewController(root, true);
dv.Style = UITableViewStyle.Plain;

//Remove the extra blank table lines from the bottom of the table.
UIView footer = new UIView(new System.Drawing.RectangleF(0,0,0,0));
dv.TableView.TableFooterView = footer;

dv.TableView.SeparatorColor = UIColor.White;
dv.TableView.BackgroundColor = UIColor.White;
tableFitnessExercises.AddSubview(dv.View);      
}

private void AddExercise(FitnessExercise exercise)
{
NavigationManager.FitnessRoutine.Add(exercise);
PerformSegue(UIIdentifierConstants.SegAddExerciseToFitnessRoutine, this);
}

1 个答案:

答案 0 :(得分:8)

这是一个经典的关闭错误!

问题是您正在访问循环引用。

尝试:

foreach (var exercise in exercises)
{
    var localRef = exercise;
    var element = new StyledStringElement(exercise.ExerciseName, 
        delegate { AddExercise(localRef); }) 
        {
            Font = Fonts.H3,
            TextColor = UIColor.White,
            BackgroundColor = RGBColors.LightBlue,
            Accessory = UITableViewCellAccessory.DisclosureIndicator
        };

    section.Elements.Add(element);
}

有关详情,请参阅http://blogs.msdn.com/b/ericlippert/archive/2009/11/12/closing-over-the-loop-variable-considered-harmful.aspx