void XM_ProcessEnvelopePan(ref INSTRUMENT d, XMPATCHHEADER pth) { for (int u = 0; u < (XMENVCNT >> 1); u++) { d.panenv[u].pos = (short)pth.panenv[u << 1]; d.panenv[u].val = (short)pth.panenv[(u << 1) + 1]; } if ((pth.panflg & 1) != 0) { d.panflg |= SharpMikCommon.EF_ON; } if ((pth.panflg & 2) != 0) { d.panflg |= SharpMikCommon.EF_SUSTAIN; } if ((pth.panflg & 4) != 0) { d.panflg |= SharpMikCommon.EF_LOOP; } d.pansusbeg = d.pansusend = pth.pansus; d.panbeg = pth.panbeg; d.panend = pth.panend; d.panpts = pth.panpts; /* scale envelope */ for (int p = 0; p < XMENVCNT / 2; p++) { d.panenv[p].val <<= 2; } if ((d.panflg & SharpMikCommon.EF_ON) != 0 && (d.panpts < 2)) { int flag = d.panflg; flag &= ~SharpMikCommon.EF_ON; d.panflg = (byte)flag; } }
bool LoadInstruments() { int t, u, ck; INSTRUMENT d; uint next = 0; ushort wavcnt = 0; if (!m_Module.AllocInstruments()) { m_LoadError = MMERR_NOT_A_MODULE; return(false); } for (t = 0; t < m_Module.numins; t++) { d = m_Module.instruments[t]; XMINSTHEADER ih = new XMINSTHEADER(); long headend; d.samplenumber.Memset(0xff, SharpMikCommon.INSTNOTES); /* read instrument header */ headend = m_Reader.Tell(); ih.size = m_Reader.Read_Intel_uint(); headend += ih.size; ck = m_Reader.Tell(); m_Reader.Seek(0, SeekOrigin.End); if ((headend < 0) || (m_Reader.Tell() < headend) || (headend < ck)) { m_Reader.Seek(ck, SeekOrigin.Begin); break; } m_Reader.Seek(ck, SeekOrigin.Begin); ih.name = m_Reader.Read_String(22); ih.type = m_Reader.Read_byte(); ih.numsmp = m_Reader.Read_Intel_ushort(); d.insname = ih.name; if ((short)ih.size > 29) { ih.ssize = m_Reader.Read_Intel_uint(); if (((short)ih.numsmp > 0) && (ih.numsmp <= XMNOTECNT)) { XMPATCHHEADER pth = new XMPATCHHEADER(); m_Reader.Read_bytes(pth.what, XMNOTECNT); m_Reader.Read_Intel_ushorts(pth.volenv, XMENVCNT); m_Reader.Read_Intel_ushorts(pth.panenv, XMENVCNT); pth.volpts = m_Reader.Read_byte(); pth.panpts = m_Reader.Read_byte(); pth.volsus = m_Reader.Read_byte(); pth.volbeg = m_Reader.Read_byte(); pth.volend = m_Reader.Read_byte(); pth.pansus = m_Reader.Read_byte(); pth.panbeg = m_Reader.Read_byte(); pth.panend = m_Reader.Read_byte(); pth.volflg = m_Reader.Read_byte(); pth.panflg = m_Reader.Read_byte(); pth.vibflg = m_Reader.Read_byte(); pth.vibsweep = m_Reader.Read_byte(); pth.vibdepth = m_Reader.Read_byte(); pth.vibrate = m_Reader.Read_byte(); pth.volfade = m_Reader.Read_Intel_ushort(); /* read the remainder of the header * (2 bytes for 1.03, 22 for 1.04) */ if (headend >= m_Reader.Tell()) { for (u = (int)(headend - m_Reader.Tell()); u != 0; u--) { m_Reader.Read_byte(); } } /* we can't trust the envelope point count here, as some * modules have incorrect values (K_OSPACE.XM reports 32 volume * points, for example). */ if (pth.volpts > XMENVCNT / 2) { pth.volpts = (byte)(XMENVCNT / 2); } if (pth.panpts > XMENVCNT / 2) { pth.panpts = (byte)(XMENVCNT / 2); } if ((m_Reader.isEOF()) || (pth.volpts > XMENVCNT / 2) || (pth.panpts > XMENVCNT / 2)) { if (nextwav != null) { nextwav = null; } if (wh != null) { wh = null; } m_LoadError = MMERR_LOADING_SAMPLEINFO; return(false); } for (u = 0; u < XMNOTECNT; u++) { d.samplenumber[u] = (ushort)(pth.what[u] + m_Module.numsmp); } d.volfade = pth.volfade; XM_ProcessEnvelopeVolume(ref d, pth); XM_ProcessEnvelopePan(ref d, pth); if ((d.volflg & SharpMikCommon.EF_ON) != 0) { FixEnvelope(d.volenv, d.volpts); } if ((d.panflg & SharpMikCommon.EF_ON) != 0) { FixEnvelope(d.panenv, d.panpts); } /* Samples are stored outside the instrument struct now, so we * have to load them all into a temp area, count the m_Module.numsmp * along the way and then do an AllocSamples() and move * everything over */ if (mh.version > 0x0103) { next = 0; } for (u = 0; u < ih.numsmp; u++) { XMWAVHEADER s = null; if (wh != null && sampHeader < wh.Length) { s = wh[sampHeader]; } /* Allocate more room for sample information if necessary */ if (m_Module.numsmp + u == wavcnt) { ushort lastSize = wavcnt; wavcnt += (ushort)XM_SMPINCR; if (nextwav == null) { nextwav = new uint[wavcnt]; } else { Array.Resize(ref nextwav, wavcnt); } if (wh == null) { wh = new XMWAVHEADER[wavcnt]; } else { Array.Resize(ref wh, wavcnt); } for (ushort i = lastSize; i < wavcnt; i++) { wh[i] = new XMWAVHEADER(); } //sampHeader=(wavcnt-XM_SMPINCR); s = wh[sampHeader]; } s.length = m_Reader.Read_Intel_uint(); s.loopstart = m_Reader.Read_Intel_uint(); s.looplength = m_Reader.Read_Intel_uint(); s.volume = m_Reader.Read_byte(); s.finetune = m_Reader.Read_sbyte(); s.type = m_Reader.Read_byte(); s.panning = m_Reader.Read_byte(); s.relnote = m_Reader.Read_sbyte(); s.vibtype = pth.vibflg; s.vibsweep = pth.vibsweep; s.vibdepth = (byte)(pth.vibdepth * 4); s.vibrate = pth.vibrate; s.reserved = m_Reader.Read_byte(); s.samplename = m_Reader.Read_String(22); nextwav[m_Module.numsmp + u] = next; next += s.length; if (m_Reader.isEOF()) { nextwav = null; wh = null; m_LoadError = MMERR_LOADING_SAMPLEINFO; return(false); } sampHeader++; } if (mh.version > 0x0103) { for (u = 0; u < ih.numsmp; u++) { nextwav[m_Module.numsmp++] += (uint)m_Reader.Tell(); } m_Reader.Seek((int)next, SeekOrigin.Current); } else { m_Module.numsmp += ih.numsmp; } } else { /* read the remainder of the header */ ck = m_Reader.Tell(); m_Reader.Seek(0, SeekOrigin.End); if ((headend < 0) || (m_Reader.Tell() < headend) || (headend < ck)) { m_Reader.Seek(ck, SeekOrigin.Begin); break; } m_Reader.Seek(ck, SeekOrigin.Begin); u = (int)(headend - m_Reader.Tell()); for (; u != 0; u--) { m_Reader.Read_byte(); } if (m_Reader.isEOF()) { nextwav = null; wh = null; m_LoadError = MMERR_LOADING_SAMPLEINFO; return(false); } } } } /* sanity check */ if (m_Module.numsmp == 0) { nextwav = null; wh = null; m_LoadError = MMERR_LOADING_SAMPLEINFO; return(false); } return(true); }