WinRT XAML Validation library: UI Controls for Validation

After you’ve defined the validation logic for your entities and performed validation automatically or manually, you want to show the aggregated validation messages on the UI. Unfortunately WinRT/XAML doesn’t come with such a functionality out of the box and solutions like Prism for Windows Runtime don’t add much value here as well.

WinRT XAML Validation library to the rescue: it comes with two handy UI controls ValidationPanel and ValidationSummary that give you a generic and easy-to-use approach to show validation messages to the user.

ValidationPanel

The ValidationPanel control can be used to show validation information for a single property of your data model entity. It can be wrapped around any XAML control (e.g. a TextBox) and has the following abilities:

  • Show a red/yellow border around the control to represent Errors/Warnings.
  • Show all validation messages for a property at the bottom of the control (optionally).

The usage of the ValidationPanel is quite simple. In XAML, just wrap it around a normal UI control and bind the ValidationMessages collection with the corresponding entity property as key to the control’s ValidationSource property:

<Page x:Class="WinRTXAMLValidation.Demo.MainPage" ...
      xmlns:vc="using:WinRTXAMLValidation.Library.Controls">
    ...
    <TextBlock Text="Your bid" />
    <vc:ValidationPanel ValidationSource="{Binding Bid.ValidationMessages[NewBid]}">
        <TextBox Text="{Binding Bid.NewBid, Mode=TwoWay}" />
    </vc:ValidationPanel>
</Page>

Here’s a sample output of two ValidationPanel controls, showing warnings and errors for the wrapped user inputs:

There are several properties on ValidationPanel that define its behavior:

  • ValidationSource: Bind any ReadOnlyCollection<ValidationMessage> to this property and the control will display the corresponding validation messages (Errors/Warnings). Normally binds to ValidationBindableBase.ValidationMessages[<PropertyName>].
  • ShowValidationMessages (default: true): Indicates whether the validation message texts will be shown on the control. Otherwise, only a red/orange border will be drawn on error/warning validation messages.
  • ShowPropertyValidationMessages (default: true): Indicates whether simple validation messages for a property (identified by ValidationMessage.ValidationMessageKind.Property) will be shown as text at the control.
  • ShowGroupValidationMessages (default: true): Indicates whether property-group validation messages (identified by ValidationMessage.ValidationMessageKind.Overall) will be shown as text at the control. This can come in handy if you don’t want to use the ValidationPanel for validation messages that span several properties, but show them in the aggregating ValidationSummary instead.

If you’ve used manual validation with a fake entity that stores the validation messages for you, you can bind the fake entity to ValidationPanel and your data model entity to the wrapped control as before:

<vc:ValidationPanel ValidationSource="{Binding BidValidation.ValidationMessages[NewBid]}">
    <TextBox Text="{Binding Bid.NewBid, Mode=TwoWay}" />
</vc:ValidationPanel>

 

ValidationSummary

The second control of the WinRT XAML Validation library is the ValidationSummary. While the ValidationPanel can be used to show validation messages for a single property, the ValidationSummary is there to show all aggregated validation messages of an entity.

Usage of the ValidationSummary is very easy. Just bind its ValidationSource property to ValidationBindableBase.ValidationMessages.AllMessages, if your entity derives from ValidationBindableBase. Moreover, you can use any ReadOnlyDictionary<string, ReadOnlyCollection<ValidationMessage>> of validation messages for the properties of an entity and bind it to the control. Here’s a simple code example:

<Page x:Class="WinRTXAMLValidation.Demo.MainPage" ...
      xmlns:vc="using:WinRTXAMLValidation.Library.Controls">
    ...
    <vc:ValidationSummary ValidationSource="{Binding Bid.ValidationMessages.AllMessages}" Header="General input errors" />
</Page>

The following picture shows a sample output of the ValidationSummary for a validated entity, including errors and warnings.

