Search in sources :

Example 26 with Fraction

use of com.xenoage.utils.math.Fraction in project Zong by Xenoage.

the class VoicesBeatOffsetterTest method createVoiceSpacings.

/**
 * Create {@link VoiceSpacing}s for the first measure column
 * of the given {@link Score}.
 */
private LinkedList<VoiceSpacing> createVoiceSpacings(Score score) {
    LinkedList<VoiceSpacing> ret = new LinkedList<>();
    for (int iStaff : range(0, score.getStavesCount() - 1)) {
        Measure measure = score.getMeasure(atMeasure(iStaff, 0));
        for (Voice voice : measure.getVoices()) {
            Fraction beat = Companion.fr(0);
            ArrayList<ElementSpacing> se = alist();
            float offset = 0;
            for (VoiceElement e : voice.getElements()) {
                // compute width
                float width = 0;
                if (e.getDuration().equals(Companion.get_0()))
                    width = width_grace;
                else if (e.getDuration().equals(dur_1_8))
                    width = width_1_8;
                else if (e.getDuration().equals(dur_1_6))
                    width = width_1_6;
                else if (e.getDuration().equals(dur_1_4))
                    width = width_1_4;
                else if (e.getDuration().equals(dur_3_8))
                    width = width_3_8;
                else if (e.getDuration().equals(dur_1_2))
                    width = width_1_2;
                else if (e.getDuration().equals(dur_1_1))
                    width = width_1_1;
                // create spacing element with offset
                se.add(new ChordSpacing(new ChordNotation((Chord) e), beat, offset));
                beat = beat.add(e.getDuration());
                offset += width;
            }
            se.add(new BorderSpacing(beat, offset));
            ret.add(new VoiceSpacing(voice, score.getFormat().getInterlineSpace(), se));
        }
    }
    return ret;
}
Also used : ChordNotation(com.xenoage.zong.musiclayout.notation.ChordNotation) Fraction(com.xenoage.utils.math.Fraction) LinkedList(java.util.LinkedList) VoiceElement(com.xenoage.zong.core.music.VoiceElement) Measure(com.xenoage.zong.core.music.Measure) Voice(com.xenoage.zong.core.music.Voice)

Example 27 with Fraction

use of com.xenoage.utils.math.Fraction in project Zong by Xenoage.

the class DefaultTexts method getTempoTextNotNull.

public static FormattedText getTempoTextNotNull(Tempo tempo, SymbolPool symbolPool) {
    FormattedTextStyle style = FormattedTextStyle.Companion.getDefaultStyle();
    if (tempo.getText() != null) {
        // use custom text
        return styleText(tempo.getText(), style);
    } else {
        // show meaning, e.g. "♩ = 120"
        CList<FormattedTextElement> elements = clist();
        Fraction beat = tempo.getBaseBeat();
        if (beat.equals(Companion.fr(1, 4))) {
            elements.add(new FormattedTextSymbol(symbolPool.getSymbol(CommonSymbol.TextNoteQuarter), /* TODO staffStamping.is * FONT_SIZE_IN_IS */
            12, FormattedTextStyle.Companion.getDefaultColor()));
        } else if (beat.equals(Companion.fr(1, 2))) {
            elements.add(new FormattedTextSymbol(symbolPool.getSymbol(CommonSymbol.TextNoteHalf), /* staffStamping.is * FONT_SIZE_IN_IS */
            12, FormattedTextStyle.Companion.getDefaultColor()));
        } else {
            elements.add(new FormattedTextString(beat.toString(), style));
        }
        elements.add(new FormattedTextString(" = " + tempo.getBeatsPerMinute(), style));
        FormattedTextParagraph paragraph = new FormattedTextParagraph(elements, Alignment.Left);
        return Companion.fText(paragraph);
    }
}
Also used : FormattedTextString(com.xenoage.zong.core.text.FormattedTextString) FormattedTextStyle(com.xenoage.zong.core.text.FormattedTextStyle) FormattedTextParagraph(com.xenoage.zong.core.text.FormattedTextParagraph) Fraction(com.xenoage.utils.math.Fraction) FormattedTextElement(com.xenoage.zong.core.text.FormattedTextElement) FormattedTextSymbol(com.xenoage.zong.core.text.FormattedTextSymbol)

