Skip to content

Commit

Permalink
Optimize: Optimize the lookat function of transform. (galacean#701)
Browse files Browse the repository at this point in the history
* fix:transform lookat
  • Loading branch information
cptbtptpbcptdtptp authored Mar 22, 2022
1 parent bfe1c1a commit d693a51
Showing 1 changed file with 34 additions and 15 deletions.
49 changes: 34 additions & 15 deletions packages/core/src/Transform.ts
Original file line number Diff line number Diff line change
Expand Up @@ -10,7 +10,9 @@ import { UpdateFlagManager } from "./UpdateFlagManager";
*/
export class Transform extends Component {
private static _tempQuat0: Quaternion = new Quaternion();
private static _tempVec3: Vector3 = new Vector3();
private static _tempVec30: Vector3 = new Vector3();
private static _tempVec31: Vector3 = new Vector3();
private static _tempVec32: Vector3 = new Vector3();
private static _tempMat30: Matrix3x3 = new Matrix3x3();
private static _tempMat31: Matrix3x3 = new Matrix3x3();
private static _tempMat32: Matrix3x3 = new Matrix3x3();
Expand Down Expand Up @@ -445,7 +447,7 @@ export class Transform extends Component {
relativeToLocal?: boolean
): void {
if (typeof translationOrX === "number") {
const translate = Transform._tempVec3;
const translate = Transform._tempVec30;
translate.setValue(translationOrX, <number>relativeToLocalOrY, z);
this._translate(translate, relativeToLocal);
} else {
Expand Down Expand Up @@ -496,24 +498,41 @@ export class Transform extends Component {

/**
* Rotate and ensure that the world front vector points to the target world position.
* @param worldPosition - Target world position
* @param targetPosition - Target world position
* @param worldUp - Up direction in world space, default is Vector3(0, 1, 0)
*/
lookAt(worldPosition: Vector3, worldUp?: Vector3): void {
const position = this.worldPosition;
const EPSILON = MathUtil.zeroTolerance;
if (
Math.abs(position.x - worldPosition.x) < EPSILON &&
Math.abs(position.y - worldPosition.y) < EPSILON &&
Math.abs(position.z - worldPosition.z) < EPSILON
) {
lookAt(targetPosition: Vector3, worldUp?: Vector3): void {
const zAxis = Transform._tempVec30;
Vector3.subtract(this.worldPosition, targetPosition, zAxis);
let axisLen = zAxis.length();
if (axisLen <= MathUtil.zeroTolerance) {
// The current position and the target position are almost the same.
return;
}
const rotMat = Transform._tempMat43;
zAxis.scale(1 / axisLen);
const xAxis = Transform._tempVec31;
if (worldUp) {
Vector3.cross(worldUp, zAxis, xAxis);
} else {
xAxis.setValue(zAxis.z, 0, -zAxis.x);
}
axisLen = xAxis.length();
if (axisLen <= MathUtil.zeroTolerance) {
// @todo:
// 1.worldup is(0,0,0)
// 2.worldUp is parallel to zAxis
return;
}
xAxis.scale(1 / axisLen);
const yAxis = Transform._tempVec32;
Vector3.cross(zAxis, xAxis, yAxis);

worldUp = worldUp ?? Transform._tempVec3.setValue(0, 1, 0);
Matrix.lookAt(position, worldPosition, worldUp, rotMat);
Quaternion.invert(rotMat.getRotation(Transform._tempQuat0), this._worldRotationQuaternion);
const rotMat = Transform._tempMat41;
const { elements: e } = rotMat;
(e[0] = xAxis.x), (e[1] = xAxis.y), (e[2] = xAxis.z);
(e[4] = yAxis.x), (e[5] = yAxis.y), (e[6] = yAxis.z);
(e[8] = zAxis.x), (e[9] = zAxis.y), (e[10] = zAxis.z);
rotMat.getRotation(this._worldRotationQuaternion);
}

/**
Expand Down

0 comments on commit d693a51

Please sign in to comment.