Blue Prism で右コントロールキー(rctrl: RIGHT CONTROL KEY)を押す
久しぶりに学生時代の友達と会ったので、
酒飲んだ後にゲーセンに行ってストⅡで対戦してみた。
昇竜拳、強すぎない・・・?
今ならアプデで修正入るレベルだろ。。
Blue Prism で右コントロールキーが押せない?
こういう話、よく耳にします。
先日も同様のコメントをいただきました。
・・・そういうことなら、、
よし、自作してみるか!
若干、酒が入っておかしなテンションだけど、
たまには日曜プログラミングもいいよね!
Windows APIのSendInputを使う
- この記事は、コーディング(プログラミング)の話題を含みます。
- 苦手な方はブラウザバックをお薦めします。
- あ、でも .NET のプログラミング経験がなくても、読めないことはない、そのくらいの難度です。
(やや酔っぱらった状態で)軽く調べたところ、
デスクトップでキー操作を送る方法は複数あり、
例えば.NET FrameworkのSendKeysなんかが有名なわけですが、
他にもWindows APIを呼ぶ方式で、SendInput関数を呼び出すこともできるようです。
ほうほうなるほど・・・スゲー参考になる。
じゃあ、これをBlue Prismに組み込むにはどうすれば良いか?
いろいろ試行錯誤しつつ・・・ヤバい、このままでは完全に酔っぱらってしまう・・・
・・・あ、これで動きそう。
まず、右コントロールキー(rctrl)を押すオブジェクトを作って、
ビジネスオブジェクトのプロパティ(initialiseアクションの左上の四角をダブルクリック)を開けて、グローバルコードの中に宣言系のコードを入れていきます。
コードについては、以下のサイトを参考にさせていただきました(というか、ほとんどコピペです。。)。
中身はこんな感じ。
' マウスイベント(mouse_eventの引数と同様のデータ)
<StructLayout(LayoutKind.Sequential)> _
Private Structure MOUSEINPUT
Public dx As Integer
Public dy As Integer
Public mouseData As Integer
Public dwFlags As Integer
Public time As Integer
Public dwExtraInfo As Integer
End Structure' キーボードイベント(keybd_eventの引数と同様のデータ)
<StructLayout(LayoutKind.Sequential)> _
Private Structure KEYBDINPUT
Public wVk As Short
Public wScan As Short
Public dwFlags As Integer
Public time As Integer
Public dwExtraInfo As Integer
End Structure' ハードウェアイベント
<StructLayout(LayoutKind.Sequential)> _
Private Structure HARDWAREINPUT
Public uMsg As Integer
Public wParamL As Short
Public wParamH As Short
End Structure' 各種イベント(SendInputの引数データ)
<StructLayout(LayoutKind.Explicit)> _
Private Structure INPUT
<FieldOffset(0)> Public type As Integer
<FieldOffset(4)> Public mi As MOUSEINPUT
<FieldOffset(4)> Public ki As KEYBDINPUT
<FieldOffset(4)> Public hi As HARDWAREINPUT
End Structure' キー操作、マウス操作をシミュレート(擬似的に操作する)
<DllImport("user32.dll")> _
Private Shared Sub SendInput( _
ByVal nInputs As Integer, ByRef pInputs As INPUT, ByVal cbsize As Integer)
End Sub' 仮想キーコードをスキャンコードに変換
<DllImport("user32.dll", EntryPoint:="MapVirtualKeyA")> _
Private Shared Function MapVirtualKey( _
ByVal wCode As Integer, ByVal wMapType As Integer) As Integer
End FunctionPrivate Const INPUT_MOUSE = 0 ' マウスイベント
Private Const INPUT_KEYBOARD = 1 ' キーボードイベント
Private Const INPUT_HARDWARE = 2 ' ハードウェアイベントPrivate Const MOUSEEVENTF_MOVE = &H1 ' マウスを移動する
Private Const MOUSEEVENTF_ABSOLUTE = &H8000 ' 絶対座標指定
Private Const MOUSEEVENTF_LEFTDOWN = &H2 ' 左 ボタンを押す
Private Const MOUSEEVENTF_LEFTUP = &H4 ' 左 ボタンを離す
Private Const MOUSEEVENTF_RIGHTDOWN = &H8 ' 右 ボタンを押す
Private Const MOUSEEVENTF_RIGHTUP = &H10 ' 右 ボタンを離す
Private Const MOUSEEVENTF_MIDDLEDOWN = &H20 ' 中央ボタンを押す
Private Const MOUSEEVENTF_MIDDLEUP = &H40 ' 中央ボタンを離す
Private Const MOUSEEVENTF_WHEEL = &H800 ' ホイールを回転する
Private Const WHEEL_DELTA = 120 ' ホイール回転値Private Const KEYEVENTF_KEYDOWN = &H0 ' キーを押す
Private Const KEYEVENTF_KEYUP = &H2 ' キーを離す
Private Const KEYEVENTF_EXTENDEDKEY = &H1 ' 拡張コード
Private Const VK_SHIFT = &H10 ' SHIFTキー
今回はキーボードイベントしか送らないから、いろいろ不要なコードがあるかも。。
また、コードオプションの Namespace Imports に、System.Runtime.InteropServices を追加します。
次に、右コントロールキー(rctrl)を押すアクションを作ります。
ここには、コードステージを置いて、中身に以下のようなコードを追加します。
Dim inp As INPUT() = New INPUT(3) {}
inp(0).type = INPUT_KEYBOARD
inp(0).ki.wVk = 163
inp(0).ki.wScan = MapVirtualKey(inp(1).ki.wVk, 0)
inp(0).ki.dwFlags = KEYEVENTF_EXTENDEDKEY Or KEYEVENTF_KEYDOWN
inp(0).ki.dwExtraInfo = 0
inp(0).ki.time = 0SendInput(1, inp(0), Marshal.SizeOf(inp(0)))
右 コ ン ト ロ ー ル キ ー = 1 6 3
いま見返すと、不要なコードがたくさんある・・・もっとキレイにしよう!次の機会にな!!
動かしてみる
実際に動かしてみます。
右コントロールキー(rctrl: RIGHT CONTROL KEY)を押せたかどうかの検証は、
キー入力を仮想キーボードで視覚化できる「kbv」を使用しました。
実際にやった結果はこちら。
やったぜ。
まとめ
- Blue Prism で右コントロールキー(rctrl: RIGHT CONTROL KEY)を押す部品を自作した
- 酔っ払い日曜プログラミングなので、業務で使うには要修正。動くことは動く
- あ、キーを離すコードを書くの忘れた。。(実行すると押しっぱになります。もう一回、手動で押すと解除されます)
最初は、Blue Prism のコード記述能力って、すごく制限されていると思ったんですけど
(例えば、構造体を作る機能がないので、入出力に構造体を定義できない…とか)
・・・やればいろいろ、できるもんですね。今後もチャレンジしていきたいもんです。