Skip to content

Instantly share code, notes, and snippets.

@sonygod
Last active December 16, 2015 09:19
Show Gist options
  • Select an option

  • Save sonygod/5412347 to your computer and use it in GitHub Desktop.

Select an option

Save sonygod/5412347 to your computer and use it in GitHub Desktop.
haxe flash js remoting use async flash---async ---js js----async--flash this version only work on firefox, I don't know why ,maybe haxe Timer ge tsomthing wrong. try to build this ,you need tinkerbell r6388 , hx-async full code and project here https://github.com/sonygod/fj_aync
package ;
import haxe.ds.ObjectMap;
import haxe.ds.StringMap;
import haxe.Timer;
import haxe.remoting.ExternalConnection;
import tink.lang.Cls;
import Format;
/**
* ...
* @author sonygod
*/
class FlashMain {
public function foo(x, y) { trace("outsidecall" + x + y); }
static var js:ExternalConnection = null;
static var hello;
public static var onData: Dynamic;
public static function main() {
var ctx = new haxe.remoting.Context();
ctx.addObject("FlashMain", FlashMain);
js = haxe.remoting.ExternalConnection.jsConnect("default", ctx);
var arr:Array<Int> = [1, 2];
var arr2=arr.slice(0, arr.length - 1);
hello = new Forwarder(js);
hello.sayHello("hi", "god", onCalljs);
}
public static function onCalljs(err, data) {
trace("回来了,靠"+err+data);
}
public static function __onData(args: Array<Dynamic>) {
//trace(args.toString() + "" + Timer.stamp() * 1000);
var recall = args.pop();
trace(args.toString() + "" + Timer.stamp() * 1000);
var xxx:StringMap<CallBackObjWithFun> = js.getcallBackList();
var f :CallBackObjWithFun= xxx.get(recall.id + recall.name);
trace(f.id+f.name+f.callBack);
Reflect.callMethod(FlashMain, f.callBack, args);
}
private static function __init__() : Void {
onData = Reflect.makeVarArgs(__onData);
}
}
class Forwarder implements Cls {
var fields:Hash<Dynamic> = new Hash<Dynamic>();
public var recallFuns:ObjectMap<Caller ,Dynamic>=new ObjectMap<Caller ,Dynamic>();
@:forward(!multiply) var target:ExternalConnection;
@:forward function fwd2(hello:HelloService) {
get: fields.get($name),
set: fields.set($name, param),
call:target.resolve("main").resolve("onData").call($argsRemoting)
}
public function new(target) {
this.target = target;
}
}
typedef Caller = {
id:String,
name:String
}
@sonygod
Copy link
Copy Markdown
Author

sonygod commented Apr 18, 2013

package tink.lang.macros;

import haxe.macro.Context;
import haxe.macro.Expr;
import haxe.macro.Type;
import tink.macro.build.Member;
import tink.macro.build.MemberTransformer;

using tink.macro.tools.MacroTools;
using StringTools;
using Lambda;
using tink.core.types.Outcome;

typedef ClassFieldFilter = ClassField->Bool;
typedef ForwardRules = { call:Null, get:Null, set:Null };