There are several properties of the control that can be used to define its behavior:

  • ValidationSource: Dictionary of validation messages that should be shown in the summary. Normally binds to ValidationBindableBase.ValidationMessages.AllMessages.
  • ShowPropertyValidationMessages (default: true): Indicates whether validation messages for single properties should be shown in the summary or not.
  • ShowGroupValidationMessages (default: true): Indicates whether validation messages for property groups should be shown in the summary or not. This can come in handy, if you want to show this information only in ValidationPanel, but not in the ValidationSummary.
  • AffectedPropertyNames: Collection of property names, whose validation messages should be shown in the summary. If no value is given, the validation messages for all properties will be shown.
  • Header: Header text to be shown above the summary. If no value is given, no header will be shown.
  • ShowHeader (default: true): Indicates whether a header will be shown above the summary or not.

 

WinRT XAML Validation library: Manual Validation

Defining validation logic using Data Annotations is the default and recommended way in the WinRT XAML Validation library. But of course there are good reasons that you don’t want to use this approach. For example, you want to have all the validation logic for an entity at a central place or you don’t want your entities to implement ValidationBindableBase or you even don’t have access to the data model entities.

In this case you have the possibility to bypass the validation attributes and the ValidationBindableBase base class for your model entities. You get the flexibility to perform validation for yourself and add validation messages to the storage dictionaries.

Implement ValidationBindableBase

What you need is some entity that implements ValidationBindableBase and thus acts as store for the validation messages. Normally, this would be your „real“ model entity, but you’re able to define a fake entity as well. The only purpose of this entity is to store the validation messages through ValidationBindableBase, so this information can be bound to the UI. In the following example you can see a fake entity AuctionBidValidation that stores the validation messages for the original data model entity AuctionBid. The advantage: you don’t have to change your data model entity to derive from ValidationBindableBase:

public class AuctionBid
{
    public double CurrentBid { get; set; }
    public double NewBid { get; set; }
    public double? MaxNewBid { get; set; }
}

public class AuctionBidValidation : ValidationBindableBase { }

public class MainViewModel : BindableBase
{
    public AuctionBid Bid { get; private set; }
    public AuctionBidValidation BidValidation { get; private set; }
}

The view model contains the „real“ data model entity as well as the validation storage for the entity. Now both properties are exposed and can be bound to the UI. An upcoming blog post will show you how this happens.

Manually add validation messages

After you’ve performed validation for yourself, you can add a new validation message using ValidationBindableBase.ValidationMessages.AddMessage(). There are two overloads of this method: with the first you can add a validation message to a property, with the second you add a validation message for the whole entity. The following code example shows manual validation and adding validation messages manually:

public async Task SendBidAsync(AuctionBid bid, AuctionBidValidation bidValidation)
{
    bidValidation.ValidationMessages.ClearMessages();

    if (bid.MaxNewBid.HasValue && bid.NewBid > bid.MaxNewBid)
    {
        bidValidation.ValidationMessages.AddMessage(
            () => bid.NewBid, ValidationLevel.Error,
            "New bid can not be higher than max new bid.");
    }

    if (bid.NewBid >= bid.CurrentBid * 100)
    {
        bidValidation.ValidationMessages.AddMessage(
            () => bid.NewBid, ValidationLevel.Warning,
            "Your bid surpasses the current bid by a 100 times.");
    }

    if (bid.NewBid <= await this.GetCurrentBidAsync(bid))
    {
        bidValidation.ValidationMessages.AddMessage(
            ValidationLevel.Error, "Your bid has been surpassed.");
    }

    ...
}

Look how the original data model entity and the fake validation entity work together to get the validation information. The fake validation entity just stores the validation messages. The following screenshot shows how those validation messages will be shown on the UI:

 

Clearing old validation messages

Before you start a new validation, make sure to clear the old validation messages by using the ValidationBindableBase.ValidationMessages.ClearMessages() method as shown in the example above.

 

And a final hint: When you use manual validation and leave the validation attributes behind, you loose the ability of automatic implicit and explicit user input validation. You should be aware of this, when you decide which validation option is the best for you. Of course you can mix automatic and manual validation, performing manual validation only in critical situations like saving an entity.

WinRT XAML Validation library: Implicit and Explicit Validation Execution

Now that you have defined all your validation attributes on your model classes, you want to perform validation to detect if your entity is valid or not. Here you can go two ways with the WinRT XAML Validation library: implicit validation validates your entity automatically when properties change, while with explicit validation you call a function to perform the validation.

Validatable model classes

