head	1.5;
access;
symbols
	rel-0-2-1:1.4
	before_adj_struct:1.3.2.1
	jack:1.3.0.2
	rel-0-1-0:1.2
	rel-0-0-0:1.1;
locks; strict;
comment	@ * @;


1.5
date	2007.03.22.20.55.43;	author robertatwood;	state Exp;
branches;
next	1.4;

1.4
date	2006.04.05.21.53.36;	author robertatwood;	state Exp;
branches;
next	1.3;

1.3
date	2005.08.20.18.26.42;	author robertatwood;	state Exp;
branches
	1.3.2.1;
next	1.2;

1.2
date	2005.04.03.20.05.38;	author robertatwood;	state Exp;
branches;
next	1.1;

1.1
date	2004.04.16.11.36.56;	author robertatwood;	state Exp;
branches;
next	;

1.3.2.1
date	2006.01.04.00.06.03;	author robertatwood;	state Exp;
branches;
next	;


desc
@@


1.5
log
@Updated GPL text to reflect new address of Free Software foundation
Prepare to move repository to savannah.nongnu.org
@
text
@/**************************************************************
This file is part of the Variseq program.
Variseq -- a variable pitch and step sample sequencer
Copyright (C) 2004  Robert Atwood r.atwood (at) imperial (dot) ac (dot) uk

This program is free software; you can redistribute it and/or
modify it under the terms of the GNU General Public License
as published by the Free Software Foundation; either version 2
of the License, or (at your option) any later version.

This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
GNU General Public License for more details.

You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA 
See the file COPYING for more information
**************************************************************/


#include <math.h>
#include <pthread.h>
#include "constants.h"
#include "mysound.h"
#include "samples.h"
#include "notes.h"
#include "pattern.h"

extern pthread_mutex_t rewrite_lock;
extern samples * sampletable;

void note:: setsample(int snum,int nnum){
    if (snum == N_NONE || nnum == N_NONE) return;
    mybuf = sampletable->get_note(snum,noteoctave,nnum);
    if (mybuf == NULL) return;

    samplenum = snum;
    notelevel = nnum;
}

void note::setsample(int snum){
    if (notelevel == N_NONE) notelevel = 0;
    mybuf = sampletable->get_note(snum,noteoctave,notelevel);
    if (mybuf == NULL) return;

    samplenum = snum;
}
void note::setnote(int nlev){
    if (samplenum == N_NONE) return;

    mybuf = sampletable->get_note(samplenum,noteoctave,nlev);

    notelevel = nlev;
}
void note::setoctave(int oct){
   if(oct >= N_OCT || oct < 0 ) return;
   noteoctave = oct;
   if (samplenum == N_NONE || notelevel == N_NONE) return;
   mybuf = sampletable->get_note(samplenum,noteoctave,notelevel);
}
void note::setsmooth(float sm){
   smooth = (int)(floorf( (sm/100) * rlen ));
}

void note::setframes(int fpt){
    if (ticks < 0 ) {
       fprintf(stderr,"ERROR: note::setframes:neagive ticks! %i\n",ticks);
    }
    rlen = fpt * ticks;
    startframe = fpt*starttick;
}

/* write a note into the buffer */
/* this needs to take care of looping and overwriting neighbouring notes */
void note::write(sbuf * buf){
     float ch1,ch2,sm=1,mvol;
     float in1,in2;
     int bufpos,i;
     int nextnum;
     int nextlen;
     note * thenote;

     mvol = parent->vol;

        #ifndef JUNKCLIP 
        /* don't do anything for unused notes */
        /* TODO -- what happens on wraparound?*/
        if (state == 2 ) return;
        #endif /* CLIP */

     /* no sample or no note in the slot */
     if (state == 0 || mybuf == NULL){
        tlen = rlen;
        oldtlen=rlen;
        nover = 0;
        oldnover=0;
     } else {

   #ifdef JUNK
   pthread_mutex_lock(&rewrite_lock);
   #ifndef NOPRINT
   printf("%s locked rewrite\n",__func__);
   #endif
   #endif

     #ifndef CLIP
     /* figure out how many frames can be placed in the buffer without */
     /* overwriteing the next played note */
        oldtlen=tlen;
        oldnover=nover;
        tlen = rlen;
        nover=0;
        thenote = this;

        /* find how many notes to overwrite */
        #ifdef DEBUG_NOTE
        fprintf(stderr,"note %i mybuf %x binfo %x\n",my_num,mybuf,mybuf->binfo);
        #endif
        while  ( tlen < mybuf->binfo->frames){

            thenote = thenote->next;
            if (thenote->state != 0 ){
               break;
            }

            tlen += thenote->rlen;
            nover++;
            thenote->state = 2; /* overwritten this cycle */
        }
      #else
        nover = 0;
        tlen = this->rlen;
      #endif /* CLIP */
      #ifdef DUMPSTATE
        printf("nover %i:%i\n",my_num,nover);
      #endif /*DUMPSTATE*/

   #ifdef JUNK
   #ifndef NOPRINT
   printf("%s unlocking rewrite\n",__func__);
        #endif
   pthread_mutex_unlock(&rewrite_lock);
   #endif
     }




     bufpos=startframe;
     for (i=0;i<tlen;i++){

     if (samplenum == N_NONE || notelevel == N_NONE){
          /* this should only be for initializing the new buffer */  
          /* TODO don't zero the note execpt for initializing */
          ch1 = 0;
          ch2 = 0;
      }else{
          if (i>= mybuf->binfo->frames) break;
          in1 = mybuf->buffer[2*i];
          in2 = mybuf->buffer[2*i+1];
          if (fabsf(in1) > clip) {
              in1 = copysignf(clip,in1);
          }
          if (fabsf(in2) > clip) {
              in2 = copysignf(clip,in2);
          }
          ch1 = state * 2 * mvol* vol * pan * in1;
          ch2 = state * 2 * mvol * vol * (1-pan) * in2;
      }

      /* loop the buffer */
      if (bufpos >= buf->binfo->frames){
	      bufpos = 0;
	   }
	   /* smooth the end */
	   if (i >= tlen - smooth){
	      sm = (tlen -i )/((double)(smooth));
	   }

		 #ifdef PRINTSAMPLES
		 printf("%f %f\n",ch1,ch2);
		 #endif
		 buf->buffer[2*bufpos] =   sm * ch1;
		 buf->buffer[2*bufpos+1] = sm * ch2;
	    bufpos++;
	 }
	 /* fill up the beat with zero */
	 /* have to get samples -per-beat  */
    for(;i<oldtlen;i++){
       if (bufpos >= buf->binfo->frames){
		    bufpos = 0;
	    }
		 buf->buffer[2*bufpos] = 0;
		 buf->buffer[2*bufpos+1] = 0;
	    bufpos++;
	}

}/* end of note::write */
void note::overwrite(sbuf * buf){
    int i,bufpos;
    
    switch (state){
       case (0): /* note is not used or overwritten */
			        /* zero the sound for this note */
			 bufpos = startframe;
			 for (i=0;i<rlen;i++){
				 if (bufpos >= buf->binfo->frames){
					 bufpos = 0;
				 }
			 buf->buffer[2*bufpos] =   0;
			 buf->buffer[2*bufpos+1] = 0;
			 bufpos++;
			}
          break;
       case (1): /* note is used */
          break;
       case (2): /* note was overwritten */
                 /* reset the state flag */
            state = 0;
          break;
       default:
          fprintf(stderr,"Error: %s: illegal value %i \n",__func__,state);
          break;
     }
}/* end of note::overwrite */

