ace-colorpicker-rpk 0.0.12

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 (238) hide show
  1. package/.babelrc +30 -0
  2. package/.github/ISSUE_TEMPLATE/bug_report.md +35 -0
  3. package/.github/ISSUE_TEMPLATE/feature_request.md +17 -0
  4. package/ChangeLogs.md +22 -0
  5. package/LICENSE +21 -0
  6. package/README.md +117 -0
  7. package/addon/ace-colorpicker.css +1074 -0
  8. package/addon/ace-colorpicker.js +9602 -0
  9. package/addon/sample/colorpicker.html +199 -0
  10. package/config/rollup.config.dev.js +52 -0
  11. package/config/rollup.config.prod.js +53 -0
  12. package/dist/ace-colorpicker.css +1074 -0
  13. package/dist/ace-colorpicker.js +9736 -0
  14. package/dist/ace-colorpicker.min.js +1 -0
  15. package/gl.html +56 -0
  16. package/index.html +172 -0
  17. package/package.json +87 -0
  18. package/resources/image/ace-editor.png +0 -0
  19. package/resources/image/colorpaletts.png +0 -0
  20. package/resources/image/colorpicker.png +0 -0
  21. package/resources/image/grapes.jpg +0 -0
  22. package/resources/image/palette-type.png +0 -0
  23. package/resources/image/scalecolors-title.png +0 -0
  24. package/resources/image/scalecolors.png +0 -0
  25. package/resources/image/screen-shot.png +0 -0
  26. package/resources/image/sketch-type.png +0 -0
  27. package/src/colorpicker/BaseBox.js +94 -0
  28. package/src/colorpicker/BaseColorPicker.js +404 -0
  29. package/src/colorpicker/BaseModule.js +19 -0
  30. package/src/colorpicker/BaseSlider.js +97 -0
  31. package/src/colorpicker/BaseStore.js +71 -0
  32. package/src/colorpicker/UIElement.js +46 -0
  33. package/src/colorpicker/VerticalSlider.js +57 -0
  34. package/src/colorpicker/chromedevtool/ColorControl.js +47 -0
  35. package/src/colorpicker/chromedevtool/index.js +36 -0
  36. package/src/colorpicker/index.js +37 -0
  37. package/src/colorpicker/macos/ColorControl.js +47 -0
  38. package/src/colorpicker/macos/index.js +38 -0
  39. package/src/colorpicker/mini/ColorControl.js +40 -0
  40. package/src/colorpicker/mini/index.js +24 -0
  41. package/src/colorpicker/mini-vertical/ColorControl.js +35 -0
  42. package/src/colorpicker/mini-vertical/index.js +23 -0
  43. package/src/colorpicker/module/ColorManager.js +111 -0
  44. package/src/colorpicker/module/ColorSetsList.js +132 -0
  45. package/src/colorpicker/ring/ColorControl.js +47 -0
  46. package/src/colorpicker/ring/index.js +42 -0
  47. package/src/colorpicker/ui/ColorInformation.js +216 -0
  48. package/src/colorpicker/ui/ColorPalette.js +130 -0
  49. package/src/colorpicker/ui/ColorRing.js +68 -0
  50. package/src/colorpicker/ui/ColorSetsChooser.js +96 -0
  51. package/src/colorpicker/ui/ColorWheel.js +257 -0
  52. package/src/colorpicker/ui/CurrentColorSets.js +81 -0
  53. package/src/colorpicker/ui/CurrentColorSetsContextMenu.js +63 -0
  54. package/src/colorpicker/ui/control/Hue.js +40 -0
  55. package/src/colorpicker/ui/control/Opacity.js +65 -0
  56. package/src/colorpicker/ui/control/Value.js +50 -0
  57. package/src/colorpicker/ui/control/VerticalHue.js +39 -0
  58. package/src/colorpicker/ui/control/VerticalOpacity.js +55 -0
  59. package/src/colorpicker/vscode/ColorControl.js +40 -0
  60. package/src/colorpicker/vscode/index.js +82 -0
  61. package/src/colorpicker/xd/ColorControl.js +36 -0
  62. package/src/colorpicker/xd/index.js +36 -0
  63. package/src/extension/ace/colorview.js +198 -0
  64. package/src/extension/ace/index.js +11 -0
  65. package/src/index.js +12 -0
  66. package/src/scss/colorpicker.scss +65 -0
  67. package/src/scss/colorview.scss +32 -0
  68. package/src/scss/component/button.scss +33 -0
  69. package/src/scss/component/colorchooser.scss +141 -0
  70. package/src/scss/component/colorsets-contextmenu.scss +33 -0
  71. package/src/scss/component/colorsets.scss +89 -0
  72. package/src/scss/component/control.scss +93 -0
  73. package/src/scss/component/gradient-editor.scss +260 -0
  74. package/src/scss/component/gradient-picker.scss +241 -0
  75. package/src/scss/component/information.scss +141 -0
  76. package/src/scss/component/palette.scss +45 -0
  77. package/src/scss/index.scss +5 -0
  78. package/src/scss/mixins.scss +21 -0
  79. package/src/scss/themes/macos.scss +71 -0
  80. package/src/scss/themes/mini-vertical.scss +94 -0
  81. package/src/scss/themes/mini.scss +76 -0
  82. package/src/scss/themes/palette.scss +85 -0
  83. package/src/scss/themes/ring.scss +57 -0
  84. package/src/scss/themes/sketch.scss +172 -0
  85. package/src/scss/themes/vscode.scss +93 -0
  86. package/src/scss/themes/xd.scss +88 -0
  87. package/src/util/Blender.js +29 -0
  88. package/src/util/Canvas.js +128 -0
  89. package/src/util/Color.js +27 -0
  90. package/src/util/ColorNames.js +14 -0
  91. package/src/util/Dom.js +361 -0
  92. package/src/util/Event.js +30 -0
  93. package/src/util/EventMachin.js +349 -0
  94. package/src/util/GL.js +8 -0
  95. package/src/util/HueColor.js +49 -0
  96. package/src/util/ImageFilter.js +9 -0
  97. package/src/util/ImageLoader.js +137 -0
  98. package/src/util/Kmeans.js +237 -0
  99. package/src/util/Matrix.js +196 -0
  100. package/src/util/State.js +42 -0
  101. package/src/util/blend/composite.js +124 -0
  102. package/src/util/blend/non-separable.js +118 -0
  103. package/src/util/blend/separable.js +76 -0
  104. package/src/util/filter/StackBlur.js +517 -0
  105. package/src/util/filter/functions.js +829 -0
  106. package/src/util/filter/image/crop.js +16 -0
  107. package/src/util/filter/image/flipH.js +23 -0
  108. package/src/util/filter/image/flipV.js +25 -0
  109. package/src/util/filter/image/histogram.js +45 -0
  110. package/src/util/filter/image/index.js +18 -0
  111. package/src/util/filter/image/resize.js +18 -0
  112. package/src/util/filter/image/rotate.js +39 -0
  113. package/src/util/filter/image/rotateDegree.js +53 -0
  114. package/src/util/filter/index.js +11 -0
  115. package/src/util/filter/matrix/blur.js +12 -0
  116. package/src/util/filter/matrix/emboss.js +17 -0
  117. package/src/util/filter/matrix/gaussian-blur-5x.js +17 -0
  118. package/src/util/filter/matrix/gaussian-blur.js +16 -0
  119. package/src/util/filter/matrix/grayscale2.js +16 -0
  120. package/src/util/filter/matrix/index.js +58 -0
  121. package/src/util/filter/matrix/kirsch-horizontal.js +13 -0
  122. package/src/util/filter/matrix/kirsch-vertical.js +13 -0
  123. package/src/util/filter/matrix/laplacian-5x.js +16 -0
  124. package/src/util/filter/matrix/laplacian.js +14 -0
  125. package/src/util/filter/matrix/motion-blur-2.js +18 -0
  126. package/src/util/filter/matrix/motion-blur-3.js +19 -0
  127. package/src/util/filter/matrix/motion-blur.js +18 -0
  128. package/src/util/filter/matrix/negative.js +16 -0
  129. package/src/util/filter/matrix/normal.js +11 -0
  130. package/src/util/filter/matrix/sepia2.js +16 -0
  131. package/src/util/filter/matrix/sharpen.js +14 -0
  132. package/src/util/filter/matrix/sobel-horizontal.js +11 -0
  133. package/src/util/filter/matrix/sobel-vertical.js +11 -0
  134. package/src/util/filter/matrix/stack-blur.js +15 -0
  135. package/src/util/filter/matrix/transparency.js +16 -0
  136. package/src/util/filter/matrix/unsharp-masking.js +16 -0
  137. package/src/util/filter/multi/index.js +9 -0
  138. package/src/util/filter/multi/kirsch.js +7 -0
  139. package/src/util/filter/multi/sobel.js +7 -0
  140. package/src/util/filter/multi/vintage.js +7 -0
  141. package/src/util/filter/pixel/bitonal.js +24 -0
  142. package/src/util/filter/pixel/brightness.js +19 -0
  143. package/src/util/filter/pixel/brownie.js +23 -0
  144. package/src/util/filter/pixel/clip.js +21 -0
  145. package/src/util/filter/pixel/contrast.js +18 -0
  146. package/src/util/filter/pixel/gamma.js +13 -0
  147. package/src/util/filter/pixel/gradient.js +52 -0
  148. package/src/util/filter/pixel/grayscale.js +27 -0
  149. package/src/util/filter/pixel/hue.js +28 -0
  150. package/src/util/filter/pixel/index.js +52 -0
  151. package/src/util/filter/pixel/invert.js +16 -0
  152. package/src/util/filter/pixel/kodachrome.js +23 -0
  153. package/src/util/filter/pixel/matrix.js +28 -0
  154. package/src/util/filter/pixel/noise.js +24 -0
  155. package/src/util/filter/pixel/opacity.js +14 -0
  156. package/src/util/filter/pixel/polaroid.js +23 -0
  157. package/src/util/filter/pixel/saturation.js +30 -0
  158. package/src/util/filter/pixel/sepia.js +28 -0
  159. package/src/util/filter/pixel/shade.js +21 -0
  160. package/src/util/filter/pixel/shift.js +23 -0
  161. package/src/util/filter/pixel/solarize.js +23 -0
  162. package/src/util/filter/pixel/technicolor.js +23 -0
  163. package/src/util/filter/pixel/threshold-color.js +35 -0
  164. package/src/util/filter/pixel/threshold.js +7 -0
  165. package/src/util/filter/pixel/tint.js +20 -0
  166. package/src/util/functions/formatter.js +99 -0
  167. package/src/util/functions/fromCMYK.js +17 -0
  168. package/src/util/functions/fromHSL.js +52 -0
  169. package/src/util/functions/fromHSV.js +64 -0
  170. package/src/util/functions/fromLAB.js +99 -0
  171. package/src/util/functions/fromRGB.js +220 -0
  172. package/src/util/functions/fromYCrCb.js +16 -0
  173. package/src/util/functions/func.js +194 -0
  174. package/src/util/functions/image.js +145 -0
  175. package/src/util/functions/math.js +56 -0
  176. package/src/util/functions/mixin.js +164 -0
  177. package/src/util/functions/parser.js +294 -0
  178. package/src/util/gl/filter/index.js +9 -0
  179. package/src/util/gl/filter/matrix/blur.js +9 -0
  180. package/src/util/gl/filter/matrix/emboss.js +17 -0
  181. package/src/util/gl/filter/matrix/gaussian-blur-5x.js +15 -0
  182. package/src/util/gl/filter/matrix/gaussian-blur.js +19 -0
  183. package/src/util/gl/filter/matrix/grayscale2.js +13 -0
  184. package/src/util/gl/filter/matrix/index.js +55 -0
  185. package/src/util/gl/filter/matrix/kirsch-horizontal.js +11 -0
  186. package/src/util/gl/filter/matrix/kirsch-vertical.js +11 -0
  187. package/src/util/gl/filter/matrix/laplacian-5x.js +13 -0
  188. package/src/util/gl/filter/matrix/laplacian.js +11 -0
  189. package/src/util/gl/filter/matrix/motion-blur-2.js +17 -0
  190. package/src/util/gl/filter/matrix/motion-blur-3.js +17 -0
  191. package/src/util/gl/filter/matrix/motion-blur.js +17 -0
  192. package/src/util/gl/filter/matrix/negative.js +13 -0
  193. package/src/util/gl/filter/matrix/normal.js +8 -0
  194. package/src/util/gl/filter/matrix/sepia2.js +13 -0
  195. package/src/util/gl/filter/matrix/sharpen.js +11 -0
  196. package/src/util/gl/filter/matrix/sobel-horizontal.js +11 -0
  197. package/src/util/gl/filter/matrix/sobel-vertical.js +11 -0
  198. package/src/util/gl/filter/matrix/transparency.js +13 -0
  199. package/src/util/gl/filter/matrix/unsharp-masking.js +14 -0
  200. package/src/util/gl/filter/multi/index.js +9 -0
  201. package/src/util/gl/filter/multi/kirsch.js +7 -0
  202. package/src/util/gl/filter/multi/sobel.js +7 -0
  203. package/src/util/gl/filter/multi/vintage.js +7 -0
  204. package/src/util/gl/filter/pixel/bitonal.js +22 -0
  205. package/src/util/gl/filter/pixel/brightness.js +14 -0
  206. package/src/util/gl/filter/pixel/brownie.js +11 -0
  207. package/src/util/gl/filter/pixel/chaos.js +20 -0
  208. package/src/util/gl/filter/pixel/clip.js +20 -0
  209. package/src/util/gl/filter/pixel/contrast.js +16 -0
  210. package/src/util/gl/filter/pixel/gamma.js +16 -0
  211. package/src/util/gl/filter/pixel/gradient.js +59 -0
  212. package/src/util/gl/filter/pixel/grayscale.js +22 -0
  213. package/src/util/gl/filter/pixel/hue.js +19 -0
  214. package/src/util/gl/filter/pixel/index.js +54 -0
  215. package/src/util/gl/filter/pixel/invert.js +18 -0
  216. package/src/util/gl/filter/pixel/kodachrome.js +11 -0
  217. package/src/util/gl/filter/pixel/matrix.js +29 -0
  218. package/src/util/gl/filter/pixel/noise.js +18 -0
  219. package/src/util/gl/filter/pixel/opacity.js +17 -0
  220. package/src/util/gl/filter/pixel/polaroid.js +11 -0
  221. package/src/util/gl/filter/pixel/saturation.js +20 -0
  222. package/src/util/gl/filter/pixel/sepia.js +19 -0
  223. package/src/util/gl/filter/pixel/shade.js +20 -0
  224. package/src/util/gl/filter/pixel/shift.js +11 -0
  225. package/src/util/gl/filter/pixel/solarize.js +21 -0
  226. package/src/util/gl/filter/pixel/technicolor.js +11 -0
  227. package/src/util/gl/filter/pixel/threshold-color.js +15 -0
  228. package/src/util/gl/filter/pixel/threshold.js +7 -0
  229. package/src/util/gl/filter/pixel/tint.js +25 -0
  230. package/src/util/gl/filter/util.js +185 -0
  231. package/src/util/gl/functions.js +158 -0
  232. package/src/util/gl/index.js +543 -0
  233. package/src/util/index.js +17 -0
  234. package/stand.html +975 -0
  235. package/test/util.Blend.spec.js +15 -0
  236. package/test/util.Color.spec.js +200 -0
  237. package/test/util.Filter.spec.js +12 -0
  238. package/test/util.ImageFilter.spec.js +16 -0
