Published unlisted
Edited
Jul 18, 2020
Fork of Dataflow
2 stars
Insert cell
Insert cell
Insert cell
Changed in both
-
async function importCell( cell, // e.g., "chart" notebook, // e.g., "@d3/bar-chart" or "8d5ef3030dfd3bad"
+
function importNotebook( notebookSpecifier, // e.g., "@d3/bar-chart"
injections = {} // e.g., {data: [{name, value}, …]} ) {
+
const promise = (async () => { // Create the main module, including any injected values. const runtime = new Runtime(); const main = runtime.module(); for (const name in injections) { main.define(name, [], () => injections[name]); }
-
// Create the main module, including any injected values. const runtime = new Runtime(); const main = runtime.module(); for (const name in injections) { main.define(name, [], () => injections[name]); }
+
// Load the requested notebook’s definition as an ES module. const {default: define} = await import(/^https:/.test(notebookSpecifier) ? notebookSpecifier : `https://api.observablehq.com/${notebookSpecifier}.js?v=3`);
-
// Load the requested notebook’s definition as an ES module. const origin = `https://api.observablehq.com`; const {default: define} = await import( /^@[0-9a-z_-]+\/[0-9a-z_-]+(\/\d+)?([@~]|$)/.test(notebook += "") ? `${origin}/${notebook}.js?v=3` : /^[0-9a-f]{16}([@~]|$)/.test(notebook) ? `${origin}/d/${notebook}.js?v=3` : notebook);
+
// Create the imported notebook’s module, and then derive a module // from it to inject the desired values. (If there are none, then // this is basically a noop.) const imported = runtime.module(define); const derived = imported.derive([...Object.keys(injections)], main);
-
// Create the imported notebook’s module, and then derive a module // from it to inject the desired values. (If there are none, then // this is basically a noop.) const imported = runtime.module(define); const derived = imported.derive([...Object.keys(injections)], main);
+
// In many cases the imported cell will only have a single value, but // we must use the most generic representation (an async generator) as // the imported cell may be an async generator, or may reference one. derived.cell = (cellName) => Generators.observe((notify) => { // Create the primary variable with an observer that will report the // desired cell’s fulfilled or rejected values. main.variable({ fulfilled(value) { notify(value); }, rejected(value) { notify(Promise.reject(value)); } }).import(cellName, derived);
-
// In many cases the imported cell will only have a single value, but // we must use the most generic representation (an async generator) as // the imported cell may be an async generator, or may reference one. return Generators.observe((notify) => {
+
// Lastly, when this generator is disposed, dispose the runtime to // ensure that any imported generators terminate. return () => runtime.dispose(); });
-
// Create the primary variable with an observer that will report the // desired cell’s fulfilled or rejected values. main.variable({ fulfilled(value) { notify(value); }, rejected(value) { notify(Promise.reject(value)); } }).import(cell, derived); // Lastly, when this generator is disposed, dispose the runtime to // ensure that any imported generators terminate. return () => runtime.dispose(); });
+
return derived; })(); promise.cell = cellName => promise.then(notebook => notebook.cell(cellName)) return promise;
}
Insert cell
Added in fork
function importCell(
cellName, // e.g., "chart"
notebookSpecifier, // e.g., "@d3/bar-chart"
injections = {} // e.g., {data: [{name, value}, …]}
) {
return importNotebook(notebookSpecifier, injections).cell(cellName)
}
Insert cell
Added in fork
notebook = importNotebook("@d3/bar-chart")
Insert cell
Added in fork
notebook.cell('chart')
Insert cell
Insert cell
Changed in fork
-
importCell("chart", "@d3/bar-chart")
+
importNotebook("@d3/bar-chart").cell('chart')
Insert cell
Insert cell
importCell("chart", "@d3/bar-chart", {height: 200, color: "brown"})
Insert cell
Insert cell
importCell(
"chart",
"@d3/horizontal-bar-chart",
{
margin: {
top: 20,
right: 20,
bottom: 0,
left: 40
},
data: d3.csvParse(
await FileAttachment("us-population-by-age.csv").text(),
(({years, population}) => ({name: years, value: +population}))
)
}
)
Insert cell
Added in parent
md`In the next cell we create a *histogram* helper function, wrapping an import of the [D3 histogram example](/@d3/histogram) and passing in the specified *data* and any optional *options*. This allows us to quickly generate as many histograms as we like.`
Insert cell
Added in parent
histogram = (data, options) => importCell("chart", "@d3/histogram", {...options, data})
Insert cell
Added in parent
histogram(Array.from({length: 1000}, Math.random))
Insert cell
Added in parent
md`---

## Appendix`
Insert cell
Runtime = (await require("@observablehq/runtime@4")).Runtime
Insert cell
d3 = require("d3@5")
Insert cell