微信小程序 (vue+uniapp)--自定义导航栏头部、滑动渐变(仿小米小程序首页)


前言

提示:一个小功能大致的逻辑:
1、自定义顶部导航栏:
(1)、随着需求不断的变化,小程序原生导航栏头部已不满足现有需求
(2)、通过uniapp的uni.getSystemInfoSync、uni.getMenuButtonBoundingClientRect,获取 手机系统的信息、小程序胶囊位置信息,从而适配不同手机的尺寸
(3)、顶部导航栏由状态栏大小 + 小程序胶囊大小 + 胶囊距离状态栏高度 + 胶囊底部高度 = 总的高度
2、功能渐变效果:
(1)、顶部背景颜色根据滑动的位置渐变,用css属性background: rgba()
(2)、搜索框宽度,计算的宽度 + 滑动距离的宽度
(3)、logo图标随着滑动距离的大小渐变

一、效果(小米小程序)

在这里插入图片描述

二、我仿的效果

在这里插入图片描述

三、代码逻辑

nav.vue

<template>
  <view>
    <view class="top_navbar">
      <view class='top_pos' :style="'height:' + totalHeight + 'px;'"></view>
      <view class="navbar-fixed" :style="navStyle">
        <view :style="'height:' + statusBarHeight + 'px;'"></view>
        <view class="navbar-content" :style="'height:' + navBarHeight + 'px;'+'width:'+windowWidth+'px;'">
          <image src="https://uviewui.com/common/logo.png" class="top_icon" :style="'opacity:'+imgOpacity"></image>
          <view :style="'width:'+navInpWid+'px;'" :class="[navOpacity >= 1 ?'nav_input nav_inp_ac':'nav_input']">
            <u-icon name="search" class="find-icon"></u-icon>
            <span>选择商品</span>
          </view>
        </view>
      </view>
    </view>
    <view style='width: 100%; height: 500px; background: #FE5804'></view>
    <view style='width: 100%; height: 500px; background: pink'></view>
    <view style='width: 100%; height: 500px; background: green'></view>
    <view style='width: 100%; height: 500px; background: red'></view>
  </view>
</template>

<script>
export default {
  data() {
    return {
      totalHeight: '', // 总高度
      statusBarHeight: '', // 状态栏高度
      navBarHeight: 45, // 导航栏高度
      windowWidth: 375,
      navStyle: '',
      navOpacity: 0,
      navInpWid: '',
      navRemain: '',
      widRemain: '',
      scrollTop: 0,
      imgOpacity: 1,
      logo_block_width: 0,
    };
  },
  mounted() {
    // #ifdef  MP-WEIXIN
    this.nav();
    // #endif
  },
  methods: {
    nav() {
      let info = uni.getSystemInfoSync();
      console.log(info);
      let menuButtonInfo = uni.getMenuButtonBoundingClientRect();
      console.log(menuButtonInfo);
      this.statusBarHeight = info.statusBarHeight;
      this.windowWidth = info.windowWidth;
      this.navBarHeight =
        menuButtonInfo.bottom -
        info.statusBarHeight +
        (menuButtonInfo.top - info.statusBarHeight) +
        4;
      this.windowWidth = menuButtonInfo.left;
      this.widRemain = (info.windowWidth / 375) * 70;
      // this.navInpWid = this.windowWidth - this.widRemain;
      this.navInpWid = menuButtonInfo.left - 70;
      console.log('navInpWid:...', this.navInpWid);
      this.navRemain = this.windowWidth - this.widRemain;
      console.log('navRemain:....................', this.navRemain);
      this.totalHeight = this.statusBarHeight + this.navBarHeight;
      console.log('totalHeight:...', this.totalHeight);
      this.logo_block_width = this.windowWidth - this.navInpWid - 10;
    },
    onPageScroll(e) {
      let topHeight = e.scrollTop;
      let navOp = 0;
      navOp = topHeight / this.totalHeight;
      console.log('navOp:...', navOp);
      let mobileTop = this.navRemain;
      this.navOpacity = navOp;
      this.navInpWid =
        navOp > 0 ? mobileTop + this.widRemain * navOp : this.navRemain;
      this.logo_block_width = this.windowWidth - this.navInpWid - 10;
      console.log('scroll:...', this.navInpWid);
      this.imgOpacity = navOp <= 1 ? 1 - navOp : 0;
      const styles = `
      background: rgba(255, 255, 255, ${navOp});
      `;
      this.navStyle = topHeight > 10 ? styles : '';
    },
  },
};
</script>

