ntk 3.7.0 → 3.7.2
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/lib/renderingcontext_2d.js +34 -1
- package/lib/text/layout.js +6 -1
- package/lib/widgets/tex.js +5 -4
- package/package.json +1 -1
|
@@ -17,7 +17,7 @@ import {
|
|
|
17
17
|
} from './path.js';
|
|
18
18
|
import Picture from './picture.js';
|
|
19
19
|
import Pixmap from './pixmap.js';
|
|
20
|
-
import { drawGlyphRuns } from './text/glyphs.js';
|
|
20
|
+
import { compositeTraps, drawGlyphRuns } from './text/glyphs.js';
|
|
21
21
|
import { TextLayout } from './text/layout.js';
|
|
22
22
|
import { reorderRuns } from './text/shape.js';
|
|
23
23
|
import { trapezoidize } from './trapezoid.js';
|
|
@@ -810,6 +810,39 @@ class RenderingContext2d {
|
|
|
810
810
|
this._markDirty();
|
|
811
811
|
}
|
|
812
812
|
|
|
813
|
+
/**
|
|
814
|
+
* Trapezoid coverage under the clip — `drawGlyphs` for vector shapes that
|
|
815
|
+
* are already trapezoidized (KaTeX radicals and rules go this way).
|
|
816
|
+
* Without it they composite straight to the destination picture and spill
|
|
817
|
+
* out of clipped boxes, which is what glyphs used to do.
|
|
818
|
+
*/
|
|
819
|
+
drawTraps(op, src, traps) {
|
|
820
|
+
if (!traps.length) return;
|
|
821
|
+
const app = this.window.app;
|
|
822
|
+
const R = this.Render;
|
|
823
|
+
if (!this.clipMask) {
|
|
824
|
+
compositeTraps(app, op, src.id, this.picture.id, traps);
|
|
825
|
+
this._markDirty();
|
|
826
|
+
return;
|
|
827
|
+
}
|
|
828
|
+
const rect = this._clipRect();
|
|
829
|
+
if (rect) {
|
|
830
|
+
if (rect.w === 0 || rect.h === 0) return;
|
|
831
|
+
R.SetPictureClipRectangles(this.picture.id, 0, 0, [rect.x, rect.y, rect.w, rect.h]);
|
|
832
|
+
compositeTraps(app, op, src.id, this.picture.id, traps);
|
|
833
|
+
R.SetPictureClipRectangles(this.picture.id, 0, 0, [0, 0, this.width, this.height]);
|
|
834
|
+
this._markDirty();
|
|
835
|
+
return;
|
|
836
|
+
}
|
|
837
|
+
this._ensureFillMask();
|
|
838
|
+
this._glyphSource ??= this.createSolidPicture(1, 1, 1, 1);
|
|
839
|
+
R.FillRectangles(R.PictOp.Src, this.fillMask.id, [0, 0, 0, 0], [0, 0, this.width, this.height]);
|
|
840
|
+
compositeTraps(app, R.PictOp.Over, this._glyphSource.id, this.fillMask.id, traps);
|
|
841
|
+
R.Composite(R.PictOp.In, this.clipMask.id, 0, this.fillMask.id, 0, 0, 0, 0, 0, 0, this.width, this.height);
|
|
842
|
+
R.Composite(op, src.id, this.fillMask.id, this.picture.id, 0, 0, 0, 0, 0, 0, this.width, this.height);
|
|
843
|
+
this._markDirty();
|
|
844
|
+
}
|
|
845
|
+
|
|
813
846
|
// combined clip ∩ globalAlpha mask for direct composites (rect/image
|
|
814
847
|
// fast paths); returns a picture id or 0. Reuses the fill scratch mask.
|
|
815
848
|
_compositeMask() {
|
package/lib/text/layout.js
CHANGED
|
@@ -47,7 +47,12 @@ export class TextLayout {
|
|
|
47
47
|
// ---- normalize spans, resolve fonts eagerly ----
|
|
48
48
|
// unknown span fields ride along untouched (widgets attach markers like
|
|
49
49
|
// MarkdownView's _deco/_href and read them back from line runs)
|
|
50
|
-
|
|
50
|
+
// An empty span list is a legitimate thing to lay out — MarkdownView
|
|
51
|
+
// reaches it for a blank paragraph while a document is being typed —
|
|
52
|
+
// and every line still needs a style to take its metrics from, so
|
|
53
|
+
// stand one in rather than crashing on the first empty line.
|
|
54
|
+
const given = typeof content === 'string' ? [{ text: content }] : content;
|
|
55
|
+
const spans = (given.length ? given : [{ text: '' }]).map((s) => {
|
|
51
56
|
const merged = {
|
|
52
57
|
...s,
|
|
53
58
|
text: String(s.text ?? ''),
|
package/lib/widgets/tex.js
CHANGED
|
@@ -22,7 +22,6 @@ import { parseSvgPath } from '../path.js';
|
|
|
22
22
|
import { flatten } from '../rasterize.js';
|
|
23
23
|
import { trapezoidize } from '../trapezoid.js';
|
|
24
24
|
import Font from '../text/font.js';
|
|
25
|
-
import { compositeTraps, drawGlyphRuns } from '../text/glyphs.js';
|
|
26
25
|
|
|
27
26
|
// node builtins are fetched lazily so browser bundles never resolve them;
|
|
28
27
|
// there, inject the assets with configureTex() instead.
|
|
@@ -571,7 +570,7 @@ export class TexBox {
|
|
|
571
570
|
Render.Composite(
|
|
572
571
|
Render.PictOp.Over,
|
|
573
572
|
src.id,
|
|
574
|
-
ctx.
|
|
573
|
+
ctx._compositeMask(),
|
|
575
574
|
ctx.picture.id,
|
|
576
575
|
Math.round(x + item.x),
|
|
577
576
|
Math.round(base + item.y),
|
|
@@ -598,7 +597,9 @@ export class TexBox {
|
|
|
598
597
|
}
|
|
599
598
|
trapezoidize([clipped], x + item.x, base + item.y, traps);
|
|
600
599
|
}
|
|
601
|
-
|
|
600
|
+
// through the context, so the clip applies — compositing straight to
|
|
601
|
+
// ctx.picture spills out of scrollviews and clipped boxes
|
|
602
|
+
ctx.drawTraps(Render.PictOp.Over, src, traps);
|
|
602
603
|
}
|
|
603
604
|
|
|
604
605
|
// batch every run of the same color into a single CompositeGlyphs
|
|
@@ -612,7 +613,7 @@ export class TexBox {
|
|
|
612
613
|
}
|
|
613
614
|
for (const { color, runs } of byColor.values()) {
|
|
614
615
|
const src = color ? ctx._stylePicture(color) : ctx._backgroundPicture;
|
|
615
|
-
|
|
616
|
+
ctx.drawGlyphs(Render.PictOp.Over, src, runs);
|
|
616
617
|
}
|
|
617
618
|
|
|
618
619
|
ctx._markDirty();
|