XAML Code Generation Markup Language

I have a very simple working prototype of the XAML Code Generator that I was discussing in my last post. It turns out that it’s totally possible! So for example if you have XAML that looks like this:

<test:Parent xmlns=”clr-namespace:Xcgml;assembly=Xcgml”

     xmlns:test=”clr-namespace:Xcgml.Testing.Mock;assembly=Xcgml.Testing” >

     <test:Child Data=”{Binding}” />

</test:Parent>

What we have here are two classes that inherit from GeneratorElement (which inherits from DependencyObject) and one other class called Binding that inherits from MarkupExtension. After running this XAML through the XamlReader, you end up with deserialized objects.

public static GeneratorElement Load(string xaml)

{

    using (TextReader reader = new StringReader(xaml))

    {

        using (XmlReader xmlReader = XmlReader.Create(reader))

        {

            ParserContext context = new ParserContext();

            context.XmlLang = “xcgml”;

 

            return (GeneratorElement)System.Windows.Markup.XamlReader.Load(xmlReader);

        }

    }    

}

The interesting thing is the binding. It turns out that there is no automatic system for resolving bindings like I had hoped but fortunately it’s possible to implement your own. It seems like a lot of what we get seemingly for free in WPF sits on top of the FrameworkElement class. The framework element class is not available for this scenario; I must implement my own elements on top of DependencyObject. However it wasn’t very hard to figure out how to propagate the DataContext and how to refresh values based on bindings. Here is an example unit test:

[TestMethod]

public void Simple1()

{

    Parent element = XamlReader.Load(Resources.Simple1) as Parent;

    Assert.IsNotNull(element);

    Assert.IsNotNull(element.Content);

    Assert.IsInstanceOfType(element.Content, typeof(Child));

 

    string expected = “success”;

    element.DataContext = expected;

    string actual = (element.Content as Child).Data;

 

    Assert.AreEqual(expected, actual);

}

Notice when I set the element.DataContext the child’s Data property will change because of the binding specified! I am planning on adding these features soon:

<!–[if !supportLists]–>·         <!–[endif]–>StaticResource binding – so you can bind to values in resources

<!–[if !supportLists]–>·         <!–[endif]–>Templates – so you can customize standard objects

<!–[if !supportLists]–>·         <!–[endif]–>ItemsControl – so you can have multiple nested controls

<!–[if !supportLists]–>·         <!–[endif]–>Repeat control

<!–[if !supportLists]–>·         <!–[endif]–>If control

 

Download the Source

<!–[if !supportLists]–>·         <!–[endif]–>Xcgml-20080731.zip (17.2 KB)

Author: justinmchase

I'm a Software Developer from Minnesota.

Leave a Reply

%d bloggers like this: