Suche // Search:

04.01.2011

FormCalc Diagramme Teil 6 - Blasendiagramm
//
FormCalc Charts Pt.6 - Bubble Chart

Heute gibt's nochmal ein neues Diagramm von mir - das Blasendiagramm (oder auch Scatter Plot genannt).
Es hat wie die vorherigen Beispiele auch die Möglichkeit Werte von 0 bis 10000 darzustellen und sich entsprechend zu skalieren.
Im Unterschied zu den bisherigen Beispielen, wird hier neben der Y-Achse auch die X-Achse dynamisch angepasst.

Zum Darstellen mehrerer Blasen, die sich ggf. auch überlappen können, wird wieder ein positioniertes Layout verwendet, bei dem mittels eines Tricks wieder mehrere Instanzen eines Teilformulars hinzugefügt bzw. gelöscht werden können.

Die Blasen zeigen jeweils den Wert für die Größe aus der Eingabetabelle an, wobei sich die Schriftgröße entsprechend der Blasengröße ändert.

Aktualierung:
Für die Blasengröße kann nun ein Mindestwert (in Zoll) angegeben werden, sodass diese im Diagramm nicht zu klein dargestellt werden.


Once more a new chart from me - the bubble chart (or scatter plot).
Like the previous examples it can display values between 0 and 10000 and scale automatically.
The diffrence in this example is, that it can dynamically adapt both, the Y and X-axis.

To display multiple bubbles which possibly can overlay each other, we use a positioned layout, where we can add or remove instances of subforms with a trick.

Each bubble shows the value of the size from the input table, where the font size changes analog to the bubble size.

Update:
For the bubble size you now can define a minimum value (inch size), so the bubble don't get rendered to small in the chart.


FormCalc-Skript – Aktualisierte Version 1.2
//
FormCalc script – Updated version 1.2
func Render(Flag) do
 if (Flag eq "true") then 
  var FactorX  
  var FactorY  
  var FactorS  
  var MaxInputX = Max(Input.Table.ChartValues[*].AmountX)
  var MaxInputY = Max(Input.Table.ChartValues[*].AmountY)
  var MaxInputS = Max(Input.Table.ChartValues[*].AmountS)
  var Fmin
  var FmaxX
  var FmaxY
  var FmaxS
  var MinPlotSize = 0.10 
  var Control = "Plotsizes:"
 
  for Fmin = 0 upto 9950 step 50 do
   FmaxX = Fmin + 50
   if (Within(MaxInputX, Fmin, FmaxX) eq 1) then
    FactorX = 1 / (FmaxX / 100)
   endif
   FmaxY = Fmin + 50
   if (Within(MaxInputY, Fmin, FmaxY) eq 1) then
    FactorY = 1 / (FmaxY / 100)
   endif
   FmaxS = Fmin + 50
   if (Within(MaxInputS, Fmin, FmaxS) eq 1) then
    FactorS = 1 / (FmaxS / 100)
   endif
  endfor
 
  var nRows = Input.Table.ChartValues.instanceManager.count 

  var GraphLabel   
  var ContainerHeight  
  var ContainerWidth   
  var ValueX
  var ValueY
  var ValueS
  var OffsetX
  var OffsetY
  var PlotSize
 
  for r=0 upto nRows -1 step 1 do
   Chart.layout = "tb"
   Chart._Plot.setInstances(nRows)
   Chart._Label.setInstances(nRows)
   Chart.layout = "position"
   ContainerHeight = UnitValue(Chart.Raster.h, "in")
   ContainerWidth = UnitValue(Chart.Raster.w, "in")
   Chart.Plot[r].y = ContainerHeight  
    
   ValueX = Input.Table.ChartValues[r].AmountX
   ValueY = Input.Table.ChartValues[r].AmountY
   ValueS = Input.Table.ChartValues[r].AmountS
   Chart.Plot[r].presence = "visible"
   Chart.Label[r].presence = "visible"

   for x = 0 upto 9 step 1 do
    Output.Chart.xAxis.Mark[x].Mark.value.text.value = Round((1 + x) * 10 / FactorX)
    Output.Chart.xAxis.y = ContainerHeight 
   endfor 
   for y = 10 downto 0 step 1 do
    Output.yAxis.Mark[y].Mark.value.text.value = Round((10 - y) * 10 / FactorY)
   endfor 

   var nColor = Choose(r+1,     
        "238,0,0",   
        "255,99,71", 
        "255,127,80",  
        "255,140,0",  
        "255,165,0",  
        "255,215,0", 
        "255,255,0",  
        "238,238,0",  
        "154,205,50",  
        "69,139,0",  
        "0,139,0",  
        "0,139,69",  
        "69,139,116",
        "82,139,139", 
        "0,139,139", 
        "0,134,139", 
        "83,134,139",
        "102,139,139", 
        "104,131,139", 
        "108,123,139") 

   Chart.Plot[r].Bubble.value.arc.edge.color.value = nColor
   Chart.Plot[r].Bubble.value.arc.fill.color.value = nColor
   Input.Table.ChartValues[r].Color.value.rectangle.fill.color.value = nColor
   GraphLabel = Input.Table.ChartValues[r].Label
   Chart.Label[r].BubbleValue.assist.toolTip.value = GraphLabel

   PlotSize = (ValueS / 150) * FactorS
   if (PlotSize >= MinPlotSize) then
    Chart.Plot[r].Bubble.h =  PlotSize
    Chart.Plot[r].Bubble.w =  PlotSize 
    Chart.Label[r].BubbleValue.h =  PlotSize
    Chart.Label[r].BubbleValue.w =  PlotSize 
   else 
    Chart.Plot[r].Bubble.h = MinPlotSize
    Chart.Plot[r].Bubble.w = MinPlotSize
    Chart.Label[r].BubbleValue.h = MinPlotSize
    Chart.Label[r].BubbleValue.w = MinPlotSize
   endif
   
   OffsetX = UnitValue(ValueX, "in") / 25.4 * FactorX  
   OffsetY = ContainerHeight - UnitValue(ValueY, "in") / 25.4 * FactorY 

   Chart.Plot[r].x =  OffsetX 
   Chart.Plot[r].y =  OffsetY 
   Chart.Label[r].x = OffsetX 
   Chart.Label[r].y = OffsetY 
   
   Chart.Label[r].BubbleValue.value.text.value = ValueS
  endfor

 endif
 RenderChart.value = "false" 
