MML(Music Macro Language)を触って見たいなとおもっていたところovertoneを見つけました。clojureでプログラミングすることで音を鳴らせるようだ。気になったのでインストールしてドミソを鳴らすまでやります。
overtoneとは
実行環境
- macOS Sierra 10.12.1(16B2657)
- REPL-y 0.3.7, nREPL 0.2.7
- Clojure 1.7.0
- Leiningen 2.5.2 on Java 1.8.0_45 Java HotSpot(TM) 64-Bit Server VM
プロジェクトの作成
leinコマンドでプロジェクトを作成します。今回はtutorialという名前にします。
$ lein new tutorial
Generating a project called tutorial based on the 'default' template.
The default template is intended for library projects, not applications.
To see other templates (app, plugin, etc), try `lein help new`.
プロジェクトが作成されるとtutorialディレクトリができているので、そこに移動します。
$ cd tutorial
overtoneのインストール
overtoneをインストールできるようにproject.cljを書き換えます。
(defproject tutorial "0.1.0-SNAPSHOT"
:description "FIXME: write description"
:url "http://example.com/FIXME"
:license {:name "Eclipse Public License"
:url "http://www.eclipse.org/legal/epl-v10.html"}
:dependencies [
[org.clojure/clojure "1.7.0"]
[overtone "0.10.1"]
])
変更箇所はここです。[overtone "0.10.1"]
を追加しました。
$ git diff project.clj
diff --git a/overtone/tutorial/project.clj b/overtone/tutorial/project.clj
index 5ae6fc4..75c418d 100644
--- a/overtone/tutorial/project.clj
+++ b/overtone/tutorial/project.clj
@@ -3,4 +3,7 @@
:url "http://example.com/FIXME"
:license {:name "Eclipse Public License"
:url "http://www.eclipse.org/legal/epl-v10.html"}
- :dependencies [[org.clojure/clojure "1.7.0"]])
+ :dependencies [
+ [org.clojure/clojure "1.7.0"]
+ [overtone "0.10.1"]
+ ])
依存パッケージをインストールします。
$ lein deps
Retrieving overtone/overtone/0.10.1/overtone-0.10.1.pom from clojars
Retrieving org/clojure/clojure/1.5.1/clojure-1.5.1.pom from central
Retrieving org/clojure/data.json/0.2.3/data.json-0.2.3.pom from central
Retrieving clj-native/clj-native/0.9.3/clj-native-0.9.3.pom from clojars
Retrieving net/java/dev/jna/jna/3.4.0/jna-3.4.0.pom from central
Retrieving overtone/at-at/1.2.0/at-at-1.2.0.pom from clojars
Retrieving org/clojure/clojure/1.3.0/clojure-1.3.0.pom from central
Retrieving overtone/osc-clj/0.9.0/osc-clj-0.9.0.pom from clojars
Retrieving javax/jmdns/jmdns/3.4.1/jmdns-3.4.1.pom from central
Retrieving commons-net/commons-net/3.0.1/commons-net-3.0.1.pom from central
Retrieving org/apache/commons/commons-parent/21/commons-parent-21.pom from central
Retrieving org/apache/apache/9/apache-9.pom from central
Retrieving overtone/at-at/1.1.1/at-at-1.1.1.pom from clojars
Retrieving overtone/byte-spec/0.3.1/byte-spec-0.3.1.pom from clojars
Retrieving overtone/midi-clj/0.5.0/midi-clj-0.5.0.pom from clojars
Retrieving overtone/at-at/1.0.0/at-at-1.0.0.pom from clojars
Retrieving overtone/libs.handlers/0.2.0/libs.handlers-0.2.0.pom from clojars
Retrieving overtone/scsynth/3.5.7.0/scsynth-3.5.7.0.pom from clojars
Retrieving overtone/scsynth-extras/3.5.7.0/scsynth-extras-3.5.7.0.pom from clojars
Retrieving clj-glob/clj-glob/1.0.0/clj-glob-1.0.0.pom from clojars
Retrieving net/java/dev/jna/jna/3.4.0/jna-3.4.0.jar from central
Retrieving org/clojure/data.json/0.2.3/data.json-0.2.3.jar from central
Retrieving javax/jmdns/jmdns/3.4.1/jmdns-3.4.1.jar from central
Retrieving commons-net/commons-net/3.0.1/commons-net-3.0.1.jar from central
Retrieving clj-native/clj-native/0.9.3/clj-native-0.9.3.jar from clojars
Retrieving overtone/at-at/1.2.0/at-at-1.2.0.jar from clojars
Retrieving overtone/byte-spec/0.3.1/byte-spec-0.3.1.jar from clojars
Retrieving overtone/overtone/0.10.1/overtone-0.10.1.jar from clojars
Retrieving overtone/midi-clj/0.5.0/midi-clj-0.5.0.jar from clojars
Retrieving overtone/osc-clj/0.9.0/osc-clj-0.9.0.jar from clojars
Retrieving overtone/libs.handlers/0.2.0/libs.handlers-0.2.0.jar from clojars
Retrieving overtone/scsynth-extras/3.5.7.0/scsynth-extras-3.5.7.0.jar from clojars
Retrieving clj-glob/clj-glob/1.0.0/clj-glob-1.0.0.jar from clojars
Retrieving overtone/scsynth/3.5.7.0/scsynth-3.5.7.0.jar from clojars
$
RELPモードの起動
ちょっとした処理を試行錯誤する場合はREPLモードを使うと便利です。leinコマンドでpeplモードを起動します。
$ lein repl
nREPL server started on port 59082 on host 127.0.0.1 - nrepl://127.0.0.1:59082
REPL-y 0.3.7, nREPL 0.2.7
Clojure 1.7.0
Java HotSpot(TM) 64-Bit Server VM 1.8.0_45-b14
Docs: (doc function-name-here)
(find-doc "part-of-name-here")
Source: (source function-name-here)
Javadoc: (javadoc java-object-or-class-here)
Exit: Control+D or (exit) or (quit)
Results: Stored in vars *1, *2, *3, an exception in *e
ちょっとだけ試しに足し算します。
user=> (+ 1 3)
4
良さそうですね。
overtoneのuse
overtoneを使うのでuseします。
user=> (use 'overtone.live)
--> Loading Overtone...
--> Booting internal SuperCollider server...
Found 0 LADSPA plugins
*** ERROR: open directory failed '/Users/sximada/Library/Application Support/SuperCollider/synthdefs'
Number of Devices: 2
0 : "Built-in Microph"
1 : "Built-in Output"
"Built-in Microph" Input Device
Streams: 1
0 channels 2
"Built-in Output" Output Device
Streams: 1
0 channels 2
SC_AudioDriver: sample rate = 44100.000000, driver's block size = 512
--> Connecting to internal SuperCollider server...
--> Connection established
_____ __
/ __ /_ _____ _____/ /_____ ____ ___
/ / / / | / / _ \/ ___/ __/ __ \/ __ \/ _ / /_/ /| |/ / __/ / / /_/ /_/ / / / / __/
\____/ |___/\___/_/ \__/\____/_/ /_/\___/
Collaborative Programmable Music. v0.10.1
Cometh the hour, cometh Sximada, the overtone hacker.
nil
user=>
useできました。
user=> (use 'overtone.core)
IllegalStateException ->ShellStringList already refers to: #'overtone.live/->ShellStringList in namespace: user clojure.lang.Namespace.warnOrFailOnReplace (Namespace.java:88)
こちらは失敗してしまいます(なんでだ?)。
鳴らす
実際に音を鳴らします。
user=> (definst foo [] (saw 220))
#<instrument: foo>
user=> (odoc saw)
-------------------------
overtone.live/saw
([freq])
band limited sawtooth wave generator
[freq 440.0]
freq - Frequency in Hertz (control rate).
The sawtooth wave produces even and odd harmonics in
series and therefore produces a bright sound that is an
excellent starting point for brassy, raspy sounds. It's
also suitable for creating the gritty, bright sounds
needed for leads and raspy basses. Due to its harmonic
richness it's extremely suitable for use with sounds that
will be filter swept.
Categories: Generators -> Deterministic
Rates: [ :ar ]
Default rate: :ar
nil
user=> (definst bar [freq 220] (saw freq))
#<instrument: bar>
user=> (bar 110)
#<synth-node[loading]: user/bar 41>
鳴りましたか?成功したら鳴り続けているはずです。
止める
鳴り続けているとうるさいので止めます。
user=> (kill bar)
nil
同時に音を鳴らす
複数の音を同時に鳴らします。
user=> (bar 123)
#<synth-node[loading]: user/bar 42>
user=> (bar 124)
#<synth-node[loading]: user/bar 43>
user=> (bar 125)
#<synth-node[loading]: user/bar 44>
停止の場合は一括で停止します。
user=> (kill bar)
nil
user=>
ドミソ
ド/ミ/ソを同時に鳴らして和音にしてみます。
user=> (bar 261.626)
#<synth-node[loading]: user/bar 66>
user=> (bar 329.628)
#<synth-node[loading]: user/bar 67>
user=> (bar 391.995)
#<synth-node[loading]: user/bar 68>
user=>
停止は先ほどと同様 (kill bar)
です。
user=> (kill bar)
nil
user=>