65.9K
CodeProject 正在变化。 阅读更多。
Home

VB.NET 中 WebBrowser 控件的浏览器更新

starIconstarIconstarIconstarIconstarIcon

5.00/5 (7投票s)

2017 年 5 月 30 日

CPOL

3分钟阅读

viewsIcon

56526

在本文中,我将向您展示如何更新 WebBrowser 控件以使用主机上安装的最新浏览器。

引言

这是一个 VB.NET 类,用于更新 WebBrowser 控件以使用已安装浏览器的最新版本(Internet Explorer,Edge)。

背景

如果您需要在您的 VB.NET WinForm 或 WPF 应用程序中加载网页,您必须使用 WebBrowser 控件。 WebBrowser 控件 - 默认情况下 - 停留在 IE 7 渲染模式。 无论您是在 WPF 应用程序还是 WinForms 应用程序中使用 WebBrowser 控件,都会发生这种情况。 您会注意到,当您的应用程序加载网页时,页面看起来与您期望的不一样! 另一种情况是,当您收到一条消息,要求您更新您的 Web 浏览器 (IE)。

有几种方法可以覆盖默认的渲染行为

  1.     使用 IE X-UA-Compatible Meta 标头
  2.     使用应用程序特定的 FEATURE_BROWSER_EMULATION 注册表项

如果您控制网页的内容,提供最新版本的 IE 渲染引擎最简单的方法是使用 IE Edge 模式标头。 这就是您应用选项 1 的时候

<meta http-equiv="X-UA-Compatible" content="IE=edge" />

您还可以指定 IE 的版本

<meta http-equiv="X-UA-Compatible" content="IE=10" /> 

我将向您展示如何在您的代码中使用 VB.NET 类 (WebBrowserUpdater) 应用第二种方法。

使用代码

