Learning Xamarin–Taking the plunge

By October 4, 2013Xamarin
[Please see the Table of Contents for this series.]

RadioButtonsFor the past number of weeks, I’ve slowly been learning Xamarin for Android, as documented in this series.  I’ve been putting in about half a day a week, taking my time, not letting the anxiety of learning this seemingly complex topic overwhelm me.  Until now, I’ve been following along with other people’s exercises, or adapting exercises I found into new material. 

Today, I decided to see what would happen if I set out to write a simple program based on my knowledge of C#/.NET and the little I’ve learned so far about Xamarin and Android.  The results were, if modest, very satisfying.

I set out to create a simple single page application that would gather a bit of data from the user with RadioButtons and CheckBoxes and then display that gathered information.  See the figure to the left for both the design and the result.

My constraint was that I wasn’t going to look at a finished example or read any articles on how to do it; I was going to rely on what “made sense” given what I know of both C# and of Xamarin/Android so far.

The first thing I did was to create a new Android application in Visual Studio.  I added a TextView to the top of Main.axml by going into Design view and dragging a TextView from the toolbox onto the design surface.  I then changed the text in the properties window to “What type of phone are you using?”  Being an incrementalist, I then ran the program!

I was happy to see my prompt, but the banner across the top of the “phone” said “RadioButtons” – the name of my project. I did a “search in files” and found that it was set in the attribute at the top of Activity1.cs, and so I changed it to “Xamarin Developer”,

namespace RadioButtons
{
[Activity(Label = "Xamarin Developer",
MainLauncher = true, Icon = "@drawable/icon")]

Radio Buttons & Check Boxes

I assumed that RadioButtons must be in some sort of group and so searched for RadioButtons in the toolbar. Sure enough, up came RadioButton and RadioButtonGroup.  I dragged the group onto the design surface and was pleasantly surprised to find that it included three sample buttons.  It was a simple matter to go into the property window and name the group and each of the buttons, and to set the text for each of the buttons.  As I expected based on my .Net experience, the group existed to make the buttons mutually exclusive.  Further, the property for whether a button was selected was, as I intuited, “checked.”  Here, as elsewhere, the transition from .NET to Xamarin/Android was very natural.

I next searched for and added three CheckBoxes, updating each in the properties window as well.  The property names were consistent with the RadioButtons, so no problem there.

Add a couple TextViews for headers and one to display the results and a Button to submit the user’s choices, and voilà! instant page.  Here’s the .axml page:

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:orientation="vertical"
android:layout_width="fill_parent"
android:layout_height="fill_parent"
android:minWidth="25px"
android:minHeight="25px">
<RadioGroup
android:minWidth="25px"
android:minHeight="25px"
android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:id="@+id/Favorite">
<TextView
android:text="What type of phone are you using?"
android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:id="@+id/textView2" />
<RadioButton
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:checked="true"
android:text="Android"
android:id="@+id/android" />
<RadioButton
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="iOS"
android:id="@+id/ios" />
<RadioButton
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="Windows Phone"
android:id="@+id/windows" />
</RadioGroup>
<TextView
android:text="Which languages are you comfortable with?"
android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:id="@+id/textView1" />
<CheckBox
android:text="C#"
android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:id="@+id/csharp" />
<CheckBox
android:text="Objective C"
android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:id="@+id/objective" />
<CheckBox
android:text="Java"
android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:id="@+id/java" />
<Button
android:text="Submit Answers"
android:layout_width="185.3dp"
android:layout_height="38.0dp"
android:id="@+id/submit"
android:clickable="true" />
<TextView
android:text="Ready…"
android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:id="@+id/message" />
</LinearLayout>

With that in place, it was time to turn to the logic, in Activity1.cs.

The Code

I took out the counter and much of the logic that was placed in the file by Visual Studio, but the key lines that set the ContentView and found the Button were a good clue as to how to proceed.  One annoyance (I’ve been spoiled by .NET) is that declaring a control in the .axml does not make the control visible in the .cs file.  Thus, you have to go through the ritual of declaring the control as a private member variable,

private Button button;
private TextView message;
private CheckBox csharp;
private CheckBox objectivec;
private CheckBox java;
private RadioButton android;
private RadioButton ios;
private RadioButton windows;

and then initializing the field by calling FindViewByID, passing in the Resource ID you used in the markup,

button = FindViewById<Button>(Resource.Id.submit);
message = FindViewById<TextView>(Resource.Id.message);
csharp = FindViewById<CheckBox>(Resource.Id.csharp);
objectivec = FindViewById<CheckBox>(Resource.Id.objective);
java = FindViewById<CheckBox>(Resource.Id.java);
android = FindViewById<RadioButton>(Resource.Id.android);
ios = FindViewById<RadioButton>(Resource.Id.ios);
windows = FindViewById<RadioButton>(Resource.Id.windows);

It isn’t difficult, but it is tedious.  In fact, though, it is made a good deal easier by the fact that the controls do appear in Intellisense,

Intellisense

Next, I added a click event handler for the button, and here I took a risk and just followed the .Net convention,

button.Click += new EventHandler(submit_click);

I was pleasantly surprised that this worked fine, as did the signature on the event handler,

private void submit_click(object sender, EventArgs e)
{
//…
}

It makes for a very easy transition when things like this are consistent. 

Creating The Output

The rest was straight forward logic, checking whether the CheckBoxes were checked, and building up a string based on which ones were,

private void submit_click(object sender, EventArgs e)
{
var sb = new StringBuilder();
if (csharp.Checked || objectivec.Checked || java.Checked)
{
sb.Append("Languages: ");
sb.Append(csharp.Checked ? " C#" : string.Empty);
sb.Append(objectivec.Checked ? " Objective C" :
string.Empty);
sb.Append(java.Checked ? " Java" : string.Empty);
}

I wondered if there was a way to obtain the selected RadioButton from the RadioButtonList, but I couldn’t find anything in Intellisense, so I went with the brute force method,

sb.Append("nUses ");

if (android.Checked)
sb.Append("Android ");
if (ios.Checked)
sb.Append("Apple ");
if (windows.Checked)
sb.Append("Windows ");

sb.Append("phone.");

Once the StringBuilder was complete, I assigned the resulting string to my TextView,

message.Text = sb.ToString();

What Have You Learned, Dorothy?

It is one thing to read along with the documentation and nod your head and feel like you’re understanding, and quite another to sit down with a new Visual Studio project,  and write a working program.  It turned out to be easier than I had feared, but of course what I created was nearly trivial. 

Nonetheless, as a .NET C# developer, Xamarin clearly and unequivocally cut my learning time drastically and significantly flattened the learning curve. 

About the Author

JesseJesse Liberty is a Master Consultant for Falafel Software, an author and he creates courses for Pluralsight.    Liberty is a Microsoft MVP and he hosts the popular Yet Another Podcast. His blog is considered required reading. He was a Senior Evangelist for Microsoft,  a XAML Evangelist for Telerik, a Distinguished Software Engineer at AT&T; Software Architect for PBS and Vice President of Information Technology at Citibank. Jesse can be followed on twitter at @JesseLiberty

The following two tabs change content below.