效果图:
飞书20230721-082529
话不多说直接上代码:
html部分:
<template>
<!--自定义的头部部分-->
<nav-tap navColor="#333" title="推广二维码" isBack isHei></nav-tap>
<view class="container">
<canvas canvas-id="myCanvas" style="width: 600rpx;height:890rpx;position: fixed;top:-200%;left:-200%;opacity: 0;"></canvas>
<image :src="data.path" style="width: 100%;height: 100%;"></image>
</view>
<view class="bottomBtn">
<view class="leftBtn" @click.stop="saveImage">
<image style="width: 44rpx;height: 44rpx;margin-right: 16rpx;" src="http://wisdomhallsup.oss-cn-beijing.aliyuncs.com/uploads/20230720/973dbaf930b3988948393e1c03dc77b5.png"></image>
<text>保存图片</text>
</view>
<view class="rightBtn">
<image style="width: 44rpx;height: 44rpx;margin-right: 16rpx;" src="http://wisdomhallsup.oss-cn-beijing.aliyuncs.com/uploads/20230720/d787c0dd9f4f0e8c056d83247be77923.png"></image>
<text>分享好友</text>
</view>
</view>
<view v-if="data.show" style="display: flex;align-items: center;justify-content: center;position: fixed;width: 100vw;height: 100vh;top:0;left: 0;background-color: rgba(0,0,0,0.5);">
<view style="height: 220rpx;width:220rpx;background-color: #fff;border-radius: 20rpx;">
<view style="height: 140rpx;display: flex;align-items: center;justify-content: center;">
<view class="loading">
<view class="item"></view>
<view class="item"></view>
<view class="item"></view>
</view>
</view>
<view class="step" style="height: 34rpx;width: 100%;text-align: center;color: #999;font-size: 28rpx;margin-top:20rpx;">
<text style="--i:1">海</text>
<text style="--i:2">报</text>
<text style="--i:3">绘</text>
<text style="--i:4">制</text>
<text style="--i:5">中</text>
<text style="--i:6">.</text>
<text style="--i:7">.</text>
<text style="--i:8">.</text>
</view>
</view>
</view>
</template>
js部分:
<script setup>
import { onShow,onReady,onLoad} from '@dcloudio/uni-app'
import { inject,reactive,ref} from "vue"
import navTap from '@/components/navTap.vue'
const $request = inject('$request')
const $api = inject('$api')
const topheight = ref(0)
const painter = ref(null)
const data = reactive({
path:'',
show:false,
})
const saveImage = () => {
uni.saveImageToPhotosAlbum({ //保存到相册
filePath: data.path,
success: function () {
console.log('save success');
}
});
}
const drawDone = (flag = false,ctx) => {
return new Promise((resolve,reject)=>{
ctx.draw(flag,()=>setTimeout(()=>resolve(),100))
})
}
onLoad(()=>{
data.show = true
setTimeout(async ()=>{ //延时为了模拟请求数据
const ctx = uni.createCanvasContext('myCanvas')
const image = 'https://m.360buyimg.com/babel/jfs/t1/196317/32/13733/288158/60f4ea39E6fb378ed/d69205b1a8ed3c97.jpg'
const image2 = 'http://wisdomhallsup.oss-cn-beijing.aliyuncs.com/uploads/20230720/43123dbf0df41745dd2071481c288354.png'
ctx.drawImage(image,0,0,600,890)
await drawDone(false,ctx)
ctx.drawImage(image2,50,150,200,200)
await drawDone(true,ctx)
uni.canvasToTempFilePath({
canvasId: 'myCanvas',
destWidth: '600',
destHeight: '890',
fileType: 'jpg',
quality: 0.4,
success: function(res1) {
data.show = false
data.path = res1.tempFilePath
},
fail: function(res) {
console.log(res.errMsg)
}
})
},2000)
})
</script>
css部分:
<style lang="scss">
.container{
width: 600rpx;
height:890rpx;
background:#d9d9d9;
margin:40rpx auto;
}
.bottomBtn{
height:80rpx;
width: 100%;
padding:0 40rpx;
box-sizing: border-box;
margin-top:180rpx;
display: flex;
align-items: center;
justify-content: space-between;
.leftBtn,.rightBtn{
height: 100%;
width: 290rpx;
display: flex;
align-items: center;
justify-content: center;
background: linear-gradient(90deg, #1791FF 0%, rgba(23, 145, 255, 0.69) 100%);
border-radius: 80rpx;
font-size: 32rpx;
color: #fff;
font-weight: bold;
}
}
.loading{
width: 100rpx;
height: 100rpx;
border-radius: 50%;
position: relative;
.item {
width: 100%;
height: 100%;
border-radius: 50%;
position: absolute;
}
.item:nth-child(1) {
border-bottom: 14rpx solid #1890ff;
transform: rotateX(15deg) rotateY(-45deg);
animation: rotate_one 1s linear infinite -0.8s;
}
.item:nth-child(2) {
border-bottom: 14rpx solid #f40968;
transform: rotateX(50deg) rotateY(10deg);
animation: rotate_two 1s linear infinite -0.4s;
}
.item:nth-child(3) {
border-bottom: 14rpx solid #77d970;
transform: rotateX(35deg) rotateY(55deg);
animation: rotate_three 1s linear infinite;
}
@keyframes rotate_one {
to {
transform: rotateX(15deg) rotateY(-45deg) rotateZ(360deg);
}
}
@keyframes rotate_two {
to {
transform: rotateX(50deg) rotateY(10deg) rotateZ(360deg);
}
}
@keyframes rotate_three {
to {
transform: rotateX(35deg) rotateY(55deg) rotateZ(360deg);
}
}
.step {
position: relative;
-webkit-box-reflect: below -12px linear-gradient(transparent, rgba(0, 0, 0, 0.2))
}
}
.step text {
position: relative;
display: inline-block;
animation: animate 1.2s ease-in-out infinite;
animation-delay: calc(.1s*var(--i))
}
@keyframes animate {
0% {
transform: translateY(0)
}
20% {
transform: translateY(-18rpx)
}
40%,
100% {
transform: translateY(0)
}
}
</style>