FlashからProcessingへのデータ送信はOSCを使えば簡単に出来る。が、floscを中継したりといまいち美しくない気がする。
のでflashからProcessingへ直接XMLSocketで通信する方法を考えてみた。まあ、結論としてはさらに美しくない気もしますが、気にしない気にしない。
ActionScript側は最低限こんな感じで。
SocketP5.as
package { import flash.events.Event; import flash.net.XMLSocket; public class SocketP5{ private var ip:String; private var port:uint; private var socket:XMLSocket; /** default osc connection is <br /> IP addres :"127.0.0.1" (localhost)<br /> java Port number : 5204 */ public function SocketP5(ip:String = "127.0.0.1", port:uint = 5204){ this.ip = ip; this.port = port; socket = new XMLSocket(); socket.addEventListener(Event.CONNECT, onConnect); socket.connect(ip, port); } private function onConnect(e:Event):void { trace("connected !"); } public function close():void { socket.close(); } public function sendStr(data:String):void { socket.send(data); } } }
Processing側、というか普通のJavaですが、
FlashServerとXMLSocketの2つのクラスです。
XMLSocket.java
import java.net.Socket; import java.io.BufferedReader; import java.io.PrintWriter; import java.io.InputStreamReader; import java.io.OutputStreamWriter; import java.lang.Exception; import java.lang.reflect.Field; import java.lang.reflect.InvocationTargetException; import java.lang.reflect.Method; import processing.xml.*; public class XMLSocket extends Thread { // for invoketion private Object obj; private Method meth; // for XMLSocket Socket socket; BufferedReader in; PrintWriter out; XMLElement xml; public XMLSocket(Object obj, Socket so) { this.obj = obj; try { Class cls = obj.getClass(); Class[] params = {String.class}; meth = cls.getMethod("onFlashEvent", params); System.out.println("good!!"); } catch (NoSuchMethodException e) { e.printStackTrace(); } socket = so; try { in = new BufferedReader(new InputStreamReader(socket.getInputStream(), "UTF8")); out = new PrintWriter(new OutputStreamWriter(socket.getOutputStream(), "UTF8"),true); } catch(Exception e) { e.printStackTrace(); } this.start(); System.out.println("xmlsocket conectted......."); } public void run() { try { while(true) { String str = ""; int c = in.read(); // if disconnected if(c == -1) { break; } // flash xml socket '\0' while (c != '\0') { str += (char)c; c = in.read(); } //System.out.println(str); // invoke try { meth.invoke( obj, new Object[] { str } ); } catch (IllegalAccessException e) { e.printStackTrace(); } catch (java.lang.reflect.InvocationTargetException e){ e.printStackTrace(); } } in.close(); out.close(); socket.close(); System.out.println("xmlsocket disconnected"); } catch(Exception e) { e.printStackTrace(); } } }
と、まあ、メインのところでonFlashEvent関数にinvokeしています。
変数はStringのみ。
FlashServer.java
import java.net.ServerSocket; import java.net.Socket; public class FlashServer extends Thread { protected ServerSocket server; protected Object obj; /** Make a Server for flash xml socket connection.<br /> Simply, wait for xmlsocket connection from flash. and Run XMLSocket thread. @param port the port number of the server. */ public FlashServer(Object obj, int port) { this.obj = obj; try { server = new ServerSocket(port); System.out.println("waiting connection......."); } catch (Exception e) { e.printStackTrace(); } this.start(); } public void run() { try { while(true) { Socket socket = server.accept(); new XMLSocket(obj,socket); } } catch(Exception e) { e.printStackTrace(); } } /** need to call this function before to close the server. */ public void close() { try { server.close(); } catch (Exception e) { e.printStackTrace(); } } }
こんな感じかな?とりあえずは動いた。