起動済みのIE(InternetExplorer)を制御する

<< InternetExplorerオブジェクトのQuitメソッドでIEを閉じる :前の記事

前回は、開いているInternetExplorerを閉じる方法について解説しました。こちらは1行で完了するステートメントですので、InternetExplorerを閉じる場合は、直接InternetExplorerオブジェクトのQuitメソッドを利用するようにしましょう。

ここまででIE(InternetExplorer)を「開く・閉じる」の処理はマスターしたかと思います。ここまでの単純な処理であれば特に問題はありませんが、サイトのデータをループ処理で抽出したいなど複雑な処理になればエラーが起こることもよくあります。その際に誤って処理を終了させたりIE(InternetExplorer)を閉じてしまうと、それまでの処理が無駄になることもあります。

どう対応するかについては処理の内容にもよりますが、最初からやり直す方もいれば途中から処理ができるようにプログラムを書き換える方もいるかと思います。もちろんどちらで処理をするのが正解とういわけではなく、効率の良い方を選択するのが良いかと思います。

今回こちらで解説するのはそのような場合の対策の1つとして、エクセルVBAからIE制御ができないIE(InternetExplorer)を制御できるようにする方法について解説していきます。

目次

手動でIE(InternetExplorer)を閉じた場合のエラー確認

まずは途中で誤ってIE(InternetExplorer)を閉じた場合、どのようなエラーが表示されるのかを確認します。下記は、わざとエラーを表示させるマクロになります。

処理の内容は最初にIE(InternetExplorer)が自動で起動します。次にメッセージボックスが表示されますので、その間に自動で起動したIEを閉じてから再度手動でIEを起動させてください。手動で起動できたら、メッセージボックスの「OK」をクリックします。するとエラーが発生しますので、そちらを確認してください。

Sub sample()

  Dim objIE  As InternetExplorer

  '本サイトをIE(InternetExplorer)で起動
  Call ieView(objIE, "http://www.vba-ie.net/")
  
  MsgBox "自動で起動したIEを閉じてから再度手動でIEを起動させてください。"
  
  '指定したURLをIE(InternetExplorer)に表示
  Call ieNavi(objIE, "http://www.vba-ie.net/ie/position-size.html")

End Sub

※ドラッグ(スワイプ)すると全体を確認できます。

エラー確認サンプルコードの実行結果

「実行時エラー'462':リモートサーバーがないか、使用できる状態ではありません。」の実行時エラーが表示されます。
リモート サーバーがないか、使用できる状態ではありません

エラーの確認はできたでしょうか?一度閉じてしまったIE(InternetExplorer)を再度エクセルVBAで制御しようと思ったらこれまでの解説した内容では解決することができません。制御できていないIEを制御するためにはSetステートメントでオブジェクトをセットする必要がありますので、この方法について解説していきます。

起動済みのIE(InternetExplorer)を制御する処理の流れ

以下が今回の処理の流れになります。

利用するサブルーチン・VBA関数について

今回利用するサブルーチンVBA関数は以下になります。

ieViewサブルーチンとは

ieViewサブルーチンは指定したURLをInternetExplorerで起動させ、Webページが完全に読み込まれるまで待機処理をするマクロです。

ieView("IEオブジェクト","表示させたいURLの文字列","IE表示・非表示の値[省略可]")

ieCheckサブルーチンとは

ieCheckサブルーチン指定したInternetExplorerオブジェクトのWebページが完全に読み込まれるまで待機処理をするマクロです。

ieCheck("IEオブジェクト")

ieNaviサブルーチンとは

ieNaviサブルーチン制御中のInternetExplorer指定したURLのWebページを表示させるマクロです。

ieNavi("IEオブジェクト","表示させたいURLの文字列")

CreateObject関数とは

CreateObject関数はオートメーション機能を利用して一時的なオブジェクトを作成する関数です。この関数を利用すると、外部アプリケーションをオブジェクトとして操作することが可能となります。

Set オブジェクト変数名 = CreateObject("アプリケーション名・オブジェクトの種類")

起動済みのIE(InternetExplorer)を制御するサンプルコード

起動済みのIE(InternetExplorer)を制御して本サイトのトップページを表示させるマクロです。

