2017-07-25 42 views
0

我想要做一个简单的粒子爆炸效果,所以当用户点击应用程序的某个地方它得到的用户点击位置,创建一个画布,创建爆炸效果,然后删除画布。画布点击粒子爆炸效果不针对鼠标位置

我完全新的画布,并得到来自这个网站的想法:canvas example

的情况是它没有得到TE点击爆炸效应位置正确,它应该在点击区域中心开始。但是我越远离左/上角,越远到屏幕上我的效果就显示出来了。

因此,这里的一些代码:

在我app.components.ts(其是主要的文件,我需要它的每一页上工作,所以我决定在这里把我的代码),我有以下:

import { Particle } from './Particle'; // IMPORT A PARTICLE FUNCTION 

// THESE ARE MY PARTICLE OPTIONS 
public ANGLE: number = 90; 
public SPEED: number = 8; 
public PARTICLE_SIZE: number = 1; 
public NUMBER_OF_PARTICLES: number = 20; 
public RANGE_OF_ANGLE: number = 360; 
public PARTICLE_LIFESPAN: number = 15; 
public PARTICLE_COLOR: string = 'rgb(255,0,0)'; 
public particles: any[] = []; 
public pCtxWidth: number = window.innerWidth; // not using 
public pCtxHeight: number = window.innerHeight; // not using 

document.addEventListener('click', (data) => { 

    // CREATE MY CANVAS HTML ELEMENT AND APPEND IN THE BODY 
    let c = document.createElement('canvas'); 
    c.className = 'clique'; 
    c.style.position = 'absolute'; 
    c.style.width = String(window.innerWidth) + 'px'; //I'M USING THE WHOLE SCREEN SIZE, BUT IT DOESN'T NEEDS TO BE THAT BIG, IT CAN BE 80px 
    c.style.height = String(window.innerHeight) + 'px'; 
    c.style.left = '0px'; 
    c.style.top = '0px'; 
    document.body.appendChild(c); 

    // GET MY PAGE CLICK POSITION, ALSO TRIED WITHOUT - c.offsetLeft 
    const x = data.pageX - c.offsetLeft, 
     y = data.pageY - c.offsetTop; 

    // CREATE MY 2DCONTEXT AND CALL THE SPARK FUNCTION 
    let pCtx = c.getContext("2d"); 
    this.spark(x, y, this.ANGLE, pCtx, c); 
    this.smartAudio.play('click'); 
}, true); 

// draw a new series of spark particles 
spark = (x, y, angle, pCtx, c) => { 
    // create 20 particles 10 degrees surrounding the angle 
    for (var i = 0; i < this.NUMBER_OF_PARTICLES; i++) { 
     // get an offset between the range of the particle 
     let offset = Math.round(this.RANGE_OF_ANGLE * Math.random()) 
      - this.RANGE_OF_ANGLE/2; 
     let scaleX = Math.round(this.SPEED * Math.random()) + 1; 
     let scaleY = Math.round(this.SPEED * Math.random()) + 1; 
     this.particles.push(new Particle(x, y, 
      Math.cos((angle + offset) * Math.PI/180) * scaleX, 
      Math.sin((angle + offset) * Math.PI/180) * scaleY, 
      this.PARTICLE_LIFESPAN, this.PARTICLE_COLOR, pCtx)); 
    } 
    this.animationUpdate(pCtx, c, x, y); 
} 

animationUpdate = function (pCtx, c, x, y) { 
    // update and draw particles 
    pCtx.clearRect(0, 0, x, y); 
    for (var i = 0; i < this.particles.length; i++) { 
     if (this.particles[i].dead()) { 
      this.particles.splice(i, 1); 
      i--; 
     } 
     else { 
      this.particles[i].update(); 
      this.particles[i].draw(pCtx); 
     } 
    } 
    if (this.particles.length > 0) { 
     // await next frame 
     requestAnimationFrame(() => { this.animationUpdate(pCtx, c, x, y) }); 
    } else { 
     document.body.removeChild(c); 
    } 
} 

这里是我的Particle

export function Particle(x, y, xVelocity, yVelocity, lifespan, color, pCtx) { 
    // set initial alpha to 1.0 (fully visibile) 
    this.alpha = 1.0; 
    // dAlpha is the amount that alpha changes per frame, randomly 
    // scaled around the provided particle lifespan 
    this.dAlpha = 1/(Math.random() * lifespan + 0.001); 

    // updates the particle's position by its velocity each frame, 
    // and adjust's the alpha value 
    this.update = function() { 
    x += xVelocity; 
    y -= yVelocity; 
    this.alpha -= this.dAlpha; 
    if (this.alpha < 0) 
     this.alpha = 0; 
    } 

    // draw the particle to the screen 
    this.draw = function(pCtx: any) { 
    pCtx.save(); 
    pCtx.fillStyle = color; 
    pCtx.globalAlpha = this.alpha; 
    pCtx.beginPath(); 
    pCtx.arc(x, y, 1, 0, 2 * Math.PI, false); 
    pCtx.closePath(); 
    pCtx.fill(); 
    pCtx.restore(); 
    } 

    // returns TRUE if this particle is "dead": 
    // i.e. delete and stop updating it if this returns TRUE 
    this.dead = function() { 
    return this.alpha <= 0; 
    } 
} 

所以一个I做错了什么?我怎样才能让粒子效果爆炸到我点击的地方?

这是我得到的图片,我点击了左上方的X,但爆炸发生在点击区域的下方。

image

在此先感谢。

回答

0

我看不到你设置画布的分辨率,你只是设置画布的显示尺寸。这将解释渲染和用户IO之间的不匹配。

请尝试以下操作当您创建画布

c.style.width = (c.width = innerWidth) + 'px'; 
c.style.height = (c.height = innerHeight) + 'px'; 

将匹配屏幕的分辨率来显示大小,这样,你会在正确的像素位置进行渲染。

+0

很简单,我不能相信哈哈哈感谢的人,解决了我的问题。 –