CoreWebView2.AddHostObjectToScript throws System.Exception: 'The group or resource is not in the correct state to perform the requested operation.' Version SDK: 1.0.1245.22 latest stable - (and Microsoft.UI.Xaml 2.8.0-prerelease.210927001) Runtime: Framework: UWP OS: Windows 11, build 22000
Reproduce Steps
Example of HostObject class:
[AllowForWeb]
[ClassInterface(ClassInterfaceType.AutoDual)]
[ComVisible(true)]
public class JsCallbacksUwp
{
public JsCallbacksUwp()
{
}
}
Example code for Navigation Completed that throws the exception:
private async void WebView2_NavigationCompleted(WebView2 sender, CoreWebView2NavigationCompletedEventArgs args)
{
await sender.EnsureCoreWebView2Async();
var browserHostObject = new JSCallbacksUwp();
sender.CoreWebView2.AddHostObjectToScript("HostObject", browserHostObject);
}
I got my answer from github's community at WebView2 Feedback.
Firstly i followed the guide that Syul968 showed me there which was:
The WinRT CoreWebView2 class (the one used by WinUI) tries to automatically create a "wrapper" when this is the case, but it needs a DispatchAdapter instance to be set through CoreWebView2Settings.HostObjectDispatchAdapter. We have also been working on this feature lately. Our latest pre-release package (1.0.1248-prerelease) includes a tool, wv2winrt, to help project new and existing WinRT components: Call native-side WinRT code from web-side code
Secondly i followed the steps from david-risney answer:
Our current documentation only shows you how to do it for OS provided WinRT APIs and not for your own WinRT APIs. We need to fix this. Until then I would recommend following the existing directions from Call native-side WinRT code from web-side code, and then additionally doing the following:
- Add a third project to your VS solution that implements your winrt class.
- Have the WinRTAdapter project 'Add a reference' to your new third project containing your winrt class.
- Update the WinRTAdapter project's Include filter to also include your new class.
- Add an additional line to InitializeWebView2Async to add your winrt class's namespace WebView2.CoreWebView2.AddHostObjectToScript("MyCustomNamespace", dispatchAdapter.WrapNamedObject("MyCustomNamespace", dispatchAdapter));
- And optionally add your namespace sync proxy as a global object in script window.MyCustomNamespace = chrome.webview.hostObjects.sync.MyCustomNamespace; You should then be able to use your type via script.
Lastly you can check my changes to my example.