You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

C# WPF:如何在Menu中插入可自适应拉伸的TextBox?

WPF菜单嵌入TextBox的布局问题修复

我尝试在Menu中插入带灰色提示文本的TextBox,遇到两个问题:

  • TextBox无法沿Menu整体拉伸;
  • Menu出现异常偏移。
    即使将其放入Grid后,右侧仍存在异常偏移,以下是最新实现代码:
<Window x:Class="NotepadMain.MainWindow"
        xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
        xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
        xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
        xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
        xmlns:local="clr-namespace:NotepadMain"
        mc:Ignorable="d"
        Title="FirePad - A Notepad for the 21st Century" Height="450" Width="800">
    <Grid>
        <Grid.RowDefinitions>
            <RowDefinition Height="Auto"/>
            <RowDefinition Height="*"/>
        </Grid.RowDefinitions>

        <DockPanel LastChildFill="True" Grid.Row="0" VerticalAlignment="Center">
            <Menu DockPanel.Dock="Top"
                  FontFamily="Consolas"
                  FontSize="20">
                <MenuItem Header="_File" Width="auto">
                    <MenuItem Header="New" x:Name="newMenus" >
                        <MenuItem.Icon>
                            <Image Source="Assets/new.png"/>
                        </MenuItem.Icon>
                    </MenuItem>
                    <MenuItem Header="Save" x:Name="saveMenus" Click="saveMenus_Click" >
                        <MenuItem.Icon>
                            <Image Source="Assets/save.png"/>
                        </MenuItem.Icon>
                    </MenuItem>
                    <MenuItem Header="SaveAs" x:Name="saveAsMenus" Click="saveAsMenus_Click" >
                        <MenuItem.Icon>
                            <Image Source="Assets/save_as.png"/>
                        </MenuItem.Icon>
                    </MenuItem>
                    <MenuItem Header="Open" x:Name="openMenus" Click="openMenus_Click">
                        <MenuItem.Icon>
                            <Image Source="Assets/open.png"/>
                        </MenuItem.Icon>
                    </MenuItem>
                    <Separator />
                    <MenuItem Header="Print">
                        <MenuItem.Icon>
                            <Image Source="Assets/print.png"/>
                        </MenuItem.Icon>
                    </MenuItem>
                </MenuItem>

                <MenuItem Header="Edit">
                    <MenuItem Header="Copy" x:Name="copyMenus" >
                        <MenuItem.Icon>
                            <Image Source="Assets/copy.png"/>
                        </MenuItem.Icon>
                    </MenuItem>
                    <MenuItem Header="Paste" x:Name="pasteMenus" >
                        <MenuItem.Icon>
                            <Image Source="Assets/paste.png"/>
                        </MenuItem.Icon>
                    </MenuItem>
                    <MenuItem Header="Cut" x:Name="cutMenus" >
                        <MenuItem.Icon>
                            <Image Source="Assets/cut.png"/>
                        </MenuItem.Icon>
                    </MenuItem>
                    <Separator/>
                    <MenuItem Header="Undo" x:Name="undoMenus" >
                        <MenuItem.Icon>
                            <Image Source="Assets/undo.png"/>
                        </MenuItem.Icon>
                    </MenuItem>
                    <MenuItem Header="Redo" x:Name="redoMenus" >
                        <MenuItem.Icon>
                            <Image Source="Assets/redo.png"/>
                        </MenuItem.Icon>
                    </MenuItem>
                    <Separator/>

                    <TextBox  TextWrapping="Wrap" Width="100" Grid.Column="0">
                        <TextBox.ToolTip>Highlight a Word in the Text</TextBox.ToolTip>
                    </TextBox>

                </MenuItem>
                
            </Menu>
        </DockPanel>
        <RichTextBox Grid.Row="1" x:Name="richTextBox1">
            
        </RichTextBox>


    </Grid>
</Window>

修复方案

1. 解决TextBox拉伸问题

直接将TextBox作为MenuItem子元素会受MenuItem默认布局约束,需要将TextBox放在MenuItem的Header中,并用Grid或DockPanel包裹,让其填充MenuItem的可用宽度。同时添加灰色提示文本(水印效果),可以通过TextBox的Style实现。

2. 解决Menu偏移问题

移除DockPanel上的VerticalAlignment="Center",避免菜单垂直方向偏移;同时移除TextBox上无效的Grid.Column="0"属性(该属性仅在Grid容器内生效)。

修改后的完整代码