Sub sample()

    Dim objIE As InternetExplorer
    Dim objShell  As Object, objWin As Object

    'Shellオブジェクトを作成する
    Set objShell = CreateObject("Shell.Application")
      
  
    For Each objWin In objShell.Windows

        If objWin.name = "Internet Explorer" Then

            'InternetExplorerオブジェクトをセット
            Set objIE = objWin

            Exit For

        End If

    Next

    '本サイトをIE(InternetExplorer)で表示する
    Call ieNavi(objIE, "http://www.vba-ie.net/")

End Sub

※ドラッグ(スワイプ)すると全体を確認できます。

実行結果

制御できていなかったIE(InternetExplorer)を制御し 「VBAのIE制御」サイトのトップページを表示します。

VBAのIE制御サイト画面

解説

Sub sample()

    Dim objIE As InternetExplorer
    Dim objShell  As Object, objWin As Object

※ドラッグ(スワイプ)すると全体を確認できます。

こちらはSubステートメント引数の設定がないsampleプロシージャになります。 まずは、変数宣言でメモリ領域を割り当てるDimステートメントを利用してオブジェクト変数objIEInternetExplorer型オブジェクト変数objShell,objWinオブジェクト型(Object)変数宣言しています。

    'Shellオブジェクトを作成する
    Set objShell = CreateObject("Shell.Application")

※ドラッグ(スワイプ)すると全体を確認できます。

次にオブジェクトを参照するSetステートメントとオブジェクトを作成するCreateObject関数を利用してShellオブジェクトを作成します。Shellオブジェクトは開いているウィンドウの情報を取得するために利用します。

    For Each objWin In objShell.Windows

        If objWin.name = "Internet Explorer" Then

            'InternetExplorerオブジェクトをセット
            Set objIE = objWin

            Exit For

        End If

    Next

※ドラッグ(スワイプ)すると全体を確認できます。

こちらでは、コレクションに対し一括して同じ処理を繰り返すFor Each~Nextステートメントを利用して、現在開いているウィンドウの数だけループ処理を行っています。設定するコレクションは、ShellオブジェクトのWindowsプロパティで取得した現在開いているウィンドウ(Windowsコレクション)になります。

次にFor Each~Nextステートメント内の処理を見ると条件分岐ができるIf~Then~Elseステートメントを利用して開いているウィンドウの名前が「Internet Explorer」の場合、その対象オブジェクトをオブジェクト変数objIEにセットし、ループ処理を強制終了しています。

対象オブジェクトのNameプロパティウィンドウの名前を取得するプロパティです。IE(InternetExplorer)の場合はウィンドウ名に「Internet Explorer」を返しますので、一致するウィンドウがあった場合はさらに次の処理へ移ります。

一致するウィンドウがあった場合は、オブジェクトを参照するSetステートメントを利用してオブジェクト変数objIEに対象オブジェクトをセットします。オブジェクトがセットできたら後のループ処理は不要ですので、Exit Forステートメントを利用してループを抜け、Nextステートメントの次のステートメントに制御を移します。

この処理によりInternetExplorerオブジェクトが取得できましたので、InternetExplorerオブジェクトを制御することができます。

    '本サイトをIE(InternetExplorer)で表示する
    Call ieNavi(objIE, "http://www.vba-ie.net/")

End Sub

※ドラッグ(スワイプ)すると全体を確認できます。

次に他のプロシージャを呼び出すCallステートメントを利用してieViewサブルーチンを呼び出しています。第一引数には先ほど取得したオブジェクト変数の「objIE」を第二引数には表示させるURLの「http://www.vba-ie.net/」を設定しています。これにより本サイトがInternetExplorerで表示されます。

IE(InternetExplorer)が制御できたら、Endステートメントを利用してプロシージャを終了させます。

実際に処理をしてIE(InternetExplorer)が制御できたのを確認できたでしょうか。今回は1つのIE(InternetExplorer)に対して制御処理を行いましたが複数のIE(InternetExplorer)が起動している場合、こちらの方法では対応することができません。そこで複数のIE(InternetExplorer)でも対応できるよう改良を加えサブルーチン(ユーザー定義関数)を作成してみたいと思います。

起動済みのIE(InternetExplorer)を制御するサブルーチン「ieFind」の解説

こちらは、起動済みのIE(InternetExplorer)を制御するサブルーチン(ユーザー定義関数)になります。

Function ieFind(urlName As String) As InternetExplorer
    
    Dim objShell As Object, objWin As Object

  'Shellオブジェクトを作成する
    Set objShell = CreateObject("Shell.Application")
      
    For Each objWin In objShell.Windows

        If objWin.name = "Internet Explorer" And _
           objWin.LocationURL = urlName Then

            'InternetExplorerオブジェクトを代入
            Set ieFind = objWin

            Exit For

        End If

    Next

    Set objShell = Nothing

