Surpressing Script Errors in WebBrowser - Not Working

mixing

Regular Member
Joined
Jan 18, 2014
Messages
412
Reaction score
63
Hello everyone.. I hope someone can help me figure this out as it's been bothering the heck out of me.

So, I've got a WebBrowser component accessing webpages just fine. Some of the websites I try to access give those dreaded script errors like the one you see below.

yywVMzG


I've tried going in and changing the ScriptErrorsSuppressed to 'True' and yet these javascript errors keep coming up. I know the best thing to do would be to have the website owners fix these errors, but since my tool accesses so many different websites that will be pretty much impossible. I did some more browsing online and found a nice little class that will automatically click on Dialog Boxes for you. I tested it with a normal messagebox and it seams to do the trick. However, when I try to make it work with these javascript dialog boxes I get nowhere. Below is the code I'm trying.

DialogHandler Class
Code:
Imports System.Runtime.InteropServices

Public Class DialogHandler
    'API CONSTANTS
    Const WM_GETTEXT As Long = &HD
    Const WM_GETTEXTLENGTH As Long = &HE
    Const GW_ENABLEDPOPUP As Long = 6
    Const BM_CLICK As Long = &HF5&
    Const GW_CHILD As Long = 5
    Const GW_HWNDNEXT As Long = 2

    'FINDS CHILD WINDOWS
    Private Declare Auto Function GetWindow Lib "user32.dll" (ByVal hWnd As IntPtr, ByVal uCmd As Integer) As IntPtr

    'SEND MESSAGES TO THE BUTTON
    Private Declare Auto Function SendMessage Lib "user32.dll" Alias "SendMessage" (ByVal hWnd As IntPtr, ByVal Msg As Integer, _
    ByVal wParam As Integer, ByRef lParam As IntPtr) As IntPtr

    'GETS WINDOW TEXT
    Private Declare Auto Function SendMessageA Lib "user32.dll" Alias "SendMessageA" (ByVal hWnd As IntPtr, ByVal Msg As Integer, _
    ByVal wParam As IntPtr, ByRef lParam As IntPtr) As IntPtr
    <DllImport("User32.dll", CharSet:=CharSet.Auto, Entrypoint:="SendMessage")> Public Shared Function SendMessageString(ByVal hwnd As IntPtr, _
    ByVal wMsg As Integer, ByVal wparam As Integer, ByVal lparam As System.Text.StringBuilder) As IntPtr
    End Function

    Private Function GetChildWindowHandles(ByVal ParentWindowHandle As IntPtr) As ArrayList

        Dim ptrChild As IntPtr
        Dim clsRet As New ArrayList

        'GET FIRST CHILD HANDLE
        ptrChild = GetChildWindowHandle(ParentWindowHandle)

        Do Until ptrChild.Equals(IntPtr.Zero)
            'ADD TO COLLECTION OF HANDLES
            clsRet.Add(ptrChild)
            'GET NEXT CHILD
            ptrChild = GetNextWindowHandle(ptrChild)
        Loop

        Return clsRet

    End Function

    Private Function GetChildWindowHandle(ByVal ParentWindowHandle As IntPtr) As IntPtr
        Return GetWindow(ParentWindowHandle, GW_CHILD)
    End Function

    Private Function GetNextWindowHandle(ByVal CurrentWindowhandle As IntPtr) As IntPtr
        Return GetWindow(CurrentWindowhandle, GW_HWNDNEXT)
    End Function

    'RETURNS TEXT OF THE WINDOW FOR CONFIRMATION OF CORRECT DIALOG
    Private Function GetWindowText(ByVal WindowHandle As IntPtr) As String

        Dim ptrRet As IntPtr
        Dim ptrLength As IntPtr

        'LENGTH OF BUFFER
        ptrLength = SendMessageA(WindowHandle, WM_GETTEXTLENGTH, IntPtr.Zero, IntPtr.Zero)

        'BUFFER NEEDED FOR RETURN VALUE
        Dim sb As New System.Text.StringBuilder(ptrLength.ToInt32 + 1)

        'WINDOW TEXT
        ptrRet = SendMessageString(WindowHandle, WM_GETTEXT, ptrLength.ToInt32 + 1, sb)

        Return sb.ToString

    End Function

    'SEND A 'CLICK' TO THE BUTTON ("WINDOW")
    Private Sub PerformClick(ByVal WindowHandle As IntPtr)
        SendMessage(WindowHandle, BM_CLICK, 0, IntPtr.Zero)
    End Sub

    Public Sub LookForAndCloseIEPopup(ByVal whichButton As String)

        'GET HANDLE OF ANY POPUP WINDOW ASSOCIATED WITH MAIN FORM
        Dim ptrDialogWindow As IntPtr = GetWindow(Process.GetCurrentProcess.MainWindowHandle, GW_ENABLEDPOPUP)

        'IF IT'S A BROWSER POPUP, HANDLE IT
        If GetWindowText(ptrDialogWindow) = "Microsoft Internet Explorer" Or GetWindowText(ptrDialogWindow) = "Message from webpage" Or GetWindowText(ptrDialogWindow) = "Windows Internet Explorer" Then
            ClosePopup(ptrDialogWindow, whichButton)
        End If

    End Sub

    Private Sub ClosePopup(ByVal WindowHandle As IntPtr, ByVal whichButton As String)

        Dim clsChildHandles As ArrayList = GetChildWindowHandles(WindowHandle)

        For Each ptrHandle As IntPtr In clsChildHandles
            'IF IT FINDS A BUTTON WITH THE TEXT SPECIFIED, CLICK IT
            If GetWindowText(ptrHandle).Contains(whichButton) Then PerformClick(ptrHandle) : Exit For
        Next

    End Sub
