当前位置:   article > 正文

uniapp 录音组件_uniapp录音插件

uniapp录音插件

原生uniapp 录音组件,复制就能用

效果图

代码部分

<template>
	<view class="box">
		<uni-popup ref="popup" :animation="true" :is-mask-click="false">
			<view class="popup_box" @tap.stop = "closePop">
				<view class="move">
					<view v-if="btnStatus!==0" :class="btnStatus==3? 'move_center_clear': 'move_center'">
						<view class="move_center_top">
							<view class="move_center_item" v-for="(item,index) in 15" :key="index">
							</view>
						</view>
						<view class="move_center_footer">
							{{btnStatus==3? '松开手指,取消发送':"正在录音..."}}
						</view>
					</view>
				</view>


				<view :class=" btnStatus==0? 'footerBtn': btnStatus==1?'footerBtn_star':'footerBtn_move'">
					<view class="footerBtn_chr" @touchend="end" @touchmove="move" @touchstart="start">
						{{btnStatus==0? "按住说话":btnStatus==1? "说话中...": btnStatus==2? "松开手指发送录音": "上划取消"}}
					</view>
				</view>
				<!-- <button @click="play(voicePath)">播放</button> -->
			</view>
		</uni-popup>
	</view>
</template>
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
  • 25
  • 26
  • 27

js部分

<script>
	const recorderManager = uni.getRecorderManager()
	const innerAudioContext = uni.createInnerAudioContext()
	innerAudioContext.autoplay = true
	export default {
		name: "sound",
		props: {
			maskShow: false, //遮罩层
		},
		data() {
			return {
				recordFlg: true, //录音锁
				btnStatus: 0, //按钮状态
				audioDuration: "",
				voicePath: "", //音频本地路径
				timer: null, //定时器
				num: 0, //录音时长
			}
		},
		watch: {
			maskShow: {
				// 每个属性值发生变化就会调用这个函数
				handler(newVal, oldVal) {
					console.log(newVal, oldVal, "监听");
					if (newVal === true) {
						this.$refs.popup.open('center')
					} else {
						this.$refs.popup.close()
					}

				},
				// 立即处理 进入页面就触发
				// immediate: true,
				// 深度监听 属性的变化
				// deep: true
			},
		},
		created() {
			console.log("888");
			// 为了防止苹果手机静音无法播放
			uni.setInnerAudioOption({
				obeyMuteSwitch: false
			})
			let that = this;
			recorderManager.onStop(function(res) {
				// 解决第一次录音,挂实例挂载问题
				that.$nextTick(() => {
					console.log('recorder stop' + JSON.stringify(res));
					that.audioDuration = res.duration;
					that.voicePath = res.tempFilePath;
				})
			});

		},
		methods: {
			// 点击关闭遮罩层
			closePop() {
				this.$refs.popup.close()
				this.$emit("emitCheck", false)
			},
			start() {
				// 限制时长
				this.timer = setInterval(() => {
					this.num++
					console.log("num", this.num);
				}, 1000)

				console.log("手指按下");
				this.btnStatus = 1
				// 暂停播放
				// innerAudioContext.stop()
				recorderManager.start({
					//时长5分钟,单位毫秒
					duration: 300000
				});
				this.recordFlg = true
			},
			move(e) {
				if (Math.abs(e.touches[0].pageY) < 650 && Math.abs(e.touches[0].pageY) > 550) {
					this.btnStatus = 2
				} else if (Math.abs(e.touches[0].pageY) < 550) {
					this.btnStatus = 3

				} else {
					this.btnStatus = 1
				}
			},
			end() {

				clearInterval(this.timer)
				this.btnStatus = 0
				recorderManager.stop();
				console.log(this.voicePath, "888");
				// 异步,解决录音结束后,路径没赋值就传值,导致的路径为空
				setTimeout(() => {
					let obj = {
						status: false,
						path: [{
							src: this.voicePath,
							switchStatus: false,
							soundTime: this.num
						}]
					}
					this.$emit("emitCheck", obj)
					this.num = 0
				}, 500)

				console.log("手指松开", this.voicePath);
			},
			// play(value){
			// 	console.log("播放");
			// 	// innerAudioContext.src = value;
			// 	innerAudioContext.play();
			// },
			// 删除本地录音文件
			// del(){
			// 	uni.getSavedFileList({
			// 	  success: function (res) {
			// 	    if (res.fileList.length > 0) {
			// 	      uni.removeSavedFile({
			// 	        filePath: res.fileList[0].filePath,
			// 	        complete: function (res) {
			// 	          console.log(res);
			// 	        }
			// 	      });
			// 	    }
			// 	  }
			// 	});
			// }
		}
	}
