Share via



September 2016

Volume 31 Number 9

[Xamarin]

Cross-Platform Productivity with Xamarin

By Kevin Ashley | September 2016

If you’re in Silicon Valley these days, you’ll notice that investors and developers alike are mostly conservative about the technologies they use. Most would hire an iOS developer first, followed (if they had enough funding) by an Android and/or a Windows developer. This approach is extremely inefficient, however, and leads to multiple code rewrites: iOS developers use Objective-C; Android developers use Java; Windows developers use C#. They rarely talk to each other, much less participate in code sharing, and this results in apps that are inconsistent across platforms—and usually millions of dollars wasted to support completely separate development branches and technologies. For an effective and consistent development strategy, using a cross-platform technology like Xamarin is the key to productivity. And with the rise of native ahead-of-time (AOT) compilation technologies that translate natively from high-level languages like C# to static code for native platforms, the programming model where separate Android, iOS and Windows developers are needed is becoming a thing of the past.

This is a new direction for traditional apps, but it’s already been successful in other areas, such as gaming. For example, more than half of all 3D games for iOS, Android and Windows are developed with Unity. When you build games in Unity, you mostly develop in C# on a subset of Mono, and that’s not unlike using C# with Xamarin. Unity games run on 20-plus platforms, including Windows, Android, iOS, OS X, Xbox, PlayStation and more. This is a great path to follow for non-gaming apps, and Xamarin provides an excellent platform for doing that.

Can the same approach be used for other apps, not just games? With Xamarin, it can: I used it to create Active Fitness, a cloud-based fitness platform and mobile apps with more than 2 million users around the world (activefitness.co). I started using Xamarin early in the development cycle, beginning with very early versions, and was able to create a cross-platform solution for Windows, iOS and Android, based on the Microsoft Azure cloud. Active Fitness, shown in Figure 1, boasts upward of 90 percent code sharing across its native iOS, Windows and Android apps. That in itself is a productivity gain. In addition, most of Xamarin, including Xamarin.Forms (bit.ly/2a8Yo4g), is open source; the platform enjoys great community support; and the performance is identical to native code, thanks to AOT support on embedded systems. Moreover, Xamarin is included in Visual Studio at no additional cost, including the free Community Edition.

Active Fitness in Action, Demonstrating 3D Maps and a Rich UI
Figure 1 Active Fitness in Action, Demonstrating 3D Maps and a Rich UI

Design Aspects of Cross-Platform Apps with Xamarin

A few years back, mobile app design was strikingly different on each platform. An iOS app, for example, was really not at all like an Android or Windows app in design. That’s no longer the case. Today, most modern apps for Windows, Android, and iOS use similar concepts and design paradigms. What happened? Microsoft created the Modern design language used by Universal Windows Platform (UWP) apps; Google came up with Material design; and Apple introduced a more modern-looking OS design. All these changes made apps in iOS, Android, and Windows look and act more alike, simplifying developers’ work (see Figure 2). Developers even flock to iconic fonts, such as Font Awesome, that use similar iconic concepts for actions across multiple platforms. Platforms still have visual differences, of course; for example, Windows includes live tiles. Perhaps surprisingly, though, if you build a cross-platform app, those are easy to add once the core is there.

Active Fitness on Windows (Left), Android (Middle) and iOS (Right)
Figure 2 Active Fitness on Windows (Left), Android (Middle) and iOS (Right)

When developing with Xamarin you have the ability to craft a beautiful UI for each platform directly from inside Visual Studio. This means using iOS Storyboards, Android XML, and Windows XAML, with access to every control or widget and a huge number of custom controls from vendors. Moreover, Xamarin delivers 100 percent API access completely in C# for each platform.

With the Xamarin.Forms library, which provides an API abstraction for building a shared UI, many design concepts are automatically translated to native controls for each platform via Xamarin custom renderers, giving you the ability to customize a cross-platform control to its native representation on each platform. So you get the productivity advantage of a truly cross-platform app, plus unlimited customization possibilities!

