147 lines
4.3 KiB
Rust
147 lines
4.3 KiB
Rust
use std::cell::RefCell;
|
|
use std::error::Error;
|
|
use std::rc::Rc;
|
|
|
|
use crate::core::app::context::WindowContext;
|
|
use crate::core::render::primitives::vulkan_resource::{
|
|
VulkanCommandBufferAllocator, VulkanComputeQueue, VulkanDescriptorSetAllocator, VulkanDevice,
|
|
VulkanGraphicsQueue, VulkanInstance, VulkanMemoryAllocator, VulkanTransferQueue,
|
|
};
|
|
use bevy_ecs::world::World;
|
|
|
|
use super::{AsScene, Scene};
|
|
|
|
pub struct SceneManager {
|
|
scenes: Vec<Scene>,
|
|
current_scene_index: Option<usize>,
|
|
window_context: Option<Rc<RefCell<WindowContext>>>,
|
|
}
|
|
|
|
impl SceneManager {
|
|
pub fn new() -> Self {
|
|
Self {
|
|
scenes: Vec::new(),
|
|
current_scene_index: None,
|
|
window_context: None,
|
|
}
|
|
}
|
|
|
|
pub fn set_window_context(&mut self, window_context: Rc<RefCell<WindowContext>>) {
|
|
self.window_context = Some(window_context);
|
|
}
|
|
|
|
fn create_world_with_resources(window_context: &WindowContext) -> World {
|
|
let mut world = World::new();
|
|
|
|
// Add Vulkan resources
|
|
world.insert_resource(VulkanInstance(
|
|
window_context
|
|
.vulkan_context()
|
|
.vulkano_context()
|
|
.instance()
|
|
.clone(),
|
|
));
|
|
world.insert_resource(VulkanDevice(
|
|
window_context
|
|
.vulkan_context()
|
|
.vulkano_context()
|
|
.device()
|
|
.clone(),
|
|
));
|
|
world.insert_resource(VulkanGraphicsQueue(
|
|
window_context
|
|
.vulkan_context()
|
|
.vulkano_context()
|
|
.graphics_queue()
|
|
.clone(),
|
|
));
|
|
world.insert_resource(VulkanComputeQueue(
|
|
window_context
|
|
.vulkan_context()
|
|
.vulkano_context()
|
|
.compute_queue()
|
|
.clone(),
|
|
));
|
|
world.insert_resource(VulkanTransferQueue(
|
|
window_context
|
|
.vulkan_context()
|
|
.vulkano_context()
|
|
.transfer_queue()
|
|
.cloned(),
|
|
));
|
|
world.insert_resource(VulkanMemoryAllocator(
|
|
window_context
|
|
.vulkan_context()
|
|
.vulkano_context()
|
|
.memory_allocator()
|
|
.clone(),
|
|
));
|
|
world.insert_resource(VulkanCommandBufferAllocator(
|
|
window_context
|
|
.vulkan_context()
|
|
.command_buffer_allocator()
|
|
.clone(),
|
|
));
|
|
world.insert_resource(VulkanDescriptorSetAllocator(
|
|
window_context
|
|
.vulkan_context()
|
|
.descriptor_set_allocator()
|
|
.clone(),
|
|
));
|
|
|
|
world
|
|
}
|
|
|
|
pub fn load_scene(&mut self, scene_impl: Box<dyn AsScene>, window_context: &WindowContext) {
|
|
let world = Self::create_world_with_resources(window_context);
|
|
let scene = Scene::new(scene_impl, world);
|
|
self.scenes.push(scene);
|
|
self.current_scene_index = Some(self.scenes.len() - 1);
|
|
}
|
|
|
|
pub fn replace_current_scene(
|
|
&mut self,
|
|
scene_impl: Box<dyn AsScene>,
|
|
window_context: &WindowContext,
|
|
) {
|
|
if let Some(index) = self.current_scene_index {
|
|
if index < self.scenes.len() {
|
|
self.scenes[index].unload();
|
|
let world = Self::create_world_with_resources(window_context);
|
|
self.scenes[index] = Scene::new(scene_impl, world);
|
|
}
|
|
} else {
|
|
self.load_scene(scene_impl, window_context);
|
|
}
|
|
}
|
|
|
|
pub fn current_scene(&self) -> Option<&Scene> {
|
|
if let Some(index) = self.current_scene_index {
|
|
self.scenes.get(index)
|
|
} else {
|
|
None
|
|
}
|
|
}
|
|
|
|
pub fn current_scene_mut(&mut self) -> Option<&mut Scene> {
|
|
if let Some(index) = self.current_scene_index {
|
|
self.scenes.get_mut(index)
|
|
} else {
|
|
None
|
|
}
|
|
}
|
|
|
|
pub fn load_scene_if_not_loaded(
|
|
&mut self,
|
|
window_context: &mut WindowContext,
|
|
) -> Result<(), Box<dyn Error>> {
|
|
if let Some(scene) = self.current_scene_mut() {
|
|
if !scene.loaded() {
|
|
scene.load(window_context)?;
|
|
}
|
|
} else {
|
|
tracing::warn!("No scene found in SceneManager!");
|
|
}
|
|
Ok(())
|
|
}
|
|
}
|