This is the 9th day of my participation in the Novembermore Challenge.The final text challenge in 2021
preface
If you stare at the sun all the time, the sun will make you blind. — Lucretius
introduce
In this issue, we will talk about the perspective method, a core principle of a Canvas to make fake 3D, that is, it mainly uses the perspective phenomenon of near big and far small to show the three-dimensional sense of objects. We will do a simple case to analyze how to use the mouse wheel to achieve perspective. Let’s start with the Kangkang effect:
If you have a lot of objects, and each object controls its zoom ratio and gets close enough to go through it, it’s a hassle, and we need a more scientific way to control it. Next, let’s take a case to uncover the secrets.
The body of the
1. Basic interface
class Application {
constructor() {
this.canvas = null; / / the canvas
this.ctx = null; / / environment
this.w = 0; / / wide scene
this.h = 0; / / the scene
this.textures = new Map(a);/ / texture set
this.spriteData = new Map(a);// Sprite data
this.alpha = 1; / / transparency
this.r = 300; // Solar radius
this.x = 0; // Solar x coordinates
this.y = 0; // The sun's Y-axis
this.z = 0; // Solar z-axis coordinates
this.deep = 100; / / stadia
this.init();
}
init() {
/ / initialization
this.canvas = document.getElementById("canvas");
this.ctx = this.canvas.getContext("2d");
window.addEventListener("resize".this.reset.bind(this));
this.reset();
this.textures.set("sun".`.. /assets/sun.png`);
this.load().then(this.render.bind(this));
}
load() {
// Load the texture
const { textures, spriteData } = this;
let n = 0;
return new Promise((resolve, reject) = > {
if (textures.size == 0) resolve();
for (const key of textures.keys()) {
let _img = new Image();
spriteData.set(key, _img);
_img.onload = () = > {
if(++n == textures.size) resolve(); } _img.src = textures.get(key); }})}reset() {
// Screen changes recalculate width height and xy coordinates
this.w = this.canvas.width = this.ctx.width = window.innerWidth;
this.h = this.canvas.height = this.ctx.height = window.innerHeight;
this.x = this.w / 2;
this.y = this.h / 2;
}
render() {
/ / the main rendering
this.draw();
this.step();
this.bindWheel();
}
draw(){
/ / to draw
this.drawSun();
this.drawBackground();
}
bindWheel(){
// Bind the wheel event
}
drawSun(){
// Draw the sun
}
drawBackground(){
// Draw the background
}
step(delta) {
/ / redraw
const { w, h, ctx } = this;
requestAnimationFrame(this.step.bind(this));
ctx.clearRect(0.0, w, h);
this.draw(); }}window.onload = new Application();
Copy the code
We’ll take the canvas and give it a 2D environment, give it width and height, then load the images and store the loaded images in spriteData as sprites to use at any time. Then we haven’t drawn anything substantive, but first write the drawing structure, and then redraw the surface frame by frame. When defining variables, you should have noticed the stadia, which is the distance from the viewpoint to the corresponding point. His definition gives the whole 2D world a sense of space.
2. Paint the background color and sun
drawSun(){
const {w,h,ctx,spriteData,alpha,r,x,y,scale}= this;
let img = spriteData.get("sun");
ctx.save();
ctx.translate(x, y);
ctx.scale(scale,scale);
ctx.globalAlpha = alpha;
ctx.beginPath();
ctx.drawImage(img, -r / 2, - r / 2, r, r);
ctx.closePath();
ctx.restore();
}
drawBackground(){
const {w, h, ctx } = this;
ctx.save();
ctx.fillStyle = "# 000"
ctx.fillRect(0.0, w, h);
ctx.restore();
}
Copy the code
The background is drawn as a solid black rectangle, and the sun, which we will find from the image we just saved into spriteData, is drawn in the center of the screen, but remember that its size scale and transparency alpha are controlled from the outside, and we will use them for perspective.
3. Roller events
With all the foreshadowing done, we will complete the use of perspective in this small event.
bindWheel(){
canvas.addEventListener("wheel".e= > {
this.z += e.deltaY * 0.05;
if (this.z > -this.deep) {
this.alpha =1;
this.scale = this.deep / (this.deep + this.z);
}else{
this.alpha = 0; }}); }Copy the code
You can see we will through the wheel events to change the z axis and z axis will affect the proportion of stadia, further change its size, and we said that the only condition judgment if z coordinate within a specific value, the sun is visible, when he is not in the value of it is through the become invisible, so that every time I need to change the value, z The spatial relationship can be further realized.
conclusion
Do not look at this simple, canvas 2D simulation 3D is a necessary element, very practical. For example, making a 3D particle garden can be done without using WebGL, just using it to simulate the Z axis. The following is a long time ago personal do a cat case, using this method, in the near become large, small distance, if the students ask this cat game why not participate in the cat activities, the answer is THAT I lost the source code…