@shotstack/shotstack-canvas 1.6.6 → 1.7.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.
@@ -1,105 +1,124 @@
1
+ import { z } from 'zod';
1
2
  import { components } from '@shotstack/schemas';
2
3
 
3
- declare const CANVAS_CONFIG: {
4
- DEFAULTS: {
5
- width: number;
6
- height: number;
7
- pixelRatio: number;
8
- fontFamily: string;
9
- fontSize: number;
10
- color: string;
11
- textAlign: "center";
12
- };
13
- LIMITS: {
14
- minWidth: number;
15
- maxWidth: number;
16
- minHeight: number;
17
- maxHeight: number;
18
- minFontSize: number;
19
- maxFontSize: number;
20
- minDuration: number;
21
- maxDuration: number;
22
- maxTextLength: number;
23
- };
24
- ANIMATION_TYPES: readonly ["typewriter", "fadeIn", "slideIn", "shift", "ascend", "movingLetters"];
25
- };
4
+ declare const CanvasRichTextAssetSchema: z.ZodObject<{
5
+ type: z.ZodLiteral<"rich-text">;
6
+ text: z.ZodDefault<z.ZodString>;
7
+ width: z.ZodOptional<z.ZodDefault<z.ZodNumber>>;
8
+ height: z.ZodOptional<z.ZodDefault<z.ZodNumber>>;
9
+ font: z.ZodOptional<z.ZodObject<{
10
+ style: z.ZodOptional<z.ZodEnum<{
11
+ normal: "normal";
12
+ italic: "italic";
13
+ oblique: "oblique";
14
+ }>>;
15
+ family: z.ZodDefault<z.ZodString>;
16
+ size: z.ZodDefault<z.ZodNumber>;
17
+ weight: z.ZodDefault<z.ZodUnion<readonly [z.ZodString, z.ZodNumber]>>;
18
+ color: z.ZodDefault<z.ZodString>;
19
+ opacity: z.ZodDefault<z.ZodNumber>;
20
+ background: z.ZodOptional<z.ZodString>;
21
+ }, z.core.$strip>>;
22
+ style: z.ZodOptional<z.ZodObject<{
23
+ letterSpacing: z.ZodDefault<z.ZodNumber>;
24
+ lineHeight: z.ZodDefault<z.ZodNumber>;
25
+ textTransform: z.ZodDefault<z.ZodEnum<{
26
+ none: "none";
27
+ uppercase: "uppercase";
28
+ lowercase: "lowercase";
29
+ capitalize: "capitalize";
30
+ }>>;
31
+ textDecoration: z.ZodDefault<z.ZodEnum<{
32
+ none: "none";
33
+ underline: "underline";
34
+ "line-through": "line-through";
35
+ }>>;
36
+ gradient: z.ZodOptional<z.ZodObject<{
37
+ type: z.ZodDefault<z.ZodEnum<{
38
+ linear: "linear";
39
+ radial: "radial";
40
+ }>>;
41
+ angle: z.ZodDefault<z.ZodNumber>;
42
+ stops: z.ZodArray<z.ZodObject<{
43
+ offset: z.ZodNumber;
44
+ color: z.ZodString;
45
+ }, z.core.$strip>>;
46
+ }, z.core.$strip>>;
47
+ }, z.core.$strip>>;
48
+ stroke: z.ZodOptional<z.ZodObject<{
49
+ width: z.ZodDefault<z.ZodNumber>;
50
+ color: z.ZodDefault<z.ZodString>;
51
+ opacity: z.ZodDefault<z.ZodNumber>;
52
+ }, z.core.$strip>>;
53
+ shadow: z.ZodOptional<z.ZodObject<{
54
+ offsetX: z.ZodDefault<z.ZodNumber>;
55
+ offsetY: z.ZodDefault<z.ZodNumber>;
56
+ blur: z.ZodDefault<z.ZodNumber>;
57
+ color: z.ZodDefault<z.ZodString>;
58
+ opacity: z.ZodDefault<z.ZodNumber>;
59
+ }, z.core.$strip>>;
60
+ background: z.ZodOptional<z.ZodObject<{
61
+ borderRadius: z.ZodDefault<z.ZodOptional<z.ZodNumber>>;
62
+ color: z.ZodOptional<z.ZodString>;
63
+ opacity: z.ZodDefault<z.ZodNumber>;
64
+ }, z.core.$strip>>;
65
+ border: z.ZodOptional<z.ZodObject<{
66
+ width: z.ZodDefault<z.ZodNumber>;
67
+ color: z.ZodDefault<z.ZodString>;
68
+ opacity: z.ZodDefault<z.ZodNumber>;
69
+ radius: z.ZodDefault<z.ZodNumber>;
70
+ }, z.core.$strip>>;
71
+ padding: z.ZodOptional<z.ZodUnion<readonly [z.ZodNumber, z.ZodObject<{
72
+ top: z.ZodDefault<z.ZodNumber>;
73
+ right: z.ZodDefault<z.ZodNumber>;
74
+ bottom: z.ZodDefault<z.ZodNumber>;
75
+ left: z.ZodDefault<z.ZodNumber>;
76
+ }, z.core.$strip>]>>;
77
+ align: z.ZodOptional<z.ZodObject<{
78
+ horizontal: z.ZodDefault<z.ZodEnum<{
79
+ center: "center";
80
+ right: "right";
81
+ left: "left";
82
+ }>>;
83
+ vertical: z.ZodDefault<z.ZodEnum<{
84
+ top: "top";
85
+ bottom: "bottom";
86
+ middle: "middle";
87
+ }>>;
88
+ }, z.core.$strip>>;
89
+ animation: z.ZodOptional<z.ZodObject<{
90
+ preset: z.ZodEnum<{
91
+ typewriter: "typewriter";
92
+ fadeIn: "fadeIn";
93
+ slideIn: "slideIn";
94
+ shift: "shift";
95
+ ascend: "ascend";
96
+ movingLetters: "movingLetters";
97
+ }>;
98
+ speed: z.ZodDefault<z.ZodNumber>;
99
+ duration: z.ZodOptional<z.ZodNumber>;
100
+ style: z.ZodOptional<z.ZodEnum<{
101
+ character: "character";
102
+ word: "word";
103
+ }>>;
104
+ direction: z.ZodOptional<z.ZodEnum<{
105
+ right: "right";
106
+ left: "left";
107
+ up: "up";
108
+ down: "down";
109
+ }>>;
110
+ }, z.core.$strip>>;
111
+ customFonts: z.ZodOptional<z.ZodArray<z.ZodObject<{
112
+ src: z.ZodString;
113
+ family: z.ZodString;
114
+ weight: z.ZodOptional<z.ZodUnion<readonly [z.ZodString, z.ZodNumber]>>;
115
+ style: z.ZodOptional<z.ZodString>;
116
+ originalFamily: z.ZodOptional<z.ZodString>;
117
+ }, z.core.$strip>>>;
118
+ }, z.core.$strict>;
119
+ type CanvasRichTextAsset = z.infer<typeof CanvasRichTextAssetSchema>;
26
120
 
