DCSIMG
September 2010 - Posts - Pavel's Blog
Sign in | Join | Help

Pavel's Blog

Pavel is a software guy that is interested in almost everything
software related... way too much for too little time

September 2010 - Posts

WPF Tip: Working with ContentPresenter

Published at Sep 26 2010, 04:05 PM by pavely

When creating control templates, there is often a need to place an arbitrary content (of type object) in some location. Usually this is identified by a Content property (such as from ContentControl), but sometimes it’s some other property. The ContentPresenter class allows placing such arbitrary content that follows a few rules:

1. If the value is a string, render it as a TextBlock.

2. If the value is of a a UIElement derived type – render it as is.

3. Otherwise, if a ContentTemplate property exists and not null, use it. Otherwise, render it as a TextBlock with a Text equal to a ToString call.

In the ContentPresenter declaration, the Content needs to be specified by a TemplateBinding, as well as for ContentTemplate and ContentTemplateSelector. This is annoying, prone to errors and simple omissions.

This is where the ContentSource property comes in: Just set its value to the required property, e.g. “Content” or “Header” or whatever – and the ContentPresenter will automatically use that value appended with “Template” and “TemplateSelector” as well as getting the actual content.

So, instead of typing:

<ContentPresenter Content="{TemplateBinding Header}" ContentTemplate="{TemplateBinding HeaderTemplate}" 
ContentTemplateSelector="{TemplateBinding HeaderTemplateSelector}" />

One can simply say:

<ContentPresenter ContentSource="Header" />

How To Be a Cool C++ Programmer / Developer

Published at Sep 13 2010, 10:28 PM by pavely

A few weeks ago I blogged about how to be a cool C# programmer. if you are a C++ programmer, you can be cool, too. The next C++ standard, dubbed C++0x promises many enhancements and cool abilities, but in this post I’ll stick with the current C++ standard. Here are some ways of being a cool C++ programmer (in no particular order):

1. Zeroing out a structure and setting its first field in one swoop

One of the common needs in a native Windows applications is setting up structures in preparation for calling some API function. Most of those structures need to be zeroed out, except the first field that needs to be set to the size of the structure. This is a typical Windows programming idiom that helps deal with versioning issues (if the structure grows in a subsequent release or service pack, the implementation can read only as many fields as are relevant).

We can do that with a call to memset followed by setting the relevant field name (usually called cb, cbSize or nLength) to the size of the structure. But there is a quicker, more elegant way, which, in fact, is part of the C standard (not even C++).

For example, instead of writing (in preparation for calling CreateProcess):

STARTUPINFO si;

::memset(&si, 0, sizeof(si));

si.cb = sizeof(si);

 

You can write:

STARTUPINFO si = { sizeof(si) };

 

How cool is that?

 

2. Use const whenever possible

Many C++ developers know about const member functions – functions that declare they don’t change any member variables – but too few are actually using it. So, to be cool use it whenever possible, not only for the coolness, of course, but because it promotes a kind of “local immutability”, and more practically, allows const objects to execute these functions (and no others).

Using const (not just for member functions) is cool, too: For example, instead of:

char* greeting = "hello";

 

should be:

const char* greeting = "hello";

 

Which is not just cool, but more correct.

 

3. Use the mutable keyword where appropriate

Having said all that about const, there is a little known keyword called mutable that allows const member functions to change those member variables marked with mutable. This seems like a backdoor to circumventing const, and technically it is. It’s useful for distinguishing "physical const-ness” from “logical const-ness”. Sometimes they are not the same. Consider this simple code:

class Dictionary {

public:

   string find(const string& key) const;

 

private:

   //...

   mutable string cached_key, cached_value;

};

The find member function does not logically change the dictionary’s contents, but it wants to keep a cache of the last searched item (for instance), so it needs to update the cached_key and cached_value members. This can only be done when mutable is used.

 

4. Use the explicit keyword

Yet another infrequently and less known used keyword. This one can only be used in a converting constructor, that is, a constructor that accepts a single argument. This kind of constructor is invoked automatically if an object of that argument type is supplied where the actual type is expected. An example will illustrate:

class Database {

public:

   Database(const char* path);

   // other members

   Database();

};

 

void foo() {

   Database db;

   db = Database("hello.dat");

   // same deal

   db = "hello.dat";

}

 

The last line works because of the converting constructor, but it seems illogical to construct an entire database just to call the assignment operator with that. It also results in creation and destruction of temporaries that may be expensive. The explicit keyword makes that forbidden:

class Database {

public:

   explicit Database(const char* path);

   // other members

   Database();

};

 

void foo() {

   Database db;

   db = Database("hello.dat");

   // does not compile!

   db = "hello.dat";

}

 

5. Template Meta programming

This is a hot one. It can make you look cool, but too much of it and it will give you a C++ freak reputation that makes you less than cool – you may be expelled from your C++ peer group. Here’s an example of one basic idea (don’t freak out):

template<int N>

struct Factorial {

   enum { Result = Factorial<N-1>::Result * N };

};

 

template<>

struct Factorial<1> {

   enum { Result = 1 };

};

 

int _tmain(int argc, _TCHAR* argv[]) {

   cout << Factorial<5>::Result << endl;

}

If you’re getting a feeling like “recursion” – you’re right; but it’s a different kind of recursion – it’s compile time recursion. There are no loops possible during compilation, so recursion is the only way to go. This is done by template specialization.

