diff options
author | Michiel Van Der Kolk <not.valid@email.address> | 2005-03-17 20:50:03 +0000 |
---|---|---|
committer | Michiel Van Der Kolk <not.valid@email.address> | 2005-03-17 20:50:03 +0000 |
commit | 27be5bc72855a0fbbdae230bc144624c9eb85f5e (patch) | |
tree | b553f1321df924c4b744ffcab48dce5f4f081f7d /apps/codecs/dumb/src/it/xmeffect.c | |
parent | 7e7662bb716917ca431204f0113d400c1014f2e8 (diff) | |
download | rockbox-27be5bc72855a0fbbdae230bc144624c9eb85f5e.tar.gz rockbox-27be5bc72855a0fbbdae230bc144624c9eb85f5e.zip |
Initial check in dumb 0.9.2 - has a few usages of floating point that should
be rewritten to fixed point. seems to compile cleanly for iriver.
git-svn-id: svn://svn.rockbox.org/rockbox/trunk@6197 a1c6a512-1295-4272-9138-f99709370657
Diffstat (limited to 'apps/codecs/dumb/src/it/xmeffect.c')
-rw-r--r-- | apps/codecs/dumb/src/it/xmeffect.c | 242 |
1 files changed, 242 insertions, 0 deletions
diff --git a/apps/codecs/dumb/src/it/xmeffect.c b/apps/codecs/dumb/src/it/xmeffect.c new file mode 100644 index 0000000000..51995f3bb8 --- /dev/null +++ b/apps/codecs/dumb/src/it/xmeffect.c | |||
@@ -0,0 +1,242 @@ | |||
1 | /* _______ ____ __ ___ ___ | ||
2 | * \ _ \ \ / \ / \ \ / / ' ' ' | ||
3 | * | | \ \ | | || | \/ | . . | ||
4 | * | | | | | | || ||\ /| | | ||
5 | * | | | | | | || || \/ | | ' ' ' | ||
6 | * | | | | | | || || | | . . | ||
7 | * | |_/ / \ \__// || | | | ||
8 | * /_______/ynamic \____/niversal /__\ /____\usic /| . . ibliotheque | ||
9 | * / \ | ||
10 | * / . \ | ||
11 | * xmeffect.c - Code for converting MOD/XM / / \ \ | ||
12 | * effects to IT effects. | < / \_ | ||
13 | * | \/ /\ / | ||
14 | * By Julien Cugniere. Ripped out of readxm.c \_ / > / | ||
15 | * by entheh. | \ / / | ||
16 | * | ' / | ||
17 | * \__/ | ||
18 | */ | ||
19 | |||
20 | |||
21 | |||
22 | #include <stdlib.h> | ||
23 | #include <string.h> | ||
24 | |||
25 | #include "dumb.h" | ||
26 | #include "internal/it.h" | ||
27 | |||
28 | |||
29 | |||
30 | #if 0 | ||
31 | unsigned char **_dumb_malloc2(int w, int h) | ||
32 | { | ||
33 | unsigned char **line = malloc(h * sizeof(*line)); | ||
34 | int i; | ||
35 | if (!line) return NULL; | ||
36 | |||
37 | line[0] = malloc(w * h * sizeof(*line[0])); | ||
38 | if (!line[0]) { | ||
39 | free(line); | ||
40 | return NULL; | ||
41 | } | ||
42 | |||
43 | for (i = 1; i < h; i++) | ||
44 | line[i] = line[i-1] + w; | ||
45 | |||
46 | memset(line[0], 0, w*h); | ||
47 | |||
48 | return line; | ||
49 | } | ||
50 | |||
51 | |||
52 | |||
53 | void _dumb_free2(unsigned char **line) | ||
54 | { | ||
55 | if (line) { | ||
56 | if (line[0]) | ||
57 | free(line[0]); | ||
58 | free(line); | ||
59 | } | ||
60 | } | ||
61 | |||
62 | |||
63 | |||
64 | /* Effects having a memory. 2 means that the two parts of the effectvalue | ||
65 | * should be handled separately. | ||
66 | */ | ||
67 | static const char xm_has_memory[] = { | ||
68 | /* 0 1 2 3 4 5 6 7 8 9 A B C D (E) F G H K L P R T (X) */ | ||
69 | 0, 1, 1, 1, 2, 1, 1, 2, 0, 0, 1, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 1, 0, 2, 0, 0, 0, 0, 0, 0, 0, 0, | ||
70 | |||
71 | /* E0 E1 E2 E3 E4 E5 E6 E7 E9 EA EB EC ED EE X1 X2 */ | ||
72 | 0, 1, 1, 0, 0, 0, 0, 0, 0, 0, 1, 1, 0, 0, 0, 0, 0, 1, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 | ||
73 | }; | ||
74 | #endif | ||
75 | |||
76 | |||
77 | |||
78 | /* Effects marked with 'special' are handled specifically in itrender.c */ | ||
79 | void _dumb_it_xm_convert_effect(int effect, int value, IT_ENTRY *entry) | ||
80 | { | ||
81 | const int log = 0; | ||
82 | |||
83 | if ((!effect && !value) || (effect >= XM_N_EFFECTS)) | ||
84 | return; | ||
85 | |||
86 | if (log) printf("%c%02X", (effect<10)?('0'+effect):('A'+effect-10), value); | ||
87 | |||
88 | /* Linearisation of the effect number... */ | ||
89 | if (effect == XM_E) { | ||
90 | effect = EBASE + HIGH(value); | ||
91 | value = LOW(value); | ||
92 | } else if (effect == XM_X) { | ||
93 | effect = XBASE + HIGH(value); | ||
94 | value = LOW(value); | ||
95 | } | ||
96 | |||
97 | if (log) printf(" - %2d %02X", effect, value); | ||
98 | |||
99 | #if 0 // This should be handled in itrender.c! | ||
100 | /* update effect memory */ | ||
101 | switch (xm_has_memory[effect]) { | ||
102 | case 1: | ||
103 | if (!value) | ||
104 | value = memory[entry->channel][effect]; | ||
105 | else | ||
106 | memory[entry->channel][effect] = value; | ||
107 | break; | ||
108 | |||
109 | case 2: | ||
110 | if (!HIGH(value)) | ||
111 | SET_HIGH(value, HIGH(memory[entry->channel][effect])); | ||
112 | else | ||
113 | SET_HIGH(memory[entry->channel][effect], HIGH(value)); | ||
114 | |||
115 | if (!LOW(value)) | ||
116 | SET_LOW(value, LOW(memory[entry->channel][effect])); | ||
117 | else | ||
118 | SET_LOW(memory[entry->channel][effect], LOW(value)); | ||
119 | break; | ||
120 | } | ||
121 | #endif | ||
122 | |||
123 | /* convert effect */ | ||
124 | entry->mask |= IT_ENTRY_EFFECT; | ||
125 | switch (effect) { | ||
126 | |||
127 | case XM_APPREGIO: effect = IT_ARPEGGIO; break; | ||
128 | case XM_VIBRATO: effect = IT_VIBRATO; break; | ||
129 | case XM_TONE_PORTAMENTO: effect = IT_TONE_PORTAMENTO; break; /** TODO: glissando control */ | ||
130 | case XM_TREMOLO: effect = IT_TREMOLO; break; | ||
131 | case XM_SET_PANNING: effect = IT_SET_PANNING; break; | ||
132 | case XM_SAMPLE_OFFSET: effect = IT_SET_SAMPLE_OFFSET; break; | ||
133 | case XM_POSITION_JUMP: effect = IT_JUMP_TO_ORDER; break; | ||
134 | case XM_MULTI_RETRIG: effect = IT_RETRIGGER_NOTE; break; | ||
135 | case XM_TREMOR: effect = IT_TREMOR; break; | ||
136 | case XM_PORTAMENTO_UP: effect = IT_XM_PORTAMENTO_UP; break; | ||
137 | case XM_PORTAMENTO_DOWN: effect = IT_XM_PORTAMENTO_DOWN; break; | ||
138 | case XM_SET_CHANNEL_VOLUME: effect = IT_SET_CHANNEL_VOLUME; break; /* special */ | ||
139 | case XM_VOLSLIDE_TONEPORTA: effect = IT_VOLSLIDE_TONEPORTA; break; /* special */ | ||
140 | case XM_VOLSLIDE_VIBRATO: effect = IT_VOLSLIDE_VIBRATO; break; /* special */ | ||
141 | |||
142 | case XM_PATTERN_BREAK: | ||
143 | effect = IT_BREAK_TO_ROW; | ||
144 | value = BCD_TO_NORMAL(value); | ||
145 | break; | ||
146 | |||
147 | case XM_VOLUME_SLIDE: /* special */ | ||
148 | effect = IT_VOLUME_SLIDE; | ||
149 | value = HIGH(value) ? EFFECT_VALUE(HIGH(value), 0) : EFFECT_VALUE(0, LOW(value)); | ||
150 | break; | ||
151 | |||
152 | case XM_PANNING_SLIDE: | ||
153 | effect = IT_PANNING_SLIDE; | ||
154 | value = HIGH(value) ? EFFECT_VALUE(0, HIGH(value)) : EFFECT_VALUE(LOW(value), 0); | ||
155 | break; | ||
156 | |||
157 | case XM_GLOBAL_VOLUME_SLIDE: /* special */ | ||
158 | effect = IT_GLOBAL_VOLUME_SLIDE; | ||
159 | value = HIGH(value) ? EFFECT_VALUE(HIGH(value), 0) : EFFECT_VALUE(0, LOW(value)); | ||
160 | break; | ||
161 | |||
162 | case XM_SET_TEMPO_BPM: | ||
163 | effect = (value < 0x20) ? (IT_SET_SPEED) : (IT_SET_SONG_TEMPO); | ||
164 | break; | ||
165 | |||
166 | case XM_SET_GLOBAL_VOLUME: | ||
167 | effect = IT_SET_GLOBAL_VOLUME; | ||
168 | value *= 2; | ||
169 | break; | ||
170 | |||
171 | case XM_KEY_OFF: | ||
172 | /** WARNING: In FT2, the value seems to do something... Oh well, | ||
173 | * this is undocumented anyway! | ||
174 | */ | ||
175 | entry->mask &= ~IT_ENTRY_EFFECT; | ||
176 | entry->mask |= IT_ENTRY_NOTE; | ||
177 | entry->note = IT_NOTE_OFF; | ||
178 | break; | ||
179 | |||
180 | case EBASE+XM_E_SET_FILTER: effect = SBASE+IT_S_SET_FILTER; break; | ||
181 | case EBASE+XM_E_SET_GLISSANDO_CONTROL: effect = SBASE+IT_S_SET_GLISSANDO_CONTROL; break; /** TODO */ | ||
182 | case EBASE+XM_E_SET_FINETUNE: effect = SBASE+IT_S_FINETUNE; break; /** TODO */ | ||
183 | case EBASE+XM_E_SET_LOOP: effect = SBASE+IT_S_PATTERN_LOOP; break; | ||
184 | case EBASE+XM_E_NOTE_CUT: effect = SBASE+IT_S_DELAYED_NOTE_CUT; break; | ||
185 | case EBASE+XM_E_NOTE_DELAY: effect = SBASE+IT_S_NOTE_DELAY; break; | ||
186 | case EBASE+XM_E_PATTERN_DELAY: effect = SBASE+IT_S_PATTERN_DELAY; break; | ||
187 | case EBASE+XM_E_FINE_VOLSLIDE_UP: effect = IT_XM_FINE_VOLSLIDE_UP; break; | ||
188 | case EBASE+XM_E_FINE_VOLSLIDE_DOWN: effect = IT_XM_FINE_VOLSLIDE_DOWN; break; | ||
189 | |||
190 | case EBASE + XM_E_FINE_PORTA_UP: | ||
191 | effect = IT_PORTAMENTO_UP; | ||
192 | value = EFFECT_VALUE(0xF, value); | ||
193 | break; | ||
194 | |||
195 | case EBASE + XM_E_FINE_PORTA_DOWN: | ||
196 | effect = IT_PORTAMENTO_DOWN; | ||
197 | value = EFFECT_VALUE(0xF, value); | ||
198 | break; | ||
199 | |||
200 | case EBASE + XM_E_RETRIG_NOTE: | ||
201 | effect = IT_XM_RETRIGGER_NOTE; | ||
202 | value = EFFECT_VALUE(0, value); | ||
203 | break; | ||
204 | |||
205 | case EBASE + XM_E_SET_VIBRATO_CONTROL: | ||
206 | effect = SBASE+IT_S_SET_VIBRATO_WAVEFORM; | ||
207 | value &= ~4; /** TODO: value&4 -> don't retrig wave */ | ||
208 | break; | ||
209 | |||
210 | case EBASE + XM_E_SET_TREMOLO_CONTROL: | ||
211 | effect = SBASE+IT_S_SET_TREMOLO_WAVEFORM; | ||
212 | value &= ~4; /** TODO: value&4 -> don't retrig wave */ | ||
213 | break; | ||
214 | |||
215 | case XBASE + XM_X_EXTRAFINE_PORTA_UP: | ||
216 | effect = IT_PORTAMENTO_UP; | ||
217 | value = EFFECT_VALUE(0xE, value); | ||
218 | break; | ||
219 | |||
220 | case XBASE + XM_X_EXTRAFINE_PORTA_DOWN: | ||
221 | effect = IT_PORTAMENTO_DOWN; | ||
222 | value = EFFECT_VALUE(0xE, value); | ||
223 | break; | ||
224 | |||
225 | default: | ||
226 | /* user effect (often used in demos for synchronisation) */ | ||
227 | entry->mask &= ~IT_ENTRY_EFFECT; | ||
228 | } | ||
229 | |||
230 | if (log) printf(" - %2d %02X", effect, value); | ||
231 | |||
232 | /* Inverse linearisation... */ | ||
233 | if (effect >= SBASE && effect < SBASE+16) { | ||
234 | value = EFFECT_VALUE(effect-SBASE, value); | ||
235 | effect = IT_S; | ||
236 | } | ||
237 | |||
238 | if (log) printf(" - %c%02X\n", 'A'+effect-1, value); | ||
239 | |||
240 | entry->effect = effect; | ||
241 | entry->effectvalue = value; | ||
242 | } | ||