You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Blazor WASM中路由切换后Rive动画卡顿问题求助

问题:Blazor WASM中反复切换页面后Rive动画卡顿、内存泄漏

我基于Blazor WASM基础模板开发,在首页("/")展示Rive动画。反复切换到Counter页("/counter")再返回首页约20次后,动画出现严重卡顿;切换27次后,甚至需要20秒才能渲染动画。同时CPU占用上升12%,内存占用增加120MB。通过开发者工具排查发现内存占用主要来自Rive库,我已尝试实现Dispose逻辑(代码如下),想确认是代码实现有误,还是需要向Rive仓库或ASP.NET提交新issue?

相关代码

Index.razor

@page "/"
@inject IJSRuntime JSRuntime
@implements IAsyncDisposable

<canvas id="canvas" width="500" height="500"></canvas>

@code {
    IJSObjectReference? rivWrapper;

    protected override async Task OnAfterRenderAsync(bool firstRender)
    {
        if (firstRender)
        {
            rivWrapper = await JSRuntime.InvokeAsync<IJSObjectReference>("import", "./Pages/Index.razor.js");
            await rivWrapper.InvokeVoidAsync("createRive");
        }
    }

    public async ValueTask DisposeAsync()
    {
        await rivWrapper!.DisposeAsync();
    }
}

Index.razor.js

export function createRive() {
    const r = new rive.Rive({
        src: 'bear.riv',
        canvas: document.getElementById('canvas'),
        autoplay: true,
    });
}

index.html代码片段

<script src="https://unpkg.com/@rive-app/canvas@1.0.97"></script>

问题分析与结论

你的代码存在资源未正确清理的问题,并非框架或库的原生bug:

  1. Rive实例未销毁:当前代码只Dispose了JS模块引用,但每次创建的rive.Rive实例没有被销毁。Rive动画会持续占用CPU和内存资源,即使组件已被卸载,这些实例仍在后台运行,导致内存泄漏。
  2. 模块引用Dispose的局限性:IJSObjectReference.DisposeAsync()仅清理Blazor与JS模块的绑定关系,不会自动销毁JS内部创建的Rive实例。

修复方案

修改JS代码,保存Rive实例引用,并添加销毁方法;在Blazor组件的Dispose逻辑中调用该方法:

修改后的Index.razor.js

let riveInstance = null;

export function createRive() {
    riveInstance = new rive.Rive({
        src: 'bear.riv',
        canvas: document.getElementById('canvas'),
        autoplay: true,
    });
}

export function destroyRive() {
    if (riveInstance) {
        riveInstance.stop(); // 停止动画
        riveInstance.dispose(); // 销毁实例释放资源
        riveInstance = null;
    }
}

修改后的Index.razor的Dispose逻辑

public async ValueTask DisposeAsync()
{
    if (rivWrapper != null)
    {
        await rivWrapper.InvokeVoidAsync("destroyRive");
        await rivWrapper.DisposeAsync();
    }
}

验证建议

修复后反复切换页面,通过浏览器开发者工具的内存面板查看内存占用变化:如果切换后内存能稳定回落,说明泄漏问题已解决。若问题仍存在,再考虑向Rive仓库提交issue(需附带复现步骤和内存快照)。

内容的提问来源于stack exchange,提问作者Laftek

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.04 04:25:16