VBAのマクロ実行中にExcelが固まったように見える場合は、ループの中に DoEvents を1行入れることで改善できます。DoEvents はマクロの処理を止めずに、画面の更新や操作の受け付けを一時的に許可する命令です。
この記事では、次の内容を順番に解説します。
- なぜマクロ実行中にExcelが固まって見えるのか
- DoEventsの基本的な使い方
- 使いすぎによるパフォーマンス低下と対処法
なぜマクロ実行中にExcelが固まって見えるのか?
VBAがマクロを動かしている間、ExcelはWindowsからの操作(マウスクリック・画面更新など)をいったん無視します。そのため、大量のデータを処理するループが動いている間は「Excelが反応しない」状態になってしまいます。
マクロ自体は正常に動いているのですが、操作を受け付けていないため、ユーザーには固まっているように見えてしまいます。
DoEventsとは?
DoEvents はマクロの処理中に「ちょっとの間、他の操作も受け付けていいよ」とExcelに伝える命令です。これを入れることで、画面がリアルタイムで更新されたり、マウス操作が効くようになったりします。
DoEventsなしとありの違い
次のコードはA1セルに1から100万までの数を順番に表示します。
' DoEventsなし:最後にいきなり1000000になる
Sub NoDoEvents()
Dim i As Long
For i = 1 To 1000000
Cells(1, 1).Value = i
Next i
MsgBox "完了しました"
End Sub
' DoEventsあり:数字がリアルタイムで変わっていく
Sub WithDoEvents()
Dim i As Long
For i = 1 To 1000000
Cells(1, 1).Value = i
DoEvents
Next i
MsgBox "完了しました"
End Sub
DoEvents を入れるだけで、セルの値がリアルタイムで更新されるようになり、マウス操作も効くようになります。
DoEventsを使いすぎると処理が遅くなる?
はい、毎回のループに DoEvents を入れると、そのたびにExcelが「他に操作はないか」を確認するため、処理が遅くなります。
大量のループで使う場合は、100回に1回など間隔を空けて入れるのがおすすめです。
For i = 1 To 100000
Cells(i, 1).Value = i
' 100回に1回だけDoEventsを実行する
If i Mod 100 = 0 Then
DoEvents
End If
Next i
i Mod 100 = 0 は「iを100で割った余りが0のとき」という意味です。100の倍数のときだけ DoEvents が実行されます。
よくある使い方:処理の途中でキャンセルできるようにするには?
長い処理の途中でユーザーがキャンセルできるようにしたい場合も、DoEvents が役立ちます。
Sub LongProcess()
Dim i As Long
For i = 1 To 50000
DoEvents
' Escキーが押されたら処理を止める
If GetAsyncKeyState(vbKeyEscape) Then
MsgBox "処理を中断しました"
Exit Sub
End If
Cells(i, 1).Value = i
Next i
MsgBox "完了しました"
End Sub
DoEvents を入れておくことで、マクロ実行中でもEscキーなどの操作を受け付けられるようになります。
まとめ
DoEvents はたった1行ですが、マクロの使いやすさを大きく変えられます。長い処理を書くときはぜひ活用してみてください。
- 役割:マクロ実行中に画面更新や操作の受け付けを一時的に許可する。
- 使い方:ループの中に
DoEventsと1行書くだけ。 - 使いすぎに注意:毎ループではなく、
If i Mod 100 = 0 Then DoEventsのように間隔を空ける。 - よくある用途:処理の途中経過を画面に表示したい・途中でキャンセルできるようにしたい。
よくある質問
DoEventsを入れたら処理が遅くなった場合は?
入れる間隔を広げましょう。毎ループではなく If i Mod 1000 = 0 Then DoEvents のように1000回に1回にすると、速度への影響をほとんどなくせます。処理の速さと操作の反応のバランスを見て調整してください。
DoEventsを入れるとマクロが途中で止まることがある?
はい、DoEventsを入れると操作を受け付けるため、ユーザーがセルをクリックしたりボタンを押したりして、意図しない別の処理が走ることがあります。DoEventsを使う場合は、ユーザーが操作できる状態になることを意識して設計しましょう。
ScreenUpdatingとDoEventsはどう違う?
Application.ScreenUpdating = False は画面更新を止めてマクロを速くする設定です。一方 DoEvents は画面更新や操作を一時的に許可する設定です。目的が逆なので、通常は併用しません。速度重視なら ScreenUpdating = False、操作を受け付けたいなら DoEvents を使います。
DoEventsはループ以外でも使える?
使えます。たとえば時間のかかるファイル処理や外部データの読み込みの途中に入れることもできます。ただし基本的にはループ処理の中で使うことが多いです。
マクロ実行中に強制終了する方法は?
DoEventsを使っていれば Esc キーでマクロを止められることがあります。止まらない場合はVBAの編集画面(Alt+F11)を開いて、ツールバーの「■(停止)」ボタンをクリックするのが確実です。それでも止まらない場合はタスクマネージャーからExcelを終了する方法があります。
動画で学びたい方へ
「記事を読んでも、実際に自分で書けるか不安…」という方には、動画で基礎からじっくり学べる講座がおすすめです。
VBAが初めての方を前提に、つまずきやすいポイントを先回りして解説しています。サンプル動画は無料でご覧いただけます。



