Embedding Xamarin.Forms in Native Apps

Xamarin.Forms is really cool! It allows you to almost write your app once and then compile for many platforms. With Xamarin.Forms, you can quickly produce multiple apps, but, you can also take advantage of some awesome features – such as cross-platform UIs in XAML, data binding, sharing code and much more.

Xamarin.iOS, Xamarin.Android and UWP are also fantastic! You can get 100% of the platform APIs and you can produce apps that are super fast and polished.

Most of the time you have to choose between one or the other. Sure, you can do custom renderers or effects in Xamarin.Forms to get more platform API access. And sure, you can use frameworks that help you share code with native Xamarin and Windows apps. Before today, you had one of two choices:

  • Xamarin.Forms for 100% shared code and UI
  • Xamarin/Windows Native for polished, platform-specific APIs and UIs

But… why not have both? Recently Xamarin/Microsoft shared on the blog that Xamarin.Forms can be embedded into native apps. This means that you can take your existing (or new) native app and just drop in a Xamarin.Forms page without doing anything special. You lose nothing, and gain a whole lot more. You can still use XAML, data binding, converters, effects and everything else that comes with Xamarin.Forms – but now from within you native app code and UI.

I have a nice sample app that you can pull from GitHub. Be sure to check it out and let me know what you think of this new functionality. I will try and keep that repository up to date with any new developments.

Xamarin.Forms embedded in native apps

Getting the Bits

To embed Xamarin.Forms into your native app, you just need to install a preview NuGet from the Xamarin.Forms pre-release feed:


Then, you want to install the NuGet into any Xamarin.Forms projects as well as into the native app projects.

That is it! Now you should be able to create your shared page.

If you have any questions or comments you can do this using the Xamarin discussion (Preview: Xamarin.Forms Embedding) on the forums.

It is important to note that this is a pre-release and functionality may change with subsequent releases.

Creating Shared Pages

Let’s take an example of an existing app that you want to add the ability to register and/or login to save user preferences on some cloud service – such as Azure. Your app is out and in the wild, users are loving it, and, you have just received feedback that they want to login across devices and keep their preferences.

What do you do? Well you could create a few screens for each platform and then share some code. But, as all the login screens are going to look the same and work the same, why not do everything in shared XAML?

So, the first thing we can do is to either create a shared project, a .NET Standard library or even a PCL. We then just need to install the pre-release Xamarin.Forms NuGet. Finally, we can go ahead an add a new XAML page. Just right-click and do “Add” > “New Item…” > “Content Page (XAML)” and then you have a new page.

In this page below, I am using data binding, converters, resource dictionaries and good old XAML markup:

<?xml version="1.0" encoding="utf-8"?>
<ContentPage xmlns="http://xamarin.com/schemas/2014/forms"
            <app:NegateConverter x:Key="Negate" />
            <app:NullInvisibilityConverter x:Key="NullInvisibility" />
                <RowDefinition Height="*" />
                <RowDefinition Height="Auto" />
                <RowDefinition Height="*" />
            <StackLayout Spacing="12" Grid.Row="1">
                    <OnPlatform x:TypeArguments="Thickness" 
                                Android="24" iOS="24" WinPhone="0" />
                <Label Text="Enter any username/password:"
                       FontSize="12" />
                <Entry Keyboard="Email" 
                       Placeholder="username or email"
                       Text="{Binding UserName}" 
                       IsEnabled="{Binding IsBusy, Converter={StaticResource Negate}}" />
                <Entry IsPassword="True" 
                       Text="{Binding Password}" 
                       IsEnabled="{Binding IsBusy, Converter={StaticResource Negate}}" />
                <Button Text="Log In" 
                        Command="{Binding LoginCommand}"
                        IsEnabled="{Binding IsBusy, Converter={StaticResource Negate}}" />
                <Label Text="{Binding ErrorMessage}" 
                       IsVisible="{Binding ErrorMessage, Converter={StaticResource NullInvisibility}}" />
                <ActivityIndicator IsRunning="{Binding IsBusy}" 
                                   IsVisible="{Binding IsBusy}" />

