/***************************/ /* texgen.c */ /***************************/ #include #include #include #include "maintypes.h" #include "defines.h" #include "texgen.h" void write_note(bindvar, beamstr) struct bind *bindvar; char beamstr[10]; { struct Note *notestart, *noteend; char accord_kind; char extremeposflag; /* shows that a position is lower than A */ short accord_type; char lastpos; char notepos[6]; char note[9]; char pflag, ppflag; /* for storing information about points */ pflag = 0; ppflag = 0; notestart = (struct Note *) bindvar->data; noteend = notestart; if ((noteend->flags) & 0x2) ppflag = 1; if ((noteend->flags) & 0x1) pflag = 1; accord_type = 0; lastpos = ((noteend->note_pos) & 0x3f); if (notestart->accord_next) { accord_type = (notestart->flags) & 0x38; if (((notestart->flags) & 0x38) >= 0x28) accord_kind = 'h'; else accord_kind = 'q'; while (noteend->accord_next) { extremeposflag = 0; if (((noteend->note_pos) & 0x3f) < 5) { fprintf( tfp, "{\\transpose=-7\\relax "); extremeposflag = 1; } sprintf( notepos, "%c", positions[(noteend->note_pos) & 0x3f]); if (ppflag) fprintf( tfp, "\\ppt %s", notepos); else if (pflag) fprintf( tfp, "\\pt %s", notepos); if ((noteend->flags) & 0x4) if ((noteend->flags) & 0x400) fprintf( tfp, "\\upz %s", notepos); else fprintf( tfp, "\\lpz %s", notepos); if (((noteend->note_pos) & 0xc0) == 0) sprintf( note, "%s", notepos); else if (((noteend->note_pos) & 0xc0) == 0x40) sprintf( note, "{^%c}", positions[(noteend->note_pos) & 0x3f]); else if (((noteend->note_pos) & 0xc0) == 0x80) sprintf( note, "{_%c}", positions[(noteend->note_pos) & 0x3f]); else sprintf( note, "{=%c}", positions[(noteend->note_pos) & 0x3f]); if ((lastpos + 1) == ((noteend->accord_next->note_pos) & 0x3f)) { if (note[1] == '^') fprintf( tfp, "\\lsh %s", notepos); if (note[1] == '_') fprintf( tfp, "\\lfl %s", notepos); if (note[1] == '=') fprintf( tfp, "\\lna %s", notepos); if (((!((notestart->beam_nr) && (beamstr))) && (!((notestart->flags) & 0x400))) || (((notestart->beam_nr) && (beamstr)) && ((*(beamstr + 1)) == 'h'))) { /* upper stem */ fprintf( tfp, "\\r"); } else { /* lower stem */ fprintf( tfp, "\\l"); } fprintf( tfp, "%c %s", accord_kind, notepos); } else { lastpos = (noteend->accord_next->note_pos) & 0x3f; fprintf( tfp, "\\z%c %s", accord_kind, note); } noteend = noteend->accord_next; if (extremeposflag) fprintf( tfp, "}"); } } noteend->flags |= accord_type; extremeposflag = 0; if (((noteend->note_pos) & 0x3f) < 5) { fprintf( tfp, "{\\transpose=-7\\relax "); extremeposflag = 1; } sprintf( notepos, "%c", positions[(noteend->note_pos) & 0x3f]); if (ppflag) fprintf( tfp, "\\ppt %s", notepos); else if (pflag) fprintf( tfp, "\\pt %s", notepos); if ((noteend->flags) & 0x4) if ((noteend->flags) & 0x400) fprintf( tfp, "\\upz %s", notepos); else fprintf( tfp, "\\lpz %s", notepos); if (((noteend->note_pos) & 0xc0) == 0) sprintf( note, " %s", notepos); else if (((noteend->note_pos) & 0xc0) == 0x40) sprintf( note, "{^%c}", positions[(noteend->note_pos) & 0x3f]); else if (((noteend->note_pos) & 0xc0) == 0x80) sprintf( note, "{_%c}", positions[(noteend->note_pos) & 0x3f]); else sprintf( note, "{=%c}", positions[(noteend->note_pos) & 0x3f]); if ((notestart->beam_nr) && (beamstr)) { fprintf(tfp, "\\%s%s", beamstr, note); } else { fprintf( tfp, "\\%s", notecode[((noteend->flags) & 0x38) >> 3]); if (!(((notestart->flags) & 0x38) == 0x30)) { if ((notestart->flags) & 0x400) fprintf( tfp, "l"); else fprintf( tfp, "u"); } fprintf( tfp, "%s", note); } if (extremeposflag) fprintf( tfp, "}"); } /* put the times in relation to previous barre */ void prepare_times() { unsigned char i; unsigned long barrtime; for (i=0;imarker) == 'b') { barrtime = akt[i]->time; akt[i]->time = 0; } else akt[i]->time -= barrtime; akt[i] = akt[i]->next; } } } void delete_track(tr) int tr; { while (begin[tr]) { akt[tr] = begin[tr]->next; free(begin[tr]->data); free(begin[tr]); begin[tr] = akt[tr]; } } void write_texfile() { char flag, notready, readyflag, ksflag, tsflag, whilecrit, nothing; int i, j, index; int looping; struct bind *beghelp[MAXTRACKS]; char reghelp[MAXTRACKS]; char store; int startwith, zval; short events, innerbar; unsigned int measurecounter; unsigned int mintime; unsigned short l, k; int delflg; /* shows deleting of tracks */ short firstnom, kscontent, firstdenom; unsigned long slur[10], beam[10][3]; char beamstring[10], slur_and_beam[10], todelete[10]; char helpInst[MAXTRACKS][180]; prepare_times(); notready = 0; firstnom = 0; kscontent = 0; ksflag = 0; i = 0; /* wtmark1 */ while ((notready < CURRENTMAXTRACKS) && (imarker) == 't')) { ts = (struct TimeSig *) akt[i]->data; firstnom = ts->nom; firstdenom = ts->denom; } if ((akt[i]->marker) == 'n') flag = 1; if ((!ksflag) && ((akt[i]->marker) == 'k')) { ks = (struct KeySig *) akt[i]->data; kscontent = ks->sign; ksflag = 1; } akt[i] = akt[i]->next; } if ((!flag) && (begin[i])) delete_track(i); if (begin[i]) notready++; i++; } /* cut some tracks if neccesary because tex only support up to 9 */ delflg = 0; while (i 1) fprintf(stderr, "sorry, had to cut %d tracks\n", delflg); /* wtmark2 */ if (notready) { /* turn over the voices */ for (i=0; i=0; looping--) { if (begin[looping]) { zval = 0; while (zval < 180) { helpInst[startwith][zval] = Inst[looping][zval]; zval++; } reghelp[startwith] = region[looping]; beghelp[startwith++] = begin[looping]; } } for (i=0; imarker) == 'k') || ((akt[i]->marker) == 't'))) { if ((akt[i]->marker) == 't') { ts = (struct TimeSig *) akt[i]->data; if ((firstnom != ts->nom) || (firstdenom != ts->denom)) { fprintf(tfp, "\\metertoks%s={{\\meterfrac{%u}{%u}}", romans[i], ts->nom, ts->denom); if (region[i] == 0) fprintf(tfp, "{\\meterfrac{%u}{%u}}", ts->nom, ts->denom); fprintf(tfp, "}%c\n", '\045'); } } if ((akt[i]->marker) == 'k') { ks = (struct KeySig *) akt[i]->data; if (kscontent != ks->sign) { fprintf(tfp, "\\sign%s=", romans[i]); if ((ks->sign) & 0x80) fprintf(tfp, "-"); fprintf(tfp, "%u\n", (ks->sign) & 0xf); } } akt[i] = akt[i]->next; } } /* wtmark4 */ fprintf(tfp, "\\debutmorceau\n"); measurecounter = 1; fprintf(tfp, "%c measure %u\n", '\045', measurecounter); for (j=0; j<10; j++) { slur_and_beam[j] = 0; todelete[j] = 0; slur[j] = 0; beam[j][0] = 0; } readyflag = 1; events = 0; innerbar = 0; while (readyflag) { mintime = 0xfffffff; for (i=0; imarker) != 'b') && ((akt[i]->time) < mintime)) mintime = akt[i]->time; if (mintime == 0xfffffff) { /* ready or barres */ readyflag = 0; for (i=0; inext)) readyflag = 1; if (readyflag) { /* wtmark5: time for barre */ flag = 0; for (i=0; inext; if ((akt[i]) && (((akt[i]->marker) == 't') || ((akt[i]->marker) == 'k'))) flag = 1; } fprintf(tfp, "%c measure %u\n", '\045', ++measurecounter); if (!flag) { if ((events > LINEBREAKER) || (innerbar > INNERBARMAX)) { fprintf(tfp, "\\alaligne\n"); events = 0; } else { fprintf(tfp, "\\barre\n"); events += 3; } innerbar = 0; } else { for (i=0;imarker) == 'k') || ((akt[i]->marker) == 't')) { if ((akt[i]->marker) == 't') { ts = (struct TimeSig *) akt[i]->data; fprintf(tfp, "\\metertoks%s={{\\meterfrac{%u}{%u}}", romans[i], ts->nom, ts->denom); if (region[i] == 0) fprintf(tfp, "{\\meterfrac{%u}{%u}}", ts->nom, ts->denom); fprintf(tfp, "}%c\n", '\045'); } else { ks = (struct KeySig *) akt[i]->data; fprintf(tfp, "\\signaturegenerale{%u}\n", (ks->sign) & 0x8f); } akt[i] = akt[i]->next; } } fprintf(tfp, "\\changecontext\n"); } } } else { /* process all events of time mintime */ events ++; innerbar++; if (innerbar > INNERBARZ) { /* allow line breaking in the middle of a takt */ fprintf(tfp, "\\zbarre\n"); innerbar = 0; } ksflag = 0; tsflag = 0; for (i=0; itime) == mintime) && (((dynhelp->marker) == 'k') || ((dynhelp->marker) == 't'))) { switch (dynhelp->marker) { case 'k': ksflag = 1; ks = (struct KeySig *) dynhelp->data; fprintf(tfp, "\\sign%s=", romans[i]); if ((ks->sign) & 0x80) fprintf(tfp, "-"); fprintf(tfp, "%u\n", (ks->sign) & 0xf); break; case 't': tsflag = 1; ts = (struct TimeSig *) akt[i]->data; fprintf(tfp, "\\metertoks%s={{\\meterfrac{%u}{%u}}", romans[i], ts->nom, ts->denom); if (region[i] == 0) fprintf(tfp, "{\\meterfrac{%u}{%u}}", ts->nom, ts->denom); fprintf(tfp, "}%c\n", '\045'); break; default: fprintf (stderr, "warning: unknown element1\n"); break; } dynhelp = dynhelp->next; } akt[i] = dynhelp; } if (ksflag || tsflag) fprintf(tfp, "\\changecontext\n"); /* wtmark8 */ fprintf(tfp, "\\Notes"); for (i=0; i 0) fprintf(tfp, " & "); /* put a '&' between the satffs */ while ((akt[i]) && ((akt[i]->time) == mintime) && ((akt[i]->marker) != 'r') && ((akt[i]->marker) != 'n')) { switch (akt[i]->marker) { case 'l': ly = (struct Lyric *) akt[i]->data; if (!(region[i] & 0x1)) fprintf(tfp, "\\zcharnote {%s} {%s}", VIOLINELYRICPOSITION, ly->text); else fprintf(tfp, "\\zcharnote {%s} {%s}", BASSLYRICPOSITION, ly->text); break; case 'p': lo = (struct Loudness *) akt[i]->data; if (!(region[i] & 0x1)) fprintf(tfp, "\\zcharnote {%s} ", VIOLINELOUDNESSPOSITION); else fprintf(tfp, "\\zcharnote {%s} ", BASSLOUDNESSPOSITION); if (lo->statics) { /* deal with statics */ fprintf(tfp, "{%s}", static_loudness[(lo->statics) - 1]); } else { /* deal with dynamics */ fprintf(tfp, "{\\%s}", dynamic_loudness[(lo->dynamics) - 1]); } break; default: fprintf (stderr, "warning: unknown element2\n"); break; } akt[i] = akt[i]->next; } dynhelp = akt[i]; whilecrit = region[i]; for (j=0; j<10; j++) todelete[j] = 0; while (whilecrit < 5) { akt[i] = dynhelp; if (whilecrit == 4) fprintf(tfp, " | "); while ((akt[i]) && ((akt[i]->time) == mintime) && ((akt[i]->marker) != 'b')) { switch (akt[i]->marker) { case 'r': re = (struct Rest *) akt[i]->data; if (((whilecrit == 0) && (re->position & 0x40)) || ((whilecrit == 4) && (re->position & 0x80))) break; if (((re->position) & 0x3f) < 5) fprintf(tfp, "{\\transpose=-7\\relax "); if ((re->kind) < 5) { fprintf(tfp, "\\zcharnote {%c}{", positions[(re->position) & 0x3f]); if (re->flg) fprintf(tfp, "\\off{0.56\\noteskip}"); fprintf(tfp, "\\%s}", restcode[re->kind]); } else { fprintf(tfp, "\\ex%s ", restcode[re->kind]); fprintf(tfp, "%c", positions[(re->position) & 0x3f]); } if (((re->position) & 0x3f) < 5) fprintf(tfp, "}"); break; case 'n': /* wtmark9 */ not = (struct Note *) akt[i]->data; if (((whilecrit == 0) && ((not->flags) & 0x100)) || ((whilecrit == 4) && ((not->flags) & 0x200))) break; if (not->slur_nr) { /* search slur number in array */ j = 0; nothing = 10; while ((j < 10) && ((slur[j]) != (not->slur_nr))) { /* it's strange but true: number 9 is not allowed for slurs */ if ((!slur_and_beam[j]) && (j != 9) && (nothing == 10)) nothing = j; j++; } if ((j < 10) || ((j == 10) && (nothing < 10) && (!((not->flags) & 0x80)))) { /* valid slur */ if (j == 10) { /* begin of slur */ /* write slur as tie because of a better appearance */ j = nothing; slur_and_beam[j] = 1; slur[j] = not->slur_nr; if (((not->slur_pos) & 0x3f) < 5) fprintf(tfp, "{\\transpose=-7\\relax "); fprintf(tfp, "\\ITen"); if ((not->slur_pos) & 0x80) fprintf(tfp, "u"); else fprintf(tfp, "l"); fprintf(tfp, "%d%c", j, positions[(not->slur_pos) & 0x3f]); if (((not->slur_pos) & 0x3f) < 5) fprintf(tfp, "}"); } else { /* end of slur */ if ((not->flags) & 0x80) { slur[j] = 0; todelete[j] = 1; fprintf(tfp, "\\tten%d", j); } } } } if (not->beam_nr) { /* search beam number in array */ j = 0; nothing = 10; while ((j < 10) && ((beam[j][0]) != (not->beam_nr))) { if ((!slur_and_beam[j]) && (nothing == 10)) nothing = j; j++; } if ((j < 10) || ((j == 10) && (nothing < 10) && (!((not->flags) & 0x40)))) { /* valid beam */ if (j == 10) { /* begin of beam */ j = nothing; slur_and_beam[j] = 1; beam[j][0] = not->beam_nr; k = 4; l = (not->flags) & 0x38; l = (l >> 3); if (((not->beam_pos) & 0x3f) < 5) fprintf( tfp, "{\\transpose=-7\\relax "); fprintf(tfp, "\\i"); beam[j][1] = 0; while (k > l) { fprintf(tfp, "b"); k--; (beam[j][1])++; } if ((not->beam_pos) & 0x80) { beam[j][2] = 1; fprintf(tfp, "u"); } else { beam[j][2] = 0; fprintf(tfp, "l"); } fprintf(tfp, "%d", j); if (((not->beam_pos) & 0x3f) > 41) printf("errerr %d\n", store); fprintf(tfp, "%c", positions[(not->beam_pos) & 0x3f]); /* output slope */ l = (not->flags) & 0x7800; l = (l >> 11); if ((not->flags) & 0x8000) fprintf(tfp, "{-%d}", l); else fprintf(tfp, "%d", l); if (((not->beam_pos) & 0x3f) < 5) fprintf(tfp, "}"); if ((4 - k) > (not->next_beamn_kind)) { k = 5 - (not->next_beamn_kind); beam[j][1] = k - 1; fprintf(tfp, "\\rlap{\\qsk\\t"); while (k--) fprintf(tfp, "b"); if (beam[j][2]) fprintf(tfp, "u"); else fprintf(tfp, "l"); fprintf(tfp, "%d}", j); } } else { if ((not->flags) & 0x40) { /* end of beam */ fprintf(tfp, "\\t"); k = 4; l = (not->flags) & 0x38; l = (l >> 3); while (k > l) { fprintf(tfp, "b"); k--; } if (beam[j][2]) fprintf(tfp, "u"); else fprintf(tfp, "l"); todelete[j] = 1; fprintf(tfp, "%d", j); if (k != 3) { fprintf(tfp, "\\tb"); if (beam[j][2]) fprintf(tfp, "u"); else fprintf(tfp, "l"); fprintf(tfp, "%d", j); } beam[j][0] = 0; beam[j][1] = 0; beam[j][2] = 0; } else { /* middle of beam */ l = (not->flags) & 0x38; l = (l >> 3); if ((beam[j][1] < (4 - l)) && ((not->next_beamn_kind) <= (beam[j][1]))) { fprintf(tfp, "\\t"); k = 4 - l; while (k--) fprintf(tfp, "b"); if (beam[j][2]) fprintf(tfp, "u"); else fprintf(tfp, "l"); fprintf(tfp, "%d", j); fprintf(tfp, "\\t"); k = (not->next_beamn_kind) + 1; while (k--) fprintf(tfp, "b"); if (beam[j][2]) fprintf(tfp, "u"); else fprintf(tfp, "l"); fprintf(tfp, "%d", j); } else { /* not->next_beamn_kind > beam[j][1] */ /* means: next note more beamed than the minimum of previous and aktual */ if (beam[j][1] < (4 - l)) { if ((4 - l) > (not->next_beamn_kind)) k = (not->next_beamn_kind); else k = (4 - l); fprintf(tfp, "\\n"); while (k--) { fprintf(tfp, "b"); } if (beam[j][2]) fprintf(tfp, "u"); else fprintf(tfp, "l"); fprintf(tfp, "%d", j); if ((4 - l) > (not->next_beamn_kind)) { fprintf(tfp, "\\rlap{\\qsk\\t"); k = (4 - l); while (k--) fprintf(tfp, "b"); if (beam[j][2]) fprintf(tfp, "u"); else fprintf(tfp, "l"); fprintf(tfp, "%d}", j); } } else { /* beam[j][1] == (4 - l) */ if ((4 - l) > (not->next_beamn_kind)) { fprintf(tfp, "\\t"); k = (not->next_beamn_kind) + 1; while (k--) fprintf(tfp, "b"); if (beam[j][2]) fprintf(tfp, "u"); else fprintf(tfp, "l"); fprintf(tfp, "%d", j); } } } if ((4 -l) > (not->next_beamn_kind)) beam[j][1] = (not->next_beamn_kind); else beam[j][1] = (4 -l); } } if (((((not->note_pos) & 0x3f) < (((not->beam_pos) & 0x3f) + UPPLOWSHIFT)) && ((not->beam_pos) & 0x80)) || ((((not->note_pos) & 0x3f) < (((not->beam_pos) & 0x3f) - UPPLOWSHIFT)) && (!((not->beam_pos) & 0x80)))) sprintf(beamstring, "qh%d", j); else sprintf(beamstring, "qb%d", j); write_note(akt[i], beamstring); } else { not->beam_nr = 0; write_note(akt[i], ""); } } else write_note(akt[i], ""); break; default: fprintf (stderr, "warning: unknown element3\n"); break; } akt[i] = akt[i]->next; } whilecrit = (whilecrit * 5) + 4; } for (j=0; j<10; j++) if (todelete[j]) slur_and_beam[j] = 0; } fprintf(tfp, "\\enotes\n"); } } /* wtmark10 */ fprintf(tfp, "\\finmorceau\n\\end\n"); } }