diff --git a/NetWebView2Lib.au3 b/NetWebView2Lib.au3 index df65642..0a3c54e 100644 --- a/NetWebView2Lib.au3 +++ b/NetWebView2Lib.au3 @@ -6,7 +6,7 @@ #Tidy_Parameters=/tcb=-1 -; NetWebView2Lib.au3 - Script Version: 2.2.1-alpha (2026.03.20.09) 🚩 +; NetWebView2Lib.au3 - Script Version: 2.2.1-alpha1 (2026.04.14.10) 🚩 #include #include @@ -112,6 +112,7 @@ Global Enum _ ; $NETWEBVIEW2_MESSAGE__* are set by mainly by __NetWebView2_Event $NETWEBVIEW2_MESSAGE__COOKIE_ADD_ERROR, _ $NETWEBVIEW2_MESSAGE__BLOCKED_AD, _ $NETWEBVIEW2_MESSAGE__DOWNLOAD_STARTING, _ + $NETWEBVIEW2_MESSAGE__DOWNLOAD_CANCELLED, _ ; <<--( NEW )--<< $NETWEBVIEW2_MESSAGE__DOWNLOAD_IN_PROGRESS, _ $NETWEBVIEW2_MESSAGE__DOWNLOAD_INTERRUPTED, _ $NETWEBVIEW2_MESSAGE__DOWNLOAD_COMPLETED, _ @@ -152,12 +153,13 @@ Global Enum _ ; Indicates the reason for the process failure. ; $bVerbose = False]]]]) ; Parameters ....: $sUserAgent - [optional] a string value. Default is "". ; $s_fnEventPrefix - [optional] a string value. Default is "". -; $s_AddBrowserArgs - [optional] a string value. Default is "". Allows passing command-line switches (e.g., --disable-gpu, --mute-audio, --proxy-server="...") to the Chromium engine. +; $s_AddBrowserArgs - [optional] a string value. Default is "". Allows passing command-line switches (e.g., --disable-gpu --mute-audio --proxy-server="...") to the Chromium engine. ; $bVerbose - [optional] True/False - Enable/Disable diagnostic logging. Default is False = Disabled. ; Return values .: None ; Author ........: mLipok, ioa747 ; Modified ......: -; Remarks .......: $s_AddBrowserArgs must be set before calling Initialize(). +; Remarks .......: $s_AddBrowserArgs must be set before calling _NetWebView2_Initialize(). +; Multiple arguments must be separated by a SPACE, not a comma (e.g., "--mute-audio --disable-gpu"). ; Related .......: ; Link ..........: https://www.chromium.org/developers/how-tos/run-chromium-with-flags ; Link ..........: https://chromium.googlesource.com/chromium/src/+/main/docs/configuration.md#switches @@ -2102,6 +2104,10 @@ Volatile Func __NetWebView2_Events__OnMessageReceived($oWebV2M, $hGUI, $sMsg) __NetWebView2_Log(@ScriptLineNumber, $s_Prefix & " COMMAND:" & $sCommand, 1) __NetWebView2_LastMessage_KEEPER($oWebV2M, $NETWEBVIEW2_MESSAGE__DOWNLOAD_STARTING) + Case "DOWNLOAD_CANCELLED" + __NetWebView2_Log(@ScriptLineNumber, $s_Prefix & " COMMAND:" & $sCommand, 1) + __NetWebView2_LastMessage_KEEPER($oWebV2M, $NETWEBVIEW2_MESSAGE__DOWNLOAD_CANCELLED) ; <<--( NEW )--<< + Case "BROWSER_GOT_FOCUS" __NetWebView2_Log(@ScriptLineNumber, $s_Prefix & " COMMAND:" & $sCommand, 1) __NetWebView2_LastMessage_KEEPER($oWebV2M, $NETWEBVIEW2_MESSAGE__BROWSER_GOT_FOCUS) @@ -2405,46 +2411,55 @@ EndFunc ;==>__NetWebView2_Events__OnContextMenu ; #INTERNAL_USE_ONLY# =========================================================================================================== ; Name ..........: __NetWebView2_Events__OnWebResourceResponseReceived -; Description ...: -; Syntax ........: __NetWebView2_Events__OnWebResourceResponseReceived($oWebV2M, $hGUI, $iStatusCode, $sReasonPhrase, -; $sRequestUrl) +; Description ...: Internal handler for the WebResourceResponseReceived event. +; Syntax ........: __NetWebView2_Events__OnWebResourceResponseReceived($oWebV2M, $hGUI, $oArgs) ; Parameters ....: $oWebV2M - WebView2 object that fired the event -; $hGUI - a handle to Window that fired the event -; $iStatusCode - HTTP StatusCode -; $sReasonPhrase - StatusCode rephrased to human resonable string -; $sRequestUrl - the URL that fired the event +; $hGUI - A handle to Window that fired the event +; $oArgs - An Event Arguments Object containing: +; | .StatusCode (int) [RO]: The HTTP status code (e.g., 200, 404). +; | .ReasonPhrase (string) [RO]: The HTTP reason phrase (e.g., "OK"). +; | .RequestUri (string) [RO]: The URL of the request. +; | .IsDocument (bool) [RO]: True if the resource is the main document. ; Return values .: None -; Author ........: mLipok -; Modified ......: +; Author ........: ioa747, mLipok +; Modified ......: 2026-04-14 (Refactored to Object-Oriented Event Model) ; Remarks .......: ; Related .......: ; Link ..........: https://learn.microsoft.com/en-us/dotnet/api/microsoft.web.webview2.core.corewebview2.webresourceresponsereceived -; Example .......: No +; Example .......: 007-HTTP_StatusCodeTracking.au3 ; =============================================================================================================================== -Volatile Func __NetWebView2_Events__OnWebResourceResponseReceived($oWebV2M, $hGUI, $iStatusCode, $sReasonPhrase, $sRequestUrl) - Local Const $s_Prefix = ">>>[EVENT: OnWebResourceResponseReceived]: GUI:" & $hGUI & " HTTPStatusCode:" & $iStatusCode & " (" & $sReasonPhrase & ") URL:" & $sRequestUrl - __NetWebView2_Log(@ScriptLineNumber, (StringLen($s_Prefix) > 150 ? StringLeft($s_Prefix, 150) & "..." : $s_Prefix), 1) +Volatile Func __NetWebView2_Events__OnWebResourceResponseReceived($oWebV2M, $hGUI, $oArgs) ; <<--( NEW )--<< + Local Const $s_Prefix = ">>>[EVENT: OnWebResourceResponseReceived]: GUI:" & $hGUI & _ + " HTTPStatusCode:" & $oArgs.StatusCode & " (" & $oArgs.ReasonPhrase & ") URL:" & $oArgs.RequestUri & " URL:" & $oArgs.IsDocument + + __NetWebView2_Log(@ScriptLineNumber, $s_Prefix, 1) __NetWebView2_LastMessage_KEEPER($oWebV2M, $NETWEBVIEW2_MESSAGE__RESPONSE_RECEIVED) EndFunc ;==>__NetWebView2_Events__OnWebResourceResponseReceived ; #INTERNAL_USE_ONLY# =========================================================================================================== ; Name ..........: __NetWebView2_Events__OnDownloadStarting -; Description ...: -; Syntax ........: __NetWebView2_Events__OnDownloadStarting($oWebV2M, $hGUI, $sURL, $sDefaultPath) -; Parameters ....: $oWebV2M - an object. -; $hGUI - a handle value. -; $sURL - a string value. -; $sDefaultPath - a string value. +; Description ...: Internal handler for the DownloadStarting event. Dispatches the event to the user's callback with an Args Object. +; Syntax ........: __NetWebView2_Events__OnDownloadStarting($oWebV2M, $hGUI, $oArgs) +; Parameters ....: $oWebV2M - The WebView2 Manager object. +; $hGUI - The handle to the GUI window. +; $oArgs - An Event Arguments Object containing: +; | .Uri (String) [RO]: The source URL of the download. +; | .MimeType (String) [RO]: The MIME type (e.g., "application/pdf"). +; | .ContentDisposition (String) [RO]: The HTTP Content-Disposition header. +; | .TotalBytesToReceive (Int64) [RO]: Total size in bytes (-1 if unknown). +; | .ResultFilePath (String) [RW]: Get/Set the full target save path. +; | .Cancel (Boolean) [RW]: Set to True to abort the download. +; | .Handled (Boolean) [RW]: Set to True to exit the C# wait loop immediately. ; Return values .: None ; Author ........: ioa747, mLipok -; Modified ......: -; Remarks .......: -; Related .......: -; Link ..........: -; Example .......: No +; Modified ......: 2026-04-14 (Refactored to Object-Oriented Event Model) +; Remarks .......: This event uses a 5000ms synchronization loop in C# to allow for AutoIt interaction (e.g., MsgBox). +; Related .......: _NetWebView2_CreateManager +; Link ..........: https://learn.microsoft.com/en-us/dotnet/api/microsoft.web.webview2.core.corewebview2downloadstartingeventargs +; Example .......: 021 - Handle Unviewable Content (MIME).au3 ; =============================================================================================================================== -Volatile Func __NetWebView2_Events__OnDownloadStarting($oWebV2M, $hGUI, $sURL, $sDefaultPath) - Local Const $s_Prefix = ">>>[EVENT: OnDownloadStarting]: GUI:" & $hGUI & " URL:" & $sURL & " DEFAULT_PATH:" & $sDefaultPath +Volatile Func __NetWebView2_Events__OnDownloadStarting($oWebV2M, $hGUI, $oArgs) ; <<--( NEW )--<< + Local Const $s_Prefix = "[>>>EVENT: OnDownloadStarting]: GUI:" & $hGUI & " URL: " & $oArgs.Uri & " PATH: " & $oArgs.ResultFilePath & " MIME: " & $oArgs.MimeType __NetWebView2_Log(@ScriptLineNumber, (StringLen($s_Prefix) > 150 ? StringLeft($s_Prefix, 150) & "..." : $s_Prefix), 1) __NetWebView2_LastMessage_KEEPER($oWebV2M, $NETWEBVIEW2_MESSAGE__DOWNLOAD_STARTING) EndFunc ;==>__NetWebView2_Events__OnDownloadStarting @@ -2456,48 +2471,56 @@ EndFunc ;==>__NetWebView2_Events__OnDownloadStarting ; $iReceived_Bytes) ; Parameters ....: $oWebV2M - an object. ; $hGUI - a handle value. -; $sState - a string value. -; $sURL - a string value. -; $iTotal_Bytes - an integer value. -; $iReceived_Bytes - an integer value. +; $oArgs - An Event Arguments Object containing: +; | .Uri (String) [RO]: The source URL of the download. +; | .State (String) [RO]: The current state ("InProgress", "Completed", "Interrupted"). +; | .TotalBytesToReceive (int) [RO]: Estimated total size. +; | .BytesReceived (int) [RO]: Number of bytes received so far. +; | .PercentComplete (int) [RO]: Calculation (0-100) or -1 if unknown. ; Return values .: None ; Author ........: ioa747, mLipok ; Modified ......: ; Remarks .......: ; Related .......: ; Link ..........: -; Example .......: No +; Example .......: 006-DownloadDemo.au3 ; =============================================================================================================================== -Volatile Func __NetWebView2_Events__OnDownloadStateChanged($oWebV2M, $hGUI, $sState, $sURL, $iTotal_Bytes, $iReceived_Bytes) - Local Const $s_Prefix = ">>>[EVENT: OnDownloadStateChanged]: GUI:" & $hGUI & " State:" & $sState & " URL:" & $sURL & " Total_Bytes:" & $iTotal_Bytes & " Received_Bytes:" & $iReceived_Bytes - Local $iPercent = 0 - If $iTotal_Bytes > 0 Then $iPercent = Round(($iReceived_Bytes / $iTotal_Bytes), 5) * 100 +Volatile Func __NetWebView2_Events__OnDownloadStateChanged($oWebV2M, $hGUI, $oArgs) ; <<--( NEW )--<< + Local $iReceived_MB = Round($oArgs.BytesReceived / 1048576, 2) ; 1024*1024 + Local $iTotal_MB = Round($oArgs.TotalBytesToReceive / 1048576, 2) + + Local Const $s_Prefix = "[>>>EVENT: OnDownloadStateChanged]: GUI:" & $hGUI & " State: " & $oArgs.State & " | " & _ + $oArgs.PercentComplete & "% (" & $iReceived_MB & "/" & $iTotal_MB & " MB) URL: " & $oArgs.Uri - ; Convert to MB for easy-to-read log - Local $iReceived_MegaBytes = Round($iReceived_Bytes / 1024 / 1024) - Local $iTotal_MegaBytes = Round($iTotal_Bytes / 1024 / 1024) + __NetWebView2_Log(@ScriptLineNumber, $s_Prefix, 1) - Local Const $s_Message = " " & $iPercent & "% (" & $iReceived_MegaBytes & " / " & $iTotal_MegaBytes & " Mega Bytes)" - Switch $sState + Switch $oArgs.State Case "InProgress" - __NetWebView2_Log(@ScriptLineNumber, $s_Prefix & $s_Message, 1) __NetWebView2_LastMessage_KEEPER($oWebV2M, $NETWEBVIEW2_MESSAGE__DOWNLOAD_IN_PROGRESS) Case "Interrupted" - __NetWebView2_Log(@ScriptLineNumber, $s_Prefix & $s_Message, 1) __NetWebView2_LastMessage_KEEPER($oWebV2M, $NETWEBVIEW2_MESSAGE__DOWNLOAD_INTERRUPTED) Case "Completed" - __NetWebView2_Log(@ScriptLineNumber, $s_Prefix & $s_Message, 1) __NetWebView2_LastMessage_KEEPER($oWebV2M, $NETWEBVIEW2_MESSAGE__DOWNLOAD_COMPLETED) EndSwitch -EndFunc ;==>__NetWebView2_Events__OnDownloadStateChanged +EndFunc ; #INTERNAL_USE_ONLY# =========================================================================================================== ; Name ..........: __NetWebView2_Events__OnAcceleratorKeyPressed -; Description ...: +; Description ...: It allows the application to intercept and handle system keys and keyboard shortcuts (Accelerators) before the WebView2 engine processes them. ; Syntax ........: __NetWebView2_Events__OnAcceleratorKeyPressed($oWebV2M, $hGUI, $oArgs) ; Parameters ....: $oWebV2M - an object. ; $hGUI - a handle value. -; $oArgs - an object. +; $oArgs - An Event Arguments Object containing: +; | .VirtualKey (uint) [RO]: The VK code of the key. +; | .KeyEventKind (int) [RO]: Type of key event (0:KeyDown, 1:KeyUp, etc.). +; | .RepeatCount (uint) [RO]: The number of times the key has repeated. +; | .ScanCode (uint) [RO]: Hardware scan code. +; | .IsExtendedKey (bool) [RO]: True if it's an extended key (e.g., right Alt). +; | .IsMenuKeyDown (bool) [RO]: True if Alt is pressed. +; | .WasKeyDown (bool) [RO]: True if the key was already down. +; | .IsKeyReleased (bool) [RO]: True if the event is a key up. +; | .KeyEventLParam (int) [RO]: The native LPARAM window message value. +; | .Handled (bool) [RW]: Set to True to prevent the browser from executing the default action. ; Return values .: None ; Author ........: ioa747, mLipok ; Modified ......: diff --git a/README.md b/README.md index e543d4c..9dfda9f 100644 --- a/README.md +++ b/README.md @@ -62,33 +62,29 @@ https://www.autoitscript.com/forum/topic/213375-webview2autoit-autoit-webview2-c This project is provided "as-is". You are free to use, modify, and distribute it for both personal and commercial projects. -