Example 28 with Fraction

use of com.xenoage.utils.math.Fraction in project Zong by Xenoage.

the class StemNotatorTest method testPitch.

private void testPitch(Pitch[] pitches, float start, float end) {
    MusicContext context = MusicContext.Companion.getSimpleInstance();
    Chord chord;
    NotesNotation chordNotesAlignment;
    StemNotation chordStemAlignment;
    Fraction fraction = Companion.fr(1, 1);
    chord = ChordFactory.chord(pitches, fraction);
    ChordLps linepositions = new ChordLps(chord, context);
    StemDirection stemDirection = singleStemDirector.compute(linepositions, 5);
    chordNotesAlignment = notesNotator.compute(chord, stemDirection, defaultChordWidthsNormal, context);
    chordStemAlignment = testee.compute(Stem.Companion.getDefaultStem(), chordNotesAlignment.getLps(), stemDirection, 0, Companion.getStaff5Lines(), 1);
    assertEquals(start, chordStemAlignment.startSlp.lp, Delta.DELTA_FLOAT);
    assertEquals(end, chordStemAlignment.endSlp.lp, Delta.DELTA_FLOAT);
}
Also used : ChordLps(com.xenoage.zong.musiclayout.notation.chord.ChordLps) NotesNotation(com.xenoage.zong.musiclayout.notation.chord.NotesNotation) Fraction(com.xenoage.utils.math.Fraction) MusicContext(com.xenoage.zong.core.music.MusicContext) Chord(com.xenoage.zong.core.music.chord.Chord) StemDirection(com.xenoage.zong.core.music.chord.StemDirection) StemNotation(com.xenoage.zong.musiclayout.notation.chord.StemNotation)

Example 29 with Fraction

use of com.xenoage.utils.math.Fraction in project Zong by Xenoage.

the class CursorOutput method write.

