Skip to content

Commit

Permalink
feat: handle unstable unprojection for fov
Browse files Browse the repository at this point in the history
  • Loading branch information
oscarlorentzon committed Nov 15, 2023
1 parent 7fe4052 commit 0dd4386
Show file tree
Hide file tree
Showing 3 changed files with 69 additions and 17 deletions.
69 changes: 58 additions & 11 deletions src/geo/Geo.ts
Original file line number Diff line number Diff line change
Expand Up @@ -38,6 +38,15 @@ export function computeProjectedPoints(
pointsPerLine: number,
viewportCoords: ViewportCoords): number[][] {

// @ts-ignore
const camera: THREE.Camera = new THREE.Camera();
camera.up.copy(transform.upVector());
camera.position.copy(new THREE.Vector3().fromArray(transform.unprojectSfM([0, 0], 0)));
camera.lookAt(new THREE.Vector3().fromArray(transform.unprojectSfM([0, 0], 10)));
camera.updateMatrix();
camera.updateMatrixWorld(true);


const basicPoints: number[][] = [];

for (let side: number = 0; side < basicVertices.length; ++side) {
Expand All @@ -52,6 +61,33 @@ export function computeProjectedPoints(
}
}


const projectedPoints: number[][] = [];
for (const [index, basicPoint] of basicPoints.entries()) {
const worldPoint = transform.unprojectBasic(basicPoint, 10000);
const cameraPoint = viewportCoords.worldToCamera(worldPoint, camera);
if (cameraPoint[2] > 0) {
continue;
}

projectedPoints.push([
cameraPoint[0] / cameraPoint[2],
cameraPoint[1] / cameraPoint[2],
index,
]);
}


return projectedPoints;
}

export function computeProjectedPointsSafe(
transform: Transform,
basicVertices: number[][],
basicDirections: number[][],
pointsPerLine: number,
viewportCoords: ViewportCoords): number[][] {

// @ts-ignore
const camera: THREE.Camera = new THREE.Camera();
camera.up.copy(transform.upVector());
Expand All @@ -60,17 +96,28 @@ export function computeProjectedPoints(
camera.updateMatrix();
camera.updateMatrixWorld(true);

const projectedPoints = basicPoints
.map(
(basicPoint: number[]): number[] => {
const worldPoint = transform.unprojectBasic(basicPoint, 10000);
const cameraPoint = viewportCoords.worldToCamera(worldPoint, camera);

return [
cameraPoint[0] / cameraPoint[2],
cameraPoint[1] / cameraPoint[2],
];
});
const projectedPoints: number[][] = [];
for (let side: number = 0; side < basicVertices.length; ++side) {
const v: number[] = basicVertices[side];
const d: number[] = basicDirections[side];

for (let i: number = 0; i <= pointsPerLine; ++i) {
const basicPoint = [
v[0] + d[0] * i / pointsPerLine,
v[1] + d[1] * i / pointsPerLine,
];
const worldPoint = transform.unprojectBasic(basicPoint, 10000);
const cameraPoint = viewportCoords.worldToCamera(worldPoint, camera);
if (cameraPoint[2] > 0) {
break;
}

projectedPoints.push([
cameraPoint[0] / cameraPoint[2],
cameraPoint[1] / cameraPoint[2],
]);
}
}

return projectedPoints;
}
4 changes: 4 additions & 0 deletions src/geometry/camera/FisheyeCamera.ts
Original file line number Diff line number Diff line change
Expand Up @@ -90,6 +90,10 @@ vec2 projectToSfm(vec3 bearing, Parameters parameters, Uniforms uniforms) {
float radialPeak = uniforms.radialPeak;
// Projection
if (z < 0.) {
return vec2(POSITIVE_INFINITY, POSITIVE_INFINITY);
}
float r = sqrt(x * x + y * y);
float theta = atan(r, z);
Expand Down
13 changes: 7 additions & 6 deletions src/render/RenderCamera.ts
Original file line number Diff line number Diff line change
Expand Up @@ -419,11 +419,11 @@ export class RenderCamera {
}

private _computeProjectedPoints(transform: Transform): number[][] {
const vertices = [[0, 0], [1, 0]];
const directions = [[1, 0], [0, 1]];
const pointsPerLine = 50;
const vertices = [[0.5, 0], [0.5, 0], [1, 0.5], [1, 0.5]];
const directions = [[-0.5, 0], [0.5, 0], [0, -0.5], [0, 0.5]];
const pointsPerLine = 25;

return Geo.computeProjectedPoints(
return Geo.computeProjectedPointsSafe(
transform,
vertices,
directions,
Expand Down Expand Up @@ -475,7 +475,9 @@ export class RenderCamera {
aspect);
});

const vFovFill = Math.min(...fovs) * 0.995;
const fovMax = 125;
const minFov = Math.min(...fovs) * 0.995;
const vFovFill = Math.min(minFov, fovMax);
if (renderMode === RenderMode.Fill) {
return vFovFill;
}
Expand All @@ -492,7 +494,6 @@ export class RenderCamera {
vFov *= hFovMax / hFovLetterbox;
}

const fovMax = 135;
const vFovMax = aspect > 2 ? vFovFill : fovCoeff * vFovFill;
vFov = Math.min(vFov, vFovMax, fovMax);
vFov = Math.max(vFov, vFovFill);
Expand Down

0 comments on commit 0dd4386

Please sign in to comment.