Coder Social home page Coder Social logo

superdirt's Introduction

SuperDirt

SuperCollider implementation of the Dirt sampler, originally designed for the TidalCycles environment. SuperDirt is a general purpose framework for playing samples and synths, controllable over the Open Sound Control protocol, and locally from the SuperCollider language. SuperDirt is also used by Sardine, a live coding environment for Python 3.10+.

(C) 2015-2023 Julian Rohrhuber, Alex McLean and contributors

SuperDirt is free software: you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation, either version 2 of the License, or (at your option) any later version.

This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details.

You should have received a copy of the GNU General Public License along with this library. If not, see http://www.gnu.org/licenses/.

Requirements

Installation from SuperCollider

include("SuperDirt");

Note: this also automatically installs the DirtSamples quark, which contains a large collection of sound files. It downloads them as a zip file. Sometimes, git fails to unpack these samples and they don't get listed. In this case, you have to unpack them "manually".

Simple Setup

SuperDirt.start

You can pass port, outBusses, senderAddr as arguments.

Setup with options

For an example startup file, see the file superdirt_startup.scd. you can load(<path>) this from the SuperCollider startup file.

Automatic startup

If you want SuperDirt to start automatically, you can load it from the startup file. To do this, open the sc startup file (File>Open startup file) and add: load("... path to your tidal startup file ..."). This path you can get by dropping the file onto the text editor.

Options on startup

Options on-the-fly

Trouble Shooting

If you run into unspecific troubles and want to quickly reset everything, you can run the following: SuperDirt.resetEverything You can minimize downtime if you have a startup file that automatically starts SuperDirt (see Automatic startup, above).

Using SuperDirt with SuperCollider 3.6

It is in principle possible to use SuperCollider 3.6, but startup will be much slower by comparison. It is not recommended if you expect it to run smoothly.

For reference, we leave here the instructions if you want to try anyway:

The install works differently: don't do include("SuperDirt"), but instead download the three quarks to the SuperCollider Extensions folder:

Note that for automatically loading the sound files, the folder Dirt-Samples should have this name (not Dirt-Samples-master e.g.) and should be next to the SuperDirt folder.

superdirt's People

Contributors

ahihi avatar bgold-cosmos avatar bubobubobubobubo avatar calumgunn avatar dktr0 avatar f00b455 avatar fracnesco avatar geikha avatar john-d-murphy avatar juniorctl avatar loopier avatar madskjeldgaard avatar msp avatar ndr-brt avatar pd3v avatar telephon avatar theoleanse avatar thgrund avatar wimmers avatar yaxu avatar zalastax avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

superdirt's Issues

MIDI via superdirt

Currently tidal-midi works separately from tidal, generally works well but needs some bugfixes as it can glitch and go out of time.
Would it be easy to send MIDI via superdirt instead? That could have some advantages in terms of getting accurate sync, and taking advantage of the well developed+used MIDI support there. Perhaps it wouldn't be a lot of code to achieve the basics?

Accelerate question

Why is the accelerate parameter exponential? I have a patch to modify it to a linear speed change (like in classic Dirt), but I don't know whether to submit a PR since I don't understand the reason for it.

CheckBadValues with SuperDirt 1.0Dev

Hey All,

I've had this issue on windows where once I boot the server I get these errors below and I also get these errors every time I trigger a sample from Tidal : / Any ideas?

... file reading complete. Required 149 MB of memory.
SuperDirt: listening to Tidal on port 57120
CheckBadValues: unknown found in Synth 1035, ID 0
CheckBadValues: unknown found in Synth 1035, ID 0
CheckBadValues: unknown found in Synth 1030, ID 0
CheckBadValues: unknown found in Synth 1030, ID 0
CheckBadValues: unknown found in Synth 1025, ID 0
CheckBadValues: unknown found in Synth 1025, ID 0
CheckBadValues: unknown found in Synth 1020, ID 0
CheckBadValues: unknown found in Synth 1020, ID 0
CheckBadValues: unknown found in Synth 1015, ID 0
CheckBadValues: unknown found in Synth 1015, ID 0
CheckBadValues: unknown found in Synth 1010, ID 0
CheckBadValues: unknown found in Synth 1010, ID 0
CheckBadValues: unknown found in Synth 1005, ID 0
CheckBadValues: unknown found in Synth 1005, ID 0
CheckBadValues: unknown found in Synth 1000, ID 0
CheckBadValues: unknown found in Synth 1000, ID 0

leslie is always running

The leslie synth def doesn't use DirtPause and gatelike the others, so it is always running and eating cycles, and doesn't fade out gracefully. (DirtPause was introduced in 0.9-dev to pause unused effects).

Orbits wrapping wrongly?

I have ten orbits defined, but orbit 4 is going to orbit 0, orbit 5 is going to orbit 1, and so on. Here's my current startup file:

(
// configure the sound server: here you could add hardware specific options
// see http://doc.sccode.org/Classes/ServerOptions.html
// s.options.maxLogins = 8;
s.options.numBuffers = 1024 * 256 * 4; // increase this if you need to load more samples
s.options.memSize = 8192 * 16 * 4; // increase this if you get "alloc failed" messages
s.options.maxNodes = 1024 * 64; // increase this if you are getting drop outs and the message "too many nodes"
s.options.maxLogins = 10;

s.options.numOutputBusChannels = 2; // set this to your hardware output channel size, if necessary
s.options.numInputBusChannels = 2; // set this to your hardware output channel size, if necessary
// boot the server and start SuperDirt
s.waitForBoot {
	~dirt = SuperDirt(2, s); // two output channels, increase if you want to pan across more channels
	~dirt.loadSoundFiles;   // load samples (path containing a wildcard can be passed in)
    ~dirt.loadSoundFiles("/home/alex/SparkleShare/spicule/extra-samples/*");
	~dirt.loadSoundFiles("/home/alex/src/damu-samples/*");
	~dirt.loadSoundFiles("/home/alex/src/bloodsport/*");

	// for example: ~dirt.loadSoundFiles("/Users/myUserName/Dirt/samples/*");
	// s.sync; // optionally: wait for samples to be read
	~dirt.start(57120, [0,0,0,0,0,0,0,0,0,0]);   // start listening on port 57120, create two busses each sending audio to channel 0

    ~dirt.startSendRMS;
};
s.latency = 0.3; // increase this if you get "late" messages
);