One huge benefit of using Xamarin.Forms is that it’s simply an add-on, a library you add to your project. In terms of productivity and the lifecycle management of your app, this is priceless because you can create code that doesn’t depend much on platform release cycles, which are usually much slower. Xamarin has always had same-day compatibility with major releases of iOS, Android, and Windows, and now that it’s open source, if you need to add a control to Xamarin.Forms, you can always do it yourself by looking at the source code or participating in the GitHub repository for Xamarin.Forms. In addition, Xamarin offers virtually unlimited extensibility options via the custom control renderers for native platforms. If you already have a XAML app, you’re in luck because Xamarin.Forms is just another dialect of XAML, and if your app already uses Silverlight, UWP, or XAML, you can easily add a cross-platform companion in iOS or Android.

Creating Master-Detail Navigation with Xamarin

Let’s take a look at the advantage of using Xamarin by focusing on one example: a typical app in iOS, Android and Windows containing a master-detail (or “hamburger”) navigation pattern, from the open source Xamarin samples repository (bit.ly/29Tk9VJ). If you were to write this app as traditional iOS, Android, and Windows developers do, you’d end up with three separate projects in Objective-C, Java, and C#, and you’d have to use different controls for each: SplitView in Windows, and similar patterns in iOS and Android. Instead, you can use a single Xamarin.Forms instance to do all that hard work for all platforms, as Figure 3 shows.

Xamarin Master-Detail Project with Android, iOS and Windows Targets
Figure 3 Xamarin Master-Detail Project with Android, iOS and Windows Targets

In the App.cs file of the portable project, I instantiate the root page of the app:

public App ()
{
  MainPage =
    new MasterDetailPageNavigation.
    MainPage ();
}

Note that most of the project code resides in a portable project, shared among all OSes, plus in Xamarin.Forms you can use XAML. The XAML in Figure 4 likely looks pretty simple if you’re familiar with the UWP native SplitView control.

Figure 4 Creating a Master-Detail Page Using XAML

<?xml version="1.0" encoding="UTF-8"?>
<MasterDetailPage xmlns="https://xamarin.com/schemas/2014/forms"
xmlns:x="https://schemas.microsoft.com/winfx/2009/xaml"
xmlns:local="clr-namespace:MasterDetailPageNavigation;assembly=MasterDetailPageNavigation"
x:Class="MasterDetailPageNavigation.MainPage">
  <MasterDetailPage.Master>
    <local:MasterPage x:Name="masterPage" />
  </MasterDetailPage.Master>
    <MasterDetailPage.Detail>
      <NavigationPage>
        <x:Arguments>
        <local:ContactsPage />
        </x:Arguments>
      </NavigationPage>
    </MasterDetailPage.Detail>
</MasterDetailPage>

Xamarin provides a lot of flexibility in terms of what developers can do with conditional compilation and platform selection. The following code changes the icon of the master page if the platform is Windows:

if (Device.OS == TargetPlatform.Windows)
{
  Master.Icon = "hamburger.png";
}

Device-Specific Code and Xamarin

So far so good, but can I really get very close to the physical platform in my Xamarin code? In other words, can I differentiate code created for different types of devices? Fortunately, Xamarin is one of the few cross-platform technologies that support native coding and API access. Similar to UWP apps that let you differentiate device family (phone, tablet or desktop), Xamarin contains a very useful Device.Idiom selector, as Figure 5 shows.

Figure 5 Using Device.Idiom to Select the Platform

switch (Device.Idiom)
  {
  case TargetIdiom.Phone:
    heading.Text += " Phone ";
    break;
  case TargetIdiom.Tablet:
    heading.Text += " Tablet ";
    break;
  case TargetIdiom.Desktop:
    heading.Text += " Desktop ";
    break;
  default:
    heading.Text += " unknown ";
    break;
  }

Figure 6 shows another very useful selector, Device.OnPlatform, which can be used in both the codebehind and in your XAML to execute different actions depending on the target OS.

Figure 6 Using Device.OnPlatform to Target Different Platforms

// Device.OnPlatform (Action)
//
var box = new BoxView {
  Color = Color.Green,
  WidthRequest = Device.OnPlatform (30, 40, 50),
  HorizontalOptions = LayoutOptions.Center
};
Device.OnPlatform(
  iOS: () =>{
    box.Color = box.Color.MultiplyAlpha(0.5);
    heading.TextColor = Color.Blue;
  },
  Android: () =>{
    box.Color = box.Color.AddLuminosity(0.3);
    heading.TextColor = Color.FromRgb(115, 129, 130);
  },
  WinPhone: () =>{
    box.Color = box.Color.AddLuminosity(0.3);
    heading.TextColor = Color.Accent;
  },
  Default: () =>{
    heading.Text = "what platform is this?!" + Device.OS;
  }
);

In XAML, Xamarin adds OnPlatform tags supporting different platforms, for example:

<Button Text="Start Timer"
  Clicked="TimerClicked"
  BackgroundColor="Gray"
  HorizontalOptions="Center">
  <Button.WidthRequest>
    <OnPlatform x:TypeArguments="x:Double"
      iOS="200"
      Android="300"
      WinPhone="100" />
  </Button.WidthRequest>
</Button>

But what if I want to customize a control provided by Xamarin.Forms on a native platform? I mentioned earlier the Xamarin feature called custom renderers, which provides that flexibility. Custom renderers are classes you can derive from built-in objects and provide functionality in platform-specific implementations. Let’s say I want to build my own CustomMap control:

public class CustomMap : Map
  {
    public List<CustomPin> CustomPins { get; set; }
  }

On a native platform, the signature of my object will include the following:

[assembly:ExportRenderer (typeof(CustomMap), typeof(CustomMapRenderer))]

So, in Android, iOS and Windows, I can always customize the way my Map control looks and feels. Interestingly, the wrapper for the Xamarin Map control natively wraps the Windows Maps control on Windows, the Google Maps control on Android and the native iOS Maps control on iOS. What else can you customize with custom renderers? Pretty much any control! The Map control is a fairly sophisticated example, but you can also customize buttons, labels, sliders or any control available in Xamarin.Forms.

With Xamarin.Forms 2.2, Xamarin now includes native embedding, which allows adding any native control to a Xamarin.Forms app (bit.ly/29IEvxH).

Accessing the Cloud from Xamarin

Azure has always been cross-platform-friendly, with a variety of SDKs for many different platforms, including iOS, Android, and dedicated cross-platform examples and support for Xamarin. My Active Fitness app was able to scale to 2 million users because of this. Thanks to Azure—its reliability, support and performance—users are able to keep running, jogging and performing various sports activities every day with thousands of devices connected every minute. You can find several great guides dedicated to Xamarin on the Azure Web site, which can help you discover the Microsoft cloud services most suitable for your apps (bit.ly/2a5kciF). In the meantime, I’d like to mention a few common areas where the cloud is very useful for mobile apps:

Authentication: If you need to authenticate or identify users, you’ll likely need to use cloud services in your Xamarin app. Visit bit.ly/29HlDD3 to see how.

Adding push notifications to your apps: Push notifications not only provide a communication mechanism for apps, but also help update platform-specific features, such as tiles. Find out more at bit.ly/29HlDD3.

Offline synchronization:Mobile apps in everyday use are not always online, yet the data needs to synchronize seamlessly, even when devices become disconnected from the back end. See my MSDN Magazine article about occasionally disconnected data sets at msdn.com/magazine/dn890372, as well as a quick start for Xamarin apps at bit.ly/29QkXqT.

Azure Mobile Apps is a great starting point for integrating many cloud services including storage, notifications and authentication. Check out the tutorial at bit.ly/29K3IHi, which is dedicated to Xamarin apps.

Extensions, Components and Plug-ins

