home *** CD-ROM | disk | FTP | other *** search
/ OS/2 Shareware BBS: Multimed / Multimed.zip / rxwavsrc.zip / RxWavFIR.c < prev    next >
C/C++ Source or Header  |  2000-03-06  |  5KB  |  193 lines

  1. /*  RxWav
  2.    Copyright (C) 1999 2000  Giorgio Vicario
  3.  
  4.    This program is free software; you can redistribute it and/or modify
  5.    it under the terms of the GNU General Public License as published by
  6.    the Free Software Foundation; either version 2 of the License, or
  7.    (at your option) any later version.
  8.  
  9.    This program is distributed in the hope that it will be useful,
  10.    but WITHOUT ANY WARRANTY; without even the implied warranty of
  11.    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  12.    GNU General Public License for more details.
  13.  
  14.    You should have received a copy of the GNU General Public License
  15.    along with this program; if not, write to the Free Software
  16.    Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA     */
  17.  
  18. #define INCL_REXXSAA
  19. #include <os2emx.h>
  20. #include <stdlib.h>
  21. #include <stdio.h>
  22. #include <string.h>
  23. #include <regexp.h>
  24. #include <math.h>
  25. #include <float.h>
  26. #include "RxWav.h"
  27.  
  28. /***********************************************************************
  29. FIR: filtro a risposta finita all'impulso
  30. Vuole il puntatore ad una traccia gia' allocate, la durata in campioni,
  31. uno stem con i valori di ampiezza per ciascuna banda
  32. ***********************************************************************/
  33. ULONG
  34. WavGraphEQ (PCSZ name, LONG argc, const RXSTRING * argv,
  35.         PCSZ queuename, PRXSTRING retstr)
  36. {
  37.   PSHORT pCh = NULL;
  38.   ULONG nCamp, nbandeF;
  39.   float tmp;
  40.   double ampBanda[MAX], *coef;
  41.   RXSTEMDATA bandeFreq;
  42.   double sum, fh, fl;
  43.   INT i, j, nCoeff;
  44.   APIRET rc;
  45.  
  46.   if (argc != 3)
  47.     {
  48.       SendMsg (FUNC_GRAPHEQ, ERR_NUMERO_PARAMETRI);
  49.       return INVALID_ROUTINE;
  50.     }
  51.  
  52.   if (!sscanf (argv[0].strptr, "%d", &pCh))
  53.     {
  54.       SendMsg (FUNC_GRAPHEQ, ERR_PUNTATORE_ERRATO);
  55.       return INVALID_ROUTINE;
  56.     }
  57.  
  58.   nCamp = atol (argv[1].strptr);
  59.   if (!nCamp)
  60.     {
  61.       SendMsg (FUNC_GRAPHEQ, ERR_NUMERO_CAMPIONI);
  62.       return INVALID_ROUTINE;
  63.     }
  64.  
  65.   bandeFreq.count = 0;
  66.   strcpy (bandeFreq.varname, argv[2].strptr);
  67.   bandeFreq.stemlen = argv[2].strlength;
  68.   strupr (bandeFreq.varname);
  69.   if (bandeFreq.varname[bandeFreq.stemlen - 1] != '.')
  70.     bandeFreq.varname[bandeFreq.stemlen++] = '.';
  71.   if (FetchStem (bandeFreq, &tmp))
  72.     {
  73.       SendMsg (FUNC_GRAPHEQ, ERR_LETTURA_STEM);
  74.       printf ("       RexxVariablePool rc:%i\n", bandeFreq.shvb.shvret);
  75.       return INVALID_ROUTINE;
  76.     }
  77.   else
  78.     bandeFreq.count = tmp;
  79.  
  80.   if (bandeFreq.count > MAX)
  81.     {
  82.       SendMsg (FUNC_GRAPHEQ, ERR_STEM_MASSIMO);
  83.       return INVALID_ROUTINE;
  84.     }
  85.  
  86.   nbandeF = bandeFreq.count;
  87.   bandeFreq.count = 0;
  88.   pCh = AllineaCh (pCh, nCamp, FUNC_GRAPHEQ);
  89.   if (!pCh)
  90.     return INVALID_ROUTINE;
  91.  
  92.   for (i = 0; i < nbandeF; i++)
  93.     {
  94.       bandeFreq.count++;
  95.       if (FetchStem (bandeFreq, &tmp))
  96.     {
  97.       SendMsg (FUNC_GRAPHEQ, ERR_LETTURA_STEM);
  98.       printf ("       RexxVariablePool rc:%i\n", bandeFreq.shvb.shvret);
  99.       return INVALID_ROUTINE;
  100.     }
  101.       ampBanda[i + 1] = (double) tmp;
  102.     }
  103.  
  104.   nCoeff = 32 + nbandeF * 32;
  105.   fvec (coef, nCoeff);
  106.   fl = (double) (20480 / ((double) FreqCamp / 2));
  107.   fh = 1;
  108.   for (i = 0; i < nCoeff; i++)
  109.     coef[i] = 0;
  110.  
  111.   for (j = nbandeF; j != 0; j--)
  112.     {
  113.       fl = fl / pow ((double) 2048, (double) (1 / (double) nbandeF));
  114.       FIRCoef (coef, (int) nCoeff, fl, fh, ampBanda[j]);
  115.       fh = fl;
  116.     }
  117.  
  118.   pCh = pCh + nCamp;
  119.   for (i = nCamp - nCoeff; i != 0; i--)
  120.     {
  121.       sum = 0.0;
  122.       for (j = nCoeff; j != 0; j--)
  123.     {
  124.       sum += coef[j] * *pCh--;
  125.     }
  126.       pCh = pCh + nCoeff;
  127.       *pCh-- = (SHORT) sum;
  128.     }
  129.  
  130.   for (i = nCoeff; i != 0; i--)
  131.     {
  132.       sum = 0.0;
  133.       for (j = nCoeff; j != 0; j--)
  134.     {
  135.       sum += coef[j] * *pCh--;
  136.     }
  137.       pCh = pCh + nCoeff--;
  138.       *pCh-- = (SHORT) sum;
  139.     }
  140.  
  141.  
  142.  
  143.   retstr->strlength = strlen (retstr->strptr);
  144.   return VALID_ROUTINE;
  145. }
  146.  
  147.  
  148.  
  149.  
  150. int
  151. FIRCoef (double *cf, int Len, double fl, double fh, double amp)
  152. {
  153.   int i;
  154.   double *Coef;
  155.  
  156.   double Sum, TmpFloat;
  157.   int CoefNum, HalfLen, Cnt;
  158.  
  159.   fvec (Coef, 8192);
  160.  
  161.   CoefNum = Len;
  162.   if (Len % 2 == 0)
  163.     {
  164.       CoefNum++;
  165.     }
  166.   HalfLen = (CoefNum - 1) / 2;
  167.  
  168.  
  169.   Coef[HalfLen] = fh - fl;
  170.   for (Cnt = 1; Cnt <= HalfLen; Cnt++)
  171.     {
  172.       TmpFloat = M_PI * Cnt;
  173.       Coef[HalfLen + Cnt] = 2.0 * sin ((fh - fl) / 2.0 * TmpFloat) *
  174.     cos ((fh + fl) / 2.0 * TmpFloat) / TmpFloat;
  175.       Coef[HalfLen - Cnt] = Coef[HalfLen + Cnt];
  176.     }
  177.  
  178.   TmpFloat = 2.0 * M_PI / (CoefNum - 1.0);
  179.   Sum = 0.0;
  180.   for (Cnt = 0; Cnt < CoefNum; Cnt++)
  181.     {
  182.       Coef[Cnt] *= (0.54 - 0.46 * cos (TmpFloat * Cnt));
  183.       Sum += Coef[Cnt];
  184.     }
  185.  
  186.   for (Cnt = 0; Cnt < CoefNum; Cnt++)
  187.     cf[Cnt] = cf[Cnt] + Coef[Cnt] * amp;
  188.  
  189.   free (Coef);
  190.  
  191.   return 0;
  192. }
  193.