public JsonObject write(ScoreDoc doc) {
    JsonObject ret = new JsonObject();
    // create midi sequence and mp mappings
    Score score = doc.getScore();
    val seq = MidiConverter.convertToSequence(score, optionsForFileExport, new JseMidiSequenceWriter());
    // save time map
    JsonArray jsonMPs = new JsonArray();
    val timeMap = seq.getTimeMap();
    for (int iRep : range(timeMap.getRepetitionsCount())) {
        for (val time : timeMap.getTimesSorted(iRep)) {
            val midiTime = timeMap.getByRepTime(iRep, time);
            JsonObject jsonMP = new JsonObject();
            jsonMP.addProperty("measure", time.measure);
            jsonMP.addProperty("beat", "" + time.beat);
            jsonMP.addProperty("ms", midiTime.ms);
            jsonMPs.add(jsonMP);
        }
    }
    ret.add("mps", jsonMPs);
    // collect data
    int measuresCount = score.getMeasuresCount();
    ArrayList<System> systems = new ArrayList<>();
    ArrayList<Measure> measures = new ArrayList<>();
    for (int i = 0; i < measuresCount; i++) {
        measures.add(new Measure());
    }
    int systemCount = 0;
    Layout layout = doc.getLayout();
    for (int iPage : range(layout.getPages())) {
        Page page = layout.getPages().get(iPage);
        Size2f pageSize = page.getFormat().getSize();
        for (Frame frame : page.getFrames()) {
            if (frame instanceof ScoreFrame) {
                Point2f absPos = frame.getAbsolutePosition();
                float offsetX = absPos.x - frame.getSize().width / 2;
                float offsetY = absPos.y - frame.getSize().height / 2;
                ScoreFrameLayout sfl = ((ScoreFrame) frame).getScoreFrameLayout();
                for (SystemSpacing systemSpacing : sfl.getFrameSpacing().getSystems()) {
                    // read system data
                    int systemIndex = systemCount + systemSpacing.getSystemIndexInFrame();
                    while (systems.size() - 1 < systemIndex) systems.add(new System());
                    System system = systems.get(systemIndex);
                    system.page = iPage;
                    system.top = (offsetY + systemSpacing.offsetYMm) / pageSize.height;
                    system.bottom = (offsetY + systemSpacing.offsetYMm + systemSpacing.getHeightMm()) / pageSize.height;
                    // read measure beats
                    float systemOffsetX = systemSpacing.marginLeftMm;
                    for (int iMeasure : systemSpacing.getMeasures()) {
                        Measure measure = measures.get(iMeasure);
                        measure.system = systemIndex;
                        measure.left = (offsetX + systemOffsetX + systemSpacing.getMeasureStartMm(iMeasure)) / pageSize.width;
                        measure.right = (offsetX + systemOffsetX + systemSpacing.getMeasureEndMm(iMeasure)) / pageSize.width;
                        for (BeatOffset bo : systemSpacing.getColumn(iMeasure).getBeatOffsets()) {
                            measure.beats.put(bo.getBeat(), (offsetX + systemOffsetX + bo.getOffsetMm()) / pageSize.width);
                        }
                    }
                }
                systemCount += sfl.getFrameSpacing().getSystems().size();
            }
        }
    }
    // save systems
    JsonArray jsonSystems = new JsonArray();
    for (int i = 0; i < systems.size(); i++) {
        System system = systems.get(i);
        JsonObject jsonSystem = new JsonObject();
        jsonSystem.addProperty("number", i);
        jsonSystem.addProperty("page", system.page);
        jsonSystem.addProperty("top", system.top);
        jsonSystem.addProperty("bottom", system.bottom);
        jsonSystems.add(jsonSystem);
    }
    ret.add("systems", jsonSystems);
    // save measures
    JsonArray jsonMeasures = new JsonArray();
    for (int i = 0; i < measuresCount; i++) {
        Measure measure = measures.get(i);
        JsonObject jsonMeasure = new JsonObject();
        jsonMeasure.addProperty("number", i);
        jsonMeasure.addProperty("system", measure.system);
        jsonMeasure.addProperty("left", measure.left);
        jsonMeasure.addProperty("right", measure.right);
        // beats
        JsonArray jsonBeats = new JsonArray();
        ArrayList<Fraction> sortedBeats = new ArrayList<>(measure.beats.keySet());
        Collections.sort(sortedBeats);
        for (Fraction beat : sortedBeats) {
            JsonObject jsonBeat = new JsonObject();
            jsonBeat.addProperty("at", "" + beat);
            jsonBeat.addProperty("x", measure.beats.get(beat));
            jsonBeats.add(jsonBeat);
        }
        jsonMeasure.add("beats", jsonBeats);
        jsonMeasures.add(jsonMeasure);
    }
    ret.add("measures", jsonMeasures);
    // save time cursors
    JsonArray jsonTCs = new JsonArray();
    for (int iRep : range(timeMap.getRepetitionsCount())) {
        for (val time : timeMap.getTimesSorted(iRep)) {
            val midiTime = timeMap.getByRepTime(iRep, time);
            JsonObject jsonTC = new JsonObject();
            jsonTC.addProperty("time", midiTime.ms);
            Measure measure = measures.get(time.measure);
            System system = systems.get(measure.system);
            jsonTC.addProperty("page", system.page);
            jsonTC.addProperty("top", system.top);
            jsonTC.addProperty("left", measure.beats.get(time.beat));
            jsonTC.addProperty("bottom", system.bottom);
            jsonTCs.add(jsonTC);
        }
    }
    ret.add("timecursors", jsonTCs);
    return ret;
}
Also used : lombok.val(lombok.val) Frame(com.xenoage.zong.layout.frames.Frame) ScoreFrame(com.xenoage.zong.layout.frames.ScoreFrame) ScoreFrame(com.xenoage.zong.layout.frames.ScoreFrame) ArrayList(java.util.ArrayList) JsonObject(com.google.gson.JsonObject) Page(com.xenoage.zong.layout.Page) Fraction(com.xenoage.utils.math.Fraction) SystemSpacing(com.xenoage.zong.musiclayout.spacing.SystemSpacing) JsonArray(com.google.gson.JsonArray) Score(com.xenoage.zong.core.Score) Point2f(com.xenoage.utils.math.geom.Point2f) ScoreFrameLayout(com.xenoage.zong.musiclayout.ScoreFrameLayout) Layout(com.xenoage.zong.layout.Layout) Size2f(com.xenoage.utils.math.geom.Size2f) BeatOffset(com.xenoage.zong.musiclayout.spacing.BeatOffset) JseMidiSequenceWriter(com.xenoage.zong.desktop.io.midi.out.JseMidiSequenceWriter) ScoreFrameLayout(com.xenoage.zong.musiclayout.ScoreFrameLayout)

