骑驴找蚂蚁

全干工程师

纯CSS实现小程序导航栏过渡动画

大多数应用中导航栏目是必不可少的组件之一。为导航栏加上选中激活过渡动画也是必不可少的,比如下面效果图中选中导航底部蓝色线条跟随的过渡动画,它是以纯CSS3实现的。
css3-nav-animation

实现

实现此效果比较简单,定义好导航数据,为导航编写css样式表,点击选中导航附加选中的样式名。

导航结构和数据

Page({
data: {
	navigations: [
		{label:  '全部', selected:  true, value:  ''},
		{label:  '已发布', selected:false, value:  'published'},
		{label:  '草稿', selected:  false, value:  'draft'},
		{label:  '已下架', selected:  false, value:  'expired'},
	],
	// 默认方向
	direction: 'left',
}
});
<view  class="headerContainer">
	<view  class="headerNavigation">
		<view  bind:tap="onTab" data-index="{{index}}" class="{{item.selected  ?  'active active-'+direction  :  ''}}" wx:for="{{navigations}}"><text>{{item.label}}</text></view>
	</view>
</view>

基础CSS

这里使用scss作为css预处理器。

.headerContainer  {
	background-color:  var(--weui-BG-2);
	position:  fixed;
	top:  0;
	z-index:  1000;
	width:  100vw;
	.headerNavigation  {
	width:  100%;
	height:  110rpx;
	white-space:  nowrap;
	flex-direction:  row;
	display:  flex;
	justify-content:  space-between;
		view  {
			padding:  0  20rpx;
			position:  relative;
			color:  var(--weui-FG-0);
			display:  flex;
			font-size:  32rpx;
			align-items:  center;
		}
	}
}

选中和过渡动画

为导航增加选中的css和选中的过渡动画css

  • 选中CSS
.active  {
	font-weight:  700;
	color:  var(--weui-BRAND)  !important;
}
.active::after  {
	content:  "  ";
	width:  24px;
	height:  4px;
	position:  absolute;
	background-color:  var(--weui-BRAND);
	bottom:  0;
	left:  calc(50%  -  12px);
	text-align:  center;
	border-radius:  2px;
}
  • 过渡动画

使用css3animation实现过渡动画。

/*从左向右跟随*/
.active-left::after  {
	animation: slideLeftToRight ease  .3s  forwards;
}
/*从右向左跟随*/
.active-right::after  {
	animation: slideRightToLeft ease  .3s  forwards;
}
@keyframes  slideLeftToRight  {
	from  {
		transform:  translate3d(-100%,  0,  0);
	}
	to  {
		transform:  translate3d(0,  0,  0);
	}
}
@keyframes  slideRightToLeft  {
	from  {
		transform:  translate3d(100%,  0,  0);
	}
	to  {
		transform:  translate3d(0,  0,  0);
	}
}

选中事件

这里是在微信小程序的实现,为view标签增加一个bind:tap="onTab"
事件。


...
// 具体实现
onTab(e:  WechatMiniprogram.CustomEvent)  {
	const  index  =  e.currentTarget.dataset.index;
	const  tabs  =  this.data.navigations;
	if (tabs[index].selected) {
		return  ;
	}
	const  prevIndex  =  tabs.findIndex(item  =>  item.selected);
	tabs.forEach((element,  eIndex)  =>  {
		element.selected  =  false;
		if (index  ==  eIndex) {
			element.selected  =  true;
		}
	});
	this.setData({
		navigations:  tabs,
		direction: index  >  prevIndex  ?  'left'  :  'right',
	});
},
...

推荐阅读

留言