1

Background

I recently have been trialing the WebView2 control in place of the WebBrowser control that is built into Visual Studios. I have followed the steps for installing:

  1. Install standalone installer
  2. Right click Solution Explorer > Manage NuGet Packages > Browse > WebView2 > Install

I built a very simple program that literally just has the WebView2 control on it, with a text box and two buttons:

enter image description here

enter image description here

So supposedly when I click the "Go" button (Button 1) it should navigate to https://www.google.com

The problem

The problem is that it does not load the webpage. I have tried both the WebView21.Source = New Uri(TextBox1.Text) method as well as the loadpage method which calls it using an asynchronous call. The resulting page every time that loads:

enter image description here

What else have I tried?

I just walked through the steps shown here which is why I have the initialization procedure. I have called the initialization with button2, but the page still looks the same.

Question

I really am not sure what else to try to get this to work? I did search and it appears most do not have this issue. Any help is greatly appreciated!

Eric F
  • 899
  • 2
  • 21
  • 45
  • In the [post](https://stackoverflow.com/questions/66500241/webview2-site-not-loading) that you reference, the return type is `Task` not `void`. What does this mean for VB.NET? Instead of `Public Async Sub Initialization()`, you should have `Public Async Function Initialization() as Task`. Likewise for `loadpage`. You may want to check the value of TextBox1.Text: `Debug.WriteLine("TextBox1.Text: " & TextBox1.Text)` – Tu deschizi eu inchid Jan 07 '22 at 19:42
  • I think that it's no longer necessary to use the standalone installer unless you want to stick to a particular version of WebView2 because the WebView2 runtime should be automatically installed through Windows Update. Check "Programs and Features" to check if "Microsoft Edge WebView2 Runtime" is installed on your computer. – Tu deschizi eu inchid Jan 07 '22 at 19:51
  • `EnsureCoreWebView2Async()` needs to be called once, when the container Form is initialized. You can handle the `Load` event or override `OnLoad()` (for example). See here: [Which WebView2 event/function can be use to replace ScriptNotify Webview event?](https://stackoverflow.com/a/68278278/7444103) and here: [e.NewWindow = (CoreWebView2)sender still results in a separate instance](https://stackoverflow.com/a/68790332/7444103) -- Make sure the loader Library can be reached. That's all. – Jimi Jan 08 '22 at 02:42
  • Of course, the `Load` handler or the `OnLoad()` method must be declared async (`async void` / `async sub` are ok here). – Jimi Jan 08 '22 at 02:48
  • Have you tried with other addresses, like: `https://stackoverflow.com` ? – Poul Bak Jan 08 '22 at 05:58
  • All, Thanks for the help! @user9938 I updated the Initialization function as you suggested. – Eric F Jan 08 '22 at 14:20
  • @Jimi I believe you are 100% correct for why it is not loading. See updated code in question, now called during form initialization but still no luck. – Eric F Jan 08 '22 at 14:21
  • @PoulBak Yes I tried that URL just now and still no luck :( – Eric F Jan 08 '22 at 14:21
  • You should never include code and error messages as images, please EDIT your question with text. Also, what .net version and WebView2 version are you using? – Poul Bak Jan 08 '22 at 14:37
  • 2
    It is a very low-level mishap, the communication with the background process that renders a web page is getting corrupted. A bug in one of the many recent updates is unlikely, you'd normally suspect the security software on this machine. – Hans Passant Jan 08 '22 at 14:57
  • All - Thanks for the help! I created the project listed user9938 below, but it did not work. When I tried it on a different machine, then it worked! @HansPassant I believe security software was the root cause. – Eric F Jan 10 '22 at 14:32
  • Glad you got it working. There are a number of possibilities for it not working. The minimum version number required for MS Edge depends on the version of WebView2 that you choose to use. See the [WebView2 release notes](https://learn.microsoft.com/en-us/microsoft-edge/webview2/release-notes) for more information. Also, anti-virus may cause an issue. You can report issues at [WebView2Feedback](https://github.com/MicrosoftEdge/WebView2Feedback/issues). – Tu deschizi eu inchid Jan 10 '22 at 15:12

1 Answers1

3

Below shows how to create a project that uses a WebView2 control in VB.NET . I've written it in a manner that will allow it to also be useful to others who may have varying levels of experience.

Using WebView2 requires that MS Edge is installed. The minimum version number required for MS Edge depends on the version of WebView2 that you choose to use. See the WebView2 release notes for more information.

Ensure that MS Edge is installed. If not, Download/Install MS Edge.

If you already have MS Edge installed, to check the MS Edge version number type the following into the MS Edge address bar: edge://settings/help

Alternatively,

  • Open MS Edge
  • Click enter image description here in upper-right corner
  • Select Help and Feedback
  • Select About Microsoft Edge

The WebView2 runtime may have been already installed on your computer by Windows Update.

Check if WebView2 runtime is installed:

  • Open Control Panel
  • Select View by: Small icons
  • Click Programs and Features

Note: WebView2 runtime is named: Microsoft Edge WebView2 Runtime. If the WebView2 runtime isn't installed (or you want to use a specific version), you can Download the WebView2 Runtime and install it.

64-bit OS:

WebView2 runtime:

%ProgramFiles(x86)%\Microsoft\EdgeWebView\Application\<version>

Registry:

HKEY_LOCAL_MACHINE\SOFTWARE\WOW6432Node\Microsoft\EdgeUpdate\Clients\{F3017226-FE2A-4295-8BDF-00C3A9A7E4C5}

32-bit OS:

WebView2 runtime:

%ProgramFiles%\Microsoft\EdgeWebView\Application\<version>

The instructions below are written for VS 2019.

VS 2019:

  • Open Visual Studio
  • Click Continue without code
  • Click File
  • Select New
  • Select Project
  • Visual Basic Windows Desktop enter image description here
  • Click Windows Forms App (.NET Framework) enter image description here
  • Click Next
  • Specify project name (name: WebView2Test)
  • Click Create

Open Properties Window

  • In VS menu, select View
  • Select Properties Window

Open Solution Explorer

  • In VS menu, select View
  • Select Solution Explorer

Set NuGet Package Manager settings (recommended)

  • In VS menu, click Tools
  • Select Options...
  • Expand NuGet Package Manager
  • Click General
  • Under Package Management, for Default package management format, select PackageReference
  • Click OK

Add WebView2 NuGet package

  • In Solution Explorer, right-click <project name>
  • Select Manage NuGet Packages...
  • Click Browse
  • In the search box, type: Microsoft.Web.WebView2
  • Select desired version (ex: 1.0.1054.31), and click Install
  • If prompted, "Visual Studio is about to make changes to this solution. Click OK to proceed with the changes listed below.", click OK

Add Load event handler to Form

  • In Solution Explorer, double-click <form name> to open the designer (ex: Form1)
  • In Properties Window, select your form (ex: Form1)
  • Click the lightning bolt enter image description here
  • Double-click Load to add the event handler to the form

Add FormClosed event handler to Form

  • In Solution Explorer, double-click <form name> to open the designer (ex: Form1)
  • In Properties Window, select your form (ex: Form1)
  • Click the lightning bolt enter image description here
  • Double-click FormClosed to add the event handler to the form

Add TableLayoutPanel to Form

  • In Solution Explorer, double-click form that you wish to add WebView2 control to (ex: Form1)

  • In VS menu, click View

  • Select Toolbox

  • In Toolbox, expand All Windows Forms

  • Drag TableLayoutPanel to your Form (ex: Form1)

  • In Properties Window, select the TableLayoutPanel you just added (ex: TableLayoutPanel1)

  • Select Rows. On right side, click enter image description here

  • Modify so you have the following:

    enter image description here

  • In the drop-down for Show select Columns and modify so you have the following:

    enter image description here

  • Click OK

  • In Properties Window, for the TableLayoutPanel, set the Dock property to Fill

Add TableLayoutPanel to first row of TableLayoutPanel

  • From Toolbox, drag TableLayoutPanel to the first row of TableLayoutPanel1

    enter image description here

  • In Properties Window, select the TableLayoutPanel you just added (ex: TableLayoutPanel2)

  • Select Rows. On right side, click enter image description here

  • Modify so you have the following:

    enter image description here

  • In the drop-down for Show, select Columns and modify so you have the following:

    enter image description here

Add TextBox to TableLayoutPanel2 for URL

  • From Toolbox, drag TextBox to the 4th column of TableLayoutPanel2 (largest column)
  • In Properties Window, for TextBox1, set (Name) property to desired value (ex: textBoxAddressBar). Set Anchor property to Left, Right, and set Text property to desired value (ex: https://www.microsoft.com)
  • Click the lightning bolt enter image description here
  • Double-click KeyDown to add the event handler to the form

Add Buttons

  • From Toolbox, drag Button to the 2nd column of TableLayoutPanel2
  • In Properties Window, for Button1, set Text property to Back, set (Name) property to desired value (ex: btnBack), and set Anchor property to Left, Right.
  • Click the lightning bolt enter image description here
  • Double-click Click to add the event handler to the form
  • Repeat the process above for: Forward (3rd column), Go (4th column), and Refresh (5th column)

When finished, it should look like the following:

enter image description here

Add WebView2 control to Form

  • In VS menu, click View
  • Select Toolbox
  • In Toolbox, expand WebView2 Windows Forms Control
  • Drag WebView2 to the 2nd row of TableLayoutPanel (ex: TableLayoutPanel1)
  • In Properties Window, for WebView21, set Dock property to Fill

Your form should look like the following:

enter image description here

Add CoreWebView2InitializationCompleted event handler:

  • In Properties Window, select your instance of the WebView2 control (ex: WebView21)
  • Click the lightning bolt enter image description here
  • Double-click CoreWebView2InitializationCompleted to add the event handler to the form

Add NavigationCompleted event handler:

  • In Properties Window, select your instance of the WebView2 control (ex: WebView21)
  • Click the lightning bolt enter image description here
  • Double-click NavigationCompleted to add the event handler to the form

Add WebMessageReceived event handler: (optional)

  • In Properties Window, select your instance of the WebView2 control (ex: WebView21)
  • Click the lightning bolt enter image description here
  • Double-click WebMessageReceived to add the event handler to the form

Modify code:

  • In Solution Explorer, right-click <form name> (ex: Form1)
  • Select View Code

Form1.vb

Imports Microsoft.Web.WebView2.Core
Imports Microsoft.Web.WebView2
Imports System.IO

Public Class Form1
    Private Sub Form1_Load(sender As Object, e As EventArgs) Handles MyBase.Load
        LogMsg("MS Edge Version: " + CoreWebView2Environment.GetAvailableBrowserVersionString())

        If Not String.IsNullOrEmpty(textBoxAddressBar.Text) Then
            'navigate to URL
            'WebView21.Source = New Uri(textBoxAddressBar.Text)
            WebsiteNavigate(textBoxAddressBar.Text)
        End If
    End Sub

    Private Sub Form1_FormClosed(sender As Object, e As FormClosedEventArgs) Handles MyBase.FormClosed
        'unsubscribe from CoreWebView2 event(s) (remove event handlers) 
        RemoveHandler WebView21.CoreWebView2.HistoryChanged, AddressOf CoreWebView2_HistoryChanged
    End Sub

    Private Sub LogMsg(msg As String, Optional addTimestamp As Boolean = True)
        'ToDo: add desired code

        If addTimestamp Then
            msg = String.Format("{0} - {1}", DateTime.Now.ToString("yyyy/MM/dd HH:mm:ss.fff"), msg)
        End If

        Debug.WriteLine(msg)
    End Sub

    Private Sub UpdateAddressBar()
        'if necessary, update address bar
        If textBoxAddressBar.Text <> WebView21.Source.ToString() Then
            textBoxAddressBar.Text = WebView21.Source.ToString()

            'move cursor to end of text
            textBoxAddressBar.SelectionStart = textBoxAddressBar.Text.Length
            textBoxAddressBar.SelectionLength = 0
        End If
    End Sub

    Private Sub WebsiteNavigate(ByVal dest As String)
        If WebView21 IsNot Nothing AndAlso Not String.IsNullOrWhiteSpace(dest) Then

            'URL must start with one of the specified strings
            'if Not, pre-pend with "https://"
            If Not dest = "about:blank" AndAlso
                   Not dest.StartsWith("edge://") AndAlso
                   Not dest.StartsWith("file://") AndAlso
                   Not dest.StartsWith("http://") AndAlso
                   Not dest.StartsWith("https://") AndAlso
                   Not System.Text.RegularExpressions.Regex.IsMatch(dest, "^([A-Z]|[a-z]):") Then

                'set value
                dest = "https://" & dest
            End If

            'option 1
            WebView21.Source = New Uri(dest, UriKind.Absolute)

            'option 2
            'WebView21.CoreWebView2.Navigate(dest)

            'update address bar
            UpdateAddressBar()
        End If
    End Sub

    Private Sub textBoxAddressBar_KeyDown(sender As Object, e As KeyEventArgs) Handles textBoxAddressBar.KeyDown
        If e.KeyCode = Keys.Enter Then
            WebsiteNavigate(textBoxAddressBar.Text)
        End If
    End Sub

    Private Sub btnBack_Click(sender As Object, e As EventArgs) Handles btnBack.Click
        If WebView21 IsNot Nothing AndAlso WebView21.CanGoBack Then
            WebView21.GoBack()
        End If
    End Sub

    Private Sub btnForward_Click(sender As Object, e As EventArgs) Handles btnForward.Click
        If WebView21 IsNot Nothing AndAlso WebView21.CanGoForward Then
            WebView21.GoForward()
        End If
    End Sub

    Private Sub btnGo_Click(sender As Object, e As EventArgs) Handles btnGo.Click
        WebsiteNavigate(textBoxAddressBar.Text)
    End Sub

    Private Sub btnRefresh_Click(sender As Object, e As EventArgs) Handles btnRefresh.Click
        If WebView21 IsNot Nothing Then
            WebView21.Refresh()
        End If
    End Sub

    Private Sub WebView21_CoreWebView2InitializationCompleted(sender As Object, e As Microsoft.Web.WebView2.Core.CoreWebView2InitializationCompletedEventArgs) Handles WebView21.CoreWebView2InitializationCompleted
        LogMsg("WebView21_CoreWebView2InitializationCompleted")
        LogMsg("UserDataFolder: " & WebView21.CoreWebView2.Environment.UserDataFolder.ToString())

        'subscribe to CoreWebView2 event(s) (add event handlers) 
        AddHandler WebView21.CoreWebView2.HistoryChanged, AddressOf CoreWebView2_HistoryChanged

    End Sub

    Private Sub CoreWebView2_HistoryChanged(sender As Object, e As Object)
        'LogMsg("CoreWebView2_HistoryChanged")
        btnBack.Enabled = WebView21.CoreWebView2.CanGoBack
        btnForward.Enabled = WebView21.CoreWebView2.CanGoForward

        'update address bar
        UpdateAddressBar()
    End Sub

    Private Sub WebView21_NavigationCompleted(sender As Object, e As Microsoft.Web.WebView2.Core.CoreWebView2NavigationCompletedEventArgs) Handles WebView21.NavigationCompleted
        LogMsg("WebView21_NavigationCompleted")
    End Sub

    Private Sub WebView21_WebMessageReceived(sender As Object, e As Microsoft.Web.WebView2.Core.CoreWebView2WebMessageReceivedEventArgs) Handles WebView21.WebMessageReceived
        LogMsg("WebView21_WebMessageReceived")
    End Sub
End Class

WebView2 creates a user data folder. If the location isn't specified, according to the documentation:

When userDataFolder is not specified, WebView2 creates user data folders at default locations as follows:

For packaged Windows Store apps, the default user folder is the ApplicationData\LocalFolder subfolder in the package's folder. For existing desktop apps, the default user data folder is the exe path of your application + .WebView2. Instead of using the default, we recommend that you specify a user data folder, and that you create it in the same folder where all other app data is stored.

Note: Writing to %ProgramFiles% or %ProgramFiles(x86)% requires Administrator access - it's not recommended to store data in this location.

If one desires to programmatically initialize CoreWebView2, one must initialize it before setting the Source property of your WebView2 control. If CoreWebView2 isn't initialized, setting Source will cause it to be initialized. Once CoreWebView2 has been initialized, attempting to initialize it again, will have no effect.

See EnsureCoreWebView2Async for more information.

If you desire to specify a location for the user data folder, add the following function:

Private Async Function InitializeCoreWebView2Async(Optional userDataFolder As String = "") As Task
    Dim options As CoreWebView2EnvironmentOptions = Nothing
    Dim cwv2Environment As CoreWebView2Environment = Nothing

    'it's recommended to create the userDataFolder in the same location
    'that your other application data is stored (ie: in a folder in %APPDATA%)
    'if not specified, we'll create a folder in %TEMP%
    If String.IsNullOrEmpty(userDataFolder) Then
        userDataFolder = Path.Combine(Path.GetTempPath(), System.Reflection.Assembly.GetExecutingAssembly().GetName().Name)
    End If

    'create WebView2 Environment using the installed or specified WebView2 Runtime version.
    'cwv2Environment = Await CoreWebView2Environment.CreateAsync("C:\Program Files (x86)\Microsoft\Edge Dev\Application\1.0.1054.31", userDataFolder, options)
    cwv2Environment = Await CoreWebView2Environment.CreateAsync(Nothing, userDataFolder, options)

    'initialize
    Await WebView21.EnsureCoreWebView2Async(cwv2Environment)
End Function

Then replace the code for Form1_Load, with the following:

Note: It's important to use await to ensure that the intialization completes prior to setting the Source property (ie: navigating to the URL). In the code below, the userDataFolder will be created in: C:\Temp\<application name> (ex: C:\Temp\WebView2Test).

Private Async Sub Form1_Load(sender As Object, e As EventArgs) Handles MyBase.Load
    LogMsg("MS Edge Version: " + CoreWebView2Environment.GetAvailableBrowserVersionString())

    'initialize 
    'Await InitializeCoreWebView2Async()
    Await InitializeCoreWebView2Async(Path.Combine("C:\Temp", System.Reflection.Assembly.GetExecutingAssembly().GetName().Name))

    If Not String.IsNullOrEmpty(textBoxAddressBar.Text) Then
        'navigate to URL
        'WebView21.Source = New Uri(textBoxAddressBar.Text)
        WebsiteNavigate(textBoxAddressBar.Text)
    End If
End Sub

To execute JavaScript, see ExecuteScriptAsync.


Update:

For additional CoreWebView2 initialization options see this post.


Resources:

Tu deschizi eu inchid
  • 4,117
  • 3
  • 13
  • 24
  • Thank you for the very detailed execution of a successful setup. Ultimately the root cause was security settings on my computer. Deploying the solution on another computer worked. I think your solution here will hopefully help others getting into using the WebView2 control for the first time. – Eric F Jan 10 '22 at 14:33