apexify.js 4.9.25 → 4.9.27

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.
Files changed (198) hide show
  1. package/README.md +358 -47
  2. package/dist/cjs/Canvas/ApexPainter.d.ts +189 -0
  3. package/dist/cjs/Canvas/ApexPainter.d.ts.map +1 -0
  4. package/dist/{esm/canvas → cjs/Canvas}/ApexPainter.js +461 -352
  5. package/dist/cjs/Canvas/ApexPainter.js.map +1 -0
  6. package/dist/cjs/Canvas/utils/Background/bg.d.ts +43 -0
  7. package/dist/cjs/Canvas/utils/Background/bg.d.ts.map +1 -0
  8. package/dist/cjs/Canvas/utils/Background/bg.js +228 -0
  9. package/dist/cjs/Canvas/utils/Background/bg.js.map +1 -0
  10. package/dist/cjs/{canvas → Canvas}/utils/Charts/charts.d.ts.map +1 -1
  11. package/dist/{esm/canvas → cjs/Canvas}/utils/Charts/charts.js.map +1 -1
  12. package/dist/cjs/{canvas → Canvas}/utils/Custom/customLines.d.ts.map +1 -1
  13. package/dist/{esm/canvas → cjs/Canvas}/utils/Custom/customLines.js +2 -2
  14. package/dist/cjs/Canvas/utils/Custom/customLines.js.map +1 -0
  15. package/dist/cjs/{canvas → Canvas}/utils/General/conversion.d.ts.map +1 -1
  16. package/dist/cjs/{canvas → Canvas}/utils/General/conversion.js.map +1 -1
  17. package/dist/cjs/{canvas → Canvas}/utils/General/general functions.d.ts.map +1 -1
  18. package/dist/{esm/canvas → cjs/Canvas}/utils/General/general functions.js.map +1 -1
  19. package/dist/cjs/Canvas/utils/Image/imageFilters.d.ts +11 -0
  20. package/dist/cjs/Canvas/utils/Image/imageFilters.d.ts.map +1 -0
  21. package/dist/cjs/Canvas/utils/Image/imageFilters.js +307 -0
  22. package/dist/cjs/Canvas/utils/Image/imageFilters.js.map +1 -0
  23. package/dist/cjs/Canvas/utils/Image/imageProperties.d.ts +50 -0
  24. package/dist/cjs/Canvas/utils/Image/imageProperties.d.ts.map +1 -0
  25. package/dist/cjs/Canvas/utils/Image/imageProperties.js +271 -0
  26. package/dist/cjs/Canvas/utils/Image/imageProperties.js.map +1 -0
  27. package/dist/cjs/Canvas/utils/Image/professionalImageFilters.d.ts +11 -0
  28. package/dist/cjs/Canvas/utils/Image/professionalImageFilters.d.ts.map +1 -0
  29. package/dist/cjs/Canvas/utils/Image/professionalImageFilters.js +351 -0
  30. package/dist/cjs/Canvas/utils/Image/professionalImageFilters.js.map +1 -0
  31. package/dist/cjs/Canvas/utils/Image/simpleProfessionalFilters.d.ts +11 -0
  32. package/dist/cjs/Canvas/utils/Image/simpleProfessionalFilters.d.ts.map +1 -0
  33. package/dist/cjs/Canvas/utils/Image/simpleProfessionalFilters.js +215 -0
  34. package/dist/cjs/Canvas/utils/Image/simpleProfessionalFilters.js.map +1 -0
  35. package/dist/cjs/Canvas/utils/Patterns/enhancedPatternRenderer.d.ts +71 -0
  36. package/dist/cjs/Canvas/utils/Patterns/enhancedPatternRenderer.d.ts.map +1 -0
  37. package/dist/cjs/Canvas/utils/Patterns/enhancedPatternRenderer.js +392 -0
  38. package/dist/cjs/Canvas/utils/Patterns/enhancedPatternRenderer.js.map +1 -0
  39. package/dist/cjs/Canvas/utils/Shapes/shapes.d.ts +29 -0
  40. package/dist/cjs/Canvas/utils/Shapes/shapes.d.ts.map +1 -0
  41. package/dist/cjs/Canvas/utils/Shapes/shapes.js +334 -0
  42. package/dist/cjs/Canvas/utils/Shapes/shapes.js.map +1 -0
  43. package/dist/cjs/Canvas/utils/Texts/enhancedTextRenderer.d.ts +127 -0
  44. package/dist/cjs/Canvas/utils/Texts/enhancedTextRenderer.d.ts.map +1 -0
  45. package/dist/cjs/Canvas/utils/Texts/enhancedTextRenderer.js +365 -0
  46. package/dist/cjs/Canvas/utils/Texts/enhancedTextRenderer.js.map +1 -0
  47. package/dist/cjs/{canvas → Canvas}/utils/Texts/textProperties.d.ts.map +1 -1
  48. package/dist/{esm/canvas → cjs/Canvas}/utils/Texts/textProperties.js.map +1 -1
  49. package/dist/{esm/canvas → cjs/Canvas}/utils/types.d.ts +227 -131
  50. package/dist/cjs/Canvas/utils/types.d.ts.map +1 -0
  51. package/dist/cjs/{canvas → Canvas}/utils/types.js +0 -1
  52. package/dist/cjs/Canvas/utils/types.js.map +1 -0
  53. package/dist/cjs/Canvas/utils/utils.d.ts +22 -0
  54. package/dist/cjs/Canvas/utils/utils.d.ts.map +1 -0
  55. package/dist/{esm/canvas → cjs/Canvas}/utils/utils.js +17 -7
  56. package/dist/cjs/Canvas/utils/utils.js.map +1 -0
  57. package/dist/cjs/index.d.ts +6 -3
  58. package/dist/cjs/index.d.ts.map +1 -1
  59. package/dist/cjs/index.js +8 -6
  60. package/dist/cjs/index.js.map +1 -1
  61. package/dist/cjs/tsconfig.cjs.tsbuildinfo +1 -1
  62. package/dist/cjs/utils.d.ts +1 -1
  63. package/dist/cjs/utils.js +1 -1
  64. package/dist/esm/Canvas/ApexPainter.d.ts +189 -0
  65. package/dist/esm/Canvas/ApexPainter.d.ts.map +1 -0
  66. package/dist/{cjs/canvas → esm/Canvas}/ApexPainter.js +461 -352
  67. package/dist/esm/Canvas/ApexPainter.js.map +1 -0
  68. package/dist/esm/Canvas/utils/Background/bg.d.ts +43 -0
  69. package/dist/esm/Canvas/utils/Background/bg.d.ts.map +1 -0
  70. package/dist/esm/Canvas/utils/Background/bg.js +228 -0
  71. package/dist/esm/Canvas/utils/Background/bg.js.map +1 -0
  72. package/dist/esm/{canvas → Canvas}/utils/Charts/charts.d.ts.map +1 -1
  73. package/dist/{cjs/canvas → esm/Canvas}/utils/Charts/charts.js.map +1 -1
  74. package/dist/esm/{canvas → Canvas}/utils/Custom/customLines.d.ts.map +1 -1
  75. package/dist/{cjs/canvas → esm/Canvas}/utils/Custom/customLines.js +2 -2
  76. package/dist/esm/Canvas/utils/Custom/customLines.js.map +1 -0
  77. package/dist/esm/{canvas → Canvas}/utils/General/conversion.d.ts.map +1 -1
  78. package/dist/esm/{canvas → Canvas}/utils/General/conversion.js.map +1 -1
  79. package/dist/esm/{canvas → Canvas}/utils/General/general functions.d.ts.map +1 -1
  80. package/dist/{cjs/canvas → esm/Canvas}/utils/General/general functions.js.map +1 -1
  81. package/dist/esm/Canvas/utils/Image/imageFilters.d.ts +11 -0
  82. package/dist/esm/Canvas/utils/Image/imageFilters.d.ts.map +1 -0
  83. package/dist/esm/Canvas/utils/Image/imageFilters.js +307 -0
  84. package/dist/esm/Canvas/utils/Image/imageFilters.js.map +1 -0
  85. package/dist/esm/Canvas/utils/Image/imageProperties.d.ts +50 -0
  86. package/dist/esm/Canvas/utils/Image/imageProperties.d.ts.map +1 -0
  87. package/dist/esm/Canvas/utils/Image/imageProperties.js +271 -0
  88. package/dist/esm/Canvas/utils/Image/imageProperties.js.map +1 -0
  89. package/dist/esm/Canvas/utils/Image/professionalImageFilters.d.ts +11 -0
  90. package/dist/esm/Canvas/utils/Image/professionalImageFilters.d.ts.map +1 -0
  91. package/dist/esm/Canvas/utils/Image/professionalImageFilters.js +351 -0
  92. package/dist/esm/Canvas/utils/Image/professionalImageFilters.js.map +1 -0
  93. package/dist/esm/Canvas/utils/Image/simpleProfessionalFilters.d.ts +11 -0
  94. package/dist/esm/Canvas/utils/Image/simpleProfessionalFilters.d.ts.map +1 -0
  95. package/dist/esm/Canvas/utils/Image/simpleProfessionalFilters.js +215 -0
  96. package/dist/esm/Canvas/utils/Image/simpleProfessionalFilters.js.map +1 -0
  97. package/dist/esm/Canvas/utils/Patterns/enhancedPatternRenderer.d.ts +71 -0
  98. package/dist/esm/Canvas/utils/Patterns/enhancedPatternRenderer.d.ts.map +1 -0
  99. package/dist/esm/Canvas/utils/Patterns/enhancedPatternRenderer.js +392 -0
  100. package/dist/esm/Canvas/utils/Patterns/enhancedPatternRenderer.js.map +1 -0
  101. package/dist/esm/Canvas/utils/Shapes/shapes.d.ts +29 -0
  102. package/dist/esm/Canvas/utils/Shapes/shapes.d.ts.map +1 -0
  103. package/dist/esm/Canvas/utils/Shapes/shapes.js +334 -0
  104. package/dist/esm/Canvas/utils/Shapes/shapes.js.map +1 -0
  105. package/dist/esm/Canvas/utils/Texts/enhancedTextRenderer.d.ts +127 -0
  106. package/dist/esm/Canvas/utils/Texts/enhancedTextRenderer.d.ts.map +1 -0
  107. package/dist/esm/Canvas/utils/Texts/enhancedTextRenderer.js +365 -0
  108. package/dist/esm/Canvas/utils/Texts/enhancedTextRenderer.js.map +1 -0
  109. package/dist/esm/{canvas → Canvas}/utils/Texts/textProperties.d.ts.map +1 -1
  110. package/dist/{cjs/canvas → esm/Canvas}/utils/Texts/textProperties.js.map +1 -1
  111. package/dist/{cjs/canvas → esm/Canvas}/utils/types.d.ts +227 -131
  112. package/dist/esm/Canvas/utils/types.d.ts.map +1 -0
  113. package/dist/esm/{canvas → Canvas}/utils/types.js +0 -1
  114. package/dist/esm/Canvas/utils/types.js.map +1 -0
  115. package/dist/esm/Canvas/utils/utils.d.ts +22 -0
  116. package/dist/esm/Canvas/utils/utils.d.ts.map +1 -0
  117. package/dist/{cjs/canvas → esm/Canvas}/utils/utils.js +17 -7
  118. package/dist/esm/Canvas/utils/utils.js.map +1 -0
  119. package/dist/esm/index.d.ts +6 -3
  120. package/dist/esm/index.d.ts.map +1 -1
  121. package/dist/esm/index.js +8 -6
  122. package/dist/esm/index.js.map +1 -1
  123. package/dist/esm/tsconfig.esm.tsbuildinfo +1 -1
  124. package/dist/esm/utils.d.ts +1 -1
  125. package/dist/esm/utils.js +1 -1
  126. package/lib/{canvas → Canvas}/ApexPainter.ts +1325 -1218
  127. package/lib/Canvas/utils/Background/bg.ts +285 -0
  128. package/lib/{canvas → Canvas}/utils/Custom/customLines.ts +3 -3
  129. package/lib/Canvas/utils/Image/imageFilters.ts +356 -0
  130. package/lib/Canvas/utils/Image/imageProperties.ts +382 -0
  131. package/lib/Canvas/utils/Image/professionalImageFilters.ts +391 -0
  132. package/lib/Canvas/utils/Image/simpleProfessionalFilters.ts +229 -0
  133. package/lib/Canvas/utils/Patterns/enhancedPatternRenderer.ts +444 -0
  134. package/lib/Canvas/utils/Shapes/shapes.ts +528 -0
  135. package/lib/Canvas/utils/Texts/enhancedTextRenderer.ts +478 -0
  136. package/lib/{canvas → Canvas}/utils/types.ts +301 -117
  137. package/lib/{canvas → Canvas}/utils/utils.ts +85 -72
  138. package/lib/index.ts +8 -9
  139. package/lib/utils.ts +1 -1
  140. package/package.json +107 -191
  141. package/dist/cjs/canvas/ApexPainter.d.ts +0 -145
  142. package/dist/cjs/canvas/ApexPainter.d.ts.map +0 -1
  143. package/dist/cjs/canvas/ApexPainter.js.map +0 -1
  144. package/dist/cjs/canvas/utils/Background/bg.d.ts +0 -31
  145. package/dist/cjs/canvas/utils/Background/bg.d.ts.map +0 -1
  146. package/dist/cjs/canvas/utils/Background/bg.js +0 -161
  147. package/dist/cjs/canvas/utils/Background/bg.js.map +0 -1
  148. package/dist/cjs/canvas/utils/Custom/customLines.js.map +0 -1
  149. package/dist/cjs/canvas/utils/Image/imageProperties.d.ts +0 -115
  150. package/dist/cjs/canvas/utils/Image/imageProperties.d.ts.map +0 -1
  151. package/dist/cjs/canvas/utils/Image/imageProperties.js +0 -602
  152. package/dist/cjs/canvas/utils/Image/imageProperties.js.map +0 -1
  153. package/dist/cjs/canvas/utils/types.d.ts.map +0 -1
  154. package/dist/cjs/canvas/utils/types.js.map +0 -1
  155. package/dist/cjs/canvas/utils/utils.d.ts +0 -19
  156. package/dist/cjs/canvas/utils/utils.d.ts.map +0 -1
  157. package/dist/cjs/canvas/utils/utils.js.map +0 -1
  158. package/dist/esm/canvas/ApexPainter.d.ts +0 -145
  159. package/dist/esm/canvas/ApexPainter.d.ts.map +0 -1
  160. package/dist/esm/canvas/ApexPainter.js.map +0 -1
  161. package/dist/esm/canvas/utils/Background/bg.d.ts +0 -31
  162. package/dist/esm/canvas/utils/Background/bg.d.ts.map +0 -1
  163. package/dist/esm/canvas/utils/Background/bg.js +0 -161
  164. package/dist/esm/canvas/utils/Background/bg.js.map +0 -1
  165. package/dist/esm/canvas/utils/Custom/customLines.js.map +0 -1
  166. package/dist/esm/canvas/utils/Image/imageProperties.d.ts +0 -115
  167. package/dist/esm/canvas/utils/Image/imageProperties.d.ts.map +0 -1
  168. package/dist/esm/canvas/utils/Image/imageProperties.js +0 -602
  169. package/dist/esm/canvas/utils/Image/imageProperties.js.map +0 -1
  170. package/dist/esm/canvas/utils/types.d.ts.map +0 -1
  171. package/dist/esm/canvas/utils/types.js.map +0 -1
  172. package/dist/esm/canvas/utils/utils.d.ts +0 -19
  173. package/dist/esm/canvas/utils/utils.d.ts.map +0 -1
  174. package/dist/esm/canvas/utils/utils.js.map +0 -1
  175. package/lib/canvas/utils/Background/bg.ts +0 -211
  176. package/lib/canvas/utils/Image/imageProperties.ts +0 -835
  177. /package/dist/cjs/{canvas → Canvas}/utils/Charts/charts.d.ts +0 -0
  178. /package/dist/cjs/{canvas → Canvas}/utils/Charts/charts.js +0 -0
  179. /package/dist/cjs/{canvas → Canvas}/utils/Custom/customLines.d.ts +0 -0
  180. /package/dist/cjs/{canvas → Canvas}/utils/General/conversion.d.ts +0 -0
  181. /package/dist/cjs/{canvas → Canvas}/utils/General/conversion.js +0 -0
  182. /package/dist/cjs/{canvas → Canvas}/utils/General/general functions.d.ts +0 -0
  183. /package/dist/cjs/{canvas → Canvas}/utils/General/general functions.js +0 -0
  184. /package/dist/cjs/{canvas → Canvas}/utils/Texts/textProperties.d.ts +0 -0
  185. /package/dist/cjs/{canvas → Canvas}/utils/Texts/textProperties.js +0 -0
  186. /package/dist/esm/{canvas → Canvas}/utils/Charts/charts.d.ts +0 -0
  187. /package/dist/esm/{canvas → Canvas}/utils/Charts/charts.js +0 -0
  188. /package/dist/esm/{canvas → Canvas}/utils/Custom/customLines.d.ts +0 -0
  189. /package/dist/esm/{canvas → Canvas}/utils/General/conversion.d.ts +0 -0
  190. /package/dist/esm/{canvas → Canvas}/utils/General/conversion.js +0 -0
  191. /package/dist/esm/{canvas → Canvas}/utils/General/general functions.d.ts +0 -0
  192. /package/dist/esm/{canvas → Canvas}/utils/General/general functions.js +0 -0
  193. /package/dist/esm/{canvas → Canvas}/utils/Texts/textProperties.d.ts +0 -0
  194. /package/dist/esm/{canvas → Canvas}/utils/Texts/textProperties.js +0 -0
  195. /package/lib/{canvas → Canvas}/utils/Charts/charts.ts +0 -0
  196. /package/lib/{canvas → Canvas}/utils/General/conversion.ts +0 -0
  197. /package/lib/{canvas → Canvas}/utils/General/general functions.ts +0 -0
  198. /package/lib/{canvas → Canvas}/utils/Texts/textProperties.ts +0 -0
