Xamarin iOS: Learning by Examples: Part#1


Target Audience:

I expect you have basic iOS development experiences. A “Hello World” app written by you and installed in an iOS device would be suffice.

Also you have minimal working knowledge on C# language. You don’t have to be a guru. It also might possible if you know Java or C++. It should be hard for you to follow along C#.

Why Xamarin

  • Single language C# with convenience of .NET platform/libraries.
  • Native UI and Code sharing capabilities
  • Performance is as good as Native apps.

Xamarin cons

  • UI is not shared. As such, you need to have working knowledge of both Android and iOS platforms separately to develop apps in Xamarin. You will build Android UI with Android xml and iOS UI with storyboard. They have Xamarin.Forms, but thats a whole other story. I will try to write another series based on Xamarin.Forms
  • Implicitly the above point also means you need to have working knowledge of Android (Java/Xml), iOS (Swift/Storyboard) and C#/.NET. A great looking learning curve …helping_hand_on_edge_800_wht_10663
  • Xamarin is a commercial product. You need to pay $25 for each platform. So, building for iOS + Android + Windows, you need to pay $75/month. They do have a trial version and followed by a Starter edition after the trial period. However, it will get you only that much a free version can get.
  • Application size will be a bit larger than Native apps. like, 2.5 MB as of now.

Which part of code will be shared?

Following components can be shared across platforms

  • Models
  • Service layer
  • Data + Data access layer
  • Business layer
  • Network layer

Shared components will be written in C#. On top of this C# layer we will create UI layer using Xamarin.iOS and/or Xamarin.Android. App layer (connection between UI and App) will also be written in C#, but it won’t be shared. On average you can share 60% code, rest 40% will be UI and App layer.

PCL (Portable Class Library)

PCL is a C# library that can be used as a library project on multiple platforms. PCL follows common denominator approach. That means, you can incorporate common features of the platforms in a PCL library.

Task:

  • Download and Install Xamarin Studio.
    • I am using Mac. You can use either Mac or Windows. For iOS development, Mac OS is required. If we choose to develop in Windows, you need to be connected with a Mac for building iOS app.
  • Create a New Solution -> Other -> Miscellaneous -> Blank solution. Do not enter any Project name. Only enter a Solution name. For example, DemoAppName.
  • Right click on newly created solution and Add -> Add New Project… -> Cross-platform -> Portable Library -> Name: DemoAppName.Core
  • Right click MyClass.cs -> Remove -> Delete.
  • Right click on DemoAppName.Core -> Add -> New Folder -> Name: Model
  • Right click on Model -> Add -> New File… -> Name: User.cs

This model class User contains basic informations of an User.

using System;
using System.Collections.Generic;

namespace DemoAppName.Core
{
	public class User
	{
		public User ()
		{
		}

		public int UserId {
			get;
			set;
		}

		public string FirstName {
			get;
			set;
		}

		public string LastName {
			get;
			set;
		}

		public int Age {
			get;
			set;
		}

		public string ProfileImagePath {
			get;
			set;
		}

		public bool Active {
			get;
			set;
		}

		public string Email {
			get;
			set;
		}

		public List<string> PhoneNumbers {
			get;
			set;
		}
	}
}

Lets Create another model class named ProfessionalGroup, that will be a collection of Users. Each ProfessionalGroup will contain a number of Users.

using System;
using System.Collections.Generic;

namespace DemoAppName.Core
{
	public class ProfessionGroup
	{
		public ProfessionGroup ()
		{
		}

		public int ProfessionId {
			get;
			set;
		}

		public string Title {
			get;
			set;
		}

		public string ImagePath {
			get;
			set;
		}

		public List<User> People {
			get;
			set;
		}
	}
}

Create a UserRepo.cs class. This class will contain a demo collection of ProfessionalGroup objects. It will also contain some convenient method to query the ProfessionalGroup collection.

Create a folder named Data and place the UserRepo.cs class inside it.

using System;
using System.Collections.Generic;
using System.Linq;

namespace DemoAppName.Core
{
	public class UserRepo
	{
		public UserRepo ()
		{
		}

		/*
		 * Returns all Users in the collection
		 */
		public List<User> GetAllUsers()
		{
			IEnumerable <User> ret =
				from professionGroup in professionGroups
				from user in professionGroup.People
				select user;
			return ret.ToList<User> ();
		}

