其实也不能说仿微信,大部分通讯录都一样,先来看两张效果图
第一张是微信、第二张是我写的
简单介绍一下功能点
1、好友排序
2、点击右侧快捷操作区,相应跳转到所属通讯录区域
3、ScrollView 在滑动过程中自动匹配右侧字母分类,同时作出UI更新
详细讲讲
好友信息数据结构
let typeList = [
{ nickname: '曾泰', picture: '', letter: 'Z' },
{ nickname: '狄仁杰', picture: '', letter: 'D' },
{ nickname: '李元芳', picture: '', letter: 'L' },
......
]
右侧操作栏数据结构
let addressAllList = [
{ title: 'A', number: 0, scrollHeight: 0 },
{ title: 'B', number: 0, scrollHeight: 0 },
{ title: 'C', number: 0, scrollHeight: 0 },
{ title: 'D', number: 0, scrollHeight: 0 },
{ title: 'E', number: 0, scrollHeight: 0 },
{ title: 'F', number: 0, scrollHeight: 0 },
......
】
1、好友排序
这个是基本操作,没什么可说的,为了功能的完整性,纯当做记录吧
/** 对列表信息进行排序 放在saga中进行处理 */
sortFriend () {
this.friendListSource = typeList.sort((a, b) => { return a.letter.localeCompare(b.letter) })
}
2、点击右侧快捷操作区,相应跳转到所属通讯录区域
原理是这样的,通过计算获得,每个字母区间所包含的好友个数,相应的就能得到该字幕区间的高度Height值,如果有了ScrollView的y值和每一行的高度值,那么我们就能精确的算出点击每个字母我们需要跳转到的绝对位置,嗯
但前提是,我们需要精确的得到这两个值
componentDidMount () {
/** 获取列表组件高度 */
const that = this
setTimeout(function () {
that.refs.friendArea.measure((x, y, width, height, left, top) => {
console.log('好友列表从高度' + y + '开始渲染***************')
that.setState({ y })
})
that.refs.friendItem.measure((x, y, width, height, left, top) => {
console.log('列表Item高度为' + height + '***************')
that.rowHeight = height
that.setState({ rowHeight: height })
})
})
}
接下来,我们就开始定量计算了
/** 右侧通讯录 */
sortAddress () {
/**
* 计算每层个数
*/
let tempList = addressAllList
typeList.map((item) => {
addressAllList.map((element, index) => {
if (element.title === item.letter) {
let { number } = tempList[index]
// console.log('出现一个相同项' + item.letter)
tempList.splice(index, 1, { ...tempList[index], number: number + 1 })
}
})
})
/**
* 计算每层y
*/
tempList.map((item, index) => {
let change = {}
if (index === 0) {
change = { ...item, scrollHeight: this.state.y }
} else {
const { scrollHeight, number } = this.addressListSource[index - 1]
change = { ...item, scrollHeight: scrollHeight + number * this.state.rowHeight }
}
this.addressListSource.push(change)
})
// console.log(this.addressListSource)
this.setState({ addressList: this.addressListSource })
}
界面操作呢????
this.refs.scroll.scrollTo({ y: scrollHeight, animated: true })} 就好了
<View style={
{ position: 'absolute', top: y, right: px2dp(6) }}>
{ addressList.map((item, index) => {
const { title, number, scrollHeight } = item
return (number !== 0 &&
<TouchableWithoutFeedback onPress={() => this.refs.scroll.scrollTo({ y: scrollHeight, animated: true })} key