27
121
  type ShotstackRichTextAsset = components["schemas"]["RichTextAsset"];
28
- type RichTextValidated = Required<{
29
- type: "rich-text";
30
- text: string;
31
- width?: number;
32
- height?: number;
33
- font?: {
34
- family: string;
35
- size: number;
36
- weight: string | number;
37
- color: string;
38
- opacity: number;
39
- background?: string;
40
- };
41
- style?: {
42
- letterSpacing: number;
43
- lineHeight: number;
44
- textTransform: "none" | "uppercase" | "lowercase" | "capitalize";
45
- textDecoration: "none" | "underline" | "line-through";
46
- gradient?: {
47
- type: "linear" | "radial";
48
- angle: number;
49
- stops: {
50
- offset: number;
51
- color: string;
52
- }[];
53
- };
54
- };
55
- stroke?: {
56
- width: number;
57
- color: string;
58
- opacity: number;
59
- };
60
- shadow?: {
61
- offsetX: number;
62
- offsetY: number;
63
- blur: number;
64
- color: string;
65
- opacity: number;
66
- };
67
- background?: {
68
- color?: string;
69
- opacity: number;
70
- };
71
- border?: {
72
- width: number;
73
- color: string;
74
- opacity: number;
75
- radius: number;
76
- };
77
- padding?: number | {
78
- top: number;
79
- right: number;
80
- bottom: number;
81
- left: number;
82
- };
83
- align?: {
84
- horizontal: "left" | "center" | "right";
85
- vertical: "top" | "middle" | "bottom";
86
- };
87
- animation?: {
88
- preset: typeof CANVAS_CONFIG.ANIMATION_TYPES[number];
89
- speed: number;
90
- duration?: number;
91
- style?: "character" | "word";
92
- direction?: "left" | "right" | "up" | "down";
93
- };
94
- customFonts?: {
95
- src: string;
96
- family: string;
97
- weight?: string | number;
98
- style?: string;
99
- originalFamily?: string;
100
- }[];
101
- }>;
102
-
103
122
  type RGBA = {
104
123
  r: number;
105
124
  g: number;
@@ -221,7 +240,7 @@ type Renderer = {
221
240
  render(ops: DrawOp[]): Promise<void>;
222
241
  toPNG?: () => Promise<Buffer>;
223
242
  };
224
- type ValidAsset = RichTextValidated;
243
+ type ValidAsset = CanvasRichTextAsset;
225
244
  declare const isShadowFill: (op: DrawOp) => op is Extract<DrawOp, {
226
245
  op: "FillPath";
227
246
  }> & {
@@ -258,7 +277,7 @@ declare function createTextEngine(opts?: {
258
277
  wasmBaseURL?: string;
259
278
  }): Promise<{
260
279
  validate(input: unknown): {
261
- value: RichTextValidated;
280
+ value: CanvasRichTextAsset;
262
281
  };
263
282
  registerFontFromFile(path: string, desc: {
264
283
  family: string;
@@ -268,7 +287,7 @@ declare function createTextEngine(opts?: {
268
287
  family: string;
269
288
  weight?: string | number;
270
289
  }): Promise<void>;
271
- renderFrame(asset: RichTextValidated, tSeconds: number, clipDuration?: number): Promise<DrawOp[]>;
290
+ renderFrame(asset: CanvasRichTextAsset, tSeconds: number, clipDuration?: number): Promise<DrawOp[]>;
272
291
  createRenderer(p: {
273
292
  width?: number;
274
293
  height?: number;
@@ -277,8 +296,8 @@ declare function createTextEngine(opts?: {
277
296
  render(ops: DrawOp[]): Promise<void>;
278
297
  toPNG(): Promise<Buffer>;
279
298
  }>;
280
- generateVideo(asset: RichTextValidated, options: Partial<VideoGenerationOptions>): Promise<string>;
299
+ generateVideo(asset: CanvasRichTextAsset, options: Partial<VideoGenerationOptions>): Promise<string>;
281
300
  destroy(): void;
282
301
  }>;
283
302
 
284
- export { type DrawOp, type EngineInit, type Glyph, type GradientSpec, type RGBA, type Renderer, type ShapedLine, type ShotstackRichTextAsset, type ValidAsset, createTextEngine, isGlyphFill, isShadowFill };
303
+ export { type CanvasRichTextAsset, CanvasRichTextAssetSchema, type DrawOp, type EngineInit, type Glyph, type GradientSpec, type RGBA, type Renderer, type ShapedLine, type ShotstackRichTextAsset, type ValidAsset, createTextEngine, isGlyphFill, isShadowFill };
@@ -1,5 +1,15 @@
1
- // src/schema/asset-schema.ts
2
- import Joi from "joi";
1
+ // src/schema/zod-schema.ts
2
+ import { z } from "zod";
3
+ import {
4
+ richTextAssetSchema,
5
+ richTextFontSchema,
6
+ richTextStyleSchema,
7
+ richTextStrokeSchema,
8
+ richTextShadowSchema,
9
+ richTextBackgroundSchema,
10
+ richTextAlignmentSchema,
11
+ richTextAnimationSchema
12
+ } from "@shotstack/schemas/zod";
3
13
 
4
14
  // src/config/canvas-constants.ts
5
15
  var CANVAS_CONFIG = {
@@ -33,110 +43,127 @@ var CANVAS_CONFIG = {
33
43
  ]
34
44
  };
35
45
 
36
- // src/schema/asset-schema.ts
46
+ // src/schema/zod-schema.ts
37
47
  var HEX6 = /^#[A-Fa-f0-9]{6}$/;
38
- var gradientSchema = Joi.object({
39
- type: Joi.string().valid("linear", "radial").default("linear"),
40
- angle: Joi.number().min(0).max(360).default(0),
41
- stops: Joi.array().items(
42
- Joi.object({
43
- offset: Joi.number().min(0).max(1).required(),
44
- color: Joi.string().pattern(HEX6).required()
45
- }).unknown(false)
46
- ).min(2).required()
47
- }).unknown(false);
48
- var shadowSchema = Joi.object({
49
- offsetX: Joi.number().default(0),
50
- offsetY: Joi.number().default(0),
51
- blur: Joi.number().min(0).default(0),
52
- color: Joi.string().pattern(HEX6).default("#000000"),
53
- opacity: Joi.number().min(0).max(1).default(0.5)
54
- }).unknown(false);
55
- var strokeSchema = Joi.object({
56
- width: Joi.number().min(0).default(0),
57
- color: Joi.string().pattern(HEX6).default("#000000"),
58
- opacity: Joi.number().min(0).max(1).default(1)
59
- }).unknown(false);
60
- var fontSchema = Joi.object({
61
- family: Joi.string().default(CANVAS_CONFIG.DEFAULTS.fontFamily),
62
- size: Joi.number().min(CANVAS_CONFIG.LIMITS.minFontSize).max(CANVAS_CONFIG.LIMITS.maxFontSize).default(CANVAS_CONFIG.DEFAULTS.fontSize),
63
- weight: Joi.alternatives().try(Joi.string(), Joi.number()).default("400"),
64
- color: Joi.string().pattern(HEX6).default(CANVAS_CONFIG.DEFAULTS.color),
65
- opacity: Joi.number().min(0).max(1).default(1),
66
- background: Joi.string().pattern(HEX6).optional()
67
- }).unknown(false);
68
- var styleSchema = Joi.object({
69
- letterSpacing: Joi.number().default(0),
70
- lineHeight: Joi.number().min(0).max(10).default(1.2),
71
- textTransform: Joi.string().valid("none", "uppercase", "lowercase", "capitalize").default("none"),
72
- textDecoration: Joi.string().valid("none", "underline", "line-through").default("none"),
73
- gradient: gradientSchema.optional()
74
- }).unknown(false);
75
- var alignmentSchema = Joi.object({
76
- horizontal: Joi.string().valid("left", "center", "right").default(CANVAS_CONFIG.DEFAULTS.textAlign),
77
- vertical: Joi.string().valid("top", "middle", "bottom").default("middle")
78
- }).unknown(false);
79
- var animationSchema = Joi.object({
80
- preset: Joi.string().valid(...CANVAS_CONFIG.ANIMATION_TYPES),
81
- speed: Joi.number().min(0.1).max(10).default(1),
82
- duration: Joi.number().min(CANVAS_CONFIG.LIMITS.minDuration).max(CANVAS_CONFIG.LIMITS.maxDuration).optional(),
83
- style: Joi.string().valid("character", "word").optional().when("preset", {
84
- is: Joi.valid("typewriter", "shift", "fadeIn", "slideIn"),
85
- then: Joi.optional(),
86
- otherwise: Joi.forbidden()
87
- }),
88
- direction: Joi.string().optional().when("preset", {
89
- switch: [
90
- { is: "ascend", then: Joi.valid("up", "down") },
91
- { is: "shift", then: Joi.valid("left", "right", "up", "down") },
92
- { is: "slideIn", then: Joi.valid("left", "right", "up", "down") },
93
- { is: "movingLetters", then: Joi.valid("left", "right", "up", "down") }
94
- ],
95
- otherwise: Joi.forbidden()
48
+ var customFontSchema = z.object({
49
+ src: z.string().url(),
50
+ family: z.string(),
51
+ weight: z.union([z.string(), z.number()]).optional(),
52
+ style: z.string().optional(),
53
+ originalFamily: z.string().optional()
54
+ });
55
+ var borderSchema = z.object({
56
+ width: z.number().min(0).default(0),
57
+ color: z.string().regex(HEX6).default("#000000"),
58
+ opacity: z.number().min(0).max(1).default(1),
59
+ radius: z.number().min(0).default(0)
60
+ });
61
+ var paddingSchema = z.union([
62
+ z.number().min(0),
63
+ z.object({
64
+ top: z.number().min(0).default(0),
65
+ right: z.number().min(0).default(0),
66
+ bottom: z.number().min(0).default(0),
67
+ left: z.number().min(0).default(0)
96
68
  })
97
- }).unknown(false);
98
- var borderSchema = Joi.object({
99
- width: Joi.number().min(0).default(0),
100
- color: Joi.string().pattern(HEX6).default("#000000"),
101
- opacity: Joi.number().min(0).max(1).default(1),
102
- radius: Joi.number().min(0).default(0)
103
- }).unknown(false);
104
- var backgroundSchema = Joi.object({
105
- color: Joi.string().pattern(HEX6).optional(),
106
- opacity: Joi.number().min(0).max(1).default(1)
107
- }).unknown(false);
108
- var paddingSchema = Joi.alternatives().try(
109
- Joi.number().min(0).default(0),
110
- Joi.object({
111
- top: Joi.number().min(0).default(0),
112
- right: Joi.number().min(0).default(0),
113
- bottom: Joi.number().min(0).default(0),
114
- left: Joi.number().min(0).default(0)
115
- }).unknown(false)
116
- );
117
- var customFontSchema = Joi.object({
118
- src: Joi.string().uri().required(),
119
- family: Joi.string().required(),
120
- weight: Joi.alternatives().try(Joi.string(), Joi.number()).optional(),
121
- style: Joi.string().optional(),
122
- originalFamily: Joi.string().optional()
123
- }).unknown(false);
124
- var RichTextAssetSchema = Joi.object({
125
- type: Joi.string().valid("rich-text").required(),
126
- text: Joi.string().allow("").max(CANVAS_CONFIG.LIMITS.maxTextLength).default(""),
127
- width: Joi.number().min(CANVAS_CONFIG.LIMITS.minWidth).max(CANVAS_CONFIG.LIMITS.maxWidth).default(CANVAS_CONFIG.DEFAULTS.width).optional(),
128
- height: Joi.number().min(CANVAS_CONFIG.LIMITS.minHeight).max(CANVAS_CONFIG.LIMITS.maxHeight).default(CANVAS_CONFIG.DEFAULTS.height).optional(),
129
- font: fontSchema.optional(),
130
- style: styleSchema.optional(),
131
- stroke: strokeSchema.optional(),
132
- shadow: shadowSchema.optional(),
133
- background: backgroundSchema.optional(),
69
+ ]);
70
+ var canvasFontSchema = richTextFontSchema.extend({
71
+ family: z.string().default(CANVAS_CONFIG.DEFAULTS.fontFamily),
72
+ size: z.number().int().min(CANVAS_CONFIG.LIMITS.minFontSize).max(CANVAS_CONFIG.LIMITS.maxFontSize).default(CANVAS_CONFIG.DEFAULTS.fontSize),
73
+ weight: z.union([z.string(), z.number()]).default("400"),
74
+ color: z.string().regex(HEX6).default(CANVAS_CONFIG.DEFAULTS.color),
75
+ opacity: z.number().min(0).max(1).default(1),
76
+ background: z.string().regex(HEX6).optional()
77
+ });
78
+ var canvasGradientSchema = z.object({
79
+ type: z.enum(["linear", "radial"]).default("linear"),
80
+ angle: z.number().min(0).max(360).default(0),
81
+ stops: z.array(z.object({
82
+ offset: z.number().min(0).max(1),
83
+ color: z.string().regex(HEX6)
84
+ })).min(2)
85
+ });
86
+ var canvasStyleSchema = richTextStyleSchema.extend({
87
+ letterSpacing: z.number().default(0),
88
+ lineHeight: z.number().min(0).max(10).default(1.2),
89
+ textTransform: z.enum(["none", "uppercase", "lowercase", "capitalize"]).default("none"),
90
+ textDecoration: z.enum(["none", "underline", "line-through"]).default("none"),
91
+ gradient: canvasGradientSchema.optional()
92
+ });
93
+ var canvasStrokeSchema = richTextStrokeSchema.extend({
94
+ width: z.number().min(0).default(0),
95
+ color: z.string().regex(HEX6).default("#000000"),
96
+ opacity: z.number().min(0).max(1).default(1)
97
+ });
98
+ var canvasShadowSchema = richTextShadowSchema.extend({
99
+ offsetX: z.number().default(0),
100
+ offsetY: z.number().default(0),
101
+ blur: z.number().min(0).default(0),
102
+ color: z.string().regex(HEX6).default("#000000"),
103
+ opacity: z.number().min(0).max(1).default(0.5)
104
+ });
105
+ var canvasBackgroundSchema = richTextBackgroundSchema.extend({
106
+ color: z.string().regex(HEX6).optional(),
107
+ opacity: z.number().min(0).max(1).default(1)
108
+ });
109
+ var canvasAlignmentSchema = richTextAlignmentSchema.extend({
110
+ horizontal: z.enum(["left", "center", "right"]).default(CANVAS_CONFIG.DEFAULTS.textAlign),
111
+ vertical: z.enum(["top", "middle", "bottom"]).default("middle")
112
+ });
113
+ var canvasAnimationSchema = richTextAnimationSchema.extend({
114
+ preset: z.enum(CANVAS_CONFIG.ANIMATION_TYPES),
115
+ speed: z.number().min(0.1).max(10).default(1),
116
+ duration: z.number().min(CANVAS_CONFIG.LIMITS.minDuration).max(CANVAS_CONFIG.LIMITS.maxDuration).optional(),
117
+ style: z.enum(["character", "word"]).optional(),
118
+ direction: z.enum(["left", "right", "up", "down"]).optional()
119
+ }).superRefine((data, ctx) => {
120
+ const presetsWithStyle = ["typewriter", "shift", "fadeIn", "slideIn"];
121
+ if (data.style && !presetsWithStyle.includes(data.preset)) {
122
+ ctx.addIssue({
123
+ code: z.ZodIssueCode.custom,
124
+ message: `style is not allowed for preset "${data.preset}"`,
125
+ path: ["style"]
126
+ });
127
+ }
128
+ const directionRules = {
129
+ ascend: ["up", "down"],
130
+ shift: ["left", "right", "up", "down"],
131
+ slideIn: ["left", "right", "up", "down"],
132
+ movingLetters: ["left", "right", "up", "down"]
133
+ };
134
+ if (data.direction) {
135
+ const allowedDirections = directionRules[data.preset];
136
+ if (!allowedDirections) {
137
+ ctx.addIssue({
138
+ code: z.ZodIssueCode.custom,
139
+ message: `direction is not allowed for preset "${data.preset}"`,
140
+ path: ["direction"]
141
+ });
142
+ } else if (!allowedDirections.includes(data.direction)) {
143
+ ctx.addIssue({
144
+ code: z.ZodIssueCode.custom,
145
+ message: `direction "${data.direction}" is not valid for preset "${data.preset}"`,
146
+ path: ["direction"]
147
+ });
148
+ }
149
+ }
150
+ });
151
+ var CanvasRichTextAssetSchema = richTextAssetSchema.extend({
152
+ type: z.literal("rich-text"),
153
+ text: z.string().max(CANVAS_CONFIG.LIMITS.maxTextLength).default(""),
154
+ width: z.number().int().min(CANVAS_CONFIG.LIMITS.minWidth).max(CANVAS_CONFIG.LIMITS.maxWidth).default(CANVAS_CONFIG.DEFAULTS.width).optional(),
155
+ height: z.number().int().min(CANVAS_CONFIG.LIMITS.minHeight).max(CANVAS_CONFIG.LIMITS.maxHeight).default(CANVAS_CONFIG.DEFAULTS.height).optional(),
156
+ font: canvasFontSchema.optional(),
157
+ style: canvasStyleSchema.optional(),
158
+ stroke: canvasStrokeSchema.optional(),
159
+ shadow: canvasShadowSchema.optional(),
160
+ background: canvasBackgroundSchema.optional(),
134
161
  border: borderSchema.optional(),
135
162
  padding: paddingSchema.optional(),
136
- align: alignmentSchema.optional(),
137
- animation: animationSchema.optional(),
138
- customFonts: Joi.array().items(customFontSchema).optional()
139
- }).unknown(false);
163
+ align: canvasAlignmentSchema.optional(),
164
+ animation: canvasAnimationSchema.optional(),
165
+ customFonts: z.array(customFontSchema).optional()
166
+ }).strict();
140
167
 
141
168
  // src/wasm/hb-loader.ts
142
169
  var hbSingleton = null;
@@ -2444,19 +2471,12 @@ async function createTextEngine(opts = {}) {
2444
2471
  }
2445
2472
  return {
2446
2473
  validate(input) {
2447
- try {
2448
- const { value, error } = RichTextAssetSchema.validate(input, {
2449
- abortEarly: false,
2450
- convert: true
2451
- });
2452
- if (error) throw error;
2453
- return { value };
2454
- } catch (err) {
2455
- if (err instanceof Error) {
2456
- throw new Error(`Validation failed: ${err.message}`);
2457
- }
2458
- throw new Error(`Validation failed: ${String(err)}`);
2474
+ const result = CanvasRichTextAssetSchema.safeParse(input);
2475
+ if (!result.success) {
2476
+ const messages = result.error.issues.map((i) => i.message).join(". ");
2477
+ throw new Error(`Validation failed: ${messages}`);
2459
2478
  }
2479
+ return { value: result.data };
2460
2480
  },
2461
2481
  async registerFontFromFile(path, desc) {
2462
2482
  try {
@@ -2650,6 +2670,7 @@ async function createTextEngine(opts = {}) {
2650
2670
  };
2651
2671
  }
2652
2672
  export {
2673
+ CanvasRichTextAssetSchema,
2653
2674
  createTextEngine,
2654
2675
  isGlyphFill2 as isGlyphFill,
2655
2676
  isShadowFill2 as isShadowFill