A prerequisite to perform validation on a model entity with the WinRT XAML Validation library is that your model class derives from the ValidationBindableBase class. This class stores all validation messages for you and is able to perform validation on your entity:

public class AuctionBid : ValidationBindableBase { ... }

Implicit Validation Execution

Implicit validation is triggered automatically when an entity property changes, thus the setter is called. Implicit validation is an opt-in mechanism, meaning that you have to activate this functionality first before your entity gets validated. Just set the IsImplicitValidationEnabled property on your model entity that derives from ValidationBindableBase to true:

var bid = new AuctionBid();
bid.IsImplicitValidationEnabled = true;

If you want to disable implicit validation execution temporarily, you are able to set IsImplicitValidationEnabled=false at any time. Finally for implicit validation to fire, you have to implement your model properties explicitly with a backing field. In the property’s setter, you’ve to call the SetProperty() method from the base class ValidationBindableBase, which performs the validation of the matching attributes for the property:

[ValidateAgainstMaxBid(ShowMessageOnProperty = false)]
public class AuctionBid : ValidationBindableBase
{
    private double newBid;

    [Range(0, double.MaxValue, ErrorMessage = "Value must be greater 0.")]
    [ValidateGreaterCurrentBid]
    public double NewBid
    {
        get { return this.newBid; }
        set { base.SetProperty(ref this.newBid, value); }
    }

    ...
}

Explicit Validation Execution

In many situations you don’t want to execute implicit validation everytime a property changes. For this case the WinRT XAML Validation library gives you the ability to execute validation explicitly by calling the ValidationBindableBase.ValidateAsync() method. Because ValidationBindableBase will be the base class for your model entities, that means calling the method on the entity itself:

var bid = new AuctionBid();
...
bool isValid = await bid.ValidateAsync();

The method returns true if the entity is valid and false otherwise. It’s async because of the async validation ability of attributes from the WinRT XAML Validation library.

WinRT XAML Validation library: Async Validation Attributes

Last posts have shown how basic validation attributes and property-group based validation attributes can be used to define custom validation logic, that goes beyond the default capabilities of Data Annotations. There’s another validation attribute base class in the WinRT XAML Validation library and that’s the AsyncValidationAttribute and its sister, the AsyncGroupValidationAttribute.

Both attributes define the abstract method IsValidAsync(), which you can use in your derived validation attribute classes to perform asynchronous operations during validation. The following code gives an example for the AsyncValidationAttribute class:

[AttributeUsage(AttributeTargets.Property, AllowMultiple = false, Inherited = true)]
public sealed class ValidateActualCurrentBidAttribute : AsyncValidationAttribute
{
    protected override async Task<ValidationResult> IsValidAsync(object value, ValidationContext validationContext)
    {
        var newBid = (double)value;
        var auctionBid = (AuctionBid)validationContext.ObjectInstance;
            
        var service = new AuctionService();
        var currentBid = await service.GetCurrentBidAsync(auctionBid);

        return (newBid > auctionBid.CurrentBid && newBid <= currentBid)
            ? new ValidationResult("Your bid has been surpassed.")
            : ValidationResult.Success;
    }
}

This sample async validation attribute calls the async service method AuctionService.GetCurrentBidAsync() to retrieve actual data from a server. It gets await’ed and returns the validation result after the async operations has returned. Thus you’re able to define custom validation logic in our asynchronous app world.

AsyncGroupValidationAttribute is a specialization of AsyncValidationAttribute, its usage doesn’t differ, so I will not show it here. The usage of an async validation attribute equals the usage of any other attribute on your entity and you’re able to use the functionality of the ExtendedValidationAttribute.

public class AuctionBid : ValidationBindableBase
{
    [ValidateActualCurrentBid(UseInImplicitValidation = false)]
    public double NewBid { ... }
}

WinRT XAML Validation library: Property-Group Validation Attributes

All predefined validation attributes in the System.ComponentModel.DataAnnotations namespace can be used to annotate a single property of an entity. So they cannot be used for validation that spans multiple properties.

For this case, the WinRT XAML Validation library comes with the GroupValidationAttribute base class. Its member CausativeProperties can be used to define properties, which cause the validation to run, when their values are changing. With the member AffectedProperties you can set properties, that will be marked invalid when the validation of a property from the CausativeProperties group fails.

