home *** CD-ROM | disk | FTP | other *** search
/ Simtel MSDOS - Coast to Coast / simteldosarchivecoasttocoast2.iso / windows3 / mtlabsnd.zip / AVG.C < prev    next >
Text File  |  1993-04-26  |  3KB  |  152 lines

  1.  
  2. /*
  3.  * July 5, 1991
  4.  * Copyright 1991 Lance Norskog And Sundry Contributors
  5.  * This source code is freely redistributable and may be used for
  6.  * any purpose.  This copyright notice must be maintained. 
  7.  * Lance Norskog And Sundry Contributors are not responsible for 
  8.  * the consequences of using this software.
  9.  */
  10.  
  11. /*
  12.  * Sound Tools stereo/quad -> mono mixdown effect file.
  13.  *
  14.  * Does not mix up to more channels.
  15.  *
  16.  * What's in a center channel?
  17.  */
  18.  
  19. #include "st.h"
  20.  
  21. /* Private data for SKEL file */
  22. typedef struct avgstuff {
  23.     int    mix;            /* How are we mixing it? */
  24. } *avg_t;
  25.  
  26. #define MIX_CENTER    0
  27. #define MIX_LEFT    1
  28. #define MIX_RIGHT    2
  29.  
  30. /*
  31.  * Process options
  32.  */
  33. avg_getopts(effp, n, argv) 
  34. eff_t effp;
  35. int n;
  36. char **argv;
  37. {
  38.     avg_t avg = (avg_t) effp->priv;
  39.  
  40.     avg->mix = MIX_CENTER;
  41.     if (n)
  42.         if(!strcmp(argv[0], "-l"))
  43.             avg->mix = MIX_LEFT;
  44.         else if (!strcmp(argv[0], "-r"))
  45.             avg->mix = MIX_RIGHT;
  46.         else
  47.             fail("Averaging effect takes options '-l' or '-r'.");
  48. }
  49.  
  50. /*
  51.  * Start processing
  52.  */
  53. void
  54. avg_start(effp)
  55. eff_t effp;
  56. {
  57.     switch (effp->outinfo.channels) {
  58.         case 1: switch (effp->ininfo.channels) {
  59.             case 2: 
  60.             case 4:
  61.                 return;
  62.         }
  63.         case 2: switch (effp->ininfo.channels) {
  64.             case 4:
  65.                 return;
  66.         }
  67.     }
  68.     fail("Can't average %d channels into %d channels",
  69.         effp->ininfo.channels, effp->outinfo.channels);
  70. }
  71.  
  72. /*
  73.  * Process either isamp or osamp samples, whichever is smaller.
  74.  */
  75.  
  76. avg_flow(effp, ibuf, obuf, isamp, osamp)
  77. eff_t effp;
  78. long *ibuf, *obuf;
  79. int *isamp, *osamp;
  80. {
  81.     avg_t avg = (avg_t) effp->priv;
  82.     int len, done;
  83.     
  84.     switch (effp->outinfo.channels) {
  85.         case 1: switch (effp->ininfo.channels) {
  86.             case 2:
  87.                 len = ((*isamp/2 > *osamp) ? *osamp : *isamp/2);
  88.                 for(done = 0; done < len; done++) {
  89.                 switch(avg->mix) {
  90.                     case MIX_CENTER:
  91.                     *obuf++ = ibuf[0]/2 + ibuf[1]/2;
  92.                     break;
  93.                     case MIX_LEFT:
  94.                     *obuf++ = ibuf[0];
  95.                     break;
  96.                     case MIX_RIGHT:
  97.                     *obuf++ = ibuf[1];
  98.                     break;
  99.                 }
  100.                 }
  101.                 ibuf += 2;
  102.                 *isamp = len * 2;
  103.                 *osamp = len;
  104.                 break;
  105.             case 4:
  106.                 len = ((*isamp/4 > *osamp) ? *osamp : *isamp/4);
  107.                 for(done = 0; done < len; done++) {
  108.                     *obuf++ = ibuf[0]/4 + ibuf[1]/4 +
  109.                         ibuf[2]/4 + ibuf[3]/4;
  110.                     ibuf += 4;
  111.                 }
  112.                 *isamp = len * 4;
  113.                 *osamp = len;
  114.                 break;
  115.                 
  116.         }
  117.         break;
  118.         case 2: switch (effp->ininfo.channels) {
  119.             /*
  120.              * After careful inspection of CSOUND source code,
  121.              * I'm mildly sure the order is:
  122.              *     front-left, front-right, rear-left, rear-right
  123.              */
  124.             case 4:
  125.                 len = ((*isamp/2 > *osamp) ? *osamp : *isamp/2);
  126.                 len &= ~1;
  127.                 for(done = 0; done < len; done++) {
  128.                     obuf[0] = ibuf[0]/2 + ibuf[2]/2;
  129.                     obuf[1] = ibuf[1]/2 + ibuf[3]/2;
  130.                     ibuf += 4;
  131.                     obuf += 2;
  132.                 }
  133.                 *isamp = len * 2;
  134.                 *osamp = len;
  135.                 break;
  136.         }
  137.     }
  138. }
  139.  
  140. /*
  141.  * Do anything required when you stop reading samples.  
  142.  * Don't close input file! 
  143.  *
  144.  * Should have statistics on right, left, and output amplitudes.
  145.  */
  146. avg_stop(effp)
  147. eff_t effp;
  148. {
  149.     /* nothing to do */
  150. }
  151.  
  152.