The Xamarin Developer Center has a lot of great content to help developers build apps using Xamarin iOS/Droid using many of the components users expect in modern mobile apps. One very common component is a Table View. In this article I am going to show how to extend the UITableViewSource from the BasicTable sample (update: This is Part0 in the GitHub project I’ve created) to be generic and a bit more flexible. Doing so allows the developer to focus on expanding application functionality and not dealing with boilerplate code over and over. The first step is to make the TableSource class generic, change the internal data structure from a string[] to a List and update the class constructors. Here is what the code looks like after this change:

“`csharp
public class TableSource<T> : UITableViewSource {
public List<T> Data { get; set; }
protected string cellIdentifier = "TableCell";

public TableSource ()
{
Data = new List<T> ();
}

public TableSource(List<T> data)
{
Data = data;
}

/// <summary>
/// Called by the TableView to determine how many cells to create for that particular section.
/// </summary>
public override int RowsInSection (UITableView tableview, int section)
{
return Data.Count;
}
“`

We also need to adjust how the GetCell method populates the cell’s title. This is done by changing this the line that sets the cell title from cell.TextLabel.Text = tableItems[indexPath.Row]; to cell.TextLabel.Text = Data[indexPath.Row].ToString();. This convention allows you to easily change what displays in the cell title by overriding the model object’s ToString method.

Now we need to fix the ViewDidLoad method in the HomeScreen class to accommodate these update, which now looks like:

  public override void ViewDidLoad ()
  {
    base.ViewDidLoad ();
    table = new UITableView(View.Bounds); // defaults to Plain style
    table.AutoresizingMask = UIViewAutoresizing.All;
    var tableSource = new TableSource&lt;string&gt;(new List&lt;string&gt;
                                                  {&quot;Vegetables&quot;,&quot;Fruits&quot;,&quot;Flower Buds&quot;,&quot;Legumes&quot;,&quot;Bulbs&quot;,&quot;Tubers&quot;});
    table.Source = tableSource;
    Add (table);
  }

Finally, I changed the overridden RowSelected method to use an event. This allows for the customization of row clicks without modifying our base class. For our example app this required two changes. The first to the TableSource class where I replaced the existing RowSelected method:

“`csharp
/// <summary>
/// Called when a row is touched
/// </summary>
public override void RowSelected (UITableView tableView, NSIndexPath indexPath)
{
if (OnRowSelected != null) {
OnRowSelected (this, new RowSelectedEventArgs (tableView, indexPath));
}
}

public class RowSelectedEventArgs : EventArgs
{
public UITableView tableView { get; set; }
public NSIndexPath indexPath { get; set; }

<pre><code>public RowSelectedEventArgs(UITableView tableView, NSIndexPath indexPath) : base()
{
this.tableView = tableView;
this.indexPath = indexPath;
}
</code></pre>

}

public event EventHandler<RowSelectedEventArgs> OnRowSelected;
“`

And second where I updated the ViewDidLoad method in the HomeScreen class to handle the row click.

csharp
public override void ViewDidLoad ()
{
base.ViewDidLoad ();
table = new UITableView(View.Bounds); // defaults to Plain style
table.AutoresizingMask = UIViewAutoresizing.All;
var tableSource = new TableSource<string>(new List<string>{"Vegetables","Fruits","Flower Buds","Legumes","Bulbs","Tubers"});
tableSource.OnRowSelected += (object sender, TableSource<string>.RowSelectedEventArgs e) => {
new UIAlertView("Row Selected",
tableSource.Data[e.indexPath.Row].ToString(), null, "OK", null).Show();
e.tableView.DeselectRow (e.indexPath, true);
};
table.Source = tableSource;
Add (table);
}

This should give you a good starting point to use UITableView’s in you Xamarin iOS app without having to worry about repeating the UITableViewSource code again and again. The final source is Part1 in my TableDemo GitHub Project.

Leave a Reply

I’m Peter

I’ve spent my career building software and leading engineering teams. I started as a developer and architect, grew into engineering leadership, and today I serve as a Chief Technology Officer.

Here, I share practical insights on technology, leadership, and building high-performing teams.

Connect with me on LinkedIn.

Discover more from Peter Mourfield

Subscribe now to keep reading and get access to the full archive.

Continue reading