Upgrade to Pro
— share decks privately, control downloads, hide ads and more …
Speaker Deck
Features
Speaker Deck
PRO
Sign in
Sign up for free
Search
Search
Elixir, MIDI and LiveView
Search
Thibaut Barrère
June 18, 2019
Programming
410
0
Share
Embed
Copy iframe code
Copy JS code
Copy link
Start on current slide
Elixir, MIDI and LiveView
(Paris.Ex meetup)
Thibaut Barrère
June 18, 2019
More Decks by Thibaut Barrère
See All by Thibaut Barrère
Kiba ETL: feedback on OSS / open-core sustainability for a Ruby gem
thbar
0
150
Elixir, MIDI & LiveView (CodeElixir London 2019)
thbar
0
1.1k
Kiba ETL v2 - RubyKaigi 2018
thbar
4
2k
Elixir hot-reloading & MIDI events generation
thbar
1
560
De Rails à Phoenix - retour d'expérience sur une réécriture d'application SaaS
thbar
3
2.3k
Processing data with Ruby and Kiba ETL
thbar
0
250
Retour d'expérience sur le bootstrapping de WiseCash (produit SaaS)
thbar
0
910
Bootstrapping your SaaS product (with freelancing)
thbar
3
620
Prestations agiles avec Acunote et Freckle
thbar
3
600
Other Decks in Programming
See All in Programming
【やさしく解説 設計編・中級 #4】ルールの寿命と、システムの年輪
panda728
PRO
2
180
S3 を使うアプリケーションをローカル完結で動かすことに全力を注いでみた / Running S3 Apps Offline
contour_gara
0
400
Detecting Compromised CI with eBPF and Cilium Tetragon
lizrice
0
160
今さら聞けない .NET CLI
htkym
0
180
数百円から始めるRuby電子工作
tarosay
0
140
Laravel Boostに学ぶ、AIにPHPを書かせる技術 〜OSSの実装から蒸留するエージェント制御の王道〜
kentaroutakeda
3
670
Laravelで学ぶ Webアプリケーションチューニング入門/web_application_tuning_101
hanhan1978
4
1.7k
進化を続けるGo toolsの現在地 / The Current State of Ever-Evolving Go Tools
hond0413
0
160
What's New in Android 2026
veronikapj
0
250
「人を評価する AI」の設計と実装
ryoyanara
0
180
生成AIで帳票OCRが「簡単に」作れる時代になった?
kon_shou
0
630
Augmenting AI with the Power of Jakarta EE
ivargrimstad
0
540
Featured
See All Featured
Redefining SEO in the New Era of Traffic Generation
szymonslowik
1
380
Being A Developer After 40
akosma
91
590k
Impact Scores and Hybrid Strategies: The future of link building
tamaranovitovic
0
370
Let's Do A Bunch of Simple Stuff to Make Websites Faster
chriscoyier
508
140k
Typedesign – Prime Four
hannesfritz
42
3.1k
From Legacy to Launchpad: Building Startup-Ready Communities
dugsong
0
290
Writing Fast Ruby
sferik
630
63k
ReactJS: Keep Simple. Everything can be a component!
pedronauck
666
130k
Making Projects Easy
brettharned
120
6.7k
The Invisible Side of Design
smashingmag
301
52k
Reality Check: Gamification 10 Years Later
codingconduct
0
2.2k
brightonSEO & MeasureFest 2025 - Christian Goodrich - Winning strategies for Black Friday CRO & PPC
cargoodrich
3
760
Transcript
Elixir, MIDI & LiveView
@thibaut_barrere Consultant Ruby / Elixir / Ansible Kiba ETL /
Kiba Pro Remote 100% (Charente Maritime)
Elixir => Code-Centric Digital Audio Workstation? infiniwip (tm)
Previous episode https://github.com/thbar/demo-elixir-reloading-music Code.eval_file("music.exs")
MIDI
Note On {0x90 + channel, note, velocity} Note Off {0x80
+ channel, note, release_velocity}
Keyboard / Piano / Synthetizers photo by Clavia
MIDI controllers photo by Novation
Virtual Instruments (on computer)
Virtual Instruments (on iOS) photo by Korg
Lightning = Inter-Device Audio & MIDI (IDAM) photo by Apple
Elixir Code / DRY Refactoring Music Augmented Human (theory, scales)
Soft realtime
brew install portmidi
None
# Start a process for MIDI event queue {:ok, pid}
= PortMidi.open(:output, "Kontakt Virtual Input") note = 48 # C-4 velocity = 127 # Send "NOTE ON" PortMidi.write(pid, {0x90, note, velocity}) # Send "NOTE OFF" PortMidi.write(pid, {0x80, note})
None
Computer: Note 60 Human: WTF????
Translation def note_number_to_latin_name(midi_note, middle_c \\ @default_middle_c) do remap_note(midi_note, @latin_names, middle_c)
end defp remap_note(midi_note, names, middle_c) do offset = get_base_offset(middle_c) octave = div(midi_note + offset, 12) octave_note = rem(midi_note + offset, 12) octave_note = names |> Enum.at(octave_note) "#{octave_note}#{octave}" end defp get_base_offset("C4"), do: -12
DocTests ❤ ## Examples iex> MusicRef.note_number_to_latin_name(60) "Do4" iex> MusicRef.note_number_to_latin_name(78) "Fa#5"
Phoenix LiveView <div> <p> Time is <%= @time %> </p>
</div> HTML? ✔
Phoenix LiveView <svg> <%= for note <- notes do %>
<rect x="..." y="0" width="10" height="20" fill="<%= note.color %>"> <% end %> </svg> SVG? ✔
Phoenix LiveView <svg> <g> # white notes </g> <g> #
black notes </g> </svg>
None
None
def note_on({channel, note, velocity}, device, portmidi \\ PortMidi) do Phoenix.PubSub.broadcast(Widgets.PubSub,
"notes", {:note_on, note}) :ok = portmidi.write(device, {0x90 + channel, note, velocity}) end
None
Code & Demo