Wednesday, June 22, 2011

WPF UserControl .cs file compilation error

I've met a very interesting WPF bug today, something that is hard to explain or reproduce, but might give terrible headaches if you don't know its source.

I had a WPF UserControl, with its xaml and cs files. Now, I know that in MVVM I shouldn't really use those much, but it was out of my control. The control had a section of resources (UserControl.Resources) in which there was a ResourceDictionary with some stuff in it. Considering that I'd removed all the merged dictionaries from this, I thought that I had no need of the dictionary tags, after all the Resources property of an element is already a ResourceDictionary. So it was something like this:

<UserControl ... >
<UserControl.Resources>
<!-- <ResourceDictionary> with these tags commented the error occurs -->
... stuff ...
<!-- </ResourceDictionary> -->
</UserControl.Resources>
</UserControl>

The error itself is that, during compilation, the partial user control class defines in the code behind doesn't seem to find things from the xaml. Probably, the compiler fails building the xaml into a class, but fails silently, while the codebehind is completely disconnected from the xaml because it is the only partial file for that class name.

By selectively removing items in the resources I've narrowed it down to one of the converters. It was creating using the MarkupExtension trick, but it was also declared as a resource for some reason. I do not see why that should matter, but still.

Bottom line: when the partial codebehind class for a WPF user control (or maybe for windows as well) fails to connect to the xaml, it means it silently fails the compilation of the XAML and you should try checking the resources of the elements therein.

Star Trek Deep Space 9

I've just finished watching the seven seasons of Star Trek DS9. I've decided to do it since I've only seen it on TV when I was younger and never from start to finish. Frankly, when I think about it, watching anything on TV, waiting for it to start at specific hours and then having no possibility to pause, stop or fast forward (not to mention the idiotic commercials), seems insane. But I digress.

What I found most interesting in this Star Trek series is that it showed so many pieces of technology that are now available. However, they were doing it wrong :) Let's take the "pad". They were using something looking like IPads. However, they were using multiple pads, one for each of the things they were reading or working on! Or they had these very complex communication systems: a badge that acted as a communicator, holographic video calls, screens everywhere. Yet whenever something was happening, they were calling the other person to come to them: "Captain, I think you'll want to see this". You can't really expect technical perspective from TV designer people, but they were so bloody close!

Another interesting thing, and that goes for the entire Star Trek franchise, is how they split the human mentality into clich├ęs, made entire races out of them, then explored each one in particular. That is different from making the heroes be envomittingly good and the bad people nauseatingly evil. They took the mercantile personality, pushed it to an extreme, then built the Ferengi species around it. I still don't get how they did it without the Hollywood higherups shouting racism, since the race was clearly modelled after Jews. The Klingons were fierce warriors, honourable and brave. The Romulans were sneaky. The Kardasians were imperial invaders. And so on and so on.

But then, they explored each of these human traits and readded depth from the places where they took it. What happens with Ferengis when their lives are at stake or when their friends are in peril? What do Klingons do when imperial leaders become more and more political and corrupt? What do the worst enemies when they are forced to fight or work together and find themselves in the very situations they has previously forced the other to be? As far as I know, this is the only show that did this. The few other multispecies sci fi series, like Babylon 5, centered on the story more than on the characters.

As for what differentiates DS9 from the other Star Trek series, it's the grit. I suppose that is why it didn't have that much success with the audience, as it was a decent show with some deep (pardon the pun) ideas. It did had its sillyness: the entire Bajoran faith thing, with the alien Prophets intervening whenever the script went nowhere, the episodes about the crew getting to the past or locked in some holodeck fantasy or being mentally manipulated, all so that they get to act in present day situations that had nothing to do with the show. The silliest thing yet, I believe, are the fights. The ridiculous fighting style of the Federation "elites" and the ships that either resist dozens of hits or die from a single one.

I believe that there is much to be learned from Star Trek, from a television and scifi perspective, and DS9 specifically. We lack a space opera with real war scenes and actual grit.

Pro ASP.Net MVC Framework by Steven Sanderson

Book coverI've finally finished reading Pro ASP.Net MVC Framework by Steven Sanderson. The book is slightly dated, since it discusses the technology used in Visual Studio 2008 and without any mention of the new Razor engine, but these are details that are not important to the content of the book anyway. I can say that it is a very nice book and it was worth reading, especially the first part.

There are two parts to this, the first being a TDD ASP.Net MVC web shop application built step by step and explained line by line. It goes through some Domain Driven Design concepts as well, it does unit testing and mocking, even shows off a little dependency injection via Castle Windsor. What I liked most, though, is how painstakingly thorough Sanderson was explaining every single detail. He didn't assume anything as he documented every step of the way, down to what lambda expressions are and what .Net features he was using.

The second part of the book is a little less readable, as it goes through the classes and features of ASP.Net MVC, complete with methods, properties and small samples. I highly recommend reading this part while actually experimenting with the framework on the computer. Even if you do not, this part of the book remains a very valuable reference for when you do. In this section of the book you can learn about data entry, Ajax and partial updates, application security and deployment, even how to mix classic ASP.Net with MVC, though not really recommended.

The bottom line is that Pro ASP.Net MVC Framework is a must read for a developer learning ASP.Net MVC. There is an updated version of the book for VS2010 and .Net 4 that I think that I will also read (the book was so good). Here is the link for Pro ASP.NET MVC 2 Framework.

Tuesday, June 21, 2011

ContentControl and ContentPresenter do not propagate their DataContext to their Content

