前言:有的时候,我们需要一个既能翻页又能上下滑动、列表里的item还可以点击的界面,这时候就会遇到能滚动列表和滑动翻页的矛盾,以下为简单的处理方法。
一、在pageView里面的页面里面添加ScrollView:
为了方便区分,图中白色的背景是pageView的,说粉不粉说红又不红的颜色,是翻页容器page_1的背景色,蓝色的是ScrollView的背景色,列表里面的item的背景色为白色(下边会看到)。
二、item
加了label是为了方便区分,同时为item添加button组件(我们要用代码添加事件)。
三、脚本里面添加属性如下:
properties: {
//测试item
item_test: {
default: null,
type: cc.Prefab
},
//列表
test_scrollView: {
default: null,
type: cc.ScrollView
},
//翻页容器
test_pageView: {
default: null,
type: cc.PageView
}
},
然后给列表里面加item
for (let i = 0; i < 10; i++) {
let item_test = cc.instantiate(this.item_test);
item_test.parent = this.content;
}
四、给列表ScrollView的content添加layout组件,选择竖向滚动,元素之间的间隔是为了方便区分。
运行一下,如图:
五、注册触摸事件
里面的50,是判断点击和滑动的界限,可以自己修改。
addTouchEvent(node_1) {
node_1.on(cc.Node.EventType.TOUCH_START, this.touchStart, this);
node_1.on(cc.Node.EventType.TOUCH_MOVE, this.touchMove, this);
node_1.on(cc.Node.EventType.TOUCH_END, this.touchEnd, this);
},
touchStart(event) {
this.chuandi = true; //chuandi:是否可以传递,默认为true;
console.log("开始", event.getLocation());
this.startPosition = event.getLocation();
this.pageIdx = this.getPageViewPageIndex();
},
touchMove(event) {
if (this.chuandi == false) {
return;
}
this.chuandi = true;
console.log("移动 = ", event.getLocation());
this.movePosition = event.getLocation();
let distance_x = this.movePosition.x - this.startPosition.x;
let distance_y = this.movePosition.y - this.startPosition.y;
console.log("距离差== ", distance_x, distance_y);
//判断是否需要翻页
if (Math.abs(distance_x) > 50 && distance_x > 0) {
console.log("向前翻页", this.node, event.target);
this.onShowPageViewIndex(this.pageIdx - 1);
this.chuandi = false;
} else if (Math.abs(distance_x) > 50 && distance_x < 0) {
console.log("向后翻页");
this.onShowPageViewIndex(this.pageIdx + 1);
this.chuandi = false;
}
console.log("是否能传递 == ", this.chuandi);
},
touchEnd(event) {
this.endPosition = event.getLocation();
let distance_x = this.endPosition.x - this.startPosition.x;
let distance_y = this.endPosition.y - this.startPosition.y;
//判断是否是点击
if (Math.abs(distance_y) < 50 && Math.abs(distance_x) < 50) {
console.log("触摸结束,是点击");
} else {
console.log("结束1");
}
},
获取当前翻页容器的页码。
getPageViewPageIndex() {
let pageIndex = this.test_pageView.getCurrentPageIndex();
console.log("当前翻页容器的页码 == ", pageIndex);
return pageIndex;
},
设置翻页容器当前滚动到某页。
onShowPageViewIndex(index) {
this.test_pageView.scrollToPage(index);
}
然后个item添加触摸事件,就是在上面添加item的时候调用addTouchEvent方法。
for (let i = 0; i < 10; i++) {
let item_test = cc.instantiate(this.item_test);
item_test.parent = this.content;
this.addTouchEvent(item_test); //添加触摸事件
}
原理就是给item加上触摸事件之后,一旦x轴滑动超过界限判定,我们就手动给翻页,x不超界限、y轴滑动超过界限我们则认为是滑动,x和y轴均未超界限,我们就认为是点击。
效果图如下(有点卡卡的gif):
因为这是用了监听处理的,下篇文章讲述了怎么改写引擎源码来实现该功能,点此传送
如有不足,请多多指教。
如有转载请注明出处,谢谢。