Editor integration

Two ideas really, but thought I'd put them together as maybe general discussion about editor integration would be nice
First is, shall we create ten or eleven orbits by default, and have each connection (d1..) go to a different orbit (again by default)?
Second, would it be possible for an editor to subscribe to an rms analysis of each orbit? For display in the editor next to active patterns

Cutoff behavior with negative numbers

I accidentally sent some negative numbers to cutoff. The behavior at values around -50 or less clip in an abrasive way & might be bypassing the built-in limiter? The clipping gets worse the more negative you go.

play at the below example at low volumes only!
Example:
d1 $ sound (samples "amencutup*8" $ run "8") # cutoff "<5000 2000 0 -10 -20 -50 -100>"

"ERROR: binary operator '+' failed." for multichannel (in this case 4 channels)

*** Welcome to SuperCollider 3.7alpha1. *** For help press Ctrl-D.
booting 57110
-> localhost
Found 0 LADSPA plugins
JackDriver: client name is 'SuperCollider'
SC_AudioDriver: sample rate = 44100.000000, driver's block size = 1024
JackDriver: connected  system:capture_1 to SuperCollider:in_1
JackDriver: connected  system:capture_2 to SuperCollider:in_2
JackDriver: connected  SuperCollider:out_1 to system:playback_1
JackDriver: connected  SuperCollider:out_2 to system:playback_2
SuperCollider 3 server ready.
JackDriver: max output latency 69.7 ms
Receiving notification messages from server localhost
Shared memory server interface initialized
loading synthdefs in /home/alex/Dropbox/quarks/SuperDirt/classes/../synths/core-modules.scd
ERROR: binary operator '+' failed.
RECEIVER:
   nil
ARGS:
Instance of Array {    (0x505dc58, gc=C0, fmt=01, flg=00, set=02)
  indexed slots [4]
      0 : instance of BinaryOpUGen (0x5ba8c08, size=9, set=4)
      1 : instance of BinaryOpUGen (0x5ba5f18, size=9, set=4)
      2 : instance of BinaryOpUGen (0x5ba4b38, size=9, set=4)
      3 : instance of BinaryOpUGen (0x5ba2ce8, size=9, set=4)
}
   nil
PATH: /home/alex/Dropbox/quarks/SuperDirt/classes/../synths/core-synths.scd

