Selecting last path of svg with d3.js

I am fairly new in D3.js I want to build a real time collaborating blackboard. One admin client draw paths on svg and other clients receive them. I'm trying to pick last path element from clients side. I walked around last few hours finding several posts as How can I select :last-child in d3.js? but cannot make it work. When i ask:

 console.log('svg ='+svg.selectAll("path")

having drawn two paths i get

svg ={"_groups":[{"0":{},"1":{}}],"_parents":[{"__on":[{"type":"click","name":"","capture":false},{"type":"mousedown","name":"drag","capture":false},{"type":"touchstart","name":"drag","capture":false},{"type":"touchmove","name":"drag","capture":false},{"type":"touchend","name":"drag","capture":false},{"type":"touchcancel","name":"drag","capture":false}]}]}  

EDIT: my DOM structure

<svg id="myCanvas" width="960" height="500">
            <rect fill="#F2EDE4" width="100%" height="100%"></rect>
        <path fill="none" stroke="black" stroke-width="2" stroke-linejoin="round" stroke-linecap="round" d="M223.64999389648438,304.25L223.98332722981772,304.5833333333333C224.31666056315103,304.9166666666667,224.98332722981772,305.5833333333333,226.31666056315103,306.75C227.64999389648438,307.9166666666667,229.64999389648438,309.5833333333333,231.14999389648438,310.4166666666667C232.64999389648438,311.25,233.64999389648438,311.25,234.98332722981772,310.4166666666667C236.31666056315103,309.5833333333333,237.98332722981772,307.9166666666667,238.81666056315103,307.0833333333333L239.64999389648438,306.25"></path><path></path></svg>

Thanks in advance

Have you tried something like this?

const lastPath = d3.select('svg>path:last-child')

You should be able to use a string like :last-child in the d3 selection api.

How can I select :last-child in d3.js?, One thing you could do is to create custom sub-selections by adding methods to d3.selection.prototype . You could create a selection.first()  When creating your data container with append(), you can save it as a selection to a variable.. var dataContainer = graph.append("svg:g") .attr("id","data"); If done in this way, you won't ever need to make the d3 selection again (in a similar way you have done with var graph on the 1st line of the code in your question), because a reference to this selection is already stored in your var

Peter's answer is working.

You get a {"_groups":[[{}]],"_parents":[{}]}, as you said in your comment, because that is a D3 selection, and that's the expected object.

If you want to get the DOM element, simply use the node() function:

const lastPath = d3.select('svg>path:last-child').node();
//getting the DOM element -------------------------^

Here is a demo using your SVG, it will log that empty path, which is the last one (since S.O. snippets freeze — at least in my machine, using Chrome — when trying to log D3 selections, here is a fiddle with the same code):

const lastPath = d3.select('svg>path:last-child').node();
console.log(lastPath)
<script src="https://d3js.org/d3.v4.min.js"></script>
<svg id="myCanvas" width="960" height="500">
  <rect fill="#F2EDE4" width="100%" height="100%"></rect>
  <path fill="none" stroke="black" stroke-width="2" stroke-linejoin="round" stroke-linecap="round" d="M223.64999389648438,304.25L223.98332722981772,304.5833333333333C224.31666056315103,304.9166666666667,224.98332722981772,305.5833333333333,226.31666056315103,306.75C227.64999389648438,307.9166666666667,229.64999389648438,309.5833333333333,231.14999389648438,310.4166666666667C232.64999389648438,311.25,233.64999389648438,311.25,234.98332722981772,310.4166666666667C236.31666056315103,309.5833333333333,237.98332722981772,307.9166666666667,238.81666056315103,307.0833333333333L239.64999389648438,306.25"></path>
  <path></path>
</svg>

SVG Paths and D3.js, SVG Paths and D3.js: The Goal, The Shape to Make All Shapes, SVG Path circular arc) and closepath (close the current shape by drawing a line to the last moveto). SVG Container 13var svgContainer = d3.select("body").append("svg") 14  D3.js - Introduction. Data visualization is the presentation of data in a pictorial or graphical format. The primary goal of data visualization is to communicate information clearly and efficiently via statistical graphics, plots and information graphics.

This is what solved this problem for me. According to d3.selections docs, this is what you should do:

var lastPath = d3.selectAll('svg>path').filter(':last-child');

Manipulating SVG using D3.js library, Selecting SVG elements using D3: // select all SVG path elements in document order d3.selectAll("path"); // select only the first SVG path element  Which is where D3.js comes to the rescue with Path Data Generators! D3.js Path Data Generator Line Example. D3.js includes a set of helper classes for generating SVG Path instructions. Before we go into all of the D3.js Path Data Generators, let us look at a specific example for the line path data generator.

Selections, This method is used to return a new selection merging with the specified other selection. Example − Let us consider the following example. var rect = svg.​selectAll  Attributes/Styles Changing Attributes and Styles. D3 provides methods for changing attributes and styles of elements. We'll look at the basics of .attr() and .style() so you can begin using these to adjust SVG attributes and styles.

D3.js - Selection API, Each function takes a single argument which specifies the selector string. For example to select all elements with class item use d3.selectAll('.item') . Modifying​  The last thing we have to do is to color the SVG Circle based on the data. Styling SVG Elements Based on Data. If you recall the Adding an SVG Element section, we used D3.js' .style() operator to modify the CSS style property. D3.js lets us use a function inside of the .style() operator! This means we can write the following:

Selections, d3-selection. Selections allow powerful data-driven transformation of the document object model (DOM): set attributes, styles, properties, HTML or text content,  For example, "svg:text" will create a "text" element in the SVG namespace. By default, D3 supports svg, xhtml, xlink, xml and xmlns namespaces. Additional namespaces can be registered by adding to d3.ns.prefix. If no namespace is specified, then the namespace will be inherited from the enclosing element; or, if the name is one of the known

Comments
  • I get svg ={"_groups":[[{}]],"_parents":[{}]} no matter how many paths i draw. The only solution i think is to reverse path elements on svg given that svg.select("path") returns first element. But it is not an elegant solution
  • hmm ... what happens when you console.log(d3.select('svg').node())?
  • Interesting. Are you sure you have an svg element on your page?
  • I can see it clearly on Web Console inspector ( Firefox)
  • Very strange. I put your svg element into a sample codepen and was able to select the last path and log it to the console ...