<?xml version="1.0" encoding="UTF-8"?>
<?xml-stylesheet type="text/xsl" media="screen" href="/~d/styles/rss2full.xsl"?><?xml-stylesheet type="text/css" media="screen" href="http://feeds.feedburner.com/~d/styles/itemcontent.css"?><rss xmlns:dc="http://purl.org/dc/elements/1.1/" xmlns:slash="http://purl.org/rss/1.0/modules/slash/" xmlns:wfw="http://wellformedweb.org/CommentAPI/" xmlns:feedburner="http://rssnamespace.org/feedburner/ext/1.0" version="2.0"><channel><title>Christopher Bennage</title><link>http://devlicious.com/blogs/christopher_bennage/default.aspx</link><description>&lt;div style="float:left;"&gt;Our &lt;a href="http://www.amazon.com/gp/product/0672329859?&amp;amp;camp=212361&amp;amp;linkCode=wey&amp;amp;tag=bluspiconinc-20&amp;amp;creative=380733"&gt;WPF book&lt;/a&gt; is now available!&lt;/div&gt;
&lt;div style="float:right;"&gt;follow &lt;a href="http://twitter.com/bennage"&gt;@bennage&lt;/a&gt; on Twitter!&lt;/div&gt;
&lt;div style="clear:both;"&gt;
&amp;nbsp;
&lt;/div&gt;
</description><dc:language>en</dc:language><generator>CommunityServer 2008.5 SP1 (Build: 31106.3070)</generator><atom10:link xmlns:atom10="http://www.w3.org/2005/Atom" rel="self" href="http://feeds.feedburner.com/ChristopherBennage" type="application/rss+xml" /><item><title>One day with Balsamiq Mockups: a review</title><link>http://feedproxy.google.com/~r/ChristopherBennage/~3/2fyhWqW8Clo/one-day-with-balsamiq-mockups-a-review.aspx</link><pubDate>Fri, 19 Jun 2009 04:03:00 GMT</pubDate><guid isPermaLink="false">40756a8b-6212-4073-9d98-6c26781577de:47989</guid><dc:creator>Christopher Bennage</dc:creator><slash:comments>6</slash:comments><wfw:commentRss>http://devlicious.com/blogs/christopher_bennage/rsscomments.aspx?PostID=47989</wfw:commentRss><comments>http://devlicious.com/blogs/christopher_bennage/archive/2009/06/19/one-day-with-balsamiq-mockups-a-review.aspx#comments</comments><description>&lt;p&gt;We’ve just started a new Silverlight project and since &lt;strike&gt;our&lt;/strike&gt; &lt;em&gt;the&lt;/em&gt; &lt;a title="if you don&amp;#39;t believe, just ask him!" href="http://ayende.com/about-me.aspx"&gt;UI guy&lt;/a&gt; is not on site with us, I ended up with the task of producing screen mockups. Some interest was expressed in using &lt;a href="http://www.balsamiq.com/"&gt;Balsamiq Mockups&lt;/a&gt;, and this seemed like a good time to really take it for a&amp;#160; test drive.&lt;/p&gt;  &lt;h3&gt;What does it do?&lt;/h3&gt;  &lt;p&gt;Balsamiq is a tool for quickly authoring mockups of applications and websites. My favorite tool for doing mockups is pencil and paper (turns out that it’s really, really good). However, we needed something that we could readily show during a review meeting and my sketches don’t photocopy well.&lt;/p&gt;  &lt;p&gt;Nevertheless, I did my brainstorming on paper and I used it for my first round of reviews with the team. This left me with about a dozen pages storyboarding the core of our application. &lt;/p&gt;  &lt;p&gt;After the first review, I began recreate it with Balsamiq.&lt;/p&gt;  &lt;p&gt;In Balsamiq you start with a blank, gridded canvas and drag various UI elements from a library onto the canvas. It reminds me of Visio a bit, but without so much pain. All of the elements are styled to look like hand-drawn. This is important because it prevents anyone from assuming that the application is “done” when you’re just presenting mockups.&lt;img style="border-bottom:0px;border-left:0px;display:inline;margin-left:0px;border-top:0px;margin-right:0px;border-right:0px;" title="making a web page with Balsamiq" border="0" alt="making a web page with Balsamiq" src="http://devlicious.com/cfs-file.ashx/__key/CommunityServer.Blogs.Components.WeblogFiles/christopher_5F00_bennage/Untitled1_5F00_016725E9.jpg" width="646" height="667" /&gt; &lt;/p&gt;  &lt;p&gt;The elements in Balsamiq are impressively intelligent. Most elements allow you to type in some content and they react intuitively to that content. I was amazed a couple of time at how smartly they responded. Balsamiq ships with about 75 elements in its library and there are more &lt;a href="http://www.mockupstogo.net/"&gt;being posted&lt;/a&gt; all the time. You cannot really extend the library yourself however, though you can incorporate your own images.&lt;/p&gt;  &lt;p&gt;Each mockup screen is a single file. They are XML so it’s source control friendly. If you are mocking up an entire application (like I was) you can link the files together. Many of the elements have a link property that you can point to any other Balsamiq files in the same directory. Once you’ve linked up some files, you can “run” your mockups in presentation mode. This allows you to navigate around the application and toggle annotations (like the sticky note in my screen shot). The presentation mode is really cool.&lt;/p&gt;  &lt;h3&gt;Should you buy it?&lt;/h3&gt;  &lt;p&gt;I think that mocking up the UI is a very useful exercise. It helps to expose the behavior of the application that you are going to build and surfaces many insights into what it &lt;em&gt;really&lt;/em&gt; needs to do. I still prefer to use paper and pencil for the initial pass. However, I found that following this up with Balsamiq forced me to think through the entire flow of my appplication. My paper storyboards had holes in them that I did not realize until I attempted to express them in Balsamiq.&lt;/p&gt;  &lt;p&gt;The reviewers were really excited to see the Balsamiq mockups and being able to walk them through the application was a definite plus for them. The tool is easy to use. I would say that any &lt;strike&gt;designer&lt;/strike&gt; developer doing UI work should be using a tool like Balsamiq.&lt;/p&gt;  &lt;p&gt;What it offers for $79 is really hard to beat. Admittedly, I don’t know what other tools are out there and how they compare. By itself, I think it definitely worth it for anyone doing UI work.&lt;/p&gt;  &lt;p&gt;Of course, there is SketchFlow. It is coming. I think that SketchFlow looks very promising, especially for us XAML guys, but it’s not available yet. I’ll let you know what I think about the overlap once I get a change to actually use SketchFlow.&lt;/p&gt;  &lt;h3&gt;Little Things&lt;/h3&gt;  &lt;p&gt;I had a couple of annoyances that are worth pointing out. &lt;/p&gt;  &lt;p&gt;First, you cannot create reusable components. For example, I had certain elements of the application that appeared in several places. I had to clone these elements, but when I needed to change them, I had to make the change in each element. (Another reason to start with pencil).&lt;/p&gt;  &lt;p&gt;I think that it would also be nice if there was a “back button” in presentation mode. Within my mockup I had a few screens that you could get too in multiple ways, however I did not have an easy way of returning the the previous screen.&lt;/p&gt;  &lt;p&gt;I also get the impression that the community around Balsamiq likes to poke fun at us PC guys. I smile politely.&lt;/p&gt;  &lt;p&gt;Finally, Balsamiq likes to keep all of the linked files open. You’ll notice an excessive number of tabs on the bottom of the screen shot. Those are all the screens within the application I was mocking. It became a little difficult to find that right one.&lt;/p&gt;  &lt;p&gt;On the whole, Balsamiq is a smart application and I expect to see great things as it matures. Many of its features are intuitive and “just work”, and that’s how I like my software to roll.&lt;/p&gt;  &lt;pre&gt;:-P&lt;/pre&gt;&lt;div style="clear:both;"&gt;&lt;/div&gt;&lt;img src="http://devlicious.com/aggbug.aspx?PostID=47989" width="1" height="1"&gt;&lt;img src="http://feeds.feedburner.com/~r/ChristopherBennage/~4/2fyhWqW8Clo" height="1" width="1"/&gt;</description><category domain="http://devlicious.com/blogs/christopher_bennage/archive/tags/development+tools/default.aspx">development tools</category><category domain="http://devlicious.com/blogs/christopher_bennage/archive/tags/UI/default.aspx">UI</category><category domain="http://devlicious.com/blogs/christopher_bennage/archive/tags/UX/default.aspx">UX</category><feedburner:origLink>http://devlicious.com/blogs/christopher_bennage/archive/2009/06/19/one-day-with-balsamiq-mockups-a-review.aspx</feedburner:origLink></item><item><title>The Influence of MVC on my WPF</title><link>http://feedproxy.google.com/~r/ChristopherBennage/~3/iMG4OD_4kvA/the-influence-of-mvc-on-my-wpf.aspx</link><pubDate>Wed, 06 May 2009 19:48:01 GMT</pubDate><guid isPermaLink="false">40756a8b-6212-4073-9d98-6c26781577de:46528</guid><dc:creator>Christopher Bennage</dc:creator><slash:comments>9</slash:comments><wfw:commentRss>http://devlicious.com/blogs/christopher_bennage/rsscomments.aspx?PostID=46528</wfw:commentRss><comments>http://devlicious.com/blogs/christopher_bennage/archive/2009/05/06/the-influence-of-mvc-on-my-wpf.aspx#comments</comments><description>&lt;p&gt;I was introduced to MVC as a pattern for Web development through &lt;a href="http://www.castleproject.org/monorail/" target="_blank"&gt;Castle MonoRail&lt;/a&gt;. From there I studied a bit of &lt;a href="http://rubyonrails.org/" target="_blank"&gt;Ruby on Rails&lt;/a&gt; (not enough) as well as the general philosophy of &lt;a href="http://www.37signals.com/" target="_blank"&gt;37signals&lt;/a&gt;.&lt;/p&gt;  &lt;p&gt;As I mentioned before, I thought I was moving away from Web development. However, the dive into ASP.NET MVC that &lt;a title="Silver Arcade, a free online gaming community" href="http://www.silverarcade.com/" target="_blank"&gt;Silver Arcade&lt;/a&gt; brought about has roped me back in.&lt;/p&gt;  &lt;p&gt;My work during the day (and some nights too) is still WPF though. I’ve discovered that MVC thinking has seeped into my WPF development.&lt;/p&gt;  &lt;h3&gt;Convention Over Configuration&lt;/h3&gt;  &lt;p&gt;A characteristic of most MVC frameworks is &lt;a href="http://en.wikipedia.org/wiki/Convention_over_Configuration" target="_blank"&gt;Convention Over Configuration&lt;/a&gt;. In short, it means that your “environment” makes assumptions about what you want and that you only need to be explicit about the exceptions.&lt;/p&gt;  &lt;p&gt;A practical example of this is the way that the View for an Action is inferred from the name of the Controller and Action. After creating your Action, you create a folder for the controller and and view that matches the name of the action. It just works. If you need to make exception, you can.&lt;/p&gt;  &lt;h3&gt;An Example in WPF&lt;/h3&gt;  &lt;p&gt;In our WPF development we employ a number of &lt;a title="I strongly dislike the term MVVM." href="http://msdn.microsoft.com/en-us/library/cc707862.aspx" target="_blank"&gt;Separated Presentation&lt;/a&gt; patterns. One of the more common patterns we use is MVP (in particular, the flavor of MVP implemented in &lt;a title="free WPF and Silverlight from the stone" href="http://www.codeplex.com/caliburn"&gt;Caliburn&lt;/a&gt;, which is really Supervising Controller).&lt;/p&gt;  &lt;p&gt;Imagine a simple contact manager application. We can add new contacts, view a list of all contacts, and open individual contacts for viewing or editing. We can open as many individual contacts as we like.&lt;/p&gt;  &lt;p&gt;&lt;img style="border-bottom:0px;border-left:0px;display:inline;margin-left:0px;border-top:0px;margin-right:0px;border-right:0px;" title="mvc" border="0" alt="mvc" src="http://devlicious.com/cfs-file.ashx/__key/CommunityServer.Blogs.Components.WeblogFiles/christopher_5F00_bennage/mvc_5F00_313933F1.png" width="539" height="511" /&gt; &lt;/p&gt;  &lt;p&gt;Let’s say that there are buttons to open up the “Add New” view and “All Contacts” view. We can open an existing contact by double-clicking on them in the “All Contacts” view. &lt;/p&gt;  &lt;p&gt;&lt;img style="border-right-width:0px;margin:0px 8px 0px 0px;display:inline;border-top-width:0px;border-bottom-width:0px;border-left-width:0px;" title="my imaginary solution" border="0" alt="my imaginary solution" align="left" src="http://devlicious.com/cfs-file.ashx/__key/CommunityServer.Blogs.Components.WeblogFiles/christopher_5F00_bennage/56200930845PM_5F00_24D92471.png" width="271" height="341" /&gt;My solution setup for this imaginary (and highly contrived) application might look like this.&lt;/p&gt;  &lt;p&gt;ApplicationPresenter would be the root object of my UI. It would have an ObservableCollection of IPresenter that would be bound to a TabControl in Shell.xaml. Likewise, ApplicationPresenter will have a CurrentPresenter of IPresenter that will be bound to the SelectedItem on the TabControl. &lt;/p&gt;  &lt;p&gt;Shell.xaml is my only window in this example. All of the other views are user controls. I named it “shell” because I think of it as the outermost level of the views. Shell’s data context is set to ApplicationPresenter.&lt;/p&gt;  &lt;p&gt;I’m not going to dive too much deeper into this, because I want to get to my real point.&lt;/p&gt;  &lt;p&gt;My presenters don’t know anything about their views. It’s up to data binding to render each presenter with the correct view. This means that I need to create data templates for each of the presenters. Not such a big deal in a small application, but it can get tedious as the application grows.&lt;/p&gt;  &lt;p&gt;Hmmm… This structure is beginning to look a lot like an MVC app. Perhaps I can have it automatically infer my data templates for me?&lt;/p&gt;  &lt;h3&gt;Some Code&lt;/h3&gt;  &lt;p&gt;Yes we can. Here’s a &lt;em&gt;very naiveté&lt;/em&gt; bit of code that will do just that. It makes some big assumptions:&lt;/p&gt;  &lt;ul&gt;   &lt;li&gt;all of your presenters implement IPresenter &lt;/li&gt;    &lt;li&gt;all of your presenters are in a namespace containing “.Presenters” &lt;/li&gt;    &lt;li&gt;all of your views are in an analogous namespace containing in “.Views” &lt;/li&gt; &lt;/ul&gt;  &lt;p&gt;Again, this is &lt;strong&gt;&lt;em&gt;not&lt;/em&gt;&lt;/strong&gt; production ready code, just my spike to prove the idea works. Please feel free to make suggestions.&lt;/p&gt;  &lt;pre class="c#:nogutter:nocontrols" name="code"&gt;public static class MvpConfiguration
{
    /// &amp;lt;summary&amp;gt;
    /// Creates a set of data templates pair to presenter classes based on naming conventions.
    /// &amp;lt;/summary&amp;gt;
    /// &amp;lt;remarks&amp;gt;If a data template is already present in the resources, then it is skipped.&amp;lt;/remarks&amp;gt;
    /// &amp;lt;param name=&amp;quot;resources&amp;quot;&amp;gt;The ResourceDictionary that the data templates for the views will be added to.&amp;lt;/param&amp;gt;
    public static void InferViewsFromPresenters(ResourceDictionary resources)
    {
        var lookup = MatchPresentersToViews();

        foreach (var pair in lookup)
        {
            var template = CreateDataTemplate(pair.Value, pair.Key);
            if (resources.Contains(template.DataTemplateKey)) continue;
            resources.Add(template.DataTemplateKey, template);
        }
    }

    private static Dictionary&amp;lt;Type, Type&amp;gt; MatchPresentersToViews()
    {
        var presenters = from type in Assembly.GetExecutingAssembly().GetTypes()
                         where typeof (IPresenter).IsAssignableFrom(type)
                         select type;

        var first = presenters.FirstOrDefault();
        if (first == null) throw new Exception(&amp;quot;I expected to find at least one presenters!&amp;quot;);

        string viewNamespace = first.Namespace
            .Replace(&amp;quot;.Presenters&amp;quot;, &amp;quot;.Views&amp;quot;);
        viewNamespace = viewNamespace.Substring(0, viewNamespace.IndexOf(&amp;quot;.Views&amp;quot;)+6);
        //yeah, that was hackish

        var views = from view in Assembly.GetExecutingAssembly().GetTypes()
                    where !string.IsNullOrEmpty(view.Namespace)
                          &amp;amp;&amp;amp; view.Namespace.StartsWith(viewNamespace)
                    select view;

        var table = new Dictionary&amp;lt;Type, Type&amp;gt;();

        foreach (var view in views)
        {
            var presenter = GetPresenterForView(view, presenters);
            if(presenter == null) continue;

            table.Add(presenter,view);
        }

        return table;
    }

    private static Type GetPresenterForView(Type type, IEnumerable&amp;lt;Type&amp;gt; presenters)
    {
        string name = type.Name.Replace(&amp;quot;View&amp;quot;, &amp;quot;Presenter&amp;quot;);
        var presenter =
            presenters.Where(p =&amp;gt; p.Name == name).FirstOrDefault();
        return presenter;
    }

    private static DataTemplate CreateDataTemplate(Type viewType, Type dataType)
    {
        var template = new DataTemplate(dataType);

        var factory = new FrameworkElementFactory(viewType);
        template.VisualTree = factory;
        return template;
    }
}&lt;/pre&gt;