class Forward {
static inline var TAG = ":forward";
static public function process(ctx:ClassBuildContext) {
new Forward(ctx.has, ctx.add, ctx.cls.isInterface).processMembers(ctx.members);
}
var hasField:String->Bool;
var addField:Member->?Bool->Member;
var ownerIsInterface:Bool;
function new(hasField, addField, ownerIsInterface) {
this.hasField = hasField;
this.addField = addField;
this.ownerIsInterface = ownerIsInterface;
}
function processMembers(members:Array) {
for (member in members)
switch (member.extractMeta(TAG)) {
case Success(tag):
switch (member.kind) {
case FVar(t, ):
forwardTo(member, t, tag.pos, tag.params);
case FProp(
, _, t, _):
forwardTo(member, t, tag.pos, tag.params);
case FFun(f):
member.excluded = true;
forwardWithFunction(f, tag.pos, tag.params);
}
default:
}

}
function forwardWithFunction(f:Function, pos:Position, params:Array<Expr>) {
    var rules = {
        call: null,
        get: null,
        set: null
    };
    switch (f.expr.expr) {
        case EObjectDecl(fields):
            for (field in fields) 
                switch (field.field) {
                    case 'get':  rules.get = field.expr;
                    case 'set':  rules.set = field.expr;
                    case 'call': rules.call = field.expr;
                }
        default: f.expr.reject();
    }

    var filter = makeFilter(params);
    for (arg in f.args) 
        forwardWith(arg.name, rules, arg.type, pos, filter);
}
function forwardWith(id:String, rules:ForwardRules, t:ComplexType, pos:Position, filter:ClassFieldFilter) {
    var fields = t.toType(pos).sure().getFields().sure();
    for (field in fields) 
        if (field.isPublic && filter(field) && !hasField(field.name)) {
            switch (field.kind) {
                case FVar(read, write):
                    forwardVarWith(id, rules.get, rules.set, isAccessible(read, true), isAccessible(write, false), field.name, field.type.toComplex(), pos);
                case FMethod(_):
                    if (rules.call != null) {
                        switch (Context.follow(field.type)) {
                            case TFun(args, ret):
                                forwardFunctionWith(id, rules.call, pos, field.name, args, ret, field.params);
                            default: 
                                pos.error('wtf?');
                        }                               
                    }
            }
        }
}
function forwardToType(t:Type, included:ClassFieldFilter, target:Expr, pos:Position, bound:Null<Bool>) {
    for (field in t.getFields().sure()) 
        if (field.isPublic && included(field) && !hasField(field.name)) {
            switch (field.kind) {
                case FVar(read, write):
                    forwardVarTo(target, field.name, field.type.toComplex(), read, write, bound);
                case FMethod(_):
                    switch (Context.follow(field.type)) {
                        case TFun(args, ret):
                            forwardFunctionTo(target, field.name, args, ret, field.params, bound);
                        default: 
                            pos.error('wtf?');
                    }
            }
        }       
}
function forwardTo(to:Member, t:ComplexType, pos:Position, params:Array<Expr>) {
    var t = t.toType(pos).sure().reduce(),
        target = ['this', to.name].drill(pos),
        included = makeFilter(params);

    forwardToType(t, included, target, pos, to.isBound);
}
function forwardFunctionWith(id:String, callExpr:Expr, pos:Position, name:String, args:Array<{ name : String, opt : Bool, t : Type }>, ret : Type, params: Array<{ name : String, t : Type }>) {
    //TODO: there's a lot of duplication with forwardFunctionTo here 
    var methodArgs = [],
        callArgs = [];


    for (arg in args) {
        callArgs.push(arg.name.resolve(pos));
        methodArgs.push( { name : arg.name, opt : arg.opt, type : arg.t.toComplex(), value : null } );
    }
    var methodParams = [].toBlock().func().params;//TODO: be less lazy
    for (param in params) 
        methodParams.push( { name : param.name, constraints: [] } );

  var argsRemoting = callArgs.slice(0, callArgs.length - 1);


  argsRemoting.push( { id:id, name:name}.toExpr() );
  argsRemoting.push(  callArgs[callArgs.length - 1] ); 





    var call = callExpr.substitute( { 

        "$argsRemoting":argsRemoting.toArray(),
        "$args": callArgs.toArray(),
        "$id": id.toExpr(),
        "$name": name.toExpr()
    });
    addField(Member.method(name, call.func(methodArgs, methodParams)));
}
function forwardVarWith(id:String, eGet:Null<Expr>, eSet:Null<Expr>, read:Bool, write:Bool, name, t, pos) {
    read = read && eGet != null;
    write = write && eSet != null;

    if (!(read || write)) return;//I hate guard clauses, but I feel very lazy now
    addField(Member.prop(name, t, pos, !read, !write));
    var vars = {
        "$name": name.toExpr(),
        "$id": id.toExpr()
    }
    if (read)
        addField(Member.getter(name, pos, eGet.substitute(vars), t));
    if (write)
        addField(Member.setter(name, pos, eSet.substitute(vars), t));
}
function forwardFunctionTo(target:Expr, name:String, args:Array<{ name : String, opt : Bool, t : Type }>, ret : Type, params: Array<{ name : String, t : Type }>, bound:Null<Bool>) {
    var methodArgs = [],
        callArgs = [],
        pos = target.pos;

    for (arg in args) {
        callArgs.push(arg.name.resolve(target.pos));
        methodArgs.push( { name : arg.name, opt : arg.opt, type : arg.t.toComplex(true), value : null } );
    }
    var methodParams = [].toBlock().func().params;//TODO: be less lazy
    for (param in params) 
        methodParams.push( { name : param.name, constraints: [] } );
    addField(Member.method(name, target.field(name, pos).call(callArgs, pos).func(methodArgs, ret.toComplex(), methodParams))).isBound = bound;
}
function isAccessible(a:VarAccess, read:Bool) {
    return switch(a) {
        case AccNormal, AccCall(_): true;
        case AccInline: read;
        default: false;
    }
}
function forwardVarTo(target:Expr, name:String, t:ComplexType, read:VarAccess, write:VarAccess, bound:Null<Bool>) {
    var pos = target.pos;
    if (!isAccessible(read, true)) 
        pos.error('cannot forward to non-readable field ' + name + ' of ' + t);
    addField(Member.prop(name, t, pos, false, !isAccessible(write, false))).isBound = bound;
    if (!hasField('get_$name'))
        addField(Member.getter(name, pos, target.field(name, pos), t)).isBound = bound;
    if (!hasField('set_$name'))
        if (isAccessible(write, false))
            addField(Member.setter(name, pos, target.field(name, pos).assign('param'.resolve(pos), pos), t));
}
static function and(a, b) {
    return function (c) return a(c) && b(c);
}
static function or(a, b) {
    return function (c) return a(c) || b(c);
}
static function not(a) {
    return function (c) return !a(c);
}
static function one(filters:Iterable<ClassFieldFilter>) {
    return function (c) {
        for (filter in filters)
            if (filter(c)) 
                return true;
        return false;
    }       
}
static function makeFilter(exprs:Array<Expr>) {
    return
        if (exprs.length == 0) 
            function (_) return true;
        else
            one(exprs.map(makeFieldFilter));
}
static function matchRegEx(r:String, opt:String):ClassFieldFilter {
    var r = new EReg(r, opt);
    return function (field) return r.match(field.name);
}
static public function makeFieldFilter(e:Expr):ClassFieldFilter {
    return
        switch (e.expr) {
            case EArrayDecl(exprs): one(exprs.map(makeFieldFilter));
            case EConst(c): 
                switch (c) {
                    case CIdent(s):
                        if (s.startsWith('$')) 
                            switch (s.substr(1)) {
                                case 'var': function (field:ClassField) return field.isVar();
                                case 'function': function (field:ClassField) return !field.isVar();
                                default: e.reject('invalid option');
                            }
                        else 
                            function (field) return field.name == s;
                    case CString(s): 
                        matchRegEx('^' + StringTools.replace(s, '*', '.*') + '$', 'i');
                    case CRegexp(r, opt): 
                        matchRegEx(r, opt);
                    default: e.reject('invalid constant');
                }
            case EBinop(op, e1, e2):
                switch (op) {
                    case OpAnd, OpBoolAnd: and(makeFieldFilter(e1), makeFieldFilter(e2));
                    case OpOr, OpBoolOr: or(makeFieldFilter(e1), makeFieldFilter(e2));
                    default: e.reject('invalid operator');
                }
            case EUnop(op, postfix, arg): 
                if (postfix || op != OpNot) e.reject();
                not(makeFieldFilter(arg));
            case EParenthesis(e): 
                makeFieldFilter(e);
            default: e.reject();
        }
}   

}

