温馨提示×

温馨提示×

您好,登录后才能下订单哦!

密码登录×
登录注册×
其他方式登录
点击 登录注册 即表示同意《亿速云用户服务条款》

小程序如何实现带索引的城市列表

发布时间:2022-07-18 09:22:50 来源:亿速云 阅读:148 作者:iii 栏目:开发技术

今天小编给大家分享一下小程序如何实现带索引的城市列表的相关知识点,内容详细,逻辑清晰,相信大部分人都还太了解这方面的知识,所以分享这篇文章给大家参考一下,希望大家阅读完这篇文章后有所收获,下面我们一起来了解一下吧。

效果

小程序如何实现带索引的城市列表

代码实现

因为我的城市数据没有而项目里先有的是省市区代码数据所以要先处理一下数据
用来获取首字母:

//用来获取首字母
import py from '../../utils/strChineseFirstPY'
checkCh(ch) {
      let uni = ch.charCodeAt(0);
      //如果不在汉字处理范围之内,返回原字符,也可以调用自己的处理函数
      if (uni > 40869 || uni < 19968) {
        return ch;
      } //dealWithOthers(ch);
      //检查是否是多音字,是按多音字处理,不是就直接在strChineseFirstPY字符串中找对应的首字母
      return (py.oMultiDiff[uni] ? py.oMultiDiff[uni] : (py.strChineseFirstPY.charAt(uni - 19968)));
    }

利用首字母讲城市数据整理:

//用来获取首字母
/**
     * @name: 
     * @test: test font
     * @msg: 
     * @param {*} data 数组
     * @param {*} field 依据那个字段排序
     * @return {*}
     */
    data_letter_sort (data, field) {
      let list = new Array();
      let letter = ''
      for (let i = 0; i < data.length; i++) {
        // 首字母 转 大写英文
        letter = (data[i][field]).substr(0, 1).toUpperCase();
        // 创建 字母 分组
        if (!(letter in list)) {
          list[letter] = new Array();
        }
        // 字母 分组 添加 数据
        list[letter].push(data[i]);
      }
       // 转换 格式 进行 排序;
      let resault = new Array();
      for (let key in list) {
        resault.push({
          letter: key,
          list: list[key]
        });
      }
      resault.sort(function (x, y) {
        return x.letter.charCodeAt(0) - y.letter.charCodeAt(0);
      });
      // 转换 数据 格式
      let json_sort = {}
      for (let i = 0; i < resault.length; i++) {
        json_sort[resault[i].letter] = resault[i].list;
      }
      return json_sort;
    },

处理过后的数据为按首字母排序的一个对象

小程序如何实现带索引的城市列表

然后难点就在右边的索引怎么按照左边的区域来进行高亮显示
首先我想的是获取每个字母距离上边的高度然后页面滑动时进行高度判断

//获取城市数据的首字母列表
for (let key in this.cityList) {
      let obj = {
        py: key,
        active: false
      }
      if (obj.py == 'A') {
        obj.active = true
      }
      wx.createSelectorQuery().select('#'+ key).boundingClientRect(function(rect){
        obj.top = rect.top     // 节点的上边界坐标
      }).exec()
      //pylist是用来渲染右边索引列表的
      this.pyList.push(obj);
    }
//滑动时间
scroll(e) {
      let scrollTop = e.target.scrollTop
      this.pyList.map(item => {
        if ((scrollTop - item.top)>-76) {
          this.pyList.map(item => {
          //active是用来是否高亮显示
            item.active = false
          })
          item.active = true
          return
        }
      })
    },

整体代码

<!--
 * @Descripttion: 
 * @version: 
 * @Author: Songtutu
 * @Date: 2021-04-06 10:30:36
 * @LastEditors: Songtutu
 * @LastEditTime: 2021-04-08 13:40:32
