home *** CD-ROM | disk | FTP | other *** search
/ Mods Anthology 4 / Music-AmigaModsAnthology-4of4-Psychodk.mcsteam.iso / Tools / BeBox / Ralf_Tracker_0.3_Src / notes.c < prev    next >
Encoding:
C/C++ Source or Header  |  1995-11-16  |  2.5 KB  |  120 lines

  1. /* notes.c */
  2.  
  3. /* $Id: notes.c,v 3.5 1993/11/17 15:31:16 espie Exp espie $
  4.  * $Log: notes.c,v $
  5.  * Revision 3.5  1993/11/17  15:31:16  espie
  6.  * *** empty log message ***
  7.  *
  8.  * Revision 3.4  1993/11/11  20:00:03  espie
  9.  * Amiga support.
  10.  *
  11.  * Revision 3.2  1992/11/20  14:53:32  espie
  12.  * Added finetune.
  13.  *
  14.  * Revision 3.1  1992/11/19  20:44:47  espie
  15.  * Protracker commands.
  16.  *
  17.  * Revision 3.0  1992/11/18  16:08:05  espie
  18.  * New release.
  19.  *
  20.  */
  21.  
  22. #ifdef AMIGA
  23. #include <stdlib.h>
  24. #else
  25. //#include <malloc.h>
  26. #endif
  27. #include <stdio.h>
  28. #include <string.h>
  29. #include <ctype.h>
  30. #include <assert.h>
  31. #include <math.h>
  32.  
  33. #include "defs.h"
  34. #include "extern.h"
  35. #include "song.h"
  36. #include "channel.h"
  37.  
  38. LOCAL char *id = "$Id: notes.c,v 3.5 1993/11/17 15:31:16 espie Exp espie $";
  39.  
  40.  
  41. /* the musical notes correspond to some specific pitch.
  42.  * It's useful to be able to find them back, at least for
  43.  * arpeggii.
  44.  */
  45. int pitch_table[NUMBER_NOTES][NUMBER_FINETUNES];
  46. char note_name[NUMBER_NOTES][4];
  47.  
  48. char *note_template[12] = {"C-", "C#", "D-", "D#", "E-", "F-", "F#", "G-",
  49. "G#", "A-", "A#", "B-"};
  50.  
  51. /* find_note(pitch): find note corresponding to the stated pitch */
  52. int find_note(pitch)
  53. int pitch;
  54.     {
  55.     int a, b, i;
  56.     if (pitch == 0)
  57.         return -1;
  58.     a = 0;
  59.     b = NUMBER_NOTES-1;
  60.     while(b-a > 1)
  61.         {
  62.         i = (a+b)/2;
  63.         if (pitch_table[i][0] == pitch)
  64.             return i;
  65.         if (pitch_table[i][0] > pitch)
  66.             a = i;
  67.         else
  68.             b = i;
  69.         }
  70.     if (pitch_table[a][0] - FUZZ <= pitch)
  71.         return a;
  72.     if (pitch_table[b][0] + FUZZ >= pitch)
  73.         return b;
  74.     return NO_NOTE;
  75.     }
  76.  
  77. void create_notes_table()
  78.     {
  79.     double base, pitch;
  80.     int i, j, k;
  81.  
  82.     for (j = -8; j < 8; j++)
  83.         {
  84.         k = j < 0 ? j + 16 : j;
  85.         base = AMIGA_CLOCKFREQ/440.0/4.0 / pow(2.0, j/96.0);
  86.  
  87.         for (i = 0; i < NUMBER_NOTES; i++)
  88.             {
  89.             pitch = base / pow(2.0, i/12.0);
  90.             pitch_table[i][k] = floor(pitch + 0.5);
  91.             if (j == 0)
  92.                 {
  93.                 note_name[i][0] = note_template[(i+9)%12][0];
  94.                 note_name[i][1] = note_template[(i+9)%12][1];
  95.                 note_name[i][2] = '0'+ (i-3)/12;
  96.                 note_name[i][3] = '\0';
  97.                 }
  98.             }
  99.         }
  100.     }
  101.  
  102. int transpose_song(s, transpose)
  103. struct song *s;
  104. int transpose;
  105.     {
  106.     int oldt;
  107.     int i, j, n;
  108.  
  109.     if (!s)
  110.         return 0;
  111.     oldt = s->info.transpose;
  112.     for (n = 0; n < s->info.maxpat; n++)
  113.         for (i = 0; i < BLOCK_LENGTH; i++)
  114.             for (j = 0; j < NUMBER_TRACKS; j++)
  115.                 if (s->info.pblocks[n].e[j][i].note != NO_NOTE)
  116.                     s->info.pblocks[n].e[j][i].note += transpose - oldt;
  117.     s->info.transpose = transpose;
  118.     return oldt;
  119.     }
  120.