The following code gives an example of a concrete validation class that extends the GroupValidationAttribute base class. CausativeProperties equals AffectedProperties, thus the group of properties that cause the validation equals the group of properties that are affected by the validation:

[AttributeUsage(AttributeTargets.Class, AllowMultiple = false, Inherited = true)]
public sealed class ValidateAgainstMaxBidAttribute : GroupValidationAttribute
{
    protected override IEnumerable<Expression<Func<object>>> AffectedProperties
    {
        get
        {
            AuctionBid entity = null;
            return new Expression>[]
                {
                    () => entity.NewBid,
                    () => entity.MaxNewBid
                };
        }
    }

    protected override IEnumerable<Expression<Func<object>>> CausativeProperties
    {
        get { return this.AffectedProperties; }
    }

    protected override ValidationResult IsValid(object value, ValidationContext validationContext)
    {
        var auctionBid = (AuctionBid)validationContext.ObjectInstance;

        return auctionBid.MaxNewBid.HasValue && auctionBid.NewBid > auctionBid.MaxNewBid.Value
            ? new ValidationResult("New bid must not be greater than highest bid.")
            : ValidationResult.Success;
    }
}

This group validation property can now be used to annotate the whole model entity on class level:

[ValidateAgainstMaxBid(ShowMessageOnProperty = false)]
public class AuctionBid : ValidationBindableBase
{
    public double CurrentBid { ... }
    public double NewBid { ... }
    public double? MaxNewBid { ... }
}

Additionally, the GroupValidationAttribute class derives from the ExtendedValidationAttribute class, so you’re able to use additional functionality brought by the ValidationLevel,  ShowMessageOnProperty and ShowMessageInSummary properties and others.

WinRT XAML Validation library: Basic Validation Attributes

Validation in the WinRT XAML Validation library is mainly based on .NET Data Annotations from the System.ComponentModel.DataAnnotations namespace. Here you can find several attributes, that you can attach to your entities and its properties. This annotates them with additional information/metadata, which’s evaluated elsewhere in your code or by the .NET framework.

WPF, Silverlight and e.g. ASP.NET MVC can evaluate those attributes automatically to display further information for an entity like a property label, etc.. And you can define validation logic with Data Annotations on your entity, which gets evaluated and presented to the user when the entity is validated.

ValidationAttribute

The WinRT XAML Validation library uses the Data Annotations approach as well to define validation logic on model entities. First you can use the already defined validation attributes from the System.ComponentModel.DataAnnotations namespace: RangeAttribute, RegularExpressionAttribute, RequiredAttribute, StringLengthAttribute, CustomValidationAttribute. All of those predefined attributes implement the ValidationAttribute base class. You can derive from this class as well to implement validation attributes with your encapsulated custom validation logic, for example:

[AttributeUsage(AttributeTargets.Property, AllowMultiple = false, Inherited = true)]
public sealed class ValidateGreaterCurrentBidAttribute : ValidationAttribute
{
    protected override ValidationResult IsValid(object value, ValidationContext validationContext)
    {
        var newBid = (double?)value;
        var auctionBid = (AuctionBid)validationContext.ObjectInstance;

        return newBid.HasValue && newBid.Value <= auctionBid.CurrentBid
            ? new ValidationResult("Value must be greater than current bid")
            : ValidationResult.Success;
    }
}

Now you can easily decorate your model entities with this attribute:

public class AuctionBid : ValidationBindableBase
{
    private double currentBid;
    private double newBid;
    private double? maxNewBid;

    public double CurrentBid
    {
        get { return this.currentBid; }
        set { this.SetProperty(ref this.currentBid, value); }
    }

    [Range(0, double.MaxValue, ErrorMessage = "Value must not be negative")]
    [ValidateGreaterCurrentBid]
    public double NewBid
    {
        get { return this.newBid; }
        set { this.SetProperty(ref this.newBid, value); }
    }

    [ValidateGreaterCurrentBid]
    public double? MaxNewBid
    {
        get { return this.maxNewBid; }
        set { this.SetProperty(ref this.maxNewBid, value); }
    }
}

 

