追踪资源加载

点击这里下载完整示例代码


你如果想使用一个第三方库来做这个功能,请查看我推荐的可以为你做这件事的辅助库。如果不想用第三方库,本页面将告诉你如何自己实现追踪资源加载。


你或许想知道你的各种资源何时完成加载,以便依此采取一些行动,例如退出加载页面并开始游戏。

要做到这一点,我们可以把我们的各种资源句柄转换成 HandleUntyped,这样我们就可以把它们全部加入到一个集合中。

然后我们可以向 AssetServer 询问该集合的加载状态。

struct AssetsLoading(Vec<HandleUntyped>);

fn setup(server: Res<AssetServer>, mut loading: ResMut<AssetsLoading>) {
    // we can have different asset types
    let font: Handle<Font> = server.load("my_font.ttf");
    let menu_bg: Handle<Image> = server.load("menu.png");
    let scene: Handle<Scene> = server.load("level01.gltf#Scene0");

    // add them all to our collection for tracking
    loading.0.push(font.clone_untyped());
    loading.0.push(menu_bg.clone_untyped());
    loading.0.push(scene.clone_untyped());
}

fn check_assets_ready(
    mut commands: Commands,
    server: Res<AssetServer>,
    loading: Res<AssetsLoading>
) {
    use bevy::asset::LoadState;

    match server.get_group_load_state(loading.0.iter().map(|h| h.id)) {
        LoadState::Failed => {
            // one of our assets had an error
        }
        LoadState::Loaded => {
            // all assets are now ready

            // this might be a good place to transition into your in-game state

            // remove the resource to drop the tracking handles
            commands.remove_resource::<AssetsLoading>();
            // (note: if you don't have any other handles to the assets
            // elsewhere, they will get unloaded after this)
        }
        _ => {
            // NotLoaded/Loading: not fully ready yet
        }
    }
}

也可以通过向 AssetServer.get_load_state() 传递单个句柄来查询单个资源的加载状态。