Example 30 with Fraction

use of com.xenoage.utils.math.Fraction in project Zong by Xenoage.

the class ChordReader method readFirstNote.

private void readFirstNote() {
    mxlFirstNote = mxlNotes.get(0);
    MxlNoteContentType mxlFirstNoteType = mxlFirstNote.getContent().getNoteContentType();
    // type of chord/rest
    // (unpitched is still unsupported)
    MxlFullNote mxlFirstFullNote = mxlFirstNote.getContent().getFullNote();
    MxlNormalNote mxlFirstNormalNote = null;
    MxlCueNote mxlFirstCueNote = null;
    MxlGraceNote mxlFirstGraceNote = null;
    boolean isCue = false;
    boolean isGrace = false;
    if (mxlFirstNoteType == MxlNoteContentType.Normal) {
        mxlFirstNormalNote = (MxlNormalNote) mxlNotes.get(0).getContent();
    } else if (mxlFirstNoteType == MxlNoteContentType.Cue) {
        mxlFirstCueNote = (MxlCueNote) mxlNotes.get(0).getContent();
        isCue = true;
    } else if (mxlFirstNoteType == MxlNoteContentType.Grace) {
        mxlFirstGraceNote = (MxlGraceNote) mxlNotes.get(0).getContent();
        isGrace = true;
        // may also be true later, see (TODO) "Zong-Library/Discussions/MusicXML/Note - cue vs grace.txt"
        isCue = false;
    }
    MxlFullNoteContentType mxlFNCType = mxlFirstFullNote.getContent().getFullNoteContentType();
    // duration. here, the first duration is the duration of the whole chord.
    Fraction duration = Companion.get_0();
    if (mxlFirstNormalNote != null) {
        duration = readDuration(mxlFirstNormalNote.getDuration(), context.getDivisions());
    } else if (mxlFirstCueNote != null) {
        duration = readDuration(mxlFirstCueNote.getDuration(), context.getDivisions());
    }
    // when duration of normal note is 0, ignore the chord
    if (false == isGrace && false == duration.isGreater0()) {
        context.reportError("duration of chord is 0");
        return;
    }
    // create new chord or rest
    if (mxlFNCType == MxlFullNoteContentType.Pitch || mxlFNCType == MxlFullNoteContentType.Unpitched) {
        // create a chord
        Pitch pitch;
        if (mxlFNCType == MxlFullNoteContentType.Pitch)
            pitch = ((MxlPitch) mxlFirstFullNote.getContent()).getPitch();
        else
            // TODO (ZONG-96): better support for unpitched notes
            pitch = Pitch.Companion.pi(0, 4);
        Grace grace = null;
        if (mxlFirstGraceNote != null) {
            // read grace duration from note-type ("eighth", "16th", ...)
            Fraction graceDuration = Companion.fr(1, 8);
            if (mxlFirstNote.getNoteType() != null)
                graceDuration = mxlFirstNote.getNoteType().getDuration();
            boolean slash = mxlFirstGraceNote.getSlash() == MxlYesNo.Yes;
            grace = new Grace(slash, graceDuration);
            chord = new Chord(alist(new Note(pitch)), grace);
        } else {
            chord = new Chord(alist(new Note(pitch)), duration);
        }
        chord.setCue(isCue);
        chordOrRest = chord;
    } else if (mxlFNCType == MxlFullNoteContentType.Rest) {
        // create a rest
        Rest rest = new Rest(duration);
        rest.setCue(isCue);
        chordOrRest = rest;
    }
}
Also used : MxlFullNote(com.xenoage.zong.musicxml.types.groups.MxlFullNote) MxlCueNote(com.xenoage.zong.musicxml.types.choice.MxlCueNote) Grace(com.xenoage.zong.core.music.chord.Grace) Fraction(com.xenoage.utils.math.Fraction) MxlFullNoteContentType(com.xenoage.zong.musicxml.types.choice.MxlFullNoteContent.MxlFullNoteContentType) Rest(com.xenoage.zong.core.music.rest.Rest) MxlPitch(com.xenoage.zong.musicxml.types.MxlPitch) MxlGraceNote(com.xenoage.zong.musicxml.types.choice.MxlGraceNote) MxlNormalNote(com.xenoage.zong.musicxml.types.choice.MxlNormalNote) Note(com.xenoage.zong.core.music.chord.Note) MxlFullNote(com.xenoage.zong.musicxml.types.groups.MxlFullNote) MxlNote(com.xenoage.zong.musicxml.types.MxlNote) MxlCueNote(com.xenoage.zong.musicxml.types.choice.MxlCueNote) MxlGraceNote(com.xenoage.zong.musicxml.types.choice.MxlGraceNote) Pitch(com.xenoage.zong.core.music.Pitch) MxlPitch(com.xenoage.zong.musicxml.types.MxlPitch) MxlNormalNote(com.xenoage.zong.musicxml.types.choice.MxlNormalNote) MxlNoteContentType(com.xenoage.zong.musicxml.types.choice.MxlNoteContent.MxlNoteContentType) Chord(com.xenoage.zong.core.music.chord.Chord)

