【问题标题】:Blazor JSInvokable without static function没有静态函数的 Blazor JSInvokable
【发布时间】:2022-11-07 21:26:54
【问题描述】:
我的 Blazor 组件带有一些 JavaScript 代码。当 JavaScript 代码检测到点击时,我想在 Blazor 组件中调用 JSInvokable 函数来更新 UI。
所以,我创建了一个这样的函数
[JSInvokable]
public static async Task ChangeTab(string val)
{
Console.WriteLine(val);
}
在JavaScript 中,我添加了以下行:
DotNet.invokeMethodAsync('myComponent', 'ChangeTab', tabText);
此代码正在运行,函数ChangeTab 接收到我期望的值。问题是这个函数是static。所以,我不能改变变量。我试图改变这样的代码(激活页面是组件中的一个函数)
[JSInvokable("ChangeTab")]
public async Task ChangeTab(string val)
{
ActivatePage(val);
}
但在这种情况下,我收到一个错误,因为该函数不是静态的。
错误:System.ArgumentException:程序集“PSC.Blazor.Components.ScrollTabs”不包含具有 [JSInvokableAttribute("ChangeTab")] 的公共可调用方法
我检查了Microsoft documentation,但我不明白如何将JSInvokable 函数更改为不是static。
【问题讨论】:
标签:
javascript
blazor
blazor-webassembly
blazor-component
【解决方案1】:
您可以执行以下操作:
MyComponent.razor
@code {
DotNetObjectReference<MyComponent> _componentReference => DotNetObjectReference.Create(this); //Create an object reference for JS
protected override async Task OnAfterRenderAsync(bool firstRender)
{
await JsRuntime.InvokeVoidAsync("MyJS.CacheMyComponent", _componentReference); //Send object reference to JS to cache
}
[JSInvokable("ChangeTab")]
public async Task ChangeTab(string val)
{
//do something
}
}
JavaScript
window.MyJS = {
MyComponentReference: null,
CacheMyComponent: function (componentReference) {
MyJS.MyComponentReference = componentReference; //Cache
},
ChangeTabOnMyComponent: function (tabText) {
MyJS.MyComponentReference.invokeMethodAsync('ChangeTab', tabText); //Use cached reference
}
}
【解决方案2】:
您需要将组件的 DotNetObjectReference 传递给 JavaScript。这通常在组件渲染后完成。
Example.razor:
@implements IDisposable
@inject IJSRuntime JS
@code {
private DotNetObjectReference<Example>? dotNetHelper;
protected override async Task OnAfterRenderAsync(bool firstRender)
{
if (firstRender)
{
dotNetHelper = DotNetObjectReference.Create(this);
await JS.InvokeVoidAsync("Helpers.setDotNetHelper", dotNetHelper);
}
}
[JSInvokable("ChangeTab")]
public async Task ChangeTab(string val)
{
ActivatePage(val);
}
public void Dispose()
{
dotNetHelper?.Dispose();
}
}
然后使用该引用从 JavaScript 调用您的组件方法:
<script>
class Helpers {
static dotNetHelper;
static setDotNetHelper(value) {
Helpers.dotNetHelper = value;
}
static async changeTab(tabText) {
await Helpers.dotNetHelper.invokeMethodAsync('ChangeTab', tabText);
}
}
window.GreetingHelpers = GreetingHelpers;
</script>
Documentation