WPF and Powershell: Using a compiled type in XAML(Part 3)

Here is another example of how to use WPF with Powershell. This example shows how to use a custom control in WPF. This example is somewhat esoteric and does not pertain directly to Powershell, but custom types can make it easier to create different interfaces. Knowing how to do this is important because many of the base WPF types do not expose much useful functionality(e.g. a Button doesn’t do anything on it’s own and needs to have code added to it’s events).

The first half of the example script compiles a new WPF class derived from the Button class. This new class does not necessarily need to be defined in the script. XAML can use any WPF class from any loaded assembly. This class could be part of a library of custom controls.

The new class, CountButton, is derived from the Button class in the System.Windows.Controls namespace. The button functionality is extended by making the button count the number of times it is clicked by overriding the OnClick method. The number of times the button is clicked is then exposed by the read only dependancy property ClickCount.

The second half of the example script contains XAML that will use the new WPF class. In the XAML the "t" xml namespace corresponds to the Test namespace in the embedded C# code. The element name for our CountButton class is then t:CountButton. The example XAML defines a CountButton with the name "countbutton" and the display text as "Click this!" The example XAML also defines a label with it’s content bounded to the ClickCount property of the named button.

When this example script is invoked, the button will keep track of the number of times it is clicked and the label will automatically update it’s content.

Combining example one and this example, a person could display some properties of a collection of objects, and have buttons available to invoke methods on those objects.

. Library-PresentationInterface

[void](new-cassembly @'
using System;
using System.Windows;
using System.Windows.Controls;
using System.Windows.Controls.Primitives;

[assembly:System.Windows.Markup.XmlnsDefinition("http://testschema/test","Test")]

namespace Test {
	public class CountButton : Button {
		int _ClickCount = 0;
		public int ClickCount {get {return _ClickCount;}}
		internal static readonly DependencyPropertyKey ClickCountKey = DependencyProperty.RegisterReadOnly(
			"ClickCount", typeof(int), typeof(CountButton),new PropertyMetadata(0));
		public static readonly DependencyProperty ClickCountProperty = ClickCountKey.DependencyProperty;
		
		protected override void OnClick() {
			this._ClickCount++;
			base.OnClick();
			this.SetValue(ClickCountKey, this._ClickCount);
		}
	}
}
'@)

$result = start-PresentationInterface -xaml ([xml]@'
<Window xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
	xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
	xmlns:t="http://testschema/test"
	Title="Example 2" SizeToContent="WidthAndHeight">
	<StackPanel>
		<t:CountButton Name="countbutton" Width="150" HorizontalAlignment="Left">Click this!</t:CountButton>
		<StackPanel Orientation="Horizontal">
			<Label>Button click event count:</Label>
			<Label Content="{Binding ElementName=countbutton, Path=ClickCount}" />
		</StackPanel>
	</StackPanel>
</Window>
'@)
[void](stop-PresentationInterface $result)
Advertisements

~ by lunaticexperimentalist on November 20, 2007.

Leave a Reply

Fill in your details below or click an icon to log in:

WordPress.com Logo

You are commenting using your WordPress.com account. Log Out / Change )

Twitter picture

You are commenting using your Twitter account. Log Out / Change )

Facebook photo

You are commenting using your Facebook account. Log Out / Change )

Google+ photo

You are commenting using your Google+ account. Log Out / Change )

Connecting to %s

 
%d bloggers like this: