Copy and Modify selected text in different application
Asked Answered
U

5

11

I have a windows application running at the backend. I have functions in this applications mapped to hot keys. Like if I put a message box into this function and give hot key as Alt+Ctrl+D. then on pressing Alt, Ctrl and D together the message box comes up. My application is working fine till this point.

Now I want to write a code inside this function so that when I am using another application like notepad, I select a particular line of text and press the hot key Alt + Ctrl + D it is supposed to copy the selected text append it with "_copied" and paste it back to notepad.

Anyone who has tried a similar application please help me with your valuable inputs.

Unbecoming answered 25/10, 2008 at 5:53 Comment(0)
C
15

Your question has two answers

How can my app set a global hotkey

You have to call an API funcion called RegisterHotKey

BOOL RegisterHotKey(
    HWND hWnd,         // window to receive hot-key notification
    int id,            // identifier of hot key
    UINT fsModifiers,  // key-modifier flags
    UINT vk            // virtual-key code
);

More info here: http://www.codeproject.com/KB/system/nishhotkeys01.aspx

How to get the selected text from the foreground window

Easiest way is to send crl-C to the window and then capture the clipboard content.

[DllImport("User32.dll")] 
private static extern bool SetForegroundWindow(IntPtr hWnd);

[DllImport("user32.dll", CharSet=CharSet.Auto)]
static public extern IntPtr GetForegroundWindow();

[DllImport("user32.dll")]
static extern void keybd_event(byte bVk, byte bScan, uint dwFlags, uint dwExtraInfo);


.....

private void SendCtrlC(IntPtr hWnd)
    {
    uint KEYEVENTF_KEYUP = 2;
    byte VK_CONTROL = 0x11;
    SetForegroundWindow(hWnd);
    keybd_event(VK_CONTROL,0,0,0);
    keybd_event (0x43, 0, 0, 0 ); //Send the C key (43 is "C")
    keybd_event (0x43, 0, KEYEVENTF_KEYUP, 0);
    keybd_event (VK_CONTROL, 0, KEYEVENTF_KEYUP, 0);// 'Left Control Up

}

Disclaimer: Code by Marcus Peters from here: http://bytes.com/forum/post1029553-5.html
Posted here for your convenience.

Cockerel answered 7/11, 2008 at 18:49 Comment(1)
How do I use SendCtrlC ? I understand I pass in an IntPtr but what property of my control provides this?Antinode
P
3

UPDATE 2020

How to get the selected text from the foreground window

No idea for how long has this been possible but instead of fighting with Win32 programming (mostly user32.dll and various Windows messages like WM_GETTEXT, WM_COPY and various SendMessage(handle, WM_GETTEXT, maxLength, sb) calls) which is advised in most of SO threads on this topic, I easily managed to access selected text in any window in my C# code followingly:

// programatically copy selected text into clipboard
await System.Threading.Tasks.Task.Factory.StartNew(fetchSelectionToClipboard);

// access clipboard which now contains selected text in foreground window (active application)
await System.Threading.Tasks.Task.Factory.StartNew(useClipBoardValue);

Here the methods being called:

static void fetchSelectionToClipboard()
{
  Thread.Sleep(400);
  SendKeys.SendWait("^c");   // magic line which copies selected text to clipboard
  Thread.Sleep(400);
}

// depends on the type of your app, you sometimes need to access clipboard from a Single Thread Appartment model..therefore I'm creating a new thread here
static void useClipBoardValue()
{
  Exception threadEx = null;
  // Single Thread Apartment model
  Thread staThread = new Thread(
     delegate ()
       {
          try
          {
             Console.WriteLine(Clipboard.GetText());
          }
          catch (Exception ex)
          {
            threadEx = ex;
          }
      });
  staThread.SetApartmentState(ApartmentState.STA);
  staThread.Start();
  staThread.Join();
}
Paternity answered 28/1, 2020 at 16:1 Comment(0)
D
1

Use the Clipboard class to copy the contents to the clipboard, then paste in the notepad.

You could also write the contents to a text file and open it with notepad by running the notepad.exe application with the text file's path as a command line parameter.

Decontaminate answered 25/10, 2008 at 9:54 Comment(1)
Thanks for the information. My main problem was, is it possible for a application to get to know the selected text in someother application like notepad. Please let me know if this would be possible?Unbecoming
C
0

I think you can use SendInput function to send the text to the target window or just the command to paste it if you have put it in clipboard before.

Crippling answered 25/10, 2008 at 16:4 Comment(0)
I
0

In addition to other comments. When you're using global hotkeys to send keystrokes you NEED to set delay (or to use more complex logic) as in DurkoMatko's example, before sending keystrokes or your pressed keys will overlap with sended keystrokes, also you may need to bring app window in focus with SetForegroundWindow() method, you'll need handle Process.MainWindowHandle from process or from FindWindow() method, depends on your use-case.

https://learn.microsoft.com/en-us/dotnet/desktop/winforms/input-keyboard/how-to-simulate-events?view=netdesktop-6.0

[DllImport("USER32.DLL", CharSet = CharSet.Unicode)]
public static extern IntPtr FindWindow(string lpClassName, string lpWindowName);

[DllImport("USER32.DLL")]
public static extern bool SetForegroundWindow(IntPtr hWnd);

Example:

Clipboard.Clear();
await Task.Delay(300);
SendKeys.SendWait("^{c}");
if (!Clipboard.ContainsText()) return;
var clipboard = Clipboard.GetText();
... // modifying logic here
Clipboard.SetText(clipboard)
SendKeys.SendWait("^{v}");
Impoverished answered 23/10, 2022 at 10:3 Comment(0)

© 2022 - 2024 — McMap. All rights reserved.