&lt;p&gt;To use this, in your App.xaml.cs within OnStartup() add:&lt;/p&gt;

&lt;pre class="c#:nogutter:nocontrols" name="code"&gt;MvpConfiguration.InferViewsFromPresenters(Resources);&lt;/pre&gt;

&lt;p&gt;What do you think? Am I totally nuts?&lt;/p&gt;

&lt;p&gt;Oh, and I should also point out that &lt;a href="http://msdn.microsoft.com/en-us/library/system.windows.frameworkelementfactory.aspx" target="_blank"&gt;FrameworkElementFactory&lt;/a&gt; is actually deprecated. :-( Caveat emptor.&lt;/p&gt;&lt;div style="clear:both;"&gt;&lt;/div&gt;&lt;img src="http://devlicious.com/aggbug.aspx?PostID=46528" width="1" height="1"&gt;&lt;img src="http://feeds.feedburner.com/~r/ChristopherBennage/~4/iMG4OD_4kvA" height="1" width="1"/&gt;</description><category domain="http://devlicious.com/blogs/christopher_bennage/archive/tags/WPF/default.aspx">WPF</category><category domain="http://devlicious.com/blogs/christopher_bennage/archive/tags/MVC/default.aspx">MVC</category><category domain="http://devlicious.com/blogs/christopher_bennage/archive/tags/data+templates/default.aspx">data templates</category><category domain="http://devlicious.com/blogs/christopher_bennage/archive/tags/UI+Patterns/default.aspx">UI Patterns</category><category domain="http://devlicious.com/blogs/christopher_bennage/archive/tags/Caliburn/default.aspx">Caliburn</category><feedburner:origLink>http://devlicious.com/blogs/christopher_bennage/archive/2009/05/06/the-influence-of-mvc-on-my-wpf.aspx</feedburner:origLink></item><item><title>JavaScript Gotcha in IE7</title><link>http://feedproxy.google.com/~r/ChristopherBennage/~3/CG4DKPMW_50/javascript-gotcha-in-ie7.aspx</link><pubDate>Sun, 03 May 2009 22:10:22 GMT</pubDate><guid isPermaLink="false">40756a8b-6212-4073-9d98-6c26781577de:46466</guid><dc:creator>Christopher Bennage</dc:creator><slash:comments>5</slash:comments><wfw:commentRss>http://devlicious.com/blogs/christopher_bennage/rsscomments.aspx?PostID=46466</wfw:commentRss><comments>http://devlicious.com/blogs/christopher_bennage/archive/2009/05/03/javascript-gotcha-in-ie7.aspx#comments</comments><description>&lt;p&gt;I thought for a while that I was done with Web development. I mean the HTML, CSS, JavaScript stack specifically. WPF and Silverlight have just been so much more fun.&lt;/p&gt;  &lt;p&gt;Well, despite that sentiment my weekends have been full for the last couple of months with HTML, CSS, and JavaScript work for &lt;a href="http://www.silverarcade.com/" target="_blank"&gt;Silver Arcade&lt;/a&gt;. Surprisingly, I have found it refreshing.&lt;/p&gt;  &lt;p&gt;In fact, it’s even influenced my WPF development, but that’s another post.&lt;/p&gt;  &lt;p&gt;Silver Arcade passes around a lot of data using JSON. I kept having problems with IE7 and spent too much time scratching my head.&lt;/p&gt;  &lt;p&gt;Take a look at this little bit of jQuery that wires up the featured games rotator on the home page.&lt;/p&gt;  &lt;pre class="js:nogutter:nocontrols" name="code"&gt;jQuery(function($) {
    $(&amp;#39;#rotator-content&amp;#39;).cycle({
        fx: &amp;#39;scrollLeft&amp;#39;,
        easing: &amp;#39;easeOutQuad&amp;#39;, 
        speed: 1000,
        timeout: 6000,
        next: &amp;#39;#next-feature&amp;#39;,
        prev: &amp;#39;#prev-feature&amp;#39; ,
        pause:1,
    });
});&lt;/pre&gt;

&lt;p&gt;This code executes correctly in IE 8, Firefox 3, Safari 4, and Chrome. It breaks in IE 7. (It also works in Opera, but there are other problems there.)&lt;/p&gt;

&lt;p&gt;&lt;em&gt;The problem is the comma on the last line&lt;/em&gt;. IE 7 expects something more because of the comma. Specifically, the error is:&lt;/p&gt;

&lt;p&gt;“Expected identifier, string or number”&lt;/p&gt;&lt;div style="clear:both;"&gt;&lt;/div&gt;&lt;img src="http://devlicious.com/aggbug.aspx?PostID=46466" width="1" height="1"&gt;&lt;img src="http://feeds.feedburner.com/~r/ChristopherBennage/~4/CG4DKPMW_50" height="1" width="1"/&gt;</description><category domain="http://devlicious.com/blogs/christopher_bennage/archive/tags/javascript/default.aspx">javascript</category><category domain="http://devlicious.com/blogs/christopher_bennage/archive/tags/json/default.aspx">json</category><category domain="http://devlicious.com/blogs/christopher_bennage/archive/tags/browser+bugs/default.aspx">browser bugs</category><feedburner:origLink>http://devlicious.com/blogs/christopher_bennage/archive/2009/05/03/javascript-gotcha-in-ie7.aspx</feedburner:origLink></item><item><title>Idealistic vs. Practical</title><link>http://feedproxy.google.com/~r/ChristopherBennage/~3/9pylsX_ykEA/idealistic-vs-practical.aspx</link><pubDate>Tue, 24 Mar 2009 14:05:09 GMT</pubDate><guid isPermaLink="false">40756a8b-6212-4073-9d98-6c26781577de:45121</guid><dc:creator>Christopher Bennage</dc:creator><slash:comments>2</slash:comments><wfw:commentRss>http://devlicious.com/blogs/christopher_bennage/rsscomments.aspx?PostID=45121</wfw:commentRss><comments>http://devlicious.com/blogs/christopher_bennage/archive/2009/03/24/idealistic-vs-practical.aspx#comments</comments><description>&lt;p&gt;I often identify myself as an Agilist. When I first began to use the term, I was met with a great deal of trepidation. I remember the first few times I attended the local user group. “Oh, you’re one of those guys”. This hesitation has diminished considerably, but I still find that there are some interesting misconceptions about agile.&lt;/p&gt;  &lt;p&gt;For example, people frequently contrast &lt;em&gt;Agile&lt;/em&gt; with &lt;em&gt;Pragmatic&lt;/em&gt;.&lt;/p&gt;  &lt;p&gt;&lt;em&gt;“Oh, I’ve heard about SOLID principles (or whatever), but I’m really more pragmatic.”&lt;/em&gt; &lt;/p&gt;  &lt;p&gt;This has actually made me laugh out loud. You see, it was pragmatism that drove me towards the agile philosophy.&lt;/p&gt;  &lt;p&gt;According to Meriam-Webster, &lt;a href="http://www.merriam-webster.com/dictionary/pragmatic" target="_blank"&gt;pragmatic&lt;/a&gt; means:&lt;/p&gt;  &lt;blockquote&gt;   &lt;p&gt;relating to matters of fact or practical affairs often to the exclusion of intellectual or artistic matters &lt;strong&gt;:&lt;/strong&gt; practical as opposed to idealistic&lt;/p&gt; &lt;/blockquote&gt;  &lt;p&gt;So here is the relevant contrast: &lt;/p&gt;  &lt;p align="center"&gt;&lt;strong&gt;Idealistic vs. Practical&lt;/strong&gt;&lt;/p&gt;  &lt;p align="left"&gt;Is Agile idealistic or practical? Agile does embraces a set of principles (ideals) and I’ve seen many of its adherents become drunk with the beauty of it. I’ve been there a few times myself. So yes, it is idealistic in that respect. However, I think a better question is this:&lt;/p&gt;  &lt;p align="left"&gt;Is Agile &lt;em&gt;merely&lt;/em&gt; idealistic?&lt;/p&gt;  &lt;p align="left"&gt;There is a strong idealistic streak in Agile, we will not deny it, however the ideal is actually “get work done”. In other words, Agile is the art of pragmatism.&lt;/p&gt;  &lt;p align="left"&gt;I am motivated by success. I am motivated by accomplishing things. The quickest route to depressing me (or frustrating me) is to prevent me from getting work done. Because of this, when I first encountered the agile idea that change is expensive and therefore we should reduce the cost of change, I was listening. When I discovered that agile methodology offers a set of tools for reducing the cost of change, I was ecstatic.&lt;/p&gt;  &lt;p align="left"&gt;In the interest of being brief, I’ll jump to my conclusion:&lt;/p&gt;  &lt;p align="left"&gt;The application of the &lt;a href="http://agilemanifesto.org/principles.html" target="_blank"&gt;agile principles&lt;/a&gt; is about being successful in software development projects. It is not ars gratia artis. While some enthusiasts may forget that, it doesn’t change the nature of the underlying principles. &lt;/p&gt;  &lt;p align="left"&gt;Agile is the art of being pragmatic.&lt;/p&gt;&lt;div style="clear:both;"&gt;&lt;/div&gt;&lt;img src="http://devlicious.com/aggbug.aspx?PostID=45121" width="1" height="1"&gt;&lt;img src="http://feeds.feedburner.com/~r/ChristopherBennage/~4/9pylsX_ykEA" height="1" width="1"/&gt;</description><category domain="http://devlicious.com/blogs/christopher_bennage/archive/tags/Agile/default.aspx">Agile</category><category domain="http://devlicious.com/blogs/christopher_bennage/archive/tags/Opinion/default.aspx">Opinion</category><feedburner:origLink>http://devlicious.com/blogs/christopher_bennage/archive/2009/03/24/idealistic-vs-practical.aspx</feedburner:origLink></item><item><title>Displaying Today’s Date with XAML</title><link>http://feedproxy.google.com/~r/ChristopherBennage/~3/fBrNbRRrmaI/displaying-today-s-date-with-xaml.aspx</link><pubDate>Fri, 13 Mar 2009 22:06:11 GMT</pubDate><guid isPermaLink="false">40756a8b-6212-4073-9d98-6c26781577de:44956</guid><dc:creator>Christopher Bennage</dc:creator><slash:comments>1</slash:comments><wfw:commentRss>http://devlicious.com/blogs/christopher_bennage/rsscomments.aspx?PostID=44956</wfw:commentRss><comments>http://devlicious.com/blogs/christopher_bennage/archive/2009/03/13/displaying-today-s-date-with-xaml.aspx#comments</comments><description>&lt;p&gt;This one is easy on the brain. Some quick WPF lovin’ 101.&lt;/p&gt;  &lt;p&gt;I need to display the current date, and have it formatted like this:&lt;/p&gt;  &lt;p&gt;&lt;strong&gt;Friday, March 13, 2009&lt;/strong&gt;&lt;/p&gt;  &lt;p&gt;In my opinion, this is purely a matter for the view and so I’m handling it entirely in the xaml. Here’s the markup:&lt;/p&gt;  &lt;pre class="xml:nogutter:nocontrols" name="code"&gt;&amp;lt;TextBlock Text=&amp;quot;{Binding Source={x:Static sys:DateTime.Today},
           StringFormat=&amp;#39;{}{0:dddd, MMMM dd, yyyy}&amp;#39;}&amp;quot;/&amp;gt;&lt;/pre&gt;

