-
Notifications
You must be signed in to change notification settings - Fork 2
/
FragmentAnchor.js
68 lines (57 loc) · 1.64 KB
/
FragmentAnchor.js
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
export default class FragmentAnchor {
constructor(root, id) {
if (root === undefined) {
throw new Error('missing required parameter "root"');
}
if (id === undefined) {
throw new Error('missing required parameter "id"');
}
this.root = root;
this.id = id;
}
static fromRange(root, range) {
if (root === undefined) {
throw new Error('missing required parameter "root"');
}
if (range === undefined) {
throw new Error('missing required parameter "range"');
}
let el = range.commonAncestorContainer;
while (el != null && !el.id) {
if (root.compareDocumentPosition(el) &
Node.DOCUMENT_POSITION_CONTAINED_BY) {
el = el.parentElement;
} else {
throw new Error('no fragment identifier found');
}
}
return new FragmentAnchor(root, el.id);
}
static fromSelector(root, selector = {}) {
return new FragmentAnchor(root, selector.value);
}
toRange() {
let el = this.root.querySelector('#' + this.id);
if (el == null) {
throw new Error('no element found with id "' + this.id + '"');
}
let range = this.root.ownerDocument.createRange();
range.selectNodeContents(el);
return range;
}
toSelector() {
let el = this.root.querySelector('#' + this.id);
if (el == null) {
throw new Error('no element found with id "' + this.id + '"');
}
let conformsTo = 'https://tools.ietf.org/html/rfc3236';
if (el instanceof SVGElement) {
conformsTo = 'http://www.w3.org/TR/SVG/';
}
return {
type: 'FragmentSelector',
value: this.id,
conformsTo: conformsTo,
};
}
}