From fa8730fc57d4dbb28c15677369cdac113e1fec0b Mon Sep 17 00:00:00 2001 From: Oscar Lorentzon Date: Fri, 15 Mar 2024 13:25:29 +0100 Subject: [PATCH] feat: use bearings in pan service Support combined panning for fisheyes with horizontal fov >180 degrees. --- src/viewer/PanService.ts | 41 ++++++++++++---------------------------- 1 file changed, 12 insertions(+), 29 deletions(-) diff --git a/src/viewer/PanService.ts b/src/viewer/PanService.ts index 052c0181..ffd9a2fd 100644 --- a/src/viewer/PanService.ts +++ b/src/viewer/PanService.ts @@ -195,9 +195,7 @@ export class PanService { 0, 2 * Math.PI); - const currentProjectedPoints: number[][] = this._computeProjectedPoints(currentTransform); - - const currentHFov: number = this._computeHorizontalFov(currentProjectedPoints) / 180 * Math.PI; + const currentHFov: number = this._computeHorizontalFov(currentTransform) / 180 * Math.PI; const preferredOverlap: number = Math.PI / 8; let left: [number, Image, Transform, number] = undefined; @@ -210,8 +208,7 @@ export class PanService { reference); const transform: Transform = this._createTransform(a, translation); - const projectedPoints: number[][] = this._computeProjectedPoints(transform); - const hFov: number = this._computeHorizontalFov(projectedPoints) / 180 * Math.PI; + const hFov: number = this._computeHorizontalFov(transform) / 180 * Math.PI; const direction: THREE.Vector3 = this._spatial.viewingDirection(a.rotation); const azimuthal: number = this._spatial.wrap( @@ -367,34 +364,20 @@ export class PanService { image.cameraParameters)); } - private _computeProjectedPoints(transform: Transform): number[][] { + private _computeHorizontalFov(transform: Transform): number { const vertices: number[][] = [[1, 0]]; const directions: number[][] = [[0, 0.5]]; - const pointsPerLine: number = 20; - - return Geo - .computeProjectedPoints( - transform, - vertices, - directions, - pointsPerLine, - this._viewportCoords) - .map(([x, y]) => [Math.abs(x), Math.abs(y)]); - } + const pointsPerLine: number = 12; - private _computeHorizontalFov(projectedPoints: number[][]): number { - const fovs: number[] = projectedPoints - .map( - (projectedPoint: number[]): number => { - return this._coordToFov(projectedPoint[0]); - }); + const bearings = Geo.computeBearings( + transform, vertices, directions, pointsPerLine, this._viewportCoords); + const projections = bearings + .map(b => this._spatial.projectToPlane(b, [0, 1, 0])) + .map(p => [p[0], -p[2]]); - const fov: number = Math.min(...fovs); - - return fov; - } + const angles = projections.map(p => Math.abs(Math.atan2(p[0], p[1]))); + const fov = 2 * Math.max(...angles); - private _coordToFov(x: number): number { - return 2 * Math.atan(x) * 180 / Math.PI; + return this._spatial.radToDeg(fov); } }