use crate::render_features::render_features_prelude::*;
use crate::render_features::{BeginSubmitNodeBatchArgs, RenderSubmitNodeArgs};
use fnv::FnvHashMap;
use rafx_api::RafxResult;
use std::sync::Arc;
pub type RenderViewSubmitNodeCount = FnvHashMap<RenderViewIndex, Vec<usize>>;
pub type SubmitNodeBlocks = FnvHashMap<ViewPhase, ViewPhaseSubmitNodeBlock>;
pub struct PreparedRenderData<'write> {
submit_node_blocks: &'write SubmitNodeBlocks,
write_jobs: Vec<Option<Arc<dyn RenderFeatureWriteJob<'write> + 'write>>>,
}
impl<'write> PreparedRenderData<'write> {
pub fn new(
submit_node_blocks: &'write SubmitNodeBlocks,
write_jobs: Vec<Option<Arc<dyn RenderFeatureWriteJob<'write> + 'write>>>,
) -> Self {
Self {
submit_node_blocks,
write_jobs,
}
}
pub fn on_begin_execute_graph(
&self,
write_context: &mut RenderJobBeginExecuteGraphContext,
) -> RafxResult<()> {
for writer in &self.write_jobs {
if let Some(writer) = writer {
writer.on_begin_execute_graph(write_context)?;
}
}
Ok(())
}
pub fn write_view_phase<PhaseT: RenderPhase>(
&self,
view: &RenderView,
write_context: &mut RenderJobCommandBufferContext,
) -> RafxResult<()> {
profiling::scope!({
use rafx_base::memory::force_to_static_lifetime;
unsafe { force_to_static_lifetime(view).debug_name() }
});
let render_phase_index = PhaseT::render_phase_index();
let view_phase = ViewPhase {
view_index: view.view_index(),
phase_index: render_phase_index,
};
let submit_node_block = self.submit_node_blocks.get(&view_phase);
let submit_nodes: &[RenderFeatureSubmitNode] =
if let Some(submit_node_block) = submit_node_block {
submit_node_block.submit_nodes()
} else {
&[]
};
let mut previous_node_feature_index: Option<RenderFeatureIndex> = None;
let mut previous_node_sort_key: Option<SubmitNodeSortKey> = None;
let mut view_frame_index: Option<ViewFrameIndex> = None;
for submit_node in submit_nodes {
let feature_index = submit_node.feature_index();
let sort_key = submit_node.sort_key();
let feature_changed = Some(feature_index) != previous_node_feature_index;
let sort_key_changed = Some(sort_key) != previous_node_sort_key;
if feature_changed {
view_frame_index = Some(view.view_frame_index(feature_index).unwrap());
}
if feature_changed || sort_key_changed {
self.write_jobs[submit_node.feature_index() as usize]
.as_ref()
.unwrap()
.begin_submit_node_batch(
write_context,
BeginSubmitNodeBatchArgs {
view_frame_index: view_frame_index.unwrap(),
render_phase_index,
feature_changed,
sort_key: submit_node.sort_key(),
},
)?;
}
log::trace!(
"draw render node feature: {} node id: {}",
submit_node.feature_index(),
submit_node.submit_node_id(),
);
self.write_jobs[submit_node.feature_index() as usize]
.as_ref()
.unwrap()
.render_submit_node(
write_context,
RenderSubmitNodeArgs {
view_frame_index: view_frame_index.unwrap(),
render_phase_index,
submit_node_id: submit_node.submit_node_id(),
},
)?;
previous_node_feature_index = Some(feature_index);
previous_node_sort_key = Some(sort_key);
}
Ok(())
}
}