| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172 |
- <template>
- <div class="software-intro-container">
- <!-- 加载状态 -->
- <div v-if="isLoading" class="loading-message">加载中...</div>
- <!-- 错误信息 -->
- <div v-else-if="error" class="error-message">{{ error }}</div>
- <!-- 正常展示内容 -->
- <div v-else class="content-wrapper">
- <h1 class="title">{{ softwareIntro.title }}</h1>
- <div v-for="(paragraph, index) in softwareIntro.introParagraphs" :key="index" class="paragraph">
- <p v-html="paragraph"></p>
- </div>
- </div>
- </div>
- </template>
- <script setup lang="ts">
- import { ref, onMounted } from 'vue';
- import { api5000 } from '@/utils/request'; // 导入封装的api5000
- // 定义 targetId 为 prop
- const props = defineProps({
- targetId: {
- type: Number,
- default: 1
- }
- });
- // 存储介绍内容
- const softwareIntro = ref({
- title: '',
- introParagraphs: []
- });
- // 加载状态
- const isLoading = ref(true);
- // 错误信息
- const error = ref('');
- // 判断是否为标题段落
- // 处理段落,将图片路径转换为 标签
- onMounted(async () => {
- try {
- // 使用 api5000 调用接口
- const response = await api5000.get(`/admin/software-intro/${props.targetId}`);
- const { title, intro } = response.data;
- // 保留 \r\n 换行符
- const processedIntro = intro.replace(/<p>/g, '').replace(/<\/p>/g, '\r\n').replace(/<br>/g, '');
- softwareIntro.value.introParagraphs = processedIntro.split('\r\n').filter((paragraph: string) => paragraph.trim()!== '');
- softwareIntro.value.title = title;
- } catch (err: any) {
- error.value = err.message || '请求数据时发生错误';
- } finally {
- isLoading.value = false;
- }
- // 页面加载完成后,监听视频播放事件
- const container = document.querySelector('.software-intro-container');
- if (container) {
- container.addEventListener('play', (event) => {
- if (event.target instanceof HTMLVideoElement) {
- const video = event.target;
- setVideoStyle(video);
- }
- }, true);
- // 监听窗口大小变化事件,确保视频在窗口大小改变时也能适应
- window.addEventListener('resize', () => {
- const videos = container.querySelectorAll('video');
- videos.forEach((video) => {
- if (video instanceof HTMLVideoElement) {
- setVideoStyle(video);
- }
- });
- });
- }
- });
- // 封装设置视频样式的函数
- const setVideoStyle = (video: HTMLVideoElement) => {
- const containerWidth = (document.querySelector('.software-intro-container') as HTMLElement).offsetWidth;
- const maxWidth = containerWidth * 0.8; // 最大宽度为容器宽度的 80%
- if (video.videoWidth > maxWidth) {
- video.style.width = `${maxWidth}px`;
- video.style.height = 'auto';
- } else {
- video.style.width = 'auto';
- video.style.height = 'auto';
- }
- video.style.maxWidth = '80%';
- video.style.objectFit = 'contain';
- };
- </script>
- <style scoped lang="scss">
- .software-intro-container {
- width: 95%;
- margin: 0 auto;
- padding: 20px;
- background-color: #fff;
- border-radius: 8px; /* 圆角 */
- box-shadow: 0 4px 8px rgba(0, 0, 0, 0.1); /* 阴影 */
- height: 80vh; /* 设置容器高度为视口高度的 80% */
- overflow-y: auto; /* 当内容超出容器高度时,显示垂直滚动条 */
- scrollbar-width: none; /* Firefox */
- -ms-overflow-style: none; /* Internet Explorer 10+ */
- }
- .loading-message {
- text-align: center;
- font-size: 18px;
- color: #999;
- padding: 20px;
- }
- .error-message {
- text-align: center;
- font-size: 18px;
- color: #ff0000; /* 红色错误信息 */
- padding: 20px;
- }
- .title {
- font-size: 36px;
- text-align: center;
- margin-bottom: 20px;
- color: #333; /* 深灰色标题 */
- }
- .paragraph {
- margin-bottom: 20px;
- }
- p {
- font-size: 16px;
- line-height: 1.8; /* 增大行高 */
- color: #666; /* 灰色文字 */
- }
- .intro-image {
- max-width: 100%;
- height: auto;
- border-radius: 4px; /* 图片圆角 */
- box-shadow: 0 2px 4px rgba(0, 0, 0, 0.1); /* 图片阴影 */
- margin-bottom: 10px;
- }
- /* 控制视频尺寸 */
- video {
- width: 80%;
- max-width: 80%;
- height: auto;
- object-fit: contain;
- }
- /* 响应式设计 */
- @media (max-width: 768px) {
- .software-intro-container {
- padding: 15px;
- height: 90vh; /* 在小屏幕上,调整容器高度为视口高度的 90% */
- }
- .title {
- font-size: 28px;
- }
- p {
- font-size: 14px;
- }
- }
- </style>
|