<Window x:Class="NotepadMain.MainWindow"
        xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
        xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
        xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
        xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
        xmlns:local="clr-namespace:NotepadMain"
        mc:Ignorable="d"
        Title="FirePad - A Notepad for the 21st Century" Height="450" Width="800">
    <Window.Resources>
        <!-- 带灰色提示文本的TextBox样式 -->
        <Style TargetType="TextBox" x:Key="WatermarkTextBox">
            <Setter Property="Template">
                <Setter.Value>
                    <ControlTemplate TargetType="TextBox">
                        <Grid>
                            <TextBox x:Name="PART_ContentHost" Background="Transparent"/>
                            <TextBlock x:Name="WatermarkText" 
                                       Text="Highlight a Word in the Text" 
                                       Foreground="Gray" 
                                       IsHitTestVisible="False"
                                       Margin="5,0"
                                       Visibility="Collapsed"/>
                        </Grid>
                        <ControlTemplate.Triggers>
                            <Trigger Property="Text" Value="">
                                <Setter TargetName="WatermarkText" Property="Visibility" Value="Visible"/>
                            </Trigger>
                        </ControlTemplate.Triggers>
                    </ControlTemplate>
                </Setter.Value>
            </Setter>
        </Style>
    </Window.Resources>
    <Grid>
        <Grid.RowDefinitions>
            <RowDefinition Height="Auto"/>
            <RowDefinition Height="*"/>
        </Grid.RowDefinitions>

        <DockPanel LastChildFill="True" Grid.Row="0">
            <Menu DockPanel.Dock="Top"
                  FontFamily="Consolas"
                  FontSize="20">
                <MenuItem Header="_File">
                    <MenuItem Header="New" x:Name="newMenus" >
                        <MenuItem.Icon>
                            <Image Source="Assets/new.png"/>
                        </MenuItem.Icon>
                    </MenuItem>
                    <MenuItem Header="Save" x:Name="saveMenus" Click="saveMenus_Click" >
                        <MenuItem.Icon>
                            <Image Source="Assets/save.png"/>
                        </MenuItem.Icon>
                    </MenuItem>
                    <MenuItem Header="SaveAs" x:Name="saveAsMenus" Click="saveAsMenus_Click" >
                        <MenuItem.Icon>
                            <Image Source="Assets/save_as.png"/>
                        </MenuItem.Icon>
                    </MenuItem>
                    <MenuItem Header="Open" x:Name="openMenus" Click="openMenus_Click">
                        <MenuItem.Icon>
                            <Image Source="Assets/open.png"/>
                        </MenuItem.Icon>
                    </MenuItem>
                    <Separator />
                    <MenuItem Header="Print">
                        <MenuItem.Icon>
                            <Image Source="Assets/print.png"/>
                        </MenuItem.Icon>
                    </MenuItem>
                </MenuItem>

                <MenuItem Header="Edit">
                    <MenuItem Header="Copy" x:Name="copyMenus" >
                        <MenuItem.Icon>
                            <Image Source="Assets/copy.png"/>
                        </MenuItem.Icon>
                    </MenuItem>
                    <MenuItem Header="Paste" x:Name="pasteMenus" >
                        <MenuItem.Icon>
                            <Image Source="Assets/paste.png"/>
                        </MenuItem.Icon>
                    </MenuItem>
                    <MenuItem Header="Cut" x:Name="cutMenus" >
                        <MenuItem.Icon>
                            <Image Source="Assets/cut.png"/>
                        </MenuItem.Icon>
                    </MenuItem>
                    <Separator/>
                    <MenuItem Header="Undo" x:Name="undoMenus" >
                        <MenuItem.Icon>
                            <Image Source="Assets/undo.png"/>
                        </MenuItem.Icon>
                    </MenuItem>
                    <MenuItem Header="Redo" x:Name="redoMenus" >
                        <MenuItem.Icon>
                            <Image Source="Assets/redo.png"/>
                        </MenuItem.Icon>
                    </MenuItem>
                    <Separator/>
                    <!-- 用MenuItem包裹TextBox,设置Header为Grid让TextBox拉伸 -->
                    <MenuItem>
                        <MenuItem.Header>
                            <Grid Margin="-4,0,-10,0">
                                <TextBox Style="{StaticResource WatermarkTextBox}" 
                                         TextWrapping="Wrap"
                                         HorizontalAlignment="Stretch"/>
                            </Grid>
                        </MenuItem.Header>
                    </MenuItem>
                </MenuItem>
            </Menu>
        </DockPanel>
        <RichTextBox Grid.Row="1" x:Name="richTextBox1"/>
    </Grid>
</Window>

关键修改说明

  • 新增WatermarkTextBox样式,实现灰色提示文本(水印)效果:TextBox为空时显示提示文本,有内容时自动隐藏;
  • 将TextBox放在MenuItem.Header内的Grid中,设置HorizontalAlignment="Stretch"让TextBox填充MenuItem的可用宽度;
  • 移除DockPanel的VerticalAlignment="Center",消除菜单垂直偏移;
  • 给Grid添加Margin="-4,0,-10,0",调整TextBox与MenuItem边缘的间距,消除默认布局带来的偏移。

内容的提问来源于stack exchange,提问作者user3348988

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.26 11:07:05