test carousel

This commit is contained in:
mubai
2024-02-21 23:44:54 +08:00
parent 53a243a4fb
commit 93b9855f52
16 changed files with 807 additions and 492 deletions

View File

@@ -13,6 +13,8 @@ declare module '@vue/runtime-core' {
ElAside: typeof import('element-plus/es')['ElAside']
ElAvatar: typeof import('element-plus/es')['ElAvatar']
ElButton: typeof import('element-plus/es')['ElButton']
ElCarousel: typeof import('element-plus/es')['ElCarousel']
ElCarouselItem: typeof import('element-plus/es')['ElCarouselItem']
ElCol: typeof import('element-plus/es')['ElCol']
ElCollapseTransition: typeof import('element-plus/es')['ElCollapseTransition']
ElConfigProvider: typeof import('element-plus/es')['ElConfigProvider']

Binary file not shown.

View File

@@ -1,6 +1,7 @@
<template>
<div class="c_content" v-if="true">
<div class="item" v-for="item in d.list" :style="{width: `calc(${d.width-1}%)`}">
<div class="c_content" v-if="d.list" >
<template v-if="d.list.length > 0">
<div class="item" v-for="item in d.list" :style="{width: `calc(${d.width-1}%)`}">
<div v-if="item.id != -99">
<a :href="`/filmDetail?link=${item.id}`" class="default_image link_content">
<div class="tag_group">
@@ -14,7 +15,9 @@
<a :href="`/filmDetail?link=${item.id}`" class="content_text_tag">{{ item.name.split("[")[0] }}</a>
<span class="cus_remark hidden-md-and-down">{{ item.remarks }}</span>
</div>
</div>
</div>
</template>
<el-empty v-if="d.list.length <= 0" style="padding: 10px 0;margin: 0 auto" description="暂无相关数据"/>
</div>
</template>
@@ -37,18 +40,18 @@ const handleImg = (e: Event) => {
}
// 监听父组件传递的参数的变化
watchEffect(()=>{
watchEffect(() => {
// 首先获取当前设备类型
const userAgent = navigator.userAgent.toLowerCase();
let isMobile = /mobile|android|iphone|ipad|phone/i.test(userAgent)
// 如果是PC, 为防止flex布局最后一行元素不足出现错位, 使用空元素补齐list
let c = isMobile ? 3 : props.col? props.col: 0
let l:any= props.list
let c = isMobile ? 3 : props.col ? props.col : 0
let l: any = props.list
let len = l.length
d.width = isMobile ? 31 : Math.floor(100 / c)
if (len % c !=0) {
for (let i = 0; i < c - len %c ; i++) {
let temp:any = {...l[0] as any}
if (len % c != 0) {
for (let i = 0; i < c - len % c; i++) {
let temp: any = {...l[0] as any}
temp.id = -99
l.push(temp)
}
@@ -57,7 +60,6 @@ watchEffect(()=>{
})
</script>
<style scoped>
@@ -66,6 +68,18 @@ watchEffect(()=>{
background-size: cover;
}
:deep(.el-empty) {
--el-empty-fill-color-1: rgba(155, 73, 231, 0.72);
--el-empty-fill-color-2: #67d9e891;
--el-empty-fill-color-3: rgb(106 19 187 / 72%);
--el-empty-fill-color-4: #67d9e8;
--el-empty-fill-color-5: #5abcc9;
--el-empty-fill-color-6: #9fb2d9;
--el-empty-fill-color-7: #61989f;
--el-empty-fill-color-8: #697dc5;
--el-empty-fill-color-9: rgb(43 51 63 / 44%);
}
/*wrap*/
@media (max-width: 768px) {
/*展示区域*/
@@ -77,8 +91,8 @@ watchEffect(()=>{
}
.c_content .item {
/* flex-basis: calc(33% - 7px);
max-width: 33%;*/
/* flex-basis: calc(33% - 7px);
max-width: 33%;*/
margin: 0 4px 20px 4px;
box-sizing: border-box;
overflow: hidden;

View File

@@ -13,10 +13,12 @@
</div>
<!--右侧顶级分类导航 -->
<div class="nav_right">
<a href="/">首页</a>
<template v-for="n in data.nav">
<a :href="`/filmClassify?Pid=${n.id}`">{{ n.name }}</a>
</template>
<div class="nav_link">
<a href="/">首页</a>
<template v-for="n in data.nav">
<a :href="`/filmClassify?Pid=${n.id}`">{{ n.name }}</a>
</template>
</div>
<div class="history-link hidden-md-and-down" v-on:mouseenter="handleHistory(true)"
v-on:mouseleave="handleHistory(false)">
<a :href="`/filmClassify?Pid=${nav.variety.id}`">
@@ -137,19 +139,31 @@ onMounted(() => {
@media (max-width: 768px) {
.nav_right {
display: flex;
width: 100%;
justify-content: space-between;
/*display: none!important;*/
height: 40px;
}
.nav_right a {
.nav_link {
display: flex;
justify-content: space-between;
height: 40px;
width: 90%;
overflow-y: scroll;
}
.nav_link a {
white-space: nowrap;
color: #ffffff;
flex-basis: calc(19% - 5px);
padding: 0 10px;
line-height: 40px;
/*border-radius: 5px;*/
/*border: 1px solid rebeccapurple;*/
}
.nav_right .hidden-md-and-up {
color: #ffffff;
flex-basis: calc(19% - 5px);
padding: 0 10px;
line-height: 40px;
}
.nav_right a:hover {
color: #ffffff;
@@ -245,7 +259,7 @@ onMounted(() => {
flex-direction: row;
}
.nav_right > a {
.nav_right a {
min-width: 60px;
height: 40px;
line-height: 40px;

View File

@@ -1,15 +1,15 @@
<template>
<el-container>
<el-header>
<Header/>
</el-header>
<el-main>
<router-view></router-view>
</el-main>
<el-footer>
<Footer/>
</el-footer>
</el-container>
<el-container>
<el-header>
<Header/>
</el-header>
<el-main>
<router-view></router-view>
</el-main>
<el-footer>
<Footer/>
</el-footer>
</el-container>
</template>
<script setup lang="ts">
@@ -21,45 +21,46 @@ import Footer from "../components/index/Footer.vue";
<style scoped>
:deep(.el-main) {
padding-top: 70px !important;
padding-bottom: 30px !important;
min-height: 85vh;
padding-top: 70px !important;
padding-bottom: 30px !important;
min-height: 85vh;
}
:deep(.el-header) {
padding: 0 !important;
position: fixed !important;
width: 100% !important;
min-height: 60px;
transform: translateZ(0);
z-index: 1000;
background-color: rgba(0, 0, 0, 0.85);
top: 0;
padding: 0 !important;
position: fixed !important;
width: 100% !important;
min-height: 60px;
transform: translateZ(0);
z-index: 1000;
background-color: rgba(0, 0, 0, 0.85);
top: 0;
}
@media (min-width: 768px) {
.el-main {
margin: 0 auto;
padding: 100px 0;
/*padding-top: 100px!important;*/
}
.el-main {
margin: 0 auto;
padding: 100px 0;
/*padding-top: 100px!important;*/
}
}
@media (max-width: 768px) {
.el-main {
/*margin: 0 auto;*/
padding: 55px 0!important;
/*padding-top: 100px!important;*/
}
:deep(.el-header) {
height: 40px!important;
min-height: 40px!important;
}
.el-main {
/*margin: 0 auto;*/
padding: 55px 0 !important;
/*padding-top: 100px!important;*/
}
:deep(.el-header) {
height: 40px !important;
min-height: 40px !important;
}
}
:deep(.el-menu--horizontal) {
border-bottom: 1px solid rgb(46, 46, 46);
border-bottom: 1px solid rgb(46, 46, 46);
}
/*@media (min-width: 768px){ //>=768的设备 }*/
@@ -67,33 +68,35 @@ import Footer from "../components/index/Footer.vue";
/*@media (min-width: 1200){ //>=1200的设备 }*/
@media (min-width: 1024px) {
.el-main {
width: 1023px
}
.el-main {
width: 1023px
}
}
@media (min-width: 990px) {
.el-main {
width: 970px
}
.el-main {
width: 970px
}
}
@media (min-width: 1200px) {
.el-main {
width: 1180px
}
.el-main {
width: 1180px
}
}
@media (min-width: 1400px) {
.el-main {
width: 1400px
}
.el-main {
width: 1400px
}
}
@media (min-width: 1560px) {
.el-main {
width: 1500px
}
.el-main {
width: 1500px
}
}
</style>

View File

@@ -1,5 +1,5 @@
<template>
<div class="container" v-if="d.list.length >0">
<div class="container" v-if="d.title.name">
<div class="title">
<a :href="`/filmClassify?Pid=${d.title.id}`" >{{ d.title.name }}</a>
<span class="line"/>

View File

@@ -1,175 +1,263 @@
<template>
<div class="container">
<div class="content_item" v-for="item in data.info.content">
<template v-if="item.nav.show">
<el-row class="row-bg cus_nav" justify="space-between">
<el-col :span="12" class="title">
<span :class="`iconfont ${item.nav.name.search('电影') != -1?'icon-film':item.nav.name.search('剧') != -1?'icon-tv':item.nav.name.search('动漫')!= -1?'icon-cartoon':'icon-variety'}`"
style="color: #79bbff;font-size: 32px;margin-right: 10px; line-height: 130%"/>
<a :href="`/filmClassify?Pid=${item.nav.id}`">{{ item.nav.name }}</a>
</el-col>
<el-col :span="12">
<ul class="nav_ul">
<template v-for="c in item.nav.children">
<li class="nav_category hidden-md-and-down" v-if="c.show" ><a
:href="`/filmClassifySearch?Pid=${c.pid}&Category=${c.id}`">{{ c.name }}</a></li>
</template>
<li class="nav_category hidden-md-and-down"><a :href="`/filmClassify?Pid=${item.nav.id}`">更多 ></a></li>
</ul>
</el-col>
</el-row>
<el-row class="cus_content">
<el-col :md="24" :lg="20" :xl="20" class="cus_content">
<!--影片列表-->
<FilmList v-if="item.movies" :col="6" :list="item.movies.slice(0,12)"/>
</el-col>
<el-col :md="0" :lg="4" :xl="4" class="hidden-md-and-down content_right">
<h3 class="hot_title">🔥热播{{item.nav.name}}</h3>
<template v-for="(m,i) in item.hot.slice(0,12)">
<div class="content_right_item">
<a :href="`/filmDetail?link=${m.mid}`"><b class="top_item">{{ i + 1 + '.' }}</b>
<span>{{ m.name }}</span></a>
</div>
</template>
</el-col>
</el-row>
</template>
</div>
<div class="container">
<div class="hidden-sm-and-up banner_wrap" @touchstart="touchS" @touchend="touchE" >
<el-carousel v-model="data.banner.current" ref="wrap" :interval="3000" trigger="hover" height="200px" arrow="never" >
<el-carousel-item v-for="item in banners" :key="item" >
<el-image style="width: 100%; height: 100%;" :src="item.picture" fit="fill"/>
<p class="carousel-title">{{ item.name }}</p>
</el-carousel-item>
</el-carousel>
</div>
<div class="banner hidden-sm-and-down"
:style="{background:`url(${data.banner.current.picture})`, backgroundRepeat: 'no-repeat', backgroundSize: 'cover'}">
<div class="preview">
<el-carousel @change="carousel" :interval="3000" height="240px" arrow="always">
<el-carousel-item v-for="item in banners" :key="item">
<el-image style="width: 60%; height: 80%;border-radius: 5px;" :src="item.poster" fit="contain"/>
<div class="carousel-tags">
<span>{{ item.year }}</span>
<span>{{ item.cName }}</span>
</div>
<p class="carousel-title">{{ item.name }}</p>
</el-carousel-item>
</el-carousel>
</div>
</div>
<div class="content_item" v-for="item in data.info.content">
<template v-if="item.nav.show">
<el-row class="row-bg cus_nav" justify="space-between">
<el-col :span="12" class="title">
<span
:class="`iconfont ${item.nav.name.search('电影') != -1?'icon-film':item.nav.name.search('剧') != -1?'icon-tv':item.nav.name.search('动漫')!= -1?'icon-cartoon':'icon-variety'}`"
style="color: #79bbff;font-size: 32px;margin-right: 10px; line-height: 130%"/>
<a :href="`/filmClassify?Pid=${item.nav.id}`">{{ item.nav.name }}</a>
</el-col>
<el-col :span="12">
<ul class="nav_ul">
<template v-for="c in item.nav.children">
<li class="nav_category hidden-md-and-down" v-if="c.show"><a
:href="`/filmClassifySearch?Pid=${c.pid}&Category=${c.id}`">{{ c.name }}</a></li>
</template>
<li class="nav_category hidden-md-and-down"><a :href="`/filmClassify?Pid=${item.nav.id}`">更多 ></a></li>
</ul>
</el-col>
</el-row>
<el-row class="cus_content">
<el-col :md="24" :lg="20" :xl="20" class="cus_content">
<!--影片列表-->
<FilmList v-if="item.movies" :col="6" :list="item.movies.slice(0,12)"/>
</el-col>
<el-col :md="0" :lg="4" :xl="4" class="hidden-md-and-down content_right">
<h3 class="hot_title">🔥热播{{ item.nav.name }}</h3>
<template v-for="(m,i) in item.hot.slice(0,12)">
<div class="content_right_item">
<a :href="`/filmDetail?link=${m.mid}`"><b class="top_item">{{ i + 1 + '.' }}</b>
<span>{{ m.name }}</span></a>
</div>
</template>
</el-col>
</el-row>
</template>
</div>
</div>
</template>
<script lang="ts" setup>
// 顶部轮播图
import 'element-plus/theme-chalk/display.css'
import {onBeforeMount, reactive} from "vue";
import {onBeforeMount, reactive, ref} from "vue";
import {ApiGet} from "../../utils/request";
import FilmList from "../../components/index/FilmList.vue";
import {ElMessage} from "element-plus";
// 轮播数据拟态
let banners = [
{
name: '樱花庄的宠物女孩',
year: 2012,
cName: '动漫',
poster: 'https://img.bfzypic.com/upload/vod/20230424-43/06e79232a4650aea00f7476356a49847.jpg',
picture: 'https://s2.loli.net/2024/02/21/Wt1QDhabdEI7HcL.jpg'
},
{
name: '从零开始的异世界生活',
year: 2016,
cName: '动漫',
poster: 'https://img.bfzypic.com/upload/vod/20230424-29/82e3aec3f43103fa1b7e5a0e7f7c3806.jpg',
picture: 'https://s2.loli.net/2024/02/21/UkpdhIRO12fsy6C.jpg'
},
{
name: '五等分的新娘',
year: 2020,
cName: '动漫',
poster: 'https://img.bfzypic.com/upload/vod/20230424-38/dfff403cfd9a5b7d6eed8b4f1b3dedb1.jpg',
picture: 'https://s2.loli.net/2024/02/21/wXJr59Zuv4tcKNp.jpg'
},
{
name: '我的青春恋爱物语果然有问题',
year: 2018,
cName: '动漫',
poster: 'https://img.bfzypic.com/upload/vod/20230424-37/e5c9ec121c2cba230243c333447e818a.jpg',
picture: 'https://s2.loli.net/2024/02/21/oMAGzSliK2YbhRu.jpg'
},
]
// pc 背景图同步响应
const carousel = (index: number) => {
data.banner.current = banners[index]
}
// 滑动开始
const wrap = ref<HTMLFormElement>()
const touchS = (e:any)=>{
//记录触摸起始位置
data.banner.touch.star = e.changedTouches[0].pageX
}
// 滑动结束
const touchE = (e:any)=>{
data.banner.touch.end = e.changedTouches[0].pageX
let distance = data.banner.touch.end - data.banner.touch.star
console.log(distance)
if (distance >= 50) {
let index = data.banner.touch.index - 1
data.banner.touch.index = index >= 0 ? index : banners.length-1
} else if (distance <= -50) {
let index = data.banner.touch.index + 1
data.banner.touch.index = index <= banners.length - 1 ? index : 0
}
wrap.value?.setActiveItem(data.banner.touch.index)
}
const data = reactive({
info: {}
info: {},
banner: {
current: {name: '', year: 2024, cName: '', poster: '', picture: ''},
touch: {index: 0, star: 0, end: 0,}
}
})
onBeforeMount(() => {
ApiGet('/index').then((resp: any) => {
if (resp.code == 0) {
data.info = resp.data
} else {
ElMessage.error({message: resp.message})
}
})
data.banner.current = banners[0]
ApiGet('/index').then((resp: any) => {
if (resp.code == 0) {
data.info = resp.data
} else {
ElMessage.error({message: resp.message})
}
})
})
</script>
<style scoped>
.container {
margin: 0 auto;
margin: 0 auto;
}
.content_item {
padding: 10px;
margin-bottom: 25px;
padding: 10px;
margin-bottom: 25px;
}
.title {
display: flex;
text-align: left;
height: 40px;
display: flex;
text-align: left;
height: 40px;
}
.title > a {
min-width: 40px;
color: rgb(221, 221, 221)
min-width: 40px;
color: rgb(221, 221, 221)
}
a {
color: #333;
padding-top: 10px;
text-decoration: none;
outline: none;
-webkit-tap-highlight-color: transparent;
color: #333;
padding-top: 10px;
text-decoration: none;
outline: none;
-webkit-tap-highlight-color: transparent;
}
.cus_nav {
border-bottom: 1px solid rgb(46, 46, 46);
border-bottom: 1px solid rgb(46, 46, 46);
height: 40px;
height: 40px;
}
.nav_ul {
list-style-type: none;
display: flex;
flex-direction: row;
justify-content: end;
margin: 0;
list-style-type: none;
display: flex;
flex-direction: row;
justify-content: end;
margin: 0;
}
.nav_category > a {
color: #c9c4c4;
color: #c9c4c4;
}
.nav_category > a:hover {
color: #1890ff;
color: #1890ff;
}
.nav_ul > li {
/*min-width: 60px;*/
white-space: nowrap;
line-height: 40px;
margin: 0 8px;
text-align: center;
color: #999;
font-size: 14px;
font-weight: 400;
/*min-width: 60px;*/
white-space: nowrap;
line-height: 40px;
margin: 0 8px;
text-align: center;
color: #999;
font-size: 14px;
font-weight: 400;
}
/*影片简介区域*/
.cus_content {
display: flex;
padding-top: 15px;
display: flex;
padding-top: 15px;
}
.content_right {
width: 100%;
padding-left: 18px;
width: 100%;
padding-left: 18px;
}
.content_right_item {
display: flex;
padding-left: 10px;
border-bottom: 1px solid rgb(46, 46, 46);
display: flex;
padding-left: 10px;
border-bottom: 1px solid rgb(46, 46, 46);
}
.content_right_item > a {
padding: 10px 15px 10px 0;
color: hsla(0, 0%, 100%, .87);
display: block;
flex-grow: 1;
text-align: left;
overflow: hidden;
text-overflow: ellipsis;
-o-text-overflow: ellipsis;
white-space: nowrap;
padding: 10px 15px 10px 0;
color: hsla(0, 0%, 100%, .87);
display: block;
flex-grow: 1;
text-align: left;
overflow: hidden;
text-overflow: ellipsis;
-o-text-overflow: ellipsis;
white-space: nowrap;
}
.hot_title {
text-align: left;
margin: 8px 0;
text-align: left;
margin: 8px 0;
}
:deep(.top_item) {
color: red;
/*font-style: oblique 10deg;*/
font-style: italic;
/*font-family: Inter;*/
margin-right: 6px;
color: red;
/*font-style: oblique 10deg;*/
font-style: italic;
/*font-family: Inter;*/
margin-right: 6px;
}
.content_right_item a span:hover {
color: orange;
color: orange;
}
@@ -178,22 +266,214 @@ a {
<!--移动端修改-->
<style scoped>
@media (min-width: 768px) {
.cus_content_item {
padding: 10px;
overflow: hidden;
/*margin-bottom: 10px;*/
}
.cus_content_item {
padding: 10px;
overflow: hidden;
/*margin-bottom: 10px;*/
}
}
@media (max-width: 768px) {
.cus_content_item {
padding: 0 6px 0 0;
margin-bottom: 10px;
overflow: hidden;
}
.cus_content_item {
padding: 0 6px 0 0;
margin-bottom: 10px;
overflow: hidden;
}
.nav_ul {
justify-content: end;
}
.nav_ul {
justify-content: end;
}
}
</style>
</style>
<!--轮播图双端样式-->
<style scoped>
@media (max-width: 768px) {
:deep(.el-carousel) {
--el-carousel-arrow-size: 30px;
--el-carousel-arrow-background: rgba(115, 133, 159, 0.5);
}
:deep(.el-carousel__arrow) {
outline: none;
border: none !important;
}
.el-carousel__item h3 {
color: #475669;
opacity: 0.75;
line-height: 200px;
margin: 0;
text-align: center;
}
.el-carousel__item:nth-child(2n) {
background-color: transparent;
}
.el-carousel__item:nth-child(2n + 1) {
background-color: transparent;
}
:deep(.el-carousel__indicators) {
width: 100% !important;
text-align: right;
height: 20px;
line-height: 20px;
padding-right: 10px;
--el-carousel-indicator-padding-vertical: 0;
}
:deep(.el-carousel__button) {
width: 8px;
height: 8px;
border-radius: 50%;
padding: 0 0!important;
margin: 0 2px;
}
.banner_wrap {
margin: -15px 0 20px 0;
position: relative;
box-shadow: 0 5px 30px 0 rgba(255, 255, 255, 0.15);
}
.carousel-tags {
position: absolute;
top: 170px;
left: 25%;
}
.carousel-tags span {
font-size: 12px;
background: rgba(0, 0, 0, 0.55);
color: #ffffff;
padding: 2px 5px;
margin: 2px 5px;
}
.carousel-title {
font-size: 12px;
position: absolute;
bottom: 0;
height: 20px;
line-height: 20px;
background: rgba(0, 0, 0, 0.5);
text-align: left;
width: 100%;
margin: 0 auto;
white-space: nowrap;
overflow: hidden;
text-overflow: ellipsis; /* 显示省略号 */
}
}
@media (min-width: 768px) {
:deep(.el-carousel) {
--el-carousel-arrow-size: 30px;
--el-carousel-arrow-background: rgba(115, 133, 159, 0.5);
}
:deep(.el-carousel__arrow) {
outline: none;
border: none !important;
}
.container {
/* padding-top: 660px;*/
}
.banner2 {
height: 600px;
position: absolute;
margin-top: 60px;
left: 0;
top: 0;
box-shadow: inset 0 -40px 30px 20px rgba(0, 0, 0, 0.6), 0 5px 30px 0 rgba(255, 255, 255, 0.15);
padding: 2%;
margin-bottom: 10px;
border-radius: 0 0 6px 6px;
width: 100%;
}
.preview2 {
width: 260px;
height: 200px;
position: absolute;
right: 50px;
bottom: 60px;
}
.banner {
height: 600px;
box-shadow: inset 0 -40px 30px 20px rgba(0, 0, 0, 0.6), 0 5px 30px 0 rgba(255, 255, 255, 0.15);
position: relative;
padding: 2%;
margin-bottom: 10px;
border-radius: 6px;
width: 100%;
}
.preview {
width: 260px;
height: 200px;
position: absolute;
right: 50px;
bottom: 60px;
/* border: 1px solid skyblue;*/
}
.el-carousel__item h3 {
color: #475669;
opacity: 0.75;
line-height: 200px;
margin: 0;
text-align: center;
}
.el-carousel__item:nth-child(2n) {
background-color: transparent;
}
.el-carousel__item:nth-child(2n + 1) {
background-color: transparent;
}
:deep(.el-carousel__indicators) {
width: 100% !important;
}
:deep(.el-carousel__button) {
width: 8px;
height: 8px;
border-radius: 50%;
margin: 0 2px;
}
.carousel-tags {
position: absolute;
top: 170px;
left: 25%;
}
.carousel-tags span {
font-size: 12px;
background: rgba(0, 0, 0, 0.55);
color: #ffffff;
padding: 2px 5px;
margin: 2px 5px;
}
.carousel-title {
font-size: 12px;
max-width: 50%;
margin: 0 auto;
white-space: nowrap;
overflow: hidden;
text-overflow: ellipsis; /* 显示省略号 */
}
}
</style>

View File

@@ -231,7 +231,8 @@ const getTaskList = ()=>{
if (resp.status === "ok") {
data.taskList = resp.data
} else {
ElMessage.error({message: resp.message})
data.taskList = []
ElMessage.warning({message: resp.message})
}
})
}