cocos2d事件监听机制

下面就以我们常用的单点触摸监听来讲一下事件监听机制原理:

实现触摸监听代码如下:

 

	local listener = cc.EventListenerTouchOneByOne:create()
	local function onTouchBegan(touch, event)
		return true
	end
	local function onTouchMoved(touch,event)
	end
	local function onTouchEnded(touch,event)
	end
	listener:registerScriptHandler(onTouchBegan,cc.Handler.EVENT_TOUCH_BEGAN)
	listener:registerScriptHandler(onTouchMoved,cc.Handler.EVENT_TOUCH_MOVED)
	listener:registerScriptHandler(onTouchEnded,cc.Handler.EVENT_TOUCH_ENDED)
	listener:setSwallowTouches(true)
	local eventDispatcher = self:getEventDispatcher()
	eventDispatcher:addEventListenerWithSceneGraphPriority(listener, self)

只要实现以上代码,在触摸屏幕的时候,onTouchBegan、onTouchMoved、onTouchEnded这几个方法就能被回调,那么具体的原理是什么呢?下面来看一下。

 

1、绑定listener和node

整个程序只有一个EventDispatcher,保存在Director里。通过eventDispatcher:addEventListenerWithSceneGraphPriority(listener, self),listener和被监听的节点(node)会被关联保存在一个Map【std::unordered_map<Node*, std::vector<EventListener*>*> _nodeListenersMap】,node和listener是一对多的关系。

void EventDispatcher::addEventListenerWithSceneGraphPriority(EventListener* listener, Node* node)
{
    CCASSERT(listener && node, "Invalid parameters.");
    CCASSERT(!listener->isRegistered(), "The listener has been registered.");
    
    if (!listener->checkAvailable())
        return;
    
    listener->setAssociatedNode(node);
    listener->setFixedPriority(0);
    listener->setRegistered(true);
    
    addEventListener(listener);
}

注意:

每个监听器(Listener)和节点绑定后都会有个被注册标记,同一个监听器不能多次注册;

上面代码的最后一句将监听器都被保存在一个Map容器里面,以监听器ID为key, 该类型的所有监听器为value。结构如下:

{

"__cc_touch_all_at_once"  = {ListenerA, ListenerB},

"__cc_keyboard"  = {ListenerC, ListenerD}

};

 

2、分发事件

当产生触摸事件时,系统调用void EventDispatcher::dispatchEvent(Event* event),根据事件类型调用void EventDispatcher::dispatchTouchEvent(EventTouch* event)分发触摸事件

void EventDispatcher::dispatchEvent(Event* event)
{
    if (!_isEnabled)
        return;
    
    updateDirtyFlagForSceneGraph();
    
    
    DispatchGuard guard(_inDispatch);
    
    if (event->getType() == Event::Type::TOUCH)
    {
        dispatchTouchEvent(static_cast<EventTouch*>(event));
        return;
    }
    // ---------省略以下内容----
    
}

 

3、回调函数

最后查找所有的触摸监听器,回调所有符合要求的监听器dispatchEventToListeners

 

 

 

 

 

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值