James Montemagno: DataBinding Settings in Xamarin.Forms

For nearly four years now I have been using my cross-platform settings plugin to save preferences across all the different platforms. Ever since I pushed it up to NuGet it has been extremely popular with over 18,000 installs! The plugin gives you a very simple way of saving out native settings from shared code. Usually, you will create a native UI for each platform and in the case of Android use the PreferenceActivity to automagically create a settings page from XML (which is magical), but what if you are using Xamarin.Forms and want to databind stuff up? This is the exact question I got over on StackOverflow. Of cource you can, let’s do it.

Given this Settings Class:


public static class Settings 
{

    private static ISettings AppSettings
    {
        get
        {
            return CrossSettings.Current;
        }
    }

    const string CountKey = "count";
    private static readonly int CountDefault = 0;


    public static int Count
    {
        get { return AppSettings.GetValueOrDefault<int>(CountKey, CountDefault); }
        set { AppSettings.AddOrUpdateValue<int>(CountKey, value); }
    }
}

Approach 1: Essentially you need to create a view model with a public property that you wish to data bind to and then call into settings from there and raise a property changed notification if the value changed. Your Settings.cs can stay the same but you will need to create the viewmodel such as:


public class MyViewModel : INotifyPropertyChanged
{

    public int Count
    {
        get { return Settings.Count; }
        set
        {
            if (Settings.Count == value)
                return;

            Settings.Count = value;
            OnPropertyChanged();
        }

    }

    private Command increase;
    public Command IncreaseCommand
    {
        get 
        { 
            return increase ?? (increase = new Command(() =>Count++));
        }
    }

    public event PropertyChangedEventHandler PropertyChanged;

    public void OnPropertyChanged([CallerMemberName]string name = "")
    {
        var changed = PropertyChanged;
        if (changed == null)
            return;
        changed(this, new PropertyChangedEventArgs(name));
    }

}

Then you XAML will look like this inside your Content page:


<StackLayout Padding="25">
 <Button Text="Increase" Command="{Binding IncreaseCommand}"/>
 <Label Text="{Binding Count, StringFormat='The count is {0:F0}'}"/>
</StackLayout>

Make sure you set the BindingContext in the xaml.cs of the page:


public partial class MyPage : ContentPage
{
    public MyPage()
    {
        InitializeComponent();
        BindingContext = new MyViewModel();
    }
}

This actually isn’t too much code to actually implement as your ViewModel would have a BaseViewModel that implements INotifyPropertyChanged, so really you are just adding in


public int Count
{
    get { return Settings.Count; }
    set
    {
        if (Settings.Count == value)
            return;

        Settings.Count = value;
        OnPropertyChanged();
    }
}

Approach 2: More magical way

However, using the powers of C# and knowing how Databinding works you could first create a BaseViewModel that everything will use:


public class BaseViewModel : INotifyPropertyChanged
{
    public Settings Settings
    {
        get { return Settings.Current; }
    }
    public event PropertyChangedEventHandler PropertyChanged;

    public void OnPropertyChanged([CallerMemberName]string name = "")
    {
        var changed = PropertyChanged;
        if (changed == null)
            return;
        changed(this, new PropertyChangedEventArgs(name));
    }
}

Notice my reference to Settings.Current, we will need to implement that now as a singleton, but we will use our BaseViewModel so we don’t have to re-implement INotifyPropertyChanged:


public class Settings : BaseViewModel
{
    static ISettings AppSettings
    {
        get
        {
            return CrossSettings.Current;
        }
    }

    static Settings settings;
    public static Settings Current
    {
        get { return settings ?? (settings = new Settings()); }
    }

    const string CountKey = "count";
    static readonly int CountDefault = 0;

    public int Count
    {
        get
        { 
            return AppSettings.GetValueOrDefault<int>(CountKey, CountDefault); 
        }
        set
        { 
            if (AppSettings.AddOrUpdateValue<int>(CountKey, value))
                OnPropertyChanged();

        }
    }
}