&lt;p&gt;And now for a quick analysis.&lt;/p&gt;

&lt;p&gt;I wanted to use the builtin DateTime structure, because there is no need for me to expose the current time through my presentation/view model. In my root element, I create a namespace alias:&lt;/p&gt;

&lt;pre class="xml:nogutter:nocontrols" name="code"&gt;xmlns:sys=&amp;quot;clr-namespace:System;assembly=mscorlib&amp;quot;&lt;/pre&gt;

&lt;p&gt;This allows me to reference DateTime in the markup. Since DateTime has a static property, I can get at it using &lt;a href="http://msdn.microsoft.com/en-us/library/system.windows.markup.staticextension.aspx" target="_blank"&gt;StaticExtension&lt;/a&gt;. So far, that explains {x:Static sys:DateTime.Today}. I’m working from the inside out.&lt;/p&gt;

&lt;p&gt;Inside the binding, I need to set the &lt;a href="http://msdn.microsoft.com/en-us/library/system.windows.data.binding.source.aspx" target="_blank"&gt;Source&lt;/a&gt; property because otherwise the binding is looking to the DataContext. We don’t care about the context, we just want to directly access the value of DateTime.Today.&lt;/p&gt;

&lt;p&gt;Finally, we have &lt;a href="http://msdn.microsoft.com/en-us/library/system.windows.data.bindingbase.stringformat.aspx" target="_blank"&gt;StringFormat&lt;/a&gt;. It’s a tasty little bit that was introduced in 3.5sp1. You can pass it any of your standard formatting strings and it just works. Let’s say that I want to display this:&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Today is Friday March 13.&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;I could used:&lt;/p&gt;

&lt;pre class="xml:nogutter:nocontrols" name="code"&gt;&amp;lt;TextBlock Text=&amp;quot;{Binding Source={x:Static sys:DateTime.Today},
           StringFormat=Today is {0:dddd, MMMM dd}}&amp;quot;/&amp;gt;&lt;/pre&gt;

&lt;p&gt;Notice that my quotes from the first example were omitted. They are actually optional. I like to include them though for readability.&lt;/p&gt;

&lt;p&gt;You might also have notice in the first example an extra set of angle brackets. If your formatting string starts off with an angle bracket, the Xaml parser gets confused. It thinks that it’s encountering another markup extension. We have to use an escape sequence and in Xaml it’s &lt;a href="http://msdn.microsoft.com/en-us/library/ms744986.aspx" target="_blank"&gt;{}&lt;/a&gt;.&lt;/p&gt;

&lt;p&gt;Once final note, DateTime doesn’t raise any change notification. So don’t expect the view to be update as the time changes.&lt;/p&gt;&lt;div style="clear:both;"&gt;&lt;/div&gt;&lt;img src="http://devlicious.com/aggbug.aspx?PostID=44956" width="1" height="1"&gt;&lt;img src="http://feeds.feedburner.com/~r/ChristopherBennage/~4/fBrNbRRrmaI" height="1" width="1"/&gt;</description><category domain="http://devlicious.com/blogs/christopher_bennage/archive/tags/WPF/default.aspx">WPF</category><category domain="http://devlicious.com/blogs/christopher_bennage/archive/tags/Tips+_2600_amp_3B00_+Tricks/default.aspx">Tips &amp;amp; Tricks</category><category domain="http://devlicious.com/blogs/christopher_bennage/archive/tags/UI/default.aspx">UI</category><category domain="http://devlicious.com/blogs/christopher_bennage/archive/tags/XAML/default.aspx">XAML</category><category domain="http://devlicious.com/blogs/christopher_bennage/archive/tags/101/default.aspx">101</category><feedburner:origLink>http://devlicious.com/blogs/christopher_bennage/archive/2009/03/13/displaying-today-s-date-with-xaml.aspx</feedburner:origLink></item><item><title>Mirroring Subversion from Windows</title><link>http://feedproxy.google.com/~r/ChristopherBennage/~3/IU3qJonF3DA/mirroring-subversion-from-windows.aspx</link><pubDate>Wed, 11 Mar 2009 20:08:00 GMT</pubDate><guid isPermaLink="false">40756a8b-6212-4073-9d98-6c26781577de:44927</guid><dc:creator>Christopher Bennage</dc:creator><slash:comments>10</slash:comments><wfw:commentRss>http://devlicious.com/blogs/christopher_bennage/rsscomments.aspx?PostID=44927</wfw:commentRss><comments>http://devlicious.com/blogs/christopher_bennage/archive/2009/03/11/mirroring-subversion-from-windows.aspx#comments</comments><description>&lt;p&gt;We’ve been using Unfuddle for hosting our Subversion repositories (for almost two years I think). We’re a consulting shop and we move from project to project. It’s wonderful not having to worry about where the source is physically located or how it’s being backed.&lt;/p&gt;  &lt;p&gt;One of our current clients wanted to have the repository for their project physically located at their facility. They gave me access to a couple of Windows 2003 boxes and asked me to get everything setup. I used &lt;a href="http://www.visualsvn.com/server/" target="_blank"&gt;VisualSVN Server&lt;/a&gt; and &lt;a href="http://www.jetbrains.com/teamcity/" target="_blank"&gt;TeamCity&lt;/a&gt; and I had things running smoothly in almost no time. By the way, if you are not familiar with these products, you should be. They are both free (mostly) and very low friction. &lt;/p&gt;  &lt;p&gt;Even though the repositories weren’t hosted, we were still using Unfuddle for general project management (such as tracking tickets).&lt;/p&gt;  &lt;p&gt;Earlier this week, I was talking to our team lead and explained how Unfuddle integrates with their hosted repositories. For example, if I make comment when committing, such as “fixes and closes #147”, Unfuddle will update the status of ticket #147 as well as associate the changeset with the ticket. I can quickly jump to the committed code directly from the ticket. (Unfuddle is certainly not the only tool that does this, it’s just the one I’ve been using).&amp;#160; &lt;/p&gt;  &lt;p&gt;Anyway, the team lead was impressed and asked why we weren’t doing this. Well, because the customer wanted the source on site, and this feature of only works with the integrated repositories.&lt;/p&gt;  &lt;h3&gt;Mirroring a Repository&lt;/h3&gt;  &lt;p&gt;What we needed was a way to automatically propagate updates from an Unfuddle hosted repository to client’s onsite repository. The onsite repository could be read-only; that satisfies the client’s need. A couple of quick web searches revealed that Subversion includes a tool doing exactly this: &lt;em&gt;&lt;a href="http://svn.collab.net/repos/svn/trunk/notes/svnsync.txt" target="_blank"&gt;svnsync&lt;/a&gt;&lt;/em&gt;.&lt;/p&gt;  &lt;p&gt;Unfortunately, the directions that I found might be a little opaque to Windows users. &lt;/p&gt;  &lt;p&gt;Here’s a step by step of what I did.&lt;/p&gt;  &lt;ol&gt;   &lt;li&gt;I created a new repository to be my destination repository. You have to have a fresh repository to be the destination. With VisualSVN Server, this is merely a right click Create New Repository. &lt;/li&gt;    &lt;li&gt;     &lt;p&gt;Next, you have to edit the &lt;em&gt;pre-revision property change&lt;/em&gt; hook for the destination repository. This hook allows you to execute some logic to determine if a revision property can be changed. By default, svn will say “no, sorry, you can’t change the revision property”. The hooks are located in the hooks directory in the actual folder for the repository. In our case, the hook will be a batch file named “&lt;em&gt;pre-revprop-change.cmd&lt;/em&gt;”. &lt;/p&gt;      &lt;p&gt;You can (and maybe should) perform some logic here to verify what’s happening. For example, you could verify that the user performing the change is the user that you expect. &lt;/p&gt;      &lt;p&gt;In my case, I simply said “exit 0”. (If you want it to fail and not allow the change, then exit 1.)&lt;/p&gt; 
&lt;p&gt;&lt;em&gt;&lt;strong&gt;Update:&lt;/strong&gt; Ivan Zhakov made a comment that you should avoid exit 0, and verify the user&amp;#39;s identity with something like this:&lt;/em&gt; &lt;p&gt;
&lt;pre class="nogutter:nocontrols" name="code"&gt;IF &amp;quot;%3&amp;quot; == &amp;quot;sync_user&amp;quot; exit 0 exit 1&lt;/pre&gt;

     &lt;p&gt;Once again, in VisualSVN Server this was very easy:&lt;/p&gt;      &lt;ul&gt;       &lt;li&gt;right-click Properties &lt;/li&gt;        &lt;li&gt;switch to Hooks tab &lt;/li&gt;        &lt;li&gt;select Pre-revision property change hook &lt;/li&gt;        &lt;li&gt;click Edit &lt;/li&gt;        &lt;li&gt;and type “exit 0” &lt;/li&gt;     &lt;/ul&gt;   &lt;/li&gt;    &lt;li&gt;     &lt;p&gt;Next you need to initialize the destination. This is a one time process that prepares the destination repository for the synchronization process.&lt;/p&gt;      &lt;p&gt;Use the &lt;em&gt;svnsync init&lt;/em&gt; command to do this. Mine looked something like this:&lt;/p&gt;      &lt;pre class="nogutter:nocontrols" name="code"&gt;svnsync init %dst_repo% %src_repo% 
	--source-username buildserver --source-password 1234 
	--sync-username sync_user --sync-password 1234&lt;/pre&gt;

    &lt;p&gt;I had the two repositories as environment variables&lt;/p&gt;
  &lt;/li&gt;

  &lt;li&gt;Now you need to call &lt;em&gt;svnsync sync&lt;/em&gt; each time you want to mirroring to take place. If you had sufficient access to the source repository you could actually use another hook or two to trigger the mirroring process. In my case, I didn’t have that access. (Though I think Unfuddle might provide a callback url on commits). Instead, I chose to schedule the sync to execute once an hour during the most active development hours of the day. &lt;/li&gt;

  &lt;li&gt;
    &lt;p&gt;My batch file that looked something like this:&lt;/p&gt;

    &lt;pre class="nogutter:nocontrols" name="code"&gt;svnsync sync %dst_repo% 
	--source-username buildserver --source-password 1234 
	--sync-username user --sync-password 1234&lt;/pre&gt;
  &lt;/li&gt;

  &lt;li&gt;
    &lt;p&gt;That’s all you need for your repository to be mirrored. However there is one more useful bit to know. It’s very easy to lock up the destination repository if you execute svnsync with bad arguements. In order to remove the bad locks, just run this&lt;/p&gt;

    &lt;pre class="nogutter:nocontrols" name="code"&gt;svn pdel --revprop -r 0 svn:sync-lock %dst_repo%&lt;/pre&gt;
  &lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;Be sure to use &lt;em&gt;svnsync help &lt;/em&gt;if you run into problems. Here’s is a &lt;a href="http://svn.collab.net/repos/svn/trunk/notes/svnsync.txt" target="_blank"&gt;guide&lt;/a&gt; that helped me out as well.&lt;/p&gt;

