2013-05-08 70 views
0

我正在将excel桌面应用程序转换为flex。很明显,excel具有更好的网格功能,但它看起来更好,所以我试图手动重新创建它,而不是使用spark advanceddatagrid/datagrid。为此,我创建了大量的组,并将每个单元格作为嵌入标签的边框容器。它看起来不错,但是在我遍历我的arraycollection时绘制每个组件时需要花费一些时间。创建自定义组件时的性能问题。需要TIPS

的代码类似于此

for each(var factor:Factor in this._model.assessment.factors) 
      { 
       //draw factor header 
       var factorHeaderBackground:BorderContainer = new BorderContainer(); 
       factorHeaderBackground.setStyle("backgroundColor", "0x2d4a6c"); 
       factorHeaderBackground.width = 1370; 
       factorHeaderBackground.height = 30; 

       var factorNameLabel:Label = new Label(); 
       factorNameLabel.percentWidth = 100; 
       factorNameLabel.setStyle("verticalAlign", "middle"); 
       factorNameLabel.setStyle("horizontalAlign", "middle"); 
       factorNameLabel.setStyle("textAlign", "center"); 
       factorNameLabel.setStyle("fontSize", "18"); 
       factorNameLabel.setStyle("color", "white"); 
       factorNameLabel.text = factor.name; 
       factorNameLabel.verticalCenter = 1; 

       factorHeaderBackground.addElement(factorNameLabel) 
       this.chart.addElement(factorHeaderBackground); 
       for each (var metric:Metric in factor.children) 
       { 
        var headerGroup:HGroup = new HGroup(); 
        headerGroup.gap = 0; 
        /** 
        * this adds the first section of the header (far left) 
        * */ 
        var criteriaColumn:VGroup = new VGroup(); 
        criteriaColumn.gap = 0; 

        var topCriteriaHeader:HGroup = new HGroup(); 
        topCriteriaHeader.gap = 0; 
        var bottomCriteriaHeader:HGroup = new HGroup(); 
        bottomCriteriaHeader.gap = 0; 

        //draw top section of criteria header 
        var metricNumberBackground:BorderContainer = new BorderContainer(); 
        metricNumberBackground.setStyle("backgroundColor", "0x6699CC"); 
        metricNumberBackground.width = 70; 
        metricNumberBackground.height = 30; 

        var metricNumberLabel:Label = new Label(); 
        metricNumberLabel.percentWidth = 100; 
        metricNumberLabel.setStyle("verticalAlign", "middle"); 
        metricNumberLabel.setStyle("horizontalAlign", "middle"); 
        metricNumberLabel.setStyle("textAlign", "center"); 
        metricNumberLabel.text = 'Metric ' + metric.measureNumber; 
        metricNumberLabel.verticalCenter = 1; 

        metricNumberBackground.addElement(metricNumberLabel); 

        var metricNameBackground:BorderContainer = new BorderContainer(); 
        metricNameBackground.setStyle("backgroundColor", "0x6699CC"); 
        metricNameBackground.width = 300; 
        metricNameBackground.height = 30; 

        var metricNameLabel:Label = new Label(); 
        metricNameLabel.percentWidth = 100; 
        metricNameLabel.setStyle("verticalAlign", "middle"); 
        metricNameLabel.setStyle("horizontalAlign", "middle"); 
        metricNameLabel.setStyle("textAlign", "center"); 
        metricNameLabel.setStyle("fontSize", "16"); 
        metricNameLabel.setStyle("fontWeight", "bold"); 
        metricNameLabel.text = metric.name; 
        metricNameLabel.verticalCenter = 1; 

        metricNameBackground.addElement(metricNameLabel); 
        topCriteriaHeader.addElement(metricNumberBackground); 
        topCriteriaHeader.addElement(metricNameBackground); 

        criteriaColumn.addElement(topCriteriaHeader); 

        //draw bottom section of criteria header 
        var blankBackground:BorderContainer = new BorderContainer(); 
        blankBackground.setStyle("backgroundColor", "0x6699CC"); 
        blankBackground.width = 70; 
        blankBackground.height = 30; 

        var criteriaNameBackground:BorderContainer = new BorderContainer(); 
        criteriaNameBackground.setStyle("backgroundColor", "0x6699CC"); 
        criteriaNameBackground.width = 300; 
        criteriaNameBackground.height = 30; 

        var criteriaNameLabel:Label = new Label(); 
        criteriaNameLabel.percentWidth = 100; 
        criteriaNameLabel.setStyle("verticalAlign", "middle"); 
        criteriaNameLabel.setStyle("horizontalAlign", "middle"); 
        criteriaNameLabel.setStyle("textAlign", "center"); 
        criteriaNameLabel.setStyle("fontSize", "14"); 
        criteriaNameLabel.setStyle("fontWeight", "bold"); 
        criteriaNameLabel.text = "Criteria"; 
        criteriaNameLabel.verticalCenter = 1; 

        criteriaNameBackground.addElement(criteriaNameLabel); 
        bottomCriteriaHeader.addElement(blankBackground); 
        bottomCriteriaHeader.addElement(criteriaNameBackground); 

        criteriaColumn.addElement(bottomCriteriaHeader); 

        /** 
        * this adds the second section of the header 
        * */ 
        var currentColumn:VGroup = new VGroup(); 
        currentColumn.gap = 0; 

        var bottomCurrentHeader:HGroup = new HGroup(); 
        bottomCurrentHeader.gap = 0; 

        //draw top section of current header 
        var currentBackground:BorderContainer = new BorderContainer(); 
        currentBackground.setStyle("backgroundColor", "0x6699CC"); 
        currentBackground.width = 300; 
        currentBackground.height = 30; 

        var currentLabel:Label = new Label(); 
        currentLabel.percentWidth = 100; 
        currentLabel.setStyle("verticalAlign", "middle"); 
        currentLabel.setStyle("horizontalAlign", "middle"); 
        currentLabel.setStyle("textAlign", "center"); 
        currentLabel.setStyle("fontSize", "18"); 
        currentLabel.setStyle("fontWeight", "bold"); 
        currentLabel.text = 'Current'; 
        currentLabel.verticalCenter = 1; 
        currentBackground.addElement(currentLabel); 

        currentColumn.addElement(currentBackground); 

        //draw bottom section of current header 
        var ratingBackground:BorderContainer = new BorderContainer(); 
        ratingBackground.setStyle("backgroundColor", "0x6699CC"); 
        ratingBackground.width = 60; 
        ratingBackground.height = 30; 

        var ratingLabel:Label = new Label(); 
        ratingLabel.percentWidth = 100; 
        ratingLabel.setStyle("verticalAlign", "middle"); 
        ratingLabel.setStyle("horizontalAlign", "middle"); 
        ratingLabel.setStyle("textAlign", "center"); 
        ratingLabel.setStyle("fontSize", "10"); 
        ratingLabel.setStyle("fontWeight", "bold"); 
        ratingLabel.text = "Rating"; 
        ratingLabel.verticalCenter = 1; 

        ratingBackground.addElement(ratingLabel); 
        bottomCurrentHeader.addElement(ratingBackground); 

        var manualUpDownBackground:BorderContainer = new BorderContainer(); 
        manualUpDownBackground.setStyle("backgroundColor", "0x6699CC"); 
        manualUpDownBackground.width = 60; 
        manualUpDownBackground.height = 30; 

        var manualUpDownLabel:Label = new Label(); 
        manualUpDownLabel.percentWidth = 100; 
        manualUpDownLabel.height = 30; 
        manualUpDownLabel.setStyle("verticalAlign", "top"); 
        manualUpDownLabel.setStyle("horizontalAlign", "middle"); 
        manualUpDownLabel.setStyle("textAlign", "center"); 
        manualUpDownLabel.setStyle("fontSize", "10"); 
        manualUpDownLabel.setStyle("fontWeight", "bold"); 
        manualUpDownLabel.text = "Manual" + "\nUp/Down"; 
        manualUpDownLabel.verticalCenter = -6; 

        manualUpDownBackground.addElement(manualUpDownLabel); 
        bottomCurrentHeader.addElement(manualUpDownBackground); 

        var standardWeightingBackground:BorderContainer = new BorderContainer(); 
        standardWeightingBackground.setStyle("backgroundColor", "0x6699CC"); 
        standardWeightingBackground.width = 60; 
        standardWeightingBackground.height = 30; 

        var standardWeightingLabel:Label = new Label(); 
        standardWeightingLabel.percentWidth = 100; 
        standardWeightingLabel.height = 30 
        standardWeightingLabel.setStyle("verticalAlign", "top"); 
        standardWeightingLabel.setStyle("horizontalAlign", "middle"); 
        standardWeightingLabel.setStyle("textAlign", "center"); 
        standardWeightingLabel.setStyle("fontSize", "10"); 
        standardWeightingLabel.setStyle("fontWeight", "bold"); 
        standardWeightingLabel.text = "Standard" + "\nWeighting"; 
        standardWeightingLabel.verticalCenter = -6; 

        standardWeightingBackground.addElement(standardWeightingLabel); 
        bottomCurrentHeader.addElement(standardWeightingBackground); 

        var customWeightingBackground:BorderContainer = new BorderContainer(); 
        customWeightingBackground.setStyle("backgroundColor", "0x6699CC"); 
        customWeightingBackground.width = 60; 
        customWeightingBackground.height = 30; 

        var customWeightingLabel:Label = new Label(); 
        customWeightingLabel.percentWidth = 100; 
        customWeightingLabel.height = 30; 
        customWeightingLabel.setStyle("verticalAlign", "top"); 
        customWeightingLabel.setStyle("horizontalAlign", "middle"); 
        customWeightingLabel.setStyle("textAlign", "center"); 
        customWeightingLabel.setStyle("fontSize", "10"); 
        customWeightingLabel.setStyle("fontWeight", "bold"); 
        customWeightingLabel.text = "Custom" + "\nWeighting"; 
        customWeightingLabel.verticalCenter = -6; 

        customWeightingBackground.addElement(customWeightingLabel); 
        bottomCurrentHeader.addElement(customWeightingBackground); 

        var scoreBackground:BorderContainer = new BorderContainer(); 
        scoreBackground.setStyle("backgroundColor", "0x6699CC"); 
        scoreBackground.width = 60; 
        scoreBackground.height = 30; 

        var scoreLabel:Label = new Label(); 
        scoreLabel.percentWidth = 100; 
        scoreLabel.setStyle("verticalAlign", "middle"); 
        scoreLabel.setStyle("horizontalAlign", "middle"); 
        scoreLabel.setStyle("textAlign", "center"); 
        scoreLabel.setStyle("fontSize", "10"); 
        scoreLabel.setStyle("fontWeight", "bold"); 
        scoreLabel.text = "Score"; 
        scoreLabel.verticalCenter = 1; 

        scoreBackground.addElement(scoreLabel); 
        bottomCurrentHeader.addElement(scoreBackground); 

        currentColumn.addElement(bottomCurrentHeader); 

        headerGroup.addElement(criteriaColumn); 
        headerGroup.addElement(currentColumn); 
        headerGroup.addElement(rationaleColumn); 
        headerGroup.addElement(futureColumn); 
        headerGroup.addElement(futureRationaleColumn); 

        this.chart.addElement(headerGroup); 

        var criteriaLength:int = metric.children.length; 
        var criterionCounter:int = 0; 

        for each (var criterion:Criterion in metric.children) 
        { 
         criterionCounter += 1; 

         var criteriaGroup:HGroup = new HGroup(); 
         criteriaGroup.gap = 0; 

         //adds name column 
         var criterionNumberBackground:BorderContainer = new BorderContainer(); 
         criterionNumberBackground.setStyle("backgroundColor", criterion.isCritical ? "0xFF9933" : "0xFFFFFF"); 
         criterionNumberBackground.width = 70; 
         criterionNumberBackground.height = 60; 

         var criterionNumberLabel:Label = new Label(); 
         criterionNumberLabel.percentWidth = 100; 
         criterionNumberLabel.setStyle("textAlign", "center"); 
         criterionNumberLabel.setStyle("horizontalAlign", "middle"); 
         criterionNumberLabel.setStyle("verticalAlign", "middle"); 
         criterionNumberLabel.setStyle("fontSize", "12"); 
         criterionNumberLabel.text = criterion.measureNumber; 
         criterionNumberLabel.verticalCenter = 1; 

         criterionNumberBackground.addElement(criterionNumberLabel); 
         criteriaGroup.addElement(criterionNumberBackground); 

         //adds criteria description column  
         var criterionDescriptionBackground:BorderContainer = new BorderContainer(); 
         criterionDescriptionBackground.width = 300; 
         criterionDescriptionBackground.height = 60; 

         var criterionDescriptionLabel:Label = new Label(); 
         criterionDescriptionLabel.percentWidth = 100; 
         criterionDescriptionLabel.setStyle("textAlign", "left"); 
         criterionDescriptionLabel.setStyle("horizontalAlign", "middle"); 
         criterionDescriptionLabel.setStyle("verticalAlign", "middle"); 
         criterionDescriptionLabel.setStyle("fontSize", "12"); 
         criterionDescriptionLabel.text = criterion.description; 
         criterionDescriptionLabel.verticalCenter = 1; 

         criterionDescriptionBackground.addElement(criterionDescriptionLabel); 
         criteriaGroup.addElement(criterionDescriptionBackground); 

         //add current standard rating column 
         var criterionCurrentStandardRatingBackground:BorderContainer = new BorderContainer(); 
         criterionCurrentStandardRatingBackground.setStyle("backgroundColor", criterion.score.currentStandardRatingType.color().toString()); 
         criterionCurrentStandardRatingBackground.width = 60; 
         criterionCurrentStandardRatingBackground.height = 60; 

         var criterionCurrentStandardRatingLabel:Label = new Label(); 
         criterionCurrentStandardRatingLabel.percentWidth = 100; 
         criterionCurrentStandardRatingLabel.setStyle("verticalAlign", "middle"); 
         criterionCurrentStandardRatingLabel.setStyle("horizontalAlign", "middle"); 
         criterionCurrentStandardRatingLabel.setStyle("textAlign", "center"); 
         criterionCurrentStandardRatingLabel.setStyle("fontSize", "12"); 
         criterionCurrentStandardRatingLabel.text = criterion.score.currentStandardRatingType.toString(); 
         criterionCurrentStandardRatingLabel.verticalCenter = 1; 

         criterionCurrentStandardRatingBackground.addElement(criterionCurrentStandardRatingLabel); 
         criteriaGroup.addElement(criterionCurrentStandardRatingBackground); 

         //add current manual/upgrade combobox column     
         var criterionCurrentManualUpgradeDowngradeComboBox:ComboBox = new ComboBox(); 
         criterionCurrentManualUpgradeDowngradeComboBox.width = 60; 
         criterionCurrentManualUpgradeDowngradeComboBox.height = 60; 
         criterionCurrentManualUpgradeDowngradeComboBox.dataProvider = rateTypeComboBoxItems; 
         BindingUtils.bindProperty(criterionCurrentManualUpgradeDowngradeComboBox, "selectedItem", criterion.score, "currentUpgradeDowngradeRatingType"); 
         BindingUtils.bindProperty(criterion.score, "currentUpgradeDowngradeRatingTypeFromComboBox", criterionCurrentManualUpgradeDowngradeComboBox, "selectedItem"); 
         criterionCurrentManualUpgradeDowngradeComboBox.verticalCenter = 1; 
         criterionCurrentManualUpgradeDowngradeComboBox.labelField = "Text"; 

         criteriaGroup.addElement(criterionCurrentManualUpgradeDowngradeComboBox);        

         var totalGroup:HGroup = new HGroup(); 
         totalGroup.gap = 0; 

         //draw last row for each criterion 
         if(criterionCounter == criteriaLength) 
         { 
          //stores weights for current/future 
          var totalCurrentStandardWeight:Number = metric.AggregateWeights(true, true); 
          var totalCurrentCustomWeight:Number = metric.AggregateWeights(true, false); 
          var totalFutureStandardWeight:Number = metric.AggregateWeights(false, true); 
          var totalFutureCustomWeight:Number = metric.AggregateWeights(false, false); 
          //adds total column 
          var criterionTotalBackground:BorderContainer = new BorderContainer(); 
          criterionTotalBackground.setStyle("backgroundColor", "0xa6a6a6"); 
          criterionTotalBackground.width = 370; 
          criterionTotalBackground.height = 15; 

          var criterionTotalLabel:Label = new Label(); 
          criterionTotalLabel.percentWidth = 100; 
          criterionTotalLabel.setStyle("textAlign", "center"); 
          criterionTotalLabel.setStyle("horizontalAlign", "middle"); 
          criterionTotalLabel.setStyle("verticalAlign", "middle"); 
          criterionTotalLabel.setStyle("fontSize", "12"); 
          criterionTotalLabel.setStyle("fontWeight", "bold"); 
          criterionTotalLabel.text = metric.name + "Criteria Total"; 
          criterionTotalLabel.verticalCenter = 1; 

          criterionTotalBackground.addElement(criterionTotalLabel); 
          totalGroup.addElement(criterionTotalBackground); 

          //add rating dummy column 
          var criterionRatingFillerBackground:BorderContainer = new BorderContainer(); 
          criterionRatingFillerBackground.setStyle("backgroundColor", "0xa6a6a6"); 
          criterionRatingFillerBackground.width = 60; 
          criterionRatingFillerBackground.height = 15; 

          totalGroup.addElement(criterionRatingFillerBackground); 

          //add manual up/down dummy column 
          var criterionUpDownFillerBackground:BorderContainer = new BorderContainer(); 
          criterionUpDownFillerBackground.setStyle("backgroundColor", "0xa6a6a6"); 
          criterionUpDownFillerBackground.width = 60; 
          criterionUpDownFillerBackground.height = 15; 

          totalGroup.addElement(criterionUpDownFillerBackground); 

          //add current standard weight column 
          var criterionCurrentStandardWeightingTotalBackground:BorderContainer = new BorderContainer(); 
          criterionCurrentStandardWeightingTotalBackground.setStyle("backgroundColor", totalCurrentStandardWeight < 100 ? "0xf4f120" : "0xa6a6a6"); 
          criterionCurrentStandardWeightingTotalBackground.width = 60; 
          criterionCurrentStandardWeightingTotalBackground.height = 15; 

          var criterionCurrentStandardWeightingTotalLabel:Label = new Label(); 
          criterionCurrentStandardWeightingTotalLabel.percentWidth = 100; 
          criterionCurrentStandardWeightingTotalLabel.setStyle("verticalAlign", "middle"); 
          criterionCurrentStandardWeightingTotalLabel.setStyle("horizontalAlign", "middle"); 
          criterionCurrentStandardWeightingTotalLabel.setStyle("textAlign", "center"); 
          criterionCurrentStandardWeightingTotalLabel.setStyle("fontSize", "12"); 
          criterionCurrentStandardWeightingTotalLabel.text = totalCurrentStandardWeight.toString(); 
          criterionCurrentStandardWeightingTotalLabel.verticalCenter = 1; 

          criterionCurrentStandardWeightingTotalBackground.addElement(criterionCurrentStandardWeightingTotalLabel); 
          totalGroup.addElement(criterionCurrentStandardWeightingTotalBackground); 
         } 
         this.chart.addElement(criteriaGroup); 
         this.chart.addElement(totalGroup); 
        } 
       } 
      } 

