Re: Using MapAt with Play
- To: mathgroup at smc.vnet.net
- Subject: [mg113899] Re: Using MapAt with Play
- From: Albert Retey <awnl at gmx-topmail.de>
- Date: Wed, 17 Nov 2010 05:31:05 -0500 (EST)
- References: <ibr391$8vi$1@smc.vnet.net> <ibtku8$5gt$1@smc.vnet.net> <ibtp28$8ni$1@smc.vnet.net>
Am 16.11.2010 12:14, schrieb BenT: > On Nov 16, 4:03 am, Albert Retey <a... at gmx-topmail.de> wrote: >> Am 15.11.2010 11:50, schrieb BenT: >> >> >> >> >> >>> Using Mathematica 7, please consider this code: >> >>> Play[{Sin[440 t 2 Pi], Sin[441 t 2 Pi]}, {t, 0, 1}, >>> SampleRate -> 44100, SampleDepth -> 16] >> >>> which works as intended. >> >>> But now attempting to use the MapAt function, >> >>> p = {440, 550, 660, 770, 880}; >>> Play[{Sin[# t 2 Pi], Sin[(# + 1) t 2 Pi] &} /@ p, {t, 0, 1}, >>> SampleRate -> 44100, SampleDepth -> 16] >> >>> I get the following error coding: >> >>> During evaluation of In[28]:= Sound::ssnm: A good PlayRange could not >>> be found since most of the samples are not evaluating to machine-size >>> real numbers. >> >> >>> Out[28]= Sound[ >>> SampledSoundFunction[ >>> Function[{Play`Time37}, >>> Block[{t = >>> 0. + 0.0000226757 Play`Time37}, ({Sin[#1 t 2 \[Pi]], >>> Sin[(#1 + 1) t 2 \[Pi]] &} /@ p + 0.) 1.]], >>> 44100, {44100, 16}]] >> >>> Can anyone tell me how to "correct" the problem? The intent is to >>> "automate" the playback of several "paired" pitches. >> >> There seem to be three problems with your code: >> 1) the pure function termination is at the wrong place >> 2) Play doesn't like the list of list, so I Flatten the resulting list >> of lists >> 3) Play has attribute HoldAll, so we need to Evaluate to enforce the >> evaluation. >> >> Honestly my impression is that Play has some problems handling input >> that it doesn't accept, my Kernel died a few times when experimenting >> with it... >> >> The follwing works, although I doubt it does what you intended (it plays >> on 10 channels.): >> >> p = {440, 550, 660, 770, 880}; >> >> Play[ >> Evaluate[Flatten[{Sin[# t 2 Pi], Sin[(# + 1) t 2 Pi]} & /@ p]], >> {t, 0, 1}, SampleRate -> 44100, SampleDepth -> 16 >> ] >> >> Maybe this is closer to what you want? It adds up the signals instead of >> playing them on different channels... >> >> Play[ >> Evaluate[ >> Plus @@ Flatten[{Sin[# t 2 Pi], Sin[(# + 1) t 2 Pi]} & /@ p]], >> {t, 0, 1}, SampleRate -> 44100, SampleDepth -> 16 >> ] >> >> hth, >> >> albert- Hide quoted text - >> >> - Show quoted text - > > No, I want consecutive note playback for one second _each_, not > simulataneous. The use of two of more channels is not important. > Summing works fine, as the effect I want is an example of chorusing. > For example (although this code _still_ doesn't work!): > > p = {440, 550, 660, 770, 880}; > Play[{N[Sin[# t 2 Pi] + Sin[(# + 1) t 2 Pi]]} & /@ p, {t, 0, 1}, > SampleRate -> 44100, SampleDepth -> 16] > > I'm (still) getting the error: > > Sound::ssnm: A good PlayRange could not be found since most of the > samples are not evaluating to machine-size real numbers. >> > > What can be done to correct this? I'm still not sure if I understood correctly what you try to achieve, but here is another try: notes = {440, 550, 440, 770, 660}; Show[Map[Play[#, {t, 0, 0.5}] &, Plus[N[Sin[# t 2 Pi] + Sin[(# + 300) t 2 Pi]]] & /@ notes]] this makes use of the fact that a Show of a list of Plays obviously joins them to one Sound object. I have also increased the difference of the two frequencies, otherwise you will only see a beat effect but not something that sounds like two voices. The code above works on my machine, but honestly, I would be disappointed by that chorus :-) hth, albert