手机版

今日头条AppTopbar在微信小程序中的实现

时间:2021-12-16 来源:互联网 编辑:宝哥软件园 浏览:

作者;剪影男孩,授权地址的Topbar今天的头条App是一个典型的渠道管理和切换组件。前段时间研究过,在微信小程序上也取得了类似的效果。

先看具体效果。

微信小程序中实现仿今日头条AppTopbar(图1)

微信小程序中实现仿今日头条AppTopbar(图2)

微信小程序中实现仿今日头条AppTopbar(图3)

这个项目(wx-topbar)已经放在GitHub上——点了。欢迎学习交流。

接下来,简单说说实现思路。

先看视图层,Topbar水平滚动对应的WXML代码如下:

scroll-view class=' nav bar ' scroll-x=' true ' scroll-left=' { { scrollNavbarLeft } } ' view class=' nav bar-item { { nav bararray[item]}。type } } ' id=' { { item } } ' wx : for=' { { navBarshowindexarray } } ' catch tap=' onTapNavbar ' view class=' navbar-item-wrap ' { navBararray[item]。text } }/View/View class=' nav bar-项目可见性-隐藏' View class=' nav bar-项目-环绕' blank/View/scroll-View class=' nav bar-箭头-向下' catch tap=' showchannelsettingtomid ' View class=' nav bar-箭头-向下-环绕' image class=' nav bar-箭头-图标' src='/Images/index/icon _ arrow _ down . png '/image/View/View scroll-View负责Topbar中每个通道的呈现,而

不难猜测通道是否高亮显示,这与阵列navbarArray有关;频道是否显示与数组navbarShowIndexArray有关。

点击频道名称将触发相应频道的切换操作。

view . nav bar-向下箭头对应右上角的向下箭头。可以使用固定定位类型。点击弹出管理渠道模式。

view class=' channel-setting-modal { { channel setting modal show } } ' hidden=' { { channel setting modal hide } } ' view class=' channel-show-text ' view class=' channel-show-text-wrap ' display channel/view/view class

s="channel-item" wx:for="{{ navbarShowIndexArray }}"> <view class="channel-item-wrap"> <view class="channel-item-left"> <image class="channel-item-icon-minus {{ !index || navbarShowIndexArray.length < 4 ? 'visibility-hidden' : '' }}" id="{{ item }}.0" src="/images/index/icon_minus.png" catchtap="hideChannel"></image> <view class="channel-item-text">{{ navbarArray[item].text }}</view> </view> <view class="channel-item-up {{ index < 2 ? 'visibility-hidden' : '' }}" id="{{ item }}.00" catchtap="upChannel">上移</view> </view> </view> <view class="channel-hide-text"> <view class="channel-hide-text-wrap">隐藏频道</view> </view> <view class="channel-item" wx:for="{{ navbarHideIndexArray }}"> <view class="channel-item-wrap"> <view class="channel-item-left"> <image class="channel-item-icon-plus" id="{{ item }}.0" src="/images/index/icon_plus.png" catchtap="showChannel"></image> <view class="channel-item-text">{{ navbarArray[item].text }}</view> </view> <view class="channel-item-up visibility-hidden">上移</view> </view> </view></view>

在这个管理频道的Modal里,通过改变数组navbarShowIndexArray来控制频道是否显示和显示顺序,同时,需要另外一个数组navbarHideIndexArray来存储隐藏的频道。

Modal显示的时候,Topbar需要被另一个写有“频道设置”字样的Bar覆盖。

<view class="channel-setting {{ channelSettingShow }}">    <view class="channel-setting-text">频道设置</view>    <view class="navbar-arrow-up" catchtap="hideChannelSettingModal">        <image class="navbar-arrow-icon navbar-arrow-icon-up" src="/images/index/icon_arrow_up.png"></image>    </view></view>

然后,我们来看逻辑层的实现。初始化的部分data如下:

