ListView's ItemContainerStyle blocks Column Item Binding on GridView

478 Views Asked by At

Why does the implementation of ItemContainerStyle (detailed below) cause the individual data column bindings to fail on an otherwise working ListView/GridView?

Here is the visual result of the failure where the total items in 3 rows are shown but not the individual column items:

enter image description here

Implementation without the overridden ItemContainerStyle:

enter image description here


Actual Goal Before answering the question consider what my ultimate goal is for an alternate workaround. I want a GridView like structure where each row has a drop shadow; preferably shown on the selected item/on hover operation to make the row pop. As somewhat shown on the failure example above


Code

<ListView ItemsSource="{StaticResource People}">

                            <!--Comment this out to see working display-->
<ListView.ItemContainerStyle>
    <Style TargetType="ListViewItem">
        <Setter Property="Template">
            <Setter.Value>
                <ControlTemplate TargetType="ListViewItem">
                    <Grid Background="White" Margin="20">
                        <Grid.Effect>
                            <DropShadowEffect />
                        </Grid.Effect>
                        <ContentPresenter Content="{TemplateBinding Content}" 
                                          ContentTemplate="{TemplateBinding ContentTemplate}"
                                          HorizontalAlignment="{TemplateBinding HorizontalContentAlignment}"
                                          VerticalAlignment="{TemplateBinding VerticalContentAlignment}"
                                          SnapsToDevicePixels="{TemplateBinding SnapsToDevicePixels}" />
                    </Grid>
                </ControlTemplate>
        </Setter.Value>
        </Setter>
    </Style>
</ListView.ItemContainerStyle>
                                <!--End Failure Point-->
<ListView.View>
    <GridView >
        <GridViewColumn Header="First" DisplayMemberBinding="{Binding Path=First}"  />
        <GridViewColumn Header="Last"  DisplayMemberBinding="{Binding Path=Last}" />
        <GridViewColumn Header="Phone" DisplayMemberBinding="{Binding Path=Phone}" />
    </GridView>
</ListView.View>
</ListView>

To reproduce you will need

StaticResource Data defined in Xaml

xmlns:model="clr-namespace:{your namespace}.Model"

<UserControl.Resources>
    <model:People x:Key="People">
        <model:Person First="Joe" Last="Smith" Phone="303-555-5555"/>
        <model:Person First="Jenny" Last="Johnson" Phone="720-867-5309" />
        <model:Person First="Frank" Last="Wright" Phone="202-555-5555" />
    </model:People>
</UserControl.Resources>

People.cs in Model namspace

public class People : List<Person> { }

public class Person
{
    public string First { get; set; }
    public string Last { get; set; }
    public string Phone { get; set; }
}
1

There are 1 best solutions below

0
ΩmegaMan On

The ContentPresenter is the wrong node type to use for the ControlTemplate of the ItemContainerStyle.

To fix change ContentPresenter to GridViewRowPresenter and also remove ContentTemplate as such:

<ControlTemplate TargetType="ListViewItem">
    <Grid Background="White" Margin="20">
        <Grid.Effect>
            <DropShadowEffect />
        </Grid.Effect>
        <GridViewRowPresenter Content="{TemplateBinding Content}"                                  
                              HorizontalAlignment="{TemplateBinding HorizontalContentAlignment}"
                              VerticalAlignment="{TemplateBinding VerticalContentAlignment}"
                              SnapsToDevicePixels="{TemplateBinding SnapsToDevicePixels}" />
    </Grid>
</ControlTemplate>

Visual Result

enter image description here