</script>
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
  • 25
  • 26
  • 27
  • 28
  • 29
  • 30
  • 31
  • 32
  • 33
  • 34
  • 35
  • 36
  • 37
  • 38
  • 39
  • 40
  • 41
  • 42
  • 43
  • 44
  • 45
  • 46
  • 47
  • 48
  • 49
  • 50
  • 51
  • 52
  • 53
  • 54
  • 55
  • 56
  • 57
  • 58
  • 59
  • 60
  • 61
  • 62
  • 63
  • 64
  • 65
  • 66
  • 67
  • 68
  • 69
  • 70
  • 71
  • 72
  • 73
  • 74
  • 75
  • 76
  • 77
  • 78
  • 79
  • 80
  • 81
  • 82
  • 83
  • 84
  • 85
  • 86
  • 87
  • 88
  • 89
  • 90
  • 91
  • 92
  • 93
  • 94
  • 95
  • 96
  • 97
  • 98
  • 99
  • 100
  • 101
  • 102
  • 103
  • 104
  • 105
  • 106
  • 107
  • 108
  • 109
  • 110
  • 111
  • 112
  • 113
  • 114
  • 115
  • 116
  • 117
  • 118
  • 119
  • 120
  • 121
  • 122
  • 123
  • 124
  • 125
  • 126
  • 127
  • 128
  • 129
  • 130
  • 131
  • 132

css部分

