2016-09-01 4 views
1

Ich habe tatsächlich ein Kreisdiagramm mit mehreren Datenreihen, die jeweils durch ein Kreisdiagramm dargestellt werden (siehe JSFiddle-Link).Highcharts Automatische Berechnung mehrerer Serienposition

Ich bin auf der Suche nach einer Möglichkeit, eine "automatische" Berechnung der optimalen Größe für jede Kreisdiagramme und eine optimale Position zu implementieren, um alle von ihnen in einem einzigen Container in einer generischen Weise zu rendern.

Ich habe Actualy mit dem Beginn der Lösung, aber es ist wirklich nicht optimal.

Entweder habe ich nicht verstanden, wie Highcharts beim Generieren von Diagrammen funktioniert, oder es gibt zu viel unbekannten Wert für mein System, um die Berechnung oder beides zu machen.

Bitte beachten Sie, dass der Generator nur für 1 bis 6 verschiedene Datenserien funktioniert. Wenn Sie mehr Serien verwenden, wird die Platzierung nicht möglich sein, da ich die Berechnung nicht durchgeführt habe.

Auch ist es actualy bestätigt nur auf Behälter dieser Größe zu arbeiten:

  • Breite: 340px Höhe: 170px
  • Breite: 680px Höhe: 170px

Auf Behälter mit highter Breite oder Höhe berechnet das System die Position nicht.

Das ist tatsächlich ein Teil davon, warum ich nach Ideen suchte, wie man optimalen und allgemeinen Positionsrechner bekommt.

Hier ist der Code, mit dem ich kam und eine JSFiddle Link nach dem Codebeispiel.

// Pie Chart Class 
var pieChart = { 
    create: function(_title, _data, _color, _height, _width) { 
     return (function() { 

      var type = 'pie'; 
      var title = _title || "defaultName"; 
      var color = _color || "#EBEBEB"; 
      var height = _height || 170; 
      var width = _width || 340; 
      var series = []; 
      var chart; 
      var sizeData = getSize(height, width); 
      if (_data) 
       newSeries(_data); 

      // Public functions 
      function newSeries(_data) { 
       var _datas = []; 

       for (var dataSet in _data) { 
        if (_data.hasOwnProperty(dataSet) && (color != null && color != undefined)) { 
         _datas.push({ 
          name: dataSet, 
          y: _data[dataSet], 
         }); 
        } 
       } 

       series.push({ 
        data: _datas, 
        borderWidth: 0, 
        center: [] 
       }); 
       setPos(series.length); 
      } 

      function Series() { 
       return (JSON.stringify(series)); 
      } 

      function drawOn(item) { 
       if (!item || !document.getElementById(item) && !chart) 
        return (null); 
       else { 
        chart = new Highcharts.Chart({ 
         chart: { 
          renderTo: item, 
          backgroundColor: color, 
          plotBackgroundColor: null, 
          plotBorderWidth: null, 
          plotShadow: false, 
          type: 'pie' 
         }, 
         title: { 
          text: title 
         }, 
         plotOptions: { 
          pie: { 
           allowPointSelect: false, 
           borderWidth: 0, 
           dataLabels: { 
            distance: -1, 
            enabled: true, 
            format: '<b>{point.name}</b>: {point.y}', 
            style: { 
             color: 'black' 
            } 
           }, 
           size: sizeData.size 
          } 
         }, 
         series: JSON.parse(Series()) 
        }); 
       } 
      } 

      // Private functions 
      function setPos(_len) { 
       if (_len == 1) 
        series[0].center = [sizeData.center, sizeData.h]; 
       else if (_len == 2) { 
        series[0].center = [sizeData.second, sizeData.h]; 
        series[1].center = [sizeData.fourth, sizeData.h]; 
       } else if (_len == 3) { 
        series[0].center = [sizeData.w1, sizeData.h]; 
        series[1].center = [sizeData.center, sizeData.h]; 
        series[2].center = [sizeData.w6, sizeData.h]; 
       } else if (_len == 4) { 
        series[0].center = [(sizeData.w1 + sizeData.w2)/2, sizeData.h]; 
        series[1].center = [sizeData.w3, sizeData.h]; 
        series[2].center = [(sizeData.w4 + sizeData.w5)/2, sizeData.h]; 
        series[3].center = [sizeData.w6, sizeData.h]; 
       } else if (_len == 5) { 
        series[0].center = [sizeData.w1, sizeData.h]; 
        series[1].center = [sizeData.second, sizeData.h]; 
        series[2].center = [sizeData.center, sizeData.h]; 
        series[3].center = [sizeData.fourth, sizeData.h]; 
        series[4].center = [sizeData.w6, sizeData.h]; 
       } else if (_len == 6) { 
        series[0].center = [sizeData.w1, sizeData.h]; 
        series[1].center = [sizeData.w2, sizeData.h]; 
        series[2].center = [sizeData.w3, sizeData.h]; 
        series[3].center = [sizeData.w4, sizeData.h]; 
        series[4].center = [sizeData.w5, sizeData.h]; 
        series[5].center = [sizeData.w6, sizeData.h]; 
       } 
      } 

      function getSize(height, width) { 
       var nbChart = 6; 
       var diam; 
       var tmpWidth = width - 30; 
       if (nbChart == 1) 
        diam = height - (height/3); 
       else { 
        diam = (tmpWidth - (tmpWidth/nbChart))/nbChart; 
       } 
       var test = (tmpWidth - (diam * nbChart)); 
       var h = ((height - diam)/2)/2; 
       var w = diam + (test/(nbChart * 2)); 
       var decal; 
       if (width >= 680) 
        decal = test/10; 
       else 
        decal = 0; 
       return { 
        width: width, 
        height: height, 
        size: diam, 
        h: h, 
        w1: ((diam/2) + decal), 
        w2: (((w) + diam/2) + decal), 
        w3: (((w * 2) + diam/2) + decal), 
        w4: (((w * 3) + diam/2) + decal), 
        w5: (((w * 4) + diam/2) + decal), 
        w6: (((w * 5) + diam/2) + decal), 
        center: (((((w * 2) + diam/2) + decal) + (((w * 3) + diam/2) + decal))/2), 
        second: (((diam/2) + decal) + (((((w * 2) + diam/2) + decal) + (((w * 3) + diam/2) + decal))/2))/2, 
        fourth: ((((((w * 2) + diam/2) + decal) + (((w * 3) + diam/2) + decal))/2) + (((w * 5) + diam/2) + decal))/2 
       } 
      } 

      return { 
       Series: Series, 
       drawOn: drawOn, 
       newSeries: newSeries 
      } 
     })(); 
    } 
}; 

