首屏添加视频播放
This commit is contained in:
@@ -0,0 +1,108 @@
|
|||||||
|
<template>
|
||||||
|
<transition name="video-fade">
|
||||||
|
<div v-if="isVisible" id="videoComponent">
|
||||||
|
<video
|
||||||
|
ref="videoRef"
|
||||||
|
class="video"
|
||||||
|
:src="src"
|
||||||
|
muted
|
||||||
|
autoplay
|
||||||
|
preload="auto"
|
||||||
|
playsinline
|
||||||
|
:controls="false"
|
||||||
|
@ended="handleEnded"
|
||||||
|
@error="handleError"
|
||||||
|
></video>
|
||||||
|
</div>
|
||||||
|
</transition>
|
||||||
|
</template>
|
||||||
|
|
||||||
|
<script setup lang="ts">
|
||||||
|
import { ref, onMounted, onUnmounted } from 'vue';
|
||||||
|
|
||||||
|
interface Props {
|
||||||
|
src: string;
|
||||||
|
}
|
||||||
|
|
||||||
|
defineProps<Props>();
|
||||||
|
const emit = defineEmits<{
|
||||||
|
(e: 'complete'): void;
|
||||||
|
}>();
|
||||||
|
|
||||||
|
const videoRef = ref<HTMLVideoElement | null>(null);
|
||||||
|
const isVisible = ref<boolean>(true);
|
||||||
|
|
||||||
|
// 视频结束处理
|
||||||
|
const handleEnded = (): void => {
|
||||||
|
isVisible.value = false;
|
||||||
|
// 延迟发射完成事件,等待淡出动画结束(800ms)
|
||||||
|
setTimeout(() => {
|
||||||
|
emit('complete');
|
||||||
|
}, 800);
|
||||||
|
};
|
||||||
|
|
||||||
|
// 异常处理:大屏如果视频加载失败,直接隐藏,避免遮挡看板
|
||||||
|
const handleError = (): void => {
|
||||||
|
console.error('视频资源加载失败');
|
||||||
|
isVisible.value = false;
|
||||||
|
emit('complete');
|
||||||
|
};
|
||||||
|
|
||||||
|
onMounted(() => {
|
||||||
|
if (videoRef.value) {
|
||||||
|
// 显式静音
|
||||||
|
videoRef.value.muted = true;
|
||||||
|
// 尝试播放
|
||||||
|
const playPromise = videoRef.value.play();
|
||||||
|
if (playPromise !== undefined) {
|
||||||
|
playPromise.catch((error) => {
|
||||||
|
console.warn('自动播放尝试失败,请检查视频源:', error);
|
||||||
|
// 如果依然无法播放,直接销毁遮罩
|
||||||
|
isVisible.value = false;
|
||||||
|
});
|
||||||
|
}
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
onUnmounted(() => {
|
||||||
|
// 组件卸载时确保释放资源
|
||||||
|
if (videoRef.value) {
|
||||||
|
videoRef.value.pause();
|
||||||
|
videoRef.value.src = '';
|
||||||
|
videoRef.value.load();
|
||||||
|
}
|
||||||
|
});
|
||||||
|
</script>
|
||||||
|
|
||||||
|
<style scoped lang="less">
|
||||||
|
#videoComponent {
|
||||||
|
position: fixed;
|
||||||
|
left: 0;
|
||||||
|
right: 0;
|
||||||
|
top: 0;
|
||||||
|
bottom: 0;
|
||||||
|
width: 100vw;
|
||||||
|
height: 100vh;
|
||||||
|
overflow: hidden;
|
||||||
|
pointer-events: none;
|
||||||
|
z-index: 99999;
|
||||||
|
background-color: #000;
|
||||||
|
|
||||||
|
.video {
|
||||||
|
width: 100%;
|
||||||
|
height: 100%;
|
||||||
|
/* 关键:确保大屏视频拉伸填充,不留黑边 */
|
||||||
|
object-fit: cover;
|
||||||
|
/* 某些超宽大屏可能需要 fill,视具体视频比例而定 */
|
||||||
|
/* object-fit: fill; */
|
||||||
|
}
|
||||||
|
|
||||||
|
/* 淡出动画 */
|
||||||
|
.video-fade-leave-active {
|
||||||
|
transition: opacity 0.8s ease-in-out;
|
||||||
|
}
|
||||||
|
.video-fade-leave-to {
|
||||||
|
opacity: 0;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
</style>
|
||||||
@@ -33,10 +33,13 @@
|
|||||||
<a-spin size="large" />
|
<a-spin size="large" />
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
|
<VideoComponent :src="videoUrl" />
|
||||||
</div>
|
</div>
|
||||||
</template>
|
</template>
|
||||||
<script setup lang="ts">
|
<script setup lang="ts">
|
||||||
import LoginOutButton from '/@/views/components/loginOutButton.vue';
|
import LoginOutButton from '/@/views/components/loginOutButton.vue';
|
||||||
|
import VideoComponent from '/@/views/components/videoComponent.vue';
|
||||||
import { useUserStore } from '/@/store/modules/user.ts';
|
import { useUserStore } from '/@/store/modules/user.ts';
|
||||||
import { onMounted, ref, watch } from 'vue';
|
import { onMounted, ref, watch } from 'vue';
|
||||||
import dayjs from 'dayjs';
|
import dayjs from 'dayjs';
|
||||||
@@ -86,6 +89,9 @@
|
|||||||
document.title = centerInfo.screenTitle || '健康服务中心';
|
document.title = centerInfo.screenTitle || '健康服务中心';
|
||||||
});
|
});
|
||||||
|
|
||||||
|
// 定义网络视频地址
|
||||||
|
const videoUrl = 'https://api-xj.tri.icdat.cn/file/show/temp/20251229/20251229_1766980290812.mp4';
|
||||||
|
|
||||||
const getTime = () => {
|
const getTime = () => {
|
||||||
dateInfo.value = {
|
dateInfo.value = {
|
||||||
day: dayjs().format('YYYY年MM月DD日'),
|
day: dayjs().format('YYYY年MM月DD日'),
|
||||||
|
|||||||
@@ -170,6 +170,21 @@
|
|||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
const requestFull = () => {
|
||||||
|
const docElm = document.documentElement as any;
|
||||||
|
const requestMethod =
|
||||||
|
docElm.requestFullscreen ||
|
||||||
|
docElm.mozRequestFullScreen ||
|
||||||
|
docElm.webkitRequestFullScreen ||
|
||||||
|
docElm.msRequestFullscreen;
|
||||||
|
|
||||||
|
if (requestMethod) {
|
||||||
|
// 返回 promise 以便捕获可能的拒绝
|
||||||
|
return requestMethod.call(docElm);
|
||||||
|
}
|
||||||
|
return Promise.reject('浏览器不支持全屏API');
|
||||||
|
};
|
||||||
|
|
||||||
async function accountLogin() {
|
async function accountLogin() {
|
||||||
if (!checkFormField(formData, 'username', 'login.accountPlaceholder')) return;
|
if (!checkFormField(formData, 'username', 'login.accountPlaceholder')) return;
|
||||||
if (!checkFormField(formData, 'password', 'login.passwordPlaceholder')) return;
|
if (!checkFormField(formData, 'password', 'login.passwordPlaceholder')) return;
|
||||||
@@ -213,6 +228,13 @@
|
|||||||
}
|
}
|
||||||
goPath = PageEnum.BASE_HOME;
|
goPath = PageEnum.BASE_HOME;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
try {
|
||||||
|
await requestFull();
|
||||||
|
} catch (screenError) {
|
||||||
|
console.warn('自动进入全屏失败,请手动按 F11:', screenError);
|
||||||
|
}
|
||||||
|
|
||||||
notification.success({
|
notification.success({
|
||||||
message: t('login.loginSuccessTitle'),
|
message: t('login.loginSuccessTitle'),
|
||||||
description: `${t('login.loginSuccessDesc')}: ${userInfo.realname}`,
|
description: `${t('login.loginSuccessDesc')}: ${userInfo.realname}`,
|
||||||
|
|||||||
Reference in New Issue
Block a user