我试图制作一个小游戏,用户将鼠标放在从天花板上掉落的圆圈上。圆圈被添加到一个容器中并被推入一个数组中以容纳它们,当它们被鼠标悬停或离开舞台时被移除和拼接。
一切正常,直到几乎同时移除两个圆圈,无论是同时脱落还是非常快速地将两个圆圈移除。发生这种情况时,舞台上的孩子将被移除,但该对象仍然留在阵列中,这意味着另一个圆圈无法取代它,每次出现问题时都会产生一个较少的圆圈。
主时间轴上的代码:
import flash.events.Event;
import flash.events.MouseEvent;
import flash.display.MovieClip;
import flash.display.Sprite;
var ballContainer:Sprite = new Sprite();
addChild(ballContainer);
var maxBalls:uint = 10;
var balls:Array = [];
var ballTypes:Array = [GreenBall];
var ballChances:Array = [800];
var ballVelocities:Array = [1.5];
var ballAccelerations:Array = [1.02];
stage.addEventListener(Event.ENTER_FRAME, onTick);
function onTick(e:Event):void {
while (balls.length < maxBalls){
addBall();
}
}
function addBall():void {
var ballType = ballTypes[0];
var ball = new ballType;
ball.x = Math.ceil(Math.random()*(stage.stageWidth - ball.width));
ball.y = 0 - (ball.height*1.5);
ballContainer.addChild(ball);
balls.push(ball);
}
GreenBall中的代码:
import flash.events.Event;
var mainStage = Sprite(root);
var index = mainStage.balls.indexOf(this);
var velocity:Number = mainStage.ballVelocities[0]*randomNumber(0.5, 1.5);
var acceleration:Number = mainStage.ballAccelerations[0];
this.addEventListener(MouseEvent.MOUSE_OVER, onMouseOver);
function onMouseOver(e:MouseEvent):void {
this.removeEventListener(MouseEvent.MOUSE_OVER, onMouseOver);
removeBall();
}
this.addEventListener(Event.ENTER_FRAME, onTick);
function onTick(e:Event):void {
this.y += velocity;
velocity = velocity*acceleration;
if (this.y > stage.stageHeight + this.height){
this.removeEventListener(MouseEvent.MOUSE_OVER, onMouseOver);
removeBall();
}
}
function removeBall():void {
mainStage.balls.splice(index, 1);//doesn't get spliced if balls are removed too quickly
mainStage.ballContainer.removeChild(this);
this.removeEventListener(Event.ENTER_FRAME, onTick);
}
function randomNumber(min:Number, max:Number):Number {
return Math.random()*(max - min) + min;
}
那是怎么回事?我错误地设置了什么吗?我该如何解决这个问题?
非常感谢任何帮助。
答案 0 :(得分:4)
您的逻辑存在缺陷 - 应在删除时计算index
。通过splice
从数组中删除对象时,删除后的所有元素的索引减1。
这意味着如果您有10个球并且移除了第一个球,则每个其他球的index
值将不正确,并且您将在后续移除时从阵列中移除错误的球。
将indexOf
语句移至removeBall
方法应该可以解决问题:
function removeBall():void
{
var index:int = mainStage.balls.indexOf(this);
if(index >= 0)
{
mainStage.balls.splice(index, 1);
mainStage.ballContainer.removeChild(this);
this.removeEventListener(Event.ENTER_FRAME, onTick);
}
}
为了方便自己,您可以延长Array
并制作remove
功能:
public dynamic class List extends Array
{
public function remove(item:*):void
{
var i:int = indexOf(item);
if(i >= 0) splice(i, 1);
}
}