/* * OSCRouterWrapper.java * Eisenkraut * * Copyright (c) 2004-2016 Hanns Holger Rutz. All rights reserved. * * This software is published under the GNU General Public License v3+ * * * For further information, please contact Hanns Holger Rutz at * contact@sciss.de */ package de.sciss.eisenkraut.net; import java.io.IOException; import java.lang.reflect.InvocationTargetException; import java.lang.reflect.Method; import java.util.HashMap; import java.util.Map; public class OSCRouterWrapper implements OSCRouter { private final OSCRouter r; private final OSCRouter superRouter; private final Map<String, OSCRouter> mapSubRouters = new HashMap<String, OSCRouter>(); private static final Class[] oscCmdMethodTypes = { RoutedOSCMessage.class }; private static final Class[] oscGetMethodTypes = { RoutedOSCMessage.class }; public OSCRouterWrapper(OSCRouter superRouter, OSCRouter thisRouter) { r = thisRouter; this.superRouter = superRouter; if (superRouter != null) superRouter.oscAddRouter(r); } public void remove() { if (superRouter != null) superRouter.oscRemoveRouter(r); } public void oscRoute(RoutedOSCMessage rom) { final int argCnt = rom.msg.getArgCount(); if( rom.hasNext() ) { rom = rom.next(); final OSCRouter nextR = mapSubRouters.get(rom.getPathComponent()); if (nextR != null) { nextR.oscRoute(rom); } else { OSCRoot.failedUnknownPath(rom); } } else { final Object[] replyArgs; final String cmd; Method oscMethod; if (argCnt == 0) { OSCRoot.failedArgCount(rom); return; } try { cmd = rom.msg.getArg(0).toString(); if (cmd.equals(OSCRoot.OSC_QUERY)) { if (argCnt < 2) { OSCRoot.failedArgCount(rom); return; } replyArgs = new Object[argCnt - 1]; replyArgs[0] = rom.msg.getArg(1); int argIdx = 2; try { for (; argIdx < argCnt; argIdx++) { oscMethod = r.getClass().getMethod("oscQuery_" + rom.msg.getArg(argIdx).toString(), (Class[]) null); replyArgs[argIdx - 1] = oscMethod.invoke(r, (Object[]) null); } } catch (NoSuchMethodException e1) { OSCRoot.failedArgValue(rom, argIdx); return; } rom.reply(OSCRoot.OSC_QUERYREPLY, replyArgs); } else if (cmd.equals(OSCRoot.OSC_GET)) { if (argCnt < 3) { OSCRoot.failedArgCount(rom); return; } final Object[] methodResult; try { oscMethod = r.getClass().getMethod("oscGet_" + rom.msg.getArg(2), oscGetMethodTypes); methodResult = (Object[]) oscMethod.invoke(r, rom); if (methodResult != null) { replyArgs = new Object[methodResult.length + 1]; replyArgs[0] = rom.msg.getArg(1); System.arraycopy(methodResult, 0, replyArgs, 1, methodResult.length); rom.reply(OSCRoot.OSC_GETREPLY, replyArgs); } } catch (NoSuchMethodException e1) { OSCRoot.failedArgValue(rom, 2); } } else { // any other command try { oscMethod = r.getClass().getMethod("oscCmd_" + cmd, oscCmdMethodTypes); oscMethod.invoke(r, rom); } catch (NoSuchMethodException e1) { OSCRoot.failedUnknownCmd(rom); } } } catch (SecurityException e1) { OSCRoot.failed(rom, e1); } catch (IllegalAccessException e1) { OSCRoot.failed(rom, e1); } catch (IllegalArgumentException e1) { OSCRoot.failed(rom, e1); } catch (InvocationTargetException e1) { OSCRoot.failed(rom, e1); } catch (ExceptionInInitializerError e1) { OSCRoot.failed(rom, e1); } catch (IOException e1) { OSCRoot.failed(rom, e1); } } } public void oscAddRouter(OSCRouter subRouter) { if (mapSubRouters.put(subRouter.oscGetPathComponent(), subRouter) != null) { throw new IllegalArgumentException("Tried to overwrite existing router for sub path " + subRouter.oscGetPathComponent()); } } public void oscRemoveRouter(OSCRouter subRouter) { if (mapSubRouters.remove(subRouter.oscGetPathComponent()) == null) { throw new IllegalArgumentException("Tried to remove unknown router for sub path " + subRouter.oscGetPathComponent()); } } public String oscGetPathComponent() { return r.oscGetPathComponent(); } }