2013-03-20 76 views
0

我想創建一個擴展圈,原因有幾個。對於測試平臺,我使用actionscript來開發它的開始。Actionscript - 擴展圈 - 性能問題

這是我的代碼至今:

編輯

更新的代碼13.39 GMT + 1 - 更新代碼再次

更新的代碼14.54 GMT + 1 - 更新代碼,現在感謝Vesper的幫助

Main.as

package 
{ 
import flash.display.MovieClip; 
import flash.events.Event; 
import Wavelet; 
import flash.geom.Point; 
import flash.events.TimerEvent; 
import flash.utils.Timer; 
import flash.display.Bitmap; 
import flash.display.BitmapData; 
import flash.utils.getTimer; 

public class Main extends MovieClip 
{ 

    var startColor:Number = 0x00AA00; 
    var particleBitmapdata:BitmapData; 
    var m_temptimer:int; 

    private var myVector:Vector.<Wavelet> = new Vector.<Wavelet>(); 
    public function Main() 
    { 
     // constructor code   
     addEventListener(Event.ADDED_TO_STAGE, init); 
     addEventListener(Event.ENTER_FRAME, update); 
    } 

    public function init(evt:Event) 
    { 
     particleBitmapdata = new BitmapData(3,3,false, startColor); 

     var myTimer:Timer = new Timer(100, 0); 
     myTimer.addEventListener(TimerEvent.TIMER, run); 
     myTimer.start(); 
    } 

    public function run(tevt:TimerEvent) 
    { 
     for(var i:int=0; i < 360; i+=1) 
     { 
      myVector.push(new Wavelet(3, 1, i, startColor,particleBitmapdata)); 
      myVector[myVector.length-1].x = stage.stageWidth/2; 
      myVector[myVector.length-1].y = stage.stageHeight/2; 
      addChild(myVector[myVector.length-1]); 
     } 

    } 

    public function update(evt:Event) 
    { 
     var time:int = getTimer(); 
     var dt:Number = (time - m_temptimer) * 0.001; 
     m_temptimer = time; 

     for(var i:int=0; i < myVector.length-1; i++) 
     { 
      var w:Wavelet = myVector[i]; 

      if(w.x > stage.stageWidth || w.x < 0 ) 
      { 
       removeChild(myVector[i]); 
       myVector[i] = null; 
       myVector.splice(i,1); 
      } 
      if(w.y > stage.stageHeight || w.y < 0) 
      { 
       removeChild(myVector[i]); 
       myVector[i] = null; 
       myVector.splice(i,1); 
      } 

     } 

     for(var j:int=0; j < myVector.length; j++) 
     { 
      myVector[j].update(dt); 
     } 
    } 
} 

} 

Wavelet.as

package 
{ 
import flash.display.*; 
import flash.events.*; 
import flash.geom.Point; 
import flash.filters.*; 
import flash.geom.*; 

public class Wavelet extends Bitmap 
{ 
    private var m_velocity:Number; 
    private var m_angle:Number; 
    private var m_radius:Number; 
    private var m_bmd:BitmapData; 
    private var m_color=0x0000FF; 
    private var m_angleX,m_angleY; 

    public function getAngle():Number 
    { 
     return m_angle; 
    } 


    public function getVelocity():Number 
    { 
     return m_velocity; 
    } 

    public function setVelocity(input:Number) 
    { 
     m_velocity = input; 
    } 

    public function Wavelet(radius:int, velocity:Number, angle:Number, color:Number, bitmapData:BitmapData) 
    { 
     // constructor code 
     m_radius = radius; 
     m_angle = angle * Math.PI/180 ; 
     m_velocity = velocity; 
     m_angleX = Math.cos(angle); 
     m_angleY = Math.sin(angle); 
     m_color = color; 
     m_bmd = bitmapData; 
     this.bitmapData = m_bmd; 
    } 

    public function update(dt:Number) 
    { 
     this.x+= m_angleX * m_velocity; 
     this.y+= m_angleY * m_velocity; 
     m_velocity+=dt; 
    } 
} 

} 

無論如何,我得到了它的性能是可怕可怕的慢。 我不想創建一個擴展的圓作爲一個整體,我需要像素來計算它們與牆壁和物體碰撞時,使它們改變方向。

是否有無論如何你可以做一個更好的表現的exanding圈?

+0

通過在每個Wavelet對象中不使用內部更新偵聽器,而是從Main.as處理位置更新,但是性能仍然很差,我自己做了第一次修復。 – Hiam 2013-03-20 09:25:35

回答

0

由於更新代碼而編輯。

首先,你可以把所有的小波常規移動到Wavelet類,以及預緩存Math.sin(angle)Math.cos(angle)到班上vxvy變量。這將爲您節省720 Math.sin()Math.cos()每循環運行。

其次,你在前向循環上拼接了一個粒子 - 在這種情況下,當它之前的粒子會被拼接時,你的向量中的下一個粒子將不會移動。這是一個常見的錯誤,但大多數情況下結果更糟,如果我查詢元素過去splice(),從而得到空例外。

第三,您請求myVector[i]你的循環內的十多倍 - 這個要求是不是在代碼緩存,所以不是你這樣做:var w:Wavelet=myVector[i];並通過w指針地址的一切,它使一個輕微的性能提升,爲Flash不需要經常檢查出界問題或檢索列表元素。

+0

感謝您的幫助,但是當我將更新例程從Wavelet對象移動到Main時,它們一起被刪除(請參閱上面的註釋) – Hiam 2013-03-20 10:47:55

+1

請更新問題中的代碼。也許還有另一個性能提示被重新分配BD所遮擋。 – Vesper 2013-03-20 10:59:39

+0

@Hiam好吧,編輯答案。也許這將會放大一些性能。 – Vesper 2013-03-20 11:21:52