endfunc

Render(RenderChart.value)

Blasendiagramm - mit automatischer Skalierung
//
Bubble chart - with automatic scaling




Beispiel-Formular
//
Example form
https://workspaces.acrobat.com/app.html#d=71mOKqbTBCQOGuBLaSBndg

4 Kommentare:

  1. Hallo Marcus:

    How can i limit the x and y scale to 5 with steps of 0.5?

    Im tryong to incorporate this graph in some inhouse reports.

    thanks

    rdebakker@cogeco.ca

    AntwortenLöschen
  2. Hi,

    you can do this by changing the factors calculations:

    for Fmin = 0 upto 9950 step 50 do
    FmaxX = Fmin + 50
    if (Within(MaxInputX, Fmin, FmaxX) eq 1) then
    FactorX = 1 / (FmaxX / 100) * 10
    endif
    FmaxY = Fmin + 50
    if (Within(MaxInputY, Fmin, FmaxY) eq 1) then
    FactorY = 1 / (FmaxY / 100) * 10
    endif
    FmaxS = Fmin + 50
    if (Within(MaxInputS, Fmin, FmaxS) eq 1) then
    FactorS = 1 / (FmaxS / 100) * 10
    endif
    endfor

    And the axis calculations:

    ;Calculate X-Axis
    for x = 0 upto 9 step 1 do
    Output.Chart.xAxis.Mark[x].Mark.value.text.value = Round((1 + x) * 10 / FactorX, 1)
    Output.Chart.xAxis.y = ContainerHeight
    endfor
    ;Calculate Y-Axis
    for y = 10 downto 0 step 1 do
    Output.yAxis.Mark[y].Mark.value.text.value = Round((10 - y) * 10 / FactorY, 1)
    endfor

    To limit the input values in the table you also need to add some scripting.

    AntwortenLöschen
  3. Ah, that works. it took some time to limit the input values properly

    I'm trying to feed the AmountX, AmountS, AmountS from values elsewhere in the form so all outcomes eventually show on the analysis page.

    AntwortenLöschen
  4. The download for the example form no longer works, do you have an updated link to it?

    AntwortenLöschen