		/*
		 * Return a User with specific Id
		 */
		public User GetUserById(int id)
		{
			IEnumerable <User> ret =
				from professionalGroup in professionGroups
				from user in professionalGroup.People
				where user.UserId == id
				select user;

			return ret.FirstOrDefault ();
		}

		/*
		 * Get the list of all ProfessionalGroup
		 */
		public List<ProfessionGroup> GetProfessionalGroups()
		{
			return professionGroups;
		}

		/**
		 * Get a list of all users under a specific ProfessionalGroup
		 */
		public List<User> GetUsersOfGroupId(int groupId)
		{
			var group = professionGroups.Where (h => h.ProfessionId == groupId).FirstOrDefault ();

			if (group != null) {
				return group.People;
			}

			return null;
		}

		/**
		 * Get All active users in the collection
		 */
		public List<User> GetActiveUsers()
		{
			IEnumerable <User> ret =
				from professionalGroup in professionGroups
				from user in professionalGroup.People
				where user.Active
				select user;
			return ret.ToList<User> ();
		}

		/**
		 * Dummy data of ProfessionGroup. Each ProfessionGroup will contain a number of User.
		 */
		private static List<ProfessionGroup> professionGroups = new List<ProfessionGroup>()
		{
			new ProfessionGroup()
			{
				ProfessionId = 1,
				Title = "Doctor",
				ImagePath = "",
				People = new List<User>()
				{
					new User ()
					{
						UserId = 1,
						FirstName = "DFN1",
						LastName = "DLN1",
						Age = 30,
						ProfileImagePath = "",
						Active = true,
						Email = "DFN1@gmail.com",
						PhoneNumbers = new List<string>() { "+0123456789", "+0123456789"}
					},
					new User ()
					{
						UserId = 2,
						FirstName = "DFN2",
						LastName = "DLN2",
						Age = 32,
						ProfileImagePath = "",
						Active = true,
						Email = "DFN2@gmail.com",
						PhoneNumbers = new List<string>() { "+0123456789", "+0123456789"}
					}
				}
			},
			new ProfessionGroup ()
			{
				ProfessionId = 2,
				Title = "Engineer",
				ImagePath = "",
				People = new List<User>()
				{
					new User ()
					{
						UserId = 3,
						FirstName = "EFN1",
						LastName = "ELN1",
						Age = 30,
						ProfileImagePath = "",
						Active = true,
						Email = "EFN1@gmail.com",
						PhoneNumbers = new List<string>() { "+0123456789", "+0123456789"}
					},
					new User ()
					{
						UserId = 4,
						FirstName = "EFN2",
						LastName = "ELN2",
						Age = 32,
						ProfileImagePath = "",
						Active = true,
						Email = "EFN2@gmail.com",
						PhoneNumbers = new List<string>() { "+0123456789", "+0123456789"}
					}
				}
			}
		};
	}
}

You may encounter an issue of not resolving method. Syntax highlighting will display the error like this,

Screen Shot 2016-01-31 at 1.59.53 PM.png

To resolve this case, Right click on the item -> Resolve -> using System.Linq;

Alternatively add this line at the top of the file,

using System.Linq;

To make separation of concern, create another class named UserDataService.cs under Service Folder (Create a folder named Service). This class will contain methods of same signature as UserRepo.cs. The purpose of this class to delegate task to UserRepo class.

using System;
using System.Collections.Generic;

namespace DemoAppName.Core
{
	public class UserDataService
	{

		private static UserRepo userRepository = new UserRepo();

		public UserDataService ()
		{
		}

		public List<User> GetAllUsers()
		{
			return userRepository.GetAllUsers ();
		}

		public User GetUserById(int id)
		{
			return userRepository.GetUserById (id);
		}

		public List<ProfessionGroup> GetProfessionalGroups()
		{
			return userRepository.GetProfessionalGroups ();
		}

		public List<User> GetUsersOfGroupId(int groupId)
		{
			return userRepository.GetUsersOfGroupId (groupId);
		}

		public List<User> GetActiveUsers()
		{
			return userRepository.GetActiveUsers ();
		}
	}
}

To be continued…

Leave a Reply

Fill in your details below or click an icon to log in:

WordPress.com Logo

You are commenting using your WordPress.com account. Log Out / Change )

Twitter picture

You are commenting using your Twitter account. Log Out / Change )

Facebook photo

You are commenting using your Facebook account. Log Out / Change )

Google+ photo

You are commenting using your Google+ account. Log Out / Change )

Connecting to %s