它结束了在所有的数据迭代后看起来像这样。约150 - 200行。 enter link description here

我拿出了一些代码,这样它的可读性就更高了,你不必滚动很远,但是你可以获得我在这里所做的一切。有一个更好的方法吗?因为我每次迭代创建大量组件,是否甚至有可能让它更快地执行?任何提示赞赏,在用户界面方面我不能更快乐,但表现是荒谬的。

+0

我想你应该问这个问题,Spark DataGrid无法做到你想做的事情。从你添加的图像来看,我看不到DataGrid无法完成的任何事情。重新创建类似的功能真的值几周的开发时间,可能性能较差? (附注:没有Spark AdvancedDataGrid,因为你似乎建议)。 – RIAstar 2013-05-08 16:37:50

+0

每个组都会显示浅蓝色标题,并且每个组的底部都有一个自定义总行。如果这可以用datagrid完成,请告诉我。我很乐意再次尝试该路线 – atsituab 2013-05-08 18:16:39

+0

如果您需要“Flex中的Excel”,我建议您检查一下:https://github.com/mraak/AS-Spreadsheet(source)和本示例http:// currentlabel。 co.uk/flexuscalculus/。在最初的开发阶段,我在这个API背后有一些粗略的输入,并认为这是一个非常令人印象深刻的工程技术。 – JeffryHouser 2013-05-08 18:23:02

