HTML and CSS Reference
In-Depth Information
Calculate scale using the perspective formula we just covered, and size and position the ball accordingly.
The x and y positions of the ball on the canvas element are calculated from the vanishing point, adding on
the xpos and ypos times the scale . Thus, as scale becomes small, the ball converges on the vanishing
point.
When this example is run in your browser, at first it looks like you're simply dragging the ball with the
mouse. This is because zpos is zero, making scale 1.0. So, no noticeable perspective is applied. As you
press the up cursor key, the ball appears to slide into the distance, as shown in Figure 15-4. Now as you
move the mouse around, the ball moves with it, but much less, giving you a parallax effect. If you want to
set up a scene to use parallax, hard-code the z value for each layer, rather than calculating it dynamically.
Figure 15-4. Perspective in action
You might notice that if you keep pressing the down key, the ball gets very large. This is expected—if you
hold a pebble close to your eye, it looks like a boulder. However, if you continue to press the down key,
you see that the ball grows to an infinite size and then shrinks down again. (It's actually upside down and
reversed, but it's difficult to tell that from a circle.) This is the ball going behind the viewpoint.
Mathematically, what happens is that when zpos is equal to -fl , the formula scale = fl / (fl +
zpos) becomes scale = fl / 0 . In many languages, dividing by zero gives you an error. In JavaScript,
it gives you Infinity . As you decrease zpos even more, you divide fl by a negative number. scale
becomes negative, which when applied to the canvas context, has the effect of flipping the image
coordinate system, so your ball looks upside down and backward.
A simple way to handle this is to make the ball invisible if it goes past a certain point. If zpos is less than or
equal to -fl , you have a problem, so you can test for that condition and handle it. Here's the updated
drawFrame function in document 02-perspective-2.html (the rest of the script is the same as the
previous example):
(function drawFrame () {
window.requestAnimationFrame(drawFrame, canvas);
context.clearRect(0, 0, canvas.width, canvas.height);
if (zpos > -fl) {
var scale = fl / (fl + zpos);
xpos = mouse.x - vpX;
ypos = mouse.y - vpY;
ball.scaleX = ball.scaleY = scale;
ball.x = vpX + xpos * scale;
ball.y = vpY + ypos * scale;
ball.visible = true;
Search WWH ::




Custom Search