PROTECTED CALL STACK:
    Meta_MethodError:new    0x3c49b00
        arg this = BinaryOpFailureError
        arg what = nil
        arg receiver = nil
    Meta_DoesNotUnderstandError:new 0x3c4bac0
        arg this = BinaryOpFailureError
        arg receiver = nil
        arg selector = +
        arg args = [ [ a BinaryOpUGen, a BinaryOpUGen, a BinaryOpUGen, a BinaryOpUGen ], nil ]
    Object:performBinaryOpOnSomething   0x45ba9c0
        arg this = nil
        arg aSelector = +
        arg thing = [ a BinaryOpUGen, a BinaryOpUGen, a BinaryOpUGen, a BinaryOpUGen ]
        arg adverb = nil
    a FunctionDef   0x245da00
        sourceCode = "<an open Function>"
        arg elem = nil
    ArrayedCollection:do    0x247fe80
        arg this = [ [ an OutputProxy, an OutputProxy, an OutputProxy, an OutputProxy ], [ an OutputProxy, an OutputProxy, an OutputProxy, an OutputProxy ], nil, nil ]
        arg function = a Function
        var i = 2
    Collection:sum  0x245d1c0
        arg this = [ [ an OutputProxy, an OutputProxy, an OutputProxy, an OutputProxy ], [ an OutputProxy, an OutputProxy, an OutputProxy, an OutputProxy ], nil, nil ]
        arg function = nil
        var sum = [ a BinaryOpUGen, a BinaryOpUGen, a BinaryOpUGen, a BinaryOpUGen ]
    Meta_DirtPan:ar 0x41eb480
        arg this = DirtPan
        arg signal = [ an OutputProxy, an OutputProxy ]
        arg numChannels = 4
        arg pan = an OutputProxy
        arg mul = 1
        arg mix = false
        var output = [ [ an OutputProxy, an OutputProxy, an OutputProxy, an OutputProxy ], [ an OutputProxy, an OutputProxy, an OutputProxy, an OutputProxy ], nil, nil ]
        var mono = false
    a FunctionDef   0x52d2708
        sourceCode = "<an open Function>"
        arg out = an OutputProxy
        arg bufnum = an OutputProxy
        arg sustain = an OutputProxy
        arg begin = an OutputProxy
        arg speed = an OutputProxy
        arg endSpeed = an OutputProxy
        arg pan = an OutputProxy
        var sound = [ an OutputProxy, an OutputProxy ]
        var rate = a Line
        var phase = a BinaryOpUGen
    SynthDef:buildUgenGraph 0x494d180
        arg this = a SynthDef
        arg func = a Function
        arg rates = [ ir, ir, ir, ir, ir, ir, ir ]
        arg prependArgs = [  ]
        var result = nil
        var saveControlNames = nil
    a FunctionDef   0x493b580
        sourceCode = "<an open Function>"
    Function:prTry  0x39306c0
        arg this = a Function
        var result = nil
        var thread = a Routine
        var next = a Function
        var wasInProtectedFunc = true
    Function:protect    0x392fc40
        arg this = a Function
        arg handler = a Function
        var result = nil
    SynthDef:build  0x493b1c0
        arg this = a SynthDef
        arg ugenGraphFunc = a Function
        arg rates = [ ir, ir, ir, ir, ir, ir, ir ]
        arg prependArgs = nil
    a FunctionDef   0x52d3c58
        sourceCode = "<an open Function>"
        arg sampleNumChannels = 2
        var name = dirt_sample_2_4
    Number:forSeries    0x46e5440
        arg this = 1
        arg second = 1
        arg last = 2
        arg function = a Function
        var step = 2
        var j = 1
    a FunctionDef   0x53a5438
        sourceCode = "{
    var numChannels = ~dirt.numChannels;



    // write variants for different sample buffer sizes
    (1..SuperDirt.maxSampleNumChannels).do { |sampleNumChannels|

        var name = format(\"dirt_sample_%_%\", sampleNumChannels, numChannels);

        SynthDef(name, { |out, bufnum, sustain = 1, begin, speed = 1, endSpeed = 1, pan = 0|

            var sound, rate, phase;

            // playback speed
            rate = Line.kr(speed, endSpeed, sustain);

            // sample phase
            // BufSampleRate adjusts the rate if the sound file doesn...etc..."
        var numChannels = 4
    a FunctionDef   0x3fe4500
        sourceCode = "<an open Function>"
    Function:prTry  0x39306c0
        arg this = a Function
        var result = nil
        var thread = a Routine
        var next = a Function
        var wasInProtectedFunc = true
    Function:protect    0x392fc40
        arg this = a Function
        arg handler = a Function
        var result = nil
    Interpreter:executeFile 0x3fe3e80
        arg this = an Interpreter
        arg pathName = /home/alex/Dropbox/quarks/SuperDirt/classes/../synths/core-synths.scd
        arg args = nil
        var result = [  ]
        var saveExecutingPath = nil
    a FunctionDef   0x19d4ec0
        sourceCode = "<an open Function>"
    Function:prTry  0x39306c0
        arg this = a Function
        var result = nil
        var thread = a Routine
        var next = nil
        var wasInProtectedFunc = true

CALL STACK:
    DoesNotUnderstandError:reportError   0x4faa408
        arg this = <instance of BinaryOpFailureError>
    < closed FunctionDef >   0x1af5b18
        arg error = <instance of BinaryOpFailureError>
    Integer:forBy   0x4ceb698
        arg this = 0
        arg endval = 2
        arg stepval = 2
        arg function = <instance of Function>
        var i = 2
        var j = 1
    SequenceableCollection:pairsDo   0x556dbb8
        arg this = [*4]
        arg function = <instance of Function>
    Scheduler:seconds_   0x56d7608
        arg this = <instance of Scheduler>
        arg newSeconds = 79.440693975
    Meta_AppClock:tick   0x562c258
        arg this = <instance of Meta_AppClock>
        var saveClock = <instance of Meta_SystemClock>
    Process:tick   0x5627528
        arg this = <instance of Main>
^^ The preceding error dump is for ERROR: binary operator '+' failed.
RECEIVER: nil

`shape` > 1 bug

Repost from datamads:

Hi everyone

I noticed this problem when messing around with the Shape synth parameter and since I'm new to Tidal I do a lot of stupid shit like for example set the Shape param to 1.5 or something. But if I accidentaly do that, it'll crash the synth totally.

It's not a huge issue if you know what you're doing but could be a problem live if you by accident or lack of knowledge put a value higher than 1.0 into that one shape parameter. It doesn't do the same for other parameters with a 0.0-1.0 range (for example hcutoff) as far as I can see.

Here's a simple example that'll make your SuperDirt cry:

-- Keep this going so you'll hear when the synth crashes
d2 $ sound "hh*4"

--  Now, start this: it WON't crash the synth
d1 $ sound "bd"
# shape "0.5" 

--  But this will crash the synth
d1 $ sound "bd"
# shape "1.0" 

Failing multichannel output

I believe this may be related to a SuperCollider issue (see below) but I'd like to make an issue here in case I'm wrong or there's a workaround.

The problem arises when trying to use more than 2 output channels while also assigning different orbits to different channels. This necessitates the "long" startup method, something like (as a close-to-minimal example):

s.options.memSize = 8192 * 64; // increase this if you get "alloc failed" messages
s.options.numOutputBusChannels = 8;
s.waitForBoot {
    ~dirt = SuperDirt(8, s); 
    ~dirt.loadSoundFiles("/Users/bgold/tidal/samples/*"); // load samples (path can be passed in)
    s.sync; // wait for samples to be read
    ~dirt.start(57120, [0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15]);   // start listening on port 57120
};
);

This however results in a flood of messages: ERROR: Meta_Bus:audio: failed to get an audio bus allocated. numChannels: 8 server: localhost

This looks a lot like this issue: supercollider/supercollider#2758 which in turn I think was fixed by supercollider/supercollider#2761 somewhat after the 3.8.0 release. So this may resolve itself with the next SuperCollider release, but I haven't tested yet (by compiling devel from scratch), and meanwhile this is a pretty serious issue for anyone trying to use multichannel SuperDirt.

Conditionals in SuperDirt

Hi all,

As there's a refactor going on for Tidal, I thought it would be the right time to share this idea I've been experimenting with Tidal/SuperDirt/JS combo.

This allows to me receive Tidal parameters via SuperDirt to be forwarded to the stdout

f = { |msg, time, addr|
			if(msg[0] == '/play2') {
				"time: % sender: %\nmessage: %\n".postf(time, addr, msg);
			}
		};
		thisProcess.addOSCRecvFunc(f);

then I can parse the code do conditional triggers from Tidal like

let (trigLookup,trigLookup_p)  = pS "trigLookup" (Nothing)
    (trigEvery,trigEvery_p)  = pF "trigEvery" (Nothing)
    (trigSound,trigSound_p)  = pS "trigSound" (Nothing) 

d1 $ note "0 1" #s "synth" #trigLookup "0" #trigEvery "7" #trigSound  (pure "(type:\\dirt, orbit:0, s: \\303bass).play;")

then I can simply compile trigSound param within SuperColliderJS's sclang.

I find this to be a quite funky feature so I wonder if this can be supported within the SuperDirt to avoid any redundant latency caused by parsing and moving messages around

Specifying sample folders doesn't work

``~dirt.loadSoundFiles("/home/alex/Dropbox/projects/dirt/samples/");` (with or without the trailing slash) results in:

loading 1 sample bank:
samples (0) 
... file reading complete

the path exists without symlinks.. My workaround is to make a symlink from Dirt-Samples in the quarks folder to my sample folder, which works, so doesn't seem to be something about the folder itself.

lrwxrwxrwx  1 alex alex   41 Apr 16 20:16 Dirt-Samples -> /home/alex/Dropbox/projects/dirt/samples/

ERROR: class not defined when loading superdirt_start.scd

Hi. I am running

sclang superdirt_startup.scd

I expect that sc starts, so I can use tidal. But what actually happens is this

compiling class library...
Qt: Session management error: Could not open network socket
	Found 845 primitives.
	Compiling directory '/opt/supercollider/3.10.0/share/SuperCollider/SCClassLibrary'
	Compiling directory '/opt/supercollider/3.10.0/share/SuperCollider/Extensions'
	Compiling directory '/home/waldmann/.local/share/SuperCollider/Extensions'
	Compiling directory '/home/waldmann/.local/share/SuperCollider/downloaded-quarks/Vowel'
	numentries = 1257911 / 18817904 = 0.067
	5624 method selectors, 3346 classes
	method table size 20374728 bytes, big table size 150543232
	Number of Symbols 14675
	Byte Code Size 433421
	compiled 544 files in 1.42 seconds

Info: 4 methods are currently overwritten by extensions. To see which, execute:
MethodOverride.printAll

compile done
localhost : setting clientID to 0.
internal : setting clientID to 0.
Class tree inited in 0.01 seconds


*** Welcome to SuperCollider 3.10.0. *** For help type ctrl-c ctrl-h (Emacs) or :SChelp (vim) or ctrl-U (sced/gedit).
ERROR: Class not defined.
  in interpreted text
  line 17 char 18:

  	~dirt = SuperDirt(2, s); // two output channels, increase if you want to pan across more channels
                    
  	~dirt.loadSoundFiles;   // load samples (path containing a wildcard can be passed in)
-----------------------------------

Is the "Qt session management error" actually an error? I compiled sc without QT, which makes the message vanish, but does not change what follows.

MIDI note data dropout with SuperDirt MIDI

I'm getting pretty frequent MIDI note dropout with SuperDirt MIDI at the moment.

In trying to fix this, I set the scheduling priority for jackd and scsynth processes to FIFO priority 99, which seems to have no effect on the problem. I've also set my processor scheduling to performance, am running a real time kernel (AVLinux distro -- Debian based) and have a number of other audio performance optimisations applied.

I've tried with a few different MIDI targets to make sure that it's not an issue on the 'other end'.

Here's my startup file:

s.options.numBuffers = 4096 * 16;
s.options.memSize = 8192 * 16;
s.options.maxNodes = 1024 * 32;
s.options.device = "PreSonus AudioBox iTwo";
s.options.numOutputBusChannels = 16;
s.waitForBoot {
	~dirt = SuperDirt(2, s);
	// ~dirt.loadSoundFiles("/home/oscarsouth/dirt_samples/*");
	s.sync;
	~dirt.start(57120, [0,2,4,6,8]);
	MIDIClient.init;
	~midiOut = MIDIOut.newByName("PreSonus AudioBox iTwo", "PreSonus AudioBox iTwo MIDI 1");
	~latency = 0.05;
	~midiOut.latency = ~latency;
	~dirt.soundLibrary.addMIDI(\midi, ~midiOut);

I've recorded a clip of a generic drumbeat repeating for a few bars to give an example:
https://www.dropbox.com/s/n8u55vde1kmgtrv/Ch%201%20-%20120%20bpm%20-%20001-trimmed-converted.m4a?dl=0

function-hacks posts: instrument not found: nil

The example function-hacks, in the hacks directory, would be perfect for my case, but I'm guessing its outdated, isn't it?
Or maybe I don't understand what ~diversions is and I made something wrong.
I followed the step and I only could get the message in the title.

best regards,
Gil

'failed to get an audio bus allocated' with increased maxLogins/orbits

In order to request the RMS OSC, I increase the number of users with s.options.maxLogins = 8;. However if I do that, I get this error:

ERROR: Meta_Bus:audio: failed to get an audio bus allocated. numChannels: 2 server: localhost

The number of times that this error prints increases both with the number of orbits I add, and with the number of maxLogins.

develop branch now default?

I noticed a workshop attendee was running the 'develop' branch, without intending to. They were happy to have superdirt midi, but is it intended that the develop branch is installed by default?

single sample causes glitchy timing, audio artifacts

This particular sample causes SuperDirt to perform strangely on the develop and 1.0-dev branches (as of June 21 2018):

https://drive.google.com/open?id=1Xw-9wekJZQEshKrbeRIZdRDAEkYukYzW

Assuming this sample is in a folder named "cp_bad", this simple pattern playing this sample causes the problem: d1 $ s "cp_bad"

The problems I'm observing:

  1. Glitchy timing. The pattern's tempo fluctuates.
  2. Audio artifacts. After the main sample plays, there is a faint sound of glitchy, digital artifacts. Like a buffering sound or something. You can probably hear it if you wear headphones and turn up the volume.
  3. The SuperCollider console is spammed with these messages:
...
CheckBadValues: normal found in Synth 1000, ID 0 (previous 1 values were unknown)
CheckBadValues: unknown found in Synth 1000, ID 0 (previous 1 values were normal)
CheckBadValues: normal found in Synth 1000, ID 0 (previous 134 values were unknown)
CheckBadValues: unknown found in Synth 1000, ID 0 (previous 3 values were normal)
CheckBadValues: normal found in Synth 1000, ID 0 (previous 1 values were unknown)
CheckBadValues: unknown found in Synth 1000, ID 0 (previous 1 values were normal)
CheckBadValues: normal found in Synth 1000, ID 0 (previous 11 values were unknown)
CheckBadValues: unknown found in Synth 1000, ID 0 (previous 5 values were normal)
CheckBadValues: normal found in Synth 1000, ID 0 (previous 1 values were unknown)
CheckBadValues: unknown found in Synth 1000, ID 0 (previous 2 values were normal)
CheckBadValues: normal found in Synth 1000, ID 0 (previous 15 values were unknown)
CheckBadValues: unknown found in Synth 1000, ID 0 (previous 4 values were normal)
CheckBadValues: normal found in Synth 1000, ID 0 (previous 8 values were unknown)
CheckBadValues: unknown found in Synth 1000, ID 0 (previous 4 values were normal)
CheckBadValues: normal found in Synth 1000, ID 0 (previous 11 values were unknown)
CheckBadValues: unknown found in Synth 1000, ID 0 (previous 5 values were normal)
CheckBadValues: normal found in Synth 1000, ID 0 (previous 1 values were unknown)
CheckBadValues: unknown found in Synth 1000, ID 0 (previous 2 values were normal)
CheckBadValues: normal found in Synth 1000, ID 0 (previous 15 values were unknown)
CheckBadValues: unknown found in Synth 1000, ID 0 (previous 4 values were normal)
CheckBadValues: normal found in Synth 1000, ID 0 (previous 8 values were unknown)
CheckBadValues: unknown found in Synth 1000, ID 0 (previous 4 values were normal)
...

SuperDirt fails to start on Windows 10

Running include("SuperDirt") seems to work fine

Running SuperDirt.start consistently throws the below. Rebooting the interpreter has not effect

*** Welcome to SuperCollider 3.7.2. *** For help press Ctrl-D.
booting 57110
-> SuperDirt
Exception in World_New: boost::interprocess::intermodule_singleton initialization failed
RESULT = -1073740791
ERROR: server failed to start
For advice: [http://supercollider.sf.net/wiki/index.php/ERROR:_server_failed_to_start]

My specs

  • Windows 10
  • SuperCollider 3.7.2

strange behavior, seemingly `cut` related

Originally raised by kindohm on Slack, I've tried to reduce it to the most minimal example I can find using stock samples and explore what's going on. With 0.8 Tidal and SuperDirt, try the following code in Tidal:

d1
  $ stut 8 0.2 0.1
  $ jux (iter 8)
  $ stack[
    s "supersaw([3 5 3 2]/4,8)" # cut "1" # sustain "0.5",
    s "d*4 drum*2" # n (run 30),
    s "super808*8" # sustain "0.1"
  ]

hush

d1 $ sound "superpwm/2"

hush

Let the first (long) pattern play for a while... at some point I hear an audible glitch. Hush playback, and evaluate the second pattern. On stock 0.8 Tidal and SuperDirt I then hear a bunch of other sounds playing whenever the "superpwm" is triggered. This behavior lasts until SuperDirt is rebooted.

The cut parameter seems to be critical, I haven't found any odd behavior without it. Also the added-on stut and iter seem to be important too, I haven't managed to reproduce the behavior without those lines.

My guess is that something odd happens when too many events arrive to SuperDirt trying to cut each other simultaneously. It seems to also happen when non-sample-based synths using cut are combined with both samples and non-sample-based synths without cut, but that's been tricky to investigate.

Long samples and synths (not) being freed after envelope end

I've had some issues with superdirt when using long samples in tidal in conjunction with the envelope. Looking at the plot tree it seems it doesn't free the synth even after the envelope has ended (tested with #attack 0.5 # release 1 so quite modest envelope) which results in a buildup of cpu usage.

After looking at the source code for a while and trying different hacks I solved it by adding a doneAction: 14 to the EnvGen.ar ugen as is in the superdirt cut group ugen.

Posting my solution here because I suck at using github and don't know where else to put it, haha.

/****** FIXES PROBLEMS WITH NO RELEASE OF SYNTH GROUP ON LONG SAMPLES ****/ 
SynthDef("dirt_envelope" ++ numChannels, { |out, attack = 0, hold = 0, release = inf |
        var signal = In.ar(out, numChannels);
        signal = signal * EnvGen.ar(Env.linen(attack, hold, release, 1, -3), doneAction:14) // Added: doneAction: 14; // doneAction: 14 added to make sure synth is freed after envelope is done
        ReplaceOut.ar(out, signal);
    }, [\ir, \ir, \ir, \ir]).add;

leslie is stereo only

The global effects in SuperDirt all spread out to multiple channels. We still need a multichannel version of leslie.

Essentially it would mean to replace Balance2 by (a still fictional, but straightforward) BalanceAz UGen.

Routing external input through SuperDirt

Hey,

Is it possible to route hardware inputs through SuperDirt ecosystem? It would be interesting to use it alongside with superdirt-midi and apply various orbit-wise effects to midi patterns/channels

~d5 = ~dirt.orbits[4];
SynthDef(\ucx1, { arg in=0, amp = 1, out = ~d5.dryBus;
    var input;
    input = SoundIn.ar(in,2);
    input = input  * amp;
    OffsetOut.ar(out, DirtPan.ar(input, ~dirt.numChannels,amp));
}).play;

I also tried .outBus and didn't seem to work. any tips?

cheers!
C

A list of superdirt controls?

@kindohm is in the process of bringing documentation of all the superdirt controls (pan, gain, n, s etc) into the wiki:
https://userbase.tidalcycles.org/index.php/Category:SuperDirt_Functions

There are a lot of controls in Sound.Tidal.Params, including old midi ones etc, here's the long list:
https://userbase.tidalcycles.org/index.php/All_the_controls

It'd be good to rationalise this list as tidal's singular namespace is starting to get a bit busy.

Is there an official list of all the default superdirt params? If so we could the make a separate tidal module with those in, and make sure they're all properly documented in the wiki.

cut/orbit interaction bug

As noticed on Slack, when evaluating the following:

d1 $ gain "1 0 0 1 1 1 0 0 1 0 1 0 1 1 0 0" # sound "h:0" # cut "1"

d2 $ gain "1 0 0 0.9 0.9 0.9 0 0 0.9 0 0.9 0 0.9 0.9 0 0" # sound "k:4" # cut "2"

once the second line is evaluated, cut stops working properly on the first line. After some experimentation on my own, I could get the correct behavior, but only by explicitly setting d1 and d2 to different orbits. I've tested this on 0.9-dev, haven't checked prior versions yet.

sharing synth and using by superdirt

hi @telephon,

I'm having a little problem about sharing synth to used with superdirt, maybe you could give some guide on this

I'm using some custom server to sharing sc sytndef with my frined. We are using some like

SynthDef(\test, {
}).doSend(~hub)

and the hub forward msg to our client, and our client using s.listSendMsg(msg); to execute this, so we can both have the SynthDef test on both our machine.

But when we're using superdirt here, it seems not working. And we found it's trying to found syntndef from SynthDescLib, do you know any way to solve this somehow?

I think our client is getting the Int8Array here, not sure how to load that in SynthDescLib.

Again , thanks for hardwork on this!

let's sort out the panning scheme

There "stereo image" of a sample is lost when played in SuperDirt. For example, a sample that inherently contains right and left panning sounds like a "mono" sample without any panning in SuperDirt. Example:

https://soundcloud.com/kindohm/stereo-image-difference/s-Oh8f6

The above is a recording of the sample played in SuperDirt, then in Classic Dirt. The sample has a panning oscillation that should be audible in any audio player. In SuperDirt, it sounds like a "mono" sample that doesn't pan. In classic Dirt, the panning is audible.

'defaultParentEvent' not understood

This happens in 0.9-dev when no orbit output channel array was provided at startup, e.g. ~dirt.start(57120). The default is wrong.

Workaround: specify this value.

~dirt.start(57120, [0, 0]);

Accessing to a single SuperDirt instance/node

The idea is to control a synth from SuperCollider while using Tidal.
Usually in SC, I store Synth_ids to be able to change the parameters on the fly without having to re-allocate the voice. e.g syntharray[0].set(\coarse, 2);

Is there any way to access the synth_ids within the sclang?
If I can access globaleffect_ids, that would be super useful too.

dynamic used some sc buffer

Hi,
Just some idea came up recently, I want use some live recorded sc buffer in tidal.

For example if have a sc Buffer live recorded some stuff, like b1 = Buffer(), can I use this buffer directly in tidal? (maybe with some kind of registration on the dirt sound lib itself?)

~dirt.addSoundBuffer("buffer", b1)

and then I can

d1 $ sound "buffer * 3"

Not sure it's already possible or it's something will added soon, thanks!

"ERROR: Primitive '_FileWrite' failed" after installing SuperDirt

I have installed haskell and TidalCycles with Atom on my laptop with Windows 10.

I am using SuperCollider 3.9 and have installed SuperDirt using the Quarks GUI.

After installation I cannot run SuperDirt. Everytime I try SuperDirt.start I get this error message!

ERROR: Primitive '_FileWrite' failed.
Failed.
RECEIVER:
Instance of File {    (00000199F711C6F8, gc=A8, fmt=00, flg=00, set=02)
  instance variables [1]
    fileptr : nil
}

PROTECTED CALL STACK:
	Meta_MethodError:new	00000199F4678000
		arg this = PrimitiveFailedError
		arg what = Failed.
		arg receiver = a File
	Meta_PrimitiveFailedError:new	00000199F467E500
		arg this = PrimitiveFailedError
		arg receiver = a File
	Object:primitiveFailed	00000199F41B0D80
		arg this = a File
	UnixFILE:putAll	00000199F4EAFB00
		arg this = a File
		arg aCollection = docmap = {

	String:printOn	00000199F5306740
		arg this = docmap = {

		arg stream = a File
	IOStream:<<	00000199F4EAB700
		arg this = a File
		arg item = docmap = {

	Meta_SCDoc:exportDocMapJS	00000199F4560E40
		arg this = SCDoc
		arg path = C:\Users\Stefano\AppData\Local\SuperCollider\Help\docmap.js
		var f = a File
	Meta_SCDoc:indexAllDocuments	00000199F455BF40
		arg this = SCDoc
		arg clearCache = false
		var now = 3.1338962
		var key = Classes/String
		var doc = SCDocEntry("Classes/SynthDefOld", "SynthDefOld", "(Undocumented class)")
		var nonHelpFiles = [ [ C:\Program Files\SuperCollider-3.9.1\HelpSource\BrokenLink.html, BrokenLink.html ], [ C:\Program Files\SuperCollider-3.9.1\HelpSource\browse.css, browse.css ], [ C:\Program Files\SuperCollider-3.9.1\HelpSource\Browse.html, Browse.html ], [ C:\Program Files\SuperCollider-3.9.1\HelpSource\browse.js, browse.js ], [ C:\Program Files\SuperCollider-3.9.1\HelpSource\lang-sc.js, lang-sc.js ], [ C:\Program Files\SuperCollider-3.9.1\HelpSource\OldHelpWrapper.html, OldHelpWrapper.html ], [ C:\Program Files\SuperCo...etc...
		var undocClasses = IdentitySet[ QView, QWindow, HIDElementProtoDispatcher, QLevelIndicator, QDragView, ScaleAD, CoverMe, AbstractMDPlugin, Pstretch, FMGrainBBF, PmonoStream, CosineWarp, QSlider, QOrientation, QEnvelopeView, Pretty, PfadeIn, FFTSubbandFlux, TaskProxyAllGui, QKeyModifiers, MustBeBooleanError, ZHPF, QAbstractScroll, Rotate, BinaryOpXStream, PrimitiveFailedError, ItemViewBase, ClearBuf, StreamControl, WiiCalibrationInfo, BinaryOpFunctionProxy, Inspector, HIDElementDispatcher, PV_MagMulAdd, NotificationRegistratio...etc...
		var additions = Dictionary[ (Classes/String -> [ C:\Program Files\SuperCollider-3.9.1\HelpSource\Classes\String.ext.schelp ]) ]
	Meta_SCDoc:documents	00000199F455F780
		arg this = SCDoc
	Meta_SCDoc:prepareHelpForURL	00000199F45636C0
		arg this = SCDoc
		arg url = file:///C:/Users/Stefano/AppData/Local/SuperCollider/Help/Help.html
		var path = C:\Users\Stefano\AppData\Local\SuperCollider\Help\Help.html
		var targetBasePath = C:\Users\Stefano\AppData\Local\SuperCollider\Help
		var pathIsCaseInsensitive = true
		var subtarget = Help
		var src = nil
		var c = nil
		var cmd = nil
		var doc = nil
		var destExist = true
		var destMtime = 1521035096
		var verpath = C:\Users\Stefano\AppData\Local\SuperCollider\Help\version
	a FunctionDef	00000199F44C9380
		sourceCode = "<an open Function>"
	Function:prTry	00000199F48EA6C0
		arg this = a Function
		var result = nil
		var thread = a Routine
		var next = nil
		var wasInProtectedFunc = true
	
CALL STACK:
	MethodError:reportError
		arg this = <instance of PrimitiveFailedError>
	< closed FunctionDef >
		arg error = <instance of PrimitiveFailedError>
	Integer:forBy
		arg this = 0
		arg endval = 0
		arg stepval = 2
		arg function = <instance of Function>
		var i = 0
		var j = 0
	SequenceableCollection:pairsDo
		arg this = [*2]
		arg function = <instance of Function>
	Scheduler:seconds_
		arg this = <instance of Scheduler>
		arg newSeconds = 7.5610486
	Meta_AppClock:tick
		arg this = <instance of Meta_AppClock>
		var saveClock = <instance of Meta_SystemClock>
	Process:tick
		arg this = <instance of Main>
^^ The preceding error dump is for ERROR: Primitive '_FileWrite' failed.
Failed.
RECEIVER: a File


Do you know what could be the problem? It happens also when opening SuperCollider, while before installation of SuperDirt it was working properly.

SuperDirt not completing startup

SuperDirt will often (maybe 50% of time) not finish initialising. It seems to read in all the samples but then not come up with the message saying it's listening to Tidal. I have to close scide, make sure scsynth and sclang processes are killed then reload, usually it's fine the second time. From talking ot others this appears to be a common experience, cross-platform.

diversion is broken in master

In the old event-based branch, one could divert the incoming function call to do something else. A customising hack is in hacks/function-hacks.scd, this currently doesn't work.

cmd line startup fails

When calling "/Applications/.../SuperCollider.app/.../sclang" and passing in the tidal_startup.scd file, the sound samples load and then program crashes with "could not open udp port error". The same file executes as expected from IDE.

I should also mention that I have manually checked whether any of these ports were open, but they were free. Also, I am using 3.7alpha1.

ERROR: Could not open UDP port [ 57120, 57121, 57122, 57123, 57124, 57125, 57126, 57127, 57128, 57129 ]

PROTECTED CALL STACK:
    OSCFunc:init    0x10d3d4080
        arg this = OSCFunc(/play2, a NetAddr(127.0.0.1, nil), [ 57120, 57121, 57122, 57123, 57124, 57125, 57126, 57127, 57128, 57129 ], nil)
        arg argfunc = a Function
        arg argpath = /play2
        arg argsrcID = a NetAddr(127.0.0.1, nil)
        arg argrecvPort = [ 57120, 57121, 57122, 57123, 57124, 57125, 57126, 57127, 57128, 57129 ]
        arg argtemplate = nil
        arg argdisp = an OSCMessageDispatcher
    SuperDirt:connect   0x10baee580
        arg this = a SuperDirt
        arg argSenderAddr = a NetAddr(127.0.0.1, nil)
        arg argPort = [ 57120, 57121, 57122, 57123, 57124, 57125, 57126, 57127, 57128, 57129 ]
    SuperDirt:start 0x10bae5780
        arg this = a SuperDirt
        arg port = [ 57120, 57121, 57122, 57123, 57124, 57125, 57126, 57127, 57128, 57129 ]
        arg outBusses = 0
        arg senderAddr = a NetAddr(127.0.0.1, nil)
    Routine:prStart 0x10c91e980
        arg this = a Routine
        arg inval = 14.569675264

CALL STACK:
    Exception:reportError   0x10f878278
        arg this = <instance of Error>
    < closed FunctionDef >   0x10f8783d8
        arg error = <instance of Error>
    Integer:forBy   0x10fb968d8
        arg this = 0
        arg endval = 0
        arg stepval = 2
        arg function = <instance of Function>
        var i = 0
        var j = 0
    SequenceableCollection:pairsDo   0x10f87f338
        arg this = [*2]
        arg function = <instance of Function>
    Scheduler:seconds_   0x10f87f3e8
        arg this = <instance of Scheduler>
        arg newSeconds = 35.337763629
    Meta_AppClock:tick   0x10f87f548
        arg this = <instance of Meta_AppClock>
        var saveClock = <instance of Meta_SystemClock>
    Process:tick   0x10f87f5f8
        arg this = <instance of Main>
^^ The preceding error dump is for ERROR: Could not open UDP port [ 57120, 57121, 57122, 57123, 57124, 57125, 57126, 57127, 57128, 57129 ]

SuperDirt temporarily breaks on silence

If I run something like this: d1 $ sound "bd"

then stop it for a few seconds: d1 silence

then start it again: d1 $ sound "bd"

Nothing happens.. until about 10 or so seconds later there are glitches and it comes back again.

This problem appears to be local to the 'orbit'. As long as a sound is keeping a particular orbit 'alive' it's ok.

I noticed this a few days ago but assumed it was a hardware issue with the backup laptop I was using, but now several others have experienced the same kind of behaviour.

This looks related: 7b5d700

defining new synths with different envelope behavior

Suppose you want to define an instrument with built-in ADSR envelopes (as opposed to attack-hold-release envelope effect existing in SuperDirt). notes from this instrument should release when the sound ends. i.e. using legato of 1, each note releases as the next one starts.

It seems that when a sound ends according to its sustain, legato and cut parameters, it is immediately cut off with a very short fade and the synth destroyed, making such behavior impossible.

But sustain could be extended by a new release-time parameter. It seems to work with the following change to calcRange in DirtEvent.sc:

// sustain = ~sustain ?? { if(~legato.notNil) { ~delta * ~legato } { unitDuration } };
unitDuration= if(~legato.notNil) { ~delta * ~legato } { unitDuration };
unitDuration= if(~rel.notNil) { unitDuration+~rel } { unitDuration };
sustain = ~sustain ?? {unitDuration};

where rel is the new release-time parameter.

Now you can write a synth like:

SynthDef(\adsrsynth, { |out, att=0, dec=0, sus=0.5, rel=0, curve=0, sustain=1, pan, freq|
    var fadein = 0.001, fadeout = 0.003;
    var begin = Impulse.ar(0);
    var cut_env = EnvGen.ar(
        Env.asr(fadein, 1, fadeout, 1, -3),
        Trig.ar(begin, sustain-fadeout), doneAction:2);
    var sound_env = EnvGen.ar(
        Env.adsr(att, dec, sus, rel, 1, curve),
        Trig.ar(begin, sustain-rel));
    var sound = ...;
    OffsetOut.ar(out, DirtPan.ar(sound, ~dirt.numChannels, pan, cut_env))
}).add;

Am I missing some way to do this without altering SuperDirt? Or would there be interest in making a built-in parameter like this?

How to upgrade SuperDirt?

I think this has been brought up before but what's the proper process for upgrading SuperDirt via supercollider?

I tried all the buttons in Quarks.gui but none worked.. So I hastily created a v1.0 release in the SuperDirt repo (hope that's OK). After opening and closing supercollider a couple of times that appeared at an option and works..

But there's still a "LATEST" option that seems very old, I'm not sure how to get rid of that (and maybe the other old versions), or make it point at the real latest version.

Support multiple band pass filters

See discussion at tidalcycles/Tidal#233

It would be great to be able to do something like this in Tidal:

let eq = grp [
      cutoff_p, resonance_p,
      bandf_p, bandq_p,
      bandf_p, bandq_p,
      hcutoff_p, hresonance_p
      ]
...
let filter = "100 : 0.2 : 1000: 0.2 : 2000 : 0.2 : 5000: 0.2"
...
# eq filter

Currently you can do:

# bandf "[800, 1100, 1700, 1800]" # bandq 5

Tempo synced delay

Would it be possible/a good idea to have an option where delaytime is relative to cps?

Startup volume

Is there a way to set the volume in the startup file? I see there is a Volume object in SuperCollider, but I can't figure out how to use it.

amplitudes of global effects should not be global

To use delay as an example, my understanding of the current behavior is that all sounds get sent into the "dry" bus, which the delay effect processes, and the amount of output into the "wet" bus is scaled by the delay parameter. This means global effects are all-or-nothing in terms of the sounds they affect on each orbit.

While delaytime and delayfeedback are necessarily global parameters, what I'm proposing is that delay itself shouldn't have to be. In fact, I think most people would like to think of it as basically a "send" amount that can be changed for each sound. This is how it worked in Classic Dirt, but I think this is worth more than just backwards compatibility, it's a nice feature that people tend to expect based on how DAWs and analog systems work.

As a test case, if you fire up Classic Dirt and send this:

c1 $ sound "bd" # delay "1" # delayt "0.1" # delayfb "0.8"

c2 $ sound "~ cp ~ cp" # delay "0"

You'll hear that the claps don't interrupt or interefere with the echoing drum. But in SuperDirt this sounds rather different, because there as soon as the clap hits the delay output is clamped off (because delay is global).

I think this can be implemented without too much overhead in SuperDirt by having a "send" bus for each global effect. Then dirt_gate on each sound can use a local delay to scale the input into that bus, and finally the global delay unit reads from that bus, does the processing (using the global delaytime and delayfeedback), and outputs to the wet bus as normal. The same could be done with room for the reverb, and leslie for that effect.

My attempts to do this have failed in bizarre ways, however. It seems I don't understand how to set up the busses, and maybe I'm not thinking about this correctly. Any suggestions?

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.