<style lang="scss" scoped>
.top_navbar {
  .top_pos {
    width: 100%;
    position: fixed;
    top: 0;
    left: 0;
    background-color: #fe5804;
  }
  .navbar-fixed {
    position: fixed;
    top: 0;
    left: 0;
    z-index: 100;
    width: 100%;
    .navbar-content {
      display: flex;
      align-items: center;
      justify-content: flex-end;
      height: 45px;
      padding: 0 10px 0 10px;
      box-sizing: border-box;
      position: relative;
      // background: yellowgreen;
      .top_icon {
        position: absolute;
        left: 30rpx;
        // transform: translateX(-50%);
        width: 40px;
        height: 40px;
        display: block;
        opacity: 0;
        border-radius: 50%;
        // background: gray;
      }
      .logo-block {
        position: relative;
        background: violet;
        // width: 50px;
        height: 40px;
        .top_icon {
          position: absolute;
          left: 50%;
          transform: translateX(-50%);
          width: 40px;
          height: 40px;
          display: block;
          opacity: 0;
          border-radius: 50%;
          // background: gray;
        }
      }
      .nav_input {
        width: 430px;
        height: 43px;
        line-height: 43px;
        border-radius: 40px;
        background-color: #fff;
        position: relative;
        padding-left: 15px;
        color: gray;
        .find-icon {
          color: gray;
          padding-right: 10px;
        }
      }
      .nav_inp_ac {
        transition: all ease 0.3s;
        background-color: #f7f7f7;
      }
      .return_icon {
        width: 54rpx;
        height: 54rpx;
        margin-bottom: 4px;
        display: block;
        border-radius: 50%;
      }
      .return_icon2 {
        width: 22rpx;
        height: 38rpx;
        transform: rotateY(180deg);
      }
    }
  }
}
</style>

总结

以上就是仿微信小程序小米商城的效果内容

  • 9
    点赞
  • 71
    收藏
    觉得还不错? 一键收藏
  • 4
    评论
