-
Notifications
You must be signed in to change notification settings - Fork 25
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Access to world in on_load_prototype? #63
Comments
Just another user here chiming in. Not sure if I understand you 100%, but couldn't this be addressed by having a separate "boolean if toggle" for the load functions? pseudo code (haven't tested):
One thing to be extra careful of, is that the prototype has some delay in loading the ron files, so need to ensure to use prototype.is_ready before using them. You might also have the toggle to be specific for each mod rather one big toggle. Hopefully this helps. |
Thanks for the answer, but I think this is not what I'm trying to achieve! My main goal is, that I can define a schedule (a state transition) on which the mod should be spawned on, not loaded. Currently my prototype file looks something like this: (
name: "UiManager2",
schematics: {
"pgc::states::SpawnOnSchedule": (
OnEnter(
Loading(
PreMainMenu
)
),
false
),
"pgc::states::DespawnOnSchedule": (
OnExit(
Menu(
MainMenu
)
),
true
),
}
)
pub struct SpawnOnSchedule(pub AllStatesScheduleHandler, pub bool);
impl Schematic for SpawnOnSchedule {
type Input = Self;
fn apply(_input: &Self::Input, _context: &mut SchematicContext) {}
fn remove(_input: &Self::Input, _context: &mut SchematicContext) {}
} So my current Idea is to use the on_load_prototype function of my custom Loader, because it seems to be the perfect place to do this. if let Some(spawn_on_schedule) = prototype.schematics().get::<SpawnOnSchedule>() {
let spawn_on_schedule = spawn_on_schedule
.input()
.downcast_ref::<SpawnOnSchedule>()
.unwrap();
} And then all I need to do would be get a specific resource and insert the schedule and the Name of the prototype, so that the rest of my bevy backend can handle the spawning at said state transition. That would be the easiest, probably. But thanks to your comment I got another Idea, which will probably work, but seems like more work. I now got following solution, that works: fn load(
mut prototypes: PrototypesMut,
asset_server: Res<AssetServer>,
prototype_assets: Res<Assets<Prototype>>,
mut mods_loading: Local<Vec<Handle<Prototype>>>,
mut mods_started_loading: Local<bool>,
mut spawn_on_schedule: ResMut<ModsToSpawnOnSchedule>,
) {
if !*mods_started_loading {
let paths = vec!["examples/custom_loader/Player.mod.ron"];
for path in paths {
// keep a reference to all mods that are loading
mods_loading.push(prototypes.load(path));
}
*mods_started_loading = true;
} else {
// go through all loaded mods, check which ones are ready
mods_loading.retain(|mod_handle| match asset_server.get_load_state(mod_handle) {
LoadState::Loading => {
// keep it loading
true
}
LoadState::Loaded => {
// if they're loaded, get the prototype and check if it has a SpawnOnSchedule.
let prototype = prototype_assets.get(mod_handle).unwrap();
if let Some(spawn_schedule) = prototype.schematics().get::<SpawnOnSchedule>() {
let spawn_schedule = spawn_schedule
.input()
.downcast_ref::<SpawnOnSchedule>()
.unwrap();
// if it does, put it in the resource for later use
if let Some(mods) = spawn_on_schedule.mods.get_mut(&spawn_schedule.0) {
mods.push((prototype.id().clone(), spawn_schedule.1));
} else {
spawn_on_schedule.mods.insert(
spawn_schedule.0.clone(),
vec![(prototype.id().clone(), spawn_schedule.1)],
);
}
}
// remove it from the local list
false
}
LoadState::Failed => {
// remove the mod from the list (also notify about error somehow)
false
}
LoadState::NotLoaded => todo!(),
LoadState::Unloaded => todo!(),
});
}
if mods_loading.is_empty() {
// done loading (or there was nothing to load), next state
}
} |
Awesome work and thanks for sharing. Happy to trigger some ideas. I myself often stuck when doing solo dev. |
Hi, I have following scenario.
I'm working on adding mod support to my game, and I want to be able to define Mods via .ron files that then are interpreted by the game into entities. And with this crate that works great!
I encountered one problem though, I want the user to have control over when the mod will be spawned. For example, a UI Manager that will be spawned once the MainMenu is ready.
For this I've created an Enum that defines in what schedule it should be spawned. The only problem, for this to work, I need to register the name of the Prototype in a Bevy resource.
But in the on_load_prototype of a custom loader, as far as I can see, i don't have any way to do so?
Something like that, is there maybe a possible workaround?
The text was updated successfully, but these errors were encountered: