9 ms·
D4 – Declarative Data-Driven Documents
- koopatrol 10y agoI'm excited to play with this. I wonder what kind of overhead it has. I imagine it would be fairly low.
- gavinpc 10y agoMy CPU fan begs to differ. Or maybe you meant something different by overhead?
- weego 10y agoSorry, I don't get it. The code in any of the given example comparisons has no less obvious complexity and just removes the abstraction that writes the SVG nodes for you with having to explicitly write them in your JS which I similarly have never understood why we're intent on going back to. Different for the sake of different is fine, but "preferable" is a bold statement that appears to have no evidence.
- moogleii 10y agoIt just makes it more declarative. That's all. One can continue with their preference.
- chickenfries 10y agoAre you saying the react way is more declarative?
- olmo 10y agoOf course it is! to start with, it looks like SVG, but also you only have to provide the state that you want and React adds and removes what is necessary, while in D3 you need to use `enter` and `exit` imperatively. I'm just concerned about speed. Diffing works ok for forms but charts with 1000s of elements... let's see. As someone who has worked with D3 and React a lot, D4 makes a lot of sense. And the name is great!
- andrewstuart2 10y agoenter() and exit() are declarative. You're not causing anything at all to happen, but rather declaring what should happen, in the form of a function, when new data is found or data becomes stale.
- lhnz 10y agoDeclaring 'what' structure should exist - vs - Declaring 'how' this structure is created
- noobermin 10y agoIt sounds like the difference is just syntactical. Is this true? I have no experience with react, so I wouldn't know.
- olmo 10y agoD3 is more declarative than jQuery, but not so much as React. selection.enter().append("div").attr("class", "bar") .style("height", function(d){ return d + "px"; }) .style(“margin-top”, function(d){ return (100 — d) + "px"; }); enter is not imperative, but what you write just afterwards is.
- morgante 10y agoThe problem is that calling a function called "enter" does not feel like writing declarative code. It's an active verb and seems to imply an imperative style. Except it's actually declarative. The problem with d3 is that it takes a declarative system and gives it an imperative-looking API.
- krebby 10y agoI think you're reading it wrong. `enter` isn't imperative. You're asking for the `enter` selection, which is the list of entering nodes. Same thing with `exit`. Calling either of those methods doesn't actually alter any data
- 10y ago
- adamwong246 10y agoIt might be proven to be more performant, as it's relying on React's virtual DOM rather than d3's presumably made-from-scratch data binding. Would love to see some benchmarks though.
- woah 10y agoI suppose that everything is a matter of opinion, but d3's syntax is the worst combination of obtuse (".enter"???), cute (the incredibly obnoxious chained api), and cumbersome (all the mutation, and the fact that d3 code always ends up being a long string of procedural spaghetti). Of course, it does have a lot of useful code around math, projections, etc. This project looks like a very welcome step in the right direction, showing that d3's great math can be used with obvious, declarative syntax.
- jakub_h 10y agoSounds like an opportunity for applying Ohm/OMeta?
- olmo 10y ago+1 I couldn't express it better.
- jordache 10y agoare you objecting D3's API lexicon, or the entire notion of how it abstracts data, and binding? ".enter" actually makes sense in terms of describing how data flows through the D3 processing pipeline.
- dirtyaura 10y agoCan you explain why do you feel 'enter' is obtuse? I found enter/update/exit pretty logical. I do agree that long-term value of Bostock's work is in other parts than data-binding, but I didn't find enter/update/exit particularly hard
- dimgl 10y agoI agree with you as well. The enter/update/exit cycle is actually very intuitive although the documentation could do a better job of explaining what the functions are doing to the DOM.
- Bahamut 10y agoIn this case, I think a little more verbosity in the names of these methods would assist in understanding significantly. For example, enterAnimation/enterTransition would increase the clarity for someone new to d3, or who has been away from it for a while.
- cs02rm0 10y agoYeah. I think the premise is reasonable - d3 can be a bit of a pain, but I'm not convinced this is the answer.
- piotrkubisa 10y agoI agree with you that is his personal opinion about "preferable" way to use D3. > "Unfortunately, I always find D3 code surprisingly difficult to understand and extend" I would say something different - it is very easy to extend and create various visualization. It is easy to scaffold new chart (line, pie, box-plot, heatmap etc.) and customize it to specified needs. I'd rather say that it is difficult to create a brand new type of visualization which wasn't been already developed [1] and it is easy to understand by random folk. [1] https://github.com/d3/d3/wiki/Gallery https://github.com/d3/d3/wiki/Gallery
- jtwaleson 10y agoI'm not sure if this is it, but the world needs a simple way to integrate D3 and React. Looks good at first sight though.
- smaili 10y agoFrom the site: This is not a library, but rather a demonstration that it's possible (and preferable) to use React instead of the core of d3.
- danieljoonlee 10y agoHere's a library that integrates the two https://github.com/react-d3-library/react-d3-library https://github.com/react-d3-library/react-d3-library
- happyslobro 10y agoThat's actually a pretty reasonable idea, considering that we have several fairly different renderers for React already: DOM, Native and Three.js (http://izzimach.github.io/demos/react-three-interactive/index.html http://izzimach.github.io/demos/react-three-interactive/inde...). The big question is, should it render down to D3's API, or should it implement it in a way that is idiomatic to React, like this demo?
- otoburb 10y ago>>There are some pieces of d3 that I would love to use but aren't easily portable. For example, d3-drag and d3-zoom smooth over a lot of the quirks you'd have to deal with when implementing dragging and zooming, but they're only designed to work with d3 selections [...] Ideally we could decouple these libraries from selections, but it might also be possible to mock the selection interface they expect while still using React. According to the changelog for the recently released version 4.0.0 of D3.js by Mike Bostock[1], one of the big shifts is for D3 v4.0.0 to be "composed of many small libraries that"[2] can be used independently. So the author of D4.js can now more easily examine Bostock's refactored code for Zoom and Drag as they please. [1] https://github.com/d3/d3/blob/master/CHANGES.md https://github.com/d3/d3/blob/master/CHANGES.md [2] https://github.com/d3/d3/releases/tag/v4.0.0 https://github.com/d3/d3/releases/tag/v4.0.0
- ctvo 10y agoIf you look at the example code, the author is aware of the new modules pulled out of d3. He's actively using them. It doesn't change his comments re: those two modules specifically.
- nthitz 10y agod3.transition works on element attributes not just CSS. Wish React had something like that!
- nathancahill 10y agoYou can do that easily with https://github.com/chenglou/react-motion https://github.com/chenglou/react-motion
- SamBam 10y agoI've played with ReactMotion, but I was under the impression that it was only for styles, not for arbitrary component attributes. In the Readme they say the `style` property is required, and they also don't show any examples of animating something other than style.
- nathancahill 10y agoIt gives you a continuously changing variable that you can use for whatever you want. The name style is confusing, because it isn't actually a style. In the very first example it's just displaying the changing value.
- guylepage3 10y agoVery cool.. My only question is.. Is this "D4.js" a full feature replacement for D3.js? Could be a bit misleading. Might want to have a new name for it? Thoughts?
- the_duke 10y agoThe very second sentence of the article answers your question: This is not a library, but rather a demonstration that it's possible (and preferable) to use React instead of the core of d3.
- guylepage3 10y agoYes. So then the title is very misleading and should not be called D4.js.
- ctvo 10y agoDid the title get changed? Both on this post and the article, there's nowhere that it says it's D4.js.
- adamwong246 10y agoI've used the d4 pattern, but I've referred to it as d3act, as in "dee-three-act".
- adamwong246 10y agoI've been working with a similar approach for a while and I give it my vote of confidence. Much more elegant than d3's awkward data-binding.
- colemannerd 10y agoI need something exactly like this.
- colinmegill 10y agoCheck out: http://formidable.com/blog/2015/05/21/react-d3-layouts/ http://formidable.com/blog/2015/05/21/react-d3-layouts/ http://formidable.com/open-source/victory/docs/victory-axis/ http://formidable.com/open-source/victory/docs/victory-axis/
- deno 10y agoHybrid approach: > let React do all the migraine-inducing heavy lifting to figure out what to enter and exit, and have D3 take care of the updates. https://medium.com/@sxywu/on-d3-react-and-a-little-bit-of-flux-88a226f328f3#.h143joihp https://medium.com/@sxywu/on-d3-react-and-a-little-bit-of-fl...
- jordache 10y agoargh.. I hate the style of mixing JS with markup language....
- intrasight 10y agoAgreed. Please tell me there's another syntax for this. Please don't tell me that we're stuck with this sad relic of the past.
- dcre 10y agoThere is. You can write regular function calls like this: React.createElement('h1', {}, 'Hello') Personally I like JSX a lot, but you don't have to use it.
- kasbah 10y agoI prefer: h1('Hello') https://github.com/Jador/react-hyperscript-helpers https://github.com/Jador/react-hyperscript-helpers
- aljones 10y agoWell its actually function calls that look like markup language. Which is why you can write the function calls yourself if you hate it.
- doublerebel 10y agoMe too, so last week I created gulp-pug-hyperscript to compile Pug/Jade templates to Hyperscript [1]. In order to completely avoid JS in the markup, event binding must be done outside of the markup. I do this by using event delegation rather than binding directly to elements. [1]: https://github.com/nextorigin/gulp-pug-hyperscript https://github.com/nextorigin/gulp-pug-hyperscript
- deleted 10y ago[deleted]
- krebby 10y agoThis is a good start but it glosses over the hardest part of making React work with D3, which is animations. Most animations you want to do with D3 don't fall neatly into categories you can use with CSS animation (namely updating paths and entering / updating / exiting animations). React as an ecosystem is pretty fantastic but the React animation story is still pretty terrible unfortunately. "Portals" / "reparenting" is a majorly hacky way of getting an element from one part of the DOM to another, and even React Motion, which solves a few of the animation gripes, is hard to use, slow, and brittle in my experience. There just isn't a good substitute for the enter-update-exit selections that make up the core of D3. My usual workflow is to get as much DOM building done in React as I can, with D3 filling out the tricky bits. D3's lifecycles and direct DOM manipulation are much more complicated to reason about than React, on the whole.
- thom 10y agoHas anyone worked on these issues in Om or Om Next? I feel I'm coming up against exactly this wall myself, and I don't think my worldview is sufficiently Ommy to know which way to go.
- deleted 10y ago[deleted]
- randall 10y agoHave you seen Samsara? http://samsarajs.org/ http://samsarajs.org/ I'm hopeful it could do some of the middle bits.
- dechov 10y agoMy team and I have been using and finding success with such a pattern for a couple of years now. As others are alluding to, transitions are not currently so easy to express with React alone. We wrote and recently open-sourced a React component that aims to encapsulate the power and simplicity of d3 transitions (feedback & contributions welcome): https://github.com/dechov/join-transition/ https://github.com/dechov/join-transition/
- colinmegill 10y agoNice - thanks for sharing this
- pathsjs 10y agoShameless plug: I have been proposing this approach for long. I found that the missing piece is how to generate the actual geometric information starting from data, hence I wrote a library to this effect https://github.com/andreaferretti/paths-js https://github.com/andreaferretti/paths-js For the animations, it is often just a matter of continuosly updating the state of some component, something that I did in this mixin https://github.com/andreaferretti/paths-js-react-demo/blob/master/js/animate.jsx https://github.com/andreaferretti/paths-js-react-demo/blob/m...
- FoeNyx 10y ago@joelburget, btw the "demos" link leads to a 404. ( https://github.com/joelburget/d4/demo https://github.com/joelburget/d4/demo )
- athenot 10y agoI've done the opposite: use d3 to provide React-like semantics. - Basically the data fetches get pushed to a lightweight queue/topic system in the browser (using publish.js). - Each part of the page listens for messages it cares about and updates the page accordingly. There is still some of the d3 plumbing (I must specify how updates differ from mere element creations, and handle the exits). But I still get a nice decoupling between the different parts of my app. Coupled with browserify, this ends up with semantics not unlike Erlang (I even named the listener method "receive" and it acts on patterns of messages).
- aurelianito 10y agoI find that D3 is great, but it needs an abstraction for the general update pattern (https://bl.ocks.org/mbostock/3808218 https://bl.ocks.org/mbostock/3808218). I did that! One function that receives actions for update, create, delete, etc. Now my code is easier to read. Check the function gupChildren (AKA: General update pattern for child nodes of a selection) in my code, and feel free to use it: https://bitbucket.org/aurelito/sandro-lib/src/83b81c4b55684866fbab50ff98088822b1d42410/src/sandro/nadaMas/d3.js?at=default&fileviewer=file-view-default https://bitbucket.org/aurelito/sandro-lib/src/83b81c4b556848... At last, unless you understand what you are doing, use selectAll and no select. Cheers!
- colinmegill 10y agoLove this - awesome work. Wrote an article on this concept last year: http://formidable.com/blog/2015/05/21/react-d3-layouts/ http://formidable.com/blog/2015/05/21/react-d3-layouts/ and spoke about it at Reactive2015: https://www.youtube.com/watch?v=n8TwLWsR40Y https://www.youtube.com/watch?v=n8TwLWsR40Y Have been doing data visualizations like this ever since, it works. Yes, the hardest part is animation, which we had to address, as well as the axis components and other higher order functionality that builds on d3 itself: https://github.com/FormidableLabs/victory-animation https://github.com/FormidableLabs/victory-animation http://formidable.com/open-source/victory/docs/victory-axis/ http://formidable.com/open-source/victory/docs/victory-axis/
- choward 10y agoWhat is this? I can't even scroll.
- b34r 10y agoIntelligently-optimized JS animations are generally more performant than CSS ones by an order of magnitude. See Greensock for relevant examples. Side note, your examples don't assign keys to your array-mapped paths, which will emit warnings.