2015-06-08 20 views
7

Ich habe ein Problem mit ListBoxItem s. Ich versuche, alle Kontrollen in der ListBoxItem wählen Sie es auch, so klicken Sie auf eine TextBox, Label, etc. wird die ListBoxItem auswählen. Ziemlich einfach so weit.WPF ListBoxItem ControlTemplate bricht einige MouseDown/Selection

Ich ändere auch die ListBoxItem Vorlage, um die Auswahl Visualisierung von der Hervorhebung des Hintergrunds zu ändern, nur um einen Rahmen zu zeichnen. Auch ziemlich einfach.

Die Kombination dieser beiden scheint jedoch einige wirklich irritierend Probleme mit MouseDown und PreviewMouseDown, speziell in meinem Fall in Bezug auf Label s in einem Grid zu verursachen, wo man eine „Lücke“ besetzt von Grid Raum schafft.

Snoop verwenden, kann ich das PreviewMouseDown Ereignis sehen im ScrollViewer innerhalb des ListBox stoppen, und nicht auf die ListBoxItem den ganzen Weg gehen.

click no worky

XAML:

<Window x:Class="ListBoxClickThroughTest.MainWindow" 
     xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation" 
     xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" 
     Title="MainWindow" 
     Width="525" 
     Height="350"> 
    <Grid> 
     <ListBox ItemsSource="{Binding Items}" 
       SelectionMode="Single"> 

      <ListBox.ItemTemplate> 
       <DataTemplate> 
        <Grid> 
         <Grid.ColumnDefinitions> 
          <ColumnDefinition Width="Auto" /> 
          <ColumnDefinition Width="*" /> 
         </Grid.ColumnDefinitions> 
         <Grid.RowDefinitions> 
          <RowDefinition /> 
          <RowDefinition /> 
         </Grid.RowDefinitions> 

         <Label Name="VerySuperLongLabel" 
           Grid.Row="0" 
           Grid.Column="0" 
           HorizontalAlignment="Left" 
           Content="VerySuperLongLabel" 
           Padding="0" /> 

         <TextBox Name="Textbox1" 
           Grid.Row="0" 
           Grid.Column="1" 
           HorizontalAlignment="Stretch" 
           HorizontalContentAlignment="Right" 
           Text="Textbox1 Text" /> 


         <Label Name="ShortLabel" 
           Grid.Row="1" 
           Grid.Column="0" 
           HorizontalAlignment="Left" 
           Content="ShortLabel" 
           Padding="0" /> 
         <TextBox Name="Textbox2" 
           Grid.Row="1" 
           Grid.Column="1" 
           HorizontalAlignment="Stretch" 
           HorizontalContentAlignment="Right" 
           Text="Textbox2 Text" /> 
        </Grid> 
       </DataTemplate> 
      </ListBox.ItemTemplate> 

      <ListBox.ItemContainerStyle> 
       <Style TargetType="{x:Type ListBoxItem}"> 
        <EventSetter Event="PreviewMouseDown" 
           Handler="ListBoxItem_PreviewMouseDown" /> 
        <EventSetter Event="MouseDown" 
           Handler="ListBoxItem_PreviewMouseDown" /> 
        <Setter Property="HorizontalContentAlignment" Value="Stretch" /> 
        <Setter Property="Template"> 
         <Setter.Value> 
          <ControlTemplate TargetType="{x:Type ListBoxItem}"> 
           <Border x:Name="Bd" 
             BorderThickness="1"> 
            <ContentPresenter /> 
           </Border> 
           <ControlTemplate.Triggers> 
            <Trigger Property="IsSelected" Value="true"> 
             <Setter TargetName="Bd" Property="BorderBrush" Value="Gray" /> 
            </Trigger> 
           </ControlTemplate.Triggers> 
          </ControlTemplate> 
         </Setter.Value> 
        </Setter> 
       </Style> 
      </ListBox.ItemContainerStyle> 
     </ListBox> 

    </Grid> 
</Window> 

-Code-behind:

using System.Collections.Generic; 
using System.Windows; 
using System.Windows.Controls; 
using System.Windows.Input; 

namespace ListBoxClickThroughTest 
{ 
    /// <summary> 
    /// Interaction logic for MainWindow.xaml 
    /// </summary> 
    public partial class MainWindow : Window 
    { 
     public MainWindow() 
     { 
      Items = new List<string>() { "1", "2" }; 
      InitializeComponent(); 
      DataContext = this; 
     } 

     public List<string> Items { get; set; } 

     private void ListBoxItem_PreviewMouseDown(object sender, MouseButtonEventArgs e) 
     { 
      var listBoxItem = (ListBoxItem)sender; 
      listBoxItem.IsSelected = true; 
     } 
    } 
} 

Allerdings, wenn ich die Template Setter zu entfernen, ist alles gut. Gibt es Magie in der Vorlage, die ich vermisse? Ich habe versucht, die Umrandung auf "Bd" umzubenennen, denn das war der Name der Standardvorlage, aber kein Glück. Irgendwelche Ideen?

+0

Versuchen Sie, einen Rahmen zu erhalten, wenn Sie in das Leerzeichen rechts neben dem zweiten Listeneintrag klicken? –

+0

@Aaron, Ich versuche, das 'ListBoxItem' durch Klicken auf _anywhere_ darin auszuwählen und zeige die Auswahl über einen Rahmen (wie das oben ausgewählte Element im Screenshot). Der Code funktioniert überall mit Ausnahme der Lücke rechts von "ShortLabel". –

+0

Wusste nicht, dass Sie Snoop verwenden können, um Ereignisse zu sehen! – Contango

Antwort

5

Wenn Sie die horizontale Ausrichtung der Beschriftungen von "Links" auf "Strecken" ändern, wird das Problem behoben und die visuelle Formatierung beibehalten.

Mousedown-Ereignisse funktionieren nur in Bereichen, in denen Elemente vorhanden sind. Wenn Sie die Beschriftungen in einer "linken" horizontalen Ausrichtung haben, erstellen Sie die von Ihnen erwähnte "Leere", in der auf dieser Ebene kein Element vorhanden ist, auf das geklickt werden kann. Um den Unterschied visuell zu erkennen, versuchen Sie vorübergehend, die Hintergrundeigenschaft der Beschriftungselemente, die Ihnen Probleme verursachen, zu setzen, und Sie werden feststellen, dass das Element nicht bis zum Textfeld reicht.

+0

Brilliant! Dies behebt ein lang andauerndes Problem, das ich in meinem Projekt hatte. – Contango

+0

So einfach. Vielen Dank! Ich dachte, das 'ListBoxItem' würde das 'MouseDown'-Ereignis in einer Situation wie dieser, in der es eine Lücke gibt, bekommen. Danke noch einmal! –

+0

Irgendeine Idee, warum das 'ListBoxItem' das Ereignis nicht empfängt? Ich denke, das ist eine gute Lösung, aber es erklärt nicht, warum dieses Ereignis beim 'ScrollViewer' zu sterben scheint. –

Verwandte Themen