ExtendedValidationAttribute

With the abstract ExtendedValidationAttribute class there’s another base validation attribute in the WinRT XAML Validation library that extends the functionality of the ValidationAttribute. Specifically with this base class you can:

  • define a level for the validation message (Warning or Error)
  • define if the validation message should be shown on the property and in the validation summary on the UI
  • define if the validation attribute should be considered in implicit validation (when a property changes)

For example, a validation level „Warning“ leads to the following output on the UI:

The definition on the entity property (taking a custom validation attribute ValidatePossibleMisentryBid as example) looks as follows:

[ValidatePossibleMisentryBid(ValidationLevel = ValidationLevel.Warning)]
public double NewBid { ... }

Like the ValidationAttribute you can use the ExtendedValidationAttribute as base class for your custom validation attributes.

WinRT XAML Validation library: Getting Started

This little blog posts describes how you can include the WinRT XAML Validation library in your project and get it to work.

Download

First go to the WinRT XAML Validation Codeplex project page and download the latest bits. The download package includes the sources of the library as well as a demo project (Windows Store App), which showcases many of the concepts and features of the library:

 

Usage by Source

To use the WinRT XAML Validation library, you have two possibilities. The first one is to include the library sources. To do this, copy the WinRTXAMLValidation.Library project to your app’s solution folder and add the existing WinRTXAMLValidation.Library.csproj project to your solution.

Add a reference to the library project everywhere you want to use the validation functionality. To get the UI control to work properly, you have to include the ValidationStyles.xaml file from the Styles folder of the library in your project. There are two different ways to do this:

  • Copy the ValidationStyles.xaml file to your Windows Store App project and reference it as ResourceDictionary in your App.xaml.
  • Add the ValidationStyles.xaml file as link in your Windows Store App project and reference it as ResourceDictionary in your App.xaml.

You’re free to choose from these approaches. Go the „copy way“ if you want to adapt the validation styles to your needs. Go the „add as link“ way if you simply want to use the UI controls as they are.

Usage by Assembly

If you don’t want to include the library’s sources to your solution, you can just add the compiled assembly as reference. To do this, first compile the WinRT XAML Validation library as Debug or Release. Copy the output assembly to your solution and reference it in every project where you want to use the validation functionality.

Copy the ValidationStyles.xaml file from the Styles folder of the library to your Windows Store App project and reference it as ResourceDictionary in your App.xaml.

Introducing the WinRT XAML Validation library

In this article I’m going to introduce „WinRT XAML Validation“, a library that brings consistent validation of user input to WinRT/C#/XAML apps. Upcoming blog posts will cover several aspects of the library in depth.

Prologue

I like WinRT. I like its approach of bringing common functionality to very different languages. But WinRT is not perfect. At least in „version 1“ (shipped with Windows 8 ) it has several shortcomings in various parts.

One of those shortcomings is user input validation in C#/XAML Windows Store Apps. Of course there are Data Annotations in .NET 4.5 for WinRT and the ValidationAttribute, also the INotifyDataErrorInfo interface is available. But what’s missing is the whole UI stuff. There are no UI controls or attributes on existing UI controls to show errors for validated properties. Hence at the moment you’re forced to execute validation manually and react accordingly to update the UI state.

„WinRT XAML Validation“ library

I’ve been unsatisfied with this lack of support for complete user input validation in WinRT/XAML. Thus a colleague and I developed a library, that fills the missing pieces and goes beyond trivial validation tasks. We needed comfortable and extended validation functionality for one of our development projects and now we want to make the resulting bits available as easy-to-use library.

WinRT XAML Validation has a project page on Codeplex and is free-to-use under the Ms-PL license.

>> Codeplex Project Page <<

Functionality Overview

The WinRT XAML Validation library is aimed to give developers a consistent, flexible and easy-to-use library to perform user input validation in WinRT/XAML apps. Developers should get a generic approach, that guides them through all steps of validating user input and performs the work for them.

