90-second limit on audio buffers?
internally phasor~ uses something like 32-bit fixed-point. So the comparative error is really introduced when multiplying by the buffer size I guess.
Also looking at what I think is the Phasor code, it looks to me like it outputs 64-bit doubles.. https://github.com/supercollider/supercollider/blob/137cb4cd56f5bdf4484c9ad6761d4724dc8d7818/server/plugins/TriggerUGens.cpp#L134
I think the difference is that the output of Phasor is already scaled and output as a 64-bit value before being converted to 32-bit whereas when using phasor~ it is output as 32-bit and also scaled from range 0-1 as a 32-bit by multiplying by buffer size
If there were a Phasor equivalent in pd it might be comparable..
(and that also seems to be the case if [rpole~]
gives similar results)
[vline~]
should work as well
ofelia on raspberry pi?
Hi,
I am trying to get ofelia to run on a couple of rpi. Right now I am trying a rpi 3B+ running https://blokas.io/patchbox-os/
I run ofeila with the ofelia-fast-prototyping abs on my mac successfully.
Following install instructions here https://github.com/cuinjune/Ofelia
after running
sudo ./install_dependencies.sh
it ends like this:
detected Raspberry Pi
installing gstreamer omx
Reading package lists... Done
Building dependency tree... Done
Reading state information... Done
gstreamer1.0-omx is already the newest version (1.0.0.1-0+rpi12+jessiepmg).
The following package was automatically installed and is no longer required:
raspinfo
Use 'sudo apt autoremove' to remove it.
0 upgraded, 0 newly installed, 0 to remove and 0 not upgraded.
Updating ofxOpenCV to use openCV4
sed: can't read /home/patch/Documents/Pd/externals/addons/ofxOpenCv/addon_config.mk: No such file or directory
sed: can't read /home/patch/Documents/Pd/externals/addons/ofxOpenCv/addon_config.mk: No such file or directory
When running the example patches in Pd I get this in PD console:
opened alsa MIDI client 130 in:1 out:1
JACK: cannot connect input ports system:midi_capture_1 -> pure_data:input_2
/home/patch/Documents/Pd/externals/ofelia/ofelia.l_arm: libboost_filesystem.so.1.67.0: cannot open shared object file: No such file or directory
ofelia d $0-of
... couldn't create
/home/patch/Documents/Pd/externals/ofelia/ofelia.l_arm: libboost_filesystem.so.1.67.0: cannot open shared object file: No such file or directory
ofelia d $0-of
... couldn't create
/home/patch/Documents/Pd/externals/ofelia/ofelia.l_arm: libboost_filesystem.so.1.67.0: cannot open shared object file: No such file or directory
ofelia d $0-of
... couldn't create
/home/patch/Documents/Pd/externals/ofelia/ofelia.l_arm: libboost_filesystem.so.1.67.0: cannot open shared object file: No such file or directory
ofelia d $0-of
... couldn't create
/home/patch/Documents/Pd/externals/ofelia/ofelia.l_arm: libboost_filesystem.so.1.67.0: cannot open shared object file: No such file or directory
ofelia d $0-of
... couldn't create
/home/patch/Documents/Pd/externals/ofelia/ofelia.l_arm: libboost_filesystem.so.1.67.0: cannot open shared object file: No such file or directory
ofelia f ;
ofBackground(20) ;
ofSetSmoothLighting(true) ;
ofSetSphereResolution(24) ;
local width , height = ofGetWidth() * 0.12 , ofGetHeight() * 0.12 ;
sphere = ofSpherePrimitive() ;
sphere:setRadius(width) ;
icoSphere = ofIcoSpherePrimitive() ;
icoSphere:setRadius(width) ;
plane = ofPlanePrimitive() ;
plane:set(width * 1.5 , height * 1.5) ;
cylinder = ofCylinderPrimitive() ;
cylinder:set(width * 0.7 , height * 2.2) ;
cone = ofConePrimitive() ;
cone:set(width * 0.75 , height * 2.2) ;
box = ofBoxPrimitive() ;
box:set(width * 1.25) ;
local screenWidth , screenHeight = ofGetWidth() , ofGetHeight() ;
plane:setPosition(screenWidth * 0.2 , screenHeight * 0.25 , 0) ;
box:setPosition(screenWidth * 0.5 , screenHeight * 0.25 , 0) ;
sphere:setPosition(screenWidth * 0.8 , screenHeight * 0.25 , 0) ;
icoSphere:setPosition(screenWidth * 0.2 , screenHeight * 0.75 , 0) ;
cylinder:setPosition(screenWidth * 0.5 , screenHeight * 0.75 , 0) ;
cone:setPosition(screenWidth * 0.8 , screenHeight * 0.75 , 0) ;
pointLight = ofLight() ;
pointLight:setPointLight() ;
pointLight:setDiffuseColor(ofFloatColor(0.85 , 0.85 , 0.55)) ;
pointLight:setSpecularColor(ofFloatColor(1 , 1 , 1)) ;
pointLight2 = ofLight() ;
pointLight2:setPointLight() ;
pointLight2:setDiffuseColor(ofFloatColor(238 / 255 , 57 / 255 , 135 / 255)) ;
pointLight2:setSpecularColor(ofFloatColor(0.8 , 0.8 , 0.9)) ;
pointLight3 = ofLight() ;
pointLight3:setPointLight() ;
pointLight3:setDiffuseColor(ofFloatColor(19 / 255 , 94 / 255 , 77 / 255)) ;
pointLight3:setSpecularColor(ofFloatColor(18 / 255 , 150 / 255 , 135 / 255)) ;
material = ofMaterial() ;
material:setShininess(120) ;
material:setSpecularColor(ofFloatColor(1 , 1 , 1)) ;
... couldn't create
/home/patch/Documents/Pd/externals/ofelia/ofelia.l_arm: libboost_filesystem.so.1.67.0: cannot open shared object file: No such file or directory
ofelia f ;
pointLight = nil ;
pointLight2 = nil ;
pointLight3 = nil ;
collectgarbage() ;
... couldn't create
/home/patch/Documents/Pd/externals/ofelia/ofelia.l_arm: libboost_filesystem.so.1.67.0: cannot open shared object file: No such file or directory
ofelia f ;
local width , height , time = ofGetWidth() , ofGetHeight() , ofGetElapsedTimef() ;
pointLight:setPosition((width * 0.5) + math.cos(time * 0.5) * (width * 0.3) , height / 2 , 500) ;
pointLight2:setPosition((width * 0.5) + math.cos(time * 0.15) * (width * 0.3) , height * 0.5 + math.sin(time * 0.7) * height , -300) ;
pointLight3:setPosition(math.cos(time * 1.5) * width * 0.5 , math.sin(time * 1.5) * width * 0.5 , math.cos(time * 0.2) * width) ;
... couldn't create
/home/patch/Documents/Pd/externals/ofelia/ofelia.l_arm: libboost_filesystem.so.1.67.0: cannot open shared object file: No such file or directory
ofelia f ;
local spinX = math.sin(ofGetElapsedTimef() * 0.35) ;
local spinY = math.cos(ofGetElapsedTimef() * 0.075) ;
ofEnableDepthTest() ;
ofEnableLighting() ;
pointLight:enable() ;
pointLight2:enable() ;
pointLight3:enable() ;
material:beginMaterial() ;
plane:rotateDeg(spinX , 1 , 0 , 0) ;
plane:rotateDeg(spinY , 0 , 1 , 0) ;
plane:draw() ;
box:rotateDeg(spinX , 1 , 0 , 0) ;
box:rotateDeg(spinY , 0 , 1 , 0) ;
box:draw() ;
sphere:rotateDeg(spinX , 1 , 0 , 0) ;
sphere:rotateDeg(spinY , 0 , 1 , 0) ;
sphere:draw() ;
icoSphere:rotateDeg(spinX , 1 , 0 , 0) ;
icoSphere:rotateDeg(spinY , 0 , 1 , 0) ;
icoSphere:draw() ;
cylinder:rotateDeg(spinX , 1 , 0 , 0) ;
cylinder:rotateDeg(spinY , 0 , 1 , 0) ;
cylinder:draw() ;
cone:rotateDeg(spinX , 1 , 0 , 0) ;
cone:rotateDeg(spinY , 0 , 1 , 0) ;
cone:draw() ;
material:endMaterial() ;
ofDisableLighting() ;
ofDisableDepthTest() ;
... couldn't create
Thankful for help!
Controlling ramp time
Hi all, beginner here.
I'm trying to find a way to simultaneously modulate my METRO time and the ramp time of my LINE. I tried to crudely illustrate that concept in the red line drawing on my patch.
What I have here is
- METRO sends regular pulses to RANDOM
- with each pulse RANDOM chooses a random value
- values ramp from one to the next via LINE
- LINE passes values to NUMBER
- NUMBER passes values to PHASOR~ as frequency values
I want to be able to use one control that overrides the METRO time with a value that simultaneously becomes my LINE's ramp time. So when METRO is 1000ms, LINE ramp time is also 1000ms; when METRO is 750ms, LINE ramp time is also 750ms, etc.
Any insights on how to patch this up? Thank you!
maths regarding conversion from metro speed to pitch
Another approach is to design the implementation around the requirement.
You want to be able to produce a specific frequency. So... make frequency the input parameter, rather than metro time interval.
You want to step through array values, with an equal amount of time for each. That suggests a linear ramp, with a given frequency... i.e., phasor~.
phasor~ always goes 0.0 - 1.0. With 12 points, the array indices go 0.0 - 11 -- but here, note that if you say 0.0 - 11.0, then index 0 covers a span of 1, but index 11 covers a span of 0! That doesn't sound right. Instead, define the span for each index as i <= x < (i+1) -- inclusive at the bottom, exclusive at the top. Now the entire range is 0 <= x < 12... leading to the idea of multiplying the phasor by 12 (number of points).
The array indexing should truncate away any fractional part: if (phasor * 12) = 3.546, it should just read 3. Fortunately, this is the normal behavior of tabread~ (not tabread4~).
So we can get a sample-and-hold waveform this way. (The third array is just showing the floor-ed indices, to demonstrate that tabread~ really is truncating rather than rounding.)
All that's left is to add linear interpolation. A standard way to do linear interpolation is:
x = crossfade factor (0.0 - 1.0)
a = value when x = 0
b = value when x = 1
xfade = (b-a) * x + a (this is a reduction of (a * (1-x)) + (b * x)
).
If i is the index, then a = array "at" i, and b = array "at" i+1 -- but here, b needs to be modulo-wrapped back around, because i+1 could be 12-point-something. Pd vanilla doesn't have [%~] at signal rate, but [expr~] has fmod().
So we can index the two values, subtract, multiply by the crossfade factor (which is phasor * 12 --> wrap~), then add the "array[i]" value back in.
Now you can do whatever frequency you want, without the awkward conversion. Doesn't matter what that online tutorial said, IMO this fits the stated requirement better.
hjh
Question about [tabread4~]
I would test Pd by recording a few seconds of [phasor~ 1], and measuring the number of samples per cycle. Obviously this should be the system sample rate, give or take floating point rounding error.
The worry in this thread is that Pd is playing at the wrong speed.
The only way this could happen is if [phasor~ 1] is running at the wrong speed, because in the demo patch, phasor~ is the only thing controlling the speed.
Therefore, if there is no evidence of phasor~ running at the wrong speed, then Pd must be playing the file at the true speed!
"But what if the system sample rate differs from the file's?" The file is at the lowest sample rate in common use. If Pd is playing it slower than Audacity, then Pd would have to be running below 44.1 kHz, which is unlikely to be supported in hardware. So I'm comfortable ruling that out (not to mention that scaling the phasor~ by the file's number of samples already accounts for this). Common scenario would be: 44.1 kHz file, 48 kHz system SR, without correcting for this then Pd would play faster, but that isn't the report.
is audacity running at 44100?
I'm pretty sure Audacity has no power to override the hardware sample rate. I've never heard of soundcards issuing separate, per-app interrupts at different rates (imagine how difficult that would be, to make it work, highly implausible). AFAIK Audacity does sample rate conversion when the file is at a different rate from the hardware... just like all other audio software.
Is it 100% guaranteed that Audacity is playing it at the right speed?
hjh
[SOLVED]small granular patch. how to reset to start
@KMETE If you stop the [metro] then the cloned players will eventually stop as the [ine~] objects reach their "end".
A reset of the [phasor~] by a 0 to its right inlet will restart the [phasor~] at 0 .... but [phasor~] is always running at its set rate.
So you need to send the 0 to [phasor~] and bang the [snapshot~] immediately afterwards......but only once your time "x" has elapsed.
In your patch that should start the "next" clone at the start of the array.
David.
looper overdubbing not lining up.....
Hey @whale-av and anyone else interested in this issue.
I'm still trying to wrap my head around this.
So this looper works if you loop one pass and play it. It works with overdubbing at speed = 1 or -1.. The problem is if you overdub at any speed other than 1 or -1.
I am going to explain the issue as I see it, although I may be mistaken. It is set up so the buffer length will not change after the first recording, so when overdubbing the buffer size doesn't change. If you doing playback at a speed other than 1 or -1 the speed of the phasor~ reading the array with the loop will change to that new speed. When you are done overdubbing, it would seem that the phasor~ should be at the same speed it was during the overdub, but if this is the case things get out of whack. At least that was my observation in the "simple3.pd" patch a few posts up.
I added an [expr] object to try and accomodate for what I was hearing. But now what is happening is it seems that the loop is getting shorter if it is less than 1 and it's too long if it's greater than 1.
I must be missing something obvious here.
I haven't tried this yet, but maybe I should add another phasor~ that is lined up to start with the first phasor~ playing the array, but when I alter playback speed this 2nd phasor will change as well and i can use that to start and stop the overdub process. What I am hearing is the overdub, when playing at speed = 2, will double in speed , then double in speed again during a recording. and the opposite is true for half speed. I think maybe a 2nd phasor can modulate to the new speed when an overdub is activated then take over reading the array when an overdub is finished. It's just an idea I had.
Anyway, any suggestions into this would be much appreciated.
Here is what I have now. simple6.pd
Thank you.
Polyrytm , dividing master metro
@gentleclockdivider Does sending a start at the same time to the [metro] left inlet help?
Between the green [/ 3] and the left inlet of the blue [metro] put the message [1 $1(
The parts of the message are distributed across the inlets of the [metro] so you know it gets them at the same time.
Disconnect the direct cord between [/ 3] and the right inlet of the [metro] of course.
When you say... "out of sync" ..... out of sync with the red [metro]..?
You might need to do the same for both?
David.
Polyrytm , dividing master metro
I am having some issues here with automating the tempo of second metro (denominator )
The structure is pretty simple
There are 2 metro objects , a red and a blue one
The red one (bottom left corner and left channel ) is triggering a sine , the blue metro is triggering another sine ( bottom right right channel).
Both are using a curve envelope ( cyclone )
The master tempo is located at the top , default is 90 bpm
This goes into a tbf , the float is first send to he right inlet of a division , then the bang is triggering a message of 60000 ms
The result is the time of a beat (one minute divided by BPM) .
It all works fine when disabling-enabling mast toggle but that's not what I want.
Now the issue , the purple and orange boxes all house different denomitor values , used to calculate the new tempo for the second metro ( blue right channel )
When manually triggered these go into a tff , the right outlet of tff goes into a division modue ( green box) and the left output
is trigerring a bang to redo the calculation .
As some of you have guessed , when doing this realtime the second metro is losing sync because of the recalculation .
I tried to automate this ( yellow box, enable spigot ) by sending a bang from the master RED metro into a count-selet module , the ouput is triggering new
denominator values that is send to the tff module (using send receive boxes ) , but again Blue metro is not starting on sync .
Anyone help is appreciated to keep blue metro on sync when receiving a new value .
get phase of [osc~]
[phasor~]
|
[cos~]
should be the same as
[osc~]
but this time I need to measure the phase of [osc~]
and do the same as
with [osc~] instead of [phasor~].
I have a running patch, but sometimes it flips the phase by 180 degrees.
Do you know why or how to avoid that?
Here is the patch:
phase_of_normalized_cosine~.pd
The patch calculates the phase of a normalized cosine y(x) by
asin(y(x)) / (pi/2)
this is a triangle wave, following cosine's shape linearized.
Then a tri-to-saw waveshper:
invert the falling part of the triangle
and divide it's frequency by 2.
late EDIT: also read this: https://forum.pdpatchrepo.info/topic/15128/snapshotting-and-restoring-the-state-of-a-phasor-exactly