001 002 package ibxm; 003 004 public class IBXM { 005 public static final String VERSION = "ibxm alpha 51 (c)2008 mumart@gmail.com"; 006 007 public static final int FP_SHIFT = 15; 008 public static final int FP_ONE = 1 << FP_SHIFT; 009 public static final int FP_MASK = FP_ONE - 1; 010 011 private int sampling_rate, resampling_quality, volume_ramp_length; 012 private int tick_length_samples, current_tick_samples; 013 private int[] mixing_buffer, volume_ramp_buffer; 014 015 private Module module; 016 private Channel[] channels; 017 private int[] global_volume, note; 018 private int current_sequence_index, next_sequence_index; 019 private int current_row, next_row; 020 private int tick_counter, ticks_per_row; 021 private int pattern_loop_count, pattern_loop_channel; 022 023 public IBXM( int sample_rate ) { 024 025 /** MODIFIED 13 Oct 2009 by Paul Lamb **/ 026 // System.out.println( VERSION ); 027 /***************************************/ 028 029 if( sample_rate < 8000 ) { 030 sample_rate = 8000; 031 } 032 sampling_rate = sample_rate; 033 volume_ramp_length = sampling_rate >> 10; 034 volume_ramp_buffer = new int[ volume_ramp_length * 2 ]; 035 mixing_buffer = new int[ sampling_rate / 6 ]; 036 global_volume = new int[ 1 ]; 037 note = new int[ 5 ]; 038 set_module( new Module() ); 039 set_resampling_quality( 1 ); 040 } 041 042 public void set_module( Module m ) { 043 int channel_idx; 044 module = m; 045 channels = new Channel[ module.get_num_channels() ]; 046 for( channel_idx = 0; channel_idx < channels.length; channel_idx++ ) { 047 channels[ channel_idx ] = new Channel( module, sampling_rate, global_volume ); 048 } 049 set_sequence_index( 0, 0 ); 050 } 051 052 public void set_resampling_quality( int quality ) { 053 resampling_quality = quality; 054 } 055 056 public int calculate_song_duration() { 057 int song_duration; 058 set_sequence_index( 0, 0 ); 059 next_tick(); 060 song_duration = tick_length_samples; 061 while( !next_tick() ) { 062 song_duration += tick_length_samples; 063 } 064 set_sequence_index( 0, 0 ); 065 return song_duration; 066 } 067 068 public void set_sequence_index( int sequence_index, int row ) { 069 int channel_idx; 070 global_volume[ 0 ] = 64; 071 for( channel_idx = 0; channel_idx < channels.length; channel_idx++ ) { 072 channels[ channel_idx ].reset(); 073 channels[ channel_idx ].set_panning( module.get_initial_panning( channel_idx ) ); 074 } 075 set_global_volume( module.global_volume ); 076 set_speed( 6 ); 077 set_speed( module.default_speed ); 078 set_tempo( 125 ); 079 set_tempo( module.default_tempo ); 080 pattern_loop_count = -1; 081 next_sequence_index = sequence_index; 082 next_row = row; 083 tick_counter = 0; 084 current_tick_samples = tick_length_samples; 085 clear_vol_ramp_buffer(); 086 } 087 088 public void seek( int sample_position ) { 089 int idx; 090 set_sequence_index( 0, 0 ); 091 next_tick(); 092 while( sample_position > tick_length_samples ) { 093 sample_position -= tick_length_samples; 094 next_tick(); 095 } 096 mix_tick(); 097 current_tick_samples = sample_position; 098 } 099 100 public void get_audio( byte[] output_buffer, int frames ) { 101 int output_idx, mix_idx, mix_end, count, amplitude; 102 output_idx = 0; 103 while( frames > 0 ) { 104 count = tick_length_samples - current_tick_samples; 105 if( count > frames ) { 106 count = frames; 107 } 108 mix_idx = current_tick_samples << 1; 109 mix_end = mix_idx + ( count << 1 ) - 1; 110 while( mix_idx <= mix_end ) { 111 amplitude = mixing_buffer[ mix_idx ]; 112 if( amplitude > 32767 ) { 113 amplitude = 32767; 114 } 115 if( amplitude < -32768 ) { 116 amplitude = -32768; 117 } 118 output_buffer[ output_idx ] = ( byte ) ( amplitude >> 8 ); 119 output_buffer[ output_idx + 1 ] = ( byte ) ( amplitude & 0xFF ); 120 output_idx += 2; 121 mix_idx += 1; 122 } 123 current_tick_samples = mix_idx >> 1; 124 frames -= count; 125 if( frames > 0 ) { 126 next_tick(); 127 mix_tick(); 128 current_tick_samples = 0; 129 } 130 } 131 } 132 133 private void mix_tick() { 134 int channel_idx, mix_idx, mix_len; 135 mix_idx = 0; 136 mix_len = tick_length_samples + volume_ramp_length << 1; 137 while( mix_idx < mix_len ) { 138 mixing_buffer[ mix_idx ] = 0; 139 mix_idx += 1; 140 } 141 for( channel_idx = 0; channel_idx < channels.length; channel_idx++ ) { 142 mix_len = tick_length_samples + volume_ramp_length; 143 channels[ channel_idx ].resample( mixing_buffer, 0, mix_len, resampling_quality ); 144 } 145 volume_ramp(); 146 } 147 148 private boolean next_tick() { 149 int channel_idx; 150 boolean song_end; 151 for( channel_idx = 0; channel_idx < channels.length; channel_idx++ ) { 152 channels[ channel_idx ].update_sample_idx( tick_length_samples ); 153 } 154 tick_counter -= 1; 155 if( tick_counter <= 0 ) { 156 tick_counter = ticks_per_row; 157 song_end = next_row(); 158 } else { 159 for( channel_idx = 0; channel_idx < channels.length; channel_idx++ ) { 160 channels[ channel_idx ].tick(); 161 } 162 song_end = false; 163 } 164 return song_end; 165 } 166 167 private boolean next_row() { 168 int channel_idx, effect, effect_param; 169 boolean song_end; 170 Pattern pattern; 171 song_end = false; 172 if( next_sequence_index < 0 ) { 173 /* Bad next sequence index.*/ 174 next_sequence_index = 0; 175 next_row = 0; 176 } 177 if( next_sequence_index >= module.get_sequence_length() ) { 178 /* End of sequence.*/ 179 song_end = true; 180 next_sequence_index = module.restart_sequence_index; 181 if( next_sequence_index < 0 ) { 182 next_sequence_index = 0; 183 } 184 if( next_sequence_index >= module.get_sequence_length() ) { 185 next_sequence_index = 0; 186 } 187 next_row = 0; 188 } 189 if( next_sequence_index < current_sequence_index ) { 190 /* Jump to previous pattern. */ 191 song_end = true; 192 } 193 if( next_sequence_index == current_sequence_index ) { 194 if( next_row <= current_row ) { 195 if( pattern_loop_count < 0 ) { 196 /* Jump to previous row in the same pattern, but not a pattern loop. */ 197 song_end = true; 198 } 199 } 200 } 201 current_sequence_index = next_sequence_index; 202 pattern = module.get_pattern_from_sequence( current_sequence_index ); 203 if( next_row < 0 || next_row >= pattern.num_rows ) { 204 /* Bad next row.*/ 205 next_row = 0; 206 } 207 current_row = next_row; 208 next_row = current_row + 1; 209 if( next_row >= pattern.num_rows ) { 210 next_sequence_index = current_sequence_index + 1; 211 next_row = 0; 212 } 213 for( channel_idx = 0; channel_idx < channels.length; channel_idx++ ) { 214 pattern.get_note( note, current_row * channels.length + channel_idx ); 215 effect = note[ 3 ]; 216 effect_param = note[ 4 ]; 217 channels[ channel_idx ].row( note[ 0 ], note[ 1 ], note[ 2 ], effect, effect_param ); 218 switch( effect ) { 219 case 0x0B: 220 /* Pattern Jump.*/ 221 if( pattern_loop_count < 0 ) { 222 next_sequence_index = effect_param; 223 next_row = 0; 224 } 225 break; 226 case 0x0D: 227 /* Pattern Break.*/ 228 if( pattern_loop_count < 0 ) { 229 next_sequence_index = current_sequence_index + 1; 230 next_row = ( effect_param >> 4 ) * 10 + ( effect_param & 0x0F ); 231 } 232 break; 233 case 0x0E: 234 /* Extended.*/ 235 switch( effect_param & 0xF0 ) { 236 case 0x60: 237 /* Pattern loop.*/ 238 if( ( effect_param & 0x0F ) == 0 ) { 239 /* Set loop marker on this channel. */ 240 channels[ channel_idx ].pattern_loop_row = current_row; 241 } 242 if( channels[ channel_idx ].pattern_loop_row < current_row ) { 243 /* Marker and parameter are valid. Begin looping. */ 244 if( pattern_loop_count < 0 ) { 245 /* Not already looping, begin. */ 246 pattern_loop_count = effect_param & 0x0F; 247 pattern_loop_channel = channel_idx; 248 } 249 if( pattern_loop_channel == channel_idx ) { 250 /* Loop in progress on this channel. Next iteration. */ 251 if( pattern_loop_count == 0 ) { 252 /* Loop finished. */ 253 /* Invalidate current marker. */ 254 channels[ channel_idx ].pattern_loop_row = current_row + 1; 255 } else { 256 /* Count must be higher than zero. */ 257 /* Loop and cancel any breaks on this row. */ 258 next_row = channels[ channel_idx ].pattern_loop_row; 259 next_sequence_index = current_sequence_index; 260 } 261 pattern_loop_count -= 1; 262 } 263 } 264 break; 265 case 0xE0: 266 /* Pattern delay.*/ 267 tick_counter += ticks_per_row * ( effect_param & 0x0F ); 268 break; 269 } 270 break; 271 case 0x0F: 272 /* Set Speed/Tempo.*/ 273 if( effect_param < 32 ) { 274 set_speed( effect_param ); 275 tick_counter = ticks_per_row; 276 } else { 277 set_tempo( effect_param ); 278 } 279 break; 280 case 0x25: 281 /* S3M Set Speed.*/ 282 set_speed( effect_param ); 283 tick_counter = ticks_per_row; 284 break; 285 } 286 } 287 return song_end; 288 } 289 290 private void set_global_volume( int volume ) { 291 if( volume < 0 ) { 292 volume = 0; 293 } 294 if( volume > 64 ) { 295 volume = 64; 296 } 297 global_volume[ 0 ] = volume; 298 } 299 300 private void set_speed( int speed ) { 301 if( speed > 0 && speed < 256 ) { 302 ticks_per_row = speed; 303 } 304 } 305 306 private void set_tempo( int bpm ) { 307 if( bpm > 31 && bpm < 256 ) { 308 tick_length_samples = ( sampling_rate * 5 ) / ( bpm * 2 ); 309 } 310 } 311 312 private void volume_ramp() { 313 int ramp_idx, next_idx, ramp_end; 314 int volume_ramp_delta, volume, sample; 315 sample = 0; 316 volume_ramp_delta = FP_ONE / volume_ramp_length; 317 volume = 0; 318 ramp_idx = 0; 319 next_idx = 2 * tick_length_samples; 320 ramp_end = volume_ramp_length * 2 - 1; 321 while( ramp_idx <= ramp_end ) { 322 sample = volume_ramp_buffer[ ramp_idx ] * ( FP_ONE - volume ) >> FP_SHIFT; 323 mixing_buffer[ ramp_idx ] = sample + ( mixing_buffer[ ramp_idx ] * volume >> FP_SHIFT ); 324 volume_ramp_buffer[ ramp_idx ] = mixing_buffer[ next_idx + ramp_idx ]; 325 sample = volume_ramp_buffer[ ramp_idx + 1 ] * ( FP_ONE - volume ) >> FP_SHIFT; 326 mixing_buffer[ ramp_idx + 1 ] = sample + ( mixing_buffer[ ramp_idx + 1 ] * volume >> FP_SHIFT ); 327 volume_ramp_buffer[ ramp_idx + 1 ] = mixing_buffer[ next_idx + ramp_idx + 1 ]; 328 volume += volume_ramp_delta; 329 ramp_idx += 2; 330 } 331 } 332 333 private void clear_vol_ramp_buffer() { 334 int ramp_idx, ramp_end; 335 ramp_idx = 0; 336 ramp_end = volume_ramp_length * 2 - 1; 337 while( ramp_idx <= ramp_end ) { 338 volume_ramp_buffer[ ramp_idx ] = 0; 339 ramp_idx += 1; 340 } 341 } 342 } 343