-
-
Notifications
You must be signed in to change notification settings - Fork 19
/
audio_graph.c
107 lines (82 loc) · 2.42 KB
/
audio_graph.c
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
#include <uvm/syscalls.h>
#include <uvm/window.h>
#include <uvm/math.h>
#include <uvm/graphics.h>
#include <stdlib.h>
#include <stdint.h>
#include <stdio.h>
#define FRAME_WIDTH 600
#define FRAME_HEIGHT 200
#define SAMPLE_RATE 44100
#define DISP_SAMPLES 176400 // SAMPLE_RATE * 4
// RGBA pixels
u32 frame_buffer[FRAME_HEIGHT][FRAME_WIDTH];
// Buffer for incoming samples
i16 buffer[1024];
// Buffer for display
i16 disp_samples[DISP_SAMPLES];
// Current recording position
size_t rec_pos = 0;
void update()
{
// Clear the frame buffer, set all pixels to black
memset32(frame_buffer, 0, sizeof(frame_buffer) / sizeof(u32));
int prev_y = FRAME_HEIGHT / 2;
for (size_t x = 1; x < FRAME_WIDTH; ++x)
{
size_t sample_idx = x * DISP_SAMPLES / FRAME_WIDTH;
// Bring sample into the [-1, 1] range
float sample = (float)disp_samples[sample_idx] / (INT16_MAX + 1);
// Bring the sample into the [0, 1] range
sample = (sample + 1.0f) / 2;
int y = (int)(sample * (FRAME_HEIGHT - 1));
draw_line(
(u32*)&frame_buffer,
FRAME_WIDTH,
FRAME_HEIGHT,
x - 1,
prev_y,
x,
y,
COLOR_RED,
);
prev_y = y;
}
// Draw vertical line at recording position
u32 rec_x = rec_pos * FRAME_WIDTH / DISP_SAMPLES;
draw_line(
(u32*)&frame_buffer,
FRAME_WIDTH,
FRAME_HEIGHT,
rec_x,
0,
rec_x,
FRAME_HEIGHT - 1,
COLOR_WHITE,
);
window_draw_frame(0, frame_buffer);
}
void audio_cb(u16 num_channels, u32 num_samples)
{
assert(num_channels == 1);
assert(num_samples <= 1024);
audio_read_samples(&buffer, num_samples);
size_t end_pos = MIN(rec_pos + num_samples, sizeof(disp_samples) / sizeof(i16));
size_t num_copy = end_pos - rec_pos;
memcpy(&disp_samples[rec_pos], &buffer, num_copy * sizeof(i16));
rec_pos = (rec_pos + num_copy) % DISP_SAMPLES;
if (num_copy < num_samples)
{
size_t buf_pos = num_copy;
size_t num_copy = num_samples - buf_pos;
memcpy(&disp_samples, &buffer[buf_pos], num_copy * sizeof(i16));
rec_pos = num_copy;
}
//printf("%d\n", rec_pos);
}
void main()
{
window_create(FRAME_WIDTH, FRAME_HEIGHT, "Audio Input Graph", 0);
audio_open_input(SAMPLE_RATE, 1, AUDIO_FORMAT_I16, audio_cb);
anim_event_loop(30, update);
}