2010-04-17 6 views
0

J'essaie de lier une liste d'éléments à un ListBox dans WPF. Les articles sont groupés par une valeur et chaque groupe doit être hébergé dans un Expander. Tout fonctionne correctement lorsque je n'utilise aucun style personnalisé. Toutefois, lorsque j'utilise des styles personnalisés (qui fonctionnent correctement avec des éléments non groupés et comme des contrôles indépendants), la liaison n'affiche aucun élément. Voici le code que j'exécute. Des idées pour lesquelles les éléments n'apparaîtront pas dans le Expander?Strange WPF ListBox Behavior

Test.xaml:

<Window x:Class="Glossy.Test" 
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation" 
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" 
Title="Test" Height="300" Width="300"> 
<Window.Resources> 
    <ResourceDictionary> 
     <ResourceDictionary.MergedDictionaries> 
      <ResourceDictionary Source="..\TestStyles.xaml"/> 
      <ResourceDictionary> 
       <Style x:Key="ContainerStyle" TargetType="{x:Type GroupItem}"> 
        <Setter Property="Template"> 
         <Setter.Value> 
          <ControlTemplate> 
           <Expander Header="{Binding}" IsExpanded="True"> 
            <ItemsPresenter /> 
           </Expander> 
          </ControlTemplate> 
         </Setter.Value> 
        </Setter> 
       </Style> 
      </ResourceDictionary> 
     </ResourceDictionary.MergedDictionaries> 
    </ResourceDictionary> 
</Window.Resources> 

<Grid>   
    <ListBox x:Name="TestList"> 
     <ListBox.GroupStyle> 
      <GroupStyle ContainerStyle="{StaticResource ContainerStyle}"/> 
     </ListBox.GroupStyle> 
    </ListBox> 
</Grid> 

Test.xaml.cs:

public partial class Test : Window 
{ 
    private List<Contact> _ContactItems; 
    public List<Contact> ContactItems 
    { 
     get { return _ContactItems; } 
     set { _ContactItems = value; } 
    } 

    public Test() 
    { 
     InitializeComponent(); 

     ContactItems = new List<Contact>(); 
     ContactItems.Add(new Contact()); 
     ContactItems.Last().CompanyName = "ABC"; 
     ContactItems.Last().Name = "Contact 1"; 
     ContactItems.Add(new Contact()); 
     ContactItems.Last().CompanyName = "ABC"; 
     ContactItems.Last().Name = "Contact 2"; 
     ContactItems.Add(new Contact()); 
     ContactItems.Last().CompanyName = "ABC"; 
     ContactItems.Last().Name = "Contact 3"; 
     ContactItems.Add(new Contact()); 
     ContactItems.Last().CompanyName = "ABC"; 
     ContactItems.Last().Name = "Contact 10"; 
     ContactItems.Add(new Contact()); 
     ContactItems.Last().CompanyName = "ABC"; 
     ContactItems.Last().Name = "Contact 11"; 
     ContactItems.Add(new Contact()); 
     ContactItems.Last().CompanyName = "ABC"; 
     ContactItems.Last().Name = "Contact 12"; 

     ContactItems.Add(new Contact()); 
     ContactItems.Last().CompanyName = "RST"; 
     ContactItems.Last().Name = "Contact 7"; 
     ContactItems.Add(new Contact()); 
     ContactItems.Last().CompanyName = "RST"; 
     ContactItems.Last().Name = "Contact 8"; 
     ContactItems.Add(new Contact()); 
     ContactItems.Last().CompanyName = "RST"; 
     ContactItems.Last().Name = "Contact 9"; 

     ContactItems.Add(new Contact()); 
     ContactItems.Last().CompanyName = "XYZ"; 
     ContactItems.Last().Name = "Contact 4"; 
     ContactItems.Add(new Contact()); 
     ContactItems.Last().CompanyName = "XYZ"; 
     ContactItems.Last().Name = "Contact 5"; 
     ContactItems.Add(new Contact()); 
     ContactItems.Last().CompanyName = "XYZ"; 
     ContactItems.Last().Name = "Contact 6"; 

     ICollectionView view = CollectionViewSource.GetDefaultView(ContactItems); 
     view.GroupDescriptions.Add(new PropertyGroupDescription("CompanyName")); 
     view.SortDescriptions.Add(new SortDescription("Name", ListSortDirection.Ascending)); 
     TestList.ItemsSource = view; 
    } 
} 

public class Contact 
{ 
    public string CompanyName { get; set; } 
    public string Name { get; set; } 

    public override string ToString() 
    { 
     return Name; 
    } 
} 

TestStyles.xaml:

