@jbrowse/svgcanvas 6.5.0 → 7.0.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.
@@ -0,0 +1,67 @@
1
+ // @vitest-environment jsdom
2
+ import { beforeAll, expect, test } from 'vitest';
3
+ import { Context } from './index.js';
4
+ class Matrix {
5
+ m;
6
+ constructor(m = [1, 0, 0, 1, 0, 0]) {
7
+ this.m = m;
8
+ }
9
+ get a() {
10
+ return this.m[0];
11
+ }
12
+ get b() {
13
+ return this.m[1];
14
+ }
15
+ get c() {
16
+ return this.m[2];
17
+ }
18
+ get d() {
19
+ return this.m[3];
20
+ }
21
+ get e() {
22
+ return this.m[4];
23
+ }
24
+ get f() {
25
+ return this.m[5];
26
+ }
27
+ multiply(o) {
28
+ return new Matrix([
29
+ this.a * o.a + this.c * o.b,
30
+ this.b * o.a + this.d * o.b,
31
+ this.a * o.c + this.c * o.d,
32
+ this.b * o.c + this.d * o.d,
33
+ this.a * o.e + this.c * o.f + this.e,
34
+ this.b * o.e + this.d * o.f + this.f,
35
+ ]);
36
+ }
37
+ translate(x, y = 0) {
38
+ return this.multiply(new Matrix([1, 0, 0, 1, x, y]));
39
+ }
40
+ scale(x, y = x) {
41
+ return this.multiply(new Matrix([x, 0, 0, y, 0, 0]));
42
+ }
43
+ }
44
+ beforeAll(() => {
45
+ globalThis.DOMMatrix = Matrix;
46
+ });
47
+ test('a fill covering the whole context paints over, it does not clear', () => {
48
+ const ctx = new Context(100, 50);
49
+ ctx.fillStyle = '#123456';
50
+ ctx.fillRect(0, 0, 10, 10);
51
+ ctx.fillText('A', 1, 1);
52
+ // a full-width highlight band is exactly this call, and it used to throw the
53
+ // drawing away
54
+ ctx.fillStyle = 'rgba(255,140,0,0.28)';
55
+ ctx.fillRect(0, 0, 100, 50);
56
+ const svg = ctx.getSvg().innerHTML;
57
+ expect(svg).toContain('>A<');
58
+ expect(svg).toContain('#123456');
59
+ expect(svg).toContain('fill-opacity="0.28"');
60
+ });
61
+ test('clearRect over the whole context still clears it', () => {
62
+ const ctx = new Context(100, 50);
63
+ ctx.fillText('A', 1, 1);
64
+ ctx.clearRect(0, 0, 100, 50);
65
+ expect(ctx.getSvg().innerHTML).not.toContain('>A<');
66
+ });
67
+ //# sourceMappingURL=context.test.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"context.test.js","sourceRoot":"","sources":["../src/context.test.ts"],"names":[],"mappings":"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"}
package/dist/index.d.ts CHANGED
@@ -9,33 +9,24 @@
9
9
  * Copyright (c) 2014 Gliffy Inc.
10
10
  * Copyright (c) 2021 Zeno Zeng
11
11
  *
12
- * Vendored and converted to ESM/TypeScript for pure ESM compatibility.
12
+ * Vendored and converted to ESM/TypeScript for pure ESM compatibility, and cut
13
+ * down to the drawing calls the renderers make: what a multiple sequence
14
+ * alignment needs is rectangles, paths, arcs and a great many glyphs. Gradients,
15
+ * patterns, clipping, rotation, bezier curves, stroked text, shadows and image
16
+ * drawing are gone with the state they carried.
13
17
  */
14
- declare class CanvasGradient {
15
- __root: SVGElement;
16
- __ctx: Context;
17
- constructor(gradientNode: SVGElement, ctx: Context);
18
- addColorStop(offset: number, color: string): void;
19
- }
20
18
  interface ContextOptions {
21
- width?: number;
22
- height?: number;
23
- enableMirroring?: boolean;
24
19
  document?: Document;
25
20
  ctx?: CanvasRenderingContext2D;
26
- debug?: boolean;
27
21
  }
