void doTrack()

in blocks/cocoon-midi/cocoon-midi-impl/src/main/java/org/apache/cocoon/generation/XMidiGenerator.java [651:1018]


    void doTrack(byte[] dta, int len)
        throws SAXException, ProcessingException {
        AttributesImpl attr = new AttributesImpl();
        String text = "";

        boolean tFlag = true;
        int offset = 0;

        // initialize variables
        String edata = null;
        String snam = null;
        String nmData = "";
        String ctag = null;
        String ctagAttr[] = new String[4];
        String ctagAttrVal[] = new String[4];
        int ctagnum = 0;
        String cnum = null;
        String ctyp = null;
        int slen = 0;
        int chanType = 0;
        int hiName = 0;
        int status = 0;
        int noff = 0;
        String sval = null;
        boolean ecFlag = true; // assume edata
        boolean nFlag = true; // use slen for noff
        boolean firstTime = true;

        while (tFlag) {
            // do delta
            ByteLen bl = Utils.deltaToInt(dta, offset);
            offset += bl.len;
            String deltaLen = Utils.baToHex(bl.ba, 0, 3);

            nFlag = true; // assume simple (slen) offset
            // may or may not be status
            boolean statFlag = false;
            int first = Utils.baToInt(dta, offset, offset);
            this.getLogger().debug(
                "doTrack: in loop; deltaLen="
                    + deltaLen
                    + ", len="
                    + bl.len
                    + ", first="
                    + first);

            if ((first & 128) == 128) {
                // it is a status byte
                statFlag = true;
                sval = Utils.baToHex(dta, offset, offset);
                status = first;
                this.getLogger().debug("doTrack: have status: " + sval);
                if (status < 240 && status > 127) {
                    ecFlag = false;
                    chanType = (status - 128) / 16;
                    snam = chanArray[chanType];
                    ctyp = sval.substring(0, 1);
                    cnum = sval.substring(1, 2);
                } else {
                    ecFlag = true;
                    if (status > 239 && status < 256) {
                        hiName = status - 240;
                        snam = fArray[hiName];
                    } else {
                        throw new ProcessingException(
                            "Invalid status: " + status);
                    }
                }
                offset++;
            } else {
                this.getLogger().debug("doTrack: running status");
            }

            nmData = "";
            if (firstTime) {
                firstTime = false;
                if (!statFlag) {
                    throw new ProcessingException(
                        "first time, but no status; first = " + first);
                }
            }

            // offset points to the byte after the status
            // or first byte of "running status"

            attr.clear();
            attr.addAttribute("", "DTIME", "DTIME", "CDATA", "" + deltaLen);
            this.contentHandler.startElement("", "DELTA", "DELTA", attr);

            if (status > 127 && status < 144) {
                // note off
                slen = 2;
                // set up tag
                int pitch = Utils.baToInt(dta, offset, offset);
                int vel = Utils.baToInt(dta, offset + 1, offset + 1);
                ctag = "NOTE_OFF";
                ctagAttr[0] = "PITCH";
                ctagAttrVal[0] = "" + pitch;
                ctagAttr[1] = "VELOCITY";
                ctagAttrVal[1] = "" + vel;
                ctagnum = 2;
                if (local_verbose) {
                    ctagAttr[2] = "NAME";
                    ctagAttrVal[2] = notes[pitch];
                    ctagAttr[3] = "REGISTER";
                    ctagAttrVal[3] = "" + register[pitch];
                    ctagnum = 4;
                }
            } else if (status > 143 && status < 160) {
                // note on
                slen = 2;
                int pitch = Utils.baToInt(dta, offset, offset);
                int vel = Utils.baToInt(dta, offset + 1, offset + 1);
                ctag = "NOTE_ON";
                ctagAttr[0] = "PITCH";
                ctagAttrVal[0] = "" + pitch;
                ctagAttr[1] = "VELOCITY";
                ctagAttrVal[1] = "" + vel;
                ctagnum = 2;
                if (local_verbose) {
                    ctagAttr[2] = "NAME";
                    ctagAttrVal[2] = notes[pitch];
                    ctagAttr[3] = "REGISTER";
                    ctagAttrVal[3] = "" + register[pitch];
                    ctagnum = 4;
                }
            } else if (status > 159 && status < 176) {
                // after touch
                slen = 2;
                int pitch = Utils.baToInt(dta, offset, offset);
                int pres = Utils.baToInt(dta, offset + 1, offset + 1);
                ctag = "AFTER";
                ctagAttr[0] = "PITCH";
                ctagAttrVal[0] = "" + pitch;
                ctagAttr[1] = "PRESSURE";
                ctagAttrVal[1] = "" + pres;
                ctagnum = 2;
                if (local_verbose) {
                    ctagAttr[2] = "NAME";
                    ctagAttrVal[2] = notes[pitch];
                    ctagAttr[3] = "REGISTER";
                    ctagAttrVal[3] = "" + register[pitch];
                    ctagnum = 4;
                }
            } else if (status > 175 && status < 192) {
                // control change
                slen = 2;
                int contnum = Utils.baToInt(dta, offset, offset);
                int contval = Utils.baToInt(dta, offset + 1, offset + 1);
                ctag = "CONTROL";
                ctagAttr[0] = "NUMBER";
                ctagAttrVal[0] = "" + contnum;
                ctagAttr[1] = "VALUE";
                ctagAttrVal[1] = "" + contval;
                ctagnum = 2;
                if (local_verbose) {
                    ctagAttr[2] = "NAME";
                    ctagAttrVal[2] = (String) contHash.get("" + contnum);
                    ctagnum = 3;
                }
            } else if (status > 191 && status < 208) {
                // program (patch) change
                slen = 1;
                int patch = Utils.baToInt(dta, offset, offset);
                ctag = "PROGRAM";
                ctagAttr[0] = "NUMBER";
                ctagAttrVal[0] = "" + patch;
                ctagnum = 1;
            } else if (status > 207 && status < 224) {
                // channel pressure
                slen = 1;
                int pamt = Utils.baToInt(dta, offset, offset);
                ctag = "PRESSURE";
                ctagAttr[0] = "AMOUNT";
                ctagAttrVal[0] = "" + pamt;
                ctagnum = 1;
            } else if (status > 223 && status < 240) {
                // pitch wheel
                slen = 2;
                int pwamt = Utils.getPW(dta, offset);
                ctag = "WHEEL";
                ctagAttr[0] = "AMOUNT";
                ctagAttrVal[0] = "" + pwamt;
                ctagnum = 1;
            } else if (status == 240) {
                // sysex
                bl = Utils.deltaToInt(dta, offset);
                slen = Utils.baToInt(bl.ba, 0, 3);
                noff = bl.len;
                nFlag = false;
                edata =
                    Utils.baToHex(dta, offset + noff, offset + noff + slen - 1);
                noff += slen;
            } else if (status == 255) {
                // non midi (reset only in "live" midi")
                nmData = Utils.baToHex(dta, offset, offset);
                //						nmData = "SNMT=\""+nmDta+"\" ";
                snam = "non-MIDI";
                String nmNam = (String) ffHash.get(nmData);
                if (nmNam != null) {
                    snam += " - " + nmNam;
                } else {
                    snam += " - Unknown";
                }
                //						int nmt = baToInt(dta,offset+1,offset+1);
                bl = Utils.deltaToInt(dta, offset + 1);
                slen = Utils.baToInt(bl.ba, 0, 3);
                noff = bl.len + 1;
                nFlag = false;
                if (slen == 0) {
                    edata = "No data";
                } else {
                    edata =
                        Utils.baToHex(
                            dta,
                            offset + noff,
                            offset + noff + slen - 1);
                    noff += slen;
                }
                this.getLogger().debug(
                    "doTrack: status FF" + nmData + ", edata = " + edata);
            } else if (status == 241 || status == 243) {
                int tcv = dta[offset];
                Integer tc = new Integer(tcv);
                edata = tc.toString();
                slen = 1;
            } else if (status == 242) {
                int tcv = Utils.getPW(dta, offset);
                Integer tc = new Integer(tcv);
                edata = tc.toString();
                slen = 2;
            } else if (
                status == 246
                    || status == 248
                    || status == 250
                    || status == 251
                    || status == 252
                    || status == 254) {
                edata = "No data for " + snam;
                slen = 0;
            } else { // really unknown
                int ol = Utils.getNextHiOrd(dta, offset);
                edata = Utils.baToHex(dta, offset + 1, ol);
                ol -= offset + 1;
                slen = ol;
            }

            if (ecFlag) {
                if (statFlag) {
                    attr.clear();
                    attr.addAttribute("", "SLEN", "SLEN", "CDATA", "" + slen);
                    attr.addAttribute("", "SNAM", "SNAM", "CDATA", snam);
                    if (!nmData.equals("")) {
                        attr.addAttribute("", "SNMT", "SNMT", "CDATA", nmData);
                    }
                    attr.addAttribute("", "SVAL", "SVAL", "CDATA", sval);
                    this.contentHandler.startElement(
                        "",
                        "STATUS",
                        "STATUS",
                        attr);

                    attr.clear();
                    this.contentHandler.startElement(
                        "",
                        "EDATA",
                        "EDATA",
                        attr);
                    text = edata;
                    this.contentHandler.characters(
                        text.toCharArray(),
                        0,
                        text.length());
                    this.contentHandler.endElement("", "EDATA", "EDATA");

                    this.contentHandler.endElement("", "STATUS", "STATUS");
                } else {
                    attr.clear();
                    this.contentHandler.startElement(
                        "",
                        "EDATA",
                        "EDATA",
                        attr);
                    text = edata;
                    this.contentHandler.characters(
                        text.toCharArray(),
                        0,
                        text.length());
                    this.contentHandler.endElement("", "EDATA", "EDATA");
                }
            } else {

                if (statFlag) {
                    attr.clear();
                    attr.addAttribute("", "SLEN", "SLEN", "CDATA", "" + slen);
                    attr.addAttribute("", "SNAM", "SNAM", "CDATA", snam);
                    if (!nmData.equals("")) {
                        attr.addAttribute("", "SNMT", "SNMT", "CDATA", nmData);
                    }
                    attr.addAttribute("", "SVAL", "SVAL", "CDATA", sval);
                    this.contentHandler.startElement(
                        "",
                        "STATUS",
                        "STATUS",
                        attr);

                    attr.clear();
                    attr.addAttribute("", "NUMBER", "NUMBER", "CDATA", cnum);
                    attr.addAttribute("", "TYPE", "TYPE", "CDATA", ctyp);
                    this.contentHandler.startElement(
                        "",
                        "CHANNEL",
                        "CHANNEL",
                        attr);

                    attr.clear();
                    for (int c = 0; c < ctagnum; c++) {
                        attr.addAttribute(
                            "",
                            ctagAttr[c],
                            ctagAttr[c],
                            "CDATA",
                            ctagAttrVal[c]);
                    }
                    this.contentHandler.startElement("", ctag, ctag, attr);
                    this.contentHandler.endElement("", ctag, ctag);

                    this.contentHandler.endElement("", "CHANNEL", "CHANNEL");
                    this.contentHandler.endElement("", "STATUS", "STATUS");
                } else {
                    attr.clear();
                    attr.addAttribute("", "NUMBER", "NUMBER", "CDATA", cnum);
                    attr.addAttribute("", "TYPE", "TYPE", "CDATA", ctyp);
                    this.contentHandler.startElement(
                        "",
                        "CHANNEL",
                        "CHANNEL",
                        attr);

                    attr.clear();
                    for (int c = 0; c < ctagnum; c++) {
                        attr.addAttribute(
                            "",
                            ctagAttr[c],
                            ctagAttr[c],
                            "CDATA",
                            ctagAttrVal[c]);
                    }
                    this.contentHandler.startElement("", ctag, ctag, attr);
                    this.contentHandler.endElement("", ctag, ctag);

                    this.contentHandler.endElement("", "CHANNEL", "CHANNEL");
                }

            }

            this.contentHandler.endElement("", "DELTA", "DELTA");

            if (nFlag) {
                offset += slen;
            } else {
                offset += noff;
            }
            if (offset >= len) {
                tFlag = false;
            }
        }
    }