Recipe 14.9. Control Applications by Simulating Keystrokes


Problem

You need another application to perform some tasks while your application is running, but it doesn't expose any type of control interface, whether ActiveX or .NET.

Solution

Sample code folder: Chapter 14\UsingSendKeys

Use the My.Computer.Keyboard.SendKeys() method to simulate the user controlling the other application from the keyboard.

Discussion

The following method uses SendKeys() to control the built-in Windows Paint program, using it to convert an existing image to black and white:

 Public Sub MakeBitmapBW(ByVal sourceFile As String, _       ByVal destFile As String)    ' ----- Use the Paint program built into Windows to    '       convert an existing bitmap file from color to    '       black and white.    Dim paintProcess As Process    On Error Resume Next    ' ----- Remove the existing output file.    Kill(destFile)    ' ----- Start Paint using the original file.    paintProcess = Process.Start("mspaint.exe", sourceFile)    appactivate(paintProcess.Id)    ' ----- Wait a bit for the file to open.    System.Threading.Thread.Sleep(2000)    ' ----- Convert the image to black and white. First,    '       display the Attributes form using Control-E.    My.Computer.Keyboard.SendKeys("^e", True)    System.Threading.Thread.Sleep(500)    ' ----- Alt-B sets the "Black and White" field.    My.Computer.Keyboard.SendKeys("%b", True)    System.Threading.Thread.Sleep(500)    ' ----- Use Enter to accept the change. A confirmation    '       window will appear. Use Enter for that window    '       as well.    My.Computer.Keyboard.SendKeys("~", True)    System.Threading.Thread.Sleep(500)    My.Computer.Keyboard.SendKeys("~", True)    System.Threading.Thread.Sleep(500)    ' ----- Save the file using the File->Save As… feature.    My.Computer.Keyboard.SendKeys("%fa", True)    System.Threading.Thread.Sleep(500)    ' ----- Add the filename to the Save As window.    '       Hopefully, the name has no special characters.    My.Computer.Keyboard.SendKeys(destFile, True)    My.Computer.Keyboard.SendKeys("~", True)    System.Threading.Thread.Sleep(1000)    ' ----- Exit the   application.    My.Computer.Keyboard.SendKeys("%{F4}", True) End Sub 

To use this method, pass it the full path to an existing bitmap file and a path to the desired output location.

The SendKeys() method inserts specific keyboard commands into the global keyboard input stream. Those commands appear as if the user had actually typed them from the keyboard. The first argument to SendKeys() is a string containing each character to be inserted into the input stream. The second argument, a Boolean, indicates whether SendKeys() should wait until the active window acknowledges acceptance of the input.

Normally, each character you include in the character string is sent to the active window, one by one. However, some keys, such as the function keys (F1, F2, etc.) and the arrow keys, don't have single-character equivalents. Instead, there are special sequences you can use for these keys, most enclosed in curly braces. Some normal characters that have special meaning to SendKeys() must also appear in curly braces. Table 14-1 lists the text to include in the character string when you wish to use one of these special keyboard keys.

Table 14-1. Special SendKeys( ) key sequences

To include this key…

…use this text

Backspace

{BACKSPACE} or {BS} or {BKSP}

Break

{BREAK}

Caps lock

{CAPSLOCK}

Caret (^)

{^}

Clear

{CLEAR}

Close brace (})

{}}

Close bracket (])

{]}

Close parenthesis ())

{)}

Delete

{DELETE} or {DEL}

Down arrow

{DOWN}

End

{END}

Enter

~

Escape

{ESCAPE} or {ESC}

F1 through F16

{F1} through {F16}

Help

{HELP}

Home

{HOME}

Insert

{INSERT} or {INS}

Keypad add

{ADD}

Keypad divide

{DIVIDE}

Keypad enter

{ENTER}

Keypad multiply

{MULTIPLY}

Keypad subtract

{SUBTRACT}

Left arrow

{LEFT}

Num lock

{NUMLOCK}

Open brace ({ )

{{}

Open bracket ([)

{[}

Open parenthesis (()

{(}

Page down

{PGDN}

Page up

{PGUP}

Percent sign (%)

{%}

Plus (+)

{+}

Print screen

{PRTSC}

Return

{RETURN}

Right arrow

{RIGHT}

Scroll lock

{SCROLLLOCK}

Tab

{TAB}

Tilde (~)

{~}

Up arrow

{UP}


For example, if you want to send the number 25, a tab character, and then the number 50 to the input stream, send the following sequence:

 25{TAB}50 

You can also simulate the simultaneous use of the Shift, Control, or Alt keys in combination with other keys. Special prefix characters represent these three special modification keys:

  • For Shift, use + (the plus sign).

  • For Control, use ^ (the caret).

  • For Alt, use % (the percent sign).

So, to send the Control-C character, use:

 ^c 

If you want several characters to be used with one of these three modifiers, surround those keys with parentheses, and put the modifier just before that set. For instance, to send "hello" with the Shift key held down, use:

 +(hello) 

The key string provides a shortcut to transmit the same key multiple times, too. To use it, enclose the character to repeat and a count within curly braces. Separate the character and the count with a space. The following text sends 10 question marks:

 {? 10} 

There are some caveats when using SendKeys(). Just because you include characters in the input stream doesn't mean that they will arrive at the program you target. Remember, the user still has access to the real keyboard, and to the mouse. The user could start pressing keys and clicking around the display right in the middle of your SendKeys() action, and you would have no control over the destination or sequence of the streaming input.

Similarly, even if you use True for the second argument to have your program wait until the keys are processed, there is no guarantee that the impact of those keys on the destination will complete before the wait is complete. A target program may acknowledge receipt of an input character and start to process it, but it could take several seconds (or longer) for it to complete the associated action. Meanwhile, your call to SendKeys() has exited, and your code is continuing on its way, possibly starting another call to SendKeys().

If you can control the other application through more direct means, such as through an exposed library or interface, that is preferred. Avoid having an application control itself with SendKeys().

Besides the SendKeys() command within the My namespace, Visual Basic includes a SendKeys class in the System.Windows.Forms namespace. This class includes shared Send() and SendWait() methods. Each accepts a string that is identical to the one used with the SendKeys() method. Except for slight differences in syntax and location in the .NET hierarchy, there is no essential difference between the My version and the Forms version.




Visual Basic 2005 Cookbook(c) Solutions for VB 2005 Programmers
Visual Basic 2005 Cookbook: Solutions for VB 2005 Programmers (Cookbooks (OReilly))
ISBN: 0596101775
EAN: 2147483647
Year: 2006
Pages: 400

flylib.com © 2008-2017.
If you may any questions please contact us: flylib@qtcs.net