1use {
2 noise::{
3 core::worley::{
4 self,
5 distance_functions::{chebyshev, euclidean, euclidean_squared, manhattan},
6 },
7 Abs, Add, BasicMulti, Billow, Blend, Checkerboard, Clamp, Constant, Curve, Cylinders,
8 Displace, Exponent, Fbm, HybridMulti, Max, Min, MultiFractal, Multiply, Negate, NoiseFn,
9 OpenSimplex, Perlin, PerlinSurflet, Power, RidgedMulti, RotatePoint, ScaleBias, ScalePoint,
10 Seedable, Select, Simplex, SuperSimplex, Terrace, TranslatePoint, Turbulence, Value,
11 Worley,
12 },
13 ordered_float::OrderedFloat,
14 serde::{Deserialize, Serialize},
15 std::cell::RefCell,
16};
17
18pub const MAX_FRACTAL_OCTAVES: u32 = BasicMulti::<Perlin>::MAX_OCTAVES as _;
19
20#[derive(Clone, Debug, Deserialize, Serialize)]
21pub struct BlendExpr {
22 pub sources: [Box<Expr>; 2],
23 pub control: Box<Expr>,
24}
25
26impl BlendExpr {
27 fn set_f64(&mut self, name: &str, value: f64) {
28 self.sources.iter_mut().for_each(|expr| {
29 expr.set_f64(name, value);
30 });
31 self.control.set_f64(name, value);
32 }
33
34 fn set_u32(&mut self, name: &str, value: u32) {
35 self.sources.iter_mut().for_each(|expr| {
36 expr.set_u32(name, value);
37 });
38 self.control.set_u32(name, value);
39 }
40}
41
42#[derive(Clone, Debug, Deserialize, Serialize)]
43pub struct ClampExpr {
44 pub source: Box<Expr>,
45
46 pub lower_bound: Variable<f64>,
47 pub upper_bound: Variable<f64>,
48}
49
50impl ClampExpr {
51 fn set_f64(&mut self, name: &str, value: f64) {
52 self.source.set_f64(name, value);
53 self.lower_bound.set_if_named(name, value);
54 self.lower_bound.set_if_named(name, value);
55 }
56
57 fn set_u32(&mut self, name: &str, value: u32) {
58 self.source.set_u32(name, value);
59 }
60}
61
62#[derive(Clone, Debug, Deserialize, Serialize)]
63pub struct ControlPointExpr {
64 pub input_value: Variable<f64>,
65 pub output_value: Variable<f64>,
66}
67
68impl ControlPointExpr {
69 fn set_f64(&mut self, name: &str, value: f64) {
70 self.input_value.set_if_named(name, value);
71 self.output_value.set_if_named(name, value);
72 }
73}
74
75#[derive(Clone, Debug, Deserialize, Serialize)]
76pub struct CurveExpr {
77 pub source: Box<Expr>,
78
79 pub control_points: Vec<ControlPointExpr>,
80}
81
82impl CurveExpr {
83 fn set_f64(&mut self, name: &str, value: f64) {
84 self.source.set_f64(name, value);
85 self.control_points
86 .iter_mut()
87 .for_each(|expr| expr.set_f64(name, value));
88 }
89
90 fn set_u32(&mut self, name: &str, value: u32) {
91 self.source.set_u32(name, value);
92 }
93}
94
95#[derive(Clone, Debug, Deserialize, Serialize)]
96pub struct DisplaceExpr {
97 pub source: Box<Expr>,
98
99 pub axes: [Box<Expr>; 4],
100}
101
102impl DisplaceExpr {
103 fn set_f64(&mut self, name: &str, value: f64) {
104 self.source.set_f64(name, value);
105 self.axes.iter_mut().for_each(|expr| {
106 expr.set_f64(name, value);
107 });
108 }
109
110 fn set_u32(&mut self, name: &str, value: u32) {
111 self.source.set_u32(name, value);
112 self.axes.iter_mut().for_each(|expr| {
113 expr.set_u32(name, value);
114 });
115 }
116}
117
118#[derive(Clone, Copy, Debug, PartialEq, Serialize, Deserialize)]
119pub enum DistanceFunction {
120 Chebyshev,
121 Euclidean,
122 EuclideanSquared,
123 Manhattan,
124}
125
126#[derive(Clone, Debug, Deserialize, Serialize)]
127pub struct ExponentExpr {
128 pub source: Box<Expr>,
129
130 pub exponent: Variable<f64>,
131}
132
133impl ExponentExpr {
134 fn set_f64(&mut self, name: &str, value: f64) {
135 self.source.set_f64(name, value);
136 self.exponent.set_if_named(name, value);
137 }
138
139 fn set_u32(&mut self, name: &str, value: u32) {
140 self.source.set_u32(name, value);
141 }
142}
143
144#[derive(Clone, Debug, Deserialize, Serialize)]
145pub struct FractalExpr {
146 pub source_ty: SourceType,
147 pub seed: Variable<u32>,
148 pub octaves: Variable<u32>,
149 pub frequency: Variable<f64>,
150 pub lacunarity: Variable<f64>,
151 pub persistence: Variable<f64>,
152}
153
154impl FractalExpr {
155 fn set_f64(&mut self, name: &str, value: f64) {
156 self.frequency.set_if_named(name, value);
157 self.lacunarity.set_if_named(name, value);
158 self.persistence.set_if_named(name, value);
159 }
160
161 fn set_u32(&mut self, name: &str, value: u32) {
162 self.seed.set_if_named(name, value);
163 self.octaves.set_if_named(name, value);
164 }
165}
166
167#[derive(Clone, Debug, Deserialize, Serialize)]
168pub enum Expr {
169 Abs(Box<Expr>),
170 Add([Box<Expr>; 2]),
171 BasicMulti(FractalExpr),
172 Billow(FractalExpr),
173 Blend(BlendExpr),
174 Checkerboard(Variable<u32>),
175 Clamp(ClampExpr),
176 Constant(Variable<f64>),
177 ConstantU32(Variable<u32>),
178 Curve(CurveExpr),
179 Cylinders(Variable<f64>),
180 Displace(DisplaceExpr),
181 Exponent(ExponentExpr),
182 Fbm(FractalExpr),
183 HybridMulti(FractalExpr),
184 Max([Box<Expr>; 2]),
185 Min([Box<Expr>; 2]),
186 Multiply([Box<Expr>; 2]),
187 Negate(Box<Expr>),
188 OpenSimplex(Variable<u32>),
189 Perlin(Variable<u32>),
190 PerlinSurflet(Variable<u32>),
191 Power([Box<Expr>; 2]),
192 RidgedMulti(RigidFractalExpr),
193 RotatePoint(TransformExpr),
194 ScaleBias(ScaleBiasExpr),
195 ScalePoint(TransformExpr),
196 Select(SelectExpr),
197 Simplex(Variable<u32>),
198 SuperSimplex(Variable<u32>),
199 Terrace(TerraceExpr),
200 TranslatePoint(TransformExpr),
201 Turbulence(TurbulenceExpr),
202 Value(Variable<u32>),
203 Worley(WorleyExpr),
204}
205
206impl Expr {
207 fn basic_multi<T>(expr: &FractalExpr) -> Box<BasicMulti<T>>
208 where
209 T: Default + Seedable,
210 {
211 Box::new(
212 BasicMulti::<T>::new(expr.seed.value())
213 .set_octaves(expr.octaves.value().clamp(1, MAX_FRACTAL_OCTAVES) as _)
214 .set_frequency(expr.frequency.value())
215 .set_lacunarity(expr.lacunarity.value())
216 .set_persistence(expr.persistence.value()),
217 )
218 }
219
220 fn billow<T>(expr: &FractalExpr) -> Box<Billow<T>>
221 where
222 T: Default + Seedable,
223 {
224 Box::new(
225 Billow::<T>::new(expr.seed.value())
226 .set_octaves(expr.octaves.value().clamp(1, MAX_FRACTAL_OCTAVES) as _)
227 .set_frequency(expr.frequency.value())
228 .set_lacunarity(expr.lacunarity.value())
229 .set_persistence(expr.persistence.value()),
230 )
231 }
232
233 fn curve(expr: &CurveExpr) -> Box<dyn NoiseFn<f64, 3>> {
234 fn invalid_inputs(control_points: &[ControlPointExpr]) -> bool {
235 debug_assert!(control_points.len() >= 4);
236
237 type Inputs = Vec<OrderedFloat<f64>>;
238
239 thread_local! {
240 static INPUTS: RefCell<Option<Inputs>> = RefCell::new(Some(Vec::with_capacity(3)));
241 }
242
243 let mut inputs = INPUTS.take().unwrap();
244
245 for ControlPointExpr { input_value, .. } in control_points {
246 let input_value = OrderedFloat(input_value.value());
247 if let Err(idx) = inputs.binary_search(&input_value) {
248 if inputs.len() == 3 {
249 inputs.clear();
250 INPUTS.set(Some(inputs));
251
252 return false;
253 }
254
255 inputs.insert(idx, input_value);
256 }
257 }
258
259 inputs.clear();
260 INPUTS.set(Some(inputs));
261
262 true
263 }
264
265 if expr.control_points.len() < 4 || invalid_inputs(&expr.control_points) {
267 return Box::new(Constant::new(0.0));
268 }
269
270 let mut res = Curve::new(expr.source.noise());
271
272 for control_point in &expr.control_points {
273 res = res.add_control_point(
274 control_point.input_value.value(),
275 control_point.output_value.value(),
276 );
277 }
278
279 Box::new(res)
280 }
281
282 fn fbm<T>(expr: &FractalExpr) -> Box<Fbm<T>>
283 where
284 T: Default + Seedable,
285 {
286 Box::new(
287 Fbm::<T>::new(expr.seed.value())
288 .set_octaves(expr.octaves.value().clamp(1, MAX_FRACTAL_OCTAVES) as _)
289 .set_frequency(expr.frequency.value())
290 .set_lacunarity(expr.lacunarity.value())
291 .set_persistence(expr.persistence.value()),
292 )
293 }
294
295 fn hybrid_multi<T>(expr: &FractalExpr) -> Box<HybridMulti<T>>
296 where
297 T: Default + Seedable,
298 {
299 Box::new(
300 HybridMulti::<T>::new(expr.seed.value())
301 .set_octaves(expr.octaves.value().clamp(1, MAX_FRACTAL_OCTAVES) as _)
302 .set_frequency(expr.frequency.value())
303 .set_lacunarity(expr.lacunarity.value())
304 .set_persistence(expr.persistence.value()),
305 )
306 }
307
308 pub fn noise(&self) -> Box<dyn NoiseFn<f64, 3>> {
309 match self {
310 Self::Abs(expr) => Box::new(Abs::new(expr.noise())),
311 Self::Add([source1, source2]) => Box::new(Add::new(source1.noise(), source2.noise())),
312 Self::BasicMulti(expr) => match expr.source_ty {
313 SourceType::OpenSimplex => Self::basic_multi::<OpenSimplex>(expr),
314 SourceType::Perlin => Self::basic_multi::<Perlin>(expr),
315 SourceType::PerlinSurflet => Self::basic_multi::<PerlinSurflet>(expr),
316 SourceType::Simplex => Self::basic_multi::<Simplex>(expr),
317 SourceType::SuperSimplex => Self::basic_multi::<OpenSimplex>(expr),
318 SourceType::Value => Self::basic_multi::<Value>(expr),
319 SourceType::Worley => Self::basic_multi::<Worley>(expr),
320 },
321 Self::Billow(expr) => match expr.source_ty {
322 SourceType::OpenSimplex => Self::billow::<OpenSimplex>(expr),
323 SourceType::Perlin => Self::billow::<Perlin>(expr),
324 SourceType::PerlinSurflet => Self::billow::<PerlinSurflet>(expr),
325 SourceType::Simplex => Self::billow::<Simplex>(expr),
326 SourceType::SuperSimplex => Self::billow::<OpenSimplex>(expr),
327 SourceType::Value => Self::billow::<Value>(expr),
328 SourceType::Worley => Self::billow::<Worley>(expr),
329 },
330 Self::Blend(expr) => Box::new(Blend::new(
331 expr.sources[0].noise(),
332 expr.sources[1].noise(),
333 expr.control.noise(),
334 )),
335 Self::Checkerboard(size) => Box::new(Checkerboard::new(size.value() as _)),
336 Self::Clamp(expr) => Box::new(
337 Clamp::new(expr.source.noise())
338 .set_lower_bound(expr.lower_bound.value().min(expr.upper_bound.value()))
339 .set_upper_bound(expr.lower_bound.value().max(expr.upper_bound.value())),
340 ),
341 Self::Constant(value) => Box::new(Constant::new(value.value())),
342 Self::ConstantU32(_) => unreachable!(),
343 Self::Curve(expr) => Self::curve(expr),
344 Self::Cylinders(frequency) => {
345 Box::new(Cylinders::new().set_frequency(frequency.value()))
346 }
347 Self::Displace(expr) => Box::new(Displace::new(
348 expr.source.noise(),
349 expr.axes[0].noise(),
350 expr.axes[1].noise(),
351 expr.axes[2].noise(),
352 expr.axes[3].noise(),
353 )),
354 Self::Exponent(expr) => {
355 Box::new(Exponent::new(expr.source.noise()).set_exponent(expr.exponent.value()))
356 }
357 Self::Fbm(expr) => match expr.source_ty {
358 SourceType::OpenSimplex => Self::fbm::<OpenSimplex>(expr),
359 SourceType::Perlin => Self::fbm::<Perlin>(expr),
360 SourceType::PerlinSurflet => Self::fbm::<PerlinSurflet>(expr),
361 SourceType::Simplex => Self::fbm::<Simplex>(expr),
362 SourceType::SuperSimplex => Self::fbm::<OpenSimplex>(expr),
363 SourceType::Value => Self::fbm::<Value>(expr),
364 SourceType::Worley => Self::fbm::<Worley>(expr),
365 },
366 Self::HybridMulti(expr) => match expr.source_ty {
367 SourceType::OpenSimplex => Self::hybrid_multi::<OpenSimplex>(expr),
368 SourceType::Perlin => Self::hybrid_multi::<Perlin>(expr),
369 SourceType::PerlinSurflet => Self::hybrid_multi::<PerlinSurflet>(expr),
370 SourceType::Simplex => Self::hybrid_multi::<Simplex>(expr),
371 SourceType::SuperSimplex => Self::hybrid_multi::<OpenSimplex>(expr),
372 SourceType::Value => Self::hybrid_multi::<Value>(expr),
373 SourceType::Worley => Self::hybrid_multi::<Worley>(expr),
374 },
375 Self::Max([source1, source2]) => Box::new(Max::new(source1.noise(), source2.noise())),
376 Self::Min([source1, source2]) => Box::new(Min::new(source1.noise(), source2.noise())),
377 Self::Multiply([source1, source2]) => {
378 Box::new(Multiply::new(source1.noise(), source2.noise()))
379 }
380 Self::Negate(expr) => Box::new(Negate::new(expr.noise())),
381 Self::OpenSimplex(seed) => Box::new(OpenSimplex::new(seed.value())),
382 Self::Perlin(seed) => Box::new(Perlin::new(seed.value())),
383 Self::PerlinSurflet(seed) => Box::new(PerlinSurflet::new(seed.value())),
384 Self::Power([source1, source2]) => {
385 Box::new(Power::new(source1.noise(), source2.noise()))
386 }
387 Self::RidgedMulti(expr) => match expr.source_ty {
388 SourceType::OpenSimplex => Self::rigid_multi::<OpenSimplex>(expr),
389 SourceType::Perlin => Self::rigid_multi::<Perlin>(expr),
390 SourceType::PerlinSurflet => Self::rigid_multi::<PerlinSurflet>(expr),
391 SourceType::Simplex => Self::rigid_multi::<Simplex>(expr),
392 SourceType::SuperSimplex => Self::rigid_multi::<OpenSimplex>(expr),
393 SourceType::Value => Self::rigid_multi::<Value>(expr),
394 SourceType::Worley => Self::rigid_multi::<Worley>(expr),
395 },
396 Self::RotatePoint(expr) => Box::new(RotatePoint::new(expr.source.noise()).set_angles(
397 expr.axes[0].value(),
398 expr.axes[1].value(),
399 expr.axes[2].value(),
400 expr.axes[3].value(),
401 )),
402 Self::ScaleBias(expr) => Box::new(
403 ScaleBias::new(expr.source.noise())
404 .set_bias(expr.bias.value())
405 .set_scale(expr.scale.value()),
406 ),
407 Self::ScalePoint(expr) => {
408 Box::new(ScalePoint::new(expr.source.noise()).set_all_scales(
409 expr.axes[0].value(),
410 expr.axes[1].value(),
411 expr.axes[2].value(),
412 expr.axes[3].value(),
413 ))
414 }
415 Self::Select(expr) => Box::new(
416 Select::new(
417 expr.sources[0].noise(),
418 expr.sources[1].noise(),
419 expr.control.noise(),
420 )
421 .set_bounds(expr.lower_bound.value(), expr.upper_bound.value())
422 .set_falloff(expr.falloff.value()),
423 ),
424 Self::Simplex(seed) => Box::new(Simplex::new(seed.value())),
425 Self::SuperSimplex(seed) => Box::new(SuperSimplex::new(seed.value())),
426 Self::Terrace(expr) => Self::terrace(expr),
427 Self::TranslatePoint(expr) => Box::new(
428 TranslatePoint::new(expr.source.noise()).set_all_translations(
429 expr.axes[0].value(),
430 expr.axes[1].value(),
431 expr.axes[2].value(),
432 expr.axes[3].value(),
433 ),
434 ),
435 Self::Turbulence(expr) => match expr.source_ty {
436 SourceType::OpenSimplex => Self::turbulence::<OpenSimplex>(expr),
437 SourceType::Perlin => Self::turbulence::<Perlin>(expr),
438 SourceType::PerlinSurflet => Self::turbulence::<PerlinSurflet>(expr),
439 SourceType::Simplex => Self::turbulence::<Simplex>(expr),
440 SourceType::SuperSimplex => Self::turbulence::<OpenSimplex>(expr),
441 SourceType::Value => Self::turbulence::<Value>(expr),
442 SourceType::Worley => Self::turbulence::<Worley>(expr),
443 },
444 Self::Value(seed) => Box::new(Value::new(seed.value())),
445 Self::Worley(expr) => Box::new(
446 Worley::new(expr.seed.value())
447 .set_frequency(expr.frequency.value())
448 .set_distance_function(match expr.distance_fn {
449 DistanceFunction::Chebyshev => chebyshev,
450 DistanceFunction::Euclidean => euclidean,
451 DistanceFunction::EuclideanSquared => euclidean_squared,
452 DistanceFunction::Manhattan => manhattan,
453 })
454 .set_return_type(match expr.return_ty {
455 ReturnType::Distance => worley::ReturnType::Distance,
456 ReturnType::Value => worley::ReturnType::Value,
457 }),
458 ),
459 }
460 }
461
462 fn rigid_multi<T>(expr: &RigidFractalExpr) -> Box<RidgedMulti<T>>
463 where
464 T: Default + Seedable,
465 {
466 Box::new(
467 RidgedMulti::<T>::new(expr.seed.value())
468 .set_octaves(expr.octaves.value().clamp(1, MAX_FRACTAL_OCTAVES) as _)
469 .set_frequency(expr.frequency.value())
470 .set_lacunarity(expr.lacunarity.value())
471 .set_persistence(expr.persistence.value())
472 .set_attenuation(expr.attenuation.value()),
473 )
474 }
475
476 #[allow(unused)]
477 pub fn set_f64(&mut self, name: &str, value: f64) -> &mut Self {
478 match self {
479 Self::Abs(expr) | Self::Negate(expr) => {
480 expr.set_f64(name, value);
481 }
482 Self::Add(exprs)
483 | Self::Max(exprs)
484 | Self::Min(exprs)
485 | Self::Multiply(exprs)
486 | Self::Power(exprs) => exprs.iter_mut().for_each(|expr| {
487 expr.set_f64(name, value);
488 }),
489 Self::BasicMulti(expr)
490 | Self::Billow(expr)
491 | Self::Fbm(expr)
492 | Self::HybridMulti(expr) => expr.set_f64(name, value),
493 Self::Blend(expr) => expr.set_f64(name, value),
494 Self::Clamp(expr) => expr.set_f64(name, value),
495 Self::Constant(expr) | Self::Cylinders(expr) => expr.set_if_named(name, value),
496 Self::Curve(expr) => expr.set_f64(name, value),
497 Self::Displace(expr) => expr.set_f64(name, value),
498 Self::Exponent(expr) => expr.set_f64(name, value),
499 Self::RidgedMulti(expr) => expr.set_f64(name, value),
500 Self::RotatePoint(expr) | Self::ScalePoint(expr) | Self::TranslatePoint(expr) => {
501 expr.set_f64(name, value)
502 }
503 Self::ScaleBias(expr) => expr.set_f64(name, value),
504 Self::Select(expr) => expr.set_f64(name, value),
505 Self::Terrace(expr) => expr.set_f64(name, value),
506 Self::Turbulence(expr) => expr.set_f64(name, value),
507 Self::Worley(expr) => expr.set_f64(name, value),
508 Self::Checkerboard(_)
509 | Self::ConstantU32(_)
510 | Self::OpenSimplex(_)
511 | Self::Perlin(_)
512 | Self::PerlinSurflet(_)
513 | Self::Simplex(_)
514 | Self::SuperSimplex(_)
515 | Self::Value(_) => (),
516 }
517
518 self
519 }
520
521 #[allow(unused)]
522 pub fn set_u32(&mut self, name: &str, value: u32) -> &mut Self {
523 match self {
524 Self::Abs(expr) | Self::Negate(expr) => {
525 expr.set_u32(name, value);
526 }
527 Self::Add(exprs)
528 | Self::Max(exprs)
529 | Self::Min(exprs)
530 | Self::Multiply(exprs)
531 | Self::Power(exprs) => exprs.iter_mut().for_each(|expr| {
532 expr.set_u32(name, value);
533 }),
534 Self::BasicMulti(expr)
535 | Self::Billow(expr)
536 | Self::Fbm(expr)
537 | Self::HybridMulti(expr) => expr.set_u32(name, value),
538 Self::Blend(expr) => expr.set_u32(name, value),
539 Self::Checkerboard(expr)
540 | Self::ConstantU32(expr)
541 | Self::OpenSimplex(expr)
542 | Self::Perlin(expr)
543 | Self::PerlinSurflet(expr)
544 | Self::Simplex(expr)
545 | Self::SuperSimplex(expr)
546 | Self::Value(expr) => expr.set_if_named(name, value),
547 Self::Clamp(expr) => expr.set_u32(name, value),
548 Self::Curve(expr) => expr.set_u32(name, value),
549 Self::Displace(expr) => expr.set_u32(name, value),
550 Self::Exponent(expr) => expr.set_u32(name, value),
551 Self::RidgedMulti(expr) => expr.set_u32(name, value),
552 Self::RotatePoint(expr) | Self::ScalePoint(expr) | Self::TranslatePoint(expr) => {
553 expr.set_u32(name, value)
554 }
555 Self::Select(expr) => expr.set_u32(name, value),
556 Self::ScaleBias(expr) => expr.set_u32(name, value),
557 Self::Terrace(expr) => expr.set_u32(name, value),
558 Self::Turbulence(expr) => expr.set_u32(name, value),
559 Self::Worley(expr) => expr.set_u32(name, value),
560 Self::Constant(_) | Self::Cylinders(_) => (),
561 }
562
563 self
564 }
565
566 fn turbulence<T>(expr: &TurbulenceExpr) -> Box<Turbulence<Box<dyn NoiseFn<f64, 3>>, T>>
567 where
568 T: Default + Seedable,
569 {
570 Box::new(
571 Turbulence::<Box<dyn NoiseFn<f64, 3>>, T>::new(expr.source.noise())
572 .set_seed(expr.seed.value())
573 .set_frequency(expr.frequency.value())
574 .set_power(expr.power.value())
575 .set_roughness(expr.roughness.value() as _),
576 )
577 }
578
579 fn terrace(expr: &TerraceExpr) -> Box<dyn NoiseFn<f64, 3>> {
580 fn invalid_inputs(control_points: &[Variable<f64>]) -> bool {
581 debug_assert!(control_points.len() >= 2);
582
583 let first_input = OrderedFloat(control_points[0].value());
584
585 for input_value in &control_points[1..] {
586 let input_value = OrderedFloat(input_value.value());
587 if input_value != first_input {
588 return false;
589 }
590 }
591
592 true
593 }
594
595 if expr.control_points.len() < 2 || invalid_inputs(&expr.control_points) {
597 return Box::new(Constant::new(0.0));
598 }
599
600 let mut res = Terrace::new(expr.source.noise()).invert_terraces(expr.inverted);
601
602 for control_point in expr.control_points.iter() {
603 res = res.add_control_point(control_point.value());
604 }
605
606 Box::new(res)
607 }
608}
609
610#[derive(Clone, Copy, Debug, PartialEq, Serialize, Deserialize)]
611pub enum OpType {
612 Add,
613 Divide,
614 Multiply,
615 Subtract,
616}
617
618#[derive(Clone, Copy, Debug, PartialEq, Serialize, Deserialize)]
619pub enum ReturnType {
620 Distance,
621 Value,
622}
623
624#[derive(Clone, Debug, Deserialize, Serialize)]
625pub struct RigidFractalExpr {
626 pub source_ty: SourceType,
627 pub seed: Variable<u32>,
628 pub octaves: Variable<u32>,
629 pub frequency: Variable<f64>,
630 pub lacunarity: Variable<f64>,
631 pub persistence: Variable<f64>,
632 pub attenuation: Variable<f64>,
633}
634
635impl RigidFractalExpr {
636 fn set_f64(&mut self, name: &str, value: f64) {
637 self.frequency.set_if_named(name, value);
638 self.lacunarity.set_if_named(name, value);
639 self.persistence.set_if_named(name, value);
640 self.attenuation.set_if_named(name, value);
641 }
642
643 fn set_u32(&mut self, name: &str, value: u32) {
644 self.seed.set_if_named(name, value);
645 self.octaves.set_if_named(name, value);
646 }
647}
648
649#[derive(Clone, Debug, Deserialize, Serialize)]
650pub struct ScaleBiasExpr {
651 pub source: Box<Expr>,
652
653 pub scale: Variable<f64>,
654 pub bias: Variable<f64>,
655}
656
657impl ScaleBiasExpr {
658 fn set_f64(&mut self, name: &str, value: f64) {
659 self.source.set_f64(name, value);
660 self.scale.set_if_named(name, value);
661 self.bias.set_if_named(name, value);
662 }
663
664 fn set_u32(&mut self, name: &str, value: u32) {
665 self.source.set_u32(name, value);
666 }
667}
668
669#[derive(Clone, Debug, Deserialize, Serialize)]
670pub struct SelectExpr {
671 pub sources: [Box<Expr>; 2],
672 pub control: Box<Expr>,
673
674 pub lower_bound: Variable<f64>,
675 pub upper_bound: Variable<f64>,
676 pub falloff: Variable<f64>,
677}
678
679impl SelectExpr {
680 fn set_f64(&mut self, name: &str, value: f64) {
681 self.sources.iter_mut().for_each(|expr| {
682 expr.set_f64(name, value);
683 });
684 self.control.set_f64(name, value);
685 self.lower_bound.set_if_named(name, value);
686 self.upper_bound.set_if_named(name, value);
687 self.falloff.set_if_named(name, value);
688 }
689
690 fn set_u32(&mut self, name: &str, value: u32) {
691 self.sources.iter_mut().for_each(|expr| {
692 expr.set_u32(name, value);
693 });
694 self.control.set_u32(name, value);
695 }
696}
697
698#[derive(Clone, Copy, Debug, PartialEq, Serialize, Deserialize, Default)]
699pub enum SourceType {
700 OpenSimplex,
701 #[default]
702 Perlin,
703 PerlinSurflet,
704 Simplex,
705 SuperSimplex,
706 Value,
707 Worley,
708}
709
710#[derive(Clone, Debug, Deserialize, Serialize)]
711pub struct TerraceExpr {
712 pub source: Box<Expr>,
713
714 pub inverted: bool,
715 pub control_points: Vec<Variable<f64>>,
716}
717
718impl TerraceExpr {
719 fn set_f64(&mut self, name: &str, value: f64) {
720 self.source.set_f64(name, value);
721 self.control_points
722 .iter_mut()
723 .for_each(|control_point| control_point.set_if_named(name, value));
724 }
725
726 fn set_u32(&mut self, name: &str, value: u32) {
727 self.source.set_u32(name, value);
728 }
729}
730
731#[derive(Clone, Debug, Deserialize, Serialize)]
732pub struct TransformExpr {
733 pub source: Box<Expr>,
734
735 pub axes: [Variable<f64>; 4],
736}
737
738impl TransformExpr {
739 fn set_f64(&mut self, name: &str, value: f64) {
740 self.source.set_f64(name, value);
741 self.axes
742 .iter_mut()
743 .for_each(|axis| axis.set_if_named(name, value));
744 }
745
746 fn set_u32(&mut self, name: &str, value: u32) {
747 self.source.set_u32(name, value);
748 }
749}
750
751#[derive(Clone, Debug, Deserialize, Serialize)]
752pub struct TurbulenceExpr {
753 pub source: Box<Expr>,
754
755 pub source_ty: SourceType,
756 pub seed: Variable<u32>,
757 pub frequency: Variable<f64>,
758 pub power: Variable<f64>,
759 pub roughness: Variable<u32>,
760}
761
762impl TurbulenceExpr {
763 fn set_f64(&mut self, name: &str, value: f64) {
764 self.source.set_f64(name, value);
765 self.frequency.set_if_named(name, value);
766 self.power.set_if_named(name, value);
767 }
768
769 fn set_u32(&mut self, name: &str, value: u32) {
770 self.source.set_u32(name, value);
771 self.seed.set_if_named(name, value);
772 self.roughness.set_if_named(name, value);
773 }
774}
775
776#[derive(Clone, Debug, Deserialize, Serialize)]
777pub enum Variable<T> {
778 #[serde(rename = "Value")]
779 Anonymous(T),
780
781 #[serde(rename = "Variable")]
782 Named(String, T),
783
784 Operation([Box<Self>; 2], OpType),
785}
786
787impl<T> Variable<T> {
788 fn set_if_named(&mut self, name: &str, value: T)
789 where
790 T: Copy,
791 {
792 match self {
793 Self::Anonymous(_) => (),
794 Self::Named(named, valued) => {
795 if named == name {
796 *valued = value;
797 }
798 }
799 Self::Operation(vars, _) => {
800 vars.iter_mut()
801 .for_each(|var| var.set_if_named(name, value));
802 }
803 }
804 }
805}
806
807impl Variable<f64> {
808 fn value(&self) -> f64 {
809 match self {
810 Self::Anonymous(value) | Self::Named(_, value) => *value,
811 Self::Operation(vars, op) => {
812 let (lhs, rhs) = (vars[0].value(), vars[1].value());
813 match op {
814 OpType::Add => lhs + rhs,
815 OpType::Divide => {
816 if rhs != 0.0 {
817 lhs / rhs
818 } else {
819 0.0
820 }
821 }
822 OpType::Multiply => lhs * rhs,
823 OpType::Subtract => lhs - rhs,
824 }
825 }
826 }
827 }
828}
829
830impl Variable<u32> {
831 fn value(&self) -> u32 {
832 match self {
833 Self::Anonymous(value) | Self::Named(_, value) => *value,
834 Self::Operation(vars, op) => {
835 let (lhs, rhs) = (vars[0].value(), vars[1].value());
836 match op {
837 OpType::Add => lhs.checked_add(rhs),
838 OpType::Divide => lhs.checked_div(rhs),
839 OpType::Multiply => lhs.checked_mul(rhs),
840 OpType::Subtract => lhs.checked_sub(rhs),
841 }
842 .unwrap_or_default()
843 }
844 }
845 }
846}
847
848#[derive(Clone, Debug, Deserialize, Serialize)]
849pub struct WorleyExpr {
850 pub seed: Variable<u32>,
851 pub frequency: Variable<f64>,
852 pub distance_fn: DistanceFunction,
853 pub return_ty: ReturnType,
854}
855
856impl WorleyExpr {
857 fn set_f64(&mut self, name: &str, value: f64) {
858 self.frequency.set_if_named(name, value);
859 }
860
861 fn set_u32(&mut self, name: &str, value: u32) {
862 self.seed.set_if_named(name, value);
863 }
864}