Question

I have a textview and when something is pasted into it from the clipboard I need to intercept that text and do some preprocessing on it before it ends up in the textview.

I've tried listening to the "PasteClipboard" event which doesn't give me a way to modify the incoming text. and the "textview.Buffer.Changed" event which fires after the pasted text makes it into the textview.

Thanks in advance.

Was it helpful?

Solution

AFAIK your best option is to postprocess the text after it's been inserted - the InsertText event on the TextBuffer has arguments that tell you the position and size of the inserted text, so you can remove, process and re-insert it. You would of course want to avoid catching 1-char insertions (keystrokes) and your own re-insertions, but that's trivial.

The only other option I can think of is to re-implement paste support, by catching the paste key command, middle-click, etc. - but note that the command keys can be overridden in users' gtkrc files, so implementing this correctly could get hairy.

It might also be worth asking in the #gtk+ IRC channel on irc.gnome.org.

OTHER TIPS

Doing some short googling, I found the following documentation on Gtk.TextBuffer and GTK alternative to .net WndProc in Mono. It appears that you might want to add the [GLib.ConnectBefore] attribute to your code to access GTK's WndProc method. Beaner's code above would probably work with slight modification for the GTK framework.

This may not be a help to you, but I am catching the WM_PASTE message in a custom control that implements TextBox. I get the GetText from the clipboard into a string variable and if it matches what I am looking for I make my changes to the variable and set the .Text to my variable and swallow the event so the textbox neer gets it. If it is not what I am looking for, but is allowed I just pass the event on with base.WndProc(ref m).

Sample:

protected override void WndProc(ref Message m)
{
    if (m.Msg == WM_PASTE)
    {
        string clipboardVin = Clipboard.GetText();
        string newVin = "";
        if (SelectionLength > 0)
        {
            newVin = Text.Replace(SelectedText, "");
        }
        else
        {
            newVin = Text;
        }
        newVin = newVin.Insert(SelectionStart, clipboardVin);
        if (!vinRegEx.IsMatch(newVin))
        {
            m.Result = new IntPtr(Convert.ToInt32(true));
            MessageBox.Show("The resulting text is not a valid VIN.", "Can Not Paste", MessageBoxButtons.OK, MessageBoxIcon.Error);
        }
        else
        {
            base.WndProc(ref m);
        }
    }
    else
    {
        base.WndProc(ref m);
    }
}
Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top