SandGame/renderer.js

73 lines
2.1 KiB
JavaScript
Raw Permalink Normal View History

import { ctx, canvas, grid, cols, rows, cellSize, brushSize, cursor } from './state.js';
2026-10-22 14:05:51 +00:00
import { config } from './config.js';
let offscreenCanvas = document.createElement('canvas');
let offscreenCtx = offscreenCanvas.getContext('2d', { willReadFrequently: false });
let imgData = null;
let pixelBuffer = null;
let lastCols = 0;
let lastRows = 0;
2026-10-22 14:05:51 +00:00
const BG_COLOR = 0xFF151211; // 0xAABBGGRR for #111215
2026-10-22 14:05:51 +00:00
function ensureBuffer() {
if (cols !== lastCols || rows !== lastRows || !imgData) {
lastCols = cols;
lastRows = rows;
offscreenCanvas.width = cols;
offscreenCanvas.height = rows;
imgData = offscreenCtx.createImageData(cols, rows);
pixelBuffer = new Uint32Array(imgData.data.buffer);
2026-10-22 14:05:51 +00:00
}
}
export function draw() {
if (cols <= 0 || rows <= 0) return;
ensureBuffer();
const totalPixels = cols * rows;
const style = config.visual.style;
2026-10-22 14:05:51 +00:00
// Fast-fill background or render particles
for (let y = 0; y < rows; y++) {
const rowOffset = y * cols;
for (let x = 0; x < cols; x++) {
const cell = grid[x][y];
if (cell) {
pixelBuffer[rowOffset + x] = cell.u32Color || 0xFFFFFFFF;
} else {
pixelBuffer[rowOffset + x] = BG_COLOR;
2026-10-22 14:05:51 +00:00
}
}
}
offscreenCtx.putImageData(imgData, 0, 0);
// Blit to main canvas with desired smoothing
ctx.imageSmoothingEnabled = (style === 'fuzzy' || style === 'bloby');
if (style === 'fuzzy') {
ctx.filter = 'blur(1px)';
} else {
ctx.filter = 'none';
}
ctx.drawImage(offscreenCanvas, 0, 0, canvas.width, canvas.height);
2026-10-22 14:05:51 +00:00
if (style === 'fuzzy') {
ctx.filter = 'none';
}
// Brush cursor indicator
if (cursor.visible && cursor.x >= 0 && cursor.y >= 0) {
ctx.save();
ctx.beginPath();
const screenRadius = Math.max(cellSize, brushSize * cellSize);
ctx.arc(cursor.x, cursor.y, screenRadius, 0, Math.PI * 2);
ctx.strokeStyle = 'rgba(255, 255, 255, 0.45)';
ctx.lineWidth = 1.5;
ctx.setLineDash([4, 4]);
ctx.stroke();
ctx.restore();
}
2026-10-22 14:05:51 +00:00
}