This is just the tip of the iceberg in template meta programming. Check out more in the boost libraries, and other sources. Be careful, though, this may be a dangerous road, and a lonely one at that.

 

6. functors

Functors, or function objects are just that: objects pretending to be functions. Technically, using them in C++ is pretty easy: just overload the function call operator(). Here’s a simple example:

int quad(int x) {

   return x * x + 4 * x - 10;

}

 

void foo() {

   vector<int> v;

   //...

   // transforms the vector into x*x+4*x-10 for each item

   transform(v.begin(), v.end(), v.begin(), quad);

}

 

A typical example from STL is the ordering of items in a set or map. These entities are not hash tables, but binary trees. By default, they are ordered by using the less<T> class (which is a functor). To change the order of objects, a new functor can be plugged in:

class BookCompare {

public:

   bool operator()(const Book& b1, const Book& b2) const {

      return b1.yearPublished > b2.yearPublished;

   }

};

 

set<Book, BookCompare> books;

map<Book, Shelf, BookCompare> library;

 

Use functors: they are cool.

 

7. The Comma operator

The comma operator is not usually regarded as an operator at all. For example, what would be the value of the variable x, assuming the array a is initialized with the values 0 through 9:

int a[10];

//...

int x = a[2, 3];

 

If you can’t guess, read on (yes, it does compile just fine).

The comma operator just says that thing will be done from left to right, and (and this is important) that value of the expression is the rightmost one. Now do you know what will x equal?

If not, read on still.

One of the things I had to do in the COM days was to set some value and return an HRESULT. One way to do this was this:

HRESULT CMyClass::SomeMethod(int x, int* result) {

   if(x > 5) {

      *result = 0;

      return S_OK;

   }

   return E_FAIL;

}

 

I had to open curly braces and do the two things I needed to do. But the small comma can help:

HRESULT CMyClass::SomeMethod(int x, int* result) {

   if(x > 5) return *result = 0, S_OK;

   return E_FAIL;

}

 

Remember, the S_OK is the expression value, but the *result=0 is executed as well. Cool!

 

There are other ways to be cool in C++, but this should get you started!

WPF Auto Size ComboBox, Improved

Published at Sep 07 2010, 02:36 PM by pavely

I’ve blogged about the problem of an auto sized ComboBox. I proposed a solution that seemed to work well enough, but it appears it did not work correctly if the SelectedItem or SelectedIndex properties were used with a Binding expression.

Here’s an improved version that takes both situations into account:

public class ComboBoxEx : ComboBox {

   private int _selected;

   Binding _indexBinding, _itemBinding;

   object _selectedItem;

 

   public override void OnApplyTemplate() {

      base.OnApplyTemplate();

 

      _indexBinding = BindingOperations.GetBinding(this, ComboBox.SelectedIndexProperty);

      _itemBinding = BindingOperations.GetBinding(this, ComboBox.SelectedItemProperty);

      if(_indexBinding != null)

         BindingOperations.ClearBinding(this, ComboBox.SelectedIndexProperty);

      else if(_itemBinding != null)

         BindingOperations.ClearBinding(this, ComboBox.SelectedItemProperty);

      else {

         _selected = SelectedIndex;

         _selectedItem = SelectedItem;

      }

      SelectedIndex = -1;

      SelectedItem = null;

 

      Loaded += ComboBoxEx_Loaded;

   }

 

   void ComboBoxEx_Loaded(object sender, RoutedEventArgs e) {

      double width = ActualWidth;

      var popup = GetTemplateChild("PART_Popup") as Popup;

      var content = popup.Child as FrameworkElement;

      content.Measure(new Size(double.PositiveInfinity, double.PositiveInfinity));

      MinWidth = content.DesiredSize.Width + width;

      if(_indexBinding != null)

         BindingOperations.SetBinding(this, ComboBox.SelectedIndexProperty, _indexBinding);

      else if(_itemBinding != null)

         BindingOperations.SetBinding(this, ComboBox.SelectedItemProperty, _itemBinding);

      else if(_selectedItem == null)

         SelectedIndex = _selected;

      else

         SelectedItem = _selectedItem;

   }

}

 

This is slightly more complex, as I wanted to remove the bindings (if exist), so that the ComboBox will have its minimal width, later to be added to the largest width of the Popup’s Content.

How to Annoy Your Boss (or get yourself fired)

Published at Sep 04 2010, 05:24 PM by pavely

If you want to make your boss a bit crazy, here’s what you can do:

First, get him away from his computer. You can explain you need to run some connectivity test or configure some important service for the sake of the project. Once he’s out of the way, you can proceed:

1. Install the Debugging Tools For Windows package (if you don’t have it already). You can get the latest version from the Windows SDK installation, but any previous version will do. We’ll need the Global Flags utility from that package.

2. Run gflags.exe (Start->Programs->Debugging Tool For Windows->Global Flags). You should see the following:

image

3. Click on the “Image File” tab. You should see something like this:

image

4. Now comes the tricky part: enter the name of an exe (including the EXE extension) of some application. Good examples are outlook.exe, winword.exe, but can be anything. Anything your boss uses on a regular basis, that is.

5. Hit the Tab key. Now the display should change to this:

image

6. Now for the last piece of the puzzle: Check the “Debugger” option and enter some other application you want to run instead. Here’s an example:

image

7. And you’re done. Click OK. Now every time outlook is started, calc.exe will run instead.

If you lose your job over this (your boss found out somehow) – don’t blame me. I’m just the messenger.