This week I was called on to do a very strange on-site custom course. They basically couldn’t decide on any one topic so they wanted me to talk a little bit about everything, mainly concentrating on:

  1. Advanced Windows Forms
  2. Windows Communication Foundation
  3. Unit Testing

As I have covered Windows Communication Foundation many times, and I didn’t have quite enough time to do unit testing any justice, the most interesting of the talks (I thought) was Windows Forms. We covered MDI, Notify Icons, and to my surprise had an interesting eventing discussion. Someone had asked about the difference between WPF and Windows Forms. I was trying to describe how they can be very similar but if you program WPF the right way how very different they really were and how complicated WPF was compared to Windows Forms. As part of this description I mentioned that Windows Forms has only the direct event model, but WPF has both bubbling and tunneling in addition to the direct model. Again someone raised their hand and asked if there was no way to simulate the bubbling model that they had in MFC (and WPF) using Windows Forms. He mentioned that they were having problems with coupling between components. I told them that the Client Application Block had something like this built in. He said that they found the CAB a little too heavy, and I agreed. I told him I would think more about it and get back to him tomorrow.

When I got back to the hotel that evening I started thinking about it and realized that there was a way to simulate it using a publish and subscribe type mechanism. This is basically a lightweight version of what the CAB clock does. I named my class the same as theirs as a form of flattery.

When you specify that you want to subscribe to a button click using the following syntax.

EventBroker.Instance.Subscribe(this, typeof(Button), "Click", OnButtonClick);

The EventBroker basically just walks the tree of controls recursively searching for controls of the type button, and then adds itself as a subscriber to that button. If someone else in the hierarchy also subscribes for button clicks the EventBroker knows which subscriber to call first. If the inner subscriber handles the event then the outer subscriber never sees the event, just like bubbling.

Best of all, you only need to drop in this one file, and away you go.
Here is the file in its entirety:

using System;
using System.Windows.Forms;
using System.Collections.Generic;
using System.Diagnostics;
using System.Reflection;

namespace WindowsFormsApp
	// helper method to make the code below more readable
	public static class ControlExtensions
		public static bool IsParentOf(this Control c, Control other)
			Control parent = other;
			while (parent != null)
				if (c == parent)
					return true;
				parent = parent.Parent;
			return false;


	public class EventBroker
		class EventHolder
			public Control Control { get; set; }
			public EventHandler<BubblingEventArgs> EventHandler { get; set; }

		// singleton
		public static readonly EventBroker Instance = new EventBroker();

		readonly Dictionary<Control, List<EventHolder>> subscribers = new Dictionary<Control, List<EventHolder>>();

		public void Subscribe(Control c, Type type, string eventName, EventHandler<BubblingEventArgs> callback)
			SubscribeRecursive(c, c, type, eventName, callback);

		private void SubscribeRecursive(Control subscriber, Control c, Type type, string eventName, EventHandler<BubblingEventArgs> callback)
			if (type.IsInstanceOfType(c))
				// check to see if this eventName exists and subscribe
				Debug.WriteLine(string.Format("{0} is of type {1}", c.Name, type.Name));

				List<EventHolder> list;
				var newHolder = new EventHolder
					Control = subscriber,
					EventHandler = callback,

				// do we already have a subscriber for this object?
				if (subscribers.TryGetValue(c, out list))
					// walk through the list trying to find where to insert this subscriber
					bool inserted = false;
					for (int cnt = 0; cnt < list.Count; cnt++)
						EventHolder holder = list[cnt];

						// uses the extension method above
						if (holder.Control.IsParentOf(subscriber))
							list.Insert(cnt, newHolder);
							inserted = true;
					// if they weren't inserted add them at the end
					if (!inserted)
					// this is a new object, subscribe to its event
					EventInfo eventInfo = c.GetType().GetEvent(eventName);
					eventInfo.AddEventHandler(c, new EventHandler(OnEvent));

					// then create a new list of subscribers keyed to this object
					list = new List<EventHolder> {newHolder};
					subscribers.Add(c, list);

			// now recursively subscribe
			foreach (Control child in c.Controls)
				SubscribeRecursive(subscriber, child, type, eventName, callback);

		public void OnEvent(object sender, EventArgs e)
			// grab the list of subscribers for this control
			List<EventHolder> list = subscribers[(Control)sender];

			foreach (EventHolder holder in list)
				Debug.WriteLine(string.Format("About to call {0}", holder.Control.Name));

				// call this subscriber
				var handledArgs = new BubblingEventArgs {InnerArgs = e};
				holder.EventHandler(sender, handledArgs);

				// if they handled the event don't propogate further
				if (handledArgs.Handled)

