如何在TreeviewItem中进行文本换行?

时间:2018-05-12 09:41:42

标签: c# wpf treeview

修改以下Francesco B.提供的解决方案正在发挥作用。我想知道是否还有XAML解决方案。

我想将TreeViewItem中的TextBlock中的Text设置为Wrap。 我尝试了this链接的解决方案。它将使Header文本换行,但不会扩展TextBlock。

这是我的TreeView与父Grid:

<Grid Background="LightGray">
    <Grid.ColumnDefinitions>
        <ColumnDefinition/>
        <ColumnDefinition Width="auto"/>
        <ColumnDefinition />
    </Grid.ColumnDefinitions>

    <Grid Grid.Column="0" ScrollViewer.HorizontalScrollBarVisibility="Disabled">
        <TreeView ScrollViewer.HorizontalScrollBarVisibility="Disabled">
            <TreeViewItem Style="{DynamicResource TreeViewItemStyle1}">
                <TreeViewItem.Header>

                    <TextBlock Text="Header Header Header Header Header Header Header Header "
                               TextWrapping="Wrap" />

                </TreeViewItem.Header>
                <TextBlock Text="1very 2very 3very 4very 5long 6very 7very 8very 9very 10Long"
                           TextWrapping="Wrap"
                           Background="LightCyan" />

            </TreeViewItem>
        </TreeView>

    </Grid>

    <GridSplitter Grid.Column="1"
                  Width="10"
                  ResizeBehavior="PreviousAndNext" />
    <Grid Grid.Column="2"
          Background="LightPink" />
</Grid>

以下是TreeViewItemStyle1中已更改模板的一部分:

                            <Border x:Name="Bd"
                                BorderBrush="Red"
                                BorderThickness="1"
                                Background="{TemplateBinding Background}"
                                Grid.Column="1"
                                Grid.ColumnSpan="2"
                                Grid.Row="0"
                                Padding="{TemplateBinding Padding}"
                                SnapsToDevicePixels="true">
                            <ContentPresenter x:Name="PART_Header"
                                              ContentSource="Header"
                                              HorizontalAlignment="{TemplateBinding HorizontalContentAlignment}"
                                              SnapsToDevicePixels="{TemplateBinding SnapsToDevicePixels}" />
                        </Border>
                        <ItemsPresenter x:Name="ItemsHost"
                                        ScrollViewer.HorizontalScrollBarVisibility="Disabled"
                                        TextBlock.FontSize="35"
                                        Grid.Column="1"
                                        Grid.ColumnSpan="2"
                                        Grid.Row="1">
                        </ItemsPresenter>

我将Grid.ColumnSpan="2"添加到边框作为另一个解决方案,但这只会使标头被包装。 我觉得我必须对ItemsPresender做点什么。但没有任何作用!

请提出解决方案!

感谢。

2 个答案:

答案 0 :(得分:1)

我能想到的最快的事情主要是使用代码隐藏。 它只需要在外部GridTreeView中添加一个名称,我从中删除了样式声明:

<Grid  x:Name="MyGrid" Background="LightGray" >
...
<TreeView x:Name="MyTree" ScrollViewer.HorizontalScrollBarVisibility="Disabled">

然后,在代码隐藏中,我添加了一个方法来调整每个TreeViewItem的标题和项目的大小:

private void ResizeTree()
{
    var MaxWidth = Convert.ToDouble(MyGrid.ColumnDefinitions[0].ActualWidth);
    foreach (TreeViewItem item in MyTree.Items)
    {
        var Header = item.Header as TextBlock;
        var Body = item.Items[0] as TextBlock;
        Header.Width = MaxWidth - 30;
        Body.Width = MaxWidth - 60;
    }
}

然后,使用此solution,我在第一次显示TreeView时添加了对该方法的调用以调整Window的大小:

private bool _shown = false;

public MainWindow()
{
    InitializeComponent();
}

protected override void OnContentRendered(EventArgs e)
{
    base.OnContentRendered(e);
    if (_shown)
    {
        return;
    }

    _shown = true;
    ResizeTree();
}

最后,我添加了一个在移动GridSplitter时引发的事件:

<GridSplitter Grid.Column="1" DragCompleted="GridSplitter_DragCompleted"
              Width="10" ResizeBehavior="PreviousAndNext" />

当然必须调用ResizeTree方法:

private void GridSplitter_DragCompleted(object sender, System.Windows.Controls.Primitives.DragCompletedEventArgs e)
{
    ResizeTree();
}

可能要处理的其他事情是窗口调整大小,或者使用标题和项目的不同边距(我选择30和60)。

答案 1 :(得分:1)

要查看XAML解决方案,您可以尝试从treeviewitem模板中删除ContentPresenter,并将其更改为具有所需属性的TextBlock,例如MaxWidth&amp; TextWrapping,就是这样。 如果您在模板Text="{TemplateBinding Header}"中设置TextBlock,一切仍然有效。现在你不需要在每个treeviewitem中放置一个文本块 - 模板只是在里面) 然后你可以根据需要添加treeviewitems:使用ItemsSource(在这种情况下你可能也应该指定DataTemplate)或者像

一样
<TreeView> <TreeViewItem Header="first"/><TreeViewItem Header="second"/>...</TreeView> 

或者从后面的代码来看,没关系。