Main Page | Class Hierarchy | Alphabetical List | Class List | Directories | File List | Class Members | File Members

audioidevice.C

Go to the documentation of this file.
00001 #include "audiodevice.h"
00002 #include "condition.h"
00003 #include "dcoffset.h"
00004 #include "bcprogressbox.h"
00005 
00006 
00007 int AudioDevice::set_record_dither(int bits)
00008 {
00009         rec_dither = bits;
00010         return 0;
00011 }
00012 
00013 
00014 int AudioDevice::get_dc_offset(int *output, RecordGUIDCOffsetText **dc_offset_text)
00015 {
00016         dc_offset_thread->calibrate_dc_offset(output, dc_offset_text, get_ichannels());
00017         return 0;
00018 }
00019 
00020 int AudioDevice::set_dc_offset(int dc_offset, int channel)
00021 {
00022         dc_offset_thread->dc_offset[channel] = dc_offset;
00023         return 0;
00024 }
00025 
00026 #define GET_PEAK_MACRO \
00027                                         input_channel[j] = sample;                          \
00028                                         if(sample > max[i]) max[i] = sample;           \
00029                                         else if(-sample > max[i]) max[i] = -sample;
00030 
00031 // ============================ use 2 macros to allow for getting dc_offset
00032 // ============= must check for overload after dc_offset because of byte wrapping on save
00033 
00034 #define GET_8BIT_SAMPLE_MACRO1 \
00035 sample = input_buffer[k];      \
00036 sample -= dc_offset_value;        \
00037 k += input_channels;           \
00038 if(sample >= max_sample[i]) { sample = max_sample[i]; if(over_count < 3) over_count++; } \
00039 else                           \
00040 if(sample <= min_sample[i]) { sample = min_sample[i]; if(over_count < 3) over_count++; } \
00041 else                           \
00042 if(over_count < 3) over_count = 0; 
00043 
00044 #define GET_8BIT_SAMPLE_MACRO2 \
00045 sample /= 0x7f;                  
00046 
00047 
00048 
00049 #define GET_16BIT_SAMPLE_MACRO1                            \
00050 sample = input_buffer_16[k];                               \
00051 if(dither_scale) { dither_value = rand() % dither_scale; sample -= dither_value; } \
00052 sample -= dc_offset_value;                                    \
00053 k += input_channels;                                       \
00054 if(sample >= max_sample[i]) { sample = max_sample[i]; if(over_count < 3) over_count++; } \
00055 else                                                       \
00056 if(sample <= min_sample[i]) { sample = min_sample[i]; if(over_count < 3) over_count++; } \
00057 else                                                       \
00058 if(over_count < 3) over_count = 0;                         \
00059 
00060 #define GET_16BIT_SAMPLE_MACRO2                            \
00061 sample /= 0x7fff;                  
00062 
00063 
00064 
00065 #define GET_24BIT_SAMPLE_MACRO1 \
00066 sample = (unsigned char)input_buffer[k] | \
00067                         (((unsigned char)input_buffer[k + 1]) << 8) | \
00068                         (((int)input_buffer[k + 2]) << 16); \
00069 sample -= dc_offset_value; \
00070 k += input_channels * 3; \
00071 if(sample >= max_sample[i]) { sample = max_sample[i]; if(over_count < 3) over_count++; } \
00072 else                                                 \
00073 if(sample <= min_sample[i]) { sample = min_sample[i]; if(over_count < 3) over_count++; } \
00074 else                                                 \
00075 if(over_count < 3) over_count = 0; 
00076 
00077 #define GET_24BIT_SAMPLE_MACRO2       \
00078 sample /= 0x7fffff;
00079 
00080 
00081 
00082 #define GET_32BIT_SAMPLE_MACRO1 \
00083 sample = (unsigned char)input_buffer[k] | \
00084                         (((unsigned char)input_buffer[k + 1]) << 8) | \
00085                         (((unsigned char)input_buffer[k + 2]) << 16) | \
00086                         (((int)input_buffer[k + 3]) << 24); \
00087 sample -= dc_offset_value; \
00088 k += input_channels * 4; \
00089 if(sample >= max_sample[i]) { sample = max_sample[i]; if(over_count < 3) over_count++; } \
00090 else \
00091 if(sample <= min_sample[i]) { sample = min_sample[i]; if(over_count < 3) over_count++; } \
00092 else \
00093 if(over_count < 3) over_count = 0; 
00094 
00095 #define GET_32BIT_SAMPLE_MACRO2       \
00096 sample /= 0x7fffffff;
00097 
00098 int AudioDevice::read_buffer(double **input, 
00099         int samples, 
00100         int channels, 
00101         int *over, 
00102         double *max, 
00103         int input_offset)
00104 {
00105         int i, j, k, frame, bits;
00106         double sample, denominator;
00107         double min_sample[MAXCHANNELS], max_sample[MAXCHANNELS];
00108         int sample_int;
00109         int over_count;
00110         int dither_value, dither_scale;
00111         int input_channels;
00112         int result = 0;
00113         double *input_channel;
00114         int *dc_offset_total;
00115         int dc_offset_value;
00116 
00117         is_recording = 1;
00118         record_timer.update();
00119 
00120         bits = get_ibits();
00121         input_channels = get_ichannels();
00122         frame = input_channels * bits / 8;
00123 
00124         dither_scale = 0;
00125         total_samples_read += samples;
00126 
00127         switch(bits)
00128         {
00129                 case 8:       
00130                         denominator = 0x7f;          
00131                         break;
00132                 case 16:      
00133                         denominator = 0x7fff;        
00134                         if(rec_dither == 8)
00135                         {
00136                                 dither_scale = 255;
00137                         }
00138                         break;
00139                 case 24:      
00140                         denominator = 0x7fffff;      
00141                         if(rec_dither == 8)
00142                         {
00143                                 dither_scale = 65535;
00144                         }
00145                         else 
00146                         if (rec_dither == 16)
00147                         {
00148                                 dither_scale = 255;
00149                         }
00150                         break;
00151                 case 32:      
00152                         denominator = 0x7fffffff;      
00153                         dither_scale = 0;
00154                         break;
00155         }
00156 
00157         if(input_buffer == 0) input_buffer = new char[samples * frame];
00158 
00159         if(duplex_init && !record_before_play)
00160         {
00161 // block until playback starts
00162                 duplex_lock->lock("AudioDevice::read_buffer");
00163                 duplex_init = 0;
00164         }
00165 
00166         result = get_lowlevel_in()->read_buffer(input_buffer, samples * frame);
00167 
00168 // allow playback to start
00169         if(duplex_init && record_before_play)
00170         {
00171                 duplex_lock->unlock();
00172                 duplex_init = 0;
00173         }
00174 
00175 
00176         if(result < 0)
00177         {
00178                 perror("AudioDevice::read_buffer");
00179                 sleep(1);
00180         }
00181 
00182         for(i = 0; i < channels && i < get_ichannels(); i++)
00183         {
00184                 input_channel = &input[i][input_offset];
00185                 dc_offset_value = dc_offset_thread->dc_offset[i];
00186 
00187 // calculate minimum and maximum samples
00188                 if(dc_offset_thread->dc_offset[i] <= 0) 
00189                 { 
00190                         min_sample[i] = -denominator - dc_offset_thread->dc_offset[i]; 
00191                         max_sample[i] = denominator; 
00192                 }
00193                 else 
00194                 { 
00195                         min_sample[i] = -denominator; 
00196                         max_sample[i] = denominator - dc_offset_thread->dc_offset[i]; 
00197                 }
00198                 max[i] = 0; 
00199                 over_count = 0;
00200 
00201 // device is set to little endian
00202                 switch(bits)
00203                 {
00204                         case 8:
00205                                 if(dc_offset_thread->getting_dc_offset)
00206                                 {
00207                                         dc_offset_total = &(dc_offset_thread->dc_offset_total[i]);
00208                                         for(j = 0, k = i; j < samples; j++)
00209                                         {
00210                                                 GET_8BIT_SAMPLE_MACRO1
00211                                                 (*dc_offset_total) += (int)sample;
00212                                                 GET_8BIT_SAMPLE_MACRO2
00213                                                 GET_PEAK_MACRO
00214                                         }
00215                                 }
00216                                 else
00217                                 {
00218                                         for(j = 0, k = i; j < samples; j++)
00219                                         {
00220                                                 GET_8BIT_SAMPLE_MACRO1
00221                                                 GET_8BIT_SAMPLE_MACRO2
00222                                                 GET_PEAK_MACRO
00223                                         }
00224                                 }
00225                                 break;
00226                                 
00227                         case 16:
00228                                 {
00229                                         int16_t *input_buffer_16;
00230                                         input_buffer_16 = (int16_t *)input_buffer;
00231                                         dc_offset_total = &(dc_offset_thread->dc_offset_total[i]);
00232                                         
00233                                         if(dc_offset_thread->getting_dc_offset)
00234                                         {
00235                                                 for(j = 0, k = i; j < samples; j++)
00236                                                 {
00237                                                         GET_16BIT_SAMPLE_MACRO1
00238                                                         (*dc_offset_total) += (int)sample;
00239                                                         GET_16BIT_SAMPLE_MACRO2
00240                                                         GET_PEAK_MACRO
00241                                                 }
00242                                         }
00243                                         else
00244                                         {
00245                                                 for(j = 0, k = i; j < samples; j++)
00246                                                 {
00247                                                         GET_16BIT_SAMPLE_MACRO1
00248                                                         GET_16BIT_SAMPLE_MACRO2
00249                                                         GET_PEAK_MACRO
00250                                                 }
00251                                         }
00252                                 }
00253                                 break;
00254                                 
00255                         case 24:
00256                                 {
00257                                         dc_offset_total = &(dc_offset_thread->dc_offset_total[i]);
00258                                         
00259                                         if(dc_offset_thread->getting_dc_offset)
00260                                         {
00261                                                 for(j = 0, k = i * 3; j < samples; j++)
00262                                                 {
00263                                                         GET_24BIT_SAMPLE_MACRO1
00264                                                         (*dc_offset_total) += (int)sample;
00265                                                         GET_24BIT_SAMPLE_MACRO2
00266                                                         GET_PEAK_MACRO
00267                                                 }
00268                                         }
00269                                         else
00270                                         {
00271                                                 for(j = 0, k = i * 3; j < samples; j++)
00272                                                 {
00273                                                         GET_24BIT_SAMPLE_MACRO1
00274                                                         GET_24BIT_SAMPLE_MACRO2
00275                                                         GET_PEAK_MACRO
00276                                                 }
00277                                         }
00278                                 }
00279                                 
00280                         case 32:
00281                                 {
00282                                         dc_offset_total = &(dc_offset_thread->dc_offset_total[i]);
00283                                         
00284                                         if(dc_offset_thread->getting_dc_offset)
00285                                         {
00286                                                 for(j = 0, k = i * 4; j < samples; j++)
00287                                                 {
00288                                                         GET_32BIT_SAMPLE_MACRO1
00289                                                         (*dc_offset_total) += (int)sample;
00290                                                         GET_32BIT_SAMPLE_MACRO2
00291                                                         GET_PEAK_MACRO
00292                                                 }
00293                                         }
00294                                         else
00295                                         {
00296                                                 for(j = 0, k = i * 4; j < samples; j++)
00297                                                 {
00298                                                         GET_32BIT_SAMPLE_MACRO1
00299                                                         GET_32BIT_SAMPLE_MACRO2
00300                                                         GET_PEAK_MACRO
00301                                                 }
00302                                         }
00303                                 }
00304                                 break;
00305                 }
00306                 if(over_count >= 3) over[i] = 1; else over[i] = 0;
00307         }
00308 
00309         if(dc_offset_thread->getting_dc_offset) 
00310         {
00311                 dc_offset_thread->dc_offset_count += samples * channels;
00312                 if(dc_offset_thread->progress->update(dc_offset_thread->dc_offset_count, 1))
00313                 {
00314                         dc_offset_thread->getting_dc_offset = 0;
00315                         dc_offset_thread->dc_offset_lock->unlock();
00316                 }
00317                 else
00318                 if(dc_offset_thread->dc_offset_count > 256000)
00319                 {
00320                         for(i = 0; i < get_ichannels(); i++)
00321                         {
00322                                 dc_offset_thread->dc_offset[i] = dc_offset_thread->dc_offset_total[i] / dc_offset_thread->dc_offset_count * 2; // don't know why * 2
00323                         }
00324                         dc_offset_thread->getting_dc_offset = 0;
00325                         dc_offset_thread->dc_offset_lock->unlock();
00326                 }
00327         }
00328         return result < 0;
00329 }

Generated on Sun Jan 8 13:38:50 2006 for Cinelerra-svn by  doxygen 1.4.4