summaryrefslogtreecommitdiff
path: root/apps/codecs/dumb/src/core/rendsig.c
diff options
context:
space:
mode:
Diffstat (limited to 'apps/codecs/dumb/src/core/rendsig.c')
-rw-r--r--apps/codecs/dumb/src/core/rendsig.c299
1 files changed, 299 insertions, 0 deletions
diff --git a/apps/codecs/dumb/src/core/rendsig.c b/apps/codecs/dumb/src/core/rendsig.c
new file mode 100644
index 0000000000..a36ceb41cf
--- /dev/null
+++ b/apps/codecs/dumb/src/core/rendsig.c
@@ -0,0 +1,299 @@
1/* _______ ____ __ ___ ___
2 * \ _ \ \ / \ / \ \ / / ' ' '
3 * | | \ \ | | || | \/ | . .
4 * | | | | | | || ||\ /| |
5 * | | | | | | || || \/ | | ' ' '
6 * | | | | | | || || | | . .
7 * | |_/ / \ \__// || | |
8 * /_______/ynamic \____/niversal /__\ /____\usic /| . . ibliotheque
9 * / \
10 * / . \
11 * rendsig.c - Wrappers to render samples from / / \ \
12 * the signals in a DUH. | < / \_
13 * | \/ /\ /
14 * By entheh. \_ / > /
15 * | \ / /
16 * | ' /
17 * \__/
18 */
19
20#include <stdlib.h>
21
22#include "dumb.h"
23#include "internal/dumb.h"
24
25
26
27struct DUH_SIGRENDERER
28{
29 DUH_SIGTYPE_DESC *desc;
30
31 sigrenderer_t *sigrenderer;
32
33 int n_channels;
34
35 long pos;
36 int subpos;
37
38 DUH_SIGRENDERER_ANALYSER_CALLBACK callback;
39 void *callback_data;
40};
41
42
43
44DUH_SIGRENDERER *duh_start_sigrenderer(DUH *duh, int sig, int n_channels, long pos)
45{
46 DUH_SIGRENDERER *sigrenderer;
47
48 DUH_SIGNAL *signal;
49 DUH_START_SIGRENDERER proc;
50
51 if ((unsigned int)sig >= (unsigned int)duh->n_signals)
52 return NULL;
53
54 signal = duh->signal[sig];
55 if (!signal)
56 return NULL;
57
58 sigrenderer = malloc(sizeof(*sigrenderer));
59 if (!sigrenderer)
60 return NULL;
61
62 sigrenderer->desc = signal->desc;
63
64 proc = sigrenderer->desc->start_sigrenderer;
65
66 if (proc) {
67 duh->signal[sig] = NULL;
68 sigrenderer->sigrenderer = (*proc)(duh, signal->sigdata, n_channels, pos);
69 duh->signal[sig] = signal;
70
71 if (!sigrenderer->sigrenderer) {
72 free(sigrenderer);
73 return NULL;
74 }
75 } else
76 sigrenderer->sigrenderer = NULL;
77
78 sigrenderer->n_channels = n_channels;
79
80 sigrenderer->pos = pos;
81 sigrenderer->subpos = 0;
82
83 sigrenderer->callback = NULL;
84
85 return sigrenderer;
86}
87
88
89
90#include <stdio.h>
91void duh_sigrenderer_set_callback(
92 DUH_SIGRENDERER *sigrenderer,
93 DUH_SIGRENDERER_CALLBACK callback, void *data
94)
95{
96 (void)sigrenderer;
97 (void)callback;
98 (void)data;
99/* FIXME
100 fprintf(stderr,
101 "Call to deprecated function duh_sigrenderer_set_callback(). The callback\n"
102 "was not installed. See dumb/docs/deprec.txt for how to fix this.\n");*/
103}
104
105
106
107void duh_sigrenderer_set_analyser_callback(
108 DUH_SIGRENDERER *sigrenderer,
109 DUH_SIGRENDERER_ANALYSER_CALLBACK callback, void *data
110)
111{
112 if (sigrenderer) {
113 sigrenderer->callback = callback;
114 sigrenderer->callback_data = data;
115 }
116}
117
118
119
120int duh_sigrenderer_get_n_channels(DUH_SIGRENDERER *sigrenderer)
121{
122 return sigrenderer ? sigrenderer->n_channels : 0;
123}
124
125
126
127long duh_sigrenderer_get_position(DUH_SIGRENDERER *sigrenderer)
128{
129 return sigrenderer ? sigrenderer->pos : -1;
130}
131
132
133
134void duh_sigrenderer_set_sigparam(
135 DUH_SIGRENDERER *sigrenderer,
136 unsigned char id, long value
137)
138{
139 DUH_SIGRENDERER_SET_SIGPARAM proc;
140
141 if (!sigrenderer) return;
142
143 proc = sigrenderer->desc->sigrenderer_set_sigparam;
144 if (proc)
145 (*proc)(sigrenderer->sigrenderer, id, value);
146 else
147 TRACE("Parameter #%d = %ld for signal %c%c%c%c, which does not take parameters.\n",
148 (int)id,
149 value,
150 (int)(sigrenderer->desc->type >> 24),
151 (int)(sigrenderer->desc->type >> 16),
152 (int)(sigrenderer->desc->type >> 8),
153 (int)(sigrenderer->desc->type));
154}
155
156
157
158long duh_sigrenderer_get_samples(
159 DUH_SIGRENDERER *sigrenderer,
160 float volume, float delta,
161 long size, sample_t **samples
162)
163{
164 long rendered;
165 LONG_LONG t;
166
167 if (!sigrenderer) return 0;
168
169 rendered = (*sigrenderer->desc->sigrenderer_get_samples)
170 (sigrenderer->sigrenderer, volume, delta, size, samples);
171
172 if (rendered) {
173 if (sigrenderer->callback)
174 (*sigrenderer->callback)(sigrenderer->callback_data,
175 (const sample_t *const *)samples, sigrenderer->n_channels, rendered);
176
177 t = sigrenderer->subpos + (LONG_LONG)(delta * 65536.0 + 0.5) * rendered;
178
179 sigrenderer->pos += (long)(t >> 16);
180 sigrenderer->subpos = (int)t & 65535;
181 }
182
183 return rendered;
184}
185
186
187
188/* DEPRECATED */
189long duh_render_signal(
190 DUH_SIGRENDERER *sigrenderer,
191 float volume, float delta,
192 long size, sample_t **samples
193)
194{
195 sample_t **s = create_sample_buffer(sigrenderer->n_channels, size);
196 long rendered;
197 long i;
198 int j;
199 if (!s) return 0;
200 rendered = duh_sigrenderer_get_samples(sigrenderer, volume, delta, size, s);
201 for (j = 0; j < sigrenderer->n_channels; j++)
202 for (i = 0; i < rendered; i++)
203 samples[j][i] += s[j][i] >> 8;
204 destroy_sample_buffer(s);
205 return rendered;
206}
207
208
209
210void duh_sigrenderer_get_current_sample(DUH_SIGRENDERER *sigrenderer, float volume, sample_t *samples)
211{
212 if (sigrenderer)
213 (*sigrenderer->desc->sigrenderer_get_current_sample)(sigrenderer->sigrenderer, volume, samples);
214}
215
216
217
218void duh_end_sigrenderer(DUH_SIGRENDERER *sigrenderer)
219{
220 if (sigrenderer) {
221 if (sigrenderer->desc->end_sigrenderer)
222 if (sigrenderer->sigrenderer)
223 (*sigrenderer->desc->end_sigrenderer)(sigrenderer->sigrenderer);
224
225 free(sigrenderer);
226 }
227}
228
229
230
231DUH_SIGRENDERER *duh_encapsulate_raw_sigrenderer(sigrenderer_t *vsigrenderer, DUH_SIGTYPE_DESC *desc, int n_channels, long pos)
232{
233 DUH_SIGRENDERER *sigrenderer;
234
235 if (desc->start_sigrenderer && !vsigrenderer) return NULL;
236
237 sigrenderer = malloc(sizeof(*sigrenderer));
238 if (!sigrenderer) {
239 if (desc->end_sigrenderer)
240 if (vsigrenderer)
241 (*desc->end_sigrenderer)(vsigrenderer);
242 return NULL;
243 }
244
245 sigrenderer->desc = desc;
246 sigrenderer->sigrenderer = vsigrenderer;
247
248 sigrenderer->n_channels = n_channels;
249
250 sigrenderer->pos = pos;
251 sigrenderer->subpos = 0;
252
253 sigrenderer->callback = NULL;
254
255 return sigrenderer;
256}
257
258
259
260sigrenderer_t *duh_get_raw_sigrenderer(DUH_SIGRENDERER *sigrenderer, long type)
261{
262 if (sigrenderer && sigrenderer->desc->type == type)
263 return sigrenderer->sigrenderer;
264
265 return NULL;
266}
267
268
269
270#if 0
271// This function is disabled because we don't know whether we want to destroy
272// the sigrenderer if the type doesn't match. We don't even know if we need
273// the function at all. Who would want to keep an IT_SIGRENDERER (for
274// instance) without keeping the DUH_SIGRENDERER?
275sigrenderer_t *duh_decompose_to_raw_sigrenderer(DUH_SIGRENDERER *sigrenderer, long type)
276{
277 if (sigrenderer && sigrenderer->desc->type == type) {
278
279
280
281 if (sigrenderer) {
282 if (sigrenderer->desc->end_sigrenderer)
283 if (sigrenderer->sigrenderer)
284 (*sigrenderer->desc->end_sigrenderer)(sigrenderer->sigrenderer);
285
286 free(sigrenderer);
287 }
288
289
290
291
292
293
294 return sigrenderer->sigrenderer;
295 }
296
297 return NULL;
298}
299#endif