VBAを使ってフレーム構造のページを操作する①


あなたはVBAを使ってInternetExplorer(以下IE)を操作しようとしています。そのコンテンツが表示されている部分のソース右クリックで確認し、プログラムを組みました。さぁ操作しよう!

・・・と思ったら動かない。しかもソースを表示させてみるとさっき右クリックで確認したソースと違う・・・なんてことに遭遇したことはありませんか?

もしかしたらそのサイトは”(インライン)フレーム構造”になっているのかもしれません。今回はこの”フレーム”というものがどの様なものか、どの様にして操作すれば良いかをご紹介します。

はじめに

つい最近ebayの操作に関する仕事を受けたのですが、ebayの商品ページは一部がインラインフレーム構造になっていました。

久しぶりだったので「何であの部分のソースが見えないんだっけ」と少し悩みましたが、今後のための備忘録的な意味も込めて書いていきます。まずは基本的な”フレーム構造”の操作から。

インラインフレーム”については次回の記事で紹介致します。

処理は至ってシンプルなので、すぐに実装できるはずです。

フレーム構造とは?

上記の様な構造になっているページを見たことはありませんか?

A側にメニューなどの項目が表示されており、項目をクリックするとB側のページが切り替わるといったページです。

この場合、A、Bそれぞれの位置で「右クリック」⇒「ソースの表示」を行うと、それぞれ異なるソースが表示されると思います。これは以下の様に、

  

「A.html」、「B.html」という別々のページが存在しているためです。”フレーム”と呼ばれる仕組みを使うことで、一つのページに複数のhtmlファイルのページを表示させることができます。そして実はもう一つ、これらのページを繋げて表示させるために、

「C.html」というページも存在しています。

VBAで上図①のページを取得した際にdocumentの内容を見ると、この「C.html」のソースが確認できるはずです。その他にもIE上で「表示」⇒「ソース」、「Ctrl」+「U」でも確認することができます。

サンプルとして以下の様なページを用意致しました。

https://rabbitfoot.xyz/sample/frame-c.html(新しいタブで開きます)

上記サイトの左側、右側で右クリック。「Ctrl」+「U」でC.htmlのページの確認等を行ってみましょう。

<FRAMESET cols="200,*" border=0>

	<FRAME SRC="frame-a.html" NAME="pageleft">
	<FRAME SRC="frame-b.html" NAME="pageright">

</FRAMESET>

<FRAMESET>が記述されている部分がフレームの指定箇所となります。

各フレームの要素を取得する

では本題へ。

先ほど開いたサンプルのページから「frame-a.html(A)」、「frame-b.html(B)」のドキュメントタイトルを取得してみましょう。

※参照設定が必要になりますので、こちらの記事をご確認下さい(新規タブで開きます)

Option Explicit

Sub main()
    Dim objIE As InternetExplorer
    Dim objFrame As Object
    
    Set objIE = getTargetUrlIE("https://rabbitfoot.xyz/sample/frame-c.html")
    
    Set objFrame = objIE.document.frames
    
    Debug.Print objFrame(0).document.title
    Debug.Print objFrame(1).document.title
End Sub

'指定したURLのサイトを返す
Function getTargetUrlIE(url As String) As InternetExplorer
    Dim objIE As InternetExplorer      'IE格納
    Dim objSh As Object                'shellオブジェクト格納
    Dim objWindow As Object            'ウィンドウを格納
    Dim sWindowName As String        'ウィンドウタイトルを格納
            
    Set objSh = CreateObject("Shell.Application")

    For Each objWindow In objSh.Windows
        On Error Resume Next
        sWindowName = ""
        sWindowName = objWindow.FullName
        On Error GoTo 0
        
        'IEウィンドウかどうかの判定
        If LCase(Right(sWindowName, 12)) = "iexplore.exe" Then
        
            'URLが指定のものかどうかを判定
            If InStr(objWindow.LocationURL, url) > 0 Then
                Set objIE = objWindow
                Exit For
            End If
        End If
    Next
    
    '目的のIEが開かれていない場合は作成する
    If objIE Is Nothing Then
        Set objIE = CreateObject("InternetExplorer.Application")
        objIE.Visible = True
        objIE.Navigate2 url
        
        Do While objIE.Busy Or objIE.readyState <> READYSTATE_COMPLETE
            DoEvents
        Loop
    End If
    
    Set getTargetUrlIE = objIE
End Function

上記のソースをそのまま実行してみて下さい。イミディエイトウィンドウに「メニュー」、「フレームのトップ」と出力されれば成功です。

「objIE.document.frames」でフレームのオブジェクトを取得することができます。予め使用されているフレームの数や位置が分かっているのであれば、サンプルの様に「objFrame(0).document.title」と指定するだけでそのフレーム内の要素に簡単にアクセスすることができます。(添え字の開始は0から始まります)

何番目のフレームにデータが存在するか分からない場合は、for分等を用いてフレームの内容を一つずつ確認していく処理に置き換えれば問題ありません。

forを用いたサンプル

Sub main()
    Dim objIE As InternetExplorer
    Dim objFrame As Object
    Dim iFrameCnt As Integer
    
    Set objIE = getTargetUrlIE("https://rabbitfoot.xyz/sample/frame-c.html")
    
    Set objFrame = objIE.document.frames
    
    For iFrameCnt = 0 To objFrame.length - 1
        Debug.Print objFrame(iFrameCnt).document.title
    Next
End Sub

ちなみに”frame”のオブジェクトは必ず一度変数に格納する様にしましょう。

横着をして「objIE.document.frames(0).document.title」と記述するとエラーになります。

フレーム構造となっているサイトの操作方法は以上です。

次回はインラインフレーム構造になっている場合について解説します。

次回:VBAを使ってフレーム構造のページを操作する②

関連記事と広告

シェアする

  • このエントリーをはてなブックマークに追加

フォローする