Esempio n. 1
0
void scanMusic(voice_index voice_, short *left_over)
{
  struct LOC_scanMusic V;
  Char buf[256], enote[256], xnote[256];
  boolean has_next = false, done = false;
  Char dur1, lastdur;
  music_word nscan;
  Char STR1[256];

  V.voice = voice_;
  strcpy(terminators, "d.x");
  resetInfo(V.voice, buf);
  *left_over = 0;
  V.store_macro = false;
  V.bar = full_bar;
  V.bar_length = 0;
  V.ngrace = 0;
  V.nmulti = 0;
  if (meternum == 0)
    V.bar = 32000;
  dur1 = duration(V.voice);
  lastdur = dur1;
  do {
    getNextMusWord(buf, V.note, &nscan);
    if (*V.note == '\0')
      break;
    V.count = 0;
    /*    if isNoteOrRest(note) and not (isPause(note) or isMultibarRest(note))
          then note:=toStandard(note); */
    V.doublex = (pos1('D', V.note) > 0);
    if (nscan == mword) {
      if (*V.note == '\0')
	error3(V.voice, "You may not end a line with a meter change");
      if (V.bar_length > 0)
	error3(V.voice, "Meter change only allowed at start of bar");
      else
	V.bar = barLength(V.note);
    } else if (nscan == rword) {
      if (!(isPause(V.note) || isMultiBarRest(V.note))) {
	processNote(V.note, xnote, dur1, &lastdur, &V.count);
	checkSticky(V.note, rest_attrib[V.voice-1]);
      }
    }
    if (*V.note != '\0')
      appendNote(V.voice, nscan);
    strcpy(enote, V.note);
    if (nscan == macro || nscan == endmacro)
      examineMacro(&V);
    if (nscan == abcdefg) {
      if (!multi_bar_rest && V.ngrace + V.nmulti == 0) {
	processNote(enote, xnote, dur1, &lastdur, &V.count);
	if (*xnote != '\0') {
	  checkSticky(enote, note_attrib[V.voice-1]);
	  appendToLine(V.voice, enote);
	  appendNote(V.voice, nscan);
	  strcpy(enote, xnote);
	}
	checkSticky(enote, note_attrib[V.voice-1]);
      }
    }
    appendToLine(V.voice, enote);
    if (*V.note == '\0')   /* !!! else word_bound[here]:=length(line); */
      done = true;
    sprintf(STR1, "%c", barsym);
    if (!strcmp(V.note, STR1)) {
      if (meternum == 0)
	error3(V.voice, "You may not use bar lines in barless music");
      else if (V.bar_length == 0)
	markBar(V.voice);
      else if (numberOfBars(V.voice) == 0 && V.bar_length < V.bar) {
	if (has_next)
	  has_next = false;   /*Should check whether pickups are equal*/
	else if (*left_over > 0)
	  error3(V.voice, "Bar is too short");
	*left_over = V.bar_length;
	V.bar_length = 0;
      }
    }
    if (nscan == nextvoice) {
      if (V.bar_length > 0)
	error3(V.voice, "Next voice before bar is full");
      else
	barForward(V.voice, -1);
      has_next = true;
    } else if (isPause(V.note))
      V.bar_length += V.bar;
    else if (!multi_bar_rest) {   /*do nothing*/
      if (!done && isNoteOrRest(V.note))
	countIt(&V);
      else
	maybeGroup(&V);
    }
    dur1 = lastdur;
    if (V.bar_length >= V.bar && V.ngrace + V.nmulti == 0 && !V.store_macro) {
      if (debugMode())
	printf("%d %d\n", V.voice, V.bar_length);
      barForward(V.voice, V.bar_length / V.bar);
      V.bar_length %= V.bar;
/* p2c: mtx.pas, line 268:
 * Note: Using % for possibly-negative arguments [317] */
    }
  } while (!done);
  setExtraLength(V.voice, V.bar_length);
  resetDuration(V.voice, dur1);
  regroup(V.voice);
}
Esempio n. 2
0
void testParagraph(void)
{
  voice_index0 voice;
  voice_index0 leader = 0, nv = 0;
  paragraph_index0 mus;
  short extra, l, nbar;
  voice_index0 FORLIM;
  Char STR2[256];
  Char STR4[256];

  nbars = 0;
  pickup = 0;
  nleft = 0;
  if (top > bottom)
    return;
  pickup = 0;
  *multi_bar_rest = '\0';
  FORLIM = bottom;
  for (voice = top; voice <= FORLIM; voice++) {
    mus = musicLineNo(voice);
    if (mus > 0) {   /** -------------- Voice is present  ---- */
      nv++;
      line_no = orig_line_no[mus-1];
      scanMusic(voice, &l);
      if (*multi_bar_rest != '\0' && nv > 1)
	error("Multi-bar rest allows only one voice", print);
      if (!pmx_preamble_done) {
	if (voice == top)
	  pickup = l;
	else if (pickup != l)
	  error3(voice, "The same pickup must appear in all voices");
      }
      nbar = numberOfBars(voice);
      extra = ExtraLength(voice);
      if (*multi_bar_rest != '\0' && (nbar > 0 || extra > 0))
	error3(voice, "Multi-bar rest allows no other rests or notes");
      if (nbar > nbars || nbar == nbars && extra > nleft) {
	nbars = nbar;
	nleft = extra;
	leader = voice;
      }
      if (!final_paragraph && meternum > 0 && extra > 0) {
	printf("Line has %s\n", describe(STR2, nbar, extra));
	error("   Line does not end at complete bar", print);
      }
      if (pmx_preamble_done && l > 0 && meternum > 0) {
	printf("l=%d meternum=%d\n", l, meternum);
	error3(voice, "Short bar with no meter change");
      }
    }
  }
  if (!pmx_preamble_done) {
    xmtrnum0 = (double)pickup / one_beat;   /* Don't want an integer result */
    if (beVerbose())
      printf("Pickup = %d/64\n", pickup);
  }
  if (leader <= 0)
    return;
  FORLIM = bottom;
  for (voice = top; voice <= FORLIM; voice++) {
    if (musicLineNo(voice) > 0) {
      if (voice != leader) {
	mus = musicLineNo(voice);
	line_no = orig_line_no[mus-1];
	if (numberOfBars(voice) != numberOfBars(leader) ||
	    ExtraLength(voice) != ExtraLength(leader)) {
	  printf("Following line has %s\n",
		 describe(STR4, numberOfBars(voice), ExtraLength(voice)));
	  puts(musicLine(STR4, voice));
	  printf("Longest line has %s\n",
		 describe(STR2, numberOfBars(leader), ExtraLength(leader)));
	  puts(musicLine(STR2, leader));
	  error("Line duration anomaly", print);
	}
      }
    }
  }
}