&lt;p&gt;P.S. There is some stuff in TortoiseSVN to work with hooks as well, but I’ve never explored it. Honestly, I was able to get the mirroring setup in well under an hour and I only looked at TortoiseSVN as an afterthought.&lt;/p&gt;

&lt;p&gt;&lt;em&gt;Update May 18, 2009:&lt;/em&gt; Andy Pook added:&lt;/p&gt;
&lt;p&gt;You should also check &amp;quot;svnlook uuid&amp;quot; and &amp;quot;svnadmin setuuid&amp;quot;. Getting the uuid&amp;#39;s in sync will make it _much_ easier to switch your working copy if you need to use the mirror.&lt;/p&gt;&lt;div style="clear:both;"&gt;&lt;/div&gt;&lt;img src="http://devlicious.com/aggbug.aspx?PostID=44927" width="1" height="1"&gt;&lt;img src="http://feeds.feedburner.com/~r/ChristopherBennage/~4/IU3qJonF3DA" height="1" width="1"/&gt;</description><category domain="http://devlicious.com/blogs/christopher_bennage/archive/tags/source+control/default.aspx">source control</category><category domain="http://devlicious.com/blogs/christopher_bennage/archive/tags/Continuous+Integration/default.aspx">Continuous Integration</category><category domain="http://devlicious.com/blogs/christopher_bennage/archive/tags/Tips+_2600_amp_3B00_+Tricks/default.aspx">Tips &amp;amp; Tricks</category><category domain="http://devlicious.com/blogs/christopher_bennage/archive/tags/svn/default.aspx">svn</category><feedburner:origLink>http://devlicious.com/blogs/christopher_bennage/archive/2009/03/11/mirroring-subversion-from-windows.aspx</feedburner:origLink></item><item><title>Testing Bindings In WPF</title><link>http://feedproxy.google.com/~r/ChristopherBennage/~3/RGYyW1sbtNo/testing-bindings-in-wpf.aspx</link><pubDate>Fri, 20 Feb 2009 03:56:00 GMT</pubDate><guid isPermaLink="false">40756a8b-6212-4073-9d98-6c26781577de:44397</guid><dc:creator>Christopher Bennage</dc:creator><slash:comments>3</slash:comments><wfw:commentRss>http://devlicious.com/blogs/christopher_bennage/rsscomments.aspx?PostID=44397</wfw:commentRss><comments>http://devlicious.com/blogs/christopher_bennage/archive/2009/02/19/testing-bindings-in-wpf.aspx#comments</comments><description>&lt;p&gt;I was inspired to get off my duff and blog today by &lt;a title="seriously, it&amp;#39;s voyeurism" href="http://twitter.com/shanselman/statuses/1228349932" target="_blank"&gt;a tweet from Scott Hanselman&lt;/a&gt;. I didn’t really dig into the context of his tweet, but it was about TDD and WPF. In case you haven’t figured it out, I’m a big fan of WPF and TDD. Luckily, I’ve had the opportunity to work on a number of varied WPF projects (most using TDD) over the last couple of years. One problem I experienced over and over was incorrect bindings in my Xaml (as I alluded to in &lt;a href="http://devlicious.com/blogs/christopher_bennage/archive/2009/01/19/ui-patterns-for-wpf.aspx" target="_blank"&gt;this post&lt;/a&gt;). Binding errors are silent. They sneak up on you ninja-like. If you are keeping an eye on your Output window you can catch them, but it is very easy for them to just slip by.&lt;/p&gt;  &lt;p&gt;&lt;img style="border-bottom:0px;border-left:0px;display:inline;margin-left:0px;border-top:0px;margin-right:0px;border-right:0px;" title="Karate Lessons" border="0" alt="Karate Lessons" align="right" src="http://devlicious.com/cfs-file.ashx/__key/CommunityServer.Blogs.Components.WeblogFiles/christopher_5F00_bennage/iStock_5F00_000004919619XSmall_5F00_18DE0A5B.jpg" width="240" height="159" /&gt;About two years ago, Rob and I were working on a student records application for the &lt;a href="http://music.fsu.edu/" target="_blank"&gt;FSU College of Music&lt;/a&gt;. The system handled the entire lifecycle of a student, from application to graduation, and that involved lots of data. We had a number of screens in the app that were merely large data entry screens. Binding errors where a problem, and it seemed like a new batch showed up every time we made a release to the users.&lt;/p&gt;  &lt;p&gt;The errors might have been the result of renaming a bound property, bad spelling, or some other such silliness. They were easy mistakes to make and thus I began to think that we really needed a way to automatically test them.&lt;/p&gt;  &lt;p&gt;Well, I’m lazy and time passed (maybe a year) and then I mentioned it again to Rob. The next day he committed a prototype to the &lt;a title="free WPF and Silverlight from the stone" href="http://www.codeplex.com/caliburn"&gt;Caliburn&lt;/a&gt; trunk. (&lt;a title="No, Ayende and Rob are not Jesus, but I couldn&amp;#39;t resist the allusion." href="http://www.youtube.com/watch?v=jQcNiD0Z3MU" target="_blank"&gt;He’s like my own personal Ayende&lt;/a&gt;.)&lt;/p&gt;  &lt;p&gt;Here’s an example test copied directly from Caliburn’s &lt;a href="http://www.codeplex.com/caliburn/Wiki/View.aspx?title=Unit%20Testing%20Data%20Bindings&amp;amp;referringTitle=Table%20Of%20Contents" target="_blank"&gt;documentation&lt;/a&gt;:&lt;/p&gt;  &lt;pre class="c#:nogutter:nocontrols" name="code"&gt;public class TestBase
{
    static TestBase()
    {
        var app = new MyApplication();
        app.InitializeComponent();
    }
}&lt;/pre&gt;

&lt;pre class="c#:nogutter:nocontrols" name="code"&gt;[TestFixture]
public class TestCase : TestBase
{
    [Test]
    public void Test()
    {
        var validator = Validator.For&amp;lt;MyUserControl, MyModel&amp;gt;();
        var result = validator.Validate();

        Assert.That(result.HasErrors, Is.False, result.ErrorSummary);
    }
}&lt;/pre&gt;

&lt;p&gt;In TestBase, we initialize the actual application so that we have access to application level resources. We need to this in a static constructor because we don’t want more than one instance of the application in the AppDomain. &lt;/p&gt;

&lt;p&gt;Now, check out the Test() method. The static class Validator.For&amp;lt;T,K&amp;gt;() method returns an instance of BindingValidator&amp;lt;K&amp;gt;. The type T is some FrameworkElement that contains the bindings we’re interested in and K is the type that the FrameworkElement is bound to. Calling the Validate() method causes Caliburn to instantiate T, crawl it’s tree, and collect all the bindings. It then compares those bindings to the type K to see if they are valid. Validate() actually returns an instance of ValidationResult&amp;lt;K&amp;gt;, which is a summary of everything that Caliburn found while comparing the bindings against the actual type T. &lt;/p&gt;

&lt;p&gt;The assertion in the test means that we expect Caliburn to find no errors, and if it does to provide us the summary. This is useful because there might be a number of binding errors and the ErrorSummary will give us the whole list.&lt;/p&gt;

&lt;p&gt;At this point, I’m just repeat what’s stated in Caliburn’s documentation. &lt;a title="you know you want it!" href="http://nhprof.com/" target="_blank"&gt;NH Prof&lt;/a&gt; was the first project where we’ve actually used the Testability features of Caliburn. Let’s check out a real live test from it:&lt;/p&gt;

&lt;pre class="c#:nogutter:nocontrols" name="code"&gt;[TestFixture]
public class MessageBoxViewTextFixture : ViewTestFixtureBase
{
    private readonly ValidationResult&amp;lt;MessagePresenter&amp;gt; bindings;

    public MessageBoxViewTextFixture()
    {
        bindings = Validator.For&amp;lt;MessageBoxView, MessagePresenter&amp;gt;()
            .Validate();
    }

    [Test]
    public void BindingsDoNotHaveErrors()
    {
        Assert.That(bindings.HasErrors, Is.False, bindings.ErrorSummary);
    }

    [Test]
    public void MessageIsBound()
    {
        Assert.That(bindings.WasBoundTo(x =&amp;gt; x.Message));
    }
}&lt;/pre&gt;

&lt;p&gt;This test is for the view that displays a simple popup message. We have a simple presenter that backs the view and it has a message to display in its property Message. It’s tested independent of the view. (This is nice because we have a case in NH Prof where a single presenter might be bound to multiple views.)&lt;/p&gt;

&lt;p&gt;The ViewTestFixtureBase is identical to TestBase from the example above. Since it’s expensive to have Caliburn instantiate and crawl the UI validating the bindings, we only want to do this once. (I’m not really sure why I used the constructor, instead of [TestFixtureSetUp], but I did.) &lt;/p&gt;

&lt;p&gt;The first test covers 90% of what you typically need, catching spelling errors, etc. The second test however explicitly checks to see if we are bound to the Message property on the presenter. This is useful because that’s the core reason for this view. There may be other properties bound, but this is the one we definitely care about. (I think this affords liberty to designers while ensuring that a view delivers the business value that was intended.)&lt;/p&gt;

&lt;p&gt;Now, let’s pretend that I have a bad binding in my markup. Here’s the core snippet for the view used in the test above, MessageBoxView:&lt;/p&gt;

&lt;pre class="xml:nogutter:nocontrols" name="code"&gt;&amp;lt;Grid MaxWidth=&amp;quot;260&amp;quot;&amp;gt;
    &amp;lt;StackPanel&amp;gt;
        &amp;lt;TextBlock Foreground=&amp;quot;{StaticResource Text}&amp;quot; 
                   FontSize=&amp;quot;14&amp;quot;
                   TextWrapping=&amp;quot;Wrap&amp;quot;
                   Text=&amp;quot;{Binding Messyage}&amp;quot; /&amp;gt;
        &amp;lt;Button Content=&amp;quot;OK&amp;quot;
                Margin=&amp;quot;4 8 4 4&amp;quot;
                HorizontalAlignment=&amp;quot;Center&amp;quot;
                IsCancel=&amp;quot;True&amp;quot; /&amp;gt;
    &amp;lt;/StackPanel&amp;gt;    
&amp;lt;/Grid&amp;gt;&lt;/pre&gt;

&lt;p&gt;Oops, I misspelled Message in the binding! When I execute my tests, they both fail. The first because there is a binding error and the second because it can’t find Message. Here’s the actual exception from the first test:&lt;/p&gt;

&lt;blockquote&gt;
  &lt;p&gt;NUnit.Framework.AssertionException:&amp;#160;&amp;#160; [MessageBoxView.Grid.StackPanel.TextBlock] The property &amp;#39;Messyage&amp;#39; was not found on &amp;#39;MessagePresenter&amp;#39;. 
    &lt;br /&gt;&amp;#160; Expected: False 

    &lt;br /&gt;&amp;#160; But was:&amp;#160; True&lt;/p&gt;
&lt;/blockquote&gt;

&lt;p&gt;Notice that it actually gives you the path to the offending binding: &lt;em&gt;MessageBoxView.Grid.StackPanel.TextBlock&lt;/em&gt;. Now that’s just cool! Thanks Rob!&lt;/p&gt;

&lt;p&gt;I can’t explain how much pain it saves to be able to do this. If you are doing TDD with WPF, you really need to check this out.&lt;/p&gt;

