re_types/archetypes/
pinhole.rs

1// DO NOT EDIT! This file was auto-generated by crates/build/re_types_builder/src/codegen/rust/api.rs
2// Based on "crates/store/re_types/definitions/rerun/archetypes/pinhole.fbs".
3
4#![allow(unused_braces)]
5#![allow(unused_imports)]
6#![allow(unused_parens)]
7#![allow(clippy::clone_on_copy)]
8#![allow(clippy::cloned_instead_of_copied)]
9#![allow(clippy::map_flatten)]
10#![allow(clippy::needless_question_mark)]
11#![allow(clippy::new_without_default)]
12#![allow(clippy::redundant_closure)]
13#![allow(clippy::too_many_arguments)]
14#![allow(clippy::too_many_lines)]
15
16use ::re_types_core::try_serialize_field;
17use ::re_types_core::SerializationResult;
18use ::re_types_core::{ComponentBatch as _, SerializedComponentBatch};
19use ::re_types_core::{ComponentDescriptor, ComponentType};
20use ::re_types_core::{DeserializationError, DeserializationResult};
21
22/// **Archetype**: Camera perspective projection (a.k.a. intrinsics).
23///
24/// ⚠️ **This type is _unstable_ and may change significantly in a way that the data won't be backwards compatible.**
25///
26/// ## Examples
27///
28/// ### Simple pinhole camera
29/// ```ignore
30/// use ndarray::{Array, ShapeBuilder as _};
31/// use rand::prelude::*;
32///
33/// fn main() -> Result<(), Box<dyn std::error::Error>> {
34///     let rec = rerun::RecordingStreamBuilder::new("rerun_example_pinhole").spawn()?;
35///
36///     let mut image = Array::<u8, _>::default((3, 3, 3).f());
37///     let mut rng = rand::rngs::SmallRng::seed_from_u64(42);
38///     image.map_inplace(|x| *x = rng.r#gen());
39///
40///     rec.log(
41///         "world/image",
42///         &rerun::Pinhole::from_focal_length_and_resolution([3., 3.], [3., 3.]),
43///     )?;
44///     rec.log(
45///         "world/image",
46///         &rerun::Image::from_color_model_and_tensor(rerun::ColorModel::RGB, image)?,
47///     )?;
48///
49///     Ok(())
50/// }
51/// ```
52/// <center>
53/// <picture>
54///   <source media="(max-width: 480px)" srcset="https://static.rerun.io/pinhole_simple/9af9441a94bcd9fd54e1fea44fb0c59ff381a7f2/480w.png">
55///   <source media="(max-width: 768px)" srcset="https://static.rerun.io/pinhole_simple/9af9441a94bcd9fd54e1fea44fb0c59ff381a7f2/768w.png">
56///   <source media="(max-width: 1024px)" srcset="https://static.rerun.io/pinhole_simple/9af9441a94bcd9fd54e1fea44fb0c59ff381a7f2/1024w.png">
57///   <source media="(max-width: 1200px)" srcset="https://static.rerun.io/pinhole_simple/9af9441a94bcd9fd54e1fea44fb0c59ff381a7f2/1200w.png">
58///   <img src="https://static.rerun.io/pinhole_simple/9af9441a94bcd9fd54e1fea44fb0c59ff381a7f2/full.png" width="640">
59/// </picture>
60/// </center>
61///
62/// ### Perspective pinhole camera
63/// ```ignore
64/// fn main() -> Result<(), Box<dyn std::error::Error>> {
65///     let rec = rerun::RecordingStreamBuilder::new("rerun_example_pinhole_perspective").spawn()?;
66///
67///     let fov_y = std::f32::consts::FRAC_PI_4;
68///     let aspect_ratio = 1.7777778;
69///     rec.log(
70///         "world/cam",
71///         &rerun::Pinhole::from_fov_and_aspect_ratio(fov_y, aspect_ratio)
72///             .with_camera_xyz(rerun::components::ViewCoordinates::RUB)
73///             .with_image_plane_distance(0.1),
74///     )?;
75///
76///     rec.log(
77///         "world/points",
78///         &rerun::Points3D::new([(0.0, 0.0, -0.5), (0.1, 0.1, -0.5), (-0.1, -0.1, -0.5)])
79///             .with_radii([0.025]),
80///     )?;
81///
82///     Ok(())
83/// }
84/// ```
85/// <center>
86/// <picture>
87///   <source media="(max-width: 480px)" srcset="https://static.rerun.io/pinhole_perspective/317e2de6d212b238dcdad5b67037e9e2a2afafa0/480w.png">
88///   <source media="(max-width: 768px)" srcset="https://static.rerun.io/pinhole_perspective/317e2de6d212b238dcdad5b67037e9e2a2afafa0/768w.png">
89///   <source media="(max-width: 1024px)" srcset="https://static.rerun.io/pinhole_perspective/317e2de6d212b238dcdad5b67037e9e2a2afafa0/1024w.png">
90///   <source media="(max-width: 1200px)" srcset="https://static.rerun.io/pinhole_perspective/317e2de6d212b238dcdad5b67037e9e2a2afafa0/1200w.png">
91///   <img src="https://static.rerun.io/pinhole_perspective/317e2de6d212b238dcdad5b67037e9e2a2afafa0/full.png" width="640">
92/// </picture>
93/// </center>
94#[derive(Clone, Debug, PartialEq, Default)]
95pub struct Pinhole {
96    /// Camera projection, from image coordinates to view coordinates.
97    pub image_from_camera: Option<SerializedComponentBatch>,
98
99    /// Pixel resolution (usually integers) of child image space. Width and height.
100    ///
101    /// Example:
102    /// ```text
103    /// [1920.0, 1440.0]
104    /// ```
105    ///
106    /// `image_from_camera` project onto the space spanned by `(0,0)` and `resolution - 1`.
107    pub resolution: Option<SerializedComponentBatch>,
108
109    /// Sets the view coordinates for the camera.
110    ///
111    /// All common values are available as constants on the [`components::ViewCoordinates`][crate::components::ViewCoordinates] class.
112    ///
113    /// The default is `ViewCoordinates::RDF`, i.e. X=Right, Y=Down, Z=Forward, and this is also the recommended setting.
114    /// This means that the camera frustum will point along the positive Z axis of the parent space,
115    /// and the cameras "up" direction will be along the negative Y axis of the parent space.
116    ///
117    /// The camera frustum will point whichever axis is set to `F` (or the opposite of `B`).
118    /// When logging a depth image under this entity, this is the direction the point cloud will be projected.
119    /// With `RDF`, the default forward is +Z.
120    ///
121    /// The frustum's "up" direction will be whichever axis is set to `U` (or the opposite of `D`).
122    /// This will match the negative Y direction of pixel space (all images are assumed to have xyz=RDF).
123    /// With `RDF`, the default is up is -Y.
124    ///
125    /// The frustum's "right" direction will be whichever axis is set to `R` (or the opposite of `L`).
126    /// This will match the positive X direction of pixel space (all images are assumed to have xyz=RDF).
127    /// With `RDF`, the default right is +x.
128    ///
129    /// Other common formats are `RUB` (X=Right, Y=Up, Z=Back) and `FLU` (X=Forward, Y=Left, Z=Up).
130    ///
131    /// NOTE: setting this to something else than `RDF` (the default) will change the orientation of the camera frustum,
132    /// and make the pinhole matrix not match up with the coordinate system of the pinhole entity.
133    ///
134    /// The pinhole matrix (the `image_from_camera` argument) always project along the third (Z) axis,
135    /// but will be re-oriented to project along the forward axis of the `camera_xyz` argument.
136    pub camera_xyz: Option<SerializedComponentBatch>,
137
138    /// The distance from the camera origin to the image plane when the projection is shown in a 3D viewer.
139    ///
140    /// This is only used for visualization purposes, and does not affect the projection itself.
141    pub image_plane_distance: Option<SerializedComponentBatch>,
142}
143
144impl Pinhole {
145    /// Returns the [`ComponentDescriptor`] for [`Self::image_from_camera`].
146    ///
147    /// The corresponding component is [`crate::components::PinholeProjection`].
148    #[inline]
149    pub fn descriptor_image_from_camera() -> ComponentDescriptor {
150        ComponentDescriptor {
151            archetype: Some("rerun.archetypes.Pinhole".into()),
152            component: "Pinhole:image_from_camera".into(),
153            component_type: Some("rerun.components.PinholeProjection".into()),
154        }
155    }
156
157    /// Returns the [`ComponentDescriptor`] for [`Self::resolution`].
158    ///
159    /// The corresponding component is [`crate::components::Resolution`].
160    #[inline]
161    pub fn descriptor_resolution() -> ComponentDescriptor {
162        ComponentDescriptor {
163            archetype: Some("rerun.archetypes.Pinhole".into()),
164            component: "Pinhole:resolution".into(),
165            component_type: Some("rerun.components.Resolution".into()),
166        }
167    }
168
169    /// Returns the [`ComponentDescriptor`] for [`Self::camera_xyz`].
170    ///
171    /// The corresponding component is [`crate::components::ViewCoordinates`].
172    #[inline]
173    pub fn descriptor_camera_xyz() -> ComponentDescriptor {
174        ComponentDescriptor {
175            archetype: Some("rerun.archetypes.Pinhole".into()),
176            component: "Pinhole:camera_xyz".into(),
177            component_type: Some("rerun.components.ViewCoordinates".into()),
178        }
179    }
180
181    /// Returns the [`ComponentDescriptor`] for [`Self::image_plane_distance`].
182    ///
183    /// The corresponding component is [`crate::components::ImagePlaneDistance`].
184    #[inline]
185    pub fn descriptor_image_plane_distance() -> ComponentDescriptor {
186        ComponentDescriptor {
187            archetype: Some("rerun.archetypes.Pinhole".into()),
188            component: "Pinhole:image_plane_distance".into(),
189            component_type: Some("rerun.components.ImagePlaneDistance".into()),
190        }
191    }
192}
193
194static REQUIRED_COMPONENTS: once_cell::sync::Lazy<[ComponentDescriptor; 1usize]> =
195    once_cell::sync::Lazy::new(|| [Pinhole::descriptor_image_from_camera()]);
196
197static RECOMMENDED_COMPONENTS: once_cell::sync::Lazy<[ComponentDescriptor; 1usize]> =
198    once_cell::sync::Lazy::new(|| [Pinhole::descriptor_resolution()]);
199
200static OPTIONAL_COMPONENTS: once_cell::sync::Lazy<[ComponentDescriptor; 2usize]> =
201    once_cell::sync::Lazy::new(|| {
202        [
203            Pinhole::descriptor_camera_xyz(),
204            Pinhole::descriptor_image_plane_distance(),
205        ]
206    });
207
208static ALL_COMPONENTS: once_cell::sync::Lazy<[ComponentDescriptor; 4usize]> =
209    once_cell::sync::Lazy::new(|| {
210        [
211            Pinhole::descriptor_image_from_camera(),
212            Pinhole::descriptor_resolution(),
213            Pinhole::descriptor_camera_xyz(),
214            Pinhole::descriptor_image_plane_distance(),
215        ]
216    });
217
218impl Pinhole {
219    /// The total number of components in the archetype: 1 required, 1 recommended, 2 optional
220    pub const NUM_COMPONENTS: usize = 4usize;
221}
222
223impl ::re_types_core::Archetype for Pinhole {
224    #[inline]
225    fn name() -> ::re_types_core::ArchetypeName {
226        "rerun.archetypes.Pinhole".into()
227    }
228
229    #[inline]
230    fn display_name() -> &'static str {
231        "Pinhole"
232    }
233
234    #[inline]
235    fn required_components() -> ::std::borrow::Cow<'static, [ComponentDescriptor]> {
236        REQUIRED_COMPONENTS.as_slice().into()
237    }
238
239    #[inline]
240    fn recommended_components() -> ::std::borrow::Cow<'static, [ComponentDescriptor]> {
241        RECOMMENDED_COMPONENTS.as_slice().into()
242    }
243
244    #[inline]
245    fn optional_components() -> ::std::borrow::Cow<'static, [ComponentDescriptor]> {
246        OPTIONAL_COMPONENTS.as_slice().into()
247    }
248
249    #[inline]
250    fn all_components() -> ::std::borrow::Cow<'static, [ComponentDescriptor]> {
251        ALL_COMPONENTS.as_slice().into()
252    }
253
254    #[inline]
255    fn from_arrow_components(
256        arrow_data: impl IntoIterator<Item = (ComponentDescriptor, arrow::array::ArrayRef)>,
257    ) -> DeserializationResult<Self> {
258        re_tracing::profile_function!();
259        use ::re_types_core::{Loggable as _, ResultExt as _};
260        let arrays_by_descr: ::nohash_hasher::IntMap<_, _> = arrow_data.into_iter().collect();
261        let image_from_camera = arrays_by_descr
262            .get(&Self::descriptor_image_from_camera())
263            .map(|array| {
264                SerializedComponentBatch::new(array.clone(), Self::descriptor_image_from_camera())
265            });
266        let resolution = arrays_by_descr
267            .get(&Self::descriptor_resolution())
268            .map(|array| {
269                SerializedComponentBatch::new(array.clone(), Self::descriptor_resolution())
270            });
271        let camera_xyz = arrays_by_descr
272            .get(&Self::descriptor_camera_xyz())
273            .map(|array| {
274                SerializedComponentBatch::new(array.clone(), Self::descriptor_camera_xyz())
275            });
276        let image_plane_distance = arrays_by_descr
277            .get(&Self::descriptor_image_plane_distance())
278            .map(|array| {
279                SerializedComponentBatch::new(
280                    array.clone(),
281                    Self::descriptor_image_plane_distance(),
282                )
283            });
284        Ok(Self {
285            image_from_camera,
286            resolution,
287            camera_xyz,
288            image_plane_distance,
289        })
290    }
291}
292
293impl ::re_types_core::AsComponents for Pinhole {
294    #[inline]
295    fn as_serialized_batches(&self) -> Vec<SerializedComponentBatch> {
296        use ::re_types_core::Archetype as _;
297        [
298            self.image_from_camera.clone(),
299            self.resolution.clone(),
300            self.camera_xyz.clone(),
301            self.image_plane_distance.clone(),
302        ]
303        .into_iter()
304        .flatten()
305        .collect()
306    }
307}
308
309impl ::re_types_core::ArchetypeReflectionMarker for Pinhole {}
310
311impl Pinhole {
312    /// Create a new `Pinhole`.
313    #[inline]
314    pub fn new(image_from_camera: impl Into<crate::components::PinholeProjection>) -> Self {
315        Self {
316            image_from_camera: try_serialize_field(
317                Self::descriptor_image_from_camera(),
318                [image_from_camera],
319            ),
320            resolution: None,
321            camera_xyz: None,
322            image_plane_distance: None,
323        }
324    }
325
326    /// Update only some specific fields of a `Pinhole`.
327    #[inline]
328    pub fn update_fields() -> Self {
329        Self::default()
330    }
331
332    /// Clear all the fields of a `Pinhole`.
333    #[inline]
334    pub fn clear_fields() -> Self {
335        use ::re_types_core::Loggable as _;
336        Self {
337            image_from_camera: Some(SerializedComponentBatch::new(
338                crate::components::PinholeProjection::arrow_empty(),
339                Self::descriptor_image_from_camera(),
340            )),
341            resolution: Some(SerializedComponentBatch::new(
342                crate::components::Resolution::arrow_empty(),
343                Self::descriptor_resolution(),
344            )),
345            camera_xyz: Some(SerializedComponentBatch::new(
346                crate::components::ViewCoordinates::arrow_empty(),
347                Self::descriptor_camera_xyz(),
348            )),
349            image_plane_distance: Some(SerializedComponentBatch::new(
350                crate::components::ImagePlaneDistance::arrow_empty(),
351                Self::descriptor_image_plane_distance(),
352            )),
353        }
354    }
355
356    /// Partitions the component data into multiple sub-batches.
357    ///
358    /// Specifically, this transforms the existing [`SerializedComponentBatch`]es data into [`SerializedComponentColumn`]s
359    /// instead, via [`SerializedComponentBatch::partitioned`].
360    ///
361    /// This makes it possible to use `RecordingStream::send_columns` to send columnar data directly into Rerun.
362    ///
363    /// The specified `lengths` must sum to the total length of the component batch.
364    ///
365    /// [`SerializedComponentColumn`]: [::re_types_core::SerializedComponentColumn]
366    #[inline]
367    pub fn columns<I>(
368        self,
369        _lengths: I,
370    ) -> SerializationResult<impl Iterator<Item = ::re_types_core::SerializedComponentColumn>>
371    where
372        I: IntoIterator<Item = usize> + Clone,
373    {
374        let columns = [
375            self.image_from_camera
376                .map(|image_from_camera| image_from_camera.partitioned(_lengths.clone()))
377                .transpose()?,
378            self.resolution
379                .map(|resolution| resolution.partitioned(_lengths.clone()))
380                .transpose()?,
381            self.camera_xyz
382                .map(|camera_xyz| camera_xyz.partitioned(_lengths.clone()))
383                .transpose()?,
384            self.image_plane_distance
385                .map(|image_plane_distance| image_plane_distance.partitioned(_lengths.clone()))
386                .transpose()?,
387        ];
388        Ok(columns.into_iter().flatten())
389    }
390
391    /// Helper to partition the component data into unit-length sub-batches.
392    ///
393    /// This is semantically similar to calling [`Self::columns`] with `std::iter::take(1).repeat(n)`,
394    /// where `n` is automatically guessed.
395    #[inline]
396    pub fn columns_of_unit_batches(
397        self,
398    ) -> SerializationResult<impl Iterator<Item = ::re_types_core::SerializedComponentColumn>> {
399        let len_image_from_camera = self.image_from_camera.as_ref().map(|b| b.array.len());
400        let len_resolution = self.resolution.as_ref().map(|b| b.array.len());
401        let len_camera_xyz = self.camera_xyz.as_ref().map(|b| b.array.len());
402        let len_image_plane_distance = self.image_plane_distance.as_ref().map(|b| b.array.len());
403        let len = None
404            .or(len_image_from_camera)
405            .or(len_resolution)
406            .or(len_camera_xyz)
407            .or(len_image_plane_distance)
408            .unwrap_or(0);
409        self.columns(std::iter::repeat(1).take(len))
410    }
411
412    /// Camera projection, from image coordinates to view coordinates.
413    #[inline]
414    pub fn with_image_from_camera(
415        mut self,
416        image_from_camera: impl Into<crate::components::PinholeProjection>,
417    ) -> Self {
418        self.image_from_camera =
419            try_serialize_field(Self::descriptor_image_from_camera(), [image_from_camera]);
420        self
421    }
422
423    /// This method makes it possible to pack multiple [`crate::components::PinholeProjection`] in a single component batch.
424    ///
425    /// This only makes sense when used in conjunction with [`Self::columns`]. [`Self::with_image_from_camera`] should
426    /// be used when logging a single row's worth of data.
427    #[inline]
428    pub fn with_many_image_from_camera(
429        mut self,
430        image_from_camera: impl IntoIterator<Item = impl Into<crate::components::PinholeProjection>>,
431    ) -> Self {
432        self.image_from_camera =
433            try_serialize_field(Self::descriptor_image_from_camera(), image_from_camera);
434        self
435    }
436
437    /// Pixel resolution (usually integers) of child image space. Width and height.
438    ///
439    /// Example:
440    /// ```text
441    /// [1920.0, 1440.0]
442    /// ```
443    ///
444    /// `image_from_camera` project onto the space spanned by `(0,0)` and `resolution - 1`.
445    #[inline]
446    pub fn with_resolution(mut self, resolution: impl Into<crate::components::Resolution>) -> Self {
447        self.resolution = try_serialize_field(Self::descriptor_resolution(), [resolution]);
448        self
449    }
450
451    /// This method makes it possible to pack multiple [`crate::components::Resolution`] in a single component batch.
452    ///
453    /// This only makes sense when used in conjunction with [`Self::columns`]. [`Self::with_resolution`] should
454    /// be used when logging a single row's worth of data.
455    #[inline]
456    pub fn with_many_resolution(
457        mut self,
458        resolution: impl IntoIterator<Item = impl Into<crate::components::Resolution>>,
459    ) -> Self {
460        self.resolution = try_serialize_field(Self::descriptor_resolution(), resolution);
461        self
462    }
463
464    /// Sets the view coordinates for the camera.
465    ///
466    /// All common values are available as constants on the [`components::ViewCoordinates`][crate::components::ViewCoordinates] class.
467    ///
468    /// The default is `ViewCoordinates::RDF`, i.e. X=Right, Y=Down, Z=Forward, and this is also the recommended setting.
469    /// This means that the camera frustum will point along the positive Z axis of the parent space,
470    /// and the cameras "up" direction will be along the negative Y axis of the parent space.
471    ///
472    /// The camera frustum will point whichever axis is set to `F` (or the opposite of `B`).
473    /// When logging a depth image under this entity, this is the direction the point cloud will be projected.
474    /// With `RDF`, the default forward is +Z.
475    ///
476    /// The frustum's "up" direction will be whichever axis is set to `U` (or the opposite of `D`).
477    /// This will match the negative Y direction of pixel space (all images are assumed to have xyz=RDF).
478    /// With `RDF`, the default is up is -Y.
479    ///
480    /// The frustum's "right" direction will be whichever axis is set to `R` (or the opposite of `L`).
481    /// This will match the positive X direction of pixel space (all images are assumed to have xyz=RDF).
482    /// With `RDF`, the default right is +x.
483    ///
484    /// Other common formats are `RUB` (X=Right, Y=Up, Z=Back) and `FLU` (X=Forward, Y=Left, Z=Up).
485    ///
486    /// NOTE: setting this to something else than `RDF` (the default) will change the orientation of the camera frustum,
487    /// and make the pinhole matrix not match up with the coordinate system of the pinhole entity.
488    ///
489    /// The pinhole matrix (the `image_from_camera` argument) always project along the third (Z) axis,
490    /// but will be re-oriented to project along the forward axis of the `camera_xyz` argument.
491    #[inline]
492    pub fn with_camera_xyz(
493        mut self,
494        camera_xyz: impl Into<crate::components::ViewCoordinates>,
495    ) -> Self {
496        self.camera_xyz = try_serialize_field(Self::descriptor_camera_xyz(), [camera_xyz]);
497        self
498    }
499
500    /// This method makes it possible to pack multiple [`crate::components::ViewCoordinates`] in a single component batch.
501    ///
502    /// This only makes sense when used in conjunction with [`Self::columns`]. [`Self::with_camera_xyz`] should
503    /// be used when logging a single row's worth of data.
504    #[inline]
505    pub fn with_many_camera_xyz(
506        mut self,
507        camera_xyz: impl IntoIterator<Item = impl Into<crate::components::ViewCoordinates>>,
508    ) -> Self {
509        self.camera_xyz = try_serialize_field(Self::descriptor_camera_xyz(), camera_xyz);
510        self
511    }
512
513    /// The distance from the camera origin to the image plane when the projection is shown in a 3D viewer.
514    ///
515    /// This is only used for visualization purposes, and does not affect the projection itself.
516    #[inline]
517    pub fn with_image_plane_distance(
518        mut self,
519        image_plane_distance: impl Into<crate::components::ImagePlaneDistance>,
520    ) -> Self {
521        self.image_plane_distance = try_serialize_field(
522            Self::descriptor_image_plane_distance(),
523            [image_plane_distance],
524        );
525        self
526    }
527
528    /// This method makes it possible to pack multiple [`crate::components::ImagePlaneDistance`] in a single component batch.
529    ///
530    /// This only makes sense when used in conjunction with [`Self::columns`]. [`Self::with_image_plane_distance`] should
531    /// be used when logging a single row's worth of data.
532    #[inline]
533    pub fn with_many_image_plane_distance(
534        mut self,
535        image_plane_distance: impl IntoIterator<Item = impl Into<crate::components::ImagePlaneDistance>>,
536    ) -> Self {
537        self.image_plane_distance = try_serialize_field(
538            Self::descriptor_image_plane_distance(),
539            image_plane_distance,
540        );
541        self
542    }
543}
544
545impl ::re_byte_size::SizeBytes for Pinhole {
546    #[inline]
547    fn heap_size_bytes(&self) -> u64 {
548        self.image_from_camera.heap_size_bytes()
549            + self.resolution.heap_size_bytes()
550            + self.camera_xyz.heap_size_bytes()
551            + self.image_plane_distance.heap_size_bytes()
552    }
553}