You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

126 lines
3.9 KiB

import {throttle} from "../../../js/utils";
Component({
options: {
addGlobalClass: true,
pureDataPattern: /^_/
},
properties: {
list: {
type: Array,
value: [],
observer: function observer(newVal) {
var _this = this;
if (newVal.length === 0) return;
var data = this.data;
var alphabet = data.list.map(function (item) {
return item.letter;
});
alphabet.unshift("↑");
this.setData({
alphabet: alphabet,
current: alphabet[0]
}, function () {
_this.computedSize();
});
}
},
ext:{
type:Object
},
vibrated: {
type: Boolean,
value: true
}
},
data: {
current: 'A',
intoView: '',
touching: false,
alphabet: [],
_tops: [],
_anchorItemH: 0,
_anchorTop: 0
},
lifetimes: {
created: function created() {},
attached: function attached() {
this.__scrollTo = throttle(this._scrollTo, 100, {});
this.__onScroll = throttle(this._onScroll, 100, {});
}
},
methods: {
choose: function choose(e) {
5 years ago
;
var item = e.target.dataset.item;
this.triggerEvent('choose', { item: item });
},
scrollTo: function scrollTo(e) {
this.__scrollTo(e);
},
_scrollTo: function _scrollTo(e) {
var data = this.data;
var clientY = e.changedTouches[0].clientY;
5 years ago
;
var index = Math.floor((clientY - data._anchorTop) / data._anchorItemH);
if(index<0||index>=data.alphabet.length)
return;
var current = data.alphabet[index];
if(current=='↑')
this.setData({current, scrollTop:0, touching:true});
else
this.setData({ current: current, intoView: current=='#'?'hash':current, touching: true });
if (data.vibrated) wx.vibrateShort();
},
computedSize: function computedSize() {
var data = this.data;
var query = this.createSelectorQuery();
query.selectAll('.index_list_item').boundingClientRect();
query.select(".top-view").boundingClientRect();
query.select('.anchor-list').boundingClientRect(function (rect) {
data._anchorItemH = rect.height / data.alphabet.length;
data._anchorTop = rect.top;
5 years ago
;
});
query.exec(res=>{
data._tops = res[0].map(function (item) {
return item.top-res[1].top;
});
5 years ago
;
});
},
removeTouching: function removeTouching() {
var _this2 = this;
setTimeout(function () {
_this2.setData({ touching: false });
}, 150);
},
onScroll: function onScroll(e) {
this.__onScroll(e);
},
_onScroll: function _onScroll(e) {
if(this.data.touching)
return;
var data = this.data;
var _tops = data._tops,
alphabet = data.alphabet;
5 years ago
;
var pageTop = e.detail.scrollTop;
var current = '';
if (pageTop < _tops[0]) {
current = alphabet[0];
} else {
for (var i = 0, len = _tops.length; i < len - 1; i++) {
if (pageTop >= _tops[i] && pageTop < _tops[i + 1]) {
current = alphabet[i+1];
}
}
}
if (!current) current = alphabet[alphabet.length - 1];
this.setData({ current: current });
}
}
});