WPF -DataGrid: Programmatisch die aktuelle Zelle einstellen, ohne dass die Registerkartenfunktionalität geschlossen wirdC#

Ein Treffpunkt für C#-Programmierer
Anonymous
 WPF -DataGrid: Programmatisch die aktuelle Zelle einstellen, ohne dass die Registerkartenfunktionalität geschlossen wird

Post by Anonymous »

Ich versuche programmgesteuert die aktuelle Zelle eines WPF -Datagrids und starten Sie den Bearbeitungsmodus wie folgt: < /p>

Code: Select all

MyDataGrid.CurrentCell = new DataGridCellInfo(myViewModel, PunktzahlColumn);
MyDataGrid.BeginEdit();
< /code>
Dieser Code wird ausgeführt, nachdem der Benutzer etwas in ein Suchtextfeld über dem Raster eingeleitet hat. Die text 
Eigenschaft dieses Textfelds ist in meinem ViewModel an einen EigenschaftssuchText gebunden. Ich verwende dann ReactiveUi, um die Benutzereingabe wie folgt zu verarbeiten: < /p>

Code: Select all

this.WhenAnyValue(x => x.SearchText)
.Throttle(TimeSpan.FromMilliseconds(300))
.ObserveOn(RxApp.MainThreadScheduler)
.Subscribe(_ => searchAndFocus());
< /code>
FocusRequested
wird dann in der Ansicht von meiner OnfocusRequested -Funktion behandelt. Die Zelle ist ausgewählt und wird bearbeitet. Wenn der Benutzer beim Bearbeiten dieser Zelle jedoch auf die Registerkarte gedrückt wird, anstatt sich in derselben Zeile zur nächsten Spalte zu bewegen, springt der Fokus zurück zum Suchtext.Dispatcher.InvokeAsync(() =>
{
var cellContent = PunktzahlColumn.GetCellContent(MyDataGrid.CurrentItem);
if (cellContent != null)
{
var textBox = FindVisualChild(cellContent);
textBox?.Focus();
}
});
< /code>
But this doesn't change the behavior — pressing Tab still jumps to the search box instead of navigating within the DataGrid. I've also tried focusing the grid first, but no matter what I try, I can't seem to change this behaviour. Here is a minimal reproducible example:
MainWindow.xaml:




















< /code>
MainWindow.xaml.cs:
using System.Windows;
using System.Windows.Controls;

namespace WpfApp1;

public partial class MainWindow : Window
{
private readonly MainWindowViewModel mainWindowViewModel;

public MainWindow()
{
InitializeComponent();
mainWindowViewModel = new MainWindowViewModel();
mainWindowViewModel.FocusRequested += OnFocusRequested;
this.DataContext = mainWindowViewModel;
}

private void MyDataGrid_CellEditEnding(object sender, DataGridCellEditEndingEventArgs e)
{
if (e.Column == PunktzahlColumn && e.EditAction == DataGridEditAction.Commit && SearchTextBox.Text.Length > 0)
{
SearchTextBox.Focus();
mainWindowViewModel.SearchText = string.Empty;
}
}

private void OnFocusRequested(MyViewModel myViewModel)
{
MyDataGrid.UnselectAllCells();
MyDataGrid.CurrentCell = new DataGridCellInfo(myViewModel, PunktzahlColumn);
MyDataGrid.BeginEdit();
}
}
< /code>
MainWindowViewModel.cs
using ReactiveUI;
using ReactiveUI.Fody.Helpers;
using System.Collections.ObjectModel;
using System.Reactive.Linq;
using System.Windows;

namespace WpfApp1;

public class MainWindowViewModel : ReactiveObject
{
private ObservableCollection myViewModels;
public IEnumerable MyViewModels => myViewModels;
public event Action? FocusRequested;

[Reactive]
public string? SearchText { get; set; }

public MainWindowViewModel()
{
myViewModels = new ObservableCollection();

for (int i = 0; i < 10; i++)
{
myViewModels.Add(new MyViewModel($"Name {i}", i * 10, $"Kommentar {i}"));
}

this.WhenAnyValue(x => x.SearchText)
.Throttle(TimeSpan.FromMilliseconds(300))
.ObserveOn(RxApp.MainThreadScheduler)
.Subscribe(_ => searchAndFocus());
}

private void searchAndFocus()
{
if (string.IsNullOrWhiteSpace(SearchText))
{
return;
}

var matches = MyViewModels
.Where(b => b.Name.Contains(SearchText, StringComparison.OrdinalIgnoreCase))
.ToList();

if (matches.Count == 1)
{
// Set focus with delay
Application.Current.Dispatcher.InvokeAsync(() =>
{
FocusRequested?.Invoke(matches[0]);
});
}
}
}
< /code>
MyViewModel.cs:
using ReactiveUI;
using ReactiveUI.Fody.Helpers;

namespace WpfApp1;

public class MyViewModel : ReactiveObject
{
[Reactive]
public string Name { get; set; }

[Reactive]
public int? Punktzahl { get; set; }

[Reactive]
public string? Kommentar { get; set; }

public MyViewModel(string name, int? punktzahl, string? kommentar)
{
Name = name;
Punktzahl = punktzahl;
Kommentar = kommentar;
}
}
< /code>
Dependencies:
  • ReactiveUI version 20.2.45
  • ReactiveUI.Fody version 19.5.41
  • ReactiveUI.WPF version 20.2.45

Quick Reply

Change Text Case: 
   
  • Similar Topics
    Replies
    Views
    Last post