Public Class WebBrowserUpdater
    Shared is64BitProcess As Boolean = (IntPtr.Size = 8)
    Shared is64BitOperatingSystem As Boolean = is64BitProcess OrElse InternalCheckIsWow64()

    <dllimport("kernel32.dll", callingconvention:="CallingConvention.Winapi)" setlasterror:="True,">_
    Private Shared Function IsWow64Process(<[In]()> ByVal hProcess As IntPtr, <out()> ByRef wow64Process As Boolean) As <marshalas(unmanagedtype.bool)> Boolean
    End Function

    Public Shared Function InternalCheckIsWow64() As Boolean
        If (Environment.OSVersion.Version.Major = 5 AndAlso Environment.OSVersion.Version.Minor >= 1) OrElse Environment.OSVersion.Version.Major >= 6 Then
            Using p As Process = Process.GetCurrentProcess()
                Dim retVal As Boolean
                If Not IsWow64Process(p.Handle, retVal) Then
                    Return False
                End If
                Return retVal
            End Using
        Else
            Return False
        End If
    End Function

    Public Shared Function GetEmbVersion() As Integer
        Dim ieVer As Integer = GetBrowserVersion()

        If ieVer > 9 Then
            Return ieVer * 1000 + 1
        End If

        If ieVer > 7 Then
            Return ieVer * 1111
        End If

        Return 7000
    End Function
    ' End Function GetEmbVersion
    Public Shared Sub FixBrowserVersion()
        Dim appName As String = System.IO.Path.GetFileNameWithoutExtension(System.Reflection.Assembly.GetExecutingAssembly().Location)
        FixBrowserVersion(appName)
    End Sub

    Public Shared Sub FixBrowserVersion(ByVal appName As String)
        FixBrowserVersion(appName, GetEmbVersion())
    End Sub
    ' End Sub FixBrowserVersion
    Public Shared Sub FixBrowserVersion(ByVal appName As String, ByVal ieVer As Integer)
        FixBrowserVersion_Internal("HKEY_LOCAL_MACHINE", appName & Convert.ToString(".exe"), ieVer)
        FixBrowserVersion_Internal("HKEY_CURRENT_USER", appName & Convert.ToString(".exe"), ieVer)
        FixBrowserVersion_Internal("HKEY_LOCAL_MACHINE", appName & Convert.ToString(".vshost.exe"), ieVer)
        FixBrowserVersion_Internal("HKEY_CURRENT_USER", appName & Convert.ToString(".vshost.exe"), ieVer)
    End Sub
    ' End Sub FixBrowserVersion 
    Private Shared Sub FixBrowserVersion_Internal(ByVal root As String, ByVal appName As String, ByVal ieVer As Integer)
        Try
            'For 64 bit Machine 
            If InternalCheckIsWow64() Then
                Microsoft.Win32.Registry.SetValue(root & Convert.ToString("\Software\Wow6432Node\Microsoft\Internet Explorer\Main\FeatureControl\FEATURE_BROWSER_EMULATION"), appName, ieVer)
            Else
                'For 32 bit Machine 
                Microsoft.Win32.Registry.SetValue(root & Convert.ToString("\Software\Microsoft\Internet Explorer\Main\FeatureControl\FEATURE_BROWSER_EMULATION"), appName, ieVer)


            End If
        Catch generatedExceptionName As Exception
            MessageBox.Show("You have to be administrator to run start this process. Please close the software. Right click on the iGiftCard icon and select RUN AS ADMINISTRATOR .", "Administrator", MessageBoxButtons.OK, MessageBoxIcon.Information, MessageBoxDefaultButton.Button1)
        End Try
    End Sub
    ' End Sub FixBrowserVersion_Internal 
    Public Shared Function GetBrowserVersion() As Integer
        Dim strKeyPath As String = "HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\Internet Explorer"
        Dim ls As String() = New String() {"svcVersion", "svcUpdateVersion", "Version", "W2kVersion"}

        Dim maxVer As Integer = 0
        For i As Integer = 0 To ls.Length - 1
            Dim objVal As Object = Microsoft.Win32.Registry.GetValue(strKeyPath, ls(i), "0")
            Dim strVal As String = System.Convert.ToString(objVal)
            If strVal IsNot Nothing Then
                Dim iPos As Integer = strVal.IndexOf("."c)
                If iPos > 0 Then
                    strVal = strVal.Substring(0, iPos)
                End If

                Dim res As Integer = 0
                If Integer.TryParse(strVal, res) Then
                    maxVer = Math.Max(maxVer, res)
                End If
            End If
        Next
        Return maxVer
    End Function
    ' End Function GetBrowserVersion 

 由于 IE 8 微软引入了注册表项,当 WebBrowser 控件嵌入到应用程序中时,可以控制浏览器行为。 系统上的许多应用程序都使用这些注册表值

您可以使用可执行文件的名称指定一个注册表,并指定您希望加载的 IE 版本。 这些数字指定为 11000、10000、9000、8000 和 7000。

该值指定 IE 版本,如下所示

设置此键的值是(取自 MSDN)作为十进制值

11001 (0x2AF9)
Internet Explorer 11。 网页以 IE11 标准模式显示,无论 !DOCTYPE 指令如何。

11000 (0x2AF8)
Internet Explorer 11。 包含基于标准的 !DOCTYPE 指令的网页以 IE9 模式显示。

10001 (0x2AF7)
Internet Explorer 10。 网页以 IE10 标准模式显示,无论 !DOCTYPE 指令如何。

10000 (0x2710)
Internet Explorer 10。 包含基于标准的 !DOCTYPE 指令的网页以 IE9 模式显示。

9999 (0x270F)
Internet Explorer 9。 网页以 IE9 标准模式显示,无论 !DOCTYPE 指令如何。

9000 (0x2328)
Internet Explorer 9。 包含基于标准的 !DOCTYPE 指令的网页以 IE9 模式显示。

8888 (0x22B8)
网页以 IE8 标准模式显示,无论 !DOCTYPE 指令如何。

8000 (0x1F40)
包含基于标准的 !DOCTYPE 指令的网页以 IE8 模式显示。

7000 (0x1B58)
包含基于标准的 !DOCTYPE 指令的网页以 IE7 标准模式显示。 这种模式有点毫无意义,因为它就是默认的。

设置这些键使您的应用程序能够在主机上使用最新的 Internet Explorer 版本。

WebBrowserUpdater 类完成了您运行应用程序并使用已安装 IE 最新版本所需的操作。

关注点

WebBrowserUpdater 必须确定它是在处理 32 位还是 64 位应用程序。 这项任务由以下方法完成

    Public Shared Function InternalCheckIsWow64() As Boolean
        If (Environment.OSVersion.Version.Major = 5 AndAlso Environment.OSVersion.Version.Minor >= 1) OrElse Environment.OSVersion.Version.Major >= 6 Then
            Using p As Process = Process.GetCurrentProcess()
                Dim retVal As Boolean
                If Not IsWow64Process(p.Handle, retVal) Then
                    Return False
                End If
                Return retVal
            End Using
        Else
            Return False
        End If
    End Function
    HKEY_LOCAL_MACHINE\SOFTWARE\WOW6432Node\Microsoft\Internet Explorer\Main\FeatureControl\FEATURE_BROWSER_EMULATION

并且值设置在这里完成

     ' End Sub FixBrowserVersion 
    Private Shared Sub FixBrowserVersion_Internal(ByVal root As String, ByVal appName As String, ByVal ieVer As Integer)
        Try
            'For 64 bit Machine 
            If InternalCheckIsWow64() Then
                Microsoft.Win32.Registry.SetValue(root & Convert.ToString("\Software\Wow6432Node\Microsoft\Internet Explorer\Main\FeatureControl\FEATURE_BROWSER_EMULATION"), appName, ieVer)
            Else
                'For 32 bit Machine 
                Microsoft.Win32.Registry.SetValue(root & Convert.ToString("\Software\Microsoft\Internet Explorer\Main\FeatureControl\FEATURE_BROWSER_EMULATION"), appName, ieVer)


            End If
        Catch generatedExceptionName As Exception
            MessageBox.Show("You have to be administrator to run start this process. Please close the software. Right click on the iGiftCard icon and select RUN AS ADMINISTRATOR .", "Administrator", MessageBoxButtons.OK, MessageBoxIcon.Information, MessageBoxDefaultButton.Button1)
        End Try
    End Sub

如下所示使用此类

WebBrowserUpdater.FixBrowserVersion()
WebBrowserUpdater.FixBrowserVersion("AppName")
WebBrowserUpdater.FixBrowserVersion("AppName",IEVer)

请记住,IEVer 必须是之前向您显示的允许值之一。

最后但并非最不重要的一点。 由于我们设置了一个注册表值,并且为了避免任何错误,您将需要具有提升的权限才能应用更改。 将以下内容添加到您的应用程序清单中

    <requestedExecutionLevel level="requireAdministrator" uiAccess="false" />

此代码与 .NET 2 到 .NET 4.5 兼容。 如果您仅在您的应用程序中使用最新版本的 .NET,那么可以缩短该过程。

历史

© . All rights reserved.