我实现了硕士学位的项目。 我必须创建一个三js太空入侵者游戏。
项目进展顺利,但我遇到了问题。我的外星人(THREE.Mesh对象)必须能够随机射击。 为了实现这一点,我创建了一个应该绘制随机数的函数。这个功能有效。 问题来自animate()函数。实际上我不能将SetTimeOut()放在animate()函数中。
SetTimeOut()在第一次调用animate()时工作,但是在没有计时器之后。代码连续执行而不等待计时器。
可能问题来了,因为requestAnimationFrame();
不断调用animate我的代码:
Index.html =>
if (!init())animate();
function animate(){
requestAnimationFrame( animate );
level1.animate();
render();
}
Level.js =>
Level.prototype.animate = function()
{
//Timer doesn't work
var that = this;
//Just a test with a simple console.log test
setTimeout(function() { console.log("test"); },10000);*/
this.sky.rotation.x -=0.005;
this.spaceship.fire();
for (var i=0; i<this.ducks.length;i++)
{
this.ducks[i].move();
if (this.ducks[i].is_ready_to_fire())
this.ducks[i].fire_if_ready();
}
};
通过这个例子,程序将在打印之前第一次等待10秒&#34; test&#34;在第一次通话后,打印&#34;测试&#34;没有等待。
你有什么想法吗?
非常感谢你。
抱歉我的英语不好。
答案 0 :(得分:1)
问题是你需要一个计时器用于你的目的。
如果我理解你的问题,你需要外星人在一段时间后开火。
如果你不关心确切的时间,只关心外星人在随机场合拍摄,我会在每个外星人身上使用一个计数器来计算帧数,直到它射击。
所以你的代码看起来像这样:
var MAX_FRAMES_TO_WAIT = 600000;
Alien.prototype.init = function() {
this.framesUntilFire = Math.round(Math.random() * MAX_FRAMES_TO_WAIT);
}
Alien.prototype.fireWhenReady = function() {
if(--this.framesUntilFire === 0) {
this.fire();
this.framesUntilFire = Math.round(Math.random() * MAX_FRAMES_TO_WAIT);
}
}
function animate() {
requestAnimationFrame(animate);
/* ... */
for (var i=0; i<this.ducks.length;i++)
{
this.ducks[i].move();
this.ducks[i].fireWhenReady();
}
这应该可以解决问题。请注意,这意味着当帧速率越高时,敌人会更快地射击,当帧速率下降时,敌人会更慢。
您也可以通过计算帧速率并将其用作分频器来对抗它。
我希望对你有所帮助!
答案 1 :(得分:0)
您可以通过在上一个计时器完成后重置新计时器来避免每帧设置一个新计时器。一个简单的解决方案是递归的:
Level.prototype.fireDelayed = function() {
setTimeout(function() {
if (!this.currentLevel) {
return;
}
this.fireDelayed();
this.fire();
}.bind(this), Math.random() * 1000);
};
如果级别不再是currentLevel
,它就会停止触发。
这有意义吗?