-
Notifications
You must be signed in to change notification settings - Fork 0
Expand file tree
/
Copy pathmodsynth.cpp
More file actions
103 lines (75 loc) · 2.28 KB
/
modsynth.cpp
File metadata and controls
103 lines (75 loc) · 2.28 KB
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
#include "modsynth.h"
#include <algorithm>
#include <stdexcept>
#include <vector>
#include <mutex>
namespace ModSynth {
// Module registry
static std::vector<Module *> modules;
static std::mutex mutex;
Module::Module() {
std::lock_guard<std::mutex> lock(mutex);
modules.push_back(this);
}
Module::~Module() {
std::lock_guard<std::mutex> lock(mutex);
modules.erase(std::find(modules.begin(), modules.end(), this));
}
// Audio output
static struct Audio {
static float left;
static float right;
static void callback(void *userdata, uint8_t *stream, int len) {
std::lock_guard<std::mutex> lock(mutex);
float *ptr = reinterpret_cast<float *>(stream);
for (size_t i = 0; i < len / sizeof ptr; i++) {
left = 0;
right = 0;
for (auto mod: modules) {
mod->update();
}
// Make the output a bit softer so we don't immediately clip
*ptr++ = left * 0.1;
*ptr++ = right * 0.1;
}
}
Audio() {
if( SDL_Init(SDL_INIT_AUDIO | SDL_INIT_VIDEO) < 0){
fprintf( stderr, "Could not initialise SDL: %s\n", SDL_GetError() );
exit( -1 );
}
SDL_Window *window = SDL_CreateWindow(
"Window", SDL_WINDOWPOS_CENTERED, SDL_WINDOWPOS_CENTERED,
680, 480, SDL_WINDOW_SHOWN | SDL_WINDOW_RESIZABLE);
if(!window) {
fprintf(stderr, "Failed to create window.\n");
exit(-1);
}
// Create renderer and select the color for drawing.
SDL_Renderer* renderer = SDL_CreateRenderer(window, -1, 0);
SDL_SetRenderDrawColor(renderer, 200, 200, 200, 255);
SDL_AudioSpec desired{};
desired.freq = 48000;
desired.format = AUDIO_F32;
desired.channels = 2;
desired.samples = 128;
desired.callback = callback;
if (SDL_OpenAudio(&desired, nullptr) != 0) {
throw std::runtime_error(SDL_GetError());
}
SDL_PauseAudio(0);
}
} audio;
float Audio::left;
float Audio::right;
void VCA::update() {
audio_out = audio_in * amplitude;
}
void Speaker::update() {
audio.left += left_in;
audio.right += right_in;
}
void Wire::update() {
output = input;
}
}