/* Name: LOAD_XM.C Description: Fasttracker (XM) module loader Portability: All systems - all compilers (hopefully) */ package audio.jmikmod.MikMod.Loaders; import java.io.IOException; import audio.jmikmod.MikMod.clLOADER; import audio.jmikmod.MikMod.clMainBase; import persist.SimulatedRandomAccessFile; class XMHEADER{ byte id[]; /* ID text: 'Extended module: ' */ byte songname[]; /* Module name, padded with zeroes and 0x1a at the end */ byte trackername[]; /* Tracker name */ int version; /* (word) Version number, hi-byte major and low-byte minor */ int headersize; /* Header size */ short songlength; /* (word) Song length (in patten order table) */ int restart; /* (word) Restart position */ short numchn; /* (word) Number of channels (2,4,6,8,10,...,32) */ short numpat; /* (word) Number of patterns (max 256) */ short numins; /* (word) Number of instruments (max 128) */ short flags; /* (word) Flags: bit 0: 0 = Amiga frequency table (see below) 1 = Linear frequency table */ int tempo; /* (word) Default tempo */ int bpm; /* (word) Default BPM */ short orders[]; /* (byte) Pattern order table */ public XMHEADER() { id = new byte[17]; songname = new byte[21]; trackername = new byte[20]; orders = new short[256]; } } class XMNOTE{ short note,ins,vol,eff,dat; } class XMINSTHEADER{ int size; /* (dword) Instrument size */ byte name[]; /* (char) Instrument name */ short type; /* (byte) Instrument type (always 0) */ short numsmp; /* (word) Number of samples in instrument */ int ssize; /* */ public XMINSTHEADER() { name = new byte[22]; } } class XMPATCHHEADER{ short what[]; /* (byte) Sample number for all notes */ short volenv[]; /* (byte) Points for volume envelope */ short panenv[]; /* (byte) Points for panning envelope */ short volpts; /* (byte) Number of volume points */ short panpts; /* (byte) Number of panning points */ short volsus; /* (byte) Volume sustain point */ short volbeg; /* (byte) Volume loop start point */ short volend; /* (byte) Volume loop end point */ short pansus; /* (byte) Panning sustain point */ short panbeg; /* (byte) Panning loop start point */ short panend; /* (byte) Panning loop end point */ short volflg; /* (byte) Volume type: bit 0: On; 1: Sustain; 2: Loop */ short panflg; /* (byte) Panning type: bit 0: On; 1: Sustain; 2: Loop */ short vibflg; /* (byte) Vibrato type */ short vibsweep; /* (byte) Vibrato sweep */ short vibdepth; /* (byte) Vibrato depth */ short vibrate; /* (byte) Vibrato rate */ int volfade; /* (word) Volume fadeout */ short reserved[]; /* (word) Reserved */ public XMPATCHHEADER() { what = new short[96]; volenv = new short[48]; panenv = new short[48]; reserved = new short[11]; } } class XMWAVHEADER{ int length; /* (dword) Sample length */ int loopstart; /* (dword) Sample loop start */ int looplength; /* (dword) Sample loop length */ short volume; /* (byte) Volume */ byte finetune; /* (byte) Finetune (signed byte -128..+127) */ short type; /* (byte) Type: Bit 0-1: 0 = No loop, 1 = Forward loop, */ /* 2 = Ping-pong loop; */ /* 4: 16-bit sampledata */ short panning; /* (byte) Panning (0-255) */ byte relnote; /* (byte) Relative note number (signed byte) */ byte reserved; /* (byte) Reserved */ byte samplename[]; /* (char) Sample name */ public XMWAVHEADER() { samplename = new byte[22]; } } class XMPATHEADER{ int size; /* (dword) Pattern header length */ short packing; /* (byte) Packing type (always 0) */ short numrows; /* (word) Number of rows in pattern (1..256) */ int packsize; /* (word) Packed patterndata size */ } public class XM_Loader extends clLOADER { public XMNOTE [] xmpat; public XMHEADER mh; public XM_Loader(clMainBase theMain) { super(theMain); mh = null; type = new String("XM"); version = new String("Portable XM loader v0.4 - for your ears only / MikMak"); } public boolean Test() { byte id[] = new byte[17], should_be[] = new byte[20]; String szShould="Extended Module: "; szShould.getBytes(0,17,should_be,0); int a; //if(!fread(id,17,1,m_.MLoader.modfp)) return 0; //if (!m_.MLoader.modfp.read(id,0,17)) return 0; if (m_.MLoader.modfp.read(id,0,17) != 17) return false; for (a=0; a<17;a++) { if (id[a] != should_be[a]) return false; } return true; } public boolean Init() { int i; mh=null; //if(!(mh=(XMHEADER *)m_.MLoader.MyCalloc(1,sizeof(XMHEADER)))) return 0; mh = new XMHEADER(); mh.version = mh.headersize = mh.restart = mh.tempo = mh.bpm = 0; mh.songlength = mh.numchn = mh.numpat = mh.numins = mh.flags = (short)0; for(i=0;i<17;i++) mh.id[i] = 0; for(i=0;i<21;i++) mh.songname[i] = 0; for(i=0;i<20;i++) mh.trackername[i] = 0; for(i=0;i<256;i++) mh.orders[i] = 0; return true; } public void Cleanup() { if(mh!=null) mh = null; } public void XM_ReadNote(XMNOTE n) { short cmp; //memset(n,0,sizeof(XMNOTE)); n.note = n.ins = n.vol = n.eff = n.dat = 0; //cmp=fgetc(m_.MLoader.modfp); cmp = (short)m_.MLoader.modfp.read(); if((cmp&0x80) != 0){ if((cmp&1) != 0) n.note=(short)m_.MLoader.modfp.read(); if((cmp&2) != 0) n.ins=(short)m_.MLoader.modfp.read(); if((cmp&4) != 0) n.vol=(short)m_.MLoader.modfp.read(); if((cmp&8) != 0) n.eff=(short)m_.MLoader.modfp.read(); if((cmp&16) != 0) n.dat=(short)m_.MLoader.modfp.read(); } else{ n.note=cmp; n.ins=(short)m_.MLoader.modfp.read(); n.vol=(short)m_.MLoader.modfp.read(); n.eff=(short)m_.MLoader.modfp.read(); n.dat=(short)m_.MLoader.modfp.read(); } if (n.note == -1) n.note = 255; if (n.ins == -1) n.ins = 255; if (n.vol == -1) n.vol = 255; if (n.eff == -1) n.eff = 255; if (n.dat == -1) n.dat = 255; } public short [] XM_Convert(XMNOTE [] xmtrack,int offset, int rows) { int t; short note,ins,vol,eff,dat; m_.MUniTrk.UniReset(); int xmi = offset; for(t=0;t<rows;t++){ note=xmtrack[xmi].note; ins=xmtrack[xmi].ins; vol=xmtrack[xmi].vol; eff=xmtrack[xmi].eff; dat=xmtrack[xmi].dat; if(note!=0) m_.MUniTrk.UniNote((short)(note-1)); if(ins!=0) m_.MUniTrk.UniInstrument((short)(ins-1)); /* printf("Vol:%d\n",vol); */ switch(vol>>4){ case 0x6: /* volslide down */ if((vol&0xf) != 0){ m_.MUniTrk.UniWrite(m_.MUniTrk.UNI_XMEFFECTA); m_.MUniTrk.UniWrite((short)(vol&0xf)); } break; case 0x7: /* volslide up */ if((vol&0xf) != 0){ m_.MUniTrk.UniWrite(m_.MUniTrk.UNI_XMEFFECTA); m_.MUniTrk.UniWrite((short)(vol<<4)); } break; /* volume-row fine volume slide is compatible with protracker EBx and EAx effects i.e. a zero nibble means DO NOT SLIDE, as opposed to 'take the last sliding value'. */ case 0x8: /* finevol down */ m_.MUniTrk.UniPTEffect((short)0xe,(short)(0xb0 | (vol&0xf))); break; case 0x9: /* finevol up */ m_.MUniTrk.UniPTEffect((short)0xe,(short)(0xa0 | (vol&0xf))); break; case 0xa: /* set vibrato speed */ m_.MUniTrk.UniPTEffect((short)0x4,(short)(vol<<4)); break; case 0xb: /* vibrato */ m_.MUniTrk.UniPTEffect((short)0x4,(short)(vol&0xf)); break; case 0xc: /* set panning */ m_.MUniTrk.UniPTEffect((short)0x8,(short)(vol<<4)); break; case 0xd: /* panning slide left */ /* only slide when data nibble not zero: */ if((vol&0xf) != 0){ m_.MUniTrk.UniWrite(m_.MUniTrk.UNI_XMEFFECTP); m_.MUniTrk.UniWrite((short)(vol&0xf)); } break; case 0xe: /* panning slide right */ /* only slide when data nibble not zero: */ if((vol&0xf) != 0){ m_.MUniTrk.UniWrite(m_.MUniTrk.UNI_XMEFFECTP); m_.MUniTrk.UniWrite((short)(vol<<4)); } break; case 0xf: /* tone porta */ m_.MUniTrk.UniPTEffect((short)0x3,(short)(vol<<4)); break; default: if(vol>=0x10 && vol<=0x50){ m_.MUniTrk.UniPTEffect((short)0xc,(short)(vol-0x10)); } } /* if(eff>0xf) printf("Effect %d",eff); */ switch(eff){ case 'G'-55: /* G - set global volume */ if(dat>64) dat=64; m_.MUniTrk.UniWrite(m_.MUniTrk.UNI_XMEFFECTG); m_.MUniTrk.UniWrite(dat); break; case 'H'-55: /* H - global volume slide */ m_.MUniTrk.UniWrite(m_.MUniTrk.UNI_XMEFFECTH); m_.MUniTrk.UniWrite(dat); break; case 'K'-55: /* K - keyoff */ m_.MUniTrk.UniNote((short)96); break; case 'L'-55: /* L - set envelope position */ break; case 'P'-55: /* P - panning slide */ m_.MUniTrk.UniWrite(m_.MUniTrk.UNI_XMEFFECTP); m_.MUniTrk.UniWrite(dat); break; case 'R'-55: /* R - multi retrig note */ m_.MUniTrk.UniWrite(m_.MUniTrk.UNI_S3MEFFECTQ); m_.MUniTrk.UniWrite(dat); break; case 'T'-55: /* T - Tremor !! (== S3M effect I) */ m_.MUniTrk.UniWrite(m_.MUniTrk.UNI_S3MEFFECTI); m_.MUniTrk.UniWrite(dat); break; case 'X'-55: if((dat>>4)==1){ /* X1 extra fine porta up */ } else{ /* X2 extra fine porta down */ } break; default: if(eff==0xa){ m_.MUniTrk.UniWrite(m_.MUniTrk.UNI_XMEFFECTA); m_.MUniTrk.UniWrite(dat); } else if(eff<=0xf) m_.MUniTrk.UniPTEffect(eff,dat); break; } m_.MUniTrk.UniNewline(); xmi++; } return m_.MUniTrk.UniDup(); } public boolean Load() { try { //INSTRUMENT *d; //SAMPLE *q; int inst_num; int t,u,v,p,numtrk; int next; int i; /* try to read module header */ m_.mmIO._mm_read_str(mh.id,17,m_.MLoader.modfp); m_.mmIO._mm_read_str(mh.songname,21,m_.MLoader.modfp); m_.mmIO._mm_read_str(mh.trackername,20,m_.MLoader.modfp); mh.version =m_.mmIO._mm_read_I_UWORD(m_.MLoader.modfp); mh.headersize =m_.mmIO._mm_read_I_ULONG(m_.MLoader.modfp); mh.songlength =(short)m_.mmIO._mm_read_I_UWORD(m_.MLoader.modfp); mh.restart =m_.mmIO._mm_read_I_UWORD(m_.MLoader.modfp); mh.numchn =(short)m_.mmIO._mm_read_I_UWORD(m_.MLoader.modfp); mh.numpat =(short)m_.mmIO._mm_read_I_UWORD(m_.MLoader.modfp); mh.numins =(short)m_.mmIO._mm_read_I_UWORD(m_.MLoader.modfp); mh.flags =(short)m_.mmIO._mm_read_I_UWORD(m_.MLoader.modfp); mh.tempo =m_.mmIO._mm_read_I_UWORD(m_.MLoader.modfp); mh.bpm =m_.mmIO._mm_read_I_UWORD(m_.MLoader.modfp); m_.mmIO._mm_read_UBYTES2(mh.orders,256,m_.MLoader.modfp); //if(feof(m_.MLoader.modfp)){ if (m_.MLoader.modfp.getFilePointer() >= m_.MLoader.modfp.length()) { m_.mmIO.myerr = m_.ERROR_LOADING_HEADER; return false; } /* set module variables */ m_.MLoader.of.initspeed=(short)mh.tempo; m_.MLoader.of.inittempo=(short)mh.bpm; m_.MLoader.of.modtype=m_.MLoader.DupStr(mh.trackername,20); m_.MLoader.of.numchn=mh.numchn; m_.MLoader.of.numpat=mh.numpat; m_.MLoader.of.numtrk=(short)(m_.MLoader.of.numpat*m_.MLoader.of.numchn); /* get number of channels */ m_.MLoader.of.songname=m_.MLoader.DupStr(mh.songname,20); /* make a cstr of songname */ m_.MLoader.of.numpos=mh.songlength; /* copy the songlength */ m_.MLoader.of.reppos=(short)mh.restart; m_.MLoader.of.numins=mh.numins; m_.MLoader.of.flags |= m_.MUniTrk.UF_XMPERIODS; if((mh.flags&1) != 0) m_.MLoader.of.flags|= m_.MUniTrk.UF_LINEAR; //memcpy(m_.MLoader.of.positions,mh.orders,256); for(t=0;t<256;t++) m_.MLoader.of.positions[t] = mh.orders[t]; /* WHY THIS CODE HERE?? I CAN'T REMEMBER! m_.MLoader.of.numpat=0; for(t=0;t<m_.MLoader.of.numpos;t++){ if(m_.MLoader.of.positions[t]>m_.MLoader.of.numpat) m_.MLoader.of.numpat=m_.MLoader.of.positions[t]; } m_.MLoader.of.numpat++; */ if(!m_.MLoader.AllocTracks()) return false; if(!m_.MLoader.AllocPatterns()) return false; numtrk=0; for(t=0;t<mh.numpat;t++){ XMPATHEADER ph = new XMPATHEADER(); /* printf("Reading pattern %d\n",t); */ ph.size =m_.mmIO._mm_read_I_ULONG(m_.MLoader.modfp); ph.packing =m_.mmIO._mm_read_UBYTE(m_.MLoader.modfp); ph.numrows =(short)m_.mmIO._mm_read_I_UWORD(m_.MLoader.modfp); ph.packsize =m_.mmIO._mm_read_I_UWORD(m_.MLoader.modfp); /* printf("headln: %ld\n",ph.size); */ /* printf("numrows: %d\n",ph.numrows); */ /* printf("packsize:%d\n",ph.packsize); */ m_.MLoader.of.pattrows[t]=ph.numrows; /* Gr8.. when packsize is 0, don't try to load a pattern.. it's empty. This bug was discovered thanks to Khyron's module.. */ //if(!(xmpat=(XMNOTE *)m_.MLoader.MyCalloc(ph.numrows*m_.MLoader.of.numchn,sizeof(XMNOTE)))) return false; xmpat = new XMNOTE[ph.numrows*m_.MLoader.of.numchn]; for(i=0 ; i<ph.numrows*m_.MLoader.of.numchn ; i++) xmpat[i] = new XMNOTE(); for(i=0;i<ph.numrows*m_.MLoader.of.numchn;i++) { xmpat[i].note = xmpat[i].ins = xmpat[i].vol = xmpat[i].eff = xmpat[i].dat = 0; } if(ph.packsize>0){ for(u=0;u<ph.numrows;u++){ for(v=0;v<m_.MLoader.of.numchn;v++){ XM_ReadNote(xmpat[(v*ph.numrows)+u]); } } } for(v=0;v<m_.MLoader.of.numchn;v++){ m_.MLoader.of.tracks[numtrk++]=XM_Convert(xmpat, v*ph.numrows,ph.numrows); } xmpat = null; } if(!m_.MLoader.AllocInstruments()) return false; //d=m_.MLoader.of.instruments; inst_num=0; for(t=0;t<m_.MLoader.of.numins;t++){ XMINSTHEADER ih = new XMINSTHEADER(); /* read instrument header */ ih.size =m_.mmIO._mm_read_I_ULONG(m_.MLoader.modfp); m_.mmIO._mm_read_str (ih.name, 22, m_.MLoader.modfp); ih.type =m_.mmIO._mm_read_UBYTE(m_.MLoader.modfp); ih.numsmp =(short)m_.mmIO._mm_read_I_UWORD(m_.MLoader.modfp); ih.ssize =m_.mmIO._mm_read_I_ULONG(m_.MLoader.modfp); /* printf("Size: %ld\n",ih.size); printf("Name: %22.22s\n",ih.name); printf("Samples:%d\n",ih.numsmp); printf("sampleheadersize:%ld\n",ih.ssize); */ m_.MLoader.of.instruments[inst_num].insname=m_.MLoader.DupStr(ih.name,22); m_.MLoader.of.instruments[inst_num].numsmp=ih.numsmp; if(!m_.MLoader.AllocSamples((m_.MLoader.of.instruments[inst_num]))) return false; if(ih.numsmp>0){ XMPATCHHEADER pth = new XMPATCHHEADER(); XMWAVHEADER wh = new XMWAVHEADER(); m_.mmIO._mm_read_UBYTES2 (pth.what, 96, m_.MLoader.modfp); m_.mmIO._mm_read_UBYTES2 (pth.volenv, 48, m_.MLoader.modfp); m_.mmIO._mm_read_UBYTES2 (pth.panenv, 48, m_.MLoader.modfp); pth.volpts =m_.mmIO._mm_read_UBYTE(m_.MLoader.modfp); pth.panpts =m_.mmIO._mm_read_UBYTE(m_.MLoader.modfp); pth.volsus =m_.mmIO._mm_read_UBYTE(m_.MLoader.modfp); pth.volbeg =m_.mmIO._mm_read_UBYTE(m_.MLoader.modfp); pth.volend =m_.mmIO._mm_read_UBYTE(m_.MLoader.modfp); pth.pansus =m_.mmIO._mm_read_UBYTE(m_.MLoader.modfp); pth.panbeg =m_.mmIO._mm_read_UBYTE(m_.MLoader.modfp); pth.panend =m_.mmIO._mm_read_UBYTE(m_.MLoader.modfp); pth.volflg =m_.mmIO._mm_read_UBYTE(m_.MLoader.modfp); pth.panflg =m_.mmIO._mm_read_UBYTE(m_.MLoader.modfp); pth.vibflg =m_.mmIO._mm_read_UBYTE(m_.MLoader.modfp); pth.vibsweep =m_.mmIO._mm_read_UBYTE(m_.MLoader.modfp); pth.vibdepth =m_.mmIO._mm_read_UBYTE(m_.MLoader.modfp); pth.vibrate =m_.mmIO._mm_read_UBYTE(m_.MLoader.modfp); pth.volfade =m_.mmIO._mm_read_I_UWORD(m_.MLoader.modfp); m_.mmIO._mm_read_I_SWORDS(pth.reserved, 11, m_.MLoader.modfp); //memcpy(m_.MLoader.of.instruments[inst_num].samplenumber,pth.what,96); for(i=0 ; i<96 ; i++) { m_.MLoader.of.instruments[inst_num].samplenumber[i] = pth.what[i]; } m_.MLoader.of.instruments[inst_num].volfade=pth.volfade; /* printf("Volfade %x\n",m_.MLoader.of.instruments[inst_num].volfade); */ //memcpy(m_.MLoader.of.instruments[inst_num].volenv,pth.volenv,24); for(i = 0;i < 6; i++) { m_.MLoader.of.instruments[inst_num].volenv[i].pos = (short)(pth.volenv[i*4] + (pth.volenv[i*4+1]<<8)); m_.MLoader.of.instruments[inst_num].volenv[i].val = (short)(pth.volenv[i*4+2] + (pth.volenv[i*4+3]<<8)); } /* for (i = 0; i < 12; i++) { byte tmp = ((byte*)m_.MLoader.of.instruments[inst_num].volenv)[i*2]; ((byte*)m_.MLoader.of.instruments[inst_num].volenv)[i*2] = ((byte*)m_.MLoader.of.instruments[inst_num].volenv)[i*2+1]; ((byte*)m_.MLoader.of.instruments[inst_num].volenv)[i*2+1] = tmp; } */ m_.MLoader.of.instruments[inst_num].volflg=pth.volflg; m_.MLoader.of.instruments[inst_num].volsus=pth.volsus; m_.MLoader.of.instruments[inst_num].volbeg=pth.volbeg; m_.MLoader.of.instruments[inst_num].volend=pth.volend; m_.MLoader.of.instruments[inst_num].volpts=pth.volpts; /* printf("volume points : %d\n" "volflg : %d\n" "volbeg : %d\n" "volend : %d\n" "volsus : %d\n", m_.MLoader.of.instruments[inst_num].volpts, m_.MLoader.of.instruments[inst_num].volflg, m_.MLoader.of.instruments[inst_num].volbeg, m_.MLoader.of.instruments[inst_num].volend, m_.MLoader.of.instruments[inst_num].volsus); */ /* scale volume envelope: */ for(p=0;p<12;p++){ m_.MLoader.of.instruments[inst_num].volenv[p].val<<=2; /* printf("%d,%d,",m_.MLoader.of.instruments[inst_num].volenv[p].pos,m_.MLoader.of.instruments[inst_num].volenv[p].val); */ } //memcpy(m_.MLoader.of.instruments[inst_num].panenv,pth.panenv,24); for (i=0;i<6;i++) { m_.MLoader.of.instruments[inst_num].panenv[i].pos = (short)(pth.panenv[i*4] + (pth.panenv[i*4+1]<<8)); m_.MLoader.of.instruments[inst_num].panenv[i].val = (short)(pth.panenv[i*4+2] + (pth.panenv[i*4+3]<<8)); } /* for (i = 0; i < 12; i++) { short tmp = ((byte*)m_.MLoader.of.instruments[inst_num].panenv)[i*2]; ((byte*)m_.MLoader.of.instruments[inst_num].panenv)[i*2] = ((byte*)m_.MLoader.of.instruments[inst_num].panenv)[i*2+1]; ((byte*)m_.MLoader.of.instruments[inst_num].panenv)[i*2+1] = tmp; } */ m_.MLoader.of.instruments[inst_num].panflg=pth.panflg; m_.MLoader.of.instruments[inst_num].pansus=pth.pansus; m_.MLoader.of.instruments[inst_num].panbeg=pth.panbeg; m_.MLoader.of.instruments[inst_num].panend=pth.panend; m_.MLoader.of.instruments[inst_num].panpts=pth.panpts; /* printf("Panning points : %d\n" "panflg : %d\n" "panbeg : %d\n" "panend : %d\n" "pansus : %d\n", m_.MLoader.of.instruments[inst_num].panpts, m_.MLoader.of.instruments[inst_num].panflg, m_.MLoader.of.instruments[inst_num].panbeg, m_.MLoader.of.instruments[inst_num].panend, m_.MLoader.of.instruments[inst_num].pansus); */ /* scale panning envelope: */ for(p=0;p<12;p++){ m_.MLoader.of.instruments[inst_num].panenv[p].val<<=2; /* printf("%d,%d,",m_.MLoader.of.instruments[inst_num].panenv[p].pos,m_.MLoader.of.instruments[inst_num].panenv[p].val); */ } /* for(u=0;u<256;u++){ */ /* printf("%2.2x ",fgetc(m_.MLoader.modfp)); */ /* } */ next=0; for(u=0;u<ih.numsmp;u++){ //q=&m_.MLoader.of.instruments[inst_num].samples[u]; wh.length =m_.mmIO._mm_read_I_ULONG (m_.MLoader.modfp); wh.loopstart =m_.mmIO._mm_read_I_ULONG (m_.MLoader.modfp); wh.looplength =m_.mmIO._mm_read_I_ULONG (m_.MLoader.modfp); wh.volume =m_.mmIO._mm_read_UBYTE (m_.MLoader.modfp); wh.finetune =m_.mmIO._mm_read_SBYTE (m_.MLoader.modfp); wh.type =m_.mmIO._mm_read_UBYTE (m_.MLoader.modfp); wh.panning =m_.mmIO._mm_read_UBYTE (m_.MLoader.modfp); wh.relnote =m_.mmIO._mm_read_SBYTE (m_.MLoader.modfp); wh.reserved =(byte)m_.mmIO._mm_read_UBYTE (m_.MLoader.modfp); m_.mmIO._mm_read_str(wh.samplename, 22, m_.MLoader.modfp); /*printf("wav %d:%22.22s\n",u,wh.samplename);*/ m_.MLoader.of.instruments[t].samples[u].samplename = new String(wh.samplename,0,0,22); m_.MLoader.of.instruments[t].samples[u].length =wh.length; m_.MLoader.of.instruments[t].samples[u].loopstart =wh.loopstart; m_.MLoader.of.instruments[t].samples[u].loopend =wh.loopstart+wh.looplength; m_.MLoader.of.instruments[t].samples[u].volume =wh.volume; m_.MLoader.of.instruments[t].samples[u].c2spd =wh.finetune+128; m_.MLoader.of.instruments[t].samples[u].transpose =wh.relnote; m_.MLoader.of.instruments[t].samples[u].panning =wh.panning; m_.MLoader.of.instruments[t].samples[u].seekpos =next; if((wh.type&0x10) != 0){ m_.MLoader.of.instruments[t].samples[u].length>>=1; m_.MLoader.of.instruments[t].samples[u].loopstart>>=1; m_.MLoader.of.instruments[t].samples[u].loopend>>=1; } next+=wh.length; /* printf("Type %u\n",wh.type); */ /* printf("Trans %d\n",wh.relnote); */ m_.MLoader.of.instruments[t].samples[u].flags|=(m_.MDriver.SF_OWNPAN); if((wh.type&0x3) != 0) m_.MLoader.of.instruments[t].samples[u].flags|=(m_.MDriver.SF_LOOP); if((wh.type&0x2) != 0) m_.MLoader.of.instruments[t].samples[u].flags|=(m_.MDriver.SF_BIDI); if((wh.type&0x10) != 0) m_.MLoader.of.instruments[t].samples[u].flags|=(m_.MDriver.SF_16BITS); m_.MLoader.of.instruments[t].samples[u].flags|=(m_.MDriver.SF_DELTA); m_.MLoader.of.instruments[t].samples[u].flags|=(m_.MDriver.SF_SIGNED); } for(u=0;u<ih.numsmp;u++) m_.MLoader.of.instruments[inst_num].samples[u].seekpos+=m_.mmIO._mm_ftell(m_.MLoader.modfp); m_.mmIO._mm_fseek(m_.MLoader.modfp,next,m_.mmIO.SEEK_CUR); } //d++; inst_num++; } return true; } catch (IOException ioe1) { return false; } } }