use core::ops::{Add, Neg, Sub};
use crate::linear_algebra::{Vector, Vector3D, Vector6D};
use crate::scalar::Numeric;
#[derive(Debug, Clone, Copy, PartialEq)]
pub struct Wrench<T: Numeric = f64> {
force: Vector3D<T>,
torque: Vector3D<T>,
}
impl<T: Numeric> Wrench<T> {
#[inline]
#[must_use]
pub fn new(force: Vector3D<T>, torque: Vector3D<T>) -> Self {
Wrench { force, torque }
}
#[inline]
#[must_use]
pub fn zeros() -> Self {
Wrench {
force: Vector::zeros(),
torque: Vector::zeros(),
}
}
#[inline]
#[must_use]
pub fn from_array(a: [T; 6]) -> Self {
let [vx, vy, vz, wx, wy, wz] = a;
Wrench {
force: Vector::new([vx, vy, vz]),
torque: Vector::new([wx, wy, wz]),
}
}
#[inline]
#[must_use]
pub fn as_array(self) -> [T; 6] {
let [fx, fy, fz] = *self.force.as_array();
let [tx, ty, tz] = *self.torque.as_array();
[fx, fy, fz, tx, ty, tz]
}
#[inline]
#[must_use]
pub fn from_vector(v: Vector6D<T>) -> Self {
Self::from_array(v.into_array())
}
#[inline]
pub fn to_vector(self) -> Vector6D<T> {
Vector::new(self.as_array())
}
#[inline]
pub fn force(self) -> Vector3D<T> {
self.force
}
#[inline]
pub fn torque(self) -> Vector3D<T> {
self.torque
}
#[inline]
#[must_use]
pub fn scale(self, scalar: T) -> Self {
Wrench {
force: self.force.scale(scalar),
torque: self.torque.scale(scalar),
}
}
}
impl<T: Numeric> Add for Wrench<T> {
type Output = Self;
#[inline]
fn add(self, rhs: Self) -> Self {
Wrench {
force: self.force + rhs.force,
torque: self.torque + rhs.torque,
}
}
}
impl<T: Numeric> Sub for Wrench<T> {
type Output = Self;
#[inline]
fn sub(self, rhs: Self) -> Self {
Wrench {
force: self.force - rhs.force,
torque: self.torque - rhs.torque,
}
}
}
impl<T: Numeric> Neg for Wrench<T> {
type Output = Self;
#[inline]
fn neg(self) -> Self {
Wrench {
force: -self.force,
torque: -self.torque,
}
}
}
impl<T: Numeric> From<Vector6D<T>> for Wrench<T> {
#[inline]
fn from(v: Vector6D<T>) -> Self {
Self::from_vector(v)
}
}
impl<T: Numeric> From<Wrench<T>> for Vector6D<T> {
#[inline]
fn from(w: Wrench<T>) -> Self {
w.to_vector()
}
}
impl<T: Numeric> Default for Wrench<T> {
fn default() -> Self {
Self::zeros()
}
}