static bool js_cocos2dx_Sprite3D_createAsync(JSContext *cx, uint32_t argc, jsval *vp)
{
    JS::CallArgs args = JS::CallArgsFromVp(argc, vp);
    if(argc == 4 || argc == 5)
    {
        std::string modelPath;
        jsval_to_std_string(cx, args.get(0), &modelPath);

        std::function<void(Sprite3D*, void*)> callback;
        JS::RootedValue targetVal(cx, args.get(argc == 4 ? 2 : 3));
        JS::RootedObject target(cx, targetVal.toObjectOrNull());
        JS::RootedValue fval(cx, args.get(argc == 4 ? 1 : 2));
        std::shared_ptr<JSFunctionWrapper> func(new JSFunctionWrapper(cx, target, fval));
        auto lambda = [=](Sprite3D* larg0, void* larg1) -> void{
            JSB_AUTOCOMPARTMENT_WITH_GLOBAL_OBJCET
            jsval largv[2];
            largv[0] = OBJECT_TO_JSVAL(js_get_or_create_jsobject<Sprite3D>(cx, larg0));
            JSB_HeapValueWrapper* v = (JSB_HeapValueWrapper*)larg1;
            JS::RootedValue dataVal(cx, v->get());
            largv[1] = dataVal;

            JS::RootedValue rval(cx);
		    bool ok = func->invoke(2, largv, &rval);
		    if (!ok && JS_IsExceptionPending(cx)) {
		        JS_ReportPendingException(cx);
		    }

            delete v;
        };
        callback = lambda;

        JSB_HeapValueWrapper* data = new (std::nothrow) JSB_HeapValueWrapper(cx, args.get(argc == 4 ? 3 : 4));

        if(argc == 4)
            cocos2d::Sprite3D::createAsync(modelPath, callback, data);
        else
        {
            std::string texturePath;
            jsval_to_std_string(cx, args.get(1), &texturePath);
            cocos2d::Sprite3D::createAsync(modelPath, texturePath, callback, data);
        }
        return true;
    }

    JS_ReportError(cx, "wrong number of arguments");
    return false;
}
static bool js_cocos2dx_Sprite3D_createAsync(JSContext *cx, uint32_t argc, jsval *vp)
{
    JS::CallArgs args = JS::CallArgsFromVp(argc, vp);
    if(argc == 4 || argc == 5)
    {
        std::string modelPath;
        jsval_to_std_string(cx, args.get(0), &modelPath);

        std::function<void(Sprite3D*, void*)> callback;
        std::shared_ptr<JSFunctionWrapper> func(new JSFunctionWrapper(cx, args.get(argc == 4 ? 2 : 3).toObjectOrNull(), args.get(argc == 4 ? 1 : 2)));
        auto lambda = [=](Sprite3D* larg0, void* larg1) -> void{
            
            jsval largv[2];
            js_proxy_t* proxy = js_get_or_create_proxy(cx, larg0);
            largv[0] = proxy ? OBJECT_TO_JSVAL(proxy->obj) : JS::UndefinedValue();
            JSB_HeapValueWrapper* v = (JSB_HeapValueWrapper*)larg1;
            largv[1] = v->get();
            
            JS::RootedValue rval(cx);
		    bool ok = func->invoke(2, largv, &rval);
		    if (!ok && JS_IsExceptionPending(cx)) {
		        JS_ReportPendingException(cx);
		    }
            
            delete v;
        };
        callback = lambda;
        
        JSB_HeapValueWrapper* data = new JSB_HeapValueWrapper(cx, args.get(argc == 4 ? 3 : 4));
        
        if(argc == 4)
            cocos2d::Sprite3D::createAsync(modelPath, callback, data);
        else
        {
            std::string texturePath;
            jsval_to_std_string(cx, args.get(1), &texturePath);
            cocos2d::Sprite3D::createAsync(modelPath, texturePath, callback, data);
        }
        return true;
    }
    
    JS_ReportError(cx, "wrong number of arguments");
    return false;
}