Adobe Flex:pushView popView时内存泄漏

时间:2013-11-18 11:46:23

标签: flex memory memory-leaks air adobe

我使用Flex Builder在Adobe Flex中构建的应用程序存在内存泄漏问题。使用30-40分钟后,它开始变得越来越慢。

该应用程序将图像显示为目录,但是当我按下并弹出视图时,我的记忆力会大大增加。

我的想法是,如果我将所有对象设置为null并处理我使用的所有bitmapdata,我可以释放足够的内存来继续使用应用程序而没有任何问题,但似乎问题不存在。

我的应用程序menuView.mxml,categoriesView.mxml和productsView.mxml中有3个视图。

我的应用程序使用TotalMemory在我的电脑(不是平板电脑)中启动:47Mb和私有内存:88 MB

推送并弹出视图5次后,我得到TotalMemory:61Mb和私有内存:101 MB

想象一下,如果我多次这样做。我的Ipad或三星Galaxy Tab中的应用程序开始变得很慢。

为什么会这样?我不知道如何解决这个问题。

请帮忙!非常感谢!!

我在下面放了一些代码。

当我在menuView中时,我使用以下代码将视图从menuView推送到categoriesView

protected function button3_clickHandler(event:MouseEvent):void
{
    if((FlexGlobals.topLevelApplication.getIdClienteServidorCompraActual( )!=null)&&  (FlexGlobals.topLevelApplication.getIdClienteServidorCompraA ctual()>0))
            {
                navigator.pushView(categoriesView);
            }
}

当我在categoriesView中时,我使用以下代码将视图从categoriesView推送到productsView。在这个视图中,每个类别都有3个按钮。

protected function buttonC1_clickHandler(event:MouseEvent):void
{
            //Categoria general con todos
            var ab:ArrayCollection =  getIdAmbienteServidor();
           cleanMemory();
            navigator.pushView(productsView, null);
}



private function cleanMemory():void
{
    result.splice(0);
    result = null;
    System.gc();
}

当我在productsView中时,我使用以下代码来弹出(我使用不同的选项,因为我有不同的选项),从productsView到categoriesView的视图。

protected function button1_clickHandler(event:MouseEvent):void
{
    cleanMemory();               
    navigator.pushView(menuView);        
}

private function cleanMemory():void
{
    if(image1 != null)
    {
        image1.source = "";
        if(image1.bitmapData != null)
        {
            image1.bitmapData.dispose();
        }
    }
    if(image2 != null)
    {
        image2.source = "";

        if(image2.bitmapData != null)
        {
            image2.bitmapData.dispose();
        }
    }

    if(result != null)
    {
        result.splice(0);
        result = null;
    }
    if(result1 != null)
    {
        result1.splice(0);
        result1 = null;
    }
    if(result2 != null)
    {
        result2.splice(0);
        result2 = null;
    }

    dbConnection = null;
    object1 = null;
    object2 = null;
    dataToSave = null;
    cGreyImageSmallAsset = null;
    cRedImageSmallAsset.bitmapData.dispose();
    cRedImageSmallAsset = null;
    cOrangeImageAsset.bitmapData.dispose();
    cOrangeImageAsset = null;
    cGreenImageAsset.bitmapData.dispose();
    cGreenImageAsset = null;
    cPinkImageAsset.bitmapData.dispose();
    cPinkImageAsset = null;
    cBlueImageAsset.bitmapData.dispose();
    cBlueImageAsset = null;
    cGreyImageAsset.bitmapData.dispose();
    cGreyImageAsset = null;
    cRedImageAsset.bitmapData.dispose();
    cRedImageAsset = null;
    cGreenImageSmall = null;
    cOrangeImageSmall = null;
    cPinkImageSmall = null;
    cBlueImageSmall = null;
    cGreyImageSmall = null;
    cRedImageSmall= null;
    cGreenImage = null;
    cPinkImage = null;
    cBlueImage= null;
    cGreyImage = null;
    cRedImage= null;
    cOrangeImage= null;
    System.gc();
}

我用。加载图片。

private function setImages():void
{               
    if(object1!=null)
    {                   
        panelLeft.visible = true;
        buttonLeftMore.visible = true;
        image1.source = "file://" + File.applicationStorageDirectory.nativePath + "/b"+object1.idArchivo+"_500.jpg";
        setObject1MainTexts();
     }
     else
     {
         image1.source = "";
         panelLeft.visible = false;
         buttonLeftMore.visible = false;
     }

     if(object2!=null)
     {   
         panelRight.visible = true;
         buttonRightMore.visible = true;
         image2.source = "file://" + File.applicationStorageDirectory.nativePath + "/b"+object2.idArchivo+"_500.jpg";
         setObject2MainTexts();
     }
     else
     {
         image2.source = "";
         panelRight.visible = false;
         buttonRightMore.visible = false;
     }
  }

当我在categoriesView中时,我使用以下代码来弹出(我使用不同的选项,因为我有不同的选项),从categoriesView到menuView的视图。

protected function button1_clickHandler(event:MouseEvent):void
{
    cleanMemory();
    navigator.pushView(menuPrincipalBelda);
}

private function cleanMemory():void
{
    result.splice(0);
    result = null;
    System.gc();
}

提前致谢!

3 个答案:

答案 0 :(得分:1)

我发现了问题:我没有删除EventListener,现在工作正常。

我给你们留下一些例子。如果你不删除它们,那么内存会增加很多!小心这个。

stage.addEventListener("keyUp", handleButtons, false, 1);
stage.removeEventListener("keyUp",handleButtons,false);
xeasy.addEventListener(ResultEvent.RESULT, AppWS_resultHandler);
xeasy.removeEventListener(ResultEvent.RESULT,AppWS_resultHandler, false);

感谢大家!!

答案 1 :(得分:0)

请记住,Flex Builder使用Flash虚拟机,这可以在必要时释放内存,即使您试图强制他清理垃圾收集器,如果您有空闲内存并且不认为有必要也不会这样做。 在应用程序中所需的图像中测试电影 嵌入式 ,而不是经常加载。因为这可能会让一些低级别的关系。

问候

答案 2 :(得分:0)

当我使用GC时,我发现尝试几种不同的方式变得有利!随着时间的推移,我总共使用了3个,但目前只能找到一个,因为这是一个明显更好的工作在这个应用程序。所以在这里,如果需要我可以发送其他两个也必须只是寻找他们!

        private var gcCount:int;

        private function startGCCycle():void {

            gcCount = 0;
            addEventListener(Event.ENTER_FRAME, doGC);
        }
        private function doGC(evt:Event):void {

            flash.system.System.gc();

            if(++gcCount > 1) {

                removeEventListener(Event.ENTER_FRAME, doGC);
                setTimeout(lastGC, 40);
            }
        }
        private function lastGC():void{
            flash.system.System.gc();
        }
    ]]>

我正在寻找你应该尝试的其他东西,这对我来说非常有用!

FlexGlobals.topLevelApplication.deleteReferenceOnParentDocument(this)我在MXML的creationComplete中使用了这些,我不得不一个接一个地打开45个主画布,但每次都有三个PopUps = 180,这在我工作的GC中很容易处理在!关于aktell