use rafx::render_feature_prepare_job_predule::*;
use super::*;
use crate::phases::UiRenderPhase;
use crate::shaders::egui::{egui_frag, egui_vert};
use rafx::api::RafxBufferDef;
use rafx::base::resource_map::WriteBorrow;
pub struct EguiPrepareJob<'prepare> {
font_atlas_cache: TrustCell<WriteBorrow<'prepare, EguiFontAtlasCache>>,
}
impl<'prepare> EguiPrepareJob<'prepare> {
pub fn new(
prepare_context: &RenderJobPrepareContext<'prepare>,
frame_packet: Box<EguiFramePacket>,
submit_packet: Box<EguiSubmitPacket>,
) -> Arc<dyn RenderFeaturePrepareJob<'prepare> + 'prepare> {
Arc::new(PrepareJob::new(
Self {
font_atlas_cache: TrustCell::new(
prepare_context
.render_resources
.fetch_mut::<EguiFontAtlasCache>(),
),
},
prepare_context,
frame_packet,
submit_packet,
))
}
}
impl<'prepare> PrepareJobEntryPoints<'prepare> for EguiPrepareJob<'prepare> {
fn begin_per_frame_prepare(
&self,
context: &PreparePerFrameContext<'prepare, '_, Self>,
) {
let per_frame_data = context.per_frame_data();
let mut per_frame_submit_data = EguiPerFrameSubmitData::default();
let dyn_resource_allocator_set = context
.resource_context()
.create_dyn_resource_allocator_set();
let descriptor_set_layouts = &per_frame_data
.egui_material_pass
.as_ref()
.unwrap()
.get_raw()
.descriptor_set_layouts;
let mut descriptor_set_allocator =
context.resource_context().create_descriptor_set_allocator();
let mut font_atlas_cache = self.font_atlas_cache.borrow_mut();
per_frame_submit_data.per_view_descriptor_set = descriptor_set_allocator
.create_descriptor_set_with_writer(
&descriptor_set_layouts[egui_vert::UNIFORM_BUFFER_DESCRIPTOR_SET_INDEX],
egui_vert::DescriptorSet0Args {
uniform_buffer: &per_frame_data.view_ubo,
},
)
.ok();
if let Some(draw_data) = &per_frame_data.egui_draw_data {
let vertex_buffer = context
.device_context()
.create_buffer(&RafxBufferDef::for_staging_vertex_buffer_data(
&draw_data.vertices,
))
.unwrap();
vertex_buffer
.copy_to_host_visible_buffer(&draw_data.vertices)
.unwrap();
let vertex_buffer = dyn_resource_allocator_set.insert_buffer(vertex_buffer);
per_frame_submit_data.vertex_buffer = Some(vertex_buffer);
let index_buffer = context
.device_context()
.create_buffer(&RafxBufferDef::for_staging_index_buffer_data(
&draw_data.indices,
))
.unwrap();
index_buffer
.copy_to_host_visible_buffer(&draw_data.indices)
.unwrap();
let index_buffer = dyn_resource_allocator_set.insert_buffer(index_buffer);
per_frame_submit_data.index_buffer = Some(index_buffer);
per_frame_submit_data.image_update = font_atlas_cache
.update(&dyn_resource_allocator_set, &draw_data.font_atlas)
.unwrap();
}
if let Some(font_atlas_resource) = font_atlas_cache.font_atlas_resource().as_ref() {
per_frame_submit_data.per_font_descriptor_set = descriptor_set_allocator
.create_descriptor_set_with_writer(
&descriptor_set_layouts[egui_frag::TEX_DESCRIPTOR_SET_INDEX],
egui_frag::DescriptorSet1Args {
tex: font_atlas_resource,
},
)
.ok();
}
context
.submit_packet()
.per_frame_submit_data()
.set(per_frame_submit_data);
}
fn end_per_view_prepare(
&self,
context: &PreparePerViewContext<'prepare, '_, Self>,
) {
let per_frame_data = context.per_frame_data();
if per_frame_data.egui_draw_data.is_none() || per_frame_data.egui_material_pass.is_none() {
return;
}
context
.view_submit_packet()
.push_submit_node::<UiRenderPhase>((), 0, 0.);
}
fn feature_debug_constants(&self) -> &'static RenderFeatureDebugConstants {
super::render_feature_debug_constants()
}
fn feature_index(&self) -> RenderFeatureIndex {
super::render_feature_index()
}
type RenderObjectInstanceJobContextT = DefaultJobContext;
type RenderObjectInstancePerViewJobContextT = DefaultJobContext;
type FramePacketDataT = EguiRenderFeatureTypes;
type SubmitPacketDataT = EguiRenderFeatureTypes;
}