Skip to content
Draft
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
207 changes: 150 additions & 57 deletions src.ts/dynamics/rigid_body.ts
Original file line number Diff line number Diff line change
@@ -1,5 +1,11 @@
import {RawRigidBodySet, RawRigidBodyType} from "../raw";
import {Rotation, RotationOps, Vector, VectorOps} from "../math";
import {
Rotation,
RotationOps,
Vector,
VectorOps,
scratchBuffer
} from "../math";
// #if DIM3
import {SdpMatrix3, SdpMatrix3Ops} from "../math";
// #endif
Expand Down Expand Up @@ -294,42 +300,96 @@ export class RigidBody {
/**
* The world-space translation of this rigid-body.
*/
public translation(): Vector {
let res = this.rawSet.rbTranslation(this.handle);
public translationOriginal(): Vector {
let res = this.rawSet.rbTranslationOriginal(this.handle);
return VectorOps.fromRaw(res);
}

/**
* The world-space orientation of this rigid-body.
*/
public rotation(): Rotation {
let res = this.rawSet.rbRotation(this.handle);
public rotationOriginal(): Rotation {
let res = this.rawSet.rbRotationOriginal(this.handle);
return RotationOps.fromRaw(res);
}

/**
* The world-space translation of this rigid-body.
*
* @param {Vector?} target - The object to be populated. If provided,
* the function returns this object instead of creating a new one.
*/
public translation(target?: Vector): Vector {
this.rawSet.rbTranslation(this.handle, scratchBuffer);
return VectorOps.fromBuffer(scratchBuffer, target);
}

// #if DIM2
/**
* The world-space orientation of this rigid-body.
*/
public rotation(): number {
return this.rawSet.rbRotation(this.handle);
}
// #endif

// #if DIM3
/**
* The world-space orientation of this rigid-body.
*
* @param {Rotation?} target - The object to be populated. If provided,
* the function returns this object instead of creating a new one.
*/
public rotation(target?: Rotation): Rotation {
this.rawSet.rbRotation(this.handle, scratchBuffer);
return RotationOps.fromBuffer(scratchBuffer, target);
}
// #endif

/**
* The world-space next translation of this rigid-body.
*
* If this rigid-body is kinematic this value is set by the `setNextKinematicTranslation`
* method and is used for estimating the kinematic body velocity at the next timestep.
* For non-kinematic bodies, this value is currently unspecified.
*
* @param {Vector?} target - The object to be populated. If provided,
* the function returns this object instead of creating a new one.
*/
public nextTranslation(): Vector {
let res = this.rawSet.rbNextTranslation(this.handle);
return VectorOps.fromRaw(res);
public nextTranslation(target?: Vector): Vector {
this.rawSet.rbNextTranslation(this.handle, scratchBuffer);
return VectorOps.fromBuffer(scratchBuffer, target);
}

// #if DIM2
/**
* The world-space next orientation of this rigid-body.
*
* If this rigid-body is kinematic this value is set by the `setNextKinematicRotation`
* method and is used for estimating the kinematic body velocity at the next timestep.
* For non-kinematic bodies, this value is currently unspecified.
*/
public nextRotation(): Rotation {
let res = this.rawSet.rbNextRotation(this.handle);
return RotationOps.fromRaw(res);
public nextRotation(): number {
return this.rawSet.rbNextRotation(this.handle);
}
// #endif

// #if DIM3
/**
* The world-space next orientation of this rigid-body.
*
* If this rigid-body is kinematic this value is set by the `setNextKinematicRotation`
* method and is used for estimating the kinematic body velocity at the next timestep.
* For non-kinematic bodies, this value is currently unspecified.
*
* @param {Rotation?} target - The object to be populated. If provided,
* the function returns this object instead of creating a new one.
*/
public nextRotation(target?: Rotation): Rotation {
this.rawSet.rbNextRotation(this.handle, scratchBuffer);
return RotationOps.fromBuffer(scratchBuffer, target);
}
// #endif

/**
* Sets the translation of this rigid-body.
Expand Down Expand Up @@ -502,31 +562,39 @@ export class RigidBody {

/**
* The linear velocity of this rigid-body.
*
* @param {Vector?} target - The object to be populated. If provided,
* the function returns this object instead of creating a new one.
*/
public linvel(): Vector {
return VectorOps.fromRaw(this.rawSet.rbLinvel(this.handle));
public linvel(target?: Vector): Vector {
this.rawSet.rbLinvel(this.handle, scratchBuffer);
return VectorOps.fromBuffer(scratchBuffer, target);
}

/**
* The velocity of the given world-space point on this rigid-body.
*
* @param {Vector?} target - The object to be populated. If provided,
* the function returns this object instead of creating a new one.
*/
public velocityAtPoint(point: Vector): Vector {
public velocityAtPoint(point: Vector, target?: Vector): Vector {
const rawPoint = VectorOps.intoRaw(point);
let result = VectorOps.fromRaw(
this.rawSet.rbVelocityAtPoint(this.handle, rawPoint),
);
this.rawSet.rbVelocityAtPoint(this.handle, rawPoint, scratchBuffer);
rawPoint.free();
return result;
return VectorOps.fromBuffer(scratchBuffer, target);
}

// #if DIM3
/**
* The angular velocity of this rigid-body.
*
* @param {Vector?} target - The object to be populated. If provided,
* the function returns this object instead of creating a new one.
*/
public angvel(): Vector {
return VectorOps.fromRaw(this.rawSet.rbAngvel(this.handle));
public angvel(target?: Vector): Vector {
this.rawSet.rbAngvel(this.handle, scratchBuffer);
return VectorOps.fromBuffer(scratchBuffer, target);
}

// #endif

// #if DIM2
Expand All @@ -536,7 +604,6 @@ export class RigidBody {
public angvel(): number {
return this.rawSet.rbAngvel(this.handle);
}

// #endif

/**
Expand All @@ -548,9 +615,13 @@ export class RigidBody {

/**
* The inverse mass taking into account translation locking.
*
* @param {Vector?} target - The object to be populated. If provided,
* the function returns this object instead of creating a new one.
*/
public effectiveInvMass(): Vector {
return VectorOps.fromRaw(this.rawSet.rbEffectiveInvMass(this.handle));
public effectiveInvMass(target?: Vector): Vector {
this.rawSet.rbEffectiveInvMass(this.handle, scratchBuffer);
return VectorOps.fromBuffer(scratchBuffer, target);
}

/**
Expand All @@ -564,16 +635,24 @@ export class RigidBody {

/**
* The center of mass of a rigid-body expressed in its local-space.
*
* @param {Vector?} target - The object to be populated. If provided,
* the function returns this object instead of creating a new one.
*/
public localCom(): Vector {
return VectorOps.fromRaw(this.rawSet.rbLocalCom(this.handle));
public localCom(target?: Vector): Vector {
this.rawSet.rbLocalCom(this.handle, scratchBuffer);
return VectorOps.fromBuffer(scratchBuffer, target);
}

/**
* The world-space center of mass of the rigid-body.
*
* @param {Vector?} target - The object to be populated. If provided,
* the function returns this object instead of creating a new one.
*/
public worldCom(): Vector {
return VectorOps.fromRaw(this.rawSet.rbWorldCom(this.handle));
public worldCom(target?: Vector): Vector {
this.rawSet.rbWorldCom(this.handle, scratchBuffer);
return VectorOps.fromBuffer(scratchBuffer, target);
}

// #if DIM2
Expand All @@ -585,21 +664,21 @@ export class RigidBody {
public invPrincipalInertia(): number {
return this.rawSet.rbInvPrincipalInertia(this.handle);
}

// #endif

// #if DIM3
/**
* The inverse of the principal angular inertia of the rigid-body.
*
* Components set to zero are assumed to be infinite along the corresponding principal axis.
*
* @param {Vector?} target - The object to be populated. If provided,
* the function returns this object instead of creating a new one.
*/
public invPrincipalInertia(): Vector {
return VectorOps.fromRaw(
this.rawSet.rbInvPrincipalInertia(this.handle),
);
public invPrincipalInertia(target?: Vector): Vector {
this.rawSet.rbInvPrincipalInertia(this.handle, scratchBuffer);
return VectorOps.fromBuffer(scratchBuffer, target);
}

// #endif

// #if DIM2
Expand All @@ -609,29 +688,32 @@ export class RigidBody {
public principalInertia(): number {
return this.rawSet.rbPrincipalInertia(this.handle);
}

// #endif

// #if DIM3
/**
* The angular inertia along the principal inertia axes of the rigid-body.
*
* @param {Vector?} target - The object to be populated. If provided,
* the function returns this object instead of creating a new one.
*/
public principalInertia(): Vector {
return VectorOps.fromRaw(this.rawSet.rbPrincipalInertia(this.handle));
public principalInertia(target?: Vector): Vector {
this.rawSet.rbPrincipalInertia(this.handle, scratchBuffer);
return VectorOps.fromBuffer(scratchBuffer, target);
}

// #endif

// #if DIM3
/**
* The principal vectors of the local angular inertia tensor of the rigid-body.
*
* @param {Rotation?} target - The object to be populated. If provided,
* the function returns this object instead of creating a new one.
*/
public principalInertiaLocalFrame(): Rotation {
return RotationOps.fromRaw(
this.rawSet.rbPrincipalInertiaLocalFrame(this.handle),
);
public principalInertiaLocalFrame(target?: Rotation): Rotation {
this.rawSet.rbPrincipalInertiaLocalFrame(this.handle, scratchBuffer);
return RotationOps.fromBuffer(scratchBuffer, target);
}

// #endif

// #if DIM2
Expand All @@ -642,18 +724,19 @@ export class RigidBody {
public effectiveWorldInvInertia(): number {
return this.rawSet.rbEffectiveWorldInvInertia(this.handle);
}

// #endif

// #if DIM3
/**
* The world-space inverse angular inertia tensor of the rigid-body,
* The square-root of the world-space inverse angular inertia tensor of the rigid-body,
* taking into account rotation locking.
*
* @param {SdpMatrix3?} target - The object to be populated. If provided,
* the function returns this object instead of creating a new one.
*/
public effectiveWorldInvInertia(): SdpMatrix3 {
return SdpMatrix3Ops.fromRaw(
this.rawSet.rbEffectiveWorldInvInertia(this.handle),
);
public effectiveWorldInvInertia(target?: SdpMatrix3): SdpMatrix3 {
this.rawSet.rbEffectiveWorldInvInertia(this.handle, scratchBuffer);
return SdpMatrix3Ops.fromBuffer(scratchBuffer, target);
}

// #endif
Expand All @@ -673,11 +756,13 @@ export class RigidBody {
/**
* The effective world-space angular inertia (that takes the potential rotation locking into account) of
* this rigid-body.
*
* @param {SdpMatrix3?} target - The object to be populated. If provided,
* the function returns this object instead of creating a new one.
*/
public effectiveAngularInertia(): SdpMatrix3 {
return SdpMatrix3Ops.fromRaw(
this.rawSet.rbEffectiveAngularInertia(this.handle),
);
public effectiveAngularInertia(target?: SdpMatrix3): SdpMatrix3 {
this.rawSet.rbEffectiveAngularInertia(this.handle, scratchBuffer);
return SdpMatrix3Ops.fromBuffer(scratchBuffer, target);
}

// #endif
Expand Down Expand Up @@ -1084,9 +1169,13 @@ export class RigidBody {
/**
* Retrieves the constant force(s) the user added to this rigid-body
* Returns zero if the rigid-body is not dynamic.
*
* @param {Vector?} target - The object to be populated. If provided,
* the function returns this object instead of creating a new one.
*/
public userForce(): Vector {
return VectorOps.fromRaw(this.rawSet.rbUserForce(this.handle));
public userForce(target?: Vector): Vector {
this.rawSet.rbUserForce(this.handle, scratchBuffer);
return VectorOps.fromBuffer(scratchBuffer, target);
}

// #if DIM2
Expand All @@ -1103,9 +1192,13 @@ export class RigidBody {
/**
* Retrieves the constant torque(s) the user added to this rigid-body
* Returns zero if the rigid-body is not dynamic.
*
* @param {Vector?} target - The object to be populated. If provided,
* the function returns this object instead of creating a new one.
*/
public userTorque(): Vector {
return VectorOps.fromRaw(this.rawSet.rbUserTorque(this.handle));
public userTorque(target?: Vector): Vector {
this.rawSet.rbUserTorque(this.handle, scratchBuffer);
return VectorOps.fromBuffer(scratchBuffer, target);
}
// #endif
}
Expand Down
Loading