Search code examples
wpfwindowsoutlookclipboardsendinput

System.Windows.Clipboard and MS Office applications


I am currently using System.Windows.Clipboard to: set some text, call SendInput with control+V, finally restoring the previous clipboard.

This works in most applications, though in Microsoft's Office applications the send input is causing the previous clipboard to be restored. I am assuming it is something to do with a delay in the SendInput method, so I added a wait before restoring and resolved the issue for most users, but Outlook for a user is still restoring the previous clipboard.

is there a better way of doing it than below?

 try
    {
      //method that uses GetDataObject and stores it to be restored
      _clipboard.Acquire();

      try
         {
            _clipboard.SetText(ClipboardText);

            //a wrapper for SendInput()
            SendInputWrapper.SendKeyCombination(new KeyCode(VirtualKeyShort.Control),
                                        new KeyCode(VirtualKeyShort.KeyV));
         }
         finally
         {
          //without this pause word and outlook would paste the original clipboard
          await Task.Delay(TimeSpan.FromMilliseconds(200));
          
          //wrapper method for Clipboard.SetDataObject() using the above stored 
            clipboard
          _clipboard.Restore();
          }
     }
     catch (Exception ex)
     {
       _log.Error("Error caught pasting text", ex);
     }

Solution

  • Though it does not answer my direct question to Offices Clipboard buffer, the solution I have which now works is using Word.Interop:

            var currentSelection = _word.Selection;
    
            // Store the user's current Overtype selection
            var userOvertype = _word.Options.Overtype;
    
            // Make sure Overtype is turned off.
            if (_word.Options.Overtype) _word.Options.Overtype = false;
    
            // Test to see if selection is an insertion point.
            if (currentSelection.Type == WdSelectionType.wdSelectionIP)
                currentSelection.TypeText(text);
            else if (currentSelection.Type == WdSelectionType.wdSelectionNormal)
            {
                // Move to start of selection.
                if (_word.Options.ReplaceSelection)
                {
                    object direction = WdCollapseDirection.wdCollapseStart;
                    currentSelection.Collapse(ref direction);
                }
    
                currentSelection.TypeText(text);
            }
    
            // Restore the user's Overtype selection
            _word.Options.Overtype = userOvertype;