&lt;p&gt;I’ll post over the weekend some tests that are a bit more BDD in their styles.&lt;/p&gt;&lt;div style="clear:both;"&gt;&lt;/div&gt;&lt;img src="http://devlicious.com/aggbug.aspx?PostID=44397" width="1" height="1"&gt;&lt;img src="http://feeds.feedburner.com/~r/ChristopherBennage/~4/RGYyW1sbtNo" height="1" width="1"/&gt;</description><category domain="http://devlicious.com/blogs/christopher_bennage/archive/tags/WPF/default.aspx">WPF</category><category domain="http://devlicious.com/blogs/christopher_bennage/archive/tags/TDD/default.aspx">TDD</category><category domain="http://devlicious.com/blogs/christopher_bennage/archive/tags/UI/default.aspx">UI</category><category domain="http://devlicious.com/blogs/christopher_bennage/archive/tags/UI+Patterns/default.aspx">UI Patterns</category><category domain="http://devlicious.com/blogs/christopher_bennage/archive/tags/XAML/default.aspx">XAML</category><category domain="http://devlicious.com/blogs/christopher_bennage/archive/tags/Caliburn/default.aspx">Caliburn</category><feedburner:origLink>http://devlicious.com/blogs/christopher_bennage/archive/2009/02/19/testing-bindings-in-wpf.aspx</feedburner:origLink></item><item><title>Garbled Text in WPF</title><link>http://feedproxy.google.com/~r/ChristopherBennage/~3/3FhP8Ow5IZQ/garbled-text-in-wpf.aspx</link><pubDate>Mon, 16 Feb 2009 21:41:18 GMT</pubDate><guid isPermaLink="false">40756a8b-6212-4073-9d98-6c26781577de:44284</guid><dc:creator>Christopher Bennage</dc:creator><slash:comments>1</slash:comments><wfw:commentRss>http://devlicious.com/blogs/christopher_bennage/rsscomments.aspx?PostID=44284</wfw:commentRss><comments>http://devlicious.com/blogs/christopher_bennage/archive/2009/02/16/garbled-text-in-wpf.aspx#comments</comments><description>&lt;p&gt;We&amp;#39;ve had a number of rendering issues with NH Prof. I&amp;#39;ve been embarrassed about how frequently I have asked users to update their video drivers. It’s not surprising to encounter driver issues &lt;em&gt;occasionally&lt;/em&gt; with WPF. It is built on top of DirectX you know. (In fact, all my WPF apps break horribly when I enable SLI mode.) However, too many people were reporting problems with NH Prof, and that led us to think that something else was going on.&lt;/p&gt;  &lt;p&gt;&lt;img style="border-bottom:0px;border-left:0px;margin:0px;display:inline;border-top:0px;border-right:0px;" title="Please help me, I&amp;#39;m ugly!" border="0" alt="Please help me, I&amp;#39;m ugly!" align="right" src="http://devlicious.com/cfs-file.ashx/__key/CommunityServer.Blogs.Components.WeblogFiles/christopher_5F00_bennage/UGLY1_5F00_7DB8FF4F.png" width="280" height="139" /&gt; During a shared coding session using Microsoft’s &lt;a href="http://en.wikipedia.org/wiki/Microsoft_SharedView" target="_blank"&gt;SharedView&lt;/a&gt; we noticed some of the graphical glitches that users were complaining about. This was important because we had not been able to reproduce any of these problems previously. Discovering this, I was able to create a sample application to help me isolate the problem. The symptom is garbled text. It’s interesting to point out that the text is only garbled when the window containing the text is over certain elements in &lt;em&gt;other&lt;/em&gt; applications. Usually the culprit elements were the &lt;a href="http://en.wikipedia.org/wiki/User_interface_chrome" target="_blank"&gt;chrome bits&lt;/a&gt; of another window or control. Moving the offending window with garbled text would result in an effect that looked as if the text was transparent… Hmm…&lt;/p&gt;  &lt;p&gt;Here is the Xaml sufficient to reproduce the issue:&lt;/p&gt;  &lt;pre class="xml:nogutter:nocontrols" name="code"&gt;&amp;lt;Window x:Class=&amp;quot;GarbledTextTest.Window1&amp;quot;
        xmlns=&amp;quot;http://schemas.microsoft.com/winfx/2006/xaml/presentation&amp;quot;
        xmlns:x=&amp;quot;http://schemas.microsoft.com/winfx/2006/xaml&amp;quot;
        Title=&amp;quot;Garbled Text Test&amp;quot;
        AllowsTransparency=&amp;quot;True&amp;quot;
        WindowStyle=&amp;quot;None&amp;quot;
        Height=&amp;quot;300&amp;quot;
        Width=&amp;quot;300&amp;quot;&amp;gt;
    &amp;lt;Grid MouseLeftButtonDown=&amp;quot;Grid_MouseLeftButtonDown&amp;quot;
          Background=&amp;quot;Black&amp;quot;&amp;gt;
        &amp;lt;TextBlock Text=&amp;quot;Help me!&amp;quot;
                   FontSize=&amp;quot;32&amp;quot;
                   Foreground=&amp;quot;#cfff&amp;quot; /&amp;gt;
    &amp;lt;/Grid&amp;gt;
&amp;lt;/Window&amp;gt;&lt;/pre&gt;

&lt;p&gt;(By the way, the event handler in the Xaml is just for me to drag the window around.)&lt;/p&gt;

&lt;p&gt;But remember, I said that the developers were not experiencing the problem, so what else gives? I also mentioned that we noticed this while using SharedView. &lt;img style="border-bottom:0px;border-left:0px;margin:2px 0px 0px;display:inline;border-top:0px;border-right:0px;" title="going back to a classic" border="0" alt="going back to a classic" align="right" src="http://devlicious.com/cfs-file.ashx/__key/CommunityServer.Blogs.Components.WeblogFiles/christopher_5F00_bennage/goingbacktoaclassic_5F00_75C15CED.png" width="414" height="459" /&gt;In fact, we fixed it in NH Prof during that same session. Something was special about SharedView. I recalled that SharedView used to tell me that it was disabling Aero when I started it (It doesn’t always do so, but I didn’t bother to find out why.) So I just disabled it myself by changing my theme back to Windows Classic.&lt;/p&gt;

&lt;h3&gt;Okay, so…&lt;/h3&gt;

&lt;p&gt;What does all this add up to? It seems that three different things stacked up to cause the rendering bug. &lt;/p&gt;

&lt;p&gt;The first bit of wonkiness is the&amp;#160; &lt;strong&gt;AllowTransparency&lt;/strong&gt; property on the &lt;strong&gt;Window&lt;/strong&gt; element. If I set this property to false, the problem goes away. This wasn’t really an option for NH Prof as we preferred the custom chrome and need the transparency.&lt;/p&gt;

&lt;p&gt;Second, the brush used for the text had partial opacity. It might not jump out at you, but the value #cfff translates to &lt;em&gt;white with 80% opacity&lt;/em&gt;. If I make the brush 100% opaque, the problem goes away. That’s actually how we fixed it.&lt;/p&gt;

&lt;p&gt;Of course, the third way was the doozy, and I can only qualify it as an Unhappy Rendering Environment. It might be an out of date driver, a remote desktop, your pretty Vista theme being disabled, or a picture of an angry monkey.&lt;/p&gt;

&lt;p&gt;&lt;/p&gt;

&lt;p&gt;&lt;/p&gt;

&lt;p&gt;&lt;/p&gt;

&lt;p&gt;&lt;/p&gt;

&lt;p&gt;&lt;/p&gt;

&lt;p&gt;&lt;/p&gt;