data: {    navbarArray: [{        text: '推荐',        type: 'navbar-item-active'    }, {        text: '热点',        type: ''    }, {        text: '视频',        type: ''    }, {        text: '图片',        type: ''    }, {        text: '段子',        type: ''    }, {        text: '社会',        type: ''    }, {        text: '娱乐',        type: ''    }, {        text: '科技',        type: ''    }, {        text: '体育',        type: ''    }, {        text: '汽车',        type: ''    }, {        text: '财经',        type: ''    }, {        text: '搞笑',        type: ''    }],    navbarShowIndexArray: Array.from(Array(12).keys()),    navbarHideIndexArray: [],    channelSettingShow: '',    channelSettingModalShow: '',    channelSettingModalHide: true}

navbar-item-active是一个可使频道高亮的Class,navbarShowIndexArray初始化的结果是一个0到11的数组,刚好是数组navbarArray的所有元素的索引。显然,初始化的结果是所有频道都将显示。

为了实现频道个性化配置的保存,navbarShowIndexArray还需要通过小程序的数据缓存API储存起来。

storeNavbarShowIndexArray: function() {    const that = this;    wx.setStorage({        key: 'navbarShowIndexArray',        data: that.data.navbarShowIndexArray    });}

切换频道的函数如下:

switchChannel: function(targetChannelIndex) {    this.getArticles(targetChannelIndex);    let navbarArray = this.data.navbarArray;    navbarArray.forEach((item, index, array) => {        item.type = '';        if (index === targetChannelIndex) {            item.type = 'navbar-item-active';        }    });    this.setData({        navbarArray: navbarArray,        currentChannelIndex: targetChannelIndex    });}

这样,频道的管理和简单切换我们就实现了。

但是,到此为止,频道的切换只能通过点击对应Topbar中频道那一小块区域来实现,要是在正文区域左滑和右滑也能切换频道就好了。

一个容易想到的思路是,在正文区域绑定touch事件,通过坐标判断滑动方向,然后使Topbar中当前频道的上一个或下一个频道高亮,同时,控制Topbar横向滚动合适的偏移长度,以确保切换后的频道能出现在视图区域。

onTouchstartArticles: function(e) {    this.setData({        'startTouchs.x': e.changedTouches[0].clientX,        'startTouchs.y': e.changedTouches[0].clientY    });},onTouchendArticles: function(e) {    let deltaX = e.changedTouches[0].clientX - this.data.startTouchs.x;    let deltaY = e.changedTouches[0].clientY - this.data.startTouchs.y;    if (Math.abs(deltaX) > Math.abs(deltaY) && Math.abs(deltaX) > 10) {        let deltaNavbarIndex = deltaX > 0 ? -1 : 1;        let currentChannelIndex = this.data.currentChannelIndex;        let navbarShowIndexArray = this.data.navbarShowIndexArray;        let targetChannelIndexOfNavbarShowIndexArray = navbarShowIndexArray.indexOf(currentChannelIndex) + deltaNavbarIndex;        let navbarShowIndexArrayLength = navbarShowIndexArray.length;        if (targetChannelIndexOfNavbarShowIndexArray >= 0 && targetChannelIndexOfNavbarShowIndexArray <= navbarShowIndexArrayLength - 1) {            let targetChannelIndex = navbarShowIndexArray[targetChannelIndexOfNavbarShowIndexArray];            if (navbarShowIndexArrayLength > 6) {                let scrollNavbarLeft;                if (targetChannelIndexOfNavbarShowIndexArray < 5) {                    scrollNavbarLeft = 0;                } else if (targetChannelIndexOfNavbarShowIndexArray === navbarShowIndexArrayLength - 1) {                    scrollNavbarLeft = this.rpx2px(110 * (navbarShowIndexArrayLength - 6));                } else {                    scrollNavbarLeft = this.rpx2px(110 * (targetChannelIndexOfNavbarShowIndexArray - 4));                }                this.setData({                    scrollNavbarLeft: scrollNavbarLeft                });            }            this.switchChannel(targetChannelIndex);        }    }}

版权声明:今日头条AppTopbar在微信小程序中的实现是由宝哥软件园云端程序自动收集整理而来。如果本文侵犯了你的权益,请联系本站底部QQ或者邮箱删除。