zy-vue-library/components/ali-player/index.vue

153 lines
3.7 KiB
Vue

<template>
<div :id="className" :style="{ width, height }" />
</template>
<script setup>
import { nextTick, onBeforeUnmount, onMounted, ref, watch } from "vue";
import { useDocumentVisibility } from "@vueuse/core";
import { uniqueId } from "lodash-es";
let player = null;
defineOptions({
name: "AppAliPlayer",
});
const props = defineProps({
source: { type: [String, Array], default: "" },
vid: { type: String, default: "" },
playAuth: { type: String, default: "" },
cover: { type: String, default: "" },
width: { type: String, default: "100%" },
height: { type: String, default: "600px" },
visible: { type: Boolean, default: false },
autoplay: { type: Boolean, default: true },
showProgress: { type: Boolean, default: true },
isLive: { type: Boolean, default: false },
playTime: { type: Number, default: 0 },
});
const emits = defineEmits(["ended", "timeupdate"]);
const visibility = useDocumentVisibility();
const className = ref(uniqueId("_"));
onMounted(() => {
watch(
[() => props.source, () => props.vid, () => props.playAuth],
() => {
if (props.source || (props.vid && props.playAuth)) fnCreateAliPlayer();
},
{
immediate: true,
}
);
watch(
() => visibility.value,
() => {
if (visibility.value === "hidden") {
props.visible && pause();
} else {
props.visible && play();
}
},
{
immediate: true,
}
);
});
const fnCreateAliPlayer = async () => {
await nextTick();
fnDisposeAliPlayer();
const skinLayout = [
{ name: "bigPlayButton", align: "blabs", x: 30, y: 80 },
{ name: "H5Loading", align: "cc" },
{ name: "errorDisplay", align: "tlabs", x: 0, y: 0 },
{ name: "infoDisplay" },
{ name: "tooltip", align: "blabs", x: 0, y: 56 },
{ name: "thumbnail" },
{
name: "controlBar",
align: "blabs",
x: 0,
y: 0,
children: [
{ name: "playButton", align: "tl", x: 15, y: 12 },
{ name: "timeDisplay", align: "tl", x: 10, y: 7 },
{ name: "fullScreenButton", align: "tr", x: 10, y: 12 },
{ name: "setting", align: "tr", x: 15, y: 12 },
{ name: "volume", align: "tr", x: 5, y: 10 },
],
},
];
props.showProgress &&
skinLayout.at(-1).children.unshift({
name: "progress",
align: "blabs",
x: 0,
y: 44,
});
player = new window.Aliplayer(
{
id: className.value,
...(props.source
? { source: props.source }
: {
vid: props.vid,
playauth: props.playAuth,
qualitySort: "asc",
format: "m3u8",
encryptType: 1,
mediaType: "video",
isLive: true,
rePlay: false,
playsinline: true,
controlBarVisibility: "hover",
}),
cover: props.cover,
width: props.width,
height: props.height,
autoplay: props.autoplay,
isLive: props.isLive,
useH5Prism: true,
skinLayout,
},
(player) => {
props.autoplay && player.play();
player.on("ended", fnPlayerEnded);
player.on("timeupdate", fnPlayTimeUpdate);
player.seek(props.playTime);
}
);
};
const fnPlayerEnded = () => {
emits("ended");
};
const fnPlayTimeUpdate = () => {
emits("timeupdate", player.getCurrentTime());
};
const fnDisposeAliPlayer = () => {
if (!player) return;
player.dispose();
player = null;
};
onBeforeUnmount(() => {
fnDisposeAliPlayer();
});
const play = () => {
player && player.play();
};
const pause = () => {
player && player.pause();
};
defineExpose({
play,
pause,
});
</script>
<style scoped lang="scss">
:deep {
.prism-setting-speed,
.prism-setting-cc,
.prism-setting-audio {
display: none;
}
}
</style>