ExcelマクロVBA入門
第121回.SendKeysメソッドとAppActivateステートメント

Excelマクロの基礎と応用、エクセルVBAの入門・初級・初心者向け解説
最終更新日:2019-07-23

第121回.SendKeysメソッドとAppActivateステートメント


マクロVBAから直接連携操作できない他のアプリケーションに対しても、VBAのキーコードを転送を使って操作することが可能です。
SendKeysメソッドを使い、アクティブなアプリケーションにキーコードを転送することで操作します。
これは、他のアプリケーションにキーホード入力をすることができるという事です。
もちろん、マクロが動作しているExcel自身にもキーコードを転送できます。


キーコードを転送するアプリケーションはアクティブなアプリケーションだけです。
アクティブではないアプリケーションにキーコードを転送したい場合は、
事前に、AppActivateステートメントでアクティブにしてからSendKeysを使います。

SendKeysメソッド

SendkeysはApplicationのメソッドです。
グローバル定義されているので、Applicationは省略できます。
キーストロークまたはキーストロークの組み合わせを、キーボードから入力したときと同様にアクティブウィンドウに渡します。
アクティブウィンドウに対してしか作用しませんので、必ず対象のアプリケーションをアクティブにしておきます。
SendKeys string[, wait]

名前付き引数については、以下になります。



string 必ず指定します。
転送するキーコードを表す文字列式を指定します。
wait 省略可能です。
名前付き引数 string の転送によって行われる処理が終了するまで、実行を一時中断するかどうかを次に示すブール型の値で指定します。
False(既定値) プロシージャの終了を待たずに次の行に制御を移します。
True 処理が終了するまで実行を一時中断します。

キーボード上の文字を渡すには、その文字をそのまま使います。
キーボード上の文字 A を表すには、名前付き引数 stringに"A"を指定します。
複数の文字は連続して設定します、文字 A、B、C を表すには、名前付き引数 string に "ABC" と指定します。

プラス記号 (+)、キャレット (^)、パーセント記号 (%)、チルダ (~)、かっこ (( )) はそれぞれ SendKeys ステートメントで特別です。
これらの文字を渡すには、文字を中かっこ ({ }) で囲んで指定します、プラス記号であれは {+} のように指定します。

特殊なキーを表す文字

キーを押したときに表示されない文字 (Enter キーや Tab キーなど)
文字ではなく動作を表すキーを指定するには、次に示すコードを使います。

キー コード
BackSpace {BACKSPACE}、{BS}、または {BKSP}
Ctrl + Break {BREAK}
CapsLock {CAPSLOCK}
Del または Delete {DELETE} または {DEL}
{DOWN}
End {END}
Enter {ENTER}または {~}
Esc {ESC}
Help {HELP}
Home {HOME}
Ins または Insert {INSERT} または {INS}
{LEFT}
NumLock {NUMLOCK}
PageDown {PGDN}
PageUp {PGUP}
PrintScreen {PRTSC}
{RIGHT}
ScrollLock {SCROLLLOCK}
Tab {TAB}
{UP}
F1 {F1}
F2 {F2}
F3 {F3}
F4 {F4}
F5 {F5}
F6 {F6}
F7 {F7}
F8 {F8}
F9 {F9}
F10 {F10}
F11 {F11}
F12 {F12}
F13 {F13}
F14 {F14}
F15 {F15}
F16 {F16}

Shiftキー、Ctrlキー、Altキーと他のキーとの組み合わせを指定するには、
通常のキーコードの前に次のコードを単独、または組み合わせて記述します。

キー コード
Shift +
Ctrl ^
Alt %

Shift キー、Ctrl キー、Alt キーを押しながら他のキーを押す場合は、キーのコードをかっこで囲みます。
Shift キーを押しながらEとCを押す操作を指定するには、"+(EC)" を使います。
Shift キーを押しながらEを押し、その後Shiftキーを離してCを押す場合は、"+EC" とします。

AppActivateステートメント

アプリケーション ウィンドウをアクティブにします。
AppActivate title[, wait]



指定項目 内容
title 必ず指定します。
アクティブにするアプリケーション ウィンドウのタイトル バーのタイトルを表す文字列式を指定します。
名前付き引数 title に Shell 関数によって返されるタスク ID を指定して、アプリケーションをアクティブにすることもできます。
wait 省略可能です。
名前付き引数 title で指定したアプリケーションをアクティブにする前に呼び出し側のアプリケーションにフォーカスを持たせるかどうかを、次に示すブール型 (Boolean) の値を使って設定します。
False(既定値) :呼び出し側のアプリケーションがフォーカスを持っていなくても、指定したアプリケーションをアクティブにします。
True:呼び出し側のアプリケーションがフォーカスを持つまで待機し、指定したアプリケーションをアクティブにします。

