mirror of https://github.com/axmolengine/axmol.git
Merge pull request #4559 from dumganhar/more_container_bind
[Scripting] Supports to bind more container: std::vector<std::string>, std::vector<int>, cocos2d::Map<std::string, T>.
This commit is contained in:
commit
c00bf38ab3
|
@ -1205,10 +1205,12 @@ const kmMat4& Node::getNodeToParentTransform() const
|
|||
|
||||
// Build Transform Matrix
|
||||
// Adjusted transform calculation for rotational skew
|
||||
_transform = { cy * _scaleX, sy * _scaleX, 0, 0,
|
||||
kmScalar mat[] = { cy * _scaleX, sy * _scaleX, 0, 0,
|
||||
-sx * _scaleY, cx * _scaleY, 0, 0,
|
||||
0, 0, 1, 0,
|
||||
x, y, 0, 1 };
|
||||
|
||||
kmMat4Fill(&_transform, mat);
|
||||
|
||||
// XXX: Try to inline skew
|
||||
// If skew is needed, apply skew and then anchor point
|
||||
|
|
|
@ -1504,58 +1504,4 @@ void jsb_remove_proxy(js_proxy_t* nativeProxy, js_proxy_t* jsProxy)
|
|||
JS_REMOVE_PROXY(nativeProxy, jsProxy);
|
||||
}
|
||||
|
||||
// JSStringWrapper
|
||||
JSStringWrapper::JSStringWrapper()
|
||||
: _buffer(nullptr)
|
||||
{
|
||||
}
|
||||
|
||||
JSStringWrapper::JSStringWrapper(JSString* str, JSContext* cx/* = NULL*/)
|
||||
: _buffer(nullptr)
|
||||
{
|
||||
set(str, cx);
|
||||
}
|
||||
|
||||
JSStringWrapper::JSStringWrapper(jsval val, JSContext* cx/* = NULL*/)
|
||||
: _buffer(nullptr)
|
||||
{
|
||||
set(val, cx);
|
||||
}
|
||||
|
||||
JSStringWrapper::~JSStringWrapper()
|
||||
{
|
||||
CC_SAFE_DELETE_ARRAY(_buffer);
|
||||
}
|
||||
|
||||
void JSStringWrapper::set(jsval val, JSContext* cx)
|
||||
{
|
||||
if (val.isString())
|
||||
{
|
||||
this->set(val.toString(), cx);
|
||||
}
|
||||
else
|
||||
{
|
||||
CC_SAFE_DELETE_ARRAY(_buffer);
|
||||
}
|
||||
}
|
||||
|
||||
void JSStringWrapper::set(JSString* str, JSContext* cx)
|
||||
{
|
||||
CC_SAFE_DELETE_ARRAY(_buffer);
|
||||
|
||||
if (!cx)
|
||||
{
|
||||
cx = ScriptingCore::getInstance()->getGlobalContext();
|
||||
}
|
||||
// JS_EncodeString isn't supported in SpiderMonkey ff19.0.
|
||||
//buffer = JS_EncodeString(cx, string);
|
||||
unsigned short* pStrUTF16 = (unsigned short*)JS_GetStringCharsZ(cx, str);
|
||||
|
||||
_buffer = cc_utf16_to_utf8(pStrUTF16, -1, NULL, NULL);
|
||||
}
|
||||
|
||||
const char* JSStringWrapper::get()
|
||||
{
|
||||
return _buffer ? _buffer : "";
|
||||
}
|
||||
|
||||
|
|
|
@ -207,57 +207,6 @@ public:
|
|||
|
||||
JSObject* NewGlobalObject(JSContext* cx, bool debug = false);
|
||||
|
||||
// just a simple utility to avoid mem leaking when using JSString
|
||||
class JSStringWrapper
|
||||
{
|
||||
public:
|
||||
JSStringWrapper();
|
||||
JSStringWrapper(JSString* str, JSContext* cx = NULL);
|
||||
JSStringWrapper(jsval val, JSContext* cx = NULL);
|
||||
~JSStringWrapper();
|
||||
|
||||
void set(jsval val, JSContext* cx);
|
||||
void set(JSString* str, JSContext* cx);
|
||||
const char* get();
|
||||
|
||||
private:
|
||||
const char* _buffer;
|
||||
|
||||
/* Copy and assignment are not supported. */
|
||||
JSStringWrapper(const JSStringWrapper &another);
|
||||
JSStringWrapper &operator=(const JSStringWrapper &another);
|
||||
};
|
||||
|
||||
// wraps a function and "this" object
|
||||
class JSFunctionWrapper
|
||||
{
|
||||
JSContext *_cx;
|
||||
JSObject *_jsthis;
|
||||
jsval _fval;
|
||||
public:
|
||||
JSFunctionWrapper(JSContext* cx, JSObject *jsthis, jsval fval)
|
||||
: _cx(cx)
|
||||
, _jsthis(jsthis)
|
||||
, _fval(fval)
|
||||
{
|
||||
JS_AddNamedValueRoot(cx, &this->_fval, "JSFunctionWrapper");
|
||||
JS_AddNamedObjectRoot(cx, &this->_jsthis, "JSFunctionWrapper");
|
||||
}
|
||||
~JSFunctionWrapper() {
|
||||
JS_RemoveValueRoot(this->_cx, &this->_fval);
|
||||
JS_RemoveObjectRoot(this->_cx, &this->_jsthis);
|
||||
}
|
||||
JSBool invoke(unsigned int argc, jsval *argv, jsval &rval) {
|
||||
JSB_AUTOCOMPARTMENT_WITH_GLOBAL_OBJCET
|
||||
|
||||
return JS_CallFunctionValue(this->_cx, this->_jsthis, this->_fval, argc, argv, &rval);
|
||||
}
|
||||
private:
|
||||
/* Copy and assignment are not supported. */
|
||||
JSFunctionWrapper(const JSFunctionWrapper &another);
|
||||
JSFunctionWrapper &operator=(const JSFunctionWrapper &another);
|
||||
};
|
||||
|
||||
JSBool jsb_set_reserved_slot(JSObject *obj, uint32_t idx, jsval value);
|
||||
JSBool jsb_get_reserved_slot(JSObject *obj, uint32_t idx, jsval& ret);
|
||||
|
||||
|
|
|
@ -12,6 +12,84 @@
|
|||
|
||||
USING_NS_CC;
|
||||
|
||||
// JSStringWrapper
|
||||
JSStringWrapper::JSStringWrapper()
|
||||
: _buffer(nullptr)
|
||||
{
|
||||
}
|
||||
|
||||
JSStringWrapper::JSStringWrapper(JSString* str, JSContext* cx/* = NULL*/)
|
||||
: _buffer(nullptr)
|
||||
{
|
||||
set(str, cx);
|
||||
}
|
||||
|
||||
JSStringWrapper::JSStringWrapper(jsval val, JSContext* cx/* = NULL*/)
|
||||
: _buffer(nullptr)
|
||||
{
|
||||
set(val, cx);
|
||||
}
|
||||
|
||||
JSStringWrapper::~JSStringWrapper()
|
||||
{
|
||||
CC_SAFE_DELETE_ARRAY(_buffer);
|
||||
}
|
||||
|
||||
void JSStringWrapper::set(jsval val, JSContext* cx)
|
||||
{
|
||||
if (val.isString())
|
||||
{
|
||||
this->set(val.toString(), cx);
|
||||
}
|
||||
else
|
||||
{
|
||||
CC_SAFE_DELETE_ARRAY(_buffer);
|
||||
}
|
||||
}
|
||||
|
||||
void JSStringWrapper::set(JSString* str, JSContext* cx)
|
||||
{
|
||||
CC_SAFE_DELETE_ARRAY(_buffer);
|
||||
|
||||
if (!cx)
|
||||
{
|
||||
cx = ScriptingCore::getInstance()->getGlobalContext();
|
||||
}
|
||||
// JS_EncodeString isn't supported in SpiderMonkey ff19.0.
|
||||
//buffer = JS_EncodeString(cx, string);
|
||||
unsigned short* pStrUTF16 = (unsigned short*)JS_GetStringCharsZ(cx, str);
|
||||
|
||||
_buffer = cc_utf16_to_utf8(pStrUTF16, -1, NULL, NULL);
|
||||
}
|
||||
|
||||
const char* JSStringWrapper::get()
|
||||
{
|
||||
return _buffer ? _buffer : "";
|
||||
}
|
||||
|
||||
// JSFunctionWrapper
|
||||
JSFunctionWrapper::JSFunctionWrapper(JSContext* cx, JSObject *jsthis, jsval fval)
|
||||
: _cx(cx)
|
||||
, _jsthis(jsthis)
|
||||
, _fval(fval)
|
||||
{
|
||||
JS_AddNamedValueRoot(cx, &this->_fval, "JSFunctionWrapper");
|
||||
JS_AddNamedObjectRoot(cx, &this->_jsthis, "JSFunctionWrapper");
|
||||
}
|
||||
|
||||
JSFunctionWrapper::~JSFunctionWrapper()
|
||||
{
|
||||
JS_RemoveValueRoot(this->_cx, &this->_fval);
|
||||
JS_RemoveObjectRoot(this->_cx, &this->_jsthis);
|
||||
}
|
||||
|
||||
JSBool JSFunctionWrapper::invoke(unsigned int argc, jsval *argv, jsval &rval)
|
||||
{
|
||||
JSB_AUTOCOMPARTMENT_WITH_GLOBAL_OBJCET
|
||||
|
||||
return JS_CallFunctionValue(this->_cx, this->_jsthis, this->_fval, argc, argv, &rval);
|
||||
}
|
||||
|
||||
static Color3B getColorFromJSObject(JSContext *cx, JSObject *colorObject)
|
||||
{
|
||||
JS::RootedValue jsr(cx);
|
||||
|
@ -1124,6 +1202,72 @@ JSBool jsval_to_ssize( JSContext *cx, jsval vp, ssize_t* ret)
|
|||
return jsval_to_long(cx, vp, reinterpret_cast<long*>(ret));
|
||||
}
|
||||
|
||||
JSBool jsval_to_std_vector_string( JSContext *cx, jsval vp, std::vector<std::string>* ret)
|
||||
{
|
||||
JSObject *jsobj;
|
||||
JSBool ok = vp.isObject() && JS_ValueToObject( cx, vp, &jsobj );
|
||||
JSB_PRECONDITION3( ok, cx, JS_FALSE, "Error converting value to object");
|
||||
JSB_PRECONDITION3( jsobj && JS_IsArrayObject( cx, jsobj), cx, JS_FALSE, "Object must be an array");
|
||||
|
||||
uint32_t len = 0;
|
||||
JS_GetArrayLength(cx, jsobj, &len);
|
||||
|
||||
for (uint32_t i=0; i < len; i++)
|
||||
{
|
||||
jsval value;
|
||||
if (JS_GetElement(cx, jsobj, i, &value))
|
||||
{
|
||||
if (JSVAL_IS_STRING(value))
|
||||
{
|
||||
JSStringWrapper valueWapper(JSVAL_TO_STRING(value), cx);
|
||||
ret->push_back(valueWapper.get());
|
||||
}
|
||||
else
|
||||
{
|
||||
JS_ReportError(cx, "not supported type in array");
|
||||
return JS_FALSE;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return JS_TRUE;
|
||||
}
|
||||
|
||||
JSBool jsval_to_std_vector_int( JSContext *cx, jsval vp, std::vector<int>* ret)
|
||||
{
|
||||
JSObject *jsobj;
|
||||
JSBool ok = vp.isObject() && JS_ValueToObject( cx, vp, &jsobj );
|
||||
JSB_PRECONDITION3( ok, cx, JS_FALSE, "Error converting value to object");
|
||||
JSB_PRECONDITION3( jsobj && JS_IsArrayObject( cx, jsobj), cx, JS_FALSE, "Object must be an array");
|
||||
|
||||
uint32_t len = 0;
|
||||
JS_GetArrayLength(cx, jsobj, &len);
|
||||
|
||||
for (uint32_t i=0; i < len; i++)
|
||||
{
|
||||
jsval value;
|
||||
if (JS_GetElement(cx, jsobj, i, &value))
|
||||
{
|
||||
if (JSVAL_IS_NUMBER(value))
|
||||
{
|
||||
double number = 0.0;
|
||||
JSBool ok = JS_ValueToNumber(cx, value, &number);
|
||||
if (ok)
|
||||
{
|
||||
ret->push_back(static_cast<int>(number));
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
JS_ReportError(cx, "not supported type in array");
|
||||
return JS_FALSE;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return JS_TRUE;
|
||||
}
|
||||
|
||||
// native --> jsval
|
||||
|
||||
jsval ccarray_to_jsval(JSContext* cx, Array *arr)
|
||||
|
|
|
@ -7,9 +7,46 @@
|
|||
|
||||
#include "jsapi.h"
|
||||
#include "js_bindings_core.h"
|
||||
#include "js_bindings_config.h"
|
||||
#include "cocos2d.h"
|
||||
#include "spidermonkey_specifics.h"
|
||||
|
||||
|
||||
// just a simple utility to avoid mem leaking when using JSString
|
||||
class JSStringWrapper
|
||||
{
|
||||
public:
|
||||
JSStringWrapper();
|
||||
JSStringWrapper(JSString* str, JSContext* cx = NULL);
|
||||
JSStringWrapper(jsval val, JSContext* cx = NULL);
|
||||
~JSStringWrapper();
|
||||
|
||||
void set(jsval val, JSContext* cx);
|
||||
void set(JSString* str, JSContext* cx);
|
||||
const char* get();
|
||||
|
||||
private:
|
||||
const char* _buffer;
|
||||
|
||||
private:
|
||||
CC_DISALLOW_COPY_AND_ASSIGN(JSStringWrapper);
|
||||
};
|
||||
|
||||
// wraps a function and "this" object
|
||||
class JSFunctionWrapper
|
||||
{
|
||||
public:
|
||||
JSFunctionWrapper(JSContext* cx, JSObject *jsthis, jsval fval);
|
||||
~JSFunctionWrapper();
|
||||
|
||||
JSBool invoke(unsigned int argc, jsval *argv, jsval &rval);
|
||||
private:
|
||||
JSContext *_cx;
|
||||
JSObject *_jsthis;
|
||||
jsval _fval;
|
||||
private:
|
||||
CC_DISALLOW_COPY_AND_ASSIGN(JSFunctionWrapper);
|
||||
};
|
||||
|
||||
JSBool jsval_to_opaque( JSContext *cx, jsval vp, void **out );
|
||||
JSBool jsval_to_int( JSContext *cx, jsval vp, int *out);
|
||||
JSBool jsval_to_uint( JSContext *cx, jsval vp, unsigned int *out);
|
||||
|
@ -115,6 +152,62 @@ JSBool jsval_to_ccvaluemap(JSContext* cx, jsval v, cocos2d::ValueMap* ret);
|
|||
JSBool jsval_to_ccintvaluemap(JSContext* cx, jsval v, cocos2d::IntValueMap* ret);
|
||||
JSBool jsval_to_ccvaluevector(JSContext* cx, jsval v, cocos2d::ValueVector* ret);
|
||||
JSBool jsval_to_ssize( JSContext *cx, jsval vp, ssize_t* ret);
|
||||
JSBool jsval_to_std_vector_string( JSContext *cx, jsval vp, std::vector<std::string>* ret);
|
||||
JSBool jsval_to_std_vector_int( JSContext *cx, jsval vp, std::vector<int>* ret);
|
||||
|
||||
template <class T>
|
||||
JSBool jsval_to_ccmap_string_key(JSContext *cx, jsval v, cocos2d::Map<std::string, T>* ret)
|
||||
{
|
||||
if (JSVAL_IS_NULL(v) || JSVAL_IS_VOID(v))
|
||||
{
|
||||
return JS_TRUE;
|
||||
}
|
||||
|
||||
JSObject* tmp = JSVAL_TO_OBJECT(v);
|
||||
if (!tmp) {
|
||||
CCLOG("%s", "jsval_to_ccvaluemap: the jsval is not an object.");
|
||||
return JS_FALSE;
|
||||
}
|
||||
|
||||
JSObject* it = JS_NewPropertyIterator(cx, tmp);
|
||||
|
||||
while (true)
|
||||
{
|
||||
jsid idp;
|
||||
jsval key;
|
||||
if (! JS_NextProperty(cx, it, &idp) || ! JS_IdToValue(cx, idp, &key)) {
|
||||
return JS_FALSE; // error
|
||||
}
|
||||
|
||||
if (key == JSVAL_VOID) {
|
||||
break; // end of iteration
|
||||
}
|
||||
|
||||
if (!JSVAL_IS_STRING(key)) {
|
||||
continue; // ignore integer properties
|
||||
}
|
||||
|
||||
JSStringWrapper keyWrapper(JSVAL_TO_STRING(key), cx);
|
||||
|
||||
JS::RootedValue value(cx);
|
||||
JS_GetPropertyById(cx, tmp, idp, &value);
|
||||
if (value.isObject())
|
||||
{
|
||||
js_proxy_t *proxy = nullptr;
|
||||
JSObject* jsobj = JSVAL_TO_OBJECT(value);
|
||||
proxy = jsb_get_js_proxy(jsobj);
|
||||
CCASSERT(proxy, "Native object should be added!");
|
||||
T cobj = (T)(proxy ? proxy->ptr : nullptr);
|
||||
ret->insert(keyWrapper.get(), cobj);
|
||||
}
|
||||
else
|
||||
{
|
||||
CCASSERT(false, "not supported type");
|
||||
}
|
||||
}
|
||||
|
||||
return JS_TRUE;
|
||||
}
|
||||
|
||||
// from native
|
||||
jsval int32_to_jsval( JSContext *cx, int32_t l);
|
||||
|
@ -171,6 +264,32 @@ jsval ccvector_to_jsval(JSContext* cx, const cocos2d::Vector<T>& v)
|
|||
return OBJECT_TO_JSVAL(jsretArr);
|
||||
}
|
||||
|
||||
template <class T>
|
||||
jsval ccmap_string_key_to_jsval(JSContext* cx, const cocos2d::Map<std::string, T>& v)
|
||||
{
|
||||
JSObject* jsRet = JS_NewObject(cx, NULL, NULL, NULL);
|
||||
|
||||
for (auto iter = v.begin(); iter != v.end(); ++iter)
|
||||
{
|
||||
JS::RootedValue element(cx);
|
||||
|
||||
std::string key = iter->first;
|
||||
T obj = iter->second;
|
||||
|
||||
//First, check whether object is associated with js object.
|
||||
js_proxy_t* jsproxy = js_get_or_create_proxy<cocos2d::Object>(cx, obj);
|
||||
if (jsproxy) {
|
||||
element = OBJECT_TO_JSVAL(jsproxy->obj);
|
||||
}
|
||||
|
||||
if (!key.empty())
|
||||
{
|
||||
JS_SetProperty(cx, jsRet, key.c_str(), element);
|
||||
}
|
||||
}
|
||||
return OBJECT_TO_JSVAL(jsRet);
|
||||
}
|
||||
|
||||
jsval ccvalue_to_jsval(JSContext* cx, const cocos2d::Value& v);
|
||||
jsval ccvaluemap_to_jsval(JSContext* cx, const cocos2d::ValueMap& v);
|
||||
jsval ccintvaluemap_to_jsval(JSContext* cx, const cocos2d::IntValueMap& v);
|
||||
|
|
|
@ -1423,6 +1423,17 @@ bool luaval_to_ccvaluevector(lua_State* L, int lo, cocos2d::ValueVector* ret)
|
|||
return ok;
|
||||
}
|
||||
|
||||
bool luaval_to_std_vector_string(lua_State* L, int lo, std::vector<std::string>* ret)
|
||||
{
|
||||
// TO BE DONE IN CPP FILE
|
||||
return false;
|
||||
}
|
||||
|
||||
bool luaval_to_std_vector_int(lua_State* L, int lo, std::vector<int>* ret)
|
||||
{
|
||||
// TO BE DONE IN CPP FILE
|
||||
return false;
|
||||
}
|
||||
|
||||
void point_to_luaval(lua_State* L,const Point& pt)
|
||||
{
|
||||
|
|
|
@ -114,6 +114,17 @@ bool luaval_to_ccvector(lua_State* L, int lo , cocos2d::Vector<T>* ret)
|
|||
return ok;
|
||||
}
|
||||
|
||||
bool luaval_to_std_vector_string(lua_State* L, int lo, std::vector<std::string>* ret);
|
||||
bool luaval_to_std_vector_int(lua_State* L, int lo, std::vector<int>* ret);
|
||||
|
||||
template <class T>
|
||||
bool luaval_to_ccmap_string_key(lua_State* L, int lo, cocos2d::Map<std::string, T>* ret)
|
||||
{
|
||||
// TO BE DONE:
|
||||
return false;
|
||||
}
|
||||
|
||||
|
||||
extern bool luaval_to_ccvalue(lua_State* L, int lo, cocos2d::Value* ret);
|
||||
extern bool luaval_to_ccvaluemap(lua_State* L, int lo, cocos2d::ValueMap* ret);
|
||||
extern bool luaval_to_ccintvaluemap(lua_State* L, int lo, cocos2d::IntValueMap* ret);
|
||||
|
@ -165,6 +176,12 @@ void ccvector_to_luaval(lua_State* L,const cocos2d::Vector<T>& inValue)
|
|||
}
|
||||
}
|
||||
|
||||
template <class T>
|
||||
void ccmap_string_key_to_luaval(lua_State* L, const cocos2d::Map<std::string, T>& v)
|
||||
{
|
||||
// TO BE DONE:
|
||||
}
|
||||
|
||||
void ccvalue_to_luaval(lua_State* L,const cocos2d::Value& inValue);
|
||||
void ccvaluemap_to_luaval(lua_State* L,const cocos2d::ValueMap& inValue);
|
||||
void ccintvaluemap_to_luaval(lua_State* L, const cocos2d::IntValueMap& inValue);
|
||||
|
|
|
@ -1 +1 @@
|
|||
Subproject commit a8e5123121a4c537bfa9e79f7adb981c17b18e6e
|
||||
Subproject commit f0b6cc8dd3d375f0999ec4e49dd90dbe1938c460
|
|
@ -43,7 +43,7 @@ skip = *::[^visit$ copyWith.* onEnter.* onExit.* ^description$ getObjectType .*H
|
|||
BatchNode::[init draw],
|
||||
Armature::[createBone updateBlendType getBody setBody getShapeList .*BlendFunc],
|
||||
Skin::[getSkinData setSkinData],
|
||||
ArmatureAnimation::[updateHandler updateFrameData frameEvent (s|g)etAnimationData],
|
||||
ArmatureAnimation::[updateHandler updateFrameData frameEvent (s|g)etAnimationData setMovementEventCallFunc setFrameEventCallFunc],
|
||||
ArmatureDataManager::[getTextureDatas],
|
||||
ActionManagerEx::[initWithDictionary],
|
||||
Bone::[getTweenData getBoneData],
|
||||
|
|
|
@ -40,7 +40,7 @@ skip = *::[^visit$ copyWith.* onEnter.* onExit.* ^description$ getObjectType .*
|
|||
ArmatureDataManager::[CCArmatureDataManager ~CCArmatureDataManager],
|
||||
Armature::[createBone updateBlendType setBody getShapeList ^getBody$],
|
||||
Skin::[(s|g)etSkinData],
|
||||
ArmatureAnimation::[updateHandler updateFrameData frameEvent],
|
||||
ArmatureAnimation::[updateHandler updateFrameData frameEvent setMovementEventCallFunc setFrameEventCallFunc],
|
||||
Bone::[(s|g)etIgnoreMovementBoneData],
|
||||
UILayer::[getInputManager],
|
||||
UILayoutParameter::[(s|g)etMargin],
|
||||
|
|
Loading…
Reference in New Issue