lin

返回

WPF 布局基础核心就一句话:用容器(Panel)管理子元素的排列,而不是用绝对坐标硬定位。所有布局容器都继承自 Panel。

布局流程#

WPF 布局分两轮测量:

  1. Measure(测量):父容器问每个子元素”你想要多大?”
  2. Arrange(排列):父容器根据可用空间决定子元素最终位置和大小

理解这个有助于明白为什么 Width/Height 与 HorizontalAlignment 会”失效”——因为容器拥有最终裁量权。


五大布局容器#

1. Grid —— 最常用(表格化布局)#

用 RowDefinitions / ColumnDefinitions 定义行列,子元素用 Grid.Row / Grid.Column 指定位置:

<Grid>
    <Grid.RowDefinitions>
        <RowDefinition Height="Auto"/>   <!-- 高度随内容 -->
        <RowDefinition Height="*"/>      <!-- 占满剩余 -->
        <RowDefinition Height="2*"/>     <!-- 占剩余的 2/3 -->
        <RowDefinition Height="50"/>     <!-- 固定 50 -->
    </Grid.RowDefinitions>
    <Grid.ColumnDefinitions>
        <ColumnDefinition Width="100"/>
        <ColumnDefinition Width="*"/>
    </Grid.ColumnDefinitions>

    <TextBlock Grid.Row="0" Grid.Column="0" Text="姓名:"/>
    <TextBox  Grid.Row="0" Grid.Column="1"/>
    <Button   Grid.Row="2" Grid.ColumnSpan="2" Content="确定"/>
</Grid>
xml
  • *(星号)= 按比例分配剩余空间,是做自适应界面的关键
  • Auto = 内容多大它就多大
  • 支持 Grid.RowSpan / Grid.ColumnSpan 跨行跨列

2. StackPanel —— 简单堆叠#

<StackPanel Orientation="Vertical">  <!-- 或 Horizontal -->
    <TextBlock Text="第一行"/>
    <TextBlock Text="第二行"/>
    <Button Content="按钮"/>
</StackPanel>
xml
  • 垂直方向:高度由内容决定,宽度默认拉伸
  • 坑:放 ScrollViewer 里没问题;直接放进窗口可能导致内容被裁掉(不自动换行也不出现滚动条)

3. WrapPanel —— 自动换行#

<WrapPanel Orientation="Horizontal">
    <Button Content="A" Width="60"/>
    <Button Content="B" Width="60"/>
    <!-- 一行放不下时自动换到下一行 -->
</WrapPanel>
xml

适合做标签流、图片墙。

4. DockPanel —— 边缘停靠#

<DockPanel>
    <Menu DockPanel.Dock="Top"/>
    <StatusBar DockPanel.Dock="Bottom"/>
    <TreeView DockPanel.Dock="Left" Width="150"/>
    <ContentControl/>  <!-- 剩余空间默认占满 -->
</DockPanel>
xml

最后一个子元素默认填满剩余区域。经典主窗口布局全靠它。

5. Canvas —— 绝对定位#

<Canvas>
    <Button Canvas.Left="50" Canvas.Top="30" Content="确定"/>
</Canvas>
xml

唯一用坐标(Left/Top)的容器。除非做游戏、画图、拖动控件等场景,一般不要用。


对齐与边距(所有容器通用)#

属性说明
HorizontalAlignmentStretch(拉伸填满)/ Left / Center / Right
VerticalAlignmentStretch / Top / Center / Bottom
Margin外边距,如 Margin="10,20,10,20"(左、上、右、下)
Padding内边距(部分控件如 Button、Border 有)
VisibilityVisible / Collapsed(Collapsed 不占空间,区别于 Hidden)

⚠️ 常见误区:在 StackPanel 里设 VerticalAlignment="Stretch" 无效——因为 StackPanel 给子元素的高度就是内容高度,没有”剩余空间”可拉伸。Grid 里才可以。


经典实战:登录窗口布局#

<Grid Margin="20">
    <Grid.RowDefinitions>
        <RowDefinition Height="Auto"/>
        <RowDefinition Height="Auto"/>
        <RowDefinition Height="Auto"/>
    </Grid.RowDefinitions>
    <Grid.ColumnDefinitions>
        <ColumnDefinition Width="Auto"/>
        <ColumnDefinition Width="*"/>
    </Grid.ColumnDefinitions>

    <TextBlock Grid.Row="0" Grid.Column="0" Text="用户名" VerticalAlignment="Center" Margin="0,0,8,8"/>
    <TextBox  Grid.Row="0" Grid.Column="1" Margin="0,0,0,8"/>

    <TextBlock Grid.Row="1" Grid.Column="0" Text="密码" VerticalAlignment="Center" Margin="0,0,8,8"/>
    <PasswordBox Grid.Row="1" Grid.Column="1" Margin="0,0,0,12"/>

    <StackPanel Grid.Row="2" Grid.Column="1" Orientation="Horizontal" HorizontalAlignment="Right">
        <Button Content="登录" Width="80" Margin="0,0,8,0"/>
        <Button Content="取消" Width="80"/>
    </StackPanel>
</Grid>
xml

效果:标签自动宽度、输入框拉伸填满、按钮靠右——窗口拉大缩小都能自适应。


布局原则小结#

  1. 优先 Grid,配合 * 做自适应;DockPanel 做主窗口骨架
  2. 局部小布局(按钮组、表单)用 StackPanel
  3. 避免用 Margin 做绝对定位凑布局
  4. 需要滚动条就把内容包进 <ScrollViewer>
  5. 复杂界面可以容器嵌套(Grid 里嵌 DockPanel 里再嵌 StackPanel),但嵌套别太深,影响性能
2.WPF布局基础
作者 lin
发布于 2026年10月17日

留言

无需登录,留下你的想法。

0
昵称颜色
可见范围