1use enum_iterator::Sequence;
2use parse_display_derive::{Display, FromStr};
3use schemars::{schema::SchemaObject, JsonSchema};
4use serde::{Deserialize, Serialize};
5use uuid::Uuid;
6
7#[cfg(feature = "cxx")]
8use crate::impl_extern_type;
9use crate::{length_unit::LengthUnit, output::ExtrusionFaceInfo, units::UnitAngle};
10
11pub use point::{Point2d, Point3d, Point4d, Quaternion};
12
13mod point;
14
15#[derive(Debug, Clone, Copy, PartialEq, Serialize, Deserialize, JsonSchema, Default)]
17#[serde(rename_all = "snake_case")]
18#[cfg_attr(feature = "ts-rs", derive(ts_rs::TS))]
19#[cfg_attr(feature = "ts-rs", ts(export_to = "ModelingCmd.ts"))]
20pub enum CutType {
21 #[default]
23 Fillet,
24 Chamfer,
26}
27
28#[derive(Debug, Clone, PartialEq, Serialize, Deserialize, JsonSchema)]
30#[serde(rename_all = "snake_case")]
31#[cfg_attr(feature = "ts-rs", derive(ts_rs::TS))]
32#[cfg_attr(feature = "ts-rs", ts(export_to = "ModelingCmd.ts"))]
33pub struct Rotation {
34 pub axis: Point3d<f64>,
37 pub angle: Angle,
40 pub origin: OriginType,
42}
43
44impl Default for Rotation {
45 fn default() -> Self {
47 Self {
48 axis: z_axis(),
49 angle: Angle::default(),
50 origin: OriginType::Local,
51 }
52 }
53}
54
55#[derive(Debug, Clone, PartialEq, Serialize, Deserialize, JsonSchema)]
57#[serde(rename_all = "snake_case")]
58#[cfg_attr(feature = "ts-rs", derive(ts_rs::TS))]
59#[cfg_attr(feature = "ts-rs", ts(export_to = "ModelingCmd.ts"))]
60pub struct Transform {
61 #[serde(default)]
64 pub translate: Point3d<LengthUnit>,
65 #[serde(default = "same_scale")]
68 pub scale: Point3d<f64>,
69 #[serde(default)]
72 pub rotation: Rotation,
73 #[serde(default = "bool_true")]
75 pub replicate: bool,
76}
77
78impl Default for Transform {
79 fn default() -> Self {
80 Self {
81 scale: same_scale(),
82 replicate: true,
83 translate: Default::default(),
84 rotation: Rotation::default(),
85 }
86 }
87}
88
89#[derive(Debug, Clone, PartialEq, Serialize, Deserialize, JsonSchema)]
91#[serde(rename_all = "snake_case")]
92#[cfg_attr(feature = "ts-rs", derive(ts_rs::TS))]
93#[cfg_attr(feature = "ts-rs", ts(export_to = "ModelingCmd.ts"))]
94pub struct AnnotationOptions {
95 pub text: Option<AnnotationTextOptions>,
97 pub line_ends: Option<AnnotationLineEndOptions>,
99 pub line_width: Option<f32>,
101 pub color: Option<Color>,
103 pub position: Option<Point3d<f32>>,
105}
106
107#[derive(Debug, Clone, PartialEq, Serialize, Deserialize, JsonSchema)]
109#[serde(rename_all = "snake_case")]
110#[cfg_attr(feature = "ts-rs", derive(ts_rs::TS))]
111#[cfg_attr(feature = "ts-rs", ts(export_to = "ModelingCmd.ts"))]
112pub struct AnnotationLineEndOptions {
113 pub start: AnnotationLineEnd,
115 pub end: AnnotationLineEnd,
117}
118
119#[derive(Debug, Clone, PartialEq, Serialize, Deserialize, JsonSchema)]
121#[serde(rename_all = "snake_case")]
122#[cfg_attr(feature = "ts-rs", derive(ts_rs::TS))]
123#[cfg_attr(feature = "ts-rs", ts(export_to = "ModelingCmd.ts"))]
124pub struct AnnotationTextOptions {
125 pub x: AnnotationTextAlignmentX,
127 pub y: AnnotationTextAlignmentY,
129 pub text: String,
131 pub point_size: u32,
133}
134
135#[derive(Debug, Clone, Copy, PartialEq, Serialize, Deserialize, JsonSchema)]
139#[serde(rename_all = "snake_case", tag = "type")]
140#[cfg_attr(feature = "ts-rs", derive(ts_rs::TS))]
141#[cfg_attr(feature = "ts-rs", ts(export_to = "ModelingCmd.ts"))]
142pub enum DistanceType {
143 Euclidean {},
145 OnAxis {
147 axis: GlobalAxis,
149 },
150}
151
152#[derive(Debug, Clone, Copy, PartialEq, Serialize, Deserialize, JsonSchema, Default)]
154#[serde(rename_all = "snake_case", tag = "type")]
155#[cfg_attr(feature = "ts-rs", derive(ts_rs::TS))]
156#[cfg_attr(feature = "ts-rs", ts(export_to = "ModelingCmd.ts"))]
157pub enum OriginType {
158 #[default]
160 Local,
161 Global,
163 Custom {
165 origin: Point3d<f64>,
167 },
168}
169
170#[derive(Debug, Clone, Copy, PartialEq, Serialize, Deserialize, JsonSchema)]
172#[cfg_attr(feature = "ts-rs", derive(ts_rs::TS))]
173#[cfg_attr(feature = "ts-rs", ts(export_to = "ModelingCmd.ts"))]
174pub struct Color {
175 pub r: f32,
177 pub g: f32,
179 pub b: f32,
181 pub a: f32,
183}
184
185#[allow(missing_docs)]
187#[derive(
188 Display, FromStr, Copy, Eq, PartialEq, Debug, JsonSchema, Deserialize, Serialize, Sequence, Clone, Ord, PartialOrd,
189)]
190#[serde(rename_all = "lowercase")]
191#[cfg_attr(feature = "ts-rs", derive(ts_rs::TS))]
192#[cfg_attr(feature = "ts-rs", ts(export_to = "ModelingCmd.ts"))]
193pub enum AnnotationTextAlignmentX {
194 Left,
195 Center,
196 Right,
197}
198
199#[allow(missing_docs)]
201#[derive(
202 Display, FromStr, Copy, Eq, PartialEq, Debug, JsonSchema, Deserialize, Serialize, Sequence, Clone, Ord, PartialOrd,
203)]
204#[serde(rename_all = "lowercase")]
205#[cfg_attr(feature = "ts-rs", derive(ts_rs::TS))]
206#[cfg_attr(feature = "ts-rs", ts(export_to = "ModelingCmd.ts"))]
207pub enum AnnotationTextAlignmentY {
208 Bottom,
209 Center,
210 Top,
211}
212
213#[allow(missing_docs)]
215#[derive(
216 Display, FromStr, Copy, Eq, PartialEq, Debug, JsonSchema, Deserialize, Serialize, Sequence, Clone, Ord, PartialOrd,
217)]
218#[serde(rename_all = "lowercase")]
219#[cfg_attr(feature = "ts-rs", derive(ts_rs::TS))]
220#[cfg_attr(feature = "ts-rs", ts(export_to = "ModelingCmd.ts"))]
221pub enum AnnotationLineEnd {
222 None,
223 Arrow,
224}
225
226#[derive(
228 Display, FromStr, Copy, Eq, PartialEq, Debug, JsonSchema, Deserialize, Serialize, Sequence, Clone, Ord, PartialOrd,
229)]
230#[serde(rename_all = "lowercase")]
231#[cfg_attr(feature = "ts-rs", derive(ts_rs::TS))]
232#[cfg_attr(feature = "ts-rs", ts(export_to = "ModelingCmd.ts"))]
233pub enum AnnotationType {
234 T2D,
236 T3D,
238}
239
240#[derive(
242 Display, FromStr, Copy, Eq, PartialEq, Debug, JsonSchema, Deserialize, Serialize, Sequence, Clone, Ord, PartialOrd,
243)]
244#[serde(rename_all = "lowercase")]
245#[cfg_attr(feature = "ts-rs", derive(ts_rs::TS))]
246#[cfg_attr(feature = "ts-rs", ts(export_to = "ModelingCmd.ts"))]
247pub enum CameraDragInteractionType {
248 Pan,
250 Rotate,
252 RotateTrackball,
254 Zoom,
256}
257
258#[derive(Debug, Clone, Copy, Serialize, Deserialize, JsonSchema, PartialEq)]
261#[serde(rename_all = "snake_case", tag = "type")]
262#[cfg_attr(feature = "ts-rs", derive(ts_rs::TS))]
263#[cfg_attr(feature = "ts-rs", ts(export_to = "ModelingCmd.ts"))]
264pub enum PathSegment {
265 Line {
268 end: Point3d<LengthUnit>,
270 relative: bool,
272 },
273 Arc {
276 center: Point2d<LengthUnit>,
278 radius: LengthUnit,
280 start: Angle,
282 end: Angle,
284 relative: bool,
286 },
287 Bezier {
291 control1: Point3d<LengthUnit>,
293 control2: Point3d<LengthUnit>,
295 end: Point3d<LengthUnit>,
297 relative: bool,
299 },
300 TangentialArc {
302 radius: LengthUnit,
305 offset: Angle,
307 },
308 TangentialArcTo {
311 to: Point3d<LengthUnit>,
315 angle_snap_increment: Option<Angle>,
317 },
318 ArcTo {
320 interior: Point3d<LengthUnit>,
322 end: Point3d<LengthUnit>,
324 relative: bool,
326 },
327 CircularInvolute {
330 start_radius: LengthUnit,
333 end_radius: LengthUnit,
336 angle: Angle,
339 reverse: bool,
342 },
343}
344
345#[derive(Clone, Copy, PartialEq, Debug, JsonSchema, Deserialize, Serialize)]
347#[cfg_attr(feature = "ts-rs", derive(ts_rs::TS))]
348#[cfg_attr(feature = "ts-rs", ts(export_to = "ModelingCmd.ts"))]
349pub struct Angle {
350 pub unit: UnitAngle,
352 pub value: f64,
354}
355
356impl Angle {
357 pub fn to_degrees(self) -> f64 {
359 match self.unit {
360 UnitAngle::Degrees => self.value,
361 UnitAngle::Radians => self.value.to_degrees(),
362 }
363 }
364 pub fn to_radians(self) -> f64 {
366 match self.unit {
367 UnitAngle::Degrees => self.value.to_radians(),
368 UnitAngle::Radians => self.value,
369 }
370 }
371 pub const fn from_degrees(value: f64) -> Self {
373 Self {
374 unit: UnitAngle::Degrees,
375 value,
376 }
377 }
378 pub const fn from_radians(value: f64) -> Self {
380 Self {
381 unit: UnitAngle::Radians,
382 value,
383 }
384 }
385 pub const fn turn() -> Self {
387 Self::from_degrees(360.0)
388 }
389 pub const fn half_circle() -> Self {
391 Self::from_degrees(180.0)
392 }
393 pub const fn quarter_circle() -> Self {
395 Self::from_degrees(90.0)
396 }
397 pub const fn zero() -> Self {
399 Self::from_degrees(0.0)
400 }
401}
402
403impl Default for Angle {
405 fn default() -> Self {
407 Self::zero()
408 }
409}
410
411impl PartialOrd for Angle {
412 fn partial_cmp(&self, other: &Self) -> Option<std::cmp::Ordering> {
413 match (self.unit, other.unit) {
414 (UnitAngle::Degrees, UnitAngle::Degrees) => self.value.partial_cmp(&other.value),
416 (UnitAngle::Radians, UnitAngle::Radians) => self.value.partial_cmp(&other.value),
417 _ => self.to_degrees().partial_cmp(&other.to_degrees()),
418 }
419 }
420}
421
422impl std::ops::Add for Angle {
423 type Output = Self;
424
425 fn add(self, rhs: Self) -> Self::Output {
426 Self {
427 unit: UnitAngle::Degrees,
428 value: self.to_degrees() + rhs.to_degrees(),
429 }
430 }
431}
432
433impl std::ops::AddAssign for Angle {
434 fn add_assign(&mut self, rhs: Self) {
435 match self.unit {
436 UnitAngle::Degrees => {
437 self.value += rhs.to_degrees();
438 }
439 UnitAngle::Radians => {
440 self.value += rhs.to_radians();
441 }
442 }
443 }
444}
445
446#[derive(
448 Display, FromStr, Copy, Eq, PartialEq, Debug, JsonSchema, Deserialize, Serialize, Sequence, Clone, Ord, PartialOrd,
449)]
450#[serde(rename_all = "lowercase")]
451#[cfg_attr(feature = "ts-rs", derive(ts_rs::TS))]
452#[cfg_attr(feature = "ts-rs", ts(export_to = "ModelingCmd.ts"))]
453pub enum SceneSelectionType {
454 Replace,
456 Add,
458 Remove,
460}
461
462#[allow(missing_docs)]
464#[derive(
465 Display, FromStr, Copy, Eq, PartialEq, Debug, JsonSchema, Deserialize, Serialize, Sequence, Clone, Ord, PartialOrd,
466)]
467#[serde(rename_all = "snake_case")]
468#[cfg_attr(feature = "ts-rs", derive(ts_rs::TS))]
469#[cfg_attr(feature = "ts-rs", ts(export_to = "ModelingCmd.ts"))]
470pub enum SceneToolType {
471 CameraRevolve,
472 Select,
473 Move,
474 SketchLine,
475 SketchTangentialArc,
476 SketchCurve,
477 SketchCurveMod,
478}
479
480#[allow(missing_docs)]
482#[derive(
483 Display,
484 FromStr,
485 Copy,
486 Eq,
487 PartialEq,
488 Debug,
489 JsonSchema,
490 Deserialize,
491 Serialize,
492 Sequence,
493 Clone,
494 Ord,
495 PartialOrd,
496 Default,
497)]
498#[serde(rename_all = "snake_case")]
499#[cfg_attr(feature = "ts-rs", derive(ts_rs::TS))]
500#[cfg_attr(feature = "ts-rs", ts(export_to = "ModelingCmd.ts"))]
501pub enum PathComponentConstraintBound {
502 #[default]
503 Unconstrained,
504 PartiallyConstrained,
505 FullyConstrained,
506}
507
508#[allow(missing_docs)]
510#[derive(
511 Display,
512 FromStr,
513 Copy,
514 Eq,
515 PartialEq,
516 Debug,
517 JsonSchema,
518 Deserialize,
519 Serialize,
520 Sequence,
521 Clone,
522 Ord,
523 PartialOrd,
524 Default,
525)]
526#[serde(rename_all = "snake_case")]
527#[cfg_attr(feature = "ts-rs", derive(ts_rs::TS))]
528#[cfg_attr(feature = "ts-rs", ts(export_to = "ModelingCmd.ts"))]
529pub enum PathComponentConstraintType {
530 #[default]
531 Unconstrained,
532 Vertical,
533 Horizontal,
534 EqualLength,
535 Parallel,
536 AngleBetween,
537}
538
539#[allow(missing_docs)]
541#[derive(
542 Display, FromStr, Copy, Eq, PartialEq, Debug, JsonSchema, Deserialize, Serialize, Sequence, Clone, Ord, PartialOrd,
543)]
544#[serde(rename_all = "snake_case")]
545#[cfg_attr(feature = "ts-rs", derive(ts_rs::TS))]
546#[cfg_attr(feature = "ts-rs", ts(export_to = "ModelingCmd.ts"))]
547pub enum PathCommand {
548 MoveTo,
549 LineTo,
550 BezCurveTo,
551 NurbsCurveTo,
552 AddArc,
553}
554
555#[allow(missing_docs)]
557#[derive(
558 Display, FromStr, Copy, Eq, PartialEq, Debug, JsonSchema, Deserialize, Serialize, Sequence, Clone, Ord, PartialOrd,
559)]
560#[serde(rename_all = "lowercase")]
561#[cfg_attr(feature = "ts-rs", derive(ts_rs::TS))]
562#[cfg_attr(feature = "ts-rs", ts(export_to = "ModelingCmd.ts"))]
563#[repr(u8)]
564pub enum EntityType {
565 Entity,
566 Object,
567 Path,
568 Curve,
569 Solid2D,
570 Solid3D,
571 Edge,
572 Face,
573 Plane,
574 Vertex,
575}
576
577#[allow(missing_docs)]
579#[derive(
580 Display, FromStr, Copy, Eq, PartialEq, Debug, JsonSchema, Deserialize, Serialize, Sequence, Clone, Ord, PartialOrd,
581)]
582#[serde(rename_all = "snake_case")]
583#[cfg_attr(feature = "ts-rs", derive(ts_rs::TS))]
584#[cfg_attr(feature = "ts-rs", ts(export_to = "ModelingCmd.ts"))]
585pub enum CurveType {
586 Line,
587 Arc,
588 Nurbs,
589}
590
591#[derive(Debug, Serialize, Deserialize, JsonSchema, Clone)]
593pub struct ExportFile {
594 pub name: String,
596 pub contents: crate::base64::Base64Data,
598}
599
600#[derive(
602 Display, FromStr, Copy, Eq, PartialEq, Debug, JsonSchema, Deserialize, Serialize, Clone, Ord, PartialOrd, Sequence,
603)]
604#[serde(rename_all = "lowercase")]
605#[display(style = "lowercase")]
606#[cfg_attr(feature = "ts-rs", derive(ts_rs::TS))]
607#[cfg_attr(feature = "ts-rs", ts(export_to = "ModelingCmd.ts"))]
608pub enum FileExportFormat {
609 Fbx,
611 Glb,
618 Gltf,
629 Obj,
633 Ply,
635 Step,
637 Stl,
639}
640
641#[derive(
643 Display, FromStr, Copy, Eq, PartialEq, Debug, JsonSchema, Deserialize, Serialize, Clone, Ord, PartialOrd, Sequence,
644)]
645#[serde(rename_all = "lowercase")]
646#[display(style = "lowercase")]
647#[cfg_attr(feature = "ts-rs", derive(ts_rs::TS))]
648#[cfg_attr(feature = "ts-rs", ts(export_to = "ModelingCmd.ts"))]
649pub enum FileExportFormat2d {
650 Dxf,
652}
653
654#[derive(
656 Display, FromStr, Copy, Eq, PartialEq, Debug, JsonSchema, Deserialize, Serialize, Clone, Ord, PartialOrd, Sequence,
657)]
658#[serde(rename_all = "lowercase")]
659#[display(style = "lowercase")]
660#[cfg_attr(feature = "ts-rs", derive(ts_rs::TS))]
661#[cfg_attr(feature = "ts-rs", ts(export_to = "ModelingCmd.ts"))]
662pub enum FileImportFormat {
663 Fbx,
665 Gltf,
667 Obj,
671 Ply,
673 Sldprt,
675 Step,
677 Stl,
679}
680
681#[derive(Display, FromStr, Copy, Eq, PartialEq, Debug, JsonSchema, Deserialize, Serialize, Clone, Ord, PartialOrd)]
683#[serde(rename_all = "snake_case")]
684#[cfg_attr(feature = "ts-rs", derive(ts_rs::TS))]
685#[cfg_attr(feature = "ts-rs", ts(export_to = "ModelingCmd.ts"))]
686pub enum EngineErrorCode {
687 BadRequest = 1,
691 InternalEngine,
693}
694
695impl From<EngineErrorCode> for http::StatusCode {
696 fn from(e: EngineErrorCode) -> Self {
697 match e {
698 EngineErrorCode::BadRequest => Self::BAD_REQUEST,
699 EngineErrorCode::InternalEngine => Self::INTERNAL_SERVER_ERROR,
700 }
701 }
702}
703
704#[derive(Debug, PartialEq, Serialize, Deserialize, JsonSchema, Clone)]
706#[cfg_attr(feature = "ts-rs", derive(ts_rs::TS))]
707#[cfg_attr(feature = "ts-rs", ts(export_to = "ModelingCmd.ts"))]
708pub struct ExtrudedFaceInfo {
709 pub bottom: Option<Uuid>,
714 pub top: Uuid,
716 pub sides: Vec<SideFace>,
718}
719
720#[derive(Debug, PartialEq, Serialize, Deserialize, JsonSchema, Clone)]
722#[cfg_attr(feature = "ts-rs", derive(ts_rs::TS))]
723#[cfg_attr(feature = "ts-rs", ts(export_to = "ModelingCmd.ts"))]
724pub struct SideFace {
725 pub path_id: Uuid,
727 pub face_id: Uuid,
729}
730
731#[derive(Debug, Serialize, Deserialize, JsonSchema, Clone)]
733#[cfg_attr(feature = "ts-rs", derive(ts_rs::TS))]
734#[cfg_attr(feature = "ts-rs", ts(export_to = "ModelingCmd.ts"))]
735pub struct CameraSettings {
736 pub pos: Point3d,
738
739 pub center: Point3d,
741
742 pub up: Point3d,
744
745 pub orientation: Quaternion,
747
748 pub fov_y: Option<f32>,
750
751 pub ortho_scale: Option<f32>,
753
754 pub ortho: bool,
756}
757
758#[allow(missing_docs)]
759#[repr(u8)]
760#[derive(Default, Clone, Copy, Debug, Eq, PartialEq, Serialize, Deserialize, JsonSchema)]
761#[serde(rename_all = "snake_case")]
762#[cfg_attr(feature = "ts-rs", derive(ts_rs::TS))]
763#[cfg_attr(feature = "ts-rs", ts(export_to = "ModelingCmd.ts"))]
764pub enum WorldCoordinateSystem {
765 #[default]
766 RightHandedUpZ,
767 RightHandedUpY,
768}
769
770#[allow(missing_docs)]
771#[repr(C)]
772#[derive(Clone, Copy, Debug, PartialEq, Serialize, Deserialize, JsonSchema)]
773#[cfg_attr(feature = "ts-rs", derive(ts_rs::TS))]
774#[cfg_attr(feature = "ts-rs", ts(export_to = "ModelingCmd.ts"))]
775pub struct CameraViewState {
776 pub pivot_rotation: Quaternion,
777 pub pivot_position: Point3d,
778 pub eye_offset: f32,
779 pub fov_y: f32,
780 pub ortho_scale_factor: f32,
781 pub is_ortho: bool,
782 pub ortho_scale_enabled: bool,
783 pub world_coord_system: WorldCoordinateSystem,
784}
785
786impl Default for CameraViewState {
787 fn default() -> Self {
788 CameraViewState {
789 pivot_rotation: Default::default(),
790 pivot_position: Default::default(),
791 eye_offset: 10.0,
792 fov_y: 45.0,
793 ortho_scale_factor: 1.6,
794 is_ortho: false,
795 ortho_scale_enabled: true,
796 world_coord_system: Default::default(),
797 }
798 }
799}
800
801#[cfg(feature = "cxx")]
802impl_extern_type! {
803 [Trivial]
804 CameraViewState = "Endpoints::CameraViewState"
805}
806
807impl From<CameraSettings> for crate::output::DefaultCameraZoom {
808 fn from(settings: CameraSettings) -> Self {
809 Self { settings }
810 }
811}
812impl From<CameraSettings> for crate::output::CameraDragMove {
813 fn from(settings: CameraSettings) -> Self {
814 Self { settings }
815 }
816}
817impl From<CameraSettings> for crate::output::CameraDragEnd {
818 fn from(settings: CameraSettings) -> Self {
819 Self { settings }
820 }
821}
822impl From<CameraSettings> for crate::output::DefaultCameraGetSettings {
823 fn from(settings: CameraSettings) -> Self {
824 Self { settings }
825 }
826}
827impl From<CameraSettings> for crate::output::ZoomToFit {
828 fn from(settings: CameraSettings) -> Self {
829 Self { settings }
830 }
831}
832impl From<CameraSettings> for crate::output::OrientToFace {
833 fn from(settings: CameraSettings) -> Self {
834 Self { settings }
835 }
836}
837impl From<CameraSettings> for crate::output::ViewIsometric {
838 fn from(settings: CameraSettings) -> Self {
839 Self { settings }
840 }
841}
842
843#[derive(Copy, PartialEq, Debug, JsonSchema, Deserialize, Serialize, Clone, PartialOrd, Default)]
845#[serde(rename_all = "snake_case")]
846#[cfg_attr(feature = "ts-rs", derive(ts_rs::TS))]
847#[cfg_attr(feature = "ts-rs", ts(export_to = "ModelingCmd.ts"))]
848pub struct PerspectiveCameraParameters {
849 pub fov_y: Option<f32>,
851 pub z_near: Option<f32>,
853 pub z_far: Option<f32>,
855}
856
857#[derive(
859 Default,
860 Display,
861 FromStr,
862 Copy,
863 Eq,
864 PartialEq,
865 Debug,
866 JsonSchema,
867 Deserialize,
868 Serialize,
869 Sequence,
870 Clone,
871 Ord,
872 PartialOrd,
873)]
874#[serde(rename_all = "snake_case")]
875#[cfg_attr(feature = "ts-rs", derive(ts_rs::TS))]
876#[cfg_attr(feature = "ts-rs", ts(export_to = "ModelingCmd.ts"))]
877pub enum CameraMovement {
878 #[default]
880 Vantage,
881 None,
883}
884
885#[derive(
887 Display, FromStr, Copy, Eq, PartialEq, Debug, JsonSchema, Deserialize, Serialize, Sequence, Clone, Ord, PartialOrd,
888)]
889#[serde(rename_all = "lowercase")]
890#[cfg_attr(feature = "ts-rs", derive(ts_rs::TS))]
891#[cfg_attr(feature = "ts-rs", ts(export_to = "ModelingCmd.ts"))]
892pub enum GlobalAxis {
893 X,
895 Y,
897 Z,
899}
900
901#[derive(
903 Display, FromStr, Copy, Eq, PartialEq, Debug, JsonSchema, Deserialize, Serialize, Sequence, Clone, Ord, PartialOrd,
904)]
905#[serde(rename_all = "snake_case")]
906#[cfg_attr(feature = "ts-rs", derive(ts_rs::TS))]
907#[cfg_attr(feature = "ts-rs", ts(export_to = "ModelingCmd.ts"))]
908#[repr(u8)]
909pub enum ExtrusionFaceCapType {
910 None,
912 Top,
914 Bottom,
916 Both,
918}
919
920#[allow(missing_docs)]
922#[derive(
923 Display,
924 FromStr,
925 Copy,
926 Eq,
927 PartialEq,
928 Debug,
929 JsonSchema,
930 Deserialize,
931 Serialize,
932 Sequence,
933 Clone,
934 Ord,
935 PartialOrd,
936 Default,
937)]
938#[serde(rename_all = "lowercase")]
939#[cfg_attr(feature = "ts-rs", derive(ts_rs::TS))]
940#[cfg_attr(feature = "ts-rs", ts(export_to = "ModelingCmd.ts"))]
941pub enum PostEffectType {
942 Phosphor,
943 Ssao,
944 #[default]
945 NoEffect,
946}
947
948#[cfg(feature = "cxx")]
951impl_extern_type! {
952 [Trivial]
953 FileImportFormat = "Enums::_FileImportFormat"
955 FileExportFormat = "Enums::_FileExportFormat"
956 CameraDragInteractionType = "Enums::_CameraDragInteractionType"
958 SceneSelectionType = "Enums::_SceneSelectionType"
960 SceneToolType = "Enums::_SceneToolType"
961 EntityType = "Enums::_EntityType"
962 AnnotationType = "Enums::_AnnotationType"
963 AnnotationTextAlignmentX = "Enums::_AnnotationTextAlignmentX"
964 AnnotationTextAlignmentY = "Enums::_AnnotationTextAlignmentY"
965 AnnotationLineEnd = "Enums::_AnnotationLineEnd"
966
967 CurveType = "Enums::_CurveType"
968 PathCommand = "Enums::_PathCommand"
969 PathComponentConstraintBound = "Enums::_PathComponentConstraintBound"
970 PathComponentConstraintType = "Enums::_PathComponentConstraintType"
971 ExtrusionFaceCapType = "Enums::_ExtrusionFaceCapType"
972
973 EngineErrorCode = "Enums::_ErrorCode"
975 GlobalAxis = "Enums::_GlobalAxis"
976 OriginType = "Enums::_OriginType"
977
978 PostEffectType = "Enums::_PostEffectType"
980}
981
982fn bool_true() -> bool {
983 true
984}
985fn same_scale() -> Point3d<f64> {
986 Point3d::uniform(1.0)
987}
988
989fn z_axis() -> Point3d<f64> {
990 Point3d { x: 0.0, y: 0.0, z: 1.0 }
991}
992
993impl ExtrudedFaceInfo {
994 pub fn list_faces(self) -> Vec<ExtrusionFaceInfo> {
997 let mut face_infos: Vec<_> = self
998 .sides
999 .into_iter()
1000 .map(|side| ExtrusionFaceInfo {
1001 curve_id: Some(side.path_id),
1002 face_id: Some(side.face_id),
1003 cap: ExtrusionFaceCapType::None,
1004 })
1005 .collect();
1006 face_infos.push(ExtrusionFaceInfo {
1007 curve_id: None,
1008 face_id: Some(self.top),
1009 cap: ExtrusionFaceCapType::Top,
1010 });
1011 if let Some(bottom) = self.bottom {
1012 face_infos.push(ExtrusionFaceInfo {
1013 curve_id: None,
1014 face_id: Some(bottom),
1015 cap: ExtrusionFaceCapType::Bottom,
1016 });
1017 }
1018 face_infos
1019 }
1020}
1021
1022#[cfg(test)]
1023mod tests {
1024 use super::*;
1025
1026 #[test]
1027 fn test_angle_comparison() {
1028 let a = Angle::from_degrees(90.0);
1029 assert!(a < Angle::from_degrees(91.0));
1030 assert!(a > Angle::from_degrees(89.0));
1031 assert!(a <= Angle::from_degrees(90.0));
1032 assert!(a >= Angle::from_degrees(90.0));
1033 let b = Angle::from_radians(std::f64::consts::FRAC_PI_4);
1034 assert!(b < Angle::from_radians(std::f64::consts::FRAC_PI_2));
1035 assert!(b > Angle::from_radians(std::f64::consts::FRAC_PI_8));
1036 assert!(b <= Angle::from_radians(std::f64::consts::FRAC_PI_4));
1037 assert!(b >= Angle::from_radians(std::f64::consts::FRAC_PI_4));
1038 assert!(a > b);
1040 assert!(a >= b);
1041 assert!(b < a);
1042 assert!(b <= a);
1043 let c = Angle::from_radians(std::f64::consts::FRAC_PI_2 * 3.0);
1044 assert!(a < c);
1045 assert!(a <= c);
1046 assert!(c > a);
1047 assert!(c >= a);
1048 }
1049}
1050
1051#[derive(Clone, Debug, PartialEq, Deserialize, Serialize)]
1053#[cfg_attr(feature = "ts-rs", derive(ts_rs::TS))]
1054#[cfg_attr(feature = "ts-rs", ts(export_to = "ModelingCmd.ts"))]
1055pub struct TransformBy<T> {
1056 pub property: T,
1058 pub set: bool,
1063 pub is_local: bool,
1066}
1067
1068impl<T: JsonSchema> JsonSchema for TransformBy<T> {
1069 fn schema_name() -> String {
1070 format!("TransformByFor{}", T::schema_name())
1071 }
1072
1073 fn schema_id() -> std::borrow::Cow<'static, str> {
1074 std::borrow::Cow::Owned(format!("{}::TransformBy<{}>", module_path!(), T::schema_id()))
1075 }
1076
1077 fn json_schema(_: &mut schemars::gen::SchemaGenerator) -> schemars::schema::Schema {
1078 SchemaObject {
1079 instance_type: Some(schemars::schema::InstanceType::String.into()),
1080 ..Default::default()
1081 }
1082 .into()
1083 }
1084}
1085
1086#[derive(Clone, Debug, PartialEq, Deserialize, JsonSchema, Serialize)]
1088#[cfg_attr(feature = "ts-rs", derive(ts_rs::TS))]
1089#[cfg_attr(feature = "ts-rs", ts(export_to = "ModelingCmd.ts"))]
1090pub struct ComponentTransform {
1091 pub translate: Option<TransformBy<Point3d<LengthUnit>>>,
1093 pub rotate_rpy: Option<TransformBy<Point3d<f64>>>,
1096 pub rotate_angle_axis: Option<TransformBy<Point4d<f64>>>,
1100 pub scale: Option<TransformBy<Point3d<f64>>>,
1102}
1103
1104#[derive(Default, Debug, Clone, PartialEq, Serialize, Deserialize)]
1107#[cfg_attr(feature = "ts-rs", derive(ts_rs::TS))]
1108#[cfg_attr(feature = "ts-rs", ts(export_to = "ModelingCmd.ts"))]
1109pub enum Opposite<T> {
1110 #[default]
1112 None,
1113 Symmetric,
1115 Other(T),
1117}
1118
1119impl<T: JsonSchema> JsonSchema for Opposite<T> {
1120 fn schema_name() -> String {
1121 format!("OppositeFor{}", T::schema_name())
1122 }
1123
1124 fn schema_id() -> std::borrow::Cow<'static, str> {
1125 std::borrow::Cow::Owned(format!("{}::Opposite<{}>", module_path!(), T::schema_id()))
1126 }
1127
1128 fn json_schema(_: &mut schemars::gen::SchemaGenerator) -> schemars::schema::Schema {
1129 SchemaObject {
1130 instance_type: Some(schemars::schema::InstanceType::String.into()),
1131 ..Default::default()
1132 }
1133 .into()
1134 }
1135}