2010-05-07 2 views
5

ecco cosa vorrei fare. Ricevo un elenco di oggetti da un database e associo questo elenco a un controllo ListBox. I ListBoxItem sono costituiti da una casella di testo e un pulsante. Ecco cosa mi è venuto in mente. Fino a questo punto funziona come previsto. L'oggetto ha un numero di Proprietà come ID, Nome. Se clicco sul pulsante nella ListBoxItem l'articolo dovrebbe essere cancellata dalla casella di riepilogo e anche dal database ...WPF - Come ottengo un oggetto associato a un oggetto ListBoxItem

<ListBox x:Name="taglistBox">  
         <ListBox.ItemContainerStyle> 
          <Style TargetType="{x:Type ListBoxItem}"> 
           <Setter Property="HorizontalAlignment" Value="Stretch"/> 
           <Setter Property="Template"> 
            <Setter.Value> 
             <ControlTemplate TargetType="ListBoxItem"> 
              <ContentPresenter HorizontalAlignment="Stretch"/> 
             </ControlTemplate> 
            </Setter.Value> 
           </Setter> 
           <Setter Property="Tag" Value="{Binding TagSelf}"></Setter> 
          </Style> 
         </ListBox.ItemContainerStyle> 
         <ListBox.ItemTemplate> 
          <DataTemplate> 
           <Grid HorizontalAlignment="Stretch"> 
            <Grid.ColumnDefinitions> 
             <ColumnDefinition Width="Auto"/> 
             <ColumnDefinition/> 
            </Grid.ColumnDefinitions> 
            <Button Grid.Column="0" Name="btTag" VerticalAlignment="Center" Click="btTag_Click" HorizontalAlignment="Left"> 
             <Image Width="16" Height="16" Source="/WpfApplication1;component/Resources/104.png"/> 
            </Button> 
            <TextBlock Name="tbtagBoxTagItem" Margin="5" Grid.Column="1" Text="{Binding Name}" VerticalAlignment="Center" />           
           </Grid> 
          </DataTemplate> 
         </ListBox.ItemTemplate> 
        </ListBox> 

Il Textblock.Text è destinata a object.Name e il ListBoxItem.Tag di opporsi. TagSelf (che è solo una copia dell'oggetto stesso).

Ora le mie domande

  1. Se si fa clic sul pulsante nella ListBoxItem Come faccio ad avere il ListBoxItem e l'oggetto legato ad indietro. Per poter cancellare l'oggetto dal database, devo recuperarlo in qualche modo. Ho provato qualcosa come

    ListBoxItem lbi1 =
    (ListBoxItem) (taglistBox.ItemContainerGenerator.ContainerFromItem (taglistBox.Items.CurrentItem)); ObjectInQuestion t = (ObjectInQuestion) lbi1.Tag;

  2. C'è un modo per aggiornare automaticamente il contenuto del ListBox se la risorsa Item cambia? In questo momento lo sto raggiungendo per

    taglistBox.ItemsSource = null;
    taglistBox.ItemsSource = ObjectInQuestion;

Apprezzerei tutto l'aiuto che potete dare: D Grazie in anticipo

risposta

35

Ogni ListBoxItem avrà l'elemento corrispondente nella raccolta associata ai dati come DataContext. E ogni controllo in ListBoxItem.ItemTemplate erediterà DataContext. Per ottenere l'oggetto dietro il pulsante cliccato è possibile effettuare le seguenti operazioni nel gestore di eventi click:

MyClass item = (MyClass)(sender as Button).DataContext; 

Per avere alterazioni della fonte di dati aggiornati automaticamente alla casella di riepilogo, è possibile utilizzare un ObservableCollection.

1

Usa ObservableCollection per vedere immediati cambiamenti automatici

Prendi il SelectedItem utilizzando il DataContext

private void Button_Click(object sender, RoutedEventArgs e) 
{ 
    var btn = sender as Button; 
    myListBox.SelectedItem = btn.DataContext; 
} 

Dovresti avere una proprietà SelectedItem nel tuo viewmodel associato all'elemento selezionato della casella di riepilogo. Elimina quel particolare oggetto dalla tua ObservableCollection. La tua lista rifletterà le modifiche.

1

Alla domanda 2: utilizzare una ObservableCollection. Questo implementa INotifyCollectionChanged in modo che gli elementi vengano aggiunti e rimossi man mano che la collezione cambia.

Alla domanda 1: trasmettere il mittente come pulsante e utilizzarlo come DataContext. Questo sarà l'oggetto a cui è destinato. Se è anche necessario ottenere lo stesso ListBoxItem, è possibile effettuare il VisualTreeHelper.GetParent() per cercare l'albero.