Now of course we will still want to create a unique ViewModel that our XAML view will bind to:


public class MyViewModel : BaseViewModel
{
    private Command increase;
    public Command IncreaseCommand
    {
        get 
        { 
            return increase ?? (increase = new Command(() =>Settings.Count++));
        }
    }
}

Notice that we are now inheriting from BaseViewModel, which means our command can actually just increment Settings.HotTimeCount! But now we must adjust our Xaml just a bit as to what we are actually data binding to for our label:


<StackLayout Padding="25">
 <Button Text="Increase" Command="{Binding IncreaseCommand}"/>
 <Label BindingContext="{Binding Settings}" Text="{Binding Count, StringFormat='The count is {0:F0}'}"/>
</StackLayout>

Notice I am setting the BindingContext to our Settings, which is in our BaseViewModel for the Label, this must be done because that is where it is located now. And there you have it.

Details

Xamarin: Be First To Try Our New Release Candidate

To keep pace with the rapid evolution of iOS, Android, and our own mobile innovations, we publish many updates to Xamarin over the course of the year. As Xamarin has grown, it has become increasingly important for our customers that every release of Xamarin be enterprise-grade: stable and high-quality. Today, we are instituting a new release […]

The post Be First To Try Our New Release Candidate appeared first on Xamarin Blog.

Details

Johan Karlsson: FontAwesome using Xamarin Forms and iOS

This is the same post as the one for Android, except this one is for iOS. I didn’t really plan to write this one since the same info can be found https://blog.xamarin.com/custom-fonts-in-ios/. However, I got some comments about the previous post being incomplete, so I guess I have to complete myself.

Read this one first to get the background – http://www.johankarlsson.net/2015/09/fontawesome-using-xamarin-forms-and.html

I also moved the source to github since I might be adding stuff to it as I go along. Find it under johankson/awesome.

Here we go!

Download the font

Download the FontAwesome font and drop it in your Resource folder for the iOS project. Remember to change the “Copy to output directory” to “Always”, otherwise you’ll get a null reference exception.

Edit the info.plist file

In the root of your iOS project you’ll find a file called info.plist. We need to add stuff to it by editing the file using a text editor. If you simply double click it then Xamarin Studio (or Visual Studio) will open a GUI for it. We don’t want that. I recommend Sublime Text for all you text editing needs.
Add a key named UIAppFonts followed by an array. One entry in the array should point to the font, in this case the fontawesome.ttf. If you have multiple fonts just add more entries. Make sure you add the complete path if you add the font to a folder.

Edit the XAML

Add a FontFamily attribute to what ever control you’d like display an icon through. The FontFamily attribute will be ignored on Android so you still need the custom renderer covered in the last blog post. The XAML is from the file MyPage.Xaml in the Forms project.

The result

As expected, we see some FontAwesome icons. 

Extras

Remember that you can adjust the size and color by using the FontSize and TextColor properties. You can also add icons to buttons.
    <Button Text=&#xf041; FontSize=40 FontFamily=FontAwesome />

Summary

So you see that iOS is simpler than Android when it comes to using custom fonts. I also know at the time of writing I haven’t created a Windows Phone solution yet. I will as soon as time permits.
Details

Xamarin: World Bank App Makes Complex Surveys Accessible Anywhere

The World Bank seeks to end extreme poverty and to push for greater equity. They have been providing loans to countries in development and transition since 1946, with more than $40 billion in loans supplied in 2014 alone. Supported by the 188 states of the United Nations and more than 12,000 staff in Washington D.C. […]

The post World Bank App Makes Complex Surveys Accessible Anywhere appeared first on Xamarin Blog.

Details

Marcos Cobeña Morián: Colors in iOS: Same Value, Different Tonality

This entry was originally written at Plain Concepts’ Xamarin Team Blog. While working on a native Xamarin.iOS app, I noticed a difference between the same color applied through source code to the navigation bar and through Interface Builder to the background of a scroll view. There was a small difference between both colors’ tonality, although […]
Details