egra: do not record cells outside of the vertical canvas (framebuffer) in agg mini...
[iv.d.git] / dopus / xalsa.d
blobb32588af8dee8393d25f980fe6f6010cc8f61f27
1 module xalsa /*is aliced*/;
3 import iv.alice;
4 import iv.alsa;
5 import iv.follin.utils;
8 // ////////////////////////////////////////////////////////////////////////// //
9 __gshared snd_pcm_t* pcm;
12 enum Rate = 48000;
13 __gshared uint Chans = 2;
16 // ////////////////////////////////////////////////////////////////////////// //
17 void alsaOpen (int chans=-1) {
18 if (chans >= 0) {
19 if (chans < 1 || chans > 2) assert(0, "fuck");
20 Chans = chans;
22 int err;
23 if ((err = snd_pcm_open(&pcm, "plug:default", SND_PCM_STREAM_PLAYBACK, 0)) < 0) {
24 import core.stdc.stdio : printf;
25 import core.stdc.stdlib : exit, EXIT_FAILURE;
26 printf("Playback open error: %s\n", snd_strerror(err));
27 exit(EXIT_FAILURE);
30 if ((err = snd_pcm_set_params(pcm, SND_PCM_FORMAT_S16_LE, SND_PCM_ACCESS_RW_INTERLEAVED, Chans, Rate, 1, 500000)) < 0) {
31 import core.stdc.stdio : printf;
32 import core.stdc.stdlib : exit, EXIT_FAILURE;
33 printf("Playback open error: %s\n", snd_strerror(err));
34 exit(EXIT_FAILURE);
39 // ////////////////////////////////////////////////////////////////////////// //
40 void alsaClose () {
41 if (pcm !is null) {
42 snd_pcm_close(pcm);
43 pcm = null;
48 // ////////////////////////////////////////////////////////////////////////// //
49 void alsaWriteX (short* sptr, uint frms) {
50 while (frms > 0) {
51 snd_pcm_sframes_t frames = snd_pcm_writei(pcm, sptr, frms);
52 if (frames < 0) {
53 frames = snd_pcm_recover(pcm, cast(int)frames, 0);
54 if (frames < 0) {
55 import core.stdc.stdio : printf;
56 import core.stdc.stdlib : exit, EXIT_FAILURE;
57 printf("snd_pcm_writei failed: %s\n", snd_strerror(cast(int)frames));
58 exit(EXIT_FAILURE);
60 } else {
61 frms -= frames;
62 sptr += frames*Chans;
68 // ////////////////////////////////////////////////////////////////////////// //
69 void alsaWrite2B (ubyte** eptr, uint frms) {
70 static float[4096] fbuf;
71 static short[4096] sbuf;
72 auto fptr = cast(float**)eptr;
73 while (frms > 0) {
74 uint len = cast(uint)(fbuf.length/Chans);
75 if (len > frms) len = frms;
76 uint dpos = 0;
77 foreach (immutable pos; 0..len) {
78 foreach (immutable chn; 0..Chans) {
79 //assert(*sptr[chn] >= -1.0f && *sptr[chn] <= 1.0f);
80 fbuf[dpos++] = *fptr[chn]++;
83 tflFloat2Short(fbuf[0..dpos], sbuf[0..dpos]);
84 dpos = 0;
85 while (dpos < len) {
86 snd_pcm_sframes_t frames = snd_pcm_writei(pcm, sbuf.ptr+dpos*Chans, len-dpos);
87 if (frames < 0) {
88 frames = snd_pcm_recover(pcm, cast(int)frames, 0);
89 import core.stdc.stdio : printf;
90 import core.stdc.stdlib : exit, EXIT_FAILURE;
91 printf("snd_pcm_writei failed: %s\n", snd_strerror(cast(int)frames));
92 exit(EXIT_FAILURE);
93 } else {
94 frms -= frames;
95 dpos += frames*Chans;