评论
盆友用Corsor 重构了我用uni-app写的Tab选项卡,UX交互效果拉满

盆友用Corsor 重构了我用uni-app写的Tab选项卡,UX交互效果拉满

努力做一个可爱的人,不埋怨谁,不嘲笑谁,也不羡慕谁,阳光下灿烂,风雨中奔跑,做自己的梦,走自己的路

盆友用Corsor 重构了我用uni-app写的Tab选项卡,UX交互效果拉满

缘由

最近也是疯狂的欧一个uni-app的前端项目。有一个登录注册页面,想着用扁平一点的风格去写

登录有两种方式一个是短信登录,另一个正常的账户密码;我用了常见的写法只是在下方店添加了一个点击事件切换,顶部用了一个tab他交互

盆友用Corsor 重构了我用uni-app写的Tab选项卡,UX交互效果拉满

Corsor 

为了保证UI设计风格的统一,因此整体看起来有点平;估计和我一样希望页面有高饱和的效果可以更好的吸引用户;于是盆友丢给Corsor 重构得出以下UI

盆友用Corsor 重构了我用uni-app写的Tab选项卡,UX交互效果拉满

牛蛙!这效果还是不错的,于是我要了源码一运行,好家伙!UX一点也没落下切换动画 输入框点击效果,错误提示 都是杆杆的

盆友用Corsor 重构了我用uni-app写的Tab选项卡,UX交互效果拉满

保持学习的心态看了一下 密码登入和短信登录Tab的切换效果,是使用animation动画,用贝塞尔曲线使得整体丝滑

animation: slideIn 0.3s cubic-bezier(0.4, 0, 0.2, 1);

@keyframes slideIn {
  from {
    transform: translateX(-100%);
  }
  to {
    transform: translateX(0);
  }

}

案例

<template>
	<view class="login-container">
		<!-- 选项卡 -->
		<view class="card-container">
			<!-- 登录表单 -->
			<view class="form-container" v-if="active==0">
				<view class="login-type-switch">
					<view class="switch-item" :class="{ active: loginType==='password' }"
						@tap="switchLoginType('password')">密码登录</view>
					<view class="switch-item" :class="{ active: loginType==='sms' }" @tap="switchLoginType('sms')">
						短信登录</view>
				</view>
			</view>
		</view>
	</view>
</template>


<script>
	export default {
		data() {
			return {
				active: 0,
				loginType: 'password', // 登录方式:password-密码登录,sms-短信登录
				isAnimating: false, // 添加动画状态控制
			};
		},
		methods: {
			// 切换登录方式
			switchLoginType(type) {
				if (this.isAnimating || this.loginType === type) return;
				this.isAnimating = true;
				this.loginType = type;
				// 动画结束后重置状态
				setTimeout(() => {
					this.isAnimating = false;
				}, 300);
			},
		},

	};
</script>



<style>
	page {
		background-color: #f5f7fa;
	}

	/* 卡片容器 */
	.card-container {
		position: relative;
		margin: 80rpx 40rpx 40rpx;
		border-radius: 24rpx;
		background-color: #fff;
		box-shadow: 0 10rpx 40rpx rgba(0, 0, 0, 0.08);
		padding: 40rpx 30rpx;
		z-index: 10;
	}


	/* 登录方式切换样式 */

	.login-type-switch {
		display: flex;
		justify-content: center;
		margin-bottom: 50rpx;
		background: #f7f9fc;
		border-radius: 40rpx;
		padding: 8rpx;
		position: relative;
		overflow: hidden;
	}


	.switch-item {
		flex: 1;
		text-align: center;
		padding: 20rpx 0;
		font-size: 28rpx;
		color: #666;
		border-radius: 32rpx;
		transition: all 0.3s cubic-bezier(0.4, 0, 0.2, 1);
		position: relative;
		z-index: 1;
	}


	.switch-item.active {
		color: #335eea;
		font-weight: 600;
	}


	.switch-item.active::after {
		content: '';
		position: absolute;
		top: 0;
		left: 0;
		right: 0;
		bottom: 0;
		background: #fff;
		border-radius: 32rpx;
		box-shadow: 0 4rpx 12rpx rgba(51, 94, 234, 0.1);
		z-index: -1;
		animation: slideIn 0.3s cubic-bezier(0.4, 0, 0.2, 1);

	}


	@keyframes slideIn {

		from {

			transform: translateX(-100%);

		}

		to {

			transform: translateX(0);

		}
	}

	.form-wrapper {

		position: relative;

		min-height: 400rpx;

	}
</style>