I am attempting to create an ambisonic encoder and decoder object set for MaxMSP5. Although I seem to have been able to create the objects I cannot get them to function correctly.

The main processing has been built into a DSP chain using the standard ‘svec’ process. The result however is distorted audio, which is apparently quite a difficult issue to resolve. The formulas used are:

‘

*out1 = *in1 * 1 / sqrt2

*out2 = *in1 * cos(A) * sin(E)

*out3 = *in1 * sin(A) * cos(E)

*out4 = *in1 * sin(E)

‘

As this is the most simple (first order, non velocity orientated) encoder I cannot seem to find an issue.

The decoder process is then set for ‘n’ speakers as:

‘

*Speaker = 1 / n * (*in1 / sqrt2 + *in2 *cos(A) * *cos(E) + *in3 * sin(A) * cos(E) + *in4 * sin(E))

‘

Where A is azimuth, E is elevation and n is number of speakers.

In order to do the encoding/decoding in real time will I need to implement a buffer system that is more advanced than svec?

Many thanks in advance, it is something I am really struggling with, any suggestions are extremely appreciated.

Thanks!!

]]>Any of the out pointers could be the same as your in1 vector, so when you write to them you may overwrite the input sample, then when you read from the input pointer again you get a different value. To solve this, read your input into a local variable before calculating .Like this:

float input_sample = *in1++;

*out1++ = input_sample * 1 / sqrt2;

*out2++ = input_sample * cos(A) * sin(E);

*out3++ = input_sample * sin(A) * cos(E);

*out4++ = input_sample * sin(E);

Likewise for the decoder example. What you’ve posted isn’t proper or full code though, so there could be other errors. I am assuming you are incrementing your pointers elsewhere correctly, and looping over the block/vector and that the other variables are valid and correct.

YOu should not need to implement your own buffer.

Hope this helps

Alex

]]>After implementing it into the code the ins/outs do seem to be more stable and more responsive in the MaxMSP environment, but unfortunately my decoder does not like having the ‘++’ units added to it’s equations.

Thanks again, you’re help is extremely appreciated, hopefully this will sort it, I’ll post again as soon as I’ve got a result.

:D

]]>Alex

]]>The equation used is the W,X,Y,Z,D to implement distance, but even with this removed I am receiving noise.

I have also attached the full C file in case I have left a strange error inside it, but other than some currently dormant ‘set’ messages there is little more to do with the actual encode process there.

Again I thank any suggestions or comments as I would simply love to get this working.

Thanks again for your help :D

void aambiencoderd_dsp(t_aambiencoderd *x, t_signal **sp, short *count)

{

dsp_add(aambiencoderd_perform, 7, sp[0]->s_vec, sp[1]->s_vec,

sp[2]->s_vec, sp[3]->s_vec, sp[4]->s_vec, sp[5]->s_vec, sp[0]->s_n);

}

/// 8.2 Actual Perform Funtion

t_int *aambiencoderd_perform(t_int *w)

{

t_float *in1 = (t_float *)(w[1]); //// Defining Inputs

t_float *out1 = (t_float *)(w[2]); //// Defining Outputs

t_float *out2 = (t_float *)(w[3]);

t_float *out3 = (t_float *)(w[4]);

t_float *out4 = (t_float *)(w[5]);

t_float *out5 = (t_float *)(w[6]);

int n = (int)w[7];

float input_1 = *in1++;

while (n–) //// Function is Active With DSP

*out1++ = input_1 * 1 / sqrt(2); //// Equation 1

*out2++ = input_1 * cos(0.0) * cos(0.0) * sin(1.0); //// Equation 2

*out3++ = input_1 * sin(0.0) * cos(0.0) * sin(1.0); //// Equation 3

*out4++ = input_1 * sin(0.0) * sin(1.0); //// Equation 4

*out5++ = input_1 * cos(0.0); //// Equation 5

return w + 8; //// Return Value is One Above DSP Links to Prevent Crashes

}

input_1 = *in1++

is not inside your while loop. So that means it is only assigned/incremented once per vector rather than for every single sample. Is this the problem?

HTH,

Tim

Does anyone know if there are ways of actually splitting the input from one channel into four to process it separately, rather than use a store and recall system, or would this be likely to result in the same issue?

Thanks again for your help with this.

int n = (int)w[7];

float input_1 = *in1++;

while (n–) //// Function is Active With DSP

input_1 = *in1++;

*out1++ = input_1 * 1 / sqrt(2); //// Equation 1

*out2++ = input_1 * cos(0.0) * cos(0.0) * sin(1.0); //// Equation 2

*out3++ = input_1 * sin(0.0) * cos(0.0) * sin(1.0); //// Equation 3

*out4++ = input_1 * sin(0.0) * sin(1.0); //// Equation 4

*out5++ = input_1 * cos(0.0); //// Equation 5

return w + 8; //// Return Value is One Above DSP Links to Prevent Crashes

}

try this:

int n = (int)w[7];

float input_1; ///< --- no need to assign a value yet

while (n–) //// Function is Active With DSP

{ /// < ------------- dsp loop begin

input_1 = *in1++;

*out1++ = input_1 * 1 / sqrt(2); //// Equation 1

*out2++ = input_1 * cos(0.0) * cos(0.0) * sin(1.0); //// Equation 2

*out3++ = input_1 * sin(0.0) * cos(0.0) * sin(1.0); //// Equation 3

*out4++ = input_1 * sin(0.0) * sin(1.0); //// Equation 4

*out5++ = input_1 * cos(0.0); //// Equation 5

} /// < -------- dsp loop end

return w + 8; //// Return Value is One Above DSP Links to Prevent Crashes

}

I will update my decoder with my new gained knowledge and and just drop a post in when it is finished, but I have every confidence now that the encoder is performing correctly. Thanks again. I can simply not express my gratitude enough.

]]>