With the WinRT XAML Validation library, you get a whole bunch of functionality, including:

  • Validation Attributes: Define custom validation logic with Data Annotations on your model entities. The library contains extended base attributes for validation with support of warnings/errors, async validation and validation logic, that spans more than one property.
  • Implicit Validation Execution: Use the ValidationBindableBase class on your model entities to perform validation. You can opt-in to let validation execute automatically when a entity property changes (implicit validation).
  • Explicit Validation Execution: Instead of running validation everytime a property changes on your model entities, you can call the ValidationBindableBase.ValidateAsync() method explicitly to validate the defined validation attributes.
  • Manual Validation: Besides the use of validation attributes to define validation logic, you can easily perform custom validation logic and add corresponding validation messages to a Dictionary, using the ValidationBindableBase.ValidationMessages.Add() method. The provided UI controls will update themselves automatically.
  • Validation UI Controls: There are two easy-to-use XAML UI controls to show validation messages. First there is the ValidationPanel control that wraps a control whose bound property should be validated (for example a TextBox). If validation fires for the property, the ValidationPanel will show a red border (orange for warnings) and optionally the validation message. More than one validation message is supported. The second control is the ValidationSummary, which can show aggregated validation messages for a whole form and its bound entity. Both controls update immediately when validation messages change, even in async scenarios.

Credits

I want to give credit to the Patterns and Practices group at Microsoft for developing and releasing the Prism for Windows Runtime library (f.k.a. Kona). It’s an awesome library that adds much value to the development of WinRT apps and I encourage you to check it out if you’re serious about Windows 8 business app development.

Basic ideas and concepts for the WinRT XAML Validation library are borrowed from Prism for WinRT. For example, the BindableValidator class has been taken over, but includes much more functionality now. While Prism for WinRT comes with some validation bits, WinRT XAML Validation comes with a more complete approach to user input validation.

WinRT/C#: DataPackage and custom objects

Ok, after some intensive implementation weeks, I think I should blog some articles about tips’n’tricks when developing Windows 8 Metro apps with WinRT and C#. This first article is about the DataPackage class. You need to get in touch with this class when you want to exchange data from app to app by implementing the Share contract or when you want to implement custom drag&drop functionality in your own app. DataPackage has built-in functionality for exchanging a variety of document formats: Bitmap, Html, Rtf, Text, Uri and StorageItems (files and folders).

Especially in the drag&drop scenario these standard data formats often aren’t enough. Imagine a grouped ListView or GridView. Because of the grouping you have to implement drag&drop manually in WinRT Metro apps. Now if you want to exchange data between the drag event and the drop event, you often want to fill the DataPackage with data objects of your custom data types. Unfortunately, that’s not possible out of the box with the DataPackage. Only scalar types, implementations of IRandomAccessStream or IStorageItem and IUri are supported.

So, there’s no possibility to write the real instances of your objects into a data package in the drag event and read them in the drop event. But here’s the solution: serialization and writing into an IRandomAccessStream. While you serialize and deserialize your object, you won’t get the original instance in the drop event, but if it’s ok for you, then this method works fine.

I’ve written some extensions for DataPackage and IRandomAccessStream, that you can use to get this task really quickly done:

public static class IRandomAccessStreamExtensions
{
    public static async void WriteObject<T>(this IRandomAccessStream stream, T obj)
    {
        var serializer = new DataContractSerializer(typeof(T));
        serializer.WriteObject(stream.AsStreamForWrite(), obj);
    }

    public static T ReadObject<T>(this IRandomAccessStream stream)
    {
        var serializer = new DataContractSerializer(typeof(T));
        return (T)serializer.ReadObject(stream.GetInputStreamAt(0).AsStreamForRead());
    }
}

public static class DataPackageExtensions
{
    public static void SetObject<T>(this DataPackage data, string formatId, T obj)
    {
        var randomAccessStream = new InMemoryRandomAccessStream();
        randomAccessStream.WriteObject(obj);
        data.SetData(formatId, randomAccessStream);
    }

    public static async Task<T> GetObjectAsync<T>(this DataPackage data, string formatId)
    {
        var randomAccessStream = await data.GetView().GetDataAsync(formatId) as IRandomAccessStream;
        if ((randomAccessStream == null) || (randomAccessStream.Size == 0) || !randomAccessStream.CanRead)
        {
            return default(T);
        }

        return randomAccessStream.ReadObject<T>();
    }
}