-->
<template>
  <div class="main">
    <div class="search">
        <div class="search-box">
          <img :src="imglist.map_search"/>
          <input placeholder="请输入城市名称" @focus="focus" :focus="true" v-model="search" type="digit" -splaceholdertyle="font-size:14px;color: rgba(0, 0, 0, 0.3);" confirm-type="search" @confirm='doSearch'/>
        </div>
      </div>
    <!-- 城市列表 -->
    <scroll-view scroll-y="true" scroll-with-animation="true" enable-back-to-top="true" class="city-list" @scroll="scroll" :scroll-top="scrollTop" v-show="searchList.length == 0">
      
      <div class="dw-box">
        <div>定位城市:{{city}}</div>
        <img :src="imglist.map_sx" @click="sx()"/>
      </div>
      <div :id='key' class="city-group" v-for="(value, key, index) in cityList" :key="index">
        <div  class="city-group-title">{{key}}</div>
        <div class="city-item" :id="i == value.length -1?key:''" v-for="(item, i) in value" :key="i">
          {{item.cityName}}
        </div>
      </div>
    </scroll-view>
    <div class="search-list" v-show="searchList.length != 0">
      <div class="city-item" v-for="(item, i) in searchList" :key="i">
        {{item.cityName}}
      </div>
    </div>
    <div class="py-box" v-show="searchList.length == 0">
      <div class="py-item" :class="item.active?'active':''" v-for="(item, index) in pyList" :key="index" @click="clickPy(item, index)">{{item.py}}</div>
    </div>
  </div>
