From 2592873d76dd94d32a092f71cd778a8063ef1273 Mon Sep 17 00:00:00 2001 From: MelekTaus Date: Thu, 24 Sep 2026 08:44:26 +0200 Subject: [PATCH] Pull nearest tilemap uvs a tenth of a texel in, 0.02 still showed lines At 0.02 texel the lines between tiles of a nearest tilemap were gone at the zooms tried first, but still showed at others. The user raised the inset to 0.1 by hand and checked it in the browser. - A tenth of a texel is still far below half a texel, so the texel picked at every pixel centre stays the same. - The comment names the new value. Tests: - tilemap.test.ts follows the value: the inset test expects 0.1/96, the sliver test allows up to 0.25 texel from the edge, and the quad test checks its uvs to 2 digits instead of 3. - ./check.sh: 156 files, 2314 tests, CHECK EXIT 0. Co-Authored-By: Claude Opus 5.5 --- src/viewport/tilemapMesh.ts | 4 ++-- tests/core/tilemap.test.ts | 12 ++++++------ 2 files changed, 8 insertions(+), 8 deletions(-) diff --git a/src/viewport/tilemapMesh.ts b/src/viewport/tilemapMesh.ts index 50adb008..e7b75e3a 100644 --- a/src/viewport/tilemapMesh.ts +++ b/src/viewport/tilemapMesh.ts @@ -54,8 +54,8 @@ export function tileMesh( const half = tile / 2; // Linear sampling needs half a texel so the blend never reaches the neighbour. Nearest needs only // a sliver: at odd zooms a pixel centre on the quad edge can round onto the neighbour's first - // texel and draw a line. 1/50 texel keeps every picked texel the same. - const inset = sheet.smooth ? 0.5 : 0.02; + // texel and draw a line. 1/10 texel keeps every picked texel the same. + const inset = sheet.smooth ? 0.5 : 0.1; const insetX = inset / sheet.textureWidth; const insetY = inset / sheet.textureHeight; let v = 0; diff --git a/tests/core/tilemap.test.ts b/tests/core/tilemap.test.ts index fb38c486..39a948ca 100644 --- a/tests/core/tilemap.test.ts +++ b/tests/core/tilemap.test.ts @@ -500,10 +500,10 @@ describe('the mesh a layer becomes', () => { expect([positions[0], positions[1]]).toEqual([48, 0]); expect([positions[2], positions[3]]).toEqual([72, 0]); // Quadrant (0, 0) of a 96 × 144 sheet cut into 24 px quarters is the first quarter of the uvs. - expect(uvs[0]).toBeCloseTo(0, 3); - expect(uvs[1]).toBeCloseTo(0, 3); - expect(uvs[2]).toBeCloseTo(24 / 96, 3); - expect(uvs[3]).toBeCloseTo(0, 3); + expect(uvs[0]).toBeCloseTo(0, 2); + expect(uvs[1]).toBeCloseTo(0, 2); + expect(uvs[2]).toBeCloseTo(24 / 96, 2); + expect(uvs[3]).toBeCloseTo(0, 2); }); it('pulls the uvs half a texel in when the picture is sampled smoothly', () => { @@ -527,7 +527,7 @@ describe('the mesh a layer becomes', () => { ]; const hard = tileMesh(tiles, 48, { x: 0, y: 0 }, { ...sheet, smooth: false }); const soft = tileMesh(tiles, 48, { x: 0, y: 0 }, { ...sheet, smooth: true }); - expect(hard.uvs[0]).toBeCloseTo(0.02 / 96, 6); + expect(hard.uvs[0]).toBeCloseTo(0.1 / 96, 6); expect(soft.uvs[0]).toBeCloseTo(0.5 / 96, 6); // The positions are untouched: only what is sampled moves, never where it lands. expect([...soft.positions]).toEqual([...hard.positions]); @@ -560,7 +560,7 @@ describe('the mesh a layer becomes', () => { for (const t of [...us, ...vs]) { expect(t).toBeGreaterThan(24); expect(t).toBeLessThan(48); - expect(Math.min(t - 24, 48 - t)).toBeLessThan(0.05); + expect(Math.min(t - 24, 48 - t)).toBeLessThan(0.25); } }); });