Skip to content

Commit

Permalink
fix cameraUp when pitch >= 90 (#2417)
Browse files Browse the repository at this point in the history
  • Loading branch information
fuzhenn authored Sep 5, 2024
1 parent 0ca28ec commit 65a7141
Showing 1 changed file with 24 additions and 5 deletions.
29 changes: 24 additions & 5 deletions src/map/Map.Camera.ts
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@ import Map from './Map';
import Point from '../geo/Point';
import Coordinate from '../geo/Coordinate';
import * as mat4 from '../core/util/mat4';
import { subtract, add, scale, normalize, dot, set, distance, angle } from '../core/util/vec3';
import { subtract, add, scale, normalize, dot, set, distance, angle, cross } from '../core/util/vec3';
import { clamp, interpolate, isNumber, isNil, wrap, toDegree, toRadian, Matrix4 } from '../core/util';
import { applyMatrix, matrixToQuaternion, quaternionToMatrix, lookAt, setPosition } from '../core/util/math';
import Browser from '../core/Browser';
Expand Down Expand Up @@ -57,7 +57,7 @@ const RADIAN = Math.PI / 180;
const DEFAULT_FOV = 0.6435011087932844;
const TEMP_COORD = new Coordinate(0, 0);
const TEMP_POINT = new Point(0, 0);
const SOUTH = [0, -1, 0], BEARING = []
const SOUTH = [0, -1, 0], BEARING = [];

const altitudesHasData = (altitudes) => {
if (isNumber(altitudes)) {
Expand Down Expand Up @@ -706,6 +706,7 @@ Map.include(/** @lends Map.prototype */{
_getCameraFar(fov, pitch) {
const cameraCenterDistance = this.cameraCenterDistance = distance(this.cameraPosition, this.cameraLookAt);
const distanceInMeter = cameraCenterDistance / this._meterToGLPoint;
pitch = Math.min(pitch, 85);
pitch = pitch * Math.PI / 180;
const cameraFarDistance = distanceInMeter + this.options['cameraFarUndergroundInMeter'] / Math.cos(pitch);
return Math.max(cameraFarDistance * this._meterToGLPoint, cameraCenterDistance * 5);
Expand Down Expand Up @@ -841,12 +842,11 @@ Map.include(/** @lends Map.prototype */{
// if you want to rotate the map after up an incline,please rotateZ like this:
// let up = new vec3(0,1,0);
// up.rotateZ(target,radians);
const d = dist || 1;
// const up = this.cameraUp = set(this.cameraUp || [0, 0, 0], Math.sin(bearing) * d, Math.cos(bearing) * d, 0);
this.cameraUp = this.cameraUp || [0, 0, 0];
const up = this.cameraUp = set(this.cameraUp, Math.sin(bearing) * d, Math.cos(bearing) * d, Math.sin(pitch) * d);
this.cameraUp = this._getCameraUp(this.cameraUp, this.cameraLookAt, this.cameraPosition, pitch, bearing);
const m = this.cameraWorldMatrix = this.cameraWorldMatrix || createMat4();
lookAt(m, this.cameraPosition, this.cameraLookAt, up);
lookAt(m, this.cameraPosition, this.cameraLookAt, this.cameraUp);

const cameraForward = this.cameraForward || [0, 0, 0];
subtract(cameraForward, this.cameraLookAt, this.cameraPosition);
Expand All @@ -861,6 +861,25 @@ Map.include(/** @lends Map.prototype */{
};
}(),

_getCameraUp: function () {
const q: [number, number, number] = [0, 0, 0];
const c: [number, number, number] = [0, 0, 0];
const axis: [number, number, number] = [0, 0, 0];
return function (out, cameraPosition, cameraLookAt, pitch, bearing) {
set(axis, 0, 0, 1);
if (pitch === 0) {
set(axis, Math.sin(bearing), Math.cos(bearing), 0);
} else if (pitch === Math.PI) {
set(axis, -Math.sin(bearing), -Math.cos(bearing), 0);
}
// https://stackoverflow.com/questions/3427379/effective-way-to-calculate-the-up-vector-for-glulookat-which-points-up-the-y-axi
const lookAt = subtract(q, cameraPosition, cameraLookAt);
normalize(lookAt, lookAt);
const right = cross(c, lookAt, axis);
return cross(out, right, lookAt);
}
}(),

updateCenterAltitude() {
this.getRenderer().setToRedraw();
if (!this.centerAltitude && this._hasAltitudeLayer()) {
Expand Down

0 comments on commit 65a7141

Please sign in to comment.