@sonygod
Copy link
Copy Markdown
Author

sonygod commented Apr 18, 2013

package ;
import js.Browser;
import haxe.remoting.ExternalConnection;
import Format;

class JsMain {
public static var cnx = null;
static var ctx = null;

public static var onData: Dynamic;
 private static function __init__() : Void {
onData = Reflect.makeVarArgs(__onData);

}

public static function main() {
   ctx = new haxe.remoting.Context();

   ctx.addObject("main",JsMain);
    cnx = ExternalConnection.flashConnect("default", "myFlashObject", ctx);




    }
    //http://www.verydemo.com/demo_c98_i5393.html

    public static function __onData(args: Array<Dynamic>) {



        Browser.window.alert("length=" + args[2].id);


        Test.bubblesort([1, 2, 9, 7, 6, 0.3], function (err, data) { 

             cnx = ExternalConnection.flashConnect("default", "myFlashObject", ctx);
            cnx.FlashMain.onData.call([err,data,args[2]]); 

            } );

    }

}

@sonygod
Copy link
Copy Markdown
Author

sonygod commented Apr 18, 2013

package ;

/**

import async.Build;
import async.Async;
import haxe.Timer;
import org.transition9.async.Step;
using org.transition9.async.AsyncLambda;
class Test implements Build
{

static function asyncGet2<T1, T2>(v1:T1, v2:T2, cb){
cb(null, v1, v2);
}

@async(var ret: Array<Float>) public static function bubblesort(array : Array<Float>)  {


    var swapping = false;
    var temp : Float;
    while (!swapping) {
        swapping = true;
        for (i in 0...array.length) {

            []=delay(1);
            if (array[i] > array[i+1]) {
                temp = array[i+1];
                array[i+1] = array[i];
                array[i] = temp;
                swapping = false;
            }
        }
    }


    return array;
}


@async(var ret: Array<Float>) static function asynchronous(){
  var arry:Array<Float>;

   [ arry] = bubblesort([1337, 1, -465, 3.141592653589793, 789, 69, 789, -132, 3.141592653589793, 465, 789, 0, 27]);




    return arry;

}



static function bubblesortSync(array : Array<Float>)  {


    var swapping = false;
    var temp : Float;
    while (!swapping) {
        swapping = true;
        for (i in 0...array.length) {


            if (array[i] > array[i+1]) {
                temp = array[i+1];
                array[i+1] = array[i];
                array[i] = temp;
                swapping = false;
            }
        }
    }


    return array;
}

public static function getResult(err:NodeErr, data:Array<Float>) {
    trace("end"+(Timer.stamp()*1000-startTime));
    trace(data);


}

 @async(var ret:Bool) public static function doFooParallel(arrayData:Array<Float>) {
    trace(Timer.stamp() * 10000 + "" + arrayData);
return true;
};

//
@async(var ret:Bool) public static function doFooGroup(?arg1:String) {
    trace(Timer.stamp() * 10000 + "doFooGroup" + arg1);
return true;
};

 @async(var ret:Bool)public static function  doSomethingElseAsync(array) {
    trace(Timer.stamp() * 10000 + " doSomethingElseAsync" + array);
return true;
};

 @async(var ret:Int) public static function  doSomethingElseAsync2(element:Int ) {
    trace(element);
    return  element;

};

 @async(var ret:Int,var ret2:String) public static function  doSomethingElseAsync3(element:Int ) {

   return many(element, "1");

};

public static var startTime:Float;
public static function main() {




      var step = new Step();
      step.chain([

           function () {
               bubblesort([2, 1, 4, 7], step.cb);
           },
           function (err, arrayData) {


             doFooParallel(arrayData, step.parallel());
             doFooParallel(arrayData, step.parallel());
             doFooParallel(arrayData, step.parallel());


           }
           ,function (err, ?arg1,?arg2,?arg3) {
              // trace("finish now..."+Timer.stamp()+"arg"+arg1+arg2+arg3);
             doFooGroup("group1", step.group());
              doFooGroup("group1", step.group());
               doFooGroup("group1", step.group());
              }
              ,function (err, args) {
                  trace("finish"+args);
              }

      ]);



     var fromArray = [1, 2, 3, 4];

var onElement = function (element :Int, cb :String->Int->Void) {
platformDelay(100,function () {
cb("Some int=" + element,1);
});

}

var onFinish = function (err :Dynamic, result1:String->Int->Void) {
if (err != null) trace("Oh no: " + err);
trace("result=" + result1);
}

//AsyncLambda.map( fromArray,onElement , onFinish);

  doSomethingElseAsync3(1, function(err:String, e:Int,s:String):Void { trace("e=========="+e); } );



}
static inline function delay(ms:Int, cb){
    platformDelay(ms, function(){ trace(ms+' passed'); cb(null); });
}

static inline function platformDelay(ms:Int, fun){

if (cpp || neko || php) fun(); #else haxe.Timer.delay(fun, ms); #end

}

}

typedef NodeErr = Null;

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment