@blinkorb/rcx 0.0.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/.eslintignore +4 -0
- package/.eslintrc.json +286 -0
- package/.gitattributes +2 -0
- package/.github/CODEOWNERS +1 -0
- package/.github/workflows/ci.yml +19 -0
- package/.nvmrc +1 -0
- package/.prettierignore +28 -0
- package/.prettierrc.json +4 -0
- package/demo/index.html +29 -0
- package/demo/index.tsx +316 -0
- package/demo/tsconfig.json +12 -0
- package/jest.config.ts +21 -0
- package/package.json +80 -0
- package/scripts/prep-package.js +29 -0
- package/src/components/canvas/context.ts +6 -0
- package/src/components/canvas/index.ts +98 -0
- package/src/components/index.ts +5 -0
- package/src/components/paths/arc-to.ts +66 -0
- package/src/components/paths/clip.ts +32 -0
- package/src/components/paths/index.ts +5 -0
- package/src/components/paths/line.ts +53 -0
- package/src/components/paths/path.ts +59 -0
- package/src/components/paths/point.ts +24 -0
- package/src/components/shapes/circle.tsx +32 -0
- package/src/components/shapes/ellipse.ts +75 -0
- package/src/components/shapes/index.ts +3 -0
- package/src/components/shapes/rectangle.ts +45 -0
- package/src/components/text/index.ts +1 -0
- package/src/components/text/text.ts +137 -0
- package/src/components/transform/index.ts +3 -0
- package/src/components/transform/rotate.ts +26 -0
- package/src/components/transform/scale.ts +34 -0
- package/src/components/transform/translate.ts +27 -0
- package/src/context/create-context.ts +49 -0
- package/src/context/index.ts +1 -0
- package/src/hooks/index.ts +8 -0
- package/src/hooks/use-canvas-context.ts +11 -0
- package/src/hooks/use-linear-gradient.ts +39 -0
- package/src/hooks/use-loop.ts +11 -0
- package/src/hooks/use-on.ts +18 -0
- package/src/hooks/use-radial-gradient.ts +45 -0
- package/src/hooks/use-render.ts +14 -0
- package/src/hooks/use-state.ts +9 -0
- package/src/hooks/use-window-size.ts +24 -0
- package/src/index.ts +6 -0
- package/src/internal/emitter.ts +39 -0
- package/src/internal/global.ts +5 -0
- package/src/internal/hooks.ts +32 -0
- package/src/internal/reactive.test.ts +20 -0
- package/src/internal/reactive.ts +20 -0
- package/src/jsx-runtime.ts +21 -0
- package/src/render.ts +299 -0
- package/src/types.ts +151 -0
- package/src/utils/apply-fill-and-stroke-style.ts +33 -0
- package/src/utils/get-recommended-pixel-ratio.ts +2 -0
- package/src/utils/index.ts +8 -0
- package/src/utils/is-own-property-of.ts +6 -0
- package/src/utils/is-valid-fill-or-stroke-style.ts +5 -0
- package/src/utils/is-valid-stroke-cap.ts +10 -0
- package/src/utils/is-valid-stroke-join.ts +10 -0
- package/src/utils/resolve-styles.ts +21 -0
- package/src/utils/type-guards.ts +4 -0
- package/src/utils/with-px.ts +4 -0
- package/tsb.config.ts +11 -0
- package/tsconfig.dist.json +13 -0
- package/tsconfig.json +25 -0
package/.eslintignore
ADDED
package/.eslintrc.json
ADDED
|
@@ -0,0 +1,286 @@
|
|
|
1
|
+
{
|
|
2
|
+
"extends": [
|
|
3
|
+
"eslint:recommended",
|
|
4
|
+
"plugin:prettier/recommended",
|
|
5
|
+
"plugin:@typescript-eslint/eslint-recommended",
|
|
6
|
+
"plugin:@typescript-eslint/recommended"
|
|
7
|
+
],
|
|
8
|
+
"plugins": ["prettier", "simple-import-sort"],
|
|
9
|
+
"env": {
|
|
10
|
+
"es6": true,
|
|
11
|
+
"commonjs": true
|
|
12
|
+
},
|
|
13
|
+
"parser": "@typescript-eslint/parser",
|
|
14
|
+
"parserOptions": {
|
|
15
|
+
"sourceType": "module",
|
|
16
|
+
"ecmaVersion": 9
|
|
17
|
+
},
|
|
18
|
+
"globals": {
|
|
19
|
+
"window": false,
|
|
20
|
+
"performance": false,
|
|
21
|
+
"document": false,
|
|
22
|
+
"navigator": false,
|
|
23
|
+
"location": false,
|
|
24
|
+
"console": false,
|
|
25
|
+
"setTimeout": false,
|
|
26
|
+
"clearTimeout": false,
|
|
27
|
+
"setInterval": false,
|
|
28
|
+
"clearInterval": false,
|
|
29
|
+
"alert": false,
|
|
30
|
+
"requestAnimationFrame": false,
|
|
31
|
+
"cancelAnimationFrame": false,
|
|
32
|
+
"localStorage": false,
|
|
33
|
+
"sessionStorage": false,
|
|
34
|
+
"FormData": false,
|
|
35
|
+
"Node": false,
|
|
36
|
+
"Image": false,
|
|
37
|
+
"CanvasRenderingContext2D": false
|
|
38
|
+
},
|
|
39
|
+
"rules": {
|
|
40
|
+
"strict": [2, "global"],
|
|
41
|
+
"no-duplicate-imports": [2, { "includeExports": true }],
|
|
42
|
+
|
|
43
|
+
"eqeqeq": 2,
|
|
44
|
+
"block-scoped-var": 2,
|
|
45
|
+
"no-constant-condition": 2,
|
|
46
|
+
"no-console": 2,
|
|
47
|
+
"no-debugger": 2,
|
|
48
|
+
"no-lonely-if": 2,
|
|
49
|
+
"no-lone-blocks": 2,
|
|
50
|
+
"no-nested-ternary": 2,
|
|
51
|
+
"no-dupe-keys": 2,
|
|
52
|
+
"no-extra-boolean-cast": 2,
|
|
53
|
+
"no-irregular-whitespace": 2,
|
|
54
|
+
"no-else-return": 2,
|
|
55
|
+
"no-eval": 2,
|
|
56
|
+
"no-multi-str": 2,
|
|
57
|
+
"no-self-compare": 2,
|
|
58
|
+
"no-useless-call": 2,
|
|
59
|
+
"no-shadow-restricted-names": 2,
|
|
60
|
+
"no-shadow": 0,
|
|
61
|
+
"no-undef": 2,
|
|
62
|
+
"no-undef-init": 2,
|
|
63
|
+
"no-unreachable": 2,
|
|
64
|
+
"no-unused-vars": [2, { "varsIgnorePattern": "^_\\w" }],
|
|
65
|
+
"no-use-before-define": 2,
|
|
66
|
+
|
|
67
|
+
"radix": 2,
|
|
68
|
+
"curly": 2,
|
|
69
|
+
"no-fallthrough": 2,
|
|
70
|
+
"default-case": 2,
|
|
71
|
+
|
|
72
|
+
"no-var": 2,
|
|
73
|
+
"no-unused-expressions": 2,
|
|
74
|
+
"camelcase": [
|
|
75
|
+
2,
|
|
76
|
+
{
|
|
77
|
+
"properties": "always",
|
|
78
|
+
"allow": ["^UNSAFE_", "call_id"]
|
|
79
|
+
}
|
|
80
|
+
],
|
|
81
|
+
"@typescript-eslint/no-explicit-any": 2,
|
|
82
|
+
"@typescript-eslint/explicit-function-return-type": 0,
|
|
83
|
+
"@typescript-eslint/member-delimiter-style": 0,
|
|
84
|
+
"@typescript-eslint/type-annotation-spacing": 0,
|
|
85
|
+
"@typescript-eslint/no-unused-vars": 2,
|
|
86
|
+
"@typescript-eslint/no-use-before-define": 2,
|
|
87
|
+
"@typescript-eslint/no-shadow": 2,
|
|
88
|
+
"no-restricted-globals": [
|
|
89
|
+
"error",
|
|
90
|
+
"URL",
|
|
91
|
+
"history",
|
|
92
|
+
"dispatchEvent",
|
|
93
|
+
"require",
|
|
94
|
+
"postMessage",
|
|
95
|
+
"blur",
|
|
96
|
+
"focus",
|
|
97
|
+
"close",
|
|
98
|
+
"frames",
|
|
99
|
+
"self",
|
|
100
|
+
"parent",
|
|
101
|
+
"opener",
|
|
102
|
+
"top",
|
|
103
|
+
"length",
|
|
104
|
+
"closed",
|
|
105
|
+
"location",
|
|
106
|
+
"origin",
|
|
107
|
+
"name",
|
|
108
|
+
"locationbar",
|
|
109
|
+
"menubar",
|
|
110
|
+
"personalbar",
|
|
111
|
+
"scrollbars",
|
|
112
|
+
"statusbar",
|
|
113
|
+
"toolbar",
|
|
114
|
+
"status",
|
|
115
|
+
"frameElement",
|
|
116
|
+
"navigator",
|
|
117
|
+
"customElements",
|
|
118
|
+
"external",
|
|
119
|
+
"screen",
|
|
120
|
+
"innerWidth",
|
|
121
|
+
"innerHeight",
|
|
122
|
+
"scrollX",
|
|
123
|
+
"pageXOffset",
|
|
124
|
+
"scrollY",
|
|
125
|
+
"pageYOffset",
|
|
126
|
+
"screenX",
|
|
127
|
+
"screenY",
|
|
128
|
+
"outerWidth",
|
|
129
|
+
"outerHeight",
|
|
130
|
+
"devicePixelRatio",
|
|
131
|
+
"clientInformation",
|
|
132
|
+
"screenLeft",
|
|
133
|
+
"screenTop",
|
|
134
|
+
"defaultStatus",
|
|
135
|
+
"defaultstatus",
|
|
136
|
+
"styleMedia",
|
|
137
|
+
"onanimationend",
|
|
138
|
+
"onanimationiteration",
|
|
139
|
+
"onanimationstart",
|
|
140
|
+
"onsearch",
|
|
141
|
+
"ontransitionend",
|
|
142
|
+
"onwebkitanimationend",
|
|
143
|
+
"onwebkitanimationiteration",
|
|
144
|
+
"onwebkitanimationstart",
|
|
145
|
+
"onwebkittransitionend",
|
|
146
|
+
"isSecureContext",
|
|
147
|
+
"onabort",
|
|
148
|
+
"onblur",
|
|
149
|
+
"oncancel",
|
|
150
|
+
"oncanplay",
|
|
151
|
+
"oncanplaythrough",
|
|
152
|
+
"onchange",
|
|
153
|
+
"onclick",
|
|
154
|
+
"onclose",
|
|
155
|
+
"oncontextmenu",
|
|
156
|
+
"oncuechange",
|
|
157
|
+
"ondblclick",
|
|
158
|
+
"ondrag",
|
|
159
|
+
"ondragend",
|
|
160
|
+
"ondragenter",
|
|
161
|
+
"ondragleave",
|
|
162
|
+
"ondragover",
|
|
163
|
+
"ondragstart",
|
|
164
|
+
"ondrop",
|
|
165
|
+
"ondurationchange",
|
|
166
|
+
"onemptied",
|
|
167
|
+
"onended",
|
|
168
|
+
"onerror",
|
|
169
|
+
"onfocus",
|
|
170
|
+
"oninput",
|
|
171
|
+
"oninvalid",
|
|
172
|
+
"onkeydown",
|
|
173
|
+
"onkeypress",
|
|
174
|
+
"onkeyup",
|
|
175
|
+
"onload",
|
|
176
|
+
"onloadeddata",
|
|
177
|
+
"onloadedmetadata",
|
|
178
|
+
"onloadstart",
|
|
179
|
+
"onmousedown",
|
|
180
|
+
"onmouseenter",
|
|
181
|
+
"onmouseleave",
|
|
182
|
+
"onmousemove",
|
|
183
|
+
"onmouseout",
|
|
184
|
+
"onmouseover",
|
|
185
|
+
"onmouseup",
|
|
186
|
+
"onmousewheel",
|
|
187
|
+
"onpause",
|
|
188
|
+
"onplay",
|
|
189
|
+
"onplaying",
|
|
190
|
+
"onprogress",
|
|
191
|
+
"onratechange",
|
|
192
|
+
"onreset",
|
|
193
|
+
"onresize",
|
|
194
|
+
"onscroll",
|
|
195
|
+
"onseeked",
|
|
196
|
+
"onseeking",
|
|
197
|
+
"onselect",
|
|
198
|
+
"onstalled",
|
|
199
|
+
"onsubmit",
|
|
200
|
+
"onsuspend",
|
|
201
|
+
"ontimeupdate",
|
|
202
|
+
"ontoggle",
|
|
203
|
+
"onvolumechange",
|
|
204
|
+
"onwaiting",
|
|
205
|
+
"onwheel",
|
|
206
|
+
"onauxclick",
|
|
207
|
+
"ongotpointercapture",
|
|
208
|
+
"onlostpointercapture",
|
|
209
|
+
"onpointerdown",
|
|
210
|
+
"onpointermove",
|
|
211
|
+
"onpointerup",
|
|
212
|
+
"onpointercancel",
|
|
213
|
+
"onpointerover",
|
|
214
|
+
"onpointerout",
|
|
215
|
+
"onpointerenter",
|
|
216
|
+
"onpointerleave",
|
|
217
|
+
"onafterprint",
|
|
218
|
+
"onbeforeprint",
|
|
219
|
+
"onbeforeunload",
|
|
220
|
+
"onhashchange",
|
|
221
|
+
"onlanguagechange",
|
|
222
|
+
"onmessage",
|
|
223
|
+
"onmessageerror",
|
|
224
|
+
"onoffline",
|
|
225
|
+
"ononline",
|
|
226
|
+
"onpagehide",
|
|
227
|
+
"onpageshow",
|
|
228
|
+
"onpopstate",
|
|
229
|
+
"onrejectionhandled",
|
|
230
|
+
"onstorage",
|
|
231
|
+
"onunhandledrejection",
|
|
232
|
+
"onunload",
|
|
233
|
+
"performance",
|
|
234
|
+
"stop",
|
|
235
|
+
"open",
|
|
236
|
+
"print",
|
|
237
|
+
"captureEvents",
|
|
238
|
+
"releaseEvents",
|
|
239
|
+
"getComputedStyle",
|
|
240
|
+
"matchMedia",
|
|
241
|
+
"moveTo",
|
|
242
|
+
"moveBy",
|
|
243
|
+
"resizeTo",
|
|
244
|
+
"resizeBy",
|
|
245
|
+
"getSelection",
|
|
246
|
+
"find",
|
|
247
|
+
"createImageBitmap",
|
|
248
|
+
"scroll",
|
|
249
|
+
"scrollTo",
|
|
250
|
+
"scrollBy",
|
|
251
|
+
"onappinstalled",
|
|
252
|
+
"onbeforeinstallprompt",
|
|
253
|
+
"crypto",
|
|
254
|
+
"ondevicemotion",
|
|
255
|
+
"ondeviceorientation",
|
|
256
|
+
"ondeviceorientationabsolute",
|
|
257
|
+
"indexedDB",
|
|
258
|
+
"webkitStorageInfo",
|
|
259
|
+
"chrome",
|
|
260
|
+
"visualViewport",
|
|
261
|
+
"speechSynthesis",
|
|
262
|
+
"webkitRequestFileSystem",
|
|
263
|
+
"webkitResolveLocalFileSystemURL",
|
|
264
|
+
"openDatabase",
|
|
265
|
+
"setTimeout",
|
|
266
|
+
"clearTimeout",
|
|
267
|
+
"setInterval",
|
|
268
|
+
"clearInterval",
|
|
269
|
+
"requestAnimationFrame",
|
|
270
|
+
"cancelAnimationFrame",
|
|
271
|
+
"addEventListener",
|
|
272
|
+
"removeEventListener"
|
|
273
|
+
],
|
|
274
|
+
"simple-import-sort/imports": "error"
|
|
275
|
+
},
|
|
276
|
+
"overrides": [
|
|
277
|
+
{
|
|
278
|
+
"files": ["*.ts", "*.tsx"],
|
|
279
|
+
"rules": {
|
|
280
|
+
"no-undef": 0,
|
|
281
|
+
"no-unused-vars": 0,
|
|
282
|
+
"no-use-before-define": 0
|
|
283
|
+
}
|
|
284
|
+
}
|
|
285
|
+
]
|
|
286
|
+
}
|
package/.gitattributes
ADDED
|
@@ -0,0 +1 @@
|
|
|
1
|
+
* @jakesidsmith
|
|
@@ -0,0 +1,19 @@
|
|
|
1
|
+
name: CI
|
|
2
|
+
on: [pull_request]
|
|
3
|
+
|
|
4
|
+
jobs:
|
|
5
|
+
test:
|
|
6
|
+
runs-on: ubuntu-latest
|
|
7
|
+
steps:
|
|
8
|
+
- uses: actions/checkout@v4
|
|
9
|
+
- uses: actions/cache@v4
|
|
10
|
+
with:
|
|
11
|
+
path: ~/.npm
|
|
12
|
+
key: ${{ runner.os }}-node-${{ hashFiles('package-lock.json') }}
|
|
13
|
+
- uses: actions/setup-node@v4
|
|
14
|
+
with:
|
|
15
|
+
node-version-file: '.nvmrc'
|
|
16
|
+
- name: Install dependencies
|
|
17
|
+
run: npm ci
|
|
18
|
+
- name: Run tests
|
|
19
|
+
run: npm test
|
package/.nvmrc
ADDED
|
@@ -0,0 +1 @@
|
|
|
1
|
+
22.14.0
|
package/.prettierignore
ADDED
|
@@ -0,0 +1,28 @@
|
|
|
1
|
+
/coverage/*
|
|
2
|
+
/build/*
|
|
3
|
+
/dist/*
|
|
4
|
+
/packages/*/coverage/*
|
|
5
|
+
/packages/*/static/*
|
|
6
|
+
/packages/*/server/*
|
|
7
|
+
/packages/*/build/*
|
|
8
|
+
/packages/*/dist/*
|
|
9
|
+
/.vscode/*
|
|
10
|
+
**/*.txt
|
|
11
|
+
**/*.snap
|
|
12
|
+
*.toml
|
|
13
|
+
*.png
|
|
14
|
+
*.svg
|
|
15
|
+
*.jpg
|
|
16
|
+
*.jpeg
|
|
17
|
+
*.gif
|
|
18
|
+
|
|
19
|
+
.DS_Store
|
|
20
|
+
.eslintignore
|
|
21
|
+
.prettierignore
|
|
22
|
+
.gitignore
|
|
23
|
+
.gitattributes
|
|
24
|
+
.npmignore
|
|
25
|
+
.nvmrc
|
|
26
|
+
.browserslistrc
|
|
27
|
+
.env
|
|
28
|
+
LICENSE.txt
|
package/.prettierrc.json
ADDED
package/demo/index.html
ADDED
|
@@ -0,0 +1,29 @@
|
|
|
1
|
+
<!doctype html>
|
|
2
|
+
<html>
|
|
3
|
+
<head>
|
|
4
|
+
<meta charset="utf-8" />
|
|
5
|
+
<meta
|
|
6
|
+
name="viewport"
|
|
7
|
+
content="width=device-width, initial-scale=1, maximum-scale=1"
|
|
8
|
+
/>
|
|
9
|
+
<title>
|
|
10
|
+
RCX - Reactive JSX-based library for creating HTML5 canvas applications
|
|
11
|
+
</title>
|
|
12
|
+
<style type="text/css">
|
|
13
|
+
html,
|
|
14
|
+
body {
|
|
15
|
+
margin: 0;
|
|
16
|
+
padding: 0;
|
|
17
|
+
width: 100%;
|
|
18
|
+
height: 100%;
|
|
19
|
+
overflow: hidden;
|
|
20
|
+
}
|
|
21
|
+
|
|
22
|
+
canvas {
|
|
23
|
+
width: 100%;
|
|
24
|
+
height: 100%;
|
|
25
|
+
}
|
|
26
|
+
</style>
|
|
27
|
+
</head>
|
|
28
|
+
<body></body>
|
|
29
|
+
</html>
|
package/demo/index.tsx
ADDED
|
@@ -0,0 +1,316 @@
|
|
|
1
|
+
import {
|
|
2
|
+
ArcTo,
|
|
3
|
+
Canvas,
|
|
4
|
+
Circle,
|
|
5
|
+
Clip,
|
|
6
|
+
Ellipse,
|
|
7
|
+
Line,
|
|
8
|
+
Path,
|
|
9
|
+
Point,
|
|
10
|
+
RCXComponent,
|
|
11
|
+
Rectangle,
|
|
12
|
+
render,
|
|
13
|
+
Rotate,
|
|
14
|
+
Scale,
|
|
15
|
+
Text,
|
|
16
|
+
Translate,
|
|
17
|
+
useCanvasContext,
|
|
18
|
+
useLinearGradient,
|
|
19
|
+
useLoop,
|
|
20
|
+
useOnMount,
|
|
21
|
+
useRadialGradient,
|
|
22
|
+
useReactive,
|
|
23
|
+
} from '@blinkorb/rcx';
|
|
24
|
+
|
|
25
|
+
const RendersChildren: RCXComponent = ({ children }) => children;
|
|
26
|
+
|
|
27
|
+
const Unmounts: RCXComponent = () => {
|
|
28
|
+
// eslint-disable-next-line no-console
|
|
29
|
+
console.log('rendered');
|
|
30
|
+
|
|
31
|
+
useOnMount(() => {
|
|
32
|
+
// eslint-disable-next-line no-console
|
|
33
|
+
console.log('mounted');
|
|
34
|
+
|
|
35
|
+
return () => {
|
|
36
|
+
// eslint-disable-next-line no-console
|
|
37
|
+
console.log('unmounted');
|
|
38
|
+
};
|
|
39
|
+
});
|
|
40
|
+
|
|
41
|
+
return (
|
|
42
|
+
<Rectangle x={0} y={0} width={10} height={10} style={{ fill: 'black' }} />
|
|
43
|
+
);
|
|
44
|
+
};
|
|
45
|
+
|
|
46
|
+
const Gradients: RCXComponent = () => {
|
|
47
|
+
const stroke = useLinearGradient({
|
|
48
|
+
startX: 10,
|
|
49
|
+
startY: 480,
|
|
50
|
+
endX: 10 + 50,
|
|
51
|
+
endY: 480 + 50,
|
|
52
|
+
stops: [
|
|
53
|
+
{
|
|
54
|
+
offset: 0,
|
|
55
|
+
color: '#f00',
|
|
56
|
+
},
|
|
57
|
+
{
|
|
58
|
+
offset: 1,
|
|
59
|
+
color: '#000',
|
|
60
|
+
},
|
|
61
|
+
],
|
|
62
|
+
});
|
|
63
|
+
|
|
64
|
+
const fill = useRadialGradient({
|
|
65
|
+
startX: 10 + 25,
|
|
66
|
+
startY: 480 + 25,
|
|
67
|
+
startRadius: 0,
|
|
68
|
+
endX: 10 + 25,
|
|
69
|
+
endY: 480 + 25,
|
|
70
|
+
endRadius: 25,
|
|
71
|
+
stops: [
|
|
72
|
+
{
|
|
73
|
+
offset: 0,
|
|
74
|
+
color: '#000',
|
|
75
|
+
},
|
|
76
|
+
{
|
|
77
|
+
offset: 1,
|
|
78
|
+
color: 'cyan',
|
|
79
|
+
},
|
|
80
|
+
],
|
|
81
|
+
});
|
|
82
|
+
|
|
83
|
+
return (
|
|
84
|
+
<Rectangle
|
|
85
|
+
x={10}
|
|
86
|
+
y={480}
|
|
87
|
+
width={50}
|
|
88
|
+
height={50}
|
|
89
|
+
style={{ fill, stroke, strokeWidth: 5, strokeCap: 'round' }}
|
|
90
|
+
/>
|
|
91
|
+
);
|
|
92
|
+
};
|
|
93
|
+
|
|
94
|
+
const Page: RCXComponent = () => {
|
|
95
|
+
const canvasContext = useCanvasContext();
|
|
96
|
+
const getOffset = () => Math.cos(Date.now() * 0.001) * 10;
|
|
97
|
+
const reactive = useReactive({ isMounted: true, offset: getOffset() });
|
|
98
|
+
|
|
99
|
+
useLoop(() => {
|
|
100
|
+
reactive.offset = getOffset();
|
|
101
|
+
});
|
|
102
|
+
|
|
103
|
+
useOnMount(() => {
|
|
104
|
+
window.setTimeout(() => {
|
|
105
|
+
reactive.isMounted = false;
|
|
106
|
+
}, 1000);
|
|
107
|
+
});
|
|
108
|
+
|
|
109
|
+
return (
|
|
110
|
+
<>
|
|
111
|
+
<Rectangle
|
|
112
|
+
x={canvasContext.width * 0.25}
|
|
113
|
+
y={canvasContext.height * 0.25 + reactive.offset}
|
|
114
|
+
width={canvasContext.width * 0.5}
|
|
115
|
+
height={canvasContext.height * 0.5}
|
|
116
|
+
style={{ fill: 'red' }}
|
|
117
|
+
/>
|
|
118
|
+
<Ellipse
|
|
119
|
+
x={canvasContext.width * 0.5}
|
|
120
|
+
y={canvasContext.height * 0.5}
|
|
121
|
+
radiusX={canvasContext.width * 0.2}
|
|
122
|
+
radiusY={canvasContext.width * 0.1}
|
|
123
|
+
style={{ fill: 'black' }}
|
|
124
|
+
rotation={((Date.now() % 5000) / 5000) * Math.PI * 2}
|
|
125
|
+
/>
|
|
126
|
+
<Circle
|
|
127
|
+
x={canvasContext.width * 0.5}
|
|
128
|
+
y={canvasContext.height * 0.5}
|
|
129
|
+
radius={canvasContext.width * 0.05}
|
|
130
|
+
endAngle={
|
|
131
|
+
Math.PI +
|
|
132
|
+
Math.cos(((Date.now() % 5000) / 5000) * Math.PI * 2) * Math.PI
|
|
133
|
+
}
|
|
134
|
+
style={{ fill: 'white' }}
|
|
135
|
+
>
|
|
136
|
+
<Point x={canvasContext.width * 0.5} y={canvasContext.height * 0.5} />
|
|
137
|
+
</Circle>
|
|
138
|
+
<Line
|
|
139
|
+
startX={10}
|
|
140
|
+
startY={10}
|
|
141
|
+
endX={20}
|
|
142
|
+
endY={20}
|
|
143
|
+
style={{ stroke: 'green', strokeWidth: 5, strokeJoin: 'bevel' }}
|
|
144
|
+
>
|
|
145
|
+
<Point x={30} y={10} />
|
|
146
|
+
</Line>
|
|
147
|
+
<Path
|
|
148
|
+
points={[
|
|
149
|
+
[0, 20],
|
|
150
|
+
[5, 50],
|
|
151
|
+
[10, 0],
|
|
152
|
+
[15, 20],
|
|
153
|
+
[20, 5],
|
|
154
|
+
]}
|
|
155
|
+
style={{ stroke: 'black' }}
|
|
156
|
+
/>
|
|
157
|
+
<Path style={{ stroke: 'black' }} closePath>
|
|
158
|
+
<Point x={0} y={50} />
|
|
159
|
+
<Point x={5} y={55} />
|
|
160
|
+
<Point x={10} y={50} />
|
|
161
|
+
<Point x={15} y={55} />
|
|
162
|
+
<Point x={20} y={50} />
|
|
163
|
+
<Point x={20} y={75} />
|
|
164
|
+
<Point x={0} y={75} />
|
|
165
|
+
</Path>
|
|
166
|
+
<Path style={{ stroke: 'blue', strokeWidth: 5, strokeCap: 'round' }}>
|
|
167
|
+
<Point x={200} y={200} />
|
|
168
|
+
<ArcTo
|
|
169
|
+
startControlX={200}
|
|
170
|
+
startControlY={100}
|
|
171
|
+
endControlX={300}
|
|
172
|
+
endControlY={100}
|
|
173
|
+
radius={50}
|
|
174
|
+
/>
|
|
175
|
+
<Point x={300} y={100} />
|
|
176
|
+
</Path>
|
|
177
|
+
<Text x={305} y={102} style={{ fill: 'red', stroke: 'black' }}>
|
|
178
|
+
The offset is {reactive.offset.toFixed(2)} {[1, 2, 3].map((n) => n)}{' '}
|
|
179
|
+
<RendersChildren>Children</RendersChildren>
|
|
180
|
+
</Text>
|
|
181
|
+
<Translate x={100} y={100}>
|
|
182
|
+
<Rotate rotation={Math.PI * 0.25}>
|
|
183
|
+
<Scale scale={0.5}>
|
|
184
|
+
<Rectangle
|
|
185
|
+
x={0}
|
|
186
|
+
y={0}
|
|
187
|
+
width={100}
|
|
188
|
+
height={50}
|
|
189
|
+
style={{ fill: 'cyan' }}
|
|
190
|
+
/>
|
|
191
|
+
</Scale>
|
|
192
|
+
</Rotate>
|
|
193
|
+
</Translate>
|
|
194
|
+
<Rectangle x={0} y={100} width={50} height={50}>
|
|
195
|
+
<Clip>
|
|
196
|
+
<Circle x={25} y={125} radius={30} style={{ fill: '#d5d5d5' }} />
|
|
197
|
+
<Text x={10} y={125} style={{ fill: 'red' }}>
|
|
198
|
+
This text is clipped by a rectangle
|
|
199
|
+
</Text>
|
|
200
|
+
</Clip>
|
|
201
|
+
</Rectangle>
|
|
202
|
+
|
|
203
|
+
<Line
|
|
204
|
+
startX={100}
|
|
205
|
+
endX={100}
|
|
206
|
+
startY={190}
|
|
207
|
+
endY={290}
|
|
208
|
+
style={{ stroke: '#d5d5d5' }}
|
|
209
|
+
/>
|
|
210
|
+
<Text x={100} y={200} style={{ fill: 'black' }}>
|
|
211
|
+
Left (default)
|
|
212
|
+
</Text>
|
|
213
|
+
<Text x={100} y={220} style={{ fill: 'black', align: 'right' }}>
|
|
214
|
+
Right
|
|
215
|
+
</Text>
|
|
216
|
+
<Text x={100} y={240} style={{ fill: 'black', align: 'center' }}>
|
|
217
|
+
Center
|
|
218
|
+
</Text>
|
|
219
|
+
<Text x={100} y={260} style={{ fill: 'black', align: 'start' }}>
|
|
220
|
+
Start
|
|
221
|
+
</Text>
|
|
222
|
+
<Text x={100} y={280} style={{ fill: 'black', align: 'end' }}>
|
|
223
|
+
End
|
|
224
|
+
</Text>
|
|
225
|
+
|
|
226
|
+
<Line
|
|
227
|
+
startX={50}
|
|
228
|
+
endX={150}
|
|
229
|
+
startY={300}
|
|
230
|
+
endY={300}
|
|
231
|
+
style={{ stroke: '#d5d5d5' }}
|
|
232
|
+
/>
|
|
233
|
+
<Text x={100} y={300} style={{ fill: 'black', baseline: 'alphabetic' }}>
|
|
234
|
+
Alphabetic (default)
|
|
235
|
+
</Text>
|
|
236
|
+
<Line
|
|
237
|
+
startX={50}
|
|
238
|
+
endX={150}
|
|
239
|
+
startY={320}
|
|
240
|
+
endY={320}
|
|
241
|
+
style={{ stroke: '#d5d5d5' }}
|
|
242
|
+
/>
|
|
243
|
+
<Text x={100} y={320} style={{ fill: 'black', baseline: 'bottom' }}>
|
|
244
|
+
Bottom
|
|
245
|
+
</Text>
|
|
246
|
+
<Line
|
|
247
|
+
startX={50}
|
|
248
|
+
endX={150}
|
|
249
|
+
startY={340}
|
|
250
|
+
endY={340}
|
|
251
|
+
style={{ stroke: '#d5d5d5' }}
|
|
252
|
+
/>
|
|
253
|
+
<Text x={100} y={340} style={{ fill: 'black', baseline: 'hanging' }}>
|
|
254
|
+
Hanging
|
|
255
|
+
</Text>
|
|
256
|
+
<Line
|
|
257
|
+
startX={50}
|
|
258
|
+
endX={150}
|
|
259
|
+
startY={360}
|
|
260
|
+
endY={360}
|
|
261
|
+
style={{ stroke: '#d5d5d5' }}
|
|
262
|
+
/>
|
|
263
|
+
<Text x={100} y={360} style={{ fill: 'black', baseline: 'ideographic' }}>
|
|
264
|
+
Ideographic
|
|
265
|
+
</Text>
|
|
266
|
+
<Line
|
|
267
|
+
startX={50}
|
|
268
|
+
endX={150}
|
|
269
|
+
startY={380}
|
|
270
|
+
endY={380}
|
|
271
|
+
style={{ stroke: '#d5d5d5' }}
|
|
272
|
+
/>
|
|
273
|
+
<Text x={100} y={380} style={{ fill: 'black', baseline: 'middle' }}>
|
|
274
|
+
Middle
|
|
275
|
+
</Text>
|
|
276
|
+
<Line
|
|
277
|
+
startX={50}
|
|
278
|
+
endX={150}
|
|
279
|
+
startY={400}
|
|
280
|
+
endY={400}
|
|
281
|
+
style={{ stroke: '#d5d5d5' }}
|
|
282
|
+
/>
|
|
283
|
+
<Text x={100} y={400} style={{ fill: 'black', baseline: 'top' }}>
|
|
284
|
+
Top
|
|
285
|
+
</Text>
|
|
286
|
+
<Text
|
|
287
|
+
x={10}
|
|
288
|
+
y={450}
|
|
289
|
+
style={{
|
|
290
|
+
fill: 'black',
|
|
291
|
+
fontSize: 20,
|
|
292
|
+
fontFamily: 'serif',
|
|
293
|
+
fontWeight: 'bold',
|
|
294
|
+
fontStyle: 'italic',
|
|
295
|
+
fontVariant: 'small-caps',
|
|
296
|
+
}}
|
|
297
|
+
>
|
|
298
|
+
Styled font
|
|
299
|
+
</Text>
|
|
300
|
+
<Gradients />
|
|
301
|
+
{reactive.isMounted && <Unmounts />}
|
|
302
|
+
</>
|
|
303
|
+
);
|
|
304
|
+
};
|
|
305
|
+
|
|
306
|
+
Page.displayName = 'Page';
|
|
307
|
+
|
|
308
|
+
const App = () => {
|
|
309
|
+
return (
|
|
310
|
+
<Canvas>
|
|
311
|
+
<Page />
|
|
312
|
+
</Canvas>
|
|
313
|
+
);
|
|
314
|
+
};
|
|
315
|
+
|
|
316
|
+
render(<App />, document.body);
|