&lt;p&gt;&lt;em&gt;By the way, if you find any more of these glitches in NH Prof, please post about it in the &lt;a href="http://groups.google.com/group/nhprof" target="_blank"&gt;forums&lt;/a&gt;. Also, there are other issues around rendering that are not related to this.&lt;/em&gt;&lt;/p&gt;&lt;div style="clear:both;"&gt;&lt;/div&gt;&lt;img src="http://devlicious.com/aggbug.aspx?PostID=44284" width="1" height="1"&gt;&lt;img src="http://feeds.feedburner.com/~r/ChristopherBennage/~4/3FhP8Ow5IZQ" height="1" width="1"/&gt;</description><category domain="http://devlicious.com/blogs/christopher_bennage/archive/tags/WPF/default.aspx">WPF</category><category domain="http://devlicious.com/blogs/christopher_bennage/archive/tags/UI/default.aspx">UI</category><category domain="http://devlicious.com/blogs/christopher_bennage/archive/tags/XAML/default.aspx">XAML</category><feedburner:origLink>http://devlicious.com/blogs/christopher_bennage/archive/2009/02/16/garbled-text-in-wpf.aspx</feedburner:origLink></item><item><title>UX Patterns (and not UI Architecture Patterns)</title><link>http://feedproxy.google.com/~r/ChristopherBennage/~3/onn21enJbdc/ux-patterns-and-not-ui-architecture-patterns.aspx</link><pubDate>Thu, 05 Feb 2009 19:19:00 GMT</pubDate><guid isPermaLink="false">40756a8b-6212-4073-9d98-6c26781577de:43983</guid><dc:creator>Christopher Bennage</dc:creator><slash:comments>5</slash:comments><wfw:commentRss>http://devlicious.com/blogs/christopher_bennage/rsscomments.aspx?PostID=43983</wfw:commentRss><comments>http://devlicious.com/blogs/christopher_bennage/archive/2009/02/05/ux-patterns-and-not-ui-architecture-patterns.aspx#comments</comments><description>&lt;p&gt;Just when you think that you finally have an accurate label to describe something, you discover the true ambiguity of the term.&lt;/p&gt;  &lt;h3&gt;What is UX?&lt;/h3&gt;  &lt;p&gt;UX means &lt;em&gt;&lt;a href="http://en.wikipedia.org/wiki/User_experience" target="_blank"&gt;User Experience&lt;/a&gt;&lt;/em&gt;. You might say that it is the &lt;em&gt;ergonomics&lt;/em&gt; of an user interface, or possibly the&lt;em&gt; level of intuitiveness&lt;/em&gt;. More plainly, good UX means that the users of the software are able to quickly understand how to use and don’t have to go out of their way to make things happen. This blurs a little bit into the concept &lt;a href="http://en.wikipedia.org/wiki/Usability" target="_blank"&gt;Usability&lt;/a&gt;. But UX just sounds so much sexier, and there is this aspect of producing chemistry between the user and software that transcends mere Usability.&lt;/p&gt;  &lt;p&gt;Why do I bring this up? Well, I’ve just started talking about &lt;a href="http://devlicious.com/blogs/christopher_bennage/archive/2009/01/19/ui-patterns-for-wpf.aspx" target="_blank"&gt;UI Architecture patterns&lt;/a&gt; and I wanted to make sure the concepts were distinct. When I talk about UI architecture patterns I’m talking about the structure of the code that underlies a user interface. It’s all non-visual stuff. On the other hand, UX patterns deal with the rendered view that is presented to the user.&lt;/p&gt;  &lt;p&gt;&lt;a href="http://devlicious.com/cfs-file.ashx/__key/CommunityServer.Blogs.Components.WeblogFiles/christopher_5F00_bennage/Quince_5F00_2E46BB8C.png"&gt;&lt;img style="border-bottom:0px;border-left:0px;margin:0px 0px 4px;display:inline;border-top:0px;border-right:0px;" title="Quince" border="0" alt="Quince" align="right" src="http://devlicious.com/cfs-file.ashx/__key/CommunityServer.Blogs.Components.WeblogFiles/christopher_5F00_bennage/Quince_5F00_thumb_5F00_5BC7DB4F.png" width="244" height="47" /&gt;&lt;/a&gt;Infragistics just recently published a very cool (and Silverlight-based) catalog of UX Patterns called &lt;a href="http://quince.infragistics.com/" target="_blank"&gt;Quince&lt;/a&gt;.&lt;/p&gt;  &lt;p&gt;You might be inclined to say, “Well, that’s nice for designers, but…”. Please don’t, this is really a useful for tool for anyone building user interfaces, even if those interfaces are basic and handed off to a design team. In the very least, this will help establish a common vocabulary for talking about user interfaces.&lt;/p&gt;  &lt;h3&gt;More Resources&lt;/h3&gt;  &lt;p&gt;If you are interested in know more about UX and usability, here’s a couple of resources: &lt;/p&gt;  &lt;p&gt;&lt;a href="http://www.useit.com/" target="_blank"&gt;Jakob Nielsen&lt;/a&gt; – very well know and full of good info, but he is definitely plain usability with none of the sizzle.&lt;/p&gt;  &lt;p&gt;&lt;a href="http://www.amazon.com/gp/product/0321344758?ie=UTF8&amp;amp;tag=bluspiconinc-20&amp;amp;linkCode=as2&amp;amp;camp=1789&amp;amp;creative=390957&amp;amp;creativeASIN=0321344758" target="_blank"&gt;Don’t Make Me Think&lt;/a&gt; – one of the first books I read on the subject. (I probably need to reread it, it’s been so long…)&lt;/p&gt;&lt;div style="clear:both;"&gt;&lt;/div&gt;&lt;img src="http://devlicious.com/aggbug.aspx?PostID=43983" width="1" height="1"&gt;&lt;img src="http://feeds.feedburner.com/~r/ChristopherBennage/~4/onn21enJbdc" height="1" width="1"/&gt;</description><category domain="http://devlicious.com/blogs/christopher_bennage/archive/tags/UI/default.aspx">UI</category><category domain="http://devlicious.com/blogs/christopher_bennage/archive/tags/UI+Patterns/default.aspx">UI Patterns</category><category domain="http://devlicious.com/blogs/christopher_bennage/archive/tags/UX/default.aspx">UX</category><category domain="http://devlicious.com/blogs/christopher_bennage/archive/tags/Usability/default.aspx">Usability</category><feedburner:origLink>http://devlicious.com/blogs/christopher_bennage/archive/2009/02/05/ux-patterns-and-not-ui-architecture-patterns.aspx</feedburner:origLink></item><item><title>An Essential Tip for Working With XAML</title><link>http://feedproxy.google.com/~r/ChristopherBennage/~3/rNWfq5bQXGQ/an-essential-tip-for-working-with-xaml.aspx</link><pubDate>Wed, 04 Feb 2009 14:51:00 GMT</pubDate><guid isPermaLink="false">40756a8b-6212-4073-9d98-6c26781577de:43978</guid><dc:creator>Christopher Bennage</dc:creator><slash:comments>10</slash:comments><wfw:commentRss>http://devlicious.com/blogs/christopher_bennage/rsscomments.aspx?PostID=43978</wfw:commentRss><comments>http://devlicious.com/blogs/christopher_bennage/archive/2009/02/04/an-essential-tip-for-working-with-xaml.aspx#comments</comments><description>&lt;p&gt;Most WPF and Silverlight devs already know to turn off the default design view for XAML. I don’t &lt;em&gt;ever&lt;/em&gt; use the designer in Visual Studio for either Silverlight or WPF. My apologies to the team that worked on it, but it is a hindrance and not a help. When I give presentations, my audiences are often surprised to discover how much XAML I edit manually. Now, I do use both Blend and &lt;a title="an excellent, lightweight, wysiwyg XAML editor" href="http://www.kaxaml.com/" target="_blank"&gt;Kaxaml&lt;/a&gt; quite a bit, but never the builtin designer.&lt;/p&gt;  &lt;p&gt;In case you don’t know how to disable the design view (the option is buried somewhat):&lt;/p&gt;  &lt;p&gt;&lt;strong&gt;Tools &amp;gt; Options &amp;gt; Text Editor &amp;gt; XAML &amp;gt; Miscellaneous&lt;/strong&gt;&lt;/p&gt;  &lt;p&gt;Then check “&lt;strong&gt;Always open documents in full XAML view&lt;/strong&gt;”&lt;/p&gt;  &lt;h3&gt;Other Troubles&lt;/h3&gt;  &lt;p&gt;I upgraded to 64-bit Vista a month or so back, and despite the positive experience overall, I had one very frustrating problem. Frequently, when I worked with a XAML file, Visual Studio would get all wonky. It only seemed to affect a single XAML file at a time, even if I had a dozen open. &lt;a href="http://devlicious.com/cfs-file.ashx/__key/CommunityServer.Blogs.Components.WeblogFiles/christopher_5F00_bennage/24200991748AM_5F00_157772DE.jpg"&gt;&lt;img style="border-bottom:0px;border-left:0px;margin:3px 0px;display:inline;border-top:0px;border-right:0px;" title="VS being wonky" border="0" alt="VS being wonky" align="right" src="http://devlicious.com/cfs-file.ashx/__key/CommunityServer.Blogs.Components.WeblogFiles/christopher_5F00_bennage/24200991748AM_5F00_thumb_5F00_74840036.jpg" width="461" height="400" /&gt;&lt;/a&gt;I could reset the troubled file by closing it and opening it again. The problem usually started with my scrollbar failing to repaint. At first I was fearful that it might be related to ReSharper (which has awesome XAML features BTW). Then I suspected my video drivers (which I still do actually). Nevertheless, I didn’t find a solution.&lt;/p&gt;  &lt;p&gt;Fortunately, &lt;a href="http://weblogs.asp.net/fmarguerie" target="_blank"&gt;Fabrice Marquerie&lt;/a&gt; (of &lt;a href="http://www.amazon.com/gp/product/1933988169?ie=UTF8&amp;amp;tag=bluspiconinc-20&amp;amp;linkCode=as2&amp;amp;camp=1789&amp;amp;creative=390957&amp;amp;creativeASIN=1933988169" target="_blank"&gt;LINQ in Action&lt;/a&gt; fame) made this &lt;a href="http://weblogs.asp.net/fmarguerie/archive/2009/01/29/life-changer-xaml-tip-for-visual-studio.aspx" target="_blank"&gt;very useful post&lt;/a&gt; on his site a few days.&lt;/p&gt;  &lt;p&gt;Fabrice discovered an excellent trick: using the &lt;em&gt;Source Code Editor&lt;/em&gt; for XAML. It’s really fast and you have all of the same features as the default XAML editor. The only thing you lose it the Design tab at the bottom. And hey, if you really need it, it’s only a right-click away! &lt;/p&gt;  &lt;p&gt;Here’s the instructions copied from his blog:&lt;/p&gt;  &lt;blockquote&gt;   &lt;ol&gt;     &lt;li&gt;Right-click on a XAML file in the Solution Explorer &lt;/li&gt;      &lt;li&gt;Select &amp;quot;Open With...&amp;quot; &lt;/li&gt;      &lt;li&gt;Select &amp;quot;Source Code (Text) Editor&amp;quot; &lt;/li&gt;      &lt;li&gt;Click on &amp;quot;Set as Default&amp;quot; &lt;/li&gt;      &lt;li&gt;Click OK &lt;/li&gt;      &lt;li&gt;You&amp;#39;re done! &lt;/li&gt;   &lt;/ol&gt; &lt;/blockquote&gt;  &lt;p&gt;Trust me, if you work with XAML, you’ll want to do this.&lt;/p&gt;&lt;div style="clear:both;"&gt;&lt;/div&gt;&lt;img src="http://devlicious.com/aggbug.aspx?PostID=43978" width="1" height="1"&gt;&lt;img src="http://feeds.feedburner.com/~r/ChristopherBennage/~4/rNWfq5bQXGQ" height="1" width="1"/&gt;</description><category domain="http://devlicious.com/blogs/christopher_bennage/archive/tags/WPF/default.aspx">WPF</category><category domain="http://devlicious.com/blogs/christopher_bennage/archive/tags/Silverlight/default.aspx">Silverlight</category><category domain="http://devlicious.com/blogs/christopher_bennage/archive/tags/Tips+_2600_amp_3B00_+Tricks/default.aspx">Tips &amp;amp; Tricks</category><category domain="http://devlicious.com/blogs/christopher_bennage/archive/tags/Visual+Studio/default.aspx">Visual Studio</category><category domain="http://devlicious.com/blogs/christopher_bennage/archive/tags/XAML/default.aspx">XAML</category><category domain="http://devlicious.com/blogs/christopher_bennage/archive/tags/64+bit/default.aspx">64 bit</category><feedburner:origLink>http://devlicious.com/blogs/christopher_bennage/archive/2009/02/04/an-essential-tip-for-working-with-xaml.aspx</feedburner:origLink></item><item><title>UI Patterns for WPF</title><link>http://feedproxy.google.com/~r/ChristopherBennage/~3/FRjyZKnKHSk/ui-patterns-for-wpf.aspx</link><pubDate>Tue, 20 Jan 2009 03:19:00 GMT</pubDate><guid isPermaLink="false">40756a8b-6212-4073-9d98-6c26781577de:43807</guid><dc:creator>Christopher Bennage</dc:creator><slash:comments>16</slash:comments><wfw:commentRss>http://devlicious.com/blogs/christopher_bennage/rsscomments.aspx?PostID=43807</wfw:commentRss><comments>http://devlicious.com/blogs/christopher_bennage/archive/2009/01/19/ui-patterns-for-wpf.aspx#comments</comments><description>&lt;p&gt;There’s a lot of &lt;a href="http://channel9.msdn.com/shows/Continuum/MVVM/"&gt;recent buzz&lt;/a&gt; about the &lt;em&gt;Model-View-ViewModel&lt;/em&gt; or &lt;em&gt;MVVM.&lt;/em&gt; (I pronounce it like it rhymes with &lt;em&gt;Auntie Em&lt;/em&gt;.) Rather timely for me as a lot of my thinking about implementing UI patterns in WPF has begun to coalesce.&lt;/p&gt;  &lt;p&gt;There’s has been a lot of thought given to UI patterns prior to the advent of WPF. Martin Fowler has a relatively &lt;a href="http://martinfowler.com/eaaDev/uiArchs.html"&gt;succinct historical overview&lt;/a&gt; of GUI architectures. I’d like to start here by discussing how these established patterns are mapped to WPF. After that, I’d like to explore how WPF allows us to improve on these patterns. We’re probably in for a series of posts here.&lt;/p&gt;  &lt;h2&gt;Why Patterns?&lt;/h2&gt;  &lt;p&gt;One guiding principle, both for testability’s sake as well as for myriad other reasons, is &lt;a href="http://martinfowler.com/eaaDev/SeparatedPresentation.html" target="_blank"&gt;Separated Presentation&lt;/a&gt;. This is a just a special case of the general principle &lt;a href="http://en.wikipedia.org/wiki/Separation_of_concerns" target="_blank"&gt;Separation of Concerns&lt;/a&gt;. We separate the concerns because they are easier to &lt;a title="this is my apology" href="http://devlicious.com/blogs/christopher_bennage/archive/2008/03/30/the-roots-of-best-practices.aspx"&gt;test, maintain, and extend&lt;/a&gt;.&lt;/p&gt;  &lt;p&gt;Let’s assume that you buy into the value of testability. The next problem is that UI code is notoriously difficult to test. This is a product of the way UI frameworks generally work. The common solution is to push as much behavior as possible into &lt;a href="http://en.wikipedia.org/wiki/Plain_Old_CLR_Object" target="_blank"&gt;Plain Old CLR Objects&lt;/a&gt; (POCO). In other words, if a class is tied to the UI framework, and thus is difficult to test, it should have as little logic in it as possible; instead that logic should be delegated to classes that are easier to test.&lt;/p&gt;  &lt;h2&gt;The Patterns&lt;/h2&gt;  &lt;p&gt;There are number of standard approaches, er, patterns, that have been recognized. My influences for interpreting&amp;#160; these patterns are Martin Fowler, Jeremy Miller, John Gossman, and Dan Crevier. &lt;/p&gt;  &lt;p&gt;&lt;a href="http://devlicious.com/cfs-file.ashx/__key/CommunityServer.Blogs.Components.WeblogFiles/christopher_5F00_bennage/registration_5F00_233140DF.png"&gt;&lt;img style="border-bottom:0px;border-left:0px;margin:0px;display:inline;border-top:0px;border-right:0px;" title="An example of the registration form" border="0" alt="An example of the registration form" align="right" src="http://devlicious.com/cfs-file.ashx/__key/CommunityServer.Blogs.Components.WeblogFiles/christopher_5F00_bennage/registration_5F00_thumb_5F00_2978176D.png" width="400" height="179" /&gt;&lt;/a&gt;I want to show you have these patterns look in code, so let’s establish a quick (and highly contrived) scenario. We have a registration form that accepts an email address, a password, and a confirmation of the password. There’s a button to initiate the registration, but the form has to be in a valid state in order for the button to be enabled. The rules are:&lt;/p&gt;  &lt;ul&gt;   &lt;li&gt;The email address cannot be blank. &lt;/li&gt;    &lt;li&gt;The password cannot be blank. &lt;/li&gt;    &lt;li&gt;The confirmation must match the password. &lt;/li&gt; &lt;/ul&gt;  &lt;p&gt;Now for the patterns…&lt;/p&gt;  &lt;h3&gt;The Autonomous View&lt;/h3&gt;  &lt;p&gt;This is what we don’t want to do, but usually do. All of the logic is in the code-behind. Very little is delegated out to other classes, and when it is, it is typically delegated to concrete types so that hard dependencies exist. It’s impossible to test with this pattern because it is impossible to&lt;em&gt; isolate the behavior&lt;/em&gt; that need to be tested. Here’s the &lt;a href="http://www.codeplex.com/wpfpatterns/SourceControl/changeset/view/4380#112128" target="_blank"&gt;xaml&lt;/a&gt; and the &lt;a href="http://www.codeplex.com/wpfpatterns/SourceControl/changeset/view/4380#112089" target="_blank"&gt;code-behind&lt;/a&gt;.&lt;/p&gt;  &lt;h3&gt;Model-View-Presenter&lt;/h3&gt;  &lt;p&gt;I’ve used the term MVP a lot. (&lt;a title="the Most Value Professional or some such thing, not a UI pattern" href="http://devlicious.com/blogs/rob_eisenberg/archive/2009/01/01/mvp-goodness.aspx" target="_blank"&gt;Hey, I am one now&lt;/a&gt;!) Fowler has suggested that MVP subsumes two more specific patterns (and that the term MVP should be retired in favor of them). Both of the child patterns have the same elements: a model, a view, and a presenter. Generally, the model is data that you are interested in, the view renders the data on screen, and the presenter handles all the “presentation concerns”. What constitutes “presentation concerns” though is part of what distinguishes the two child patterns.&lt;/p&gt;  &lt;h4&gt;Supervising Controller&lt;/h4&gt;  &lt;p&gt;The first of the MVP patterns is the supervising controller, or supervising presenter. (The terms controller and presenter are somewhat ambiguous themselves and are frequently interchanged.) The&amp;#160; presenter in the supervising presenter pattern has properties that interact with the view through data binding. Frequently, you’ll have simple event handlers (e.g., the click event for a button) that merely call methods on the presenter. (There is an alternative to the event handlers, but I’ll get to that later.) &lt;/p&gt;  &lt;p&gt;This pattern is easy to test because the presenter has most of the behavior for the UI and it is POCO. The deficit is that the view still contains some logic in the form of bindings.&lt;/p&gt;  &lt;p&gt;Notice here that we’ve introduced bindings into the &lt;a href="http://www.codeplex.com/wpfpatterns/SourceControl/changeset/view/4380#112098" target="_blank"&gt;xaml&lt;/a&gt; and that there is almost nothing in the &lt;a href="http://www.codeplex.com/wpfpatterns/SourceControl/changeset/view/4380#112126" target="_blank"&gt;code-behind&lt;/a&gt;. The real behavior is here in the &lt;a href="http://www.codeplex.com/wpfpatterns/SourceControl/changeset/view/4380#112132" target="_blank"&gt;presenter&lt;/a&gt;.&lt;/p&gt;  &lt;h4&gt;Passive View&lt;/h4&gt;  &lt;p&gt;This flavor of MVP squeezes out the remaining behavior out of the view. With this pattern you define an interface for the view that the presenter operates against. The implementation of the view interface has to be very simple, you want the absolute bare minimum in the view. The view is passive because it doesn’t know or do anything. The presenter handles all of the logic and manipulates the view. In WPF, you’ll end up with more code in the code-behind (because you are implementing the interface), but you can avoid bindings. Why do you want to avoid bindings? Because they are harder to tests… &lt;em&gt;or are they? &lt;/em&gt;More on that later.&lt;/p&gt;  &lt;p&gt;Here’s the view’s &lt;a href="http://www.codeplex.com/wpfpatterns/SourceControl/changeset/view/4380#112080" target="_blank"&gt;interface&lt;/a&gt;. Note that the &lt;a href="http://www.codeplex.com/wpfpatterns/SourceControl/changeset/view/4380#112138" target="_blank"&gt;code-behind&lt;/a&gt; is more involved, but the &lt;a href="http://www.codeplex.com/wpfpatterns/SourceControl/changeset/view/4380#112091" target="_blank"&gt;xaml&lt;/a&gt; no longer has bindings. Also, notice how the &lt;a href="http://www.codeplex.com/wpfpatterns/SourceControl/changeset/view/4380#112120" target="_blank"&gt;presenter&lt;/a&gt; has to know a lot more about the view.&lt;/p&gt;  &lt;h3&gt;A Warning&lt;/h3&gt;  &lt;p&gt;We all want patterns to be distinct and specific, but the reality is that they are blurry. Often you will be combining elements from various patterns in order to accomplish what you need to do. Don’t get hung up on implementing a pure pattern.&lt;/p&gt;  &lt;h3&gt;Presentation Model vs MVVM&lt;/h3&gt;  &lt;p&gt;Actually, I will pick up here next time. I need to give you a reason to come back, right? :-)&lt;/p&gt;  &lt;p&gt;If you are interested in the playing with the code examples, I’m posting it on &lt;a href="http://www.codeplex.com/wpfpatterns" target="_blank"&gt;CodePlex&lt;/a&gt;.&lt;/p&gt;&lt;div style="clear:both;"&gt;&lt;/div&gt;&lt;img src="http://devlicious.com/aggbug.aspx?PostID=43807" width="1" height="1"&gt;&lt;img src="http://feeds.feedburner.com/~r/ChristopherBennage/~4/FRjyZKnKHSk" height="1" width="1"/&gt;</description><category domain="http://devlicious.com/blogs/christopher_bennage/archive/tags/Design+Patterns/default.aspx">Design Patterns</category><category domain="http://devlicious.com/blogs/christopher_bennage/archive/tags/WPF/default.aspx">WPF</category><category domain="http://devlicious.com/blogs/christopher_bennage/archive/tags/Software+Architecture/default.aspx">Software Architecture</category><category domain="http://devlicious.com/blogs/christopher_bennage/archive/tags/TDD/default.aspx">TDD</category><category domain="http://devlicious.com/blogs/christopher_bennage/archive/tags/Best+Practices/default.aspx">Best Practices</category><category domain="http://devlicious.com/blogs/christopher_bennage/archive/tags/UI+Patterns/default.aspx">UI Patterns</category><feedburner:origLink>http://devlicious.com/blogs/christopher_bennage/archive/2009/01/19/ui-patterns-for-wpf.aspx</feedburner:origLink></item><item><title>Building a WPF Application: Part 6</title><link>http://feedproxy.google.com/~r/ChristopherBennage/~3/NLcwLGSMQTQ/building-a-wpf-application-part-6.aspx</link><pubDate>Tue, 13 Jan 2009 05:29:21 GMT</pubDate><guid isPermaLink="false">40756a8b-6212-4073-9d98-6c26781577de:43729</guid><dc:creator>Christopher Bennage</dc:creator><slash:comments>3</slash:comments><wfw:commentRss>http://devlicious.com/blogs/christopher_bennage/rsscomments.aspx?PostID=43729</wfw:commentRss><comments>http://devlicious.com/blogs/christopher_bennage/archive/2009/01/13/building-a-wpf-application-part-6.aspx#comments</comments><description>&lt;p&gt;&lt;a href="http://devlicious.com/blogs/christopher_bennage/pages/building-a-wpf-application-table-of-contents.aspx"&gt;&lt;em&gt;ChumChase Table of Contents&lt;/em&gt;&lt;/a&gt;&lt;/p&gt;  &lt;p&gt;I opened up the ChumChase code this evening with the sad realization that my last commits were on November 14th. Ouch. In reading over the code, something jumped out at me immediately. In the code-behind for Shell.xaml, I had a lot of logic that didn&amp;#39;t need to be there. It was clumsy and not tested, but at least I had left myself a comment to that effect.&lt;/p&gt;  &lt;p&gt;The code handled switching from the default view to the 3D view. If you don&amp;#39;t know what I&amp;#39;m talking about, go back and read the &lt;a href="http://devlicious.com/blogs/christopher_bennage/pages/building-a-wpf-application-table-of-contents.aspx"&gt;older posts&lt;/a&gt;. The important part of Shell.xaml looked like this:&lt;/p&gt;  &lt;pre class="xml:nogutter:nocontrols" name="code"&gt;&amp;lt;Grid&amp;gt;
    &amp;lt;ContentControl x:Name=&amp;quot;MainView&amp;quot; /&amp;gt;

    &amp;lt;Button Content=&amp;quot;Toggle View&amp;quot;
            VerticalAlignment=&amp;quot;Top&amp;quot;
            HorizontalAlignment=&amp;quot;Right&amp;quot;
            Click=&amp;quot;ToggleView_Click&amp;quot; /&amp;gt;
