回答編集履歴
3
動作説明追記
test
CHANGED
@@ -124,3 +124,7 @@
|
|
124
124
|
select {}
|
125
125
|
}
|
126
126
|
```
|
127
|
+
|
128
|
+
動作例:
|
129
|
+

|
130
|
+
ボタンクリックで「ミ->レ->ド」を3回繰り返します。
|
2
JS版の最小サンプルを追記
test
CHANGED
@@ -19,3 +19,108 @@
|
|
19
19
|
|
20
20
|
もしくは「やりたいこと」はどういうことなのかをもう少し具体的に示してください。
|
21
21
|
|
22
|
+
## 追記
|
23
|
+
|
24
|
+
質問の意味を取り違えていました。
|
25
|
+
スクリプトエンジンを使って書いたシナリオに基づき音を鳴らしたいという事でした。
|
26
|
+
|
27
|
+
下記に「JSスクリプトエンジン」を使ってシナリオプログラムを記述しそれに基づいて音楽を鳴らす最小のサンプルを示します。
|
28
|
+
ここからMonkeyに移植するなどしてもらえば実現できそうですね。
|
29
|
+
|
30
|
+
|
31
|
+
https://go.dev/play/p/4LW0Jjzr5mO
|
32
|
+
```go
|
33
|
+
package main
|
34
|
+
|
35
|
+
import (
|
36
|
+
"math"
|
37
|
+
"syscall/js"
|
38
|
+
)
|
39
|
+
|
40
|
+
var (
|
41
|
+
window = js.Global()
|
42
|
+
document = window.Get("document")
|
43
|
+
|
44
|
+
AudioContext = js.Global().Get("AudioContext")
|
45
|
+
OscillatorNode = js.Global().Get("OscillatorNode")
|
46
|
+
GainNode = js.Global().Get("GainNode")
|
47
|
+
|
48
|
+
note2freq = []float64{}
|
49
|
+
)
|
50
|
+
|
51
|
+
func init() {
|
52
|
+
for i := 0; i < 128; i++ {
|
53
|
+
note2freq = append(note2freq, 440*math.Pow(2, float64(i-69)/12))
|
54
|
+
}
|
55
|
+
}
|
56
|
+
|
57
|
+
type Note struct {
|
58
|
+
Number int
|
59
|
+
Duration float64
|
60
|
+
}
|
61
|
+
|
62
|
+
type MusicBox struct {
|
63
|
+
ctx js.Value
|
64
|
+
osc js.Value
|
65
|
+
gain js.Value
|
66
|
+
current float64
|
67
|
+
}
|
68
|
+
|
69
|
+
func NewMusicBox() *MusicBox {
|
70
|
+
ctx := AudioContext.New()
|
71
|
+
osc := OscillatorNode.New(ctx)
|
72
|
+
gain := GainNode.New(ctx)
|
73
|
+
osc.Call("connect", gain)
|
74
|
+
osc.Get("frequency").Set("value", 0)
|
75
|
+
gain.Call("connect", ctx.Get("destination"))
|
76
|
+
gain.Get("gain").Set("value", 0)
|
77
|
+
osc.Call("start")
|
78
|
+
return &MusicBox{
|
79
|
+
ctx: ctx,
|
80
|
+
osc: osc,
|
81
|
+
gain: gain,
|
82
|
+
current: ctx.Get("currentTime").Float(),
|
83
|
+
}
|
84
|
+
}
|
85
|
+
|
86
|
+
func (mb *MusicBox) Play(note Note) {
|
87
|
+
mb.osc.Get("frequency").Call("setValueAtTime", note2freq[note.Number], mb.current)
|
88
|
+
mb.gain.Get("gain").Call("setValueAtTime", 0.3, mb.current)
|
89
|
+
mb.gain.Get("gain").Call("setValueAtTime", 0.0, mb.current+note.Duration)
|
90
|
+
mb.current += note.Duration
|
91
|
+
}
|
92
|
+
|
93
|
+
const sample = `for (let i=0; i< 3; i++) {
|
94
|
+
play(64, 0.2)
|
95
|
+
play(0, 0.1)
|
96
|
+
play(62, 0.2)
|
97
|
+
play(0, 0.1)
|
98
|
+
play(60, 0.2)
|
99
|
+
play(0, 0.1)
|
100
|
+
}
|
101
|
+
`
|
102
|
+
|
103
|
+
func main() {
|
104
|
+
code := document.Call("createElement", "textarea")
|
105
|
+
code.Set("id", "code")
|
106
|
+
code.Set("value", sample)
|
107
|
+
code.Get("style").Set("width", "50%")
|
108
|
+
code.Get("style").Set("height", "20em")
|
109
|
+
document.Get("body").Call("appendChild", code)
|
110
|
+
btn := document.Call("createElement", "button")
|
111
|
+
btn.Set("textContent", "music start!")
|
112
|
+
btn.Call("addEventListener", "click", js.FuncOf(func(js.Value, []js.Value) interface{} {
|
113
|
+
mb := NewMusicBox()
|
114
|
+
window.Set("play", js.FuncOf(func(this js.Value, args []js.Value) interface{} {
|
115
|
+
mb.Play(Note{args[0].Int(), args[1].Float()})
|
116
|
+
return nil
|
117
|
+
}))
|
118
|
+
code := document.Call("getElementById", "code")
|
119
|
+
src := code.Get("value")
|
120
|
+
window.Call("eval", src)
|
121
|
+
return nil
|
122
|
+
}))
|
123
|
+
document.Get("body").Call("appendChild", btn)
|
124
|
+
select {}
|
125
|
+
}
|
126
|
+
```
|
1
回答の方針を追記
test
CHANGED
@@ -1,3 +1,7 @@
|
|
1
|
+
「標準入力」という概念はコマンドラインのプログラムのための仕組みなのでブラウザにはありません。
|
2
|
+
ノート番号を引数に渡して音を鳴らす関数を作成することはもちろんできるはずです。
|
3
|
+
その引数にインタラクティブに渡す手段を質問されているという仮定で回答します。
|
4
|
+
|
1
5
|
「調べてでてきたもの」でなにか不都合はありますか?
|
2
6
|
ブラウザのフォームに番号を入力したものを読み取って動くというのはどうでしょうか?
|
3
7
|
|
@@ -13,6 +17,5 @@
|
|
13
17
|
|
14
18
|
というのではどうでしょうか。
|
15
19
|
|
16
|
-
もしくは「やりたいこと」はどういうことなのかを具体的に示してください。
|
20
|
+
もしくは「やりたいこと」はどういうことなのかをもう少し具体的に示してください。
|
17
21
|
|
18
|
-
「標準入力」という概念はコマンドラインのプログラムのための仕組みなのでブラウザにはありません。
|