1
var rec=svg.append("rect")
    .attr("width",30)
    .attr("height", 30)
    .attr("x", 10)
    .attr("y", 20)
    .attr("fill","#00ffff");

rec.attr("transform"," translate(50,10)");

Is there any automatic method to set the transformed position (60,30) as the new untransformed position? (that is, to add to x and y attributes the translate parameters to their previously values and at the same time to set transform attribute to null)

Gerardo Furtado
  • 100,839
  • 9
  • 121
  • 171
tic
  • 4,009
  • 15
  • 45
  • 86

1 Answers1

1

As I already explained in your previous question, there is no native method in D3 v4/v5 to easily get the translate values of an element. However, just as in that question, I'll use the function provided in this answer to get those values:

function getTranslation(transform) {
  var g = document.createElementNS("http://www.w3.org/2000/svg", "g");
  g.setAttributeNS(null, "transform", transform);
  var matrix = g.transform.baseVal.consolidate().matrix;
  return [matrix.e, matrix.f];
}

With that in hand, it's just a matter of getting all values (x, y, transform), setting the new x and y values and the transform to null. It can be a function like this:

function setTranslated(element) {
  var currentTranslation = getTranslation(element.attr("transform"));
  element.attr("x", +element.attr("x") + currentTranslation[0]);
  element.attr("y", +element.attr("y") + currentTranslation[1]);
  element.attr("transform", null)
}

Here is the demo:

var svg = d3.select('svg');

var rec = svg.append("rect")
  .attr("width", 30)
  .attr("height", 30)
  .attr("x", 10)
  .attr("y", 20)
  .attr("fill", "#00ffff");

rec.attr("transform", "translate(50,10)");

setTranslated(rec)

function setTranslated(element) {
  var currentTranslation = getTranslation(element.attr("transform"));
  element.attr("x", +element.attr("x") + currentTranslation[0]);
  element.attr("y", +element.attr("y") + currentTranslation[1]);
  element.attr("transform", null)
}

function getTranslation(transform) {
  var g = document.createElementNS("http://www.w3.org/2000/svg", "g");
  g.setAttributeNS(null, "transform", transform);
  var matrix = g.transform.baseVal.consolidate().matrix;
  return [matrix.e, matrix.f];
}
<script src="https://d3js.org/d3.v5.min.js"></script>
<svg></svg>

If you inspect the rectangle you'll see something like tis:

<rect width="30" height="30" x="60" y="30" fill="#00ffff"></rect>
Gerardo Furtado
  • 100,839
  • 9
  • 121
  • 171
  • Thank you for having understood me. I was a bit confused and I tried to split my question in basic blocks. – tic Sep 07 '18 at 07:21
  • Furthermore: which approach do you suggest? To use the function you show, or to save translation values into variable to reuse after? – tic Sep 07 '18 at 07:23
  • Well, it depends on what your goals are, which are not very clear in your questions. – Gerardo Furtado Sep 07 '18 at 09:35