- -## πŸš€ What's New in v2.2.1-alpha - UI Responsiveness & Refactoring +## πŸš€ What's New in v2.2.1-alpha1 - UI Responsiveness & Refactoring This release marks a major architectural milestone for the library by introducing **Event Object Refactoring**. Key events have been transitioned from passing raw data (strings) to passing full **COM-visible objects**, granting developers absolute control over the application's navigation flow. ### ⚑ Key Features & Enhancements -#### 1. Advanced Navigation Control (`IWebView2NavigationStartingEventArgs`) - -Navigation is no longer a passive process. With the new `Args` object, you can programmatically intervene in the navigation lifecycle before it even begins. +#### 1. Advanced Navigation Control (`IWebView2NavigationStartingEventArgs`) +Navigation is no longer a passive process. +With the new `Args` object, you can programmatically intervene in the navigation lifecycle before it even begins. - **`Cancel` [Property]**: The ability to kill a navigation request at its source. Perfect for content filtering, security, and custom protocol handling. - + - **`IsUserInitiated`**: Determine whether the navigation was triggered by a physical user click or programmatically via JavaScript. - + - **`IsRedirected`**: Automatically detect if the current request is a server-side or client-side redirect. - + - **`NavigationId`**: A unique identifier for precise request tracking across complex web sessions. - #### 2. Event Object Refactoring & API Maturity - We are moving away from "Raw Parameter" callbacks toward an **Object-Oriented Event Model**. - **Breaking Change**: `OnNavigationStarting` and `OnFrameNavigationStarting` now return an **Args Object**. This change is essential to support bi-directional communication (e.g., AutoIt telling C# to `Cancel = True`). @@ -96,13 +92,39 @@ We are moving away from "Raw Parameter" callbacks toward an **Object-Oriented Ev - **Future-Proofing**: Adding new metadata in future WebView2 updates will no longer break existing user code, as new properties will simply be appended to the existing object. #### 3. UI Responsiveness & Interception-Based Locking (Critical Patch) - Following the initial alpha release, we identified and resolved a critical issue where Developer Tools (F12) and Right-Click menus could become unresponsive after navigation. - **Interception-Based Locking**: We moved away from toggling engine-level properties (which caused state lag) to a robust **C# Interception Model**. Features are kept "On" at the engine level but are blocked via the `_isLocked` flag in C#, ensuring the "Inspect" menu item never disappears. + - **C# Fast Path**: Common actions like F12 are now handled instantly within the C# layer, bypassing the AutoIt COM overhead for maximum performance. + - **Guaranteed Unlock**: Improved the AutoIt navigation functions (`_NetWebView2_Navigate`) to ensure the browser is always unlocked, even if a navigation times out or fails. +#### 4. Refactored: OnDownloadStarting Event +- **Transitioned from a parameter-based signature to a robust, object-oriented argument model.** + - **New Argument Wrapper**: `IWebView2DownloadStartingEventArgs` provides access to `Uri`, `ResultFilePath`, `Handled`, `Cancel`, `MimeType`, `ContentDisposition`, and `TotalBytesToReceive`. + + - **Hybrid Deferral Model**: Implemented a performance-optimized synchronization mechanism using `CoreWebView2Deferral`. The C# core now waits up to 5000ms for AutoIt to set `Handled` or `Cancel` on the argument object, proceeding immediately once a decision is made. + + - **MimeType Support (Issue #123)**: Exposed `MimeType` directly in the download arguments, allowing AutoIt scripts to identify "unviewable content" (e.g., PDFs, ZIPs) at the start of the download lifecycle. + +- **Improved: Download Logic**: Automatic redirection to `_customDownloadPath` is now applied *before* the event fires, allowing **AutoIt** to see and potentially override the final destination. + +#### 5. Refactored: OnDownloadStateChanged Event +- **Transitioned to an object-oriented argument model for consistent event handling.** + - **New Argument Wrapper**: `IWebView2DownloadStateChangedEventArgs` + provides access to `State`, `Uri`, `TotalBytesToReceive`, `BytesReceived`, and a new `PercentComplete` helper. + + - **Buffered Property Pattern**: Applied to ensure thread-safe progress updates during rapid download cycles. + +#### 6. Fixed: HTTP Status Code Detection +- Resolved a bug where `OnWebResourceResponseReceived` failed to fire due to a missing legacy header hack. Replaced with native `ResourceContext` detection. + + + +> [!CAUTION] +> **Breaking Change**: If you have custom scripts using `OnWebResourceResponseReceived` or `OnDownloadStateChanged`, please update their signatures to use the new `$oArgs` object as demonstrated in the updated examples. + ### πŸ—οΈ Architectural Inheritance & Refactoring @@ -116,7 +138,6 @@ Building on the foundation of v2.1.0, this version further strengthens the **Eve > **Why this matters:** The shift to objects transforms **NetWebView2Lib** from a "simple browser wrapper" into a **Professional-Grade SDK** for AutoIt. It brings low-level controlβ€”previously reserved for languages like C# or C++β€”directly into the hands of the AutoIt developer. -