End Class

I have a timer which kicks off looking for the dialog boxes. Here is the code for my timer

Code:
    Private Sub Timer1_Tick(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Timer1.Tick
        Dim dh As New DialogHandler
        dh.LookForAndCloseIEPopup("No") 'This single parameter is the text of the button you want to click (case insensitive)
    End Sub

As I mentioned, this code works fine for a traditional dialog box, such as a message box. But, for the one in my screenshot above nothing happens. At first I thought maybe I needed to change the parameter in my timer code. So I tried both..
Code:
dh.LookForAndCloseIEPopup(&No") 'This single parameter is the text of the button you want to click (case insensitive)

and

Code:
dim noo as string = string.format("&No")
dh.LookForAndCloseIEPopup(noo) 'This single parameter is the text of the button you want to click (case insensitive)

Still nothing..Any ideas where I could be going wrong here? I can see the Yes/No buttons in the screenshot have lines under them and I'm not sure if that would make any difference.
 
Last edited:
Microsoft webbrowsers use the older browser possible (IE 7), even if they have IE 11 installed.
I had the same issue for a project , and had to use this code

Private Sub CreateBrowserKey(Optional ByVal IgnoreIDocDirective As Boolean = False)
Dim basekey As String = Microsoft.Win32.Registry.CurrentUser.ToString
Dim value As Int32
Dim thisAppsName As String = My.Application.Info.AssemblyName & ".exe"
' Value reference: http://msdn.microsoft.com/en-us/library/ee330730%28v=VS.85%29.aspx
' IDOC Reference: http://msdn.microsoft.com/en-us/library/ms535242%28v=vs.85%29.aspx
Select Case (New WebBrowser).Version.Major
Case 8
If IgnoreIDocDirective Then
value = 8888
Else
value = 8000
End If
Case 9
If IgnoreIDocDirective Then
value = 9999
Else
value = 9000
End If
Case 10
If IgnoreIDocDirective Then
value = 10001
Else
value = 10000
End If
Case 11
If IgnoreIDocDirective Then
value = 11001
Else
value = 11000
End If




Case Else
Exit Sub
End Select
Microsoft.Win32.Registry.SetValue(Microsoft.Win32.Registry.CurrentUser.ToString & BrowserKeyPath, _
Process.GetCurrentProcess.ProcessName & ".exe", _
value, _
Microsoft.Win32.RegistryValueKind.DWord)
End Sub

Using the latest version of the browser should allow you to suppress errors and maybe even stop them
 
Back
Top