调用方法并将数据从视图控制器B传递到Xamarin.iOS中的控制器A.

时间:2014-09-04 09:01:45

标签: c# ios xamarin.ios xamarin

我有一个视图控制器A,我在其中检索一些值。在某些情况下,如果有多个值,用户必须选择一个值。所以我提出另一个视图控制器B(UITableView),我让用户选择条目。当我目前在B上时,如何从A调用方法? (避免重复代码)我怎样才能在该方法中传递一些参数?

我了解了delegates/protocolsevents (.NET style)和通知中心。传递字符串并从A调用方法的最佳方法是什么?你能提供一个例子吗?在Xamarin的示例中,没有关于如何定义自定义协议的示例。

或者我应该从公众中创建一个字段并传递此字段以查看我处理数据的控制器B?

1 个答案:

答案 0 :(得分:2)

活动

我设法让活动approch正常工作。我的信息基于以下链接:

在我的UITableViewController(查看控制器B)中,我添加了以下内容:

// class variable  
public event EventHandler<BLevelSelectedEventArgs> BLevelSelected;

// event handler
public class BLevelSelectedEventArgs : EventArgs
{
    public BLevelItem bLevel { get; set; }

    public BLevelSelectedEventArgs(BLevelItem bLevel) : base()
    { 
        this.bLevel = bLevel;
    }
}

此处定义了事件以及自定义事件处理程序。您可以使用事件定义要传输数据的属性,例如串。这里使用了自定义BLevelItem。应为您的应用程序更改事件处理程序的名称和事件的名称。在此UITableViewController课程中,我还定义了UITableViewSource

public override void RowSelected (UITableView tableView, NSIndexPath indexPath)
{
    tableView.DeselectRow (indexPath, true); // iOS convention is to remove the highlight

    if (this.controller.BLevelSelected != null) {
        this.controller.BLevelSelected (this, new BLevelSelectedEventArgs (controller.bLevelList[indexPath.Row]));
    }

}

此处引发事件并且参数随事件一起传递。现在只有一个侦听器丢失,它会对事件做出反应。这在视图控制器A上进行:

bLevelController.BLevelSelected += (object sender, BLevelController.BLevelSelectedEventArgs e) => {
    System.Diagnostics.Debug.WriteLine(e.bLevel.bLevelName);
};

bLevelController是我的视图控制器B的一个实例。您可以访问定义的事件,如上所示,但您必须知道您使用类名(BLevelController)来访问{{ 1}}。

如果您还可以添加其他可能性来在视图控制器之间传递数据(通知中心,协议/代理,...),那将是很好的。


代表

使用了一种委托方法Part 5 - Working with Tables in the iOS Designer。您可以在BLevelSelectedEventArgs

中定义代理
UITableViewController

MasterViewController 中实例化 DetailViewController 时,设置 Delegate 属性。例如:

public MasterViewController Delegate {get;set;} // will be used to Save, Delete later

DetailViewController 中,您可以从 MasterViewController 中调用任何方法:

public override void PrepareForSegue (UIStoryboardSegue segue, NSObject sender)
{
    base.PrepareForSegue (segue, sender);

    var detailViewController = segue.DestinationViewController as DetailViewController;

    if (detailViewController != null) {
        detailViewController.Delegate = this;
    }
}

这是有效的,因为我将 DetailViewController 传递给 DetailViewSource

public override void RowSelected (UITableView tableView, NSIndexPath indexPath)
    {
    tableView.DeselectRow (indexPath, true); // iOS convention is to remove the highlight
    if (this.controller.Delegate != null) {
        this.controller.Delegate.SetItems (this.controller.items[indexPath.Row]);
    }
}

// a method in MasterViewController
public void SetItems(string items){
    this.items = items;
    this.NavigationController.PopViewControllerAnimated (true);
    // do something here
}

NSNotificationCenter

我的信息基于xamarin/monotouch-samplesXamarin NSNotificatioCenter: How can I get the NSObject being passed?

没有数据传输的简单示例:

// in ViewDidLoad of DetailViewController
this.TableView.Source = new DetailViewSource (this);

// in the constructor of DetailViewSource
private CostCentreController controller;

public CostCentreListSource (CostCentreController controller)
{
    this.controller = controller;
}