“打工搬砖记”中首页的功能实现(一)

打工搬砖记

先来一个小程序首页预览图,首页较为复杂的也就是“秒薪”以及弹出文字的动画。
已上线小程序“随心的打工搬砖记”,进行预览观看。
请添加图片描述

请添加图片描述

秒薪的计算

秒薪计算公式:秒薪 = 平均月薪/工作天数/(工作时间-午休时间)
平均月薪以及工作天数是用户自行设置的,一天工作多少秒这个比较难点需要计算一下。
"new Date(new Date(new Date().toLocaleDateString()).getTime()) " 代表获取今天0点的时间戳。
时间点乘60乘60乘1000再加上0点的时间戳得出时间点的时间戳
详细实现过程代码如下:

			// 这是通过接口获取的数据,这里为了方便演示定易了一下
			let workerStartArr=['9','30']
			let noonStartArr=['11','30']
			let noonEndArr=['1','30']
			let workerEndArr=['18','30']
			// 时间转换为时间戳
			let workerStart = new Date(new Date().toLocaleDateString()).getTime() + parseInt(workerStartArr[0]) * 60 * 60 * 1000 - 1 + workerStartArr[1] * 60 * 1000

			let noonStart = new Date(new Date().toLocaleDateString()).getTime() + parseInt(noonStartArr[0]) * 60 * 60 * 1000 - 1 + noonStartArr[1] * 60 * 1000

			let noonEnd = new Date(new Date().toLocaleDateString()).getTime() + parseInt(noonEndArr[0]) * 60 * 60 * 1000 - 1 + noonEndArr[1] * 60 * 1000

			let workerEnd = new Date(new Date().toLocaleDateString()).getTime() + parseInt(workerEndArr[0]) * 60 * 60 * 1000 - 1 + workerEndArr[1] * 60 * 1000

			let newTime = Date.parse(new Date())
			// 工作时长 多少秒 
			let secondWorker = (workerEnd - workerStart - (noonEnd - noonStart)) / 1000
			// 秒薪
			this.secondMoney = (this.userInfo.wage / this.userInfo.workDay / secondWorker).toFixed(4)
				
			// 根据当前时间在哪个区间然后计算已经挣到的薪资
			this.statusWork = 2
			if(newTime < workerStart){
				this.money = 0
				this.titleTime = 0
				this.statusWork = 1
			} else if (newTime > workerStart && newTime < noonStart) {
				this.money = ((newTime - workerStart) / 1000) * this.secondMoney
				this.titleTime = noonStart - newTime
			} else if (newTime > noonEnd && newTime < workerEnd) {
				let haveMoney = (noonStart - workerStart)/1000 * this.secondMoney
				this.money = ((newTime - noonEnd) / 1000) * this.secondMoney + haveMoney
				this.titleTime = workerEnd - newTime
			}else{
				let haveMoney = (noonStart - workerStart)/1000 * this.secondMoney
				this.money = ((workerEnd - noonEnd) / 1000) * this.secondMoney + haveMoney
				this.titleTime = 0
				this.statusWork = 1
			}

文字弹出动画

用户点击人物后,人物会纵向的动一下,并且文字会先从人物头上冒出来,然后快速移动到手机屏幕中件。
通过CSS中animation动画结合JS中setTimeout()方法来实现。通过绑定class,然后控制active状态是true和false来实现动画过程。

			<!-- 主体结构内容 -->
			<view @click="setWork" class="basis_right">
				<view :class="[active?'bubble_boxActive':'bubble_box']">
					<image src="../../static/role/bubble.png" class="bubbleImg" mode=""></image>
					<view class="bubble_text">
						<text v-for="(item,index) in funnyList" :key="index" >{{item}}</text>
					</view>
				</view>
				<image v-show="statusWork == 1" src="../../static/role/luXun_rest.png"
					:class="[active?'luxunImgActive':'luxunImg']" mode=""></image>
				<image v-show="statusWork == 2" src="../../static/role/luXun_active.png"
					:class="[active?'luxunImgActive':'luxunImg']" mode=""></image>
			</view>
