WPF
DataGrid
Single Click Edit
User Interface
C#

Single click edit in WPF DataGrid

Master System Design with Codemia

Enhance your system design skills with over 120 practice problems, detailed solutions, and hands-on exercises.

Introduction

WPF DataGrid defaults to selection-first behavior, which usually requires two clicks before editing starts. That is safe for read-heavy grids but slow for spreadsheet-like data entry screens. Enabling single-click edit can improve throughput, as long as focus, validation, and keyboard behavior stay correct.

Why Default Behavior Uses Two Clicks

By default, the first click selects a cell or row and the second click enters edit mode. This prevents accidental edits during navigation.

For data-entry workflows, this default can feel inefficient. In those screens, explicit single-click edit behavior is often worth the change.

Base XAML Configuration

Start with explicit edit-focused settings.

xml
1<DataGrid x:Name="OrdersGrid"
2          AutoGenerateColumns="False"
3          SelectionUnit="Cell"
4          SelectionMode="Extended"
5          CanUserAddRows="False"
6          PreviewMouseLeftButtonDown="OrdersGrid_PreviewMouseLeftButtonDown">
7    <DataGrid.Columns>
8        <DataGridTextColumn Header="Product"
9                            Binding="{Binding ProductName, UpdateSourceTrigger=PropertyChanged}" />
10        <DataGridTextColumn Header="Qty"
11                            Binding="{Binding Quantity, UpdateSourceTrigger=PropertyChanged}" />
12    </DataGrid.Columns>
13</DataGrid>

SelectionUnit="Cell" usually matches single-click editing expectations better than row selection.

Enter Edit Mode on First Click

Handle preview mouse click, locate the clicked cell, set focus, then call BeginEdit.

csharp
1using System.Windows;
2using System.Windows.Controls;
3using System.Windows.Input;
4using System.Windows.Media;
5
6private void OrdersGrid_PreviewMouseLeftButtonDown(object sender, MouseButtonEventArgs e)
7{
8    if (sender is not DataGrid grid)
9        return;
10
11    var origin = e.OriginalSource as DependencyObject;
12    var cell = FindParent<DataGridCell>(origin);
13
14    if (cell is null || cell.IsReadOnly || cell.IsEditing)
15        return;
16
17    if (!cell.IsFocused)
18        cell.Focus();
19
20    grid.BeginEdit(e);
21}
22
23private static T? FindParent<T>(DependencyObject? child) where T : DependencyObject
24{
25    while (child != null)
26    {
27        if (child is T typed)
28            return typed;
29        child = VisualTreeHelper.GetParent(child);
30    }
31    return null;
32}

This keeps the edit trigger precise and avoids activating edit mode on non-cell clicks.

MVVM-Friendly Attached Behavior

If you avoid code-behind, wrap the same logic in an attached behavior.

csharp
1public static class DataGridEditBehavior
2{
3    public static readonly DependencyProperty EnableSingleClickEditProperty =
4        DependencyProperty.RegisterAttached(
5            "EnableSingleClickEdit",
6            typeof(bool),
7            typeof(DataGridEditBehavior),
8            new PropertyMetadata(false, OnChanged));
9
10    public static void SetEnableSingleClickEdit(DependencyObject d, bool value) =>
11        d.SetValue(EnableSingleClickEditProperty, value);
12
13    public static bool GetEnableSingleClickEdit(DependencyObject d) =>
14        (bool)d.GetValue(EnableSingleClickEditProperty);
15
16    private static void OnChanged(DependencyObject d, DependencyPropertyChangedEventArgs e)
17    {
18        if (d is not DataGrid grid) return;
19
20        if ((bool)e.NewValue)
21            grid.PreviewMouseLeftButtonDown += GridPreviewMouseLeftButtonDown;
22        else
23            grid.PreviewMouseLeftButtonDown -= GridPreviewMouseLeftButtonDown;
24    }
25
26    private static void GridPreviewMouseLeftButtonDown(object sender, MouseButtonEventArgs e)
27    {
28        // reuse same focus and BeginEdit logic
29    }
30}

Enable it in XAML where needed.

Validation and Commit Flow

Single-click edit should not break validation or keyboard commit behavior. Check:

  • Tab navigation commits correctly.
  • Enter key behavior matches product expectations.
  • Validation errors still appear with clear visual feedback.
xml
1<DataGridTextColumn Header="Qty">
2    <DataGridTextColumn.Binding>
3        <Binding Path="Quantity"
4                 UpdateSourceTrigger="PropertyChanged"
5                 ValidatesOnDataErrors="True"
6                 NotifyOnValidationError="True" />
7    </DataGridTextColumn.Binding>
8</DataGridTextColumn>

Test both valid and invalid edits in realistic row counts.

Performance and Virtualization Notes

For large datasets:

  • Keep row and column virtualization enabled where possible.
  • Avoid expensive visual-tree operations per click.
  • Keep cell templates lightweight.

Single-click edit should improve usability without degrading scroll and selection performance.

In high-velocity entry screens, this small interaction change often yields measurable operator efficiency gains when paired with validation that surfaces errors immediately.

Common Pitfalls

  • Triggering BeginEdit for every click, including headers and scrollbars.
  • Ignoring read-only cells and creating confusing interaction.
  • Testing only mouse paths and breaking keyboard editing workflows.
  • Hardcoding visual tree assumptions that fail with custom templates.
  • Skipping validation and virtualization tests before release.

Summary

  • Single-click edit is a strong fit for edit-heavy, spreadsheet-like grids.
  • Use preview click handling to focus the cell and call BeginEdit intentionally.
  • Keep behavior reusable through attached behaviors in MVVM codebases.
  • Preserve validation and keyboard semantics while changing click interaction.
  • Verify behavior under realistic templates and large virtualized datasets.

Course illustration
Course illustration

All Rights Reserved.