Aggregations

Fraction (com.xenoage.utils.math.Fraction)32 BeatOffset (com.xenoage.zong.musiclayout.spacing.BeatOffset)6 Chord (com.xenoage.zong.core.music.chord.Chord)5 ElementSpacing (com.xenoage.zong.musiclayout.spacing.ElementSpacing)5 lombok.val (lombok.val)5 Voice (com.xenoage.zong.core.music.Voice)4 Measure (com.xenoage.zong.core.music.Measure)3 VoiceElement (com.xenoage.zong.core.music.VoiceElement)3 Clef (com.xenoage.zong.core.music.clef.Clef)3 TraditionalKey (com.xenoage.zong.core.music.key.TraditionalKey)3 TimeSignature (com.xenoage.zong.core.music.time.TimeSignature)3 VoiceSpacing (com.xenoage.zong.musiclayout.spacing.VoiceSpacing)3 ColumnElementWrite (com.xenoage.zong.commands.core.music.ColumnElementWrite)2 Score (com.xenoage.zong.core.Score)2 Part (com.xenoage.zong.core.music.Part)2 Note (com.xenoage.zong.core.music.chord.Note)2 Rest (com.xenoage.zong.core.music.rest.Rest)2 ChordNotation (com.xenoage.zong.musiclayout.notation.ChordNotation)2 JsonArray (com.google.gson.JsonArray)1 JsonObject (com.google.gson.JsonObject)1