prosperon/source/engine/sound/mix.c

118 lines
2.4 KiB
C
Raw Normal View History

2022-07-05 20:49:51 -05:00
#include "mix.h"
#include "stddef.h"
2022-07-06 17:17:06 -05:00
#include "time.h"
2022-07-05 20:49:51 -05:00
#include "sound.h"
#include "dsp.h"
#include <string.h>
#include "log.h"
#include "stdlib.h"
2022-07-05 20:49:51 -05:00
2023-01-25 21:32:58 -06:00
#include <assert.h>
#define BUS_N 256
static struct bus *bus;
2023-01-15 11:16:25 -06:00
static int first = 0; /* First bus available */
2023-01-31 17:41:09 -06:00
static int first_on = -1; /* First bus to fill buffer with */
soundbyte *mastermix = NULL;
2023-01-17 15:09:14 -06:00
static float master_volume = 1.f;
void mix_master_vol(float v) {
if (v < 0.f) v = 0.f;
if (v > 100.f) v = 100.f;
master_volume = v / 100.f;
}
2023-01-15 11:16:25 -06:00
void mixer_init() {
bus = malloc(sizeof(struct bus)*BUS_N);
mastermix = malloc(BUF_FRAMES*CHANNELS);
for (int i = 0; i < BUS_N; i++) {
2023-01-15 11:16:25 -06:00
bus[i].next = i+1;
bus[i].on = 0;
bus[i].id = i;
2022-07-05 20:49:51 -05:00
}
bus[BUS_N-1].next = -1;
2023-01-15 11:16:25 -06:00
}
void filter_to_bus(struct dsp_filter *f)
{
struct bus *b = first_free_bus(*f);
if (b)
f->bus = b;
}
void unplug_filter(struct dsp_filter *f)
{
if (!f->bus) return;
bus_free(f->bus);
f->bus = NULL;
}
2023-01-15 11:16:25 -06:00
struct bus *first_free_bus(struct dsp_filter in) {
2023-03-10 13:13:48 -06:00
for (int i = 0; i < 255; i++)
if (!bus[i].on) {
bus[i].on = 1;
bus[i].in = in;
return &bus[i];
}
return NULL;
2023-01-31 17:41:09 -06:00
2023-01-15 11:16:25 -06:00
if (first == -1) return NULL;
int ret = first;
first = bus[ret].next;
2023-01-15 11:16:25 -06:00
bus[ret].on = 1;
bus[ret].in = in;
2023-01-15 11:16:25 -06:00
if (first_on != -1) bus[first_on].prev = ret;
bus[ret].next = first_on;
bus[ret].prev = -1;
first_on = ret;
return &bus[ret];
2022-07-05 20:49:51 -05:00
}
void bus_free(struct bus *b)
2022-07-19 15:13:15 -05:00
{
2023-04-07 12:52:35 -05:00
if (!b) return;
2023-03-10 13:13:48 -06:00
b->on = 0;
return;
if (first_on == b->id) first_on = b->next;
if (b->next != -1) bus[b->next].prev = b->prev;
if (b->prev != -1) bus[b->prev].next = b->next;
b->next = first;
first = b->id;
b->on = 0;
2022-07-19 15:13:15 -05:00
}
void bus_fill_buffers(soundbyte *master, int n) {
int curbus = first_on;
2023-03-10 13:13:48 -06:00
// if (curbus == -1) return;
memset(master, 0, BUF_FRAMES*CHANNELS*sizeof(soundbyte));
2023-03-10 13:13:48 -06:00
for (int i = 0; i < 255; i++) {
if (!bus[i].on) continue;
dsp_run(bus[i].in, bus[i].buf, BUF_FRAMES);
for (int j = 0; j < BUF_FRAMES*CHANNELS; j++)
master[j] += bus[i].buf[j] * master_volume;
}
return;
while (curbus != -1) {
int nextbus = bus[curbus].next; /* Save this in case busses get changed during fill */
2023-01-15 11:16:25 -06:00
dsp_run(bus[curbus].in, bus[curbus].buf, BUF_FRAMES);
for (int i = 0; i < BUF_FRAMES*CHANNELS; i++)
2023-01-17 15:09:14 -06:00
master[i] += bus[curbus].buf[i] * master_volume;
2023-01-15 11:16:25 -06:00
curbus = nextbus;
2022-07-05 20:49:51 -05:00
}
}