一、單點觸摸
關於單點觸摸事件的創建和監聽有以下幾個步驟:
1,創建一個空間如labelTTF,並且初始化,添加控件進層
2、設置一個事件監聽器,並且定義和實現他的回調函數。
3、最後讓導演將前面定義的監聽器按照監聽器和監聽事件對應的方式添加進來。
<span style="font-size:18px;"> Size visibleSize = Director::getInstance()->getVisibleSize();
Vec2 origin = Director::getInstance()->getVisibleOrigin();
auto label = LabelTTF::create("click me", "宋體", 36);
addChild(label);
label->setPosition(visibleSize.width/2, visibleSize.height/2);
auto *listener = EventListenerTouchOneByOne::create();
listener->onTouchBegan = [](Touch* t, Event* e){
log("ontouchbegan");
return false;
};
Director::getInstance()->getEventDispatcher()->addEventListenerWithSceneGraphPriority(listener, label);</span>
二、觸摸目標的判斷
在實現觸摸事件的時候,我們常常會要求只有點擊到特定的區域纔會出現相應。這就需要你再代碼 中進行判斷,你觸摸的那一點是不是在觸摸目標的範圍內。
在觸摸事件中,監聽器Lintener給label事件指定了一個觸摸後的回調函數,這個回調函數裏面有一個參數是e,類型是event,利用e->getcurrenttarget()函數就可以獲取到我們的觸摸目標,就是label,之後通過getBoundingBox()方法獲取這個觸摸目標的邊界。最後判斷一下它是否包含我們的觸摸點。
containsPoint(t->getLocation())
t->getLocation()顯示的就是獲取我們觸摸點的位置。而且,要注意的一件事就是,如果你是用labelttf來創建的label空間,那麼獲取的點的左邊很可能是錯誤的。所以用label::create();這個函數來創建。這時cocos的一個Bug把。
<span style="font-size:18px;">auto label = Label::create("click me", "宋體", 36);
addChild(label);
label->setPosition(visibleSize.width/2, visibleSize.height/2);
auto *listener = EventListenerTouchOneByOne::create();
listener->onTouchBegan = [](Touch* t, Event* e){
if(e->getCurrentTarget()->getBoundingBox().containsPoint(t->getLocation()))
{
log("ontouchbegan");
}
return false;
};</span>
三、事件傳遞
事件的傳遞機制說白了,就是你在遊戲中觸發的事件是由順序的。
一般來說事件有以下幾種
<span style="font-size:18px;"> std::function<bool(Touch*, Event*)> onTouchBegan;
std::function<void(Touch*, Event*)> onTouchMoved;
std::function<void(Touch*, Event*)> onTouchEnded;
std::function<void(Touch*, Event*)> onTouchCancelled;
</span>
從字面意思上我們基本 就能確定這些個 事件能夠做什麼。但是仔細 觀察可以發現,幾個事件的函數只有一個比較特殊就是onTouchBegan。它要求返回值是Bool類型。也就是說,所以的事件,Ontouchbegan這個事件應該先執行,因爲你一定要先按下你的鼠標,纔去執行拖動,彈起,取消等動作,假如我現在有以下代碼:
<span style="font-size:18px;"> listener->onTouchBegan = [](Touch* t, Event* e){
if(e->getCurrentTarget()->getBoundingBox().containsPoint(t->getLocation()))
{
log("ontouchbegan");
}
return false;
};
listener->onTouchMoved = [](Touch *t, Event* e)
{
log("ontouchmoved");
};</span>
如果onTouchBegan在函數中返回值是false,那麼它將不會觸發以後所設定的事件,但是如果設定爲true,就表明可以繼續除法之後的事件。
四、監聽物理按鍵事件
手機上面的每一個物理按鍵和電腦上面的一樣都是有一個整數值代表他們。
首先就是創建一個專門用來監聽物理按鍵事件的監聽器:
auto listener = EventListenerKeyboard::create();
然後通過指定onKeyReleased函數,並且將創建的監聽器加入到導演的管理。在真機上調試的時候就可以看到,每次按一個鍵,相應的鍵的數值都會顯現出來。
auto listener = EventListenerKeyboard::create();
listener->onKeyReleased = [](EventKeyboard::KeyCode code, Event* e){
log("key code %d", code); //顯示按鍵數值
switch(code)
{
case EventKeyboard::KeyCode::KEY_ESCAPE: //通過switch語句讓不同的按鍵執行不同的 動作
Director::getInstance()->end();
break;
default:
break;
}
};
Director::getInstance()->getEventDispatcher()->addEventListenerWithSceneGraphPriority(listener, this);