moonscratch 0.1.1 → 0.1.2
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/chunk-DQk6qfdC.mjs +18 -0
- package/dist/index.d.mts +1173 -0
- package/dist/index.mjs +27135 -0
- package/package.json +6 -1
- package/.agents/skills/moonbit-agent-guide/LICENSE +0 -202
- package/.agents/skills/moonbit-agent-guide/SKILL.mbt.md +0 -1126
- package/.agents/skills/moonbit-agent-guide/SKILL.md +0 -1126
- package/.agents/skills/moonbit-agent-guide/ide.md +0 -116
- package/.agents/skills/moonbit-agent-guide/references/advanced-moonbit-build.md +0 -106
- package/.agents/skills/moonbit-agent-guide/references/moonbit-language-fundamentals.mbt.md +0 -422
- package/.agents/skills/moonbit-agent-guide/references/moonbit-language-fundamentals.md +0 -422
- package/.agents/skills/moonbit-practice/SKILL.md +0 -258
- package/.agents/skills/moonbit-practice/assets/ci.yaml +0 -25
- package/.agents/skills/moonbit-practice/reference/agents.md +0 -1469
- package/.agents/skills/moonbit-practice/reference/configuration.md +0 -228
- package/.agents/skills/moonbit-practice/reference/ffi.md +0 -229
- package/.agents/skills/moonbit-practice/reference/ide.md +0 -189
- package/.agents/skills/moonbit-practice/reference/performance.md +0 -217
- package/.agents/skills/moonbit-practice/reference/refactor.md +0 -154
- package/.agents/skills/moonbit-practice/reference/stdlib.md +0 -351
- package/.agents/skills/moonbit-practice/reference/testing.md +0 -228
- package/.agents/skills/moonbit-refactoring/LICENSE +0 -21
- package/.agents/skills/moonbit-refactoring/SKILL.md +0 -323
- package/.githooks/README.md +0 -23
- package/.githooks/pre-commit +0 -3
- package/.github/workflows/copilot-setup-steps.yml +0 -40
- package/AGENTS.md +0 -91
- package/PLAN.md +0 -64
- package/TODO.md +0 -120
- package/benchmarks/calc.bench.ts +0 -144
- package/benchmarks/draw.bench.ts +0 -215
- package/benchmarks/load.bench.ts +0 -28
- package/benchmarks/render.bench.ts +0 -53
- package/benchmarks/run.bench.ts +0 -8
- package/benchmarks/types.d.ts +0 -15
- package/docs/scratch-vm-specs/eventloop.md +0 -103
- package/docs/scratch-vm-specs/moonscratch-time-separation.md +0 -50
- package/index.html +0 -91
- package/js/AGENTS.md +0 -5
- package/js/a.ts +0 -52
- package/js/assets/AGENTS.md +0 -5
- package/js/assets/base64.test.ts +0 -14
- package/js/assets/base64.ts +0 -21
- package/js/assets/build-asset.test.ts +0 -26
- package/js/assets/build-asset.ts +0 -28
- package/js/assets/create.test.ts +0 -142
- package/js/assets/create.ts +0 -122
- package/js/assets/index.test.ts +0 -15
- package/js/assets/index.ts +0 -2
- package/js/assets/types.ts +0 -26
- package/js/assets/validation.test.ts +0 -34
- package/js/assets/validation.ts +0 -25
- package/js/assets.test.ts +0 -14
- package/js/assets.ts +0 -1
- package/js/index.test.ts +0 -26
- package/js/index.ts +0 -3
- package/js/render/index.test.ts +0 -65
- package/js/render/index.ts +0 -13
- package/js/render/sharp.ts +0 -87
- package/js/render/svg.ts +0 -68
- package/js/render/types.ts +0 -35
- package/js/render/utils.ts +0 -108
- package/js/render/webgl.ts +0 -274
- package/js/sharp-optional.d.ts +0 -16
- package/js/test/helpers.ts +0 -116
- package/js/test/hikkaku-sample.test.ts +0 -37
- package/js/test/rubik-components.input-motion.test.ts +0 -60
- package/js/test/rubik-components.lists.test.ts +0 -49
- package/js/test/rubik-components.operators.test.ts +0 -104
- package/js/test/rubik-components.pen.test.ts +0 -112
- package/js/test/rubik-components.procedures-loops.test.ts +0 -72
- package/js/test/rubik-components.variables-branches.test.ts +0 -57
- package/js/test/rubik-components.visibility-entry.test.ts +0 -31
- package/js/test/test-projects.ts +0 -598
- package/js/test/variable.ts +0 -200
- package/js/test/warp.test.ts +0 -59
- package/js/vm/AGENTS.md +0 -6
- package/js/vm/README.md +0 -183
- package/js/vm/bindings.test.ts +0 -13
- package/js/vm/bindings.ts +0 -5
- package/js/vm/compare-operators.test.ts +0 -145
- package/js/vm/constants.test.ts +0 -11
- package/js/vm/constants.ts +0 -4
- package/js/vm/effect-guards.test.ts +0 -68
- package/js/vm/effect-guards.ts +0 -44
- package/js/vm/factory.test.ts +0 -486
- package/js/vm/factory.ts +0 -615
- package/js/vm/headless-vm.test.ts +0 -131
- package/js/vm/headless-vm.ts +0 -342
- package/js/vm/index.test.ts +0 -28
- package/js/vm/index.ts +0 -5
- package/js/vm/internal-types.ts +0 -32
- package/js/vm/json.test.ts +0 -40
- package/js/vm/json.ts +0 -273
- package/js/vm/normalize.test.ts +0 -48
- package/js/vm/normalize.ts +0 -65
- package/js/vm/options.test.ts +0 -30
- package/js/vm/options.ts +0 -55
- package/js/vm/pen-transparency.test.ts +0 -115
- package/js/vm/program-wasm.ts +0 -322
- package/js/vm/scheduler-render.test.ts +0 -401
- package/js/vm/scratch-assets.test.ts +0 -136
- package/js/vm/scratch-assets.ts +0 -202
- package/js/vm/types.ts +0 -358
- package/js/vm/value-guards.test.ts +0 -25
- package/js/vm/value-guards.ts +0 -18
- package/moon.mod.json +0 -10
- package/scripts/preinstall.ts +0 -4
- package/src/AGENTS.md +0 -6
- package/src/api.mbt +0 -161
- package/src/api_aot_commands.mbt +0 -184
- package/src/api_effects_json.mbt +0 -72
- package/src/api_options.mbt +0 -60
- package/src/api_program_wasm.mbt +0 -1647
- package/src/api_program_wat.mbt +0 -2206
- package/src/api_snapshot_json.mbt +0 -44
- package/src/cmd/AGENTS.md +0 -5
- package/src/cmd/main/AGENTS.md +0 -5
- package/src/cmd/main/main.mbt +0 -29
- package/src/cmd/main/moon.pkg +0 -7
- package/src/cmd/main/pkg.generated.mbti +0 -13
- package/src/json_helpers.mbt +0 -176
- package/src/moon.pkg +0 -65
- package/src/moonscratch.mbt +0 -3
- package/src/moonscratch_wbtest.mbt +0 -40
- package/src/parser_sb3.mbt +0 -890
- package/src/pkg.generated.mbti +0 -479
- package/src/runtime_eval.mbt +0 -2844
- package/src/runtime_exec.mbt +0 -3850
- package/src/runtime_render.mbt +0 -2550
- package/src/runtime_state.mbt +0 -870
- package/src/test/AGENTS.md +0 -3
- package/src/test/projects/AGENTS.md +0 -6
- package/src/test/projects/moon.pkg +0 -4
- package/src/test/projects/moonscratch_compat_test.mbt +0 -642
- package/src/test/projects/moonscratch_core_test.mbt +0 -1332
- package/src/test/projects/moonscratch_runtime_test.mbt +0 -1087
- package/src/test/projects/pkg.generated.mbti +0 -13
- package/src/test/projects/test_support.mbt +0 -35
- package/src/types_effects.mbt +0 -20
- package/src/types_error.mbt +0 -4
- package/src/types_options.mbt +0 -31
- package/src/types_runtime_structs.mbt +0 -254
- package/src/types_vm.mbt +0 -109
- package/tsconfig.json +0 -29
- package/viewer/index.ts +0 -399
- package/viewer/vite.d.ts +0 -1
- package/viewer/worker.ts +0 -161
- package/vite.config.ts +0 -61
package/AGENTS.md
DELETED
|
@@ -1,91 +0,0 @@
|
|
|
1
|
-
# Project Agents.md Guide
|
|
2
|
-
|
|
3
|
-
This is a [MoonBit](https://docs.moonbitlang.com) project.
|
|
4
|
-
|
|
5
|
-
You can browse and install extra skills here:
|
|
6
|
-
<https://github.com/moonbitlang/skills>
|
|
7
|
-
|
|
8
|
-
## Project Structure
|
|
9
|
-
|
|
10
|
-
- MoonBit packages are organized per directory; each directory contains a
|
|
11
|
-
`moon.pkg` file listing its dependencies. Each package has its files and
|
|
12
|
-
blackbox test files (ending in `_test.mbt`) and whitebox test files (ending in
|
|
13
|
-
`_wbtest.mbt`).
|
|
14
|
-
|
|
15
|
-
- In the toplevel directory, there is a `moon.mod.json` file listing module
|
|
16
|
-
metadata.
|
|
17
|
-
|
|
18
|
-
* Tests under `src/` are unit tests only; macro-style tests should be written in `test/`.
|
|
19
|
-
|
|
20
|
-
## AGENTS.md Maintenance
|
|
21
|
-
|
|
22
|
-
- Place `AGENTS.md` files not only at the root but also in major directories where responsibilities diverge.
|
|
23
|
-
- Agents should autonomously update related `AGENTS.md` files when project structure or operating rules change, keeping instructions synchronized with the current state.
|
|
24
|
-
|
|
25
|
-
## Coding convention
|
|
26
|
-
|
|
27
|
-
- MoonBit code is organized in block style, each block is separated by `///|`,
|
|
28
|
-
the order of each block is irrelevant. In some refactorings, you can process
|
|
29
|
-
block by block independently.
|
|
30
|
-
|
|
31
|
-
- Try to keep deprecated blocks in file called `deprecated.mbt` in each
|
|
32
|
-
directory.
|
|
33
|
-
|
|
34
|
-
## Tooling
|
|
35
|
-
|
|
36
|
-
- `moon fmt` is used to format your code properly.
|
|
37
|
-
|
|
38
|
-
- `moon ide` provides project navigation helpers like `peek-def`, `outline`, and
|
|
39
|
-
`find-references`. See $moonbit-agent-guide for details.
|
|
40
|
-
|
|
41
|
-
- `moon info` is used to update the generated interface of the package, each
|
|
42
|
-
package has a generated interface file `.mbti`, it is a brief formal
|
|
43
|
-
description of the package. If nothing in `.mbti` changes, this means your
|
|
44
|
-
change does not bring the visible changes to the external package users, it is
|
|
45
|
-
typically a safe refactoring.
|
|
46
|
-
|
|
47
|
-
- In the last step, run `moon info && moon fmt` to update the interface and
|
|
48
|
-
format the code. Check the diffs of `.mbti` file to see if the changes are
|
|
49
|
-
expected.
|
|
50
|
-
|
|
51
|
-
- Run `moon test` to check tests pass. MoonBit supports snapshot testing; when
|
|
52
|
-
changes affect outputs, run `moon test --update` to refresh snapshots.
|
|
53
|
-
|
|
54
|
-
- Prefer `assert_eq` or `assert_true(pattern is Pattern(...))` for results that
|
|
55
|
-
are stable or very unlikely to change. Use snapshot tests to record current
|
|
56
|
-
behavior. For solid, well-defined results (e.g. scientific computations),
|
|
57
|
-
prefer assertion tests. You can use `moon coverage analyze > uncovered.log` to
|
|
58
|
-
see which parts of your code are not covered by tests.
|
|
59
|
-
|
|
60
|
-
## Commit & Pull Request Guidelines
|
|
61
|
-
|
|
62
|
-
- Commit messages follow Conventional Commit-style prefixes (e.g., `feat:`, `fix:`, `rename:`, `feat(blocks):`). Keep them concise and action-oriented.
|
|
63
|
-
- PRs should include a clear summary, link relevant issues/PRs, and add screenshots/GIFs for visible UI changes in `examples/example1`.
|
|
64
|
-
|
|
65
|
-
* If you are Codex, use `Co-authored-by: chatgpt-codex-connector[bot] <199175422+chatgpt-codex-connector[bot]@users.noreply.github.com>` in the commit message to credit the human collaborator.
|
|
66
|
-
- You have to add `--author="chatgpt-codex-connector[bot] <199175422+chatgpt-codex-connector[bot]@users.noreply.github.com>" --no-gpg-sign` option to git commit command.
|
|
67
|
-
Example:
|
|
68
|
-
```sh
|
|
69
|
-
git commit -m "fix: correct minor typos in code\n\nCo-authored-by: chatgpt-codex-connector[bot] <199175422+chatgpt-codex-connector[bot]@users.noreply.github.com>" --author="chatgpt-codex-connector[bot] <199175422+chatgpt-codex-connector[bot]@users.noreply.github.com>" --no-gpg-sign
|
|
70
|
-
```
|
|
71
|
-
* You can use git command and gh command to commit, push and create PR.
|
|
72
|
-
* Use "Squash and merge" to merge the PR on GitHub.
|
|
73
|
-
|
|
74
|
-
## JS
|
|
75
|
-
|
|
76
|
-
- Uses Bun as runtime environment.
|
|
77
|
-
- `bun run test` to run tests. `vite-plus/test` API is same as `vitest`.
|
|
78
|
-
- `bun run build` to build the project.
|
|
79
|
-
- `bun typecheck` to typecheck the code using `tsgo`.
|
|
80
|
-
- If you add or modify tests, run `bun run test` before reporting completion.
|
|
81
|
-
- Required before finishing any change in `packages/moonscratch`:
|
|
82
|
-
- `bun typecheck`
|
|
83
|
-
- `moon check`
|
|
84
|
-
- `bun run test`
|
|
85
|
-
- For project-level tests, generate `project.json` using `hikkaku`.
|
|
86
|
-
|
|
87
|
-
## Precompiled Cache Safety
|
|
88
|
-
|
|
89
|
-
- Caches stored in `PrecompiledProject` must be limited to immutable data derived from the initial compiled project state.
|
|
90
|
-
- Never store or feed back mutable VM execution state (runtime threads, pen/render buffers, variable/list mutations, etc.) into `PrecompiledProject`.
|
|
91
|
-
- Creating a new VM from the same compiled program must always produce the same initial state as a fresh compile, and must not be affected by prior VM execution (including `emptyCompiled`-style reuse).
|
package/PLAN.md
DELETED
|
@@ -1,64 +0,0 @@
|
|
|
1
|
-
## MoonScratch Headless Interpreter Plan (Skill適用版)
|
|
2
|
-
|
|
3
|
-
### Summary
|
|
4
|
-
|
|
5
|
-
scratch-editor/packages/scratch-vm を参照して、project.json + assets(Map) 入力のヘッドレス
|
|
6
|
-
コアは MoonBit、音声/時刻/入力/乱数/ログは Host 抽象経由で差し替え可能にする(JS固定実装に
|
|
7
|
-
しない)。
|
|
8
|
-
JS からは Wasm ラッパ API で利用可能にする。
|
|
9
|
-
|
|
10
|
-
### Skill Usage(追加反映)
|
|
11
|
-
|
|
12
|
-
この計画では moonscratch/.agents/skills の以下を使う。
|
|
13
|
-
|
|
14
|
-
1. moonbit-agent-guide(最初)
|
|
15
|
-
|
|
16
|
-
- パッケージ境界確認、moon ツール運用、検証手順の標準化に使う。
|
|
17
|
-
|
|
18
|
-
2. moonbit-practice(実装中ずっと)
|
|
19
|
-
|
|
20
|
-
- MoonBit 構文/テスト/moon ide 優先の実装規約に従うために使う。
|
|
21
|
-
|
|
22
|
-
3. moonbit-refactoring(中盤以降)
|
|
23
|
-
|
|
24
|
-
- API縮小・責務分割・互換を崩さない整理を行う際に使う。
|
|
25
|
-
|
|
26
|
-
### Public APIs / Interfaces
|
|
27
|
-
|
|
28
|
-
- trait HostAdapter
|
|
29
|
-
- HostEffect(PlaySound, StopAllSounds, MonitorUpdate, CloudUpdate など)
|
|
30
|
-
- Vm API
|
|
31
|
-
- new/start/green_flag/step/post_io/broadcast/stop_all/snapshot/dispose
|
|
32
|
-
- JS API
|
|
33
|
-
- createHeadlessVM({projectJson, assets, options, host})
|
|
34
|
-
- start(), greenFlag(), setTime(nowMs), stepFrame(frameCount?), postIO(), onEffect(), getSnapshot()
|
|
35
|
-
|
|
36
|
-
### Implementation
|
|
37
|
-
|
|
38
|
-
1. moonscratch を分割
|
|
39
|
-
|
|
40
|
-
- sb3(project.json デシリアライズと block graph)
|
|
41
|
-
- host(HostAdapter + default no-op)
|
|
42
|
-
|
|
43
|
-
- Scratch3 主要カテゴリを scratch-vm 挙動に合わせる。
|
|
44
|
-
- 副作用は全て HostEffect 化し、ランタイム本体はヘッドレスを維持。
|
|
45
|
-
|
|
46
|
-
3. 拡張互換
|
|
47
|
-
|
|
48
|
-
- extension registry を用意し、ペン/音楽/ビデオ/TTS を段階的に対応。
|
|
49
|
-
|
|
50
|
-
### Tests / Scenarios
|
|
51
|
-
|
|
52
|
-
- 統合: 主要サンプル project.json + assets 実行で状態遷移検証。
|
|
53
|
-
|
|
54
|
-
### Acceptance Criteria
|
|
55
|
-
|
|
56
|
-
- project.json + assets Map だけで実行可能。
|
|
57
|
-
- 主要サンプルでクラッシュせず想定状態へ到達。
|
|
58
|
-
- JS API が start/step/postIO/stop/snapshot で運用可能。
|
|
59
|
-
|
|
60
|
-
### Assumptions
|
|
61
|
-
|
|
62
|
-
- 入力は Scratch3 (project.json) を標準対象とする。
|
|
63
|
-
- Host 実装は利用側差し替え前提(JS直書き固定ではない)。
|
|
64
|
-
- 完全互換志向だが、実装は段階的に進める。
|
package/TODO.md
DELETED
|
@@ -1,120 +0,0 @@
|
|
|
1
|
-
# TODO
|
|
2
|
-
|
|
3
|
-
Scratch VM (`scratch-editor/packages/scratch-vm`) と比較した未実装 opcode 管理。
|
|
4
|
-
|
|
5
|
-
## Done in this pass (`control_*`)
|
|
6
|
-
|
|
7
|
-
- [x] `control_all_at_once`
|
|
8
|
-
- [x] `control_clear_counter`
|
|
9
|
-
- [x] `control_create_clone_of`
|
|
10
|
-
- [x] `control_for_each`
|
|
11
|
-
- [x] `control_get_counter`
|
|
12
|
-
- [x] `control_incr_counter`
|
|
13
|
-
- [x] `control_repeat_until`
|
|
14
|
-
- [x] `control_start_as_clone`
|
|
15
|
-
- [x] `control_wait_until`
|
|
16
|
-
- [x] `control_while`
|
|
17
|
-
|
|
18
|
-
## Remaining core opcodes
|
|
19
|
-
|
|
20
|
-
### `data_*`
|
|
21
|
-
|
|
22
|
-
- [x] `data_hidelist` (headless no-op)
|
|
23
|
-
- [x] `data_hidevariable` (headless no-op)
|
|
24
|
-
- [x] `data_itemnumoflist`
|
|
25
|
-
- [x] `data_showlist` (headless no-op)
|
|
26
|
-
- [x] `data_showvariable` (headless no-op)
|
|
27
|
-
|
|
28
|
-
### `event_*`
|
|
29
|
-
|
|
30
|
-
- [x] `event_whenbackdropswitchesto`
|
|
31
|
-
- [x] `event_whengreaterthan`
|
|
32
|
-
- [x] `event_whenkeypressed`
|
|
33
|
-
- [x] `event_whenstageclicked`
|
|
34
|
-
- [x] `event_whenthisspriteclicked`
|
|
35
|
-
- [x] `event_whentouchingobject`
|
|
36
|
-
|
|
37
|
-
### `looks_*`
|
|
38
|
-
|
|
39
|
-
- [x] `looks_backdropnumbername`
|
|
40
|
-
- [x] `looks_changeeffectby`
|
|
41
|
-
- [x] `looks_changestretchby` (headless no-op)
|
|
42
|
-
- [x] `looks_cleargraphiceffects`
|
|
43
|
-
- [x] `looks_costumenumbername`
|
|
44
|
-
- [x] `looks_goforwardbackwardlayers` (headless no-op)
|
|
45
|
-
- [x] `looks_gotofrontback` (headless no-op)
|
|
46
|
-
- [x] `looks_hideallsprites`
|
|
47
|
-
- [x] `looks_nextbackdrop`
|
|
48
|
-
- [x] `looks_seteffectto`
|
|
49
|
-
- [x] `looks_setstretchto` (headless no-op)
|
|
50
|
-
- [x] `looks_size`
|
|
51
|
-
- [x] `looks_switchbackdropto`
|
|
52
|
-
- [x] `looks_switchbackdroptoandwait`
|
|
53
|
-
|
|
54
|
-
### `motion_*`
|
|
55
|
-
|
|
56
|
-
- [x] `motion_align_scene` (headless no-op)
|
|
57
|
-
- [x] `motion_direction`
|
|
58
|
-
- [x] `motion_glidesecstoxy`
|
|
59
|
-
- [x] `motion_glideto`
|
|
60
|
-
- [x] `motion_goto`
|
|
61
|
-
- [x] `motion_ifonedgebounce`
|
|
62
|
-
- [x] `motion_pointindirection`
|
|
63
|
-
- [x] `motion_pointtowards`
|
|
64
|
-
- [x] `motion_scroll_right` (headless no-op)
|
|
65
|
-
- [x] `motion_scroll_up` (headless no-op)
|
|
66
|
-
- [x] `motion_setrotationstyle` (headless no-op)
|
|
67
|
-
- [x] `motion_xposition`
|
|
68
|
-
- [x] `motion_xscroll` (returns `0`)
|
|
69
|
-
- [x] `motion_yposition`
|
|
70
|
-
- [x] `motion_yscroll` (returns `0`)
|
|
71
|
-
|
|
72
|
-
### `procedures_*`
|
|
73
|
-
|
|
74
|
-
- [x] `procedures_call`
|
|
75
|
-
- [x] `procedures_definition`
|
|
76
|
-
|
|
77
|
-
### `sensing_*`
|
|
78
|
-
|
|
79
|
-
- [x] `sensing_coloristouchingcolor`
|
|
80
|
-
- [x] `sensing_current`
|
|
81
|
-
- [x] `sensing_dayssince2000`
|
|
82
|
-
- [x] `sensing_distanceto`
|
|
83
|
-
- [x] `sensing_keypressed`
|
|
84
|
-
- [x] `sensing_loud`
|
|
85
|
-
- [x] `sensing_loudness`
|
|
86
|
-
- [x] `sensing_mousedown`
|
|
87
|
-
- [x] `sensing_mousex`
|
|
88
|
-
- [x] `sensing_mousey`
|
|
89
|
-
- [x] `sensing_of`
|
|
90
|
-
- [x] `sensing_online`
|
|
91
|
-
- [x] `sensing_resettimer`
|
|
92
|
-
- [x] `sensing_touchingcolor`
|
|
93
|
-
- [x] `sensing_touchingobject`
|
|
94
|
-
- [x] `sensing_userid`
|
|
95
|
-
- [x] `sensing_username`
|
|
96
|
-
|
|
97
|
-
### `sound_*`
|
|
98
|
-
|
|
99
|
-
- [x] `sound_beats_menu`
|
|
100
|
-
- [x] `sound_changeeffectby`
|
|
101
|
-
- [x] `sound_changevolumeby`
|
|
102
|
-
- [x] `sound_cleareffects`
|
|
103
|
-
- [x] `sound_effects_menu`
|
|
104
|
-
- [x] `sound_seteffectto`
|
|
105
|
-
- [x] `sound_setvolumeto`
|
|
106
|
-
- [x] `sound_sounds_menu`
|
|
107
|
-
- [x] `sound_volume`
|
|
108
|
-
|
|
109
|
-
## Extensions
|
|
110
|
-
|
|
111
|
-
### Implemented
|
|
112
|
-
|
|
113
|
-
- `music_*` (`playDrumForBeats`, `midiPlayDrumForBeats`, `restForBeats`, `playNoteForBeats`, `setInstrument`, `midiSetInstrument`, `setTempo`, `changeTempo`, `getTempo`)
|
|
114
|
-
- `pen_*` (`clear`, `stamp`, `penDown`, `penUp`, `setPenColorToColor`, `changePenColorParamBy`, `setPenColorParamTo`, `changePenSizeBy`, `setPenSizeTo`, `setPenHueToNumber`, `changePenHueBy`, `setPenShadeToNumber`, `changePenShadeBy`)
|
|
115
|
-
- `text2speech_*` (`speakAndWait`, `setVoice`, `setLanguage`)
|
|
116
|
-
- `translate_*` (`getTranslate`, `getViewerLanguage`)
|
|
117
|
-
|
|
118
|
-
### Not started
|
|
119
|
-
|
|
120
|
-
`videoSensing_*`, `wedo2_*`, `ev3_*`, `boost_*`, `gdxfor_*`, `makeymakey_*`, `microbit_*`, `faceSensing_*`
|
package/benchmarks/calc.bench.ts
DELETED
|
@@ -1,144 +0,0 @@
|
|
|
1
|
-
import { Project } from 'hikkaku'
|
|
2
|
-
import {
|
|
3
|
-
add,
|
|
4
|
-
addToList,
|
|
5
|
-
and,
|
|
6
|
-
changeVariableBy,
|
|
7
|
-
divide,
|
|
8
|
-
equals,
|
|
9
|
-
gt,
|
|
10
|
-
ifThen,
|
|
11
|
-
lt,
|
|
12
|
-
mathop,
|
|
13
|
-
mod,
|
|
14
|
-
multiply,
|
|
15
|
-
or,
|
|
16
|
-
repeat,
|
|
17
|
-
repeatUntil,
|
|
18
|
-
setVariableTo,
|
|
19
|
-
subtract,
|
|
20
|
-
whenFlagClicked,
|
|
21
|
-
} from 'hikkaku/blocks'
|
|
22
|
-
import { bench, run } from 'mitata'
|
|
23
|
-
import {
|
|
24
|
-
createHeadlessVM,
|
|
25
|
-
createProgramModuleFromProject,
|
|
26
|
-
} from '../js/vm/factory.ts'
|
|
27
|
-
|
|
28
|
-
const runUntilFinished = (vm: {
|
|
29
|
-
greenFlag(): void
|
|
30
|
-
stepFrame(): { stopReason: string }
|
|
31
|
-
}) => {
|
|
32
|
-
vm.greenFlag()
|
|
33
|
-
while (true) {
|
|
34
|
-
const result = vm.stepFrame()
|
|
35
|
-
if (result.stopReason === 'finished') {
|
|
36
|
-
break
|
|
37
|
-
}
|
|
38
|
-
}
|
|
39
|
-
}
|
|
40
|
-
|
|
41
|
-
const calcProject = new Project()
|
|
42
|
-
const calcAcc = calcProject.stage.createVariable('acc', 0)
|
|
43
|
-
const calcAngle = calcProject.stage.createVariable('angle', 0)
|
|
44
|
-
|
|
45
|
-
calcProject.stage.run(() => {
|
|
46
|
-
whenFlagClicked(() => {
|
|
47
|
-
setVariableTo(calcAcc, 0)
|
|
48
|
-
setVariableTo(calcAngle, 0)
|
|
49
|
-
repeat(50000, () => {
|
|
50
|
-
setVariableTo(
|
|
51
|
-
calcAcc,
|
|
52
|
-
add(
|
|
53
|
-
calcAcc.get(),
|
|
54
|
-
multiply(
|
|
55
|
-
mathop('sin', calcAngle.get()),
|
|
56
|
-
mathop('cos', calcAngle.get()),
|
|
57
|
-
),
|
|
58
|
-
),
|
|
59
|
-
)
|
|
60
|
-
changeVariableBy(calcAngle, subtract(divide(calcAngle.get(), 2), -1))
|
|
61
|
-
})
|
|
62
|
-
})
|
|
63
|
-
})
|
|
64
|
-
|
|
65
|
-
const calcProjectJson = calcProject.toScratch()
|
|
66
|
-
const calcProgram = createProgramModuleFromProject({
|
|
67
|
-
projectJson: calcProjectJson,
|
|
68
|
-
})
|
|
69
|
-
const calcVM = createHeadlessVM({
|
|
70
|
-
program: calcProgram,
|
|
71
|
-
initialNowMs: 0,
|
|
72
|
-
options: {
|
|
73
|
-
stepTimeoutTicks: 1000000,
|
|
74
|
-
turbo: true,
|
|
75
|
-
},
|
|
76
|
-
})
|
|
77
|
-
|
|
78
|
-
bench('calc', () => {
|
|
79
|
-
runUntilFinished(calcVM)
|
|
80
|
-
})
|
|
81
|
-
|
|
82
|
-
const primesProject = new Project()
|
|
83
|
-
const primesList = primesProject.stage.createList('primes', [])
|
|
84
|
-
const primesCandidate = primesProject.stage.createVariable('candidate', 2)
|
|
85
|
-
const primesDivisor = primesProject.stage.createVariable('divisor', 0)
|
|
86
|
-
const primesIsPrime = primesProject.stage.createVariable('is prime', 0)
|
|
87
|
-
const primesCount = primesProject.stage.createVariable('prime count', 0)
|
|
88
|
-
|
|
89
|
-
primesProject.stage.run(() => {
|
|
90
|
-
whenFlagClicked(() => {
|
|
91
|
-
setVariableTo(primesCount, 0)
|
|
92
|
-
setVariableTo(primesCandidate, 2)
|
|
93
|
-
setVariableTo(primesDivisor, 2)
|
|
94
|
-
setVariableTo(primesIsPrime, 0)
|
|
95
|
-
repeatUntil(equals(primesCount.get(), 100), () => {
|
|
96
|
-
setVariableTo(primesIsPrime, 1)
|
|
97
|
-
setVariableTo(primesDivisor, 2)
|
|
98
|
-
repeatUntil(
|
|
99
|
-
or(
|
|
100
|
-
gt(primesDivisor.get(), mathop('sqrt', primesCandidate.get())),
|
|
101
|
-
equals(primesIsPrime.get(), 0),
|
|
102
|
-
),
|
|
103
|
-
() => {
|
|
104
|
-
ifThen(
|
|
105
|
-
and(
|
|
106
|
-
equals(mod(primesCandidate.get(), primesDivisor.get()), 0),
|
|
107
|
-
lt(primesDivisor.get(), primesCandidate.get()),
|
|
108
|
-
),
|
|
109
|
-
() => {
|
|
110
|
-
setVariableTo(primesIsPrime, 0)
|
|
111
|
-
},
|
|
112
|
-
)
|
|
113
|
-
changeVariableBy(primesDivisor, 1)
|
|
114
|
-
},
|
|
115
|
-
)
|
|
116
|
-
ifThen(equals(primesIsPrime.get(), 1), () => {
|
|
117
|
-
addToList(primesList, primesCandidate.get())
|
|
118
|
-
changeVariableBy(primesCount, 1)
|
|
119
|
-
})
|
|
120
|
-
changeVariableBy(primesCandidate, 1)
|
|
121
|
-
})
|
|
122
|
-
})
|
|
123
|
-
})
|
|
124
|
-
|
|
125
|
-
const primesProjectJson = primesProject.toScratch()
|
|
126
|
-
const primesProgram = createProgramModuleFromProject({
|
|
127
|
-
projectJson: primesProjectJson,
|
|
128
|
-
})
|
|
129
|
-
const primesVM = createHeadlessVM({
|
|
130
|
-
program: primesProgram,
|
|
131
|
-
initialNowMs: 0,
|
|
132
|
-
options: {
|
|
133
|
-
stepTimeoutTicks: 1000000,
|
|
134
|
-
turbo: true,
|
|
135
|
-
},
|
|
136
|
-
})
|
|
137
|
-
|
|
138
|
-
bench('calc-primes', () => {
|
|
139
|
-
runUntilFinished(primesVM)
|
|
140
|
-
})
|
|
141
|
-
|
|
142
|
-
if (import.meta.main) {
|
|
143
|
-
await run()
|
|
144
|
-
}
|
package/benchmarks/draw.bench.ts
DELETED
|
@@ -1,215 +0,0 @@
|
|
|
1
|
-
import { Project } from 'hikkaku'
|
|
2
|
-
import {
|
|
3
|
-
callProcedure,
|
|
4
|
-
changeXBy,
|
|
5
|
-
changeYBy,
|
|
6
|
-
defineProcedure,
|
|
7
|
-
eraseAll,
|
|
8
|
-
forEach,
|
|
9
|
-
getItemOfList,
|
|
10
|
-
gotoXY,
|
|
11
|
-
hide,
|
|
12
|
-
lengthOfList,
|
|
13
|
-
penDown,
|
|
14
|
-
penUp,
|
|
15
|
-
procedureLabel,
|
|
16
|
-
repeat,
|
|
17
|
-
setPenColorTo,
|
|
18
|
-
setPenSizeTo,
|
|
19
|
-
setVariableTo,
|
|
20
|
-
setY,
|
|
21
|
-
whenFlagClicked,
|
|
22
|
-
} from 'hikkaku/blocks'
|
|
23
|
-
import { bench, run } from 'mitata'
|
|
24
|
-
import {
|
|
25
|
-
createHeadlessVM,
|
|
26
|
-
createProgramModuleFromProject,
|
|
27
|
-
} from '../js/vm/factory.ts'
|
|
28
|
-
|
|
29
|
-
await import('scratch-storage')
|
|
30
|
-
|
|
31
|
-
const runUntilFinished = (vm: {
|
|
32
|
-
greenFlag(): void
|
|
33
|
-
stepFrame(): { stopReason: string }
|
|
34
|
-
}) => {
|
|
35
|
-
vm.greenFlag()
|
|
36
|
-
while (true) {
|
|
37
|
-
const result = vm.stepFrame()
|
|
38
|
-
if (result.stopReason === 'finished') {
|
|
39
|
-
break
|
|
40
|
-
}
|
|
41
|
-
}
|
|
42
|
-
}
|
|
43
|
-
|
|
44
|
-
const project = new Project()
|
|
45
|
-
const sprite = project.createSprite('Sprite1')
|
|
46
|
-
|
|
47
|
-
sprite.run(() => {
|
|
48
|
-
whenFlagClicked(() => {
|
|
49
|
-
gotoXY(-240, -180)
|
|
50
|
-
repeat(420, () => {
|
|
51
|
-
changeXBy(1)
|
|
52
|
-
setY(-180)
|
|
53
|
-
|
|
54
|
-
penDown()
|
|
55
|
-
repeat(360, () => {
|
|
56
|
-
changeYBy(1)
|
|
57
|
-
})
|
|
58
|
-
penUp()
|
|
59
|
-
})
|
|
60
|
-
})
|
|
61
|
-
})
|
|
62
|
-
|
|
63
|
-
const projectJson = project.toScratch()
|
|
64
|
-
const program = createProgramModuleFromProject({ projectJson })
|
|
65
|
-
const vm = createHeadlessVM({
|
|
66
|
-
program,
|
|
67
|
-
initialNowMs: 0,
|
|
68
|
-
options: {
|
|
69
|
-
stepTimeoutTicks: 1000000,
|
|
70
|
-
turbo: true,
|
|
71
|
-
},
|
|
72
|
-
})
|
|
73
|
-
|
|
74
|
-
bench('draw/moonscratch', () => {
|
|
75
|
-
runUntilFinished(vm)
|
|
76
|
-
})
|
|
77
|
-
|
|
78
|
-
const FRAME_FORCE_TIMEOUT_OUT_OF_WARP_MS = 1000 / 30
|
|
79
|
-
const FRAME_FORCE_TIMEOUT_IN_WARP_MS = 1000 / 5
|
|
80
|
-
|
|
81
|
-
const stepLikeViewerFrame = (vm: {
|
|
82
|
-
stepFrame(): { stopReason: string; isInWarp: boolean }
|
|
83
|
-
renderFrame(): unknown
|
|
84
|
-
}) => {
|
|
85
|
-
const frameStart = performance.now()
|
|
86
|
-
while (true) {
|
|
87
|
-
const frameInfo = vm.stepFrame()
|
|
88
|
-
if (
|
|
89
|
-
frameInfo.stopReason === 'finished' ||
|
|
90
|
-
frameInfo.stopReason === 'rerender'
|
|
91
|
-
) {
|
|
92
|
-
break
|
|
93
|
-
}
|
|
94
|
-
const elapsed = performance.now() - frameStart
|
|
95
|
-
if (frameInfo.isInWarp) {
|
|
96
|
-
if (elapsed > FRAME_FORCE_TIMEOUT_IN_WARP_MS) {
|
|
97
|
-
break
|
|
98
|
-
}
|
|
99
|
-
} else {
|
|
100
|
-
if (elapsed > FRAME_FORCE_TIMEOUT_OUT_OF_WARP_MS) {
|
|
101
|
-
break
|
|
102
|
-
}
|
|
103
|
-
}
|
|
104
|
-
}
|
|
105
|
-
vm.renderFrame()
|
|
106
|
-
}
|
|
107
|
-
|
|
108
|
-
const TESSERACT_VERTICES_2D = Array.from({ length: 16 }, (_, vertex) => {
|
|
109
|
-
const sign = (bit: number) => {
|
|
110
|
-
return vertex & (1 << bit) ? 1 : -1
|
|
111
|
-
}
|
|
112
|
-
const x = sign(0)
|
|
113
|
-
const y = sign(1)
|
|
114
|
-
const z = sign(2)
|
|
115
|
-
const w = sign(3)
|
|
116
|
-
const perspective4 = 1 / (2.6 - w * 0.8)
|
|
117
|
-
const x3 = x * perspective4
|
|
118
|
-
const y3 = y * perspective4
|
|
119
|
-
const z3 = z * perspective4
|
|
120
|
-
const perspective3 = 1 / (3.2 - z3)
|
|
121
|
-
return [x3 * perspective3 * 110, y3 * perspective3 * 110] as const
|
|
122
|
-
})
|
|
123
|
-
|
|
124
|
-
const TESSERACT_EDGES: Array<[number, number]> = []
|
|
125
|
-
for (let vertex = 0; vertex < 16; vertex += 1) {
|
|
126
|
-
for (let bit = 0; bit < 4; bit += 1) {
|
|
127
|
-
const neighbor = vertex ^ (1 << bit)
|
|
128
|
-
if (vertex < neighbor) {
|
|
129
|
-
TESSERACT_EDGES.push([vertex + 1, neighbor + 1])
|
|
130
|
-
}
|
|
131
|
-
}
|
|
132
|
-
}
|
|
133
|
-
|
|
134
|
-
const tesseractProject = new Project()
|
|
135
|
-
const tesseractSprite = tesseractProject.createSprite('Tesseract')
|
|
136
|
-
const edgeIndex = tesseractSprite.createVariable('edgeIndex', 1)
|
|
137
|
-
const edgeFrom = tesseractSprite.createVariable('edgeFrom', 1)
|
|
138
|
-
const edgeTo = tesseractSprite.createVariable('edgeTo', 1)
|
|
139
|
-
const vertexXList = tesseractSprite.createList(
|
|
140
|
-
'vertexX',
|
|
141
|
-
TESSERACT_VERTICES_2D.map(([x]) => x),
|
|
142
|
-
)
|
|
143
|
-
const vertexYList = tesseractSprite.createList(
|
|
144
|
-
'vertexY',
|
|
145
|
-
TESSERACT_VERTICES_2D.map(([, y]) => y),
|
|
146
|
-
)
|
|
147
|
-
const edgeFromList = tesseractSprite.createList(
|
|
148
|
-
'edgeFrom',
|
|
149
|
-
TESSERACT_EDGES.map(([from]) => from),
|
|
150
|
-
)
|
|
151
|
-
const edgeToList = tesseractSprite.createList(
|
|
152
|
-
'edgeTo',
|
|
153
|
-
TESSERACT_EDGES.map(([, to]) => to),
|
|
154
|
-
)
|
|
155
|
-
|
|
156
|
-
tesseractSprite.run(() => {
|
|
157
|
-
const drawStep = defineProcedure(
|
|
158
|
-
[procedureLabel('draw step')],
|
|
159
|
-
() => {
|
|
160
|
-
eraseAll()
|
|
161
|
-
forEach(edgeIndex, lengthOfList(edgeFromList), () => {
|
|
162
|
-
setVariableTo(edgeFrom, getItemOfList(edgeFromList, edgeIndex.get()))
|
|
163
|
-
setVariableTo(edgeTo, getItemOfList(edgeToList, edgeIndex.get()))
|
|
164
|
-
penUp()
|
|
165
|
-
gotoXY(
|
|
166
|
-
getItemOfList(vertexXList, edgeFrom.get()),
|
|
167
|
-
getItemOfList(vertexYList, edgeFrom.get()),
|
|
168
|
-
)
|
|
169
|
-
penDown()
|
|
170
|
-
gotoXY(
|
|
171
|
-
getItemOfList(vertexXList, edgeTo.get()),
|
|
172
|
-
getItemOfList(vertexYList, edgeTo.get()),
|
|
173
|
-
)
|
|
174
|
-
penUp()
|
|
175
|
-
})
|
|
176
|
-
},
|
|
177
|
-
true,
|
|
178
|
-
)
|
|
179
|
-
|
|
180
|
-
whenFlagClicked(() => {
|
|
181
|
-
hide()
|
|
182
|
-
penUp()
|
|
183
|
-
setPenSizeTo(1.2)
|
|
184
|
-
setPenColorTo('#38bdf8')
|
|
185
|
-
repeat(30, () => {
|
|
186
|
-
callProcedure(drawStep, {}, true)
|
|
187
|
-
})
|
|
188
|
-
})
|
|
189
|
-
})
|
|
190
|
-
|
|
191
|
-
const tesseractProjectJson = tesseractProject.toScratch()
|
|
192
|
-
const tesseractProgram = createProgramModuleFromProject({
|
|
193
|
-
projectJson: tesseractProjectJson,
|
|
194
|
-
})
|
|
195
|
-
const tesseractVM = createHeadlessVM({
|
|
196
|
-
program: tesseractProgram,
|
|
197
|
-
initialNowMs: 0,
|
|
198
|
-
options: {
|
|
199
|
-
stepTimeoutTicks: 1,
|
|
200
|
-
},
|
|
201
|
-
})
|
|
202
|
-
tesseractVM.start()
|
|
203
|
-
|
|
204
|
-
bench('draw/tesseract-30/moonscratch', () => {
|
|
205
|
-
tesseractVM.stopAll()
|
|
206
|
-
tesseractVM.greenFlag()
|
|
207
|
-
for (let frame = 0; frame < 30; frame += 1) {
|
|
208
|
-
stepLikeViewerFrame(tesseractVM)
|
|
209
|
-
}
|
|
210
|
-
tesseractVM.stopAll()
|
|
211
|
-
})
|
|
212
|
-
|
|
213
|
-
if (import.meta.main) {
|
|
214
|
-
await run()
|
|
215
|
-
}
|
package/benchmarks/load.bench.ts
DELETED
|
@@ -1,28 +0,0 @@
|
|
|
1
|
-
import { Project } from 'hikkaku'
|
|
2
|
-
import { moveSteps } from 'hikkaku/blocks'
|
|
3
|
-
import { bench, run } from 'mitata'
|
|
4
|
-
import {
|
|
5
|
-
createHeadlessVM,
|
|
6
|
-
createProgramModuleFromProject,
|
|
7
|
-
} from '../js/vm/factory.ts'
|
|
8
|
-
|
|
9
|
-
await import('scratch-storage')
|
|
10
|
-
|
|
11
|
-
const project = new Project()
|
|
12
|
-
project.stage.run(() => {
|
|
13
|
-
for (let i = 0; i < 10000; i++) {
|
|
14
|
-
moveSteps(10)
|
|
15
|
-
}
|
|
16
|
-
})
|
|
17
|
-
const projectJson = project.toScratch()
|
|
18
|
-
const program = createProgramModuleFromProject({ projectJson })
|
|
19
|
-
bench('load/moonscratch', () => {
|
|
20
|
-
createHeadlessVM({
|
|
21
|
-
program,
|
|
22
|
-
initialNowMs: 0,
|
|
23
|
-
})
|
|
24
|
-
})
|
|
25
|
-
|
|
26
|
-
if (import.meta.main) {
|
|
27
|
-
await run()
|
|
28
|
-
}
|