Добавьте свойство border-radius в D3js Donut Chart - PullRequest
0 голосов
/ 03 мая 2018

У меня есть эта кольцевая диаграмма, в настоящее время работающая в приложении AngularJS:

enter image description here

Но макет дизайна говорит, что мы хотели бы это, обратите внимание на свойство border-radius в зеленой части дуги:

enter image description here

Как добавить радиус границы в SVG, который выводит d3js, код, который я сейчас использую, выглядит следующим образом:

let data = [
    {
        label: 'Data',
        count: scope.data
    },
    {
        label: 'Fill',
        count: 100 - scope.data
    }
];

let width = 60;
let height = 60;
let radius = Math.min(width, height) / 2;
let color = d3.scale
    .ordinal()
    .range(['#3CC692', '#F3F3F4']);
let selector = '#donut-asset-' + scope.chartId;

d3
    .select(selector)
    .selectAll('*')
    .remove();

let svg = d3
    .selectAll(selector)
    .append('svg')
    .attr('width', width)
    .attr('height', height)
    .append('g')
    .attr(
        'transform',
        'translate(' + width / 2 + ',' + height / 2 + ')'
    );
let arc = d3.svg
    .arc()
    .innerRadius(23)
    .outerRadius(radius);
let pie = d3.layout
    .pie()
    .value(function(d) {
        return d.count;
    })
    .sort(null);
let path = svg
    .selectAll('path')
    .data(pie(data))
    .enter()
    .append('path')
    .attr('d', arc)
    .attr('fill', function(d, i) {
        return color(d.data.label);
    });
let legend = svg
    .selectAll('.legend')
    .data(data)
    .enter()
    .append('g')
    .attr('class', 'legend')
    .attr('transform', function(d, i) {
        return 'translate(' + 0 + ',' + 0 + ')';
    });
legend
    .append('text')
    .attr('x', 1)
    .attr('y', 1)
    .attr('text-anchor', 'middle')
    .attr('dominant-baseline', 'central')
    .text(function(d) {
        return d.count + '%';
    });

};

Я знаю, как использовать cornerRadius , но когда я это делаю, он устанавливает радиус для обеих дуг, он просто должен существовать на цветной. Есть идеи? Заранее спасибо за любую помощь!

Ответы [ 2 ]

0 голосов
/ 03 мая 2018

Вы можете применить угловой радиус к дуге d3, которая позволяет скруглять углы:

let arc = d3.svg
    .arc()
    .innerRadius(23)
    .outerRadius(radius)
    .cornderRadius(10);

Но недостатком является то, что границы всех дуг закруглены:

enter image description here

Если вы примените cornerRadius только к затемненной дуге - другая дуга не будет заполнять фон за закругленными углами. Вместо этого мы могли бы добавить дуги окружности (полный пончик) и поместить затемненную дугу сверху с округлением (мой пример не адаптирует ваш код, просто показывает, как это можно сделать, также с d3v4, который использует d3.arc() вместо d3.svg.arc()):

var backgroundArc = d3.arc()
  .innerRadius(30)
  .outerRadius(50)
  .startAngle(0)
  .endAngle(Math.PI*2);
  
var mainArc = d3.arc()
  .innerRadius(30)
  .outerRadius(50)
  .cornerRadius(10)
  .startAngle(0)
  .endAngle(function(d) { return d/100*Math.PI* 2 });
  
var data = [10,20,30,40,50] // percents.
  
var svg = d3.select("body").append("svg")
  .attr("width", 600)
  .attr("height", 200);
  
var charts = svg.selectAll("g")
  .data(data)
  .enter()
  .append("g")
  .attr("transform",function(d,i) { 
     return "translate("+(i*100+50)+",100)";
  });
  
charts.append("path")
  .attr("d", backgroundArc)
  .attr("fill","#ccc")

charts.append("path")
  .attr("d", mainArc) 
  .attr("fill","orange")
<script src="https://cdnjs.cloudflare.com/ajax/libs/d3/4.10.0/d3.min.js"></script>
0 голосов
/ 03 мая 2018

Попробуйте поиграть с такими атрибутами штриха, как:

  • ход
  • инсульт-dasharray
  • штрих-dashoffset
  • штрих-linecap
  • штрих-linejoin
  • штрих-miterlimit
  • штрих-непрозрачность
  • штрих-ширина * +1018 *

И установите ширину полосы на более низкие значения или 0.

Ссылка: https://developer.mozilla.org/en-US/docs/Web/SVG/Attribute

Но лучший способ - создавать диаграммы на холсте, потому что вы можете рисовать все, что захотите. Или использовать библиотеку.

...