giuliomoro@94
|
1 #include <BeagleRT.h>
|
giuliomoro@94
|
2 #include <Scope.h>
|
giuliomoro@94
|
3 #include <cmath>
|
giuliomoro@94
|
4
|
giuliomoro@94
|
5 float gPhase1, gPhase2;
|
giuliomoro@94
|
6 float gFrequency1, gFrequency2;
|
giuliomoro@94
|
7 float gInverseSampleRate;
|
giuliomoro@94
|
8
|
giuliomoro@109
|
9 Scope scope(1); //create a scope object with numChannels
|
giuliomoro@94
|
10
|
giuliomoro@94
|
11 // initialise_render() is called once before the audio rendering starts.
|
giuliomoro@94
|
12 // Use it to perform any initialisation and allocation which is dependent
|
giuliomoro@94
|
13 // on the period size or sample rate.
|
giuliomoro@94
|
14 //
|
giuliomoro@94
|
15 // userData holds an opaque pointer to a data structure that was passed
|
giuliomoro@94
|
16 // in from the call to initAudio().
|
giuliomoro@94
|
17 //
|
giuliomoro@94
|
18 // Return true on success; returning false halts the program.
|
giuliomoro@94
|
19 bool setup(BeagleRTContext *context, void *userData)
|
giuliomoro@94
|
20 {
|
giuliomoro@94
|
21 scope.setup(context->audioSampleRate); //call this once in setup to initialise the scope
|
giuliomoro@94
|
22
|
giuliomoro@94
|
23 gInverseSampleRate = 1.0/context->audioSampleRate;
|
giuliomoro@94
|
24
|
giuliomoro@94
|
25 gPhase1 = 0.0;
|
giuliomoro@94
|
26 gPhase2 = 0.0;
|
giuliomoro@94
|
27
|
giuliomoro@94
|
28 gFrequency1 = 200.0;
|
giuliomoro@94
|
29 gFrequency2 = 201.0;
|
giuliomoro@94
|
30 return true;
|
giuliomoro@94
|
31 }
|
giuliomoro@94
|
32
|
giuliomoro@94
|
33 // render() is called regularly at the highest priority by the audio engine.
|
giuliomoro@94
|
34 // Input and output are given from the audio hardware and the other
|
giuliomoro@94
|
35 // ADCs and DACs (if available). If only audio is available, numMatrixFrames
|
giuliomoro@94
|
36 // will be 0.
|
giuliomoro@94
|
37
|
giuliomoro@94
|
38 void render(BeagleRTContext *context, void *userData)
|
giuliomoro@94
|
39 {
|
giuliomoro@109
|
40 static int count=0;
|
giuliomoro@94
|
41 for(unsigned int n = 0; n < context->audioFrames; n++) {
|
giuliomoro@94
|
42
|
giuliomoro@109
|
43 float chn1 = sinf(gPhase1);
|
giuliomoro@94
|
44 float chn2 = sinf(gPhase2);
|
giuliomoro@94
|
45
|
giuliomoro@94
|
46 float chn3 = context->audioIn[n*2 + 0];
|
giuliomoro@94
|
47 float chn4 = context->audioIn[n*2 + 1];
|
giuliomoro@94
|
48
|
giuliomoro@94
|
49 float chn5 = context->analogIn[(int)n/2*8 + 0];
|
giuliomoro@94
|
50 float chn6 = context->analogIn[(int)n/2*8 + 1];
|
giuliomoro@109
|
51 if((n&1)==0)
|
giuliomoro@109
|
52 scope.log(0, chn1);
|
giuliomoro@94
|
53
|
giuliomoro@94
|
54 // scope.log(chn1, chn2, chn3, chn4, chn5, chn6);
|
giuliomoro@94
|
55 //call this once every audio frame
|
giuliomoro@94
|
56 //takes six or fewer floats as parameters
|
giuliomoro@94
|
57 //first parameter becomes channel 1 etc
|
giuliomoro@94
|
58 //to view, click the 'oscilloscope' button on the toolbar while BeagleRT is NOT running
|
giuliomoro@94
|
59 //then click the big red button on the toolbar on this page
|
giuliomoro@94
|
60
|
giuliomoro@109
|
61 gPhase1 += 2.0 * M_PI * gFrequency1 * gInverseSampleRate * ((count&4095)/4096.0+1);
|
giuliomoro@94
|
62 gPhase2 += 2.0 * M_PI * gFrequency2 * gInverseSampleRate;
|
giuliomoro@94
|
63 if(gPhase1 > 2.0 * M_PI)
|
giuliomoro@94
|
64 gPhase1 -= 2.0 * M_PI;
|
giuliomoro@94
|
65 if(gPhase2 > 2.0 * M_PI)
|
giuliomoro@94
|
66 gPhase2 -= 2.0 * M_PI;
|
giuliomoro@94
|
67
|
giuliomoro@94
|
68 }
|
giuliomoro@109
|
69 count++;
|
giuliomoro@94
|
70 }
|
giuliomoro@94
|
71
|
giuliomoro@94
|
72 // cleanup_render() is called once at the end, after the audio has stopped.
|
giuliomoro@94
|
73 // Release any resources that were allocated in initialise_render().
|
giuliomoro@94
|
74
|
giuliomoro@94
|
75 void cleanup(BeagleRTContext *context, void *userData)
|
giuliomoro@94
|
76 {
|
giuliomoro@94
|
77
|
giuliomoro@94
|
78 }
|