var crPie = pieChart.create('Test', {T1: 500, T2: 700}, "#EBEBEB", 170, 680); 
crPie.newSeries({T1: 700, T2: 800}); 
crPie.drawOn('container'); 

(Hier ist der JSFiddle Link: https://jsfiddle.net/jcL0wuwp/)

ich mehrere Forschung über das Internet tun fand aber nicht, was ich suche, so optimale Platzierung Position und Größe für die Datenreihe zu erhalten.

(Ich weiß, dass ein Teil des Codes nicht Optimals ist aber mein quetion geht es nicht darum, wie in JS zu optimieren oder die Verwendung Klassen, obwohl ich rät nicht Agaisnt bin.)

Antwort

1

ich Ihre Idee ein wenig ändern wird der Positionierung deiner Tortenserie. Ich würde es vorziehen getCenter Methode der Higcharts Einwickeln, so wird es möglich sein ansprechendes Diagramme zu verwenden:

(function(H) { 
    H.wrap(H.Chart.prototype, 'addSeries', function(proceed, options, redraw, animation) { 
     proceed.apply(this, Array.prototype.slice.call(arguments, 1)); 
     var chart = this; 
     Highcharts.each(chart.series, function(s) { 
     s.isDirty = true; 
     }); 
     chart.redraw(); 
    }); 

    H.wrap(H.seriesTypes.pie.prototype, 'getCenter', function(proceed) { 
     var series = this, 
     chart = series.chart, 
     width = chart.chartWidth, 
     height = chart.chartHeight, 
     numberOfSeries = chart.series.length, 
     index = series._i, 
     initialSize, size, centerY = height/2, 
     centerX; 
     centerX = (index + 1) * (width/(numberOfSeries + 1)); 
     initialSize = width/(numberOfSeries + 1); 
     size = initialSize > height ? height : initialSize; 
     return [centerX, centerY, size, 0] 
    }); 
    }(Highcharts)); 

I Anzahl der Serie verwendet habe neue Größe und Mittelposition Sie Kreisserie zu berechnen. Ich habe die addSeries-Methode geändert, so dass Sie auch benutzerdefinierte Tortenserien hinzufügen können.

Hier können Sie ein Beispiel finden, wie es funktionieren kann: http://jsfiddle.net/oohn3q22/6/

+0

Dankten es Arbeit wie ein Zauber, schiebe ich nicht genug, um meine Forschung highcharts interne Methode zu überlasten. – Matthias

Verwandte Themen