Gary McGill
Gary McGill

Reputation: 27516

Can I intercept a paste into a DataGrid cell?

I have a DataGrid with columns of different types that I add in code. I have subclassed the standard data grid in order that I can override the OnExecutedPaste method etc. However, this only fires if the user pastes while no cell is in edit mode; if a cell is in edit mode, the clipboard content just gets pasted into the cell. I want to trap the paste event so that if the clipboard contains multiple values (e.g. data from Excel) then I can put each value in a different cell.

Can I intercept the paste event before the cell handles it? Hopefully without subclassing all the columns and implementing my own cell generation, etc.!

Upvotes: 2

Views: 1333

Answers (1)

Gope
Gope

Reputation: 1778

You probably don't need to subclass the Grid. That is more a WinForms thing. I don't know what columntypes you need but maybe this can point you in the right direction:

DataObject.AddPastingHandler(yourControl, PastingHandler);

You could create custom ColumnTypes derived from DataGridBoundColumn. That is pretty simple and then attach the pastinghandler to the editcontrol.

namespace StackOverflow
{
    public class CustomColumn : DataGridBoundColumn
    {
        protected override FrameworkElement GenerateElement(DataGridCell cell, object dataItem)
    {
        TextBlock block = new TextBlock();
        CustomColumn column = (CustomColumn)cell.Column;
        Binding binding = (Binding)column.Binding;
        if (binding != null)
        {
            // Binde den ausgewählten Wert
            Binding cellBinding = new Binding(binding.Path.Path);
            cellBinding.Source = dataItem;
            cellBinding.UpdateSourceTrigger = UpdateSourceTrigger.PropertyChanged;
            cellBinding.ValidatesOnDataErrors = true;
            cellBinding.ValidatesOnExceptions = true;
            cellBinding.NotifyOnValidationError = true;
            cellBinding.ValidatesOnNotifyDataErrors = true;
            cellBinding.Mode = BindingMode.OneWay;

            block.SetBinding(TextBlock.TextProperty, cellBinding);

        }

        return block;
    }

    protected override FrameworkElement GenerateEditingElement(DataGridCell cell, object dataItem)
    {
        TextBox box = new TextBox();
        CustomColumn column = (CustomColumn)cell.Column;
        Binding binding = (Binding)column.Binding;
        if (binding != null)
        {
            // Binde den ausgewählten Wert
            Binding cellBinding = new Binding(binding.Path.Path);
            cellBinding.Source = dataItem;
            cellBinding.UpdateSourceTrigger = UpdateSourceTrigger.PropertyChanged;
            cellBinding.ValidatesOnDataErrors = true;
            cellBinding.ValidatesOnExceptions = true;
            cellBinding.NotifyOnValidationError = true;
            cellBinding.ValidatesOnNotifyDataErrors = true;
            cellBinding.Mode = BindingMode.TwoWay;

            box.SetBinding(TextBlock.TextProperty, cellBinding);

        }

            DataObject.AddPastingHandler(box, PastingHandler);
            return box;
        }

        private void PastingHandler(object sender, DataObjectPastingEventArgs e)
        {
            TextBox textBox = sender as TextBox;
            if (textBox == null)
            {
                return;
            }

            if (e.DataObject.GetDataPresent(typeof(string)))
            {
                //Read input
                string pasteText = e.DataObject.GetData(typeof(string)) as string;
                // Kommt ein neuer String zurück, wird dieser eingefügt und die ursprüngliche Operation abgebrochen.
                if (!string.IsNullOrEmpty(pasteText))
                {
                    // Neuen Text einbringen
                    textBox.Text = pasteText;
                    // Restliches Einfügen abbrechen
                    e.CancelCommand();
                }
            }
        }
    }
}

Upvotes: 2

Related Questions