<style lang="scss" scoped>
	@keyframes load {
		0% {
			height: 10%;
		}

		50% {
			height: 100%;
		}

		100% {
			height: 10%;
		}
	}

	// 取消发送
	.move_center_footer {
		margin-top: 20rpx;
		font-size: 24rpx;
		color: #666;
	}

	.move_center_top {
		height: 40rpx;
		width: 100%;
		display: flex;
		justify-content: center;
		align-items: center;

		.move_center_item {
			display: block;
			background: #333333;
			width: 1px;
			height: 10%;
			margin: 0 6rpx;
			float: left;
		}

		.move_center_item:nth-child(1) {
			animation: load 2.5s 1.4s infinite linear;
		}

		.move_center_item:nth-child(2) {
			animation: load 2.5s 1.2s infinite linear;
		}

		.move_center_item:nth-child(3) {
			animation: load 2.5s 1s infinite linear;
		}

		.move_center_item:nth-child(4) {
			animation: load 2.5s 0.8s infinite linear;
		}

		.move_center_item:nth-child(5) {
			animation: load 2.5s 0.6s infinite linear;
		}

		.move_center_item:nth-child(6) {
			animation: load 2.5s 0.4s infinite linear;
		}

		.move_center_item:nth-child(7) {
			animation: load 2.5s 0.2s infinite linear;
		}

		.move_center_item:nth-child(8) {
			animation: load 2.5s 0s infinite linear;
		}

		.move_center_item:nth-child(9) {
			animation: load 2.5s 0.2s infinite linear;
		}

		.move_center_item:nth-child(10) {
			animation: load 2.5s 0.4s infinite linear;
		}

		.move_center_item:nth-child(11) {
			animation: load 2.5s 0.6s infinite linear;
		}

		.move_center_item:nth-child(12) {
			animation: load 2.5s 0.8s infinite linear;
		}

		.move_center_item:nth-child(13) {
			animation: load 2.5s 1s infinite linear;
		}

		.move_center_item:nth-child(14) {
			animation: load 2.5s 1.2s infinite linear;
		}

		.move_center_item:nth-child(15) {
			animation: load 2.5s 1.4s infinite linear;
		}

	}

	.box {

		.popup_box {
			height: 100vh;
			width: 100vw;
			position: relative;

			// 取消录音区域
			.move {
				width: 100%;
				position: absolute;
				left: 0;
				bottom: 450rpx;
				display: flex;
				justify-content: center;
				align-items: center;

				.move_center_clear {
					width: 40%;
					height: 200rpx;
					border-radius: 50rpx;
					display: flex;
					justify-content: center;
					align-items: center;
					flex-direction: column;
					background: rgba(250, 83, 83, .5);
				}

				.move_center {
					width: 40%;
					height: 200rpx;
					background: rgba(149, 234, 108, .5);
					border-radius: 50rpx;
					display: flex;
					justify-content: center;
					align-items: center;
					flex-direction: column;
				}
			}

			// 底部按钮
			.footerBtn {
				padding: 20rpx 20rpx;
				width: 100%;
				position: absolute;
				left: 0;
				bottom: 60rpx;

				.footerBtn_chr {
					width: 100%;
					height: 96rpx;
					display: flex;
					justify-content: center;
					align-items: center;
					font-size: 28rpx;
					border-radius: 16rpx;
					background-image: linear-gradient(to right, #dfbe9b 0%, #f3dfc9 100%);
					color: #986546;
					transition: all 0.3s;
				}
			}

			.footerBtn_star {
				width: 100%;
				position: absolute;
				left: 0;
				bottom: 0rpx;

				.footerBtn_chr {
					width: 100%;
					height: 250rpx;
					display: flex;
					justify-content: center;
					align-items: center;
					font-size: 28rpx;
					border-radius: 140rpx 140rpx 0 0;
					background: rgba(218, 227, 232, .8);
					color: #666;
					transition: all 0.3s;
				}
			}

			.footerBtn_move {
				width: 100%;
				position: absolute;
				left: 0;
				bottom: 0rpx;

				.footerBtn_chr {
					width: 100%;
					height: 250rpx;
					display: flex;
					justify-content: center;
					align-items: center;
					font-size: 28rpx;
					border-radius: 140rpx 140rpx 0 0;
					background: rgba(51, 51, 51, .5);
					color: #dae3e8;
					transition: all 0.3s;
				}
			}
		}
	}
</style>
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
  • 25
  • 26
  • 27
  • 28
  • 29
  • 30
  • 31
  • 32
  • 33
  • 34
  • 35
  • 36
  • 37
  • 38
  • 39
  • 40
  • 41
  • 42
  • 43
  • 44
  • 45
  • 46
  • 47
  • 48
  • 49
  • 50
  • 51
  • 52
  • 53
  • 54
  • 55
  • 56
  • 57
  • 58
  • 59
  • 60
  • 61
  • 62
  • 63
  • 64
  • 65
  • 66
  • 67
  • 68
  • 69
  • 70
  • 71
  • 72
  • 73
  • 74
  • 75
  • 76
  • 77
  • 78
  • 79
  • 80
  • 81
  • 82
  • 83
  • 84
  • 85
  • 86
  • 87
  • 88
  • 89
  • 90
  • 91
  • 92
  • 93
  • 94
  • 95
  • 96
  • 97
  • 98
  • 99
  • 100
  • 101
  • 102
  • 103
  • 104
  • 105
  • 106
  • 107
  • 108
  • 109
  • 110
  • 111
  • 112
  • 113
  • 114
  • 115
  • 116
  • 117
  • 118
  • 119
  • 120
  • 121
  • 122
  • 123
  • 124
  • 125
  • 126
  • 127
  • 128
  • 129
  • 130
  • 131
  • 132
  • 133
  • 134
  • 135
  • 136
  • 137
  • 138
  • 139
  • 140
  • 141
  • 142
  • 143
  • 144
  • 145
  • 146
  • 147
  • 148
  • 149
  • 150
  • 151
  • 152
  • 153
  • 154
  • 155
  • 156
  • 157
  • 158
  • 159
  • 160
  • 161
  • 162
  • 163
  • 164
  • 165
  • 166
  • 167
  • 168
  • 169
  • 170
  • 171
  • 172
  • 173
  • 174
  • 175
  • 176
  • 177
  • 178
  • 179
  • 180
  • 181
  • 182
  • 183
  • 184
  • 185
  • 186
  • 187
  • 188
  • 189
  • 190
  • 191
  • 192
  • 193
  • 194
  • 195
  • 196
  • 197
  • 198
  • 199
  • 200
  • 201
  • 202
  • 203
  • 204

使用

<!-- maskShow决定遮罩层是否显示 / @emitCheck自定义事件,用来接收组件返回值 -->
		<sound :maskShow="footerList[1].status" @emitCheck="footerCheck"></sound>
  • 1
  • 2

借鉴

本来找的是另一个博主的代码样式,但是发现他的代码会导致ios微信小程序死机,研究一下午没解决,索性仿着写了一个,那个博主的文章地址

声明:本文内容由网友自发贡献,不代表【wpsshop博客】立场,版权归原作者所有,本站不承担相应法律责任。如您发现有侵权的内容,请联系我们。转载请注明出处:https://www.wpsshop.cn/w/花生_TL007/article/detail/565545
推荐阅读
相关标签
  

闽ICP备14008679号