2015-10-13 13 views
5

Brandneu in WPF, ziemlich komfortabel mit WinForms (die wahrscheinlich den Übergang rauer machen). Ich versuche, einige Funktionen aus einem alten WinForms-Projekt als Lernerfahrung in WPF zu portieren.WPF DataGrid Zyklus durch/Select Zellen mit bestimmten Eigenschaft

Ziel ist es, Zellenwerte in einem DataGrid zu finden, das mit einer Zeichenfolge in einer TextBox übereinstimmt. Ich habe eine great example mit Bindings gefunden, die genau das tun. Im Grunde wird der verknüpfte Code die Hintergrundfarbe einer übereinstimmenden DataGridCell in Orange ändern. Ich habe meine Version ein wenig modifiziert, aber die Funktionalität sollte die gleiche sein. Bitte beachten Sie den Link für Codebeispiele, scheint ein wenig überflüssig, um es hier zur Verfügung zu stellen. Die Daten, die mein DataGrid füllen, stammen aus einer DataTable (wenn das wichtig ist).

Was ich tun möchte, von dort ist eine Schaltfläche „Weiter“, die zyklisch durch jede dieser Zellen (entweder bestimmt mit der Hintergrundfarbe oder die benutzerdefinierte Eigenschaft DataGridTextSearch.IsTextMatch) und auswählen. Es scheint, als wäre es möglich, den bereitgestellten Code etwas zu ändern, aber ich weiß nicht, wo ich anfangen soll. In meinem alten WinForms-Projekt habe ich die DataGridViewCell in einer Liste gespeichert (nachdem ich sie mit einer Linq-Abfrage gefunden habe) und einfach das Verhalten der Schaltfläche angehängt, um die Liste zu inkrementieren und die aktuelle Zelle zu setzen. Ich vermute, dass es wahrscheinlich einen intelligenteren/besseren Weg gibt, der Bindungen involviert, und ich weiß nicht einmal, wie man diese passenden Zellen zu einer Liste hinzufügt, wenn das eine Option wäre.

Also, ich möchte eine Schaltfläche, die durch bestimmte DataGridCells (basierend auf dem Hintergrund oder der benutzerdefinierten DataGridTextSearch.IsTextMatch -Eigenschaft) zykliert und wählt sie aus.

Vielen Dank im Voraus.

Antwort

5

Basierend auf der link Sie in Ihrer Frage zur Verfügung gestellt, ich bin zu einer Lösung dafür gekommen. In meiner Lösung, wenn ein DataGridCell die Zeichenfolge in der TextBox entspricht, wird es Tag Eigenschaft wird auf "1" festgelegt und dann, wenn der Button wird angeklickt, wird es durchlaufen alle DataGridCells und finden Sie Elemente mit nicht null Tags und schließlich markierte Zellen wird eins nach dem anderen konzentriert.

Hier ist ein funktionierendes Beispiel um Ihnen eine Vorstellung zu geben:

XAML:

<Window Name="UI"> 
    <Grid> 
     <Grid.RowDefinitions> 
      <RowDefinition Height="*"/> 
      <RowDefinition Height="Auto"/> 
     </Grid.RowDefinitions> 
     <StackPanel DataContext="{Binding ElementName=UI}" Grid.Row="0"> 
      <TextBox Name="SearchBox" TextChanged="SearchBox_TextChanged"/> 
      <DataGrid x:Name="grid" 
        m:DataGridTextSearch.SearchValue="{Binding ElementName=SearchBox, Path=Text, UpdateSourceTrigger=PropertyChanged}" 
        ItemsSource="{Binding TestData}" 
        SelectionUnit="Cell"> 
       <DataGrid.Resources> 
        <m:SearchValueConverter x:Key="SearchValueConverter" /> 
        <Style TargetType="{x:Type DataGridCell}"> 
         <Setter Property="m:DataGridTextSearch.IsTextMatch"> 
          <Setter.Value> 
           <MultiBinding Converter="{StaticResource SearchValueConverter}"> 
            <Binding RelativeSource="{RelativeSource Self}" Path="Content.Text" /> 
            <Binding RelativeSource="{RelativeSource Self}" Path="(m:DataGridTextSearch.SearchValue)" /> 
           </MultiBinding> 
          </Setter.Value> 
         </Setter> 
         <Style.Triggers> 
          <Trigger Property="m:DataGridTextSearch.IsTextMatch" Value="True"> 
           <Setter Property="Background" Value="Orange" /> 
           <Setter Property="Tag" Value="1" /> 
          </Trigger> 
         </Style.Triggers> 
        </Style> 
       </DataGrid.Resources> 
      </DataGrid> 
     </StackPanel> 
     <Button Grid.Row="1" Click="Button_Click" Content="GoNext"/> 
    </Grid> 
</Window> 

MainWindow.cs:

int currentIndex = 0; 

private void SearchBox_TextChanged(object sender, TextChangedEventArgs e) 
{ 
    currentIndex = 0; 
} 

private void Button_Click(object sender, RoutedEventArgs e) 
{ 
    var selectedCells = GetHighLightedCells(); 
    if (selectedCells.Count == 0) 
     return; 

    selectedCells[currentIndex].Focus(); 

    if (currentIndex == selectedCells.Count - 1) 
     currentIndex = 0; 
    else 
     currentIndex++; 
} 

Methoden markierten Zellen zu erhalten:

public List<DataGridCell> GetHighLightedCells() 
{ 
    List<DataGridCell> selectedCells = new List<DataGridCell>(); 
    foreach (DataGridRow rowContainer in GetDataGridRows()) 
    { 
     if (rowContainer != null) 
     { 
      DataGridCellsPresenter presenter = GetVisualChild<DataGridCellsPresenter>(rowContainer); 
      foreach (var col in grid.Columns) 
      { 
       DataGridCell cell = (DataGridCell)presenter.ItemContainerGenerator.ContainerFromIndex(col.DisplayIndex); 
       if (cell == null) 
       { 
        grid.ScrollIntoView(rowContainer, col); 
        cell = (DataGridCell)presenter.ItemContainerGenerator.ContainerFromIndex(col.DisplayIndex); 
       } 
       if (cell.Tag != null) 
       { 
        selectedCells.Add(cell); 
       } 
      } 
     } 
    } 
    return selectedCells; 
} 
public IEnumerable<DataGridRow> GetDataGridRows() 
{ 
    var itemsSource = grid.ItemsSource as IEnumerable; 
    if (null == itemsSource) yield return null; 
    foreach (var item in itemsSource) 
    { 
     var row = grid.ItemContainerGenerator.ContainerFromItem(item) as DataGridRow; 
     if (null != row) yield return row; 
    } 
} 

public static T GetVisualChild<T>(Visual parent) where T : Visual 
{ 
    T child = default(T); 
    int numVisuals = VisualTreeHelper.GetChildrenCount(parent); 
    for (int i = 0; i < numVisuals; i++) 
    { 
     Visual v = (Visual)VisualTreeHelper.GetChild(parent, i); 
     child = v as T; 
     if (child == null) 
     { 
      child = GetVisualChild<T>(v); 
     } 
     if (child != null) 
     { 
      break; 
     } 
    } 
    return child; 
} 
+1

Erstaunlich. Ich arbeitete tatsächlich an etwas ähnlichem, aber es hätte ewig gedauert, bis ich die gesamte Lösung gefunden hätte. Bin dankbar! Vielen Dank. – Finch042

+0

Sie sind herzlich willkommen :) –