c# 编写 WebAssembly

发布时间 2023-06-12 15:30:17作者: IWing

创建一个.net 7.0类库工程,引用下面的nuget包:

    <PackageReference Include="Microsoft.AspNetCore.Components.WebAssembly" Version="7.0.5" />
    <PackageReference Include="Microsoft.AspNetCore.Components.WebAssembly.DevServer" Version="7.0.5" />

然后把Project sdk改成这样:

<Project Sdk="Microsoft.NET.Sdk.BlazorWebAssembly">

然后c#代码可以这样写:

using Microsoft.AspNetCore.Components.WebAssembly.Hosting;
using Microsoft.JSInterop;

namespace WebAssemblyTest
{
    public class Program
    {
        private static IJSRuntime js;
        private static async Task Main(string[] args)
        {
            var builder = WebAssemblyHostBuilder.CreateDefault(args);
            var host = builder.Build();
            js = host.Services.GetRequiredService<IJSRuntime>();
            RunInSeconds();
            await host.RunAsync();
        }

        static async void RunInSeconds()
        {
            while (true)
            {
                await Task.Delay(2000);
                //调用javascript里面的test方法
                await js.InvokeVoidAsync("test", new byte[] { 0x1, 0x2 });
            }
        }

        /// <summary>
        /// 给js调用的函数
        /// </summary>
        /// <param name="i"></param>
        /// <param name="j"></param>
        /// <returns></returns>
        [JSInvokable]
        public static byte[] Add(int i, int j)
        {
            return new byte[] { (byte)i,(byte)j};
        }
    }
}

js代码这样写:

<html lang="en">
<head>
    <meta charset="UTF-8" />
</head>
<body>
</body>
<script src="_framework/blazor.webassembly.js" autostart="false"></script>
<script>
    function test(r) {
        console.log(r);
        alert(r);
    }
    window.onload = async function () {
        await Blazor.start();
        const r = await DotNet.invokeMethodAsync(
            'WebAssemblyTest',//程序集的名字
            'Add',//要调用的标注了[JSInvokable]方法的名字
            666,//若干参数
            333
        );
        console.log(r);
    };
</script>
</html>

注意编译生成的_framework文件夹必须放在web服务器,并且设置mimeType以便前端可以顺利下载

var provider = new FileExtensionContentTypeProvider();
provider.Mappings[".dll"] = "application/octet-stream";//配置添加新的映射关系
provider.Mappings[".gz"] = "application/octet-stream";
provider.Mappings[".dat"] = "application/octet-stream";
provider.Mappings[".blat"] = "application/octet-stream";
provider.Mappings[".pdb"] = "application/octet-stream";
app.UseStaticFiles(new StaticFileOptions
{
    ContentTypeProvider = provider,//应用新的映射关系
});