AppActivateでフォーカスが移っても指定したウィンドウの状態は変化しません。
たとえば、最小化されているウィンドウにフォーカスを移しても、そのウィンドウは最小化されたままです。

アプリケーション ウィンドウのタイトル バーの文字列と、名前付き引数 title が完全に一致しているかどうかを比較することによって、どのアプリケーションをアクティブにするかが判別されます。
完全に一致するものが見つからないときは、title で始まるアプリケーションをアクティブにします。
一致するアプリケーション ウィンドウが複数ある場合は、 1 つが任意に選択されてアクティブになります。

titleの指定について
Shell 関数で起動したアプリケーションは、Shell関数の戻り値のタスク IDを指定します。
マクロが起動されている自身のExcelは、Application.Caption を指定してください。
既に起動済みの他のアプリケーションの場合は、ウィンドウのタイトルを間違えずに指定してください。

SendkeysとAppActivateの使用例

以下はヘルプにある電卓でのSenkeysの使用例を極力正しく動作するように改変したものです。
実践的な使用例ではありませんが、
SendKeysを理解する為の練習として、簡単に試せるのが良いでしょう。

Dim ReturnValue, i
' 電卓を実行します。
ReturnValue = Shell("CALC.EXE", vbNormalFocus)

'起動時にスタート画面が長くかかる場合の対処
'秒数は適宜変更してください。
Application.Wait Now() + TimeSerial(0, 0, 3)

'電卓をアクティブに:起動待ち
On Error Resume Next
Do
  Application.Wait Now() + TimeSerial(0, 0, 1)
  DoEvents
  Err.Clear
  '電卓をアクティブにします。
  AppActivate "電卓"
Loop While Err

'1~20までの数字を送る
For i = 1 To 20
  '電卓にキーコードを転送して、
  SendKeys i & "{+}", True
Next

'和を求めます。
SendKeys "=", True
MsgBox "計算終了"
※ヘルプのままでは環境により動作しないのでVBAソースは変更しています。

Shell関数については、次回の、
第122回.Shell関数
Excelを自動操作するのがVBAですが、他のアプリケーションを起動したい場合も時に出てきます。他のアプリケーションを起動する手段としてVBAに標準で用意されているものがShell関数です。VBAの実行結果をテキスト出力しておいて、マクロ終了時に、メモ帳で実行結果を表示するといったようなことが、
こちらを参考にしてください。

Sendkeysでは送信できないキーコード

プリントスクリーン(PrntScr)は、SendKeysでは送れません。
プリントスクリーン(PrntScr)を送るには、APIが必要になります。
以下のページにAPI(keybd_event )を使用したVBAサンプルを掲載しています。
全シートの画面キャプチャを取得する(keybd_event)
資料等の作成で、画面キャプチャすることがあると思います。そこで、全シートの画面キャプチャを、新規シートに全て取得するプログラムです。Alt+PrntScrnで、エクセルのウインドウのみキャプチャしています。

NumLockが解除されてしまう問題

SendKeysを実行すると、「NumLock」がOffになってしまう事があります。
というより、かなりの確率でOffになります。
上掲の電卓操作で、Windows10のExcelでは毎回Offになっていました。
キーボードにテンキーが無ければ気にならないところですが、
テンキー付きのキーボードでは、これは大変困ったことになるではないでしょうか。
これを回避するには、最後にNumLockキーを送信することで対応できます。

'NumLockが解除されてしまう事への対応
SendKeys "{NUMLOCK}"

これを最後に入れるということです。
しかし、
必ず「NumLock」が「Off」になるのなら、これで良いのですが、
もし、SenKeysを実行してもNumLockがOffになっていなかったら、逆にわざわざOffにしてしまう事になります。

NumLockがOffになっていればすぐに分かりますし、
キーボードを1回押すだけなので、気にしなければそれでも構わないと思いますが、
これでは困るという場合は、
以下のように、WScript.ShellのSendKeysを使用してください。

Public Function SendKeys(InpKeys As String, Optional Wait As Boolean = False)
  Static WSH As Object
  If WSH Is Nothing Then
    Set WSH = CreateObject("WScript.Shell")
  End If
  WSH.SendKeys InpKeys
End Function