End Function

※ドラッグ(スワイプ)すると全体を確認できます。

こちらでは、起動しているInternetExplorerオブジェクトを取得するために戻り値が必要になりますので、戻り値を返すFunctionプロシージャを利用しています。それでは、VBAコードを1つずつ見ていきましょう。

Function ieFind(urlName As String) As InternetExplorer

※ドラッグ(スワイプ)すると全体を確認できます。

こちらはFunctionステートメントに引数が1つと戻り値にInternetExplorer型を設定しているieFindサブルーチン(ユーザー定義関数)になります。こちらの構文と引数の内容は以下になります。尚、引数はすべて参照渡しで渡されます。

ieFind("制御対象のサイトURLの文字列")
構文ieFind(urlName)
引数名データ型内容値の事例初期値省略
urlNameString制御したい対象のサイトURLの文字列を指定します。"http://www.vba-ie.net/"×

引数urlNameは必須項目で、制御したい対象のサイトURLの文字列を設定します。

    Dim objShell As Object, objWin As Object

※ドラッグ(スワイプ)すると全体を確認できます。

まずは、Dimステートメントを利用してオブジェクト変数objShell,objWinオブジェクト型(Object)を変数宣言しています。

    'Shellオブジェクトを作成する
    Set objShell = CreateObject("Shell.Application")

※ドラッグ(スワイプ)すると全体を確認できます。

次にSetステートメントCreateObject関数を利用してShellオブジェクトを作成します。

    For Each objWin In objShell.Windows

        If objWin.name = "Internet Explorer" And _
           objWin.LocationURL = urlName Then

            'InternetExplorerオブジェクトを代入
            Set ieFind = objWin

            Exit For

        End If

    Next

※ドラッグ(スワイプ)すると全体を確認できます。

こちらでは、For Each~Nextステートメントを利用して現在開いているウィンドウの数だけループ処理を行っています。設定するコレクションは、ShellオブジェクトのWindowsプロパティで取得した現在開いているウィンドウ(Windowsコレクション)になります。

さらにIf~Then~Elseステートメントを利用して「開いているウィンドウの名前がInternet Explorer」かつ「サイトのURLが引数urlNameと一致」したオブジェクトを戻り値ieFindにセットします。これにより、InternetExplorerオブジェクトを制御する環境が整いました。

サイトのURLを取得する場合は、InternetExplorerオブジェクトLocationURLプロパティを利用して取得します。InternetExplorerオブジェクトをセットしたらExit Forステートメントを利用してループを抜けます。

    Set objShell = Nothing

End Function

※ドラッグ(スワイプ)すると全体を確認できます。

ループ処理を抜けたらSetステートメントを利用して、Nothingを指定することでShellオブジェクトを解除します。プロシージャレベルで宣言した変数については、そのプロシージャの実行が終了した時点で自動的に開放されるで基本不要なのですが、こちらでは記載することとしています。

最後はEndステートメントを利用してieFindサブルーチン(ユーザー定義関数)を終了させます。それでは、実際にieFindサブルーチン(ユーザー定義関数)を利用したサンプルコードを見ていきましょう。

「ieFind」を利用して起動済みのIEを制御するサンプルコード

こちらはieFindサブルーチンを利用したVBAコードになります。以下の処理を実行する前に手動で2つのIEを起動させ「http://www.vba-ie.net/ie/navigate2.html」「http://www.vba-ie.net/ie/subroutine2.html」のページを開いた状態で実行してください。

Sub sample()

  Dim objIE As InternetExplorer
  Dim objIE2 As InternetExplorer

  'ieNaviサブルーチン解説ページを表示しているIEオブジェクトをセット
  Set objIE = ieFind("http://www.vba-ie.net/ie/navigate2.html")
  
  'ieViewサブルーチン解説ページを表示しているIEオブジェクトをセット
  Set objIE2 = ieFind("http://www.vba-ie.net/ie/subroutine2.html")

  '本サイトをIEで表示
  Call ieNavi(objIE, "http://www.vba-ie.net/")
  
  'yahooサイトをIEで表示
  Call ieNavi(objIE2, "http://www.yahoo.co.jp/")

End Sub

※ドラッグ(スワイプ)すると全体を確認できます。

本サイトとyahooサイトが表示されます。

