Search code examples
c#blazor-client-sideblazor-webassembly

Blazor WebAssembly: send Float32Array from javascript to .NET


This is my JS:

window.testSendFloatArray = (obj) => {

    var iterable = function* () { yield* [1, 2, 3, 4, 5, 6]; }();
    var float32 = new Float32Array(iterable); 

    obj.invokeMethodAsync('SendFloatArray', float32);
}

This is the C#:

[JSInvokable]
public Task SendFloatArray(JsonElement wtf)
{
    return Task.CompletedTask;
}

And this is how I call testSendFloatArray from C#:

await JSRuntime.InvokeVoidAsync("testSendFloatArray", DotNetObjectReference.Create(this));

I set breakpoints everywhere and everything is wired up properly, but when the SendFloatArray gets called, I have no idea what to do with wtf. The only reason I know it's a JsonElement is because I originally had it is type object and did a wtf.GetType().Name on it.

When I serialize the value with JsonSerializer.Serialize(wtf) it returns this:

{"0":1,"1":2,"2":3,"3":4,"4":5,"5":6}

After an hour of playing with it, I figured out I could call EnumerateObject (EnumerateArray failed) on it:

[JSInvokable]
public Task SendFloatArray(JsonElement wtf)
{
    var myArray = wtf.EnumerateObject().Select(x => x.Value.GetDouble()).ToArray();

    return Task.CompletedTask;
}

But there must be a better way to do this, correct? How do I cleanly get an array of primitives to a C# assembly from Javascript?


Solution

  • This has been rectified in recent versions of Blazor. You can just set it to a float[] type and it just works.

    [JSInvokable]
    public Task SendFloatArray(float[] floatArray)
    {
        return Task.CompletedTask;
    }