Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

How to center the viewport when the resolution != 1.0 ? #511

Open
peekxc opened this issue Dec 20, 2024 · 2 comments
Open

How to center the viewport when the resolution != 1.0 ? #511

peekxc opened this issue Dec 20, 2024 · 2 comments

Comments

@peekxc
Copy link

peekxc commented Dec 20, 2024

I cannot figure out how to get everything centered and scaled directly, it's a total nightmare.

I just want to move the viewport to be centered at some fixed location. That's all.

However, unless I supply a resolution of 1.0, none of the expected coordinate transforms work.

Here's an example showing this:

<!DOCTYPE html>
  <head>
    <meta charset="utf-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0, maximum-scale=1.0, user-scalable=no">
    <meta name="description" content="">
    <meta name="theme-color" content="#000000">
  </head>
  <body>
  <script type="module">
    import { Application, Graphics, GraphicsContext } from 'pixi.js'
    import { Viewport } from 'pixi-viewport';
  
    const app = await new Application();
    await app.init({ 
      autoResize: false, 
      background: 0xededed,
      autoStart: false,
      transparent: false, 
      resolution: 1.0,  // <- this has to be 1 for centering to work, but I prefer devicePixelRatio
      antialias: true, 
      forceCanvas: false,
    });
    let canvas = app.canvas
    app.renderer.resize(1200,800,1.0) // <- this has to be 1 for centering to work
    canvas.width = 1200;
    canvas.height = 800;
    document.body.appendChild(canvas);
  
    let viewport = new Viewport({
      worldWidth: canvas.width,
      worldHeight: canvas.height,
      passiveWheel: false, 
      events: app.renderer.events,
    });
    viewport.drag().wheel(1e-3).decelerate();
    viewport.fit()
  
    // Construct some random nodes
    let node_context = new pn.GraphicsContext()
      .circle(0, 0, 6)
      .stroke({ width: 1.5, color: 0xFFFFFF })
      .fill({ color: 0x650A5A });
  
    // Add the random nodes to the viewport
    for (let i = 0; i < 300; i++){
      let node = new pn.Graphics(node_context);
      node.x = Math.random() * app.renderer.width; 
      node.y = Math.random() * app.renderer.height; 
      viewport.addChild(node);
    }
  
    // This should be at the center of the viewport!
    let node_c = new pn.Graphics()
      .circle(0, 0, 6)
      .stroke({ width: 1.5, color: 0xFFFFFF })
      .fill({color: 0x000000 });
    node_c.x = 600; 
    node_c.y = 400; 
    viewport.addChild(node_c);
  
    app.stage.addChild(viewport);
    app.start();
    viewport.moveCenter(600, 400); // <- this doesnt work
</script>
</body>
@FelixMo42
Copy link

I'm having the same problems with .fit. Is any body working on this bug? If not I can try to figure it out.

@peekxc
Copy link
Author

peekxc commented Feb 4, 2025

Ahh, I've figured out a lot now.

You need to start the pixi application w/ autoDensity = true. This automatically handles the resolution and scaling needed for High DPI screens. Then, inspired by the app.js of the example, normalize the coordinates with:

this.view.style.width = this.width
this.view.style.height = this.height
this.view.style.left = 0
this.view.style.top = 0

where width and height are the actual canvas width and height attributes, respectively. This seems to make it such that all graphics and plotting need only to work in either the nice and simple 'screen' or 'world' coordinate systems---no manual adjusting for pixel ratios. moveCenter now works in this setting with world coordinates.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

2 participants