ssCAROのブログ

色んなとこで見つけたプログラムのメモ置き場っぽい

WebBrowserコントロールでもwindow.close()で閉じたい

最近の機器にはブラウザで設定が出来るものが多いです。
そこで、WebBrowserコントロールを使って特定のページを表示する簡易ブラウザを作成しました。
作成にあたり、保守モードが最初から選択されてたり、特定の文字が入力済みであったりとHtmlDocumentを解析しながら組み込みました。

そういった設定画面は、閉じるボタンを押すとブラウザが終了するのが多いのですが作成した簡易ブラウザでは閉じるボタンを押すとフリーズしたようになります。

window.closeのイベントを取得するように変更しました。
参考にしたのは次のURLです。
WebBrowserコントロールにWindowClosingイベントもどきを拡張する

FormにExWebBrowserを配置します。
Form1.vb

Private Sub Form1_Load(sender As Object, e As EventArgs) Handles MyBase.Load
    Dim urlString As String = "http://192.168.10.1/"
    ExWebBrowser1.Navigate(urlString)
End Sub

Private Sub ExWebBrowser1_DocumentCompleted(sender As Object, e As WebBrowserDocumentCompletedEventArgs) Handles ExWebBrowser1.DocumentCompleted
    Dim name As String = "login.html"
    If e.Url.OriginalString.IndexOf(name) > 0 Then
            'フレームで構成されているため、表示されたフレームから目的のページで処理を行う
            Dim frames As HtmlWindowCollection = WebBrowser1.Document.Window.Frames
            For Each frame As HtmlWindow In frames
                '"login.html"で処理をする
                If frame.Document.Url.OriginalString.IndexOf(name) > 0 Then
                    Dim doc As HtmlDocument = frame.Document
                    Dim all As HtmlElementCollection = doc.All
                    
                    'ユーザーを入力
                    Dim user As HtmlElementCollection = all.GetElementsByName("user")
                    user(0).InnerText = "99"
                    
                    'パスワードを入力
                    Dim pass As HtmlElementCollection = all.GetElementsByName("pass")
                    pass(0).InnerText = "999999"
                End If
            Next
    End If
End Sub

Private Sub ExWebBrowser1_WindowClosing(sender As Object, e As EventArgs) Handles ExWebBrowser1.WindowClosing
    Me.Close()
End Sub

ExWebBrowser.vb

Imports System.Runtime.InteropServices

Public Class ExWebBrowser
    Inherits WebBrowser

    Sub New()
        MyBase.New()
    End Sub

    <DllImport("user32.dll", SetLastError:=True, CharSet:=CharSet.Auto)>
    Private Shared Function GetWindow(ByVal hWnd As IntPtr, ByVal uCmd As UInt32) As IntPtr
    End Function

    Private Enum GetWindowType As UInt32
        GW_HWNDFIRST = 0
        GW_HWNDLAST = 1
        GW_HWNDNEXT = 2
        GW_HWNDPREV = 3
        GW_OWNER = 4
        GW_CHILD = 5
        GW_ENABLEDPOPUP = 6
    End Enum

    Public Event WindowClosing As EventHandler

    Protected Overridable Sub OnWindowClosing(ByVal e As EventArgs)
        RaiseEvent WindowClosing(Me, e)
    End Sub

    Protected Overrides Sub WndProc(ByRef m As System.Windows.Forms.Message)
        Const WM_PARENTNOTIFY As Int32 = &H210
        Const WM_DESTROY As Int32 = &H2

        If m.Msg = WM_PARENTNOTIFY Then
            If m.WParam.ToInt32() = WM_DESTROY Then
                If m.LParam = GetWindow(Me.Handle, GetWindowType.GW_CHILD) Then
                    Dim e As EventArgs = New EventArgs()
                    OnWindowClosing(e)
                    Return
                End If
            End If
        End If
        MyBase.WndProc(m)
    End Sub

End Class