2dx关于js响应layer触摸消息的bug
cocos2dx关于js响应layer触摸消息的bug
cocos2d-x 3.7
问题描述:
目前这个版本中(3.7),c++层的layer触摸消息只能通过消息的方式发送给js,不能像lua一样直接回调js注册的触摸回调接口,为了方便,我们更改一下layer类的onTouchBegan/onTouchMove...等接口,使其支持在layer的触摸响应中直接回调js接口。
具体实现见:http://www.cnblogs.com/songcf/p/4764444.html
ok,在这之后就会发现ScriptingCore中有一个触摸响应判断的bug:
只要c++对js的ontouchbegan函数调用成功,都会被视为当前layer捕捉到了该触摸(即return true)
如果该layer开启了吞噬触摸,那么此次touch永远被该layer捕获,不再传递下去,即使你在js层中注册的onTouchBegan是return false,也无济于事。
那么造成该bug的原因如下:
//Layer判断是否捕获该touch,取决于executeScriptTouchHandler函数调用的返回值
bool Layer::onTouchBegan(Touch *touch, Event *event)
{
#if CC_ENABLE_SCRIPT_BINDING
if (kScriptTypeNone != _scriptType)
{
return executeScriptTouchHandler(EventTouch::EventCode::BEGAN, touch, event) == 0 ? false : true;
}
#endif
CC_UNUSED_PARAM(event);
CCASSERT(false, "Layer#ccTouchBegan override me");
return true;
}
//再来看看executeScriptTouchHandler的返回值,取决于ScriptingCore::sendEvent
int Layer::executeScriptTouchHandler(EventTouch::EventCode eventType, Touch* touch, Event* event)
{
#if CC_ENABLE_SCRIPT_BINDING
if (kScriptTypeNone != _scriptType)
{
TouchScriptData data(eventType, this, touch, event);
ScriptEvent scriptEvent(kTouchEvent, &data);
return ScriptEngineManager::getInstance()->getScriptEngine()->sendEvent(&scriptEvent);
}
#endif
//can not reach it
return 0;
}
//再看sendEvent中发送触摸消息的代码
//这里可以看出layer是否捕获触摸取决于handleTouchEvent的返回值
int ScriptingCore::sendEvent(ScriptEvent* evt)
{
//......
case kTouchEvent:
{
TouchScriptData* data = (TouchScriptData*)evt->data;
return handleTouchEvent(data->nativeObject, data->actionType, data->touch, data->event);
}
break;
case kTouchesEvent:
{
TouchesScriptData* data = (TouchesScriptData*)evt->data;
return handleTouchesEvent(data->nativeObject, data->actionType, data->touches, data->event);
}
break;
//......
}
//你可以继续往下跟进去就会知道,最终返回的值到底是什么
没错!如你所见,最后的返回值是JS_CallFunctionName是否调用成功,即这里c++调用js的onTouchBegan函数是否成功
只要调用成功,touch就会被该layer捕获!跟onTouchBegan的返回值没半毛钱关系。那么正确的返回值应该是js端onTouchBegan的返回值。
解决方案:
修改ScriptingCore中handleTouchEvent/handleTouchesEvent两个接口,让它们的返回值为js端onTouchBegan的返回值:
bool ScriptingCore::handleTouchEvent(void* nativeObj, cocos2d::EventTouch::EventCode eventCode, cocos2d::Touch* touch, cocos2d::Event* event)
{
JS::RootedValue ret(_cx);
if (handleTouchEvent(nativeObj, eventCode, touch, event, &ret)){
return JS::ToBoolean(ret);
}
else {
return false;
}
}
bool ScriptingCore::handleTouchesEvent(void* nativeObj, cocos2d::EventTouch::EventCode eventCode, const std::vector<cocos2d::Touch*>& touches, cocos2d::Event* event)
{
JS::RootedValue ret(_cx);
if (handleTouchesEvent(nativeObj, eventCode, touches, event, &ret)){
return JS::ToBoolean(ret);
}
else {
return false;
}
}
其实我不太明白官方为什么在layer的触摸响应中,只用c++回调lua接口,而js使用发消息的方式(不用c++回调js接口),性能?!
2dx关于js响应layer触摸消息的bug的更多相关文章
- Glide.js:响应式 & 触摸友好的 jQuery 滑块插件
Glide.js 是一款响应式和对触摸友好的 jQuery 滑块.基于 CSS3 转换实现,并在低版本浏览器降级处理.Glide.js 简单,重量轻,快速,适用于智能手机,平板电脑和台式机.它支持 s ...
- jQuery响应式幻灯片插件jquery.glide.js(支持触摸&轻量级)
找到一款好的幻灯片插件不容易,找到一款功能全并且使用很简单的幻灯片更不容易,今天为大家分享一款全能的幻灯片插件glide.js,也是我现在在使用的一款插件. jquery.glide.js是响应和触摸 ...
- 关于js-binding中Layer触摸事件的优化
关于js-binding中Layer触摸事件的优化 cocos2d-x 3.7 1. 目前js中监听触摸事件带来的不便(特别是cocosbuilder) 在目前的js-binding中,如果要监听la ...
- ImageLightbox.js – 响应式的图片 Lightbox 插件
ImageLightbox.js 是一款很简洁的用于显示图片灯箱效果(Lightbox)的插件,没有字幕,导航按钮或默认背景.如果默认功能不够用的话,你可以很容易地自定义 JavaScript 函数扩 ...
- layer.js中layer.tips
<script src="~/Content/js/layer/layer.js"></script> layer.tips('名称不能为空', '#pro ...
- Chocolat.js – 响应式的 jQuery Lightbox 插件
Chocolat.js 使您能够显示一个或多个图像在同一页面上.给用户展示一组图片缩略图,可以显示全页或块.Chocolat.js 可以很好地处理所有主要的浏览器.它在下面这些浏览器测试通过:IE7+ ...
- Dense.js - 响应式的视网膜(Rtina)图像支持
Dense 是一款 jQuery 插件,它提供一个简单的方法为设备提供精密像素比的图像,为你的网站带来视网膜支持,清除模糊,图像更清晰.通过简单地包括 jQuery 插件的页面上,就能实现响应式的视网 ...
- duilib进阶教程 -- 响应windows原生消息和自定义消息(13)
一.windows原生消息 同样,入门教程只是给出了响应windows原生消息的方法,并没给出例子,这里以自适应屏幕分辨率为例.迅雷播放器虽然可以在启动的时候自动调整窗口大小,但是当屏幕分辨率实时改变 ...
- vue.js响应式原理解析与实现
vue.js响应式原理解析与实现 从很久之前就已经接触过了angularjs了,当时就已经了解到,angularjs是通过脏检查来实现数据监测以及页面更新渲染.之后,再接触了vue.js,当时也一度很 ...
随机推荐
- vim插件开发初步
[vim插件开发初步] 将如下代码存在helloworld.vim, 放在~/.vim/plugin目录下,插件即可生效.:w保存代码后, 用:source命令执行后,也可以使用Helloworld命 ...
- 关于缺省路由传递问题的探讨(上)[ip default-network、ip default-gateway等]
指定缺省路由(last resort gateway)的指令供有3种,可以分成两类: 1.Ip default-gateway 仅在 "no ip routing" (关闭 ...
- 在VSTO界面中,调用xll中的函数
最近研究各种有点迷茫了,原来Xll的加载宏直接可以在C#中调用的,我又各种Out了. 先说明一下,在VBA中,如何调用吧 XLLFound = Application.RegisterXLL(This ...
- 3.依赖倒置原则(Dependence Inversion Principle)
1.定义 高层模块不应该依赖于低层模块,二者都应该依赖于抽象:抽象不应该依赖细节:细节应该依赖抽象. 2.定义解读 依赖倒置原则在程序编码中经常运用,其核心思想就是面向接口编程,高层模块不应该依赖低层 ...
- 关于 TIdHttp
经验总结: 1.IdHttp 不支持多线程,只支持异步.所有网上的多线程写法下,如果同时并发多个长 GET 或 POST 请求时,会阻塞. 以下代码用于显示下载数据的进程. procedure TFo ...
- SAP实施方法与过程——ASAP
ASAP是SAP公司为使R/3项目的实施更简单.更有效的一套完整的快速实施方法.ASAP优化了在实施过程中对时间.质量和资源的有效使用等方面的控制.它是一个包括了使得项目实施得以成功所有基本要素的完整 ...
- linux C(hello world)最大公约数和最小公倍数
# include <stdio.h> int main(void) { int x, y,temp; int r; printf("请输入两个正整数:\n"); sc ...
- java list三种遍历方法性能比較
从c/c++语言转向java开发,学习java语言list遍历的三种方法,顺便測试各种遍历方法的性能,測试方法为在ArrayList中插入1千万条记录,然后遍历ArrayList,发现了一个奇怪的现象 ...
- 为您的Android,iOS等应用加入声波传输功能
记得12年左右的时候,美国出现了chirp应用,该应用能够使用声波在iphone手机间传输文本,图片.甚至视频.当时认为非常高大上. 再后来,到13年的时候国内也出现了非常多声波应用.比方支付宝的声波 ...
- iOS开发——数据持久化Swift篇&(四)CoreData
CoreData import CoreData class ViewController: UIViewController { override func viewDidLoad() { supe ...