Skip to main content

dear_implot3d/
mesh_builder.rs

1use std::borrow::Cow;
2
3use crate::item_style::{Plot3DItemStyle, plot3d_spec_with_style};
4use crate::{
5    Item3DFlags, Mesh3DFlags, Plot3DDataLayout, Plot3DUi, debug_before_plot, len_i32, sys,
6};
7
8/// Mesh plot builder
9pub struct Mesh3DBuilder<'ui> {
10    pub(crate) _ui: &'ui Plot3DUi<'ui>,
11    pub(crate) label: Cow<'ui, str>,
12    pub(crate) vertices: &'ui [[f32; 3]],
13    pub(crate) indices: &'ui [u32],
14    pub(crate) flags: Mesh3DFlags,
15    pub(crate) item_flags: Item3DFlags,
16    pub(crate) style: Plot3DItemStyle,
17}
18
19impl<'ui> Mesh3DBuilder<'ui> {
20    pub fn flags(mut self, flags: Mesh3DFlags) -> Self {
21        self.flags = flags;
22        self
23    }
24    pub fn plot(self) {
25        let _guard = self._ui.bind();
26        let Some(vtx_count) = len_i32(self.vertices.len()) else {
27            return;
28        };
29        let Some(idx_count) = len_i32(self.indices.len()) else {
30            return;
31        };
32        let mut xs = Vec::with_capacity(self.vertices.len());
33        let mut ys = Vec::with_capacity(self.vertices.len());
34        let mut zs = Vec::with_capacity(self.vertices.len());
35        for [x, y, z] in self.vertices.iter().copied() {
36            xs.push(x);
37            ys.push(y);
38            zs.push(z);
39        }
40
41        let label = self.label.as_ref();
42        let label = if label.contains('\0') { "mesh" } else { label };
43        dear_imgui_rs::with_scratch_txt(label, |label_ptr| unsafe {
44            debug_before_plot();
45            let spec = plot3d_spec_with_style(
46                self.style,
47                self.flags.bits() | self.item_flags.bits(),
48                Plot3DDataLayout::DEFAULT,
49            );
50            sys::ImPlot3D_PlotMesh_FloatPtr(
51                label_ptr,
52                xs.as_ptr(),
53                ys.as_ptr(),
54                zs.as_ptr(),
55                self.indices.as_ptr(),
56                vtx_count,
57                idx_count,
58                spec,
59            );
60        })
61    }
62}
63
64impl<'ui> Plot3DUi<'ui> {
65    /// Start a mesh plot from vertices (x,y,z) and triangle indices
66    pub fn mesh(
67        &'ui self,
68        label: impl Into<Cow<'ui, str>>,
69        vertices: &'ui [[f32; 3]],
70        indices: &'ui [u32],
71    ) -> Mesh3DBuilder<'ui> {
72        let _guard = self.bind();
73        Mesh3DBuilder {
74            _ui: self,
75            label: label.into(),
76            vertices,
77            indices,
78            flags: Mesh3DFlags::NONE,
79            item_flags: Item3DFlags::NONE,
80            style: Plot3DItemStyle::default(),
81        }
82    }
83}