Skip to content

Commit 7bfb131

Browse files
committed
[gldemo] fix curved tile layer
- generation corner sourcing was always wrong - needs to be +1 cell to cover the half cell overlap all around - therefore needs to be clipped to the nominal layer bounds
1 parent 70755a2 commit 7bfb131

File tree

2 files changed

+61
-27
lines changed

2 files changed

+61
-27
lines changed

cube/gldemo.js

Lines changed: 48 additions & 27 deletions
Original file line numberDiff line numberDiff line change
@@ -42,7 +42,6 @@ export default async function demo(opts) {
4242
tileSize = 256,
4343
cellSize = 64,
4444

45-
// TODO fix curvy tile layer, needs to have dims N+1 but be scissored to cut outer ring in half
4645
worldWidth = 5,
4746
worldHeight = 5,
4847
showCurvyTiles = true,
@@ -69,26 +68,19 @@ export default async function demo(opts) {
6968
{ glyph: '⛵' }
7069
), { tileSize });
7170

72-
/**
73-
* @param {TileSheet<number>} sheet
74-
* @param {{x: number, y: number}} [offset]
75-
* @returns {Layer}
76-
*/
77-
const makeWorldLayer = ({ texture }, offset = { x: 0, y: 0 }) => {
78-
const layer = makeLayer(gl, {
79-
texture,
80-
cellSize,
81-
left: offset.x,
82-
top: offset.y,
83-
width: worldWidth,
84-
height: worldHeight,
85-
});
86-
return layer;
87-
};
88-
89-
const bg = makeWorldLayer(landCurveTiles);
90-
const fg = makeWorldLayer(foreTiles);
91-
const bgCurved = makeWorldLayer(landCurveTiles, { x: -0.5, y: -0.5 });
71+
const bg = makeLayer(gl, {
72+
texture: landCurveTiles.texture,
73+
cellSize,
74+
width: worldWidth,
75+
height: worldHeight,
76+
});
77+
78+
const fg = makeLayer(gl, {
79+
texture: foreTiles.texture,
80+
cellSize,
81+
width: worldWidth,
82+
height: worldHeight,
83+
});
9284

9385
{
9486
const { randn, random } = makeRandom();
@@ -114,15 +106,31 @@ export default async function demo(opts) {
114106
fg.set(x, y, { layerID, spin });
115107
}
116108
}
109+
}
110+
111+
const bgCurved = makeLayer(gl, {
112+
texture: landCurveTiles.texture,
113+
cellSize,
114+
left: -0.5,
115+
top: -0.5,
116+
width: worldWidth + 1,
117+
height: worldHeight + 1,
118+
});
117119

120+
{
118121
// generate curved terrain layer
119-
const stride = bgCurved.width;
122+
const filled = landCurveTiles.getLayerID(0b1111);
123+
/** @param {number} x @param {number} y */
124+
const isFilled = (x, y) => bg.get(
125+
Math.max(0, Math.min(bg.width - 1, x)),
126+
Math.max(0, Math.min(bg.height - 1, y)),
127+
).layerID == filled ? 1 : 0;
120128
for (let y = 0; y < bgCurved.height; y++) {
121129
for (let x = 0; x < bgCurved.width; x++) {
122-
const nw = isWater[(y + 0) * stride + x + 0];
123-
const ne = isWater[(y + 0) * stride + x + 1];
124-
const sw = isWater[(y + 1) * stride + x + 0];
125-
const se = isWater[(y + 1) * stride + x + 1];
130+
const nw = isFilled(x - 1, y - 1);
131+
const ne = isFilled(x + 0, y - 1);
132+
const sw = isFilled(x - 1, y + 0);
133+
const se = isFilled(x + 0, y + 0);
126134
const tileID = ((nw << 1 | ne) << 1 | se) << 1 | sw;
127135
const layerID = landCurveTiles.getLayerID(tileID);
128136
bgCurved.set(x, y, { layerID });
@@ -149,7 +157,20 @@ export default async function demo(opts) {
149157
gl.clear(gl.COLOR_BUFFER_BIT);
150158

151159
tileRend.draw(function*() {
152-
yield shouldShowCurvyTiles() ? bgCurved : bg;
160+
if (shouldShowCurvyTiles()) {
161+
gl.enable(gl.SCISSOR_TEST);
162+
gl.scissor(
163+
// NOTE: lower left corner, with 0 counting up from bottom edge of viewport
164+
bg.left * cellSize,
165+
gl.canvas.height - (bg.top + bg.height) * cellSize,
166+
bg.width * cellSize,
167+
bg.height * cellSize
168+
);
169+
yield bgCurved;
170+
gl.disable(gl.SCISSOR_TEST);
171+
} else {
172+
yield bg;
173+
}
153174
yield fg;
154175
}());
155176
}

cube/gltiles.js

Lines changed: 13 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -258,6 +258,19 @@ export function makeLayer(gl, {
258258
else index.add(id);
259259
},
260260

261+
/**
262+
* @param {number} x
263+
* @param {number} y
264+
*/
265+
get(x, y) {
266+
if (x < 0 || y < 0 || x >= width || y >= height)
267+
throw new Error(`point: ${JSON.stringify({ x, y })} outside of layer bounds: ${JSON.stringify({ width, height })}`);
268+
const id = Math.floor(y - top) * width + Math.floor(x - left);
269+
const layerID = tileData[id];
270+
const spin = spinData[id];
271+
return { layerID, spin };
272+
},
273+
261274
send() {
262275
gl.bindBuffer(gl.ARRAY_BUFFER, spinBuffer);
263276
gl.bufferData(gl.ARRAY_BUFFER, spinData, gl.STATIC_DRAW);

0 commit comments

Comments
 (0)