&amp;lt;/Grid&amp;gt;&lt;/pre&gt;

&lt;p&gt;and the handler for the click (along with a dependent method) looked like this:&lt;/p&gt;

&lt;pre class="c#:nogutter:nocontrols" name="code"&gt;private void ToggleView_Click(object sender, RoutedEventArgs e)
{
    if (MainView.Content is DefaultFeedView)
    {
        SetView(new _2Don3DView());
    }
    else
    {
        SetView(new DefaultFeedView());
    }
}

private void SetView(IFeedView view)
{
    MainView.Content = view;
    view.RefreshButton.Click += Refresh_Click;
}&lt;/pre&gt;

&lt;p&gt;Yes, _2Don3DView is &lt;em&gt;not&lt;/em&gt; a good name. I&amp;#39;ll &lt;a title="I mean, I just couldn&amp;#39;t stop laughing..." href="http://www.hulu.com/watch/38477/saturday-night-live-update-thursday-fix-it-109"&gt;fix it&lt;/a&gt;. Aside from the appalling appellation, this code is not very WPF-ish. What is it doing anyway?&lt;/p&gt;

&lt;p&gt;&lt;a href="http://msdn.microsoft.com/en-us/library/system.windows.controls.contentcontrol.aspx"&gt;ContentControl&lt;/a&gt; is really a place holder. It represents the area in the application&amp;#39;s shell where we want to stick the main content. In the handler, we check to see what is currently in the placeholder and we switch it out. Since each view had it&amp;#39;s own button for refreshing the feed we needed to wire it up each time we switched the view. (Remember this way is naughty-naughty.) Our views implemented IFeedView so we could access their respective Refresh buttons.&lt;/p&gt;

&lt;h4&gt;A More Excellent Way&lt;/h4&gt;

