I’m Nick, from Asheville NC. I’ve been lurking the forum a few weeks after discovering Crystal at exercism. So far I have started work on an ASCII library that I hope to one day be the modern equivalent of aa/caca. This has been a goal as long as I’ve been a Linux geek and Crystal has enabled my first attempt to be relatively painless, I set to work in the morning and was spitting out ASCII at midnight! Cryaa
My actual primary use of code, and in particular Ruby-esque, is with the Sonic-Pi live music coding language. I’ve been an active user for a few years and I write nearly all my music these days via Ruby, unless I’m in the mood to turn off the computer. There are a lot of wonderful things about the language, it’s great for doing some wild timing and scale tricks that make electronic jazz a breeze! The downside is that I can only use the supplied synths unless I learn to build them in Supercollider, or MIDI out as I do now, and of course, it’s Ruby so it chokes after I go to town with some wild programming ideas. I feel as if we’re “stuck” with Supercollider as a dependency, which causes a lot of development headaches and a grueling build process for me and the other two guys on Ubuntu every time there is an update.
So that’s where my grand scheme and Crystal come in. My dream live code studio would be able to give me the best of both worlds in a single package, the dexterity of interpreted Ruby to change instantly and the high efficiency of compiled code for processor intensive tasks. While live code for music and gaming are where I see the biggest benefit, I’ve already been imagining what it would be like to script live compiled objects in a web situation, where you can have all your binaries building and at full speed by the time you are ready to deploy… but that’s not my domain, so I don’t know how useful it is for a framework dev (I have barely ever touched Rails, BTW, I’m just a sucker for Ruby for fun)
So here’s a quick mockup of the workflow I’m imagining
live_loop :bass do synth :compiled_bass, note: 24, release: 0.25 sleep 1 end crystal_compile :compiled_bass, release: true do class CompiledBass < Instrument def initialize() osc1, osc2 = SinOsc.new, SqrOsc.new filter = LPF12.new osc1 + osc2 * filter end end end
So what happens is that I hit play, and there’s silence for a couple seconds while crystal is building this synth. The Ruby loop is playing on repeat, and the sound kicks in once the module is built and placed. On a subsequent play, I hit play, Crystal sees that my script hasn’t changed and so the instrument starts immediately. The next time around I decide I want osc1 * osc2 (ringmod) and Crystal goes to work building the new module while Ruby is still playing the old object up until it drops into place.
Either way, my goal is to build a low-level but simple to use synthesis library and description language in Crystal, but I can’t get that idea of trying to hotplug crystal modules into Ruby scripts out of my head, where would I even start trying to connect to a crystal object from a Ruby environment? I’ve never really worked with linking to compiled objects before, it was always reserved for the complicated languages until I discovered Crystal. I’m currently at the point where having real access to C libs is a brand new thing for me.
Any thoughts would be welcome, and if anyone has experience with creating synthesis primitives from first principles (and jackd experience), I’d be grateful to meet you. I have a friend who used to write software for Moog who I can count on for advice, but I have no illusions that my end goal will be an easy undertaking. At the end of the day, I’d love to see all the Rubyists able to specify compiled sections where speed matters and interpretation where it doesn’t, with that decision left up to the dev rather than relying on an automated MJIT as Ruby is getting into now.