@@ -124,6 +145,7 @@ Building on the foundation of v2.1.0, this version further strengthens the **Eve ## πŸ“– NetWebView2Lib Version 2.2.1-alpha (Quick Reference) + ### 🟦 WebView2Manager (ProgId: NetWebView2Lib.WebView2Manager) #### ===πŸ”§ Properties=== @@ -284,21 +306,17 @@ Toggles between Native (true) and Custom (false) context menu modes. `object.SetContextMenuEnabled(Enabled As Boolean)` ##### 🧊 LockWebView -Locks down the WebView by disabling context menus, dev tools, zoom control, default error pages, script dialogs, accelerator keys, and popups. +Locks down the WebView using a robust C# interception model. While features remain enabled at the engine level for UI stability, they are blocked internally. Disables context-menus, dev tools, zoom, error pages, script dialogs, accelerator keys, and popups. `object.LockWebView()` ##### 🧊 UnLockWebView -Re-enables the features previously restricted by `LockWebView()` (ContextMenus, DevTools, Zoom, ErrorPages, Dialogs, Keys, Popups). +Re-enables the features previously intercepted by `LockWebView()` (ContextMenus, DevTools, Zoom, ErrorPages, Dialogs, Keys, Popups). Restores user preferences from high-speed backing fields. `object.UnLockWebView()` -##### 🧊 DisableBrowserFeatures [LEGACY] +##### 🧊 DisableBrowserFeatures Disables major browser features for a controlled environment (Unified with `LockWebView`). `object.DisableBrowserFeatures()` -##### 🧊 EnableBrowserFeatures [LEGACY] -Disables major browser features for a controlled environment (Unified with `UnLockWebView`). -`object.EnableBrowserFeatures()` - ##### 🧊 GoBack Navigates back to the previous page in history. `object.GoBack()` @@ -576,8 +594,8 @@ Sets a global default folder or file path for all browser downloads. If a direct Cancels active downloads. If `uri` is empty or omitted, cancels all active downloads. `object.CancelDownloads([Uri As String])` -##### 🧊 ExportPageData [LEGACY] -Consolidated into **CaptureSnapshot**. +##### 🧊 ExportPageData +[LEGACY] Consolidated into **CaptureSnapshot**. `object.ExportPageData(Format As Integer, FilePath As String)` ##### 🧊 PrintToPdfStream @@ -592,7 +610,12 @@ Fired when a message or notification is sent from the library to AutoIt. ##### ⚑ OnWebResourceResponseReceived Fired when a web resource response is received (useful for tracking HTTP Status Codes). -`object_OnWebResourceResponseReceived(Sender As Object, ParentHandle As HWND, StatusCode As Integer, ReasonPhrase As String, RequestUrl As String)` +`object_OnWebResourceResponseReceived(Sender As Object, ParentHandle As HWND, Args As Object)` + *Args properties: + StatusCode (int): The HTTP status code (e.g., 200, 404). + ReasonPhrase (string): The HTTP reason phrase (e.g., "OK", "Not Found"). + RequestUri (string): The URI of the request. + IsDocument (bool): True if the resource is a Document.* ##### ⚑ OnNavigationStarting Fired when the browser starts navigating to a new URL. @@ -637,12 +660,26 @@ Fired when a context menu is requested (Simplified for AutoIt). `object_OnContextMenuRequested(Sender As Object, ParentHandle As HWND, LinkUrl As String, X As Integer, Y As Integer, SelectionText As String)` ##### ⚑ OnDownloadStarting -Fired when a download is starting. Provides core metadata to allow decision making. Path overrides and UI suppression should be handled via the `DownloadResultPath` and `IsDownloadHandled` properties. -`object_OnDownloadStarting(Sender As Object, ParentHandle As HWND, Uri As String, DefaultPath As String)` +Fired when a download is starting. Provides a robust argument object for decision making and metadata access (MimeType, etc.). +`object_OnDownloadStarting(Sender As Object, ParentHandle As HWND, Args As Object)` + *Args properties: + Uri (string): The target URL of the download. + ResultFilePath (string): Get/Set the target file path. + Handled (bool): Set to True to indicate AutoIt has handled the UI/Decision (stops the 5000ms wait loop). + Cancel (bool): Set to True to cancel the download immediately. + MimeType (string): The MIME type of the content (e.g., "application/pdf"). + ContentDisposition (string): The Content-Disposition header from the server. + TotalBytesToReceive (long): Estimated total size of the download (if known).* ##### ⚑ OnDownloadStateChanged Fired when a download state changes (e.g., Progress, Completed, Failed). -`object_OnDownloadStateChanged(Sender As Object, ParentHandle As HWND, State As String, Uri As String, TotalBytes As Long, ReceivedBytes As Long)` +`object_OnDownloadStateChanged(Sender As Object, ParentHandle As HWND, Args As Object)` + *Args properties: + State (string): The current state ("InProgress", "Completed", "Interrupted"). + Uri (string): The download URI. + TotalBytesToReceive (long): Estimated total size. + BytesReceived (long): Number of bytes received so far. + PercentComplete (int): Calculation (0-100) or -1 if unknown.* ##### ⚑ OnAcceleratorKeyPressed Fired when an accelerator key is pressed. Allows blocking browser shortcuts. @@ -921,3 +958,4 @@ Removes duplicate objects from a JSON array based on a key's value. --- + diff --git a/bin/x64/NetWebView2Lib.dll b/bin/x64/NetWebView2Lib.dll index 3f9b64c..9acc3b5 100644 Binary files a/bin/x64/NetWebView2Lib.dll and b/bin/x64/NetWebView2Lib.dll differ diff --git a/bin/x64/NetWebView2Lib.tlb b/bin/x64/NetWebView2Lib.tlb index ec8aaeb..f93a865 100644 Binary files a/bin/x64/NetWebView2Lib.tlb and b/bin/x64/NetWebView2Lib.tlb differ diff --git a/bin/x86/NetWebView2Lib.dll b/bin/x86/NetWebView2Lib.dll index 3f9b64c..9acc3b5 100644 Binary files a/bin/x86/NetWebView2Lib.dll and b/bin/x86/NetWebView2Lib.dll differ diff --git a/bin/x86/NetWebView2Lib.tlb b/bin/x86/NetWebView2Lib.tlb index c19d07d..f93a865 100644 Binary files a/bin/x86/NetWebView2Lib.tlb and b/bin/x86/NetWebView2Lib.tlb differ diff --git a/examples/001-BasicDemo.au3 b/examples/001-BasicDemo.au3 index c8312cf..e6cbee5 100644 --- a/examples/001-BasicDemo.au3 +++ b/examples/001-BasicDemo.au3 @@ -26,7 +26,7 @@ Func Main() GUISetState(@SW_SHOW, $hGUI) ; Initialize WebView2 Manager and register events - Local $oWebV2M = _NetWebView2_CreateManager("Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/144.0.0.0 Safari/537.36 Edg/144.0.0.0", "", "--disable-gpu, --mute-audio") + Local $oWebV2M = _NetWebView2_CreateManager("Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/144.0.0.0 Safari/537.36 Edg/144.0.0.0", "", "--disable-gpu --mute-audio") If @error Then Return SetError(@error, @extended, $oWebV2M) ; Initialize JavaScript Bridge diff --git a/examples/006-DownloadDemo.au3 b/examples/006-DownloadDemo.au3 index 718b4c8..4bff699 100644 --- a/examples/006-DownloadDemo.au3 +++ b/examples/006-DownloadDemo.au3 @@ -53,8 +53,7 @@ Func _Example() $oWebV2M.SetDownloadPath(@ScriptDir & "\Downloads_Test") ; navigate to the page -;~ _NetWebView2_Navigate($oWebV2M, "https://www.libreoffice.org/donate/dl/win-x86_64/25.8.4/en-US/LibreOffice_25.8.4_Win_x86-64.msi", $NETWEBVIEW2_MESSAGE__NAV_STARTING) - _NetWebView2_Navigate($oWebV2M, "https://www.libreoffice.org/donate/dl/win-x86_64/26.2.1/pl/LibreOffice_26.2.1_Win_x86-64.msi", $NETWEBVIEW2_MESSAGE__NAV_STARTING) + _NetWebView2_Navigate($oWebV2M, "https://downloadarchive.documentfoundation.org/libreoffice/old/26.2.3.1/win/x86_64/LibreOffice_26.2.3.1_Win_x86-64.msi", $NETWEBVIEW2_MESSAGE__NAV_STARTING) #TODO AutoDetermine MSI file location __Example_Log(@ScriptLineNumber, "END - close window to exit" & @CRLF) @@ -74,28 +73,29 @@ Func _Example() EndFunc ;==>_Example +#Region ; === EVENT HANDLERS === ; Advise using 'Volatile' for Event Handlers to ensure the WebView2 COM thread can interrupt the main script safely. -Volatile Func __UserEventHandler__OnDownloadStateChanged($oWebV2M, $hGUI, $sState, $sURL, $iTotal_Bytes, $iReceived_Bytes) +Volatile Func __UserEventHandler__OnDownloadStateChanged($oWebV2M, $hGUI, $oArgs) #forceref $oWebV2M $hGUI = HWnd("0x" & Hex($hGUI, 16)) - Local $iPercent = 0 - If $iTotal_Bytes > 0 Then $iPercent = Round(($iReceived_Bytes / $iTotal_Bytes), 5) * 100 + Local $iPercent = $oArgs.PercentComplete + If $iPercent < 0 Then $iPercent = 0 ; Convert to MB for easy-to-read log - Local $iReceived_MegaBytes = Round($iReceived_Bytes / 1024 / 1024) - Local $iTotal_MegaBytes = Round($iTotal_Bytes / 1024 / 1024) + Local $iReceived_MegaBytes = Round($oArgs.BytesReceived / 1048576, 2) ; 1024*1024 + Local $iTotal_MegaBytes = Round($oArgs.TotalBytesToReceive / 1048576, 2) - Local Const $s_Message = " " & $iPercent & "% (" & $iReceived_MegaBytes & " / " & $iTotal_MegaBytes & " Mega Bytes)" + Local Const $s_Message = " " & $iPercent & "% (" & $iReceived_MegaBytes & " / " & $iTotal_MegaBytes & " MB)" Local Static $bProgres_State = 0 - Switch $sState + Switch $oArgs.State Case "InProgress" If $bProgres_State = 0 Then - ProgressOn("Dowload in progress", StringRegExpReplace($sURL, '(.+/)(.+)', '$2'), $s_Message, -1, -1, BitOR($DLG_NOTONTOP, $DLG_MOVEABLE)) + ProgressOn("Dowload in progress", StringRegExpReplace($oArgs.Uri, '(.+/)(.+)', '$2'), $s_Message, -1, -1, BitOR($DLG_NOTONTOP, $DLG_MOVEABLE)) EndIf - $_sURLDownload_InProgress = $sURL + $_sURLDownload_InProgress = $oArgs.Uri ProgressSet(Round($iPercent), $s_Message) $bProgres_State = 1 Case "Interrupted" @@ -150,8 +150,8 @@ Volatile Func __UserEventHandler__OnAcceleratorKeyPressed($oWebV2M, $hGUI, $oArg __NetWebView2_Log(@ScriptLineNumber, $s_Prefix, 0) - $oArgs = 0 ; Explicitly release the COM reference inside the volatile scope EndFunc ;==>__UserEventHandler__OnAcceleratorKeyPressed +#EndRegion ; === EVENT HANDLERS === Func __Example_Log($s_ScriptLineNumber, $sString, $iError = @error, $iExtended = @extended) ConsoleWrite(@ScriptName & ' SLN=' & $s_ScriptLineNumber & ' [' & $iError & '/' & $iExtended & '] ::: ' & $sString & @CRLF) diff --git a/examples/007-HTTP_StatusCodeTracking.au3 b/examples/007-HTTP_StatusCodeTracking.au3 index eecb5e0..ad0a059 100644 --- a/examples/007-HTTP_StatusCodeTracking.au3 +++ b/examples/007-HTTP_StatusCodeTracking.au3 @@ -51,8 +51,8 @@ Func _Example_HTTP_Tracking() EndFunc ;==>_Example_HTTP_Tracking #Region ; === EVENT HANDLERS === -; Handles native WebView2 events -Func WebEvents_OnMessageReceived($oWebV2M, $hGUI, $sMsg) +; Advise using 'Volatile' for Event Handlers to ensure the WebView2 COM thread can interrupt the main script safely. +Volatile Func WebEvents_OnMessageReceived($oWebV2M, $hGUI, $sMsg) ; { part of the $hGUI handle explanation ; with the new Advanced Handle Formatting logic [HANDLE:0x...] @@ -67,6 +67,7 @@ Func WebEvents_OnMessageReceived($oWebV2M, $hGUI, $sMsg) ConsoleWrite("- _WinAPI_GetClientWidth($hWnd)=" & _WinAPI_GetClientWidth($hWnd) & @CRLF) ; working ; End part of the $hGUI handle explanation } + ConsoleWrite(">>> [WebEvents]: " & (StringLen($sMsg) > 150 ? StringLeft($sMsg, 150) & "..." : $sMsg) & @CRLF) Local $iSplitPos = StringInStr($sMsg, "|") Local $sCommand = $iSplitPos ? StringStripWS(StringLeft($sMsg, $iSplitPos - 1), 3) : $sMsg @@ -85,7 +86,8 @@ Func WebEvents_OnMessageReceived($oWebV2M, $hGUI, $sMsg) EndFunc ;==>WebEvents_OnMessageReceived ; Handles custom messages from JavaScript (window.chrome.webview.postMessage) -Func JavaScript_OnMessageReceived($oWebV2M, $hGUI, $sMsg) +; Advise using 'Volatile' for Event Handlers to ensure the WebView2 COM thread can interrupt the main script safely. +Volatile Func JavaScript_OnMessageReceived($oWebV2M, $hGUI, $sMsg) #forceref $oWebV2M, $hGUI ConsoleWrite(">>> [JavaScript]: " & (StringLen($sMsg) > 150 ? StringLeft($sMsg, 150) & "..." : $sMsg) & @CRLF) Local $sFirstChar = StringLeft($sMsg, 1) @@ -127,24 +129,27 @@ Func JavaScript_OnMessageReceived($oWebV2M, $hGUI, $sMsg) EndFunc ;==>JavaScript_OnMessageReceived ; OnWebResourceResponseReceived -Func WebEvents_OnWebResourceResponseReceived($oWebV2M, $hGUI, $iStatusCode, $sReasonPhrase, $sRequestUrl) +; Advise using 'Volatile' for Event Handlers to ensure the WebView2 COM thread can interrupt the main script safely. +Volatile Func WebEvents_OnWebResourceResponseReceived($oWebV2M, $hGUI, $oArgs) + ConsoleWrite("-$hGUI=" & $hGUI & @CRLF) + ConsoleWrite("-$iStatusCode=" & $oArgs.StatusCode & @CRLF) #forceref $hGUI - Local $sLog = StringFormat("! [HTTP %d] | %s | URL: %s", $iStatusCode, $sReasonPhrase, $sRequestUrl) + Local $sLog = StringFormat("! [HTTP %d] | %s | URL: %s", $oArgs.StatusCode, $oArgs.ReasonPhrase, $oArgs.RequestUri) ConsoleWrite($sLog & @CRLF) - Local $oGuard = ObjEvent("AutoIt.Error", __NetWebView2_fake_COMErrFunc) + Local $oGuard = ObjEvent("AutoIt.Error", "__NetWebView2_SilentErrorHandler") #forceref $oGuard ; Management example: - If $iStatusCode >= 400 Then - ConsoleWrite("Navigation Issue detected on: " & @CRLF & $sRequestUrl) + If $oArgs.StatusCode >= 400 Then + ConsoleWrite("Navigation Issue detected on: " & @CRLF & $oArgs.RequestUri) ; If it is the main URL and not an iframe/sub-resource - If $iStatusCode = 404 Then + If $oArgs.StatusCode = 404 And $oArgs.IsDocument Then ; We use a small Ad-hoc HTML for the error Local $sErrorHTML = "" & _ - "

