stricter window position check

notice screen size changes
This commit is contained in:
HF 2022-09-28 11:44:02 +02:00
parent 40b7bbead7
commit d835a93e8c
3 changed files with 54 additions and 49 deletions

View File

@ -106,7 +106,6 @@ persistStore(store, {}, () => {
// listen for resize
//
function onWindowResize() {
console.log('WINDOW RESIZED');
store.dispatch(windowResize());
}
window.addEventListener('resize', onWindowResize);

View File

@ -81,6 +81,7 @@ function correctPositions(state) {
const { windows: newWindows, positions } = state;
const xMax = width - SCREEN_MARGIN_EW;
const yMax = height - SCREEN_MARGIN_S;
const yMin = 0;
let modified = false;
const newPositions = {};
@ -92,12 +93,14 @@ function correctPositions(state) {
width: winWidth,
height: winHeight,
} = positions[id];
const xMin = SCREEN_MARGIN_EW - winWidth;
if (xPos > xMax || yPos > yMax
|| xPos < xMin || yPos < yMin
|| width > winWidth || height > winHeight) {
modified = true;
newPositions[id] = {
xPos: Math.min(xMax, xPos),
yPos: Math.min(yMax, yPos),
xPos: clamp(xPos, xMin, xMax),
yPos: clamp(yPos, yMin, yMax),
width: Math.min(winWidth, width - SCREEN_MARGIN_S),
height: Math.min(winHeight, height - SCREEN_MARGIN_S),
z: positions[id].z,

View File

@ -18,21 +18,9 @@ import {
} from './render2Delements';
import PixelPainterControls from '../controls/PixelPainterControls';
import ChunkLoader from './ChunkLoader2D';
import pixelNotify from './PixelNotify';
// dimensions of offscreen canvas NOT whole canvas
// eslint-disable-next-line max-len
const CANVAS_WIDTH = 2 * Math.ceil(window.screen.width / 2) + TILE_ZOOM_LEVEL * TILE_SIZE;
// eslint-disable-next-line max-len
const CANVAS_HEIGHT = 2 * Math.ceil(window.screen.height / 2) + TILE_ZOOM_LEVEL * TILE_SIZE;
const SCALE_THREASHOLD = Math.min(
CANVAS_WIDTH / TILE_SIZE / 3,
CANVAS_HEIGHT / TILE_SIZE / 3,
);
class Renderer {
is3D = false;
//
@ -61,6 +49,7 @@ class Renderer {
this.canvasMaxTiledZoom = 0;
this.historicalCanvasMaxTiledZoom = 0;
this.hover = false;
this.scaleThreshold = 1;
//--
this.forceNextRender = true;
this.forceNextSubrender = true;
@ -68,29 +57,26 @@ class Renderer {
this.oldHistoricalTime = null;
//--
const viewport = document.createElement('canvas');
viewport.width = window.innerWidth;
viewport.height = window.innerHeight;
viewport.className = 'viewport';
this.viewport = viewport;
document.body.appendChild(this.viewport);
//--
this.resizeHandle = this.resizeHandle.bind(this);
window.addEventListener('resize', this.resizeHandle);
//--
this.canvas = document.createElement('canvas');
this.canvas.width = CANVAS_WIDTH;
this.canvas.height = CANVAS_HEIGHT;
this.onWindowResize();
document.body.appendChild(this.viewport);
//--
this.onWindowResize = this.onWindowResize.bind(this);
window.addEventListener('resize', this.onWindowResize);
const context = this.canvas.getContext('2d');
context.fillStyle = '#000000';
context.fillRect(0, 0, CANVAS_WIDTH, CANVAS_HEIGHT);
context.fillRect(0, 0, this.canvas.width, this.canvas.height);
//--
this.setStore(store);
}
destructor() {
this.controls.dispose();
window.removeEventListener('resize', this.resizeHandle);
window.removeEventListener('resize', this.onWindowResize);
this.viewport.remove();
}
@ -102,10 +88,26 @@ class Renderer {
return this.chunkLoader.getAllChunks();
}
resizeHandle() {
console.log('WIN RESIZED', window.innerWidth, window.innerHeight);
onWindowResize() {
this.viewport.width = window.innerWidth;
this.viewport.height = window.innerHeight;
// dimensions of offscreen canvas NOT whole canvas
const canvasWidth = 2 * Math.ceil(window.screen.width / 2)
+ TILE_ZOOM_LEVEL * TILE_SIZE;
const canvasHeight = 2 * Math.ceil(window.screen.height / 2)
+ TILE_ZOOM_LEVEL * TILE_SIZE;
if (this.canvas.width !== canvasWidth
|| this.canvas.height !== canvasHeight
) {
// eslint-disable-next-line no-console
console.log(`Noticed screen: ${canvasWidth} / ${canvasHeight}`);
this.canvas.width = canvasWidth;
this.canvas.height = canvasHeight;
this.scaleThreshold = Math.min(
canvasWidth / TILE_SIZE / 3,
canvasHeight / TILE_SIZE / 3,
);
}
this.forceNextRender = true;
}
@ -199,7 +201,7 @@ class Renderer {
this.relScale = relScale;
this.updateView(state);
if (prevScale === null
|| viewscale < SCALE_THREASHOLD || prevScale < SCALE_THREASHOLD) {
|| viewscale < this.scaleThreshold || prevScale < this.scaleThreshold) {
this.forceNextRender = true;
} else {
this.forceNextSubrender = true;
@ -249,7 +251,7 @@ class Renderer {
this.chunkLoader.getPixelUpdate(i, j, offset, color);
if (scale < 0.8 || isHistoricalView) return;
const scaleM = (scale > SCALE_THREASHOLD) ? 1 : scale;
const scaleM = (scale > this.scaleThreshold) ? 1 : scale;
const context = this.canvas.getContext('2d');
if (!context) return;
@ -258,10 +260,11 @@ class Renderer {
const [canX, canY] = this.centerChunk
.map((z) => (z + 0.5) * TILE_SIZE - canvasSize / 2);
const px = ((x - canX) * scaleM) + (CANVAS_WIDTH / 2);
const py = ((y - canY) * scaleM) + (CANVAS_HEIGHT / 2);
const { width: canvasWidth, height: canvasHeight } = this.canvas;
const px = ((x - canX) * scaleM) + (canvasWidth / 2);
const py = ((y - canY) * scaleM) + (canvasHeight / 2);
// if not part of our current canvas, do not render
if (px < 0 || px >= CANVAS_WIDTH || py < 0 || py >= CANVAS_HEIGHT) return;
if (px < 0 || px >= canvasWidth || py < 0 || py >= canvasHeight) return;
context.fillStyle = palette.colors[color];
context.fillRect(px, py, scaleM, scaleM);
@ -337,7 +340,7 @@ class Renderer {
const CHUNK_RENDER_RADIUS_Y = Math.ceil(height / TILE_SIZE / 2 / relScale);
// If scale is so large that neighbouring chunks wouldn't fit in canvas,
// do scale = 1 and scale in render()
if (scale > SCALE_THREASHOLD) relScale = 1.0;
if (scale > this.scaleThreshold) relScale = 1.0;
// scale
context.save();
context.fillStyle = '#C4C4C4';
@ -350,8 +353,8 @@ class Renderer {
touch = true;
}
const xOffset = CANVAS_WIDTH / 2 / relScale - TILE_SIZE / 2;
const yOffset = CANVAS_HEIGHT / 2 / relScale - TILE_SIZE / 2;
const xOffset = this.canvas.width / 2 / relScale - TILE_SIZE / 2;
const yOffset = this.canvas.height / 2 / relScale - TILE_SIZE / 2;
const [xc, yc] = chunkPosition; // center chunk
// CLEAN margin
@ -494,24 +497,24 @@ class Renderer {
// If scale is so large that neighbouring chunks wouldn't fit in offscreen
// canvas, do scale = 1 in renderChunks and scale in render()
const canvasCenter = canvasSize / 2;
if (viewscale > SCALE_THREASHOLD) {
if (viewscale > this.scaleThreshold) {
viewportCtx.save();
viewportCtx.scale(viewscale, viewscale);
viewportCtx.drawImage(
this.canvas,
width / 2 / viewscale - CANVAS_WIDTH / 2 + (
width / 2 / viewscale - this.canvas.width / 2 + (
(cx + 0.5) * TILE_SIZE - canvasCenter - x),
height / 2 / viewscale - CANVAS_HEIGHT / 2 + (
height / 2 / viewscale - this.canvas.height / 2 + (
(cy + 0.5) * TILE_SIZE - canvasCenter - y),
);
viewportCtx.restore();
} else {
viewportCtx.drawImage(
this.canvas,
Math.floor(width / 2 - CANVAS_WIDTH / 2
Math.floor(width / 2 - this.canvas.width / 2
+ ((cx + 0.5) * TILE_SIZE / this.tiledScale
- canvasCenter - x) * viewscale),
Math.floor(height / 2 - CANVAS_HEIGHT / 2
Math.floor(height / 2 - this.canvas.height / 2
+ ((cy + 0.5) * TILE_SIZE / this.tiledScale
- canvasCenter - y) * viewscale),
);
@ -563,7 +566,7 @@ class Renderer {
context.imageSmoothingEnabled = true;
}
const scale = (viewscale > SCALE_THREASHOLD) ? 1.0 : viewscale;
const scale = (viewscale > this.scaleThreshold) ? 1.0 : viewscale;
// define how many chunks we will render
// don't render chunks outside of viewport
const { width, height } = viewport;
@ -574,7 +577,7 @@ class Renderer {
context.fillStyle = '#C4C4C4';
// clear canvas and do nothing if no time selected
if (!historicalDate || !historicalTime) {
context.fillRect(0, 0, CANVAS_WIDTH, CANVAS_HEIGHT);
context.fillRect(0, 0, this.canvas.width, this.canvas.height);
context.restore();
return;
}
@ -588,8 +591,8 @@ class Renderer {
touch = true;
}
const xOffset = CANVAS_WIDTH / 2 / scale - TILE_SIZE / 2;
const yOffset = CANVAS_HEIGHT / 2 / scale - TILE_SIZE / 2;
const xOffset = this.canvas.width / 2 / scale - TILE_SIZE / 2;
const yOffset = this.canvas.height / 2 / scale - TILE_SIZE / 2;
const [xc, yc] = chunkPosition; // center chunk
// CLEAN margin
@ -701,24 +704,24 @@ class Renderer {
// If scale is so large that neighbouring chunks wouldn't fit in offscreen
// canvas, do scale = 1 in renderChunks and scale in render()
const canvasCenter = historicalCanvasSize / 2;
if (viewscale > SCALE_THREASHOLD) {
if (viewscale > this.scaleThreshold) {
viewportCtx.save();
viewportCtx.scale(viewscale, viewscale);
viewportCtx.drawImage(
this.canvas,
// eslint-disable-next-line max-len
width / 2 / viewscale - CANVAS_WIDTH / 2 + ((cx + 0.5) * TILE_SIZE - canvasCenter - x),
width / 2 / viewscale - this.canvas.width / 2 + ((cx + 0.5) * TILE_SIZE - canvasCenter - x),
// eslint-disable-next-line max-len
height / 2 / viewscale - CANVAS_HEIGHT / 2 + ((cy + 0.5) * TILE_SIZE - canvasCenter - y),
height / 2 / viewscale - this.canvas.height / 2 + ((cy + 0.5) * TILE_SIZE - canvasCenter - y),
);
viewportCtx.restore();
} else {
viewportCtx.drawImage(
this.canvas,
// eslint-disable-next-line max-len
Math.floor(width / 2 - CANVAS_WIDTH / 2 + ((cx + 0.5) * TILE_SIZE - canvasCenter - x) * viewscale),
Math.floor(width / 2 - this.canvas.width / 2 + ((cx + 0.5) * TILE_SIZE - canvasCenter - x) * viewscale),
// eslint-disable-next-line max-len
Math.floor(height / 2 - CANVAS_HEIGHT / 2 + ((cy + 0.5) * TILE_SIZE - canvasCenter - y) * viewscale),
Math.floor(height / 2 - this.canvas.height / 2 + ((cy + 0.5) * TILE_SIZE - canvasCenter - y) * viewscale),
);
}