</template>
<script>
import py from '../../utils/strChineseFirstPY'
import area from '../../utils/area1'
export default {
  data() {
    return {
      cityList: [],
      imglist: [],
      search:'',
      city: '',
      pyList: [],
      scrollTop: 0,
      searchList: []
    }
  },
  created() {
    let title = "选择城市"
    let frontColor = "#000000"
    let backgroundColor = "#ffffff"
    wx.setNavigationBarTitle({
      title
    })
    wx.setNavigationBarColor({
      frontColor, //前景颜色值,包括按钮、标题、状态栏的颜色,仅支持 #ffffff 和 #000000,
      backgroundColor
    });
    const imgurl = "图片根目录"
    this.imglist = {
      map_search: `${imgurl}map_search.png`,
      map_sx: `${imgurl}map_sx.png`
    }
    area.region.map(item => {
      item.mallCityList.map(i => {
        this.cityList.push(i)
      })
    })
    this.cityList.map(item => {
      item.py = this.checkCh(item.cityName.charAt(0))
    })
    this.cityList = this.data_letter_sort(this.cityList, 'py')
    console.log(this.cityList)
  },
  mounted() {
    for (let key in this.cityList) {
      let obj = {
        py: key,
        active: false
      }
      if (obj.py == 'A') {
        obj.active = true
      }
      wx.createSelectorQuery().select('#'+ key).boundingClientRect(function(rect){
        obj.top = rect.top     // 节点的上边界坐标
      }).exec()
      this.pyList.push(obj);
    }
  },
  methods: {
    focus() {
      if (!this.search) {
        this.searchList = []
      }
    },
    doSearch() {
      this.searchList = []
      for(let key in this.cityList) {
        this.cityList[key].map(item => {
          if (item.cityName.indexOf(this.search) != -1) {
            this.searchList.push(item)
          }
        })
      }
    },
    clickPy(item) {
      this.scrollTop = item.top - 44
    },
    scroll(e) {
      let scrollTop = e.target.scrollTop
      this.pyList.map(item => {
        if ((scrollTop - item.top)>-76) {
          this.pyList.map(item => {
            item.active = false
          })
          item.active = true
          return
        }
      })
    },
    sx() {
      this.getLocation()
    },
    /**
     * 定位授权
     */
    getLocation() {
      const that = this;
      //调用自带位置获取
      wx.getSetting({
        success(res) {
          if (!res.authSetting["scope.userLocation"]) {
            wx.authorize({
              scope: "scope.userLocation",
              success() {
                that.localDetail();
              },
              fail() {
                wx.showModal({
                  title: "提示",
                  content: "获取当前位置需要授权哦~",
                  success(res) {
                    if (res.confirm) {
                      wx.openSetting({
                        success: res => {
                          if (res.authSetting["scope.userLocation"]) {
                            that.localDetail();
                          }
                        }
                      });
                    } else if (res.cancel) {
                    }
                  }
                });
              }
            });
          } else {
            that.localDetail();
          }
        }
      });
    },
    localDetail() {
      wx.getLocation({
        type: "gcj02", //返回可以用于wx.openLocation的经纬度
        success: function(res) {
          console.log(res)
        }
      });
    },
    /**
     * @name: 
     * @test: test font
     * @msg: 
     * @param {*} data 数组
     * @param {*} field 依据那个字段排序
     * @return {*}
     */
    data_letter_sort (data, field) {
      let list = new Array();
      let letter = ''
      for (let i = 0; i < data.length; i++) {
        // 首字母 转 大写英文
        letter = (data[i][field]).substr(0, 1).toUpperCase();
        // 创建 字母 分组
        if (!(letter in list)) {
          list[letter] = new Array();
        }
        // 字母 分组 添加 数据
        list[letter].push(data[i]);
      }
       // 转换 格式 进行 排序;
      let resault = new Array();
      for (let key in list) {
        resault.push({
          letter: key,
          list: list[key]
        });
      }
      resault.sort(function (x, y) {
        return x.letter.charCodeAt(0) - y.letter.charCodeAt(0);
      });
      // 转换 数据 格式
      let json_sort = {}
      for (let i = 0; i < resault.length; i++) {
        json_sort[resault[i].letter] = resault[i].list;
      }
      return json_sort;
    },
    checkCh(ch) {
      let uni = ch.charCodeAt(0);
      //如果不在汉字处理范围之内,返回原字符,也可以调用自己的处理函数
      if (uni > 40869 || uni < 19968) {
        return ch;
      } //dealWithOthers(ch);
      //检查是否是多音字,是按多音字处理,不是就直接在strChineseFirstPY字符串中找对应的首字母
      return (py.oMultiDiff[uni] ? py.oMultiDiff[uni] : (py.strChineseFirstPY.charAt(uni - 19968)));
    }
  }
}
</script>
<style scoped>
.search-list {
  margin-top: 68rpx;
  background: white;
  width: 100%;
  height: auto;
}
.active {
  width: 16px;
  height: 16px;
  background: #005F28;
  line-height: 16px;
  border-radius: 50%;
  color: white;
  text-align: center;
}
.py-box {
  width: 16px;
  text-align: center;
  height: auto;
  position: fixed;
  top: 142px;
  font-weight: 400;
  color: rgba(0, 0, 0, 0.4);
  font-size: 14px;
  right:9px;
}
.search {
  position: fixed;
  top: 0;
  left: 0;
  width: 100%;
  z-index: 99;
  background: white;
  padding-bottom: 8px;
}
.city-item {
  margin: 0 32px 0px 16px;
  height: 40px;
  line-height: 40px;
  font-size: 14px;
  font-weight: 400;
  color: rgba(0, 0, 0, 0.9);
  border-bottom: 1px solid rgba(0, 0, 0, 0.1);
}
.city-list {
  background: white;
  height: 100vh;
  position: relative;
}
.city-list .city-group-title {
  position: sticky;
  top: 33px;
  width: 100%;
  font-size: 14px;
  font-weight: 400;
  color: rgba(0, 0, 0, 0.4);
  padding: 0px 16px;
  height: 32px;
  line-height: 32px;
  background: #F5F5F5;
  box-sizing: border-box;
}
.main{
  min-height: 100vh;
  background: #F5F5F5;;
  padding-top: 6px;
}
.search-box {
  margin-top: 6px;
  margin: 0 auto;
  width: 343px;
  display: flex;
  height: auto;
  padding: 6px 8px;
  background: rgba(0, 0, 0, 0.05);
  border-radius: 4px;
}
.search-box img {
  width: 16px;
  height: 16px;
  margin-top: 2px;
  margin-right: 4px;
}
.search-box input {
  height: 20px;
  font-size: 14px;
  font-weight: 400;
  color: rgba(0, 0, 0, 0.9);
  line-height: 20px;
}
.dw-box {
  margin-top: 32px;
  height: 44px;
  display: flex;
  line-height: 44px;
  padding: 0 16px;
  font-size: 14px;
  font-weight: 400;
  color: #005F28;

}
.dw-box div {
  flex: 1;
  text-align: left;
}
.dw-box img {
  margin-top: 14px;
  width: 16px;
  height: 16px;
}
</style>

以上就是“小程序如何实现带索引的城市列表”这篇文章的所有内容,感谢各位的阅读!相信大家阅读完这篇文章都有很大的收获,小编每天都会为大家更新不同的知识,如果还想学习更多的知识,请关注亿速云行业资讯频道。

向AI问一下细节

免责声明:本站发布的内容(图片、视频和文字)以原创、转载和分享为主,文章观点不代表本网站立场,如果涉及侵权请联系站长邮箱:is@yisu.com进行举报,并提供相关证据,一经查实,将立刻删除涉嫌侵权内容。

AI