😟 Navigation Error " & $iStatusCode & " 🫒

" & _ + "

😟 Navigation Error " & $oArgs.StatusCode & " 🫒

" & _ "

The requested URL was not found.

" & _ "" @@ -153,7 +158,6 @@ Func WebEvents_OnWebResourceResponseReceived($oWebV2M, $hGUI, $iStatusCode, $sRe EndIf EndIf EndFunc ;==>WebEvents_OnWebResourceResponseReceived - #EndRegion ; === EVENT HANDLERS === Func __Example_Log($s_ScriptLineNumber, $sString, $iError = @error, $iExtended = @extended) diff --git a/examples/008-JavaScript.au3 b/examples/008-JavaScript.au3 index 4e463a5..9dd8da3 100644 --- a/examples/008-JavaScript.au3 +++ b/examples/008-JavaScript.au3 @@ -18,7 +18,7 @@ Func _Example_Console_Redirect() ; 1. Initialize WebView2 ; Initialize WebView2 Manager and register events - Local $oWebV2M = _NetWebView2_CreateManager("Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/144.0.0.0 Safari/537.36 Edg/144.0.0.0", "", "--disable-gpu, --mute-audio") + Local $oWebV2M = _NetWebView2_CreateManager("Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/144.0.0.0 Safari/537.36 Edg/144.0.0.0", "", "--disable-gpu --mute-audio") If @error Then Return SetError(@error, @extended, $oWebV2M) ; initialize browser - put it on the GUI diff --git a/examples/018-BasicFramesDemo.au3 b/examples/018-BasicFramesDemo.au3 index e00de25..e7b3d28 100644 --- a/examples/018-BasicFramesDemo.au3 +++ b/examples/018-BasicFramesDemo.au3 @@ -27,7 +27,7 @@ Func Main() ; Initialize WebView2 Manager and register events Local $oWebV2M = _NetWebView2_CreateManager("Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/144.0.0.0 Safari/537.36 Edg/144.0.0.0", _ - "", "--disable-gpu, --mute-audio") + "", "--disable-gpu --mute-audio") If @error Then Return SetError(@error, @extended, $oWebV2M) ; Initialize JavaScript Bridge diff --git a/examples/019-mdMsgBox.au3 b/examples/019-mdMsgBox.au3 index 9d24c9e..12047ce 100644 --- a/examples/019-mdMsgBox.au3 +++ b/examples/019-mdMsgBox.au3 @@ -129,6 +129,18 @@ Func _CmdLine_Parsing() $g_sFile = StringRegExpReplace($g_sFile, '^["'']|["'']$', '') EndSelect Next + Else + ; === Testing === + $g_sTitle = "Markdown MsgBox" + $g_sText = "" & _ + "# 🎯 Make your Choice" & @CRLF & _ + "This is a **Modern UI** message box." & @CRLF & _ + "* 1️⃣ **Engine:** WebView2" & @CRLF & _ + "* 2️⃣ **Parser:** Marked.js" & @CRLF & _ + "* 3️⃣ **Logic:** AutoIt Bridge" + $g_sButtons = "1|2|3|~CANCEL" + $g_aBtn = StringSplit($g_sButtons, "|", 1) + EndIf EndFunc ;==>_CmdLine_Parsing ;--------------------------------------------------------------------------------------- diff --git a/examples/020-NavigationInterception.au3 b/examples/020-NavigationInterception.au3 index 3eaebac..8e814b4 100644 --- a/examples/020-NavigationInterception.au3 +++ b/examples/020-NavigationInterception.au3 @@ -3,7 +3,7 @@ #include #include "..\NetWebView2Lib.au3" -;~ $_g_bNetWebView2_DebugInfo = False +$_g_bNetWebView2_DebugInfo = False ConsoleWrite("! MicrosoftEdgeWebview2 : version check: " & _NetWebView2_IsAlreadyInstalled() & ' ERR=' & @error & ' EXT=' & @extended & @CRLF) @@ -28,6 +28,9 @@ Func _MainGUI() _NetWebView2_Initialize($oWebV2M, $hGUI, @ScriptDir & "\NetWebView2Lib-UserDataFolder", 0, 0, 0, 0, True, True, 1, "0x2B2B2B", False) + Local $sAssetsFolder = @ScriptDir & "\MappedFolder" ; + _NetWebView2_SetVirtualHostNameToFolderMapping($oWebV2M, "local.page", $sAssetsFolder, 0) + Local $sHtml = '