@devaloop/devalang 0.0.1-alpha.4 → 0.0.1-alpha.7
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/Cargo.toml +7 -5
- package/README.md +26 -7
- package/docs/CHANGELOG.md +34 -2
- package/docs/ROADMAP.md +3 -3
- package/docs/SYNTAX.md +42 -14
- package/docs/TODO.md +9 -8
- package/examples/group.deva +12 -0
- package/examples/index.deva +10 -9
- package/examples/loop.deva +15 -0
- package/examples/variables.deva +9 -0
- package/out-tsc/bin/devalang.exe +0 -0
- package/package.json +43 -41
- package/project-version.json +5 -5
- package/rust/cli/build.rs +4 -4
- package/rust/cli/check.rs +2 -1
- package/rust/cli/init.rs +4 -2
- package/rust/cli/play.rs +5 -3
- package/rust/cli/template.rs +2 -1
- package/rust/config/loader.rs +0 -1
- package/rust/{audio → core/audio}/engine.rs +1 -5
- package/rust/core/audio/interpreter.rs +317 -0
- package/rust/{audio → core/audio}/loader.rs +4 -0
- package/rust/{audio → core/audio}/render.rs +1 -5
- package/rust/core/builder/mod.rs +9 -8
- package/rust/core/lexer/handler/indent.rs +1 -1
- package/rust/core/lexer/handler/mod.rs +3 -4
- package/rust/core/lexer/handler/newline.rs +5 -1
- package/rust/core/lexer/handler/string.rs +3 -6
- package/rust/core/lexer/mod.rs +10 -5
- package/rust/core/mod.rs +2 -1
- package/rust/core/parser/handler/identifier.rs +127 -1
- package/rust/core/parser/handler/loop_.rs +11 -0
- package/rust/core/parser/mod.rs +0 -1
- package/rust/core/parser/statement.rs +9 -5
- package/rust/core/preprocessor/loader.rs +65 -3
- package/rust/core/preprocessor/module.rs +2 -0
- package/rust/core/preprocessor/processor.rs +28 -2
- package/rust/core/preprocessor/resolver/bank.rs +10 -9
- package/rust/core/preprocessor/resolver/group.rs +113 -0
- package/rust/core/preprocessor/resolver/loop_.rs +15 -13
- package/rust/core/preprocessor/resolver/mod.rs +11 -5
- package/rust/core/preprocessor/resolver/trigger.rs +0 -3
- package/rust/lib.rs +117 -0
- package/rust/main.rs +2 -1
- package/rust/utils/logger.rs +45 -6
- package/rust/utils/spinner.rs +2 -0
- package/templates/minimal/.devalang +2 -1
- package/templates/minimal/README.md +202 -0
- package/templates/welcome/.devalang +2 -1
- package/templates/welcome/README.md +48 -31
- package/examples/exported.deva +0 -7
- package/rust/audio/interpreter.rs +0 -143
- /package/rust/{audio → core/audio}/mod.rs +0 -0
- /package/rust/{audio → core/audio}/player.rs +0 -0
package/Cargo.toml
CHANGED
|
@@ -1,20 +1,22 @@
|
|
|
1
1
|
[package]
|
|
2
2
|
name = "devalang"
|
|
3
|
-
version = "0.0.1-alpha.
|
|
3
|
+
version = "0.0.1-alpha.7"
|
|
4
4
|
authors = ["Devaloop <contact@devaloop.com>"]
|
|
5
5
|
description = "Write music like code. Devalang is a domain-specific language (DSL) for sound designers and music hackers. Compose, automate, and control sound — in plain text."
|
|
6
6
|
license = "MIT"
|
|
7
7
|
repository = "https://github.com/devaloop-labs/devalang"
|
|
8
8
|
keywords = ["music", "dsl", "audio", "cli"]
|
|
9
|
-
categories = ["command-line-utilities", "
|
|
9
|
+
categories = ["command-line-utilities", "development-tools", "parser-implementations"]
|
|
10
10
|
readme = "README.md"
|
|
11
11
|
homepage = "https://devalang.com"
|
|
12
12
|
documentation = "https://docs.devalang.com/"
|
|
13
|
+
license-file = "LICENSE"
|
|
13
14
|
edition = "2024"
|
|
14
15
|
|
|
15
16
|
[[bin]]
|
|
16
17
|
name = "devalang"
|
|
17
18
|
path = "rust/main.rs"
|
|
19
|
+
required-features = ["cli"]
|
|
18
20
|
|
|
19
21
|
[lib]
|
|
20
22
|
path = "rust/lib.rs"
|
|
@@ -25,7 +27,7 @@ opt-level = "s"
|
|
|
25
27
|
|
|
26
28
|
[features]
|
|
27
29
|
default = ["cli"]
|
|
28
|
-
cli = ["crossterm"]
|
|
30
|
+
cli = ["crossterm", "indicatif", "inquire"]
|
|
29
31
|
|
|
30
32
|
[dependencies]
|
|
31
33
|
clap = { version = "4.5", features = ["derive"] }
|
|
@@ -42,5 +44,5 @@ serde-wasm-bindgen = "0.4"
|
|
|
42
44
|
nom_locate = "4.0.0"
|
|
43
45
|
chrono = "0.4"
|
|
44
46
|
crossterm = { version = "0.27", optional = true }
|
|
45
|
-
indicatif = "0.17"
|
|
46
|
-
inquire = "0.7.5"
|
|
47
|
+
indicatif = { version = "0.17", optional = true }
|
|
48
|
+
inquire = { version = "0.7.5", optional = true }
|
package/README.md
CHANGED
|
@@ -12,6 +12,9 @@
|
|
|
12
12
|

|
|
13
13
|
|
|
14
14
|

|
|
15
|
+

|
|
16
|
+
|
|
17
|
+
[](https://marketplace.visualstudio.com/items?itemName=devaloop.devalang-vscode)
|
|
15
18
|
|
|
16
19
|
## 🎼 Devalang, by **Devaloop Labs**
|
|
17
20
|
|
|
@@ -24,9 +27,10 @@ Compose loops, control samples, render and play audio — all in clean, readable
|
|
|
24
27
|
|
|
25
28
|
From studio sketches to live sets, Devalang gives you rhythmic control — with the elegance of code.
|
|
26
29
|
|
|
27
|
-
> 🚧 **v0.0.1-alpha.
|
|
30
|
+
> 🚧 **v0.0.1-alpha.5 Notice** 🚧
|
|
28
31
|
>
|
|
29
|
-
>
|
|
32
|
+
> NEW: Devalang VSCode extension is now available !
|
|
33
|
+
> [Get it here](https://marketplace.visualstudio.com/items?itemName=devaloop.devalang-vscode).
|
|
30
34
|
>
|
|
31
35
|
> Currently, Devalang CLI is only available for **Windows**.
|
|
32
36
|
> Linux and macOS binaries will be added in future releases via cross-platform builds.
|
|
@@ -37,6 +41,8 @@ From studio sketches to live sets, Devalang gives you rhythmic control — with
|
|
|
37
41
|
|
|
38
42
|
- [📖 Documentation](./docs/)
|
|
39
43
|
- [💡 Examples](./examples/)
|
|
44
|
+
- [🧩 VSCode Extension](https://marketplace.visualstudio.com/items?itemName=devaloop.devalang-vscode)
|
|
45
|
+
- [🎨 Prettier Plugin](https://www.npmjs.com/package/@devaloop/prettier-plugin-devalang)
|
|
40
46
|
- [🌐 Project Website](https://devalang.com)
|
|
41
47
|
|
|
42
48
|
## 🚀 Features
|
|
@@ -160,13 +166,27 @@ bpm globalBpm
|
|
|
160
166
|
bank globalBank
|
|
161
167
|
# Will declare a custom instrument bank using the globalBank variable
|
|
162
168
|
|
|
169
|
+
# Loops
|
|
170
|
+
|
|
163
171
|
loop 5:
|
|
164
172
|
.customKick kickDuration {reverb=50, drive=25}
|
|
165
|
-
# Will play 5 times a
|
|
173
|
+
# Will play 5 times a custom sample for 500ms with reverb and overdrive effects
|
|
174
|
+
|
|
175
|
+
# Groups
|
|
176
|
+
|
|
177
|
+
group myGroup:
|
|
178
|
+
.customKick kickDuration {reverb=50, drive=25}
|
|
179
|
+
# Will play the same sample in a group, allowing for more complex patterns
|
|
180
|
+
|
|
181
|
+
# Will be executed line by line (sequentially)
|
|
182
|
+
call myGroup
|
|
183
|
+
|
|
184
|
+
# Will be executed in parallel (concurrently)
|
|
185
|
+
# spawn myGroup
|
|
166
186
|
```
|
|
167
187
|
|
|
168
188
|
```deva
|
|
169
|
-
#
|
|
189
|
+
# variables.deva
|
|
170
190
|
|
|
171
191
|
let globalBpm = 120
|
|
172
192
|
let globalBank = 808
|
|
@@ -177,15 +197,14 @@ let kickDuration = 500
|
|
|
177
197
|
|
|
178
198
|
## 🧯 Known issues
|
|
179
199
|
|
|
180
|
-
- No support yet for `if`, `else`, `else if` statements
|
|
181
|
-
- No support yet for `@group`, `@pattern`, `@function` statements
|
|
200
|
+
- No support yet for `if`, `else`, `else if`, `pattern`, `function`, ... statements
|
|
182
201
|
- No support yet for cross-platform builds (Linux, macOS)
|
|
183
202
|
|
|
184
203
|
## 🧪 Roadmap Highlights
|
|
185
204
|
|
|
186
205
|
For more info, see [docs/ROADMAP.md](./docs/ROADMAP.md)
|
|
187
206
|
|
|
188
|
-
- ⏳ Other statements (e.g `if`,
|
|
207
|
+
- ⏳ Other statements (e.g `if`, `function`, ...)
|
|
189
208
|
- ⏳ Cross-platform support (Linux, macOS)
|
|
190
209
|
- ⏳ More built-in instruments (e.g. snare, hi-hat, etc.)
|
|
191
210
|
|
package/docs/CHANGELOG.md
CHANGED
|
@@ -4,6 +4,38 @@
|
|
|
4
4
|
|
|
5
5
|
# Changelog
|
|
6
6
|
|
|
7
|
+
## Version 0.0.1-alpha.6 (2025-07-11)
|
|
8
|
+
|
|
9
|
+
## Examples
|
|
10
|
+
|
|
11
|
+
- Added example for `group` directive in `examples/group.devalang`.
|
|
12
|
+
|
|
13
|
+
## Structure
|
|
14
|
+
|
|
15
|
+
- Moved `rust/audio` folder to `rust/core/audio` to better organize the project structure.
|
|
16
|
+
|
|
17
|
+
### Core Components
|
|
18
|
+
|
|
19
|
+
- Implemented `group` directive to define groups of sounds.
|
|
20
|
+
- Implemented `call` directive to call a group of sounds.
|
|
21
|
+
- Implemented `spawn` directive to spawn a group of sounds in parallel.
|
|
22
|
+
- Implemented `sleep` directive to pause execution for a specified duration.
|
|
23
|
+
- Patched line and column tracking in the lexer to ensure correct indentation handling.
|
|
24
|
+
- Patched string lexing advancing to handle first character correctly.
|
|
25
|
+
|
|
26
|
+
## Version 0.0.1-alpha.5 (2025-07-05)
|
|
27
|
+
|
|
28
|
+
### Syntax
|
|
29
|
+
|
|
30
|
+
- Fixed block parsing issues caused by missing or incorrect `Indent` / `Dedent` token detection.
|
|
31
|
+
- Indentation handling now triggers correctly at each newline.
|
|
32
|
+
- Improved reliability of nested blocks (e.g., inside `loop`) with consistent `Dedent` termination.
|
|
33
|
+
|
|
34
|
+
### Core Components
|
|
35
|
+
|
|
36
|
+
- Added full **WebAssembly (WASM)** support — Devalang can now be compiled for browser or Node.js environments.
|
|
37
|
+
- Prepared the ground for future IDE integrations (e.g., VSCode extension) by stabilizing core syntax parsing.
|
|
38
|
+
|
|
7
39
|
## Version 0.0.1-alpha.4 (2025-07-03)
|
|
8
40
|
|
|
9
41
|
### Audio Engine
|
|
@@ -15,11 +47,11 @@
|
|
|
15
47
|
### Commands
|
|
16
48
|
|
|
17
49
|
- Implemented `play` command to play Devalang files.
|
|
50
|
+
|
|
18
51
|
- Added `--watch` option to watch for changes in files and automatically rebuild and play them. (once)
|
|
19
52
|
- Added `--repeat` option to repeat the playback of the audio file. (infinite)
|
|
20
|
-
|
|
53
|
+
|
|
21
54
|
Note : You cannot use `--watch` and `--repeat` options together. Use `--repeat` instead.
|
|
22
|
-
|
|
23
55
|
|
|
24
56
|
## Version 0.0.1-alpha.3 (2025-07-01)
|
|
25
57
|
|
package/docs/ROADMAP.md
CHANGED
|
@@ -6,7 +6,7 @@
|
|
|
6
6
|
|
|
7
7
|
Devalang is a work in progress. Here’s what we’re planning next:
|
|
8
8
|
|
|
9
|
-
|
|
9
|
+
## Completed
|
|
10
10
|
|
|
11
11
|
- ✅ **Audio engine**: Integrate the audio engine for sound playback.
|
|
12
12
|
- ✅ **Basic syntax**: Implement the core syntax for Devalang, including data types and basic statements.
|
|
@@ -20,11 +20,11 @@ Devalang is a work in progress. Here’s what we’re planning next:
|
|
|
20
20
|
- ✅ **Instruction calls**: Add support for instruction calls with parameters (e.g. `.kick auto {reverb:10, decay:20}`).
|
|
21
21
|
- ✅ **Let assignments**: Implement `let` assignments for storing reusable values.
|
|
22
22
|
- ✅ **Sample loading**: Add `@load` assignment to load samples (.mp3, .wav) for use as values.
|
|
23
|
+
- ✅ **WASM support**: Compile Devalang to WebAssembly for use in web applications and other environments.
|
|
23
24
|
|
|
24
|
-
|
|
25
|
+
## Upcoming
|
|
25
26
|
|
|
26
27
|
- ⏳ **VSCode extension**: Create a VSCode extension for syntax highlighting and code completion.
|
|
27
|
-
- ⏳ **WASM support**: Compile Devalang to WebAssembly for use in web applications.
|
|
28
28
|
- ⏳ **Other statements**: Implement `if`, `else`, and other control structures.
|
|
29
29
|
- ⏳ **Pattern and group statements**: Add support for `@pattern` and `@group` to organize code.
|
|
30
30
|
- ⏳ **Functions**: Add support for defining and calling functions.
|
package/docs/SYNTAX.md
CHANGED
|
@@ -17,6 +17,18 @@ The engine uses indentation to define blocks, similar to Python. Each block must
|
|
|
17
17
|
<details>
|
|
18
18
|
<summary>Show available types</summary>
|
|
19
19
|
|
|
20
|
+
### Duration
|
|
21
|
+
|
|
22
|
+
Duration is defined using a number. It represents the length of a sound in milliseconds.
|
|
23
|
+
|
|
24
|
+
```deva
|
|
25
|
+
let duration = 1000
|
|
26
|
+
```
|
|
27
|
+
|
|
28
|
+
Will play a sound for 1000 milliseconds (1 second).
|
|
29
|
+
|
|
30
|
+
NOTE: Other time units like seconds or beats are not supported yet, but will be in the future.
|
|
31
|
+
|
|
20
32
|
### String
|
|
21
33
|
|
|
22
34
|
Strings are defined using double quotes.
|
|
@@ -103,22 +115,13 @@ loop exportedIterator:
|
|
|
103
115
|
.kick auto exportedParams
|
|
104
116
|
```
|
|
105
117
|
|
|
106
|
-
###
|
|
118
|
+
### Triggers
|
|
107
119
|
|
|
108
|
-
|
|
120
|
+
You can load your own samples and use them in your music.
|
|
109
121
|
|
|
110
|
-
|
|
111
|
-
You can also create custom triggers using the `@load` directive.
|
|
122
|
+
Load usage : `@load <path> as <name>`
|
|
112
123
|
|
|
113
|
-
|
|
114
|
-
.kick
|
|
115
|
-
.kick 1/4
|
|
116
|
-
.kick auto {reverb: 50, decay: 30}
|
|
117
|
-
```
|
|
118
|
-
|
|
119
|
-
### Custom triggers
|
|
120
|
-
|
|
121
|
-
Same usage as built-in triggers, but with custom audio files or effects.
|
|
124
|
+
Trigger usage : `.<name> <duration> <params>`
|
|
122
125
|
|
|
123
126
|
```deva
|
|
124
127
|
@load "./path/to/instrument.mp3" as mySample
|
|
@@ -138,7 +141,7 @@ let map = {myKey: 200}
|
|
|
138
141
|
let array = [0, 1, 2]
|
|
139
142
|
```
|
|
140
143
|
|
|
141
|
-
###
|
|
144
|
+
### Loops
|
|
142
145
|
|
|
143
146
|
Loops are defined using the `loop` keyword, followed by the number of iterations. The body of the loop is indented.
|
|
144
147
|
|
|
@@ -146,3 +149,28 @@ Loops are defined using the `loop` keyword, followed by the number of iterations
|
|
|
146
149
|
loop 10:
|
|
147
150
|
# ...
|
|
148
151
|
```
|
|
152
|
+
|
|
153
|
+
### Groups
|
|
154
|
+
|
|
155
|
+
Groups are defined using the `group` keyword, followed by the group name. The body of the group is indented.
|
|
156
|
+
|
|
157
|
+
```deva
|
|
158
|
+
group myGroup:
|
|
159
|
+
# ...
|
|
160
|
+
```
|
|
161
|
+
|
|
162
|
+
### Calling Groups (Sequential Execution)
|
|
163
|
+
|
|
164
|
+
Groups can be called using the `call` keyword, which executes the group in sequence.
|
|
165
|
+
|
|
166
|
+
```deva
|
|
167
|
+
call myGroup
|
|
168
|
+
```
|
|
169
|
+
|
|
170
|
+
### Spawning Groups (Parallel Execution)
|
|
171
|
+
|
|
172
|
+
Groups can be spawned using the `spawn` keyword, which executes the group in parallel.
|
|
173
|
+
|
|
174
|
+
```deva
|
|
175
|
+
spawn myGroup
|
|
176
|
+
```
|
package/docs/TODO.md
CHANGED
|
@@ -42,11 +42,14 @@ This is a list of tasks and features to be implemented in Devalang. Note that th
|
|
|
42
42
|
- [x] #
|
|
43
43
|
- [x] @import
|
|
44
44
|
- [x] @export
|
|
45
|
-
- [ ] @group
|
|
46
|
-
- [ ] @pattern
|
|
47
|
-
- [ ] @function
|
|
48
45
|
- [x] @load
|
|
49
46
|
- [ ] @include
|
|
47
|
+
- [ ] function
|
|
48
|
+
- [ ] pattern
|
|
49
|
+
- [x] group
|
|
50
|
+
- [x] call
|
|
51
|
+
- [x] spawn
|
|
52
|
+
- [x] sleep
|
|
50
53
|
- [x] bpm
|
|
51
54
|
- [x] bank
|
|
52
55
|
- [x] loop
|
|
@@ -62,8 +65,6 @@ This is a list of tasks and features to be implemented in Devalang. Note that th
|
|
|
62
65
|
|
|
63
66
|
## Other TODOs
|
|
64
67
|
|
|
65
|
-
- [
|
|
66
|
-
- [
|
|
67
|
-
- [
|
|
68
|
-
- [ ] Add unit tests for all core components
|
|
69
|
-
- [ ] Comment all core components
|
|
68
|
+
- [ ] Patch path handling to support relative paths
|
|
69
|
+
- [ ] Comment all core components
|
|
70
|
+
- [ ] Add unit tests for all core components
|
|
@@ -0,0 +1,12 @@
|
|
|
1
|
+
# This file demonstrates the use of grouping in Devalang.
|
|
2
|
+
|
|
3
|
+
@import { duration, default_bank, params, loopCount, tempo } from "./examples/variables.deva"
|
|
4
|
+
|
|
5
|
+
@load "./examples/samples/kick-808.wav" as kickCustom
|
|
6
|
+
@load "./examples/samples/hat-808.wav" as hatCustom
|
|
7
|
+
|
|
8
|
+
group myGroup:
|
|
9
|
+
.kickCustom duration params
|
|
10
|
+
.hatCustom duration params
|
|
11
|
+
|
|
12
|
+
@export { myGroup }
|
package/examples/index.deva
CHANGED
|
@@ -1,16 +1,17 @@
|
|
|
1
|
-
|
|
1
|
+
# This file demonstrates the use of main features in Devalang.
|
|
2
2
|
|
|
3
|
-
@
|
|
4
|
-
@
|
|
3
|
+
@import { duration, default_bank, params, loopCount, tempo } from "./examples/variables.deva"
|
|
4
|
+
@import { myGroup } from "./examples/group.deva"
|
|
5
|
+
|
|
6
|
+
@load "./examples/samples/kick-808.wav" as kickCustom
|
|
7
|
+
@load "./examples/samples/hat-808.wav" as hatCustom
|
|
5
8
|
|
|
6
9
|
bpm tempo
|
|
7
10
|
|
|
8
11
|
bank default_bank
|
|
9
12
|
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
# Uncomment the next line (.hat) while executing "play" command
|
|
14
|
-
# with `--repeat` option to see magic happen !
|
|
13
|
+
# Will be executed line by line (sequentially)
|
|
14
|
+
call myGroup
|
|
15
15
|
|
|
16
|
-
|
|
16
|
+
# Will be executed in parallel (concurrently)
|
|
17
|
+
# spawn myGroup
|
|
@@ -0,0 +1,15 @@
|
|
|
1
|
+
# This file demonstrates the use of a loop in Devalang.
|
|
2
|
+
|
|
3
|
+
@import { duration, default_bank, params, loopCount, tempo } from "./examples/variables.deva"
|
|
4
|
+
|
|
5
|
+
@load "./examples/samples/kick-808.wav" as kickCustom
|
|
6
|
+
@load "./examples/samples/hat-808.wav" as hatCustom
|
|
7
|
+
|
|
8
|
+
loop loopCount:
|
|
9
|
+
.kickCustom duration params
|
|
10
|
+
|
|
11
|
+
# Uncomment the next line (.hat) while executing "play" command
|
|
12
|
+
# with `--repeat` option to see magic happen !
|
|
13
|
+
|
|
14
|
+
.hatCustom duration params
|
|
15
|
+
|
package/out-tsc/bin/devalang.exe
CHANGED
|
Binary file
|
package/package.json
CHANGED
|
@@ -1,42 +1,44 @@
|
|
|
1
|
-
{
|
|
2
|
-
"name": "@devaloop/devalang",
|
|
3
|
-
"private": false,
|
|
4
|
-
"version": "0.0.1-alpha.
|
|
5
|
-
"description": "Write music like code. Devalang is a domain-specific language (DSL) for sound designers and music hackers. Compose, automate, and control sound — in plain text.",
|
|
6
|
-
"main": "out-tsc/index.js",
|
|
7
|
-
"bin": {
|
|
8
|
-
"devalang": "./out-tsc/bin/index.js"
|
|
9
|
-
},
|
|
10
|
-
"scripts": {
|
|
11
|
-
"prepublish": "cargo build --release && npm run script:postbuild",
|
|
12
|
-
"rust:dev:build": "cargo run build --entry examples --output output",
|
|
13
|
-
"rust:dev:check": "cargo run check --entry examples --output output",
|
|
14
|
-
"
|
|
15
|
-
"
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
"
|
|
22
|
-
"
|
|
23
|
-
"
|
|
24
|
-
"
|
|
25
|
-
"
|
|
26
|
-
"
|
|
27
|
-
"
|
|
28
|
-
"
|
|
29
|
-
"
|
|
30
|
-
"
|
|
31
|
-
"
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
"
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
|
|
1
|
+
{
|
|
2
|
+
"name": "@devaloop/devalang",
|
|
3
|
+
"private": false,
|
|
4
|
+
"version": "0.0.1-alpha.7",
|
|
5
|
+
"description": "Write music like code. Devalang is a domain-specific language (DSL) for sound designers and music hackers. Compose, automate, and control sound — in plain text.",
|
|
6
|
+
"main": "out-tsc/index.js",
|
|
7
|
+
"bin": {
|
|
8
|
+
"devalang": "./out-tsc/bin/index.js"
|
|
9
|
+
},
|
|
10
|
+
"scripts": {
|
|
11
|
+
"prepublish": "cargo build --release && npm run script:postbuild",
|
|
12
|
+
"rust:dev:build": "cargo run build --entry examples --output output",
|
|
13
|
+
"rust:dev:check": "cargo run check --entry examples --output output",
|
|
14
|
+
"rust:wasm:web": "wasm-pack build --target=web --no-default-features",
|
|
15
|
+
"rust:wasm:node": "wasm-pack build --target=nodejs --no-default-features",
|
|
16
|
+
"script:postbuild": "tsc && node out-tsc/scripts/postbuild.js",
|
|
17
|
+
"script:version:bump": "tsc && node out-tsc/scripts/version/index.js"
|
|
18
|
+
},
|
|
19
|
+
"homepage": "https://devalang.com",
|
|
20
|
+
"keywords": [
|
|
21
|
+
"devalang",
|
|
22
|
+
"music",
|
|
23
|
+
"sound",
|
|
24
|
+
"domain-specific language",
|
|
25
|
+
"dsl",
|
|
26
|
+
"programming language",
|
|
27
|
+
"sound design",
|
|
28
|
+
"music hacking",
|
|
29
|
+
"audio",
|
|
30
|
+
"synthesis",
|
|
31
|
+
"scripting",
|
|
32
|
+
"sound synthesis",
|
|
33
|
+
"music programming"
|
|
34
|
+
],
|
|
35
|
+
"author": "Devaloop",
|
|
36
|
+
"license": "MIT",
|
|
37
|
+
"repository": {
|
|
38
|
+
"type": "git",
|
|
39
|
+
"url": "https://github.com/devaloop-labs/devalang.git"
|
|
40
|
+
},
|
|
41
|
+
"dependencies": {
|
|
42
|
+
"@types/node": "^24.0.3"
|
|
43
|
+
}
|
|
42
44
|
}
|
package/project-version.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
|
-
{
|
|
2
|
-
"version": "0.0.1-alpha.
|
|
3
|
-
"channel": "alpha",
|
|
4
|
-
"lastCommit": "
|
|
5
|
-
"build":
|
|
1
|
+
{
|
|
2
|
+
"version": "0.0.1-alpha.7",
|
|
3
|
+
"channel": "alpha",
|
|
4
|
+
"lastCommit": "81db490b7d9cc92f0512b49cf3dbaeb74cf57de1",
|
|
5
|
+
"build": 6
|
|
6
6
|
}
|
package/rust/cli/build.rs
CHANGED
|
@@ -1,5 +1,4 @@
|
|
|
1
1
|
use crate::{
|
|
2
|
-
audio::render::render_audio_with_modules,
|
|
3
2
|
config::Config,
|
|
4
3
|
core::{
|
|
5
4
|
builder::Builder,
|
|
@@ -12,6 +11,7 @@ use crate::{
|
|
|
12
11
|
};
|
|
13
12
|
use std::{ thread, time::Duration };
|
|
14
13
|
|
|
14
|
+
#[cfg(feature = "cli")]
|
|
15
15
|
pub fn handle_build_command(
|
|
16
16
|
config: Option<Config>,
|
|
17
17
|
entry: Option<String>,
|
|
@@ -104,7 +104,7 @@ fn begin_build(entry: String, output: String) {
|
|
|
104
104
|
|
|
105
105
|
// SECTION Load
|
|
106
106
|
// NOTE: We use modules in the build command, so we need to load them
|
|
107
|
-
let (modules_tokens, modules_statements) = module_loader.
|
|
107
|
+
let (modules_tokens, modules_statements) = module_loader.load_all_modules(&mut global_store);
|
|
108
108
|
|
|
109
109
|
// SECTION Write logs
|
|
110
110
|
write_lexer_log_file(&normalized_output_dir, "lexer_tokens.log", modules_tokens.clone());
|
|
@@ -116,12 +116,12 @@ fn begin_build(entry: String, output: String) {
|
|
|
116
116
|
|
|
117
117
|
// SECTION Building AST and Audio
|
|
118
118
|
let builder = Builder::new();
|
|
119
|
-
builder.build_ast(&modules_statements);
|
|
119
|
+
builder.build_ast(&modules_statements, &normalized_output_dir);
|
|
120
120
|
builder.build_audio(&modules_statements, &normalized_output_dir, &mut global_store);
|
|
121
121
|
|
|
122
122
|
// SECTION Logging
|
|
123
123
|
let logger = Logger::new();
|
|
124
|
-
|
|
124
|
+
|
|
125
125
|
let success_message = format!(
|
|
126
126
|
"Build completed successfully in {:.2?}. Output files written to: '{}'",
|
|
127
127
|
duration.elapsed(),
|
package/rust/cli/check.rs
CHANGED
|
@@ -9,6 +9,7 @@ use crate::{
|
|
|
9
9
|
};
|
|
10
10
|
use std::{ thread, time::Duration };
|
|
11
11
|
|
|
12
|
+
#[cfg(feature = "cli")]
|
|
12
13
|
pub fn handle_check_command(
|
|
13
14
|
config: Option<Config>,
|
|
14
15
|
entry: Option<String>,
|
|
@@ -101,7 +102,7 @@ fn begin_check(entry: String, output: String) {
|
|
|
101
102
|
|
|
102
103
|
// SECTION Load
|
|
103
104
|
// NOTE: We don't use modules in the check command, but we still need to load them
|
|
104
|
-
let modules = module_loader.
|
|
105
|
+
let modules = module_loader.load_all_modules(&mut global_store);
|
|
105
106
|
|
|
106
107
|
// TODO: Implement debugging
|
|
107
108
|
|
package/rust/cli/init.rs
CHANGED
|
@@ -1,11 +1,13 @@
|
|
|
1
1
|
use std::{ fs, path::Path };
|
|
2
2
|
use include_dir::{ include_dir, Dir };
|
|
3
|
-
use inquire::{ Select, Confirm };
|
|
4
|
-
|
|
5
3
|
use crate::{ cli::template::get_available_templates, utils::file::copy_dir_recursive };
|
|
6
4
|
|
|
5
|
+
#[cfg(feature = "cli")]
|
|
6
|
+
use inquire::{ Select, Confirm };
|
|
7
|
+
|
|
7
8
|
static TEMPLATES_DIR: Dir = include_dir!("$CARGO_MANIFEST_DIR/templates");
|
|
8
9
|
|
|
10
|
+
#[cfg(feature = "cli")]
|
|
9
11
|
pub fn handle_init_command(name: Option<String>, template: Option<String>) {
|
|
10
12
|
let current_dir = std::env::current_dir().unwrap();
|
|
11
13
|
let project_name = name
|
package/rust/cli/play.rs
CHANGED
|
@@ -1,5 +1,4 @@
|
|
|
1
1
|
use crate::{
|
|
2
|
-
audio::player::AudioPlayer,
|
|
3
2
|
config::Config,
|
|
4
3
|
core::{
|
|
5
4
|
builder::Builder,
|
|
@@ -15,6 +14,7 @@ use std::{ path::Path, sync::mpsc::channel, thread, time::Duration };
|
|
|
15
14
|
use std::fs;
|
|
16
15
|
use std::collections::HashMap;
|
|
17
16
|
|
|
17
|
+
#[cfg(feature = "cli")]
|
|
18
18
|
pub fn handle_play_command(
|
|
19
19
|
config: Option<Config>,
|
|
20
20
|
entry: Option<String>,
|
|
@@ -22,6 +22,8 @@ pub fn handle_play_command(
|
|
|
22
22
|
watch: bool,
|
|
23
23
|
repeat: bool
|
|
24
24
|
) {
|
|
25
|
+
use crate::core::audio::player::AudioPlayer;
|
|
26
|
+
|
|
25
27
|
let logger = Logger::new();
|
|
26
28
|
|
|
27
29
|
let entry_path = entry
|
|
@@ -144,7 +146,7 @@ fn begin_play(config: &Option<Config>, entry_file: &str, output: &str) {
|
|
|
144
146
|
let duration = std::time::Instant::now();
|
|
145
147
|
let mut global_store = GlobalStore::new();
|
|
146
148
|
let loader = ModuleLoader::new(&normalized_entry, &normalized_output_dir);
|
|
147
|
-
let (modules_tokens, modules_statements) = loader.
|
|
149
|
+
let (modules_tokens, modules_statements) = loader.load_all_modules(&mut global_store);
|
|
148
150
|
|
|
149
151
|
// SECTION Write logs
|
|
150
152
|
write_lexer_log_file(&normalized_output_dir, "lexer_tokens.log", modules_tokens.clone());
|
|
@@ -156,7 +158,7 @@ fn begin_play(config: &Option<Config>, entry_file: &str, output: &str) {
|
|
|
156
158
|
|
|
157
159
|
// SECTION Building AST and Audio
|
|
158
160
|
let builder = Builder::new();
|
|
159
|
-
builder.build_ast(&modules_statements);
|
|
161
|
+
builder.build_ast(&modules_statements, &output);
|
|
160
162
|
builder.build_audio(&modules_statements, &output, &mut global_store);
|
|
161
163
|
|
|
162
164
|
// SECTION Logging
|
package/rust/cli/template.rs
CHANGED
|
@@ -1,9 +1,9 @@
|
|
|
1
1
|
use include_dir::{ include_dir, Dir, DirEntry };
|
|
2
|
-
|
|
3
2
|
use crate::utils::file::format_file_size;
|
|
4
3
|
|
|
5
4
|
static TEMPLATES_DIR: Dir = include_dir!("$CARGO_MANIFEST_DIR/templates");
|
|
6
5
|
|
|
6
|
+
#[cfg(feature = "cli")]
|
|
7
7
|
pub fn handle_template_list_command() {
|
|
8
8
|
let available_templates = get_available_templates();
|
|
9
9
|
|
|
@@ -16,6 +16,7 @@ pub fn handle_template_list_command() {
|
|
|
16
16
|
println!("\nUsage : devalang init --name <project-name> --template <template-name>");
|
|
17
17
|
}
|
|
18
18
|
|
|
19
|
+
#[cfg(feature = "cli")]
|
|
19
20
|
pub fn handle_template_info_command(name: String) {
|
|
20
21
|
let template_dir = TEMPLATES_DIR.get_dir(name.clone()).unwrap_or_else(|| {
|
|
21
22
|
println!("❌ The template '{}' is not found.", name);
|
package/rust/config/loader.rs
CHANGED
|
@@ -2,11 +2,7 @@ use std::{ collections::HashMap, fs::File, io::BufReader };
|
|
|
2
2
|
use hound::{ SampleFormat, WavSpec, WavWriter };
|
|
3
3
|
use rodio::{ Decoder, Source };
|
|
4
4
|
|
|
5
|
-
use crate::core::{
|
|
6
|
-
parser::statement::Statement,
|
|
7
|
-
store::variable::VariableTable,
|
|
8
|
-
utils::path::normalize_path,
|
|
9
|
-
};
|
|
5
|
+
use crate::core::{ store::variable::VariableTable, utils::path::normalize_path };
|
|
10
6
|
|
|
11
7
|
const SAMPLE_RATE: u32 = 44100;
|
|
12
8
|
const CHANNELS: u16 = 2;
|