<!-- 样式 -->
<style lang="scss">
		.basis_right {
			flex: 1;
			position: relative;


		.luxunImg {
			position: absolute;
			right: 30rpx;
			bottom: 0;
			width: 210rpx;
			height: 350rpx;
		}

		.luxunImgActive {
			position: absolute;
			right: 30rpx;
			bottom: 0;
			width: 210rpx;
			height: 350rpx;
			animation: myMove 1s linear alternate 1;
		}

		@keyframes myMove {
			0% {
				height: 350rpx;
			}

			50% {
				height: 300rpx;
			}

			100% {
				height: 350rpx;
			}
		}

		.bubble_box {
			display: none;
		}

		.bubble_boxActive {
			position: absolute;
			right: 200rpx;
			top: -180rpx;
			width: 280rpx;
			height: 280rpx;
			display: flex;
			align-items: center;
			justify-content: center;

			.bubbleImg {
				position: absolute;
				width: 100%;
				height: 100%;
			}

			.bubble_text {
				position: relative;
				display: flex;
				font-size: 24rpx;
				flex-direction: column;
			}

			animation: myIdea 3s ease alternate infinite;
		}



		@keyframes myIdea {
			0% {
				transform: scale(0.1, 0.1);
				right: 10rpx;
				top: -100rpx;
			}

			30% {
				transform: scale(0.3, 0.3);
				right: 10rpx;
				top: -240rpx;
			}

			50% {
				transform: scale(1, 1);
				right: 200rpx;
				top: -180rpx;
			}

			100% {
				transform: scale(1, 1);
				right: 200rpx;
				top: -180rpx;
			}
		}


	}
</style>
	
			// getFunny方法是我这请求后端的数据,active控制class样式切换,以及3秒执行一次
			setWork() {
				if (!this.active) {
					getFunny({
						data: {},
						custom: {
							auth: true,
							toast: false,
							catch: true
						}
					}).then((res) => {
						this.funnyList =res.split(',')
					})
					
					this.active = true
					setTimeout(() => {
						this.active = false
					}, 3000)
					// 声音
					const innerAudioContext = uni.createInnerAudioContext();
					innerAudioContext.autoplay = true;
					innerAudioContext.sessionCategory = 'ambient';
					innerAudioContext.src = '/static/lunch/music.mp3';
					innerAudioContext.onPlay();
				}
				// this.statusWork = this.statusWork == 1 ? 2 : 1
			},

根据时间数字变化

每秒顶部以及秒薪会变化,是使用到了uview中的u-count-down组件。感兴趣的可以看一下如何实现。不感兴趣的会用就行
组件内的部分代码如下:

<template>
	<view class="u-count-down">
		<slot>
			<text class="u-count-down__text">{{ formattedTime }}</text>
		</slot>
	</view>
</template>

