Почему происходит событие касания, даже если я касаюсь вне спрайта?
У меня есть пользовательский интерфейс::ScrollView, содержащий ряд спрайтов.
Я создал каждый спрайт и добавил сенсорный слушатель к каждому спрайту, выполнив что-то вроде:
for(int i=0; i < 5; i++){
Sprite* foo = Sprite::createWithSpriteFrameName("foo");
myScrollView->addChild(foo);
auto listener = EventListenerTouchOneByOne::create();
listener->onTouchBegan = [this,somestring](Touch* touch, Event* event){
......some code
};
listener->onTouchMoved = [foo,this,somestring](Touch* touch, Event* event){
......some code
};
listener->onTouchEnded = [foo,this,somestring](Touch* touch, Event* event){
......some code
};
foo->getEventDispatcher->addEventListenerWithSceneGraphPriority(listener1,foo);
}
Проблема в том, что, если я щелкну ЛЮБОЕ на экране, кажется, что он вызывает события касания ВСЕХ спрайтов, созданных в цикле. Есть ли что-то неправильное в том, как я создаю слушателя, или это связано с каким-то конфликтом с касаниями в ui::ScrollView?
Я использую v 3.10
2 ответа
Потому что так работает TouchListener в cocos2d-x. Все слушатели касания будут вызваны, если кто-то не проглотил событие касания. Ваш код будет:
auto touchSwallower = EventListenerTouchOneByOne::create();
touchSwallower ->setSwallowed(true);
touchSwallower->onTouchBegan = [](){ return true;};
getEventDispatcher->addEventListenerWithSceneGraphPriority(touchSwallower ,scrollview);
for(int i=0; i < 5; i++){
Sprite* foo = Sprite::createWithSpriteFrameName("foo");
myScrollView->addChild(foo);
auto listener = EventListenerTouchOneByOne::create();
listener->setSwallowed(true);
listener->onTouchBegan = [this,somestring](Touch* touch, Event* event){
......some code
Vec2 touchPos = myScrollView->convertTouchToNodeSpace(touch);
return foo->getBoundingBox()->containsPoint(touchPos);
};
listener->onTouchMoved = [foo,this,somestring](Touch* touch, Event* event){
......some code
};
listener->onTouchEnded = [foo,this,somestring](Touch* touch, Event* event){
......some code
};
foo->getEventDispatcher->addEventListenerWithSceneGraphPriority(listener1,foo);
}
cocos2dx отправит событие касания каждому узлу, прикрепленному событию касания, если кто-то не проглотит его.
Но если вы хотите, чтобы "узел" по умолчанию определял, является ли сенсорное расположение в контенте, попробуйте использовать "UIWidget" с "addTouchEventListener". Он рассчитает сам.
bool Widget::onTouchBegan(Touch *touch, Event *unusedEvent)
{
_hitted = false;
if (isVisible() && isEnabled() && isAncestorsEnabled() && isAncestorsVisible(this) )
{
_touchBeganPosition = touch->getLocation();
auto camera = Camera::getVisitingCamera();
if(hitTest(_touchBeganPosition, camera, nullptr))
{
if (isClippingParentContainsPoint(_touchBeganPosition)) {
_hittedByCamera = camera;
_hitted = true;
}
}
}
if (!_hitted)
{
return false;
}
setHighlighted(true);
/*
* Propagate touch events to its parents
*/
if (_propagateTouchEvents)
{
this->propagateTouchEvent(TouchEventType::BEGAN, this, touch);
}
pushDownEvent();
return true;
}