<Style TargetType="{x:Type ListBox}"> 
    <Setter Property="SnapsToDevicePixels" Value="true"/> 
    <Setter Property="OverridesDefaultStyle" Value="true"/> 
    <Setter Property="ScrollViewer.HorizontalScrollBarVisibility" Value="Auto"/> 
    <Setter Property="ScrollViewer.VerticalScrollBarVisibility" Value="Auto"/> 
    <Setter Property="ScrollViewer.CanContentScroll" Value="true"/> 
    <Setter Property="MinWidth" Value="120"/> 
    <Setter Property="MinHeight" Value="95"/> 
    <Setter Property="Template"> 
     <Setter.Value> 
      <ControlTemplate TargetType="ListBox"> 
       <Grid Background="Black"> 
        <Rectangle VerticalAlignment="Stretch" 
           HorizontalAlignment="Stretch" 
           Fill="White"> 
         <Rectangle.OpacityMask> 
          <DrawingBrush> 
           <DrawingBrush.Drawing> 
            <GeometryDrawing Geometry="M65.5,33 L537.5,35 537.5,274.5 C536.5,81 119.5,177 66.5,92" Brush="#11444444"> 
             <GeometryDrawing.Pen> 
              <Pen Brush="Transparent"/> 
             </GeometryDrawing.Pen> 
            </GeometryDrawing> 
           </DrawingBrush.Drawing> 
          </DrawingBrush> 
         </Rectangle.OpacityMask> 
        </Rectangle> 
        <Border Name="Border" 
          Background="Transparent" 
          BorderBrush="Gray" 
          BorderThickness="1" 
          CornerRadius="2"> 
         <ScrollViewer Margin="0" Focusable="false"> 
          <StackPanel Margin="2" IsItemsHost="True" /> 
         </ScrollViewer> 
        </Border> 
       </Grid> 
       <ControlTemplate.Triggers> 
        <Trigger Property="IsEnabled" Value="false"> 
         <Setter TargetName="Border" Property="Background" Value="Gray" /> 
         <Setter TargetName="Border" Property="BorderBrush" Value="DimGray" /> 
        </Trigger> 
        <Trigger Property="IsGrouping" Value="true"> 
         <Setter Property="ScrollViewer.CanContentScroll" Value="false"/> 
        </Trigger> 
       </ControlTemplate.Triggers> 
      </ControlTemplate> 
     </Setter.Value> 
    </Setter> 
</Style> 

<Style TargetType="{x:Type ListBoxItem}"> 
    <Setter Property="SnapsToDevicePixels" Value="true"/> 
    <Setter Property="OverridesDefaultStyle" Value="true"/> 
    <Setter Property="Foreground" Value="Gray"/> 
    <Setter Property="Background" Value="Transparent"/> 
    <Setter Property="FontFamily" Value="Verdana"/> 
    <Setter Property="HorizontalAlignment" Value="Stretch"/> 
    <Setter Property="FontSize" Value="11"/> 
    <Setter Property="Margin" Value="3,1,3,1"/> 
    <Setter Property="Padding" Value="0"/> 
    <Setter Property="FontWeight" Value="Normal"/> 
    <Setter Property="VerticalAlignment" Value="Center"/> 
    <Setter Property="Template"> 
     <Setter.Value> 
      <ControlTemplate TargetType="ListBoxItem"> 
       <Border Name="Border" 
         Padding="2" 
         SnapsToDevicePixels="true"> 
        <ContentPresenter /> 
       </Border> 
       <ControlTemplate.Triggers> 
        <Trigger Property="IsSelected" Value="true"> 
         <Setter TargetName="Border" Property="Background" Value="Gray"/> 
        </Trigger> 
        <Trigger Property="IsEnabled" Value="false"> 
         <Setter Property="Foreground" Value="White"/> 
        </Trigger> 
       </ControlTemplate.Triggers> 
      </ControlTemplate> 
     </Setter.Value> 
    </Setter> 
</Style> 

<ControlTemplate x:Key="ExpanderToggleButton" TargetType="ToggleButton"> 
    <Border Name="Border" 
      CornerRadius="2,0,0,0" 
      Background="Transparent" 
      BorderBrush="LightGray" 
      BorderThickness="0,0,1,0"> 
     <Path Name="Arrow" 
       Fill="Blue" 
       HorizontalAlignment="Center" 
       VerticalAlignment="Center" 
       Data="M 0 0 L 4 4 L 8 0 Z"/> 
    </Border> 
    <ControlTemplate.Triggers> 
     <Trigger Property="ToggleButton.IsMouseOver" Value="True"> 
      <Setter TargetName="Border" Property="Background" Value="Gray" /> 
     </Trigger> 
     <Trigger Property="IsPressed" Value="True"> 
      <Setter TargetName="Border" Property="Background" Value="Black" /> 
     </Trigger> 
     <Trigger Property="IsChecked" Value="True"> 
      <Setter TargetName="Arrow" Property="Data" Value="M 0 4 L 4 0 L 8 4 Z" /> 
     </Trigger> 
     <Trigger Property="IsEnabled" Value="False"> 
      <Setter TargetName="Border" Property="Background" Value="DimGray" /> 
      <Setter TargetName="Border" Property="BorderBrush" Value="DimGray" /> 
      <Setter Property="Foreground" Value="LightGray"/> 
      <Setter TargetName="Arrow" Property="Fill" Value="LightBlue" /> 
     </Trigger> 
    </ControlTemplate.Triggers> 
