Search code examples
c#wpftextblocktexttrimming

CharacterEllipsis doesn't work inside ItemsControl WPF


I'm trying to set CharacterEllipsis on text inside a DataTemplate of an ItemsControl.

<Window x:Class="CustomPanel.Window1"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:local="clr-namespace:CustomPanel;assembly="
Title="Window1" Height="400" Width="400">
<Window.Resources>
    <Style TargetType="{x:Type TextBlock}">
        <Setter Property="TextTrimming" Value="CharacterEllipsis"></Setter>
    </Style>

    <DataTemplate DataType="{x:Type local:Person}">
        <StackPanel Orientation="Horizontal">
            <TextBlock Text="{Binding Name}"
                       Margin="100,0,0,0"/>
        </StackPanel>
    </DataTemplate>
</Window.Resources>

<Grid>
    <Grid.ColumnDefinitions>
        <ColumnDefinition Width="*"/>
    </Grid.ColumnDefinitions>

    <ItemsControl ItemsSource="{Binding Persons}" 
                  Grid.Column="0">
    <ItemsControl.ItemsPanel>
        <ItemsPanelTemplate>
            <StackPanel />
        </ItemsPanelTemplate>
    </ItemsControl.ItemsPanel>
</ItemsControl>

</Grid>

I've also tried setting width to the ItemsControl, StackPanel's and the TextBlock itself.

Any Ideas?

EDIT

To inhance that this is not an issue of the Style or the StackPanel, I removed both and it still doesn't work

<Window.Resources>
    <DataTemplate DataType="{x:Type local:Person}">
            <TextBlock Text="{Binding Name}"
                       TextTrimming="CharacterEllipsis"
                       Margin="100,0,0,0"
                       Width="200"/>
    </DataTemplate>
</Window.Resources>

<Grid>
    <ItemsControl ItemsSource="{Binding Persons}"/>
</Grid>

Clarification

This works perfectly when the text is too big but I want it to work when the window is getting resized to a smaller width too.


Solution

  • DataTemplate won't pick the style from window since it does not lie in that scope. Move the style either inside DataTemplate.Resources Or Application.Resources so that it can be picked by TextBlock inside DataTemplate.

    Second, you have wrapped TextBlock inside StackPanel which gives it infinite size to expand. So, remove Stackpanel which is wrapping TextBlock.

    Third, constraint width of ItemsControl or set MaxWidth as you feel like.

    <Window.Resources>
        <DataTemplate DataType="{x:Type local:Person}">
            <DataTemplate.Resources>
                <Style TargetType="{x:Type TextBlock}">
                    <Setter Property="TextTrimming" Value="CharacterEllipsis"/>
                </Style>
            </DataTemplate.Resources>
            <TextBlock Text="{Binding Name}"/>
        </DataTemplate>
    </Window.Resources>
    <ItemsControl ItemsSource="{Binding Persons}" Width="30">
        <ItemsControl.ItemsPanel>
            <ItemsPanelTemplate>
                <StackPanel/>
            </ItemsPanelTemplate>
        </ItemsControl.ItemsPanel>
    </ItemsControl>
    

    UPDATE:

    In case you want to make it work for re-size of window, instead of setting width, set max width on TextBlock:

    <Window.Resources>
        <DataTemplate DataType="{x:Type local:Person}">
            <TextBlock Text="{Binding Name}" MaxWidth="200"
                        TextTrimming="CharacterEllipsis"/>
        </DataTemplate>
    </Window.Resources>
    <ItemsControl Margin="100,0,0,0" ItemsSource="{Binding Persons}"/>