プロシージャー名をApplicationの本来のメソッドSendKeysと同一にしているので、
これを同じプロジェェクト(同じブック)の標準モジュールに入れるだけで、
先の電卓操作のマクロVBAのままで動作します。
(このような実装方法をラップするという言い方をしたりします)
本来のSendKeysを使う場合と切り替えたい時は、Applicationから書き始めて、
Application.SendKeys ・・・
このように書けば、ApplicationのSendKeysメソッドが動作するようになります。

※WScript.ShellのSendKeysで問題が発生しないとは言い切れません。
上の電卓操作を何度か実行した限りでも大丈夫でしたが、
100%発生しないかどうか、別の問題があるかどうか等々
キーコード送信は環境に依存しますので、使用するときは翌確認してください。
VBAのSendKeysよりは安定動作するという程度に考えた方が良いと思います。

Sendkeysについて

SendKeysはとても便利な機能なのですが、
上記のような問題点以外にも、
対象のアプリケーションによっては、動作が安定しない場合も多いので使用には注意が必要です。
少なくとも、SendKeysを使ったマクロVBA動作中に、ユーザーが他のウインドウをあちこちクリックしてしまったら正しく動作させることはできません。
SendKeysを使う場合は、ユーザーにマクロVBA終了までは一切操作しない事を徹底させる必要があります。

他のアプリケーションを操作する手段が無い場合や、実現したいことが他のVBAの機能ではできない場合も時にはあるでしょう。
そのような場合は、
キーボード操作可能であるならば、基本的にはSendkeysを使ってキーボード操作と同じことが実現できます。
そういった場合の最終手段として考えると良いと思います。



同じテーマ「マクロVBA入門」の記事

第118回.ファイル操作Ⅱ(Print #)
第119回.ファイルシステムオブジェクト(FileSystemObject)
第120回.OnTimeメソッド
第121回.SendKeysメソッドとAppActivateステートメント
第122回.Shell関数
第123回.APIについて(Win32API)
第124回.Workbookのイベントプロシージャー
第125回.Worksheetのイベントプロシージャー
第126回.入力規則(Validation)
第127回.他のブックのマクロを実行(Runメソッド)
第128回.マクロをショートカットで起動(OnKeyメソッド)


新着記事NEW ・・・新着記事一覧を見る

Byte配列と文字コード関数について|VBA技術解説(8月20日)
PowerQueryの強力な機能をVBAから利用する方法|VBA技術解説(8月4日)
練習問題31(セル結合を解除して値を埋める)|VBA練習問題(7月30日)
練習問題30(マトリックス→リスト形式)|VBA練習問題(7月25日)
Applicationを省略できるApplicationのメソッド・プロパティ一覧|VBA技術解説(7月22日)
コレクション(Collection)の並べ替え(Sort)に対応するクラス|VBA技術解説(7月20日)
CSVの読み込み方法(ジャグ配列)|VBAサンプル集(7月15日)
その他のExcel機能(グループ化、重複の削除、オートフィル等)|VBA入門(7月14日)
オートフィルタ退避回復クラスを複数シート対応させるVBAクラス|VBA技術解説(7月6日)
オートフィルタを退避回復するVBAクラス|VBA技術解説(7月6日)


アクセスランキング ・・・ ランキング一覧を見る

1.最終行の取得(End,Rows.Count)|VBA入門
2.セルのコピー&値の貼り付け(PasteSpecial)|VBA入門
3.RangeとCellsの使い方|ExcelマクロVBA入門
4.Range以外の指定方法(Cells,Rows,Columns)|VBA入門
5.変数とデータ型(Dim)|ExcelマクロVBA入門
6.繰り返し処理(For Next)|ExcelマクロVBA入門
7.マクロって何?VBAって何?|ExcelマクロVBA入門
8.セルに文字を入れるとは(Range,Value)|VBA入門
9.ひらがな⇔カタカナの変換|エクセル基本操作
10.空白セルを正しく判定する方法(IsEmpty,IsError,HasFormula)|VBA技術解説



  • >
  • >
  • >
  • SendKeysメソッドとAppActivateステートメント

  • このサイトがお役に立ちましたら「シェア」「Bookmark」をお願いいたします。


    記述には細心の注意をしたつもりですが、
    間違いやご指摘がありましたら、「お問い合わせ」からお知らせいただけると幸いです。
    なお、掲載のVBAコードは自己責任で使ってください。万一データ破損等の損害が発生しても責任は負いません。




    このサイトがお役に立ちましたら「シェア」「Bookmark」をお願いいたします。
    本文下部へ