现象描述
地图页面操作手势卡顿或者不生效。
可能原因
手势遮盖或者手势冲突。
主线程阻塞。
应用主线程处理大批量逻辑时,存在主线程阻塞,此时进行地图手势操作,手势应答会变慢甚至手势响应失败。
处理步骤
手势遮盖或者手势冲突。
import { AsyncCallback, BusinessError } from '@kit.BasicServicesKit';
import { map, mapCommon, MapComponent } from '@kit.MapKit';
class MyDataSource implements IDataSource {
private list: number[] = [];
constructor(list: number[]) {
this.list = list;
}
// 获取数组长度
totalCount(): number {
return this.list.length;
}
// 根据索引获取数据
getData(index: number): number {
return this.list[index];
}
// 注册数据变化监听器
registerDataChangeListener(listener: DataChangeListener): void {
}
// 取消注册数据变化监听器
unregisterDataChangeListener(listener: DataChangeListener): void {
}
}
@Entry
@Component
struct SwiperExample {
private swiperController: SwiperController = new SwiperController();
private data: MyDataSource = new MyDataSource([]);
private mapOptions?: mapCommon.MapOptions;
private callback?: AsyncCallback<map.MapComponentController>;
private mapController?: map.MapComponentController;
private mapEventManager?: map.MapEventManager;
@State mapPositionX: number = 0;
@State mapPositionY: number = 0;
@State mapHeight: number = 0;
@State mapWidth: number = 0;
@State index: number = 0;
// 判断坐标是否在地图矩形内
isMap(event: TouchEvent) {
if (event.changedTouches[0].displayX > this.mapPositionX
&& event.changedTouches[0].displayX < this.mapPositionX + this.mapWidth
&& event.changedTouches[0].displayY > this.mapPositionY
&& event.changedTouches[0].displayY < this.mapPositionY + this.mapHeight) {
return true;
}
return false;
}
aboutToAppear(): void {
let list: number[] = [];
for (let i = 1; i <= 10; i++) {
list.push(i);
}
this.data = new MyDataSource(list);
this.mapOptions = {
position: {
target: {
latitude: 31.98441025,
longitude: 118.766253
},
zoom: 10,
tilt: 10,
bearing: 90
},
scaleControlsEnabled: true
}
this.callback = async (err, mapController) => {
if (!err) {
this.mapController = mapController;
this.mapEventManager = this.mapController.getEventManager();
let callback = () => {
console.info(`on-mapLoad`);
};
this.mapEventManager.on("mapLoad", callback);
} else {
console.error(`Failed to initialize the map, code is:${err.code}, message is ${err.message}`);
}
}
}
build() {
Column({ space: 5 }) {
Swiper(this.swiperController) {
LazyForEach(this.data, (item: string) => {
if (item == "3") {
Column() {
Text(item.toString())
.width('90%')
.height(160)
.backgroundColor(0xAFEEEE)
.textAlign(TextAlign.Center)
.fontSize(30)
MapComponent({ mapOptions: this.mapOptions, mapCallback: this.callback })
// 获取MapComponent的位置和长宽
.width('100%')
.height('65%')
.onAreaChange((_oldValue: Area, newValue: Area) => {
try {
if (newValue.globalPosition.x !== undefined && newValue.globalPosition.y !== undefined) {
this.mapPositionX = Number(newValue.globalPosition.x);
this.mapPositionY = Number(newValue.globalPosition.y);
this.mapHeight = Number(newValue.height);
this.mapWidth = Number(newValue.width);
}
} catch (error) {
let e: BusinessError = error as BusinessError;
console.error("onAreaChange error code:" + e.code + "message:" + e.message);
}
})
}.height("100%")
} else {
Text(item.toString())
.width('90%')
.height(160)
.backgroundColor(0xAFEEEE)
.textAlign(TextAlign.Center)
.fontSize(30)
}
}, (item: string) => item)
}
// 手势判断 当index为存在地图页面且点击在地图矩形内时为HitTestMode.None(不响应Swiper手势,响应子组件手势)
.onTouchIntercept((event: TouchEvent) => {
if (this.index === 2 && this.isMap(event)) {
return HitTestMode.None;
}
return HitTestMode.Transparent;
})
.cachedCount(2)
.index(1)
.loop(true)
.itemSpace(0)
// 设置圆点导航点样式
.indicator(
new DotIndicator()
.itemWidth(15)
.itemHeight(15)
.selectedItemWidth(15)
.selectedItemHeight(15)
.color(Color.Gray)
.selectedColor(Color.Blue))
.displayArrow({
// 设置导航点箭头样式
showBackground: true,
isSidebarMiddle: true,
backgroundSize: 24,
backgroundColor: Color.White,
arrowSize: 18,
arrowColor: Color.Blue
}, false)
.curve(Curve.Linear)
.onChange((index: number) => {
this.index = index;
})
.onGestureSwipe((index: number, extraInfo: SwiperAnimationEvent) => {
console.info("index: " + index);
console.info("current offset: " + extraInfo.currentOffset);
})
Row({ space: 12 }) {
Button('showNext')
.onClick(() => {
this.swiperController.showNext();
})
Button('showPrevious')
.onClick(() => {
this.swiperController.showPrevious();
})
}.margin(5)
}.width('100%')
.margin({ top: 5 })
}
} 主线程阻塞。
请分析应用的业务逻辑,将复杂逻辑放到子线程中处理。