New to Observable (turning working code into a notebook)

All, I am working through Elijah Meeks D3 in Action Second Edition examples, and I thought it would be neat to try to create some of the visualizations inside an observable notebook. As I am new to Observable I am having difficulty decomposing working code from my desktop into blocks of code in an observable notebook.

I figured this would be a good opportunity to learn observable better. If I publish my notebook would someone mind taking a look, and giving me some suggestions.

Thank you

Graig

I have published the notebook at: https://beta.observablehq.com/@graig82/d3-in-action-3-5

You’re never calling the overallTeamViz function.

I’ve made some other changes which I cannot explain why they are necessary in this fork (comments added where I made changes) and now at least the circles render. I don’t have more time right now. Maybe it’s a start anyway.

Your code is a little hard to follow because the indentation is not consistent. If you fix it, it will be easier for people to help out.

You’re code is already quite good, but there are some key points to take note of:

  • In your soccerViz cell, the overallTeamViz function is currently never run. I suggest simply removing the surrounding function, letting the code run once, when the cell evaluates.
  • Instead of d3.select("svg"), you can just use svg, and write svg.append('g')... etc. The rest of that statement is correct, including the .data(data).enter().append('g')... stuff.
  • Instead of making a new selection like you do in var teamG = d3.selectAll("g.overallG"); (which I think should work too, BTW) — you may want to consider ‘saving’ your previous selection like so:
    var teamG = svg.append("g")
                   .attr("id", "teamsG")
                   .attr("transform", "translate(50,300)")
                   .selectAll("g")
                   .data(data)
                 .enter()
                   .append("g")
                   .attr("class", "overallG")
                   .attr("transform", (d, i) =>`translate(${(i * 50)}, 0)`);
    
    After you’ve applied the .enter() command, you have in your hands the selection of “newly added elements corresponding to data points”, i.e. your full selection in this case. Thus, teamG is not actually “a single <g> element”, but the whole selection of “new single <g> elements”, if that makes sense to you? :slight_smile:
  • I’m not really sure what you want to do with your code, next. If you want to do something specific to every element (team) in this selection, you should do something like teamG.each(function (d, i) { var singleTeamG = d3.select(this) ... }). This singleTeamG then refers to just the one particular <g> in question instead of the entire previous selection.
1 Like

Hi there!

Created a quick notebook to demonstrate how to translate that example to Observable, along with some references to the techniques/patterns required for translating the rest of D3 in Action:

Looks like a lot of folks are online this morning :slight_smile: I can see other people also replying…

2 Likes

BTW, you don’t need to publish. Just click Share link instead.

Indeed a lot of people replying all at once, haha. But actually it’s late over here :smiley:

Morning? Here it’s time for bed soon :sleeping: (CET)

Hahaha, wow, that was a blast of help all at once. I’ll have to take some time to digest what was just said.

Thank you all so much though, I love Observable as a “learning / teaching / communication” platform

Mid afternoon here, EST.

1 Like

Hi all, I got the majority of this working, the only issue I am having is with the control panel. That is to say that I cannot get the control panel to be visible. I see the g, and the associated buttons in the DOM, but nothing is visible on the page. Any suggestions? I updated the notebook, so you can see the current version at the same link as before.

I don’t think you can’t have a button inside an svg. Wrapping everything in a div solves it. See https://beta.observablehq.com/d/02ddf50faadd2cc3

(Good morning USA :grin:)

Ah, of course. That was dumb of me.

So question for you super smart observable users / creators. Is this the best way to author a notebook, as one block function, or should it be broken up into smaller more digestible / explainable components? What is the convention that we as a community are trying to go for here?

As for “the best way to author a notebook”, we’re still figuring it out, together.

But usually, lots of little cells, each responsible for one aspect of your program, is a nice way to go. That allows the reactivity of the system to really shine.