@@ -0,0 +1,829 @@
1
+ import Canvas from '../Canvas'
2
+ import Matrix from '../Matrix'
3
+ import ImageFilter from './index'
4
+ import Color from '../Color'
5
+
6
+ let makeId = 0
7
+
8
+ const functions = {
9
+ partial,
10
+ multi,
11
+ merge,
12
+ weight,
13
+ repeat,
14
+ colorMatrix,
15
+ each,
16
+ eachXY,
17
+ createRandomCount,
18
+ createRandRange,
19
+ createBitmap,
20
+ createBlurMatrix,
21
+ pack,
22
+ packXY,
23
+ pixel,
24
+ getBitmap,
25
+ putBitmap,
26
+ radian,
27
+ convolution,
28
+ parseParamNumber,
29
+ filter,
30
+ clamp,
31
+ fillColor,
32
+ fillPixelColor,
33
+ multi,
34
+ merge,
35
+ matches,
36
+ parseFilter,
37
+ partial
38
+ }
39
+
40
+ const LocalFilter = functions
41
+
42
+ export default functions
43
+
44
+ export function weight(arr, num = 1) {
45
+ return arr.map(i => {
46
+ return i * num;
47
+ })
48
+ }
49
+
50
+ export function repeat (value, num) {
51
+ let arr = new Array(num)
52
+ for(let i = 0; i < num; i++) {
53
+ arr[i] = value
54
+ }
55
+ return arr;
56
+ }
57
+
58
+ export function colorMatrix(pixels, i, matrix) {
59
+ var r = pixels[i], g = pixels[i + 1], b = pixels[i + 2], a = pixels[i + 3];
60
+
61
+ fillColor(
62
+ pixels,
63
+ i,
64
+ matrix[0] * r + matrix[1] * g + matrix[2] * b + matrix[3] * a,
65
+ matrix[4] * r + matrix[5] * g + matrix[6] * b + matrix[7] * a,
66
+ matrix[8] * r + matrix[9] * g + matrix[10] * b + matrix[11] * a,
67
+ matrix[12] * r + matrix[13] * g + matrix[14] * b + matrix[15] * a
68
+ )
69
+ }
70
+
71
+ export function makeFilter(filter) {
72
+
73
+ if (typeof filter == 'function') {
74
+ return filter;
75
+ }
76
+
77
+ if (typeof filter == 'string') {
78
+ filter = [filter];
79
+ }
80
+
81
+ filter = filter.slice(0);
82
+ const filterName = filter.shift();
83
+
84
+ if (typeof filterName == 'function') {
85
+ return filterName;
86
+ }
87
+
88
+ const params = filter;
89
+
90
+ const filterFunction = ImageFilter[filterName] || LocalFilter[filterName] ;
91
+
92
+ if (!filterFunction) {
93
+ throw new Error(`${filterName} is not filter. please check filter name.`)
94
+ }
95
+ return filterFunction.apply(filterFunction, params);
96
+ }
97
+
98
+ export function forLoop (max, index = 0, step = 1, callback, done, functionDumpCount = 10000, frameTimer = 'full', loopCount = 50) {
99
+ let runIndex = index
100
+ let timer = (callback) => {
101
+ setTimeout(callback, 0)
102
+ }
103
+
104
+ if (frameTimer == 'requestAnimationFrame') {
105
+ timer = requestAnimationFrame
106
+ functionDumpCount = 1000
107
+ }
108
+
109
+ if (frameTimer == 'full') { /* only for loop */
110
+ timer = null
111
+ functionDumpCount = max
112
+ }
113
+
114
+ function makeFunction (count = 50) {
115
+ const arr = [...Array(count)];
116
+
117
+ const functionStrings = arr.map(countIndex => {
118
+ return `cri = ri + i * s; if (cri >= mx) return {currentRunIndex: cri, i: null}; c(cri); i++;`
119
+ }).join('\n')
120
+
121
+ const smallLoopFunction = new Function ('ri', 'i', 's', 'mx', 'c', `
122
+ let cri = ri;
123
+
124
+ ${functionStrings}
125
+
126
+ return {currentRunIndex: cri, i: i}
127
+ `)
128
+
129
+ return smallLoopFunction
130
+ }
131
+
132
+ function runCallback () {
133
+
134
+ const smallLoopFunction = makeFunction(loopCount) // loop is call 20 callbacks at once
135
+
136
+ let currentRunIndex = runIndex
137
+ let ret = {};
138
+ let i = 0
139
+ while(i < functionDumpCount) {
140
+ ret = smallLoopFunction(runIndex, i, step, max, callback)
141
+
142
+ if (ret.i == null) {
143
+ currentRunIndex = ret.currentRunIndex
144
+ break;
145
+ }
146
+
147
+ i = ret.i
148
+ currentRunIndex = ret.currentRunIndex
149
+ }
150
+
151
+ nextCallback(currentRunIndex)
152
+ }
153
+
154
+ function nextCallback (currentRunIndex) {
155
+ if (currentRunIndex) {
156
+ runIndex = currentRunIndex
157
+ } else {
158
+ runIndex += step
159
+ }
160
+
161
+ if (runIndex >= max) {
162
+ done()
163
+ return;
164
+ }
165
+
166
+ if (timer) timer(runCallback)
167
+ else runCallback()
168
+ }
169
+
170
+ runCallback()
171
+ }
172
+
173
+ export function each(len, callback, done, opt = {}) {
174
+
175
+ forLoop(len, 0, 4, function (i) {
176
+ callback(i, i >> 2 /* xyIndex */);
177
+ }, function () {
178
+ done()
179
+ }, opt.functionDumpCount, opt.frameTimer, opt.loopCount)
180
+ }
181
+
182
+ export function eachXY(len, width, callback, done, opt = {}) {
183
+
184
+ forLoop(len, 0, 4, function (i) {
185
+ var xyIndex = i >> 2
186
+ callback(i, xyIndex % width, Math.floor(xyIndex / width));
187
+ }, function () {
188
+ done()
189
+ }, opt.functionDumpCount, opt.frameTimer, opt.loopCount)
190
+ }
191
+
192
+ export function createRandRange(min, max, count) {
193
+ var result = [];
194
+
195
+ for (var i = 1; i <= count; i++) {
196
+ var num = Math.random() * (max - min) + min;
197
+ var sign = (Math.floor(Math.random() * 10) % 2 == 0) ? -1 : 1;
198
+ result.push(sign * num);
199
+ }
200
+
201
+ result.sort();
202
+
203
+ const centerIndex = Math.floor(count >> 1);
204
+ var a = result[centerIndex];
205
+ result[centerIndex] = result[0];
206
+ result[0] = a;
207
+
208
+ return result;
209
+ }
210
+
211
+ export function createRandomCount() {
212
+ return [3 * 3, 4 * 4, 5 * 5, 6 * 6, 7 * 7, 8 * 8, 9 * 9, 10 * 10].sort(function (a, b) {
213
+ return 0.5 - Math.random();
214
+ })[0];
215
+ }
216
+
217
+ export function createBitmap(length, width, height) {
218
+ return { pixels: new Uint8ClampedArray(length), width, height }
219
+ }
220
+
221
+ export function putPixel(dstBitmap, srcBitmap, startX, startY) {
222
+
223
+ var len = srcBitmap.pixels.length / 4;
224
+ var dstX = 0, dstY = 0, x = 0, y = 0, srcIndex =0, dstIndex = 0;
225
+ for(var i = 0; i < len; i++) {
226
+ x = i % srcBitmap.width, y = Math.floor(i / srcBitmap.width);
227
+
228
+ dstX = startX + x
229
+ dstY = startY + y
230
+
231
+ if (dstX > dstBitmap.width) continue;
232
+ if (dstY > dstBitmap.height) continue;
233
+
234
+ srcIndex = (y * srcBitmap.width + x) << 2
235
+ dstIndex = (dstY * dstBitmap.width + dstX) << 2
236
+
237
+ dstBitmap.pixels[dstIndex] = srcBitmap.pixels[srcIndex]
238
+ dstBitmap.pixels[dstIndex+1] = srcBitmap.pixels[srcIndex+1]
239
+ dstBitmap.pixels[dstIndex+2] = srcBitmap.pixels[srcIndex+2]
240
+ dstBitmap.pixels[dstIndex+3] = srcBitmap.pixels[srcIndex+3]
241
+ }
242
+
243
+ }
244
+
245
+ export function getPixel(srcBitmap, dstBitmap, startX, startY) {
246
+ var len = dstBitmap.pixels.length >> 2;
247
+ var srcX = 0, srcY = 0, x = 0, y = 0, srcIndex =0, dstIndex = 0;
248
+ for(var i = 0; i < len; i++) {
249
+ var x = i % dstBitmap.width, y = Math.floor(i / dstBitmap.width);
250
+
251
+ srcX = startX + x
252
+ srcY = startY + y
253
+
254
+ if (srcX > srcBitmap.width) continue;
255
+ if (srcY > srcBitmap.height) continue;
256
+
257
+ srcIndex = (srcY * srcBitmap.width + srcX) << 2
258
+ dstIndex = (y * dstBitmap.width + x) << 2
259
+
260
+ dstBitmap.pixels[dstIndex] = srcBitmap.pixels[srcIndex]
261
+ dstBitmap.pixels[dstIndex+1] = srcBitmap.pixels[srcIndex+1]
262
+ dstBitmap.pixels[dstIndex+2] = srcBitmap.pixels[srcIndex+2]
263
+ dstBitmap.pixels[dstIndex+3] = srcBitmap.pixels[srcIndex+3]
264
+ }
265
+ }
266
+
267
+ export function cloneBitmap(bitmap, padding = 0) {
268
+
269
+
270
+ const width = bitmap.width + padding
271
+ const height = bitmap.height + padding
272
+
273
+ const newBitmap = { pixels: new Uint8ClampedArray(width * height * 4), width, height }
274
+
275
+ return newBitmap
276
+ }
277
+
278
+ export function getBitmap(bitmap, area) {
279
+ return Canvas.getBitmap(bitmap, area);
280
+ }
281
+
282
+ export function putBitmap(bitmap, subBitmap, area) {
283
+ return Canvas.putBitmap(bitmap, subBitmap, area);
284
+ }
285
+
286
+ export function parseParamNumber (param) {
287
+ if (typeof param === 'string') {
288
+ param = param.replace(/deg/, '')
289
+ param = param.replace(/px/, '')
290
+ }
291
+ return +param
292
+ }
293
+
294
+ const filter_regexp = /(([\w_\-]+)(\(([^\)]*)\))?)+/gi;
295
+ const filter_split = ' '
296
+
297
+ export { filter_regexp, filter_split }
298
+
299
+ export function pack(callback) {
300
+ return function (bitmap, done) {
301
+ each(bitmap.pixels.length, (i, xyIndex) => {
302
+ callback(bitmap.pixels, i, xyIndex, bitmap.pixels[i], bitmap.pixels[i+1], bitmap.pixels[i+2], bitmap.pixels[i+3])
303
+ }, function () {
304
+ done(bitmap);
305
+ })
306
+ }
307
+ }
308
+
309
+ export function makePrebuildUserFilterList (arr) {
310
+
311
+ const codeString = arr.map(it => {
312
+ return `
313
+ ${it.userFunction.$preContext}
314
+
315
+ ${it.userFunction.$preCallbackString}
316
+
317
+ $r = clamp($r); $g = clamp($g); $b = clamp($b); $a = clamp($a);
318
+ `
319
+ }).join('\n\n')
320
+
321
+ var rootContextObject = { clamp, Color }
322
+ arr.forEach(it => {
323
+ Object.assign(rootContextObject, it.userFunction.rootContextObject)
324
+ })
325
+
326
+ var rootContextDefine = `const ` + Object.keys(rootContextObject).map(key => {
327
+ return ` ${key} = $rc.${key} `
328
+ }).join(',')
329
+
330
+
331
+ let FunctionCode = `
332
+ let $r = $p[$pi], $g = $p[$pi+1], $b = $p[$pi+2], $a = $p[$pi+3];
333
+
334
+ ${rootContextDefine}
335
+
336
+ ${codeString}
337
+
338
+ $p[$pi] = $r; $p[$pi+1] = $g; $p[$pi+2] = $b; $p[$pi+3] = $a;
339
+ `
340
+
341
+ const userFunction = new Function('$p', '$pi', '$rc', FunctionCode)
342
+
343
+ return function ($pixels, $pixelIndex) {
344
+ userFunction($pixels, $pixelIndex, rootContextObject)
345
+ }
346
+ }
347
+
348
+ export function makeUserFilterFunctionList (arr) {
349
+ let rootContextObject = {}
350
+ const list = arr.map(it => {
351
+ let newKeys = []
352
+
353
+ Object.keys(it.context).forEach((key, i) => {
354
+ newKeys[key] = `n$${makeId++}${key}$`
355
+ })
356
+
357
+ Object.keys(it.rootContext).forEach((key, i) => {
358
+ newKeys[key] = `r$${makeId++}${key}$`
359
+
360
+ rootContextObject[newKeys[key]] = it.rootContext[key]
361
+ })
362
+
363
+ let preContext = Object.keys(it.context).filter(key => {
364
+ if (typeof it.context[key] === 'number' || typeof it.context[key] === 'string') {
365
+ return false
366
+ } else if (Array.isArray(it.context[key])) {
367
+ if (typeof it.context[key][0] == 'number' || typeof it.context[key][0] == 'string') {
368
+ return false
369
+ }
370
+ }
371
+
372
+ return true
373
+ }).map((key, i) => {
374
+ return [newKeys[key], JSON.stringify(it.context[key])].join(' = ')
375
+ })
376
+
377
+ let preCallbackString = it.callback;
378
+
379
+ if (typeof it.callback === 'function') {
380
+ preCallbackString = it.callback.toString().split("{");
381
+
382
+ preCallbackString.shift()
383
+ preCallbackString = preCallbackString.join("{")
384
+ preCallbackString = preCallbackString.split("}")
385
+ preCallbackString.pop()
386
+ preCallbackString = preCallbackString.join("}")
387
+ }
388
+
389
+ Object.keys(newKeys).forEach(key => {
390
+ var newKey = newKeys[key]
391
+
392
+ if (typeof it.context[key] === 'number' || typeof it.context[key] === 'string') {
393
+ preCallbackString = preCallbackString.replace(new RegExp("\\"+key, "g"), it.context[key])
394
+ } else if (Array.isArray(it.context[key])) {
395
+ if (typeof it.context[key][0] == 'number' || typeof it.context[key][0] == 'string') {
396
+ it.context[key].forEach((item, index) => {
397
+ preCallbackString = preCallbackString.replace(new RegExp("\\"+key+'\\[' + index + '\\]', "g"), item)
398
+ })
399
+ } else {
400
+ preCallbackString = preCallbackString.replace(new RegExp("\\"+key, "g"), newKey)
401
+ }
402
+ } else {
403
+ preCallbackString = preCallbackString.replace(new RegExp("\\"+key, "g"), newKey)
404
+ }
405
+ })
406
+
407
+ return { preCallbackString, preContext }
408
+ })
409
+
410
+ const preContext = list.map((it, i) => {
411
+ return it.preContext.length ? `const ${it.preContext};` : "";
412
+ }).join('\n\n')
413
+
414
+ const preCallbackString = list.map(it => {
415
+ return it.preCallbackString
416
+ }).join('\n\n')
417
+
418
+
419
+ let FunctionCode = `
420
+ let $r = $pixels[$pixelIndex], $g = $pixels[$pixelIndex+1], $b = $pixels[$pixelIndex+2], $a = $pixels[$pixelIndex+3];
421
+
422
+ ${preContext}
423
+
424
+ ${preCallbackString}
425
+
426
+ $pixels[$pixelIndex] = $r
427
+ $pixels[$pixelIndex+1] = $g
428
+ $pixels[$pixelIndex+2] = $b
429
+ $pixels[$pixelIndex+3] = $a
430
+ `
431
+
432
+ const userFunction = new Function('$pixels', '$pixelIndex', '$clamp', '$Color', FunctionCode)
433
+
434
+ userFunction.$preCallbackString = preCallbackString
435
+ userFunction.$preContext = preContext
436
+ userFunction.rootContextObject = rootContextObject
437
+
438
+ return userFunction
439
+ }
440
+
441
+ export function makeUserFilterFunction (callback, context = {}, rootContext = {}) {
442
+ return makeUserFilterFunctionList([{ callback, context, rootContext }])
443
+ }
444
+
445
+ export function pixel(callback, context = {}, rootContext = {}) {
446
+ const userFunction = makeUserFilterFunction(callback, context, rootContext)
447
+
448
+ const returnCallback = function (bitmap, done) { }
449
+
450
+ returnCallback.userFunction = userFunction
451
+
452
+ return returnCallback
453
+ }
454
+
455
+ const ColorListIndex = [0, 1, 2, 3]
456
+
457
+ export function swapColor (pixels, startIndex, endIndex) {
458
+
459
+ ColorListIndex.forEach(i => {
460
+ var temp = pixels[startIndex + i]
461
+ pixels[startIndex + i] = pixels[endIndex + i]
462
+ pixels[endIndex + i] = temp
463
+ })
464
+ }
465
+
466
+ export function packXY(callback) {
467
+ return function (bitmap, done, opt = {}) {
468
+ eachXY(bitmap.pixels.length, bitmap.width, (i, x, y) => {
469
+ callback(bitmap.pixels, i, x, y)
470
+ }, function () {
471
+ done(bitmap);
472
+ }, opt)
473
+
474
+ }
475
+ }
476
+
477
+ export function radian (degree) {
478
+ return Matrix.CONSTANT.radian(degree)
479
+ }
480
+
481
+
482
+ export function createBlurMatrix (amount = 3) {
483
+ const count = Math.pow(amount, 2)
484
+ const value = 1/count
485
+ return repeat (value, count)
486
+ }
487
+
488
+ export function fillColor(pixels, i, r, g, b, a) {
489
+ if (arguments.length == 3) {
490
+ var {r, g, b, a} = arguments[2]
491
+ }
492
+
493
+ if (typeof r == 'number') {pixels[i] = r; }
494
+ if (typeof g == 'number') {pixels[i + 1] = g; }
495
+ if (typeof b == 'number') {pixels[i + 2] = b; }
496
+ if (typeof a == 'number') {pixels[i + 3] = a; }
497
+ }
498
+
499
+ export function fillPixelColor (targetPixels, targetIndex, sourcePixels, sourceIndex) {
500
+ fillColor(
501
+ targetPixels,
502
+ targetIndex,
503
+ sourcePixels[sourceIndex],
504
+ sourcePixels[sourceIndex+1],
505
+ sourcePixels[sourceIndex+2],
506
+ sourcePixels[sourceIndex+3]
507
+ )
508
+ }
509
+
510
+ export function subPixelWeight (dstPixels, pixels, dstIndex, sx, sy, sw, sh, halfSide, side, weights) {
511
+ var r = 0, g = 0, b = 0, a = 0, len = side ** 2 ;
512
+
513
+ for (var i = 0; i < len; i++) {
514
+ const cy = Math.floor(i / side)
515
+ const cx = i % side
516
+
517
+ const scy = sy + cy - halfSide;
518
+ const scx = sx + cx - halfSide;
519
+
520
+ if (scy >= 0 && scy < sh && scx >= 0 && scx < sw) {
521
+ var srcIndex = (scy * sw + scx) * 4;
522
+ var wt = weights[cy * side + cx];
523
+ r += pixels[srcIndex] * wt;
524
+ g += pixels[srcIndex + 1] * wt;
525
+ b += pixels[srcIndex + 2] * wt;
526
+ a += pixels[srcIndex + 3] * wt; // weight 를 곱한 값을 계속 더한다.
527
+ }
528
+ }
529
+
530
+ fillColor(dstPixels, dstIndex, r, g, b, a)
531
+ }
532
+
533
+ export function createWeightTable (weights, min = 0, max = 255) {
534
+ var weightTable = []
535
+
536
+ weightTable = weights.map((w, i) => {
537
+ return []
538
+ })
539
+
540
+ weights.forEach( (w, i) => {
541
+
542
+ if (w != 0) {
543
+ let data = weightTable[i]
544
+
545
+ for(var i = min; i <= max; i++) {
546
+ data[i] = w * i;
547
+ }
548
+ }
549
+
550
+ })
551
+
552
+ return weightTable
553
+ }
554
+
555
+ export function createSubPixelWeightFunction(weights, weightTable, width, height, opaque) {
556
+
557
+ const side = Math.round(Math.sqrt(weights.length));
558
+ const halfSide = Math.floor(side / 2);
559
+ const alphaFac = opaque ? 1 : 0;
560
+
561
+ let FunctionCode = `let r = 0, g = 0, b = 0, a = 0, scy = 0, scx =0, si = 0; `
562
+ let R = []
563
+ let G = []
564
+ let B = []
565
+ let A = []
566
+ weights.forEach((wt, index) => {
567
+ const cy = Math.floor(index / side)
568
+ const cx = index % side
569
+ const distY = cy - halfSide
570
+ const distX = cx - halfSide
571
+
572
+ if (wt == 0) {
573
+ return;
574
+ }
575
+
576
+ R.push(`$t[${index}][$sp[(($sy + (${distY})) * ${width} + ($sx + (${distX}))) * 4]]`)
577
+ G.push(`$t[${index}][$sp[(($sy + (${distY})) * ${width} + ($sx + (${distX}))) * 4 + 1]]`)
578
+ B.push(`$t[${index}][$sp[(($sy + (${distY})) * ${width} + ($sx + (${distX}))) * 4 + 2]]`)
579
+ A.push(`$t[${index}][$sp[(($sy + (${distY})) * ${width} + ($sx + (${distX}))) * 4 + 3]]`)
580
+
581
+ })
582
+
583
+ FunctionCode += `r = ${R.join(' + ')}; g = ${G.join(' + ')}; b = ${B.join(' + ')}; a = ${A.join(' + ')};`
584
+ FunctionCode += `$dp[$di] = r; $dp[$di+1] = g;$dp[$di+2] = b;$dp[$di+3] = a + (${alphaFac})*(255-a); `
585
+
586
+ // console.log(FunctionCode)
587
+
588
+ const subPixelFunction = new Function ('$dp', '$sp', '$di', '$sx', '$sy', '$t', FunctionCode )
589
+
590
+
591
+ return function ($dp, $sp, $di, $sx, $sy) {
592
+ subPixelFunction ($dp, $sp, $di, $sx, $sy, weightTable)
593
+ }
594
+ }
595
+
596
+ export function convolution(weights, opaque = true) {
597
+ const weightTable = createWeightTable(weights)
598
+ return function (bitmap, done, opt = {}) {
599
+ const side = Math.round(Math.sqrt(weights.length));
600
+ const padding = side * 2
601
+
602
+ // 원본 크기를 늘림
603
+ let sourceBitmap = cloneBitmap(bitmap, padding)
604
+
605
+ // 원본 데이타 복사
606
+ putPixel (sourceBitmap, bitmap, side, side)
607
+
608
+ // 최종 아웃풋
609
+ let newBitmap = createBitmap(sourceBitmap.pixels.length, sourceBitmap.width, sourceBitmap.height)
610
+
611
+ // 마지막 원본 아웃풋
612
+ let returnBitmap = createBitmap(bitmap.pixels.length, bitmap.width, bitmap.height)
613
+
614
+ const subPixelWeightFunction = createSubPixelWeightFunction(weights, weightTable, sourceBitmap.width, sourceBitmap.height, opaque)
615
+
616
+ var len = bitmap.pixels.length /4
617
+ for (var i = 0; i < len; i++ ) {
618
+ var xyIndex = i , x = xyIndex % bitmap.width + side, y = Math.floor(xyIndex / bitmap.width) + side ;
619
+
620
+ subPixelWeightFunction(
621
+ newBitmap.pixels,
622
+ sourceBitmap.pixels,
623
+ (y * sourceBitmap.width + x) * 4,
624
+ x,
625
+ y
626
+ );
627
+ }
628
+
629
+ getPixel(newBitmap, returnBitmap, side, side)
630
+ done(returnBitmap)
631
+ }
632
+ }
633
+
634
+
635
+ export function matches (str) {
636
+ var ret = Color.convertMatches(str)
637
+ const matches = ret.str.match(filter_regexp);
638
+ let result = [];
639
+
640
+ if (!matches) {
641
+ return result;
642
+ }
643
+
644
+ result = matches.map((it) => {
645
+ return { filter: it, origin: Color.reverseMatches(it, ret.matches) }
646
+ })
647
+
648
+ var pos = { next: 0 }
649
+ result = result.map(item => {
650
+
651
+ const startIndex = str.indexOf(item.origin, pos.next);
652
+
653
+ item.startIndex = startIndex;
654
+ item.endIndex = startIndex + item.origin.length;
655
+
656
+ item.arr = parseFilter(item.origin)
657
+
658
+ pos.next = item.endIndex;
659
+
660
+ return item
661
+ }).filter(it => {
662
+ if (!it.arr.length) return false
663
+ return true
664
+ })
665
+
666
+ return result;
667
+ }
668
+
669
+ /**
670
+ * Filter Parser
671
+ *
672
+ * F.parseFilter('blur(30)') == ['blue', '30']
673
+ * F.parseFilter('gradient(white, black, 3)') == ['gradient', 'white', 'black', '3']
674
+ *
675
+ * @param {String} filterString
676
+ */
677
+ export function parseFilter (filterString) {
678
+
679
+ var ret = Color.convertMatches(filterString)
680
+ const matches = ret.str.match(filter_regexp);
681
+
682
+ if (!matches[0]) {
683
+ return []
684
+ }
685
+
686
+ var arr = matches[0].split('(')
687
+
688
+ var filterName = arr.shift()
689
+ var filterParams = []
690
+
691
+ if (arr.length) {
692
+ filterParams = arr.shift().split(')')[0].split(',').map(f => {
693
+ return Color.reverseMatches(f, ret.matches)
694
+ })
695
+ }
696
+
697
+ var result = [filterName, ...filterParams].map(Color.trim)
698
+
699
+ return result
700
+ }
701
+
702
+ export function clamp (num) {
703
+ return Math.min(255, num)
704
+ }
705
+
706
+ export function filter (str) {
707
+ return merge(matches(str).map(it => {
708
+ return it.arr
709
+ }))
710
+ }
711
+
712
+ export function makeGroupedFilter(filters = []) {
713
+ var groupedFilter = []
714
+ var group = []
715
+ for (var i = 0, len = filters.length; i < len; i++) {
716
+ var f = filters[i]
717
+
718
+ if (f.userFunction) {
719
+ group.push(f)
720
+ } else {
721
+ if (group.length) {
722
+ groupedFilter.push([...group])
723
+ }
724
+ groupedFilter.push(f)
725
+ group = []
726
+ }
727
+ }
728
+
729
+ if (group.length) {
730
+ groupedFilter.push([...group])
731
+ }
732
+
733
+ groupedFilter.forEach((filter, index) => {
734
+ if (Array.isArray(filter)) {
735
+ groupedFilter[index] = (function () {
736
+ const userFunction = makePrebuildUserFilterList(filter)
737
+ // console.log(userFunction)
738
+ return function (bitmap, done) {
739
+
740
+ for (var i = 0, len = bitmap.pixels.length; i< len;i += 4) {
741
+ userFunction(bitmap.pixels, i)
742
+ }
743
+
744
+ done(bitmap)
745
+ // forLoop(bitmap.pixels.length, 0, 4, function (i) {
746
+ // userFunction(bitmap.pixels, i)
747
+ // }, function () {
748
+ // done(bitmap)
749
+ // })
750
+ }
751
+ })()
752
+ }
753
+ })
754
+
755
+ return groupedFilter
756
+ }
757
+
758
+ /**
759
+ *
760
+ * multiply filters
761
+ *
762
+ * ImageFilter.multi('blur', 'grayscale', 'sharpen', ['blur', 3], function (bitmap) { return bitmap });
763
+ *
764
+ */
765
+ export function multi (...filters) {
766
+ filters = filters.map(filter => {
767
+ return makeFilter(filter);
768
+ }).filter(f => f)
769
+
770
+ filters = makeGroupedFilter(filters)
771
+
772
+ var max = filters.length
773
+
774
+ return function (bitmap, done, opt = {}) {
775
+
776
+ var currentBitmap = bitmap
777
+ var index = 0
778
+
779
+ function runFilter () {
780
+ filters[index].call(null, currentBitmap, function (nextBitmap) {
781
+ currentBitmap = nextBitmap
782
+
783
+ nextFilter()
784
+ }, opt)
785
+ }
786
+
787
+ function nextFilter () {
788
+ index++
789
+
790
+ if (index >= max) {
791
+ done(currentBitmap)
792
+ return;
793
+ }
794
+
795
+ runFilter()
796
+ }
797
+
798
+ runFilter()
799
+ }
800
+ }
801
+
802
+
803
+ export function merge (filters) {
804
+ return multi(...filters);
805
+ }
806
+
807
+ /**
808
+ * apply filter into special area
809
+ *
810
+ * F.partial({x,y,width,height}, filter, filter, filter )
811
+ * F.partial({x,y,width,height}, 'filter' )
812
+ *
813
+ * @param {{x, y, width, height}} area
814
+ * @param {*} filters
815
+ */
816
+ export function partial (area, ...filters) {
817
+ var allFilter = null
818
+ if (filters.length == 1 && typeof filters[0] === 'string') {
819
+ allFilter = filter(filters[0])
820
+ } else {
821
+ allFilter = merge(filters)
822
+ }
823
+
824
+ return (bitmap, done, opt = {}) => {
825
+ allFilter(getBitmap(bitmap, area), function (newBitmap) {
826
+ done(putBitmap(bitmap, newBitmap, area))
827
+ }, opt)
828
+ }
829
+ }