use super::BathymetryData;
use crate::{datatype::{Gradient, Point}, error::Result};
use derive_builder::Builder;
#[derive(Builder, Debug, PartialEq)]
pub(crate) struct ConstantSlope {
#[builder(default = "50.0")]
h0: f32,
#[builder(default = "0.0")]
x0: f32,
#[builder(default = "0.0")]
y0: f32,
#[builder(default = "-5e-2")]
dhdx: f32,
#[builder(default = "0.0")]
dhdy: f32,
}
impl BathymetryData for ConstantSlope {
fn depth(&self, point: &Point<f32>) -> Result<f32> {
let x = point.x();
let y = point.y();
if x.is_nan() || y.is_nan() {
Ok(f32::NAN)
} else {
Ok(self.h0 + self.dhdx * (x - self.x0) + self.dhdy * (y - self.y0))
}
}
fn depth_and_gradient(&self, point: &Point<f32>) -> Result<(f32, Gradient<f32>)> {
let x = point.x();
let y = point.y();
if x.is_nan() || y.is_nan() {
Ok((f32::NAN, Gradient::new(f32::NAN, f32::NAN)))
} else {
let h = self.h0 + self.dhdx * (x - self.x0) + self.dhdy * (y - self.y0);
Ok((h, Gradient::new(self.dhdx, self.dhdy)))
}
}
}
impl ConstantSlope {
#[allow(dead_code)]
pub(crate) fn builder() -> ConstantSlopeBuilder {
ConstantSlopeBuilder::default()
}
}
#[cfg(test)]
mod test_constant_slope {
use crate::datatype::Point;
use super::{BathymetryData, ConstantSlope};
#[test]
fn nan_input() {
let c = ConstantSlope {
h0: 100.0,
x0: 0.0,
y0: 0.0,
dhdx: -1e-2,
dhdy: 0.0,
};
assert!(c.depth(&Point::new(f32::NAN, 0.0)).unwrap().is_nan());
assert!(c.depth(&Point::new(0.0, f32::NAN)).unwrap().is_nan());
assert!(c.depth(&Point::new(f32::NAN, f32::NAN)).unwrap().is_nan());
}
}
#[cfg(test)]
mod test_builder {
use super::{ConstantSlope, ConstantSlopeBuilder};
#[test]
fn build_default() {
let c = ConstantSlopeBuilder::default().build().unwrap();
assert_eq!(
c,
ConstantSlope {
h0: 50.0,
x0: 0.0,
y0: 0.0,
dhdx: -5e-2,
dhdy: 0.0
}
);
}
#[test]
fn build() {
let c = ConstantSlopeBuilder::default().h0(42.0).build().unwrap();
assert_eq!(
c,
ConstantSlope {
h0: 42.0,
x0: 0.0,
y0: 0.0,
dhdx: -5e-2,
dhdy: 0.0
}
);
}
#[test]
fn builder() {
let c = ConstantSlope::builder().build().unwrap();
assert_eq!(
c,
ConstantSlope {
h0: 50.0,
x0: 0.0,
y0: 0.0,
dhdx: -5e-2,
dhdy: 0.0
}
);
}
}