-
Notifications
You must be signed in to change notification settings - Fork 0
/
webmidi.gleam
114 lines (101 loc) · 3.34 KB
/
webmidi.gleam
1
2
3
4
5
6
7
8
9
10
11
12
13
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
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
import gleam/javascript/promise
/// A MIDIInputMap instance is a read-only Map-like object, in which each key is the ID
/// string for MIDI input, and the associated value is the corresponding MIDIInput object.
pub type MidiInputMap
// string for MIDI output, and the associated value is the corresponding MIDIOutput object.
/// A MIDIOutputMap instance is a read-only Map-like object, in which each key is the ID
pub type MidiOutputMap
pub type MidiInput
pub type MidiOutput
pub type MidiAccess
pub type MidiPort
pub type ConnectionEvent
pub type MessageEvent
@external(javascript, "./ffi_webmidi.mjs", "request_midi")
pub fn request_midi() -> promise.Promise(MidiAccess)
//#TODO: Finish adding all events
pub type MidiData {
NoteOff(channel: Int, pitch: Int, velocity: Int)
NoteOn(channel: Int, pitch: Int, velocity: Int)
PolyPressure(channel: Int, pitch: Int, pressure: Int)
BankSelect(channel: Int, value: Int)
Modulation(channel: Int, value: Int)
BreathController(channel: Int, value: Int)
Undefined1(channel: Int, value: Int)
FootController(channel: Int, value: Int)
PortamentoTime(channel: Int, value: Int)
// DataEntry
ChannelVolume(channel: Int, value: Int)
Balance(channel: Int, value: Int)
Undefined2(channel: Int, value: Int)
Pan(channel: Int, value: Int)
ExpressionController(channel: Int, value: Int)
// ----------------
SongSelect(id: Int)
TuneRequest
EndOfSysEx
Timing
Start
Continue
Stop
ActiveSensing
SystemReset
// ----
Undefined(value: Int)
Err(value: BitArray)
}
pub fn to_data(raw: BitArray) {
case raw {
<<channel, pitch, velocity>> if 128 <= channel && channel <= 143 -> {
NoteOff(channel - 128, pitch, velocity)
}
<<channel, pitch, velocity>> if 144 <= channel && channel <= 159 -> {
NoteOn(channel - 144, pitch, velocity)
}
<<channel, pitch, pressure>> if 160 <= channel && channel <= 175 -> {
PolyPressure(channel - 160, pitch, pressure)
}
<<channel, 0, value>> if 176 <= channel && channel <= 191 -> {
BankSelect(channel - 176, value)
}
<<channel, 1, value>> if 176 <= channel && channel <= 191 -> {
Modulation(channel - 176, value)
}
<<channel, 2, value>> if 176 <= channel && channel <= 191 -> {
BreathController(channel - 176, value)
}
// <<channel, 3, value>> if 176 <= channel && channel <= 191 -> {
// _(channel - 176, value)
// }
<<channel, 4, value>> if 176 <= channel && channel <= 191 -> {
FootController(channel - 176, value)
}
<<channel, 5, value>> if 176 <= channel && channel <= 191 -> {
PortamentoTime(channel - 176, value)
}
// <<channel, 6, value>> if 176 <= channel && channel <= 191 -> {
// (channel - 176, value)
// }
<<channel, 7, value>> if 176 <= channel && channel <= 191 -> {
ChannelVolume(channel - 176, value)
}
<<channel, 8, value>> if 176 <= channel && channel <= 191 -> {
Balance(channel - 176, value)
}
// <<channel, 9, value>> if 176 <= channel && channel <= 191 -> {
// _(channel - 176, value)
// }
// -----
<<243, id>> -> SongSelect(id)
<<246>> -> TuneRequest
<<247>> -> EndOfSysEx
<<248>> -> Timing
<<249, value>> -> Undefined(value)
<<250>> -> Start
<<251>> -> Continue
<<252>> -> Stop
<<254>> -> ActiveSensing
<<255>> -> SystemReset
_ -> Err(raw)
}
}