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

Edges offseted in webgl ortho #6956

Closed
1 of 17 tasks
vicdoval opened this issue Apr 10, 2024 · 10 comments
Closed
1 of 17 tasks

Edges offseted in webgl ortho #6956

vicdoval opened this issue Apr 10, 2024 · 10 comments

Comments

@vicdoval
Copy link

Most appropriate sub-area of p5.js?

  • Accessibility
  • Color
  • Core/Environment/Rendering
  • Data
  • DOM
  • Events
  • Image
  • IO
  • Math
  • Typography
  • Utilities
  • WebGL
  • Build process
  • Unit testing
  • Internationalization
  • Friendly errors
  • Other (specify if possible)

p5.js version

1.91

Web browser and version

123.0.6312.106

Operating system

Windows

Steps to reproduce this

When creating geometry in webgl canvas in ortho() edges get offseted from the fill geometry
download (26)
image
image

link to p5 editor sketch
simpified code:

function setup() {
  createCanvas(800, 1200, WEBGL);
}

function draw() {
  background(220);
  stroke(2);

  propFactor = 0.75;
  ortho(-500 * propFactor, 500 * propFactor, -500, 500, 1, 10000);
  camera(1000, 1000, -1000, 0, 0, 0, 0, 0, 1);
  box(200, 200, 800);
}
@vicdoval vicdoval added the Bug label Apr 10, 2024
Copy link

welcome bot commented Apr 10, 2024

Welcome! 👋 Thanks for opening your first issue here! And to ensure the community is able to respond to your issue, please make sure to fill out the inputs in the issue forms. Thank you!

@davepagurek
Copy link
Contributor

The way we make lines go on top of fills on angled surfaces is by scaling down their coordinates based on their angle here:

float facingCamera = pow(
// The word space tangent's z value is 0 if it's facing the camera
abs(normalize(posqIn-posp).z),
// Using pow() here to ramp `facingCamera` up from 0 to 1 really quickly
// so most lines get scaled and don't get clipped
0.25
);

// using a scale <1 moves the lines towards the camera
// in order to prevent popping effects due to half of
// the line disappearing behind the geometry faces.
float scale = mix(1., 0.995, facingCamera);

The idea (described more in #2938 (comment)) is that when it's perpendicular to the camera, we don't need to move it forward at all, but we want to move it forward a little bit if it's on an angle that points it into the camera a bit.

I think the thing that has changed from before is that the camera is now 800 away from the subject by default, where previously things were closer. So scaling coordinates by 0.995 has a bigger impact than before.

So, if anyone wants to tackle this, some things to try:

  • Can we use a scaling factor closer to 1? maybe 0.9975?
  • Instead of shrinking the coordinates by a scaling factor (from 0.995 to 1), we subtract something from the z value to move it forward a constant amount?

@JordanSucher
Copy link
Contributor

JordanSucher commented May 21, 2024

Changing the scaling factor to 0.9985 seems to eliminate this problem, without causing any issues on the more complicated graphic from #2938

image

shape.rotation.mov

Subtracting a constant of 1.0 from the z value also works, and with fewer 'jumping' artifacts:

shape.rotation.2.mov

@davepagurek
Copy link
Contributor

Awesome, thanks for experimenting with this! Maybe we should be going with the constant offset then. Maybe the last test we should run is just drawing some rectangles on top of each other at the same depth (basically a 2d sketch but in WebGL) to make sure the latest drawn rectangle goes on top without earlier strokes poking through. If that still works, feel free to open a PR with this!

@JordanSucher
Copy link
Contributor

JordanSucher commented May 21, 2024

Good call - I tested 2 squares and found that the biggest I could offset before the stroke clipped through was ~0.00045, which isn't enough to fix the stroke jumping issue with more complex objects like the sphere above - though it does fix the edge clipping with the 3d cubes.

Perhaps there's something we could do to more explicitly handle rendering 2d shapes when using webGL? Like setting a z-offset to shift shapes that should be on top forward a bit, to create a little more room for the stroke z-offset?

@davepagurek
Copy link
Contributor

Perhaps there's something we could do to more explicitly handle rendering 2d shapes when using webGL? Like setting a z-offset to shift shapes that should be on top forward a bit, to create a little more room for the stroke z-offset?

This is a tough one because you could change the camera angle and see through the gap between them.

When you were doing the offset, was that still using a mix(a, b, facingCamera) to use an offset of 0 when facingCamera == 0? if not, that could be something to try -- facingCamera is something kinda like a 2d-ish detector, since 2d lines will have facingCamera == 0.

@JordanSucher
Copy link
Contributor

Using float zOffset = mix(-0.00045, -1., facingCamera) solves the square overlaps but reintroduces some of the jumping effects in 3d. I think it's a good compromise.

Maybe in the future we could conditionally apply the stroke z-offset only to 3d objects

@davepagurek
Copy link
Contributor

that sounds good for now, thanks for your help!

@JordanSucher
Copy link
Contributor

jumping with current code:

complex shape w current scale modifier

jumping with mix z-offset

complex shape w const offset

@davepagurek
Copy link
Contributor

Closed by #7064

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
Status: Bugs with Solutions (No PR or test)
Development

No branches or pull requests

3 participants