{"id":23934,"date":"2016-01-20T11:29:30","date_gmt":"2016-01-20T19:29:30","guid":{"rendered":"https:\/\/blog.xamarin.com\/?p=23934"},"modified":"2016-01-20T11:29:30","modified_gmt":"2016-01-20T19:29:30","slug":"advanced-data-binding-for-ios-android-and-windows","status":"publish","type":"post","link":"https:\/\/devblogs.microsoft.com\/xamarin\/advanced-data-binding-for-ios-android-and-windows\/","title":{"rendered":"Data Binding Tips and Tricks for iOS, Android, and Windows"},"content":{"rendered":"<p>\t\t\t\tUtilizing data binding in Xamarin.Forms applications can greatly simplify application development by automatically synchronizing app data to the user interface with very little work. <a href=\"https:\/\/blog.xamarin.com\/introduction-to-data-binding\/\" target=\"_blank\">Previously<\/a>, we took a look at setting up your project to begin data binding and then saw it in action in an app.<\/p>\n<p>In this blog post, I\u2019m going to explore more advanced data binding scenarios where values are formatted and converted as they are passed between <em>source<\/em> and <em>target<\/em> by the binding engine.<\/p>\n<h2>Control-to-Control Bindings<\/h2>\n<p>While data bindings are most often used to synchronize a UI with an underlying data model, they can also be defined to link properties of two controls on the same page. This is achieved by setting the <code>BindingContext<\/code> of the <em>target<\/em> object using the <code>x:Reference<\/code> markup extension, as demonstrated in the following XAML code example from the <a href=\"https:\/\/github.com\/davidbritch\/xamarin-forms\/tree\/master\/AdvancedDataBinding\" target=\"_blank\">sample application<\/a>:<\/p>\n<pre class=\"lang:xml decode:true\" title=\"RotationPage class\">&lt;ContentPage xmlns=\"http:\/\/xamarin.com\/schemas\/2014\/forms\" xmlns:x=\"http:\/\/schemas.microsoft.com\/winfx\/2009\/xaml\" x:Class=\"AdvancedDataBinding.RotationPage\" Title=\"Rotation\" Icon=\"xaml.png\"&gt;\n\t&lt;StackLayout Padding=\"0,20,0,0\"&gt;\n\t\t&lt;Label Text=\"Advanced Data Binding Demo\" FontAttributes=\"Bold\" HorizontalOptions=\"Center\" \/&gt;\n\t\t&lt;Slider x:Name=\"slider\" Maximum=\"360\" \/&gt;\n\t\t&lt;Image Source=\"waterfront.jpg\" BindingContext=\"{x:Reference slider}\" \n               Rotation=\"{Binding Value}\" VerticalOptions=\"CenterAndExpand\" \/&gt;\n\t\t&lt;Label BindingContext=\"{x:Reference slider}\" HorizontalOptions=\"Center\"\n               Text=\"{Binding Value, StringFormat='Rotation angle: {0:F0} degrees'}\" \/&gt;\n\t&lt;\/StackLayout&gt;\n&lt;\/ContentPage&gt;<\/pre>\n<p>The <code>Slider<\/code> contains an <code>x:Name<\/code> attribute that is referenced by the two <code>Label<\/code> instances, using the <code>x:Reference<\/code> markup extension. This binding extension defines a property called <code>Name<\/code> to set to the name of the referenced element, in this case <code>slider<\/code>. However, the <code>Name<\/code> property is not explicitly required and is omitted here. The <code>Value<\/code> property of the <code>Slider<\/code> is bound to from both the <code>Rotation<\/code> property of the <code>Image<\/code> and the <code>Text<\/code> property of the <code>Label<\/code>. Therefore, as the slider is moved, the <code>Image<\/code> rotates and the <code>Label<\/code> is updated with the rotation angle, as shown in the following screenshots:<\/p>\n<p><img decoding=\"async\" class=\"aligncenter size-full wp-image-23946\" src=\"https:\/\/devblogs.microsoft.com\/wp-content\/uploads\/sites\/44\/2019\/03\/rotation.png\" alt=\"rotation\" width=\"1280\" height=\"768\" \/><\/p>\n<p>In Xamarin.Forms, bindings do not perform any implicit type conversions. However, the <code>Binding<\/code> markup extension has a <code>StringFormat<\/code> property that allows you to apply a .NET formatting string to the data. In the second <code>Label<\/code> instance, a formatting string of <code>{0:F0}<\/code> is used to display the <code>Value<\/code> property of the <code>Slider<\/code> to zero decimal places. Formatting strings must be suitable for a call to the <code>string.Format<\/code> method, and the entire formatting string is placed in single quotes to avoid the curly braces being mistaken for the braces used to delimit markup extensions.<\/p>\n<h2>Converters<\/h2>\n<p>While string formatting can be used to format the data returned from a <em>source<\/em> object, it can\u2019t be used to perform type conversions. This is the role of <em>value converters<\/em>. A value converter is a class that allows you to change the format of data as it\u2019s passed between <em>source<\/em> and <em>target<\/em> by the binding engine. This is achieved by the class implementing the <code>IValueConverter<\/code> interface, which requires you to implement <code>Convert<\/code> and <code>ConvertBack<\/code> methods.<\/p>\n<p>The following code example shows the <code>IntToBooleanConverter<\/code>, used in the <a href=\"https:\/\/github.com\/davidbritch\/xamarin-forms\/tree\/master\/AdvancedDataBinding\" target=\"_blank\">sample application<\/a>, which returns a <code>boolean<\/code> value based on a comparison of two integer values:<\/p>\n<pre class=\"lang:c# decode:true \" title=\"IntToBooleanConverter class\">public class IntToBooleanConverter : IValueConverter\n{\n\tpublic object Convert (object value, Type targetType, object parameter, CultureInfo culture)\n\t{\n\t\tint minimumLength = System.Convert.ToInt32 (parameter);\n\t\treturn (int)value &gt;= minimumLength;\n\t}\n\n\tpublic object ConvertBack (object value, Type targetType, object parameter, CultureInfo culture)\n\t{\n\t\tthrow new NotImplementedException ();\n\t}\n}<\/pre>\n<p>The <code>Convert<\/code> method is called whenever a value passes from the <em>source<\/em> to the <em>target<\/em>. The <code>value<\/code> argument to <code>Convert<\/code> is the value from the <em>source<\/em> to be converted. The <code>targetType<\/code> argument is the type of the <em>target<\/em> property, and the <code>Convert<\/code> method should return an object or value that matches the <code>targetType<\/code>. The <code>parameter<\/code> argument is an optional conversion parameter that can be specified as a property to the <code>Binding<\/code> markup extension. Finally, the <code>culture<\/code> argument can be used if you need to perform a culture-specific conversion. The <code>IntToBooleanConverter<\/code> returns <code>true<\/code> if the value from the <em>source<\/em> is greater than or equal to the value of the <code>parameter<\/code> argument, otherwise it returns <code>false<\/code>.<\/p>\n<p>The <code>ConvertBack<\/code> method is called whenever a value passes from the <em>target<\/em> to the <em>source<\/em> (for <code>TwoWay<\/code> or <code>OneWayToSource<\/code> bindings). For this method, the <code>value<\/code> argument is the value from the <em>target<\/em> and the <code>targetType<\/code> argument is the type of the <em>source<\/em> property. When the <code>ConvertBack<\/code> method isn&#8217;t required, it\u2019s common to have it throw a <code>NotImplementedException<\/code>, or return <code>null<\/code>.<\/p>\n<p>Similarly, the <a href=\"https:\/\/github.com\/davidbritch\/xamarin-forms\/tree\/master\/AdvancedDataBinding\" target=\"_blank\">sample application<\/a> also contains an <code>IntToColorConverter<\/code>, which returns one of two colors depending on a comparison of two integer values.<\/p>\n<p>In XAML, value converters are usually instantiated in a <code>ResourceDictionary<\/code> and then referenced in a <code>Binding<\/code> expression by using the <code>StaticResource<\/code> markup extension. Because value converters don\u2019t maintain state, a value converter instance can be shared amongst multiple bindings.<\/p>\n<p>The following code example demonstrates the use of value converters in the <a href=\"https:\/\/github.com\/davidbritch\/xamarin-forms\/tree\/master\/AdvancedDataBinding\" target=\"_blank\">sample application<\/a>:<\/p>\n<pre class=\"lang:c# decode:true\" title=\"IntToBooleanConverter class\">&lt;ContentPage xmlns=\"http:\/\/xamarin.com\/schemas\/2014\/forms\" xmlns:x=\"http:\/\/schemas.microsoft.com\/winfx\/2009\/xaml\" xmlns:local=\"clr-namespace:AdvancedDataBinding;assembly=AdvancedDataBinding\" x:Class=\"AdvancedDataBinding.ConverterPage\" Title=\"Converter\" Icon=\"xaml.png\"&gt;\n\t&lt;ContentPage.Resources&gt;\n\t\t&lt;ResourceDictionary&gt;\n\t\t\t&lt;local:IntToBooleanConverter x:Key=\"intToBoolConverter\" \/&gt;\n\t\t\t&lt;local:IntToColorConverter x:Key=\"intToColorConverter\" \/&gt;\n\t\t&lt;\/ResourceDictionary&gt;\n\t&lt;\/ContentPage.Resources&gt;\n\t&lt;StackLayout Padding=\"0,20,0,0\"&gt;\n\t\t&lt;Label Text=\"Advanced Data Binding Demo\" FontAttributes=\"Bold\" HorizontalOptions=\"Center\" \/&gt;\n\t\t&lt;Label Text=\"Enter your response (minimum 10 characters):\" \/&gt;\n\t\t&lt;Editor x:Name=\"editor\" HeightRequest=\"100\" \/&gt;\n\t\t&lt;StackLayout Orientation=\"Horizontal\"&gt;\n\t\t\t&lt;Label Text=\"Number of characters:\" \/&gt;\n\t\t\t&lt;Label Text=\"{Binding Source={x:Reference editor}, Path=Text.Length}\" \n                   TextColor=\"{Binding Source={x:Reference editor}, Path=Text.Length, \n                               Converter={StaticResource intToColorConverter}, ConverterParameter=10}\" \/&gt;\n\t\t&lt;\/StackLayout&gt;\n\t\t&lt;Button Text=\"Send\" HorizontalOptions=\"Center\" \n                IsEnabled=\"{Binding Source={x:Reference editor}, Path=Text.Length, \n                            Converter={StaticResource intToBoolConverter}, ConverterParameter=10}\" \/&gt;\n\t&lt;\/StackLayout&gt;\n&lt;\/ContentPage&gt;<\/pre>\n<p>In order to reference value converters in XAML, their location must be specified with an XML namespace declaration (<code>xmlns<\/code>). Accessing classes that are local to the application PCL is usually achieved with the <code>local<\/code> prefix. The namespace declaration indicates the namespace name and the assembly containing the code.<\/p>\n<p>The <code>IntToBoolConverter<\/code> is instantiated in the page\u2019s <code>ResourceDictionary<\/code> and referenced in the <code>Binding<\/code> expression set on the <code>IsEnabled<\/code> property of the <code>Button<\/code>. It\u2019s used to enable the <code>Button<\/code> only when a minimum of ten characters have been entered into the <code>Editor<\/code>. Similarly, the <code>IntToColorConverter<\/code> is used to set the color of the number of characters that have been entered into the <code>Editor<\/code> to green when there\u2019s a minimum of ten characters, otherwise it sets to red. The screenshots below demonstrate this functionality:<\/p>\n<p><img decoding=\"async\" class=\"aligncenter size-full wp-image-23949\" src=\"https:\/\/devblogs.microsoft.com\/wp-content\/uploads\/sites\/44\/2019\/03\/converter-pre.png\" alt=\"converter-pre\" width=\"1280\" height=\"768\" \/><\/p>\n<p><img decoding=\"async\" class=\"aligncenter size-full wp-image-23950\" src=\"https:\/\/devblogs.microsoft.com\/wp-content\/uploads\/sites\/44\/2019\/03\/converter-post.png\" alt=\"converter-post\" width=\"1280\" height=\"768\" \/><\/p>\n<p>Note that if only one instance of a value converter is being used, it doesn\u2019t need to be stored in a <code>ResourceDictionary<\/code>. Instead, it can be instantiated directly in the <code>Binding<\/code>. For more information, see <a href=\"http:\/\/developer.xamarin.com\/guides\/xamarin-forms\/user-interface\/xaml-basics\/data_bindings_to_mvvm\/\" target=\"_blank\">From Data Bindings to MVVM<\/a>.<\/p>\n<h2>Wrapping Up<\/h2>\n<p>While data bindings are most often used to synchronize a UI with an underlying data model, they can also be defined to link properties of two views on the same page. This is achieved by setting the <code>BindingContext<\/code> of the <em>target<\/em> object using the <code>x:Reference<\/code> markup extension.<\/p>\n<p>In Xamarin.Forms, bindings do not perform any implicit type conversions. String formatting can be used to format data returned from a <em>source<\/em> object, and value converters can be used to change the format of data as it\u2019s passed between <em>source<\/em> and <em>target<\/em> by the binding engine.<\/p>\n<p>For more information about XAML markup extensions, see <a href=\"https:\/\/developer.xamarin.com\/guides\/xamarin-forms\/user-interface\/xaml-basics\/xaml_markup_extensions\/\" target=\"_blank\">XAML Markup Extensions<\/a>. For more information about data binding, see <a href=\"http:\/\/developer.xamarin.com\/guides\/xamarin-forms\/user-interface\/xaml-basics\/data_binding_basics\/\" target=\"_blank\">Data Binding Basics<\/a> and <a href=\"http:\/\/developer.xamarin.com\/guides\/xamarin-forms\/user-interface\/xaml-basics\/data_bindings_to_mvvm\/\" target=\"_blank\">From Data Bindings to MVVM<\/a>. <a href=\"https:\/\/university.xamarin.com\/\" target=\"_blank\">Xamarin University<\/a> also provides a class on data binding in Xamarin.Forms.\t\t<\/p>\n","protected":false},"excerpt":{"rendered":"<p>Utilizing data binding in Xamarin.Forms applications can greatly simplify application development by automatically synchronizing app data to the user interface with very little work. Previously, we took a look at setting up your project to begin data binding and then saw it in action in an app. In this blog post, I\u2019m going to explore [&hellip;]<\/p>\n","protected":false},"author":543,"featured_media":23946,"comment_status":"open","ping_status":"closed","sticky":false,"template":"","format":"standard","meta":{"_acf_changed":false,"footnotes":""},"categories":[2],"tags":[4,16],"class_list":["post-23934","post","type-post","status-publish","format-standard","has-post-thumbnail","hentry","category-developers","tag-xamarin-platform","tag-xamarin-forms"],"acf":[],"blog_post_summary":"<p>Utilizing data binding in Xamarin.Forms applications can greatly simplify application development by automatically synchronizing app data to the user interface with very little work. Previously, we took a look at setting up your project to begin data binding and then saw it in action in an app. In this blog post, I\u2019m going to explore [&hellip;]<\/p>\n","_links":{"self":[{"href":"https:\/\/devblogs.microsoft.com\/xamarin\/wp-json\/wp\/v2\/posts\/23934","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/devblogs.microsoft.com\/xamarin\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/devblogs.microsoft.com\/xamarin\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/devblogs.microsoft.com\/xamarin\/wp-json\/wp\/v2\/users\/543"}],"replies":[{"embeddable":true,"href":"https:\/\/devblogs.microsoft.com\/xamarin\/wp-json\/wp\/v2\/comments?post=23934"}],"version-history":[{"count":0,"href":"https:\/\/devblogs.microsoft.com\/xamarin\/wp-json\/wp\/v2\/posts\/23934\/revisions"}],"wp:featuredmedia":[{"embeddable":true,"href":"https:\/\/devblogs.microsoft.com\/xamarin\/wp-json\/"}],"wp:attachment":[{"href":"https:\/\/devblogs.microsoft.com\/xamarin\/wp-json\/wp\/v2\/media?parent=23934"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/devblogs.microsoft.com\/xamarin\/wp-json\/wp\/v2\/categories?post=23934"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/devblogs.microsoft.com\/xamarin\/wp-json\/wp\/v2\/tags?post=23934"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}