|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
*/ |
|
package com.sun.media.sound; |
|
|
|
import java.util.ArrayList; |
|
import java.util.Arrays; |
|
import java.util.HashMap; |
|
import java.util.List; |
|
import java.util.Map; |
|
|
|
import javax.sound.midi.Patch; |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
*/ |
|
public final class DLSInstrument extends ModelInstrument { |
|
|
|
int preset = 0; |
|
int bank = 0; |
|
boolean druminstrument = false; |
|
byte[] guid = null; |
|
DLSInfo info = new DLSInfo(); |
|
List<DLSRegion> regions = new ArrayList<DLSRegion>(); |
|
List<DLSModulator> modulators = new ArrayList<DLSModulator>(); |
|
|
|
public DLSInstrument() { |
|
super(null, null, null, null); |
|
} |
|
|
|
public DLSInstrument(DLSSoundbank soundbank) { |
|
super(soundbank, null, null, null); |
|
} |
|
|
|
public DLSInfo getInfo() { |
|
return info; |
|
} |
|
|
|
public String getName() { |
|
return info.name; |
|
} |
|
|
|
public void setName(String name) { |
|
info.name = name; |
|
} |
|
|
|
public ModelPatch getPatch() { |
|
return new ModelPatch(bank, preset, druminstrument); |
|
} |
|
|
|
public void setPatch(Patch patch) { |
|
if (patch instanceof ModelPatch && ((ModelPatch)patch).isPercussion()) { |
|
druminstrument = true; |
|
bank = patch.getBank(); |
|
preset = patch.getProgram(); |
|
} else { |
|
druminstrument = false; |
|
bank = patch.getBank(); |
|
preset = patch.getProgram(); |
|
} |
|
} |
|
|
|
public Object getData() { |
|
return null; |
|
} |
|
|
|
public List<DLSRegion> getRegions() { |
|
return regions; |
|
} |
|
|
|
public List<DLSModulator> getModulators() { |
|
return modulators; |
|
} |
|
|
|
public String toString() { |
|
if (druminstrument) |
|
return "Drumkit: " + info.name |
|
+ " bank #" + bank + " preset #" + preset; |
|
else |
|
return "Instrument: " + info.name |
|
+ " bank #" + bank + " preset #" + preset; |
|
} |
|
|
|
private ModelIdentifier convertToModelDest(int dest) { |
|
if (dest == DLSModulator.CONN_DST_NONE) |
|
return null; |
|
if (dest == DLSModulator.CONN_DST_GAIN) |
|
return ModelDestination.DESTINATION_GAIN; |
|
if (dest == DLSModulator.CONN_DST_PITCH) |
|
return ModelDestination.DESTINATION_PITCH; |
|
if (dest == DLSModulator.CONN_DST_PAN) |
|
return ModelDestination.DESTINATION_PAN; |
|
|
|
if (dest == DLSModulator.CONN_DST_LFO_FREQUENCY) |
|
return ModelDestination.DESTINATION_LFO1_FREQ; |
|
if (dest == DLSModulator.CONN_DST_LFO_STARTDELAY) |
|
return ModelDestination.DESTINATION_LFO1_DELAY; |
|
|
|
if (dest == DLSModulator.CONN_DST_EG1_ATTACKTIME) |
|
return ModelDestination.DESTINATION_EG1_ATTACK; |
|
if (dest == DLSModulator.CONN_DST_EG1_DECAYTIME) |
|
return ModelDestination.DESTINATION_EG1_DECAY; |
|
if (dest == DLSModulator.CONN_DST_EG1_RELEASETIME) |
|
return ModelDestination.DESTINATION_EG1_RELEASE; |
|
if (dest == DLSModulator.CONN_DST_EG1_SUSTAINLEVEL) |
|
return ModelDestination.DESTINATION_EG1_SUSTAIN; |
|
|
|
if (dest == DLSModulator.CONN_DST_EG2_ATTACKTIME) |
|
return ModelDestination.DESTINATION_EG2_ATTACK; |
|
if (dest == DLSModulator.CONN_DST_EG2_DECAYTIME) |
|
return ModelDestination.DESTINATION_EG2_DECAY; |
|
if (dest == DLSModulator.CONN_DST_EG2_RELEASETIME) |
|
return ModelDestination.DESTINATION_EG2_RELEASE; |
|
if (dest == DLSModulator.CONN_DST_EG2_SUSTAINLEVEL) |
|
return ModelDestination.DESTINATION_EG2_SUSTAIN; |
|
|
|
|
|
if (dest == DLSModulator.CONN_DST_KEYNUMBER) |
|
return ModelDestination.DESTINATION_KEYNUMBER; |
|
|
|
if (dest == DLSModulator.CONN_DST_CHORUS) |
|
return ModelDestination.DESTINATION_CHORUS; |
|
if (dest == DLSModulator.CONN_DST_REVERB) |
|
return ModelDestination.DESTINATION_REVERB; |
|
|
|
if (dest == DLSModulator.CONN_DST_VIB_FREQUENCY) |
|
return ModelDestination.DESTINATION_LFO2_FREQ; |
|
if (dest == DLSModulator.CONN_DST_VIB_STARTDELAY) |
|
return ModelDestination.DESTINATION_LFO2_DELAY; |
|
|
|
if (dest == DLSModulator.CONN_DST_EG1_DELAYTIME) |
|
return ModelDestination.DESTINATION_EG1_DELAY; |
|
if (dest == DLSModulator.CONN_DST_EG1_HOLDTIME) |
|
return ModelDestination.DESTINATION_EG1_HOLD; |
|
if (dest == DLSModulator.CONN_DST_EG1_SHUTDOWNTIME) |
|
return ModelDestination.DESTINATION_EG1_SHUTDOWN; |
|
|
|
if (dest == DLSModulator.CONN_DST_EG2_DELAYTIME) |
|
return ModelDestination.DESTINATION_EG2_DELAY; |
|
if (dest == DLSModulator.CONN_DST_EG2_HOLDTIME) |
|
return ModelDestination.DESTINATION_EG2_HOLD; |
|
|
|
if (dest == DLSModulator.CONN_DST_FILTER_CUTOFF) |
|
return ModelDestination.DESTINATION_FILTER_FREQ; |
|
if (dest == DLSModulator.CONN_DST_FILTER_Q) |
|
return ModelDestination.DESTINATION_FILTER_Q; |
|
|
|
return null; |
|
} |
|
|
|
private ModelIdentifier convertToModelSrc(int src) { |
|
if (src == DLSModulator.CONN_SRC_NONE) |
|
return null; |
|
|
|
if (src == DLSModulator.CONN_SRC_LFO) |
|
return ModelSource.SOURCE_LFO1; |
|
if (src == DLSModulator.CONN_SRC_KEYONVELOCITY) |
|
return ModelSource.SOURCE_NOTEON_VELOCITY; |
|
if (src == DLSModulator.CONN_SRC_KEYNUMBER) |
|
return ModelSource.SOURCE_NOTEON_KEYNUMBER; |
|
if (src == DLSModulator.CONN_SRC_EG1) |
|
return ModelSource.SOURCE_EG1; |
|
if (src == DLSModulator.CONN_SRC_EG2) |
|
return ModelSource.SOURCE_EG2; |
|
if (src == DLSModulator.CONN_SRC_PITCHWHEEL) |
|
return ModelSource.SOURCE_MIDI_PITCH; |
|
if (src == DLSModulator.CONN_SRC_CC1) |
|
return new ModelIdentifier("midi_cc", "1", 0); |
|
if (src == DLSModulator.CONN_SRC_CC7) |
|
return new ModelIdentifier("midi_cc", "7", 0); |
|
if (src == DLSModulator.CONN_SRC_CC10) |
|
return new ModelIdentifier("midi_cc", "10", 0); |
|
if (src == DLSModulator.CONN_SRC_CC11) |
|
return new ModelIdentifier("midi_cc", "11", 0); |
|
if (src == DLSModulator.CONN_SRC_RPN0) |
|
return new ModelIdentifier("midi_rpn", "0", 0); |
|
if (src == DLSModulator.CONN_SRC_RPN1) |
|
return new ModelIdentifier("midi_rpn", "1", 0); |
|
|
|
if (src == DLSModulator.CONN_SRC_POLYPRESSURE) |
|
return ModelSource.SOURCE_MIDI_POLY_PRESSURE; |
|
if (src == DLSModulator.CONN_SRC_CHANNELPRESSURE) |
|
return ModelSource.SOURCE_MIDI_CHANNEL_PRESSURE; |
|
if (src == DLSModulator.CONN_SRC_VIBRATO) |
|
return ModelSource.SOURCE_LFO2; |
|
if (src == DLSModulator.CONN_SRC_MONOPRESSURE) |
|
return ModelSource.SOURCE_MIDI_CHANNEL_PRESSURE; |
|
|
|
if (src == DLSModulator.CONN_SRC_CC91) |
|
return new ModelIdentifier("midi_cc", "91", 0); |
|
if (src == DLSModulator.CONN_SRC_CC93) |
|
return new ModelIdentifier("midi_cc", "93", 0); |
|
|
|
return null; |
|
} |
|
|
|
private ModelConnectionBlock convertToModel(DLSModulator mod) { |
|
ModelIdentifier source = convertToModelSrc(mod.getSource()); |
|
ModelIdentifier control = convertToModelSrc(mod.getControl()); |
|
ModelIdentifier destination_id = |
|
convertToModelDest(mod.getDestination()); |
|
|
|
int scale = mod.getScale(); |
|
double f_scale; |
|
if (scale == Integer.MIN_VALUE) |
|
f_scale = Double.NEGATIVE_INFINITY; |
|
else |
|
f_scale = scale / 65536.0; |
|
|
|
if (destination_id != null) { |
|
ModelSource src = null; |
|
ModelSource ctrl = null; |
|
ModelConnectionBlock block = new ModelConnectionBlock(); |
|
if (control != null) { |
|
ModelSource s = new ModelSource(); |
|
if (control == ModelSource.SOURCE_MIDI_PITCH) { |
|
((ModelStandardTransform)s.getTransform()).setPolarity( |
|
ModelStandardTransform.POLARITY_BIPOLAR); |
|
} else if (control == ModelSource.SOURCE_LFO1 |
|
|| control == ModelSource.SOURCE_LFO2) { |
|
((ModelStandardTransform)s.getTransform()).setPolarity( |
|
ModelStandardTransform.POLARITY_BIPOLAR); |
|
} |
|
s.setIdentifier(control); |
|
block.addSource(s); |
|
ctrl = s; |
|
} |
|
if (source != null) { |
|
ModelSource s = new ModelSource(); |
|
if (source == ModelSource.SOURCE_MIDI_PITCH) { |
|
((ModelStandardTransform)s.getTransform()).setPolarity( |
|
ModelStandardTransform.POLARITY_BIPOLAR); |
|
} else if (source == ModelSource.SOURCE_LFO1 |
|
|| source == ModelSource.SOURCE_LFO2) { |
|
((ModelStandardTransform)s.getTransform()).setPolarity( |
|
ModelStandardTransform.POLARITY_BIPOLAR); |
|
} |
|
s.setIdentifier(source); |
|
block.addSource(s); |
|
src = s; |
|
} |
|
ModelDestination destination = new ModelDestination(); |
|
destination.setIdentifier(destination_id); |
|
block.setDestination(destination); |
|
|
|
if (mod.getVersion() == 1) { |
|
//if (mod.getTransform() == DLSModulator.CONN_TRN_CONCAVE) { |
|
// ((ModelStandardTransform)destination.getTransform()) |
|
// .setTransform( |
|
// ModelStandardTransform.TRANSFORM_CONCAVE); |
|
|
|
if (mod.getTransform() == DLSModulator.CONN_TRN_CONCAVE) { |
|
if (src != null) { |
|
((ModelStandardTransform)src.getTransform()) |
|
.setTransform( |
|
ModelStandardTransform.TRANSFORM_CONCAVE); |
|
((ModelStandardTransform)src.getTransform()) |
|
.setDirection( |
|
ModelStandardTransform.DIRECTION_MAX2MIN); |
|
} |
|
if (ctrl != null) { |
|
((ModelStandardTransform)ctrl.getTransform()) |
|
.setTransform( |
|
ModelStandardTransform.TRANSFORM_CONCAVE); |
|
((ModelStandardTransform)ctrl.getTransform()) |
|
.setDirection( |
|
ModelStandardTransform.DIRECTION_MAX2MIN); |
|
} |
|
} |
|
|
|
} else if (mod.getVersion() == 2) { |
|
int transform = mod.getTransform(); |
|
int src_transform_invert = (transform >> 15) & 1; |
|
int src_transform_bipolar = (transform >> 14) & 1; |
|
int src_transform = (transform >> 10) & 8; |
|
int ctr_transform_invert = (transform >> 9) & 1; |
|
int ctr_transform_bipolar = (transform >> 8) & 1; |
|
int ctr_transform = (transform >> 4) & 8; |
|
|
|
|
|
if (src != null) { |
|
int trans = ModelStandardTransform.TRANSFORM_LINEAR; |
|
if (src_transform == DLSModulator.CONN_TRN_SWITCH) |
|
trans = ModelStandardTransform.TRANSFORM_SWITCH; |
|
if (src_transform == DLSModulator.CONN_TRN_CONCAVE) |
|
trans = ModelStandardTransform.TRANSFORM_CONCAVE; |
|
if (src_transform == DLSModulator.CONN_TRN_CONVEX) |
|
trans = ModelStandardTransform.TRANSFORM_CONVEX; |
|
((ModelStandardTransform)src.getTransform()) |
|
.setTransform(trans); |
|
((ModelStandardTransform)src.getTransform()) |
|
.setPolarity(src_transform_bipolar == 1); |
|
((ModelStandardTransform)src.getTransform()) |
|
.setDirection(src_transform_invert == 1); |
|
|
|
} |
|
|
|
if (ctrl != null) { |
|
int trans = ModelStandardTransform.TRANSFORM_LINEAR; |
|
if (ctr_transform == DLSModulator.CONN_TRN_SWITCH) |
|
trans = ModelStandardTransform.TRANSFORM_SWITCH; |
|
if (ctr_transform == DLSModulator.CONN_TRN_CONCAVE) |
|
trans = ModelStandardTransform.TRANSFORM_CONCAVE; |
|
if (ctr_transform == DLSModulator.CONN_TRN_CONVEX) |
|
trans = ModelStandardTransform.TRANSFORM_CONVEX; |
|
((ModelStandardTransform)ctrl.getTransform()) |
|
.setTransform(trans); |
|
((ModelStandardTransform)ctrl.getTransform()) |
|
.setPolarity(ctr_transform_bipolar == 1); |
|
((ModelStandardTransform)ctrl.getTransform()) |
|
.setDirection(ctr_transform_invert == 1); |
|
} |
|
|
|
/* No output transforms are defined the DLS Level 2 |
|
int out_transform = transform % 8; |
|
int trans = ModelStandardTransform.TRANSFORM_LINEAR; |
|
if (out_transform == DLSModulator.CONN_TRN_SWITCH) |
|
trans = ModelStandardTransform.TRANSFORM_SWITCH; |
|
if (out_transform == DLSModulator.CONN_TRN_CONCAVE) |
|
trans = ModelStandardTransform.TRANSFORM_CONCAVE; |
|
if (out_transform == DLSModulator.CONN_TRN_CONVEX) |
|
trans = ModelStandardTransform.TRANSFORM_CONVEX; |
|
if (ctrl != null) { |
|
((ModelStandardTransform)destination.getTransform()) |
|
.setTransform(trans); |
|
} |
|
*/ |
|
|
|
} |
|
|
|
block.setScale(f_scale); |
|
|
|
return block; |
|
} |
|
|
|
return null; |
|
} |
|
|
|
public ModelPerformer[] getPerformers() { |
|
List<ModelPerformer> performers = new ArrayList<ModelPerformer>(); |
|
|
|
Map<String, DLSModulator> modmap = new HashMap<String, DLSModulator>(); |
|
for (DLSModulator mod: getModulators()) { |
|
modmap.put(mod.getSource() + "x" + mod.getControl() + "=" + |
|
mod.getDestination(), mod); |
|
} |
|
|
|
Map<String, DLSModulator> insmodmap = |
|
new HashMap<String, DLSModulator>(); |
|
|
|
for (DLSRegion zone: regions) { |
|
ModelPerformer performer = new ModelPerformer(); |
|
performer.setName(zone.getSample().getName()); |
|
performer.setSelfNonExclusive((zone.getFusoptions() & |
|
DLSRegion.OPTION_SELFNONEXCLUSIVE) != 0); |
|
performer.setExclusiveClass(zone.getExclusiveClass()); |
|
performer.setKeyFrom(zone.getKeyfrom()); |
|
performer.setKeyTo(zone.getKeyto()); |
|
performer.setVelFrom(zone.getVelfrom()); |
|
performer.setVelTo(zone.getVelto()); |
|
|
|
insmodmap.clear(); |
|
insmodmap.putAll(modmap); |
|
for (DLSModulator mod: zone.getModulators()) { |
|
insmodmap.put(mod.getSource() + "x" + mod.getControl() + "=" + |
|
mod.getDestination(), mod); |
|
} |
|
|
|
List<ModelConnectionBlock> blocks = performer.getConnectionBlocks(); |
|
for (DLSModulator mod: insmodmap.values()) { |
|
ModelConnectionBlock p = convertToModel(mod); |
|
if (p != null) |
|
blocks.add(p); |
|
} |
|
|
|
|
|
DLSSample sample = zone.getSample(); |
|
DLSSampleOptions sampleopt = zone.getSampleoptions(); |
|
if (sampleopt == null) |
|
sampleopt = sample.getSampleoptions(); |
|
|
|
ModelByteBuffer buff = sample.getDataBuffer(); |
|
|
|
float pitchcorrection = (-sampleopt.unitynote * 100) + |
|
sampleopt.finetune; |
|
|
|
ModelByteBufferWavetable osc = new ModelByteBufferWavetable(buff, |
|
sample.getFormat(), pitchcorrection); |
|
osc.setAttenuation(osc.getAttenuation() / 65536f); |
|
if (sampleopt.getLoops().size() != 0) { |
|
DLSSampleLoop loop = sampleopt.getLoops().get(0); |
|
osc.setLoopStart((int)loop.getStart()); |
|
osc.setLoopLength((int)loop.getLength()); |
|
if (loop.getType() == DLSSampleLoop.LOOP_TYPE_FORWARD) |
|
osc.setLoopType(ModelWavetable.LOOP_TYPE_FORWARD); |
|
if (loop.getType() == DLSSampleLoop.LOOP_TYPE_RELEASE) |
|
osc.setLoopType(ModelWavetable.LOOP_TYPE_RELEASE); |
|
else |
|
osc.setLoopType(ModelWavetable.LOOP_TYPE_FORWARD); |
|
} |
|
|
|
performer.getConnectionBlocks().add( |
|
new ModelConnectionBlock(SoftFilter.FILTERTYPE_LP12, |
|
new ModelDestination( |
|
new ModelIdentifier("filter", "type", 1)))); |
|
|
|
performer.getOscillators().add(osc); |
|
|
|
performers.add(performer); |
|
|
|
} |
|
|
|
return performers.toArray(new ModelPerformer[performers.size()]); |
|
} |
|
|
|
public byte[] getGuid() { |
|
return guid == null ? null : Arrays.copyOf(guid, guid.length); |
|
} |
|
|
|
public void setGuid(byte[] guid) { |
|
this.guid = guid == null ? null : Arrays.copyOf(guid, guid.length); |
|
} |
|
} |