Hi,
Has anyone implemented 'phasor time scaling' as an abstraction (or external)? I know it is relatively easy scale a phasor where the frequency of the scaled phasor is an integer multiple of the master phasor:
[phasor~] | [*~ 2] | [wrap~]
...but what about non-integer multiples, and fractional scaling?
Jamie
Hallo, Jamie Bullock hat gesagt: // Jamie Bullock wrote:
Has anyone implemented 'phasor time scaling' as an abstraction (or external)? I know it is relatively easy scale a phasor where the frequency of the scaled phasor is an integer multiple of the master phasor:
[phasor~] | [*~ 2] | [wrap~]
...but what about non-integer multiples, and fractional scaling?
A full phasor~ whose frequency is a non-integer multiple of the freq of another phasor~ will not start again at zero everytime, when the first phasor~ starts at zero. For example a phasor with 1.5 times the frequency of the first phasor~ would be in sync only every 3 cycles. So you cannot sync the second phasor with the first phasor on *every* jump of the first phasor with wrap~ ... without keeping track of where the second phasor is.
What you could do instead is calculate wrapped phasors from a very slow phasor like [phasor~ 1] as a base. All phasors derived from that will sync once every second.
Frank Barknecht _ ______footils.org__
Hi Frank,
On Sat, 2007-12-08 at 14:24 +0100, Frank Barknecht wrote:
Hallo, Jamie Bullock hat gesagt: // Jamie Bullock wrote:
Has anyone implemented 'phasor time scaling' as an abstraction (or external)? I know it is relatively easy scale a phasor where the frequency of the scaled phasor is an integer multiple of the master phasor:
[phasor~] | [*~ 2] | [wrap~]
...but what about non-integer multiples, and fractional scaling?
A full phasor~ whose frequency is a non-integer multiple of the freq of another phasor~ will not start again at zero everytime, when the first phasor~ starts at zero. For example a phasor with 1.5 times the frequency of the first phasor~ would be in sync only every 3 cycles. So you cannot sync the second phasor with the first phasor on *every* jump of the first phasor with wrap~ ... without keeping track of where the second phasor is.
Sure. I think you might have misunderstood the question. What I am asking relates to two things:
i) If you use the above technique to generate a phasor that has a frequency that is a non-integer multiple (e.g. 1.5) of the 'master' phasor, then you don't get a full phasor. For the 'scaled' phasor, every other peak will have an amplitude that is proportional to the size of the fractional part of the right operand of the multiplication (see attached).
ii) For 'scaled' phasors where the multiplier is less than 1, the result is simply an amplitude scaling (also see attached).
I guess all this is fairly obvious stuff, but my question is, how does one achieve proper non-integer rate scaling? The [rate~] object in Max/MSP does this so I know it is possible! I don't mind coding up and external for this if it can't be done in Pd, but I don't know what the algorithm for such an operation would be...
What you could do instead is calculate wrapped phasors from a very slow phasor like [phasor~ 1] as a base. All phasors derived from that will sync once every second.
What difference does it make how fast or slow the master phasor is? Surely it's only the ratio between the phasor rates we're interested in.
Jamie
Jamie Bullock a écrit :
Hi Frank,
On Sat, 2007-12-08 at 14:24 +0100, Frank Barknecht wrote:
Hallo, Jamie Bullock hat gesagt: // Jamie Bullock wrote:
Has anyone implemented 'phasor time scaling' as an abstraction (or external)? I know it is relatively easy scale a phasor where the frequency of the scaled phasor is an integer multiple of the master phasor:
[phasor~] | [*~ 2] | [wrap~]
...but what about non-integer multiples, and fractional scaling?
A full phasor~ whose frequency is a non-integer multiple of the freq of another phasor~ will not start again at zero everytime, when the first phasor~ starts at zero. For example a phasor with 1.5 times the frequency of the first phasor~ would be in sync only every 3 cycles. So you cannot sync the second phasor with the first phasor on *every* jump of the first phasor with wrap~ ... without keeping track of where the second phasor is.
Sure. I think you might have misunderstood the question. What I am asking relates to two things:
i) If you use the above technique to generate a phasor that has a frequency that is a non-integer multiple (e.g. 1.5) of the 'master' phasor, then you don't get a full phasor. For the 'scaled' phasor, every other peak will have an amplitude that is proportional to the size of the fractional part of the right operand of the multiplication (see attached).
ii) For 'scaled' phasors where the multiplier is less than 1, the result is simply an amplitude scaling (also see attached).
I guess all this is fairly obvious stuff, but my question is, how does one achieve proper non-integer rate scaling? The [rate~] object in Max/MSP does this so I know it is possible! I don't mind coding up and external for this if it can't be done in Pd, but I don't know what the algorithm for such an operation would be...
i think if the input can only be a phasor you can : -differenciate the phasor (with a biquad: out(t) = in(t) - in(t-1) ) -ignore negative value (with a test on a expr~ object by exemple) -multiply by scale factor -integrated this value (with a biquad: out(t) = in(t) + out(t-1) ) -wrap the result
cyrille
What you could do instead is calculate wrapped phasors from a very slow phasor like [phasor~ 1] as a base. All phasors derived from that will sync once every second.
What difference does it make how fast or slow the master phasor is? Surely it's only the ratio between the phasor rates we're interested in.
Jamie
PD-list@iem.at mailing list UNSUBSCRIBE and account-management -> http://lists.puredata.info/listinfo/pd-list
Hallo, cyrille henry hat gesagt: // cyrille henry wrote:
i think if the input can only be a phasor you can : -differenciate the phasor (with a biquad: out(t) = in(t) - in(t-1) ) -ignore negative value (with a test on a expr~ object by exemple) -multiply by scale factor -integrated this value (with a biquad: out(t) = in(t) + out(t-1) ) -wrap the result
I tested this (attached) and it kind of works, but it doesn't seem to be phase synced, so one could just as well use a second phasor~. Or did I do something wrong?
Frank Barknecht _ ______footils.org__
Frank Barknecht a écrit :
Hallo, cyrille henry hat gesagt: // cyrille henry wrote:
i think if the input can only be a phasor you can : -differenciate the phasor (with a biquad: out(t) = in(t) - in(t-1) ) -ignore negative value (with a test on a expr~ object by exemple) -multiply by scale factor -integrated this value (with a biquad: out(t) = in(t) + out(t-1) ) -wrap the result
I tested this (attached) and it kind of works, but it doesn't seem to be phase synced, so one could just as well use a second phasor~. Or did I do something wrong?
well, the max~ 0 is not the perfect way to remove negative value. it would be beter to replace the negative value with the previus value.
if you want exactly f1/f2 = 1.5, then you can use a lower frequency phasor and generated 2 phasor at 2f and 3f. so phasor 2 frequency / phasor 3 will be a 1.5.
if sync is important, this is certainly a better way to do it. but less generic, as you can't have f1/f2=pi...
cyrille
Ciao
PD-list@iem.at mailing list UNSUBSCRIBE and account-management -> http://lists.puredata.info/listinfo/pd-list
Hi Cyrille,
Thanks for the reply - very interesting!
On Sun, 2007-12-09 at 23:08 +0100, cyrille henry wrote:
i think if the input can only be a phasor you can : -differenciate the phasor (with a biquad: out(t) = in(t) - in(t-1) ) -ignore negative value (with a test on a expr~ object by exemple) -multiply by scale factor -integrated this value (with a biquad: out(t) = in(t) + out(t-1) ) -wrap the result
I tested this (attached) and it kind of works, but it doesn't seem to be phase synced, so one could just as well use a second phasor~. Or did I do something wrong?
well, the max~ 0 is not the perfect way to remove negative value. it would be beter to replace the negative value with the previus value.
Are you saying that if one replaced the negative value with the previous value, the phasors _would_ be phase synced? It would certainly be possible to do this if I implemented it as an external.
if you want exactly f1/f2 = 1.5, then you can use a lower frequency phasor and generated 2 phasor at 2f and 3f. so phasor 2 frequency / phasor 3 will be a 1.5.
In the short term, this 'low frequency master phasor' solution is the one I will go for, but it would be nice to make a generic phase-synchronous phasor rate scalor at some point. Maybe it isn't possible, but I'm sure it is what Max/MSP's rate does.
Jamie
Jamie Bullock wrote:
Hi Cyrille,
well, the max~ 0 is not the perfect way to remove negative value. it would be beter to replace the negative value with the previus value.
Are you saying that if one replaced the negative value with the previous value, the phasors _would_ be phase synced? It would certainly be possible to do this if I implemented it as an external.
It would sync if the [phasor~] doesn't change frequency, otherwise some other kind of extrapolation to replace the negative value would work.
Actually, if the [phasor~] is below the Nyquist frequency, shouldn't it be that you just add 1 to the negative value to get the correct positive increment?
An external is probably best, with a wrap~ built into the integration loop, because summing lots of tiny values to a large accumulator leads to rounding errors pretty quickly.
Thanks,
attached my version to this post. as far as i can tell it works ok.
basically the same as cyrille's idea..
input phasor~ is fed into a one sample delay [z~ 1]. then the difference between the delayed value and the current value is multiplied by samplerate. if the absolute difference between values is more than 0.5, then the signal is zeroed, to avoid clicks on the change of the original phasor.
not vanilla, but requires only zexy.
also, you can drive not only phasors, but any other oscillators with this too.
if you want to sync it, then just send a zero to the input phasor~ and output phasor~ at the same time.
Hallo, Jamie Bullock hat gesagt: // Jamie Bullock wrote:
Hi Frank,
On Sat, 2007-12-08 at 14:24 +0100, Frank Barknecht wrote:
Hallo, Jamie Bullock hat gesagt: // Jamie Bullock wrote:
Has anyone implemented 'phasor time scaling' as an abstraction (or external)? I know it is relatively easy scale a phasor where the frequency of the scaled phasor is an integer multiple of the master phasor:
[phasor~] | [*~ 2] | [wrap~]
...but what about non-integer multiples, and fractional scaling?
A full phasor~ whose frequency is a non-integer multiple of the freq of another phasor~ will not start again at zero everytime, when the first phasor~ starts at zero. For example a phasor with 1.5 times the frequency of the first phasor~ would be in sync only every 3 cycles. So you cannot sync the second phasor with the first phasor on *every* jump of the first phasor with wrap~ ... without keeping track of where the second phasor is.
Sure. I think you might have misunderstood the question.
That may well be. ;)
So to clarify:
Suppose I have a phasor with period p1 (and thus freq=1/p1) and I want to generate a signal with p2 = 1.5 * p1. Then I have (at least) two ways to do this ("|" should indicate the jumps):
p1: |.....|.....|.....|.....|.....|
p2a: |........|........|........|.... p2b: ......|........|........|........|....
Turn p1 and p2 around and you get a similar situation for trying to generate a phasor with a frequency of 1.5 times the original frequency:
p2: |........|........|........|....
p1a: |.....|.....|.....|.....|.....| p1b: ...|.....|.....|.....|.....|.....|
I suppose, you don't really care which sync point to use, only that both phasors sync at the least common multiple of their periods, right? That's where I suggested to use an additional phasor with a period of the LCM of the phasor signals you'd like to achieve in the end, and sync to that. (As the LCM of two numbers generally is larger than the single numbers, that phasor~ would be slower.)
Anyway, otherwise "something" would need to discern between jumps in the driving phasor that should and those jumps that should not trigger a jump in the resulting phasor signal. I think that's tricky: Where to get the needed info for "something"?
Frank Barknecht _ ______footils.org__
On Sun, 2007-12-09 at 18:53 +0100, Frank Barknecht wrote:
Suppose I have a phasor with period p1 (and thus freq=1/p1) and I want to generate a signal with p2 = 1.5 * p1. Then I have (at least) two ways to do this ("|" should indicate the jumps):
p1: |.....|.....|.....|.....|.....|
p2a: |........|........|........|.... p2b: ......|........|........|........|....
Turn p1 and p2 around and you get a similar situation for trying to generate a phasor with a frequency of 1.5 times the original frequency:
p2: |........|........|........|....
p1a: |.....|.....|.....|.....|.....| p1b: ...|.....|.....|.....|.....|.....|
I suppose, you don't really care which sync point to use, only that both phasors sync at the least common multiple of their periods, right? That's where I suggested to use an additional phasor with a period of the LCM of the phasor signals you'd like to achieve in the end, and sync to that. (As the LCM of two numbers generally is larger than the single numbers, that phasor~ would be slower.)
Ah, now I see what you're getting at. I think this is the solution I will probably go for, although I'm still curious to know how [rate~] works in Max/MSP. Maybe something along the lines of Cyrille's soluton...
Jamie