<script>
	import props from './props.js';
	import {
		isSameSecond,
		parseFormat,
		parseTimeData
	} from './utils';
	/**
	 * u-count-down 倒计时
	 * @description 该组件一般使用于某个活动的截止时间上,通过数字的变化,给用户明确的时间感受,提示用户进行某一个行为操作。
	 * @tutorial https://uviewui.com/components/countDown.html
	 * @property {String | Number}	time		倒计时时长,单位ms (默认 0 )
	 * @property {String}			format		时间格式,DD-日,HH-时,mm-分,ss-秒,SSS-毫秒  (默认 'HH:mm:ss' )
	 * @property {Boolean}			autoStart	是否自动开始倒计时 (默认 true )
	 * @property {Boolean}			millisecond	是否展示毫秒倒计时 (默认 false )
	 * @event {Function} finish 倒计时结束时触发 
	 * @event {Function} change 倒计时变化时触发 
	 * @event {Function} start	开始倒计时
	 * @event {Function} pause	暂停倒计时 
	 * @event {Function} reset	重设倒计时,若 auto-start 为 true,重设后会自动开始倒计时 
	 * @example <u-count-down :time="time"></u-count-down>
	 */
	export default {
		name: 'u-count-down',
		mixins: [uni.$u.mpMixin, uni.$u.mixin, props],
		data() {
			return {
				timer: null,
				// 各单位(天,时,分等)剩余时间
				timeData: parseTimeData(0),
				// 格式化后的时间,如"03:23:21"
				formattedTime: '0',
				// 倒计时是否正在进行中
				runing: false,
				endTime: 0, // 结束的毫秒时间戳
				remainTime: 0, // 剩余的毫秒时间
			}
		},
		watch: {
			time(n) {
				this.reset()
			}
		},
		mounted() {
			this.init()
		},
		methods: {
			init() {
				this.reset()
			},
			// 开始倒计时
			start() {
				if (this.runing) return
				// 标识为进行中
				this.runing = true
				// 结束时间戳 = 此刻时间戳 + 剩余的时间
				this.endTime = Date.now() + this.remainTime
				this.toTick()
			},
			// 根据是否展示毫秒,执行不同操作函数
			toTick() {
				if (this.millisecond) {
					this.microTick()
				} else {
					this.macroTick()
				}
			},
			macroTick() {
				this.clearTimeout()
				// 每隔一定时间,更新一遍定时器的值
				// 同时此定时器的作用也能带来毫秒级的更新
				this.timer = setTimeout(() => {
					// 获取剩余时间
					const remain = this.getRemainTime()
					// 重设剩余时间
					if (!isSameSecond(remain, this.remainTime) || remain === 0) {
						this.setRemainTime(remain)
					}
					// 如果剩余时间不为0,则继续检查更新倒计时
					if (this.remainTime !== 0) {
						this.macroTick()
					}
				}, 30)
			},
			microTick() {
				this.clearTimeout()
				this.timer = setTimeout(() => {
					this.setRemainTime(this.getRemainTime())
					if (this.remainTime !== 0) {
						this.microTick()
					}
				}, 50)
			},
			// 获取剩余的时间
			getRemainTime() {
				// 取最大值,防止出现小于0的剩余时间值
				return Math.max(this.endTime - Date.now(), 0)
			},
			// 设置剩余的时间
			setRemainTime(remain) {
				this.remainTime = remain
				// 根据剩余的毫秒时间,得出该有天,小时,分钟等的值,返回一个对象
				const timeData = parseTimeData(remain)
				this.$emit('change', timeData)
				// 得出格式化后的时间
				this.formattedTime = parseFormat(this.format, timeData)
				// 如果时间已到,停止倒计时
				if (remain <= 0) {
					this.pause()
					this.$emit('finish')
				}
			},
			// 重置倒计时
			reset() {
				this.pause()
				this.remainTime = this.time
				this.setRemainTime(this.remainTime)
				if (this.autoStart) {
					this.start()
				}
			},
			// 暂停倒计时
			pause() {
				this.runing = false;
				this.clearTimeout()
			},
			// 清空定时器
			clearTimeout() {
				clearTimeout(this.timer)
				this.timer = null
			}
		},
		beforeDestroy() {
			this.clearTimeout()
		}
	}
</script>

<style
	lang="scss"
	scoped
>
	@import "../../libs/css/components.scss";
	$u-count-down-text-color:$u-content-color !default;
	$u-count-down-text-font-size:15px !default;
	$u-count-down-text-line-height:22px !default;

	.u-count-down {
		&__text {
			color: $u-count-down-text-color;
			font-size: $u-count-down-text-font-size;
			line-height: $u-count-down-text-line-height;
		}
	}
</style>

小结

总的来说实现过程不难,难的是思路以及行动力。加油打工人!!!
后面写一篇关于轮盘的实现过程。

  • 26
    点赞
  • 10
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 2
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

静的小白菜

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值