WPF 文本框和滚动行为
Posted
技术标签:
【中文标题】WPF 文本框和滚动行为【英文标题】:WPF TextBox and Scroll behavior 【发布时间】:2010-09-28 00:20:07 【问题描述】:我有问题。 我需要在 ScrollViewer 中使用控件托管网格,以防止文本框在 UI 处被截断或折叠为零。我还希望在用户更改窗口宽度时扩展文本框的 with。 我正在将 Window 的内容设置为以下代码
<DockPanel>
<TreeView DockPanel.Dock="Left" Width="150"/>
<ScrollViewer VerticalScrollBarVisibility="Auto" HorizontalScrollBarVisibility="Auto">
<Grid>
<Grid.ColumnDefinitions>
<ColumnDefinition Width="Auto"/>
<ColumnDefinition />
</Grid.ColumnDefinitions>
<Grid.RowDefinitions>
<RowDefinition Height="Auto"/>
</Grid.RowDefinitions>
<TextBlock Text="Name"
Margin="5"
VerticalAlignment="Center"/>
<TextBox Grid.Column="1"
Text="Some Name"
Margin="5"
VerticalAlignment="Center"
MinWidth="200"/>
</Grid>
</ScrollViewer>
</DockPanel>
一切正常,但是当用户在 TextBox 中输入很长的文本时,文本框会被展开并出现水平滚动。 有没有什么简单的方法可以限制 TextBox 的最大宽度,并且只有在用户更改窗口大小时才允许它展开。
【问题讨论】:
【参考方案1】:问题在于父元素为 TextBox 提供了它认为需要的尽可能多的空间,当出现更多文本时,它会扩展而不是保持初始自动大小。
这里的一个解决方案是制作另一个自动调整大小的元素并将 TextBox.Width 绑定到它:
<DockPanel>
<TreeView Width="150" DockPanel.Dock="Left"/>
<ScrollViewer HorizontalScrollBarVisibility="Auto" VerticalScrollBarVisibility="Auto">
<Grid>
<Grid.ColumnDefinitions>
<ColumnDefinition Width="Auto"/>
<ColumnDefinition/>
</Grid.ColumnDefinitions>
<Grid.RowDefinitions>
<RowDefinition Height="Auto"/>
</Grid.RowDefinitions>
<TextBlock Margin="5" VerticalAlignment="Center" Text="Name"/>
<Border x:Name="b" Grid.Column="1" Margin="5"/>
<TextBox Width="Binding ActualWidth, ElementName=b"
MinWidth="200"
Grid.Column="1"
Margin="5"
VerticalAlignment="Center"
Text="Some Name"/>
</Grid>
</ScrollViewer>
</DockPanel>
请注意,我们设置了自动调整大小元素(边框)的 Margin 属性。这很重要,因为如果未设置,则会出现循环:
-
边框宽度自动调整为网格列宽
TextBox 宽度调整为 Border.ActualWidth
网格列宽调整为文本框宽度 + 文本框边距
边框宽度再次自动调整为网格列宽
通过将 Margin 设置为与 TextBox 相同,TextBox 的大小调整不会影响 Grid 的大小。
【讨论】:
根据 Robert 的解决方案修改代码后,我发现将文本框的 MaxWidth 绑定到封闭元素很有用。对于某些应用程序,它似乎避免了无限调整大小循环的问题。 工作正常,但现在当窗口变小时,TextBox 保持大尺寸。有什么解决办法吗?【参考方案2】:否 - 这是 wpf 的一个众所周知的问题,预计将在下一个版本中修复。谢谢
【讨论】:
【参考方案3】:像这样覆盖TextBox.MeasureOverride
对我有用:
protected override Size MeasureOverride(Size constraint)
Size origSize = base.MeasureOverride(constraint);
origSize.Width = MinWidth;
return origSize;
【讨论】:
你如何将 MinWidth 链接到封闭的列?以上是关于WPF 文本框和滚动行为的主要内容,如果未能解决你的问题,请参考以下文章