WPF Layout Basics
WPF provides a set of panels—special-purpose user interface elements whose job is to
arrange the elements they contain. Each individual panel type offers a straightforward
and easily understood layout mechanism. As with all WPF elements, layout objects
can be composed in any number of different ways, so although each individual panel
type is fairly simple, the flexible way in which they can be combined makes for a very
powerful layout system. And you can even create your own layout element types
should the built-in ones not meet your needs.
Table describes the main panel types built into WPF.* Whichever panel you use,
the same basicrule always applies: an element’s position is always determined by the
containing panel. Most panels also manage the size of their children.
WPF StackPanel
StackPanel is a very simple panel that arranges its children in a row or a column. You
will not normally use StackPanel to lay out your whole user interface. It is most useful
for arranging small subsections. Example 3-1 shows how to build a simple search
user interface.
Figure 3-1 shows the results. As you can see, the UI elements have simply been
stacked vertically one after another. This example used the Margin property to space
the elements out a little. Most elements use a single number, indicating a uniform
margin all around. The Button uses a pair of numbers to specify different vertical and
Table 3-1. Main panel types
Panel type Usage
StackPanel Lays children out in a vertical or horizontal stack; extremely simple, useful for managing small-scale
aspects of layout.
WrapPanel Lays children out from left to right, moving onto a new line each time it fills the available width.
DockPanel Allocates an entire edge of the panel area to each child; useful for defining the rough layout of simple
applications at a coarse scale.
Grid Arranges children within a grid; useful for aligning items without resorting to fixed sizes and positions.
The most powerful of the built-in panels.
Canvas Performs no layout logic—puts children where you tell it to; allows you to take complete control of
the layout process.
UniformGrid Arranges children in a grid where every cell is the same size.
Example . StackPanel search layout
<StackPanel Background="#ECE9D8">
<TextBlock Margin="3">Look for:</TextBlock>
<ComboBox Margin="3"/>
<TextBlock Margin="3">Filtered by:</TextBlock>
<ComboBox Margin="3"/>
<Button Margin="3,5">Search</Button>
<CheckBox Margin="3">Search in titles only</CheckBox>
<CheckBox Margin="3">Match related words</CheckBox>
<CheckBox Margin="3">Search in previous results</CheckBox>
<CheckBox Margin="3">Highlight search hits (in topics)</CheckBox>
</StackPanel>
horizontal margins. This is one of several standard layout properties available on all
WPF elements, which are all described in the “Common Layout Properties” section,
There is one problem with this layout: the Search button is much wider than you
would normally expect a button to look. The default behavior of a vertical
StackPanel is to make all of the controls the same width as the panel. Likewise, a
horizontal StackPanel will make all of the controls the same height. For the ComboBox
controls, this is exactly what we want. For the TextBlock and CheckBox controls, it
doesn’t show that the controls have been stretched to be as wide as the panel,
because they look only as wide as their text makes them look. However, a Button’s
visuals always fill its entire logical width, which is why the button in Figure 3-1 is
unusually wide. (See the upcoming “Fixed Size Versus Size to Content” sidebar for
more details on how this process works.)
When an element has been given a fixed amount of space that is greater than
required by its content, the way in which the extra space gets used is determined by
the HorizontalAlignment and VerticalAlignment properties.
We can prevent the button from being stretched across the panel’s whole width by
setting its HorizontalAlignment property to Left:
<Button Margin="3,5" HorizontalAlignment="Left">Search</Button>
HorizontalAlignment determines an element’s horizontal position and width in situations
where the containing panel gives it more space than it needs. The default is
Stretch, meaning that if more space is available than the child requires, it will be
stretched to fill that space. The alternatives—Left, Right, and Center—do not
attempt to stretch the element; these determine where the element will be placed
within the excess space, allowing the element to use its natural width. Here we are
using Left, meaning that the control will have its preferred width, and will be aligned
to the left of the available space.
The preceding example used the default vertical orientation. StackPanel also supports
horizontal layout. Example shows a StackPanel with its Orientation property set
to Horizontal.
Example Horizontal StackPanel layout
<StackPanel Orientation="Horizontal">
<TextBlock>This is some text</TextBlock>
<Button>Button</Button>
<Button>Button (different one)</Button>
<CheckBox>Check it out</CheckBox>
<TextBlock>More text</TextBlock>
</StackPanel>
WPF WrapPanel
WrapPanel works just like a StackPanel until it runs out of space. If you provide a horizontal
WrapPanel with more children than will fit in the available width, it will
arrange its content in a way similar to how a word processor lays out words on a
line. It puts the children in a row from left to right until it runs out of space, at which
point it starts on the next line.
WrapPanel is very simple to use. Just as with a StackPanel, you add a sequence of children,
as shows.
<WrapPanel Background="Beige">
<Button>One</Button>
<Button>Two</Button>
<Button>Three</Button>
<Button>Four</Button>
<Button>Five</Button>
<Button>Six</Button>
<Button>Seven</Button>
<Button>Eight</Button>
</WrapPanel>
WrapPanel also offers an Orientation property. Setting this to Vertical will arrange
the children in a sequence of vertical stacks, a layout style very similar to Windows
Explorer’s “List” view.
WrapPanel and StackPanel really are useful only for small-scale layout. You will need
to use a more powerful panel to define the overall layout of your application, such as
DockPanel.
WPF DockPanel
DockPanel is useful for describing the overall layout of a simple user interface. You
can carve up the basic structure of your window using a DockPanel, and then use the
other panels to manage the details.
A DockPanel arranges each child element so that it fills a particular edge of the panel.
If multiple children are docked to the same edge, they simply stack up against that
edge in order. By default, the final child fills any remaining space not occupied by
controls docked to the panel’s edges.
Example shows a simple DockPanel-based layout. Five buttons have been added
to illustrate each option. Notice that four of them have a DockPanel.Dock attribute
applied. This property is defined by DockPanel to allow elements inside a DockPanel
to specify their position. DockPanel.Dock is an attachedproperty (as described in the
upcoming sidebar, “Attached Properties and Layout”).
<DockPanel>
<Button DockPanel.Dock="Top">Top</Button>
<Button DockPanel.Dock="Bottom">Bottom</Button>
<Button DockPanel.Dock="Left">Left</Button>
<Button DockPanel.Dock="Right">Right</Button>
<Button>Fill</Button>
</DockPanel>
Elements never overlap in a DockPanel, so each successive child only gets to use space
not already used by the previous children. By default, the final child takes all of the
remaining space, but if you would prefer to leave a blank space in the middle, you
can set the LastChildFill attribute of the DockPanel to False. (It defaults to True.)
The final child will dock to the left by default, leaving the center empty.