Xamarin succeeded and evolved via considerable support of components, plug-ins and extensions. Many extensions are available on GitHub or via NuGet. Some libraries—for example, Android Support Libraries, Google Play Services client libraries, Facebook SDKs, and event charting libraries such as OxyPlot—are supported by Xamarin or its community. Plug-ins are unique offerings that enable developers to access native functionality from shared code. This means that if you want to access GPS functionality you no longer have to write the code three times—you simply download a NuGet package and access the GPS right in your shared code. Some plug-ins are open source and are supported by developers. For example, James Montemagno has developed a large number of plug-ins for Xamarin, such as Connectivity, Settings, Media and others (bit.ly/2a2mM7J).

Figure 7 shows several useful extensions I recommend using as you get deeper into Xamarin development.

Figure 7 Xamarin Extensions

Name Description NuGet Link Docs and Source on GitHub
Battery Status Gather battery level, charging status and type. bit.ly/2a4gbZ6 bit.ly/2a5Ofqm
Barcode Scanner Scan and create barcodes with ZXing.NET.Mobile. bit.ly/2a5Ofqm bit.ly/29QykY9
Compass Access device compass heading. bit.ly/2a32UAZ bit.ly/29KfcKV
Connectivity Get network connectivity info such as type and if connection is available. bit.ly/29QDplO bit.ly/2a33PBr
Cryptography PCL Crypto provides a consistent, portable set of crypto APIs. bit.ly/29Qz5AE bit.ly/29PzwAb
Device Info Get properties about a device, such as OS, model, version and Id. bit.ly/29PzPeg bit.ly/29QzSBq
Device Motion Provides access to Accelerometer, Gyroscope, Magnetometer and Compass. bit.ly/2a6SzTk bit.ly/2a35maG
Embedded Resource Unpack embedded resource for cross-platform use. bit.ly/29J6Wf3 bit.ly/29J6z46
External Maps Launch external maps from latitude/longitude or address. bit.ly/29KgNR0 bit.ly/2abuJbI
File System PCL Storage offers cross-platform storage APIs. bit.ly/29LEOru bit.ly/28Ju1AB
Geolocator Detect GPS location of device. bit.ly/2a70ekG bit.ly/29Tpuvd
Local Notifications Show local notifications. bit.ly/2arOGYf bit.ly/29TpSd7
Media Take or pick photos and videos. bit.ly/2a6rpxi bit.ly/29TqlMm
Messaging Make phone call, send sms and send e-mail. bit.ly/2a8Uie5 bit.ly/29SEdDm
Permissions Check and request runtime permissions. bit.ly/29Tnvo8 bit.ly/29S6ZKv
Akavache key-value store An asynchronous, persistent (writes to disk) key-value store. bit.ly/29Tou7I bit.ly/2arPSLf
Push Notifications Cross-platform push notifications for iOS and Android. bit.ly/29ToDs5 bit.ly/2aex4CR
Settings Simple, consistent cross-platform settings API. bit.ly/29ToTXT bit.ly/2a6tn0Q
Share Easily share text, links or open a browser. bit.ly/2aa2R51 bit.ly/2aa3sUk
Sockets TCP and UDP listeners and clients, plus UDP multicast. bit.ly/1rQIyyR bit.ly/1y1UHPb
Text to Speech Text to speech from shared code. bit.ly/29S7Yud bit.ly/29MMA3S
User Dialogs Enables messagebox-style dialogs. bit.ly/2aa4dMV bit.ly/29Tqzkd
Version Tracking Track which versions of your app a user has installed. bit.ly/29S8YhH bit.ly/2a74lNW

For example, checking connectivity with the Connectivity plug-in in a cross-platform solution becomes a one-liner instead of platform-specific code that needs to be implemented separately in iOS, Android and Windows:

public static bool IsOnline
  {
    get
    {
      return Plugin.Connectivity.CrossConnectivity.Current.IsConnected;
    }
  }

You’ll find even more plug-ins and extensions are available at bit.ly/29XZ3VM.

Device Support: Android Wear, WatchKit and Microsoft Band