@@ -0,0 +1,444 @@
1
+ import { SKRSContext2D, Canvas } from '@napi-rs/canvas';
2
+ import { PatternOptions, GradientConfig } from '../types';
3
+ import { createGradientFill } from '../Image/imageProperties';
4
+ import { loadImage } from '@napi-rs/canvas';
5
+ import path from 'path';
6
+
7
+ /**
8
+ * Enhanced pattern renderer supporting all pattern types
9
+ */
10
+ export class EnhancedPatternRenderer {
11
+ /**
12
+ * Renders a pattern overlay on the canvas
13
+ * @param ctx - Canvas 2D context
14
+ * @param canvas - Canvas instance
15
+ * @param patternOptions - Pattern configuration
16
+ */
17
+ static async renderPattern(
18
+ ctx: SKRSContext2D,
19
+ canvas: Canvas,
20
+ patternOptions: PatternOptions
21
+ ): Promise<void> {
22
+ if (!patternOptions || !patternOptions.type) return;
23
+
24
+ ctx.save();
25
+
26
+ try {
27
+ // Set pattern opacity
28
+ const opacity = patternOptions.opacity !== undefined ? patternOptions.opacity : 0.3;
29
+ ctx.globalAlpha = opacity;
30
+
31
+ // Set blend mode
32
+ const blendMode = patternOptions.blendMode || 'overlay';
33
+ ctx.globalCompositeOperation = blendMode;
34
+
35
+ // Apply rotation if specified
36
+ if (patternOptions.rotation && patternOptions.rotation !== 0) {
37
+ const centerX = canvas.width / 2;
38
+ const centerY = canvas.height / 2;
39
+ ctx.translate(centerX, centerY);
40
+ ctx.rotate((patternOptions.rotation * Math.PI) / 180);
41
+ ctx.translate(-centerX, -centerY);
42
+ }
43
+
44
+ // Apply offset if specified
45
+ if (patternOptions.offsetX || patternOptions.offsetY) {
46
+ ctx.translate(patternOptions.offsetX || 0, patternOptions.offsetY || 0);
47
+ }
48
+
49
+ // Render based on pattern type
50
+ switch (patternOptions.type) {
51
+ case 'grid':
52
+ this.renderGridPattern(ctx, canvas, patternOptions);
53
+ break;
54
+ case 'dots':
55
+ this.renderDotsPattern(ctx, canvas, patternOptions);
56
+ break;
57
+ case 'diagonal':
58
+ this.renderDiagonalPattern(ctx, canvas, patternOptions);
59
+ break;
60
+ case 'stripes':
61
+ this.renderStripesPattern(ctx, canvas, patternOptions);
62
+ break;
63
+ case 'waves':
64
+ this.renderWavesPattern(ctx, canvas, patternOptions);
65
+ break;
66
+ case 'crosses':
67
+ this.renderCrossesPattern(ctx, canvas, patternOptions);
68
+ break;
69
+ case 'hexagons':
70
+ this.renderHexagonsPattern(ctx, canvas, patternOptions);
71
+ break;
72
+ case 'checkerboard':
73
+ this.renderCheckerboardPattern(ctx, canvas, patternOptions);
74
+ break;
75
+ case 'diamonds':
76
+ this.renderDiamondsPattern(ctx, canvas, patternOptions);
77
+ break;
78
+ case 'triangles':
79
+ this.renderTrianglesPattern(ctx, canvas, patternOptions);
80
+ break;
81
+ case 'stars':
82
+ this.renderStarsPattern(ctx, canvas, patternOptions);
83
+ break;
84
+ case 'polka':
85
+ this.renderPolkaPattern(ctx, canvas, patternOptions);
86
+ break;
87
+ case 'custom':
88
+ await this.renderCustomPattern(ctx, canvas, patternOptions);
89
+ break;
90
+ default:
91
+ console.warn(`Unknown pattern type: ${patternOptions.type}`);
92
+ }
93
+ } finally {
94
+ ctx.restore();
95
+ }
96
+ }
97
+
98
+ /**
99
+ * Renders grid pattern
100
+ */
101
+ private static renderGridPattern(ctx: SKRSContext2D, canvas: Canvas, options: PatternOptions): void {
102
+ const size = options.size || 20;
103
+ const spacing = options.spacing || 10;
104
+ const color = options.color || '#ffffff';
105
+
106
+ ctx.strokeStyle = color;
107
+ ctx.lineWidth = 1;
108
+
109
+ // Vertical lines
110
+ for (let x = 0; x <= canvas.width; x += size + spacing) {
111
+ ctx.beginPath();
112
+ ctx.moveTo(x, 0);
113
+ ctx.lineTo(x, canvas.height);
114
+ ctx.stroke();
115
+ }
116
+
117
+ // Horizontal lines
118
+ for (let y = 0; y <= canvas.height; y += size + spacing) {
119
+ ctx.beginPath();
120
+ ctx.moveTo(0, y);
121
+ ctx.lineTo(canvas.width, y);
122
+ ctx.stroke();
123
+ }
124
+ }
125
+
126
+ /**
127
+ * Renders dots pattern
128
+ */
129
+ private static renderDotsPattern(ctx: SKRSContext2D, canvas: Canvas, options: PatternOptions): void {
130
+ const size = options.size || 20;
131
+ const spacing = options.spacing || 10;
132
+ const color = options.color || '#ffffff';
133
+
134
+ ctx.fillStyle = color;
135
+
136
+ for (let x = 0; x <= canvas.width; x += size + spacing) {
137
+ for (let y = 0; y <= canvas.height; y += size + spacing) {
138
+ ctx.beginPath();
139
+ ctx.arc(x, y, size / 4, 0, Math.PI * 2);
140
+ ctx.fill();
141
+ }
142
+ }
143
+ }
144
+
145
+ /**
146
+ * Renders diagonal pattern
147
+ */
148
+ private static renderDiagonalPattern(ctx: SKRSContext2D, canvas: Canvas, options: PatternOptions): void {
149
+ const size = options.size || 20;
150
+ const spacing = options.spacing || 10;
151
+ const color = options.color || '#ffffff';
152
+
153
+ ctx.strokeStyle = color;
154
+ ctx.lineWidth = 2;
155
+
156
+ const diagonalSpacing = size + spacing;
157
+
158
+ // Diagonal lines going up-right
159
+ for (let i = -canvas.height; i <= canvas.width; i += diagonalSpacing) {
160
+ ctx.beginPath();
161
+ ctx.moveTo(i, 0);
162
+ ctx.lineTo(i + canvas.height, canvas.height);
163
+ ctx.stroke();
164
+ }
165
+ }
166
+
167
+ /**
168
+ * Renders stripes pattern
169
+ */
170
+ private static renderStripesPattern(ctx: SKRSContext2D, canvas: Canvas, options: PatternOptions): void {
171
+ const size = options.size || 20;
172
+ const spacing = options.spacing || 10;
173
+ const color = options.color || '#ffffff';
174
+
175
+ ctx.fillStyle = color;
176
+
177
+ for (let y = 0; y <= canvas.height; y += size + spacing) {
178
+ ctx.fillRect(0, y, canvas.width, size);
179
+ }
180
+ }
181
+
182
+ /**
183
+ * Renders waves pattern
184
+ */
185
+ private static renderWavesPattern(ctx: SKRSContext2D, canvas: Canvas, options: PatternOptions): void {
186
+ const size = options.size || 20;
187
+ const spacing = options.spacing || 10;
188
+ const color = options.color || '#ffffff';
189
+
190
+ ctx.strokeStyle = color;
191
+ ctx.lineWidth = 2;
192
+
193
+ for (let y = 0; y <= canvas.height; y += size + spacing) {
194
+ ctx.beginPath();
195
+ ctx.moveTo(0, y);
196
+
197
+ for (let x = 0; x <= canvas.width; x += 10) {
198
+ const waveY = y + Math.sin(x * 0.1) * (size / 4);
199
+ ctx.lineTo(x, waveY);
200
+ }
201
+
202
+ ctx.stroke();
203
+ }
204
+ }
205
+
206
+ /**
207
+ * Renders crosses pattern
208
+ */
209
+ private static renderCrossesPattern(ctx: SKRSContext2D, canvas: Canvas, options: PatternOptions): void {
210
+ const size = options.size || 20;
211
+ const spacing = options.spacing || 10;
212
+ const color = options.color || '#ffffff';
213
+
214
+ ctx.strokeStyle = color;
215
+ ctx.lineWidth = 2;
216
+
217
+ for (let x = 0; x <= canvas.width; x += size + spacing) {
218
+ for (let y = 0; y <= canvas.height; y += size + spacing) {
219
+ const crossSize = size / 2;
220
+
221
+ // Horizontal line
222
+ ctx.beginPath();
223
+ ctx.moveTo(x - crossSize, y);
224
+ ctx.lineTo(x + crossSize, y);
225
+ ctx.stroke();
226
+
227
+ // Vertical line
228
+ ctx.beginPath();
229
+ ctx.moveTo(x, y - crossSize);
230
+ ctx.lineTo(x, y + crossSize);
231
+ ctx.stroke();
232
+ }
233
+ }
234
+ }
235
+
236
+ /**
237
+ * Renders hexagons pattern
238
+ */
239
+ private static renderHexagonsPattern(ctx: SKRSContext2D, canvas: Canvas, options: PatternOptions): void {
240
+ const size = options.size || 20;
241
+ const spacing = options.spacing || 10;
242
+ const color = options.color || '#ffffff';
243
+
244
+ ctx.strokeStyle = color;
245
+ ctx.lineWidth = 2;
246
+
247
+ const hexWidth = size;
248
+ const hexHeight = size * Math.sqrt(3) / 2;
249
+
250
+ for (let x = 0; x <= canvas.width + hexWidth; x += hexWidth + spacing) {
251
+ for (let y = 0; y <= canvas.height + hexHeight; y += hexHeight * 1.5 + spacing) {
252
+ this.drawHexagon(ctx, x, y, hexWidth / 2);
253
+ }
254
+ }
255
+ }
256
+
257
+ /**
258
+ * Renders checkerboard pattern
259
+ */
260
+ private static renderCheckerboardPattern(ctx: SKRSContext2D, canvas: Canvas, options: PatternOptions): void {
261
+ const size = options.size || 20;
262
+ const color = options.color || '#ffffff';
263
+ const secondaryColor = options.secondaryColor || 'transparent';
264
+
265
+ for (let x = 0; x <= canvas.width; x += size) {
266
+ for (let y = 0; y <= canvas.height; y += size) {
267
+ const isEven = ((x / size) + (y / size)) % 2 === 0;
268
+ ctx.fillStyle = isEven ? color : secondaryColor;
269
+ ctx.fillRect(x, y, size, size);
270
+ }
271
+ }
272
+ }
273
+
274
+ /**
275
+ * Renders diamonds pattern
276
+ */
277
+ private static renderDiamondsPattern(ctx: SKRSContext2D, canvas: Canvas, options: PatternOptions): void {
278
+ const size = options.size || 20;
279
+ const spacing = options.spacing || 10;
280
+ const color = options.color || '#ffffff';
281
+
282
+ ctx.strokeStyle = color;
283
+ ctx.lineWidth = 2;
284
+
285
+ for (let x = 0; x <= canvas.width + size; x += size + spacing) {
286
+ for (let y = 0; y <= canvas.height + size; y += size + spacing) {
287
+ this.drawDiamond(ctx, x, y, size / 2);
288
+ }
289
+ }
290
+ }
291
+
292
+ /**
293
+ * Renders triangles pattern
294
+ */
295
+ private static renderTrianglesPattern(ctx: SKRSContext2D, canvas: Canvas, options: PatternOptions): void {
296
+ const size = options.size || 20;
297
+ const spacing = options.spacing || 10;
298
+ const color = options.color || '#ffffff';
299
+
300
+ ctx.strokeStyle = color;
301
+ ctx.lineWidth = 2;
302
+
303
+ for (let x = 0; x <= canvas.width + size; x += size + spacing) {
304
+ for (let y = 0; y <= canvas.height + size; y += size + spacing) {
305
+ this.drawTriangle(ctx, x, y, size / 2);
306
+ }
307
+ }
308
+ }
309
+
310
+ /**
311
+ * Renders stars pattern
312
+ */
313
+ private static renderStarsPattern(ctx: SKRSContext2D, canvas: Canvas, options: PatternOptions): void {
314
+ const size = options.size || 20;
315
+ const spacing = options.spacing || 10;
316
+ const color = options.color || '#ffffff';
317
+
318
+ ctx.fillStyle = color;
319
+
320
+ for (let x = 0; x <= canvas.width + size; x += size + spacing) {
321
+ for (let y = 0; y <= canvas.height + size; y += size + spacing) {
322
+ this.drawStar(ctx, x, y, size / 4);
323
+ }
324
+ }
325
+ }
326
+
327
+ /**
328
+ * Renders polka pattern (larger dots)
329
+ */
330
+ private static renderPolkaPattern(ctx: SKRSContext2D, canvas: Canvas, options: PatternOptions): void {
331
+ const size = options.size || 20;
332
+ const spacing = options.spacing || 10;
333
+ const color = options.color || '#ffffff';
334
+
335
+ ctx.fillStyle = color;
336
+
337
+ for (let x = 0; x <= canvas.width; x += size + spacing) {
338
+ for (let y = 0; y <= canvas.height; y += size + spacing) {
339
+ ctx.beginPath();
340
+ ctx.arc(x, y, size / 2, 0, Math.PI * 2);
341
+ ctx.fill();
342
+ }
343
+ }
344
+ }
345
+
346
+ /**
347
+ * Renders custom pattern from image
348
+ */
349
+ private static async renderCustomPattern(ctx: SKRSContext2D, canvas: Canvas, options: PatternOptions): Promise<void> {
350
+ if (!options.customPatternImage) return;
351
+
352
+ try {
353
+ let imagePath = options.customPatternImage;
354
+ if (!/^https?:\/\//i.test(imagePath)) {
355
+ imagePath = path.join(process.cwd(), imagePath);
356
+ }
357
+
358
+ const image = await loadImage(imagePath);
359
+ const scale = options.scale || 1;
360
+ const repeat = options.repeat || 'repeat';
361
+
362
+ const scaledWidth = image.width * scale;
363
+ const scaledHeight = image.height * scale;
364
+
365
+ switch (repeat) {
366
+ case 'repeat':
367
+ for (let x = 0; x <= canvas.width; x += scaledWidth) {
368
+ for (let y = 0; y <= canvas.height; y += scaledHeight) {
369
+ ctx.drawImage(image, x, y, scaledWidth, scaledHeight);
370
+ }
371
+ }
372
+ break;
373
+ case 'repeat-x':
374
+ for (let x = 0; x <= canvas.width; x += scaledWidth) {
375
+ ctx.drawImage(image, x, 0, scaledWidth, scaledHeight);
376
+ }
377
+ break;
378
+ case 'repeat-y':
379
+ for (let y = 0; y <= canvas.height; y += scaledHeight) {
380
+ ctx.drawImage(image, 0, y, scaledWidth, scaledHeight);
381
+ }
382
+ break;
383
+ case 'no-repeat':
384
+ ctx.drawImage(image, 0, 0, scaledWidth, scaledHeight);
385
+ break;
386
+ }
387
+ } catch (error) {
388
+ console.warn(`Failed to load custom pattern image: ${options.customPatternImage}`, error);
389
+ }
390
+ }
391
+
392
+ // === HELPER DRAWING FUNCTIONS ===
393
+
394
+ private static drawHexagon(ctx: SKRSContext2D, x: number, y: number, radius: number): void {
395
+ ctx.beginPath();
396
+ for (let i = 0; i < 6; i++) {
397
+ const angle = (i * Math.PI) / 3;
398
+ const px = x + radius * Math.cos(angle);
399
+ const py = y + radius * Math.sin(angle);
400
+ if (i === 0) {
401
+ ctx.moveTo(px, py);
402
+ } else {
403
+ ctx.lineTo(px, py);
404
+ }
405
+ }
406
+ ctx.closePath();
407
+ ctx.stroke();
408
+ }
409
+
410
+ private static drawDiamond(ctx: SKRSContext2D, x: number, y: number, size: number): void {
411
+ ctx.beginPath();
412
+ ctx.moveTo(x, y - size);
413
+ ctx.lineTo(x + size, y);
414
+ ctx.lineTo(x, y + size);
415
+ ctx.lineTo(x - size, y);
416
+ ctx.closePath();
417
+ ctx.stroke();
418
+ }
419
+
420
+ private static drawTriangle(ctx: SKRSContext2D, x: number, y: number, size: number): void {
421
+ ctx.beginPath();
422
+ ctx.moveTo(x, y - size);
423
+ ctx.lineTo(x + size, y + size);
424
+ ctx.lineTo(x - size, y + size);
425
+ ctx.closePath();
426
+ ctx.stroke();
427
+ }
428
+
429
+ private static drawStar(ctx: SKRSContext2D, x: number, y: number, radius: number): void {
430
+ ctx.beginPath();
431
+ for (let i = 0; i < 5; i++) {
432
+ const angle = (i * 4 * Math.PI) / 5;
433
+ const px = x + radius * Math.cos(angle);
434
+ const py = y + radius * Math.sin(angle);
435
+ if (i === 0) {
436
+ ctx.moveTo(px, py);
437
+ } else {
438
+ ctx.lineTo(px, py);
439
+ }
440
+ }
441
+ ctx.closePath();
442
+ ctx.fill();
443
+ }
444
+ }