Then, in our code-behind, we can write out code to work with the UI. Here we have made use of several features such as binding, commands, messaging and async/await:

public partial class LoginPage : ContentPage
    public const string LoginMessage = "login";

    private readonly JsonPlaceholderApi api;
    private string errorMessage;

    public LoginPage()

        // initialize our fake services
        api = new JsonPlaceholderApi();

        // set up the data binding
        LoginCommand = new Command(OnLogin);
        BindingContext = this;

    private async void OnLogin()
        IsBusy = true;

        // reset errors
        ErrorMessage = "";
        // try logging in with our fake services
        var user = await api.LoginAsync(UserName, Password);
        if (user == null) {
            // there was an error
            ErrorMessage = "There was a problem logging in.";
        } else {
            // let the app know we are finished
            MessagingCenter.Send(user, LoginMessage);

        IsBusy = false;

    public string ErrorMessage
        get { return errorMessage; }
        set { errorMessage = value; OnPropertyChanged(); }

    // we don't want to save this as the user types
    public string UserName { get; set; }

    // we don't want to save this at all
    public string Password { get; set; }

    // the login button uses this
    public ICommand LoginCommand { get; }

That is basically all we need to do in order to create our UI. The JsonPlaceholderApi type just makes use of http://jsonplaceholder.typicode.com to get some random data, the User type is just a simple POCO object and the converters are basic IValueConverter implementations.

Displaying Shared Pages in Native Apps

Once we have created our shared Xamarin.Forms page, we can just instantiate out Xamarin.Forms page and then ask for the native version.

On Android, the CreateFragment extension method will return a native Android Fragment, which we can then use as we would any other fragment. On iOS, we use the CreateViewController extension method and we will get out a native UIViewController that, again, we can use as we would any other view controller. And finally, on Windows, we use the CreateFrameworkElement extension method to get out a native FrameworkElement that we can also uses as any other element.

There are two steps to obtaining this native container, first we make sure Xamarin.forms is initialized:

// Android
Xamarin.Forms.Forms.Init(this, null);

// iOS

// Windows
// the `e` from `Application.OnLaunched(LaunchActivatedEventArgs e)`

Once that is done, we can then get the native page:

// create the Xamarin.Forms page for all platforms
var formsPage = new MyFormsPage();

// Android - get the native Fragment
var nativeFragment = formsPage.CreateFragment(this);

// iOS - get the native UIViewController
var nativeController = formsPage.CreateViewController();

// Windows - get the native FrameworkElement
var nativeElement = formsPage.CreateFrameworkElement();

Now that we have the native view, we can just go ahead and use it as if it was created using the traditional mechanisms.

Xamarin.Android and Xamarin.Forms

When using Xamarin.Forms with an Android app, we are going to need to handle the native Fragment that represents the page. To this end, our Android app is using a native .axml layout with a FrameLayout that will hold all our fragments:

<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
    <!-- the other bits of UI -->
        android:id="@+id/frameLayout" />
    <!-- some more UI -->

Then, in our main activity code, we load this UI as normal and everything works as it usually does. When we want to show our new XAML page at some point, all we need to do is to just make sure Xamarin.Forms is initialized and then instantiate the page before navigating to it:

using Xamarin.Forms.Platform.Android;

public void DisplayLogin()
    if (!Xamarin.Forms.Forms.IsInitialized)
        // initialize Xamarin.Forms before we use it
        Xamarin.Forms.Forms.Init(this, null);

        // we want to listen to the messaging center
        Xamarin.Forms.MessagingCenter.Subscribe(this, LoginPage.LoginMessage, (User user) =>
            // update the app
            CurrentUser = user;

            // go back to the main page

    // create the login page (Xamarin.Forms ContentPage)
    var loginPage = new LoginPage();

    // get hold of the native Android fragment that represents the Xamarin.Forms page
    var loginFragment = loginPage.CreateFragment(this);

    // show the login screen (native Xamarin.Android)
        .Replace(Resource.Id.frameLayout, loginFragment)

Xamarin.iOS and Xamarin.Forms

If we want to use Xamarin.Forms in our iOS app, we will be showing a new UIViewController. We first need to make sure that Xamarin.Forms is initialized and then we can just go ahead and create the desired page. We then get the native view controller that can be presented using all the existing means:

using Xamarin.Forms;

partial void OnLoginClicked(UIButton sender)
    if (!Xamarin.Forms.Forms.IsInitialized)
        // initialize Xamarin.Forms before we use it

        // we want to listen to the messaging center
        Xamarin.Forms.MessagingCenter.Subscribe(this, LoginPage.LoginMessage, (User user) =>
            // update the app
            User = user;

            // go back to the main page

    // create the login page (Xamarin.Forms ContentPage)
    var loginPage = new LoginPage();

    // show the login screen
    var viewController = loginPage.CreateViewController();
    NavigationController.PushViewController(viewController, true);

Windows UWP and Xamarin.Forms

When we want to show a Xamarin.Forms page within our native UWP app, we will work with a FrameworkElement. Like with all the other platforms, we have to make sure that Xamarin.Forms is initialized and then just create the page. Once we have obtained the native element, we can just place it anywhere we need it to be. In this example, I am placing my view in a Flyout as the it is being opened:

using Xamarin.Forms;

private void OnLoginFlyoutOpening(object sender, object e)
    var flyout = sender as Flyout;

    if (!Xamarin.Forms.Forms.IsInitialized)
        // initialize Xamarin.Forms before we use it

        // we want to listen to the messaging center
        Xamarin.Forms.MessagingCenter.Subscribe(this, LoginPage.LoginMessage, (User user) =>
            // update the app
            User = user;
            // show some message for some random reason
            WelcomeText = $"Welcome back {user.Name}!";

            // hide the login screen

    // create the login page (Xamarin.Forms ContentPage)
    var loginPage = new LoginPage();

    // set the native dialog to contain the shared login
    var loginElement = loginPage.CreateFrameworkElement();
    flyout.Content = new Frame
        Content = loginElement,
        Width = 300,
        Height = 200


In this fairly long post, we looked at how to quickly embed a Xamarin.Forms page into an existing native app. The process is easy and painless, and will only get better.

You can download the full code from my GitHub repository and try it out for yourself. And maybe have a look at your app and see if some of those screens that are exactly the same could use Xamarin.Forms.

You can also check out some links:

Some other people also have blogs:

And, then there is code:

Cross-Platform Mobile Apps

One of my current projects at Jam Warehouse is to port the app, You & Your Puppy, from the iPhone/iPad to the Android devices (Smart-phones/Tablets). Over the month of November, I have completed the first version and is now undergoing review at our client, DogsTrust.

The App

It is my first ever Android app as well as my first ever mobile application. The current version that is being tested is written in Java. It is also my first Java application as well. (Lots of firsts πŸ™‚ I then re-created the app using MonoDroid using C# – this is still only been tested in the emulator as I haven’t bought the MonoDroid licence yet. I am currently porting the app to the Windows Phone as well. I opted to use the MonoDroid/MonoTouch instead of native languages for several reasons:

  • I am a total .NET addict – as you can see by the title of this blog πŸ™‚
  • Code re-usability – Write once, test once, deploy n times, get n money!
  • Automatic memory management – who wants to dispose objects manually anyway?
  • Make use of advanced C# features and short-cuts – I can churn out some serious code…
  • And who wants to learn Objective-C or use Eclipse – C# and Visual Studio for me!

The Code

Code re-usability is really cool if you are having to write apps for 4 or more different platforms:
  1. Java for Android
  2. Objective-C for iPhone
  3. C# for Windows Phone
  4. Java for Blackberry
  5. HTML 5 for everything else
We could just use PhoneGap or something similar for all the devices, but why make it too easy? Lets go native! C# for Android/iPhone/Windows Phone and HTML5 for all the other players in the game πŸ™‚
We all know (or at least I hope we do) that the iPhone has a “slightly” different layout to the Android phone. So, how do I get this “write once” thing in the list? Well, I didn’t tell the whole story as you can’t really πŸ™‚

The Database

I do have an element of “write once”, but not for the entire app, just the non-visual part. As all the versions are going to be reading from a database and showing images/videos, we can use the same code for this part.
But there’s a catch, as always, what database do we use? We can use xml files for the data, but who wants to? We are advanced guys here, we use a database when a database is “needed”, just now we have to expand this app. As the original database was a SQLite one, so I used that. No complaints there as it is one of the best (if not the best) for mobile development. But now there’s another catch – this time with Microsoft: Windows Phones don’t have SQLite. And you can’t put the C++ version on the device either. So what do we do? Do we use a different database especially for this? No! we use the C# version called System.Data.Sqlite – much easier than maintaining two databases πŸ™‚ – Don’t we all love this thing called C#?

The Data

OK, so we have the database. Now we need to read this data. We can of course write SQL queries and use the SqliteCommand classes, but who wants to use strings in a strongly typed language? Not me. After a little bit of research a found SQLite-NET a very small ORM for the iPhone. I was saved from strings! It also works on the Android phones! But maybe you noticed that I didn’t say anything about the Windows Phone, That’s right it doesn’t work! – Yup, Microsoft is making things hard for me, but I will not yield, not even to the global monopolistic software company that churns in the billions hourly! No! I re-write the SQLite-NET library (or just tweak it slightly). SQLite-NET was originally using the [DllImport] attributes (P/Invoke) to gain access to the sqlite3.dll that is stored somewhere on the filing system on each device. But for those who don’t know, no P/Invoke on the Windows Phone.
I converted the ORM to use the native SqliteCommand and SqliteConnection instead of the P/Invokes. I don’t actually know why the guys recreated those two classes when they could have just used them instead. Maybe there’s something I don’t know πŸ™‚ I practically halved the code and reduced the amount of possible bugs.
So, now we are up and running with the database, a strongly typed ORM and I can use LINQ to SQLite as well!

The UI

Now we get to the basic functionality of the app, showing the information to the user! This is where the not-so-well-documented MonoCross library comes into play. (I’m hoping to buy this book Professional Cross-Platform Mobile Development in C# that’s supposed to show me the best way to use the framework). All the navigation between screens is taken care of and all getting the data ready for showing is done. Now, the user wants to click (or touch) on something, that’s why they bought the app in the first place :). Here’s the “snag”. We want cross-platform, but we also want the app to look like it was especially designed for each device – although it wasn’t. So we recreate each GUI screen for each platform, but we don’t use any non-platform specific code and if we have to, we abstract it!
In order to get the UI updates and things to happen, I subscribe to events that are raised on the Model, and then perform the necessary tasks to show each page to the user. I also catch all the events from the UI and perform the respective actions on the Model. For example, when the user clicks a link/button the command is sent to my middle-ground library. This library checks to see if the command is a navigation command. If it is, it then notifies the MonoCross framework that we want to navigate to wherever. If it is an action command, we inform the Model of the action we want to perform. The model is then updated, and the Model then fires an event that the UI will know that it has to change.
When we navigate, each screen has an abstracted helper class that receives the command as a parameter, which is then processed and used to inform the Model of the actions required (if any). When the actions are finished, the new screen is displayed.

The Diagram

Here is a basic diagram of the flow of the app from the time the user presses start and just how little code is actually needed for the platform specific areas.
As this diagram shows, most of the code is re-used.
As this diagram shows, most of the code is re-used.
And to prove it (mostly to myself), I was able to port the basic functionality of the Android version of the app to the Windows Phone in about 2-3 hours. There was almost no need for changes to the shared code. A bit of tweaking did improve it, but all the platforms – and future ones – will benefit.