pax_global_header 0000666 0000000 0000000 00000000064 13106363305 0014512 g ustar 00root root 0000000 0000000 52 comment=48bd034ace84c077bb4b98bf66b512a4ea1d867d
d3-selection-1.1.0/ 0000775 0000000 0000000 00000000000 13106363305 0014002 5 ustar 00root root 0000000 0000000 d3-selection-1.1.0/.eslintrc 0000664 0000000 0000000 00000000234 13106363305 0015625 0 ustar 00root root 0000000 0000000 parserOptions:
sourceType: module
env:
browser: true
extends:
"eslint:recommended"
rules:
no-cond-assign: 0
no-constant-condition: 0
d3-selection-1.1.0/.gitignore 0000664 0000000 0000000 00000000100 13106363305 0015761 0 ustar 00root root 0000000 0000000 *.sublime-workspace
.DS_Store
build/
node_modules
npm-debug.log
d3-selection-1.1.0/.npmignore 0000664 0000000 0000000 00000000036 13106363305 0016000 0 ustar 00root root 0000000 0000000 *.sublime-*
build/*.zip
test/
d3-selection-1.1.0/LICENSE 0000664 0000000 0000000 00000002625 13106363305 0015014 0 ustar 00root root 0000000 0000000 Copyright (c) 2010-2016, Michael Bostock
All rights reserved.
Redistribution and use in source and binary forms, with or without
modification, are permitted provided that the following conditions are met:
* Redistributions of source code must retain the above copyright notice, this
list of conditions and the following disclaimer.
* Redistributions in binary form must reproduce the above copyright notice,
this list of conditions and the following disclaimer in the documentation
and/or other materials provided with the distribution.
* The name Michael Bostock may not be used to endorse or promote products
derived from this software without specific prior written permission.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
DISCLAIMED. IN NO EVENT SHALL MICHAEL BOSTOCK BE LIABLE FOR ANY DIRECT,
INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY
OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE,
EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
d3-selection-1.1.0/README.md 0000664 0000000 0000000 00000161646 13106363305 0015277 0 ustar 00root root 0000000 0000000 # d3-selection
Selections allow powerful data-driven transformation of the document object model (DOM): set [attributes](#selection_attr), [styles](#selection_style), [properties](#selection_property), [HTML](#selection_html) or [text](#selection_text) content, and more. Using the [data join](#joining-data)’s [enter](#selection_enter) and [exit](#selection_enter) selections, you can also [add](#selection_append) or [remove](#selection_remove) elements to correspond to data.
Selection methods typically return the current selection, or a new selection, allowing the concise application of multiple operations on a given selection via method chaining. For example, to set the class and color style of all paragraph elements in the current document:
```js
d3.selectAll("p")
.attr("class", "graf")
.style("color", "red");
```
This is equivalent to:
```js
var p = d3.selectAll("p");
p.attr("class", "graf");
p.style("color", "red");
```
By convention, selection methods that return the current selection use *four* spaces of indent, while methods that return a new selection use only *two*. This helps reveal changes of context by making them stick out of the chain:
```js
d3.select("body")
.append("svg")
.attr("width", 960)
.attr("height", 500)
.append("g")
.attr("transform", "translate(20,20)")
.append("rect")
.attr("width", 920)
.attr("height", 460);
```
Selections are immutable. All selection methods that affect which elements are selected (or their order) return a new selection rather than modifying the current selection. However, note that elements are necessarily mutable, as selections drive transformations of the document!
## Installing
If you use NPM, `npm install d3-selection`. Otherwise, download the [latest release](https://github.com/d3/d3-selection/releases/latest). You can also load directly from [d3js.org](https://d3js.org), either as a [standalone library](https://d3js.org/d3-selection.v1.min.js) or as part of [D3 4.0](https://github.com/d3/d3). AMD, CommonJS, and vanilla environments are supported. In vanilla, a `d3` global is exported:
```html
```
[Try d3-selection in your browser.](https://tonicdev.com/npm/d3-selection)
## API Reference
* [Selecting Elements](#selecting-elements)
* [Modifying Elements](#modifying-elements)
* [Joining Data](#joining-data)
* [Handling Events](#handling-events)
* [Control Flow](#control-flow)
* [Local Variables](#local-variables)
* [Namespaces](#namespaces)
### Selecting Elements
Selection methods accept [W3C selector strings](http://www.w3.org/TR/selectors-api/) such as `.fancy` to select elements with the class *fancy*, or `div` to select DIV elements. Selection methods come in two forms: select and selectAll: the former selects only the first matching element, while the latter selects all matching elements in document order. The top-level selection methods, [d3.select](#select) and [d3.selectAll](#selectAll), query the entire document; the subselection methods, [*selection*.select](#selection_select) and [*selection*.selectAll](#selection_selectAll), restrict selection to descendants of the selected elements.
# d3.selection() [<>](https://github.com/d3/d3-selection/blob/master/src/selection/index.js#L38 "Source")
[Selects](#select) the root element, `document.documentElement`. This function can also be used to test for selections (`instanceof d3.selection`) or to extend the selection prototype. For example, to add a method to check checkboxes:
```js
d3.selection.prototype.checked = function(value) {
return arguments.length < 1
? this.property("checked")
: this.property("checked", !!value);
};
```
And then to use:
```js
d3.selectAll("input[type=checkbox]").checked(true);
```
# d3.select(selector) [<>](https://github.com/d3/d3-selection/blob/master/src/select.js#L3 "Source")
Selects the first element that matches the specified *selector* string. If no elements match the *selector*, returns an empty selection. If multiple elements match the *selector*, only the first matching element (in document order) will be selected. For example, to select the first anchor element:
```js
var anchor = d3.select("a");
```
If the *selector* is not a string, instead selects the specified node; this is useful if you already have a reference to a node, such as `this` within an event listener or a global such as `document.body`. For example, to make a clicked paragraph red:
```js
d3.selectAll("p").on("click", function() {
d3.select(this).style("color", "red");
});
```
# d3.selectAll(selector) [<>](https://github.com/d3/d3-selection/blob/master/src/selectAll.js#L3 "Source")
Selects all elements that match the specified *selector* string. The elements will be selected in document order (top-to-bottom). If no elements in the document match the *selector*, or if the *selector* is null or undefined, returns an empty selection. For example, to select all paragraphs:
```js
var paragraph = d3.selectAll("p");
```
If the *selector* is not a string, instead selects the specified array of nodes; this is useful if you already have a reference to nodes, such as `this.childNodes` within an event listener or a global such as `document.links`. The nodes may instead be a pseudo-array such as a `NodeList` or `arguments`. For example, to color all links red:
```js
d3.selectAll(document.links).style("color", "red");
```
#selection.select(selector) [<>](https://github.com/d3/d3-selection/blob/master/src/selection/select.js "Source")
For each selected element, selects the first descendant element that matches the specified *selector* string. If no element matches the specified selector for the current element, the element at the current index will be null in the returned selection. (If the *selector* is null, every element in the returned selection will be null, resulting in an empty selection.) If the current element has associated data, this data is propagated to the corresponding selected element. If multiple elements match the selector, only the first matching element in document order is selected. For example, to select the first bold element in every paragraph:
```js
var b = d3.selectAll("p").select("b");
```
If the *selector* is a function, it is evaluated for each selected element, in order, being passed the current datum (*d*), the current index (*i*), and the current group (*nodes*), with *this* as the current DOM element (*nodes*[*i*]). It must return an element, or null if there is no matching element. For example, to select the previous sibling of each paragraph:
```js
var previous = d3.selectAll("p").select(function() {
return this.previousElementSibling;
});
```
Unlike [*selection*.selectAll](#selection_selectAll), *selection*.select does not affect grouping: it preserves the existing group structure and indexes, and propagates data (if any) to selected children. Grouping plays an important role in the [data join](#joining-data). See [Nested Selections](http://bost.ocks.org/mike/nest/) and [How Selections Work](http://bost.ocks.org/mike/selection/) for more on this topic.
#selection.selectAll(selector) [<>](https://github.com/d3/d3-selection/blob/master/src/selection/selectAll.js "Source")
For each selected element, selects the descendant elements that match the specified *selector* string. The elements in the returned selection are grouped by their corresponding parent node in this selection. If no element matches the specified selector for the current element, or if the *selector* is null, the group at the current index will be empty. The selected elements do not inherit data from this selection; use [*selection*.data](#selection_data) to propagate data to children. For example, to select the bold elements in every paragraph:
```js
var b = d3.selectAll("p").selectAll("b");
```
If the *selector* is a function, it is evaluated for each selected element, in order, being passed the current datum (*d*), the current index (*i*), and the current group (*nodes*), with *this* as the current DOM element (*nodes*[*i*]). It must return an array of elements (or a pseudo-array, such as a NodeList), or the empty array if there are no matching elements. For example, to select the previous and next siblings of each paragraph:
```js
var sibling = d3.selectAll("p").selectAll(function() {
return [
this.previousElementSibling,
this.nextElementSibling
];
});
```
Unlike [*selection*.select](#selection_select), *selection*.selectAll does affect grouping: each selected descendant is grouped by the parent element in the originating selection. Grouping plays an important role in the [data join](#joining-data). See [Nested Selections](http://bost.ocks.org/mike/nest/) and [How Selections Work](http://bost.ocks.org/mike/selection/) for more on this topic.
#selection.filter(filter) [<>](https://github.com/d3/d3-selection/blob/master/src/selection/filter.js "Source")
Filters the selection, returning a new selection that contains only the elements for which the specified *filter* is true. The *filter* may be specified either as a selector string or a function. If the *filter* is a function, it is evaluated for each selected element, in order, being passed the current datum (*d*), the current index (*i*), and the current group (*nodes*), with *this* as the current DOM element (*nodes*[*i*]).
For example, to filter a selection of table rows to contain only even rows:
```js
var even = d3.selectAll("tr").filter(":nth-child(even)");
```
This is approximately equivalent to using [d3.selectAll](#selectAll) directly, although the indexes may be different:
```js
var even = d3.selectAll("tr:nth-child(even)");
```
Similarly, using a function:
```js
var even = d3.selectAll("tr").filter(function(d, i) { return i & 1; });
```
Or using [*selection*.select](#selection_select):
```js
var even = d3.selectAll("tr").select(function(d, i) { return i & 1 ? this : null; });
```
Note that the `:nth-child` pseudo-class is a one-based index rather than a zero-based index. Also, the above filter functions do not have precisely the same meaning as `:nth-child`; they rely on the selection index rather than the number of preceding sibling elements in the DOM.
The returned filtered selection preserves the parents of this selection, but like [*array*.filter](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Array/filter), it does not preserve indexes as some elements may be removed; use [*selection*.select](#selection_select) to preserve the index, if needed.
#selection.merge(other) [<>](https://github.com/d3/d3-selection/blob/master/src/selection/merge.js "Source")
Returns a new selection merging this selection with the specified *other* selection. The returned selection has the same number of groups and the same parents as this selection. Any missing (null) elements in this selection are filled with the corresponding element, if present (not null), from the specified *selection*. (If the *other* selection has additional groups or parents, they are ignored.)
This method is commonly used to merge the [enter](#selection_enter) and [update](#selection_data) selections after a [data-join](#joining-data). After modifying the entering and updating elements separately, you can merge the two selections and perform operations on both without duplicate code. For example:
```js
var circle = svg.selectAll("circle").data(data) // UPDATE
.style("fill", "blue");
circle.exit().remove(); // EXIT
circle.enter().append("circle") // ENTER
.style("fill", "green")
.merge(circle) // ENTER + UPDATE
.style("stroke", "black");
```
See [*selection*.data](#selection_data) for a more complete explanation of this code, which is known as the general update pattern.
This method is not intended for concatenating arbitrary selections, however: if both this selection and the specified *other* selection have (non-null) elements at the same index, this selection’s element is returned in the merge and the *other* selection’s element is ignored.
# d3.matcher(selector) [<>](https://github.com/d3/d3-selection/blob/master/src/matcher.js "Source")
Given the specified *selector*, returns a function which returns true if `this` element [matches](https://developer.mozilla.org/en-US/docs/Web/API/Element/matches) the specified selector. This method is used internally by [*selection*.filter](#selection_filter). For example, this:
```js
var div = selection.filter("div");
```
Is equivalent to:
```js
var div = selection.filter(d3.matcher("div"));
```
(Although D3 is not a compatibility layer, this implementation does support vendor-prefixed implementations due to the recent standardization of *element*.matches.)
# d3.selector(selector) [<>](https://github.com/d3/d3-selection/blob/master/src/selector.js "Source")
Given the specified *selector*, returns a function which returns the first descendant of `this` element that matches the specified selector. This method is used internally by [*selection*.select](#selection_select). For example, this:
```js
var div = selection.select("div");
```
Is equivalent to:
```js
var div = selection.select(d3.selector("div"));
```
# d3.selectorAll(selector) [<>](https://github.com/d3/d3-selection/blob/master/src/selectAll.js "Source")
Given the specified *selector*, returns a function which returns all descendants of `this` element that match the specified selector. This method is used internally by [*selection*.selectAll](#selection_selectAll). For example, this:
```js
var div = selection.selectAll("div");
```
Is equivalent to:
```js
var div = selection.selectAll(d3.selectorAll("div"));
```
# d3.window(node) [<>](https://github.com/d3/d3-selection/blob/master/src/window.js "Source")
Returns the owner window for the specified *node*. If *node* is a node, returns the owner document’s default view; if *node* is a document, returns its default view; otherwise returns the *node*.
# d3.style(node, name) [<>](https://github.com/d3/d3-selection/blob/master/src/selection/style.js#L32 "Source")
Returns the value of the style property with the specified *name* for the specified *node*. If the *node* has an inline style with the specified *name*, its value is returned; otherwise, the [computed property value](https://developer.mozilla.org/en-US/docs/Web/CSS/computed_value) is returned. See also [*selection*.style](#selection_style).
### Modifying Elements
After selecting elements, use the selection’s transformation methods to affect document content. For example, to set the name attribute and color style of an anchor element:
```js
d3.select("a")
.attr("name", "fred")
.style("color", "red");
```
To experiment with selections, visit [d3js.org](https://d3js.org) and open your browser’s developer console! (In Chrome, open the console with ⌥⌘J.) Select elements and then inspect the returned selection to see which elements are selected and how they are grouped. Call selection methods and see how the page content changes.
#selection.attr(name[, value]) [<>](https://github.com/d3/d3-selection/blob/master/src/selection/attr.js "Source")
If a *value* is specified, sets the attribute with the specified *name* to the specified value on the selected elements and returns this selection. If the *value* is a constant, all elements are given the same attribute value; otherwise, if the *value* is a function, it is evaluated for each selected element, in order, being passed the current datum (*d*), the current index (*i*), and the current group (*nodes*), with *this* as the current DOM element (*nodes*[*i*]). The function’s return value is then used to set each element’s attribute. A null value will remove the specified attribute.
If a *value* is not specified, returns the current value of the specified attribute for the first (non-null) element in the selection. This is generally useful only if you know that the selection contains exactly one element.
The specified *name* may have a namespace prefix, such as `xlink:href` to specify the `href` attribute in the XLink namespace. See [namespaces](#namespaces) for the map of supported namespaces; additional namespaces can be registered by adding to the map.
#selection.classed(names[, value]) [<>](https://github.com/d3/d3-selection/blob/master/src/selection/classed.js "Source")
If a *value* is specified, assigns or unassigns the specified CSS class *names* on the selected elements by setting the `class` attribute or modifying the `classList` property and returns this selection. The specified *names* is a string of space-separated class names. For example, to assign the classes `foo` and `bar` to the selected elements:
```js
selection.classed("foo bar", true);
```
If the *value* is truthy, then all elements are assigned the specified classes; otherwise, the classes are unassigned. If the *value* is a function, it is evaluated for each selected element, in order, being passed the current datum (*d*), the current index (*i*), and the current group (*nodes*), with *this* as the current DOM element (*nodes*[*i*]). The function’s return value is then used to assign or unassign classes on each element. For example, to randomly associate the class *foo* with on average half the selected elements:
```js
selection.classed("foo", function() { return Math.random() > 0.5; });
```
If a *value* is not specified, returns true if and only if the first (non-null) selected element has the specified *classes*. This is generally useful only if you know the selection contains exactly one element.
#selection.style(name[, value[, priority]]) [<>](https://github.com/d3/d3-selection/blob/master/src/selection/style.js "Source")
If a *value* is specified, sets the style property with the specified *name* to the specified value on the selected elements and returns this selection. If the *value* is a constant, then all elements are given the same style property value; otherwise, if the *value* is a function, it is evaluated for each selected element, in order, being passed the current datum (*d*), the current index (*i*), and the current group (*nodes*), with *this* as the current DOM element (*nodes*[*i*]). The function’s return value is then used to set each element’s style property. A null value will remove the style property. An optional *priority* may also be specified, either as null or the string `important` (without the exclamation point).
If a *value* is not specified, returns the current value of the specified style property for the first (non-null) element in the selection. The current value is defined as the element’s inline value, if present, and otherwise its [computed value](https://developer.mozilla.org/en-US/docs/Web/CSS/computed_value). Accessing the current style value is generally useful only if you know the selection contains exactly one element.
Caution: unlike many SVG attributes, CSS styles typically have associated units. For example, `3px` is a valid stroke-width property value, while `3` is not. Some browsers implicitly assign the `px` (pixel) unit to numeric values, but not all browsers do: IE, for example, throws an “invalid arguments” error!
#selection.property(name[, value]) [<>](https://github.com/d3/d3-selection/blob/master/src/selection/property.js "Source")
Some HTML elements have special properties that are not addressable using attributes or styles, such as a form field’s text `value` and a checkbox’s `checked` boolean. Use this method to get or set these properties.
If a *value* is specified, sets the property with the specified *name* to the specified value on selected elements. If the *value* is a constant, then all elements are given the same property value; otherwise, if the *value* is a function, it is evaluated for each selected element, in order, being passed the current datum (*d*), the current index (*i*), and the current group (*nodes*), with *this* as the current DOM element (*nodes*[*i*]). The function’s return value is then used to set each element’s property. A null value will delete the specified property.
If a *value* is not specified, returns the value of the specified property for the first (non-null) element in the selection. This is generally useful only if you know the selection contains exactly one element.
#selection.text([value]) [<>](https://github.com/d3/d3-selection/blob/master/src/selection/text.js "Source")
If a *value* is specified, sets the [text content](http://www.w3.org/TR/DOM-Level-3-Core/core.html#Node3-textContent) to the specified value on all selected elements, replacing any existing child elements. If the *value* is a constant, then all elements are given the same text content; otherwise, if the *value* is a function, it is evaluated for each selected element, in order, being passed the current datum (*d*), the current index (*i*), and the current group (*nodes*), with *this* as the current DOM element (*nodes*[*i*]). The function’s return value is then used to set each element’s text content. A null value will clear the content.
If a *value* is not specified, returns the text content for the first (non-null) element in the selection. This is generally useful only if you know the selection contains exactly one element.
#selection.html([value]) [<>](https://github.com/d3/d3-selection/blob/master/src/selection/html.js "Source")
If a *value* is specified, sets the [inner HTML](http://dev.w3.org/html5/spec-LC/apis-in-html-documents.html#innerhtml) to the specified value on all selected elements, replacing any existing child elements. If the *value* is a constant, then all elements are given the same inner HTML; otherwise, if the *value* is a function, it is evaluated for each selected element, in order, being passed the current datum (*d*), the current index (*i*), and the current group (*nodes*), with *this* as the current DOM element (*nodes*[*i*]). The function’s return value is then used to set each element’s inner HTML. A null value will clear the content.
If a *value* is not specified, returns the inner HTML for the first (non-null) element in the selection. This is generally useful only if you know the selection contains exactly one element.
Use [*selection*.append](#selection_append) or [*selection*.insert](#selection_insert) instead to create data-driven content; this method is intended for when you want a little bit of HTML, say for rich formatting. Also, *selection*.html is only supported on HTML elements. SVG elements and other non-HTML elements do not support the innerHTML property, and thus are incompatible with *selection*.html. Consider using [XMLSerializer](https://developer.mozilla.org/en-US/docs/XMLSerializer) to convert a DOM subtree to text. See also the [innersvg polyfill](https://code.google.com/p/innersvg/), which provides a shim to support the innerHTML property on SVG elements.
#selection.append(type) [<>](https://github.com/d3/d3-selection/blob/master/src/selection/append.js "Source")
If the specified *type* is a string, appends a new element of this type (tag name) as the last child of each selected element, or before the next following sibling in the update selection if this is an [enter selection](#selection_enter). The latter behavior for enter selections allows you to insert elements into the DOM in an order consistent with the new bound data; however, note that [*selection*.order](#selection_order) may still be required if updating elements change order (*i.e.*, if the order of new data is inconsistent with old data).
If the specified *type* is a function, it is evaluated for each selected element, in order, being passed the current datum (*d*), the current index (*i*), and the current group (*nodes*), with *this* as the current DOM element (*nodes*[*i*]). This function should return an element to be appended. (The function typically creates a new element, but it may instead return an existing element.) For example, to append a DIV element to each paragraph:
```js
d3.selectAll("p").append("div");
```
This is equivalent to:
```js
d3.selectAll("p").append(function() {
return document.createElement("div");
});
```
Which is equivalent to:
```js
d3.selectAll("p").select(function() {
return this.appendChild(document.createElement("div"));
});
```
In both cases, this method returns a new selection containing the appended elements. Each new element inherits the data of the current elements, if any, in the same manner as [*selection*.select](#selection_select).
The specified *name* may have a namespace prefix, such as `svg:text` to specify a `text` attribute in the SVG namespace. See [namespaces](#namespaces) for the map of supported namespaces; additional namespaces can be registered by adding to the map. If no namespace is specified, the namespace will be inherited from the parent element; or, if the name is one of the known prefixes, the corresponding namespace will be used (for example, `svg` implies `svg:svg`).
#selection.insert(type[, before]) [<>](https://github.com/d3/d3-selection/blob/master/src/selection/insert.js "Source")
If the specified *type* is a string, inserts a new element of this type (tag name) before the first element matching the specified *before* selector for each selected element. For example, a *before* selector `:first-child` will prepend nodes before the first child. If *before* is not specified, it defaults to null. (To append elements in an order consistent with [bound data](#joining-data), use [*selection*.append](#selection_append).)
Both *type* and *before* may instead be specified as functions which are evaluated for each selected element, in order, being passed the current datum (*d*), the current index (*i*), and the current group (*nodes*), with *this* as the current DOM element (*nodes*[*i*]). The *type* function should return an element to be inserted; the *before* function should return the child element before which the element should be inserted. For example, to append a DIV element to each paragraph:
```js
d3.selectAll("p").insert("div");
```
This is equivalent to:
```js
d3.selectAll("p").insert(function() {
return document.createElement("div");
});
```
Which is equivalent to:
```js
d3.selectAll("p").select(function() {
return this.insertBefore(document.createElement("div"), null);
});
```
In both cases, this method returns a new selection containing the appended elements. Each new element inherits the data of the current elements, if any, in the same manner as [*selection*.select](#selection_select).
The specified *name* may have a namespace prefix, such as `svg:text` to specify a `text` attribute in the SVG namespace. See [namespaces](#namespaces) for the map of supported namespaces; additional namespaces can be registered by adding to the map. If no namespace is specified, the namespace will be inherited from the parent element; or, if the name is one of the known prefixes, the corresponding namespace will be used (for example, `svg` implies `svg:svg`).
#selection.remove() [<>](https://github.com/d3/d3-selection/blob/master/src/selection/remove.js "Source")
Removes the selected elements from the document. Returns this selection (the removed elements) which are now detached from the DOM. There is not currently a dedicated API to add removed elements back to the document; however, you can pass a function to [*selection*.append](#selection_append) or [*selection*.insert](#selection_insert) to re-add elements.
#selection.sort(compare) [<>](https://github.com/d3/d3-selection/blob/master/src/selection/sort.js "Source")
Returns a new selection that contains a copy of each group in this selection sorted according to the *compare* function. After sorting, re-inserts elements to match the resulting order (per [*selection*.order](#selection_order)).
The compare function, which defaults to [ascending](https://github.com/d3/d3-array#ascending), is passed two elements’ data *a* and *b* to compare. It should return either a negative, positive, or zero value. If negative, then *a* should be before *b*; if positive, then *a* should be after *b*; otherwise, *a* and *b* are considered equal and the order is arbitrary.
Note that sorting is not guaranteed to be stable; however, it is guaranteed to have the same behavior as your browser’s built-in [sort](https://developer.mozilla.org/en/JavaScript/Reference/Global_Objects/Array/sort) method on arrays.
#selection.order() [<>](https://github.com/d3/d3-selection/blob/master/src/selection/order.js "Source")
Re-inserts elements into the document such that the document order of each group matches the selection order. This is equivalent to calling [*selection*.sort](#selection_sort) if the data is already sorted, but much faster.
#selection.raise() [<>](https://github.com/d3/d3-selection/blob/master/src/selection/raise.js "Source")
Re-inserts each selected element, in order, as the last child of its parent. Equivalent to:
```js
selection.each(function() {
this.parentNode.appendChild(this);
});
```
#selection.lower() [<>](https://github.com/d3/d3-selection/blob/master/src/selection/lower.js "Source")
Re-inserts each selected element, in order, as the first child of its parent. Equivalent to:
```js
selection.each(function() {
this.parentNode.insertBefore(this, this.parentNode.firstChild);
});
```
# d3.creator(name) [<>](https://github.com/d3/d3-selection/blob/master/src/creator.js "Source")
Given the specified element *name*, returns a function which creates an element of the given name, assuming that `this` is the parent element. This method is used internally by [*selection*.append](#selection_append) and [*selection*.insert](#selection_insert) to create new elements. For example, this:
```js
selection.append("div");
```
Is equivalent to:
```js
selection.append(d3.creator("div"));
```
See [namespace](#namespace) for details on supported namespace prefixes, such as for SVG elements.
### Joining Data
For an introduction to D3’s data joins, see [Thinking With Joins](http://bost.ocks.org/mike/join/). Also see the [General Update Pattern](http://bl.ocks.org/mbostock/3808218) examples.
#selection.data([data[, key]]) [<>](https://github.com/d3/d3-selection/blob/master/src/selection/data.js "Source")
Joins the specified array of *data* with the selected elements, returning a new selection that represents the *update* selection: the elements successfully bound to data. Also defines the [enter](#selection_enter) and [exit](#selection_exit) selections on the returned selection, which can be used to add or remove elements to correspond to the new data. The specified *data* is an array of arbitrary values (*e.g.*, numbers or objects), or a function that returns an array of values for each group. When data is assigned to an element, it is stored in the property `__data__`, thus making the data “sticky” and available on re-selection.
The *data* is specified **for each group** in the selection. If the selection has multiple groups (such as [d3.selectAll](#selectAll) followed by [*selection*.selectAll](#selection_selectAll)), then *data* should typically be specified as a function. This function will be evaluated for each group in order, being passed the group’s parent datum (*d*, which may be undefined), the group index (*i*), and the selection’s parent nodes (*nodes*), with *this* as the group’s parent element. For example, to create an HTML table from a matrix of numbers:
```js
var matrix = [
[11975, 5871, 8916, 2868],
[ 1951, 10048, 2060, 6171],
[ 8010, 16145, 8090, 8045],
[ 1013, 990, 940, 6907]
];
var tr = d3.select("body")
.append("table")
.selectAll("tr")
.data(matrix)
.enter().append("tr");
var td = tr.selectAll("td")
.data(function(d) { return d; })
.enter().append("td")
.text(function(d) { return d; });
```
In this example the *data* function is the identity function: for each table row, it returns the corresponding row from the data matrix.
If a *key* function is not specified, then the first datum in *data* is assigned to the first selected element, the second datum to the second selected element, and so on. A *key* function may be specified to control which datum is assigned to which element, replacing the default join-by-index. This key function is evaluated for each selected element, in order, being passed the current datum (*d*), the current index (*i*), and the current group (*nodes*), with *this* as the current DOM element (*nodes*[*i*]). The key function is then also evaluated for each new datum in *data*, being passed the current datum (*d*), the current index (*i*), and the group’s new *data*, with *this* as the group’s parent DOM element. The datum for a given key is assigned to the element with the matching key. If multiple elements have the same key, the duplicate elements are put into the exit selection; if multiple data have the same key, the duplicate data are put into the enter selection.
For example, given this document:
```html
```
You could join data by key as follows:
```js
var data = [
{name: "Locke", number: 4},
{name: "Reyes", number: 8},
{name: "Ford", number: 15},
{name: "Jarrah", number: 16},
{name: "Shephard", number: 31},
{name: "Kwon", number: 34}
];
d3.selectAll("div")
.data(data, function(d) { return d ? d.name : this.id; })
.text(function(d) { return d.number; });
```
This example key function uses the datum *d* if present, and otherwise falls back to the element’s id property. Since these elements were not previously bound to data, the datum *d* is null when the key function is evaluated on selected elements, and non-null when the key function is evaluated on the new data.
The *update* and *enter* selections are returned in data order, while the *exit* selection preserves the selection order prior to the join. If a key function is specified, the order of elements in the selection may not match their order in the document; use [*selection*.order](#order) or [*selection*.sort](#sort) as needed. For more on how the key function affects the join, see [A Bar Chart, Part 2](http://bost.ocks.org/mike/bar/2/) and [Object Constancy](http://bost.ocks.org/mike/constancy/).
Although the data-join can be used simply to create (to *enter*) a set of elements corresponding to data, more generally the data-join is designed to let you create, destroy or update elements as needed so that the resulting DOM corresponds to the new data. The data-join lets you do this efficiently by executing only the minimum necessary operations on each state of element (entering, updating, or exiting), and allows you to declare concise animated transitions between states as well. Here is a simple example of the [General Update Pattern](http://bl.ocks.org/mbostock/3808218):
```js
var circle = svg.selectAll("circle") // 1
.data(data) // 2
.style("fill", "blue"); // 3
circle.exit().remove(); // 4
circle.enter().append("circle") // 5
.style("fill", "green") // 6
.merge(circle) // 7
.style("stroke", "black"); // 8
```
Breaking this down into discrete steps:
1. Any existing circles (that are descendants of the `svg` selection) are [selected](#selection_selectAll).
2. These circles are [joined to new `data`](#selection_data), returning the matching circles: the *update* selection.
3. These updating circles are given a blue fill.
4. Any existing circles that do *not* match new data—the *exit* selection—are removed.
5. New circles are [appended](#selection_append) for any new data that do *not* match any existing circle: the *enter* selection.
6. These entering circles are given a green fill.
7. A new selection representing the [union](#selection_merge) of entering and updating circles is created.
8. These entering and updating circles are given a black stroke.
As described in the preceding paragraphs, the “matching” logic is determined by the key function passed to *selection*.data; since no key function is used in the above code sample, the elements and data are joined by index.
If *data* is not specified, this method returns the array of data for the selected elements.
This method cannot be used to clear bound data; use [*selection*.datum](#selection_datum) instead.
#selection.enter() [<>](https://github.com/d3/d3-selection/blob/master/src/selection/enter.js "Source")
Returns the enter selection: placeholder nodes for each datum that had no corresponding DOM element in the selection. The enter selection is determined by [*selection*.data](#selection_data), and is empty on a selection that is not joined to data.
The enter selection is typically used to create “missing” elements corresponding to new data. For example, to create DIV elements from an array of numbers:
```js
var div = d3.select("body")
.selectAll("div")
.data([4, 8, 15, 16, 23, 42])
.enter().append("div")
.text(function(d) { return d; });
```
If the body is initially empty, the above code will create six new DIV elements, append them to the body in-order, and assign their text content as the associated (string-coerced) number:
```html
4
8
15
16
23
42
```
Conceptually, the enter selection’s placeholders are pointers to the parent element (in this example, the document body). The enter selection is typically only used transiently to append elements, and is often [merged](#selection_merge) with the update selection after appending, such that modifications can be applied to both entering and updating elements.
#selection.exit() [<>](https://github.com/d3/d3-selection/blob/master/src/selection/exit.js "Source")
Returns the exit selection: existing DOM elements in the selection for which no new datum was found. The exit selection is determined by the previous [*selection*.data](#selection_data), and is thus empty until the selection is joined to data. If the exit selection is retrieved more than once after a data join, subsequent calls return the empty selection.
The exit selection is typically used to remove “superfluous” elements corresponding to old data. For example, to update the DIV elements created previously with a new array of numbers:
```js
div = div.data([1, 2, 4, 8, 16, 32], function(d) { return d; });
```
Since a key function was specified (as the identity function), and the new data contains the numbers [4, 8, 16] which match existing elements in the document, the update selection contains three DIV elements. Leaving those elements as-is, we can append new elements for [1, 2, 32] using the enter selection:
```js
div.enter().append("div").text(function(d) { return d; });
```
Likewise, to remove the exiting elements [15, 23, 42]:
```js
div.exit().remove();
```
Now the document body looks like this:
```html
1
2
4
8
16
32
```
The order of the DOM elements matches the order of the data because the old data’s order and the new data’s order were consistent. If the new data’s order is different, use [*selection*.order](#selection_order) to reorder the elements in the DOM. See the [General Update Pattern](http://bl.ocks.org/mbostock/3808218) example thread for more on data joins.
#selection.datum([value]) [<>](https://github.com/d3/d3-selection/blob/master/src/selection/datum.js "Source")
Gets or sets the bound data for each selected element. Unlike [*selection*.data](#selection_data), this method does not compute a join and does not affect indexes or the enter and exit selections.
If a *value* is specified, sets the element’s bound data to the specified value on all selected elements. If the *value* is a constant, all elements are given the same datum; otherwise, if the *value* is a function, it is evaluated for each selected element, in order, being passed the current datum (*d*), the current index (*i*), and the current group (*nodes*), with *this* as the current DOM element (*nodes*[*i*]). The function is then used to set each element’s new data. A null value will delete the bound data.
If a *value* is not specified, returns the bound datum for the first (non-null) element in the selection. This is generally useful only if you know the selection contains exactly one element.
This method is useful for accessing HTML5 [custom data attributes](http://www.w3.org/TR/html5/dom.html#custom-data-attribute). For example, given the following elements:
```html
Shawn Allen
Mike Bostock
```
You can expose the custom data attributes by setting each element’s data as the built-in [dataset](http://www.w3.org/TR/html5/dom.html#dom-dataset) property:
```js
selection.datum(function() { return this.dataset; })
```
### Handling Events
For interaction, selections allow listening for and dispatching of events.
#selection.on(typenames[, listener[, capture]]) [<>](https://github.com/d3/d3-selection/blob/master/src/selection/on.js "Source")
Adds or removes a *listener* to each selected element for the specified event *typenames*. The *typenames* is a string event type, such as `click`, `mouseover`, or `submit`; any [DOM event type](https://developer.mozilla.org/en-US/docs/Web/Events#Standard_events) supported by your browser may be used. The type may be optionally followed by a period (`.`) and a name; the optional name allows multiple callbacks to be registered to receive events of the same type, such as `click.foo` and `click.bar`. To specify multiple typenames, separate typenames with spaces, such as `input change` or `click.foo click.bar`.
When a specified event is dispatched on a selected element, the specified *listener* will be evaluated for the element, being passed the current datum (*d*), the current index (*i*), and the current group (*nodes*), with *this* as the current DOM element (*nodes*[*i*]). Listeners always see the latest datum for their element, but the index is a property of the selection and is fixed when the listener is assigned; to update the index, re-assign the listener. To access the current event within a listener, use [d3.event](#event).
If an event listener was previously registered for the same *typename* on a selected element, the old listener is removed before the new listener is added. To remove a listener, pass null as the *listener*. To remove all listeners for a given name, pass null as the *listener* and `.foo` as the *typename*, where `foo` is the name; to remove all listeners with no name, specify `.` as the *typename*.
An optional *capture* flag may be specified which corresponds to the W3C [useCapture flag](http://www.w3.org/TR/DOM-Level-2-Events/events.html#Events-registration): “After initiating capture, all events of the specified type will be dispatched to the registered EventListener before being dispatched to any EventTargets beneath them in the tree. Events which are bubbling upward through the tree will not trigger an EventListener designated to use capture.”
If a *listener* is not specified, returns the currently-assigned listener for the specified event *typename* on the first (non-null) selected element, if any. If multiple typenames are specified, the first matching listener is returned.
#selection.dispatch(type[, parameters]) [<>](https://github.com/d3/d3-selection/blob/master/src/selection/dispatch.js "Source")
Dispatches a [custom event](http://www.w3.org/TR/dom/#interface-customevent) of the specified *type* to each selected element, in order. An optional *parameters* map may be specified to set additional properties of the event. It may contain the following fields:
* [`bubbles`](https://www.w3.org/TR/dom/#dom-event-bubbles) - if true, the event is dispatched to ancestors in reverse tree order.
* [`cancelable`](https://www.w3.org/TR/dom/#dom-event-cancelable) - if true, *event*.preventDefault is allowed.
* [`detail`](https://www.w3.org/TR/dom/#dom-customevent-detail) - any custom data associated with the event.
If *parameters* is a function, it is evaluated for each selected element, in order, being passed the current datum (*d*), the current index (*i*), and the current group (*nodes*), with *this* as the current DOM element (*nodes*[*i*]). It must return the parameters map for the current element.
# d3.event
The current [event](https://developer.mozilla.org/en-US/docs/DOM/event), if any. This is set during the invocation of an event listener, and is reset after the listener terminates. Use this to access standard event fields such as [*event*.timeStamp](https://www.w3.org/TR/dom/#dom-event-timestamp) and methods such as [*event*.preventDefault](https://www.w3.org/TR/dom/#dom-event-preventdefault). While you can use the native [*event*.pageX](https://developer.mozilla.org/en/DOM/event.pageX) and [*event*.pageY](https://developer.mozilla.org/en/DOM/event.pageY), it is often more convenient to transform the event position to the local coordinate system of the container that received the event using [d3.mouse](#mouse), [d3.touch](#touch) or [d3.touches](#touches).
If you use Babel, Webpack, or another ES6-to-ES5 bundler, be aware that the value of d3.event changes during an event! An import of d3.event must be a [live binding](http://www.2ality.com/2015/07/es6-module-exports.html), so you may need to configure the bundler to import from D3’s ES6 modules rather than from the generated UMD bundle; not all bundlers observe [jsnext:main](https://github.com/rollup/rollup/wiki/jsnext:main). Also beware of conflicts with the [*window*.event](https://developer.mozilla.org/en-US/docs/Web/API/Window/event) global.
# d3.customEvent(event, listener[, that[, arguments]]) [<>](https://github.com/d3/d3-selection/blob/master/src/selection/on.js#L98 "Source")
Invokes the specified *listener*, using the specified *that* `this` context and passing the specified *arguments*, if any. During the invocation, [d3.event](#event) is set to the specified *event*; after the listener returns (or throws an error), d3.event is restored to its previous value. In addition, sets *event*.sourceEvent to the prior value of d3.event, allowing custom events to retain a reference to the originating native event. Returns the value returned by the *listener*.
# d3.mouse(container) [<>](https://github.com/d3/d3-selection/blob/master/src/mouse.js "Source")
Returns the *x* and *y* coordinates of the [current event](#event) relative to the specified *container*. The container may be an HTML or SVG container element, such as a [G element](http://www.w3.org/TR/SVG/struct.html#Groups) or an [SVG element](http://www.w3.org/TR/SVG/struct.html#SVGElement). The coordinates are returned as a two-element array of numbers [*x*, *y*].
# d3.touch(container[, touches], identifier) [<>](https://github.com/d3/d3-selection/blob/master/src/touch.js "Source")
Returns the *x* and *y* coordinates of the touch with the specified *identifier* associated with the [current event](#event) relative to the specified *container*. The container may be an HTML or SVG container element, such as a [G element](http://www.w3.org/TR/SVG/struct.html#Groups) or an [SVG element](http://www.w3.org/TR/SVG/struct.html#SVGElement). The coordinates are returned as a two-element array of numbers [*x*, *y*]. If there is no touch with the specified identifier in *touches*, returns null; this can be useful for ignoring touchmove events where the only some touches have moved. If *touches* is not specified, it defaults to the current event’s [changedTouches](http://developer.apple.com/library/safari/documentation/UserExperience/Reference/TouchEventClassReference/TouchEvent/TouchEvent.html#//apple_ref/javascript/instp/TouchEvent/changedTouches) property.
# d3.touches(container[, touches]) [<>](https://github.com/d3/d3-selection/blob/master/src/touches.js "Source")
Returns the *x* and *y* coordinates of the touches associated with the [current event](#event) relative to the specified *container*. The container may be an HTML or SVG container element, such as a [G element](http://www.w3.org/TR/SVG/struct.html#Groups) or an [SVG element](http://www.w3.org/TR/SVG/struct.html#SVGElement). The coordinates are returned as an array of two-element arrays of numbers \[\[*x1*, *y1*], [*x2*, *y2*], …\]. If *touches* is not specified, it defaults to the current event’s [touches](http://developer.apple.com/library/safari/documentation/UserExperience/Reference/TouchEventClassReference/TouchEvent/TouchEvent.html#//apple_ref/javascript/instp/TouchEvent/touches) property.
### Control Flow
For advanced usage, selections provide methods for custom control flow.
#selection.each(function) [<>](https://github.com/d3/d3-selection/blob/master/src/selection/each.js "Source")
Invokes the specified *function* for each selected element, in order, being passed the current datum (*d*), the current index (*i*), and the current group (*nodes*), with *this* as the current DOM element (*nodes*[*i*]). This method can be used to invoke arbitrary code for each selected element, and is useful for creating a context to access parent and child data simultaneously, such as:
```js
parent.each(function(p, j) {
d3.select(this)
.selectAll(".child")
.text(function(d, i) { return "child " + d.name + " of " + p.name; });
});
```
See [Sized Donut Multiples](http://bl.ocks.org/mbostock/4c5fad723c87d2fd8273) for an example.
#selection.call(function[, arguments…]) [<>](https://github.com/d3/d3-selection/blob/master/src/selection/call.js "Source")
Invokes the specified *function* exactly once, passing in this selection along with any optional *arguments*. Returns this selection. This is equivalent to invoking the function by hand but facilitates method chaining. For example, to set several styles in a reusable function:
```js
function name(selection, first, last) {
selection
.attr("first-name", first)
.attr("last-name", last);
}
```
Now say:
```js
d3.selectAll("div").call(name, "John", "Snow");
```
This is roughly equivalent to:
```js
name(d3.selectAll("div"), "John", "Snow");
```
The only difference is that *selection*.call always returns the *selection* and not the return value of the called *function*, `name`.
#selection.empty() [<>](https://github.com/d3/d3-selection/blob/master/src/selection/empty.js "Source")
Returns true if this selection contains no (non-null) elements.
#selection.nodes() [<>](https://github.com/d3/d3-selection/blob/master/src/selection/nodes.js "Source")
Returns an array of all (non-null) elements in this selection.
#selection.node() [<>](https://github.com/d3/d3-selection/blob/master/src/selection/node.js "Source")
Returns the first (non-null) element in this selection. If the selection is empty, returns null.
#selection.size() [<>](https://github.com/d3/d3-selection/blob/master/src/selection/size.js "Source")
Returns the total number of elements in this selection.
### Local Variables
D3 locals allow you to define local state independent of data. For instance, when rendering [small multiples](http://bl.ocks.org/mbostock/e1192fe405703d8321a5187350910e08) of time-series data, you might want the same *x*-scale for all charts but distinct *y*-scales to compare the relative performance of each metric. D3 locals are scoped by DOM elements: on set, the value is stored on the given element; on get, the value is retrieved from given element or the nearest ancestor that defines it.
# d3.local() [<>](https://github.com/d3/d3-selection/blob/master/src/local.js "Source")
Declares a new local variable. For example:
```js
var foo = d3.local();
```
Like `var`, each local is a distinct symbolic reference; unlike `var`, the value of each local is also scoped by the DOM.
#local.set(node, value) [<>](https://github.com/d3/d3-selection/blob/master/src/local.js#L18 "Source")
Sets the value of this local on the specified *node* to the *value*, and returns the specified *value*. This is often performed using [*selection*.each](#selection_each):
```js
selection.each(function(d) { foo.set(this, d.value); });
```
If you are just setting a single variable, consider using [*selection*.property](#selection_property):
```js
selection.property(foo, function(d) { return d.value; });
```
#local.get(node) [<>](https://github.com/d3/d3-selection/blob/master/src/local.js#L13 "Source")
Returns the value of this local on the specified *node*. If the *node* does not define this local, returns the value from the nearest ancestor that defines it. Returns undefined if no ancestor defines this local.
#local.remove(node) [<>](https://github.com/d3/d3-selection/blob/master/src/local.js#L21 "Source")
Deletes this local’s value from the specified *node*. Returns true if the *node* defined this local prior to removal, and false otherwise. If ancestors also define this local, those definitions are unaffected, and thus [*local*.get](#local_get) will still return the inherited value.
#local.toString() [<>](https://github.com/d3/d3-selection/blob/master/src/local.js#L24 "Source")
Returns the automatically-generated identifier for this local. This is the name of the property that is used to store the local’s value on elements, and thus you can also set or get the local’s value using *element*[*local*] or by using [*selection*.property](#selection_property).
### Namespaces
XML namespaces are fun! Right? Fortunately you can mostly ignore them.
# d3.namespace(name) [<>](https://github.com/d3/d3-selection/blob/master/src/namespace.js "Source")
Qualifies the specified *name*, which may or may not have a namespace prefix. If the name contains a colon (`:`), the substring before the colon is interpreted as the namespace prefix, which must be registered in [d3.namespaces](#namespaces). Returns an object `space` and `local` attributes describing the full namespace URL and the local name. For example:
```js
d3.namespace("svg:text"); // {space: "http://www.w3.org/2000/svg", local: "text"}
```
If the name does not contain a colon, this function merely returns the input name.
# d3.namespaces [<>](https://github.com/d3/d3-selection/blob/master/src/namespaces.js "Source")
The map of registered namespace prefixes. The initial value is:
```js
{
svg: "http://www.w3.org/2000/svg",
xhtml: "http://www.w3.org/1999/xhtml",
xlink: "http://www.w3.org/1999/xlink",
xml: "http://www.w3.org/XML/1998/namespace",
xmlns: "http://www.w3.org/2000/xmlns/"
}
```
Additional prefixes may be assigned as needed to create elements or attributes in other namespaces.
d3-selection-1.1.0/d3-selection.sublime-project 0000664 0000000 0000000 00000000271 13106363305 0021321 0 ustar 00root root 0000000 0000000 {
"folders": [
{
"path": ".",
"file_exclude_patterns": [
"*.sublime-workspace"
],
"folder_exclude_patterns": [
"build"
]
}
]
}
d3-selection-1.1.0/index.js 0000664 0000000 0000000 00000001500 13106363305 0015443 0 ustar 00root root 0000000 0000000 export {default as creator} from "./src/creator";
export {default as local} from "./src/local";
export {default as matcher} from "./src/matcher";
export {default as mouse} from "./src/mouse";
export {default as namespace} from "./src/namespace";
export {default as namespaces} from "./src/namespaces";
export {default as select} from "./src/select";
export {default as selectAll} from "./src/selectAll";
export {default as selection} from "./src/selection/index";
export {default as selector} from "./src/selector";
export {default as selectorAll} from "./src/selectorAll";
export {styleValue as style} from "./src/selection/style";
export {default as touch} from "./src/touch";
export {default as touches} from "./src/touches";
export {default as window} from "./src/window";
export {event, customEvent} from "./src/selection/on";
d3-selection-1.1.0/package.json 0000664 0000000 0000000 00000002771 13106363305 0016277 0 ustar 00root root 0000000 0000000 {
"name": "d3-selection",
"version": "1.1.0",
"description": "Data-driven DOM manipulation: select elements and join them to data.",
"keywords": [
"d3",
"d3-module",
"dom",
"selection",
"data-join"
],
"homepage": "https://d3js.org/d3-selection/",
"license": "BSD-3-Clause",
"author": {
"name": "Mike Bostock",
"url": "https://bost.ocks.org/mike"
},
"main": "build/d3-selection.js",
"module": "index",
"jsnext:main": "index",
"repository": {
"type": "git",
"url": "https://github.com/d3/d3-selection.git"
},
"scripts": {
"pretest": "rm -rf build && mkdir build && rollup --banner \"$(preamble)\" -f umd -n d3 -o build/d3-selection.js -- index.js",
"test": "tape 'test/**/*-test.js' && eslint index.js src",
"prepublish": "npm run test && uglifyjs --preamble \"$(preamble)\" build/d3-selection.js -c -m -o build/d3-selection.min.js",
"postpublish": "git push && git push --tags && cd ../d3.github.com && git pull && cp ../d3-selection/build/d3-selection.js d3-selection.v1.js && cp ../d3-selection/build/d3-selection.min.js d3-selection.v1.min.js && git add d3-selection.v1.js d3-selection.v1.min.js && git commit -m \"d3-selection ${npm_package_version}\" && git push && cd - && zip -j build/d3-selection.zip -- LICENSE README.md build/d3-selection.js build/d3-selection.min.js"
},
"devDependencies": {
"eslint": "3",
"jsdom": "10",
"package-preamble": "0.1",
"rollup": "0.41",
"tape": "4",
"uglify-js": "^2.8.11"
}
}
d3-selection-1.1.0/src/ 0000775 0000000 0000000 00000000000 13106363305 0014571 5 ustar 00root root 0000000 0000000 d3-selection-1.1.0/src/constant.js 0000664 0000000 0000000 00000000110 13106363305 0016750 0 ustar 00root root 0000000 0000000 export default function(x) {
return function() {
return x;
};
}
d3-selection-1.1.0/src/creator.js 0000664 0000000 0000000 00000001226 13106363305 0016567 0 ustar 00root root 0000000 0000000 import namespace from "./namespace";
import {xhtml} from "./namespaces";
function creatorInherit(name) {
return function() {
var document = this.ownerDocument,
uri = this.namespaceURI;
return uri === xhtml && document.documentElement.namespaceURI === xhtml
? document.createElement(name)
: document.createElementNS(uri, name);
};
}
function creatorFixed(fullname) {
return function() {
return this.ownerDocument.createElementNS(fullname.space, fullname.local);
};
}
export default function(name) {
var fullname = namespace(name);
return (fullname.local
? creatorFixed
: creatorInherit)(fullname);
}
d3-selection-1.1.0/src/local.js 0000664 0000000 0000000 00000001030 13106363305 0016213 0 ustar 00root root 0000000 0000000 var nextId = 0;
export default function local() {
return new Local;
}
function Local() {
this._ = "@" + (++nextId).toString(36);
}
Local.prototype = local.prototype = {
constructor: Local,
get: function(node) {
var id = this._;
while (!(id in node)) if (!(node = node.parentNode)) return;
return node[id];
},
set: function(node, value) {
return node[this._] = value;
},
remove: function(node) {
return this._ in node && delete node[this._];
},
toString: function() {
return this._;
}
};
d3-selection-1.1.0/src/matcher.js 0000664 0000000 0000000 00000001025 13106363305 0016550 0 ustar 00root root 0000000 0000000 var matcher = function(selector) {
return function() {
return this.matches(selector);
};
};
if (typeof document !== "undefined") {
var element = document.documentElement;
if (!element.matches) {
var vendorMatches = element.webkitMatchesSelector
|| element.msMatchesSelector
|| element.mozMatchesSelector
|| element.oMatchesSelector;
matcher = function(selector) {
return function() {
return vendorMatches.call(this, selector);
};
};
}
}
export default matcher;
d3-selection-1.1.0/src/mouse.js 0000664 0000000 0000000 00000000340 13106363305 0016254 0 ustar 00root root 0000000 0000000 import sourceEvent from "./sourceEvent";
import point from "./point";
export default function(node) {
var event = sourceEvent();
if (event.changedTouches) event = event.changedTouches[0];
return point(node, event);
}
d3-selection-1.1.0/src/namespace.js 0000664 0000000 0000000 00000000457 13106363305 0017071 0 ustar 00root root 0000000 0000000 import namespaces from "./namespaces";
export default function(name) {
var prefix = name += "", i = prefix.indexOf(":");
if (i >= 0 && (prefix = name.slice(0, i)) !== "xmlns") name = name.slice(i + 1);
return namespaces.hasOwnProperty(prefix) ? {space: namespaces[prefix], local: name} : name;
}
d3-selection-1.1.0/src/namespaces.js 0000664 0000000 0000000 00000000376 13106363305 0017254 0 ustar 00root root 0000000 0000000 export var xhtml = "http://www.w3.org/1999/xhtml";
export default {
svg: "http://www.w3.org/2000/svg",
xhtml: xhtml,
xlink: "http://www.w3.org/1999/xlink",
xml: "http://www.w3.org/XML/1998/namespace",
xmlns: "http://www.w3.org/2000/xmlns/"
};
d3-selection-1.1.0/src/point.js 0000664 0000000 0000000 00000000700 13106363305 0016255 0 ustar 00root root 0000000 0000000 export default function(node, event) {
var svg = node.ownerSVGElement || node;
if (svg.createSVGPoint) {
var point = svg.createSVGPoint();
point.x = event.clientX, point.y = event.clientY;
point = point.matrixTransform(node.getScreenCTM().inverse());
return [point.x, point.y];
}
var rect = node.getBoundingClientRect();
return [event.clientX - rect.left - node.clientLeft, event.clientY - rect.top - node.clientTop];
}
d3-selection-1.1.0/src/select.js 0000664 0000000 0000000 00000000403 13106363305 0016403 0 ustar 00root root 0000000 0000000 import {Selection, root} from "./selection/index";
export default function(selector) {
return typeof selector === "string"
? new Selection([[document.querySelector(selector)]], [document.documentElement])
: new Selection([[selector]], root);
}
d3-selection-1.1.0/src/selectAll.js 0000664 0000000 0000000 00000000432 13106363305 0017036 0 ustar 00root root 0000000 0000000 import {Selection, root} from "./selection/index";
export default function(selector) {
return typeof selector === "string"
? new Selection([document.querySelectorAll(selector)], [document.documentElement])
: new Selection([selector == null ? [] : selector], root);
}
d3-selection-1.1.0/src/selection/ 0000775 0000000 0000000 00000000000 13106363305 0016556 5 ustar 00root root 0000000 0000000 d3-selection-1.1.0/src/selection/append.js 0000664 0000000 0000000 00000000353 13106363305 0020364 0 ustar 00root root 0000000 0000000 import creator from "../creator";
export default function(name) {
var create = typeof name === "function" ? name : creator(name);
return this.select(function() {
return this.appendChild(create.apply(this, arguments));
});
}
d3-selection-1.1.0/src/selection/attr.js 0000664 0000000 0000000 00000002664 13106363305 0020076 0 ustar 00root root 0000000 0000000 import namespace from "../namespace";
function attrRemove(name) {
return function() {
this.removeAttribute(name);
};
}
function attrRemoveNS(fullname) {
return function() {
this.removeAttributeNS(fullname.space, fullname.local);
};
}
function attrConstant(name, value) {
return function() {
this.setAttribute(name, value);
};
}
function attrConstantNS(fullname, value) {
return function() {
this.setAttributeNS(fullname.space, fullname.local, value);
};
}
function attrFunction(name, value) {
return function() {
var v = value.apply(this, arguments);
if (v == null) this.removeAttribute(name);
else this.setAttribute(name, v);
};
}
function attrFunctionNS(fullname, value) {
return function() {
var v = value.apply(this, arguments);
if (v == null) this.removeAttributeNS(fullname.space, fullname.local);
else this.setAttributeNS(fullname.space, fullname.local, v);
};
}
export default function(name, value) {
var fullname = namespace(name);
if (arguments.length < 2) {
var node = this.node();
return fullname.local
? node.getAttributeNS(fullname.space, fullname.local)
: node.getAttribute(fullname);
}
return this.each((value == null
? (fullname.local ? attrRemoveNS : attrRemove) : (typeof value === "function"
? (fullname.local ? attrFunctionNS : attrFunction)
: (fullname.local ? attrConstantNS : attrConstant)))(fullname, value));
}
d3-selection-1.1.0/src/selection/call.js 0000664 0000000 0000000 00000000206 13106363305 0020025 0 ustar 00root root 0000000 0000000 export default function() {
var callback = arguments[0];
arguments[0] = this;
callback.apply(null, arguments);
return this;
}
d3-selection-1.1.0/src/selection/classed.js 0000664 0000000 0000000 00000003314 13106363305 0020533 0 ustar 00root root 0000000 0000000 function classArray(string) {
return string.trim().split(/^|\s+/);
}
function classList(node) {
return node.classList || new ClassList(node);
}
function ClassList(node) {
this._node = node;
this._names = classArray(node.getAttribute("class") || "");
}
ClassList.prototype = {
add: function(name) {
var i = this._names.indexOf(name);
if (i < 0) {
this._names.push(name);
this._node.setAttribute("class", this._names.join(" "));
}
},
remove: function(name) {
var i = this._names.indexOf(name);
if (i >= 0) {
this._names.splice(i, 1);
this._node.setAttribute("class", this._names.join(" "));
}
},
contains: function(name) {
return this._names.indexOf(name) >= 0;
}
};
function classedAdd(node, names) {
var list = classList(node), i = -1, n = names.length;
while (++i < n) list.add(names[i]);
}
function classedRemove(node, names) {
var list = classList(node), i = -1, n = names.length;
while (++i < n) list.remove(names[i]);
}
function classedTrue(names) {
return function() {
classedAdd(this, names);
};
}
function classedFalse(names) {
return function() {
classedRemove(this, names);
};
}
function classedFunction(names, value) {
return function() {
(value.apply(this, arguments) ? classedAdd : classedRemove)(this, names);
};
}
export default function(name, value) {
var names = classArray(name + "");
if (arguments.length < 2) {
var list = classList(this.node()), i = -1, n = names.length;
while (++i < n) if (!list.contains(names[i])) return false;
return true;
}
return this.each((typeof value === "function"
? classedFunction : value
? classedTrue
: classedFalse)(names, value));
}
d3-selection-1.1.0/src/selection/data.js 0000664 0000000 0000000 00000007015 13106363305 0020030 0 ustar 00root root 0000000 0000000 import {Selection} from "./index";
import {EnterNode} from "./enter";
import constant from "../constant";
var keyPrefix = "$"; // Protect against keys like “__proto__”.
function bindIndex(parent, group, enter, update, exit, data) {
var i = 0,
node,
groupLength = group.length,
dataLength = data.length;
// Put any non-null nodes that fit into update.
// Put any null nodes into enter.
// Put any remaining data into enter.
for (; i < dataLength; ++i) {
if (node = group[i]) {
node.__data__ = data[i];
update[i] = node;
} else {
enter[i] = new EnterNode(parent, data[i]);
}
}
// Put any non-null nodes that don’t fit into exit.
for (; i < groupLength; ++i) {
if (node = group[i]) {
exit[i] = node;
}
}
}
function bindKey(parent, group, enter, update, exit, data, key) {
var i,
node,
nodeByKeyValue = {},
groupLength = group.length,
dataLength = data.length,
keyValues = new Array(groupLength),
keyValue;
// Compute the key for each node.
// If multiple nodes have the same key, the duplicates are added to exit.
for (i = 0; i < groupLength; ++i) {
if (node = group[i]) {
keyValues[i] = keyValue = keyPrefix + key.call(node, node.__data__, i, group);
if (keyValue in nodeByKeyValue) {
exit[i] = node;
} else {
nodeByKeyValue[keyValue] = node;
}
}
}
// Compute the key for each datum.
// If there a node associated with this key, join and add it to update.
// If there is not (or the key is a duplicate), add it to enter.
for (i = 0; i < dataLength; ++i) {
keyValue = keyPrefix + key.call(parent, data[i], i, data);
if (node = nodeByKeyValue[keyValue]) {
update[i] = node;
node.__data__ = data[i];
nodeByKeyValue[keyValue] = null;
} else {
enter[i] = new EnterNode(parent, data[i]);
}
}
// Add any remaining nodes that were not bound to data to exit.
for (i = 0; i < groupLength; ++i) {
if ((node = group[i]) && (nodeByKeyValue[keyValues[i]] === node)) {
exit[i] = node;
}
}
}
export default function(value, key) {
if (!value) {
data = new Array(this.size()), j = -1;
this.each(function(d) { data[++j] = d; });
return data;
}
var bind = key ? bindKey : bindIndex,
parents = this._parents,
groups = this._groups;
if (typeof value !== "function") value = constant(value);
for (var m = groups.length, update = new Array(m), enter = new Array(m), exit = new Array(m), j = 0; j < m; ++j) {
var parent = parents[j],
group = groups[j],
groupLength = group.length,
data = value.call(parent, parent && parent.__data__, j, parents),
dataLength = data.length,
enterGroup = enter[j] = new Array(dataLength),
updateGroup = update[j] = new Array(dataLength),
exitGroup = exit[j] = new Array(groupLength);
bind(parent, group, enterGroup, updateGroup, exitGroup, data, key);
// Now connect the enter nodes to their following update node, such that
// appendChild can insert the materialized enter node before this node,
// rather than at the end of the parent node.
for (var i0 = 0, i1 = 0, previous, next; i0 < dataLength; ++i0) {
if (previous = enterGroup[i0]) {
if (i0 >= i1) i1 = i0 + 1;
while (!(next = updateGroup[i1]) && ++i1 < dataLength);
previous._next = next || null;
}
}
}
update = new Selection(update, parents);
update._enter = enter;
update._exit = exit;
return update;
}
d3-selection-1.1.0/src/selection/datum.js 0000664 0000000 0000000 00000000204 13106363305 0020222 0 ustar 00root root 0000000 0000000 export default function(value) {
return arguments.length
? this.property("__data__", value)
: this.node().__data__;
}
d3-selection-1.1.0/src/selection/dispatch.js 0000664 0000000 0000000 00000001573 13106363305 0020721 0 ustar 00root root 0000000 0000000 import defaultView from "../window";
function dispatchEvent(node, type, params) {
var window = defaultView(node),
event = window.CustomEvent;
if (typeof event === "function") {
event = new event(type, params);
} else {
event = window.document.createEvent("Event");
if (params) event.initEvent(type, params.bubbles, params.cancelable), event.detail = params.detail;
else event.initEvent(type, false, false);
}
node.dispatchEvent(event);
}
function dispatchConstant(type, params) {
return function() {
return dispatchEvent(this, type, params);
};
}
function dispatchFunction(type, params) {
return function() {
return dispatchEvent(this, type, params.apply(this, arguments));
};
}
export default function(type, params) {
return this.each((typeof params === "function"
? dispatchFunction
: dispatchConstant)(type, params));
}
d3-selection-1.1.0/src/selection/each.js 0000664 0000000 0000000 00000000441 13106363305 0020013 0 ustar 00root root 0000000 0000000 export default function(callback) {
for (var groups = this._groups, j = 0, m = groups.length; j < m; ++j) {
for (var group = groups[j], i = 0, n = group.length, node; i < n; ++i) {
if (node = group[i]) callback.call(node, node.__data__, i, group);
}
}
return this;
}
d3-selection-1.1.0/src/selection/empty.js 0000664 0000000 0000000 00000000065 13106363305 0020253 0 ustar 00root root 0000000 0000000 export default function() {
return !this.node();
}
d3-selection-1.1.0/src/selection/enter.js 0000664 0000000 0000000 00000001430 13106363305 0020227 0 ustar 00root root 0000000 0000000 import sparse from "./sparse";
import {Selection} from "./index";
export default function() {
return new Selection(this._enter || this._groups.map(sparse), this._parents);
}
export function EnterNode(parent, datum) {
this.ownerDocument = parent.ownerDocument;
this.namespaceURI = parent.namespaceURI;
this._next = null;
this._parent = parent;
this.__data__ = datum;
}
EnterNode.prototype = {
constructor: EnterNode,
appendChild: function(child) { return this._parent.insertBefore(child, this._next); },
insertBefore: function(child, next) { return this._parent.insertBefore(child, next); },
querySelector: function(selector) { return this._parent.querySelector(selector); },
querySelectorAll: function(selector) { return this._parent.querySelectorAll(selector); }
};
d3-selection-1.1.0/src/selection/exit.js 0000664 0000000 0000000 00000000260 13106363305 0020063 0 ustar 00root root 0000000 0000000 import sparse from "./sparse";
import {Selection} from "./index";
export default function() {
return new Selection(this._exit || this._groups.map(sparse), this._parents);
}
d3-selection-1.1.0/src/selection/filter.js 0000664 0000000 0000000 00000001042 13106363305 0020376 0 ustar 00root root 0000000 0000000 import {Selection} from "./index";
import matcher from "../matcher";
export default function(match) {
if (typeof match !== "function") match = matcher(match);
for (var groups = this._groups, m = groups.length, subgroups = new Array(m), j = 0; j < m; ++j) {
for (var group = groups[j], n = group.length, subgroup = subgroups[j] = [], node, i = 0; i < n; ++i) {
if ((node = group[i]) && match.call(node, node.__data__, i, group)) {
subgroup.push(node);
}
}
}
return new Selection(subgroups, this._parents);
}
d3-selection-1.1.0/src/selection/html.js 0000664 0000000 0000000 00000001010 13106363305 0020050 0 ustar 00root root 0000000 0000000 function htmlRemove() {
this.innerHTML = "";
}
function htmlConstant(value) {
return function() {
this.innerHTML = value;
};
}
function htmlFunction(value) {
return function() {
var v = value.apply(this, arguments);
this.innerHTML = v == null ? "" : v;
};
}
export default function(value) {
return arguments.length
? this.each(value == null
? htmlRemove : (typeof value === "function"
? htmlFunction
: htmlConstant)(value))
: this.node().innerHTML;
}
d3-selection-1.1.0/src/selection/index.js 0000664 0000000 0000000 00000004250 13106363305 0020224 0 ustar 00root root 0000000 0000000 import selection_select from "./select";
import selection_selectAll from "./selectAll";
import selection_filter from "./filter";
import selection_data from "./data";
import selection_enter from "./enter";
import selection_exit from "./exit";
import selection_merge from "./merge";
import selection_order from "./order";
import selection_sort from "./sort";
import selection_call from "./call";
import selection_nodes from "./nodes";
import selection_node from "./node";
import selection_size from "./size";
import selection_empty from "./empty";
import selection_each from "./each";
import selection_attr from "./attr";
import selection_style from "./style";
import selection_property from "./property";
import selection_classed from "./classed";
import selection_text from "./text";
import selection_html from "./html";
import selection_raise from "./raise";
import selection_lower from "./lower";
import selection_append from "./append";
import selection_insert from "./insert";
import selection_remove from "./remove";
import selection_datum from "./datum";
import selection_on from "./on";
import selection_dispatch from "./dispatch";
export var root = [null];
export function Selection(groups, parents) {
this._groups = groups;
this._parents = parents;
}
function selection() {
return new Selection([[document.documentElement]], root);
}
Selection.prototype = selection.prototype = {
constructor: Selection,
select: selection_select,
selectAll: selection_selectAll,
filter: selection_filter,
data: selection_data,
enter: selection_enter,
exit: selection_exit,
merge: selection_merge,
order: selection_order,
sort: selection_sort,
call: selection_call,
nodes: selection_nodes,
node: selection_node,
size: selection_size,
empty: selection_empty,
each: selection_each,
attr: selection_attr,
style: selection_style,
property: selection_property,
classed: selection_classed,
text: selection_text,
html: selection_html,
raise: selection_raise,
lower: selection_lower,
append: selection_append,
insert: selection_insert,
remove: selection_remove,
datum: selection_datum,
on: selection_on,
dispatch: selection_dispatch
};
export default selection;
d3-selection-1.1.0/src/selection/insert.js 0000664 0000000 0000000 00000000724 13106363305 0020423 0 ustar 00root root 0000000 0000000 import creator from "../creator";
import selector from "../selector";
function constantNull() {
return null;
}
export default function(name, before) {
var create = typeof name === "function" ? name : creator(name),
select = before == null ? constantNull : typeof before === "function" ? before : selector(before);
return this.select(function() {
return this.insertBefore(create.apply(this, arguments), select.apply(this, arguments) || null);
});
}
d3-selection-1.1.0/src/selection/lower.js 0000664 0000000 0000000 00000000253 13106363305 0020244 0 ustar 00root root 0000000 0000000 function lower() {
if (this.previousSibling) this.parentNode.insertBefore(this, this.parentNode.firstChild);
}
export default function() {
return this.each(lower);
}
d3-selection-1.1.0/src/selection/merge.js 0000664 0000000 0000000 00000001077 13106363305 0020220 0 ustar 00root root 0000000 0000000 import {Selection} from "./index";
export default function(selection) {
for (var groups0 = this._groups, groups1 = selection._groups, m0 = groups0.length, m1 = groups1.length, m = Math.min(m0, m1), merges = new Array(m0), j = 0; j < m; ++j) {
for (var group0 = groups0[j], group1 = groups1[j], n = group0.length, merge = merges[j] = new Array(n), node, i = 0; i < n; ++i) {
if (node = group0[i] || group1[i]) {
merge[i] = node;
}
}
}
for (; j < m0; ++j) {
merges[j] = groups0[j];
}
return new Selection(merges, this._parents);
}
d3-selection-1.1.0/src/selection/node.js 0000664 0000000 0000000 00000000402 13106363305 0020035 0 ustar 00root root 0000000 0000000 export default function() {
for (var groups = this._groups, j = 0, m = groups.length; j < m; ++j) {
for (var group = groups[j], i = 0, n = group.length; i < n; ++i) {
var node = group[i];
if (node) return node;
}
}
return null;
}
d3-selection-1.1.0/src/selection/nodes.js 0000664 0000000 0000000 00000000214 13106363305 0020221 0 ustar 00root root 0000000 0000000 export default function() {
var nodes = new Array(this.size()), i = -1;
this.each(function() { nodes[++i] = this; });
return nodes;
}
d3-selection-1.1.0/src/selection/on.js 0000664 0000000 0000000 00000006057 13106363305 0017540 0 ustar 00root root 0000000 0000000 var filterEvents = {};
export var event = null;
if (typeof document !== "undefined") {
var element = document.documentElement;
if (!("onmouseenter" in element)) {
filterEvents = {mouseenter: "mouseover", mouseleave: "mouseout"};
}
}
function filterContextListener(listener, index, group) {
listener = contextListener(listener, index, group);
return function(event) {
var related = event.relatedTarget;
if (!related || (related !== this && !(related.compareDocumentPosition(this) & 8))) {
listener.call(this, event);
}
};
}
function contextListener(listener, index, group) {
return function(event1) {
var event0 = event; // Events can be reentrant (e.g., focus).
event = event1;
try {
listener.call(this, this.__data__, index, group);
} finally {
event = event0;
}
};
}
function parseTypenames(typenames) {
return typenames.trim().split(/^|\s+/).map(function(t) {
var name = "", i = t.indexOf(".");
if (i >= 0) name = t.slice(i + 1), t = t.slice(0, i);
return {type: t, name: name};
});
}
function onRemove(typename) {
return function() {
var on = this.__on;
if (!on) return;
for (var j = 0, i = -1, m = on.length, o; j < m; ++j) {
if (o = on[j], (!typename.type || o.type === typename.type) && o.name === typename.name) {
this.removeEventListener(o.type, o.listener, o.capture);
} else {
on[++i] = o;
}
}
if (++i) on.length = i;
else delete this.__on;
};
}
function onAdd(typename, value, capture) {
var wrap = filterEvents.hasOwnProperty(typename.type) ? filterContextListener : contextListener;
return function(d, i, group) {
var on = this.__on, o, listener = wrap(value, i, group);
if (on) for (var j = 0, m = on.length; j < m; ++j) {
if ((o = on[j]).type === typename.type && o.name === typename.name) {
this.removeEventListener(o.type, o.listener, o.capture);
this.addEventListener(o.type, o.listener = listener, o.capture = capture);
o.value = value;
return;
}
}
this.addEventListener(typename.type, listener, capture);
o = {type: typename.type, name: typename.name, value: value, listener: listener, capture: capture};
if (!on) this.__on = [o];
else on.push(o);
};
}
export default function(typename, value, capture) {
var typenames = parseTypenames(typename + ""), i, n = typenames.length, t;
if (arguments.length < 2) {
var on = this.node().__on;
if (on) for (var j = 0, m = on.length, o; j < m; ++j) {
for (i = 0, o = on[j]; i < n; ++i) {
if ((t = typenames[i]).type === o.type && t.name === o.name) {
return o.value;
}
}
}
return;
}
on = value ? onAdd : onRemove;
if (capture == null) capture = false;
for (i = 0; i < n; ++i) this.each(on(typenames[i], value, capture));
return this;
}
export function customEvent(event1, listener, that, args) {
var event0 = event;
event1.sourceEvent = event;
event = event1;
try {
return listener.apply(that, args);
} finally {
event = event0;
}
}
d3-selection-1.1.0/src/selection/order.js 0000664 0000000 0000000 00000000557 13106363305 0020236 0 ustar 00root root 0000000 0000000 export default function() {
for (var groups = this._groups, j = -1, m = groups.length; ++j < m;) {
for (var group = groups[j], i = group.length - 1, next = group[i], node; --i >= 0;) {
if (node = group[i]) {
if (next && next !== node.nextSibling) next.parentNode.insertBefore(node, next);
next = node;
}
}
}
return this;
}
d3-selection-1.1.0/src/selection/property.js 0000664 0000000 0000000 00000001151 13106363305 0020776 0 ustar 00root root 0000000 0000000 function propertyRemove(name) {
return function() {
delete this[name];
};
}
function propertyConstant(name, value) {
return function() {
this[name] = value;
};
}
function propertyFunction(name, value) {
return function() {
var v = value.apply(this, arguments);
if (v == null) delete this[name];
else this[name] = v;
};
}
export default function(name, value) {
return arguments.length > 1
? this.each((value == null
? propertyRemove : typeof value === "function"
? propertyFunction
: propertyConstant)(name, value))
: this.node()[name];
}
d3-selection-1.1.0/src/selection/raise.js 0000664 0000000 0000000 00000000212 13106363305 0020212 0 ustar 00root root 0000000 0000000 function raise() {
if (this.nextSibling) this.parentNode.appendChild(this);
}
export default function() {
return this.each(raise);
}
d3-selection-1.1.0/src/selection/remove.js 0000664 0000000 0000000 00000000231 13106363305 0020405 0 ustar 00root root 0000000 0000000 function remove() {
var parent = this.parentNode;
if (parent) parent.removeChild(this);
}
export default function() {
return this.each(remove);
}
d3-selection-1.1.0/src/selection/select.js 0000664 0000000 0000000 00000001215 13106363305 0020372 0 ustar 00root root 0000000 0000000 import {Selection} from "./index";
import selector from "../selector";
export default function(select) {
if (typeof select !== "function") select = selector(select);
for (var groups = this._groups, m = groups.length, subgroups = new Array(m), j = 0; j < m; ++j) {
for (var group = groups[j], n = group.length, subgroup = subgroups[j] = new Array(n), node, subnode, i = 0; i < n; ++i) {
if ((node = group[i]) && (subnode = select.call(node, node.__data__, i, group))) {
if ("__data__" in node) subnode.__data__ = node.__data__;
subgroup[i] = subnode;
}
}
}
return new Selection(subgroups, this._parents);
}
d3-selection-1.1.0/src/selection/selectAll.js 0000664 0000000 0000000 00000001046 13106363305 0021025 0 ustar 00root root 0000000 0000000 import {Selection} from "./index";
import selectorAll from "../selectorAll";
export default function(select) {
if (typeof select !== "function") select = selectorAll(select);
for (var groups = this._groups, m = groups.length, subgroups = [], parents = [], j = 0; j < m; ++j) {
for (var group = groups[j], n = group.length, node, i = 0; i < n; ++i) {
if (node = group[i]) {
subgroups.push(select.call(node, node.__data__, i, group));
parents.push(node);
}
}
}
return new Selection(subgroups, parents);
}
d3-selection-1.1.0/src/selection/size.js 0000664 0000000 0000000 00000000142 13106363305 0020063 0 ustar 00root root 0000000 0000000 export default function() {
var size = 0;
this.each(function() { ++size; });
return size;
}
d3-selection-1.1.0/src/selection/sort.js 0000664 0000000 0000000 00000001251 13106363305 0020102 0 ustar 00root root 0000000 0000000 import {Selection} from "./index";
export default function(compare) {
if (!compare) compare = ascending;
function compareNode(a, b) {
return a && b ? compare(a.__data__, b.__data__) : !a - !b;
}
for (var groups = this._groups, m = groups.length, sortgroups = new Array(m), j = 0; j < m; ++j) {
for (var group = groups[j], n = group.length, sortgroup = sortgroups[j] = new Array(n), node, i = 0; i < n; ++i) {
if (node = group[i]) {
sortgroup[i] = node;
}
}
sortgroup.sort(compareNode);
}
return new Selection(sortgroups, this._parents).order();
}
function ascending(a, b) {
return a < b ? -1 : a > b ? 1 : a >= b ? 0 : NaN;
}
d3-selection-1.1.0/src/selection/sparse.js 0000664 0000000 0000000 00000000107 13106363305 0020407 0 ustar 00root root 0000000 0000000 export default function(update) {
return new Array(update.length);
}
d3-selection-1.1.0/src/selection/style.js 0000664 0000000 0000000 00000001710 13106363305 0020253 0 ustar 00root root 0000000 0000000 import defaultView from "../window";
function styleRemove(name) {
return function() {
this.style.removeProperty(name);
};
}
function styleConstant(name, value, priority) {
return function() {
this.style.setProperty(name, value, priority);
};
}
function styleFunction(name, value, priority) {
return function() {
var v = value.apply(this, arguments);
if (v == null) this.style.removeProperty(name);
else this.style.setProperty(name, v, priority);
};
}
export default function(name, value, priority) {
return arguments.length > 1
? this.each((value == null
? styleRemove : typeof value === "function"
? styleFunction
: styleConstant)(name, value, priority == null ? "" : priority))
: styleValue(this.node(), name);
}
export function styleValue(node, name) {
return node.style.getPropertyValue(name)
|| defaultView(node).getComputedStyle(node, null).getPropertyValue(name);
}
d3-selection-1.1.0/src/selection/text.js 0000664 0000000 0000000 00000001020 13106363305 0020071 0 ustar 00root root 0000000 0000000 function textRemove() {
this.textContent = "";
}
function textConstant(value) {
return function() {
this.textContent = value;
};
}
function textFunction(value) {
return function() {
var v = value.apply(this, arguments);
this.textContent = v == null ? "" : v;
};
}
export default function(value) {
return arguments.length
? this.each(value == null
? textRemove : (typeof value === "function"
? textFunction
: textConstant)(value))
: this.node().textContent;
}
d3-selection-1.1.0/src/selector.js 0000664 0000000 0000000 00000000230 13106363305 0016742 0 ustar 00root root 0000000 0000000 function none() {}
export default function(selector) {
return selector == null ? none : function() {
return this.querySelector(selector);
};
}
d3-selection-1.1.0/src/selectorAll.js 0000664 0000000 0000000 00000000253 13106363305 0017400 0 ustar 00root root 0000000 0000000 function empty() {
return [];
}
export default function(selector) {
return selector == null ? empty : function() {
return this.querySelectorAll(selector);
};
}
d3-selection-1.1.0/src/sourceEvent.js 0000664 0000000 0000000 00000000257 13106363305 0017435 0 ustar 00root root 0000000 0000000 import {event} from "./selection/on";
export default function() {
var current = event, source;
while (source = current.sourceEvent) current = source;
return current;
}
d3-selection-1.1.0/src/touch.js 0000664 0000000 0000000 00000000627 13106363305 0016256 0 ustar 00root root 0000000 0000000 import sourceEvent from "./sourceEvent";
import point from "./point";
export default function(node, touches, identifier) {
if (arguments.length < 3) identifier = touches, touches = sourceEvent().changedTouches;
for (var i = 0, n = touches ? touches.length : 0, touch; i < n; ++i) {
if ((touch = touches[i]).identifier === identifier) {
return point(node, touch);
}
}
return null;
}
d3-selection-1.1.0/src/touches.js 0000664 0000000 0000000 00000000503 13106363305 0016577 0 ustar 00root root 0000000 0000000 import sourceEvent from "./sourceEvent";
import point from "./point";
export default function(node, touches) {
if (touches == null) touches = sourceEvent().touches;
for (var i = 0, n = touches ? touches.length : 0, points = new Array(n); i < n; ++i) {
points[i] = point(node, touches[i]);
}
return points;
}
d3-selection-1.1.0/src/window.js 0000664 0000000 0000000 00000000332 13106363305 0016434 0 ustar 00root root 0000000 0000000 export default function(node) {
return (node.ownerDocument && node.ownerDocument.defaultView) // node is a Node
|| (node.document && node) // node is a Window
|| node.defaultView; // node is a Document
}
d3-selection-1.1.0/test/ 0000775 0000000 0000000 00000000000 13106363305 0014761 5 ustar 00root root 0000000 0000000 d3-selection-1.1.0/test/creator-test.js 0000664 0000000 0000000 00000002365 13106363305 0017741 0 ustar 00root root 0000000 0000000 var tape = require("tape"),
jsdom = require("./jsdom"),
d3 = require("../");
tape("d3.creator(name).call(element) returns a new element with the given name", function(test) {
var document = jsdom("");
test.deepEqual(type(d3.creator("h1").call(document.body)), {namespace: "http://www.w3.org/1999/xhtml", name: "H1"});
test.deepEqual(type(d3.creator("xhtml:h1").call(document.body)), {namespace: "http://www.w3.org/1999/xhtml", name: "H1"});
test.deepEqual(type(d3.creator("svg").call(document.body)), {namespace: "http://www.w3.org/2000/svg", name: "svg"});
test.deepEqual(type(d3.creator("g").call(document.body)), {namespace: "http://www.w3.org/1999/xhtml", name: "G"});
test.end();
});
tape("d3.creator(name).call(element) can inherit the namespace from the given element", function(test) {
var document = jsdom(""),
svg = document.querySelector("svg");
test.deepEqual(type(d3.creator("g").call(document.body)), {namespace: "http://www.w3.org/1999/xhtml", name: "G"});
test.deepEqual(type(d3.creator("g").call(svg)), {namespace: "http://www.w3.org/2000/svg", name: "g"});
test.end();
});
function type(element) {
return {namespace: element.namespaceURI, name: element.tagName};
}
d3-selection-1.1.0/test/event-test.js 0000664 0000000 0000000 00000002172 13106363305 0017417 0 ustar 00root root 0000000 0000000 var tape = require("tape"),
jsdom = require("./jsdom"),
d3 = require("../");
tape("d3.event is set exactly during the callback of an event listener", function(test) {
var event,
document = jsdom(""),
one = document.querySelector("#one"),
selection = d3.selectAll([one]).on("click", function() { event = d3.event; });
test.equal(d3.event, null);
selection.dispatch("click");
test.equal(d3.event, null);
test.equal(event.type, "click");
test.equal(event.target, one);
test.end();
});
tape("d3.event is restored to its previous value during reentrant events", function(test) {
var event1,
event2,
event3,
document = jsdom(""),
one = document.querySelector("#one"),
selection = d3.selectAll([one]).on("foo", function() { event1 = d3.event; selection.dispatch("bar"); event3 = d3.event; }).on("bar", function() { event2 = d3.event; });
test.equal(d3.event, null);
selection.dispatch("foo");
test.equal(d3.event, null);
test.equal(event1.type, "foo");
test.equal(event2.type, "bar");
test.equal(event3, event1);
test.end();
});
d3-selection-1.1.0/test/jsdom.js 0000664 0000000 0000000 00000000166 13106363305 0016436 0 ustar 00root root 0000000 0000000 var jsdom = require("jsdom");
module.exports = function(html) {
return (new jsdom.JSDOM(html)).window.document;
};
d3-selection-1.1.0/test/matcher-test.js 0000664 0000000 0000000 00000001067 13106363305 0017723 0 ustar 00root root 0000000 0000000 var tape = require("tape"),
jsdom = require("./jsdom"),
d3 = require("../");
tape("d3.matcher(selector).call(element) returns true if the element matches the selector", function(test) {
var document = jsdom("");
test.equal(d3.matcher("body").call(document.body), true);
test.equal(d3.matcher(".foo").call(document.body), true);
test.equal(d3.matcher("body.foo").call(document.body), true);
test.equal(d3.matcher("h1").call(document.body), false);
test.equal(d3.matcher("body.bar").call(document.body), false);
test.end();
});
d3-selection-1.1.0/test/namespace-test.js 0000664 0000000 0000000 00000003766 13106363305 0020244 0 ustar 00root root 0000000 0000000 var tape = require("tape"),
jsdom = require("./jsdom"),
d3 = require("../");
tape("d3.namespace(name) returns name if there is no namespace prefix", function(test) {
test.equal(d3.namespace("foo"), "foo");
test.equal(d3.namespace("foo:bar"), "bar");
test.end();
});
tape("d3.namespace(name) coerces name to a string", function(test) {
test.equal(d3.namespace({toString: function() { return "foo"; }}), "foo");
test.deepEqual(d3.namespace({toString: function() { return "svg"; }}), {space: "http://www.w3.org/2000/svg", local: "svg"});
test.end();
});
tape("d3.namespace(name) returns the expected values for built-in namespaces", function(test) {
test.deepEqual(d3.namespace("svg"), {space: "http://www.w3.org/2000/svg", local: "svg"});
test.deepEqual(d3.namespace("xhtml"), {space: "http://www.w3.org/1999/xhtml", local: "xhtml"});
test.deepEqual(d3.namespace("xlink"), {space: "http://www.w3.org/1999/xlink", local: "xlink"});
test.deepEqual(d3.namespace("xml"), {space: "http://www.w3.org/XML/1998/namespace", local: "xml"});
test.deepEqual(d3.namespace("svg:g"), {space: "http://www.w3.org/2000/svg", local: "g"});
test.deepEqual(d3.namespace("xhtml:b"), {space: "http://www.w3.org/1999/xhtml", local: "b"});
test.deepEqual(d3.namespace("xlink:href"), {space: "http://www.w3.org/1999/xlink", local: "href"});
test.deepEqual(d3.namespace("xml:lang"), {space: "http://www.w3.org/XML/1998/namespace", local: "lang"});
test.end();
});
tape("d3.namespace(\"xmlns:…\") treats the whole name as the local name", function(test) {
test.deepEqual(d3.namespace("xmlns:xlink"), {space: "http://www.w3.org/2000/xmlns/", local: "xmlns:xlink"});
test.end();
});
tape("d3.namespace(name) observes modifications to d3.namespaces", function(test) {
d3.namespaces.d3js = "https://d3js.org/2016/namespace";
test.deepEqual(d3.namespace("d3js:pie"), {space: "https://d3js.org/2016/namespace", local: "pie"});
delete d3.namespaces.d3js;
test.equal(d3.namespace("d3js:pie"), "pie");
test.end();
});
d3-selection-1.1.0/test/namespaces-test.js 0000664 0000000 0000000 00000000644 13106363305 0020417 0 ustar 00root root 0000000 0000000 var tape = require("tape"),
jsdom = require("./jsdom"),
d3 = require("../");
tape("d3.namespaces is the expected map", function(test) {
test.deepEqual(d3.namespaces, {
svg: "http://www.w3.org/2000/svg",
xhtml: "http://www.w3.org/1999/xhtml",
xlink: "http://www.w3.org/1999/xlink",
xml: "http://www.w3.org/XML/1998/namespace",
xmlns: "http://www.w3.org/2000/xmlns/"
});
test.end();
});
d3-selection-1.1.0/test/select-test.js 0000664 0000000 0000000 00000003744 13106363305 0017563 0 ustar 00root root 0000000 0000000 var tape = require("tape"),
jsdom = require("./jsdom"),
d3 = require("../");
tape("d3.select(…) returns an instanceof d3.selection", function(test) {
var document = jsdom("
hello
");
test.ok(d3.select(document) instanceof d3.selection);
test.end();
});
tape("d3.select(string) selects the first element that matches the selector string", function(test) {
var document = global.document = jsdom("
foo
bar
");
try {
test.deepEqual(d3.select("h1"), {_groups: [[document.querySelector("h1")]], _parents: [document.documentElement]});
test.end();
} finally {
delete global.document;
}
});
tape("d3.select(element) selects the given element", function(test) {
var document = jsdom("
hello
");
test.deepEqual(d3.select(document.body), {_groups: [[document.body]], _parents: [null]});
test.deepEqual(d3.select(document.documentElement), {_groups: [[document.documentElement]], _parents: [null]});
test.end();
});
tape("d3.select(window) selects the given window", function(test) {
var document = jsdom("
hello
");
test.deepEqual(d3.select(document.defaultView), {_groups: [[document.defaultView]], _parents: [null]});
test.end();
});
tape("d3.select(document) selects the given document", function(test) {
var document = jsdom("
");
test.ok(d3.selectAll([document]) instanceof d3.selection);
test.end();
});
tape("d3.selectAll(string) selects all elements that match the selector string, in order", function(test) {
var document = global.document = jsdom("
foo
bar
");
try {
test.deepEqual(d3.selectAll("h1"), {_groups: [document.querySelectorAll("h1")], _parents: [document.documentElement]});
test.end();
} finally {
delete global.document;
}
});
tape("d3.selectAll(nodeList) selects a NodeList of elements", function(test) {
var document = jsdom("
hello
world
");
test.deepEqual(d3.selectAll(document.querySelectorAll("h1,h2")), {_groups: [document.querySelectorAll("h1,h2")], _parents: [null]});
test.end();
});
tape("d3.selectAll(array) selects an array of elements", function(test) {
var document = jsdom("
hello
world
"),
h1 = document.querySelector("h1"),
h2 = document.querySelector("h2");
test.deepEqual(d3.selectAll([h1, h2]), {_groups: [[h1, h2]], _parents: [null]});
test.end();
});
tape("d3.selectAll(array) can select an empty array", function(test) {
test.deepEqual(d3.selectAll([]), {_groups: [[]], _parents: [null]});
test.end();
});
tape("d3.selectAll(null) selects an empty array", function(test) {
test.deepEqual(d3.selectAll(), {_groups: [[]], _parents: [null]});
test.deepEqual(d3.selectAll(null), {_groups: [[]], _parents: [null]});
test.deepEqual(d3.selectAll(undefined), {_groups: [[]], _parents: [null]});
test.end();
});
tape("d3.selectAll(null) selects a new empty array each time", function(test) {
var one = d3.selectAll()._groups[0],
two = d3.selectAll()._groups[0];
test.equal(one === two, false);
one.push("one");
test.deepEqual(d3.selectAll()._groups[0], []);
test.end();
});
tape("d3.selectAll(array) can select an array that contains null", function(test) {
var document = jsdom("
hello
world
"),
h1 = document.querySelector("h1");
test.deepEqual(d3.selectAll([null, h1, null]), {_groups: [[null, h1, null]], _parents: [null]});
test.end();
});
tape("d3.selectAll(array) can select an array that contains arbitrary objects", function(test) {
var object = {};
test.deepEqual(d3.selectAll([object]), {_groups: [[object]], _parents: [null]});
test.end();
});
d3-selection-1.1.0/test/selection/ 0000775 0000000 0000000 00000000000 13106363305 0016746 5 ustar 00root root 0000000 0000000 d3-selection-1.1.0/test/selection/append-test.js 0000664 0000000 0000000 00000017514 13106363305 0021540 0 ustar 00root root 0000000 0000000 var tape = require("tape"),
jsdom = require("../jsdom"),
d3 = require("../../");
tape("selection.append(…) returns a selection", function(test) {
var document = jsdom();
test.ok(d3.select(document.body).append("h1") instanceof d3.selection);
test.end();
});
tape("selection.append(name) appends a new element of the specified name as the last child of each selected element", function(test) {
var document = jsdom("
"),
one = document.querySelector("#one"),
two = document.querySelector("#two"),
selection = d3.selectAll([one, two]).append("span"),
three = one.querySelector("span:last-child"),
four = two.querySelector("span:last-child");
test.deepEqual(selection, {_groups: [[three, four]], _parents: [null]});
test.end();
});
tape("selection.append(name) observes the specified namespace, if any", function(test) {
var document = jsdom(""),
one = document.querySelector("#one"),
two = document.querySelector("#two"),
selection = d3.selectAll([one, two]).append("svg:g"),
three = one.querySelector("g"),
four = two.querySelector("g");
test.equal(three.namespaceURI, "http://www.w3.org/2000/svg");
test.equal(four.namespaceURI, "http://www.w3.org/2000/svg");
test.deepEqual(selection, {_groups: [[three, four]], _parents: [null]});
test.end();
});
tape("selection.append(name) uses createElement, not createElementNS, if the implied namespace is the same as the document", function(test) {
var pass = 0,
document = jsdom(""),
one = document.querySelector("#one"),
two = document.querySelector("#two"),
createElement = document.createElement;
document.createElement = function() {
++pass;
return createElement.apply(this, arguments);
};
var selection = d3.selectAll([one, two]).append("P"),
three = one.querySelector("p"),
four = two.querySelector("p");
test.equal(pass, 2);
test.deepEqual(selection, {_groups: [[three, four]], _parents: [null]});
test.end();
});
tape("selection.append(name) observes the implicit namespace, if any", function(test) {
var document = jsdom(""),
one = document.querySelector("#one"),
two = document.querySelector("#two"),
selection = d3.selectAll([one, two]).append("svg"),
three = one.querySelector("svg"),
four = two.querySelector("svg");
test.equal(three.namespaceURI, "http://www.w3.org/2000/svg");
test.equal(four.namespaceURI, "http://www.w3.org/2000/svg");
test.deepEqual(selection, {_groups: [[three, four]], _parents: [null]});
test.end();
});
tape("selection.append(name) observes the inherited namespace, if any", function(test) {
var document = jsdom(""),
one = document.querySelector("#one"),
two = document.querySelector("#two"),
selection = d3.selectAll([one, two]).append("svg").append("g"),
three = one.querySelector("g"),
four = two.querySelector("g");
test.equal(three.namespaceURI, "http://www.w3.org/2000/svg");
test.equal(four.namespaceURI, "http://www.w3.org/2000/svg");
test.deepEqual(selection, {_groups: [[three, four]], _parents: [null]});
test.end();
});
tape("selection.append(name) observes a custom namespace, if any", function(test) {
try {
d3.namespaces.d3js = "https://d3js.org/2016/namespace";
var document = jsdom(""),
one = document.querySelector("#one"),
two = document.querySelector("#two"),
selection = d3.selectAll([one, two]).append("d3js"),
three = one.querySelector("d3js"),
four = two.querySelector("d3js");
test.equal(three.namespaceURI, "https://d3js.org/2016/namespace");
test.equal(four.namespaceURI, "https://d3js.org/2016/namespace");
test.deepEqual(selection, {_groups: [[three, four]], _parents: [null]});
test.end();
} finally {
delete d3.namespaces.d3js;
}
});
tape("selection.append(function) appends the returned element as the last child of each selected element", function(test) {
var document = jsdom("
"),
one = document.querySelector("#one"),
two = document.querySelector("#two"),
selection = d3.selectAll([one, two]).append(function() { return document.createElement("SPAN"); }),
three = one.querySelector("span:last-child"),
four = two.querySelector("span:last-child");
test.deepEqual(selection, {_groups: [[three, four]], _parents: [null]});
test.end();
});
tape("selection.append(function) passes the creator function data, index and group", function(test) {
var document = jsdom(""),
one = document.querySelector("#one"),
two = document.querySelector("#two"),
three = document.querySelector("#three"),
four = document.querySelector("#four"),
five = document.querySelector("#five"),
results = [];
d3.selectAll([one, two])
.datum(function(d, i) { return "parent-" + i; })
.selectAll("child")
.data(function(d, i) { return [0, 1].map(function(j) { return "child-" + i + "-" + j; }); })
.append(function(d, i, nodes) { results.push([this, d, i, nodes]); return document.createElement("SPAN"); });
test.deepEqual(results, [
[three, "child-0-0", 0, [three, four]],
[four, "child-0-1", 1, [three, four]],
[five, "child-1-0", 0, [five, ]]
]);
test.end();
});
tape("selection.append(…) propagates data if defined on the originating element", function(test) {
var document = jsdom("hello"),
parent = document.querySelector("parent");
parent.__data__ = 0; // still counts as data even though falsey
test.equal(d3.select(parent).append("child").datum(), 0);
test.end();
});
tape("selection.append(…) will not propagate data if not defined on the originating element", function(test) {
var document = jsdom("hello"),
parent = document.querySelector("parent"),
child = document.querySelector("child");
child.__data__ = 42;
d3.select(parent).append(function() { return child; });
test.equal(child.__data__, 42);
test.end();
});
tape("selection.append(…) propagates parents from the originating selection", function(test) {
var document = jsdom(""),
parents = d3.select(document).selectAll("parent"),
childs = parents.append("child");
test.deepEqual(parents, {_groups: [document.querySelectorAll("parent")], _parents: [document]});
test.deepEqual(childs, {_groups: [document.querySelectorAll("child")], _parents: [document]});
test.ok(parents._parents === childs._parents); // Not copied!
test.end();
});
tape("selection.append(…) can select elements when the originating selection is nested", function(test) {
var document = jsdom(""),
one = document.querySelector("#one"),
two = document.querySelector("#two"),
selection = d3.selectAll([one, two]).selectAll("child").append("span"),
three = one.querySelector("span"),
four = two.querySelector("span");
test.deepEqual(selection, {_groups: [[three], [four]], _parents: [one, two]});
test.end();
});
tape("selection.append(…) skips missing originating elements", function(test) {
var document = jsdom(""),
h1 = document.querySelector("h1"),
selection = d3.selectAll([, h1]).append("span"),
span = h1.querySelector("span");
test.deepEqual(selection, {_groups: [[, span]], _parents: [null]});
test.end();
});
d3-selection-1.1.0/test/selection/attr-test.js 0000664 0000000 0000000 00000013175 13106363305 0021242 0 ustar 00root root 0000000 0000000 var tape = require("tape"),
jsdom = require("../jsdom"),
d3 = require("../../");
tape("selection.attr(name) returns the value of the attribute with the specified name on the first selected element", function(test) {
var document = jsdom("
hello
");
test.equal(d3.select(document).select("h1").attr("class"), "c1 c2");
test.equal(d3.selectAll([null, document]).select("h1").attr("class"), "c1 c2");
test.end();
});
tape("selection.attr(name) coerces the specified name to a string", function(test) {
var document = jsdom("
hello
");
test.equal(d3.select(document).select("h1").attr({toString: function() { return "class"; }}), "c1 c2");
test.end();
});
tape("selection.attr(name) observes the namespace prefix, if any", function(test) {
var selection = d3.select({
getAttribute: function(name) { return name === "foo" ? "bar" : null; },
getAttributeNS: function(url, name) { return url === "http://www.w3.org/2000/svg" && name === "foo" ? "svg:bar" : null; }
});
test.equal(selection.attr("foo"), "bar");
test.equal(selection.attr("svg:foo"), "svg:bar");
test.end();
});
tape("selection.attr(name) observes a custom namespace prefix, if any", function(test) {
var selection = d3.select({
getAttributeNS: function(url, name) { return url === "https://d3js.org/2016/namespace" && name === "pie" ? "tasty" : null; }
});
try {
d3.namespaces.d3js = "https://d3js.org/2016/namespace";
test.equal(selection.attr("d3js:pie"), "tasty");
} finally {
delete d3.namespaces.d3js;
}
test.end();
});
tape("selection.attr(name, value) observes the namespace prefix, if any", function(test) {
var result, selection = d3.select({
setAttribute: function(name, value) { result = name === "foo" ? value : null; },
setAttributeNS: function(url, name, value) { result = url === "http://www.w3.org/2000/svg" && name === "foo" ? value : null; }
});
test.equal((result = undefined, selection.attr("foo", "bar"), result), "bar");
test.equal((result = undefined, selection.attr("svg:foo", "svg:bar"), result), "svg:bar");
test.equal((result = undefined, selection.attr("foo", function() { return "bar"; }), result), "bar");
test.equal((result = undefined, selection.attr("svg:foo", function() { return "svg:bar"; }), result), "svg:bar");
test.end();
});
tape("selection.attr(name, null) observes the namespace prefix, if any", function(test) {
var result, selection = d3.select({
removeAttribute: function(name) { result = name === "foo" ? "foo" : null; },
removeAttributeNS: function(url, name) { result = url === "http://www.w3.org/2000/svg" && name === "foo" ? "svg:foo" : null; }
});
test.equal((result = undefined, selection.attr("foo", null), result), "foo");
test.equal((result = undefined, selection.attr("svg:foo", null), result), "svg:foo");
test.equal((result = undefined, selection.attr("foo", function() { return null; }), result), "foo");
test.equal((result = undefined, selection.attr("svg:foo", function() { return null; }), result), "svg:foo");
test.end();
});
tape("selection.attr(name, value) sets the value of the attribute with the specified name on the selected elements", function(test) {
var document = jsdom("
hello
"),
one = document.querySelector("#one"),
two = document.querySelector("#two"),
selection = d3.selectAll([one, two]);
test.equal(selection.attr("foo", "bar"), selection);
test.equal(one.getAttribute("foo"), "bar");
test.equal(two.getAttribute("foo"), "bar");
test.end();
});
tape("selection.attr(name, null) removes the attribute with the specified name on the selected elements", function(test) {
var document = jsdom("
hello
"),
one = document.querySelector("#one"),
two = document.querySelector("#two"),
selection = d3.selectAll([one, two]);
test.equal(selection.attr("foo", null), selection);
test.equal(one.hasAttribute("foo"), false);
test.equal(two.hasAttribute("foo"), false);
test.end();
});
tape("selection.attr(name, function) sets the value of the attribute with the specified name on the selected elements", function(test) {
var document = jsdom("
hello
"),
one = document.querySelector("#one"),
two = document.querySelector("#two"),
selection = d3.selectAll([one, two]);
test.equal(selection.attr("foo", function(d, i) { return i ? "bar-" + i : null; }), selection);
test.equal(one.hasAttribute("foo"), false);
test.equal(two.getAttribute("foo"), "bar-1");
test.end();
});
tape("selection.attr(name, function) passes the value function data, index and group", function(test) {
var document = jsdom(""),
one = document.querySelector("#one"),
two = document.querySelector("#two"),
three = document.querySelector("#three"),
four = document.querySelector("#four"),
five = document.querySelector("#five"),
results = [];
d3.selectAll([one, two])
.datum(function(d, i) { return "parent-" + i; })
.selectAll("child")
.data(function(d, i) { return [0, 1].map(function(j) { return "child-" + i + "-" + j; }); })
.attr("foo", function(d, i, nodes) { results.push([this, d, i, nodes]); });
test.deepEqual(results, [
[three, "child-0-0", 0, [three, four]],
[four, "child-0-1", 1, [three, four]],
[five, "child-1-0", 0, [five, ]]
]);
test.end();
});
d3-selection-1.1.0/test/selection/call-test.js 0000664 0000000 0000000 00000001477 13106363305 0021205 0 ustar 00root root 0000000 0000000 var tape = require("tape"),
jsdom = require("../jsdom"),
d3 = require("../../");
tape("selection.call(function) calls the specified function, passing the selection", function(test) {
var result,
document = jsdom(),
selection = d3.select(document);
test.equal(selection.call(function(selection) { result = selection; }), selection);
test.equal(result, selection);
test.end();
});
tape("selection.call(function, arguments…) calls the specified function, passing the additional arguments", function(test) {
var result = [],
foo = {},
bar = {},
document = jsdom(),
selection = d3.select(document);
test.equal(selection.call(function(selection, a, b) { result.push(selection, a, b); }, foo, bar), selection);
test.deepEqual(result, [selection, foo, bar]);
test.end();
});
d3-selection-1.1.0/test/selection/classed-test.js 0000664 0000000 0000000 00000014077 13106363305 0021710 0 ustar 00root root 0000000 0000000 var tape = require("tape"),
jsdom = require("../jsdom"),
d3 = require("../../");
tape("selection.classed(classes) returns true if and only if the first element has the specified classes", function(test) {
var document = jsdom("
");
test.equal(d3.select(document).select("h1").classed({toString: function() { return "c1 c2"; }}), true);
test.end();
});
tape("selection.classed(classes) gets the class attribute if classList is not supported", function(test) {
var node = new Node("c1 c2");
test.equal(d3.select(node).classed(""), true);
test.equal(d3.select(node).classed("c1"), true);
test.equal(d3.select(node).classed("c2"), true);
test.equal(d3.select(node).classed("c3"), false);
test.equal(d3.select(node).classed("c1 c2"), true);
test.equal(d3.select(node).classed("c2 c1"), true);
test.equal(d3.select(node).classed("c1 c3"), false);
test.end();
});
tape("selection.classed(classes, value) sets whether the selected elements have the specified classes", function(test) {
var document = jsdom(""),
selection = d3.select(document.body);
test.equal(selection.classed("c1"), false);
test.equal(selection.attr("class"), null);
test.equal(selection.classed("c1", true), selection);
test.equal(selection.classed("c1"), true);
test.equal(selection.attr("class"), "c1");
test.equal(selection.classed("c1 c2", true), selection);
test.equal(selection.classed("c1"), true);
test.equal(selection.classed("c2"), true);
test.equal(selection.classed("c1 c2"), true);
test.equal(selection.attr("class"), "c1 c2");
test.equal(selection.classed("c1", false), selection);
test.equal(selection.classed("c1"), false);
test.equal(selection.classed("c2"), true);
test.equal(selection.classed("c1 c2"), false);
test.equal(selection.attr("class"), "c2");
test.equal(selection.classed("c1 c2", false), selection);
test.equal(selection.classed("c1"), false);
test.equal(selection.classed("c2"), false);
test.equal(selection.attr("class"), "");
test.end();
});
tape("selection.classed(classes, function) sets whether the selected elements have the specified classes", function(test) {
var document = jsdom(""),
selection = d3.select(document.body);
test.equal(selection.classed("c1 c2", function() { return true; }), selection);
test.equal(selection.attr("class"), "c1 c2");
test.equal(selection.classed("c1 c2", function() { return false; }), selection);
test.equal(selection.attr("class"), "");
test.end();
});
tape("selection.classed(classes, function) passes the value function data, index and group", function(test) {
var document = jsdom(""),
one = document.querySelector("#one"),
two = document.querySelector("#two"),
three = document.querySelector("#three"),
four = document.querySelector("#four"),
five = document.querySelector("#five"),
results = [];
d3.selectAll([one, two])
.datum(function(d, i) { return "parent-" + i; })
.selectAll("child")
.data(function(d, i) { return [0, 1].map(function(j) { return "child-" + i + "-" + j; }); })
.classed("c1 c2", function(d, i, nodes) { results.push([this, d, i, nodes]); });
test.deepEqual(results, [
[three, "child-0-0", 0, [three, four]],
[four, "child-0-1", 1, [three, four]],
[five, "child-1-0", 0, [five, ]]
]);
test.end();
});
tape("selection.classed(classes, value) sets the class attribute if classList is not supported", function(test) {
var node = new Node(null),
selection = d3.select(node);
test.equal(selection.classed("c1"), false);
test.equal(selection.attr("class"), null);
test.equal(selection.classed("c1", true), selection);
test.equal(selection.classed("c1"), true);
test.equal(selection.attr("class"), "c1");
test.equal(selection.classed("c1 c2", true), selection);
test.equal(selection.classed("c1"), true);
test.equal(selection.classed("c2"), true);
test.equal(selection.classed("c1 c2"), true);
test.equal(selection.attr("class"), "c1 c2");
test.equal(selection.classed("c1", false), selection);
test.equal(selection.classed("c1"), false);
test.equal(selection.classed("c2"), true);
test.equal(selection.classed("c1 c2"), false);
test.equal(selection.attr("class"), "c2");
test.equal(selection.classed("c1 c2", false), selection);
test.equal(selection.classed("c1"), false);
test.equal(selection.classed("c2"), false);
test.equal(selection.attr("class"), "");
test.end();
});
tape("selection.classed(classes, value) coerces the specified classes to a string", function(test) {
var document = jsdom("
hello
"),
selection = d3.select(document).select("h1");
test.equal(selection.classed("c1 c2"), false);
test.equal(selection.classed({toString: function() { return "c1 c2"; }}, true), selection);
test.equal(selection.classed("c1 c2"), true);
test.end();
});
function Node(classes) {
this._classes = classes;
}
Node.prototype = {
getAttribute: function(name) { return name === "class" ? this._classes : null; },
setAttribute: function(name, value) { if (name === "class") this._classes = value; }
};
d3-selection-1.1.0/test/selection/data-test.js 0000664 0000000 0000000 00000026326 13106363305 0021203 0 ustar 00root root 0000000 0000000 var tape = require("tape"),
jsdom = require("../jsdom"),
d3 = require("../../");
tape("selection.data(values) binds the specified values to the selected elements by index", function(test) {
var body = jsdom("").body,
one = body.querySelector("#one"),
two = body.querySelector("#two"),
three = body.querySelector("#three"),
selection = d3.select(body).selectAll("div").data(["foo", "bar", "baz"]);
test.equal(one.__data__, "foo");
test.equal(two.__data__, "bar");
test.equal(three.__data__, "baz");
test.deepEqual(selection, {
_groups: [[one, two, three]],
_parents: [body],
_enter: [[,, ]],
_exit: [[,, ]]
});
test.end();
});
tape("selection.data(values) puts unbound data in the enter selection", function(test) {
var body = jsdom("").body,
one = body.querySelector("#one"),
two = body.querySelector("#two"),
selection = d3.select(body).selectAll("div").data(["foo", "bar", "baz"]);
test.equal(one.__data__, "foo");
test.equal(two.__data__, "bar");
test.deepEqual(selection, {
_groups: [[one, two, ]],
_parents: [body],
_enter: [[,, {
__data__: "baz",
_next: null,
_parent: body,
namespaceURI: "http://www.w3.org/1999/xhtml",
ownerDocument: body.ownerDocument
}]],
_exit: [[,, ]]
});
test.end();
});
tape("selection.data(values) puts unbound elements in the exit selection", function(test) {
var body = jsdom("").body,
one = body.querySelector("#one"),
two = body.querySelector("#two"),
three = body.querySelector("#three"),
selection = d3.select(body).selectAll("div").data(["foo", "bar"]);
test.equal(one.__data__, "foo");
test.equal(two.__data__, "bar");
test.deepEqual(selection, {
_groups: [[one, two, ]],
_parents: [body],
_enter: [[,,, ]],
_exit: [[,, three]]
});
test.end();
});
tape("selection.data(values) binds the specified values to each group independently", function(test) {
var body = jsdom("
").body,
zero = body.querySelector("#zero"),
one = body.querySelector("#one"),
two = body.querySelector("#two"),
three = body.querySelector("#three"),
four = body.querySelector("#four"),
five = body.querySelector("#five"),
selection = d3.select(body).selectAll("div").selectAll("span").data(["foo", "bar"]);
test.equal(one.__data__, "foo");
test.equal(two.__data__, "bar");
test.equal(four.__data__, "foo");
test.equal(five.__data__, "bar");
test.deepEqual(selection, {
_groups: [[one, two], [four, five]],
_parents: [zero, three],
_enter: [[, ], [, ]],
_exit: [[, ], [, ]]
});
test.end();
});
tape("selection.data(function) binds the specified return values to the selected elements by index", function(test) {
var body = jsdom("").body,
one = body.querySelector("#one"),
two = body.querySelector("#two"),
three = body.querySelector("#three"),
selection = d3.select(body).selectAll("div").data(function() { return ["foo", "bar", "baz"]; });
test.equal(one.__data__, "foo");
test.equal(two.__data__, "bar");
test.equal(three.__data__, "baz");
test.deepEqual(selection, {
_groups: [[one, two, three]],
_parents: [body],
_enter: [[,, ]],
_exit: [[,, ]]
});
test.end();
});
tape("selection.data(function) passes the values function datum, index and parents", function(test) {
var document = jsdom(""),
one = document.querySelector("#one"),
two = document.querySelector("#two"),
results = [];
d3.selectAll([one, two])
.datum(function(d, i) { return "parent-" + i; })
.selectAll("child")
.data(function(d, i, nodes) { results.push([this, d, i, nodes]); return ["foo", "bar"]; });
test.deepEqual(results, [
[one, "parent-0", 0, [one, two]],
[two, "parent-1", 1, [one, two]]
]);
test.end();
});
tape("selection.data(values, function) joins data to element using the computed keys", function(test) {
var body = jsdom("").body,
one = body.querySelector("#one"),
two = body.querySelector("#two"),
three = body.querySelector("#three"),
selection = d3.select(body).selectAll("node").data(["one", "four", "three"], function(d) { return d || this.id; });
test.deepEqual(selection, {
_groups: [[one,, three]],
_parents: [body],
_enter: [[, {
__data__: "four",
_next: three,
_parent: body,
namespaceURI: "http://www.w3.org/1999/xhtml",
ownerDocument: body.ownerDocument
}, ]],
_exit: [[, two, ]]
});
test.end();
});
tape("selection.data(values, function) puts elements with duplicate keys into update or exit", function(test) {
var body = jsdom("").body,
one = body.querySelector("#one"),
two = body.querySelector("#two"),
three = body.querySelector("#three"),
selection = d3.select(body).selectAll("node").data(["foo"], function(d) { return d || this.getAttribute("name"); });
test.deepEqual(selection, {
_groups: [[one]],
_parents: [body],
_enter: [[,]],
_exit: [[, two, three]]
});
test.end();
});
tape("selection.data(values, function) puts elements with duplicate keys into exit", function(test) {
var body = jsdom("").body,
one = body.querySelector("#one"),
two = body.querySelector("#two"),
three = body.querySelector("#three"),
selection = d3.select(body).selectAll("node").data(["bar"], function(d) { return d || this.getAttribute("name"); });
test.deepEqual(selection, {
_groups: [[three]],
_parents: [body],
_enter: [[,]],
_exit: [[one, two,]]
});
test.end();
});
tape("selection.data(values, function) puts data with duplicate keys into update and enter", function(test) {
var body = jsdom("").body,
one = body.querySelector("#one"),
two = body.querySelector("#two"),
three = body.querySelector("#three"),
selection = d3.select(body).selectAll("node").data(["one", "one", "two"], function(d) { return d || this.id; });
test.deepEqual(selection, {
_groups: [[one,, two]],
_parents: [body],
_enter: [[, {
__data__: "one",
_next: two,
_parent: body,
namespaceURI: "http://www.w3.org/1999/xhtml",
ownerDocument: body.ownerDocument
},, ]],
_exit: [[,, three]]
});
test.end();
});
tape("selection.data(values, function) puts data with duplicate keys into enter", function(test) {
var body = jsdom("").body,
one = body.querySelector("#one"),
two = body.querySelector("#two"),
three = body.querySelector("#three"),
selection = d3.select(body).selectAll("node").data(["foo", "foo", "two"], function(d) { return d || this.id; });
test.deepEqual(selection, {
_groups: [[,, two]],
_parents: [body],
_enter: [[{
__data__: "foo",
_next: two,
_parent: body,
namespaceURI: "http://www.w3.org/1999/xhtml",
ownerDocument: body.ownerDocument
}, {
__data__: "foo",
_next: two,
_parent: body,
namespaceURI: "http://www.w3.org/1999/xhtml",
ownerDocument: body.ownerDocument
}, ]],
_exit: [[one,, three]]
});
test.end();
});
tape("selection.data(values, function) passes the key function datum, index and nodes or data", function(test) {
var body = jsdom("").body,
one = body.querySelector("#one"),
two = body.querySelector("#two"),
results = [];
d3.select(one)
.datum("foo");
d3.select(body).selectAll("node")
.data(["foo", "bar"], function(d, i, nodes) { results.push([this, d, i, nodes]); return d || this.id; });
test.deepEqual(results, [
[one, "foo", 0, [one, two]],
[two, undefined, 1, [one, two]],
[body, "foo", 0, ["foo", "bar"]],
[body, "bar", 1, ["foo", "bar"]]
]);
test.end();
});
tape("selection.data(values, function) applies the order of the data", function(test) {
var body = jsdom("").body,
one = body.querySelector("#one"),
two = body.querySelector("#two"),
three = body.querySelector("#three"),
selection = d3.select(body).selectAll("div").data(["four", "three", "one", "five", "two"], function(d) { return d || this.id; });
test.deepEqual(selection, {
_groups: [[, three, one,, two]],
_parents: [body],
_enter: [[{
__data__: "four",
_next: three,
_parent: body,
namespaceURI: "http://www.w3.org/1999/xhtml",
ownerDocument: body.ownerDocument
},,, {
__data__: "five",
_next: two,
_parent: body,
namespaceURI: "http://www.w3.org/1999/xhtml",
ownerDocument: body.ownerDocument
}, ]],
_exit: [[,,,]]
});
test.end();
});
tape("selection.data(values) returns a new selection, and does not modify the original selection", function(test) {
var document = jsdom(""),
root = document.documentElement,
one = document.querySelector("#one"),
two = document.querySelector("#two"),
selection0 = d3.select(root).selectAll("h1"),
selection1 = selection0.data([1, 2, 3]),
selection2 = selection1.data([1]);
test.deepEqual(selection0, {
_groups: [[one, two]],
_parents: [root]
});
test.deepEqual(selection1, {
_groups: [[one, two, ]],
_parents: [root],
_enter: [[,, {__data__: 3, _next: null, _parent: root, namespaceURI: "http://www.w3.org/1999/xhtml", ownerDocument: document}]],
_exit: [[,]]
});
test.deepEqual(selection2, {
_groups: [[one]],
_parents: [root],
_enter: [[,]],
_exit: [[, two]]
});
test.end();
});
tape("selection.data(values, key) does not modify the groups array in-place", function(test) {
var document = jsdom(""),
root = document.documentElement,
one = document.querySelector("#one"),
two = document.querySelector("#two"),
key = function(d, i) { return i; },
selection0 = d3.select(root).selectAll("h1"),
selection1 = selection0.data([1, 2, 3], key),
selection2 = selection1.data([1], key);
test.deepEqual(selection0, {
_groups: [[one, two]],
_parents: [root]
});
test.deepEqual(selection1, {
_groups: [[one, two, ]],
_parents: [root],
_enter: [[,, {__data__: 3, _next: null, _parent: root, namespaceURI: "http://www.w3.org/1999/xhtml", ownerDocument: document}]],
_exit: [[,]]
});
test.deepEqual(selection2, {
_groups: [[one]],
_parents: [root],
_enter: [[,]],
_exit: [[, two]]
});
test.end();
});
d3-selection-1.1.0/test/selection/datum-test.js 0000664 0000000 0000000 00000004466 13106363305 0021405 0 ustar 00root root 0000000 0000000 var tape = require("tape"),
jsdom = require("../jsdom"),
d3 = require("../../");
tape("selection.datum() returns the datum on the first selected element", function(test) {
var node = {__data__: "hello"};
test.equal(d3.select(node).datum(), "hello");
test.equal(d3.selectAll([null, node]).datum(), "hello");
test.end();
});
tape("selection.datum(value) sets datum on the selected elements", function(test) {
var one = {__data__: ""},
two = {__data__: ""},
selection = d3.selectAll([one, two]);
test.equal(selection.datum("bar"), selection);
test.equal(one.__data__, "bar");
test.equal(two.__data__, "bar");
test.end();
});
tape("selection.datum(null) clears the datum on the selected elements", function(test) {
var one = {__data__: "bar"},
two = {__data__: "bar"},
selection = d3.selectAll([one, two]);
test.equal(selection.datum(null), selection);
test.equal("__data__" in one, false);
test.equal("__data__" in two, false);
test.end();
});
tape("selection.datum(function) sets the value of the datum on the selected elements", function(test) {
var one = {__data__: "bar"},
two = {__data__: "bar"},
selection = d3.selectAll([one, two]);
test.equal(selection.datum(function(d, i) { return i ? "baz" : null; }), selection);
test.equal("__data__" in one, false);
test.equal(two.__data__, "baz");
test.end();
});
tape("selection.datum(function) passes the value function data, index and group", function(test) {
var document = jsdom(""),
one = document.querySelector("#one"),
two = document.querySelector("#two"),
three = document.querySelector("#three"),
four = document.querySelector("#four"),
five = document.querySelector("#five"),
results = [];
d3.selectAll([one, two])
.datum(function(d, i) { return "parent-" + i; })
.selectAll("child")
.data(function(d, i) { return [0, 1].map(function(j) { return "child-" + i + "-" + j; }); })
.datum(function(d, i, nodes) { results.push([this, d, i, nodes]); });
test.deepEqual(results, [
[three, "child-0-0", 0, [three, four]],
[four, "child-0-1", 1, [three, four]],
[five, "child-1-0", 0, [five, ]]
]);
test.end();
});
d3-selection-1.1.0/test/selection/dispatch-test.js 0000664 0000000 0000000 00000006603 13106363305 0022065 0 ustar 00root root 0000000 0000000 var tape = require("tape"),
jsdom = require("../jsdom"),
d3 = require("../../");
tape("selection.dispatch(type) dispatches a custom event of the specified type to each selected element in order", function(test) {
var result = [],
event,
document = jsdom(""),
one = document.querySelector("#one"),
two = document.querySelector("#two"),
selection = d3.selectAll([one, two]).datum(function(d, i) { return "node-" + i; }).on("bang", function(d, i, nodes) { event = d3.event; result.push(this, d, i, nodes); });
test.equal(selection.dispatch("bang"), selection);
test.deepEqual(result, [one, "node-0", 0, [one, two], two, "node-1", 1, [one, two]]);
test.equal(event.type, "bang");
test.equal(event.bubbles, false);
test.equal(event.cancelable, false);
test.equal(event.detail, null);
test.end();
});
tape("selection.dispatch(type, params) dispatches a custom event with the specified constant parameters", function(test) {
var result = [],
event,
document = jsdom(""),
one = document.querySelector("#one"),
two = document.querySelector("#two"),
selection = d3.selectAll([one, two]).datum(function(d, i) { return "node-" + i; }).on("bang", function(d, i, nodes) { event = d3.event; result.push(this, d, i, nodes); });
test.equal(selection.dispatch("bang", {bubbles: true, cancelable: true, detail: "loud"}), selection);
test.deepEqual(result, [one, "node-0", 0, [one, two], two, "node-1", 1, [one, two]]);
test.equal(event.type, "bang");
test.equal(event.bubbles, true);
test.equal(event.cancelable, true);
test.equal(event.detail, "loud");
test.end();
});
tape("selection.dispatch(type, function) dispatches a custom event with the specified parameter function", function(test) {
var result = [],
events = [],
document = jsdom(""),
one = document.querySelector("#one"),
two = document.querySelector("#two"),
selection = d3.selectAll([one, two]).datum(function(d, i) { return "node-" + i; }).on("bang", function(d, i, nodes) { events.push(d3.event); result.push(this, d, i, nodes); });
test.equal(selection.dispatch("bang", function(d, i) { return {bubbles: true, cancelable: true, detail: "loud-" + i}; }), selection);
test.deepEqual(result, [one, "node-0", 0, [one, two], two, "node-1", 1, [one, two]]);
test.equal(events[0].type, "bang");
test.equal(events[0].bubbles, true);
test.equal(events[0].cancelable, true);
test.equal(events[0].detail, "loud-0");
test.equal(events[1].type, "bang");
test.equal(events[1].bubbles, true);
test.equal(events[1].cancelable, true);
test.equal(events[1].detail, "loud-1");
test.end();
});
tape("selection.dispatch(type) skips missing elements", function(test) {
var result = [],
event,
document = jsdom(""),
one = document.querySelector("#one"),
two = document.querySelector("#two"),
selection = d3.selectAll([, one,, two]).datum(function(d, i) { return "node-" + i; }).on("bang", function(d, i, nodes) { event = d3.event; result.push(this, d, i, nodes); });
test.equal(selection.dispatch("bang"), selection);
test.deepEqual(result, [one, "node-1", 1, [, one,, two], two, "node-3", 3, [, one,, two]]);
test.equal(event.type, "bang");
test.equal(event.detail, null);
test.end();
});
d3-selection-1.1.0/test/selection/each-test.js 0000664 0000000 0000000 00000002305 13106363305 0021161 0 ustar 00root root 0000000 0000000 var tape = require("tape"),
jsdom = require("../jsdom"),
d3 = require("../../");
tape("selection.each(function) calls the specified function for each selected element in order", function(test) {
var result = [],
document = jsdom(""),
one = document.querySelector("#one"),
two = document.querySelector("#two"),
selection = d3.selectAll([one, two]).datum(function(d, i) { return "node-" + i; });
test.equal(selection.each(function(d, i, nodes) { result.push(this, d, i, nodes); }), selection);
test.deepEqual(result, [one, "node-0", 0, [one, two], two, "node-1", 1, [one, two]]);
test.end();
});
tape("selection.each(function) skips missing elements", function(test) {
var result = [],
document = jsdom(""),
one = document.querySelector("#one"),
two = document.querySelector("#two"),
selection = d3.selectAll([, one,, two]).datum(function(d, i) { return "node-" + i; });
test.equal(selection.each(function(d, i, nodes) { result.push(this, d, i, nodes); }), selection);
test.deepEqual(result, [one, "node-1", 1, [, one,, two], two, "node-3", 3, [, one,, two]]);
test.end();
});
d3-selection-1.1.0/test/selection/empty-test.js 0000664 0000000 0000000 00000001142 13106363305 0021415 0 ustar 00root root 0000000 0000000 var tape = require("tape"),
jsdom = require("../jsdom"),
d3 = require("../../");
tape("selection.empty() return false if the selection is not empty", function(test) {
var document = jsdom("");
test.equal(d3.select(document).empty(), false);
test.end();
});
tape("selection.empty() return true if the selection is empty", function(test) {
var document = jsdom("");
test.equal(d3.select(null).empty(), true);
test.equal(d3.selectAll([]).empty(), true);
test.equal(d3.selectAll([,]).empty(), true);
test.end();
});
d3-selection-1.1.0/test/selection/enter-test.js 0000664 0000000 0000000 00000011545 13106363305 0021404 0 ustar 00root root 0000000 0000000 var tape = require("tape"),
jsdom = require("../jsdom"),
d3 = require("../../");
tape("selection.enter() returns an empty selection before a data-join", function(test) {
var body = jsdom("
hello
").body,
selection = d3.select(body);
test.deepEqual(selection.enter(), {_groups: [[]], _parents: [null]});
test.end();
});
tape("selection.enter() contains EnterNodes", function(test) {
var body = jsdom().body,
selection = d3.select(body).selectAll("div").data([1, 2, 3]);
test.equal(selection.enter().node().constructor.name, "EnterNode");
test.end();
});
tape("selection.enter() shares the update selection’s parents", function(test) {
var body = jsdom("
hello
").body,
selection = d3.select(body);
test.equal(selection.enter()._parents, selection._parents);
test.end();
});
tape("selection.enter() returns the same selection each time", function(test) {
var body = jsdom("
hello
").body,
selection = d3.select(body);
test.deepEqual(selection.enter(), selection.enter());
test.end();
});
tape("selection.enter() contains unbound data after a data-join", function(test) {
var body = jsdom("").body,
one = body.querySelector("#one"),
two = body.querySelector("#two"),
selection = d3.select(body).selectAll("div").data(["foo", "bar", "baz"]);
test.deepEqual(selection.enter(), {
_groups: [[,, {
__data__: "baz",
_next: null,
_parent: body,
namespaceURI: "http://www.w3.org/1999/xhtml",
ownerDocument: body.ownerDocument
}]],
_parents: [body]
});
test.end();
});
tape("selection.enter() uses the order of the data", function(test) {
var body = jsdom("").body,
one = body.querySelector("#one"),
two = body.querySelector("#two"),
three = body.querySelector("#three"),
selection = d3.select(body).selectAll("div").data(["one", "four", "three", "five"], function(d) { return d || this.id; });
test.deepEqual(selection.enter(), {
_groups: [[, {
__data__: "four",
_next: three,
_parent: body,
namespaceURI: "http://www.w3.org/1999/xhtml",
ownerDocument: body.ownerDocument
},, {
__data__: "five",
_next: null,
_parent: body,
namespaceURI: "http://www.w3.org/1999/xhtml",
ownerDocument: body.ownerDocument
}]],
_parents: [body]
});
test.end();
});
tape("enter.append(…) inherits the namespaceURI from the parent", function(test) {
var body = d3.select(jsdom().body),
svg = body.append("svg"),
g = svg.selectAll("g").data(["foo"]).enter().append("g");
test.equal(body.node().namespaceURI, "http://www.w3.org/1999/xhtml");
test.equal(svg.node().namespaceURI, "http://www.w3.org/2000/svg");
test.equal(g.node().namespaceURI, "http://www.w3.org/2000/svg");
test.end();
});
tape("enter.append(…) does not override an explicit namespace", function(test) {
var body = d3.select(jsdom().body),
svg = body.append("svg"),
g = svg.selectAll("g").data(["foo"]).enter().append("xhtml:g");
test.equal(body.node().namespaceURI, "http://www.w3.org/1999/xhtml");
test.equal(svg.node().namespaceURI, "http://www.w3.org/2000/svg");
test.equal(g.node().namespaceURI, "http://www.w3.org/1999/xhtml");
test.end();
});
tape("enter.append(…) inserts entering nodes before the next node in the update selection", function(test) {
var document = jsdom(),
identity = function(d) { return d; },
p = d3.select(document.body).selectAll("p");
p = p.data([1, 3], identity);
p = p.enter().append("p").text(identity).merge(p);
p = p.data([0, 1, 2, 3, 4], identity);
p = p.enter().append("p").text(identity).merge(p);
test.equal(document.body.innerHTML, "
0
1
2
3
4
");
test.end();
});
tape("enter.insert(…, before) inserts entering nodes before the sibling matching the specified selector", function(test) {
var document = jsdom(""),
identity = function(d) { return d; },
p = d3.select(document.body).selectAll("p");
p = p.data([1, 3], identity);
p = p.enter().insert("p", "hr").text(identity).merge(p);
p = p.data([0, 1, 2, 3, 4], identity);
p = p.enter().insert("p", "hr").text(identity).merge(p);
test.equal(document.body.innerHTML, "
1
3
0
2
4
");
test.end();
});
tape("enter.insert(…, null) inserts entering nodes after the last child", function(test) {
var document = jsdom(),
identity = function(d) { return d; },
p = d3.select(document.body).selectAll("p");
p = p.data([1, 3], identity);
p = p.enter().insert("p", null).text(identity).merge(p);
p = p.data([0, 1, 2, 3, 4], identity);
p = p.enter().insert("p", null).text(identity).merge(p);
test.equal(document.body.innerHTML, "
1
3
0
2
4
");
test.end();
});
d3-selection-1.1.0/test/selection/exit-test.js 0000664 0000000 0000000 00000003322 13106363305 0021232 0 ustar 00root root 0000000 0000000 var tape = require("tape"),
jsdom = require("../jsdom"),
d3 = require("../../");
tape("selection.exit() returns an empty selection before a data-join", function(test) {
var body = jsdom("
hello
").body,
selection = d3.select(body);
test.deepEqual(selection.exit(), {_groups: [[]], _parents: [null]});
test.end();
});
tape("selection.exit() shares the update selection’s parents", function(test) {
var body = jsdom("
hello
").body,
selection = d3.select(body);
test.equal(selection.exit()._parents, selection._parents);
test.end();
});
tape("selection.exit() returns the same selection each time", function(test) {
var body = jsdom("
hello
").body,
selection = d3.select(body);
test.deepEqual(selection.exit(), selection.exit());
test.end();
});
tape("selection.exit() contains unbound elements after a data-join", function(test) {
var body = jsdom("").body,
one = body.querySelector("#one"),
two = body.querySelector("#two"),
selection = d3.select(body).selectAll("div").data(["foo"]);
test.deepEqual(selection.exit(), {
_groups: [[, two]],
_parents: [body]
});
test.end();
});
tape("selection.exit() uses the order of the originating selection", function(test) {
var body = jsdom("").body,
one = body.querySelector("#one"),
two = body.querySelector("#two"),
three = body.querySelector("#three"),
selection = d3.select(body).selectAll("div").data(["three", "one"], function(d) { return d || this.id; });
test.deepEqual(selection.exit(), {
_groups: [[, two, ]],
_parents: [body]
});
test.end();
});
d3-selection-1.1.0/test/selection/filter-test.js 0000664 0000000 0000000 00000011133 13106363305 0021545 0 ustar 00root root 0000000 0000000 var tape = require("tape"),
jsdom = require("../jsdom"),
d3 = require("../../");
tape("selection.filter(…) returns a selection", function(test) {
var document = jsdom("
hello
");
test.ok(d3.select(document.body).filter("body") instanceof d3.selection);
test.end();
});
tape("selection.filter(string) retains the selected elements that matches the selector string", function(test) {
var document = jsdom("
"),
one = document.querySelector("#one"),
three = document.querySelector("#three");
test.deepEqual(d3.select(document).selectAll("span").filter("#one,#three"), {_groups: [[one, three]], _parents: [document]});
test.end();
});
tape("selection.filter(function) retains elements for which the given function returns true", function(test) {
var document = jsdom("
"),
one = document.querySelector("#one"),
two = document.querySelector("#two"),
three = document.querySelector("#three"),
four = document.querySelector("#four");
test.deepEqual(d3.selectAll([one, two, three, four]).filter(function(d, i) { return i & 1; }), {_groups: [[two, four]], _parents: [null]});
test.end();
});
tape("selection.filter(function) passes the selector function data, index and group", function(test) {
var document = jsdom(""),
one = document.querySelector("#one"),
two = document.querySelector("#two"),
three = document.querySelector("#three"),
four = document.querySelector("#four"),
five = document.querySelector("#five"),
results = [];
d3.selectAll([one, two])
.datum(function(d, i) { return "parent-" + i; })
.selectAll("child")
.data(function(d, i) { return [0, 1].map(function(j) { return "child-" + i + "-" + j; }); })
.filter(function(d, i, nodes) { results.push([this, d, i, nodes]); });
test.deepEqual(results, [
[three, "child-0-0", 0, [three, four]],
[four, "child-0-1", 1, [three, four]],
[five, "child-1-0", 0, [five, ]]
]);
test.end();
});
tape("selection.filter(…) propagates parents from the originating selection", function(test) {
var document = jsdom("12"),
parents = d3.select(document).selectAll("parent"),
parents2 = parents.filter(function() { return true; });
test.deepEqual(parents, {_groups: [document.querySelectorAll("parent")], _parents: [document]});
test.deepEqual(parents2, {_groups: [document.querySelectorAll("parent")], _parents: [document]});
test.ok(parents._parents === parents2._parents); // Not copied!
test.end();
});
tape("selection.filter(…) can filter elements when the originating selection is nested", function(test) {
var document = jsdom(""),
one = document.querySelector("#one"),
two = document.querySelector("#two"),
three = document.querySelector("#three"),
four = document.querySelector("#four");
test.deepEqual(d3.selectAll([one, two]).selectAll("span").filter("*"), {_groups: [[three], [four]], _parents: [one, two]});
test.end();
});
tape("selection.filter(…) skips missing originating elements and does not retain the original indexes", function(test) {
var document = jsdom("
hello
"),
h1 = document.querySelector("h1");
test.deepEqual(d3.selectAll([, h1]).filter("*"), {_groups: [[h1]], _parents: [null]});
test.deepEqual(d3.selectAll([null, h1]).filter("*"), {_groups: [[h1]], _parents: [null]});
test.deepEqual(d3.selectAll([undefined, h1]).filter("*"), {_groups: [[h1]], _parents: [null]});
test.end();
});
tape("selection.filter(…) skips missing originating elements when the originating selection is nested", function(test) {
var document = jsdom(""),
one = document.querySelector("#one"),
two = document.querySelector("#two"),
three = document.querySelector("#three"),
four = document.querySelector("#four");
test.deepEqual(d3.selectAll([one, two]).selectAll("child").select(function(d, i) { return i & 1 ? this : null; }).filter("*"), {_groups: [[three], [four]], _parents: [one, two]});
test.end();
});
d3-selection-1.1.0/test/selection/html-test.js 0000664 0000000 0000000 00000004464 13106363305 0021235 0 ustar 00root root 0000000 0000000 var tape = require("tape"),
jsdom = require("../jsdom"),
d3 = require("../../");
tape("selection.html() returns the inner HTML on the first selected element", function(test) {
var node = {innerHTML: "hello"};
test.equal(d3.select(node).html(), "hello");
test.equal(d3.selectAll([null, node]).html(), "hello");
test.end();
});
tape("selection.html(value) sets inner HTML on the selected elements", function(test) {
var one = {innerHTML: ""},
two = {innerHTML: ""},
selection = d3.selectAll([one, two]);
test.equal(selection.html("bar"), selection);
test.equal(one.innerHTML, "bar");
test.equal(two.innerHTML, "bar");
test.end();
});
tape("selection.html(null) clears the inner HTML on the selected elements", function(test) {
var one = {innerHTML: "bar"},
two = {innerHTML: "bar"},
selection = d3.selectAll([one, two]);
test.equal(selection.html(null), selection);
test.equal(one.innerHTML, "");
test.equal(two.innerHTML, "");
test.end();
});
tape("selection.html(function) sets the value of the inner HTML on the selected elements", function(test) {
var one = {innerHTML: "bar"},
two = {innerHTML: "bar"},
selection = d3.selectAll([one, two]);
test.equal(selection.html(function(d, i) { return i ? "baz" : null; }), selection);
test.equal(one.innerHTML, "");
test.equal(two.innerHTML, "baz");
test.end();
});
tape("selection.html(function) passes the value function data, index and group", function(test) {
var document = jsdom(""),
one = document.querySelector("#one"),
two = document.querySelector("#two"),
three = document.querySelector("#three"),
four = document.querySelector("#four"),
five = document.querySelector("#five"),
results = [];
d3.selectAll([one, two])
.datum(function(d, i) { return "parent-" + i; })
.selectAll("child")
.data(function(d, i) { return [0, 1].map(function(j) { return "child-" + i + "-" + j; }); })
.html(function(d, i, nodes) { results.push([this, d, i, nodes]); });
test.deepEqual(results, [
[three, "child-0-0", 0, [three, four]],
[four, "child-0-1", 1, [three, four]],
[five, "child-1-0", 0, [five, ]]
]);
test.end();
});
d3-selection-1.1.0/test/selection/index-test.js 0000664 0000000 0000000 00000002302 13106363305 0021365 0 ustar 00root root 0000000 0000000 var tape = require("tape"),
jsdom = require("../jsdom"),
d3 = require("../../");
tape("d3.selection() returns a selection of the document element", function(test) {
var document = global.document = jsdom();
try {
test.equal(d3.selection().node(), document.documentElement);
test.end();
} finally {
delete global.document;
}
});
tape("d3.selection.prototype can be extended", function(test) {
var document = jsdom(""),
s = d3.select(document.querySelector("[type=checkbox]"));
try {
d3.selection.prototype.checked = function(value) {
return arguments.length
? this.property("checked", !!value)
: this.property("checked");
};
test.equal(s.checked(), false);
test.equal(s.checked(true), s);
test.equal(s.checked(), true);
test.end();
} finally {
delete d3.selection.prototype.checked;
}
});
tape("d3.selection() returns an instanceof d3.selection", function(test) {
var document = global.document = jsdom();
try {
test.ok(d3.selection() instanceof d3.selection);
test.equal(d3.selection().constructor.name, "Selection");
test.end();
} finally {
delete global.document;
}
});
d3-selection-1.1.0/test/selection/insert-test.js 0000664 0000000 0000000 00000006022 13106363305 0021565 0 ustar 00root root 0000000 0000000 var tape = require("tape"),
jsdom = require("../jsdom"),
d3 = require("../../");
tape("selection.insert(name, before) inserts a new element of the specified name before the specified child of each selected element", function(test) {
var document = jsdom("
"),
one = document.querySelector("#one"),
two = document.querySelector("#two"),
selection = d3.selectAll([one, two]).insert("span", ".before"),
three = one.querySelector("span:first-child"),
four = two.querySelector("span:first-child");
test.deepEqual(selection, {_groups: [[three, four]], _parents: [null]});
test.end();
});
tape("selection.insert(function, function) inserts the returned element before the specified child of each selected element", function(test) {
var document = jsdom("
"),
one = document.querySelector("#one"),
two = document.querySelector("#two"),
selection = d3.selectAll([one, two]).insert(function() { return document.createElement("SPAN"); }, function() { return this.firstChild; }),
three = one.querySelector("span:first-child"),
four = two.querySelector("span:first-child");
test.deepEqual(selection, {_groups: [[three, four]], _parents: [null]});
test.end();
});
tape("selection.insert(function, function) inserts the returned element as the last child if the selector function returns null", function(test) {
var document = jsdom("
"),
one = document.querySelector("#one"),
two = document.querySelector("#two"),
selection = d3.selectAll([one, two]).insert(function() { return document.createElement("SPAN"); }, function() { return; }),
three = one.querySelector("span:last-child"),
four = two.querySelector("span:last-child");
test.deepEqual(selection, {_groups: [[three, four]], _parents: [null]});
test.end();
});
tape("selection.insert(name, function) passes the selector function data, index and group", function(test) {
var document = jsdom(""),
one = document.querySelector("#one"),
two = document.querySelector("#two"),
three = document.querySelector("#three"),
four = document.querySelector("#four"),
five = document.querySelector("#five"),
results = [];
d3.selectAll([one, two])
.datum(function(d, i) { return "parent-" + i; })
.selectAll("child")
.data(function(d, i) { return [0, 1].map(function(j) { return "child-" + i + "-" + j; }); })
.insert("span", function(d, i, nodes) { results.push([this, d, i, nodes]); });
test.deepEqual(results, [
[three, "child-0-0", 0, [three, four]],
[four, "child-0-1", 1, [three, four]],
[five, "child-1-0", 0, [five, ]]
]);
test.end();
});
d3-selection-1.1.0/test/selection/merge-test.js 0000664 0000000 0000000 00000006001 13106363305 0021355 0 ustar 00root root 0000000 0000000 var tape = require("tape"),
jsdom = require("../jsdom"),
d3 = require("../../");
tape("selection.merge(selection) returns a new selection, merging the two selections", function(test) {
var document = jsdom("
one
two
"),
body = document.body,
one = document.querySelector("#one"),
two = document.querySelector("#two"),
selection0 = d3.select(body).selectAll("h1"),
selection1 = selection0.select(function(d, i) { return i & 1 ? this : null; }),
selection2 = selection0.select(function(d, i) { return i & 1 ? null : this; });
test.deepEqual(selection1.merge(selection2), {_groups: [[one, two]], _parents: [body]});
test.deepEqual(selection1, {_groups: [[, two]], _parents: [body]});
test.deepEqual(selection2, {_groups: [[one, ]], _parents: [body]});
test.end();
});
tape("selection.merge(selection) returns a selection with the same size and parents as this selection", function(test) {
var document0 = jsdom("
one
two
"),
document1 = jsdom("
one
two
three
"),
body0 = document0.body,
body1 = document1.body,
one0 = document0.querySelector("#one"),
one1 = document1.querySelector("#one"),
two0 = document0.querySelector("#two"),
two1 = document1.querySelector("#two"),
three1 = document1.querySelector("#three");
test.deepEqual(d3.select(body0).selectAll("h1").merge(d3.select(body1).selectAll("h1")), {_groups: [[one0, two0]], _parents: [body0]});
test.deepEqual(d3.select(body1).selectAll("h1").merge(d3.select(body0).selectAll("h1")), {_groups: [[one1, two1, three1]], _parents: [body1]});
test.end();
});
tape("selection.merge(selection) reuses groups from this selection if the other selection has fewer groups", function(test) {
var document = jsdom(""),
body = document.body,
selection0 = d3.select(body).selectAll("parent").selectAll("child"),
selection1 = d3.select(body).selectAll("parent:first-child").selectAll("child"),
selection01 = selection0.merge(selection1),
selection10 = selection1.merge(selection0);
test.deepEqual(selection01, selection0);
test.deepEqual(selection10, selection1);
test.equal(selection01._groups[1], selection0._groups[1]);
test.end();
});
tape("selection.merge(selection) reuses this selection’s parents", function(test) {
var document = jsdom(""),
body = document.body,
selection0 = d3.select(body).selectAll("parent").selectAll("child"),
selection1 = d3.select(body).selectAll("parent:first-child").selectAll("child"),
selection01 = selection0.merge(selection1),
selection10 = selection1.merge(selection0);
test.equal(selection01._parents, selection0._parents);
test.equal(selection10._parents, selection1._parents);
test.end();
});
d3-selection-1.1.0/test/selection/node-test.js 0000664 0000000 0000000 00000002351 13106363305 0021207 0 ustar 00root root 0000000 0000000 var tape = require("tape"),
jsdom = require("../jsdom"),
d3 = require("../../");
tape("selection.node() returns the first element in a selection", function(test) {
var document = jsdom(""),
one = document.querySelector("#one"),
two = document.querySelector("#two");
test.equal(d3.selectAll([one, two]).node(), one);
test.end();
});
tape("selection.node() skips missing elements", function(test) {
var document = jsdom(""),
one = document.querySelector("#one"),
two = document.querySelector("#two");
test.equal(d3.selectAll([, one,, two]).node(), one);
test.end();
});
tape("selection.node() skips empty groups", function(test) {
var document = jsdom(""),
one = document.querySelector("#one"),
two = document.querySelector("#two");
test.equal(d3.selectAll([one, two]).selectAll(function(d, i) { return i ? [this] : []; }).node(), two);
test.end();
});
tape("selection.node() returns null for an empty selection", function(test) {
test.equal(d3.select(null).node(), null);
test.equal(d3.selectAll([]).node(), null);
test.equal(d3.selectAll([,,]).node(), null);
test.end();
});
d3-selection-1.1.0/test/selection/nodes-test.js 0000664 0000000 0000000 00000002076 13106363305 0021376 0 ustar 00root root 0000000 0000000 var tape = require("tape"),
jsdom = require("../jsdom"),
d3 = require("../../");
tape("selection.nodes() returns an array containing all selected nodes", function(test) {
var document = jsdom(""),
one = document.querySelector("#one"),
two = document.querySelector("#two");
test.deepEqual(d3.selectAll([one, two]).nodes(), [one, two]);
test.end();
});
tape("selection.nodes() merges nodes from all groups into a single array", function(test) {
var document = jsdom(""),
one = document.querySelector("#one"),
two = document.querySelector("#two");
test.deepEqual(d3.selectAll([one, two]).selectAll(function() { return [this]; }).nodes(), [one, two]);
test.end();
});
tape("selection.nodes() skips missing elements", function(test) {
var document = jsdom(""),
one = document.querySelector("#one"),
two = document.querySelector("#two");
test.deepEqual(d3.selectAll([, one,, two]).nodes(), [one, two]);
test.end();
});
d3-selection-1.1.0/test/selection/on-test.js 0000664 0000000 0000000 00000020606 13106363305 0020701 0 ustar 00root root 0000000 0000000 var tape = require("tape"),
jsdom = require("../jsdom"),
d3 = require("../../");
tape("selection.on(type, listener) registers a listeners for the specified event type on each selected element", function(test) {
var clicks = 0,
document = jsdom(""),
one = document.querySelector("#one"),
two = document.querySelector("#two"),
selection = d3.selectAll([one, two]);
test.equal(selection.on("click", function() { ++clicks; }), selection);
selection.dispatch("click");
test.equal(clicks, 2);
selection.dispatch("tick");
test.equal(clicks, 2);
test.end();
});
tape("selection.on(type, listener) observes the specified name, if any", function(test) {
var foo = 0,
bar = 0,
document = jsdom(""),
one = document.querySelector("#one"),
two = document.querySelector("#two"),
selection = d3.selectAll([one, two]).on("click.foo", function() { ++foo; }).on("click.bar", function() { ++bar; });
selection.dispatch("click");
test.equal(foo, 2);
test.equal(bar, 2);
test.end();
});
tape("selection.on(type, listener, capture) observes the specified capture flag, if any", function(test) {
var result,
selection = d3.select({addEventListener: function(type, listener, capture) { result = capture; }});
test.equal(selection.on("click.foo", function() {}, true), selection);
test.deepEqual(result, true);
test.end();
});
tape("selection.on(type) returns the listener for the specified event type, if any", function(test) {
var clicked = function() {},
document = jsdom(""),
one = document.querySelector("#one"),
two = document.querySelector("#two"),
selection = d3.selectAll([one, two]).on("click", clicked);
test.equal(selection.on("click"), clicked);
test.end();
});
tape("selection.on(type) observes the specified name, if any", function(test) {
var clicked = function() {},
document = jsdom(""),
one = document.querySelector("#one"),
two = document.querySelector("#two"),
selection = d3.selectAll([one, two]).on("click.foo", clicked);
test.equal(selection.on("click"), undefined);
test.equal(selection.on("click.foo"), clicked);
test.equal(selection.on("click.bar"), undefined);
test.equal(selection.on("tick.foo"), undefined);
test.equal(selection.on(".foo"), undefined);
test.end();
});
tape("selection.on(type, null) removes the listener with the specified name, if any", function(test) {
var clicks = 0,
document = jsdom(""),
one = document.querySelector("#one"),
two = document.querySelector("#two"),
selection = d3.selectAll([one, two]).on("click", function() { ++clicks; });
test.equal(selection.on("click", null), selection);
test.equal(selection.on("click"), undefined);
selection.dispatch("click");
test.equal(clicks, 0);
test.end();
});
tape("selection.on(type, null) observes the specified name, if any", function(test) {
var foo = 0,
bar = 0,
fooed = function() { ++foo; },
barred = function() { ++bar; },
document = jsdom(""),
one = document.querySelector("#one"),
two = document.querySelector("#two"),
selection = d3.selectAll([one, two]).on("click.foo", fooed).on("click.bar", barred);
test.equal(selection.on("click.foo", null), selection);
test.equal(selection.on("click.foo"), undefined);
test.equal(selection.on("click.bar"), barred);
selection.dispatch("click");
test.equal(foo, 0);
test.equal(bar, 2);
test.end();
});
tape("selection.on(type, null, capture) ignores the specified capture flag, if any", function(test) {
var clicks = 0,
clicked = function() { ++clicks; },
document = jsdom(),
selection = d3.select(document).on("click.foo", clicked, true);
selection.dispatch("click");
test.equal(clicks, 1);
selection.on(".foo", null, false).dispatch("click");
test.equal(clicks, 1);
test.equal(selection.on("click.foo"), undefined);
test.end();
});
tape("selection.on(name, null) removes all listeners with the specified name", function(test) {
var clicks = 0,
loads = 0,
clicked = function() { ++clicks; },
loaded = function() { ++loads; },
document = jsdom(""),
one = document.querySelector("#one"),
two = document.querySelector("#two"),
selection = d3.selectAll([one, two]).on("click.foo", clicked).on("load.foo", loaded);
test.equal(selection.on("click.foo"), clicked);
test.equal(selection.on("load.foo"), loaded);
selection.dispatch("click");
selection.dispatch("load");
test.equal(clicks, 2);
test.equal(loads, 2);
test.equal(selection.on(".foo", null), selection);
test.equal(selection.on("click.foo"), undefined);
test.equal(selection.on("load.foo"), undefined);
selection.dispatch("click");
selection.dispatch("load");
test.equal(clicks, 2);
test.equal(loads, 2);
test.end();
});
tape("selection.on(name, null) can remove a listener with capture", function(test) {
var clicks = 0,
clicked = function() { ++clicks; },
document = jsdom(),
selection = d3.select(document).on("click.foo", clicked, true);
selection.dispatch("click");
test.equal(clicks, 1);
selection.on(".foo", null).dispatch("click");
test.equal(clicks, 1);
test.equal(selection.on("click.foo"), undefined);
test.end();
});
tape("selection.on(name, listener) has no effect", function(test) {
var clicks = 0,
clicked = function() { ++clicks; },
document = jsdom(""),
one = document.querySelector("#one"),
two = document.querySelector("#two"),
selection = d3.selectAll([one, two]).on("click.foo", clicked);
test.equal(selection.on(".foo", function() { throw new Error; }), selection);
test.equal(selection.on("click.foo"), clicked);
selection.dispatch("click");
test.equal(clicks, 2);
test.end();
});
tape("selection.on(type) skips missing elements", function(test) {
var clicked = function() {},
document = jsdom(""),
one = document.querySelector("#one"),
two = document.querySelector("#two"),
selection = d3.selectAll([one, two]).on("click.foo", clicked);
test.equal(d3.selectAll([, two]).on("click.foo"), clicked);
test.end();
});
tape("selection.on(type, listener) skips missing elements", function(test) {
var clicks = 0,
clicked = function() { ++clicks; },
document = jsdom(""),
one = document.querySelector("#one"),
two = document.querySelector("#two"),
selection = d3.selectAll([, two]).on("click.foo", clicked);
selection.dispatch("click");
test.equal(clicks, 1);
test.end();
});
tape("selection.on(type, listener) passes the listener data, index and group", function(test) {
var document = jsdom(""),
one = document.querySelector("#one"),
two = document.querySelector("#two"),
three = document.querySelector("#three"),
four = document.querySelector("#four"),
five = document.querySelector("#five"),
results = [];
var selection = d3.selectAll([one, two])
.datum(function(d, i) { return "parent-" + i; })
.selectAll("child")
.data(function(d, i) { return [0, 1].map(function(j) { return "child-" + i + "-" + j; }); })
.on("foo", function(d, i, nodes) { results.push([this, d, i, nodes]); });
test.deepEqual(results, []);
selection.dispatch("foo");
test.deepEqual(results, [
[three, "child-0-0", 0, [three, four]],
[four, "child-0-1", 1, [three, four]],
[five, "child-1-0", 0, [five, ]]
]);
test.end();
});
tape("selection.on(type, listener) passes the listener the index as of registration time", function(test) {
var result,
document = jsdom(""),
one = document.querySelector("#one"),
selection = d3.selectAll([, one]).on("click", function(d, i) { result = i; });
selection.dispatch("click");
test.deepEqual(selection, {_groups: [[, one]], _parents: [null]});
test.equal(result, 1);
selection = selection.sort().dispatch("click");
test.deepEqual(selection, {_groups: [[one, ]], _parents: [null]});
test.equal(result, 1);
test.end();
});
d3-selection-1.1.0/test/selection/order-test.js 0000664 0000000 0000000 00000002463 13106363305 0021401 0 ustar 00root root 0000000 0000000 var tape = require("tape"),
jsdom = require("../jsdom"),
d3 = require("../../");
tape("selection.order() moves selected elements so that they are before their next sibling", function(test) {
var document = jsdom(""),
one = document.querySelector("#one"),
two = document.querySelector("#two"),
selection = d3.selectAll([two, one]);
test.equal(selection.order(), selection);
test.equal(one.nextSibling, null);
test.equal(two.nextSibling, one);
test.end();
});
tape("selection.order() only orders within each group", function(test) {
var document = jsdom("
"),
one = document.querySelector("#one"),
two = document.querySelector("#two"),
selection = d3.select(document).selectAll("h1").selectAll("span");
test.equal(selection.order(), selection);
test.equal(one.nextSibling, null);
test.equal(two.nextSibling, null);
test.end();
});
tape("selection.order() does not re-append nodes that are already in order", function(test) {
var two = {nextSibling: null},
one = {nextSibling: two},
selection = d3.selectAll([one, two]);
test.equal(selection.order(), selection);
test.equal(one.nextSibling, two);
test.equal(two.nextSibling, null);
test.end();
});
d3-selection-1.1.0/test/selection/property-test.js 0000664 0000000 0000000 00000004652 13106363305 0022154 0 ustar 00root root 0000000 0000000 var tape = require("tape"),
jsdom = require("../jsdom"),
d3 = require("../../");
tape("selection.property(name) returns the property with the specified name on the first selected element", function(test) {
var node = {foo: 42};
test.equal(d3.select(node).property("foo"), 42);
test.equal(d3.selectAll([null, node]).property("foo"), 42);
test.end();
});
tape("selection.property(name, value) sets property with the specified name on the selected elements", function(test) {
var one = {},
two = {},
selection = d3.selectAll([one, two]);
test.equal(selection.property("foo", "bar"), selection);
test.equal(one.foo, "bar");
test.equal(two.foo, "bar");
test.end();
});
tape("selection.property(name, null) removes the property with the specified name on the selected elements", function(test) {
var one = {foo: "bar"},
two = {foo: "bar"},
selection = d3.selectAll([one, two]);
test.equal(selection.property("foo", null), selection);
test.equal("foo" in one, false);
test.equal("foo" in two, false);
test.end();
});
tape("selection.property(name, function) sets the value of the property with the specified name on the selected elements", function(test) {
var one = {foo: "bar"},
two = {foo: "bar"},
selection = d3.selectAll([one, two]);
test.equal(selection.property("foo", function(d, i) { return i ? "baz" : null; }), selection);
test.equal("foo" in one, false);
test.equal(two.foo, "baz");
test.end();
});
tape("selection.property(name, function) passes the value function data, index and group", function(test) {
var document = jsdom(""),
one = document.querySelector("#one"),
two = document.querySelector("#two"),
three = document.querySelector("#three"),
four = document.querySelector("#four"),
five = document.querySelector("#five"),
results = [];
d3.selectAll([one, two])
.datum(function(d, i) { return "parent-" + i; })
.selectAll("child")
.data(function(d, i) { return [0, 1].map(function(j) { return "child-" + i + "-" + j; }); })
.property("color", function(d, i, nodes) { results.push([this, d, i, nodes]); });
test.deepEqual(results, [
[three, "child-0-0", 0, [three, four]],
[four, "child-0-1", 1, [three, four]],
[five, "child-1-0", 0, [five, ]]
]);
test.end();
});
d3-selection-1.1.0/test/selection/remove-test.js 0000664 0000000 0000000 00000002534 13106363305 0021562 0 ustar 00root root 0000000 0000000 var tape = require("tape"),
jsdom = require("../jsdom"),
d3 = require("../../");
tape("selection.remove() removes selected elements from their parent", function(test) {
var document = jsdom(""),
one = document.querySelector("#one"),
two = document.querySelector("#two"),
selection = d3.selectAll([two, one]);
test.equal(selection.remove(), selection);
test.equal(one.parentNode, null);
test.equal(two.parentNode, null);
test.end();
});
tape("selection.remove() skips elements that have already been detached", function(test) {
var document = jsdom(""),
one = document.querySelector("#one"),
two = document.querySelector("#two"),
selection = d3.selectAll([two, one]);
one.parentNode.removeChild(one);
test.equal(selection.remove(), selection);
test.equal(one.parentNode, null);
test.equal(two.parentNode, null);
test.end();
});
tape("selection.remove() skips missing elements", function(test) {
var document = jsdom(""),
one = document.querySelector("#one"),
two = document.querySelector("#two"),
selection = d3.selectAll([, one]);
test.equal(selection.remove(), selection);
test.equal(one.parentNode, null);
test.equal(two.parentNode, document.body);
test.end();
});
d3-selection-1.1.0/test/selection/select-test.js 0000664 0000000 0000000 00000012336 13106363305 0021545 0 ustar 00root root 0000000 0000000 var tape = require("tape"),
jsdom = require("../jsdom"),
d3 = require("../../");
tape("selection.select(…) returns a selection", function(test) {
var document = jsdom("
hello
");
test.ok(d3.select(document).select("h1") instanceof d3.selection);
test.end();
});
tape("selection.select(string) selects the first descendant that matches the selector string for each selected element", function(test) {
var document = jsdom("
"),
one = document.querySelector("#one"),
three = document.querySelector("#three");
test.deepEqual(d3.select(document).selectAll("h1").select("span"), {_groups: [[one, three]], _parents: [document]});
test.end();
});
tape("selection.select(function) selects the return value of the given function for each selected element", function(test) {
var document = jsdom(""),
one = document.querySelector("#one");
test.deepEqual(d3.select(document).select(function() { return one; }), {_groups: [[one]], _parents: [null]});
test.end();
});
tape("selection.select(function) passes the selector function data, index and group", function(test) {
var document = jsdom(""),
one = document.querySelector("#one"),
two = document.querySelector("#two"),
three = document.querySelector("#three"),
four = document.querySelector("#four"),
five = document.querySelector("#five"),
results = [];
d3.selectAll([one, two])
.datum(function(d, i) { return "parent-" + i; })
.selectAll("child")
.data(function(d, i) { return [0, 1].map(function(j) { return "child-" + i + "-" + j; }); })
.select(function(d, i, nodes) { results.push([this, d, i, nodes]); });
test.deepEqual(results, [
[three, "child-0-0", 0, [three, four]],
[four, "child-0-1", 1, [three, four]],
[five, "child-1-0", 0, [five, ]]
]);
test.end();
});
tape("selection.select(…) propagates data if defined on the originating element", function(test) {
var document = jsdom("hello"),
parent = document.querySelector("parent"),
child = document.querySelector("child");
parent.__data__ = 0; // still counts as data even though falsey
child.__data__ = 42;
d3.select(parent).select("child");
test.equal(child.__data__, 0);
test.end();
});
tape("selection.select(…) will not propagate data if not defined on the originating element", function(test) {
var document = jsdom("hello"),
parent = document.querySelector("parent"),
child = document.querySelector("child");
child.__data__ = 42;
d3.select(parent).select("child");
test.equal(child.__data__, 42);
test.end();
});
tape("selection.select(…) propagates parents from the originating selection", function(test) {
var document = jsdom("12"),
parents = d3.select(document).selectAll("parent"),
childs = parents.select("child");
test.deepEqual(parents, {_groups: [document.querySelectorAll("parent")], _parents: [document]});
test.deepEqual(childs, {_groups: [document.querySelectorAll("child")], _parents: [document]});
test.ok(parents._parents === childs._parents); // Not copied!
test.end();
});
tape("selection.select(…) can select elements when the originating selection is nested", function(test) {
var document = jsdom(""),
one = document.querySelector("#one"),
two = document.querySelector("#two"),
three = document.querySelector("#three"),
four = document.querySelector("#four");
test.deepEqual(d3.selectAll([one, two]).selectAll("child").select("span"), {_groups: [[three], [four]], _parents: [one, two]});
test.end();
});
tape("selection.select(…) skips missing originating elements", function(test) {
var document = jsdom("
hello
"),
h1 = document.querySelector("h1"),
span = document.querySelector("span");
test.deepEqual(d3.selectAll([, h1]).select("span"), {_groups: [[, span]], _parents: [null]});
test.deepEqual(d3.selectAll([null, h1]).select("span"), {_groups: [[, span]], _parents: [null]});
test.deepEqual(d3.selectAll([undefined, h1]).select("span"), {_groups: [[, span]], _parents: [null]});
test.end();
});
tape("selection.select(…) skips missing originating elements when the originating selection is nested", function(test) {
var document = jsdom(""),
one = document.querySelector("#one"),
two = document.querySelector("#two"),
three = document.querySelector("#three"),
four = document.querySelector("#four");
test.deepEqual(d3.selectAll([one, two]).selectAll("child").select(function(d, i) { return i & 1 ? this : null; }).select("span"), {_groups: [[, three], [, four]], _parents: [one, two]});
test.end();
});
d3-selection-1.1.0/test/selection/selectAll-test.js 0000664 0000000 0000000 00000012203 13106363305 0022167 0 ustar 00root root 0000000 0000000 var tape = require("tape"),
jsdom = require("../jsdom"),
d3 = require("../../");
tape("selection.selectAll(…) returns a selection", function(test) {
var document = jsdom("
hello
");
test.ok(d3.select(document).selectAll("h1") instanceof d3.selection);
test.end();
});
tape("selection.selectAll(string) selects all descendants that match the selector string for each selected element", function(test) {
var document = jsdom("
"),
one = document.querySelector("#one"),
two = document.querySelector("#two");
test.deepEqual(d3.selectAll([one, two]).selectAll("span"), {_groups: [one.querySelectorAll("span"), two.querySelectorAll("span")], _parents: [one, two]});
test.end();
});
tape("selection.selectAll(function) selects the return values of the given function for each selected element", function(test) {
var document = jsdom(""),
one = document.querySelector("#one");
test.deepEqual(d3.select(document).selectAll(function() { return [one]; }), {_groups: [[one]], _parents: [document]});
test.end();
});
tape("selection.selectAll(function) passes the selector function data, index and group", function(test) {
var document = jsdom(""),
one = document.querySelector("#one"),
two = document.querySelector("#two"),
three = document.querySelector("#three"),
four = document.querySelector("#four"),
five = document.querySelector("#five"),
results = [];
d3.selectAll([one, two])
.datum(function(d, i) { return "parent-" + i; })
.selectAll("child")
.data(function(d, i) { return [0, 1].map(function(j) { return "child-" + i + "-" + j; }); })
.selectAll(function(d, i, nodes) { results.push([this, d, i, nodes]); });
test.deepEqual(results, [
[three, "child-0-0", 0, [three, four]],
[four, "child-0-1", 1, [three, four]],
[five, "child-1-0", 0, [five, ]]
]);
test.end();
});
tape("selection.selectAll(…) will not propagate data", function(test) {
var document = jsdom("hello"),
parent = document.querySelector("parent"),
child = document.querySelector("child");
parent.__data__ = 42;
d3.select(parent).selectAll("child");
test.ok(!("__data__" in child));
test.end();
});
tape("selection.selectAll(…) groups selected elements by their parent in the originating selection", function(test) {
var document = jsdom(""),
one = document.querySelector("#one"),
two = document.querySelector("#two"),
three = document.querySelector("#three"),
four = document.querySelector("#four");
test.deepEqual(d3.select(document).selectAll("parent").selectAll("child"), {_groups: [[three], [four]], _parents: [one, two]});
test.deepEqual(d3.select(document).selectAll("child"), {_groups: [[three, four]], _parents: [document]});
test.end();
});
tape("selection.selectAll(…) can select elements when the originating selection is nested", function(test) {
var document = jsdom(""),
one = document.querySelector("#one"),
two = document.querySelector("#two"),
three = document.querySelector("#three"),
four = document.querySelector("#four"),
five = document.querySelector("#five"),
six = document.querySelector("#six");
test.deepEqual(d3.selectAll([one, two]).selectAll("child").selectAll("span"), {_groups: [[five], [six]], _parents: [three, four]});
test.end();
});
tape("selection.selectAll(…) skips missing originating elements", function(test) {
var document = jsdom("
hello
"),
h1 = document.querySelector("h1"),
span = document.querySelector("span");
test.deepEqual(d3.selectAll([, h1]).selectAll("span"), {_groups: [[span]], _parents: [h1]});
test.deepEqual(d3.selectAll([null, h1]).selectAll("span"), {_groups: [[span]], _parents: [h1]});
test.deepEqual(d3.selectAll([undefined, h1]).selectAll("span"), {_groups: [[span]], _parents: [h1]});
test.end();
});
tape("selection.selectAll(…) skips missing originating elements when the originating selection is nested", function(test) {
var document = jsdom(""),
one = document.querySelector("#one"),
two = document.querySelector("#two"),
three = document.querySelector("#three"),
four = document.querySelector("#four"),
five = document.querySelector("#five"),
six = document.querySelector("#six");
test.deepEqual(d3.selectAll([one, two]).selectAll("child").select(function(d, i) { return i & 1 ? this : null; }).selectAll("span"), {_groups: [[five], [six]], _parents: [three, four]});
test.end();
});
d3-selection-1.1.0/test/selection/size-test.js 0000664 0000000 0000000 00000001420 13106363305 0021230 0 ustar 00root root 0000000 0000000 var tape = require("tape"),
jsdom = require("../jsdom"),
d3 = require("../../");
tape("selection.size() returns the number of selected elements", function(test) {
var document = jsdom(""),
one = document.querySelector("#one"),
two = document.querySelector("#two");
test.deepEqual(d3.selectAll([]).size(), 0);
test.deepEqual(d3.selectAll([one]).size(), 1);
test.deepEqual(d3.selectAll([one, two]).size(), 2);
test.end();
});
tape("selection.size() skips missing elements", function(test) {
var document = jsdom(""),
one = document.querySelector("#one"),
two = document.querySelector("#two");
test.deepEqual(d3.selectAll([, one,, two]).size(), 2);
test.end();
});
d3-selection-1.1.0/test/selection/sort-test.js 0000664 0000000 0000000 00000011142 13106363305 0021247 0 ustar 00root root 0000000 0000000 var tape = require("tape"),
jsdom = require("../jsdom"),
d3 = require("../../");
tape("selection.sort(…) returns a new selection, sorting each group’s data, and then ordering the elements to match", function(test) {
var document = jsdom(""),
one = document.querySelector("#one"),
two = document.querySelector("#two"),
three = document.querySelector("#three"),
selection0 = d3.selectAll([two, three, one]).datum(function() { return +this.getAttribute("data-value"); }),
selection1 = selection0.sort(function(a, b) { return a - b; });
test.deepEqual(selection0, {_groups: [[two, three, one]], _parents: [null]});
test.deepEqual(selection1, {_groups: [[two, one, three]], _parents: [null]});
test.equal(two.nextSibling, one);
test.equal(one.nextSibling, three);
test.equal(three.nextSibling, null);
test.end();
});
tape("selection.sort(…) sorts each group separately", function(test) {
var document = jsdom("
"),
one = document.querySelector("#one"),
two = document.querySelector("#two"),
three = document.querySelector("#three"),
four = document.querySelector("#four"),
five = document.querySelector("#five"),
six = document.querySelector("#six"),
selection = d3.selectAll([one, two]).selectAll("h1").datum(function() { return +this.getAttribute("data-value"); });
test.deepEqual(selection.sort(function(a, b) { return a - b; }), {_groups: [[four, three], [six, five]], _parents: [one, two]});
test.equal(four.nextSibling, three);
test.equal(three.nextSibling, null);
test.equal(six.nextSibling, five);
test.equal(five.nextSibling, null);
test.end();
});
tape("selection.sort() uses natural ascending order", function(test) {
var document = jsdom(""),
one = document.querySelector("#one"),
two = document.querySelector("#two"),
selection = d3.selectAll([two, one]).datum(function(d, i) { i; });
test.deepEqual(selection.sort(), {_groups: [[two, one]], _parents: [null]});
test.equal(one.nextSibling, null);
test.equal(two.nextSibling, one);
test.end();
});
tape("selection.sort() puts missing elements at the end of each group", function(test) {
var document = jsdom(""),
one = document.querySelector("#one"),
two = document.querySelector("#two"),
selection = d3.selectAll([two, one]).datum(function(d, i) { return i; });
test.deepEqual(d3.selectAll([, one,, two]).sort(), {_groups: [[two, one,,]], _parents: [null]});
test.equal(two.nextSibling, one);
test.equal(one.nextSibling, null);
test.end();
});
tape("selection.sort(function) puts missing elements at the end of each group", function(test) {
var document = jsdom(""),
one = document.querySelector("#one"),
two = document.querySelector("#two"),
selection = d3.selectAll([two, one]).datum(function(d, i) { return i; });
test.deepEqual(d3.selectAll([, one,, two]).sort(function(a, b) { return b - a; }), {_groups: [[one, two,,]], _parents: [null]});
test.equal(one.nextSibling, two);
test.equal(two.nextSibling, null);
test.end();
});
tape("selection.sort(function) uses the specified data comparator function", function(test) {
var document = jsdom(""),
one = document.querySelector("#one"),
two = document.querySelector("#two"),
selection = d3.selectAll([two, one]).datum(function(d, i) { return i; });
test.deepEqual(selection.sort(function(a, b) { return b - a; }), {_groups: [[one, two]], _parents: [null]});
test.equal(one.nextSibling, two);
test.equal(two.nextSibling, null);
test.end();
});
tape("selection.sort(function) returns a new selection, and does not modify the groups array in-place", function(test) {
var document = jsdom(""),
one = document.querySelector("#one"),
two = document.querySelector("#two"),
selection0 = d3.selectAll([one, two]).datum(function(d, i) { return i; }),
selection1 = selection0.sort(function(a, b) { return b - a; }),
selection2 = selection1.sort();
test.deepEqual(selection0, {_groups: [[one, two]], _parents: [null]});
test.deepEqual(selection1, {_groups: [[two, one]], _parents: [null]});
test.deepEqual(selection2, {_groups: [[one, two]], _parents: [null]});
test.end();
});
d3-selection-1.1.0/test/selection/style-test.js 0000664 0000000 0000000 00000014521 13106363305 0021424 0 ustar 00root root 0000000 0000000 var tape = require("tape"),
jsdom = require("../jsdom"),
d3 = require("../../");
tape("d3.style(node, name) returns the inline value of the style property with the specified name on the first selected element, if present", function(test) {
var node = {style: {getPropertyValue: function(name) { return name === "color" ? "red" : ""}}};
test.equal(d3.style(node, "color"), "red");
test.end();
});
tape("d3.style(node, name) returns the computed value of the style property with the specified name on the first selected element, if there is no inline style", function(test) {
var style = {getPropertyValue: function(name) { return name === "color" ? "rgb(255, 0, 0)" : ""}},
node = {style: {getPropertyValue: function() { return ""; }}, ownerDocument: {defaultView: {getComputedStyle: function(n) { return n === node ? style : null; }}}};
test.equal(d3.style(node, "color"), "rgb(255, 0, 0)");
test.end();
});
tape("selection.style(name) returns the inline value of the style property with the specified name on the first selected element, if present", function(test) {
var node = {style: {getPropertyValue: function(name) { return name === "color" ? "red" : ""}}};
test.equal(d3.select(node).style("color"), "red");
test.equal(d3.selectAll([null, node]).style("color"), "red");
test.end();
});
tape("selection.style(name) returns the computed value of the style property with the specified name on the first selected element, if there is no inline style", function(test) {
var style = {getPropertyValue: function(name) { return name === "color" ? "rgb(255, 0, 0)" : ""}},
node = {style: {getPropertyValue: function() { return ""; }}, ownerDocument: {defaultView: {getComputedStyle: function(n) { return n === node ? style : null; }}}};
test.equal(d3.select(node).style("color"), "rgb(255, 0, 0)");
test.equal(d3.selectAll([null, node]).style("color"), "rgb(255, 0, 0)");
test.end();
});
tape("selection.style(name, value) sets the value of the style property with the specified name on the selected elements", function(test) {
var document = jsdom("
hello
"),
one = document.querySelector("#one"),
two = document.querySelector("#two"),
selection = d3.selectAll([one, two]);
test.equal(selection.style("color", "red"), selection);
test.equal(one.style.getPropertyValue("color"), "red");
test.equal(one.style.getPropertyPriority("color"), "");
test.equal(two.style.getPropertyValue("color"), "red");
test.equal(two.style.getPropertyPriority("color"), "");
test.end();
});
tape("selection.style(name, value, priority) sets the value and priority of the style property with the specified name on the selected elements", function(test) {
var document = jsdom("
hello
"),
one = document.querySelector("#one"),
two = document.querySelector("#two"),
selection = d3.selectAll([one, two]);
test.equal(selection.style("color", "red", "important"), selection);
test.equal(one.style.getPropertyValue("color"), "red");
test.equal(one.style.getPropertyPriority("color"), "important");
test.equal(two.style.getPropertyValue("color"), "red");
test.equal(two.style.getPropertyPriority("color"), "important");
test.end();
});
tape("selection.style(name, null) removes the attribute with the specified name on the selected elements", function(test) {
var document = jsdom("
hello
"),
one = document.querySelector("#one"),
two = document.querySelector("#two"),
selection = d3.selectAll([one, two]);
test.equal(selection.style("color", null), selection);
test.equal(one.style.getPropertyValue("color"), "");
test.equal(one.style.getPropertyPriority("color"), "");
test.equal(two.style.getPropertyValue("color"), "");
test.equal(two.style.getPropertyPriority("color"), "");
test.end();
});
tape("selection.style(name, function) sets the value of the style property with the specified name on the selected elements", function(test) {
var document = jsdom("
hello
"),
one = document.querySelector("#one"),
two = document.querySelector("#two"),
selection = d3.selectAll([one, two]);
test.equal(selection.style("color", function(d, i) { return i ? "red" : null; }), selection);
test.equal(one.style.getPropertyValue("color"), "");
test.equal(one.style.getPropertyPriority("color"), "");
test.equal(two.style.getPropertyValue("color"), "red");
test.equal(two.style.getPropertyPriority("color"), "");
test.end();
});
tape("selection.style(name, function, priority) sets the value and priority of the style property with the specified name on the selected elements", function(test) {
var document = jsdom("
hello
"),
one = document.querySelector("#one"),
two = document.querySelector("#two"),
selection = d3.selectAll([one, two]);
test.equal(selection.style("color", function(d, i) { return i ? "red" : null; }, "important"), selection);
test.equal(one.style.getPropertyValue("color"), "");
test.equal(one.style.getPropertyPriority("color"), "");
test.equal(two.style.getPropertyValue("color"), "red");
test.equal(two.style.getPropertyPriority("color"), "important");
test.end();
});
tape("selection.style(name, function) passes the value function data, index and group", function(test) {
var document = jsdom(""),
one = document.querySelector("#one"),
two = document.querySelector("#two"),
three = document.querySelector("#three"),
four = document.querySelector("#four"),
five = document.querySelector("#five"),
results = [];
d3.selectAll([one, two])
.datum(function(d, i) { return "parent-" + i; })
.selectAll("child")
.data(function(d, i) { return [0, 1].map(function(j) { return "child-" + i + "-" + j; }); })
.style("color", function(d, i, nodes) { results.push([this, d, i, nodes]); });
test.deepEqual(results, [
[three, "child-0-0", 0, [three, four]],
[four, "child-0-1", 1, [three, four]],
[five, "child-1-0", 0, [five, ]]
]);
test.end();
});
d3-selection-1.1.0/test/selection/text-test.js 0000664 0000000 0000000 00000004526 13106363305 0021254 0 ustar 00root root 0000000 0000000 var tape = require("tape"),
jsdom = require("../jsdom"),
d3 = require("../../");
tape("selection.text() returns the text content on the first selected element", function(test) {
var node = {textContent: "hello"};
test.equal(d3.select(node).text(), "hello");
test.equal(d3.selectAll([null, node]).text(), "hello");
test.end();
});
tape("selection.text(value) sets text content on the selected elements", function(test) {
var one = {textContent: ""},
two = {textContent: ""},
selection = d3.selectAll([one, two]);
test.equal(selection.text("bar"), selection);
test.equal(one.textContent, "bar");
test.equal(two.textContent, "bar");
test.end();
});
tape("selection.text(null) clears the text content on the selected elements", function(test) {
var one = {textContent: "bar"},
two = {textContent: "bar"},
selection = d3.selectAll([one, two]);
test.equal(selection.text(null), selection);
test.equal(one.textContent, "");
test.equal(two.textContent, "");
test.end();
});
tape("selection.text(function) sets the value of the text content on the selected elements", function(test) {
var one = {textContent: "bar"},
two = {textContent: "bar"},
selection = d3.selectAll([one, two]);
test.equal(selection.text(function(d, i) { return i ? "baz" : null; }), selection);
test.equal(one.textContent, "");
test.equal(two.textContent, "baz");
test.end();
});
tape("selection.text(function) passes the value function data, index and group", function(test) {
var document = jsdom(""),
one = document.querySelector("#one"),
two = document.querySelector("#two"),
three = document.querySelector("#three"),
four = document.querySelector("#four"),
five = document.querySelector("#five"),
results = [];
d3.selectAll([one, two])
.datum(function(d, i) { return "parent-" + i; })
.selectAll("child")
.data(function(d, i) { return [0, 1].map(function(j) { return "child-" + i + "-" + j; }); })
.text(function(d, i, nodes) { results.push([this, d, i, nodes]); });
test.deepEqual(results, [
[three, "child-0-0", 0, [three, four]],
[four, "child-0-1", 1, [three, four]],
[five, "child-1-0", 0, [five, ]]
]);
test.end();
});
d3-selection-1.1.0/test/selection/window-test.js 0000664 0000000 0000000 00000001136 13106363305 0021571 0 ustar 00root root 0000000 0000000 var tape = require("tape"),
jsdom = require("../jsdom"),
d3 = require("../../");
tape("d3.window(node) returns node.ownerDocument.defaultView", function(test) {
var document = jsdom();
test.equal(d3.window(document.body), document.defaultView);
test.end();
});
tape("d3.window(document) returns document.defaultView", function(test) {
var document = jsdom();
test.equal(d3.window(document), document.defaultView);
test.end();
});
tape("d3.window(window) returns window", function(test) {
var window = jsdom().defaultView;
test.equal(d3.window(window), window);
test.end();
});
d3-selection-1.1.0/test/selector-test.js 0000664 0000000 0000000 00000002051 13106363305 0020112 0 ustar 00root root 0000000 0000000 var tape = require("tape"),
jsdom = require("./jsdom"),
d3 = require("../");
tape("d3.selector(selector).call(element) returns the first element that matches the selector", function(test) {
var document = jsdom("");
test.equal(d3.selector("body").call(document.documentElement), document.body);
test.equal(d3.selector(".foo").call(document.documentElement), document.body);
test.equal(d3.selector("body.foo").call(document.documentElement), document.body);
test.equal(d3.selector("h1").call(document.documentElement), null);
test.equal(d3.selector("body.bar").call(document.documentElement), null);
test.end();
});
tape("d3.selector(null).call(element) always returns undefined", function(test) {
var document = jsdom("");
test.equal(d3.selector().call(document.documentElement), undefined);
test.equal(d3.selector(null).call(document.documentElement), undefined);
test.equal(d3.selector(undefined).call(document.documentElement), undefined);
test.end();
});
d3-selection-1.1.0/test/selectorAll-test.js 0000664 0000000 0000000 00000003115 13106363305 0020545 0 ustar 00root root 0000000 0000000 var tape = require("tape"),
jsdom = require("./jsdom"),
d3 = require("../");
tape("d3.selectorAll(selector).call(element) returns all elements that match the selector", function(test) {
var document = jsdom("
"),
body = document.body,
div = document.querySelector("div");
test.deepEqual(d3.selectorAll("body").call(document.documentElement), [body]);
test.deepEqual(d3.selectorAll(".foo").call(document.documentElement), [body, div]);
test.deepEqual(d3.selectorAll("div.foo").call(document.documentElement), [div]);
test.deepEqual(d3.selectorAll("div").call(document.documentElement), [div]);
test.deepEqual(d3.selectorAll("div,body").call(document.documentElement), [body,div]);
test.deepEqual(d3.selectorAll("h1").call(document.documentElement), []);
test.deepEqual(d3.selectorAll("body.bar").call(document.documentElement), []);
test.end();
});
tape("d3.selectorAll(null).call(element) always returns the empty array", function(test) {
var document = jsdom("");
test.deepEqual(d3.selectorAll().call(document.documentElement), []);
test.deepEqual(d3.selectorAll(null).call(document.documentElement), []);
test.deepEqual(d3.selectorAll(undefined).call(document.documentElement), []);
test.end();
});
tape("d3.selectorAll(null).call(element) returns a new empty array each time", function(test) {
var one = d3.selectorAll()(),
two = d3.selectorAll()();
test.equal(one === two, false);
one.push("one");
test.deepEqual(d3.selectorAll()(), []);
test.end();
});