You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
 
 
 
 

278 lines
6.7 KiB

<template>
<view class="audio-warp" @click="handleBtnClick">
<view class="cover-warp" :class="{ hasbg: !poster }">
<image :src="poster" v-if="poster" class="cover-img"></image>
<view class="play-btn" :class="{ pause: play }"></view>
</view>
<view class="audio-con">
<view class="info">
<text class="audio-title am-text-eill">{{ name }}</text>
<!-- <text class="audio-author am-text-eill">{{ author }}</text> -->
<text class="audio-author am-text-eill">{{ audioTimeUpdate }}</text>
<slider class="audio-slider" activeColor="#fae68f" block-size="12" block-color="#c0947d" :value="current" :max="duration" @changing="changing" @change="change"></slider>
</view>
<!-- <view class="audio-time">{{ audioTimeUpdate }}</view> -->
</view>
</view>
</template>
<script>
/**
* luch-audio 0.0.1
* @module luch-audio
* @Author lu-ch
* @Date 2019-06-11
* @Email webwork.s@qq.com
* @description 音频播放组件,使用了createInnerAudioContext
*/
/**
* Props itemsProps
* @prop {Boolean} play - 是否播放,双向绑定,绑定时需使用.sync 如果为true 则播放,为false 则暂停
* ... 其他api同文档 (https://uniapp.dcloud.io/api/media/audio-context?id=createinneraudiocontext)
*/
/**
* 将秒转换为 分:秒
* @param {Number} s - 秒数
*/
function sToHs(s) {
//计算分钟
//算法:将秒数除以60,然后下舍入,既得到分钟数
let h;
h = Math.floor(s / 60);
//计算秒
//算法:取得秒%60的余数,既得到秒数
s = s % 60;
//将变量转换为字符串
h += '';
s += '';
//如果只有一位数,前面增加一个0
h = (h.length === 1) ? '0' + h : h;
s = (s.length === 1) ? '0' + s : s;
return h + ':' + s;
}
export default {
name: 'ComAudio',
props: {
play: {
type: Boolean,
required: true
},
src: {
type: String
},
poster: {
type: String,
default: ''
},
name: {
type: String,
default: '未知音频'
},
author: {
type: String,
default: '本站编辑'
},
autoplay: {
type: Boolean,
default: false
},
loop: {
type: Boolean,
default: false
},
obeyMuteSwitch: {
type: Boolean,
default: true
}
},
data() {
return {
audioTimeUpdate: '00:00',
innerAudioContext: '',
currentTime: '', //当前播放时间
durationTime: '', //总时长
duration: '',
current: '', //slider当前进度
loading: false, //是否处于读取状态
paused: true, //是否处于暂停状态
seek: false //是否处于拖动状态
};
},
methods: {
//格式化时长
format(num) {
return '0'.repeat(2 - String(Math.floor(num / 60)).length) + Math.floor(num / 60) + ':' + '0'.repeat(2 - String(
Math.floor(num % 60)).length) + Math.floor(num % 60)
},
changing(e) {
this.seek = false;
this.current = e.detail.value;
//this.innerAudioContext.pause();
this.$emit('update:play', false);
},
//完成拖动事件
change(e) {
this.current = e.detail.value;
this.innerAudioContext.seek(this.current);
console.log(this.current);
//this.innerAudioContext.play();
this.$emit('update:play', true);
// this.audioTimeUpdate = sToHs(Math.floor(this.innerAudioContext.duration-this.innerAudioContext.currentTime));
this.audioTimeUpdate = sToHs(Math.floor(this.innerAudioContext.currentTime));
},
audioPlay() {
this.$emit('update:play', true);
},
audioPause() {
this.$emit('update:play', false);
},
handleBtnClick() {
// this.$emit('update:play', !this.play);
this.$emit('change', !this.play);
},
contextInit() {
// console.log('创建');
let that = this;
that.$emit('update:play', false);
let innerAudioContext = uni.createInnerAudioContext();
innerAudioContext.autoplay = that.autoplay;
innerAudioContext.src = that.src;
innerAudioContext.loop = that.loop;
innerAudioContext.obeyMuteSwitch = that.obeyMuteSwitch;
that.current = 0
innerAudioContext.onPlay(function() {
// that.audioTimeUpdate = sToHs(Math.floor(innerAudioContext.duration-innerAudioContext.currentTime));
that.audioTimeUpdate = sToHs(Math.floor(innerAudioContext.currentTime));
that.durationTime = sToHs(Math.floor(innerAudioContext.duration));
that.audioPlay();
});
innerAudioContext.onPause(function() {
that.audioPause();
});
innerAudioContext.onEnded(function() {
that.audioPause();
});
innerAudioContext.onTimeUpdate(function() {
// that.audioTimeUpdate = sToHs(Math.floor(innerAudioContext.duration-innerAudioContext.currentTime));
that.audioTimeUpdate = sToHs(Math.floor(innerAudioContext.currentTime));
that.duration = innerAudioContext.duration;
that.durationTime = sToHs(Math.floor(innerAudioContext.duration));
if (!that.seek) {
that.current = innerAudioContext.currentTime;
}
});
innerAudioContext.onError(err => {
// console.log(err);
});
this.innerAudioContext = innerAudioContext;
}
},
watch: {
play(n) {
if (n) {
this.innerAudioContext.play();
} else {
this.innerAudioContext.pause();
}
this.$forceUpdate();
},
src() {
this.innerAudioContext.destroy();
this.contextInit();
}
},
created() {
this.contextInit();
},
beforeDestroy() {
this.innerAudioContext.destroy();
}
};
</script>
<style lang="scss">
.am-text-eill {
/*超出省略号*/
overflow: hidden;
text-overflow: ellipsis;
white-space: nowrap;
}
.audio-warp {
display: flex;
overflow: hidden;
height: 134upx;
border-radius: 10upx;
padding: 18upx 0 0 50upx;
background-color: rgba(255, 255, 255, 1);
}
.cover-warp {
position: relative;
flex-shrink: 0;
width: 130upx;
height: 100%;
&.hasbg {
background-color: #e6e6e6;
}
.cover-img {
width: 100%;
height: 100%;
display: none;
}
.play-btn {
position: absolute;
left: 50%;
top: 50%;
width: 80upx;
height: 80upx;
transform: translateX(-50%) translateY(-50%);
border-radius: 50%;
background-size: 100% 100%;
background-image: url('http://ys.tour-ma.com/r/cms/www/m/yushan/icon-nj-ztyy.png');
&.pause {
background-image: url('http://ys.tour-ma.com/r/cms/www/m/yushan/icon-nj-bfyy.png');
}
}
}
.audio-con {
position: relative;
flex: 1;
display: flex;
width: 0;
padding: 0 30upx;
align-items: center;
// background-color: #fcfcfc;
.info {
width: 100%;
}
.audio-title {
display: block;
padding-bottom: 14upx;
// padding-right: 50upx;
font-size: 35upx;
color: #000;
font-weight: 600;
}
.audio-author {
display: inline-block;
font-size: 24upx;
color: #888888;
width: 15%;
vertical-align: middle;
}
.audio-slider{
display: inline-block;
width: 74%;
vertical-align: middle;
margin: 0;
padding: 0 10px;
}
.audio-time {
position: absolute;
right: 30upx;
top: 12upx;
font-size: 26upx;
color: #9d9d9d;
}
}
</style>