@visactor/vutils 0.18.0-alpha.0 → 0.18.0-alpha.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/cjs/color/Color.d.ts +162 -1
- package/cjs/color/Color.js +216 -9
- package/cjs/color/Color.js.map +1 -1
- package/cjs/color/index.d.ts +1 -4
- package/cjs/color/index.js +9 -9
- package/cjs/color/index.js.map +1 -1
- package/cjs/color/interpolate.d.ts +1 -1
- package/cjs/color/interpolate.js +2 -2
- package/cjs/color/interpolate.js.map +1 -1
- package/cjs/common/ascending.js +1 -2
- package/cjs/common/debounce.js +2 -1
- package/cjs/common/isArrayLike.js +1 -2
- package/cjs/common/isNull.js +2 -1
- package/cjs/common/isShallowEqual.js +1 -2
- package/cjs/common/isString.js +1 -1
- package/cjs/common/isType.js +1 -1
- package/cjs/common/isUndefined.js +1 -1
- package/cjs/common/isValid.js +1 -1
- package/cjs/common/isValidNumber.js +1 -1
- package/cjs/common/isValidUrl.js +1 -1
- package/cjs/common/lowerFirst.js +1 -1
- package/cjs/data-structure/bounds.js +1 -1
- package/cjs/data-structure/hashTable.d.ts +35 -0
- package/cjs/data-structure/hashTable.js +115 -0
- package/cjs/data-structure/hashTable.js.map +1 -0
- package/cjs/data-structure/index.d.ts +1 -0
- package/cjs/data-structure/index.js +3 -3
- package/cjs/data-structure/index.js.map +1 -1
- package/cjs/data-structure/matrix.js +1 -1
- package/cjs/data-structure/point.d.ts +1 -1
- package/cjs/data-structure/point.js +6 -7
- package/cjs/data-structure/point.js.map +1 -1
- package/cjs/format/number/formatDecimal.d.ts +2 -0
- package/cjs/format/number/formatDecimal.js +18 -0
- package/cjs/format/number/formatDecimal.js.map +1 -0
- package/cjs/format/number/formatGroup.d.ts +1 -0
- package/cjs/format/number/formatGroup.js +17 -0
- package/cjs/format/number/formatGroup.js.map +1 -0
- package/cjs/format/number/formatPrefixAuto.d.ts +2 -0
- package/cjs/format/number/formatPrefixAuto.js +18 -0
- package/cjs/format/number/formatPrefixAuto.js.map +1 -0
- package/cjs/format/number/formatRounded.d.ts +1 -0
- package/cjs/format/number/formatRounded.js +17 -0
- package/cjs/format/number/formatRounded.js.map +1 -0
- package/cjs/format/number/formatTrim.d.ts +1 -0
- package/cjs/format/number/formatTrim.js +25 -0
- package/cjs/format/number/formatTrim.js.map +1 -0
- package/cjs/format/number/index.d.ts +2 -0
- package/cjs/format/number/index.js +21 -0
- package/cjs/format/number/index.js.map +1 -0
- package/cjs/format/number/number.d.ts +53 -0
- package/cjs/format/number/number.js +121 -0
- package/cjs/format/number/number.js.map +1 -0
- package/cjs/format/number/specifier.d.ts +28 -0
- package/cjs/format/number/specifier.js +41 -0
- package/cjs/format/number/specifier.js.map +1 -0
- package/cjs/format/time.d.ts +79 -0
- package/cjs/format/time.js +204 -0
- package/cjs/format/time.js.map +1 -0
- package/cjs/graphics/algorithm/index.d.ts +1 -0
- package/cjs/graphics/algorithm/index.js +2 -1
- package/cjs/graphics/algorithm/index.js.map +1 -1
- package/cjs/graphics/graph-util.d.ts +23 -0
- package/cjs/graphics/graph-util.js +47 -0
- package/cjs/graphics/graph-util.js.map +1 -0
- package/cjs/graphics/index.d.ts +1 -1
- package/cjs/graphics/index.js +2 -2
- package/cjs/graphics/index.js.map +1 -1
- package/cjs/graphics/text/measure/textMeasure.js +1 -1
- package/cjs/graphics/text/measure/textMeasure.js.map +1 -1
- package/cjs/index.d.ts +3 -0
- package/cjs/index.js +8 -6
- package/cjs/index.js.map +1 -1
- package/cjs/lru.d.ts +25 -0
- package/cjs/lru.js +45 -0
- package/cjs/lru.js.map +1 -0
- package/dist/index.js +1140 -139
- package/dist/index.min.js +1 -1
- package/es/color/Color.d.ts +162 -1
- package/es/color/Color.js +205 -8
- package/es/color/Color.js.map +1 -1
- package/es/color/index.d.ts +1 -4
- package/es/color/index.js +1 -7
- package/es/color/index.js.map +1 -1
- package/es/color/interpolate.d.ts +1 -1
- package/es/color/interpolate.js +1 -1
- package/es/color/interpolate.js.map +1 -1
- package/es/common/ascending.js +1 -2
- package/es/common/debounce.js +2 -1
- package/es/common/isArrayLike.js +1 -2
- package/es/common/isNull.js +2 -1
- package/es/common/isShallowEqual.js +1 -2
- package/es/common/isString.js +1 -1
- package/es/common/isType.js +1 -1
- package/es/common/isUndefined.js +1 -1
- package/es/common/isValid.js +1 -1
- package/es/common/isValidNumber.js +1 -1
- package/es/common/isValidUrl.js +1 -1
- package/es/common/lowerFirst.js +1 -1
- package/es/data-structure/bounds.js +1 -1
- package/es/data-structure/hashTable.d.ts +35 -0
- package/es/data-structure/hashTable.js +105 -0
- package/es/data-structure/hashTable.js.map +1 -0
- package/es/data-structure/index.d.ts +1 -0
- package/es/data-structure/index.js +3 -1
- package/es/data-structure/index.js.map +1 -1
- package/es/data-structure/matrix.js +1 -1
- package/es/data-structure/point.d.ts +1 -1
- package/es/data-structure/point.js +4 -5
- package/es/data-structure/point.js.map +1 -1
- package/es/format/number/formatDecimal.d.ts +2 -0
- package/es/format/number/formatDecimal.js +11 -0
- package/es/format/number/formatDecimal.js.map +1 -0
- package/es/format/number/formatGroup.d.ts +1 -0
- package/es/format/number/formatGroup.js +11 -0
- package/es/format/number/formatGroup.js.map +1 -0
- package/es/format/number/formatPrefixAuto.d.ts +2 -0
- package/es/format/number/formatPrefixAuto.js +11 -0
- package/es/format/number/formatPrefixAuto.js.map +1 -0
- package/es/format/number/formatRounded.d.ts +1 -0
- package/es/format/number/formatRounded.js +9 -0
- package/es/format/number/formatRounded.js.map +1 -0
- package/es/format/number/formatTrim.d.ts +1 -0
- package/es/format/number/formatTrim.js +19 -0
- package/es/format/number/formatTrim.js.map +1 -0
- package/es/format/number/index.d.ts +2 -0
- package/es/format/number/index.js +4 -0
- package/es/format/number/index.js.map +1 -0
- package/es/format/number/number.d.ts +53 -0
- package/es/format/number/number.js +125 -0
- package/es/format/number/number.js.map +1 -0
- package/es/format/number/specifier.d.ts +28 -0
- package/es/format/number/specifier.js +34 -0
- package/es/format/number/specifier.js.map +1 -0
- package/es/format/time.d.ts +79 -0
- package/es/format/time.js +196 -0
- package/es/format/time.js.map +1 -0
- package/es/graphics/algorithm/index.d.ts +1 -0
- package/es/graphics/algorithm/index.js +2 -0
- package/es/graphics/algorithm/index.js.map +1 -1
- package/es/graphics/graph-util.d.ts +23 -0
- package/es/graphics/graph-util.js +39 -0
- package/es/graphics/graph-util.js.map +1 -0
- package/es/graphics/index.d.ts +1 -1
- package/es/graphics/index.js +2 -2
- package/es/graphics/index.js.map +1 -1
- package/es/graphics/text/measure/textMeasure.js +1 -1
- package/es/graphics/text/measure/textMeasure.js.map +1 -1
- package/es/index.d.ts +3 -0
- package/es/index.js +6 -0
- package/es/index.js.map +1 -1
- package/es/lru.d.ts +25 -0
- package/es/lru.js +37 -0
- package/es/lru.js.map +1 -0
- package/package.json +3 -3
- package/cjs/color/defaultColors.d.ts +0 -150
- package/cjs/color/defaultColors.js +0 -155
- package/cjs/color/defaultColors.js.map +0 -1
- package/cjs/color/numberToHex.d.ts +0 -1
- package/cjs/color/numberToHex.js +0 -10
- package/cjs/color/numberToHex.js.map +0 -1
- package/cjs/color/numberToRgb.d.ts +0 -3
- package/cjs/color/numberToRgb.js +0 -20
- package/cjs/color/numberToRgb.js.map +0 -1
- package/cjs/color/parseColorString.d.ts +0 -3
- package/cjs/color/parseColorString.js +0 -38
- package/cjs/color/parseColorString.js.map +0 -1
- package/cjs/color/rgb.d.ts +0 -11
- package/cjs/color/rgb.js +0 -37
- package/cjs/color/rgb.js.map +0 -1
- package/cjs/graphics/distance.d.ts +0 -4
- package/cjs/graphics/distance.js +0 -22
- package/cjs/graphics/distance.js.map +0 -1
- package/es/color/defaultColors.d.ts +0 -150
- package/es/color/defaultColors.js +0 -151
- package/es/color/defaultColors.js.map +0 -1
- package/es/color/numberToHex.d.ts +0 -1
- package/es/color/numberToHex.js +0 -4
- package/es/color/numberToHex.js.map +0 -1
- package/es/color/numberToRgb.d.ts +0 -3
- package/es/color/numberToRgb.js +0 -12
- package/es/color/numberToRgb.js.map +0 -1
- package/es/color/parseColorString.d.ts +0 -3
- package/es/color/parseColorString.js +0 -34
- package/es/color/parseColorString.js.map +0 -1
- package/es/color/rgb.d.ts +0 -11
- package/es/color/rgb.js +0 -26
- package/es/color/rgb.js.map +0 -1
- package/es/graphics/distance.d.ts +0 -4
- package/es/graphics/distance.js +0 -14
- package/es/graphics/distance.js.map +0 -1
|
@@ -0,0 +1,23 @@
|
|
|
1
|
+
interface ITextConfig {
|
|
2
|
+
text: string;
|
|
3
|
+
fontSize: number;
|
|
4
|
+
fontStyle?: string;
|
|
5
|
+
fontVariant?: string;
|
|
6
|
+
fontWeight?: number | string;
|
|
7
|
+
fontFamily?: string;
|
|
8
|
+
}
|
|
9
|
+
export declare class GraphicUtil {
|
|
10
|
+
canvas?: HTMLCanvasElement;
|
|
11
|
+
ctx?: CanvasRenderingContext2D | null;
|
|
12
|
+
static instance?: GraphicUtil;
|
|
13
|
+
constructor(canvas?: HTMLCanvasElement);
|
|
14
|
+
setCanvas(canvas?: HTMLCanvasElement): void;
|
|
15
|
+
measureText(tc: ITextConfig): {
|
|
16
|
+
width: number;
|
|
17
|
+
height: number;
|
|
18
|
+
};
|
|
19
|
+
private measureTextByCanvas;
|
|
20
|
+
private estimate;
|
|
21
|
+
static getDefaultUtils(canvas?: HTMLCanvasElement): GraphicUtil;
|
|
22
|
+
}
|
|
23
|
+
export {};
|
|
@@ -0,0 +1,47 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
|
|
3
|
+
function getContextFont({fontStyle: fontStyle, fontVariant: fontVariant, fontWeight: fontWeight, fontSize: fontSize, fontFamily: fontFamily}) {
|
|
4
|
+
return (fontStyle ? fontStyle + " " : "") + (fontVariant ? fontVariant + " " : "") + (fontWeight ? fontWeight + " " : "") + (fontSize || 12) + "px " + (fontFamily || "sans-serif");
|
|
5
|
+
}
|
|
6
|
+
|
|
7
|
+
Object.defineProperty(exports, "__esModule", {
|
|
8
|
+
value: !0
|
|
9
|
+
}), exports.GraphicUtil = void 0;
|
|
10
|
+
|
|
11
|
+
class GraphicUtil {
|
|
12
|
+
constructor(canvas) {
|
|
13
|
+
this.canvas = canvas, canvas && (this.ctx = canvas.getContext("2d"));
|
|
14
|
+
}
|
|
15
|
+
setCanvas(canvas) {
|
|
16
|
+
this.canvas = canvas, canvas && (this.ctx = canvas.getContext("2d"));
|
|
17
|
+
}
|
|
18
|
+
measureText(tc) {
|
|
19
|
+
return this.canvas ? this.measureTextByCanvas(tc) : (console.warn("[warn] no canvas, measureText might be not accurate"),
|
|
20
|
+
this.estimate(tc));
|
|
21
|
+
}
|
|
22
|
+
measureTextByCanvas(tc) {
|
|
23
|
+
return this.ctx ? (this.ctx.font = getContextFont(tc), {
|
|
24
|
+
width: this.ctx.measureText(tc.text).width,
|
|
25
|
+
height: tc.fontSize
|
|
26
|
+
}) : (console.error("[error!!!]measureTextByCanvas can not be called without canvas"),
|
|
27
|
+
{
|
|
28
|
+
width: -1,
|
|
29
|
+
height: tc.fontSize
|
|
30
|
+
});
|
|
31
|
+
}
|
|
32
|
+
estimate({text: text, fontSize: fontSize}) {
|
|
33
|
+
let eCharLen = 0, cCharLen = 0;
|
|
34
|
+
for (let i = 0; i < text.length; i++) text.charCodeAt(i) < 128 ? eCharLen++ : cCharLen++;
|
|
35
|
+
return {
|
|
36
|
+
width: ~~(.8 * eCharLen * fontSize + cCharLen * fontSize),
|
|
37
|
+
height: fontSize
|
|
38
|
+
};
|
|
39
|
+
}
|
|
40
|
+
static getDefaultUtils(canvas) {
|
|
41
|
+
return GraphicUtil.instance || (GraphicUtil.instance = new GraphicUtil(canvas)),
|
|
42
|
+
GraphicUtil.instance;
|
|
43
|
+
}
|
|
44
|
+
}
|
|
45
|
+
|
|
46
|
+
exports.GraphicUtil = GraphicUtil;
|
|
47
|
+
//# sourceMappingURL=graph-util.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"sources":["../src/graphics/graph-util.ts"],"names":[],"mappings":";;;AASA,SAAS,cAAc,CAAC,EAAE,SAAS,EAAE,WAAW,EAAE,UAAU,EAAE,QAAQ,EAAE,UAAU,EAAe;IAC/F,OAAO,CACL,EAAE;QACF,CAAC,SAAS,CAAC,CAAC,CAAC,SAAS,GAAG,GAAG,CAAC,CAAC,CAAC,EAAE,CAAC;QAClC,CAAC,WAAW,CAAC,CAAC,CAAC,WAAW,GAAG,GAAG,CAAC,CAAC,CAAC,EAAE,CAAC;QACtC,CAAC,UAAU,CAAC,CAAC,CAAC,UAAU,GAAG,GAAG,CAAC,CAAC,CAAC,EAAE,CAAC;QACpC,CAAC,QAAQ,IAAI,EAAE,CAAC;QAChB,KAAK;QACL,CAAC,UAAU,CAAC,CAAC,CAAC,UAAU,CAAC,CAAC,CAAC,YAAY,CAAC,CACzC,CAAC;AACJ,CAAC;AAED,MAAa,WAAW;IAMtB,YAAY,MAA0B;QACpC,IAAI,CAAC,MAAM,GAAG,MAAM,CAAC;QACrB,IAAI,MAAM,EAAE;YACV,IAAI,CAAC,GAAG,GAAG,MAAM,CAAC,UAAU,CAAC,IAAI,CAAC,CAAC;SACpC;IACH,CAAC;IACD,SAAS,CAAC,MAA0B;QAClC,IAAI,CAAC,MAAM,GAAG,MAAM,CAAC;QACrB,IAAI,MAAM,EAAE;YACV,IAAI,CAAC,GAAG,GAAG,MAAM,CAAC,UAAU,CAAC,IAAI,CAAC,CAAC;SACpC;IACH,CAAC;IAED,WAAW,CAAC,EAAe;QACzB,IAAI,CAAC,IAAI,CAAC,MAAM,EAAE;YAChB,OAAO,CAAC,IAAI,CAAC,qDAAqD,CAAC,CAAC;YACpE,OAAO,IAAI,CAAC,QAAQ,CAAC,EAAE,CAAC,CAAC;SAC1B;QACD,OAAO,IAAI,CAAC,mBAAmB,CAAC,EAAE,CAAC,CAAC;IACtC,CAAC;IAEO,mBAAmB,CAAC,EAAe;QACzC,IAAI,CAAC,IAAI,CAAC,GAAG,EAAE;YACb,OAAO,CAAC,KAAK,CAAC,gEAAgE,CAAC,CAAC;YAChF,OAAO,EAAE,KAAK,EAAE,CAAC,CAAC,EAAE,MAAM,EAAE,EAAE,CAAC,QAAQ,EAAE,CAAC;SAC3C;QACD,IAAI,CAAC,GAAG,CAAC,IAAI,GAAG,cAAc,CAAC,EAAE,CAAC,CAAC;QACnC,OAAO;YACL,KAAK,EAAE,IAAI,CAAC,GAAG,CAAC,WAAW,CAAC,EAAE,CAAC,IAAI,CAAC,CAAC,KAAK;YAC1C,MAAM,EAAE,EAAE,CAAC,QAAQ;SACpB,CAAC;IACJ,CAAC;IAEO,QAAQ,CAAC,EAAE,IAAI,EAAE,QAAQ,EAAe;QAE9C,IAAI,QAAQ,GAAG,CAAC,CAAC;QACjB,IAAI,QAAQ,GAAG,CAAC,CAAC;QAEjB,KAAK,IAAI,CAAC,GAAG,CAAC,EAAE,CAAC,GAAG,IAAI,CAAC,MAAM,EAAE,CAAC,EAAE,EAAE;YACpC,IAAI,CAAC,UAAU,CAAC,CAAC,CAAC,GAAG,GAAG,CAAC,CAAC,CAAC,QAAQ,EAAE,CAAC,CAAC,CAAC,QAAQ,EAAE,CAAC;SACpD;QACD,OAAO;YACL,KAAK,EAAE,CAAC,CAAC,CAAC,GAAG,GAAG,QAAQ,GAAG,QAAQ,GAAG,QAAQ,GAAG,QAAQ,CAAC;YAC1D,MAAM,EAAE,QAAQ;SACjB,CAAC;IACJ,CAAC;IAED,MAAM,CAAC,eAAe,CAAC,MAA0B;QAC/C,IAAI,CAAC,WAAW,CAAC,QAAQ,EAAE;YACzB,WAAW,CAAC,QAAQ,GAAG,IAAI,WAAW,CAAC,MAAM,CAAC,CAAC;SAChD;QACD,OAAO,WAAW,CAAC,QAAQ,CAAC;IAC9B,CAAC;CACF;AA3DD,kCA2DC","file":"graph-util.js","sourcesContent":["interface ITextConfig {\n text: string;\n fontSize: number;\n fontStyle?: string;\n fontVariant?: string;\n fontWeight?: number | string;\n fontFamily?: string;\n}\n\nfunction getContextFont({ fontStyle, fontVariant, fontWeight, fontSize, fontFamily }: ITextConfig): string {\n return (\n '' +\n (fontStyle ? fontStyle + ' ' : '') +\n (fontVariant ? fontVariant + ' ' : '') +\n (fontWeight ? fontWeight + ' ' : '') +\n (fontSize || 12) +\n 'px ' +\n (fontFamily ? fontFamily : 'sans-serif')\n );\n}\n\nexport class GraphicUtil {\n canvas?: HTMLCanvasElement;\n ctx?: CanvasRenderingContext2D | null;\n\n static instance?: GraphicUtil;\n\n constructor(canvas?: HTMLCanvasElement) {\n this.canvas = canvas;\n if (canvas) {\n this.ctx = canvas.getContext('2d');\n }\n }\n setCanvas(canvas?: HTMLCanvasElement) {\n this.canvas = canvas;\n if (canvas) {\n this.ctx = canvas.getContext('2d');\n }\n }\n\n measureText(tc: ITextConfig) {\n if (!this.canvas) {\n console.warn('[warn] no canvas, measureText might be not accurate');\n return this.estimate(tc);\n }\n return this.measureTextByCanvas(tc);\n }\n\n private measureTextByCanvas(tc: ITextConfig): { width: number; height: number } {\n if (!this.ctx) {\n console.error('[error!!!]measureTextByCanvas can not be called without canvas');\n return { width: -1, height: tc.fontSize };\n }\n this.ctx.font = getContextFont(tc);\n return {\n width: this.ctx.measureText(tc.text).width,\n height: tc.fontSize\n };\n }\n\n private estimate({ text, fontSize }: ITextConfig): { width: number; height: number } {\n // 假设只有英文和中文字符\n let eCharLen = 0; // 英文字符\n let cCharLen = 0; // 中文字符\n // 判断ascii码,如果是\n for (let i = 0; i < text.length; i++) {\n text.charCodeAt(i) < 128 ? eCharLen++ : cCharLen++;\n }\n return {\n width: ~~(0.8 * eCharLen * fontSize + cCharLen * fontSize),\n height: fontSize\n };\n }\n\n static getDefaultUtils(canvas?: HTMLCanvasElement) {\n if (!GraphicUtil.instance) {\n GraphicUtil.instance = new GraphicUtil(canvas);\n }\n return GraphicUtil.instance;\n }\n}\n"]}
|
package/cjs/graphics/index.d.ts
CHANGED
package/cjs/graphics/index.js
CHANGED
|
@@ -18,6 +18,6 @@ var __createBinding = this && this.__createBinding || (Object.create ? function(
|
|
|
18
18
|
Object.defineProperty(exports, "__esModule", {
|
|
19
19
|
value: !0
|
|
20
20
|
}), __exportStar(require("./image"), exports), __exportStar(require("./algorithm"), exports),
|
|
21
|
-
__exportStar(require("./
|
|
22
|
-
__exportStar(require("./
|
|
21
|
+
__exportStar(require("./graph-util"), exports), __exportStar(require("./polygon"), exports),
|
|
22
|
+
__exportStar(require("./text"), exports);
|
|
23
23
|
//# sourceMappingURL=index.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["../src/graphics/index.ts"],"names":[],"mappings":";;;;;;;;;;;;;;;;AACA,0CAAwB;AAGxB,8CAA4B;AAE5B,4CAA0B;AAE1B,yCAAuB
|
|
1
|
+
{"version":3,"sources":["../src/graphics/index.ts"],"names":[],"mappings":";;;;;;;;;;;;;;;;AACA,0CAAwB;AAGxB,8CAA4B;AAE5B,+CAA6B;AAE7B,4CAA0B;AAE1B,yCAAuB","file":"index.js","sourcesContent":["// image\nexport * from './image';\n\n// computer geometry algorithm, cgs.js\nexport * from './algorithm';\n\nexport * from './graph-util';\n\nexport * from './polygon';\n\nexport * from './text';\n"]}
|
|
@@ -18,7 +18,7 @@ class TextMeasure {
|
|
|
18
18
|
initContext() {
|
|
19
19
|
if (this._notSupportCanvas) return !1;
|
|
20
20
|
if ((0, common_1.isNil)(this._canvas) && ((0, common_1.isValid)(this._option.getCanvasForMeasure) && (this._canvas = this._option.getCanvasForMeasure()),
|
|
21
|
-
(0, common_1.isNil)(this._canvas) && "undefined" != typeof window && void 0 !== window.document && (0,
|
|
21
|
+
(0, common_1.isNil)(this._canvas) && "undefined" != typeof window && void 0 !== window.document && globalThis && (0,
|
|
22
22
|
common_1.isValid)(globalThis.document) && (this._canvas = globalThis.document.createElement("canvas"))),
|
|
23
23
|
(0, common_1.isNil)(this._context) && (0, common_1.isValid)(this._canvas)) {
|
|
24
24
|
const context = this._canvas.getContext("2d");
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["../src/graphics/text/measure/textMeasure.ts"],"names":[],"mappings":"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","file":"textMeasure.js","sourcesContent":["import { isArray, isNil, isString, isValid } from '../../../common';\nimport type { Maybe } from '../../../type';\nimport { eastAsianCharacterInfo } from '../stringWidth';\nimport type { ITextMeasureOption, ITextMeasureSpec, ITextSize, TextMeasureInput, TextMeasureMethod } from './interface';\nimport { getContextFont } from './util';\n\nexport class TextMeasure<T extends Partial<ITextMeasureSpec>> {\n /** 英文字母集 */\n static readonly ALPHABET_CHAR_SET = 'abcdefghijklmnopqrstuvwxyz';\n\n /** 数字集 */\n static readonly NUMBERS_CHAR_SET = '0123456789';\n\n /** 全角字符 */\n static readonly FULL_SIZE_CHAR = '字';\n\n /** 数字大小缓存 */\n _numberCharSize: Maybe<ITextSize> = null;\n\n /** 全角字符大小缓存 */\n _fullCharSize: Maybe<ITextSize> = null;\n\n /** 字母大小缓存 */\n _letterCharSize: Maybe<ITextSize> = null;\n\n /** 特殊字符缓存 */\n _specialCharSizeMap: Record<string, ITextSize> = {};\n\n /** 内置测量 canvas */\n protected _canvas: Maybe<HTMLCanvasElement> = null;\n protected _context: Maybe<CanvasRenderingContext2D> = null;\n protected _contextSaved: boolean = false;\n\n /** 是否不支持 canvas */\n protected _notSupportCanvas: boolean = false;\n /** 是否不支持 vrender */\n protected _notSupportVRender: boolean = false;\n\n /** 文字 spec */\n protected readonly _userSpec: Partial<T> = {};\n textSpec: ITextMeasureSpec;\n\n protected readonly _option: ITextMeasureOption;\n\n /** 标准测量方法 */\n protected readonly _standardMethod: (text: TextMeasureInput) => ITextSize;\n\n /** 特殊字符集 */\n specialCharSet: string = '-/: .,@%\\'\"~';\n\n constructor(option: ITextMeasureOption, textSpec?: Partial<T>) {\n this._option = option;\n this._userSpec = textSpec ?? {};\n this.textSpec = this._initSpec();\n if (isValid(option.specialCharSet)) {\n this.specialCharSet = option.specialCharSet;\n }\n this._standardMethod = isValid(option.getTextBounds)\n ? this.fullMeasure.bind(this)\n : this.measureWithNaiveCanvas.bind(this);\n }\n\n /** 初始化测量相关上下文 */\n initContext() {\n if (this._notSupportCanvas) {\n return false;\n }\n if (isNil(this._canvas)) {\n if (isValid(this._option.getCanvasForMeasure)) {\n this._canvas = this._option.getCanvasForMeasure();\n }\n if (\n isNil(this._canvas) &&\n typeof window !== 'undefined' &&\n typeof window.document !== 'undefined' &&\n isValid(globalThis.document)\n ) {\n // 默认创建方法\n this._canvas = globalThis.document.createElement('canvas');\n }\n }\n if (isNil(this._context) && isValid(this._canvas)) {\n const context = this._canvas.getContext('2d');\n if (isValid(context)) {\n context.save();\n context.font = getContextFont(this.textSpec);\n this._contextSaved = true;\n this._context = context;\n }\n }\n if (isNil(this._context)) {\n this._notSupportCanvas = true;\n return false;\n }\n return true;\n }\n\n protected _initSpec(): ITextMeasureSpec {\n const { defaultFontParams = {} } = this._option;\n const {\n fontStyle = defaultFontParams.fontStyle,\n fontVariant = defaultFontParams.fontVariant,\n fontWeight = defaultFontParams.fontWeight ?? 'normal',\n fontSize = defaultFontParams.fontSize ?? 12,\n fontFamily = defaultFontParams.fontFamily ?? 'sans-serif',\n align,\n textAlign = align ?? 'center',\n baseline,\n textBaseline = baseline ?? 'middle',\n ellipsis,\n limit\n } = this._userSpec;\n\n let { lineHeight = fontSize } = this._userSpec;\n if (isString(lineHeight) && lineHeight[lineHeight.length - 1] === '%') {\n const scale = Number.parseFloat(lineHeight.substring(0, lineHeight.length - 1)) / 100;\n lineHeight = fontSize * scale;\n }\n\n return {\n fontStyle,\n fontVariant,\n fontFamily,\n fontSize,\n fontWeight,\n textAlign,\n textBaseline,\n ellipsis,\n limit,\n lineHeight\n };\n }\n\n /** 计算文本宽高 */\n measure(text: TextMeasureInput, method?: TextMeasureMethod): ITextSize {\n switch (method) {\n case 'vrender':\n case 'canopus' as any:\n return this.fullMeasure(text);\n case 'canvas':\n return this.measureWithNaiveCanvas(text);\n case 'simple':\n return this.quickMeasureWithoutCanvas(text);\n case 'quick':\n default:\n return this.quickMeasure(text);\n }\n }\n\n /** 精确计算文本宽高 */\n fullMeasure(text: TextMeasureInput): ITextSize {\n if (isNil(text)) {\n return { width: 0, height: 0 };\n }\n if (isNil(this._option.getTextBounds) || !this._notSupportVRender) {\n return this.measureWithNaiveCanvas(text); // 降级\n }\n const { fontFamily, fontSize, fontWeight, textAlign, textBaseline, ellipsis, limit, lineHeight } = this.textSpec;\n let size: ITextSize;\n try {\n const bounds = this._option.getTextBounds({\n text,\n fontFamily,\n fontSize,\n fontWeight,\n textAlign,\n textBaseline,\n ellipsis: !!ellipsis,\n maxLineWidth: limit || Infinity,\n lineHeight\n });\n size = { width: bounds.width(), height: bounds.height() };\n } catch (e) {\n this._notSupportVRender = true;\n size = this.measureWithNaiveCanvas(text); // 降级\n }\n return size;\n }\n\n /** 通过原生 canvas 精确计算文本宽度,高度为估算 */\n measureWithNaiveCanvas(text: TextMeasureInput): ITextSize {\n return this._measureReduce(text, this._measureWithNaiveCanvas.bind(this));\n }\n protected _measureWithNaiveCanvas(text: string): ITextSize {\n if (!this.initContext()) {\n return this._quickMeasureWithoutCanvas(text); // 降级\n }\n const metrics = this._context!.measureText(text);\n const { fontSize, lineHeight } = this.textSpec;\n return { width: metrics.width, height: (lineHeight as number) ?? fontSize };\n }\n\n /** 快速估算文本宽高 */\n quickMeasure(text: TextMeasureInput): ITextSize {\n return this._measureReduce(text, this._quickMeasure.bind(this));\n }\n protected _quickMeasure(text: string): ITextSize {\n const totalSize: ITextSize = {\n width: 0,\n height: 0\n };\n\n for (let i = 0; i < text.length; i++) {\n const char = text[i];\n // 先判断是否特殊字符\n let size = this._measureSpecialChar(char);\n // 再判断是否数字\n if (isNil(size) && TextMeasure.NUMBERS_CHAR_SET.includes(char)) {\n size = this._measureNumberChar();\n }\n // 再判断全角字符\n if (isNil(size) && ['F', 'W'].includes(eastAsianCharacterInfo(char))) {\n size = this._measureFullSizeChar();\n }\n // 最后按半角字符处理\n if (isNil(size)) {\n size = this._measureLetterChar();\n }\n totalSize.width += size.width;\n totalSize.height = Math.max(totalSize.height, size.height);\n }\n return totalSize;\n }\n\n /** 不使用 canvas 来快速估算文本宽高 */\n quickMeasureWithoutCanvas(text: TextMeasureInput): ITextSize {\n return this._measureReduce(text, this._quickMeasureWithoutCanvas.bind(this));\n }\n protected _quickMeasureWithoutCanvas(text: string): ITextSize {\n const totalSize: ITextSize = {\n width: 0,\n height: 0\n };\n\n const { fontSize, lineHeight } = this.textSpec;\n for (let i = 0; i < text.length; i++) {\n const char = text[i];\n // 判断全角字符\n const size = ['F', 'W'].includes(eastAsianCharacterInfo(char)) ? 1 : 0.53;\n totalSize.width += size * fontSize;\n }\n totalSize.height = (lineHeight as number) ?? fontSize;\n return totalSize;\n }\n\n protected _measureReduce(text: TextMeasureInput, processor: (str: string) => ITextSize): ITextSize {\n const { fontSize, lineHeight } = this.textSpec;\n const defaultResult = { width: 0, height: 0 };\n\n if (isNil(text)) {\n return defaultResult;\n } else if (isArray(text)) {\n const textArr = text.filter(isValid).map(s => s.toString());\n if (textArr.length === 0) {\n return defaultResult;\n } else if (textArr.length === 1) {\n return processor(textArr[0]);\n }\n return {\n width: textArr.reduce((maxWidth, cur) => Math.max(maxWidth, processor(cur).width), 0),\n height: textArr.length * (((lineHeight as number) ?? fontSize) + 1) + 1 // 经验值\n };\n }\n return processor(text.toString());\n }\n\n /** 测量一个数字 */\n protected _measureNumberChar(): ITextSize {\n if (isNil(this._numberCharSize)) {\n const numberBounds = this._standardMethod(TextMeasure.NUMBERS_CHAR_SET);\n this._numberCharSize = {\n width: numberBounds.width / TextMeasure.NUMBERS_CHAR_SET.length, // 宽度取均值\n height: numberBounds.height\n };\n }\n return this._numberCharSize;\n }\n\n /** 测量一个全角字符 */\n protected _measureFullSizeChar(): ITextSize {\n if (isNil(this._fullCharSize)) {\n this._fullCharSize = this._standardMethod(TextMeasure.FULL_SIZE_CHAR);\n }\n return this._fullCharSize;\n }\n\n /** 测量一个英文字符 */\n protected _measureLetterChar(): ITextSize {\n if (isNil(this._letterCharSize)) {\n const alphabetBounds = this._standardMethod(TextMeasure.ALPHABET_CHAR_SET);\n this._letterCharSize = {\n width: alphabetBounds.width / TextMeasure.ALPHABET_CHAR_SET.length, // 宽度取均值\n height: alphabetBounds.height\n };\n }\n return this._letterCharSize;\n }\n\n /** 测量一个特殊字符 */\n protected _measureSpecialChar(char: string): Maybe<ITextSize> {\n if (isValid(this._specialCharSizeMap[char])) {\n return this._specialCharSizeMap[char];\n }\n if (this.specialCharSet.includes(char)) {\n this._specialCharSizeMap[char] = this._standardMethod(char);\n return this._specialCharSizeMap[char];\n }\n return null;\n }\n\n release() {\n if (isValid(this._canvas)) {\n this._canvas = null;\n }\n if (isValid(this._context)) {\n if (this._contextSaved) {\n this._context.restore();\n this._contextSaved = false;\n }\n this._context = null;\n }\n }\n}\n"]}
|
|
1
|
+
{"version":3,"sources":["../src/graphics/text/measure/textMeasure.ts"],"names":[],"mappings":";;;AAAA,4CAAoE;AAEpE,gDAAwD;AAExD,iCAAwC;AAExC,MAAa,WAAW;IA4CtB,YAAY,MAA0B,EAAE,QAAqB;QAjC7D,oBAAe,GAAqB,IAAI,CAAC;QAGzC,kBAAa,GAAqB,IAAI,CAAC;QAGvC,oBAAe,GAAqB,IAAI,CAAC;QAGzC,wBAAmB,GAA8B,EAAE,CAAC;QAG1C,YAAO,GAA6B,IAAI,CAAC;QACzC,aAAQ,GAAoC,IAAI,CAAC;QACjD,kBAAa,GAAY,KAAK,CAAC;QAG/B,sBAAiB,GAAY,KAAK,CAAC;QAEnC,uBAAkB,GAAY,KAAK,CAAC;QAG3B,cAAS,GAAe,EAAE,CAAC;QAS9C,mBAAc,GAAW,cAAc,CAAC;QAGtC,IAAI,CAAC,OAAO,GAAG,MAAM,CAAC;QACtB,IAAI,CAAC,SAAS,GAAG,QAAQ,aAAR,QAAQ,cAAR,QAAQ,GAAI,EAAE,CAAC;QAChC,IAAI,CAAC,QAAQ,GAAG,IAAI,CAAC,SAAS,EAAE,CAAC;QACjC,IAAI,IAAA,gBAAO,EAAC,MAAM,CAAC,cAAc,CAAC,EAAE;YAClC,IAAI,CAAC,cAAc,GAAG,MAAM,CAAC,cAAc,CAAC;SAC7C;QACD,IAAI,CAAC,eAAe,GAAG,IAAA,gBAAO,EAAC,MAAM,CAAC,aAAa,CAAC;YAClD,CAAC,CAAC,IAAI,CAAC,WAAW,CAAC,IAAI,CAAC,IAAI,CAAC;YAC7B,CAAC,CAAC,IAAI,CAAC,sBAAsB,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;IAC7C,CAAC;IAGD,WAAW;QACT,IAAI,IAAI,CAAC,iBAAiB,EAAE;YAC1B,OAAO,KAAK,CAAC;SACd;QACD,IAAI,IAAA,cAAK,EAAC,IAAI,CAAC,OAAO,CAAC,EAAE;YACvB,IAAI,IAAA,gBAAO,EAAC,IAAI,CAAC,OAAO,CAAC,mBAAmB,CAAC,EAAE;gBAC7C,IAAI,CAAC,OAAO,GAAG,IAAI,CAAC,OAAO,CAAC,mBAAmB,EAAE,CAAC;aACnD;YACD,IACE,IAAA,cAAK,EAAC,IAAI,CAAC,OAAO,CAAC;gBACnB,OAAO,MAAM,KAAK,WAAW;gBAC7B,OAAO,MAAM,CAAC,QAAQ,KAAK,WAAW;gBACtC,UAAU;gBACV,IAAA,gBAAO,EAAC,UAAU,CAAC,QAAQ,CAAC,EAC5B;gBAEA,IAAI,CAAC,OAAO,GAAG,UAAU,CAAC,QAAQ,CAAC,aAAa,CAAC,QAAQ,CAAC,CAAC;aAC5D;SACF;QACD,IAAI,IAAA,cAAK,EAAC,IAAI,CAAC,QAAQ,CAAC,IAAI,IAAA,gBAAO,EAAC,IAAI,CAAC,OAAO,CAAC,EAAE;YACjD,MAAM,OAAO,GAAG,IAAI,CAAC,OAAO,CAAC,UAAU,CAAC,IAAI,CAAC,CAAC;YAC9C,IAAI,IAAA,gBAAO,EAAC,OAAO,CAAC,EAAE;gBACpB,OAAO,CAAC,IAAI,EAAE,CAAC;gBACf,OAAO,CAAC,IAAI,GAAG,IAAA,qBAAc,EAAC,IAAI,CAAC,QAAQ,CAAC,CAAC;gBAC7C,IAAI,CAAC,aAAa,GAAG,IAAI,CAAC;gBAC1B,IAAI,CAAC,QAAQ,GAAG,OAAO,CAAC;aACzB;SACF;QACD,IAAI,IAAA,cAAK,EAAC,IAAI,CAAC,QAAQ,CAAC,EAAE;YACxB,IAAI,CAAC,iBAAiB,GAAG,IAAI,CAAC;YAC9B,OAAO,KAAK,CAAC;SACd;QACD,OAAO,IAAI,CAAC;IACd,CAAC;IAES,SAAS;;QACjB,MAAM,EAAE,iBAAiB,GAAG,EAAE,EAAE,GAAG,IAAI,CAAC,OAAO,CAAC;QAChD,MAAM,EACJ,SAAS,GAAG,iBAAiB,CAAC,SAAS,EACvC,WAAW,GAAG,iBAAiB,CAAC,WAAW,EAC3C,UAAU,GAAG,MAAA,iBAAiB,CAAC,UAAU,mCAAI,QAAQ,EACrD,QAAQ,GAAG,MAAA,iBAAiB,CAAC,QAAQ,mCAAI,EAAE,EAC3C,UAAU,GAAG,MAAA,iBAAiB,CAAC,UAAU,mCAAI,YAAY,EACzD,KAAK,EACL,SAAS,GAAG,KAAK,aAAL,KAAK,cAAL,KAAK,GAAI,QAAQ,EAC7B,QAAQ,EACR,YAAY,GAAG,QAAQ,aAAR,QAAQ,cAAR,QAAQ,GAAI,QAAQ,EACnC,QAAQ,EACR,KAAK,EACN,GAAG,IAAI,CAAC,SAAS,CAAC;QAEnB,IAAI,EAAE,UAAU,GAAG,QAAQ,EAAE,GAAG,IAAI,CAAC,SAAS,CAAC;QAC/C,IAAI,IAAA,iBAAQ,EAAC,UAAU,CAAC,IAAI,UAAU,CAAC,UAAU,CAAC,MAAM,GAAG,CAAC,CAAC,KAAK,GAAG,EAAE;YACrE,MAAM,KAAK,GAAG,MAAM,CAAC,UAAU,CAAC,UAAU,CAAC,SAAS,CAAC,CAAC,EAAE,UAAU,CAAC,MAAM,GAAG,CAAC,CAAC,CAAC,GAAG,GAAG,CAAC;YACtF,UAAU,GAAG,QAAQ,GAAG,KAAK,CAAC;SAC/B;QAED,OAAO;YACL,SAAS;YACT,WAAW;YACX,UAAU;YACV,QAAQ;YACR,UAAU;YACV,SAAS;YACT,YAAY;YACZ,QAAQ;YACR,KAAK;YACL,UAAU;SACX,CAAC;IACJ,CAAC;IAGD,OAAO,CAAC,IAAsB,EAAE,MAA0B;QACxD,QAAQ,MAAM,EAAE;YACd,KAAK,SAAS,CAAC;YACf,KAAK,SAAgB;gBACnB,OAAO,IAAI,CAAC,WAAW,CAAC,IAAI,CAAC,CAAC;YAChC,KAAK,QAAQ;gBACX,OAAO,IAAI,CAAC,sBAAsB,CAAC,IAAI,CAAC,CAAC;YAC3C,KAAK,QAAQ;gBACX,OAAO,IAAI,CAAC,yBAAyB,CAAC,IAAI,CAAC,CAAC;YAC9C,KAAK,OAAO,CAAC;YACb;gBACE,OAAO,IAAI,CAAC,YAAY,CAAC,IAAI,CAAC,CAAC;SAClC;IACH,CAAC;IAGD,WAAW,CAAC,IAAsB;QAChC,IAAI,IAAA,cAAK,EAAC,IAAI,CAAC,EAAE;YACf,OAAO,EAAE,KAAK,EAAE,CAAC,EAAE,MAAM,EAAE,CAAC,EAAE,CAAC;SAChC;QACD,IAAI,IAAA,cAAK,EAAC,IAAI,CAAC,OAAO,CAAC,aAAa,CAAC,IAAI,CAAC,IAAI,CAAC,kBAAkB,EAAE;YACjE,OAAO,IAAI,CAAC,sBAAsB,CAAC,IAAI,CAAC,CAAC;SAC1C;QACD,MAAM,EAAE,UAAU,EAAE,QAAQ,EAAE,UAAU,EAAE,SAAS,EAAE,YAAY,EAAE,QAAQ,EAAE,KAAK,EAAE,UAAU,EAAE,GAAG,IAAI,CAAC,QAAQ,CAAC;QACjH,IAAI,IAAe,CAAC;QACpB,IAAI;YACF,MAAM,MAAM,GAAG,IAAI,CAAC,OAAO,CAAC,aAAa,CAAC;gBACxC,IAAI;gBACJ,UAAU;gBACV,QAAQ;gBACR,UAAU;gBACV,SAAS;gBACT,YAAY;gBACZ,QAAQ,EAAE,CAAC,CAAC,QAAQ;gBACpB,YAAY,EAAE,KAAK,IAAI,QAAQ;gBAC/B,UAAU;aACX,CAAC,CAAC;YACH,IAAI,GAAG,EAAE,KAAK,EAAE,MAAM,CAAC,KAAK,EAAE,EAAE,MAAM,EAAE,MAAM,CAAC,MAAM,EAAE,EAAE,CAAC;SAC3D;QAAC,OAAO,CAAC,EAAE;YACV,IAAI,CAAC,kBAAkB,GAAG,IAAI,CAAC;YAC/B,IAAI,GAAG,IAAI,CAAC,sBAAsB,CAAC,IAAI,CAAC,CAAC;SAC1C;QACD,OAAO,IAAI,CAAC;IACd,CAAC;IAGD,sBAAsB,CAAC,IAAsB;QAC3C,OAAO,IAAI,CAAC,cAAc,CAAC,IAAI,EAAE,IAAI,CAAC,uBAAuB,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC,CAAC;IAC5E,CAAC;IACS,uBAAuB,CAAC,IAAY;;QAC5C,IAAI,CAAC,IAAI,CAAC,WAAW,EAAE,EAAE;YACvB,OAAO,IAAI,CAAC,0BAA0B,CAAC,IAAI,CAAC,CAAC;SAC9C;QACD,MAAM,OAAO,GAAG,IAAI,CAAC,QAAS,CAAC,WAAW,CAAC,IAAI,CAAC,CAAC;QACjD,MAAM,EAAE,QAAQ,EAAE,UAAU,EAAE,GAAG,IAAI,CAAC,QAAQ,CAAC;QAC/C,OAAO,EAAE,KAAK,EAAE,OAAO,CAAC,KAAK,EAAE,MAAM,EAAE,MAAC,UAAqB,mCAAI,QAAQ,EAAE,CAAC;IAC9E,CAAC;IAGD,YAAY,CAAC,IAAsB;QACjC,OAAO,IAAI,CAAC,cAAc,CAAC,IAAI,EAAE,IAAI,CAAC,aAAa,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC,CAAC;IAClE,CAAC;IACS,aAAa,CAAC,IAAY;QAClC,MAAM,SAAS,GAAc;YAC3B,KAAK,EAAE,CAAC;YACR,MAAM,EAAE,CAAC;SACV,CAAC;QAEF,KAAK,IAAI,CAAC,GAAG,CAAC,EAAE,CAAC,GAAG,IAAI,CAAC,MAAM,EAAE,CAAC,EAAE,EAAE;YACpC,MAAM,IAAI,GAAG,IAAI,CAAC,CAAC,CAAC,CAAC;YAErB,IAAI,IAAI,GAAG,IAAI,CAAC,mBAAmB,CAAC,IAAI,CAAC,CAAC;YAE1C,IAAI,IAAA,cAAK,EAAC,IAAI,CAAC,IAAI,WAAW,CAAC,gBAAgB,CAAC,QAAQ,CAAC,IAAI,CAAC,EAAE;gBAC9D,IAAI,GAAG,IAAI,CAAC,kBAAkB,EAAE,CAAC;aAClC;YAED,IAAI,IAAA,cAAK,EAAC,IAAI,CAAC,IAAI,CAAC,GAAG,EAAE,GAAG,CAAC,CAAC,QAAQ,CAAC,IAAA,oCAAsB,EAAC,IAAI,CAAC,CAAC,EAAE;gBACpE,IAAI,GAAG,IAAI,CAAC,oBAAoB,EAAE,CAAC;aACpC;YAED,IAAI,IAAA,cAAK,EAAC,IAAI,CAAC,EAAE;gBACf,IAAI,GAAG,IAAI,CAAC,kBAAkB,EAAE,CAAC;aAClC;YACD,SAAS,CAAC,KAAK,IAAI,IAAI,CAAC,KAAK,CAAC;YAC9B,SAAS,CAAC,MAAM,GAAG,IAAI,CAAC,GAAG,CAAC,SAAS,CAAC,MAAM,EAAE,IAAI,CAAC,MAAM,CAAC,CAAC;SAC5D;QACD,OAAO,SAAS,CAAC;IACnB,CAAC;IAGD,yBAAyB,CAAC,IAAsB;QAC9C,OAAO,IAAI,CAAC,cAAc,CAAC,IAAI,EAAE,IAAI,CAAC,0BAA0B,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC,CAAC;IAC/E,CAAC;IACS,0BAA0B,CAAC,IAAY;;QAC/C,MAAM,SAAS,GAAc;YAC3B,KAAK,EAAE,CAAC;YACR,MAAM,EAAE,CAAC;SACV,CAAC;QAEF,MAAM,EAAE,QAAQ,EAAE,UAAU,EAAE,GAAG,IAAI,CAAC,QAAQ,CAAC;QAC/C,KAAK,IAAI,CAAC,GAAG,CAAC,EAAE,CAAC,GAAG,IAAI,CAAC,MAAM,EAAE,CAAC,EAAE,EAAE;YACpC,MAAM,IAAI,GAAG,IAAI,CAAC,CAAC,CAAC,CAAC;YAErB,MAAM,IAAI,GAAG,CAAC,GAAG,EAAE,GAAG,CAAC,CAAC,QAAQ,CAAC,IAAA,oCAAsB,EAAC,IAAI,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,IAAI,CAAC;YAC1E,SAAS,CAAC,KAAK,IAAI,IAAI,GAAG,QAAQ,CAAC;SACpC;QACD,SAAS,CAAC,MAAM,GAAG,MAAC,UAAqB,mCAAI,QAAQ,CAAC;QACtD,OAAO,SAAS,CAAC;IACnB,CAAC;IAES,cAAc,CAAC,IAAsB,EAAE,SAAqC;;QACpF,MAAM,EAAE,QAAQ,EAAE,UAAU,EAAE,GAAG,IAAI,CAAC,QAAQ,CAAC;QAC/C,MAAM,aAAa,GAAG,EAAE,KAAK,EAAE,CAAC,EAAE,MAAM,EAAE,CAAC,EAAE,CAAC;QAE9C,IAAI,IAAA,cAAK,EAAC,IAAI,CAAC,EAAE;YACf,OAAO,aAAa,CAAC;SACtB;aAAM,IAAI,IAAA,gBAAO,EAAC,IAAI,CAAC,EAAE;YACxB,MAAM,OAAO,GAAG,IAAI,CAAC,MAAM,CAAC,gBAAO,CAAC,CAAC,GAAG,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,QAAQ,EAAE,CAAC,CAAC;YAC5D,IAAI,OAAO,CAAC,MAAM,KAAK,CAAC,EAAE;gBACxB,OAAO,aAAa,CAAC;aACtB;iBAAM,IAAI,OAAO,CAAC,MAAM,KAAK,CAAC,EAAE;gBAC/B,OAAO,SAAS,CAAC,OAAO,CAAC,CAAC,CAAC,CAAC,CAAC;aAC9B;YACD,OAAO;gBACL,KAAK,EAAE,OAAO,CAAC,MAAM,CAAC,CAAC,QAAQ,EAAE,GAAG,EAAE,EAAE,CAAC,IAAI,CAAC,GAAG,CAAC,QAAQ,EAAE,SAAS,CAAC,GAAG,CAAC,CAAC,KAAK,CAAC,EAAE,CAAC,CAAC;gBACrF,MAAM,EAAE,OAAO,CAAC,MAAM,GAAG,CAAC,CAAC,MAAC,UAAqB,mCAAI,QAAQ,CAAC,GAAG,CAAC,CAAC,GAAG,CAAC;aACxE,CAAC;SACH;QACD,OAAO,SAAS,CAAC,IAAI,CAAC,QAAQ,EAAE,CAAC,CAAC;IACpC,CAAC;IAGS,kBAAkB;QAC1B,IAAI,IAAA,cAAK,EAAC,IAAI,CAAC,eAAe,CAAC,EAAE;YAC/B,MAAM,YAAY,GAAG,IAAI,CAAC,eAAe,CAAC,WAAW,CAAC,gBAAgB,CAAC,CAAC;YACxE,IAAI,CAAC,eAAe,GAAG;gBACrB,KAAK,EAAE,YAAY,CAAC,KAAK,GAAG,WAAW,CAAC,gBAAgB,CAAC,MAAM;gBAC/D,MAAM,EAAE,YAAY,CAAC,MAAM;aAC5B,CAAC;SACH;QACD,OAAO,IAAI,CAAC,eAAe,CAAC;IAC9B,CAAC;IAGS,oBAAoB;QAC5B,IAAI,IAAA,cAAK,EAAC,IAAI,CAAC,aAAa,CAAC,EAAE;YAC7B,IAAI,CAAC,aAAa,GAAG,IAAI,CAAC,eAAe,CAAC,WAAW,CAAC,cAAc,CAAC,CAAC;SACvE;QACD,OAAO,IAAI,CAAC,aAAa,CAAC;IAC5B,CAAC;IAGS,kBAAkB;QAC1B,IAAI,IAAA,cAAK,EAAC,IAAI,CAAC,eAAe,CAAC,EAAE;YAC/B,MAAM,cAAc,GAAG,IAAI,CAAC,eAAe,CAAC,WAAW,CAAC,iBAAiB,CAAC,CAAC;YAC3E,IAAI,CAAC,eAAe,GAAG;gBACrB,KAAK,EAAE,cAAc,CAAC,KAAK,GAAG,WAAW,CAAC,iBAAiB,CAAC,MAAM;gBAClE,MAAM,EAAE,cAAc,CAAC,MAAM;aAC9B,CAAC;SACH;QACD,OAAO,IAAI,CAAC,eAAe,CAAC;IAC9B,CAAC;IAGS,mBAAmB,CAAC,IAAY;QACxC,IAAI,IAAA,gBAAO,EAAC,IAAI,CAAC,mBAAmB,CAAC,IAAI,CAAC,CAAC,EAAE;YAC3C,OAAO,IAAI,CAAC,mBAAmB,CAAC,IAAI,CAAC,CAAC;SACvC;QACD,IAAI,IAAI,CAAC,cAAc,CAAC,QAAQ,CAAC,IAAI,CAAC,EAAE;YACtC,IAAI,CAAC,mBAAmB,CAAC,IAAI,CAAC,GAAG,IAAI,CAAC,eAAe,CAAC,IAAI,CAAC,CAAC;YAC5D,OAAO,IAAI,CAAC,mBAAmB,CAAC,IAAI,CAAC,CAAC;SACvC;QACD,OAAO,IAAI,CAAC;IACd,CAAC;IAED,OAAO;QACL,IAAI,IAAA,gBAAO,EAAC,IAAI,CAAC,OAAO,CAAC,EAAE;YACzB,IAAI,CAAC,OAAO,GAAG,IAAI,CAAC;SACrB;QACD,IAAI,IAAA,gBAAO,EAAC,IAAI,CAAC,QAAQ,CAAC,EAAE;YAC1B,IAAI,IAAI,CAAC,aAAa,EAAE;gBACtB,IAAI,CAAC,QAAQ,CAAC,OAAO,EAAE,CAAC;gBACxB,IAAI,CAAC,aAAa,GAAG,KAAK,CAAC;aAC5B;YACD,IAAI,CAAC,QAAQ,GAAG,IAAI,CAAC;SACtB;IACH,CAAC;;AA5TH,kCA6TC;AA3TiB,6BAAiB,GAAG,4BAA4B,CAAC;AAGjD,4BAAgB,GAAG,YAAY,CAAC;AAGhC,0BAAc,GAAG,GAAG,CAAC","file":"textMeasure.js","sourcesContent":["import { isArray, isNil, isString, isValid } from '../../../common';\nimport type { Maybe } from '../../../type';\nimport { eastAsianCharacterInfo } from '../stringWidth';\nimport type { ITextMeasureOption, ITextMeasureSpec, ITextSize, TextMeasureInput, TextMeasureMethod } from './interface';\nimport { getContextFont } from './util';\n\nexport class TextMeasure<T extends Partial<ITextMeasureSpec>> {\n /** 英文字母集 */\n static readonly ALPHABET_CHAR_SET = 'abcdefghijklmnopqrstuvwxyz';\n\n /** 数字集 */\n static readonly NUMBERS_CHAR_SET = '0123456789';\n\n /** 全角字符 */\n static readonly FULL_SIZE_CHAR = '字';\n\n /** 数字大小缓存 */\n _numberCharSize: Maybe<ITextSize> = null;\n\n /** 全角字符大小缓存 */\n _fullCharSize: Maybe<ITextSize> = null;\n\n /** 字母大小缓存 */\n _letterCharSize: Maybe<ITextSize> = null;\n\n /** 特殊字符缓存 */\n _specialCharSizeMap: Record<string, ITextSize> = {};\n\n /** 内置测量 canvas */\n protected _canvas: Maybe<HTMLCanvasElement> = null;\n protected _context: Maybe<CanvasRenderingContext2D> = null;\n protected _contextSaved: boolean = false;\n\n /** 是否不支持 canvas */\n protected _notSupportCanvas: boolean = false;\n /** 是否不支持 vrender */\n protected _notSupportVRender: boolean = false;\n\n /** 文字 spec */\n protected readonly _userSpec: Partial<T> = {};\n textSpec: ITextMeasureSpec;\n\n protected readonly _option: ITextMeasureOption;\n\n /** 标准测量方法 */\n protected readonly _standardMethod: (text: TextMeasureInput) => ITextSize;\n\n /** 特殊字符集 */\n specialCharSet: string = '-/: .,@%\\'\"~';\n\n constructor(option: ITextMeasureOption, textSpec?: Partial<T>) {\n this._option = option;\n this._userSpec = textSpec ?? {};\n this.textSpec = this._initSpec();\n if (isValid(option.specialCharSet)) {\n this.specialCharSet = option.specialCharSet;\n }\n this._standardMethod = isValid(option.getTextBounds)\n ? this.fullMeasure.bind(this)\n : this.measureWithNaiveCanvas.bind(this);\n }\n\n /** 初始化测量相关上下文 */\n initContext() {\n if (this._notSupportCanvas) {\n return false;\n }\n if (isNil(this._canvas)) {\n if (isValid(this._option.getCanvasForMeasure)) {\n this._canvas = this._option.getCanvasForMeasure();\n }\n if (\n isNil(this._canvas) &&\n typeof window !== 'undefined' &&\n typeof window.document !== 'undefined' &&\n globalThis &&\n isValid(globalThis.document)\n ) {\n // 默认创建方法\n this._canvas = globalThis.document.createElement('canvas');\n }\n }\n if (isNil(this._context) && isValid(this._canvas)) {\n const context = this._canvas.getContext('2d');\n if (isValid(context)) {\n context.save();\n context.font = getContextFont(this.textSpec);\n this._contextSaved = true;\n this._context = context;\n }\n }\n if (isNil(this._context)) {\n this._notSupportCanvas = true;\n return false;\n }\n return true;\n }\n\n protected _initSpec(): ITextMeasureSpec {\n const { defaultFontParams = {} } = this._option;\n const {\n fontStyle = defaultFontParams.fontStyle,\n fontVariant = defaultFontParams.fontVariant,\n fontWeight = defaultFontParams.fontWeight ?? 'normal',\n fontSize = defaultFontParams.fontSize ?? 12,\n fontFamily = defaultFontParams.fontFamily ?? 'sans-serif',\n align,\n textAlign = align ?? 'center',\n baseline,\n textBaseline = baseline ?? 'middle',\n ellipsis,\n limit\n } = this._userSpec;\n\n let { lineHeight = fontSize } = this._userSpec;\n if (isString(lineHeight) && lineHeight[lineHeight.length - 1] === '%') {\n const scale = Number.parseFloat(lineHeight.substring(0, lineHeight.length - 1)) / 100;\n lineHeight = fontSize * scale;\n }\n\n return {\n fontStyle,\n fontVariant,\n fontFamily,\n fontSize,\n fontWeight,\n textAlign,\n textBaseline,\n ellipsis,\n limit,\n lineHeight\n };\n }\n\n /** 计算文本宽高 */\n measure(text: TextMeasureInput, method?: TextMeasureMethod): ITextSize {\n switch (method) {\n case 'vrender':\n case 'canopus' as any:\n return this.fullMeasure(text);\n case 'canvas':\n return this.measureWithNaiveCanvas(text);\n case 'simple':\n return this.quickMeasureWithoutCanvas(text);\n case 'quick':\n default:\n return this.quickMeasure(text);\n }\n }\n\n /** 精确计算文本宽高 */\n fullMeasure(text: TextMeasureInput): ITextSize {\n if (isNil(text)) {\n return { width: 0, height: 0 };\n }\n if (isNil(this._option.getTextBounds) || !this._notSupportVRender) {\n return this.measureWithNaiveCanvas(text); // 降级\n }\n const { fontFamily, fontSize, fontWeight, textAlign, textBaseline, ellipsis, limit, lineHeight } = this.textSpec;\n let size: ITextSize;\n try {\n const bounds = this._option.getTextBounds({\n text,\n fontFamily,\n fontSize,\n fontWeight,\n textAlign,\n textBaseline,\n ellipsis: !!ellipsis,\n maxLineWidth: limit || Infinity,\n lineHeight\n });\n size = { width: bounds.width(), height: bounds.height() };\n } catch (e) {\n this._notSupportVRender = true;\n size = this.measureWithNaiveCanvas(text); // 降级\n }\n return size;\n }\n\n /** 通过原生 canvas 精确计算文本宽度,高度为估算 */\n measureWithNaiveCanvas(text: TextMeasureInput): ITextSize {\n return this._measureReduce(text, this._measureWithNaiveCanvas.bind(this));\n }\n protected _measureWithNaiveCanvas(text: string): ITextSize {\n if (!this.initContext()) {\n return this._quickMeasureWithoutCanvas(text); // 降级\n }\n const metrics = this._context!.measureText(text);\n const { fontSize, lineHeight } = this.textSpec;\n return { width: metrics.width, height: (lineHeight as number) ?? fontSize };\n }\n\n /** 快速估算文本宽高 */\n quickMeasure(text: TextMeasureInput): ITextSize {\n return this._measureReduce(text, this._quickMeasure.bind(this));\n }\n protected _quickMeasure(text: string): ITextSize {\n const totalSize: ITextSize = {\n width: 0,\n height: 0\n };\n\n for (let i = 0; i < text.length; i++) {\n const char = text[i];\n // 先判断是否特殊字符\n let size = this._measureSpecialChar(char);\n // 再判断是否数字\n if (isNil(size) && TextMeasure.NUMBERS_CHAR_SET.includes(char)) {\n size = this._measureNumberChar();\n }\n // 再判断全角字符\n if (isNil(size) && ['F', 'W'].includes(eastAsianCharacterInfo(char))) {\n size = this._measureFullSizeChar();\n }\n // 最后按半角字符处理\n if (isNil(size)) {\n size = this._measureLetterChar();\n }\n totalSize.width += size.width;\n totalSize.height = Math.max(totalSize.height, size.height);\n }\n return totalSize;\n }\n\n /** 不使用 canvas 来快速估算文本宽高 */\n quickMeasureWithoutCanvas(text: TextMeasureInput): ITextSize {\n return this._measureReduce(text, this._quickMeasureWithoutCanvas.bind(this));\n }\n protected _quickMeasureWithoutCanvas(text: string): ITextSize {\n const totalSize: ITextSize = {\n width: 0,\n height: 0\n };\n\n const { fontSize, lineHeight } = this.textSpec;\n for (let i = 0; i < text.length; i++) {\n const char = text[i];\n // 判断全角字符\n const size = ['F', 'W'].includes(eastAsianCharacterInfo(char)) ? 1 : 0.53;\n totalSize.width += size * fontSize;\n }\n totalSize.height = (lineHeight as number) ?? fontSize;\n return totalSize;\n }\n\n protected _measureReduce(text: TextMeasureInput, processor: (str: string) => ITextSize): ITextSize {\n const { fontSize, lineHeight } = this.textSpec;\n const defaultResult = { width: 0, height: 0 };\n\n if (isNil(text)) {\n return defaultResult;\n } else if (isArray(text)) {\n const textArr = text.filter(isValid).map(s => s.toString());\n if (textArr.length === 0) {\n return defaultResult;\n } else if (textArr.length === 1) {\n return processor(textArr[0]);\n }\n return {\n width: textArr.reduce((maxWidth, cur) => Math.max(maxWidth, processor(cur).width), 0),\n height: textArr.length * (((lineHeight as number) ?? fontSize) + 1) + 1 // 经验值\n };\n }\n return processor(text.toString());\n }\n\n /** 测量一个数字 */\n protected _measureNumberChar(): ITextSize {\n if (isNil(this._numberCharSize)) {\n const numberBounds = this._standardMethod(TextMeasure.NUMBERS_CHAR_SET);\n this._numberCharSize = {\n width: numberBounds.width / TextMeasure.NUMBERS_CHAR_SET.length, // 宽度取均值\n height: numberBounds.height\n };\n }\n return this._numberCharSize;\n }\n\n /** 测量一个全角字符 */\n protected _measureFullSizeChar(): ITextSize {\n if (isNil(this._fullCharSize)) {\n this._fullCharSize = this._standardMethod(TextMeasure.FULL_SIZE_CHAR);\n }\n return this._fullCharSize;\n }\n\n /** 测量一个英文字符 */\n protected _measureLetterChar(): ITextSize {\n if (isNil(this._letterCharSize)) {\n const alphabetBounds = this._standardMethod(TextMeasure.ALPHABET_CHAR_SET);\n this._letterCharSize = {\n width: alphabetBounds.width / TextMeasure.ALPHABET_CHAR_SET.length, // 宽度取均值\n height: alphabetBounds.height\n };\n }\n return this._letterCharSize;\n }\n\n /** 测量一个特殊字符 */\n protected _measureSpecialChar(char: string): Maybe<ITextSize> {\n if (isValid(this._specialCharSizeMap[char])) {\n return this._specialCharSizeMap[char];\n }\n if (this.specialCharSet.includes(char)) {\n this._specialCharSizeMap[char] = this._standardMethod(char);\n return this._specialCharSizeMap[char];\n }\n return null;\n }\n\n release() {\n if (isValid(this._canvas)) {\n this._canvas = null;\n }\n if (isValid(this._context)) {\n if (this._contextSaved) {\n this._context.restore();\n this._contextSaved = false;\n }\n this._context = null;\n }\n }\n}\n"]}
|
package/cjs/index.d.ts
CHANGED
|
@@ -2,6 +2,7 @@ import EventEmitter from 'eventemitter3';
|
|
|
2
2
|
export { EventEmitter };
|
|
3
3
|
export * from './common';
|
|
4
4
|
export * from './data-structure';
|
|
5
|
+
export * from './lru';
|
|
5
6
|
export * from './math';
|
|
6
7
|
export * from './angle';
|
|
7
8
|
export * as ColorUtil from './color';
|
|
@@ -13,3 +14,5 @@ export * from './time';
|
|
|
13
14
|
export * from './dom';
|
|
14
15
|
export * from './geo';
|
|
15
16
|
export * from './color';
|
|
17
|
+
export * from './format/time';
|
|
18
|
+
export * from './format/number';
|
package/cjs/index.js
CHANGED
|
@@ -38,10 +38,12 @@ Object.defineProperty(exports, "__esModule", {
|
|
|
38
38
|
const eventemitter3_1 = __importDefault(require("eventemitter3"));
|
|
39
39
|
|
|
40
40
|
exports.EventEmitter = eventemitter3_1.default, __exportStar(require("./common"), exports),
|
|
41
|
-
__exportStar(require("./data-structure"), exports), __exportStar(require("./
|
|
42
|
-
__exportStar(require("./
|
|
43
|
-
|
|
44
|
-
__exportStar(require("./
|
|
45
|
-
__exportStar(require("./
|
|
46
|
-
__exportStar(require("./
|
|
41
|
+
__exportStar(require("./data-structure"), exports), __exportStar(require("./lru"), exports),
|
|
42
|
+
__exportStar(require("./math"), exports), __exportStar(require("./angle"), exports),
|
|
43
|
+
exports.ColorUtil = __importStar(require("./color")), __exportStar(require("./graphics"), exports),
|
|
44
|
+
__exportStar(require("./type"), exports), __exportStar(require("./logger"), exports),
|
|
45
|
+
__exportStar(require("./padding"), exports), __exportStar(require("./time"), exports),
|
|
46
|
+
__exportStar(require("./dom"), exports), __exportStar(require("./geo"), exports),
|
|
47
|
+
__exportStar(require("./color"), exports), __exportStar(require("./format/time"), exports),
|
|
48
|
+
__exportStar(require("./format/number"), exports);
|
|
47
49
|
//# sourceMappingURL=index.js.map
|
package/cjs/index.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["../src/index.ts"],"names":[],"mappings":";;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;AAAA,kEAAyC;AAQhC,uBARF,uBAAY,CAQE;AAErB,2CAAyB;AAGzB,mDAAiC;AAGjC,yCAAuB;AAGvB,0CAAwB;AAIxB,qDAAqC;AAGrC,6CAA2B;AAG3B,yCAAuB;AAGvB,2CAAyB;AAGzB,4CAA0B;AAE1B,yCAAuB;AAGvB,wCAAsB;AAEtB,wCAAsB;AAEtB,0CAAwB","file":"index.js","sourcesContent":["import EventEmitter from 'eventemitter3';\n\n/**\n * A high performance event emitter\n * @see {@link https://github.com/primus/eventemitter3}\n * @memberof PIXI.utils\n * @class EventEmitter\n */\nexport { EventEmitter };\n\nexport * from './common';\n\n// data structure\nexport * from './data-structure';\n\n// math\nexport * from './math';\n\n// angle\nexport * from './angle';\n\n// color\n// TODO: 后续删除这个导出,避免引入不需要的内容\nexport * as ColorUtil from './color';\n\n// methods about graphics\nexport * from './graphics';\n\n// type\nexport * from './type';\n\n// log\nexport * from './logger';\n\n// padding\nexport * from './padding';\n\nexport * from './time';\n\n// dom\nexport * from './dom';\n\nexport * from './geo';\n\nexport * from './color';\n"]}
|
|
1
|
+
{"version":3,"sources":["../src/index.ts"],"names":[],"mappings":";;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;AAAA,kEAAyC;AAQhC,uBARF,uBAAY,CAQE;AAErB,2CAAyB;AAGzB,mDAAiC;AAGjC,wCAAsB;AAGtB,yCAAuB;AAGvB,0CAAwB;AAIxB,qDAAqC;AAGrC,6CAA2B;AAG3B,yCAAuB;AAGvB,2CAAyB;AAGzB,4CAA0B;AAE1B,yCAAuB;AAGvB,wCAAsB;AAEtB,wCAAsB;AAEtB,0CAAwB;AAExB,gDAA8B;AAC9B,kDAAgC","file":"index.js","sourcesContent":["import EventEmitter from 'eventemitter3';\n\n/**\n * A high performance event emitter\n * @see {@link https://github.com/primus/eventemitter3}\n * @memberof PIXI.utils\n * @class EventEmitter\n */\nexport { EventEmitter };\n\nexport * from './common';\n\n// data structure\nexport * from './data-structure';\n\n// algorithm\nexport * from './lru';\n\n// math\nexport * from './math';\n\n// angle\nexport * from './angle';\n\n// color\n// TODO: 后续删除这个导出,避免引入不需要的内容\nexport * as ColorUtil from './color';\n\n// methods about graphics\nexport * from './graphics';\n\n// type\nexport * from './type';\n\n// log\nexport * from './logger';\n\n// padding\nexport * from './padding';\n\nexport * from './time';\n\n// dom\nexport * from './dom';\n\nexport * from './geo';\n\nexport * from './color';\n\nexport * from './format/time';\nexport * from './format/number';\n"]}
|
package/cjs/lru.d.ts
ADDED
|
@@ -0,0 +1,25 @@
|
|
|
1
|
+
interface Threshold {
|
|
2
|
+
CLEAN_THRESHOLD?: number;
|
|
3
|
+
L_TIME?: number;
|
|
4
|
+
R_COUNT?: number;
|
|
5
|
+
R_TIMESTAMP_MAX_SIZE?: number;
|
|
6
|
+
}
|
|
7
|
+
export declare class LRU {
|
|
8
|
+
private CLEAN_THRESHOLD;
|
|
9
|
+
private L_TIME;
|
|
10
|
+
private R_COUNT;
|
|
11
|
+
private R_TIMESTAMP_MAX_SIZE;
|
|
12
|
+
clearCache<TK, TV extends {
|
|
13
|
+
timestamp: number[];
|
|
14
|
+
}>(cache: Map<TK, TV>, params: Threshold): number;
|
|
15
|
+
addLimitedTimestamp<T extends {
|
|
16
|
+
timestamp: number[];
|
|
17
|
+
}>(cacheItem: T, t: number, params: Threshold): void;
|
|
18
|
+
clearTimeStamp<TK, TV extends {
|
|
19
|
+
timestamp: number[];
|
|
20
|
+
}>(cache: Map<TK, TV>, params: Threshold): void;
|
|
21
|
+
clearItemTimestamp<T extends {
|
|
22
|
+
timestamp: number[];
|
|
23
|
+
}>(cacheItem: T, params: Threshold): void;
|
|
24
|
+
}
|
|
25
|
+
export {};
|
package/cjs/lru.js
ADDED
|
@@ -0,0 +1,45 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
|
|
3
|
+
Object.defineProperty(exports, "__esModule", {
|
|
4
|
+
value: !0
|
|
5
|
+
}), exports.LRU = void 0;
|
|
6
|
+
|
|
7
|
+
class LRU {
|
|
8
|
+
constructor() {
|
|
9
|
+
this.CLEAN_THRESHOLD = 1e3, this.L_TIME = 1e3, this.R_COUNT = 1, this.R_TIMESTAMP_MAX_SIZE = 20;
|
|
10
|
+
}
|
|
11
|
+
clearCache(cache, params) {
|
|
12
|
+
const {CLEAN_THRESHOLD: CLEAN_THRESHOLD = this.CLEAN_THRESHOLD, L_TIME: L_TIME = this.L_TIME, R_COUNT: R_COUNT = this.R_COUNT} = params;
|
|
13
|
+
if (cache.size < CLEAN_THRESHOLD) return 0;
|
|
14
|
+
let clearNum = 0;
|
|
15
|
+
const clear = key => {
|
|
16
|
+
clearNum++, cache.delete(key);
|
|
17
|
+
}, now = Date.now();
|
|
18
|
+
return cache.forEach(((item, key) => {
|
|
19
|
+
if (item.timestamp.length < R_COUNT) return clear(key);
|
|
20
|
+
let useCount = 0;
|
|
21
|
+
for (;now - item.timestamp[item.timestamp.length - 1 - useCount] < L_TIME && (useCount++,
|
|
22
|
+
!(useCount >= R_COUNT)); ) ;
|
|
23
|
+
if (useCount < R_COUNT) return clear(key);
|
|
24
|
+
for (;now - item.timestamp[0] > L_TIME; ) item.timestamp.shift();
|
|
25
|
+
})), clearNum;
|
|
26
|
+
}
|
|
27
|
+
addLimitedTimestamp(cacheItem, t, params) {
|
|
28
|
+
const {R_TIMESTAMP_MAX_SIZE: R_TIMESTAMP_MAX_SIZE = this.R_TIMESTAMP_MAX_SIZE} = params;
|
|
29
|
+
cacheItem.timestamp.length > R_TIMESTAMP_MAX_SIZE && cacheItem.timestamp.shift(),
|
|
30
|
+
cacheItem.timestamp.push(t);
|
|
31
|
+
}
|
|
32
|
+
clearTimeStamp(cache, params) {
|
|
33
|
+
const {L_TIME: L_TIME = this.L_TIME} = params, now = Date.now();
|
|
34
|
+
cache.forEach((item => {
|
|
35
|
+
for (;now - item.timestamp[0] > L_TIME; ) item.timestamp.shift();
|
|
36
|
+
}));
|
|
37
|
+
}
|
|
38
|
+
clearItemTimestamp(cacheItem, params) {
|
|
39
|
+
const {L_TIME: L_TIME = this.L_TIME} = params, now = Date.now();
|
|
40
|
+
for (;now - cacheItem.timestamp[0] > L_TIME; ) cacheItem.timestamp.shift();
|
|
41
|
+
}
|
|
42
|
+
}
|
|
43
|
+
|
|
44
|
+
exports.LRU = LRU;
|
|
45
|
+
//# sourceMappingURL=lru.js.map
|
package/cjs/lru.js.map
ADDED
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"sources":["../src/lru.ts"],"names":[],"mappings":"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","file":"lru.js","sourcesContent":["interface Threshold {\n CLEAN_THRESHOLD?: number;\n L_TIME?: number;\n R_COUNT?: number;\n R_TIMESTAMP_MAX_SIZE?: number;\n}\n// LRU清除\nexport class LRU {\n private CLEAN_THRESHOLD = 1e3;\n private L_TIME = 1000; // 1000ms以内\n private R_COUNT = 1; // 使用次数为0\n private R_TIMESTAMP_MAX_SIZE = 20; // timestamp最大长度\n\n clearCache<TK, TV extends { timestamp: number[] }>(cache: Map<TK, TV>, params: Threshold): number {\n const { CLEAN_THRESHOLD = this.CLEAN_THRESHOLD, L_TIME = this.L_TIME, R_COUNT = this.R_COUNT } = params;\n if (cache.size < CLEAN_THRESHOLD) {\n return 0;\n }\n // 开始清理,清理最近1000ms内使用次数为0的缓存\n let clearNum = 0;\n const clear = (key: TK) => {\n clearNum++;\n cache.delete(key);\n };\n const now = Date.now();\n cache.forEach((item, key) => {\n if (item.timestamp.length < R_COUNT) {\n return clear(key);\n } // 最近使用次数小于R_COUNT,清除\n let useCount = 0;\n while (now - item.timestamp[item.timestamp.length - 1 - useCount] < L_TIME) {\n useCount++;\n if (useCount >= R_COUNT) {\n break;\n }\n }\n if (useCount < R_COUNT) {\n return clear(key);\n } // 最近L_TIME以内使用次数小于R_COUNT,清除\n // 清除L_TIME以外的key,避免数组过长\n while (now - item.timestamp[0] > L_TIME) {\n item.timestamp.shift();\n }\n return;\n });\n return clearNum;\n }\n\n addLimitedTimestamp<T extends { timestamp: number[] }>(cacheItem: T, t: number, params: Threshold) {\n const { R_TIMESTAMP_MAX_SIZE = this.R_TIMESTAMP_MAX_SIZE } = params;\n if (cacheItem.timestamp.length > R_TIMESTAMP_MAX_SIZE) {\n // cacheItem.timestamp[cacheItem.timestamp.length-1] =\n cacheItem.timestamp.shift();\n }\n cacheItem.timestamp.push(t);\n }\n\n clearTimeStamp<TK, TV extends { timestamp: number[] }>(cache: Map<TK, TV>, params: Threshold) {\n const { L_TIME = this.L_TIME } = params;\n const now = Date.now();\n cache.forEach(item => {\n while (now - item.timestamp[0] > L_TIME) {\n item.timestamp.shift();\n }\n });\n }\n\n clearItemTimestamp<T extends { timestamp: number[] }>(cacheItem: T, params: Threshold) {\n const { L_TIME = this.L_TIME } = params;\n const now = Date.now();\n while (now - cacheItem.timestamp[0] > L_TIME) {\n cacheItem.timestamp.shift();\n }\n }\n}\n"]}
|