/* Copyright (C) 2006 Christian Schneider * * This file is part of Nomad. * * Nomad is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * Nomad is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with Nomad; if not, write to the Free Software * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA */ package net.sf.nmedit.jsynth.clavia.nordmodular; import java.beans.PropertyChangeEvent; import java.beans.PropertyChangeListener; import net.sf.nmedit.jnmprotocol2.MidiMessage; import net.sf.nmedit.jnmprotocol2.MorphAssignmentMessage; import net.sf.nmedit.jnmprotocol2.NmProtocol; import net.sf.nmedit.jnmprotocol2.SetPatchTitleMessage; import net.sf.nmedit.jpatch.AllEventsListener; import net.sf.nmedit.jpatch.PModule; import net.sf.nmedit.jpatch.PParameter; import net.sf.nmedit.jpatch.clavia.nordmodular.NMPatch; import net.sf.nmedit.jpatch.clavia.nordmodular.PNMMorphSection; import net.sf.nmedit.jpatch.clavia.nordmodular.VoiceArea; import net.sf.nmedit.jpatch.clavia.nordmodular.event.PAssignmentEvent; import net.sf.nmedit.jpatch.clavia.nordmodular.event.PAssignmentListener; import net.sf.nmedit.jpatch.clavia.nordmodular.event.PPatchSettingsEvent; import net.sf.nmedit.jpatch.clavia.nordmodular.event.PPatchSettingsListener; import net.sf.nmedit.jpatch.clavia.nordmodular.parser.Helper; import net.sf.nmedit.jpatch.event.PConnectionEvent; import net.sf.nmedit.jpatch.event.PModuleContainerEvent; import net.sf.nmedit.jpatch.event.PModuleEvent; import net.sf.nmedit.jpatch.event.PParameterEvent; import net.sf.nmedit.jsynth.Slot; import net.sf.nmedit.jsynth.clavia.nordmodular.utils.NmUtils; public class NmPatchSynchronizer extends AllEventsListener implements PAssignmentListener, PropertyChangeListener, PPatchSettingsListener { private NordModular synth; private NMPatch patch; private NmSlot slot; private boolean installed; public NmPatchSynchronizer(NordModular synth, NMPatch patch, NmSlot slot) { listenConnections = true; listenModules = true; listenParameters = true; this.synth = synth; this.patch = patch; this.slot = slot; } public NMPatch getPatch() { return patch; } public Slot getSlot() { return slot; } public boolean isInstalled() { return installed; } public void uninstall() { if (!installed) return; patch.removePropertyChangeListener(this); patch.removeAssignmentListener(this); patch.removePatchSettingsListener(this); uninstallModuleContainer(patch.getPolyVoiceArea()); uninstallModuleContainer(patch.getCommonVoiceArea()); uninstallParameters(patch.getMorphSection().getMorphModule()); } public void install() { if (installed) return; patch.addPropertyChangeListener(this); patch.addAssignmentListener(this); patch.addPatchSettingsListener(this); installModuleContainer(patch.getPolyVoiceArea()); installModuleContainer(patch.getCommonVoiceArea()); installParameters(patch.getMorphSection().getMorphModule()); } public void moduleAdded(PModuleContainerEvent e) { super.moduleAdded(e); PModule module = e.getModule(); try { synth.getProtocol().send(NmUtils.createNewModuleMessage(slot.getPatchId(), module,slot.getSlotId())); } catch (Exception er) { // TODO handle error System.err.println(er.getStackTrace()); } } public void moduleRemoved(PModuleContainerEvent e) { super.moduleRemoved(e); PModule module = e.getModule(); int index = e.getIndex(); //System.out.println("delete@"+index); try { synth.getProtocol().send(NmUtils.createDeleteModuleMessage(slot.getPatchId(), module, index)); } catch (Exception er) { // TODO handle error } } public void moduleRenamed(PModuleEvent e) { try { MidiMessage message = NmUtils.createSetModuleTitleMessage(e.getModule(), e.getModule().getTitle(), slot.getSlotIndex(), slot.getPatchId()); synth.getProtocol().send(message); } catch (Exception e1) { e1.printStackTrace(); } } public void moduleMoved(PModuleEvent e) { try { MidiMessage message = NmUtils.createMoveModuleMessage(e.getModule(), slot.getSlotIndex(), slot.getPatchId()); // TODO if (synth.isConnected()) synth.getProtocol().send(message); } catch (Exception e1) { e1.printStackTrace(); } } public void focusRequested(PParameterEvent e) { PParameter parameter = e.getParameter(); try { if (isMorphParameter(e.getParameter()) || "parameter".equals(parameter.getAttribute("class"))) { MidiMessage message = NmUtils.createSelectParameterMessage(parameter, slot.getSlotIndex(), slot.getPatchId()); synth.getProtocol().send(message); } } catch (Exception e1) { e1.printStackTrace(); } } private boolean isMorphParameter(PParameter p) { return p.getParentComponent() == patch.getMorphSection().getMorphModule(); } public void parameterValueChanged(PParameterEvent e) { PParameter parameter = e.getParameter(); Object pclass = parameter.getAttribute("class"); try { if (isMorphParameter(e.getParameter()) || "parameter".equals(pclass)) { MidiMessage message = NmUtils.createParameterChangedMessage(parameter, slot.getSlotIndex(), slot.getPatchId()); synth.getProtocol().send(message); } else if ("morph".equals(pclass)) { // check morph group PModule module = parameter.getParentComponent(); PParameter extendedParameter = Helper.getParameter(module, "parameter", Helper.index(parameter)); if (extendedParameter == null) return; PNMMorphSection morphSec = patch.getMorphSection(); if (morphSec.getAssignedMorph(extendedParameter)<0) { // not assigned to morph group if (!morphSec.getAssignments(0).add(extendedParameter)) { // failed extendedParameter.setValue(0); return; } } MidiMessage message = NmUtils.createMorphRangeChangeMessage(parameter, slot.getSlotIndex(), slot.getPatchId()); synth.getProtocol().send(message); } } catch (Exception e1) { e1.printStackTrace(); } } public void connectionAdded(PConnectionEvent e) { try { VoiceArea va = (VoiceArea) e.getConnectionManager().getModuleContainer(); MidiMessage message = NmUtils.createNewCableMessage(va, e.getSource(), e.getDestination(), slot.getSlotId(), slot.getPatchId()); synth.getProtocol().send(message); } catch (Exception e1) { e1.printStackTrace(); } } public void connectionRemoved(PConnectionEvent e) { try { VoiceArea va = (VoiceArea) e.getConnectionManager().getModuleContainer(); synth.getProtocol().send( NmUtils.createDeleteCableMessage(va, e.getSource(), e.getDestination(), slot.getSlotId(), slot.getPatchId() )); } catch (Exception e1) { e1.printStackTrace(); } } public void parameterAssigned(PAssignmentEvent e) { // System.out.println("user assign:" +e); MidiMessage msg = null; switch (e.getId()) { case PAssignmentEvent.MORPH_ASSIGNED: msg = NmUtils.createMorphAssignmentMessage(e.getParameter(), e.getMorphGroup(), slot.getSlotIndex(), slot.getPatchId()); break; case PAssignmentEvent.KNOB_ASSIGNED: msg = NmUtils.createKnobAssignmentMessage(e.getParameter(), -1, e.getKnobId(), slot.getSlotIndex(), slot.getPatchId()); break; case PAssignmentEvent.MIDICTRL_ASSIGNED: msg = NmUtils.createMidiCtrlAssignmentMessage(e.getParameter(), -1, e.getMidiControllerId(), slot.getSlotIndex(), slot.getPatchId()); break; } if (msg != null) { try { synth.getProtocol().send(msg); } catch (Exception e1) { e1.printStackTrace(); } } } public void parameterDeassigned(PAssignmentEvent e) { // System.out.println("user deassign:" +e); MidiMessage msg = null; switch (e.getId()) { case PAssignmentEvent.MORPH_DEASSIGNED: /* SendControllerSnapshot scs = new SendControllerSnapshot(); scs.setSource(slot.getSlotIndex(), slot.getPatchId()); msg = scs; */ msg = NmUtils.createMorphAssignmentMessage(e.getParameter(), MorphAssignmentMessage.MORPH_ID_DEASSIGN, slot.getSlotIndex(), slot.getPatchId()); break; case PAssignmentEvent.KNOB_DEASSIGNED: msg = NmUtils.createKnobDeAssignmentMessage(e.getKnobId(), slot.getSlotIndex(), slot.getPatchId()); // System.out.println("user deassign:"+msg); break; case PAssignmentEvent.MIDICTRL_DEASSIGNED: msg = NmUtils.createMidiCtrlDeAssignmentMessage(e.getMidiControllerId(), slot.getSlotIndex(), slot.getPatchId()); break; } if (msg != null) { try { synth.getProtocol().send(msg); } catch (Exception e1) { e1.printStackTrace(); } } } public void propertyChange(PropertyChangeEvent e) { if (isProperty(NMPatch.NAME, e)) { String name = (String) e.getNewValue(); MidiMessage msg = new SetPatchTitleMessage( slot.getSlotId(), slot.getPatchId(), (String)e.getNewValue()); slot.setPatchNameValue(name); try { synth.getProtocol().send(msg); } catch (Exception e1) { e1.printStackTrace(); } } } private boolean isProperty(String name, PropertyChangeEvent e) { String n = e.getPropertyName(); return name == n || name.equals(n); } public void patchSettingsChanged(PPatchSettingsEvent e) { try { MidiMessage[] messages = NmUtils.createPatchSettingsMessages(patch, slot.getSlotId()); NmProtocol protocol = synth.getProtocol(); for (int i=0;i<messages.length;i++) protocol.send(messages[i]); } catch (Exception e1) { e1.printStackTrace(); } } }