A quick post here about using a ContentPresenter (or a ContentControl which uses a ContentPresenter in its template) with its Content property. The intended usage of ContentPresenter is to set the Content to some binding to a data object, then control the element tree via the ContentTemplate property. That may lead to a counterintuitive situation when you want to specify some UI element content and then use bindings in that content. Let's take an example:

<!--
This ContentControl has a MainViewModel class as a DataContext.
The MainViewModel class exposes a MyButtonCommand property.
-->
<ContentControl>
<ContentControl.Content>
<Button Command="{Binding MyButtonCommand}">Press me!</Button>
</ContentControl.Content>
</ContentControl>
You may expect to press the button and execute the command, but it doesn't work. In fact, the binding on the Command property will fail.

Here is a working example:

<!--
This ContentControl has a MainViewModel class as a DataContext.
The MainViewModel class exposes a MyButtonCommand property.
-->
<ContentControl Content="{Binding MyButtonCommand}">
<ContentControl.ContentTemplate>
<DataTemplate>
<Button Command="{Binding}">Press me!</Button>
</DataTemplate>
</ContentControl.ContentTemplate>
</ContentControl>


I realize this is not what most of you have in mind when using a ContentControl. Another solution is to use the Content as in the first example, but add an explicit DataContext property to it before using any binding, something like this:

<!--
This ContentControl has a MainViewModel class as a DataContext.
The MainViewModel class exposes a MyButtonCommand property.
-->
<ContentControl>
<ContentControl.Content>
<DataTemplate>
<Button
DataContext="{Binding DataContext,RelativeSource={RelativeSource AncestorType={x:Type ContentControl}}}"
Command="{Binding MyButtonCommand}">Press me!</Button>
</DataTemplate>
</ContentControl.Content>
</ContentControl>
In this case, though, you specify the DataContext as an ugly binding and, worst of all, you cannot set it via the ContentControl, but you need to access the actual content.

Perhaps another solution, one that would involve a custom DataTemplateSelector on the ContentControl would work, but right now I have no perfectly satisfactory solution.

Saturday, June 18, 2011

WPF Hyperlinks and the IsEnabled mystery

A colleague of mine started using a control I made in which there was a Hyperlink. Well, the purpose of it was not complex, I just needed a text that can be clicked. A Hyperlink sounded like the only solution out of the box, since there is no LinkButton control in the standard WPF controls. That aside, after I finish writing this blog post, I will write myself a LinkButton control to use in these situations instead, since Hyperlink seems to have several design flaws. It's not even a control, but a flow element.

What my colleague reported is that the Hyperlink would not get enabled in certain situations and we've come to the conclusion that after the initialization of the control, the IsEnabled property on the Hyperlink does not change when an ancestor control changes its enabledness. The only way to force it is to actually bind it to an ancestor IsEnabled.

Here is the scenario: You place several items in a XAML file. They are a text in a Hyperlink, in a TextBlock (since Hyperlinks cannot be directly part of a Panel, first design flaw), in a StackPanel. The text in the text block will appear as a clickable link. Set the StackPanel to IsEnabled="False" and the text will appear as disabled. Now, add a ToggleButton and bind its IsChecked property to the StackPanel IsEnabled property. Click the button and the StackPanel will get disabled, but not the hyperlink. Start with a disabled StackPanel, the link will be disabled, click the button and the hyperlink will stay disabled. The solution: set on the Hyperlink, inline or via a style, IsEnabled="{Binding IsEnabled,RelativeSource={RelativeSource AncestorType={x:FrameworkElement}}}". Now that is ugly.

As a sideline, whenever you see a WPF element inexplicably disabled and you use Snoop on it and try to set IsEnabled to true and you can't, there is probably one of two situations:
  1. A parent of the control is disabled
  2. The control is implementing ICommandSource and its Command property is set on an ICommand that returns false on its CanExecute method

Monday, June 13, 2011

Not dead, not alive, meet the undead (yet fashionable) Siderite

Well, I have been kind of absent from the blog lately and that is for several reasons. One is that I have been waiting for some news that would determine my direction as a professional developer. The other is that I have re-acquired a passion for chess. So, between work at the office, watching chess videos, playing chess with my PDA and watching all seven seasons of Star Trek Deep Space 9, I haven't had much time for blogging.

Also, when you think about it, the last period of my programming life has been in some sort of a limbo: switched from ASP.Net to WPF, then to ASP.Net again (while being promised it would be temporary), then back to WPF (but in a mere executive position). Meanwhile, Microsoft didn't do much to help me, and thus saw their profits plummet. Well, maybe it was a coincidence, but what if it wasn't?

I am complaining about Microsoft because I was so sold into the whole WPF/Silverlight concept, while I was totally getting fed up with web work. Yet WPF is slow, with no clear development pathway when using it, while Silverlight is essentially something else, supported by only a few platforms, and I haven't even gotten around to use it yet. And now the Internet Explorer 9/Windows 8 duo come in force placing Javascript and HTML5 in the forefront again. Check out this cool ArsTechnica blog post about Microsoft's (re)new(ed) direction.

All of this, plus the mysterious news I have been waiting for that I won't detail (don't want to jinx it :-S), but which could throw me back into the web world, plus the insanity with the mobile everything that has only one common point: web. Add to it the not too enthusiastic reaction of my blog readers when starting talking about WPF. So the world either wants web or I just have been spouting one stupid thing after another and blew my readers away.

All these shining signs pointing me towards web development also say that I should be relearning web dev with ASP.Net MVC, getting serious about Javascript, relearning HTML in its 5th incarnation and finally making some sense of CSS. Exciting and crazy at the same time. Am I getting too old for this shit or am I ready for the challenge? We'll just have to see, won't we?