在 p5.js 中放大时的模糊精灵
Blurry sprites when scaled up in p5.js
我正在尝试将 p5.js 中的精灵的大小放大一点(2 倍),但它们在渲染时看起来很模糊。显然放大通常不是一个好主意,但是我已经成功地使像素化精灵在原始 JavaScript 中看起来清晰(基于这篇文章:https://nluqo.github.io/broughlike-tutorial/stage1.html)。
在 JS 中我会这样做:
let canvas = document.querySelector("canvas");
let ctx = canvas.getContext("2d");
ctx.imageSmoothingEnabled = false;
画成这样:
let tileSize = 32;
ctx.drawImage(
spritesheet,
sprite*16,
0,
16,
16,
x*tileSize,
y*tileSize,
tileSize,
tileSize
);
当向上缩放精灵时,我得到了一个很好的干净效果(类似于我上面链接的文章中显示的效果)。
现在我正尝试将一些代码移植到 P5.js 以用于演示目的,并且一直在尝试复制上述放大(spritesheet 是 16x16,想呈现为 32x32)并且已经 尝试 复制典型的 ctx
调用,但它们的工作方式似乎不同。另外值得注意的是,我试图从 createCanvas
中获取 canvas 元素并获取 2D 上下文,但该方法不存在。
这是我目前尝试过的方法:
createCanvas(1024, 800);
noSmooth();
...
const spriteSize = 16;
const spriteScaled = 32;
let _c = 0; // col lookup into spritesheet
let _r = 0; // row lookup into spritesheet
test_image = createImage(spriteScaled, spriteScaled);
test_image.copy(
tileMap,
_c * spriteSize,
_r * spriteSize,
spriteSize,
spriteSize,
0,
0,
spriteScaled,
spriteScaled
);
// also tried this:
// test_image.resize(spriteScaled, 0);
此外,我在 style.css
中添加了这个但没有效果:
canvas {
display: block;
image-rendering: -moz-crisp-edges;
image-rendering: -webkit-crisp-edges;
image-rendering: pixelated;
image-rendering: crisp-edges;
}
虽然 noSmooth()
函数会影响使用 image()
函数绘制的图像,但它不会影响 copy()
函数的行为。
let imgUrl = "data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAABAAAAAQCAYAAAAf8/9hAAAABmJLR0QAAAAAAAD5Q7t/AAAAh0lEQVQ4y92TMQ6AIAxFX40bB3HyIE4ex00jm+dj8iDOdRGDWhMim39seeWT8gVbatSEjKIC6DY+DzpvMnUKR3AN/mnp6Inzmg6RFLbAu5p2jG4EoIqNHNhSBegy5QNr8PE5enHwVT8YcK5xmaDv+L7GUgek63xzcr/9NQvWvxhmOz9SmsZi7UmSK41htVcqAAAAAElFTkSuQmCC";
const spriteSize = 16;
const spriteScaled = 32;
let tileMap;
let test_image;
function preload() {
tileMap = loadImage(imgUrl);
}
function setup() {
createCanvas(1024, 800);
noSmooth();
let _c = 0; // col lookup into spritesheet
let _r = 0; // row lookup into spritesheet
test_image = createImage(spriteSize, spriteSize);
// Don't resize when copying. This will cause interpolation to happen.
test_image.copy(
tileMap,
_c * spriteSize,
_r * spriteSize,
spriteSize,
spriteSize,
0,
0,
spriteSize,
spriteSize
);
}
function draw() {
// Only resize when you actually draw the sprite
image(test_image, 0, 0, spriteScaled, spriteScaled);
}
<script src="https://cdnjs.cloudflare.com/ajax/libs/p5.js/1.4.0/p5.js"></script>
我正在尝试将 p5.js 中的精灵的大小放大一点(2 倍),但它们在渲染时看起来很模糊。显然放大通常不是一个好主意,但是我已经成功地使像素化精灵在原始 JavaScript 中看起来清晰(基于这篇文章:https://nluqo.github.io/broughlike-tutorial/stage1.html)。
在 JS 中我会这样做:
let canvas = document.querySelector("canvas");
let ctx = canvas.getContext("2d");
ctx.imageSmoothingEnabled = false;
画成这样:
let tileSize = 32;
ctx.drawImage(
spritesheet,
sprite*16,
0,
16,
16,
x*tileSize,
y*tileSize,
tileSize,
tileSize
);
当向上缩放精灵时,我得到了一个很好的干净效果(类似于我上面链接的文章中显示的效果)。
现在我正尝试将一些代码移植到 P5.js 以用于演示目的,并且一直在尝试复制上述放大(spritesheet 是 16x16,想呈现为 32x32)并且已经 尝试 复制典型的 ctx
调用,但它们的工作方式似乎不同。另外值得注意的是,我试图从 createCanvas
中获取 canvas 元素并获取 2D 上下文,但该方法不存在。
这是我目前尝试过的方法:
createCanvas(1024, 800);
noSmooth();
...
const spriteSize = 16;
const spriteScaled = 32;
let _c = 0; // col lookup into spritesheet
let _r = 0; // row lookup into spritesheet
test_image = createImage(spriteScaled, spriteScaled);
test_image.copy(
tileMap,
_c * spriteSize,
_r * spriteSize,
spriteSize,
spriteSize,
0,
0,
spriteScaled,
spriteScaled
);
// also tried this:
// test_image.resize(spriteScaled, 0);
此外,我在 style.css
中添加了这个但没有效果:
canvas {
display: block;
image-rendering: -moz-crisp-edges;
image-rendering: -webkit-crisp-edges;
image-rendering: pixelated;
image-rendering: crisp-edges;
}
虽然 noSmooth()
函数会影响使用 image()
函数绘制的图像,但它不会影响 copy()
函数的行为。
let imgUrl = "data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAABAAAAAQCAYAAAAf8/9hAAAABmJLR0QAAAAAAAD5Q7t/AAAAh0lEQVQ4y92TMQ6AIAxFX40bB3HyIE4ex00jm+dj8iDOdRGDWhMim39seeWT8gVbatSEjKIC6DY+DzpvMnUKR3AN/mnp6Inzmg6RFLbAu5p2jG4EoIqNHNhSBegy5QNr8PE5enHwVT8YcK5xmaDv+L7GUgek63xzcr/9NQvWvxhmOz9SmsZi7UmSK41htVcqAAAAAElFTkSuQmCC";
const spriteSize = 16;
const spriteScaled = 32;
let tileMap;
let test_image;
function preload() {
tileMap = loadImage(imgUrl);
}
function setup() {
createCanvas(1024, 800);
noSmooth();
let _c = 0; // col lookup into spritesheet
let _r = 0; // row lookup into spritesheet
test_image = createImage(spriteSize, spriteSize);
// Don't resize when copying. This will cause interpolation to happen.
test_image.copy(
tileMap,
_c * spriteSize,
_r * spriteSize,
spriteSize,
spriteSize,
0,
0,
spriteSize,
spriteSize
);
}
function draw() {
// Only resize when you actually draw the sprite
image(test_image, 0, 0, spriteScaled, spriteScaled);
}
<script src="https://cdnjs.cloudflare.com/ajax/libs/p5.js/1.4.0/p5.js"></script>