28
22
  export declare class Context {
29
23
  width: number;
30
24
  height: number;
31
- enableMirroring: boolean;
32
25
  canvas: Context;
33
26
  __document: Document;
34
27
  __ctx: CanvasRenderingContext2D;
35
28
  __canvas?: HTMLCanvasElement;
36
29
  __root: SVGSVGElement;
37
- __ids: Record<string, string>;
38
- __defs: SVGDefsElement;
39
30
  __currentElement: SVGElement;
40
31
  __styleStack: any[];
41
32
  __groupStack: SVGElement[];
@@ -46,38 +37,27 @@ export declare class Context {
46
37
  };
47
38
  __transformMatrix: DOMMatrix;
48
39
  __transformMatrixStack?: DOMMatrix[];
49
- __currentElementsToStyle?: {
50
- element: SVGElement;
51
- children: SVGElement[];
52
- };
53
- __options: ContextOptions;
54
- __id: string;
55
- __fontUnderline?: string;
56
- __fontHref?: string;
40
+ __fontCache: Map<string, CSSStyleDeclaration>;
57
41
  strokeStyle: any;
58
42
  fillStyle: any;
59
- lineCap: any;
60
- lineJoin: any;
61
- miterLimit: any;
62
43
  lineWidth: any;
63
- globalAlpha: any;
64
44
  font: any;
65
- shadowColor: any;
66
- shadowOffsetX: any;
67
- shadowOffsetY: any;
68
- shadowBlur: any;
69
45
  textAlign: any;
70
46
  textBaseline: any;
71
47
  lineDash: any;
72
- constructor(o?: ContextOptions | number, height?: number);
48
+ constructor(width: number, height: number, options?: ContextOptions);
73
49
  __createElement(elementName: string, properties?: Record<string, any>, resetFill?: boolean): SVGElement;
74
50
  __setDefaultStyles(): void;
75
51
  __applyStyleState(styleState: Record<string, any>): void;
76
52
  __getStyleState(): Record<string, any>;
53
+ /**
54
+ * A translation is what an element's own x/y already say, and repeating it as
55
+ * a matrix costs ~35 bytes on every glyph of an alignment. Anything else --
56
+ * the scale a sequence-logo letter is stretched by -- still needs the matrix.
57
+ */
77
58
  __applyTransformation(element: SVGElement, matrix?: DOMMatrix): void;
78
59
  __applyStyleToCurrentElement(type: string): void;
79
60
  __closestGroupOrSvg(node?: SVGElement): SVGElement;
80
- getSerializedSvg(fixNamedEntities?: boolean): string;
81
61
  getSvg(): SVGSVGElement;
82
62
  save(): void;
83
63
  restore(): void;
@@ -87,49 +67,28 @@ export declare class Context {
87
67
  moveTo(x: number, y: number): void;
88
68
  closePath(): void;
89
69
  lineTo(x: number, y: number): void;
90
- bezierCurveTo(cp1x: number, cp1y: number, cp2x: number, cp2y: number, x: number, y: number): void;
91
70
  quadraticCurveTo(cpx: number, cpy: number, x: number, y: number): void;
71
+ __applyPaintOrder(order: string, other: string): void;
92
72
  stroke(): void;
93
73
  fill(): void;
94
- rect(x: number, y: number, width: number, height: number): void;
95
- __clearCanvas(): void;
96
74
  fillRect(x: number, y: number, width: number, height: number): void;
97
75
  strokeRect(x: number, y: number, width: number, height: number): void;
98
76
  clearRect(x: number, y: number, width: number, height: number): void;
99
- createLinearGradient(x1: number, y1: number, x2: number, y2: number): CanvasGradient;
100
- createRadialGradient(x0: number, y0: number, r0: number, x1: number, y1: number, r1: number): CanvasGradient;
101
- __applyText(text: string, x: number, y: number, action: string): void;
77
+ __clearCanvas(): void;
78
+ __parsedFont(): CSSStyleDeclaration;
102
79
  fillText(text: string, x: number, y: number): void;
103
- strokeText(text: string, x: number, y: number): void;
104
80
  measureText(text: string): TextMetrics;
105
81
  arc(x: number, y: number, radius: number, startAngle: number, endAngle: number, counterClockwise?: boolean): void;
106
- clip(): void;
107
82
  setLineDash(dashArray: number[]): void;
108
83
  setTransform(a: number | DOMMatrix, b?: number, c?: number, d?: number, e?: number, f?: number): void;
109
84
  getTransform(): DOMMatrix;
110
85
  resetTransform(): void;
111
86
  scale(x: number, y?: number): void;
112
- rotate(angle: number): void;
113
87
  translate(x: number, y: number): void;
114
- transform(a: number, b: number, c: number, d: number, e: number, f: number): void;
115
88
  __matrixTransform(x: number, y: number): DOMPoint;
116
89
  __getTransformScale(): {
117
90
  x: number;
118
91
  y: number;
119
92
  };
120
- __getTransformRotation(): number;
121
- /**
122
- * An <image> of the source, cropped and scaled the way the canvas call asks:
123
- * a nested <svg> whose viewBox is the source rectangle maps it onto the
124
- * destination rectangle exactly. Throws rather than dropping the image, so a
125
- * renderer that draws one into an export finds out.
126
- */
127
- drawImage(image: unknown, ...args: number[]): void;
128
- imageSmoothingEnabled: boolean;
129
- drawFocusRing(): void;
130
- createImageData(): void;
131
- putImageData(): void;
132
- globalCompositeOperation(): void;
133
- createPattern(): null;
134
93
  }
135
94
  export {};