0

Team,

I am having difficulty trying to adjust placement of an image after it has been zoomed in or out (back to origin zoom level). Using ThreeJSZoomCanvas as my orthographic camera controller. Essentially how the image was being loaded in before was based off its entire height, so a landscape image will be pan-able from left and right, but locked on moving up and down because of the max height zoom. If I were to zoom in, then I'd be able to move around the image well. I am tasked to change the initial image load to be based off width. With this new implementation - the image loads in initially perfectly in center, but once I zoom in and zoom back out to origin zoom, the image gets reset to a y position that I'm not intending. I believe because of the blank screen space on top and bottom of the image, the calculation gets screwed up.

Example Diagram on what's occurring (the top screen image is how it was originally setup to work, bottom 3 screens is what is happening after changing the image load based off width, instead of height)

In the three-js-zoom-canvas.ts file, once the image is loaded, it sets this zoom variable up to have the image load based off width and works well:

this._camera.zoom = (Math.abs(this._camera.left) + Math.abs(this._camera.right)) / this.image.width;

if (this._camera.zoom < minZoom) 
{ 
   this._camera.zoom = minZoom; 
}

this._camera.updateProjectionMatrix();
this._camera = clampBounds(this.image, this._camera);

After zooming in, then out to origin zoom, is when the issue arises - here is the code of its Zoom Updates, with a ClampBounds function:

export function clampBounds(
  image: any,
  orthographicCamera: OrthographicCamera
): OrthographicCamera {

let leftBounds = (-image.width * orthographicCamera.zoom) / 2;
let rightBounds = (image.width * orthographicCamera.zoom) / 2;
let topBounds = (image.height * orthographicCamera.zoom) / 2;
let bottomBounds = (-image.height * orthographicCamera.zoom) / 2;

if (
    //if our camera goes above the top after taking zoom into account
    orthographicCamera.position.y * orthographicCamera.zoom +
      orthographicCamera.top >= topBounds
  ) {
    //set the camera position origin back, accounting for distance from origin and top of the viewport and image itself    
    orthographicCamera.position.y =
      (topBounds - orthographicCamera.top) / orthographicCamera.zoom;
  }

  if (
    orthographicCamera.position.y * orthographicCamera.zoom +
      orthographicCamera.bottom <=
    bottomBounds
  ) {
    orthographicCamera.position.y =
      (bottomBounds - orthographicCamera.bottom) / orthographicCamera.zoom;
  }

  if (
    orthographicCamera.position.x * orthographicCamera.zoom +
      orthographicCamera.left <=
    leftBounds
  ) {
    orthographicCamera.position.x =
      (leftBounds - orthographicCamera.left) / orthographicCamera.zoom;
  }

  if (
    orthographicCamera.position.x * orthographicCamera.zoom +
      orthographicCamera.right >=
    rightBounds
  ) {
    orthographicCamera.position.x =
      (rightBounds - orthographicCamera.right) / orthographicCamera.zoom;
  }

  return orthographicCamera;
}

Would appreciate any assistance on what to calculate to resolve this. Apologies if this is not articulated well, I will reply with any additional questions to give you better understanding.

danronmoon
  • 3,814
  • 5
  • 34
  • 56
mooseda
  • 1
  • 1
  • Thanks for the quick reply. The entire project uses a combination of Typescript, HTML and CSS. The two files I supplied above are of Typescript language. – mooseda Sep 16 '22 at 17:15

0 Answers0