0

I have a simple winforms application doing keyboard emulation with:

private void timer1_Tick(object sender, EventArgs e)
{
    string keys = txtUID.Text + "{ENTER}";
    SendKeys.SendWait(keys);
}

This application sends keystrokes to the active window every second. I can see easily this app working opening notepad or any other program accepting inputs. Please note I cannot change this application because in the real word I have an application not written by me that probabily use SendKeys.SendWait, and I need to get those keystrokes in my application.

My goal was to get these keyboard inputs in another winforms application, when the main window is active, and I don't find any solutions yet.

First Attempt

I tried to get input in a standard way: I setted Form.KeyPreview = true and I have implemented Form_KeyDown event. Event never raised when Form is active when other application uses SendKeys.SendWait. Event is raised when I type some key on the keyboard.

Second Attempt

I tried to override ProcessCmdKey; same behaviour of the previous attempt: the function was not called when other application uses SendKeys.SendWait, while function is called when I type on the keyboard.

Third Attempt

I implement event TextBox_PreviewKeyDow in a textbox, I put the focus on this textbox but event is never raised when other application uses SendKeys.SendWait. As other attempts, event is raised if I type on the hardware keyboard.

Fourt Attempt

I wrote a global keyboard hook as described here Global keyboard capture in C# application. The strange behaviour is that the keyboard hook callback is called only when the main form is not active! When the form is active, the callback is not called.

So I don't find any way to get keyboard event sended by SendKeys in my winforms application.

EDIT

Someone suspects this a malicious application. In the real word the application using SendKeys is an application reading Badge UID and sending them as ASCII characters via keyboard emulation. Nothing malicious.

Marco
  • 961
  • 7
  • 11
  • 1
    You need to find a handle of window to what you want send some keys like this: https://stackoverflow.com/questions/13547639/return-window-handle-by-its-name-title . If you get the handle, you can import [DllImport("User32.dll")] and use the Win32 API function SendMessage / PostMessage. – Leo Chapiro Oct 22 '19 at 13:31
  • 2
    Why are you trying to capture keystrokes anyway? This sounds kind of like a malicious application. – Ryan Wilson Oct 22 '19 at 13:31
  • you could send message key down, up etc, but you need to send the whole set, so key down, key pressed key up etc.. – BugFinder Oct 22 '19 at 13:37
  • 1
    Your first attempt (`KeyDown` or `KeyPress` event with `KeyPreview = true`) should work just fine. Are you sure you're not trying to send keys to an elevated process from a non-elevated one? If you're not sure or you don't have control over one of the apps, run both of them as administrator and try again. – 41686d6564 stands w. Palestine Oct 22 '19 at 13:38
  • @RyanWilson It seems the OP only wants to capture the keystrokes _while their application form is active_. That doesn't sound malicious to me. – 41686d6564 stands w. Palestine Oct 22 '19 at 13:38
  • @AhmedAbdelhameed " Please note I cannot change this application because in the real word I have an application not written by me that probabily use SendKeys.SendWait, and I need to get those keystrokes in my application." – Ryan Wilson Oct 22 '19 at 13:44
  • I'd suggest to run Spy++ and see what messages your form recieves when it's in focus. Is there any WM_KEYDOWN / WM_KEYUP or WM_INPUT messages? – Sergey Shevchenko Oct 22 '19 at 13:48
  • @RyanWilson If you have an application that sends keystrokes to whatever the active window happens to be, then the "sender" application has nothing to hide; you can simply open Notepad and retrieve all the text being sent; nothing malicious about that. The OP (if I understand correctly) is trying to do the same but using another WinForms app instead of Notepad. – 41686d6564 stands w. Palestine Oct 22 '19 at 13:48
  • @AhmedAbdelhameed i tried to start my winforms application as elevated process with an app.manifest, but nothing is changed. – Marco Oct 22 '19 at 13:55
  • @AhmedAbdelhameed sorry you are right. First Attempt works fine if both application start with the same elevation grade. In other word everything works fine if both apps are lunched "As Administrator" or if both apps are lunched in normal ways. In all my test I run one application "As Administrator" (via app.manifest) and the other one in nornal way. Thank you. – Marco Oct 22 '19 at 14:11

0 Answers0