Now you’re able to use the SetObject() and GetObjectAsync() extension methods on DataPackage to easily store and retrieve items to/from a data package in the drag/drop event or in your source/target implementation of the Share contract:

private void OnGridViewDragItemsStarting(object sender, DragItemsStartingEventArgs e)
{
    e.Data.SetObject("MyDataTypeList", e.Items.OfType<MyDataType>().ToList());
}

private async void OnGridViewDrop(object sender, DragEventArgs e)
{
    var myDataItems = await e.Data.GetObjectAsync<List<MyDataType>>("MyDataTypeList");
}

The string parameter „formatId“ specifies the identifier for your data format in the DataPackage. Note how the IRandomAccessStreamExtensions methods use the DataContractSerializer for serialization and deserialization. This means that your data class has to be decorated with the DataContract and DataMember attributes to specify which data should be serialized.

I hope you can use this little helper in some cases when working with the DataPackage for sharing data. In some next blog post I want to show you how to manually implement drag&drop in your grouped ListView and GridView in WinRT Metro apps. Stay tuned!

kick it on DotNetKicks.com

Why Windows Phone needs WinRT

Pretty provoking title, uhm? 😉

But pretty fitting for me, as well! Some days ago I posted a tweet saying that I believe Windows Phone needs an adoption of WinRT:

In this article I want to go into more detail and explain why I think this is true.

Windows 8 and WinRT

First things first: Windows 8 is coming around the corner, believed to be published in late summer or autumn 2012 (btw: what do you think about „Windows Metro“ as name for the final? ;-)). The beta („Consumer preview“) will come soon at the end of February. Win8 employs a new programming model for a new kind of apps: „Metro-style apps“, that are touch-first. Metro-apps can run on either Intel or ARM hardware and thus span functionality from tablet over notebooks/ultrabooks to desktop PCs. The old Windows desktop remains as part of the „Intel version“ of Windows 8, but will likely not run on ARM.

The Metro-app programming model comes with a core component called WinRT (Windows Runtime). That’s kind of Win32 API for the new (Metro) world. It’s an integral part of the operating system core and not an on-top layer like Silverlight or .NET. Instead it’s native and exposes OS functionality to developers. While calling Win32 API from managed code involves things like P/Invoke, WinRT components can be called in natural way from every supported language. Metro-apps on top of WinRT can be built with XAML/C#, XAML/VB, XAML/C++ or HTML/JavaScript, games are supported through DirectX/C++. That’s a huge deal for developers, who get great flexibility to develop Metro apps. Furthermore, they can author their own WinRT components in C#/VB or C++ and use them from every supported WinRT language, even JavaScript. Thus for example they are able to implement a WinRT component in C# which holds the core business logic and use this component naturally from a JavaScript Metro app. Way cool!

Windows Phone till now

Ok, let’s come to Windows Phone. While it has great reviews (I use it as primary smartphone system, prefering it over my iPhone 4), Windows Phone is still falling behind in sense of marketshare. Approx. 2% (or less) in the US is not where Microsoft believed to be after 15 months. There is a lot of buzz and fanboy war on each side of the smartphone community why this situation is real and if it will change. For sure, with Nokia Microsoft now has a superb partner for developing phones which attract people by design and functionality, but are manufacturers the real problem?