</ControlTemplate> 

<Style TargetType="{x:Type Expander}"> 
    <Setter Property="Foreground" Value="White"/> 
    <Setter Property="FontFamily" Value="Verdana"/> 
    <Setter Property="FontSize" Value="11"/> 
    <Setter Property="FontWeight" Value="Normal"/> 
    <Setter Property="Template"> 
     <Setter.Value> 
      <ControlTemplate TargetType="Expander"> 
       <Grid> 
        <Grid.RowDefinitions> 
         <RowDefinition Height="Auto"/> 
         <RowDefinition Name="ContentRow" Height="0"/> 
        </Grid.RowDefinitions> 
        <Border Name="Border" 
          Grid.Row="0" 
          Background="Black" 
          BorderBrush="DimGray" 
          BorderThickness="1" 
          Cursor="Hand" 
          CornerRadius="2,2,0,0" > 
         <Grid HorizontalAlignment="Left"> 
          <Grid.RowDefinitions> 
           <RowDefinition Height="23"/> 
          </Grid.RowDefinitions> 
          <Grid.ColumnDefinitions> 
           <ColumnDefinition Width="20" /> 
           <ColumnDefinition Width="*" /> 
          </Grid.ColumnDefinitions> 
          <ToggleButton IsChecked="{Binding Path=IsExpanded,Mode=TwoWay,RelativeSource={RelativeSource TemplatedParent}}" 
              Template="{StaticResource ExpanderToggleButton}" 
              Background="Black" /> 
          <Label Grid.Column="1" 
            FontSize="14" 
            FontWeight="Normal" 
            Margin="0" 
            VerticalAlignment="Top" 
            Foreground="White" 
            FontFamily="Verdana"> 
           <ContentPresenter Grid.Column="1" 
                Margin="4,3,0,0" 
                HorizontalAlignment="Left" 
                ContentSource="Header" 
                RecognizesAccessKey="True" /> 
          </Label> 
         </Grid> 
        </Border> 
        <Border Name="Content"         
          Background="Black" 
          BorderBrush="DimGray" 
          BorderThickness="1,0,1,1" 
          Grid.Row="1" 
          CornerRadius="0,0,2,2" > 
         <Grid Background="Black"> 
          <Rectangle VerticalAlignment="Stretch" 
             HorizontalAlignment="Stretch" 
             Fill="White"> 
           <Rectangle.OpacityMask> 
            <DrawingBrush> 
             <DrawingBrush.Drawing> 
              <GeometryDrawing Geometry="M65.5,33 L537.5,35 537.5,274.5 C536.5,81 119.5,177 66.5,92" Brush="#11444444"> 
               <GeometryDrawing.Pen> 
                <Pen Brush="Transparent"/> 
               </GeometryDrawing.Pen> 
              </GeometryDrawing> 
             </DrawingBrush.Drawing> 
            </DrawingBrush> 
           </Rectangle.OpacityMask> 
          </Rectangle> 
          <ContentPresenter Margin="4" /> 
         </Grid> 
        </Border> 
       </Grid> 
       <ControlTemplate.Triggers> 
        <Trigger Property="IsExpanded" Value="True"> 
         <Setter TargetName="ContentRow" Property="Height" Value="{Binding ElementName=Content,Path=DesiredHeight}" /> 
        </Trigger> 
        <Trigger Property="IsEnabled" Value="False"> 
         <Setter TargetName="Border" Property="Background" Value="Gray" /> 
         <Setter TargetName="Border" Property="BorderBrush" Value="DimGray" /> 
         <Setter Property="Foreground" Value="White"/> 
        </Trigger> 
       </ControlTemplate.Triggers> 
      </ControlTemplate> 
     </Setter.Value> 
    </Setter> 
</Style> 

Répondre

1

Utilisez un ItemsPresenter au lieu du StackPanel dans votre modèle de contrôle ListBox (en TestStyles.xaml).

+0

Merci, ça a fait l'affaire! – user304997