&lt;p&gt;My ApplicationController class should really be responsible for this behavior. In order to make that happen, I created a property on it called CurrentPresenter. This property is the presenter that will back the current view. (A &lt;em&gt;presenter&lt;/em&gt; is a class that contains the logic for a portion of the UI, the corresponding &lt;em&gt;view&lt;/em&gt; is the visual part used to render that presenter.) Since the data context for Shell.xaml is already set to an instance of ApplicationController (it&amp;#39;s named _controller in the code-behind), I was able to changed the markup to look like this:&lt;/p&gt;

&lt;pre class="xml:nogutter:nocontrols" name="code"&gt;&amp;lt;Grid&amp;gt;
    &amp;lt;ContentControl Content=&amp;quot;{Binding CurrentPresenter}&amp;quot; /&amp;gt;

    &amp;lt;Button Content=&amp;quot;Toggle View&amp;quot;
            VerticalAlignment=&amp;quot;Top&amp;quot;
            HorizontalAlignment=&amp;quot;Right&amp;quot;
            Click=&amp;quot;ToggleView_Click&amp;quot; /&amp;gt;
&amp;lt;/Grid&amp;gt;&lt;/pre&gt;

&lt;p&gt;and then the event handler to this:&lt;/p&gt;

&lt;pre class="c#:nogutter:nocontrols" name="code"&gt;private void ToggleView_Click(object sender, RoutedEventArgs e)
{
    _controller.ToggleView();
}&lt;/pre&gt;

&lt;p&gt;And now, let&amp;#39;s examine the tests for the desired behavior. I wanted ToggleView to alternate between an instance of DefaultFeedPresenter and an instance of _2Don3DPresenter. (Bad Christopher, bad!) I did not want ToggleView to create new instances, but to reuse existing ones.&lt;/p&gt;

&lt;pre class="c#:nogutter:nocontrols" name="code"&gt;[TestFixture]
public class The_application_controller
{
    [SetUp]
    public void given_a_context_of()
    {
        // stuff omitted for brevity //
        _controller = new ApplicationController();
    }

    [Test]
    public void raises_change_notification()
    {
        _controller
            .AssertThatAllProperties()
            .RaiseChangeNotification();
    }

    [Test]
    public void uses_the_expected_presenter_by_default()
    {
        Assert.That(_controller.CurrentPresenter, Is.InstanceOfType(typeof(DefaultFeedPresenter)));
    }

    [Test]
    public void toggles_to_the_3D_view_when_the_default_is_current()
    {
        _controller.ToggleView();
        Assert.That(_controller.CurrentPresenter, Is.InstanceOfType(typeof(_2Don3DPresenter)));
    }

    [Test]
    public void toggles_to_the_default_when_the_3D_view_is_current()
    {
        var default_presenter = _controller.CurrentPresenter;
        _controller.CurrentPresenter = new _2Don3DPresenter(_controller);
        _controller.ToggleView();

        Assert.That(_controller.CurrentPresenter, Is.EqualTo(default_presenter));
    }
}&lt;/pre&gt;

&lt;p&gt;&lt;em&gt;Ooo, hey, what&amp;#39;s that first test? That raises notification bit? Oh, that just some cool stuff in &lt;/em&gt;&lt;a href="http://www.codeplex.com/caliburn"&gt;&lt;em&gt;Caliburn&lt;/em&gt;&lt;/a&gt;&lt;em&gt;, you can read more about that &lt;/em&gt;&lt;a href="http://www.codeplex.com/caliburn/Wiki/View.aspx?title=Unit%20Testing%20Property%20Change%20Notification&amp;amp;referringTitle=Table%20Of%20Contents"&gt;&lt;em&gt;here&lt;/em&gt;&lt;/a&gt;&lt;em&gt;.&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;I added the following lines to ApplicationController in order to pass these tests:&lt;/p&gt;

&lt;pre class="c#:nogutter:nocontrols" name="code"&gt;private readonly IList&amp;lt;IPresenter&amp;gt; _presenters = new List&amp;lt;IPresenter&amp;gt;();
private IPresenter _currentPresenter;

public IPresenter CurrentPresenter
{
    get { return _currentPresenter; }
    set
    {
        _currentPresenter = value;
        RaisePropertyChanged(&amp;quot;CurrentPresenter&amp;quot;);
    }
}

public void ToggleView()
{
    CurrentPresenter = (CurrentPresenter is DefaultFeedPresenter)
        ? _presenters[1]
        : _presenters[0];
}&lt;/pre&gt;

&lt;p&gt;I initialized _presenters in the constructor for ApplicationController with the instances of the presenters. (I was tempted here to introduce an IoC container, but I didn&amp;#39;t. We&amp;#39;ll talk more about that later.)&lt;/p&gt;

&lt;p&gt;So now, when ToggleView is called, the CurrentPresenter property is updated and change notification is raised, but what happens in the UI? How does it render the presenter instances? Well, given the markup from Shell.xaml we listed above, it doesn&amp;#39;t do anything.&lt;/p&gt;

&lt;h4&gt;I Love DataTemplates So Much, Why Don&amp;#39;t I Marry Them?&lt;/h4&gt;

&lt;p&gt;We need to tell WPF how to render each presenter. We already have user controls that define each view. We can reuse those. I added the following to the Grid containing my ContentControl:&lt;/p&gt;

&lt;pre class="c#:nogutter:nocontrols" name="code"&gt;&amp;lt;Grid.Resources&amp;gt;
    &amp;lt;DataTemplate DataType=&amp;quot;{x:Type Model:DefaultFeedPresenter}&amp;quot;&amp;gt;
        &amp;lt;Views:DefaultFeedView /&amp;gt;
    &amp;lt;/DataTemplate&amp;gt;
    &amp;lt;DataTemplate DataType=&amp;quot;{x:Type Model:_2Don3DPresenter}&amp;quot;&amp;gt;
        &amp;lt;Views:_2Don3DView /&amp;gt;
    &amp;lt;/DataTemplate&amp;gt;
&amp;lt;/Grid.Resources&amp;gt;&lt;/pre&gt;

&lt;p&gt;The DataType property tells WPF that anything bound to an instance of the given type should use the template. Since I placed these in the resources for the grid, it will affect any bindings inside the grid. Each data template simply contains the corresponding user control. I could have inlined the user controls, but I already had tests in place and I believe this makes the markup easier to read.&lt;/p&gt;

&lt;p&gt;In making these changes, I did break something. Something that was not being tested... but it&amp;#39;s time for bed so I&amp;#39;ll leave that for another night. &lt;/p&gt;

&lt;p&gt;More to come!&lt;/p&gt;&lt;div style="clear:both;"&gt;&lt;/div&gt;&lt;img src="http://devlicious.com/aggbug.aspx?PostID=43729" width="1" height="1"&gt;&lt;img src="http://feeds.feedburner.com/~r/ChristopherBennage/~4/NLcwLGSMQTQ" height="1" width="1"/&gt;</description><category domain="http://devlicious.com/blogs/christopher_bennage/archive/tags/Design+Patterns/default.aspx">Design Patterns</category><category domain="http://devlicious.com/blogs/christopher_bennage/archive/tags/DataBinding/default.aspx">DataBinding</category><category domain="http://devlicious.com/blogs/christopher_bennage/archive/tags/WPF/default.aspx">WPF</category><category domain="http://devlicious.com/blogs/christopher_bennage/archive/tags/TDD/default.aspx">TDD</category><category domain="http://devlicious.com/blogs/christopher_bennage/archive/tags/data+binding/default.aspx">data binding</category><category domain="http://devlicious.com/blogs/christopher_bennage/archive/tags/ChumChase/default.aspx">ChumChase</category><category domain="http://devlicious.com/blogs/christopher_bennage/archive/tags/data+templates/default.aspx">data templates</category><feedburner:origLink>http://devlicious.com/blogs/christopher_bennage/archive/2009/01/13/building-a-wpf-application-part-6.aspx</feedburner:origLink></item><item><title>Tally UG Follow-up - Silverlight Game Dev</title><link>http://feedproxy.google.com/~r/ChristopherBennage/~3/U9Ka47QiOqw/tally-ug-follow-up-silverlight-game-dev.aspx</link><pubDate>Sun, 11 Jan 2009 02:19:00 GMT</pubDate><guid isPermaLink="false">40756a8b-6212-4073-9d98-6c26781577de:43711</guid><dc:creator>Christopher Bennage</dc:creator><slash:comments>0</slash:comments><wfw:commentRss>http://devlicious.com/blogs/christopher_bennage/rsscomments.aspx?PostID=43711</wfw:commentRss><comments>http://devlicious.com/blogs/christopher_bennage/archive/2009/01/10/tally-ug-follow-up-silverlight-game-dev.aspx#comments</comments><description>&lt;p&gt;I appreciate everyone who came out for my session on game development in Silverlight. &lt;/p&gt;  &lt;p&gt;Here is &lt;a href="http://www.bluespire.com/samples/spaceinvaders.zip"&gt;the code&lt;/a&gt; we wrote during the session. It&amp;#39;s &lt;em&gt;not&lt;/em&gt; pretty, and if you weren&amp;#39;t at the present, I expect it will be hard to follow. I hope to have a cleaner version published&amp;#160; soon. (So much to do!)&lt;/p&gt;  &lt;p&gt;Some resources that might be useful for your game development efforts:&lt;/p&gt;  &lt;ul&gt;   &lt;li&gt;&lt;a title="and home of Dr. Popper!" href="http://www.bluerosegames.com/silverlight-games-101/"&gt;Blue Rose Games&lt;/a&gt; - a blog about Silverlight game development in general&lt;/li&gt;    &lt;li&gt;&lt;a href="http://www.andybeaulieu.com/Default.aspx?tabid=67&amp;amp;EntryID=95"&gt;Andy Beaulieu&lt;/a&gt; on collision detection. Be sure to check out the rest of his blog, as there is lots more on Silverlight game dev.&lt;/li&gt; &lt;/ul&gt;  &lt;p&gt;You&amp;#39;ll see the influence of both of those blogs in the code from the session.&lt;/p&gt;  &lt;p&gt;Also, for the Flash crossover guys who were present,&lt;/p&gt;  &lt;ul&gt;   &lt;li&gt;&lt;a href="http://www.shinedraw.com/"&gt;Shine Draw&lt;/a&gt; does regular comparisons of Flash and Silverlight.&lt;/li&gt;    &lt;li&gt;&lt;a href="http://channel9.msdn.com/continuum/tutorials/"&gt;Project Rosetta&lt;/a&gt; is a set of Silverlight tutorials design for Flash guys.&lt;/li&gt; &lt;/ul&gt;&lt;div style="clear:both;"&gt;&lt;/div&gt;&lt;img src="http://devlicious.com/aggbug.aspx?PostID=43711" width="1" height="1"&gt;&lt;img src="http://feeds.feedburner.com/~r/ChristopherBennage/~4/U9Ka47QiOqw" height="1" width="1"/&gt;</description><category domain="http://devlicious.com/blogs/christopher_bennage/archive/tags/Game+Development/default.aspx">Game Development</category><category domain="http://devlicious.com/blogs/christopher_bennage/archive/tags/Silverlight/default.aspx">Silverlight</category><category domain="http://devlicious.com/blogs/christopher_bennage/archive/tags/Presentations/default.aspx">Presentations</category><feedburner:origLink>http://devlicious.com/blogs/christopher_bennage/archive/2009/01/10/tally-ug-follow-up-silverlight-game-dev.aspx</feedburner:origLink></item><item><title>TDD Firestarter in Tampa</title><link>http://feedproxy.google.com/~r/ChristopherBennage/~3/P3Koq-qFt4g/tdd-firestarter-in-tampa.aspx</link><pubDate>Wed, 07 Jan 2009 22:12:10 GMT</pubDate><guid isPermaLink="false">40756a8b-6212-4073-9d98-6c26781577de:43668</guid><dc:creator>Christopher Bennage</dc:creator><slash:comments>2</slash:comments><wfw:commentRss>http://devlicious.com/blogs/christopher_bennage/rsscomments.aspx?PostID=43668</wfw:commentRss><comments>http://devlicious.com/blogs/christopher_bennage/archive/2009/01/07/tdd-firestarter-in-tampa.aspx#comments</comments><description>&lt;p&gt;The new year has already gotten away from me and it&amp;#39;s only 7 days old. (&lt;a title="We watch a lot of Rankin\Bass over the holidays." href="http://en.wikipedia.org/wiki/Rudolph&amp;#39;s_Shiny_New_Year"&gt;Come back, Baby Happy!&lt;/a&gt;)&lt;/p&gt;  &lt;p&gt;&lt;b&gt;&lt;a href="http://devlicious.com/cfs-file.ashx/__key/CommunityServer.Blogs.Components.WeblogFiles/christopher_5F00_bennage/iStock_5F00_000000370181XSmall12_5F00_00046DA5.jpg"&gt;&lt;img style="border-bottom:0px;border-left:0px;display:inline;margin-left:0px;border-top:0px;margin-right:0px;border-right:0px;" border="0" alt="strike a match" align="right" src="http://devlicious.com/cfs-file.ashx/__key/CommunityServer.Blogs.Components.WeblogFiles/christopher_5F00_bennage/iStock_5F00_000000370181XSmall12_5F00_thumb_5F00_6B9EA819.jpg" width="300" height="220" /&gt;&lt;/a&gt;&lt;/b&gt;In less than 2 weeks from now, we&amp;#39;re going to a have full day of TDD in Tampa, FL. The event is designed so that everyone will find value, whether you are merely curious about methodology or a veteran practitioner.&lt;/p&gt;  &lt;p&gt;We&amp;#39;re starting off the day with introductory and intermediate session on TDD and following it up with some very focused sessions in the afternoon. (I&amp;#39;m going to be talking about doing TDD with WPF and I&amp;#39;ll be using a little bit o&amp;#39; &lt;a title="ye olde Caliburn, freed from the stone" href="http://www.codeplex.com/caliburn"&gt;Caliburn&lt;/a&gt; as well.)&amp;#160;&amp;#160; &lt;/p&gt;  &lt;p&gt;&lt;b&gt;Saturday, January 17, 2009&lt;/b&gt;&lt;/p&gt;  &lt;p&gt;&lt;b&gt;9:00 AM–5:00PM&lt;/b&gt;&lt;/p&gt;  &lt;p&gt;&lt;b&gt;&lt;/b&gt;&lt;/p&gt;  &lt;p&gt;&lt;a href="http://msevents.microsoft.com/CUI/EventDetail.aspx?EventID=1032397083&amp;amp;culture=en-US"&gt;Click here to register&lt;/a&gt; or call (877) 673-8368 with event ID 1032397083&lt;strong&gt;.&lt;/strong&gt;&lt;/p&gt;  &lt;p&gt;Speakers include &lt;a href="http://www.cornetdesign.com/"&gt;Cory Foy&lt;/a&gt;, &lt;a href="http://scottcreynolds.lostechies.com/"&gt;Scott C. Reynolds&lt;/a&gt;, &lt;a href="http://schambers.lostechies.com/"&gt;Sean Chambers&lt;/a&gt;, and &lt;a href="http://devlicio.us/blogs/rob_eisenberg"&gt;Rob Eisenberg&lt;/a&gt;.&lt;/p&gt;  &lt;p&gt;Please come out and join us! Did I mention it&amp;#39;s &lt;em&gt;free&lt;/em&gt;?&lt;/p&gt;  &lt;p&gt;More information &lt;a title="but haven&amp;#39;t I told you everyting that&amp;#39;s important?" href="http://tddfirestarter.lostechies.com/blogs/news/archive/2008/12/08/tdd-firestarter-conference-information-and-registration.aspx"&gt;here&lt;/a&gt;...&lt;/p&gt;&lt;div style="clear:both;"&gt;&lt;/div&gt;&lt;img src="http://devlicious.com/aggbug.aspx?PostID=43668" width="1" height="1"&gt;&lt;img src="http://feeds.feedburner.com/~r/ChristopherBennage/~4/P3Koq-qFt4g" height="1" width="1"/&gt;</description><category domain="http://devlicious.com/blogs/christopher_bennage/archive/tags/TDD/default.aspx">TDD</category><category domain="http://devlicious.com/blogs/christopher_bennage/archive/tags/Presentations/default.aspx">Presentations</category><category domain="http://devlicious.com/blogs/christopher_bennage/archive/tags/Events/default.aspx">Events</category><feedburner:origLink>http://devlicious.com/blogs/christopher_bennage/archive/2009/01/07/tdd-firestarter-in-tampa.aspx</feedburner:origLink></item><item><title>a method to the madness?</title><link>http://feedproxy.google.com/~r/ChristopherBennage/~3/6yqEemdD4W4/a-method-to-the-madness.aspx</link><pubDate>Sat, 13 Dec 2008 21:50:08 GMT</pubDate><guid isPermaLink="false">40756a8b-6212-4073-9d98-6c26781577de:43404</guid><dc:creator>Christopher Bennage</dc:creator><slash:comments>0</slash:comments><wfw:commentRss>http://devlicious.com/blogs/christopher_bennage/rsscomments.aspx?PostID=43404</wfw:commentRss><comments>http://devlicious.com/blogs/christopher_bennage/archive/2008/12/13/a-method-to-the-madness.aspx#comments</comments><description>&lt;pre class="rb:nogutter:nocontrols" name="code"&gt;class Madness
 def method_missing(method, *args)
  nil
 end
end&lt;/pre&gt;

&lt;p&gt;In full disclosure, my ruby is all stinky bad. I solicited this joke from my good friend Jeremy Walworth (founder of the internationally renown website, &lt;a href="http://www.hairforecast.com/"&gt;hairforecast.com&lt;/a&gt;.)&lt;/p&gt;&lt;div style="clear:both;"&gt;&lt;/div&gt;&lt;img src="http://devlicious.com/aggbug.aspx?PostID=43404" width="1" height="1"&gt;&lt;img src="http://feeds.feedburner.com/~r/ChristopherBennage/~4/6yqEemdD4W4" height="1" width="1"/&gt;</description><category domain="http://devlicious.com/blogs/christopher_bennage/archive/tags/humor/default.aspx">humor</category><category domain="http://devlicious.com/blogs/christopher_bennage/archive/tags/ruby/default.aspx">ruby</category><feedburner:origLink>http://devlicious.com/blogs/christopher_bennage/archive/2008/12/13/a-method-to-the-madness.aspx</feedburner:origLink></item></channel></rss>
