Центр SVG групповой элемент - PullRequest
1 голос
/ 10 марта 2019

Я пытаюсь центрировать g элемент, имеющий text с tspan внутри svg элемента, используя d3, используя приведенный ниже код.

var rootSVGSize = d3.select("svg.root-svg").node().getBoundingClientRect()
var dataLabelSize = d3.select("g.data-label").node().getBoundingClientRect()

var x = rootSVGSize.width / 2;
var y = rootSVGSize.height / 2;

d3.select("g.data-label").attr("transform", "translate(" + x + "," + y + ")")
<script src="https://cdnjs.cloudflare.com/ajax/libs/d3/5.7.0/d3.min.js"></script>

<svg class="root-svg" width="180" height="200" style="border: black;border-style: solid;border-width: 1px;">
   <g class="data-label">
      <text alignment-baseline="middle" style="font-family: Arial; font-size: 36px; font-style: normal; font-weight: normal; fill: rgb(242, 200, 15);" text-anchor="middle">
         <tspan x="0" dy="0">1/1/2018</tspan>
         <tspan x="0" dy="41">3:00:00</tspan>
         <tspan x="0" dy="41">AM</tspan>
      </text>
      <title>1/1/2018 3:00:00 AM</title>
   </g>
</svg>

Как видно из приведенного выше кода, элемент группы не центрирован правильно по координатам x и y.Как я могу сделать центр элемента группы внутри svg?

Я использую getBoundingClientRect, потому что я хочу получить размер svg на начальном этапе после назначения width и height, то есть до того, как что-либо станет сотней.внутри свг.

Ответы [ 2 ]

2 голосов
/ 10 марта 2019

Вы должны принять во внимание положение x и y как контейнера SVG, так и группы:

var x = (rootSVGSize.x - dataLabelSize.x) + (rootSVGSize.width - dataLabelSize.width) / 2;
var y = (rootSVGSize.y - dataLabelSize.y) + (rootSVGSize.height - dataLabelSize.height) / 2;

Таким образом, вы можете иметь любое значение для alignment-baseline, dominant-baseline и text-anchor, это не имеет значения, группа всегда будет центрирована.

Вот ваш код с этим изменением:

var rootSVGSize = d3.select("svg.root-svg").node().getBoundingClientRect()
var dataLabelSize = d3.select("g.data-label").node().getBoundingClientRect()

var x = (rootSVGSize.x - dataLabelSize.x) + (rootSVGSize.width - dataLabelSize.width) / 2;
var y = (rootSVGSize.y - dataLabelSize.y) + (rootSVGSize.height - dataLabelSize.height) / 2;

d3.select("g.data-label").attr("transform", "translate(" + x + "," + y + ")")
<script src="https://cdnjs.cloudflare.com/ajax/libs/d3/5.7.0/d3.min.js"></script>

<svg class="root-svg" width="180" height="200" style="border: black;border-style: solid;border-width: 1px;">
   <g class="data-label">
      <text alignment-baseline="middle" style="font-family: Arial; font-size: 36px; font-style: normal; font-weight: normal; fill: rgb(242, 200, 15);" text-anchor="middle">
         <tspan x="0" dy="0">1/1/2018</tspan>
         <tspan x="0" dy="41">3:00:00</tspan>
         <tspan x="0" dy="41">AM</tspan>
      </text>
      <title>1/1/2018 3:00:00 AM</title>
   </g>
</svg>
0 голосов
/ 10 марта 2019

Я сделал несколько изменений в svg, самое важное: я изменил некоторые значения для tspan s dy.Также я использую dominant-baseline="middle" вместо alignment-baseline="middle".Надеюсь, это поможет.

var rootSVGSize = d3.select("svg.root-svg").node().getBoundingClientRect()
var dataLabelSize = d3.select("g.data-label").node().getBoundingClientRect()

var x = rootSVGSize.width / 2;
var y = rootSVGSize.height / 2;

d3.select("g.data-label").attr("transform", "translate(" + x + "," + y + ")")
<script src="https://cdnjs.cloudflare.com/ajax/libs/d3/5.7.0/d3.min.js"></script>

<svg class="root-svg" width="180" height="200" style="border: black;border-style: solid;border-width: 1px;">
   <g class="data-label">
      <text dominant-baseline="middle" style="font-family: Arial; font-size: 36px; font-style: normal; font-weight: normal; fill: rgb(242, 200, 15);" text-anchor="middle">
         <tspan x="0" dy="-41">1/1/2018</tspan>
         <tspan x="0" dy="41">3:00:00</tspan>
         <tspan x="0" dy="41">AM</tspan>
      </text>
      <title>1/1/2018 3:00:00 AM</title>
   </g>
</svg>
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...