### 回答1: Uniapp是一款多端开发框架,支持开发微信小程序、H5、App等多种平台的应用程序。在微信小程序中,往往需要自定义导航栏以满足用户需求,Uniapp提供了方便易用的方法来实现此功能。 首先,在Uniapp中创建一个自定义导航栏的组件,可以使用vue组件进行实现。在此组件中,需要定义导航栏的样式,例如背景颜色、文字颜色、边框等。 其次,在每个需要自定义导航栏的页面中引入这个组件,并将页面的标题传递给组件。这样,在页面中就可以显示出我们定义的自定义导航栏了。 除此之外,我们还可以在这个组件中添加返回按钮、菜单按钮等功能,以提升用户体验。同时,还可以通过uni.getSystemInfoSync()方法获取系统信息来动态设置导航栏的高度,以兼容不同设备的屏幕尺寸。 总之,Uniapp提供了方便简洁的方法来实现自定义导航栏,在微信小程序开发中非常实用。通过此功能,我们可以为用户提供更加个性化、更加舒适的应用体验。 ### 回答2: Uniapp 是一款跨平台的开发框架,可以快速开发出支持多种小程序平台的应用,包括微信小程序。在微信小程序中,自定义导航栏能够提供更好的用户体验,同时也满足了开发者个性化设计的需求。下面将介绍如何在 Uniapp自定义微信小程序导航栏。 1. 使用插件方式 Uniapp 提供了一个可以自定义导航栏的插件 uni-navigationBar,可以方便地进行开发。使用该插件的步骤如下: (1)安装 uni-navigationBar 插件 在 HBuilderX 的插件市场搜索 uni-navigationBar 并安装。或者在项目根目录下执行以下命令: npm install --save uni-navigationbar (2)在需要使用自定义导航栏的页面引入插件 在需要使用自定义导航栏的页面的 script 标签中,引入插件并注册: import uniNavigationBar from 'uni-navigationbar/vue'; Vue.use(uniNavigationBar); (3)在页面中使用自定义导航栏 可以在页面的 template 标签中,使用 uni-navigationBar 提供的组件和组件属性来实现自定义导航栏。 2. 使用自定义组件方式 如果不想使用插件,也可以自己编写一个自定义组件来实现自定义导航栏。实现的步骤如下: (1)在项目中创建自定义组件 可以使用 HBuilderX 的“创建自定义组件”功能,在项目中创建一个自定义组件。 (2)在自定义组件中编写导航栏代码 可以在自定义组件的 template 标签中编写需要自定义导航栏代码。 (3)在需要使用自定义导航栏的页面引入自定义组件 在需要使用自定义导航栏的页面的 template 标签中,引入刚才创建的自定义组件。 (4)在页面中使用自定义导航栏 可以在页面的 template 标签中,使用刚才创建的自定义组件,来实现自定义导航栏。 总的来说,Uniapp 微信小程序自定义导航栏的实现方法比较简单。可以使用插件方式或者自定义组件方式。如果你的项目已经使用 uni-navigationBar 插件,可以直接使用该插件实现自定义导航栏;如果你需要自定义更多的样式或交互效果,可以自己编写一个自定义组件。在实际开发中,可以根据项目需求和个人喜好选择适合自己的方式来实现自定义导航栏。 ### 回答3: Uniapp 是一款跨端应用开发框架,可以同时开发出运行于多个平台的应用程序。在 Uniapp 中,为了更好地适应不同平台的导航栏样式需求,Uniapp 提供了一套自定义导航栏的解决方案。本文将介绍如何使用 Uniapp自定义导航栏功能来开发微信小程序Uniapp 提供了两种自定义导航栏的方式:native 和 js 组件两种方式。 1. native 方式: 使用 native 方式,可以直接使用小程序原生的导航栏组件,Uniapp 会提供一些额外的 API、样式、事件来方便我们在开发过程中进行调整。 2. js 组件方式: 使用 js 组件方式,可以完全自定义导航栏的样式和行为,包括可以将导航栏设置为全局组件,方便在应用程序的多个页面中复用和调用。 下面我们将以 js 组件方式为例,介绍如何使用 Uniapp自定义导航栏功能来开发微信小程序。 第一步,在 App.vue 中定义自定义导航栏组件: ``` <template> <view class="app"> <!-- 引入自定义导航栏组件 --> <custom-nav-bar title="自定义导航栏"></custom-nav-bar> <!-- 页面内容 --> <router-view></router-view> </view> </template> <script> export default { components: { // 引入自定义导航栏组件 'custom-nav-bar': () => import('@/components/CustomNavBar.vue') } } </script> <style> /* 自定义导航栏样式 */ .uni-nav-bar { height: uni-status-bar-height + 44px; padding-top: uni-status-bar-height; display: flex; justify-content: center; align-items: center; background-color: #fff; color: #000; position: relative; z-index: 100; box-shadow: 0 2px 4px rgba(0, 0, 0, 0.1); } .uni-nav-bar__title { font-size: 18px; } </style> ``` 第二步,定义自定义导航栏组件的样式和功能: ``` <template> <view class="uni-nav-bar"> <!-- 导航栏左侧返回按钮 --> <view class="uni-nav-bar__left" @tap="back"> <text class="uni-nav-bar__back">返回</text> </view> <!-- 导航栏标题 --> <view class="uni-nav-bar__title">{{ title }}</view> </view> </template> <script> export default { props: ['title'], methods: { // 导航栏左侧返回按钮点击事件 back () { uni.navigateBack() } } } </script> <style> /* 导航栏样式 */ .uni-nav-bar { height: 44px; padding: 0 16px; display: flex; justify-content: space-between; align-items: center; background-color: #fff; color: #000; position: relative; z-index: 100; box-shadow: 0 2px 4px rgba(0, 0, 0, 0.1); } .uni-nav-bar__left { width: 70px; display: flex; flex-direction: row; justify-content: flex-start; align-items: center; } .uni-nav-bar__back { font-size: 16px; color: #000; } .uni-nav-bar__title { font-size: 18px; } </style> ``` 以上即为使用 Uniapp自定义导航栏功能来开发微信小程序的完整示例。通过以上代码,我们定义了一个自定义导航栏组件 CustomNavBar,并且在 App.vue 中引入和展示了该组件。 在实际开发过程中,我们可以根据自己的需求来调整自定义导航栏的样式和功能,比如在导航栏右侧添加按钮、增加搜索栏等等。同时,也可以将自定义导航栏组件设置为全局组件,方便在应用程序的多个页面中复用和调用。
评论 4
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值