VBAのIE制御2サイト画面

解説

Sub sample()

  Dim objIE As InternetExplorer
  Dim objIE2 As InternetExplorer

※ドラッグ(スワイプ)すると全体を確認できます。

まず、Dimステートメントを利用してオブジェクト変数objIE,objIEInternetExplorer型を宣言しています。これによりInternetExplorerオブジェクトを作成した際にプロパティメソッドを利用できるようになりました。

  'ieNaviサブルーチン解説ページを表示しているIEオブジェクトをセット
  Set objIE = ieFind("http://www.vba-ie.net/ie/navigate2.html")
  
  'ieViewサブルーチン解説ページを表示しているIEオブジェクトをセット
  Set objIE2 = ieFind("http://www.vba-ie.net/ie/subroutine2.html")

※ドラッグ(スワイプ)すると全体を確認できます。

こちらはオブジェクト変数objIE,objIE2にそれぞれieFindサブルーチン(ユーザー定義関数)の戻り値をセットしています。戻り値はそれぞれ指定したURLのInternetExplorerオブジェクトになります。これにより起動済みの2つのIE(InternetExplorer)を操作することができます。

  '本サイトをIEで表示
  Call ieNavi(objIE, "http://www.vba-ie.net/")
  
  'yahooサイトをIEで表示
  Call ieNavi(objIE2, "http://www.yahoo.co.jp/")

End Sub

※ドラッグ(スワイプ)すると全体を確認できます。

そしてCallステートメントを利用してieNaviサブルーチンを呼び出しています。第一引数にはオブジェクト変数の「objIE」「objIE2」を第二引数には表示させるURLの「http://www.vba-ie.net/」「http://www.yahoo.co.jp/」を設定しています。これによりそれぞれ本サイトとyahooサイトがIE(InternetExplorer)で表示されます。

まとめ

今回は、起動済みのIE(InternetExplorer)を制御する方法について解説しました。本来であれば、エラーがでないようなプログラムにすることが大前提なのですが、対象サイトのHTML構文に間違いや、規則性に沿って処理していたもののイレギュラーなページでエラーが起こることはよくあることです。

全てを考慮してプログラムを構築することは難しいので、そのような場合にこちらの処理を行うことで効率よく対処することができます。もし、そのような状況になったら焦らずこちらを再度確認の上、利用してください。

また、今回InternetExplorerオブジェクトを特定するための条件としてサイトURLでチェックを行いましたが、特定ができるものであればサイトの名前でも何でも構いません。サイトURLを選択したのは、単にコピペができるので楽に記述しやすいという点で選びました。他にも色々な方法がありますので、その1つとして覚えておきましょう。

次回はIE(InternetExplorer)ウィンドウの位置やサイズを設定する方法について解説します。

次の記事: エクセルVBAでIEウィンドウの位置やサイズを設定する >>

Excel VBAでIEを思いのままに操作できるプログラミング術 Excel 2013/2010/2007/2003対応

IEのデータ収集&自動操作のプログラミング本はこの1冊だけ!IEの起動やポップアップウィンドウ、表示を制御する基本的なコードはもちろん、テキストボックスやラジオボタン、表、ハイパーリンクなどのHTML部品を制御する方法など、自動操作に欠かせないノウハウを丁寧に解説。

VBAのIE制御についてのQ&A掲示板

↑VBAのIE操作で分からない事があればこちらの掲示板よりご質問ください。

ExcelのVBA初心者入門

↑こちらはVBAをマスターできるよう初心者向けのエクセルVBA入門コンテンツになります。

目次

IE操作に便利なツール

こちらでは、これまでに紹介したIE(InternetExplorer)操作で便利な機能をツール化しています。無償でダウンロードできますので、目的に合わせたご利用ください。

IEのメソッド・プロパティ

こちらでは、IE(InternetExplorer)オブジェクトのメソッド・プロパティをまとめています。

IE操作のVBA関数

こちらでは、エクセルVBAのIE(InternetExplorer)操作で利用されたVBA関数をまとめています。

IE操作のステートメント

こちらでは、エクセルVBAのIE(InternetExplorer)操作で利用されたステートメントをまとめています。ExcelのVBAで基本的な部分になりますので、しっかり理解しましょう。

IE制御のVBAコード

こちらでは、これまでに作成したIE(InternetExplorer)操作で役立つサブルーチンをまとめています。
全てをコピーする必要はありませんが、目的に合わせたサブルーチンをご利用ください。