5 Replies Latest reply on Nov 10, 2010 10:53 AM by SashaKeith

    Dynamic LineChart

    dc200

      I'm trying to create a LineChart that'll have a variable number of series. I can create a new series an add it to an array, but the problem is with the chart's main dataprovider.

       

      From the following example: http://livedocs.adobe.com/flex/3/html/help.html?content=charts_types_08.html

       

       

      [Bindable]
           public var expenses:ArrayCollection = new ArrayCollection([
              {Month:"Jan", Profit:2000, Expenses:1500, Amount:450},
              {Month:"Feb", Profit:1000, Expenses:200, Amount:600},
              {Month:"Mar", Profit:1500, Expenses:500, Amount:300}
           ]);

       

      The first item in each brace looks like the x-value, followed by the y-values for each of the added LineSeries. How would I create a LineChart that has fixed x-axis, but a variable number of y-values? i.e., what if I wanted the chart in the above example to add another series after 'Amount'?

        • 1. Re: Dynamic LineChart
          SashaKeith Adobe Employee

          You can create LineSeries in Actionscript instead of MXML. As your dataprovider changes, create a new LineSeries for each new attribute and add it to the chart. The chart's series property is an Array of series.

          • 2. Re: Dynamic LineChart
            dc200 Level 1

            I know that we can create new LineSeries for the charts through the AS section, but how do we add data for the new ones that are added during runtime?

            • 3. Re: Dynamic LineChart
              SashaKeith Adobe Employee

              Set the data provider at the chart level not the LineSeries level. Create the LineChart in MXML and set it's dataProvider="{expenses}". Since expenses is bindable, it will pick up changes to the data. As you add/remove LineSeries, you don't need to set the data provider again. Your new LineSeries should update automatically as the data changes.

              • 4. Re: Dynamic LineChart
                dc200 Level 1

                Yes, I'm already setting the dataProvider at the chart level. I should clarify my problem a little further.

                 

                Here's an example of how I would add data to the chart's dataProvider, "chartData", assuming that I've got only one LineSeries called "test1".

                 

                chartData.addItem({xaxis:"2004", test1:"25"});

                chartData.addItem({xaxis:"2005", test1:"30"});

                chartData.addItem({xaxis:"2006", test1:"32"});

                 

                Now supposing in a different scenario the application queried a database and determined that it needed two LineSeries instead of one, it'll dynamically create and add two LineSeries, "test1" and "test2" to the chart's series Array (chartID.series) during one of the startup stages. The problem is, how would I add data for the new LineSeries to the chartData ArrayCollection? I can't use the method above because I don't know how many LineSeries there are.

                 

                i.e., this needs to be done dynamically...

                 

                chartData.addItem({xaxis:"2004", test1:"25", test2:"45", rest of the line series and their corresponding values});

                • 5. Re: Dynamic LineChart
                  SashaKeith Adobe Employee

                  Let's say we are adding an "Other" attribute to the expenses structure. Looping through the expenses ArrayCollection would look like this:

                   

                  var newItem:Object = {Month:"Jan", Other:1500};
                  for each (var obj:Object in expenses)
                  {
                      if (obj.Month == newItem.Month)
                      {
                          obj.Other = newItem.Other;
                          break;
                      }
                  }

                   

                  The inefficient part is looping through the structure, so you could have a lookup of Month->index and do the following:

                   

                   

                  var newItem:Object = {Month:"Jan", Other:1500};

                  var index:int = lookup[newItem.Month];

                  expenses.getItemAt(index).Other = newItem.Other;