mirror of https://github.com/axmolengine/axmol.git
Separate FinalizeHook for ref objects and non ref objects
This commit is contained in:
parent
a73485a1bc
commit
2b6e84e9a2
|
@ -365,7 +365,7 @@ void GLView::handleTouchesMove(int num, intptr_t ids[], float xs[], float ys[],
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
|
||||||
CCLOGINFO("Moving touches with id: %d, x=%f, y=%f, force=%f, maxFource=%f", id, x, y, force, maxForce);
|
CCLOGINFO("Moving touches with id: %d, x=%f, y=%f, force=%f, maxFource=%f", (int)id, x, y, force, maxForce);
|
||||||
Touch* touch = g_touches[iter->second];
|
Touch* touch = g_touches[iter->second];
|
||||||
if (touch)
|
if (touch)
|
||||||
{
|
{
|
||||||
|
@ -417,7 +417,7 @@ void GLView::handleTouchesOfEndOrCancel(EventTouch::EventCode eventCode, int num
|
||||||
Touch* touch = g_touches[iter->second];
|
Touch* touch = g_touches[iter->second];
|
||||||
if (touch)
|
if (touch)
|
||||||
{
|
{
|
||||||
CCLOGINFO("Ending touches with id: %d, x=%f, y=%f", id, x, y);
|
CCLOGINFO("Ending touches with id: %d, x=%f, y=%f", (int)id, x, y);
|
||||||
touch->setTouchInfo(iter->second, (x - _viewPortRect.origin.x) / _scaleX,
|
touch->setTouchInfo(iter->second, (x - _viewPortRect.origin.x) / _scaleX,
|
||||||
(y - _viewPortRect.origin.y) / _scaleY);
|
(y - _viewPortRect.origin.y) / _scaleY);
|
||||||
|
|
||||||
|
|
|
@ -1438,7 +1438,7 @@ bool ScriptingCore::handleTouchesEvent(void* nativeObj, cocos2d::EventTouch::Eve
|
||||||
|
|
||||||
for (const auto& touch : touches)
|
for (const auto& touch : touches)
|
||||||
{
|
{
|
||||||
JS::RootedValue jsret(_cx, OBJECT_TO_JSVAL(jsb_get_or_create_weak_jsobject(_cx, touch, typeClassTouch, "cocos2d::Touch")));
|
JS::RootedValue jsret(_cx, OBJECT_TO_JSVAL(jsb_get_or_create_weak_jsobject(_cx, touch, typeClassTouch)));
|
||||||
if (!JS_SetElement(_cx, jsretArr, count, jsret))
|
if (!JS_SetElement(_cx, jsretArr, count, jsret))
|
||||||
{
|
{
|
||||||
break;
|
break;
|
||||||
|
@ -1451,7 +1451,7 @@ bool ScriptingCore::handleTouchesEvent(void* nativeObj, cocos2d::EventTouch::Eve
|
||||||
{
|
{
|
||||||
jsval dataVal[2];
|
jsval dataVal[2];
|
||||||
dataVal[0] = OBJECT_TO_JSVAL(jsretArr);
|
dataVal[0] = OBJECT_TO_JSVAL(jsretArr);
|
||||||
dataVal[1] = OBJECT_TO_JSVAL(jsb_get_or_create_weak_jsobject(_cx, event, typeClassEvent, "cocos2d::EventTouch"));
|
dataVal[1] = OBJECT_TO_JSVAL(jsb_get_or_create_weak_jsobject(_cx, event, typeClassEvent));
|
||||||
ret = executeFunctionWithOwner(OBJECT_TO_JSVAL(p->obj), funcName.c_str(), 2, dataVal, jsvalRet);
|
ret = executeFunctionWithOwner(OBJECT_TO_JSVAL(p->obj), funcName.c_str(), 2, dataVal, jsvalRet);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1459,7 +1459,6 @@ bool ScriptingCore::handleTouchesEvent(void* nativeObj, cocos2d::EventTouch::Eve
|
||||||
{
|
{
|
||||||
removeJSObject(_cx, touch);
|
removeJSObject(_cx, touch);
|
||||||
}
|
}
|
||||||
|
|
||||||
removeJSObject(_cx, event);
|
removeJSObject(_cx, event);
|
||||||
|
|
||||||
return ret;
|
return ret;
|
||||||
|
@ -1485,8 +1484,8 @@ bool ScriptingCore::handleTouchEvent(void* nativeObj, cocos2d::EventTouch::Event
|
||||||
js_type_class_t *typeClassEvent = js_get_type_from_native<cocos2d::EventTouch>((cocos2d::EventTouch*)event);
|
js_type_class_t *typeClassEvent = js_get_type_from_native<cocos2d::EventTouch>((cocos2d::EventTouch*)event);
|
||||||
|
|
||||||
jsval dataVal[2];
|
jsval dataVal[2];
|
||||||
dataVal[0] = OBJECT_TO_JSVAL(jsb_get_or_create_weak_jsobject(_cx, touch, typeClassTouch, "cocos2d::Touch"));
|
dataVal[0] = OBJECT_TO_JSVAL(jsb_get_or_create_weak_jsobject(_cx, touch, typeClassTouch));
|
||||||
dataVal[1] = OBJECT_TO_JSVAL(jsb_get_or_create_weak_jsobject(_cx, event, typeClassEvent, "cocos2d::EventTouch"));
|
dataVal[1] = OBJECT_TO_JSVAL(jsb_get_or_create_weak_jsobject(_cx, event, typeClassEvent));
|
||||||
|
|
||||||
ret = executeFunctionWithOwner(OBJECT_TO_JSVAL(p->obj), funcName.c_str(), 2, dataVal, jsvalRet);
|
ret = executeFunctionWithOwner(OBJECT_TO_JSVAL(p->obj), funcName.c_str(), 2, dataVal, jsvalRet);
|
||||||
}
|
}
|
||||||
|
@ -1514,7 +1513,7 @@ bool ScriptingCore::handleMouseEvent(void* nativeObj, cocos2d::EventMouse::Mouse
|
||||||
if (p)
|
if (p)
|
||||||
{
|
{
|
||||||
js_type_class_t *typeClass = js_get_type_from_native<cocos2d::EventMouse>((cocos2d::EventMouse*)event);
|
js_type_class_t *typeClass = js_get_type_from_native<cocos2d::EventMouse>((cocos2d::EventMouse*)event);
|
||||||
jsval dataVal = OBJECT_TO_JSVAL(jsb_get_or_create_weak_jsobject(_cx, event, typeClass, "cocos2d::EventMouse"));
|
jsval dataVal = OBJECT_TO_JSVAL(jsb_get_or_create_weak_jsobject(_cx, event, typeClass));
|
||||||
ret = executeFunctionWithOwner(OBJECT_TO_JSVAL(p->obj), funcName.c_str(), 1, &dataVal, jsvalRet);
|
ret = executeFunctionWithOwner(OBJECT_TO_JSVAL(p->obj), funcName.c_str(), 1, &dataVal, jsvalRet);
|
||||||
|
|
||||||
removeJSObject(_cx, event);
|
removeJSObject(_cx, event);
|
||||||
|
@ -1611,7 +1610,7 @@ bool ScriptingCore::handleKeyboardEvent(void* nativeObj, cocos2d::EventKeyboard:
|
||||||
js_type_class_t *typeClass = js_get_type_from_native<cocos2d::EventKeyboard>((cocos2d::EventKeyboard*)event);
|
js_type_class_t *typeClass = js_get_type_from_native<cocos2d::EventKeyboard>((cocos2d::EventKeyboard*)event);
|
||||||
jsval args[2] = {
|
jsval args[2] = {
|
||||||
int32_to_jsval(_cx, (int32_t)keyCode),
|
int32_to_jsval(_cx, (int32_t)keyCode),
|
||||||
OBJECT_TO_JSVAL(jsb_get_or_create_weak_jsobject(_cx, event, typeClass, "cocos2d::EventKeyboard"))
|
OBJECT_TO_JSVAL(jsb_get_or_create_weak_jsobject(_cx, event, typeClass))
|
||||||
};
|
};
|
||||||
|
|
||||||
if (isPressed)
|
if (isPressed)
|
||||||
|
@ -1662,7 +1661,7 @@ int ScriptingCore::executeCustomTouchesEvent(EventTouch::EventCode eventType,
|
||||||
{
|
{
|
||||||
js_type_class_t *typeClass = js_get_type_from_native<cocos2d::Touch>(touch);
|
js_type_class_t *typeClass = js_get_type_from_native<cocos2d::Touch>(touch);
|
||||||
|
|
||||||
jsval jsret = OBJECT_TO_JSVAL(jsb_get_or_create_weak_jsobject(this->_cx, touch, typeClass, "cocos2d::Touch"));
|
jsval jsret = OBJECT_TO_JSVAL(jsb_get_or_create_weak_jsobject(this->_cx, touch, typeClass));
|
||||||
JS::RootedValue jsval(_cx, jsret);
|
JS::RootedValue jsval(_cx, jsret);
|
||||||
if (!JS_SetElement(this->_cx, jsretArr, count, jsval)) {
|
if (!JS_SetElement(this->_cx, jsretArr, count, jsval)) {
|
||||||
break;
|
break;
|
||||||
|
@ -1690,7 +1689,7 @@ int ScriptingCore::executeCustomTouchEvent(EventTouch::EventCode eventType, Touc
|
||||||
std::string funcName = getTouchFuncName(eventType);
|
std::string funcName = getTouchFuncName(eventType);
|
||||||
|
|
||||||
js_type_class_t *typeClass = js_get_type_from_native<cocos2d::Touch>(touch);
|
js_type_class_t *typeClass = js_get_type_from_native<cocos2d::Touch>(touch);
|
||||||
jsval jsTouch = OBJECT_TO_JSVAL(jsb_get_or_create_weak_jsobject(this->_cx, touch, typeClass, "cocos2d::Touch"));
|
jsval jsTouch = OBJECT_TO_JSVAL(jsb_get_or_create_weak_jsobject(this->_cx, touch, typeClass));
|
||||||
|
|
||||||
executeFunctionWithOwner(OBJECT_TO_JSVAL(obj), funcName.c_str(), 1, &jsTouch, &retval);
|
executeFunctionWithOwner(OBJECT_TO_JSVAL(obj), funcName.c_str(), 1, &jsTouch, &retval);
|
||||||
|
|
||||||
|
@ -1709,7 +1708,7 @@ int ScriptingCore::executeCustomTouchEvent(EventTouch::EventCode eventType,
|
||||||
std::string funcName = getTouchFuncName(eventType);
|
std::string funcName = getTouchFuncName(eventType);
|
||||||
|
|
||||||
js_type_class_t *typeClass = js_get_type_from_native<cocos2d::Touch>(touch);
|
js_type_class_t *typeClass = js_get_type_from_native<cocos2d::Touch>(touch);
|
||||||
jsval jsTouch = OBJECT_TO_JSVAL(jsb_get_or_create_weak_jsobject(this->_cx, touch, typeClass, "cocos2d::Touch"));
|
jsval jsTouch = OBJECT_TO_JSVAL(jsb_get_or_create_weak_jsobject(this->_cx, touch, typeClass));
|
||||||
|
|
||||||
executeFunctionWithOwner(OBJECT_TO_JSVAL(obj), funcName.c_str(), 1, &jsTouch, retval);
|
executeFunctionWithOwner(OBJECT_TO_JSVAL(obj), funcName.c_str(), 1, &jsTouch, retval);
|
||||||
|
|
||||||
|
@ -2308,12 +2307,16 @@ JSObject* jsb_create_weak_jsobject(JSContext *cx, void *native, js_type_class_t
|
||||||
JS::RootedObject parent(cx, typeClass->parentProto.ref());
|
JS::RootedObject parent(cx, typeClass->parentProto.ref());
|
||||||
JS::RootedObject jsObj(cx, JS_NewObject(cx, typeClass->jsclass, proto, parent));
|
JS::RootedObject jsObj(cx, JS_NewObject(cx, typeClass->jsclass, proto, parent));
|
||||||
auto proxy = jsb_new_proxy(native, jsObj);
|
auto proxy = jsb_new_proxy(native, jsObj);
|
||||||
|
js_add_FinalizeHook(cx, jsObj, false);
|
||||||
|
|
||||||
#if ! CC_ENABLE_GC_FOR_NATIVE_OBJECTS
|
#if ! CC_ENABLE_GC_FOR_NATIVE_OBJECTS
|
||||||
JS::AddNamedObjectRoot(cx, &proxy->obj, debug);
|
JS::AddNamedObjectRoot(cx, &proxy->obj, debug);
|
||||||
#else
|
#else
|
||||||
#if COCOS2D_DEBUG > 1
|
#if COCOS2D_DEBUG > 1
|
||||||
|
if (debug != nullptr)
|
||||||
|
{
|
||||||
CCLOG("++++++WEAK_REF++++++ Cpp(%s): %p - JS: %p", debug, native, jsObj.get());
|
CCLOG("++++++WEAK_REF++++++ Cpp(%s): %p - JS: %p", debug, native, jsObj.get());
|
||||||
|
}
|
||||||
#endif // COCOS2D_DEBUG
|
#endif // COCOS2D_DEBUG
|
||||||
#endif // CC_ENABLE_GC_FOR_NATIVE_OBJECTS
|
#endif // CC_ENABLE_GC_FOR_NATIVE_OBJECTS
|
||||||
return jsObj;
|
return jsObj;
|
||||||
|
@ -2336,7 +2339,7 @@ JSObject* jsb_ref_get_or_create_jsobject(JSContext *cx, cocos2d::Ref *ref, js_ty
|
||||||
js_proxy_t* newproxy = jsb_new_proxy(ref, jsObj);
|
js_proxy_t* newproxy = jsb_new_proxy(ref, jsObj);
|
||||||
#if CC_ENABLE_GC_FOR_NATIVE_OBJECTS
|
#if CC_ENABLE_GC_FOR_NATIVE_OBJECTS
|
||||||
ref->retain();
|
ref->retain();
|
||||||
js_add_FinalizeHook(cx, jsObj);
|
js_add_FinalizeHook(cx, jsObj, true);
|
||||||
#if COCOS2D_DEBUG > 1
|
#if COCOS2D_DEBUG > 1
|
||||||
CCLOG("++++++RETAINED++++++ Cpp(%s): %p - JS: %p", debug, ref, jsObj.get());
|
CCLOG("++++++RETAINED++++++ Cpp(%s): %p - JS: %p", debug, ref, jsObj.get());
|
||||||
#endif // COCOS2D_DEBUG
|
#endif // COCOS2D_DEBUG
|
||||||
|
@ -2398,7 +2401,7 @@ void jsb_ref_init(JSContext* cx, JS::Heap<JSObject*> *obj, Ref* ref, const char*
|
||||||
#if CC_ENABLE_GC_FOR_NATIVE_OBJECTS
|
#if CC_ENABLE_GC_FOR_NATIVE_OBJECTS
|
||||||
(void)ref;
|
(void)ref;
|
||||||
JS::RootedObject jsObj(cx, *obj);
|
JS::RootedObject jsObj(cx, *obj);
|
||||||
js_add_FinalizeHook(cx, jsObj);
|
js_add_FinalizeHook(cx, jsObj, true);
|
||||||
// don't retain it, already retained
|
// don't retain it, already retained
|
||||||
#if COCOS2D_DEBUG > 1
|
#if COCOS2D_DEBUG > 1
|
||||||
CCLOG("++++++RETAINED++++++ Cpp(%s): %p - JS: %p", debug, ref, jsObj.get());
|
CCLOG("++++++RETAINED++++++ Cpp(%s): %p - JS: %p", debug, ref, jsObj.get());
|
||||||
|
@ -2418,7 +2421,7 @@ void jsb_ref_autoreleased_init(JSContext* cx, JS::Heap<JSObject*> *obj, Ref* ref
|
||||||
(void)obj;
|
(void)obj;
|
||||||
ref->retain();
|
ref->retain();
|
||||||
JS::RootedObject jsObj(cx, *obj);
|
JS::RootedObject jsObj(cx, *obj);
|
||||||
js_add_FinalizeHook(cx, jsObj);
|
js_add_FinalizeHook(cx, jsObj, true);
|
||||||
#else
|
#else
|
||||||
// don't autorelease it, since it is already autoreleased
|
// don't autorelease it, since it is already autoreleased
|
||||||
JS::AddNamedObjectRoot(cx, obj, debug);
|
JS::AddNamedObjectRoot(cx, obj, debug);
|
||||||
|
@ -2440,7 +2443,9 @@ void jsb_ref_rebind(JSContext* cx, JS::HandleObject jsobj, js_proxy_t *proxy, co
|
||||||
// Rebind js obj with new action
|
// Rebind js obj with new action
|
||||||
js_proxy_t* newProxy = jsb_new_proxy(newRef, jsobj);
|
js_proxy_t* newProxy = jsb_new_proxy(newRef, jsobj);
|
||||||
|
|
||||||
#if !CC_ENABLE_GC_FOR_NATIVE_OBJECTS
|
#if CC_ENABLE_GC_FOR_NATIVE_OBJECTS
|
||||||
|
CC_UNUSED_PARAM(newProxy);
|
||||||
|
#else
|
||||||
JS::AddNamedObjectRoot(cx, &newProxy->obj, debug);
|
JS::AddNamedObjectRoot(cx, &newProxy->obj, debug);
|
||||||
#endif
|
#endif
|
||||||
}
|
}
|
||||||
|
|
|
@ -665,7 +665,7 @@ JSObject* jsb_ref_get_or_create_jsobject(JSContext *cx, cocos2d::Ref *ref, js_ty
|
||||||
* If it can't find it, it will create a new one associating it to Ref
|
* If it can't find it, it will create a new one associating it to Ref
|
||||||
* Call this function for objects that might return an already existing copy when you create them. For example, `Animation3D::create()`;
|
* Call this function for objects that might return an already existing copy when you create them. For example, `Animation3D::create()`;
|
||||||
*/
|
*/
|
||||||
JSObject* jsb_ref_autoreleased_get_or_create_jsobject(JSContext *cx, cocos2d::Ref *ref, js_type_class_t *typeClass, const char* debug);
|
JSObject* jsb_ref_autoreleased_get_or_create_jsobject(JSContext *cx, cocos2d::Ref *ref, js_type_class_t *typeClass, const char* debug=nullptr);
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* It will try to get the associated JSObjct for the native object.
|
* It will try to get the associated JSObjct for the native object.
|
||||||
|
@ -673,7 +673,7 @@ JSObject* jsb_ref_autoreleased_get_or_create_jsobject(JSContext *cx, cocos2d::Re
|
||||||
* The reference created from JSObject to native object is weak because it won't retain it.
|
* The reference created from JSObject to native object is weak because it won't retain it.
|
||||||
* The behavior is exactly the same with 'jsb_ref_get_or_create_jsobject' when CC_ENABLE_GC_FOR_NATIVE_OBJECTS deactivated.
|
* The behavior is exactly the same with 'jsb_ref_get_or_create_jsobject' when CC_ENABLE_GC_FOR_NATIVE_OBJECTS deactivated.
|
||||||
*/
|
*/
|
||||||
CC_JS_DLL JSObject* jsb_get_or_create_weak_jsobject(JSContext *cx, void *native, js_type_class_t *typeClass, const char* debug);
|
CC_JS_DLL JSObject* jsb_get_or_create_weak_jsobject(JSContext *cx, void *native, js_type_class_t *typeClass, const char* debug=nullptr);
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Register finalize hook and its owner as an entry in _js_hook_owner_map,
|
* Register finalize hook and its owner as an entry in _js_hook_owner_map,
|
||||||
|
|
|
@ -562,10 +562,19 @@ js_type_class_t *js_get_type_from_node(cocos2d::Node* native_obj)
|
||||||
return js_get_type_from_native<cocos2d::Node>(native_obj);
|
return js_get_type_from_native<cocos2d::Node>(native_obj);
|
||||||
}
|
}
|
||||||
|
|
||||||
void js_add_FinalizeHook(JSContext *cx, JS::HandleObject target)
|
void js_add_FinalizeHook(JSContext *cx, JS::HandleObject target, bool isRef)
|
||||||
{
|
{
|
||||||
JS::RootedObject proto(cx, jsb_FinalizeHook_prototype);
|
JS::RootedObject hook(cx);
|
||||||
JS::RootedObject hook(cx, JS_NewObject(cx, jsb_FinalizeHook_class, proto, JS::NullPtr()));
|
if (isRef)
|
||||||
|
{
|
||||||
|
JS::RootedObject proto(cx, jsb_RefFinalizeHook_prototype);
|
||||||
|
hook = JS_NewObject(cx, jsb_RefFinalizeHook_class, proto, JS::NullPtr());
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
JS::RootedObject proto(cx, jsb_ObjFinalizeHook_prototype);
|
||||||
|
hook = JS_NewObject(cx, jsb_ObjFinalizeHook_class, proto, JS::NullPtr());
|
||||||
|
}
|
||||||
jsb_register_finalize_hook(hook.get(), target.get());
|
jsb_register_finalize_hook(hook.get(), target.get());
|
||||||
JS::RootedValue hookVal(cx, OBJECT_TO_JSVAL(hook));
|
JS::RootedValue hookVal(cx, OBJECT_TO_JSVAL(hook));
|
||||||
JS_SetProperty(cx, target, "__hook", hookVal);
|
JS_SetProperty(cx, target, "__hook", hookVal);
|
||||||
|
@ -5876,15 +5885,17 @@ bool js_cocos2dx_ComponentJS_getScriptObject(JSContext *cx, uint32_t argc, jsval
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
JSClass *jsb_FinalizeHook_class;
|
JSClass *jsb_RefFinalizeHook_class;
|
||||||
JSObject *jsb_FinalizeHook_prototype;
|
JSObject *jsb_RefFinalizeHook_prototype;
|
||||||
|
JSClass *jsb_ObjFinalizeHook_class;
|
||||||
|
JSObject *jsb_ObjFinalizeHook_prototype;
|
||||||
|
|
||||||
static bool jsb_FinalizeHook_constructor(JSContext *cx, uint32_t argc, jsval *vp)
|
static bool jsb_RefFinalizeHook_constructor(JSContext *cx, uint32_t argc, jsval *vp)
|
||||||
{
|
{
|
||||||
JS::CallArgs args = JS::CallArgsFromVp(argc, vp);
|
JS::CallArgs args = JS::CallArgsFromVp(argc, vp);
|
||||||
// Create new object
|
// Create new object
|
||||||
JS::RootedObject proto(cx, jsb_FinalizeHook_prototype);
|
JS::RootedObject proto(cx, jsb_RefFinalizeHook_prototype);
|
||||||
JS::RootedObject obj(cx, JS_NewObject(cx, jsb_FinalizeHook_class, proto, JS::NullPtr()));
|
JS::RootedObject obj(cx, JS_NewObject(cx, jsb_RefFinalizeHook_class, proto, JS::NullPtr()));
|
||||||
// Register arguments[0] as owner
|
// Register arguments[0] as owner
|
||||||
if (!args.get(0).isNullOrUndefined())
|
if (!args.get(0).isNullOrUndefined())
|
||||||
{
|
{
|
||||||
|
@ -5893,7 +5904,7 @@ static bool jsb_FinalizeHook_constructor(JSContext *cx, uint32_t argc, jsval *vp
|
||||||
args.rval().set(OBJECT_TO_JSVAL(obj));
|
args.rval().set(OBJECT_TO_JSVAL(obj));
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
void jsb_FinalizeHook_finalize(JSFreeOp *fop, JSObject *obj)
|
void jsb_RefFinalizeHook_finalize(JSFreeOp *fop, JSObject *obj)
|
||||||
{
|
{
|
||||||
ScriptingCore *sc = ScriptingCore::getInstance();
|
ScriptingCore *sc = ScriptingCore::getInstance();
|
||||||
JSContext *cx = sc->getGlobalContext();
|
JSContext *cx = sc->getGlobalContext();
|
||||||
|
@ -5902,7 +5913,7 @@ void jsb_FinalizeHook_finalize(JSFreeOp *fop, JSObject *obj)
|
||||||
if (ownerPtr)
|
if (ownerPtr)
|
||||||
{
|
{
|
||||||
JS::RootedObject owner(cx, ownerPtr);
|
JS::RootedObject owner(cx, ownerPtr);
|
||||||
CCLOGINFO("jsbindings: finalizing JS object via Finalizehook %p", owner.get());
|
CCLOGINFO("jsbindings: finalizing JS object via RefFinalizehook %p", owner.get());
|
||||||
js_proxy_t* nproxy = nullptr;
|
js_proxy_t* nproxy = nullptr;
|
||||||
js_proxy_t* jsproxy = nullptr;
|
js_proxy_t* jsproxy = nullptr;
|
||||||
jsproxy = jsb_get_js_proxy(owner);
|
jsproxy = jsb_get_js_proxy(owner);
|
||||||
|
@ -5931,11 +5942,6 @@ void jsb_FinalizeHook_finalize(JSFreeOp *fop, JSObject *obj)
|
||||||
CCLOG("------RELEASED------ Cpp: %p - JS: %p", refObj, ownerPtr);
|
CCLOG("------RELEASED------ Cpp: %p - JS: %p", refObj, ownerPtr);
|
||||||
#endif // COCOS2D_DEBUG
|
#endif // COCOS2D_DEBUG
|
||||||
}
|
}
|
||||||
#if COCOS2D_DEBUG > 1
|
|
||||||
else {
|
|
||||||
CCLOG("A non ref object have registered finalize hook: %p", nproxy->ptr);
|
|
||||||
}
|
|
||||||
#endif // COCOS2D_DEBUG
|
|
||||||
sc->setFinalizing(nullptr);
|
sc->setFinalizing(nullptr);
|
||||||
}
|
}
|
||||||
#if COCOS2D_DEBUG > 1
|
#if COCOS2D_DEBUG > 1
|
||||||
|
@ -5945,24 +5951,83 @@ void jsb_FinalizeHook_finalize(JSFreeOp *fop, JSObject *obj)
|
||||||
#endif // COCOS2D_DEBUG
|
#endif // COCOS2D_DEBUG
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
static bool jsb_ObjFinalizeHook_constructor(JSContext *cx, uint32_t argc, jsval *vp)
|
||||||
|
{
|
||||||
|
JS::CallArgs args = JS::CallArgsFromVp(argc, vp);
|
||||||
|
// Create new object
|
||||||
|
JS::RootedObject proto(cx, jsb_ObjFinalizeHook_prototype);
|
||||||
|
JS::RootedObject obj(cx, JS_NewObject(cx, jsb_ObjFinalizeHook_class, proto, JS::NullPtr()));
|
||||||
|
// Register arguments[0] as owner
|
||||||
|
if (!args.get(0).isNullOrUndefined())
|
||||||
|
{
|
||||||
|
jsb_register_finalize_hook(obj.get(), args.get(0).toObjectOrNull());
|
||||||
|
}
|
||||||
|
args.rval().set(OBJECT_TO_JSVAL(obj));
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
void jsb_ObjFinalizeHook_finalize(JSFreeOp *fop, JSObject *obj)
|
||||||
|
{
|
||||||
|
ScriptingCore *sc = ScriptingCore::getInstance();
|
||||||
|
JSContext *cx = sc->getGlobalContext();
|
||||||
|
JS::RootedObject jsobj(cx, obj);
|
||||||
|
JSObject *ownerPtr = jsb_get_and_remove_hook_owner(obj);
|
||||||
|
if (ownerPtr)
|
||||||
|
{
|
||||||
|
JS::RootedObject owner(cx, ownerPtr);
|
||||||
|
CCLOGINFO("jsbindings: finalizing JS object via ObjFinalizehook %p", owner.get());
|
||||||
|
js_proxy_t* nproxy = nullptr;
|
||||||
|
js_proxy_t* jsproxy = nullptr;
|
||||||
|
jsproxy = jsb_get_js_proxy(owner);
|
||||||
|
if (jsproxy)
|
||||||
|
{
|
||||||
|
sc->setFinalizing(ownerPtr);
|
||||||
|
|
||||||
void jsb_register_FinalizeHook(JSContext *cx, JS::HandleObject global) {
|
nproxy = jsb_get_native_proxy(jsproxy->ptr);
|
||||||
jsb_FinalizeHook_class = (JSClass *)calloc(1, sizeof(JSClass));
|
jsb_remove_proxy(nproxy, jsproxy);
|
||||||
jsb_FinalizeHook_class->name = "FinalizeHook";
|
#if COCOS2D_DEBUG > 1
|
||||||
jsb_FinalizeHook_class->addProperty = JS_PropertyStub;
|
CCLOG("------WEAK_REF------ Cpp: %p - JS: %p", nproxy->ptr, ownerPtr);
|
||||||
jsb_FinalizeHook_class->delProperty = JS_DeletePropertyStub;
|
#endif // COCOS2D_DEBUG
|
||||||
jsb_FinalizeHook_class->getProperty = JS_PropertyStub;
|
sc->setFinalizing(nullptr);
|
||||||
jsb_FinalizeHook_class->setProperty = JS_StrictPropertyStub;
|
}
|
||||||
jsb_FinalizeHook_class->enumerate = JS_EnumerateStub;
|
}
|
||||||
jsb_FinalizeHook_class->resolve = JS_ResolveStub;
|
}
|
||||||
jsb_FinalizeHook_class->convert = JS_ConvertStub;
|
|
||||||
jsb_FinalizeHook_class->finalize = jsb_FinalizeHook_finalize;
|
|
||||||
jsb_FinalizeHook_class->flags = JSCLASS_HAS_RESERVED_SLOTS(2);
|
|
||||||
|
|
||||||
jsb_FinalizeHook_prototype = JS_InitClass(cx, global,
|
void jsb_register_RefFinalizeHook(JSContext *cx, JS::HandleObject global) {
|
||||||
|
jsb_RefFinalizeHook_class = (JSClass *)calloc(1, sizeof(JSClass));
|
||||||
|
jsb_RefFinalizeHook_class->name = "RefFinalizeHook";
|
||||||
|
jsb_RefFinalizeHook_class->addProperty = JS_PropertyStub;
|
||||||
|
jsb_RefFinalizeHook_class->delProperty = JS_DeletePropertyStub;
|
||||||
|
jsb_RefFinalizeHook_class->getProperty = JS_PropertyStub;
|
||||||
|
jsb_RefFinalizeHook_class->setProperty = JS_StrictPropertyStub;
|
||||||
|
jsb_RefFinalizeHook_class->enumerate = JS_EnumerateStub;
|
||||||
|
jsb_RefFinalizeHook_class->resolve = JS_ResolveStub;
|
||||||
|
jsb_RefFinalizeHook_class->convert = JS_ConvertStub;
|
||||||
|
jsb_RefFinalizeHook_class->finalize = jsb_RefFinalizeHook_finalize;
|
||||||
|
jsb_RefFinalizeHook_class->flags = JSCLASS_HAS_RESERVED_SLOTS(2);
|
||||||
|
|
||||||
|
jsb_RefFinalizeHook_prototype = JS_InitClass(cx, global,
|
||||||
JS::NullPtr(), // parent proto
|
JS::NullPtr(), // parent proto
|
||||||
jsb_FinalizeHook_class,
|
jsb_RefFinalizeHook_class,
|
||||||
jsb_FinalizeHook_constructor, 0, // constructor
|
jsb_RefFinalizeHook_constructor, 0, // constructor
|
||||||
|
NULL, NULL, NULL, NULL);
|
||||||
|
}
|
||||||
|
void jsb_register_ObjFinalizeHook(JSContext *cx, JS::HandleObject global) {
|
||||||
|
jsb_ObjFinalizeHook_class = (JSClass *)calloc(1, sizeof(JSClass));
|
||||||
|
jsb_ObjFinalizeHook_class->name = "ObjFinalizeHook";
|
||||||
|
jsb_ObjFinalizeHook_class->addProperty = JS_PropertyStub;
|
||||||
|
jsb_ObjFinalizeHook_class->delProperty = JS_DeletePropertyStub;
|
||||||
|
jsb_ObjFinalizeHook_class->getProperty = JS_PropertyStub;
|
||||||
|
jsb_ObjFinalizeHook_class->setProperty = JS_StrictPropertyStub;
|
||||||
|
jsb_ObjFinalizeHook_class->enumerate = JS_EnumerateStub;
|
||||||
|
jsb_ObjFinalizeHook_class->resolve = JS_ResolveStub;
|
||||||
|
jsb_ObjFinalizeHook_class->convert = JS_ConvertStub;
|
||||||
|
jsb_ObjFinalizeHook_class->finalize = jsb_ObjFinalizeHook_finalize;
|
||||||
|
jsb_ObjFinalizeHook_class->flags = JSCLASS_HAS_RESERVED_SLOTS(2);
|
||||||
|
|
||||||
|
jsb_ObjFinalizeHook_prototype = JS_InitClass(cx, global,
|
||||||
|
JS::NullPtr(), // parent proto
|
||||||
|
jsb_ObjFinalizeHook_class,
|
||||||
|
jsb_ObjFinalizeHook_constructor, 0, // constructor
|
||||||
NULL, NULL, NULL, NULL);
|
NULL, NULL, NULL, NULL);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -5976,7 +6041,8 @@ void register_cocos2dx_js_core(JSContext* cx, JS::HandleObject global)
|
||||||
get_or_create_js_obj(cx, global, "jsb", &jsbObj);
|
get_or_create_js_obj(cx, global, "jsb", &jsbObj);
|
||||||
|
|
||||||
// Memory management related
|
// Memory management related
|
||||||
jsb_register_FinalizeHook(cx, jsbObj);
|
jsb_register_RefFinalizeHook(cx, jsbObj);
|
||||||
|
jsb_register_ObjFinalizeHook(cx, jsbObj);
|
||||||
|
|
||||||
js_register_cocos2dx_PolygonInfo(cx, jsbObj);
|
js_register_cocos2dx_PolygonInfo(cx, jsbObj);
|
||||||
js_register_cocos2dx_AutoPolygon(cx, jsbObj);
|
js_register_cocos2dx_AutoPolygon(cx, jsbObj);
|
||||||
|
|
|
@ -79,8 +79,10 @@ extern schedFunc_proxy_t *_schedFunc_target_ht;
|
||||||
extern schedTarget_proxy_t *_schedObj_target_ht;
|
extern schedTarget_proxy_t *_schedObj_target_ht;
|
||||||
extern callfuncTarget_proxy_t *_callfuncTarget_native_ht;
|
extern callfuncTarget_proxy_t *_callfuncTarget_native_ht;
|
||||||
|
|
||||||
extern JSClass *jsb_FinalizeHook_class;
|
extern JSClass *jsb_RefFinalizeHook_class;
|
||||||
extern JSObject *jsb_FinalizeHook_prototype;
|
extern JSObject *jsb_RefFinalizeHook_prototype;
|
||||||
|
extern JSClass *jsb_ObjFinalizeHook_class;
|
||||||
|
extern JSObject *jsb_ObjFinalizeHook_prototype;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* You don't need to manage the returned pointer. They live for the whole life of
|
* You don't need to manage the returned pointer. They live for the whole life of
|
||||||
|
@ -142,7 +144,7 @@ JSObject* js_get_or_create_jsobject(JSContext *cx, typename std::enable_if<std::
|
||||||
* In the finalize function, it mainly remove native/js proxys, release/delete the native object.
|
* In the finalize function, it mainly remove native/js proxys, release/delete the native object.
|
||||||
* IMPORTANT: For Ref objects, please remember to retain the native object to correctly manage its reference count.
|
* IMPORTANT: For Ref objects, please remember to retain the native object to correctly manage its reference count.
|
||||||
*/
|
*/
|
||||||
void js_add_FinalizeHook(JSContext *cx, JS::HandleObject target);
|
void js_add_FinalizeHook(JSContext *cx, JS::HandleObject target, bool isRef=true);
|
||||||
|
|
||||||
void js_add_object_reference(JS::HandleValue owner, JS::HandleValue target);
|
void js_add_object_reference(JS::HandleValue owner, JS::HandleValue target);
|
||||||
void js_remove_object_reference(JS::HandleValue owner, JS::HandleValue target);
|
void js_remove_object_reference(JS::HandleValue owner, JS::HandleValue target);
|
||||||
|
@ -170,6 +172,7 @@ protected:
|
||||||
JS::Heap<JS::Value> _jsCallback;
|
JS::Heap<JS::Value> _jsCallback;
|
||||||
JS::Heap<JS::Value> _jsThisObj;
|
JS::Heap<JS::Value> _jsThisObj;
|
||||||
JS::Heap<JS::Value> _extraData;
|
JS::Heap<JS::Value> _extraData;
|
||||||
|
bool _rooted;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
||||||
|
|
|
@ -179,7 +179,7 @@ bool js_EventListenerAcceleration_create(JSContext *cx, uint32_t argc, jsval *vp
|
||||||
largv[0] = ccacceleration_to_jsval(cx, *acc);
|
largv[0] = ccacceleration_to_jsval(cx, *acc);
|
||||||
if (event) {
|
if (event) {
|
||||||
js_type_class_t *typeClassEvent = js_get_type_from_native<Event>(event);
|
js_type_class_t *typeClassEvent = js_get_type_from_native<Event>(event);
|
||||||
largv[1] = OBJECT_TO_JSVAL(jsb_get_or_create_weak_jsobject(cx, event, typeClassEvent, "cocos2d::EventAcceleration"));
|
largv[1] = OBJECT_TO_JSVAL(jsb_get_or_create_weak_jsobject(cx, event, typeClassEvent));
|
||||||
} else {
|
} else {
|
||||||
largv[1] = JSVAL_NULL;
|
largv[1] = JSVAL_NULL;
|
||||||
};
|
};
|
||||||
|
@ -246,7 +246,7 @@ bool js_EventListenerCustom_create(JSContext *cx, uint32_t argc, jsval *vp)
|
||||||
jsval largv[1];
|
jsval largv[1];
|
||||||
if (event) {
|
if (event) {
|
||||||
js_type_class_t *typeClassEvent = js_get_type_from_native<EventCustom>(event);
|
js_type_class_t *typeClassEvent = js_get_type_from_native<EventCustom>(event);
|
||||||
largv[0] = OBJECT_TO_JSVAL(jsb_get_or_create_weak_jsobject(cx, event, typeClassEvent, "cocos2d::EventCustom"));
|
largv[0] = OBJECT_TO_JSVAL(jsb_get_or_create_weak_jsobject(cx, event, typeClassEvent));
|
||||||
} else {
|
} else {
|
||||||
largv[0] = JSVAL_NULL;
|
largv[0] = JSVAL_NULL;
|
||||||
};
|
};
|
||||||
|
@ -298,7 +298,7 @@ bool js_EventDispatcher_addCustomEventListener(JSContext *cx, uint32_t argc, jsv
|
||||||
jsval largv[1];
|
jsval largv[1];
|
||||||
if (event) {
|
if (event) {
|
||||||
js_type_class_t *typeClassEvent = js_get_type_from_native<EventCustom>(event);
|
js_type_class_t *typeClassEvent = js_get_type_from_native<EventCustom>(event);
|
||||||
largv[0] = OBJECT_TO_JSVAL(jsb_get_or_create_weak_jsobject(cx, event, typeClassEvent, "cocos2d::EventCustom"));
|
largv[0] = OBJECT_TO_JSVAL(jsb_get_or_create_weak_jsobject(cx, event, typeClassEvent));
|
||||||
} else {
|
} else {
|
||||||
largv[0] = JSVAL_NULL;
|
largv[0] = JSVAL_NULL;
|
||||||
};
|
};
|
||||||
|
|
|
@ -400,7 +400,7 @@ JS_BINDED_CONSTRUCTOR_IMPL(MinXmlHttpRequest)
|
||||||
js_proxy_t *p = jsb_new_proxy(req, obj);
|
js_proxy_t *p = jsb_new_proxy(req, obj);
|
||||||
|
|
||||||
#if CC_ENABLE_GC_FOR_NATIVE_OBJECTS
|
#if CC_ENABLE_GC_FOR_NATIVE_OBJECTS
|
||||||
js_add_FinalizeHook(cx, obj);
|
js_add_FinalizeHook(cx, obj, true);
|
||||||
// don't retain it, already retained
|
// don't retain it, already retained
|
||||||
#if COCOS2D_DEBUG > 1
|
#if COCOS2D_DEBUG > 1
|
||||||
CCLOG("++++++RETAINED++++++ Cpp(XMLHttpRequest): %p - JS: %p", req, obj.get());
|
CCLOG("++++++RETAINED++++++ Cpp(XMLHttpRequest): %p - JS: %p", req, obj.get());
|
||||||
|
|
Loading…
Reference in New Issue