Skip to content
Branch: master
Find file Copy path
Find file Copy path
2 contributors

Users who have contributed to this file

@sunreef @marot
100 lines (89 sloc) 3.65 KB
use std::collections::HashMap;
use std::fs::read_dir;
use amethyst::{
assets::{AssetStorage, Handle, Prefab, PrefabLoader, ProgressCounter, RonFormat},
use crate::components::creatures::CreaturePrefabData;
pub struct CreaturePrefabs {
prefabs: HashMap<String, Handle<Prefab<CreaturePrefabData>>>,
impl CreaturePrefabs {
pub fn insert(
&mut self,
creature_type: String,
prefab_handle: Handle<Prefab<CreaturePrefabData>>,
) {
self.prefabs.insert(creature_type, prefab_handle);
pub fn get_prefab(&self, creature_type: &str) -> Option<&Handle<Prefab<CreaturePrefabData>>> {
pub fn get_prefabs(&self) -> &HashMap<String, Handle<Prefab<CreaturePrefabData>>> {
pub fn set_prefabs(&mut self, prefabs: HashMap<String, Handle<Prefab<CreaturePrefabData>>>) {
self.prefabs = prefabs;
// Here we load all prefabs for the different creatures in the game.
// These prefabs are then stored in a resource of type CreaturePrefabs that is used by the spawner system.
// At initialization time, we put temporary keys for the prefabs since they're not loaded yet.
// When their loading is finished, we read the name of the entity inside to change the keys. This is done in the update_prefabs function.
pub fn initialize_prefabs(world: &mut World) -> ProgressCounter {
let mut creature_prefabs = CreaturePrefabs::default();
let mut progress_counter = ProgressCounter::new();
let prefab_iter = {
let prefab_dir_path = application_root_dir() + "/resources/prefabs/creatures";
let prefab_iter = read_dir(prefab_dir_path).unwrap();|prefab_dir_entry| {
world.exec(|loader: PrefabLoader<'_, CreaturePrefabData>| {
let prefab_path_buf = prefab_dir_entry.unwrap().path();
let prefab_filename = prefab_path_buf.file_name().unwrap();
"prefabs/creatures/".to_string() + prefab_filename.to_str().unwrap(),
&mut progress_counter,
for (count, prefab) in prefab_iter.enumerate() {
creature_prefabs.insert("temp_prefab_".to_string() + &count.to_string(), prefab);
// Once the prefabs are loaded, this function is called to update the ekeys in the CreaturePrefabs struct.
// We use the Named component of the entity to determine which key to use.
pub fn update_prefabs(world: &mut World) {
let updated_prefabs = {
let creature_prefabs = world.read_resource::<CreaturePrefabs>();
let prefabs = creature_prefabs.get_prefabs();
let mut prefab_resource =
let mut new_prefabs = HashMap::new();
for (_key, handle) in prefabs.iter() {
if let Some(prefab) = prefab_resource.get_mut(handle) {
if let Some(prefab_data) = prefab.entity(0) {
let name = prefab_data
new_prefabs.insert(name, handle.clone());
You can’t perform that action at this time.