void note::dumpnote(FILE * fp){
   fprintf(fp,"samplenum %i\n",samplenum);
   fprintf(fp,"notelevel %i\n",notelevel);
   fprintf(fp,"my_num %i\n",my_num);

   fprintf(fp,"vol %f\n",vol);
   fprintf(fp,"clip %f\n",clip);
   fprintf(fp,"pan %f\n",pan);

   fprintf(fp,"smooth %i\n",smooth);
   fprintf(fp,"slen %i\n",slen);
   fprintf(fp,"rlen %i\n",rlen);
   fprintf(fp,"startframe %i\n",startframe);
   fprintf(fp,"starttick %i\n",starttick);
   fprintf(fp,"ticks %i\n",ticks);
   fprintf(fp,"state %i\n",state);
 }





     


    
    
/* $Id: notes.C,v 1.4 2006/04/05 21:53:36 robertatwood Exp $ */
@


1.4
log
@Jack version is the main branch now
@
text
@d18 1
a18 1
Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA  02111-1307, USA.
d22 1
d256 1
a256 1
/* $Id: notes.C,v 1.3.2.1 2006/01/04 00:06:03 robertatwood Exp $ */
@


1.3
log
@Added a save/restore workspace function
Added window to display names of samples
@
text
@d23 1
d30 1
d93 1
a93 1
     if (state == 0){
d100 7
d117 3
d121 1
d139 6
d255 1
a255 1
/* $Id: notes.C,v 1.2 2005/04/03 19:05:10 robert Exp $ */
@


1.3.2.1
log
@Jack input as well, and scrambling in compile-time option
@
text
@a22 1
#include <pthread.h>
a28 1
extern pthread_mutex_t rewrite_lock;
d91 1
a91 1
     if (state == 0 || mybuf == NULL){
a97 7
   #ifdef JUNK
   pthread_mutex_lock(&rewrite_lock);
   #ifndef NOPRINT
   printf("%s locked rewrite\n",__func__);
   #endif
   #endif

a107 3
        #ifdef DEBUG_NOTE
        fprintf(stderr,"note %i mybuf %x binfo %x\n",my_num,mybuf,mybuf->binfo);
        #endif
a108 1

a125 6
   #ifdef JUNK
   #ifndef NOPRINT
   printf("%s unlocking rewrite\n",__func__);
        #endif
   pthread_mutex_unlock(&rewrite_lock);
   #endif
d236 1
a236 1
/* $Id: notes.C,v 1.3 2005/08/20 18:26:42 robertatwood Exp $ */
@


1.2
log
@Changed the buffer writing so that samples extend into unused notes.
Altered file choose usage to correctly use the FLTK chooser
@
text
@@


1.1
log
@Initial version uploaded to Sourceforge
@
text
@d71 1
d78 4
d84 47
d132 1
a132 3
     for (i=0;i<rlen;i++){
          /* don't allow overwriting the next beat for now*/
          /*TODO: test if the next beat is used, write if it is not */
d135 2
d158 2
a159 2
	   if (i >= rlen - smooth){
	      sm = (rlen -i )/((double)(smooth));
d171 1
a171 1
    for(;i<rlen;i++){
d181 27
d236 1
a236 1
/* $Id: notes.C,v 1.9 2004/04/12 13:22:33 robert Exp $ */
@

