Пример #1
0
float TRACK_get_max_pitch(const struct Tracks *track){
  float max_pitch = -1;

  int num_pitches = 0;
  
  {
    struct Notes *note = track->notes;
    while(note!=NULL){
      max_pitch = R_MAX(note->note, max_pitch);
      num_pitches ++;
      struct Pitches *pitch = note->pitches;
      while(pitch != NULL){
        max_pitch = R_MAX(pitch->note, max_pitch);
        num_pitches ++;
        pitch = NextPitch(pitch);
      }
      note = NextNote(note);
    }
  }

  if (num_pitches==0)
    return -1;
  else
    return max_pitch;
}
Пример #2
0
static void RT_scheduled_hold_pitch_do(struct SeqTrack *seqtrack,
                                       int64_t time,
                                       const struct SeqBlock *seqblock,
                                       const struct Tracks *track,
                                       const struct Notes *note,
                                       const struct Pitches *pitch1,
                                       bool doit
                                       )
{
  struct Patch *patch = track->patch;

  if (patch!=NULL && pitch1!=NULL && doit) {
    
    float val = pitch1->note;

#if DO_DEBUG
    printf("  Sending HOLD pitch %f at %d\n",val,(int)time);
#endif
    
    RT_PATCH_change_pitch(seqtrack,
                          patch,
                          create_note_t2(seqblock,note->id, val),
                          time
                          );
  }

  const struct Pitches *pitch2 = pitch1==NULL ? note->pitches : NextPitch(pitch1);
  if (pitch2 != NULL)
    RT_schedule_pitch(seqtrack, time, seqblock, track, note, pitch2, false);
}
Пример #3
0
static int64_t RT_scheduled_glide_pitch(struct SeqTrack *seqtrack, int64_t time, union SuperType *args){
  const struct SeqBlock   *seqblock  = args[0].const_pointer;
  const struct Tracks     *track     = args[1].const_pointer;
  const struct Notes      *note      = args[2].pointer;
  const struct Pitches *pitch1 = args[3].pointer;
  int64_t                  time1     = args[4].int_num;
  int64_t                  time2     = args[5].int_num;
  bool                     doit      = args[6].bool_num;

  struct Patch *patch = track->patch;

  if (patch==NULL)
    return DONT_RESCHEDULE;

#if !defined(RELEASE)
  if (time < time1 || time>time2)
    RError("RT_scheduled_glide_pitch: time: %d, time1: %d, time2: %d", time, time1, time2);
#endif
  
  if (time < time1)
    time = time1;
  if (time > time2)
    time = time2;

  const struct Pitches *pitch2 = pitch1==NULL ? note->pitches : NextPitch(pitch1);

  if (doit) {
    float val1 = pitch1==NULL ? note->note      : pitch1->note;
    float val2 = pitch2==NULL ? note->pitch_end : pitch2->note;
    
    float val = time1==time2 ? val2 : scale(time, time1, time2, val1, val2); // We get divide by zero in scale() if time1==time2
    
#if DO_DEBUG
    printf("  Sending pitch %f at %d\n",val,(int)time);
#endif

    if (time==time1 || val1!=val2)
      RT_PATCH_change_pitch(seqtrack,
                            patch,
                            create_note_t2(seqblock,note->id, val),
                            time
                            );
  }
  
  if (time >= time2) {
    
    if (pitch2 != NULL)
      RT_schedule_pitch(seqtrack, time, seqblock, track, note, pitch2, true);
    
    return DONT_RESCHEDULE;
    
  } else {

    return R_MIN(time2, time + RADIUM_BLOCKSIZE);
    
  }
}
Пример #4
0
static void add_note(const struct WBlocks *wblock, vector_t *trs, struct Notes *note){
  TrackRealline2 *tr = talloc(sizeof(TrackRealline2));
  tr->p = note->l.p;
  tr->note = note;
  add_tr(wblock, trs, tr);

  struct Pitches *pitch = note->pitches;
  while(pitch != NULL){
    add_pitch(wblock, trs, note, pitch);
    pitch = NextPitch(pitch);
  }
}
Пример #5
0
void Transpose_note(
	struct Notes *note,
	int trans
){
  note->note = getTransposed(note->note, trans);
  if (note->pitch_end > 0)
    note->pitch_end = getTransposed(note->pitch_end, trans);
  
  struct Pitches *pitch = note->pitches;
  while(pitch!=NULL){
    pitch->note = getTransposed(pitch->note, trans);
    pitch = NextPitch(pitch);
  }
}
Пример #6
0
void AddPitchElements(
	struct Tracker_Windows *window,
	struct WBlocks *wblock,
	struct WTracks *wtrack
){

  float min_pitch = 10000.0f;
  float max_pitch = -10000.0f;

  TRACK_get_min_and_max_pitches(wtrack->track,&min_pitch, &max_pitch);

  struct Notes *note=wtrack->track->notes;

  while(note!=NULL){
    struct Pitches *pitch=note->pitches;
    int realline = 0;

    while(pitch!=NULL){

      realline=FindRealLineFor(wblock,R_MAX(pitch->Tline,realline),&pitch->l.p);
      int subrealline=FindSubRealLine(window,wblock,realline,&pitch->l.p);

      InsertTRLElementS(
			wtrack,
                        note,
			realline,
                        TRE_THISPITCHLINES,0,
			(float)subrealline,(float)subrealline,0.0f,(float)(wtrack->fxwidth-2),
			pitch
                        );
      
      if (wtrack->trackreallines[realline].note!=0) {
        wtrack->trackreallines[realline].note=NOTE_MUL;
	wtrack->trackreallines[realline].dasnote=NULL;
      } else {
        wtrack->trackreallines[realline].note=pitch->note;
        wtrack->trackreallines[realline].daspitch=pitch;
      }

      pitch=NextPitch(pitch);
    }

    #if !USE_OPENGL
    UpdateWPitches(window, wblock, wtrack, note, min_pitch, max_pitch);
    #endif
    
    note=NextNote(note);
  }
}
Пример #7
0
bool TRACK_get_min_and_max_pitches(const struct Tracks *track, float *ret_min_pitch, float *ret_max_pitch){
  float min_pitch = 10000.0f;
  float max_pitch = -10000.0f;

  int num_pitches = 0;
  
  // find min_pitch and max_pitch
  {
    struct Notes *note = track->notes;
    while(note!=NULL){
      min_pitch = R_MIN(note->note, min_pitch);
      max_pitch = R_MAX(note->note, max_pitch);
      num_pitches ++;
      struct Pitches *pitch = note->pitches;
      while(pitch != NULL){
        min_pitch = R_MIN(pitch->note, min_pitch);
        max_pitch = R_MAX(pitch->note, max_pitch);
        num_pitches ++;
        pitch = NextPitch(pitch);
      }
      note = NextNote(note);
    }

    float pitch_range = max_pitch - min_pitch;

    min_pitch = min_pitch - pitch_range/8.0f;
    if(min_pitch < 0)
      min_pitch = 0;

    max_pitch = max_pitch + pitch_range/8.0f;
    if(max_pitch >127)
      max_pitch = 127;
  }

  if(min_pitch == 10000.0f)
    return false;
  else {
    if (num_pitches>3) {
      *ret_min_pitch = min_pitch;
      *ret_max_pitch = max_pitch;
    } else {
      *ret_min_pitch = 0;
      *ret_max_pitch = 128;
    }
    return true;
  }
}
Пример #8
0
void CopyRange_pitches(
	struct Pitches **topitch,
	struct Pitches *frompitch,
	Place *p1,
	Place *p2
){
	struct Pitches *pitch;

	if(frompitch==NULL) return;

	if(PlaceGreaterOrEqual(&frompitch->l.p,p2)) return;

	pitch=tcopy(frompitch, sizeof(struct Pitches));

	PlaceSub(&pitch->l.p,p1);

	ListAddElement3(topitch,&pitch->l);

	CopyRange_pitches(topitch,NextPitch(frompitch),p1,p2);
}
Пример #9
0
static void PE_ChangePitch(struct PEventQueue *peq,int doit){
	float x;
	STime ntime,btime;
	struct Pitches *next;

	btime=PC_TimeToRelBlockStart(pc->end_time);

	if(btime>=peq->time2){
		next=NextPitch(peq->nextpitch);
		peq->time1=peq->time2;
		peq->pitch=peq->nextpitch;

		if(next==NULL){
			peq->time2=Place2STime(peq->block,&peq->note->end);
			peq->TreatMe=PE_ChangePitchToEnd;
			PE_ChangePitchToEnd(peq,doit);
		}else{
			peq->nextpitch=next;
			peq->time2=Place2STime(peq->block,&next->l.p);
			PE_ChangePitch(peq,doit);
		}
		return;
	}

        float pitch1,pitch2;
        if(peq->pitch==peq->nextpitch){
          pitch1=peq->note->note;
          pitch2=peq->pitch->note;
        }else{
          pitch1=peq->pitch->note;
          pitch2=peq->nextpitch->note;
        }

	ntime=PEQ_CalcNextPitchEvent(
                peq,
		peq->time1,
		btime,
		peq->time2,
                pitch1,
		&x,
                pitch2
	);

	if(btime==ntime){
		Pdebug("Samme, stopper, x: %d\n",x);
		return;
	}

	if(ntime>peq->time2)
          ntime=peq->time2;

//	Pdebug("Player vel->vel, Pitch: %d, ntime: %d, btime: %d, time1: %d, time2: %d\n",x,ntime,btime,peq->time1,peq->time2);
	if(doit){
		SendPitchChange(x,peq);
	}

	PC_InsertElement(peq,0,ntime);

	return;

}
Пример #10
0
static void RT_schedule_pitch(struct SeqTrack *seqtrack,
                              int64_t current_time,
                              const struct SeqBlock *seqblock,
                              const struct Tracks *track,
                              const struct Notes *note,
                              const struct Pitches *pitch1,
                              bool first_val_has_been_sent
                              )
{

  if(note->pitches==NULL && note->pitch_end == 0.0) // In case note is changed while playing
    return;

  const struct Pitches *pitch2 = pitch1==NULL ? note->pitches : NextPitch(pitch1);

  Place p1 = pitch1==NULL ? note->l.p : pitch1->l.p;
  Place p2 = pitch2==NULL ? note->end : pitch2->l.p;
  
  int64_t time1 = get_seqblock_place_time(seqblock, p1);
  int64_t time2 = get_seqblock_place_time(seqblock, p2);

  if (pitch2==NULL)
    time2--; // Can not send out pitch at the same time as note_end, since note_end events has higher priority than pitch events.
#if !defined(RELEASE)
  else
    R_ASSERT(time2 >= time1);
#endif
    
  if (time2 < time1)
    return;

  int logtype1 = pitch1==NULL ? note->pitch_first_logtype : pitch1->logtype;

  if (logtype1 == LOGTYPE_HOLD){

    if (current_time == time1) {
      
      RT_scheduled_hold_pitch_do(seqtrack, current_time, seqblock, track, note, pitch1, !first_val_has_been_sent);
                                    
    } else {
        
      const int num_args = 4;
    
      union SuperType args[num_args];
      args[0].const_pointer = seqblock;
      args[1].const_pointer = track;
      args[2].const_pointer = note;
      args[3].const_pointer = pitch1;
      
      SCHEDULER_add_event(seqtrack, time1, RT_scheduled_hold_pitch, &args[0], num_args, SCHEDULER_PITCH_PRIORITY);
    }
      
  } else {

    //int64_t time = R_MIN(time2, time1 + RADIUM_BLOCKSIZE);

    bool doit;

    if (pitch1==NULL)
      doit = true;
    else
      doit = pitch1->chance==0x100 || pitch1->chance > rnd(0x100);

    union SuperType args[g_num_pitches_args];
    args[0].const_pointer = seqblock;
    args[1].const_pointer = track;
    args[2].const_pointer = note;
    args[3].const_pointer = pitch1;
    args[4].int_num       = time1;
    args[5].int_num       = time2;
    args[6].bool_num      = doit;

#if DO_DEBUG
    float val1 = pitch1==NULL ? note->note      : pitch1->note;
    float val2 = pitch2==NULL ? note->pitch_end : pitch2->note;
    
    printf(" Scheduling Pitch. %f -> %f, %d -> %d\n", val1, val2, (int)time1, (int)time2);
#endif
  
    SCHEDULER_add_event(seqtrack, time1, RT_scheduled_glide_pitch, &args[0], g_num_pitches_args, SCHEDULER_PITCH_PRIORITY);

  }
}