p5.js
p5.js copied to clipboard
beginShape(TESS) does not respect UV coordinates when tessellating.
Most appropriate sub-area of p5.js?
- [ ] Accessibility (Web Accessibility)
- [ ] Build tools and processes
- [ ] Color
- [ ] Core/Environment/Rendering
- [ ] Data
- [ ] DOM
- [ ] Events
- [ ] Friendly error system
- [ ] Image
- [ ] IO (Input/Output)
- [ ] Localization
- [ ] Math
- [ ] Unit Testing
- [ ] Typography
- [ ] Utilities
- [X] WebGL
- [ ] Other (specify if possible)
p5.js version
1.4.1
Web browser and version
No response
Operating System
No response
Steps to reproduce this
Steps:
- Use WEB_GL mode
- Specify a texture
- Draw a concave shape using
beginShape(TESS)
and specify UV coordinates
Expected
Tessellation should respect/preserve the specified UV coordinates.
Actual
The resulting set of vertices do not match the specified UV coordinates at all and the texture is displayed but very distorted.
Snippet:
let tex;
function preload() {
tex = loadImage('checkerboard-spotlight.jpeg');
}
function setup() {
createCanvas(400, 400, WEBGL);
textureMode(NORMAL)
}
function draw() {
background(220);
orbitControl(4, 2, 0.1);
scale(3, 3);
translate(-50, -50);
texture(tex);
beginShape(TESS);
vertex(20, 20, 0, 0);
vertex(80, 20, 1, 0);
vertex(80, 40, 1, 0.33);
vertex(40, 40, 0.33, 0.33);
vertex(40, 60, 0.33, 0.67);
vertex(80, 60, 1, 0.67);
vertex(80, 80, 1, 1);
vertex(20, 80, 0, 1);
endShape(CLOSE);
}
I looked into this a little bit to see what it would involve. Our tesselation uses libtess, and I've found another I'm not 100% sure this is correct but I've found another library using libtess and it seems to indicate that it supports arbitrary vertex dimensions. The idea being, instead of passing in [x, y, z]
per vertex, we pass in [x, y, z, u, v]
(or if we have vertex colors and vertex normals, [x, y, z, u, v, r, g, b, nx, ny, nz]
?) and interpolating all of those along with the position data.
If we were to do something like that, it would mean adding texture coordinates (and more) here, which is where we construct the data we pass to libtess: https://github.com/processing/p5.js/blob/05c93858bcf2ed8f7b1c4362cd459c8312369112/src/webgl/p5.RendererGL.js#L1484
We would then need to update our combine and vertex callbacks to handle the extra data, and put it back into p5's buffers when libtess is done. For the combine and vertex callbacks, the aforementioned library has an implementation of this already that we could borrow from.
I think the key is this line, which uses the vertex weights (Barycentric weights?) to interpolate all the data, not just the position, which is what is all that the library does for us and is what we are currently using: https://github.com/floorplanner/polygon-tools/blob/9ae3ec6/src/tesselator.js#L176