Xamarin has always been very responsive to all sorts of devices and device platforms on the market. I had a pleasure of working with the Microsoft Band team, and at Build 2016 we jointly announced some pretty exciting functionality for Active Fitness that added support for more than 50 fitness activities, including skiing, snowboarding and more. Additionally, Active Fitness now supports Android Wear, as the beautiful watch face in Figure 8 shows. If you install Active Fitness on your Android device, the watch face is fully supported.

Android Wear Watch Face for Active Fitness App
Figure 8 Android Wear Watch Face for Active Fitness App

With Xamarin, you can add apps and support to gadgets and devices using the following:

  • Android Wear: Xamarin includes code examples and support, including creating watch faces in C#.
  • Apple WatchKit: For Xamarin support, check the documentation at bit.ly/29XZ3VM.
  • Microsoft Band: In addition to the Microsoft Band SDK, there’s a fantastic Microsoft Band wrapper for cross-­platform Xamarin apps available on GitHub (bit.ly/29WeDli) and NuGet (bit.ly/29SOoLA).

Performance and Compiled XAML

Xamarin.Forms uses a combination of XAML and codebehind logic. If you prefer, you can use only code to instantiate and manage your UI objects. In fact, nothing prevents you from coding most of your UI, apart from efficiency (the declarative nature of XAML makes it very efficient to write and manage). But if you really want to, you can derive your Page from ContentPage and write all the logic in code, no XAML involved, as Figure 9 shows.

Figure 9 Deriving a Page from ContentPage Without XAML

class ButtonCodePage : ContentPage
{
  int count = 0;
  public ButtonCodePage()
  {
    Button button = new Button
    {
      Text = String.Format("Tap for click count!")
    };
    button.Clicked += (sender, args) =>
    {
      count++;
      button.Text =
        String.Format("{0} click{1}!", count, count == 1 ? "" : "s");
    };
    this.Content = button;
  }
}

In this case, all your UI code is really compiled C#. Compiled XAML uses a similar idea: You can tell Xamarin to precompile all your XAML, which makes UI code contained in the XAML files much faster to load and execute. There are several benefits with compiled XAML: immediate compile-time checking, removing load and instantiation time, and reducing the size of your executables. You can enable XAML compilation at assembly:

[assembly: XamlCompilation(XamlCompilationOptions.Compile)]
namespace MyApp

or at the class level:

[XamlCompilation(XamlCompilationOptions.Compile)]
public partial class MyPage

Wrapping Up

Developing with Xamarin, I learned to focus on productivity and to harness the power of the Microsoft open source community. As I’ve noted, Xamarin has been very responsive to open source and device trends: Android Wear, Apple Watch, Microsoft Band, and the latest versions of Android, iOS and Windows. Here are a few notable new additions to Xamarin that make it a truly exciting platform:

  • Data Pages: Simplifies data binding and makes complex multi-page apps even easier to build (bit.ly/29SRtLk).
  • Localization and Multilingual App Toolkit: Fully supports Xamarin projects, adding industry-standard XLIFF support to your projects (bit.ly/2a5Uzwx).
  • Native Control Embedding: Makes adding native controls to Xamarin apps super easy (bit.ly/29IEvxH).
  • Effects: Adds platform-specific effects to Xamarin apps (bit.ly/29RDrbD).

Xamarin provides a powerful and efficient way to build cross-platform apps of literally any complexity that work in iOS, Android and Windows. You can truly focus on app functionality and content and build a powerful app that’ll work in any OS. And once you start building your first Xamarin app, you’ll soon discover a large and vibrant community of cross-platform developers.


Kevin Ashley is an architect evangelist for Microsoft. He’s coauthor of “Professional Windows 8 Programming” (Wrox, 2012) and a developer of top apps and games, most notably Active Fitness (activefitness.co). He often presents on technology at various events, industry shows and Webcasts. In his role, he works with startups and partners, advising on software design, business and technology strategy, architecture, and development. Follow his blog at kevinashley.com and on Twitter: @kashleytwit.

Thanks to the following Microsoft technical experts for reviewing this article: James Montemagno


Discuss this article in the MSDN Magazine forum