回答

0

我建议使用以下两种招数:

  1. 将可组合的东西到单个独立的组件(例如每个行作为成分)。我经历过,这通常会加速一些事情。

  2. 通过创建第一个10-20行(填充可见屏幕)创建快速渲染的幻觉,然后每5-10毫秒创建一行(数字只是为了给出一个想法,并且它们依赖于你的情况)。这样您的网页将保持响应并且显示更快。

希望它有帮助!

+0

屏幕保持锁定状态,直到完成遍历所有数据为止。你知道解决这个问题的方法吗? – atsituab 2013-05-08 18:19:28

+0

考虑到添加每一行之间的延迟,会阻止该冻结。你如何迭代和延迟? – 2013-05-08 18:27:18

+0

我不熟悉添加每行之间的'延迟'(在flex中相当新)。该代码只是在上面的代码中执行for循环作为场景,并在其完成页面出现时执行。如果他们仍然可以在绘制每一行的同时与页面交互,那将是非常好的 – atsituab 2013-05-08 18:35:11

0

你可以在这里做的是一个性能测试,以确定一些少量的迭代需要多长时间(以毫秒为单位获得调用前后的时间)。找出你可以推进到1/24秒。这就是Flex中帧间的多少时间。对所述行数执行数据网格数据提供程序更新,然后对下一批执行callLater()。 callLater的字面意思是“在下一帧”

请谨慎操作。由于在Flash帧之间需要发生的所有其他事情,CallLater在未来不会一致。