点击索引置顶该索引城市
-
给索引列表绑定点击事件
-
在点击事件中,通过index获取到当前项索引号
-
调用List组件的 scrollToRow方法,让List组件滚动到指定行
- 在constructor中,调用React.createRef() 创建ref对象
- 将创建好的ref对象,添加为List组件的ref属性
- 通过ref的current属性,获取到组件实例,再调用组件的scrollToRow方法
-
设置List组件的scrollToAlignment配置项值为start,保证点击行出现在页面顶部
-
对于点击索引无法正确定位的问题,调用List组件的 measureAllRows 方法,提前计算高度来解决
在这里插入代码片
// 核心代码
constructor() {
...
this.listComponent = React.createRef()
}
async componentDidMount() {
await this.getCityList()
// 计算List组件高度
this.listComponent.current.measureAllRows()
}
renderCityIndex() {
return this.state.cityIndex.map((item, index) => {
return (
<li className="city-index-item" key={item} onClick={() => {
// 拿到List组件的实例
this.listComponent.current.scrollToRow(index)
}}>
...
</li>
)
})
}
render() {
return (
<div className="citylist">
...
{/* 城市列表 */}
<AutoSizer>
{
({ width, height }) => {
return <List
ref={this.listComponent}
...
/>
}
}
</AutoSizer>
...
</div>
)
}
然而我使用时this.listComponent.current.measureAllRows()没有生效,于是我选择了scrollToPosition。
state = {
cityList: {},
cityIndex: [],
// 指定右侧字母索引列表高亮的索引号
activeIndex: 0,
}
listComponent=React.createRef()
getScrollDistance (index) {
let cityArr = this.state.cityIndex.slice(0, index )
let distance= cityArr.reduce((pre, item) => {
let distance=pre+this.state.cityList[item].length*NAME_HEIGHT + TITLE_HEIGHT
return distance
},0)
return distance
}
goCity=(index) => {
// 拿到List组件的实例
if (this.state.activeIndex !== index) { this.listComponent.current.scrollToPosition(this.getScrollDistance(index)+1) }
}
renderCityIndex () {
return this.state.cityIndex.map((item, index) => {
return (
<li className="city-index-item" key={item} onClick={()=>this.goCity(index)}>
{/*判断一下,如果高亮状态的索引等于当前索引,那么就设置高亮样式*/}
<span className={this.state.activeIndex === index ? 'index-active' : ''}>{item === 'hot' ? '热' : item}</span>
</li>
)
})
}
render() {
return (
<div className="citylist">
...
{/* 城市列表 */}
<AutoSizer>
{
({ width, height }) => {
return <List
ref={this.listComponent}
...
/>
}
}
</AutoSizer>
...
</div>
)
}