I was working with a client that wanted to be able to layout the screen using some pretty complicated but fixed layouts. All of these needed to be able to be adjusted by the client after they were shown, so they needed to use splitters. To help them to be able to produce these layouts easily I created a control. It allows them to simply set the number of reports and the layout type, and assign the reports to the various panels. To demonstrate what the result looks like and show how to programmatically use the control I created a little test project. Here is a screen shot of the result.

Unfortunately it looks a little bit like an eye chart ;) . However, the cool thing is that all of the splitters shown in the screen capture actually work. In fact if you look I adjusted some on the second row. There is another test that I did where it cycles through all the splitters one at a time. The project is included here.

That’s it. The third time you get asked about a particular topic, its time to stop making it up as you go along, and actually write something down. I was asked (again) today by another one of my clients about Validation within Windows Forms. So I am going to take some time to write up my thoughts

First let me say that there are several parts to validation. There is simple user input or "control" validation, displaying of the results of a failed validation, and then the complex business rule or "form" validation. Lets deal with each in turn

Simple user input validation

As you probably know each control in a form contains a Validating and a Validated event. In order to get those events to fire the CausesValidation property on the control needs to be true, but since that is the default, no problems there. Most people start off by using Validating to implement some simple validation rules like making sure that the input is in the proper form. ASP.NET provides the following forms of validation:

  • RequiredFieldValidator – Make some input has been chosen for the control
  • RangeValidator – Make sure the input is within a specific range
  • RegularExpressionValidator – Make sure the input looks like a regular expression
  • CompareValidator – Make sure that the input in one control "matches" the input in another
  • CustomValidator – Check the input as you see fit

Windows Forms does not provide those controls out of the box. However, there are solutions, as we will see shortly.

There are two basic approaches to validating many controls on a Form. The first is the ASP.NET approach where one or more validators are dragged onto the form for *each* control that needs validation. The second is to use an IExtenderProvider (tooltips and errorProviders are examples of ExtenderProviders). The idea behind a ExtenderProvider is that you drag one component onto the form, and it extends the properties for every control on that form.

Michael Weinhardt wrote an article providing the ASP.NET way. The model was described in a 3 part article as well as the accompanying source code. In the article just look at the first part as 2 and 3 have been obsoleted by newer versions of .NET (2.0).

Billy Hollis wrote an article providing the second way which has since been removed from MSDN. However the WebCast is still around, and the source code can still be downloaded.

The choice between the two models essentially comes down to the percentage of controls needing validation on a given page. If the percentage is large, go with Billy Hollis’ model, if the percentage is small go with Michael Weinhardt’s model. Another reason for going with Weinhardt is if you are building both Forms and ASP.NET applications in order to stay consistent. BTW – I prefer Billy Hollis’s model. His code is in VB.NET, but I ported it to C#.

Displaying errors

Most everyone agrees that the ErrorProvider is the right way to signal errors in Windows Forms. However some people feel that novice users won’t be able to tell what the error actually is. If your application is meant to be used by novices there are two approaches.
a) build a little framework that dynamically creates an error label with each control that is being checked
b) provide a ValidationSummary control ala ASP.NET that contains all of the errors
I prefer the second option here. Note the Weinhardt’s article mentioned above provides a Validation form which pops up a modal dialog containing the error information, which is another way to go. I dislike modal popups, but I recognize that as largely a matter of taste.

Form and complex business rule validation

Examples of this are the CompareValidator that I mentioned earlier. But here is where the Validating event can really shine. Typically you hook this event and the call into some business logic which tests sums of values, or certain strings when an enum has been chosen above, things like that. The same Validation summary can then be used to display the results of such validation.

Happy Validating!