【问题标题】:Camera on canvas画布上的相机
【发布时间】:2018-08-09 11:27:03
【问题描述】:

我们需要1000x1000的总图大小,但是VIEW部分只有100x100,怎么办?我能以某种方式指示 VIEW 屏幕的起点和终点的坐标吗?

【问题讨论】:

  • 如果没有看到您当前用于渲染的代码,很难为您提供帮助。否则答案可能只是“是的,您可以”,这可能不是您想要的。
  • 我已经在这里回答了类似的问题stackoverflow.com/questions/50721799/…

标签: javascript canvas


【解决方案1】:

这样的???

Math.rad = function(deg) {
  return deg * Math.PI / 180;
};

let tilesTotalX = 200,
    tilesTotalY = 200,
    tilesVisibleX = 10,
    tilesVisibleY = 7,
    tileWidth = 20,
    tileHeight = 20;

let worldSize = {
    w: tilesTotalX * tileWidth,
    h: tilesTotalY * tileHeight
};

let windowSize = {
    w: tilesVisibleX * tileWidth,
    h: tilesVisibleY * tileHeight
};

let tiles = [];
for (let row = 0; row < tilesTotalY; row++) {
    tiles.push([]);
    for (let col = 0; col < tilesTotalX; col++) {
        let r = (Math.floor(0xFF * (row / tilesTotalY))).toString(16),
            g = (Math.floor(0xFF * (col / tilesTotalX))).toString(16),
            b = (Math.floor(0xFF * Math.random())).toString(16);
        tiles[row].push(`#${r}${g}${b}`);
    }
}

let angle = 0,
step = .3;

let circle = {
    x: Math.round((worldSize.w - windowSize.w) / 2),
    y: Math.round((worldSize.h - windowSize.h) / 2),
    r: Math.round(((worldSize.h - windowSize.h) / 2) * .8),
};

let ctx = c.getContext("2d");
ctx.fillStyle = "#f0f0f0";
ctx.fillRect(0, 0, windowSize.w, windowSize.h);

let fps = 16,
    fpsInterval = 1000 / fps,
    then = Date.now();

(function animate(){
    requestAnimationFrame(animate);

    let now = Date.now(),
        elapsed = now - then;
    if (elapsed > fpsInterval) {
        then = now - (elapsed % fpsInterval);

        angle += step;
        angle %= 360;
        //console.log(angle);

        let windowPosition = {
            x: Math.round(circle.x + Math.cos(Math.rad(angle)) * circle.r),
            y: Math.round(circle.y - Math.sin(Math.rad(angle)) * circle.r)
        };

        let firstVisibleRowIndex = Math.floor(windowPosition.y / tileHeight),
            firstVisibleColIndex = Math.floor(windowPosition.x / tileWidth),
            lastVisibleRowIndex = Math.floor((windowPosition.y + windowSize.h) / tileHeight),
            lastVisibleColIndex = Math.floor((windowPosition.x + windowSize.w) / tileWidth);

        let offset = {
            x: windowPosition.x - tileWidth * Math.floor(windowPosition.x / tileWidth),
            y: windowPosition.y - tileHeight * Math.floor(windowPosition.y / tileHeight)
        };

        ctx.save();
        ctx.translate(-offset.x, -offset.y);
        for (let row = firstVisibleRowIndex; row <= lastVisibleRowIndex; row++) {
            for (let col = firstVisibleColIndex; col <= lastVisibleColIndex; col++) {
                ctx.fillStyle = tiles[row][col];
                ctx.fillRect(
                    tileWidth * (col - firstVisibleColIndex),
                    tileHeight * (row - firstVisibleRowIndex),
                    tileWidth,
                    tileHeight
                );
            }
        }
        ctx.restore();
    }
})();
&lt;canvas id=c width=200 height=140&gt;&lt;/canvas&gt;

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2013-02-16
    • 1970-01-01
    • 2020-05-21
    • 1970-01-01
    • 1970-01-01
    • 2013-06-08
    • 1970-01-01
    相关资源
    最近更新 更多