@react-x11/components 0.14.0 → 0.16.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/dist/code-editor/node.d.ts +13 -0
- package/dist/code-editor/node.d.ts.map +1 -1
- package/dist/code-editor/node.js +23 -5
- package/dist/code-editor/node.js.map +1 -1
- package/dist/html/css/cascade.d.ts +209 -23
- package/dist/html/css/cascade.d.ts.map +1 -1
- package/dist/html/css/cascade.js +873 -175
- package/dist/html/css/cascade.js.map +1 -1
- package/dist/html/css/color.d.ts +25 -0
- package/dist/html/css/color.d.ts.map +1 -1
- package/dist/html/css/color.js +307 -19
- package/dist/html/css/color.js.map +1 -1
- package/dist/html/css/content.d.ts +11 -6
- package/dist/html/css/content.d.ts.map +1 -1
- package/dist/html/css/content.js +171 -12
- package/dist/html/css/content.js.map +1 -1
- package/dist/html/css/parse.d.ts.map +1 -1
- package/dist/html/css/parse.js +62 -9
- package/dist/html/css/parse.js.map +1 -1
- package/dist/html/css/shapes.d.ts +62 -0
- package/dist/html/css/shapes.d.ts.map +1 -0
- package/dist/html/css/shapes.js +214 -0
- package/dist/html/css/shapes.js.map +1 -0
- package/dist/html/css/style.d.ts +42 -5
- package/dist/html/css/style.d.ts.map +1 -1
- package/dist/html/css/style.js +75 -27
- package/dist/html/css/style.js.map +1 -1
- package/dist/html/css/ua.js +15 -0
- package/dist/html/css/ua.js.map +1 -1
- package/dist/html/css/values.d.ts +5 -0
- package/dist/html/css/values.d.ts.map +1 -1
- package/dist/html/css/values.js +18 -9
- package/dist/html/css/values.js.map +1 -1
- package/dist/html/index.d.ts.map +1 -1
- package/dist/html/index.js +7 -0
- package/dist/html/index.js.map +1 -1
- package/dist/html/layout/block.d.ts +38 -7
- package/dist/html/layout/block.d.ts.map +1 -1
- package/dist/html/layout/block.js +160 -50
- package/dist/html/layout/block.js.map +1 -1
- package/dist/html/layout/boxes.d.ts +29 -2
- package/dist/html/layout/boxes.d.ts.map +1 -1
- package/dist/html/layout/boxes.js +159 -20
- package/dist/html/layout/boxes.js.map +1 -1
- package/dist/html/layout/css-grid.d.ts.map +1 -1
- package/dist/html/layout/css-grid.js +69 -19
- package/dist/html/layout/css-grid.js.map +1 -1
- package/dist/html/layout/flex.d.ts.map +1 -1
- package/dist/html/layout/flex.js +1648 -225
- package/dist/html/layout/flex.js.map +1 -1
- package/dist/html/layout/inline.d.ts +15 -3
- package/dist/html/layout/inline.d.ts.map +1 -1
- package/dist/html/layout/inline.js +23 -8
- package/dist/html/layout/inline.js.map +1 -1
- package/dist/html/layout/table.d.ts +27 -1
- package/dist/html/layout/table.d.ts.map +1 -1
- package/dist/html/layout/table.js +907 -323
- package/dist/html/layout/table.js.map +1 -1
- package/dist/html/node.d.ts +36 -4
- package/dist/html/node.d.ts.map +1 -1
- package/dist/html/node.js +174 -37
- package/dist/html/node.js.map +1 -1
- package/dist/html/paint.d.ts +4 -1
- package/dist/html/paint.d.ts.map +1 -1
- package/dist/html/paint.js +769 -204
- package/dist/html/paint.js.map +1 -1
- package/dist/html/resources.js +14 -1
- package/dist/html/resources.js.map +1 -1
- package/dist/html/svg.d.ts +50 -17
- package/dist/html/svg.d.ts.map +1 -1
- package/dist/html/svg.js +501 -83
- package/dist/html/svg.js.map +1 -1
- package/dist/html/widgets.d.ts.map +1 -1
- package/dist/html/widgets.js +57 -4
- package/dist/html/widgets.js.map +1 -1
- package/package.json +3 -3
- package/src/code-editor/node.ts +24 -5
- package/src/html/css/cascade.ts +987 -176
- package/src/html/css/color.ts +345 -18
- package/src/html/css/content.ts +173 -15
- package/src/html/css/parse.ts +60 -8
- package/src/html/css/shapes.ts +273 -0
- package/src/html/css/style.ts +123 -30
- package/src/html/css/ua.ts +15 -0
- package/src/html/css/values.ts +23 -9
- package/src/html/index.ts +7 -0
- package/src/html/layout/block.ts +169 -56
- package/src/html/layout/boxes.ts +198 -24
- package/src/html/layout/css-grid.ts +89 -22
- package/src/html/layout/flex.ts +1863 -219
- package/src/html/layout/inline.ts +27 -7
- package/src/html/layout/table.ts +989 -333
- package/src/html/node.ts +204 -37
- package/src/html/paint.ts +999 -252
- package/src/html/resources.ts +13 -1
- package/src/html/svg.ts +600 -78
- package/src/html/widgets.ts +61 -4
package/src/html/node.ts
CHANGED
|
@@ -56,10 +56,18 @@ import {
|
|
|
56
56
|
HOVER_PSEUDO_NONE,
|
|
57
57
|
HOVER_PSEUDO_OTHER,
|
|
58
58
|
HOVER_UNTOUCHED,
|
|
59
|
+
NO_FOCUS,
|
|
60
|
+
} from './css/cascade.js';
|
|
61
|
+
import type {
|
|
62
|
+
FocusState,
|
|
63
|
+
HoverTouch,
|
|
64
|
+
KeptStyles,
|
|
65
|
+
MetricFace,
|
|
66
|
+
PointerState,
|
|
59
67
|
} from './css/cascade.js';
|
|
60
|
-
import type { HoverTouch, KeptStyles, MetricFace } from './css/cascade.js';
|
|
61
68
|
import { mediaMatches, parseStylesheet } from './css/parse.js';
|
|
62
69
|
import type { MediaCondition, Stylesheet } from './css/parse.js';
|
|
70
|
+
import type { ShapeStyles } from './css/shapes.js';
|
|
63
71
|
import { uaStylesheet } from './css/ua.js';
|
|
64
72
|
import type { ComputedStyle, RootLook } from './css/style.js';
|
|
65
73
|
import {
|
|
@@ -74,6 +82,7 @@ import {
|
|
|
74
82
|
GENERATED_FROM,
|
|
75
83
|
INLINE_OFFSETS,
|
|
76
84
|
LINE_BOX_RAISES,
|
|
85
|
+
SHAPE_STYLES,
|
|
77
86
|
SHIFTED_LINES,
|
|
78
87
|
TEXT_SHIFTS,
|
|
79
88
|
columned,
|
|
@@ -127,7 +136,7 @@ import {
|
|
|
127
136
|
stacksLayers,
|
|
128
137
|
} from './paint.js';
|
|
129
138
|
import type { PaintContext } from './paint.js';
|
|
130
|
-
import { controlRectsOf, measureControl } from './controls.js';
|
|
139
|
+
import { controlRectsOf, measureControl, styledField } from './controls.js';
|
|
131
140
|
import type { BareField, ControlRect } from './controls.js';
|
|
132
141
|
import { ResourceStore } from './resources.js';
|
|
133
142
|
import type { ResourceRequest, ResourceResult } from './resources.js';
|
|
@@ -288,6 +297,8 @@ export class HtmlViewNode extends Node {
|
|
|
288
297
|
* the text carries surrogate pairs. null until checked. */
|
|
289
298
|
private _pointsAreUnits: boolean | null = null;
|
|
290
299
|
private _hovered: Element[] = [];
|
|
300
|
+
/** Which element's widget holds the focus (`setFocus`). */
|
|
301
|
+
private _focus: FocusState = NO_FOCUS;
|
|
291
302
|
/** Where the pointer last moved to, in logical window pixels, while it
|
|
292
303
|
* is over the element (`defaultMouseMove`). */
|
|
293
304
|
private _pointerAt: { x: number; y: number } | null = null;
|
|
@@ -400,6 +411,12 @@ export class HtmlViewNode extends Node {
|
|
|
400
411
|
controlBorder: look.controlBorder * s,
|
|
401
412
|
controlRadius: look.controlRadius * s,
|
|
402
413
|
controlFontSize: (look.controlFontSize ?? look.fontSize) * s,
|
|
414
|
+
...(look.focusRingWidth !== undefined && {
|
|
415
|
+
focusRingWidth: look.focusRingWidth * s,
|
|
416
|
+
}),
|
|
417
|
+
...(look.focusRingOffset !== undefined && {
|
|
418
|
+
focusRingOffset: look.focusRingOffset * s,
|
|
419
|
+
}),
|
|
403
420
|
};
|
|
404
421
|
this._deviceLookFor = look;
|
|
405
422
|
this._deviceLookAt = s;
|
|
@@ -709,6 +726,7 @@ export class HtmlViewNode extends Node {
|
|
|
709
726
|
hovered: new Set(this._hovered),
|
|
710
727
|
active: EMPTY_SET,
|
|
711
728
|
});
|
|
729
|
+
this._cascade.setFocus(this._focus);
|
|
712
730
|
this._mediaBand = this._cascade.mediaBand(width);
|
|
713
731
|
}
|
|
714
732
|
|
|
@@ -1029,6 +1047,10 @@ export class HtmlViewNode extends Node {
|
|
|
1029
1047
|
scale: this._scale,
|
|
1030
1048
|
imageSize: (el) => this._resources.imageSize(imageUrlOf(el) ?? ''),
|
|
1031
1049
|
urlSize: (url) => this._resources.imageSize(url),
|
|
1050
|
+
faceAscent: (style) => {
|
|
1051
|
+
const fonts = this._fonts();
|
|
1052
|
+
return fonts ? faceExtentOf(fonts, style).ascent : undefined;
|
|
1053
|
+
},
|
|
1032
1054
|
controlSize: (el, kind, style) =>
|
|
1033
1055
|
measureControl(el, kind, style, this._fonts(), look),
|
|
1034
1056
|
});
|
|
@@ -1537,37 +1559,120 @@ export class HtmlViewNode extends Node {
|
|
|
1537
1559
|
* with the styles of every element the move did not reach kept.
|
|
1538
1560
|
*/
|
|
1539
1561
|
private _restyleHover(was: readonly Element[], now: readonly Element[]) {
|
|
1562
|
+
const cascade = this._cascade;
|
|
1540
1563
|
const reach = this._hoverReach(was, now);
|
|
1541
|
-
if (reach !== null) {
|
|
1564
|
+
if (reach !== null && cascade) {
|
|
1542
1565
|
if (!reach.size) return;
|
|
1543
|
-
|
|
1566
|
+
const before = { hovered: new Set(was), active: EMPTY_SET };
|
|
1567
|
+
if (this._hoverInPlace(reach, before, this._focus, cascade.hoverPseudo)) {
|
|
1568
|
+
return;
|
|
1569
|
+
}
|
|
1544
1570
|
}
|
|
1545
1571
|
this._invalidate(Stale.Boxes, reach);
|
|
1546
1572
|
}
|
|
1547
1573
|
|
|
1574
|
+
/** The element whose widget holds the focus, or null (`setFocus`). */
|
|
1575
|
+
get focusedElement(): Element | null {
|
|
1576
|
+
return this._focus.element;
|
|
1577
|
+
}
|
|
1578
|
+
|
|
1579
|
+
/**
|
|
1580
|
+
* The focus moved: `element`'s widget took it, or, given null, no widget
|
|
1581
|
+
* of this document holds it now — it went to something else in the
|
|
1582
|
+
* window, or nowhere. `visible` is whether it shows, `:focus-visible`,
|
|
1583
|
+
* which it always does in a text field. Restyles what `:focus` and its
|
|
1584
|
+
* kin reach as a hover does (`_restyleHover`), and returns whether the
|
|
1585
|
+
* cascade's answer could have changed.
|
|
1586
|
+
*
|
|
1587
|
+
* No element of a document takes the focus: a control's widget, mounted
|
|
1588
|
+
* beside it, does, and says so here. Only a text field's does, so far —
|
|
1589
|
+
* the widgets core draws as components keep their own focus to
|
|
1590
|
+
* themselves.
|
|
1591
|
+
*/
|
|
1592
|
+
setFocus(element: Element | null, visible = true): boolean {
|
|
1593
|
+
const was = this._focus;
|
|
1594
|
+
if (was.element === element && (!element || was.visible === visible)) {
|
|
1595
|
+
return false;
|
|
1596
|
+
}
|
|
1597
|
+
const within = new Set<Element>();
|
|
1598
|
+
for (
|
|
1599
|
+
let at: Element | null = element;
|
|
1600
|
+
at;
|
|
1601
|
+
at = isElement(at.parent) ? at.parent : null
|
|
1602
|
+
) {
|
|
1603
|
+
within.add(at);
|
|
1604
|
+
}
|
|
1605
|
+
const now: FocusState = element ? { element, visible, within } : NO_FOCUS;
|
|
1606
|
+
this._focus = now;
|
|
1607
|
+
const cascade = this._cascade;
|
|
1608
|
+
cascade?.setFocus(now);
|
|
1609
|
+
if (!cascade || !cascade.focusSensitive) return false;
|
|
1610
|
+
const reach = cascade.focusLocal
|
|
1611
|
+
? this._stateReach(
|
|
1612
|
+
[...was.within],
|
|
1613
|
+
[...now.within],
|
|
1614
|
+
// one element, whose ring came or went
|
|
1615
|
+
was.element === element ? element : null,
|
|
1616
|
+
(el) => cascade.focusTouches(el),
|
|
1617
|
+
(el, into) => cascade.focusAnchors(el, into),
|
|
1618
|
+
)
|
|
1619
|
+
: null;
|
|
1620
|
+
if (reach !== null) {
|
|
1621
|
+
if (!reach.size) return true;
|
|
1622
|
+
const pointer = { hovered: new Set(this._hovered), active: EMPTY_SET };
|
|
1623
|
+
if (this._hoverInPlace(reach, pointer, was, cascade.focusPseudo)) {
|
|
1624
|
+
return true;
|
|
1625
|
+
}
|
|
1626
|
+
}
|
|
1627
|
+
this._invalidate(Stale.Boxes, reach);
|
|
1628
|
+
return true;
|
|
1629
|
+
}
|
|
1630
|
+
|
|
1548
1631
|
/**
|
|
1549
1632
|
* The elements whose styles a move of the hovered chain can change, or
|
|
1550
1633
|
* null where that cannot be said (`Cascade.hoverLocal`).
|
|
1634
|
+
*/
|
|
1635
|
+
private _hoverReach(
|
|
1636
|
+
was: readonly Element[],
|
|
1637
|
+
now: readonly Element[],
|
|
1638
|
+
): Set<Element> | null {
|
|
1639
|
+
const cascade = this._cascade;
|
|
1640
|
+
if (!cascade || !cascade.hoverLocal) return null;
|
|
1641
|
+
return this._stateReach(
|
|
1642
|
+
was,
|
|
1643
|
+
now,
|
|
1644
|
+
null,
|
|
1645
|
+
(el) => cascade.hoverTouches(el),
|
|
1646
|
+
(el, into) => cascade.hoverAnchors(el, into),
|
|
1647
|
+
);
|
|
1648
|
+
}
|
|
1649
|
+
|
|
1650
|
+
/**
|
|
1651
|
+
* The elements whose styles a move of the hovered chain can change, or
|
|
1652
|
+
* of the focus's chain.
|
|
1551
1653
|
*
|
|
1552
1654
|
* Only an element whose hover state flipped and that a compound testing
|
|
1553
1655
|
* the pointer could match can change (`Cascade.hoverTouches`), with its
|
|
1554
1656
|
* subtree, and its later siblings' where a sibling combinator is in play;
|
|
1555
1657
|
* and the elements a `:has()` testing the pointer may flip, which are
|
|
1556
1658
|
* around the ones that changed. A move between two paragraphs under
|
|
1557
|
-
* `a:hover` reaches nothing.
|
|
1659
|
+
* `a:hover` reaches nothing. The focus's the same way, its chain the
|
|
1660
|
+
* focused element and every element around it, and `also` one whose
|
|
1661
|
+
* state flipped though it is in both — the ring coming or going.
|
|
1558
1662
|
*/
|
|
1559
|
-
private
|
|
1663
|
+
private _stateReach(
|
|
1560
1664
|
was: readonly Element[],
|
|
1561
1665
|
now: readonly Element[],
|
|
1562
|
-
|
|
1563
|
-
|
|
1564
|
-
|
|
1666
|
+
also: Element | null,
|
|
1667
|
+
touches: (el: Element) => HoverTouch,
|
|
1668
|
+
anchors: (el: Element, into: Map<Element, HoverTouch>) => void,
|
|
1669
|
+
): Set<Element> {
|
|
1565
1670
|
const before = new Set(was);
|
|
1566
1671
|
const after = new Set(now);
|
|
1567
1672
|
const roots = new Map<Element, HoverTouch>();
|
|
1568
|
-
const flipped = (el: Element, other: Set<Element>): void => {
|
|
1569
|
-
if (other
|
|
1570
|
-
const touch =
|
|
1673
|
+
const flipped = (el: Element, other: Set<Element> | null): void => {
|
|
1674
|
+
if (other?.has(el)) return;
|
|
1675
|
+
const touch = touches(el);
|
|
1571
1676
|
if (touch > (roots.get(el) ?? HOVER_UNTOUCHED)) roots.set(el, touch);
|
|
1572
1677
|
};
|
|
1573
1678
|
for (const el of was) flipped(el, after);
|
|
@@ -1576,10 +1681,14 @@ export class HtmlViewNode extends Node {
|
|
|
1576
1681
|
// side is where a `:has()` is looked for from
|
|
1577
1682
|
const deepest = (chain: readonly Element[], other: Set<Element>) => {
|
|
1578
1683
|
const el = chain[0];
|
|
1579
|
-
if (el && !other.has(el))
|
|
1684
|
+
if (el && !other.has(el)) anchors(el, roots);
|
|
1580
1685
|
};
|
|
1581
1686
|
deepest(was, after);
|
|
1582
1687
|
deepest(now, before);
|
|
1688
|
+
if (also) {
|
|
1689
|
+
flipped(also, null);
|
|
1690
|
+
anchors(also, roots);
|
|
1691
|
+
}
|
|
1583
1692
|
|
|
1584
1693
|
// the roots' subtrees, which inherit from them and a descendant
|
|
1585
1694
|
// combinator reaches, and their later siblings' too where a sibling
|
|
@@ -1624,8 +1733,10 @@ export class HtmlViewNode extends Node {
|
|
|
1624
1733
|
* - The boxes take their new styles: an element's own, the text in it,
|
|
1625
1734
|
* the anonymous boxes the fix-up made around what is in it, and its
|
|
1626
1735
|
* `::before` and `::after`, styled again by their own rules. A box
|
|
1627
|
-
* whose style is derived some other way — a marker, a first letter
|
|
1628
|
-
*
|
|
1736
|
+
* whose style is derived some other way — a marker, a first letter —
|
|
1737
|
+
* is not one to restyle here. A control's is, and its widget is told
|
|
1738
|
+
* (`_reportControls`), unless the page took to drawing the field or
|
|
1739
|
+
* stopped.
|
|
1629
1740
|
* - Each layout of their text is made again from the runs it was made
|
|
1630
1741
|
* from (`TextLayoutCache.inputsOf`) with the new ink (`runFor`), where
|
|
1631
1742
|
* its geometry comes out the same.
|
|
@@ -1635,10 +1746,16 @@ export class HtmlViewNode extends Node {
|
|
|
1635
1746
|
* costs what it changed, in a document of any length. True where it was
|
|
1636
1747
|
* restyled here, or had nothing to restyle; false where the boxes have to
|
|
1637
1748
|
* be built again.
|
|
1749
|
+
*
|
|
1750
|
+
* A focus change is answered the same way (`setFocus`): `before` and
|
|
1751
|
+
* `beforeFocus` are the states the change was from, and `pseudoRules`
|
|
1752
|
+
* which pseudo-elements' rules test the state that changed.
|
|
1638
1753
|
*/
|
|
1639
1754
|
private _hoverInPlace(
|
|
1640
1755
|
reach: ReadonlySet<Element>,
|
|
1641
|
-
|
|
1756
|
+
before: PointerState,
|
|
1757
|
+
beforeFocus: FocusState,
|
|
1758
|
+
pseudoRules: 0 | 1 | 2,
|
|
1642
1759
|
): boolean {
|
|
1643
1760
|
const cascade = this._cascade;
|
|
1644
1761
|
const tree = this._tree;
|
|
@@ -1647,17 +1764,15 @@ export class HtmlViewNode extends Node {
|
|
|
1647
1764
|
if (this._stale !== Stale.Nothing || this._laidOutWidth < 0) return false;
|
|
1648
1765
|
if (reach.size > HOVER_RESTYLE_LIMIT) return false;
|
|
1649
1766
|
// a first line's, a first letter's and a marker's styles are layout's
|
|
1650
|
-
const pseudoRules = cascade.hoverPseudo;
|
|
1651
1767
|
if (pseudoRules === HOVER_PSEUDO_OTHER) return false;
|
|
1652
1768
|
|
|
1653
|
-
// whether the rules that test the pointer
|
|
1654
|
-
// element than they did before the
|
|
1655
|
-
const before = { hovered: new Set(was), active: EMPTY_SET };
|
|
1769
|
+
// whether the rules that test the pointer or the focus answer
|
|
1770
|
+
// differently for an element than they did before the change
|
|
1656
1771
|
const flips = new Map<Element, boolean>();
|
|
1657
1772
|
const flipped = (el: Element): boolean => {
|
|
1658
1773
|
let flip = flips.get(el);
|
|
1659
1774
|
if (flip === undefined) {
|
|
1660
|
-
flip = cascade.pointerChanged(el, before);
|
|
1775
|
+
flip = cascade.pointerChanged(el, before, beforeFocus);
|
|
1661
1776
|
flips.set(el, flip);
|
|
1662
1777
|
}
|
|
1663
1778
|
return flip;
|
|
@@ -1675,6 +1790,8 @@ export class HtmlViewNode extends Node {
|
|
|
1675
1790
|
let reaches = false;
|
|
1676
1791
|
let reorders = false;
|
|
1677
1792
|
const moving = new Set<Element>();
|
|
1793
|
+
/** Whether a control's box was restyled: its widget is told. */
|
|
1794
|
+
let widgets = false;
|
|
1678
1795
|
const styleOf = (el: Element): ComputedStyle | null => {
|
|
1679
1796
|
const kept = tree.styles.get(el);
|
|
1680
1797
|
if (!kept) return null;
|
|
@@ -1711,7 +1828,39 @@ export class HtmlViewNode extends Node {
|
|
|
1711
1828
|
styleOf(el);
|
|
1712
1829
|
if (refused) return false;
|
|
1713
1830
|
}
|
|
1714
|
-
|
|
1831
|
+
// The drawings the move reached. What the rules give the shapes in one
|
|
1832
|
+
// is no box's style (`BoxTree.shapeStyler`), so it is asked for again:
|
|
1833
|
+
// of a drawing whose own style changed — its colour, a custom property
|
|
1834
|
+
// — and of each where a rule that reaches into a drawing tests the
|
|
1835
|
+
// pointer, `a:hover svg path`. One with another answer is painted
|
|
1836
|
+
// again; one never painted has none yet, and asks when it is.
|
|
1837
|
+
const redrawn: [Box, ShapeStyles | null][] = [];
|
|
1838
|
+
if (tree.shapeStyler) {
|
|
1839
|
+
for (const el of reach) {
|
|
1840
|
+
if (tagOf(el) !== 'svg') continue;
|
|
1841
|
+
const style = fresh.get(el);
|
|
1842
|
+
if (!style) continue;
|
|
1843
|
+
if (!changed.has(el) && !cascade.shapesFollowPointer) continue;
|
|
1844
|
+
const box = this._firstBoxesOf(tree).get(el);
|
|
1845
|
+
const was = box && SHAPE_STYLES.get(box);
|
|
1846
|
+
if (!box || was === undefined) continue;
|
|
1847
|
+
const shapes = cascade.shapeStyles(el, style, tree.shapeCopies);
|
|
1848
|
+
if (shapes?.key !== was?.key) redrawn.push([box, shapes]);
|
|
1849
|
+
}
|
|
1850
|
+
}
|
|
1851
|
+
const redraw = (): Rect[] => {
|
|
1852
|
+
const inks: Rect[] = [];
|
|
1853
|
+
for (const [box, shapes] of redrawn) {
|
|
1854
|
+
SHAPE_STYLES.set(box, shapes);
|
|
1855
|
+
const ink = inkOf(box);
|
|
1856
|
+
if (ink) inks.push(ink);
|
|
1857
|
+
}
|
|
1858
|
+
return inks;
|
|
1859
|
+
};
|
|
1860
|
+
if (!changed.size && pseudoRules === HOVER_PSEUDO_NONE) {
|
|
1861
|
+
this._repaintInk(redraw());
|
|
1862
|
+
return true;
|
|
1863
|
+
}
|
|
1715
1864
|
for (const el of changed.keys()) {
|
|
1716
1865
|
const tag = tagOf(el);
|
|
1717
1866
|
// their backgrounds are the canvas's
|
|
@@ -1786,11 +1935,20 @@ export class HtmlViewNode extends Node {
|
|
|
1786
1935
|
if (!style) continue;
|
|
1787
1936
|
const kept = tree.styles.get(el)!.style;
|
|
1788
1937
|
// a style derived from the element's, or drawn from it somewhere
|
|
1789
|
-
// else
|
|
1790
|
-
// it
|
|
1791
|
-
//
|
|
1938
|
+
// else. A widget mounted beside the document takes its look from
|
|
1939
|
+
// it, and is told again once it is restyled — unless the page took
|
|
1940
|
+
// to drawing the field, or stopped, which is another size of box.
|
|
1941
|
+
// An image, a drawing or a rule is drawn here, from its box, like
|
|
1942
|
+
// any.
|
|
1792
1943
|
if (box.style !== kept) return false;
|
|
1793
|
-
if (box.marker
|
|
1944
|
+
if (box.marker) return false;
|
|
1945
|
+
if (WIDGETS.has(box.replaced)) {
|
|
1946
|
+
const kind = box.replaced!;
|
|
1947
|
+
if (styledField(kind, kept) !== styledField(kind, style)) {
|
|
1948
|
+
return false;
|
|
1949
|
+
}
|
|
1950
|
+
widgets = true;
|
|
1951
|
+
}
|
|
1794
1952
|
if (moving.has(el) && !movable(box, kept, style)) return false;
|
|
1795
1953
|
ink = !quiet.has(el);
|
|
1796
1954
|
} else if (above) {
|
|
@@ -1830,7 +1988,10 @@ export class HtmlViewNode extends Node {
|
|
|
1830
1988
|
}
|
|
1831
1989
|
}
|
|
1832
1990
|
}
|
|
1833
|
-
if (!restyled.length)
|
|
1991
|
+
if (!restyled.length) {
|
|
1992
|
+
this._repaintInk(redraw());
|
|
1993
|
+
return true;
|
|
1994
|
+
}
|
|
1834
1995
|
|
|
1835
1996
|
// the text: each layout holding a run of a restyled box's, made again
|
|
1836
1997
|
// with its new ink, where it comes out the same shape
|
|
@@ -1883,6 +2044,7 @@ export class HtmlViewNode extends Node {
|
|
|
1883
2044
|
for (const [el, style] of changed) {
|
|
1884
2045
|
tree.styles.set(el, { style, inFlex: tree.styles.get(el)!.inFlex });
|
|
1885
2046
|
}
|
|
2047
|
+
for (const ink of redraw()) inks.push(ink);
|
|
1886
2048
|
// A box that moved moves what is in it, as layout moved it the first
|
|
1887
2049
|
// time (`applyRelativeOffsets`), and a later layout moves it the same
|
|
1888
2050
|
// way; where it reached the document's end, before or after, the
|
|
@@ -1906,7 +2068,7 @@ export class HtmlViewNode extends Node {
|
|
|
1906
2068
|
relayout = true;
|
|
1907
2069
|
}
|
|
1908
2070
|
}
|
|
1909
|
-
if (moved.length) this._reportControls();
|
|
2071
|
+
if (moved.length || widgets) this._reportControls();
|
|
1910
2072
|
if (relayout) {
|
|
1911
2073
|
this._invalidate(Stale.Layout);
|
|
1912
2074
|
return true;
|
|
@@ -1923,14 +2085,7 @@ export class HtmlViewNode extends Node {
|
|
|
1923
2085
|
* of: made on the first move over a tree, which is one walk of it. */
|
|
1924
2086
|
private _firstBoxes: { tree: BoxTree; of: Map<Element, Box> } | null = null;
|
|
1925
2087
|
|
|
1926
|
-
|
|
1927
|
-
* The blocks a restyle of `changed` has to look in: for each element, the
|
|
1928
|
-
* box its text is set in the lines of — the nearest box around its first
|
|
1929
|
-
* that is not an inline one — which holds every box that takes its style
|
|
1930
|
-
* from it, the pieces a block in it broke it into among them
|
|
1931
|
-
* (`breakAround`). One that is inside another is left to it.
|
|
1932
|
-
*/
|
|
1933
|
-
private _blocksOf(tree: BoxTree, changed: Iterable<Element>): Box[] {
|
|
2088
|
+
private _firstBoxesOf(tree: BoxTree): Map<Element, Box> {
|
|
1934
2089
|
let index = this._firstBoxes;
|
|
1935
2090
|
if (index?.tree !== tree) {
|
|
1936
2091
|
const of = new Map<Element, Box>();
|
|
@@ -1944,9 +2099,21 @@ export class HtmlViewNode extends Node {
|
|
|
1944
2099
|
}
|
|
1945
2100
|
index = this._firstBoxes = { tree, of };
|
|
1946
2101
|
}
|
|
2102
|
+
return index.of;
|
|
2103
|
+
}
|
|
2104
|
+
|
|
2105
|
+
/**
|
|
2106
|
+
* The blocks a restyle of `changed` has to look in: for each element, the
|
|
2107
|
+
* box its text is set in the lines of — the nearest box around its first
|
|
2108
|
+
* that is not an inline one — which holds every box that takes its style
|
|
2109
|
+
* from it, the pieces a block in it broke it into among them
|
|
2110
|
+
* (`breakAround`). One that is inside another is left to it.
|
|
2111
|
+
*/
|
|
2112
|
+
private _blocksOf(tree: BoxTree, changed: Iterable<Element>): Box[] {
|
|
2113
|
+
const first = this._firstBoxesOf(tree);
|
|
1947
2114
|
const blocks = new Set<Box>();
|
|
1948
2115
|
for (const el of changed) {
|
|
1949
|
-
let box: Box | null =
|
|
2116
|
+
let box: Box | null = first.get(el) ?? null;
|
|
1950
2117
|
while (
|
|
1951
2118
|
box?.parent &&
|
|
1952
2119
|
(box.kind === 'inline' || box.kind === 'text' || box.kind === 'break')
|