For me, Windows Phone faces 2 main problems:

  • Hardware diversity: Consumers want to have a choice. They want to choose between budget phones over midrange devices up to the so-called „superphones“ on the market. Android has a great diversity in phone hardware and it sells really well. When you look at Windows Phone, you can’t see much diversity. Microsoft prescribes a relatively strict corset for hardware partners in terms of screen resolution, CPU, RAM, internal memory, interfaces, cameras, sensors and so on. Windows Phone devices don’t differ very much. And I would say the Nokia Lumia series are the first (Elop: „real“) Windows Phones that can attract people by design. For sure, diversity has its benefits and downsides. Developers don’t love it – no consistency means you must develop for the lowest common denominator or accept that your app doesn’t run everywhere without compromises. Android faces this problem and that’s one point why the Apple app ecosystem is way more attractive to users. It’s also why I think it’s a good choice from Microsoft to ensure consistency of the Windows Phone hardware, as well. But they have to loosen the rules! Budget phones need other hardware than superphones and in terms of market share Microsoft should take this into count. I know: practically specs don’t mean much for the overall experience. Look at Android: multi-core (handwarmer) CPUs and headspinning screen resolutions don’t make a good experience, in fact they can be rather harmful for the user experience. But customers aren’t really aware of this and that makes Android phones attractive. Microsoft could be the first to integrate the advantages of both the iPhone and Android phones – let’s hope they take the chance!
  • Apps: For me the app problem is of equal or higher value to the hardware diversity. While the Windows Phone Marketplace lists ~60.000 apps and is steadily growing, the main target platforms for app developers remain Android and iOS. Small companies are thinking twice if they should invest into a 2%-market-share-platform or just go with 90% on 2 other platforms. It’s kind of a doom loop: customers aren’t buying Windows Phones because relevant apps are missing… developers don’t make apps because customers are missing. While 60.000 apps sounds well and the marketplace is rapidly growing, many really important apps from Android/iOS are missing. Apps that people are asking for and which make people decide for one platform or the other. App statistics don’t say anything about the quality of the apps and in my experience Windows Phone is massively falling behind the other platforms, especially iOS.

WinRT on Windows Phone? Could this be? How could it help?

The first thing I thought when I saw the BUILD keynote and the introduction of WinRT was: ok, that’s cool… the next step should be to bring this to Windows Phone. In fact, there are rumors that Microsoft plans to swap the current Windows CE kernel from Windows Phone with the NT/MinWin kernel of Windows 8 in Windows Phone 8, codename „Apollo“, which is supposed to be released in autumn 2012.

What implications would come with such a step? First, it would be important in terms of inside development of Windows at Microsoft. One codebase means less costs and while Windows 8 is made for mobile devices like tablets as well, it would definitely make sense to have the same core OS functionality on Windows Phone.

Second, wouldn’t this consequently bring WinRT to Windows Phone? In my mind, in the mid-term this could ultimately happen. As written before and stated by Microsoft several times: WinRT is an integral part of the core operating system. Now if you get the core OS to another platform, what will happen to WinRT? In my mind, it would become part of the other platform (Windows Phone) as well! Now of course, WinRT isn’t part of MinWin (the kernel, read: the core of the core OS). But with MinWin in place, closing the gap to WinRT would be much easier. Perhaps it will not bring the full WinRT that you see for Windows 8, perhaps there are additional/adopted features and controls which are better suited for phones. But it would have the main APIs and main functionality (imho ~80% could be a level).

I believe that having the Windows kernel and WinRT on Windows Phone would give the platform an extreme boost. Let’s take a side look at Android and iOS for one moment: here you have one platform for consumers and developers that spans phones and tablets. A clear advantage of those platforms! WinRT could do the same for the Windows platform: phones and tablets… but in addition: notebooks, ultrabooks, desktop PCs – you get the point! It would be an extremely high opportunity for app developers. It would break down a wall for developers of Windows 8 Metro-apps to bring these apps on the same technology stack and the same languages to Windows Phone. Imagine: with WinRT on Windows Phone it would be possible to write HTML5/JS apps as well as XAML/C# apps and native XAML/C++ apps. Any doubts in the impacts to the Windows Phone ecosystem?

Silverlight on Windows Phone

Ok, I think that’s a pretty cool imagination. But wait: aren’t there 60.000 Silverlight/XNA apps on the Windows Phone Marketplace? What about those apps? Cut off and forget?

I believe there is another possibility. I think Microsoft could manage to build up a kind of „compatibility layer“ in parallel or on top of WinRT for Windows Phone to ensure backward compatibility, at least for a while. This layer could contain Silverlight and XNA as programming models in addition to WinRT and its supported languages. I think it will be hard if not impossible for Microsoft to develop such a thing without changing API behaviors and without cutting functionality. On the other side: what’s the option? I don’t think it’s a practicable way to cut all Windows Phone apps and scare off all current Windows Phone developers and consumers.

 

What do you think? Hot or not? Possible or insane? Call me a fool, I’m accustomed to this 😉

kick it on DotNetKicks.com