@d3plus/dom 3.0.15 → 3.1.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/LICENSE +21 -0
- package/README.md +252 -77
- package/es/index.js +1 -1
- package/es/src/D3Selection.js +4 -0
- package/es/src/assign.js +6 -8
- package/es/src/attrize.js +3 -4
- package/es/src/backgroundColor.js +14 -0
- package/es/src/date.js +4 -6
- package/es/src/elem.js +11 -18
- package/es/src/fontExists.js +5 -6
- package/es/src/getSize.js +20 -15
- package/es/src/inViewport.js +5 -7
- package/es/src/isObject.js +6 -6
- package/es/src/parseSides.js +3 -4
- package/es/src/rtl.js +3 -5
- package/es/src/stylize.js +3 -4
- package/es/src/textWidth.js +32 -27
- package/package.json +18 -9
- package/types/index.d.ts +14 -0
- package/types/src/D3Selection.d.ts +28 -0
- package/types/src/assign.d.ts +11 -0
- package/types/src/attrize.d.ts +7 -0
- package/types/src/backgroundColor.d.ts +7 -0
- package/types/src/date.d.ts +5 -0
- package/types/src/elem.d.ts +18 -0
- package/types/src/fontExists.d.ts +6 -0
- package/types/src/getSize.d.ts +5 -0
- package/types/src/inViewport.d.ts +6 -0
- package/types/src/isObject.d.ts +5 -0
- package/types/src/parseSides.d.ts +11 -0
- package/types/src/prefix.d.ts +5 -0
- package/types/src/rtl.d.ts +4 -0
- package/types/src/stylize.d.ts +7 -0
- package/types/src/textWidth.d.ts +7 -0
- package/umd/d3plus-dom.full.js +2322 -220
- package/umd/d3plus-dom.full.js.map +1 -1
- package/umd/d3plus-dom.full.min.js +186 -134
- package/umd/d3plus-dom.js +108 -218
- package/umd/d3plus-dom.js.map +1 -1
- package/umd/d3plus-dom.min.js +76 -76
- package/es/src/prefix.js +0 -10
package/umd/d3plus-dom.js
CHANGED
|
@@ -1,144 +1,37 @@
|
|
|
1
1
|
/*
|
|
2
|
-
@d3plus/dom v3.0.
|
|
2
|
+
@d3plus/dom v3.0.16
|
|
3
3
|
JavaScript functions for manipulating and analyzing DOM elements.
|
|
4
4
|
Copyright (c) 2026 D3plus - https://d3plus.org
|
|
5
5
|
@license MIT
|
|
6
6
|
*/
|
|
7
|
-
|
|
8
|
-
(function (factory) {
|
|
9
|
-
typeof define === 'function' && define.amd ? define(factory) :
|
|
10
|
-
factory();
|
|
11
|
-
})((function () { 'use strict';
|
|
12
|
-
|
|
13
|
-
if (typeof window !== "undefined") {
|
|
14
|
-
(function () {
|
|
15
|
-
try {
|
|
16
|
-
if (typeof SVGElement === 'undefined' || Boolean(SVGElement.prototype.innerHTML)) {
|
|
17
|
-
return;
|
|
18
|
-
}
|
|
19
|
-
} catch (e) {
|
|
20
|
-
return;
|
|
21
|
-
}
|
|
22
|
-
|
|
23
|
-
function serializeNode (node) {
|
|
24
|
-
switch (node.nodeType) {
|
|
25
|
-
case 1:
|
|
26
|
-
return serializeElementNode(node);
|
|
27
|
-
case 3:
|
|
28
|
-
return serializeTextNode(node);
|
|
29
|
-
case 8:
|
|
30
|
-
return serializeCommentNode(node);
|
|
31
|
-
}
|
|
32
|
-
}
|
|
33
|
-
|
|
34
|
-
function serializeTextNode (node) {
|
|
35
|
-
return node.textContent.replace(/&/g, '&').replace(/</g, '<').replace(/>/g, '>');
|
|
36
|
-
}
|
|
37
|
-
|
|
38
|
-
function serializeCommentNode (node) {
|
|
39
|
-
return '<!--' + node.nodeValue + '-->'
|
|
40
|
-
}
|
|
41
|
-
|
|
42
|
-
function serializeElementNode (node) {
|
|
43
|
-
var output = '';
|
|
44
|
-
|
|
45
|
-
output += '<' + node.tagName;
|
|
46
|
-
|
|
47
|
-
if (node.hasAttributes()) {
|
|
48
|
-
[].forEach.call(node.attributes, function(attrNode) {
|
|
49
|
-
output += ' ' + attrNode.name + '="' + attrNode.value + '"';
|
|
50
|
-
});
|
|
51
|
-
}
|
|
52
|
-
|
|
53
|
-
output += '>';
|
|
54
|
-
|
|
55
|
-
if (node.hasChildNodes()) {
|
|
56
|
-
[].forEach.call(node.childNodes, function(childNode) {
|
|
57
|
-
output += serializeNode(childNode);
|
|
58
|
-
});
|
|
59
|
-
}
|
|
60
|
-
|
|
61
|
-
output += '</' + node.tagName + '>';
|
|
62
|
-
|
|
63
|
-
return output;
|
|
64
|
-
}
|
|
65
|
-
|
|
66
|
-
Object.defineProperty(SVGElement.prototype, 'innerHTML', {
|
|
67
|
-
get: function () {
|
|
68
|
-
var output = '';
|
|
69
|
-
|
|
70
|
-
[].forEach.call(this.childNodes, function(childNode) {
|
|
71
|
-
output += serializeNode(childNode);
|
|
72
|
-
});
|
|
73
|
-
|
|
74
|
-
return output;
|
|
75
|
-
},
|
|
76
|
-
set: function (markup) {
|
|
77
|
-
while (this.firstChild) {
|
|
78
|
-
this.removeChild(this.firstChild);
|
|
79
|
-
}
|
|
80
|
-
|
|
81
|
-
try {
|
|
82
|
-
var dXML = new DOMParser();
|
|
83
|
-
dXML.async = false;
|
|
84
|
-
|
|
85
|
-
var sXML = '<svg xmlns=\'http://www.w3.org/2000/svg\' xmlns:xlink=\'http://www.w3.org/1999/xlink\'>' + markup + '</svg>';
|
|
86
|
-
var svgDocElement = dXML.parseFromString(sXML, 'text/xml').documentElement;
|
|
87
|
-
|
|
88
|
-
[].forEach.call(svgDocElement.childNodes, function(childNode) {
|
|
89
|
-
this.appendChild(this.ownerDocument.importNode(childNode, true));
|
|
90
|
-
}.bind(this));
|
|
91
|
-
} catch (e) {
|
|
92
|
-
throw new Error('Error parsing markup string');
|
|
93
|
-
}
|
|
94
|
-
}
|
|
95
|
-
});
|
|
96
|
-
|
|
97
|
-
Object.defineProperty(SVGElement.prototype, 'innerSVG', {
|
|
98
|
-
get: function () {
|
|
99
|
-
return this.innerHTML;
|
|
100
|
-
},
|
|
101
|
-
set: function (markup) {
|
|
102
|
-
this.innerHTML = markup;
|
|
103
|
-
}
|
|
104
|
-
});
|
|
105
|
-
|
|
106
|
-
})();
|
|
107
|
-
}
|
|
108
|
-
|
|
109
|
-
}));
|
|
110
|
-
|
|
111
7
|
(function (global, factory) {
|
|
112
|
-
typeof exports === 'object' && typeof module !== 'undefined' ? factory(exports, require('d3-selection'), require('d3-transition'), require('@
|
|
113
|
-
typeof define === 'function' && define.amd ? define('@d3plus/dom', ['exports', 'd3-selection', 'd3-transition', '@
|
|
114
|
-
(global = typeof globalThis !== 'undefined' ? globalThis : global || self, factory(global.d3plus = {}, global.d3Selection, global.d3Transition, global.
|
|
115
|
-
})(this, (function (exports, d3Selection, d3Transition,
|
|
8
|
+
typeof exports === 'object' && typeof module !== 'undefined' ? factory(exports, require('d3-selection'), require('d3-transition'), require('@chenglou/pretext')) :
|
|
9
|
+
typeof define === 'function' && define.amd ? define('@d3plus/dom', ['exports', 'd3-selection', 'd3-transition', '@chenglou/pretext'], factory) :
|
|
10
|
+
(global = typeof globalThis !== 'undefined' ? globalThis : global || self, factory(global.d3plus = {}, global.d3Selection, global.d3Transition, global.pretext));
|
|
11
|
+
})(this, (function (exports, d3Selection, d3Transition, pretext) { 'use strict';
|
|
116
12
|
|
|
117
13
|
/**
|
|
118
|
-
|
|
119
|
-
@
|
|
120
|
-
@param {*} item
|
|
14
|
+
Detects if a variable is a javascript Object.
|
|
15
|
+
@param item The value to test.
|
|
121
16
|
*/ function isObject(item) {
|
|
122
17
|
return item && typeof item === "object" && (typeof window === "undefined" || item !== window && item !== window.document && !(item instanceof Element)) && !Array.isArray(item) ? true : false;
|
|
123
18
|
}
|
|
124
19
|
|
|
125
20
|
/**
|
|
126
|
-
|
|
127
|
-
@
|
|
128
|
-
@param {Object} obj
|
|
129
|
-
@private
|
|
21
|
+
Determines if the object passed is the document or window.
|
|
22
|
+
@param obj @private
|
|
130
23
|
*/ function validObject(obj) {
|
|
131
24
|
if (typeof window === "undefined") return true;
|
|
132
25
|
else return obj !== window && obj !== document;
|
|
133
26
|
}
|
|
134
27
|
/**
|
|
135
|
-
|
|
136
|
-
|
|
137
|
-
|
|
138
|
-
@example <caption>this</caption>
|
|
28
|
+
A deeply recursive version of `Object.assign`.
|
|
29
|
+
|
|
30
|
+
@example <caption>this</caption>
|
|
139
31
|
assign({id: "foo", deep: {group: "A"}}, {id: "bar", deep: {value: 20}}));
|
|
140
32
|
@example <caption>returns this</caption>
|
|
141
33
|
{id: "bar", deep: {group: "A", value: 20}}
|
|
34
|
+
@param objects The source objects to merge into the target.
|
|
142
35
|
*/ function assign(...objects) {
|
|
143
36
|
const target = objects[0];
|
|
144
37
|
for(let i = 1; i < objects.length; i++){
|
|
@@ -157,19 +50,31 @@
|
|
|
157
50
|
}
|
|
158
51
|
|
|
159
52
|
/**
|
|
160
|
-
|
|
161
|
-
|
|
162
|
-
|
|
163
|
-
@param
|
|
53
|
+
Given a DOM element, returns its background color by walking up the
|
|
54
|
+
ancestor chain until a non-transparent background is found. Falls back
|
|
55
|
+
to "rgb(255, 255, 255)" (white) if every ancestor is transparent.
|
|
56
|
+
@param elem The DOM element to check.
|
|
57
|
+
*/ function backgroundColor(elem) {
|
|
58
|
+
let node = elem;
|
|
59
|
+
while(node){
|
|
60
|
+
const bg = getComputedStyle(node).backgroundColor;
|
|
61
|
+
if (bg && bg !== "transparent" && bg !== "rgba(0, 0, 0, 0)") return bg;
|
|
62
|
+
node = node.parentElement;
|
|
63
|
+
}
|
|
64
|
+
return "rgb(255, 255, 255)";
|
|
65
|
+
}
|
|
66
|
+
|
|
67
|
+
/**
|
|
68
|
+
Applies each key/value in an object as an attr.
|
|
69
|
+
@param e The d3 selection to apply attributes to.
|
|
70
|
+
@param a An object of key/value attr pairs.
|
|
164
71
|
*/ function attrize(e, a = {}) {
|
|
165
72
|
for(const k in a)if (({}).hasOwnProperty.call(a, k)) e.attr(k, a[k]);
|
|
166
73
|
}
|
|
167
74
|
|
|
168
75
|
/**
|
|
169
|
-
|
|
170
|
-
@
|
|
171
|
-
@description Returns a javascript Date object for a given a Number (representing either a 4-digit year or milliseconds since epoch), a String representing a Quarter (ie. "Q2 1987", mapping to the last day in that quarter), or a String that is in [valid dateString format](http://dygraphs.com/date-formats.html). Besides the 4-digit year parsing, this function is useful when needing to parse negative (BC) years, which the vanilla Date object cannot parse.
|
|
172
|
-
@param {Number|String} *date*
|
|
76
|
+
Parses numbers and strings into valid JavaScript Date objects, supporting years, quarters, months, and ISO 8601 formats.
|
|
77
|
+
@param d The date value to parse (number, string, or Date).
|
|
173
78
|
*/ function date(d) {
|
|
174
79
|
// returns if falsey or already Date object
|
|
175
80
|
if ([
|
|
@@ -208,8 +113,8 @@
|
|
|
208
113
|
return date;
|
|
209
114
|
}
|
|
210
115
|
// tests for monthly formats (ie. "MM-YYYY" and "YYYY-MM")
|
|
211
|
-
const monthPrefix = new RegExp(/^([-*\d]{1,2})
|
|
212
|
-
const monthSuffix = new RegExp(/^(-*\d{1,4})
|
|
116
|
+
const monthPrefix = new RegExp(/^([-*\d]{1,2})-(-*\d{1,4})$/g).exec(s);
|
|
117
|
+
const monthSuffix = new RegExp(/^(-*\d{1,4})-([-*\d]{1,2})$/g).exec(s);
|
|
213
118
|
if (monthPrefix || monthSuffix) {
|
|
214
119
|
const month = +(monthPrefix ? monthPrefix[1] : monthSuffix[2]);
|
|
215
120
|
const year = +(monthPrefix ? monthPrefix[2] : monthSuffix[1]);
|
|
@@ -230,19 +135,12 @@
|
|
|
230
135
|
}
|
|
231
136
|
|
|
232
137
|
/**
|
|
233
|
-
|
|
234
|
-
@
|
|
235
|
-
@param
|
|
236
|
-
@param {Object} params Additional parameters.
|
|
237
|
-
@param {Boolean} [params.condition = true] Whether or not the element should be rendered (or removed).
|
|
238
|
-
@param {Object} [params.enter = {}] A collection of key/value pairs that map to attributes to be given on enter.
|
|
239
|
-
@param {Object} [params.exit = {}] A collection of key/value pairs that map to attributes to be given on exit.
|
|
240
|
-
@param {D3Selection} [params.parent = d3.select("body")] The parent element for this new element to be appended to.
|
|
241
|
-
@param {Number} [params.duration = 0] The duration for the d3 transition.
|
|
242
|
-
@param {Object} [params.update = {}] A collection of key/value pairs that map to attributes to be given on update.
|
|
138
|
+
Manages the enter/update/exit pattern for a single DOM element, applying enter, update, and exit attributes with optional transitions.
|
|
139
|
+
@param selector A CSS selector string for the element tag and classes.
|
|
140
|
+
@param p Configuration object with enter, exit, update, and parent options.
|
|
243
141
|
*/ function elem(selector, p) {
|
|
244
142
|
// overrides default params
|
|
245
|
-
|
|
143
|
+
const params = Object.assign({}, {
|
|
246
144
|
condition: true,
|
|
247
145
|
enter: {},
|
|
248
146
|
exit: {},
|
|
@@ -250,18 +148,18 @@
|
|
|
250
148
|
parent: d3Selection.select("body"),
|
|
251
149
|
update: {}
|
|
252
150
|
}, p);
|
|
253
|
-
const className = /\.([^#]+)/g.exec(selector), id = /#([^.]+)/g.exec(selector), t = d3Transition.transition().duration(
|
|
254
|
-
const elem =
|
|
151
|
+
const className = /\.([^#]+)/g.exec(selector), id = /#([^.]+)/g.exec(selector), t = d3Transition.transition().duration(params.duration), tag = /^([^.^#]+)/g.exec(selector)[1];
|
|
152
|
+
const elem = params.parent.selectAll(selector.includes(":") ? selector.split(":")[1] : selector).data(params.condition ? [
|
|
255
153
|
null
|
|
256
154
|
] : []);
|
|
257
|
-
const enter = elem.enter().append(tag).call(attrize,
|
|
155
|
+
const enter = elem.enter().append(tag).call(attrize, params.enter);
|
|
258
156
|
if (id) enter.attr("id", id[1]);
|
|
259
157
|
if (className) enter.attr("class", className[1]);
|
|
260
|
-
if (
|
|
261
|
-
else elem.exit().call(attrize,
|
|
158
|
+
if (params.duration) elem.exit().transition(t).call(attrize, params.exit).remove();
|
|
159
|
+
else elem.exit().call(attrize, params.exit).remove();
|
|
262
160
|
const update = enter.merge(elem);
|
|
263
|
-
if (
|
|
264
|
-
else update.call(attrize,
|
|
161
|
+
if (params.duration) update.transition(t).call(attrize, params.update);
|
|
162
|
+
else update.call(attrize, params.update);
|
|
265
163
|
return update;
|
|
266
164
|
}
|
|
267
165
|
|
|
@@ -274,36 +172,37 @@
|
|
|
274
172
|
return doc.documentElement ? doc.documentElement.textContent : input;
|
|
275
173
|
}
|
|
276
174
|
/**
|
|
277
|
-
|
|
278
|
-
|
|
279
|
-
|
|
280
|
-
|
|
281
|
-
|
|
282
|
-
|
|
283
|
-
|
|
284
|
-
|
|
285
|
-
|
|
286
|
-
|
|
287
|
-
|
|
288
|
-
|
|
289
|
-
|
|
290
|
-
|
|
291
|
-
|
|
292
|
-
|
|
293
|
-
|
|
294
|
-
|
|
295
|
-
|
|
296
|
-
|
|
297
|
-
|
|
298
|
-
|
|
175
|
+
* Builds a CSS font shorthand string from a style object.
|
|
176
|
+
* @param {Object} styleObj
|
|
177
|
+
*/ function buildFont(styleObj) {
|
|
178
|
+
const style = styleObj["font-style"] || "normal";
|
|
179
|
+
const variant = styleObj["font-variant"] || "normal";
|
|
180
|
+
const weight = styleObj["font-weight"] || 400;
|
|
181
|
+
const size = typeof styleObj["font-size"] === "string" ? styleObj["font-size"] : `${styleObj["font-size"] || 10}px`;
|
|
182
|
+
const family = styleObj["font-family"] || "sans-serif";
|
|
183
|
+
return `${style} ${variant} ${weight} ${size} ${family}`;
|
|
184
|
+
}
|
|
185
|
+
/**
|
|
186
|
+
* Measures the width of a single text string using pretext.
|
|
187
|
+
* @param {String} text
|
|
188
|
+
* @param {String} font CSS font shorthand
|
|
189
|
+
*/ function measureWidth(text, font) {
|
|
190
|
+
if (!text) return 0;
|
|
191
|
+
const prepared = pretext.prepareWithSegments(text, font);
|
|
192
|
+
const result = pretext.layoutWithLines(prepared, Infinity, 20);
|
|
193
|
+
return result.lines.length ? result.lines[0].width : 0;
|
|
194
|
+
}
|
|
195
|
+
function textWidth(text, style = {}) {
|
|
196
|
+
const font = buildFont(style);
|
|
197
|
+
if (text instanceof Array) return text.map((t)=>measureWidth(htmlDecode(t), font));
|
|
198
|
+
return measureWidth(htmlDecode(text), font);
|
|
299
199
|
}
|
|
300
200
|
|
|
301
201
|
const alpha = "abcdefghiABCDEFGHI_!@#$%^&*()_+1234567890", checked = {}, height = 32;
|
|
302
202
|
let dejavu, macos, monospace, proportional;
|
|
303
203
|
/**
|
|
304
|
-
|
|
305
|
-
@
|
|
306
|
-
@param {String|Array} font Can be either a valid CSS font-family string (single or comma-separated names) or an Array of string names.
|
|
204
|
+
Given either a single font-family or a list of fonts, returns the name of the first font that can be rendered, or `false` if none are installed on the user's machine.
|
|
205
|
+
@param font Can be either a valid CSS font-family string (single or comma-separated names) or an Array of string names.
|
|
307
206
|
*/ const fontExists = (font)=>{
|
|
308
207
|
if (!dejavu) {
|
|
309
208
|
dejavu = textWidth(alpha, {
|
|
@@ -324,7 +223,7 @@
|
|
|
324
223
|
});
|
|
325
224
|
}
|
|
326
225
|
if (!(font instanceof Array)) font = font.split(",");
|
|
327
|
-
font = font.map((f)=>
|
|
226
|
+
font = font.map((f)=>f.trim());
|
|
328
227
|
for(let i = 0; i < font.length; i++){
|
|
329
228
|
const fam = font[i];
|
|
330
229
|
if (checked[fam] || [
|
|
@@ -348,7 +247,7 @@
|
|
|
348
247
|
};
|
|
349
248
|
|
|
350
249
|
/**
|
|
351
|
-
|
|
250
|
+
Given an HTMLElement and a "width" or "height" string, this function returns the current calculated size for the DOM element.
|
|
352
251
|
@private
|
|
353
252
|
*/ function _elementSize(element, s) {
|
|
354
253
|
if (!element) return undefined;
|
|
@@ -359,32 +258,37 @@
|
|
|
359
258
|
let val = window[`inner${s.charAt(0).toUpperCase() + s.slice(1)}`];
|
|
360
259
|
const elem = d3Selection.select(element);
|
|
361
260
|
if (s === "width") {
|
|
362
|
-
val -= parseFloat(elem.style("margin-left")
|
|
363
|
-
val -= parseFloat(elem.style("margin-right")
|
|
364
|
-
val -= parseFloat(elem.style("padding-left")
|
|
365
|
-
val -= parseFloat(elem.style("padding-right")
|
|
261
|
+
val -= parseFloat(elem.style("margin-left"));
|
|
262
|
+
val -= parseFloat(elem.style("margin-right"));
|
|
263
|
+
val -= parseFloat(elem.style("padding-left"));
|
|
264
|
+
val -= parseFloat(elem.style("padding-right"));
|
|
366
265
|
} else {
|
|
367
|
-
val -= parseFloat(elem.style("margin-top")
|
|
368
|
-
val -= parseFloat(elem.style("margin-bottom")
|
|
369
|
-
val -= parseFloat(elem.style("padding-top")
|
|
370
|
-
val -= parseFloat(elem.style("padding-bottom")
|
|
266
|
+
val -= parseFloat(elem.style("margin-top"));
|
|
267
|
+
val -= parseFloat(elem.style("margin-bottom"));
|
|
268
|
+
val -= parseFloat(elem.style("padding-top"));
|
|
269
|
+
val -= parseFloat(elem.style("padding-bottom"));
|
|
371
270
|
}
|
|
372
271
|
return val;
|
|
373
272
|
} else {
|
|
374
|
-
let val =
|
|
273
|
+
let val = element.getBoundingClientRect()[s];
|
|
375
274
|
if (typeof val === "number" && val > 0) {
|
|
376
275
|
if (s === "height") {
|
|
377
|
-
val -= parseFloat(d3Selection.select(element).style("padding-top")
|
|
378
|
-
val -= parseFloat(d3Selection.select(element).style("padding-bottom")
|
|
276
|
+
val -= parseFloat(d3Selection.select(element).style("padding-top"));
|
|
277
|
+
val -= parseFloat(d3Selection.select(element).style("padding-bottom"));
|
|
278
|
+
val -= parseFloat(d3Selection.select(element).style("border-top"));
|
|
279
|
+
val -= parseFloat(d3Selection.select(element).style("border-bottom"));
|
|
280
|
+
} else {
|
|
281
|
+
val -= parseFloat(d3Selection.select(element).style("padding-left"));
|
|
282
|
+
val -= parseFloat(d3Selection.select(element).style("padding-right"));
|
|
283
|
+
val -= parseFloat(d3Selection.select(element).style("border-left"));
|
|
284
|
+
val -= parseFloat(d3Selection.select(element).style("border-right"));
|
|
379
285
|
}
|
|
380
286
|
return val;
|
|
381
287
|
} else return _elementSize(element.parentNode, s);
|
|
382
288
|
}
|
|
383
289
|
}
|
|
384
290
|
/**
|
|
385
|
-
|
|
386
|
-
@desc Finds the available width and height for a specified HTMLElement, traversing it's parents until it finds something with constrained dimensions. Falls back to the inner dimensions of the browser window if none is found.
|
|
387
|
-
@param {HTMLElement} elem The HTMLElement to find dimensions for.
|
|
291
|
+
Finds the available width and height for a specified HTMLElement, traversing it's parents until it finds something with constrained dimensions. Falls back to the inner dimensions of the browser window if none is found.
|
|
388
292
|
@private
|
|
389
293
|
*/ function getSize(elem) {
|
|
390
294
|
return [
|
|
@@ -394,27 +298,24 @@
|
|
|
394
298
|
}
|
|
395
299
|
|
|
396
300
|
/**
|
|
397
|
-
|
|
398
|
-
|
|
399
|
-
|
|
400
|
-
@param {Number} [buffer = 0] A pixel offset from the edge of the top and bottom of the screen. If a positive value, the element will be deemed visible when it is that many pixels away from entering the viewport. If negative, the element will have to enter the viewport by that many pixels before being deemed visible.
|
|
401
|
-
@private
|
|
301
|
+
Determines whether a given DOM element is visible within the current viewport, with an optional pixel buffer.
|
|
302
|
+
@param elem The DOM element to check.
|
|
303
|
+
@param buffer Extra pixel margin around the viewport boundary.
|
|
402
304
|
*/ function inViewport(elem, buffer = 0) {
|
|
403
|
-
const pageX = window.
|
|
404
|
-
const pageY = window.
|
|
305
|
+
const pageX = window.scrollX;
|
|
306
|
+
const pageY = window.scrollY;
|
|
405
307
|
const bounds = elem.getBoundingClientRect();
|
|
406
308
|
const height = bounds.height, left = bounds.left + pageX, top = bounds.top + pageY, width = bounds.width;
|
|
407
309
|
return pageY + window.innerHeight > top + buffer && pageY + buffer < top + height && pageX + window.innerWidth > left + buffer && pageX + buffer < left + width;
|
|
408
310
|
}
|
|
409
311
|
|
|
410
312
|
/**
|
|
411
|
-
|
|
412
|
-
@
|
|
413
|
-
@param {String|Number} sides The CSS shorthand string to expand.
|
|
313
|
+
Converts a string of directional CSS shorthand values into an object with the values expanded.
|
|
314
|
+
@param sides The CSS shorthand string to expand.
|
|
414
315
|
*/ function parseSides(sides) {
|
|
415
316
|
let values;
|
|
416
317
|
if (typeof sides === "number") values = [
|
|
417
|
-
sides
|
|
318
|
+
`${sides}`
|
|
418
319
|
];
|
|
419
320
|
else values = sides.split(/\s+/);
|
|
420
321
|
if (values.length === 1) values = [
|
|
@@ -438,32 +339,22 @@
|
|
|
438
339
|
}
|
|
439
340
|
|
|
440
341
|
/**
|
|
441
|
-
|
|
442
|
-
|
|
443
|
-
|
|
444
|
-
if ("-webkit-transform" in document.body.style) return "-webkit-";
|
|
445
|
-
else if ("-moz-transform" in document.body.style) return "-moz-";
|
|
446
|
-
else if ("-ms-transform" in document.body.style) return "-ms-";
|
|
447
|
-
else if ("-o-transform" in document.body.style) return "-o-";
|
|
448
|
-
else return "";
|
|
342
|
+
Returns `true` if the HTML or body element has either the "dir" HTML attribute or the "direction" CSS property set to "rtl".
|
|
343
|
+
*/ function rtl() {
|
|
344
|
+
return document.documentElement.dir === "rtl" || document.body.dir === "rtl" || getComputedStyle(document.documentElement).direction === "rtl" || getComputedStyle(document.body).direction === "rtl";
|
|
449
345
|
}
|
|
450
346
|
|
|
451
347
|
/**
|
|
452
|
-
|
|
453
|
-
@
|
|
454
|
-
|
|
455
|
-
|
|
456
|
-
/**
|
|
457
|
-
@function stylize
|
|
458
|
-
@desc Applies each key/value in an object as a style.
|
|
459
|
-
@param {D3selection} elem The D3 element to apply the styles to.
|
|
460
|
-
@param {Object} styles An object of key/value style pairs.
|
|
348
|
+
Applies each key/value in an object as a style.
|
|
349
|
+
@param e The d3 selection to apply styles to.
|
|
350
|
+
@param s An object of key/value style pairs.
|
|
461
351
|
*/ function stylize(e, s = {}) {
|
|
462
352
|
for(const k in s)if (({}).hasOwnProperty.call(s, k)) e.style(k, s[k]);
|
|
463
353
|
}
|
|
464
354
|
|
|
465
355
|
exports.assign = assign;
|
|
466
356
|
exports.attrize = attrize;
|
|
357
|
+
exports.backgroundColor = backgroundColor;
|
|
467
358
|
exports.date = date;
|
|
468
359
|
exports.elem = elem;
|
|
469
360
|
exports.fontExists = fontExists;
|
|
@@ -471,7 +362,6 @@
|
|
|
471
362
|
exports.inViewport = inViewport;
|
|
472
363
|
exports.isObject = isObject;
|
|
473
364
|
exports.parseSides = parseSides;
|
|
474
|
-
exports.prefix = prefix;
|
|
475
365
|
exports.rtl = rtl;
|
|
476
366
|
exports.stylize = stylize;
|
|
477
367
|
exports.textWidth = textWidth;
|