bevy_asset: Add AssetServerSettings watch_for_changes member (#3643)
# Objective - `asset_server.watch_for_changes().unwrap()` only watches changes for assets loaded **_after_** that call. - Technically, the `hot_asset_reloading` example is racey as the watch on the asset path is set up in an async task scheduled from the asset `load()`, but the filesystem watcher is only constructed in a call that comes **_after_** the call to `load()`. ## Solution - It feels safest to allow enabling watching the filesystem for changes on the asset server from the point of its construction. Therefore, adding such an option to `AssetServerSettings` seemed to be the correct solution. - Fix `hot_asset_reloading` by inserting the `AssetServerSettings` resource with `watch_for_changes: true` instead of calling `asset_server.watch_for_changes().unwrap()`. - Document the shortcomings of `.watch_for_changes()`
This commit is contained in:
parent
ca83e8a6de
commit
e928acb9ff
@ -115,6 +115,8 @@ impl AssetServer {
|
|||||||
loaders.push(Arc::new(loader));
|
loaders.push(Arc::new(loader));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Enable watching of the filesystem for changes, if support is available, starting from after
|
||||||
|
/// the point of calling this function.
|
||||||
pub fn watch_for_changes(&self) -> Result<(), AssetServerError> {
|
pub fn watch_for_changes(&self) -> Result<(), AssetServerError> {
|
||||||
self.server.asset_io.watch_for_changes()?;
|
self.server.asset_io.watch_for_changes()?;
|
||||||
Ok(())
|
Ok(())
|
||||||
@ -622,7 +624,7 @@ mod test {
|
|||||||
handle_to_path: Default::default(),
|
handle_to_path: Default::default(),
|
||||||
asset_lifecycles: Default::default(),
|
asset_lifecycles: Default::default(),
|
||||||
task_pool: Default::default(),
|
task_pool: Default::default(),
|
||||||
asset_io: Box::new(FileAssetIo::new(asset_path)),
|
asset_io: Box::new(FileAssetIo::new(asset_path, false)),
|
||||||
}),
|
}),
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@ -27,12 +27,26 @@ pub struct FileAssetIo {
|
|||||||
}
|
}
|
||||||
|
|
||||||
impl FileAssetIo {
|
impl FileAssetIo {
|
||||||
pub fn new<P: AsRef<Path>>(path: P) -> Self {
|
pub fn new<P: AsRef<Path>>(path: P, watch_for_changes: bool) -> Self {
|
||||||
FileAssetIo {
|
let file_asset_io = FileAssetIo {
|
||||||
#[cfg(feature = "filesystem_watcher")]
|
#[cfg(feature = "filesystem_watcher")]
|
||||||
filesystem_watcher: Default::default(),
|
filesystem_watcher: Default::default(),
|
||||||
root_path: Self::get_root_path().join(path.as_ref()),
|
root_path: Self::get_root_path().join(path.as_ref()),
|
||||||
|
};
|
||||||
|
if watch_for_changes {
|
||||||
|
#[cfg(any(
|
||||||
|
not(feature = "filesystem_watcher"),
|
||||||
|
target_arch = "wasm32",
|
||||||
|
target_os = "android"
|
||||||
|
))]
|
||||||
|
panic!(
|
||||||
|
"Watch for changes requires the filesystem_watcher feature and cannot be used on \
|
||||||
|
wasm32 / android targets"
|
||||||
|
);
|
||||||
|
#[cfg(feature = "filesystem_watcher")]
|
||||||
|
file_asset_io.watch_for_changes().unwrap();
|
||||||
}
|
}
|
||||||
|
file_asset_io
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn get_root_path() -> PathBuf {
|
pub fn get_root_path() -> PathBuf {
|
||||||
|
|||||||
@ -44,12 +44,16 @@ pub struct AssetPlugin;
|
|||||||
|
|
||||||
pub struct AssetServerSettings {
|
pub struct AssetServerSettings {
|
||||||
pub asset_folder: String,
|
pub asset_folder: String,
|
||||||
|
/// Whether to watch for changes in asset files. Requires the `filesystem_watcher` feature,
|
||||||
|
/// and cannot be supported on the wasm32 arch nor android os.
|
||||||
|
pub watch_for_changes: bool,
|
||||||
}
|
}
|
||||||
|
|
||||||
impl Default for AssetServerSettings {
|
impl Default for AssetServerSettings {
|
||||||
fn default() -> Self {
|
fn default() -> Self {
|
||||||
Self {
|
Self {
|
||||||
asset_folder: "assets".to_string(),
|
asset_folder: "assets".to_string(),
|
||||||
|
watch_for_changes: false,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -64,7 +68,7 @@ pub fn create_platform_default_asset_io(app: &mut App) -> Box<dyn AssetIo> {
|
|||||||
.get_resource_or_insert_with(AssetServerSettings::default);
|
.get_resource_or_insert_with(AssetServerSettings::default);
|
||||||
|
|
||||||
#[cfg(all(not(target_arch = "wasm32"), not(target_os = "android")))]
|
#[cfg(all(not(target_arch = "wasm32"), not(target_os = "android")))]
|
||||||
let source = FileAssetIo::new(&settings.asset_folder);
|
let source = FileAssetIo::new(&settings.asset_folder, settings.watch_for_changes);
|
||||||
#[cfg(target_arch = "wasm32")]
|
#[cfg(target_arch = "wasm32")]
|
||||||
let source = WasmAssetIo::new(&settings.asset_folder);
|
let source = WasmAssetIo::new(&settings.asset_folder);
|
||||||
#[cfg(target_os = "android")]
|
#[cfg(target_os = "android")]
|
||||||
|
|||||||
@ -1,10 +1,15 @@
|
|||||||
use bevy::prelude::*;
|
use bevy::{asset::AssetServerSettings, prelude::*};
|
||||||
|
|
||||||
/// Hot reloading allows you to modify assets on disk and they will be "live reloaded" while your
|
/// Hot reloading allows you to modify assets on disk and they will be "live reloaded" while your
|
||||||
/// game is running. This lets you immediately see the results of your changes without restarting
|
/// game is running. This lets you immediately see the results of your changes without restarting
|
||||||
/// the game. This example illustrates hot reloading mesh changes.
|
/// the game. This example illustrates hot reloading mesh changes.
|
||||||
fn main() {
|
fn main() {
|
||||||
App::new()
|
App::new()
|
||||||
|
// Tell the asset server to watch for asset changes on disk:
|
||||||
|
.insert_resource(AssetServerSettings {
|
||||||
|
watch_for_changes: true,
|
||||||
|
..Default::default()
|
||||||
|
})
|
||||||
.add_plugins(DefaultPlugins)
|
.add_plugins(DefaultPlugins)
|
||||||
.add_startup_system(setup)
|
.add_startup_system(setup)
|
||||||
.run();
|
.run();
|
||||||
@ -14,9 +19,6 @@ fn setup(mut commands: Commands, asset_server: Res<AssetServer>) {
|
|||||||
// Load our mesh:
|
// Load our mesh:
|
||||||
let scene_handle = asset_server.load("models/monkey/Monkey.gltf#Scene0");
|
let scene_handle = asset_server.load("models/monkey/Monkey.gltf#Scene0");
|
||||||
|
|
||||||
// Tell the asset server to watch for asset changes on disk:
|
|
||||||
asset_server.watch_for_changes().unwrap();
|
|
||||||
|
|
||||||
// Any changes to the mesh will be reloaded automatically! Try making a change to Monkey.gltf.
|
// Any changes to the mesh will be reloaded automatically! Try making a change to Monkey.gltf.
|
||||||
// You should see the changes immediately show up in your app.
|
// You should see the changes immediately show up in your app.
|
||||||
|
|
||||||
|
|||||||
Loading…
Reference in New Issue
Block a user