老司机媒资库

This commit is contained in:
mac
2026-03-04 15:10:57 +08:00
parent 0e7d4bdcc7
commit 1428c55498
18 changed files with 4483 additions and 1 deletions
+34
View File
@@ -0,0 +1,34 @@
import request from '@/utils/request'
// 获取视频列表
export function lsjComicsList(data) {
return request({
url: '/api/web/laosiji/comics/search',
method: 'post',
data
})
}
// 获取视频列表
export function lsjComicsDel(data) {
return request({
url: '/api/web/laosiji/comics/search',
method: 'post',
data
})
}
export function lsjComicsDetail(data) {
return request({
url: '/api/web/laosiji/comics/detail',
method: 'post',
data
})
}
export function lsjComicsAdd(data) {
return request({
url: '/api/web/laosiji/comics/add',
method: 'post',
data
})
}
+34
View File
@@ -0,0 +1,34 @@
import request from '@/utils/request'
// 获取视频列表
export function lsjNovelList(data) {
return request({
url: '/api/web/laosiji/novel/search',
method: 'post',
data
})
}
// 获取视频列表
export function lsjNovelDel(data) {
return request({
url: '/api/web/laosiji/novel/search',
method: 'post',
data
})
}
export function lsjNovelDetail(data) {
return request({
url: '/api/web/laosiji/novel/detail',
method: 'post',
data
})
}
export function lsjNovelAdd(data) {
return request({
url: '/api/web/laosiji/novel/add',
method: 'post',
data
})
}
+34
View File
@@ -0,0 +1,34 @@
import request from '@/utils/request'
// 获取视频列表
export function lsjPostList(data) {
return request({
url: '/api/web/laosiji/post/search',
method: 'post',
data
})
}
// 获取视频列表
export function lsjPostDel(data) {
return request({
url: '/api/web/laosiji/post/search',
method: 'post',
data
})
}
export function lsjPostDetail(data) {
return request({
url: '/api/web/laosiji/post/detail',
method: 'post',
data
})
}
export function lsjPostAdd(data) {
return request({
url: '/api/web/laosiji/post/add',
method: 'post',
data
})
}
+34
View File
@@ -0,0 +1,34 @@
import request from '@/utils/request'
// 获取视频列表
export function lsjVideoList(data) {
return request({
url: '/api/web/laosiji/movie/search',
method: 'post',
data
})
}
// 获取视频列表
export function lsjVideoDel(data) {
return request({
url: '/api/web/laosiji/movie/search',
method: 'post',
data
})
}
export function lsjVideoDetail(data) {
return request({
url: '/api/web/laosiji/movie/detail',
method: 'post',
data
})
}
export function lsjVideoAdd(data) {
return request({
url: '/api/web/laosiji/movie/add',
method: 'post',
data
})
}
+98
View File
@@ -0,0 +1,98 @@
<template>
<el-dialog :visible.sync="Visible" :modal="false" @close="close" center
class="ac-dialog" width="900px">
<el-table :data="itemData" element-loading-text="拼命加载中" border height="550" highlight-current-row style="width: 100%" >
<el-table-column align="center" label="章节ID" width="80">
<template slot-scope="scope">{{ scope.row.id }}</template>
</el-table-column>
<el-table-column align="center" label="标题" show-overflow-tooltip>
<template slot-scope="scope">{{ scope.row.name }}</template>
</el-table-column>
<el-table-column align="center" label="点击预览">
<template slot-scope="scope">
<i v-if="scope.row.is_audio==='y'" class="el-icon-video-play views" title="点击预览" @click="checkMedia(scope.row.content, scope.row)"></i>
<div v-else>暂无</div>
</template>
</el-table-column>
<el-table-column align="center" label="是否有声" width="90">
<template slot-scope="scope">
<el-button :type="scope.row.is_audio? 'success' : 'danger'" plain size="mini">{{ scope.row.status ? "是" : "否" }}</el-button>
</template>
</el-table-column>
<el-table-column align="center" label="操作" width="300" show-overflow-tooltip>
<template slot-scope="scope">
<el-button size="small" type="success" @click="lookMore(scope.row.content)">查看详细内容</el-button>
</template>
</el-table-column>
</el-table>
<el-dialog
:visible.sync="showMore" :modal="false" top
class="more-img-dialog" width="900px">
<div class="more-img" >
<div v-for="(item,index) in contentData" :key="index" :style="{height:'auto',width:'100px'}">
<ShowImg :noNeedDoamin="true" :urls="item.f"></ShowImg>
</div>
</div>
</el-dialog>
</el-dialog>
</template>
<script>
import ShowImg from '@/components/ShowImg/index.vue'
export default {
props: ['itemData'],
components: {
ShowImg,
},
data() {
return {
Visible:true,
showMore:false,
contentData:[],
};
},
mounted(){
},
methods: {
changeImagesUrl(data) {
this.form.chapter = data
},
setIsUploadIng(status) {
this.isUploadIng = status
},
// 关闭编辑
close() {
this.$emit('close', false)
},
// 视频查看
checkMedia(url, data) {
this.$refs.showvideo.open(url, data,data.id)
},
lookMore(data){
this.showMore= true
this.contentData = data
}
},
};
</script>
<style lang='scss' scoped>
.ac-dialog{
overflow: hidden;
::v-deep{
.el-dialog{
margin-top: 10px !important;
}
}
}
.more-img-dialog{
.more-img{
display: flex;
flex-wrap: wrap;
}
}
</style>
+352
View File
@@ -0,0 +1,352 @@
<template>
<el-dialog :visible.sync="Visible" :modal="false" @close="close" center
class="ac-dialog" width="900px">
<el-table :data="itemData" element-loading-text="拼命加载中" border height="550" highlight-current-row style="width: 100%" >
<el-table-column align="center" label="章节ID" width="80">
<template slot-scope="scope">{{ scope.row.id }}</template>
</el-table-column>
<el-table-column align="center" label="标题" show-overflow-tooltip>
<template slot-scope="scope">{{ scope.row.name }}</template>
</el-table-column>
<el-table-column align="center" label="封面" width="80px">
<template slot-scope="scope">
<ShowImg style="width: 30px; height: 30px; margin: 0 auto" :noNeedDoamin="true" :urls="scope.row.img">
</ShowImg>
</template>
</el-table-column>
<el-table-column align="center" label="内容" width="300" show-overflow-tooltip>
<template slot-scope="scope">
<!-- <a :href="scope.row.content" target="_blank">查看详细内容</a> -->
{{ scope.row.content }}
</template>
</el-table-column>
<el-table-column align="center" label="点击预览">
<template slot-scope="scope">
<i v-if="scope.row.is_audio==='y'" class="el-icon-video-play views" title="点击预览" @click="checkMedia(scope.row.content, scope.row)"></i>
<div v-else>暂无</div>
</template>
</el-table-column>
<el-table-column align="center" label="是否有声" width="90">
<template slot-scope="scope">
<el-button :type="scope.row.is_audio? 'success' : 'danger'" plain size="mini">{{ scope.row.status ? "是" : "否" }}</el-button>
</template>
</el-table-column>
</el-table>
<ShowVideo ref="showvideo"></ShowVideo>
</el-dialog>
</template>
<script>
import ShowImg from '@/components/ShowImg/index.vue'
import DPlayer from '@/components/VueDplayerHls/index.vue'
import ShowVideo from '@/components/ShowVideo/index.vue'
export default {
props: ['itemData'],
components: {
ShowImg,
DPlayer,
ShowVideo
},
data() {
return {
Visible:true,
};
},
mounted(){
console.log(this.itemData,'11');
},
methods: {
// 关闭编辑
close() {
this.$emit('close', false)
},
// 视频查看
checkMedia(url, data) {
this.$refs.showvideo.open(url, data,data.id)
},
},
};
</script>
<style lang='scss' scoped>
.ac-dialog{
overflow: hidden;
::v-deep{
.el-dialog{
margin-top: 10px !important;
}
}
}
.itemData-main {
/* rem适配基础设置 */
font-size: 16px;
/* 基准字体大小 */
background: #000;
color: #fff;
height: 844px;
overflow-y: scroll;
padding: 10px;
a,
a:link,
a:visited,
a:hover,
a:active {
text-decoration: none;
color: inherit;
}
.topBox {
display: flex;
align-items: center;
justify-content: space-between;
padding: 8px 16px;
background: #212121;
position: fixed;
top: 0;
left: 0;
width: 100%;
z-index: 99;
/* display: none; */
}
.navBtn {
width: 51px;
height: 24px;
display: flex;
align-items: center;
justify-content: center;
font-size: 10px;
color: #E0E0E0;
border-radius: 6px;
background: rgba(255, 255, 255, 0.10);
}
.navBtn .moreIcon {
width: 16px;
height: 16px;
margin-right: 3px;
}
.logo {
width: 94px;
height: 32px;
}
.searchIcon {
width: 24px;
height: 24px;
margin-left: 27px;
}
.header {
width: 100%;
/* height: 159px; */
background: #212121;
padding: 12px 16px;
box-sizing: border-box;
margin-bottom: 20px;
}
.header .title {
text-align: center;
color: #BDBDBD;
font-size: 26px;
line-height: 32px;
margin-bottom: 14px;
}
.header .info {
font-size: 14px;
line-height: 20px;
color: rgba(255, 255, 255, 0.70);
display: flex;
align-items: center;
display: -webkit-box;
-webkit-box-orient: vertical;
-webkit-line-clamp: 3;
text-overflow: ellipsis;
overflow: hidden;
}
.header .info a {
text-decoration-line: underline;
}
.main .lineBox {
padding: 0 16px;
box-sizing: border-box;
}
.main .lineBox .line {
width: 100%;
height: 1px;
background: rgba(255, 255, 255, 0.10);
margin: 18px 0;
}
.postContent {
margin: 36px 0 0;
}
.postBox {
color: #FAFAFA;
/* margin-bottom: 18px; */
}
.postTitle {
font-size: 24px;
font-weight: 600;
line-height: 32px;
margin-bottom: 28px;
padding: 0 16px;
box-sizing: border-box;
}
.postText {
color: #FAFAFA;
margin: 0 16px 36px;
font-size: 16px;
line-height: 22px;
}
.postimage {
width: 100%;
height: auto;
margin-bottom: 18px;
/* margin-bottom: 47px; */
}
.postDesc {
font-size: 16px;
color: #FAFAFA;
line-height: 22px;
padding: 0 16px;
box-sizing: border-box;
margin-bottom: 19px;
}
.postDesc span {
font-weight: 600;
}
.postLine {
margin: 0 16px;
border-bottom: 1px dashed rgba(255, 255, 255, 0.50);
}
.tagBox {
margin-bottom: 12px;
padding: 0 16px;
}
.tagBox .tagList {
display: flex;
align-items: center;
flex-wrap: wrap;
gap: 7px;
margin-bottom: 18px;
}
.tagBox .tagList .tagItem {
padding: 8px 16px;
box-sizing: border-box;
border-radius: 62px;
background: rgba(255, 255, 255, 0.05);
display: flex;
align-items: center;
justify-content: center;
font-size: 12px;
color: #BDBDBD;
}
.lastDay {
text-align: right;
color: #BDBDBD;
line-height: 20px;
font-size: 14px;
}
.copyBox {
color: #FFF;
text-align: center;
text-shadow: 0 0 20px #FF8400, 0 0 20px #FF8400;
font-family: "PingFang SC";
font-size: 20px;
font-style: normal;
font-weight: 500;
line-height: 28px;
/* 140% */
padding: 18px;
box-sizing: border-box;
margin-bottom: 18px;
}
.copySuccess {
color: #FFF;
text-align: center;
text-shadow: 0 0 20px #FF00B2, 0 0 20px #FF00B2;
font-family: "PingFang SC";
font-size: 20px;
font-style: normal;
font-weight: 500;
line-height: 28px;
/* 140% */
padding: 18px;
box-sizing: border-box;
margin-bottom: 18px;
}
.dplayerBox {
margin-bottom: 18px;
max-height: 300px;
}
.gridAdvBox {
margin: 0 16px 18px;
}
.gridAdvBox .gridAdvTitle {
padding: 0 16px;
box-sizing: border-box;
height: 49px;
display: flex;
align-items: center;
border-top: 1px solid rgba(255, 255, 255, 0.10);
background: rgba(255, 255, 255, 0.05);
font-size: 18px;
font-style: normal;
font-weight: 600;
line-height: 24px;
}
.keywords {
box-sizing: border-box;
font-size: 16px;
line-height: 22px;
color: #BDBDBD;
}
@media screen and (min-width: 768px) {
/* body {
margin-top: 140px;
} */
body main {
max-width: 720px;
margin: 0 auto;
}
.header {
max-width: 720px;
margin: 0 auto;
}
.topBox {
display: none;
}
}
}
</style>
+332
View File
@@ -0,0 +1,332 @@
<template>
<el-dialog :visible.sync="Visible" @close="close" center
class="ac-dialog" width="390px">
<div class="itemData-main">
<div class="postContent">
<div class="postBox" v-for="(item, index) in itemData" :key="index">
<!-- <p class="postTitle">{{ item.title }}</p> -->
<ShowImg :noNeedDoamin='true' :key="imgINdex" :urls="item.image" />
<!-- <span class="postText">{{ item.text }}</span> -->
<DPlayer ref="player" class="dplayerBox" v-if="item.video_link" :video="{
url: filterM3u8(item.video_link),
type: 'hls',
pic: '',
}" hotkey></DPlayer>
</div>
</div>
</div>
</el-dialog>
</template>
<script>
import ShowImg from '@/components/ShowImg/index.vue'
import DPlayer from '@/components/VueDplayerHls/index.vue'
import { mounted } from 'qrcode.vue';
export default {
props: ['itemData'],
components: {
ShowImg,
DPlayer
},
data() {
return {
Visible:true,
};
},
mounted(){
console.log(this.itemData,'11');
},
methods: {
filterM3u8(v) {
return /\.m3u8/g.test(v) ? v : v + '.m3u8'
},
// 关闭编辑
close() {
this.$emit('close', false)
},
},
};
</script>
<style lang='scss' scoped>
.ac-dialog{
overflow: hidden;
::v-deep{
.el-dialog{
margin-top: 10px !important;
}
}
}
.itemData-main {
/* rem适配基础设置 */
font-size: 16px;
/* 基准字体大小 */
background: #000;
color: #fff;
height: 844px;
overflow-y: scroll;
padding: 10px;
a,
a:link,
a:visited,
a:hover,
a:active {
text-decoration: none;
color: inherit;
}
.topBox {
display: flex;
align-items: center;
justify-content: space-between;
padding: 8px 16px;
background: #212121;
position: fixed;
top: 0;
left: 0;
width: 100%;
z-index: 99;
/* display: none; */
}
.navBtn {
width: 51px;
height: 24px;
display: flex;
align-items: center;
justify-content: center;
font-size: 10px;
color: #E0E0E0;
border-radius: 6px;
background: rgba(255, 255, 255, 0.10);
}
.navBtn .moreIcon {
width: 16px;
height: 16px;
margin-right: 3px;
}
.logo {
width: 94px;
height: 32px;
}
.searchIcon {
width: 24px;
height: 24px;
margin-left: 27px;
}
.header {
width: 100%;
/* height: 159px; */
background: #212121;
padding: 12px 16px;
box-sizing: border-box;
margin-bottom: 20px;
}
.header .title {
text-align: center;
color: #BDBDBD;
font-size: 26px;
line-height: 32px;
margin-bottom: 14px;
}
.header .info {
font-size: 14px;
line-height: 20px;
color: rgba(255, 255, 255, 0.70);
display: flex;
align-items: center;
display: -webkit-box;
-webkit-box-orient: vertical;
-webkit-line-clamp: 3;
text-overflow: ellipsis;
overflow: hidden;
}
.header .info a {
text-decoration-line: underline;
}
.main .lineBox {
padding: 0 16px;
box-sizing: border-box;
}
.main .lineBox .line {
width: 100%;
height: 1px;
background: rgba(255, 255, 255, 0.10);
margin: 18px 0;
}
.postContent {
margin: 36px 0 0;
}
.postBox {
color: #FAFAFA;
/* margin-bottom: 18px; */
}
.postTitle {
font-size: 24px;
font-weight: 600;
line-height: 32px;
margin-bottom: 28px;
padding: 0 16px;
box-sizing: border-box;
}
.postText {
color: #FAFAFA;
margin: 0 16px 36px;
font-size: 16px;
line-height: 22px;
}
.postimage {
width: 100%;
height: auto;
margin-bottom: 18px;
/* margin-bottom: 47px; */
}
.postDesc {
font-size: 16px;
color: #FAFAFA;
line-height: 22px;
padding: 0 16px;
box-sizing: border-box;
margin-bottom: 19px;
}
.postDesc span {
font-weight: 600;
}
.postLine {
margin: 0 16px;
border-bottom: 1px dashed rgba(255, 255, 255, 0.50);
}
.tagBox {
margin-bottom: 12px;
padding: 0 16px;
}
.tagBox .tagList {
display: flex;
align-items: center;
flex-wrap: wrap;
gap: 7px;
margin-bottom: 18px;
}
.tagBox .tagList .tagItem {
padding: 8px 16px;
box-sizing: border-box;
border-radius: 62px;
background: rgba(255, 255, 255, 0.05);
display: flex;
align-items: center;
justify-content: center;
font-size: 12px;
color: #BDBDBD;
}
.lastDay {
text-align: right;
color: #BDBDBD;
line-height: 20px;
font-size: 14px;
}
.copyBox {
color: #FFF;
text-align: center;
text-shadow: 0 0 20px #FF8400, 0 0 20px #FF8400;
font-family: "PingFang SC";
font-size: 20px;
font-style: normal;
font-weight: 500;
line-height: 28px;
/* 140% */
padding: 18px;
box-sizing: border-box;
margin-bottom: 18px;
}
.copySuccess {
color: #FFF;
text-align: center;
text-shadow: 0 0 20px #FF00B2, 0 0 20px #FF00B2;
font-family: "PingFang SC";
font-size: 20px;
font-style: normal;
font-weight: 500;
line-height: 28px;
/* 140% */
padding: 18px;
box-sizing: border-box;
margin-bottom: 18px;
}
.dplayerBox {
margin-bottom: 18px;
max-height: 300px;
}
.gridAdvBox {
margin: 0 16px 18px;
}
.gridAdvBox .gridAdvTitle {
padding: 0 16px;
box-sizing: border-box;
height: 49px;
display: flex;
align-items: center;
border-top: 1px solid rgba(255, 255, 255, 0.10);
background: rgba(255, 255, 255, 0.05);
font-size: 18px;
font-style: normal;
font-weight: 600;
line-height: 24px;
}
.keywords {
box-sizing: border-box;
font-size: 16px;
line-height: 22px;
color: #BDBDBD;
}
@media screen and (min-width: 768px) {
/* body {
margin-top: 140px;
} */
body main {
max-width: 720px;
margin: 0 auto;
}
.header {
max-width: 720px;
margin: 0 auto;
}
.topBox {
display: none;
}
}
}
</style>
+164
View File
@@ -0,0 +1,164 @@
export function changePosition(val) {
switch (val) {
case 'guochan':
return '国产成人视频'
case 'av':
return '日本和欧美成人视频'
case 'movie':
return '正规影视资源'
case 'bl':
return '男同'
case 'douyin':
return '短视频'
case 'cartoon':
return '动漫'
case 'dark':
return '暗网资源'
default:
return '暂无'
}
}
export function positionList(val, list) {
return [{
value: 'guochan',
label: '国产成人视频'
},
{
value: 'av',
label: '日本和欧美成人视频'
},
{
value: 'movie',
label: '正规影视资源'
},
{
value: 'bl',
label: '男同'
},
{
value: 'douyin',
label: '短视频'
},
{
value: 'cartoon',
label: '动漫'
},
{
value: 'dark',
label: '暗网资源'
}
]
}
export function changeVideoTypeList(val) {
switch (val) {
case '1':
return 'AV'
case '2':
return 'DM'
case '3':
return 'GC'
case '4':
return '综艺'
case '5':
return '连续剧'
case '6':
return '电影'
case '7':
return '动漫'
case '8':
return '纪录片'
case '9':
return '短剧'
case '10':
return '音乐'
case '11':
return '电影解说 '
case '12':
return 'VR'
case '13':
return '成人短视频'
}
}
export function videoTypeList(val, list) {
return [{
label: '1',
value: 'AV'
},
{
label: '2',
value: 'DM'
},
{
label: '3',
value: 'GC'
},
{
label: '4',
value: '综艺'
},
{
label: '5',
value: '连续剧'
},
{
label: '6',
value: '电影'
},
{
label: '7',
value: '动漫'
},{
label: '8',
value: '纪录片'
},{
label: '9',
value: '短剧'
},{
label: '10',
value: '音乐'
},{
label: '11',
value: '电影解说'
},{
label: '12',
value: 'VR'
},{
label: '13',
value: '成人短视频'
}
]
}
export function statusList(val, list) {
return [{
label: '0',
value: '待处理'
},
{
label: '-1',
value: '处理失败'
},
{
label: '1',
value: '处理中'
},
{
label: '2',
value: '处理成功'
}
]
}
export function changeStatusListType(val) {
switch (val) {
case '0':
return '待处理'
case '-1':
return '处理失败'
case '1':
return '处理中'
case '2':
return '处理成功'
}
}
+36
View File
@@ -166,6 +166,42 @@ export const serverRouter = [
} }
] ]
}, },
{
path: '/lsjMediaLibrary',
component: 'LsjMediaLibrary',
redirect: '/lsjMediaLibrary/mediaTag',
name: 'LsjMediaLibrary',
meta: {
title: '老司机媒资库管理',
icon: 'el-icon-film'
},
children: [
{
path: 'lsjMediaLibraryVideoList',
name: 'LsjMediaLibraryVideoList',
api_url: [],
meta: { title: '影片列表', noCache: true, icon: 'el-icon-film' }
},
{
path: 'lsjMediaLibraryPostList',
name: 'LsjMediaLibraryPostList',
api_url: [],
meta: { title: '帖子列表', noCache: true, icon: 'el-icon-film' }
},
{
path: 'lsjMediaLibraryComicsList',
name: 'LsjMediaLibraryComicsList',
api_url: [],
meta: { title: '漫画列表', noCache: true, icon: 'el-icon-film' }
},
{
path: 'lsjMediaLibraryNovelList',
name: 'LsjMediaLibraryNovelList',
api_url: [],
meta: { title: '小说列表', noCache: true, icon: 'el-icon-film' }
}
]
},
{ {
path: '/videoManagement', path: '/videoManagement',
component: 'VideoManagement', component: 'VideoManagement',
+6 -1
View File
@@ -39,7 +39,12 @@ const map = {
MediaLibraryVideoList: () => import('@/views/mediaLibrary/videoList/index.vue'), // 影片列表 MediaLibraryVideoList: () => import('@/views/mediaLibrary/videoList/index.vue'), // 影片列表
MediaLibraryVideoListV1: () => import('@/views/mediaLibrary/videoListV1/index.vue'), // 影片列表V1 MediaLibraryVideoListV1: () => import('@/views/mediaLibrary/videoListV1/index.vue'), // 影片列表V1
MediaLibraryVideoListV2: () => import('@/views/mediaLibrary/videoListV2/index.vue'), // 影片列表V2 MediaLibraryVideoListV2: () => import('@/views/mediaLibrary/videoListV2/index.vue'), // 影片列表V2
// 老司机媒资库管理
LsjMediaLibrary: Layout,
LsjMediaLibraryVideoList: () => import('@/views/lsjMediaLibrary/videoList/index.vue'), // 影片列表
LsjMediaLibraryPostList: () => import('@/views/lsjMediaLibrary/postList/index.vue'), // 帖子列表
LsjMediaLibraryComicsList: () => import('@/views/lsjMediaLibrary/comicsList/index.vue'), // 漫画列表
LsjMediaLibraryNovelList: () => import('@/views/lsjMediaLibrary/novelList/index.vue'), // 小说列表
// 视频管理 // 视频管理
VideoManagement: Layout, VideoManagement: Layout,
VideoList: () => import('@/views/videoManagement/videoList/index.vue'), // 视频列表 VideoList: () => import('@/views/videoManagement/videoList/index.vue'), // 视频列表
@@ -0,0 +1,517 @@
<template>
<el-dialog :title="title" :visible.sync="Visible" width="900px" center class="ac-dialog"
:close-on-click-modal="false" @close="close">
<el-form :inline="true" :model="form" class="demo-form-inline" label-width="120px" label-position="right">
<el-row :gutter="24">
<el-col :xs="12" :sm="12" :md="12" :lg="12" :xl="12">
<el-form-item label="标题">
<el-input v-model="form.name" style="width: 200px" />
</el-form-item>
</el-col>
<el-col :xs="12" :sm="12" :md="12" :lg="12" :xl="12">
<el-form-item label="子标题">
<el-input v-model="form.sub_title" style="width: 200px" />
</el-form-item>
</el-col>
<el-col :xs="12" :sm="12" :md="12" :lg="12" :xl="12">
<el-form-item label="价格">
<el-input v-model="form.money" style="width: 200px" />
</el-form-item>
</el-col>
<el-col :xs="12" :sm="12" :md="12" :lg="12" :xl="12">
<el-form-item label="描述">
<el-input v-model="form.description" style="width: 200px" />
</el-form-item>
</el-col>
<el-col :xs="12" :sm="12" :md="12" :lg="12" :xl="12">
<el-form-item label="作者">
<el-input v-model="form.author" style="width: 200px" />
</el-form-item>
</el-col>
<el-col :xs="12" :sm="12" :md="12" :lg="12" :xl="12">
<el-form-item label="是否有声">
<el-select v-model="form.is_adult" placeholder="请选择是否有声">
<el-option :value="'y'" :label="'是'"></el-option>
<el-option :value="'n'" :label="'否'"></el-option>
</el-select>
</el-form-item>
</el-col>
<el-col :xs="12" :sm="12" :md="12" :lg="12" :xl="12">
<el-form-item label="更新状态">
<el-select v-model="form.update_status" placeholder="请选择更新状态">
<el-option :value="'0'" :label="'更新中'"></el-option>
<el-option :value="'1'" :label="'已完结'"></el-option>
</el-select>
</el-form-item>
</el-col>
<el-col :xs="12" :sm="12" :md="12" :lg="12" :xl="12">
<el-form-item label="分类">
<el-input v-model="form.category" style="width: 200px" />
</el-form-item>
</el-col>
<el-col :xs="12" :sm="12" :md="12" :lg="12" :xl="12">
<el-form-item label="章节列表">
<el-button size="small" type="success" @click="showDetailFn(form.chapter)">查看漫画章节详情</el-button>
</el-form-item>
</el-col>
<el-col :xs="12" :sm="12" :md="12" :lg="12" :xl="12">
<el-form-item label="标签">
<el-tag :key="index + 'tagData'" style="margin: 2px" v-for="(item, index) in form.tags" size="mini">
{{ item.name }}
</el-tag>
</el-form-item>
</el-col>
<el-col :lg="12" :md="12" :sm="12" :xl="12" :xs="12">
<el-form-item label="更新时间">
<el-date-picker style="width: 200px" v-model="form.updated_at" type="date" placeholder="选择日期"
value-format="yyyy-MM-ddTHH:mm:ssZ">
</el-date-picker>
</el-form-item>
</el-col>
<el-col :xs="12" :sm="12" :md="12" :lg="12" :xl="12">
<el-form-item label="封面">
<ShowImg style="width: 100px; height: 100px;" :noNeedDoamin="true" :urls="form.img">
</ShowImg>
</el-form-item>
</el-col>
</el-row>
</el-form>
<ComicsDetailView v-if="showDetail" :itemData="novelDetailData" @close="showDetail = false" />
<div slot="footer" class="dialog-footer">
<el-button @click.native.prevent="Visible = false"> </el-button>
</div>
</el-dialog>
</template>
<script>
import 'videojs-contrib-hls'
import { lsjComicsDetail } from '@/api/lsjMediaLibrary/comicsList.js'
import ShowImg from '@/components/ShowImg/index.vue'
import ComicsDetailView from '@/components/ComicsDetailView/index.vue'
export default {
name: 'AddOrEdit',
props: ['data'],
components: {
ShowImg,
ComicsDetailView
},
data() {
return {
coverTypeList: [
{ label: '横版', value: 'long' },
{ label: '竖版', value: 'short' },
],
novelDetailData:[],
showDetail:false,
type: undefined,
videoType: undefined,
innerVisible: false,
Visible: true,
title: '',
taskId: '',
tags: null,
fieldNameFs: '', // 正片地址全称
form: {
links: [{
m3u8_url: '',
preview_m3u8_url: '',
}]
},
}
},
async created() {
this.title = this.data.title
if (this.title === '查看详情') {
await this.getVideoDetail()
if (this.form.links.m3u8_url) {
this.open()
}
}
if (this.player) {
this.player.dispose()
}
},
methods: {
showDetailFn(row) {
this.novelDetailData = row
this.showDetail = true
},
getVideoDetail() {
lsjComicsDetail({ id: this.data.data.id }).then((res) => {
if (res.code === 200) {
this.form = res.data
} else {
this.$message.error('请求失败!')
}
})
},
filterM3u8(v) {
return /\.m3u8/g.test(v) ? v : v + '.m3u8'
},
// 清空某一项筛选列表
onClear(key) {
this.form.param[key] = []
},
// 上传图片返回地址
changeCoverImgUrl(data) {
this.form.coverImg = data
},
// 关闭编辑
close() {
if (this.player) {
this.player.dispose()
}
this.$emit('close')
}
}
}
</script>
<style lang="scss">
.el-dialog {
display: flex;
flex-direction: column;
margin: 0 !important;
position: absolute;
top: 50%;
left: 50%;
transform: translate(-50%, -50%);
/*height:600px;*/
max-height: calc(100% - 30px);
max-width: calc(100% - 30px);
}
.el-dialog .el-dialog__body {
flex: 1;
overflow: auto;
}
.videoBox {
display: flex;
justify-content: center;
overflow: hidden;
}
.el-textarea.is-disabled.ti .el-textarea__inner {
color: red;
}
.media-box {
width: 100%;
height: 400px;
text-align: center;
overflow: hidden;
img {
height: 100%;
max-width: 100%;
}
#my-video {
width: 100% !important;
height: 100% !important;
border: none !important;
}
}
.check_upload {
position: relative;
padding: 10px;
overflow: hidden;
border: 1px dashed #ccc;
background-color: #f5f5f5;
div {
display: inline-block;
position: relative;
padding: 4px 8px;
font-size: 100%;
line-height: 1.4;
color: #666;
border: 1px solid #666;
cursor: pointer;
border-radius: 2px;
background: none;
outline: none;
}
}
.itemData-main {
/* rem适配基础设置 */
font-size: 16px;
/* 基准字体大小 */
background: #000;
color: #fff;
height: 844px;
overflow-y: scroll;
padding: 10px;
a,
a:link,
a:visited,
a:hover,
a:active {
text-decoration: none;
color: inherit;
}
.topBox {
display: flex;
align-items: center;
justify-content: space-between;
padding: 8px 16px;
background: #212121;
position: fixed;
top: 0;
left: 0;
width: 100%;
z-index: 99;
/* display: none; */
}
.navBtn {
width: 51px;
height: 24px;
display: flex;
align-items: center;
justify-content: center;
font-size: 10px;
color: #E0E0E0;
border-radius: 6px;
background: rgba(255, 255, 255, 0.10);
}
.navBtn .moreIcon {
width: 16px;
height: 16px;
margin-right: 3px;
}
.logo {
width: 94px;
height: 32px;
}
.searchIcon {
width: 24px;
height: 24px;
margin-left: 27px;
}
.header {
width: 100%;
/* height: 159px; */
background: #212121;
padding: 12px 16px;
box-sizing: border-box;
margin-bottom: 20px;
}
.header .title {
text-align: center;
color: #BDBDBD;
font-size: 26px;
line-height: 32px;
margin-bottom: 14px;
}
.header .info {
font-size: 14px;
line-height: 20px;
color: rgba(255, 255, 255, 0.70);
display: flex;
align-items: center;
display: -webkit-box;
-webkit-box-orient: vertical;
-webkit-line-clamp: 3;
text-overflow: ellipsis;
overflow: hidden;
}
.header .info a {
text-decoration-line: underline;
}
.main .lineBox {
padding: 0 16px;
box-sizing: border-box;
}
.main .lineBox .line {
width: 100%;
height: 1px;
background: rgba(255, 255, 255, 0.10);
margin: 18px 0;
}
.postContent {
margin: 36px 0 0;
}
.postBox {
color: #FAFAFA;
/* margin-bottom: 18px; */
}
.postTitle {
font-size: 24px;
font-weight: 600;
line-height: 32px;
margin-bottom: 28px;
padding: 0 16px;
box-sizing: border-box;
}
.postText {
color: #FAFAFA;
margin: 0 16px 36px;
font-size: 16px;
line-height: 22px;
}
.postimage {
width: 100%;
height: auto;
margin-bottom: 18px;
/* margin-bottom: 47px; */
}
.postDesc {
font-size: 16px;
color: #FAFAFA;
line-height: 22px;
padding: 0 16px;
box-sizing: border-box;
margin-bottom: 19px;
}
.postDesc span {
font-weight: 600;
}
.postLine {
margin: 0 16px;
border-bottom: 1px dashed rgba(255, 255, 255, 0.50);
}
.tagBox {
margin-bottom: 12px;
padding: 0 16px;
}
.tagBox .tagList {
display: flex;
align-items: center;
flex-wrap: wrap;
gap: 7px;
margin-bottom: 18px;
}
.tagBox .tagList .tagItem {
padding: 8px 16px;
box-sizing: border-box;
border-radius: 62px;
background: rgba(255, 255, 255, 0.05);
display: flex;
align-items: center;
justify-content: center;
font-size: 12px;
color: #BDBDBD;
}
.lastDay {
text-align: right;
color: #BDBDBD;
line-height: 20px;
font-size: 14px;
}
.copyBox {
color: #FFF;
text-align: center;
text-shadow: 0 0 20px #FF8400, 0 0 20px #FF8400;
font-family: "PingFang SC";
font-size: 20px;
font-style: normal;
font-weight: 500;
line-height: 28px;
/* 140% */
padding: 18px;
box-sizing: border-box;
margin-bottom: 18px;
}
.copySuccess {
color: #FFF;
text-align: center;
text-shadow: 0 0 20px #FF00B2, 0 0 20px #FF00B2;
font-family: "PingFang SC";
font-size: 20px;
font-style: normal;
font-weight: 500;
line-height: 28px;
/* 140% */
padding: 18px;
box-sizing: border-box;
margin-bottom: 18px;
}
.dplayerBox {
margin-bottom: 18px;
max-height: 300px;
}
.gridAdvBox {
margin: 0 16px 18px;
}
.gridAdvBox .gridAdvTitle {
padding: 0 16px;
box-sizing: border-box;
height: 49px;
display: flex;
align-items: center;
border-top: 1px solid rgba(255, 255, 255, 0.10);
background: rgba(255, 255, 255, 0.05);
font-size: 18px;
font-style: normal;
font-weight: 600;
line-height: 24px;
}
.keywords {
box-sizing: border-box;
font-size: 16px;
line-height: 22px;
color: #BDBDBD;
}
@media screen and (min-width: 768px) {
/* body {
margin-top: 140px;
} */
body main {
max-width: 720px;
margin: 0 auto;
}
.header {
max-width: 720px;
margin: 0 auto;
}
.topBox {
display: none;
}
}
}
</style>
@@ -0,0 +1,337 @@
<template>
<div class="pf-warpper avlist">
<el-row class="table-form">
<el-form :inline="true" :model="searchData" class="form-inline" size="mini">
<el-form-item>
<el-input placeholder="请输入关键词" clearable v-model="searchData.keywords" @clear="onClear('keywords')" />
</el-form-item>
<el-form-item>
<el-input placeholder="请输入ID" clearable v-model="searchData.id" @clear="onClear('id')" />
</el-form-item>
<el-form-item>
<el-input placeholder="请输入源站" clearable v-model="searchData.source_site" @clear="onClear('source_site')" />
</el-form-item>
<el-form-item>
<el-input placeholder="请输入源链接" clearable v-model="searchData.source_url" @clear="onClear('source_url')" />
</el-form-item>
<el-form-item>
<el-select placeholder="请选择是否完结" clearable v-model="searchData.is_end" @clear="onClear('is_end')">
<el-option label="已完结" value="y" />
<el-option label="未完结" value="n" />
</el-select>
</el-form-item>
<el-form-item>
<el-select placeholder="请选择分类" clearable v-model="searchData.cat_id" @clear="onClear('cat_id')">
<el-option label="韩漫" value="韩漫" />
<el-option label="日漫" value="日漫" />
<el-option label="国漫" value="国漫" />
<el-option label="本子" value="本子" />
<el-option label="色图" value="色图" />
<el-option label="腐漫" value="腐漫" />
<el-option label="Cosplay" value="Cosplay" />
<el-option label="3D" value="3D" />
<el-option label="CG" value="CG" />
<el-option label="欧美漫画" value="欧美漫画" />
<el-option label="港台漫画" value="港台漫画" />
<el-option label="真人漫画" value="真人漫画" />
<el-option label="同人" value="同人" />
<el-option label="写真" value="写真" />
<el-option label="AI" value="AI" />
</el-select>
</el-form-item>
<el-form-item>
<el-date-picker v-model="time" type="daterange" range-separator="至" value-format="yyyy-MM-dd HH:mm:ss"
start-placeholder="开始日期" end-placeholder="结束日期">
</el-date-picker>
</el-form-item>
<el-form-item>
<el-button @click="onSeach" icon="el-icon-search" plain type="primary">搜索</el-button>
<!-- <el-button @click="add" icon="el-icon-circle-plus-outline" plain type="success">新增</el-button> -->
<el-button @click="addPostArray" icon="el-icon-circle-plus-outline" plain type="warning">批量加入后台视频库</el-button>
</el-form-item>
</el-form>
</el-row>
<el-row>
<el-col>
<el-table :data="resData" element-loading-text="拼命加载中" border height="735" highlight-current-row
style="width: 100%; font-size: 10px" v-loading="loading" :row-style="{ height: '30px' }"
:cell-style="{ padding: '5px' }" @selection-change="handleSelectionChange">
<el-table-column type="selection" width="50"> </el-table-column>
<el-table-column align="center" label="ID" width="190px">
<template slot-scope="scope">{{ scope.row.id }}</template>
</el-table-column>
<el-table-column align="center" label="标题" width="190px" show-overflow-tooltip>
<template slot-scope="scope">{{ scope.row.name }}</template>
</el-table-column>
<el-table-column align="center" label="描述" width="190px" show-overflow-tooltip>
<template slot-scope="scope">{{ scope.row.description }}</template>
</el-table-column>
<el-table-column align="center" label="封面" width="80px">
<template slot-scope="scope">
<ShowImg style="width: 30px; height: 30px; margin: 0 auto" :noNeedDoamin="true" :urls="scope.row.img">
</ShowImg>
</template>
</el-table-column>
<el-table-column align="center" label="分类名称" show-overflow-tooltip>
<template slot-scope="scope">{{ scope.row.category }}</template>
</el-table-column>
<el-table-column align="center" label="章节数量">
<template slot-scope="scope">{{
scope.row.chapter_count
}}</template>
</el-table-column>
<el-table-column align="center" label="标签" width="300px">
<template slot-scope="scope">
<el-tag :key="index + 'tagData'" style="margin: 2px" v-for="(item, index) in scope.row.tags"
size="mini">
{{ item.name }}
</el-tag>
</template>
</el-table-column>
<el-table-column align="center" label="类型">
<template slot-scope="scope">{{ scope.row.type }}</template>
</el-table-column>
<el-table-column align="center" label="价格">
<template slot-scope="scope">{{ scope.row.money }}</template>
</el-table-column>
<el-table-column align="center" label="是否有声" width="110px">
<template slot-scope="scope">
<el-button plain size="mini">{{
scope.row.is_adult === 'y' ? '有声' : '文本' }}</el-button>
</template>
</el-table-column>
<el-table-column align="center" label="更新状态" width="110px">
<template slot-scope="scope">{{
scope.row.update_status | changeUpdateStatus
}}</template>
</el-table-column>
<el-table-column align="center" label="是否完结" width="110px">
<template slot-scope="scope">
<el-button plain size="mini">{{
scope.row.is_end === 'y' ? '已完结' : '未完结' }}</el-button>
</template>
</el-table-column>
<el-table-column align="center" label="子标题" width="190px" show-overflow-tooltip>
<template slot-scope="scope">{{ scope.row.sub_title }}</template>
</el-table-column>
<el-table-column align="center" label="别名" width="190px" show-overflow-tooltip>
<template slot-scope="scope">{{ scope.row.alias_name }}</template>
</el-table-column>
<el-table-column align="center" width="120px" label="最后更新时间">
<template slot-scope="scope">{{ scope.row.last_update | BeiJingTime }}</template>
</el-table-column>
<el-table-column align="center" width="120px" label="创建时间">
<template slot-scope="scope">{{ scope.row.created_at | BeiJingTime }}</template>
</el-table-column>
<el-table-column align="center" fixed="right" label="操作" width="300">
<template slot-scope="scope">
<el-button @click="addPost(scope.$index, scope.row)" size="mini"
:type="scope.row.isAdd ? 'info' : 'primary'" :disabled="scope.row.isAdd ? true : false">{{
`${scope.row.isAdd ? '已加入后台资源库' : '加入后台资源库'}` }}</el-button>
<el-button @click="handleEdit(scope.$index, scope.row)" size="mini" type="primary">查看详情</el-button>
<!-- <el-button @click="handleDelete(scope.$index, scope.row)" size="mini" type="danger">删除</el-button> -->
</template>
</el-table-column>
</el-table>
</el-col>
</el-row>
<div class="table-pagination">
<el-pagination :current-page="page" :page-size="page_size"
:page-sizes="[10, 20, 30, 50, 100]" :total="total" @current-change="handleCurrentChange"
@size-change="handleSizeChange" layout="total, sizes, prev, pager, next, jumper" />
</div>
<!-- 查看详情 -->
<Edit :data="editData" v-if="editVisible" @close="closeEdit" />
<NovelDetailView v-if="showDetail" :itemData="novelDetailData" @close="closeEdit"
/>
</div>
</template>
<script>
// 引入模块
import ShowImg from '@/components/ShowImg/index.vue'
import Edit from './components/AddOrEdit'
import { lsjComicsList, lsjComicsDel, lsjComicsAdd } from '@/api/lsjMediaLibrary/comicsList.js'
import { audioAdd } from '@/api/novelsManagement/audio.js'
import { isNumber } from 'mathjs/lib/entry/typeChecks'
import NovelDetailView from '@/components/NovelDetailView/index.vue'
export default {
name: 'MediaCat',
components: {
ShowImg,
Edit,
NovelDetailView
},
data() {
return {
page: 1,
page_size: 20,
novelDetailData:[],
// 请求列表参数
searchData: {
id: undefined,
name: undefined, // 外用状态
status: undefined, // "string",当前状态
cat_id: undefined // 视频归类
},
time: undefined,
resData: [], // el-table表格数据
total: 0, // 数据总条数
selectArray: undefined,
editShowLocationVisible: undefined,
showDetail: false,
loading: true, // 列表加载状态
// 编辑数据
editVisible: false, // 新增或编辑弹出框
editData: {
title: '查看详情',
data: {}
}
}
},
filters: {
changeUpdateStatus(v){
switch (v) {
case '0':
return '更新中'
case '1':
return '更新完成'
}
},
},
mounted() {
this.getMediaSearch()
},
methods: {
showDetailFn(row) {
this.novelDetailData = row
this.showDetail = true
},
// TODO:加入后台视频库
addPost(index, row) {
lsjComicsAdd({ id: row.id }).then((res) => {
if (res.code === 200) {
this.$message.success('加入成功!')
this.getMediaSearch()
} else {
this.$message.error('加入失败!')
}
})
},
// TODO:请求影片列表数据
getMediaSearch() {
this.loading = true
if(isNumber(this.page)|| isNumber(this.page_size)){
this.searchData.page = this.page + ''
this.searchData.page_size = this.page_size + ''
}
if (this.time) {
this.searchData.start_time = this.time[0]
this.searchData.end_time = this.time[1]
} else {
this.searchData.start_time = undefined
this.searchData.end_time = undefined
}
lsjComicsList(this.searchData).then((res) => {
if (res.code === 200) {
this.resData = res.data.data
this.total = Number(res.data.total)
} else {
this.$message.error('请求列表失败!')
this.resData = []
this.total = 0
}
this.loading = false
})
},
// TODO:删除影片列表数据
handleDelete(index, row) {
this.$confirm('确定删除?', '警告', {
confirmButtonText: '确定',
cancelButtonText: '取消',
type: 'warning'
}).then(() => {
lsjComicsDel({ id: row.id }).then((res) => {
if (res.code === 200) {
this.getMediaSearch()
this.$message.success('成功删除!')
} else {
this.$message.error(res.tip)
}
})
})
},
addPostArray() {
Object.keys(this.selectArray).forEach((key) => {
if (!this.selectArray[key].isAdd) {
this.addPost(key, this.selectArray[key])
}
})
},
onSeach() {
this.page = 1
this.page_size = 20
this.getMediaSearch()
},
// 切换每页数据量
handleSizeChange(val) {
this.page_size = val
this.getMediaSearch()
},
// 切换页数
handleCurrentChange(val) {
this.page = val
this.getMediaSearch()
},
handleSelectionChange(val) {
this.selectArray = val
},
// 新增按钮
add() {
this.editVisible = true // 新增或编辑弹出框
this.editData = {
title: '新增',
data: {}
}
},
// 编辑按钮
handleEdit(index, row) {
this.editVisible = true // 新增或编辑弹出框
this.editData = {
title: '查看详情',
data: row
}
},
// 关闭编辑弹窗
closeEdit() {
this.editVisible = false
this.editShowLocationVisible = false
this.showDetail = false
this.getMediaSearch()
},
// 清空某一项筛选列表
onClear(key) {
this.searchData[key] = undefined
this.getMediaSearch()
}
}
}
</script>
@@ -0,0 +1,513 @@
<template>
<el-dialog :title="title" :visible.sync="Visible" width="900px" center class="ac-dialog" :close-on-click-modal="false"
@close="close">
<el-form :inline="true" :model="form" class="demo-form-inline" label-width="120px" label-position="right">
<el-row :gutter="24">
<el-col :xs="12" :sm="12" :md="12" :lg="12" :xl="12">
<el-form-item label="标题">
<el-input v-model="form.name" style="width: 200px" />
</el-form-item>
</el-col>
<el-col :xs="12" :sm="12" :md="12" :lg="12" :xl="12">
<el-form-item label="子标题">
<el-input v-model="form.sub_title" style="width: 200px" />
</el-form-item>
</el-col>
<el-col :xs="12" :sm="12" :md="12" :lg="12" :xl="12">
<el-form-item label="价格">
<el-input v-model="form.money" style="width: 200px" />
</el-form-item>
</el-col>
<el-col :xs="12" :sm="12" :md="12" :lg="12" :xl="12">
<el-form-item label="描述">
<el-input v-model="form.description" style="width: 200px" />
</el-form-item>
</el-col>
<el-col :xs="12" :sm="12" :md="12" :lg="12" :xl="12">
<el-form-item label="作者">
<el-input v-model="form.author" style="width: 200px" />
</el-form-item>
</el-col>
<el-col :xs="12" :sm="12" :md="12" :lg="12" :xl="12">
<el-form-item label="是否有声">
<el-select v-model="form.is_adult" placeholder="请选择是否有声">
<el-option :value="'y'" :label="'是'"></el-option>
<el-option :value="'n'" :label="'否'"></el-option>
</el-select>
</el-form-item>
</el-col>
<el-col :xs="12" :sm="12" :md="12" :lg="12" :xl="12">
<el-form-item label="更新状态">
<el-select v-model="form.update_status" placeholder="请选择更新状态">
<el-option :value="'0'" :label="'更新中'"></el-option>
<el-option :value="'1'" :label="'已完结'"></el-option>
</el-select>
</el-form-item>
</el-col>
<el-col :xs="12" :sm="12" :md="12" :lg="12" :xl="12">
<el-form-item label="分类">
<el-input v-model="form.category_name" style="width: 200px" />
</el-form-item>
</el-col>
<el-col :xs="12" :sm="12" :md="12" :lg="12" :xl="12">
<el-form-item label="章节列表">
<el-button size="small" type="success" @click="showDetailFn(form.chapter)">查看小说章节</el-button>
</el-form-item>
</el-col>
<el-col :xs="12" :sm="12" :md="12" :lg="12" :xl="12">
<el-form-item label="标签">
<el-tag :key="index + 'tagData'" style="margin: 2px" v-for="(item, index) in form.tags" size="mini">
{{ item.name }}
</el-tag>
</el-form-item>
</el-col>
<el-col :lg="12" :md="12" :sm="12" :xl="12" :xs="12">
<el-form-item label="更新时间">
<el-date-picker style="width: 200px" v-model="form.updated_at" type="date" placeholder="选择日期"
value-format="yyyy-MM-ddTHH:mm:ssZ">
</el-date-picker>
</el-form-item>
</el-col>
<el-col :xs="12" :sm="12" :md="12" :lg="12" :xl="12">
<el-form-item label="封面">
<ShowImg style="width: 100px; height: 100px;" :noNeedDoamin="true" :urls="form.img">
</ShowImg>
</el-form-item>
</el-col>
</el-row>
</el-form>
<NovelDetailView v-if="showDetail" :itemData="novelDetailData" @close="showDetail = false" />
<div slot="footer" class="dialog-footer">
<el-button @click.native.prevent="Visible = false"> </el-button>
</div>
</el-dialog>
</template>
<script>
import 'videojs-contrib-hls'
import { lsjNovelDetail } from '@/api/lsjMediaLibrary/novelList.js'
import ShowImg from '@/components/ShowImg/index.vue'
import NovelDetailView from '@/components/NovelDetailView/index.vue'
export default {
name: 'AddOrEdit',
props: ['data'],
components: {
ShowImg,
NovelDetailView
},
data() {
return {
coverTypeList: [
{ label: '横版', value: 'long' },
{ label: '竖版', value: 'short' },
],
novelDetailData: [],
showDetail: false,
type: undefined,
videoType: undefined,
innerVisible: false,
Visible: true,
title: '',
taskId: '',
tags: null,
fieldNameFs: '', // 正片地址全称
form:{
links:{}
},
}
},
async created() {
this.title = this.data.title
if (this.title === '查看详情') {
await this.getVideoDetail()
}
if (this.player) {
this.player.dispose()
}
},
methods: {
showDetailFn(row) {
this.novelDetailData = row
this.showDetail = true
},
getVideoDetail() {
lsjNovelDetail({ id: this.data.data.id }).then((res) => {
if (res.code === 200) {
this.form = res.data
} else {
this.$message.error('请求失败!')
}
})
},
filterM3u8(v) {
return /\.m3u8/g.test(v) ? v : v + '.m3u8'
},
// 清空某一项筛选列表
onClear(key) {
this.form.param[key] = []
},
// 上传图片返回地址
changeCoverImgUrl(data) {
this.form.coverImg = data
},
// 关闭编辑
close() {
if (this.player) {
this.player.dispose()
}
this.$emit('close')
}
}
}
</script>
<style lang="scss">
.el-dialog {
display: flex;
flex-direction: column;
margin: 0 !important;
position: absolute;
top: 50%;
left: 50%;
transform: translate(-50%, -50%);
/*height:600px;*/
max-height: calc(100% - 30px);
max-width: calc(100% - 30px);
}
.el-dialog .el-dialog__body {
flex: 1;
overflow: auto;
}
.videoBox {
display: flex;
justify-content: center;
overflow: hidden;
}
.el-textarea.is-disabled.ti .el-textarea__inner {
color: red;
}
.media-box {
width: 100%;
height: 400px;
text-align: center;
overflow: hidden;
img {
height: 100%;
max-width: 100%;
}
#my-video {
width: 100% !important;
height: 100% !important;
border: none !important;
}
}
.check_upload {
position: relative;
padding: 10px;
overflow: hidden;
border: 1px dashed #ccc;
background-color: #f5f5f5;
div {
display: inline-block;
position: relative;
padding: 4px 8px;
font-size: 100%;
line-height: 1.4;
color: #666;
border: 1px solid #666;
cursor: pointer;
border-radius: 2px;
background: none;
outline: none;
}
}
.itemData-main {
/* rem适配基础设置 */
font-size: 16px;
/* 基准字体大小 */
background: #000;
color: #fff;
height: 844px;
overflow-y: scroll;
padding: 10px;
a,
a:link,
a:visited,
a:hover,
a:active {
text-decoration: none;
color: inherit;
}
.topBox {
display: flex;
align-items: center;
justify-content: space-between;
padding: 8px 16px;
background: #212121;
position: fixed;
top: 0;
left: 0;
width: 100%;
z-index: 99;
/* display: none; */
}
.navBtn {
width: 51px;
height: 24px;
display: flex;
align-items: center;
justify-content: center;
font-size: 10px;
color: #E0E0E0;
border-radius: 6px;
background: rgba(255, 255, 255, 0.10);
}
.navBtn .moreIcon {
width: 16px;
height: 16px;
margin-right: 3px;
}
.logo {
width: 94px;
height: 32px;
}
.searchIcon {
width: 24px;
height: 24px;
margin-left: 27px;
}
.header {
width: 100%;
/* height: 159px; */
background: #212121;
padding: 12px 16px;
box-sizing: border-box;
margin-bottom: 20px;
}
.header .title {
text-align: center;
color: #BDBDBD;
font-size: 26px;
line-height: 32px;
margin-bottom: 14px;
}
.header .info {
font-size: 14px;
line-height: 20px;
color: rgba(255, 255, 255, 0.70);
display: flex;
align-items: center;
display: -webkit-box;
-webkit-box-orient: vertical;
-webkit-line-clamp: 3;
text-overflow: ellipsis;
overflow: hidden;
}
.header .info a {
text-decoration-line: underline;
}
.main .lineBox {
padding: 0 16px;
box-sizing: border-box;
}
.main .lineBox .line {
width: 100%;
height: 1px;
background: rgba(255, 255, 255, 0.10);
margin: 18px 0;
}
.postContent {
margin: 36px 0 0;
}
.postBox {
color: #FAFAFA;
/* margin-bottom: 18px; */
}
.postTitle {
font-size: 24px;
font-weight: 600;
line-height: 32px;
margin-bottom: 28px;
padding: 0 16px;
box-sizing: border-box;
}
.postText {
color: #FAFAFA;
margin: 0 16px 36px;
font-size: 16px;
line-height: 22px;
}
.postimage {
width: 100%;
height: auto;
margin-bottom: 18px;
/* margin-bottom: 47px; */
}
.postDesc {
font-size: 16px;
color: #FAFAFA;
line-height: 22px;
padding: 0 16px;
box-sizing: border-box;
margin-bottom: 19px;
}
.postDesc span {
font-weight: 600;
}
.postLine {
margin: 0 16px;
border-bottom: 1px dashed rgba(255, 255, 255, 0.50);
}
.tagBox {
margin-bottom: 12px;
padding: 0 16px;
}
.tagBox .tagList {
display: flex;
align-items: center;
flex-wrap: wrap;
gap: 7px;
margin-bottom: 18px;
}
.tagBox .tagList .tagItem {
padding: 8px 16px;
box-sizing: border-box;
border-radius: 62px;
background: rgba(255, 255, 255, 0.05);
display: flex;
align-items: center;
justify-content: center;
font-size: 12px;
color: #BDBDBD;
}
.lastDay {
text-align: right;
color: #BDBDBD;
line-height: 20px;
font-size: 14px;
}
.copyBox {
color: #FFF;
text-align: center;
text-shadow: 0 0 20px #FF8400, 0 0 20px #FF8400;
font-family: "PingFang SC";
font-size: 20px;
font-style: normal;
font-weight: 500;
line-height: 28px;
/* 140% */
padding: 18px;
box-sizing: border-box;
margin-bottom: 18px;
}
.copySuccess {
color: #FFF;
text-align: center;
text-shadow: 0 0 20px #FF00B2, 0 0 20px #FF00B2;
font-family: "PingFang SC";
font-size: 20px;
font-style: normal;
font-weight: 500;
line-height: 28px;
/* 140% */
padding: 18px;
box-sizing: border-box;
margin-bottom: 18px;
}
.dplayerBox {
margin-bottom: 18px;
max-height: 300px;
}
.gridAdvBox {
margin: 0 16px 18px;
}
.gridAdvBox .gridAdvTitle {
padding: 0 16px;
box-sizing: border-box;
height: 49px;
display: flex;
align-items: center;
border-top: 1px solid rgba(255, 255, 255, 0.10);
background: rgba(255, 255, 255, 0.05);
font-size: 18px;
font-style: normal;
font-weight: 600;
line-height: 24px;
}
.keywords {
box-sizing: border-box;
font-size: 16px;
line-height: 22px;
color: #BDBDBD;
}
@media screen and (min-width: 768px) {
/* body {
margin-top: 140px;
} */
body main {
max-width: 720px;
margin: 0 auto;
}
.header {
max-width: 720px;
margin: 0 auto;
}
.topBox {
display: none;
}
}
}
</style>
@@ -0,0 +1,334 @@
<template>
<div class="pf-warpper avlist">
<el-row class="table-form">
<el-form :inline="true" :model="searchData" class="form-inline" size="mini">
<el-form-item>
<el-input placeholder="请输入关键词" clearable v-model="searchData.keywords" @clear="onClear('keywords')" />
</el-form-item>
<el-form-item>
<el-input placeholder="请输入ID" clearable v-model="searchData.ids" @clear="onClear('id')" />
</el-form-item>
<el-form-item>
<el-select placeholder="请选择是否完结" clearable v-model="searchData.is_end" @clear="onClear('is_end')">
<el-option label="已完结" value="y" />
<el-option label="未完结" value="n" />
</el-select>
</el-form-item>
<el-form-item>
<el-select placeholder="请选择分类" clearable v-model="searchData.cat_id" @clear="onClear('cat_id')">
<el-option label="有声" value="audio" />
<el-option label="成人" value="18R" />
<el-option label="贤者" value="normal" />
</el-select>
</el-form-item>
<el-form-item>
<el-date-picker v-model="time" type="daterange" range-separator="至" value-format="yyyy-MM-dd HH:mm:ss"
start-placeholder="开始日期" end-placeholder="结束日期">
</el-date-picker>
</el-form-item>
<el-form-item>
<el-button @click="onSeach" icon="el-icon-search" plain type="primary">搜索</el-button>
<!-- <el-button @click="add" icon="el-icon-circle-plus-outline" plain type="success">新增</el-button> -->
<el-button @click="addPostArray" icon="el-icon-circle-plus-outline" plain type="warning">批量加入后台视频库</el-button>
</el-form-item>
</el-form>
</el-row>
<el-row>
<el-col>
<el-table :data="resData" element-loading-text="拼命加载中" border height="735" highlight-current-row
style="width: 100%; font-size: 10px" v-loading="loading" :row-style="{ height: '30px' }"
:cell-style="{ padding: '5px' }" @selection-change="handleSelectionChange">
<el-table-column type="selection" width="50"> </el-table-column>
<el-table-column align="center" label="ID" width="190px">
<template slot-scope="scope">{{ scope.row.id }}</template>
</el-table-column>
<el-table-column align="center" label="标题" width="190px" show-overflow-tooltip>
<template slot-scope="scope">{{ scope.row.name }}</template>
</el-table-column>
<el-table-column align="center" label="子标题" width="190px" show-overflow-tooltip>
<template slot-scope="scope">{{ scope.row.sub_title }}</template>
</el-table-column>
<el-table-column align="center" label="别名" width="390px" show-overflow-tooltip>
<template slot-scope="scope">{{ scope.row.alias_name }}</template>
</el-table-column>
<el-table-column align="center" label="描述" width="190px" show-overflow-tooltip>
<template slot-scope="scope">{{ scope.row.description }}</template>
</el-table-column>
<el-table-column align="center" label="封面" width="80px">
<template slot-scope="scope">
<ShowImg style="width: 30px; height: 30px; margin: 0 auto" :noNeedDoamin="true" :urls="scope.row.img">
</ShowImg>
</template>
</el-table-column>
<el-table-column align="center" label="分类名称" width="390px" show-overflow-tooltip>
<template slot-scope="scope">{{ scope.row.category_name }}</template>
</el-table-column>
<el-table-column align="center" label="章节数量">
<template slot-scope="scope">{{
scope.row.chapter_count
}}</template>
</el-table-column>
<el-table-column align="center" label="标签" width="300px">
<template slot-scope="scope">
<el-tag :key="index + 'tagData'" style="margin: 2px" v-for="(item, index) in scope.row.tags"
size="mini">
{{ item.name }}
</el-tag>
</template>
</el-table-column>
<el-table-column align="center" label="类型">
<template slot-scope="scope">{{ scope.row.type }}</template>
</el-table-column>
<el-table-column align="center" label="价格">
<template slot-scope="scope">{{ scope.row.money }}</template>
</el-table-column>
<el-table-column align="center" label="是否有声" width="110px">
<template slot-scope="scope">
<el-button plain size="mini">{{
scope.row.is_adult === 'y' ? '有声' : '文本' }}</el-button>
</template>
</el-table-column>
<el-table-column align="center" label="更新状态" width="110px">
<template slot-scope="scope">{{
scope.row.update_status | changeUpdateStatus
}}</template>
</el-table-column>
<el-table-column align="center" label="是否完结" width="110px">
<template slot-scope="scope">
<el-button plain size="mini">{{
scope.row.is_end === 'y' ? '已完结' : '未完结' }}</el-button>
</template>
</el-table-column>
<el-table-column align="center" width="120px" label="最后更新时间">
<template slot-scope="scope">{{ scope.row.last_update | BeiJingTime }}</template>
</el-table-column>
<el-table-column align="center" width="120px" label="创建时间">
<template slot-scope="scope">{{ scope.row.created_at | BeiJingTime }}</template>
</el-table-column>
<el-table-column align="center" fixed="right" label="操作" width="300">
<template slot-scope="scope">
<el-button @click="addPost(scope.$index, scope.row)" size="mini"
:type="scope.row.isAdd ? 'info' : 'primary'" :disabled="scope.row.isAdd ? true : false">{{
`${scope.row.isAdd ? '已加入后台资源库' : '加入后台资源库'}` }}</el-button>
<el-button @click="handleEdit(scope.$index, scope.row)" size="mini" type="primary">查看详情</el-button>
<!-- <el-button @click="handleDelete(scope.$index, scope.row)" size="mini" type="danger">删除</el-button> -->
</template>
</el-table-column>
</el-table>
</el-col>
</el-row>
<div class="table-pagination">
<el-pagination :current-page="page" :page-size="page_size"
:page-sizes="[10, 20, 30, 50, 100]" :total="total" @current-change="handleCurrentChange"
@size-change="handleSizeChange" layout="total, sizes, prev, pager, next, jumper" />
</div>
<!-- 查看详情 -->
<Edit :data="editData" v-if="editVisible" @close="closeEdit" />
<NovelDetailView v-if="showDetail" :itemData="novelDetailData" @close="closeEdit"
/>
</div>
</template>
<script>
// 引入模块
import ShowImg from '@/components/ShowImg/index.vue'
import Edit from './components/AddOrEdit'
import { lsjNovelList, lsjNovelDel, lsjNovelAdd } from '@/api/lsjMediaLibrary/novelList.js'
import { audioAdd } from '@/api/novelsManagement/audio.js'
import { isNumber } from 'mathjs/lib/entry/typeChecks'
import NovelDetailView from '@/components/NovelDetailView/index.vue'
export default {
name: 'MediaCat',
components: {
ShowImg,
Edit,
NovelDetailView
},
data() {
return {
page: 1,
page_size: 20,
novelDetailData:[],
// 请求列表参数
searchData: {
id: undefined,
name: undefined, // 外用状态
status: undefined, // "string",当前状态
cat_id: undefined // 视频归类
},
time: undefined,
resData: [], // el-table表格数据
total: 0, // 数据总条数
selectArray: undefined,
editShowLocationVisible: undefined,
showDetail: false,
loading: true, // 列表加载状态
// 编辑数据
editVisible: false, // 新增或编辑弹出框
editData: {
title: '查看详情',
data: {}
}
}
},
filters: {
changeUpdateStatus(v){
switch (v) {
case '0':
return '更新中'
case '1':
return '更新完成'
}
},
},
mounted() {
this.getMediaSearch()
},
methods: {
showDetailFn(row) {
this.novelDetailData = row
this.showDetail = true
},
// TODO:加入后台视频库
addPost(index, row) {
lsjNovelAdd({ id: row.id }).then((res) => {
if (res.code === 200) {
this.$message.success('加入成功!')
this.getMediaSearch()
} else {
this.$message.error('加入失败!')
}
})
},
// 加入后台音频库
addAudioArray() {
Object.keys(this.selectArray).forEach((key) => {
if (!this.selectArray[key].isAdd) {
this.audioListFn(key, this.selectArray[key])
}
})
},
// TODO:加入音频视频库
audioListFn(index, row) {
audioAdd({ fileId: row.id }).then((res) => {
if (res.code === 200) {
this.$message.success('加入成功!')
this.getMediaSearch()
} else {
this.$message.error('加入失败!')
}
})
},
// TODO:请求影片列表数据
getMediaSearch() {
this.loading = true
if(isNumber(this.page)|| isNumber(this.page_size)){
this.searchData.page = this.page + ''
this.searchData.page_size = this.page_size + ''
}
if (this.time) {
this.searchData.start_time = this.time[0]
this.searchData.end_time = this.time[1]
} else {
this.searchData.start_time = undefined
this.searchData.end_time = undefined
}
lsjNovelList(this.searchData).then((res) => {
if (res.code === 200) {
this.resData = res.data.data
this.total = Number(res.data.total)
} else {
this.$message.error('请求列表失败!')
this.resData = []
this.total = 0
}
this.loading = false
})
},
// TODO:删除影片列表数据
handleDelete(index, row) {
this.$confirm('确定删除?', '警告', {
confirmButtonText: '确定',
cancelButtonText: '取消',
type: 'warning'
}).then(() => {
lsjNovelDel({ id: row.id }).then((res) => {
if (res.code === 200) {
this.getMediaSearch()
this.$message.success('成功删除!')
} else {
this.$message.error(res.tip)
}
})
})
},
addPostArray() {
Object.keys(this.selectArray).forEach((key) => {
if (!this.selectArray[key].isAdd) {
this.addPost(key, this.selectArray[key])
}
})
},
onSeach() {
this.page = 1
this.page_size = 20
this.getMediaSearch()
},
// 切换每页数据量
handleSizeChange(val) {
this.page_size = val
this.getMediaSearch()
},
// 切换页数
handleCurrentChange(val) {
this.page = val
this.getMediaSearch()
},
handleSelectionChange(val) {
this.selectArray = val
},
// 新增按钮
add() {
this.editVisible = true // 新增或编辑弹出框
this.editData = {
title: '新增',
data: {}
}
},
// 编辑按钮
handleEdit(index, row) {
this.editVisible = true // 新增或编辑弹出框
this.editData = {
title: '查看详情',
data: row
}
},
// 关闭编辑弹窗
closeEdit() {
this.editVisible = false
this.editShowLocationVisible = false
this.showDetail = false
this.getMediaSearch()
},
// 清空某一项筛选列表
onClear(key) {
this.searchData[key] = undefined
this.getMediaSearch()
}
}
}
</script>
@@ -0,0 +1,543 @@
<template>
<el-dialog :title="title" :visible.sync="Visible" width="1800px" center class="ac-dialog"
:close-on-click-modal="false" @close="close">
<el-form :inline="true" :model="form" class="demo-form-inline" label-width="120px" label-position="right">
<el-row :gutter="24">
<el-col :xs="24" :sm="24" :md="12" :lg="12" :xl="12">
<el-form-item label="标题">
<el-input v-model="form.title" style="width: 315px" />
</el-form-item>
</el-col>
<el-col :xs="24" :sm="24" :md="12" :lg="12" :xl="12">
<el-form-item label="内容">
<el-input v-model="form.content" style="width: 315px" />
</el-form-item>
</el-col>
<el-col :xs="24" :sm="24" :md="12" :lg="12" :xl="12">
<el-form-item label="封面">
<ShowImg style="width: 300px; height: 300px; margin: 0 auto" :noNeedDoamin="true" :urls="form.img">
</ShowImg>
</el-form-item>
</el-col>
<!-- <el-col :xs="8" :sm="8" :md="8" :lg="8" :xl="8">
<el-form-item label="上架状态">
<el-switch
v-model="form.status"
active-color="#13ce66"
inactive-color="#ff4949"
style="width: 180px"></el-switch>
</el-form-item>
</el-col> -->
<!-- <el-col :xs="8" :sm="8" :md="8" :lg="8" :xl="8">
<el-form-item label="付费类型">
<el-switch
v-model="form.update_status"
active-color="#13ce66"
inactive-color="#ff4949"
style="width: 180px"></el-switch>
</el-form-item>
</el-col> -->
<el-col :xs="8" :sm="8" :md="8" :lg="8" :xl="8">
<el-form-item label="分类">
<el-tag :key="index + 'tagData'" style="margin: 2px" v-for="(item, index) in form.categories" size="mini">
{{ item.name }}
</el-tag>
</el-form-item>
</el-col>
<el-col :lg="8" :md="8" :sm="8" :xl="8" :xs="8">
<el-form-item label="更新时间">
<el-date-picker style="width: 180px" v-model="form.time" type="date" placeholder="选择日期"
value-format="yyyy-MM-ddTHH:mm:ssZ">
</el-date-picker>
</el-form-item>
</el-col>
<el-col>
<el-form-item label="节点内容">
<div class="itemData-main">
<div class="postContent">
<div class="postBox" v-for="(item, index) in form.files" :key="index">
<!-- <p class="postTitle">{{ item.title }}</p> -->
<ShowImg :noNeedDoamin='true' :key="imgINdex" :urls="item.image" />
<!-- <span class="postText">{{ item.text }}</span> -->
<DPlayer ref="player" class="dplayerBox" v-if="item.video_link" :video="{
url: filterM3u8(item.video_link),
type: 'hls',
pic: '',
}" hotkey></DPlayer>
</div>
</div>
</div>
</el-form-item>
</el-col>
</el-row>
</el-form>
<div slot="footer" class="dialog-footer">
<el-button @click.native.prevent="Visible = false"> </el-button>
</div>
</el-dialog>
</template>
<script>
import DPlayer from '@/components/VueDplayerHls/index'
import 'videojs-contrib-hls'
import { lsjPostDetail } from '@/api/lsjMediaLibrary/postList.js'
import ShowImg from '@/components/ShowImg/index.vue'
export default {
name: 'AddOrEdit',
props: ['data'],
components: {
DPlayer,
ShowImg
},
data() {
return {
coverTypeList: [
{ label: '横版', value: 'long' },
{ label: '竖版', value: 'short' },
],
type: undefined,
videoType: undefined,
innerVisible: false,
Visible: true,
title: '',
taskId: '',
tags: null,
fieldNameFs: '', // 正片地址全称
form: {
links: [{
m3u8_url: '',
preview_m3u8_url: '',
}]
},
}
},
async created() {
this.title = this.data.title
if (this.title === '查看详情') {
await this.getVideoDetail()
if (this.form.links.m3u8_url) {
this.open()
}
}
if (this.player) {
this.player.dispose()
}
},
methods: {
getVideoDetail() {
lsjPostDetail({ id: this.data.data.id }).then((res) => {
if (res.code === 200) {
this.form = res.data
} else {
this.$message.error('请求失败!')
}
})
},
filterM3u8(v) {
return /\.m3u8/g.test(v) ? v : v + '.m3u8'
},
// 清空某一项筛选列表
onClear(key) {
this.form.param[key] = []
},
// 上传图片返回地址
changeCoverImgUrl(data) {
this.form.coverImg = data
},
// / 监听视频播放的回调函数
onPlayerPlay() { },
// / 监听暂停播放的回调函数
onPlayerPause() { },
// / 监听当前视频数据加载完成
onPlayerLoadeddata() { },
// / 监听当前视频数据加载失败
onPlayerError() { },
// / 监听当前视频数据加载ing
onPlayerWaiting() { },
// / 监听当前视频播放完成
onPlayerEnded() { },
open() {
this.mediaUrl =
'api/web/media/m3u8/' +
(this.form.links[0].m3u8_url.match(RegExp(/.m3u8/))
? this.form.links[0].m3u8_url
: this.form.links[0].m3u8_url + '.m3u8')
// this.$nextTick(function () {
// document.getElementById("media-box").innerHTML =
// '<video id="my-video" class="video-js vjs-default-skin" controls preload="auto" style="width:100%;height:100%; " playsinline="true"></video>';
// this.player = videojs("my-video", {
// bigPlayButton: false,
// textTrackDisplay: false,
// posterImage: true,
// errorDisplay: true,
// controlBar: true,
// playbackRates: [0.5, 1, 1.5, 2, 3, 5, 10],
// });
// this.player.src(this.mediaUrl);
// });
},
// 关闭编辑
close() {
if (this.player) {
this.player.dispose()
}
this.$emit('close')
}
}
}
</script>
<style lang="scss">
.el-dialog {
display: flex;
flex-direction: column;
margin: 0 !important;
position: absolute;
top: 50%;
left: 50%;
transform: translate(-50%, -50%);
/*height:600px;*/
max-height: calc(100% - 30px);
max-width: calc(100% - 30px);
}
.el-dialog .el-dialog__body {
flex: 1;
overflow: auto;
}
.videoBox {
display: flex;
justify-content: center;
overflow: hidden;
}
.el-textarea.is-disabled.ti .el-textarea__inner {
color: red;
}
.media-box {
width: 100%;
height: 400px;
text-align: center;
overflow: hidden;
img {
height: 100%;
max-width: 100%;
}
#my-video {
width: 100% !important;
height: 100% !important;
border: none !important;
}
}
.check_upload {
position: relative;
padding: 10px;
overflow: hidden;
border: 1px dashed #ccc;
background-color: #f5f5f5;
div {
display: inline-block;
position: relative;
padding: 4px 8px;
font-size: 100%;
line-height: 1.4;
color: #666;
border: 1px solid #666;
cursor: pointer;
border-radius: 2px;
background: none;
outline: none;
}
}
.itemData-main {
/* rem适配基础设置 */
font-size: 16px;
/* 基准字体大小 */
background: #000;
color: #fff;
height: 844px;
overflow-y: scroll;
padding: 10px;
a,
a:link,
a:visited,
a:hover,
a:active {
text-decoration: none;
color: inherit;
}
.topBox {
display: flex;
align-items: center;
justify-content: space-between;
padding: 8px 16px;
background: #212121;
position: fixed;
top: 0;
left: 0;
width: 100%;
z-index: 99;
/* display: none; */
}
.navBtn {
width: 51px;
height: 24px;
display: flex;
align-items: center;
justify-content: center;
font-size: 10px;
color: #E0E0E0;
border-radius: 6px;
background: rgba(255, 255, 255, 0.10);
}
.navBtn .moreIcon {
width: 16px;
height: 16px;
margin-right: 3px;
}
.logo {
width: 94px;
height: 32px;
}
.searchIcon {
width: 24px;
height: 24px;
margin-left: 27px;
}
.header {
width: 100%;
/* height: 159px; */
background: #212121;
padding: 12px 16px;
box-sizing: border-box;
margin-bottom: 20px;
}
.header .title {
text-align: center;
color: #BDBDBD;
font-size: 26px;
line-height: 32px;
margin-bottom: 14px;
}
.header .info {
font-size: 14px;
line-height: 20px;
color: rgba(255, 255, 255, 0.70);
display: flex;
align-items: center;
display: -webkit-box;
-webkit-box-orient: vertical;
-webkit-line-clamp: 3;
text-overflow: ellipsis;
overflow: hidden;
}
.header .info a {
text-decoration-line: underline;
}
.main .lineBox {
padding: 0 16px;
box-sizing: border-box;
}
.main .lineBox .line {
width: 100%;
height: 1px;
background: rgba(255, 255, 255, 0.10);
margin: 18px 0;
}
.postContent {
margin: 36px 0 0;
}
.postBox {
color: #FAFAFA;
/* margin-bottom: 18px; */
}
.postTitle {
font-size: 24px;
font-weight: 600;
line-height: 32px;
margin-bottom: 28px;
padding: 0 16px;
box-sizing: border-box;
}
.postText {
color: #FAFAFA;
margin: 0 16px 36px;
font-size: 16px;
line-height: 22px;
}
.postimage {
width: 100%;
height: auto;
margin-bottom: 18px;
/* margin-bottom: 47px; */
}
.postDesc {
font-size: 16px;
color: #FAFAFA;
line-height: 22px;
padding: 0 16px;
box-sizing: border-box;
margin-bottom: 19px;
}
.postDesc span {
font-weight: 600;
}
.postLine {
margin: 0 16px;
border-bottom: 1px dashed rgba(255, 255, 255, 0.50);
}
.tagBox {
margin-bottom: 12px;
padding: 0 16px;
}
.tagBox .tagList {
display: flex;
align-items: center;
flex-wrap: wrap;
gap: 7px;
margin-bottom: 18px;
}
.tagBox .tagList .tagItem {
padding: 8px 16px;
box-sizing: border-box;
border-radius: 62px;
background: rgba(255, 255, 255, 0.05);
display: flex;
align-items: center;
justify-content: center;
font-size: 12px;
color: #BDBDBD;
}
.lastDay {
text-align: right;
color: #BDBDBD;
line-height: 20px;
font-size: 14px;
}
.copyBox {
color: #FFF;
text-align: center;
text-shadow: 0 0 20px #FF8400, 0 0 20px #FF8400;
font-family: "PingFang SC";
font-size: 20px;
font-style: normal;
font-weight: 500;
line-height: 28px;
/* 140% */
padding: 18px;
box-sizing: border-box;
margin-bottom: 18px;
}
.copySuccess {
color: #FFF;
text-align: center;
text-shadow: 0 0 20px #FF00B2, 0 0 20px #FF00B2;
font-family: "PingFang SC";
font-size: 20px;
font-style: normal;
font-weight: 500;
line-height: 28px;
/* 140% */
padding: 18px;
box-sizing: border-box;
margin-bottom: 18px;
}
.dplayerBox {
margin-bottom: 18px;
max-height: 300px;
}
.gridAdvBox {
margin: 0 16px 18px;
}
.gridAdvBox .gridAdvTitle {
padding: 0 16px;
box-sizing: border-box;
height: 49px;
display: flex;
align-items: center;
border-top: 1px solid rgba(255, 255, 255, 0.10);
background: rgba(255, 255, 255, 0.05);
font-size: 18px;
font-style: normal;
font-weight: 600;
line-height: 24px;
}
.keywords {
box-sizing: border-box;
font-size: 16px;
line-height: 22px;
color: #BDBDBD;
}
@media screen and (min-width: 768px) {
/* body {
margin-top: 140px;
} */
body main {
max-width: 720px;
margin: 0 auto;
}
.header {
max-width: 720px;
margin: 0 auto;
}
.topBox {
display: none;
}
}
}
</style>
@@ -0,0 +1,354 @@
<template>
<div class="pf-warpper avlist">
<el-row class="table-form">
<el-form :inline="true" :model="searchData" class="form-inline" size="mini">
<el-form-item>
<el-input placeholder="请输入关键词" clearable v-model="searchData.keywords" @clear="onClear('keywords')" />
</el-form-item>
<el-form-item>
<el-input placeholder="请输入ID" clearable v-model="searchData.id" @clear="onClear('id')" />
</el-form-item>
<el-form-item>
<el-input placeholder="请输入up主id" clearable v-model="searchData.home_id" @clear="onClear('home_id')" />
</el-form-item>
<el-form-item>
<el-select placeholder="请选择付费状态" clearable v-model="searchData.pay_type" @clear="onClear('pay_type')">
<el-option label="金币" value="1" />
<el-option label="会员" value="2" />
<el-option label="免费" value="0" />
</el-select>
</el-form-item>
<el-form-item>
<el-select placeholder="请选择内容类型" clearable v-model="searchData.position" @clear="onClear('position')">
<el-option v-for="item in positionList" :key="item.value" :label="item.label" :value="item.value" />
</el-select>
</el-form-item>
<el-form-item>
<el-date-picker v-model="time" type="daterange" range-separator="至" value-format="yyyy-MM-dd HH:mm:ss"
start-placeholder="开始日期" end-placeholder="结束日期">
</el-date-picker>
</el-form-item>
<el-form-item>
<el-button @click="onSeach" icon="el-icon-search" plain type="primary">搜索</el-button>
<!-- <el-button @click="add" icon="el-icon-circle-plus-outline" plain type="success">新增</el-button> -->
<el-button @click="addPostArray" icon="el-icon-circle-plus-outline" plain type="warning">批量加入后台视频库</el-button>
<el-button @click="addOutside" icon="el-icon-circle-plus-outline" plain type="warning">批量加入外用列表</el-button>
</el-form-item>
</el-form>
</el-row>
<el-row>
<el-col>
<el-table :data="resData" element-loading-text="拼命加载中" border height="735" highlight-current-row
style="width: 100%; font-size: 10px" v-loading="loading" :row-style="{ height: '30px' }"
:cell-style="{ padding: '5px' }" @selection-change="handleSelectionChange">
<el-table-column type="selection" width="50"> </el-table-column>
<el-table-column align="center" label="帖子ID" width="190px">
<template slot-scope="scope">{{ scope.row.id }}</template>
</el-table-column>
<el-table-column align="center" label="帖子标题" width="190px" show-overflow-tooltip>
<template slot-scope="scope">{{ scope.row.title }}</template>
</el-table-column>
<el-table-column align="center" label="帖子内容" width="390px" show-overflow-tooltip>
<template slot-scope="scope">{{ scope.row.content }}</template>
</el-table-column>
<el-table-column align="center" label="帖子内容预览" width="130px">
<template slot-scope="scope">
<el-button slot="reference" size="small" @click="showDetailFn(scope.row.files)">节点内容预览</el-button>
</template>
</el-table-column>
<el-table-column align="center" label="帖子类型">
<template slot-scope="scope">{{
scope.row.position | changePosition
}}</template>
</el-table-column>
<el-table-column align="center" label="发布者ID">
<template slot-scope="scope" v-if="scope.row.up_user">{{
scope.row.up_user.id
}}</template>
</el-table-column>
<el-table-column align="center" label="发布者昵称">
<template slot-scope="scope" v-if="scope.row.up_user">{{
scope.row.up_user.nickname
}}</template>
</el-table-column>
<el-table-column align="center" label="帖子封面" width="80px">
<template slot-scope="scope">
<ShowImg style="width: 30px; height: 30px; margin: 0 auto" :noNeedDoamin="true" :urls="scope.row.img">
</ShowImg>
</template>
</el-table-column>
<el-table-column align="center" label="帖子封面数量">
<template slot-scope="scope">{{
scope.row.img_count
}}</template>
</el-table-column>
<el-table-column align="center" label="分类" width="300px">
<template slot-scope="scope">
<el-tag :key="index + 'tagData'" style="margin: 2px" v-for="(item, index) in scope.row.categories"
size="mini">
{{ item.name }}
</el-tag>
</template>
</el-table-column>
<el-table-column align="center" label="价格">
<template slot-scope="scope">{{ scope.row.money }}</template>
</el-table-column>
<el-table-column align="center" label="付费类型" width="110px">
<template slot-scope="scope">
<el-button plain size="mini">{{
scope.row.pay_type === 1 ? '金币' : scope.row.pay_type === 2 ? '会员' :'免费' }}</el-button>
</template>
</el-table-column>
<el-table-column align="center" width="120px" label="更新时间">
<template slot-scope="scope">{{ scope.row.time | BeiJingTime }}</template>
</el-table-column>
<el-table-column align="center" fixed="right" label="操作" width="300">
<template slot-scope="scope">
<el-button @click="addPost(scope.$index, scope.row)" size="mini"
:type="scope.row.isAdd ? 'info' : 'primary'" :disabled="scope.row.isAdd ? true : false">{{
`${scope.row.isAdd ? '已加入后台资源库' : '加入后台资源库'}` }}</el-button>
<el-button @click="handleEdit(scope.$index, scope.row)" size="mini" type="primary">查看详情</el-button>
<!-- <el-button @click="handleDelete(scope.$index, scope.row)" size="mini" type="danger">删除</el-button> -->
</template>
</el-table-column>
</el-table>
</el-col>
</el-row>
<div class="table-pagination">
<el-pagination :current-page="searchData.page" :page-size="searchData.page_size"
:page-sizes="[10, 20, 30, 50, 100]" :total="total" @current-change="handleCurrentChange"
@size-change="handleSizeChange" layout="total, sizes, prev, pager, next, jumper" />
</div>
<!-- 查看详情 -->
<Edit :data="editData" v-if="editVisible" @close="closeEdit" />
<PostDetailView v-if="showDetail" :itemData="postDetailData" @close="closeEdit"
/>
</div>
</template>
<script>
// 引入模块
import ShowImg from '@/components/ShowImg/index.vue'
import Edit from './components/AddOrEdit'
import { lsjPostList, lsjPostDel, lsjPostAdd } from '@/api/lsjMediaLibrary/postList.js'
import {
positionList, statusList
} from '@/filters/lsjMediaLibrary/videoList.js'
import { audioAdd } from '@/api/novelsManagement/audio.js'
import PostDetailView from '@/components/PostDetailView/index.vue'
import { isNumber } from 'mathjs/lib/entry/typeChecks'
export default {
name: 'MediaCat',
components: {
ShowImg,
Edit,
PostDetailView
},
data() {
return {
positionList: positionList(),
statusList: statusList(),
page: 1,
page_size: 20,
// 请求列表参数
searchData: {
position: 'guochan', // 番号
id: undefined,
name: undefined, // 外用状态
status: undefined, // "string",当前状态
cat_id: undefined // 视频归类
},
time: undefined,
resData: [], // el-table表格数据
total: 0, // 数据总条数
selectArray: undefined,
editShowLocationVisible: undefined,
showDetail: false,
loading: true, // 列表加载状态
// 编辑数据
editVisible: false, // 新增或编辑弹出框
editData: {
title: '查看详情',
data: {}
}
}
},
filters: {
changeFormat(val) {
switch (val) {
case 1:
return '长视频'
case 2:
return '短视频'
case 3:
return '预览'
}
},
changeContentType(val) {
switch (val) {
case 1:
return 'AV(日本)'
case 2:
return '短视频(国产)'
case 3:
return '动漫'
}
}
},
mounted() {
this.getMediaSearch()
},
methods: {
showDetailFn(row) {
this.postDetailData = row
this.showDetail = true
},
addOutside() {
this.editShowLocationVisible = true
this.editData = {
title: '',
data: this.selectArray
}
},
// TODO:加入后台视频库
addPost(index, row) {
lsjPostAdd({ id: row.id }).then((res) => {
if (res.code === 200) {
this.$message.success('加入成功!')
this.getMediaSearch()
} else {
this.$message.error('加入失败!')
}
})
},
// 加入后台音频库
addAudioArray() {
Object.keys(this.selectArray).forEach((key) => {
if (!this.selectArray[key].isAdd) {
this.audioListFn(key, this.selectArray[key])
}
})
},
// TODO:加入音频视频库
audioListFn(index, row) {
audioAdd({ id: row.id }).then((res) => {
if (res.code === 200) {
this.$message.success('加入成功!')
this.getMediaSearch()
} else {
this.$message.error('加入失败!')
}
})
},
// TODO:请求影片列表数据
getMediaSearch() {
this.loading = true
if(isNumber(this.page)|| isNumber(this.page_size)){
this.searchData.page = this.page + ''
this.searchData.page_size = this.page_size + ''
}
if (this.time) {
this.searchData.start_time = this.time[0]
this.searchData.end_time = this.time[1]
} else {
this.searchData.start_time = undefined
this.searchData.end_time = undefined
}
lsjPostList(this.searchData).then((res) => {
if (res.code === 200) {
this.resData = res.data.data
this.total = Number(res.data.total)
} else {
this.$message.error('请求列表失败!')
this.resData = []
this.total = 0
}
this.loading = false
})
},
// TODO:删除影片列表数据
handleDelete(index, row) {
this.$confirm('确定删除?', '警告', {
confirmButtonText: '确定',
cancelButtonText: '取消',
type: 'warning'
}).then(() => {
lsjPostDel({ id: row.id }).then((res) => {
if (res.code === 200) {
this.getMediaSearch()
this.$message.success('成功删除!')
} else {
this.$message.error(res.tip)
}
})
})
},
addPostArray() {
Object.keys(this.selectArray).forEach((key) => {
if (!this.selectArray[key].isAdd) {
this.addPost(key, this.selectArray[key])
}
})
},
onSeach() {
this.searchData.page = 1
this.searchData.page_size = 20
this.getMediaSearch()
},
// 切换每页数据量
handleSizeChange(val) {
this.searchData.page_size = val
this.getMediaSearch()
},
// 切换页数
handleCurrentChange(val) {
this.searchData.page = val
this.getMediaSearch()
},
handleSelectionChange(val) {
this.selectArray = val
},
// 新增按钮
add() {
this.editVisible = true // 新增或编辑弹出框
this.editData = {
title: '新增',
data: {}
}
},
// 编辑按钮
handleEdit(index, row) {
this.editVisible = true // 新增或编辑弹出框
this.editData = {
title: '查看详情',
data: row
}
},
// 关闭编辑弹窗
closeEdit() {
this.editVisible = false
this.editShowLocationVisible = false
this.showDetail = false
this.getMediaSearch()
},
// 清空某一项筛选列表
onClear(key) {
this.searchData[key] = undefined
this.getMediaSearch()
}
}
}
</script>
@@ -0,0 +1,360 @@
<template>
<el-dialog
:title="title"
:visible.sync="Visible"
width="1800px"
center
class="ac-dialog"
:close-on-click-modal="false"
@close="close">
<el-form :inline="true" :model="form" class="demo-form-inline" label-width="120px" label-position="right">
<el-row :gutter="24">
<el-col :xs="24" :sm="24" :md="12" :lg="12" :xl="12">
<el-form-item label="标题">
<el-input v-model="form.name" style="width: 315px" />
</el-form-item>
</el-col>
<el-col :xs="24" :sm="24" :md="12" :lg="12" :xl="12">
<el-form-item label="视频分类ID">
<el-input v-model="form.cat_id" style="width: 315px" />
</el-form-item>
</el-col>
<el-col :xs="24" :sm="24" :md="12" :lg="12" :xl="12">
<el-form-item label="视频分类名称">
<el-input v-model="form.cat_name" style="width: 315px" />
</el-form-item>
</el-col>
<el-col :xs="24" :sm="24" :md="12" :lg="12" :xl="12">
<el-form-item label="视频描述">
<el-input v-model="form.description" style="width: 315px" />
</el-form-item>
</el-col>
<el-col :xs="24" :sm="24" :md="12" :lg="12" :xl="12">
<el-form-item label="视频导演">
<el-input v-model="form.director" style="width: 315px" />
</el-form-item>
</el-col>
<el-col :xs="24" :sm="24" :md="12" :lg="12" :xl="12">
<el-form-item label="视频语言">
<el-input v-model="form.language" style="width: 315px" />
</el-form-item>
</el-col>
<el-col :xs="24" :sm="24" :md="12" :lg="12" :xl="12">
<el-form-item label="视频系列">
<el-input v-model="form.series" style="width: 315px" />
</el-form-item>
</el-col>
<el-col :xs="24" :sm="24" :md="12" :lg="12" :xl="12">
<el-form-item label="封面类型">
<el-select style="width: 180px" placeholder="请选择封面类型" v-model="form.img_type">
<el-option :key="item.value" :label="item.label" :value="item.value" v-for="item in coverTypeList" />
</el-select>
</el-form-item>
</el-col>
<el-col :xs="24" :sm="24" :md="12" :lg="12" :xl="12">
<el-form-item label="横版封面">
<ShowImg style="width: 330px; height: 150px; margin: 0 auto" :noNeedDoamin="true" :urls="form.img_x"></ShowImg>
</el-form-item>
</el-col>
<el-col :xs="24" :sm="24" :md="12" :lg="12" :xl="12">
<el-form-item label="竖版封面">
<ShowImg style="width: 120px; height: 300px; margin: 0 auto" :noNeedDoamin="true" :urls="form.img_y"></ShowImg>
</el-form-item>
</el-col>
<el-col :xs="24" :sm="24" :md="12" :lg="12" :xl="12">
<el-form-item label="预览图片">
<ShowImg style="width: 300px; height: 300px; margin: 0 auto" :noNeedDoamin="true" :urls="form.preview_images"></ShowImg>
</el-form-item>
</el-col>
<el-col :xs="8" :sm="8" :md="8" :lg="8" :xl="8">
<el-form-item label="是否多集">
<el-switch
v-model="form.is_more_link"
active-color="#13ce66"
inactive-color="#ff4949"
style="width: 180px"></el-switch>
</el-form-item>
</el-col>
<el-col :xs="8" :sm="8" :md="8" :lg="8" :xl="8">
<el-form-item label="上架状态">
<el-switch
v-model="form.status"
active-color="#13ce66"
inactive-color="#ff4949"
style="width: 180px"></el-switch>
</el-form-item>
</el-col>
<el-col :xs="8" :sm="8" :md="8" :lg="8" :xl="8">
<el-form-item label="更新状态">
<el-switch
v-model="form.update_status"
active-color="#13ce66"
inactive-color="#ff4949"
style="width: 180px"></el-switch>
</el-form-item>
</el-col>
<el-col :xs="8" :sm="8" :md="8" :lg="8" :xl="8">
<el-form-item label="标签">
<el-tag :key="index + 'tagData'" style="margin: 2px" v-for="(item, index) in form.tags" size="mini">
{{ item.name }}
</el-tag>
</el-form-item>
</el-col>
<el-col :xs="8" :sm="8" :md="8" :lg="8" :xl="8">
<el-form-item label="采集网站标签">
<el-tag :key="index + 'tagData'" style="margin: 2px" v-for="(item, index) in form.source_tags" size="mini">
{{ item }}
</el-tag>
</el-form-item>
</el-col>
<el-col :lg="8" :md="8" :sm="8" :xl="8" :xs="8">
<el-form-item label="上传时间">
<el-date-picker
style="width: 180px"
v-model="form.issue_date"
type="date"
placeholder="选择日期"
value-format="yyyy-MM-ddTHH:mm:ssZ">
</el-date-picker>
</el-form-item>
</el-col>
<el-col :lg="8" :md="8" :sm="8" :xl="8" :xs="8">
<el-form-item label="上架时间">
<el-date-picker
style="width: 180px"
v-model="form.show_at"
type="date"
placeholder="选择日期"
value-format="yyyy-MM-ddTHH:mm:ssZ">
</el-date-picker>
</el-form-item>
</el-col>
</el-row>
</el-form>
<div style="display: flex;">
<div style="margin-right: 100px;">
<h3>预览</h3>
<div style="width: 380px; height: 240px; overflow: hidden">
<DPlayer
ref="player"
v-if="form.links[0].preview_m3u8_url.indexOf('mp4') === -1"
:video="{
url: filterM3u8(form.links[0].preview_m3u8_url),
type: 'hls',
pic: '',
}"
hotkey></DPlayer>
</div>
</div>
<div >
<h3>正片</h3>
<div v-if="form.links[0].m3u8_url" style="width: 380px; height: 240px; overflow: hidden">
<DPlayer
:video="{
url: filterM3u8(form.links[0].m3u8_url),
type: 'hls',
pic: '',
}"
hotkey></DPlayer>
</div>
</div>
</div>
<div slot="footer" class="dialog-footer">
<el-button @click.native.prevent="Visible = false"> </el-button>
</div>
</el-dialog>
</template>
<script>
import DPlayer from '@/components/VueDplayerHls/index'
import 'videojs-contrib-hls'
import { lsjVideoDetail } from '@/api/lsjMediaLibrary/videoList.js'
import ShowImg from '@/components/ShowImg/index.vue'
export default {
name: 'AddOrEdit',
props: ['data'],
components: {
DPlayer,
ShowImg
},
data() {
return {
coverTypeList: [
{label:'横版',value:'long'},
{label:'竖版',value:'short'},
],
type: undefined,
videoType: undefined,
innerVisible: false,
Visible: true,
title: '',
taskId: '',
tags: null,
fieldNameFs: '', // 正片地址全称
form: {
links:[{
m3u8_url:'',
preview_m3u8_url:'',
}]
},
}
},
async created() {
this.title = this.data.title
if (this.title === '查看详情') {
await this.getVideoDetail()
if (this.form.links.m3u8_url) {
this.open()
}
}
if (this.player) {
this.player.dispose()
}
},
methods: {
getVideoDetail(){
lsjVideoDetail({ id: this.data.data.id }).then((res) => {
if (res.code === 200) {
this.form= res.data
} else {
this.$message.error('请求失败!')
}
})
},
filterM3u8(v) {
return /\.m3u8/g.test(v) ? v : v + '.m3u8'
},
// 清空某一项筛选列表
onClear(key) {
this.form.param[key] = []
},
// 上传图片返回地址
changeCoverImgUrl(data) {
this.form.coverImg = data
},
// / 监听视频播放的回调函数
onPlayerPlay() { },
// / 监听暂停播放的回调函数
onPlayerPause() { },
// / 监听当前视频数据加载完成
onPlayerLoadeddata() { },
// / 监听当前视频数据加载失败
onPlayerError() { },
// / 监听当前视频数据加载ing
onPlayerWaiting() { },
// / 监听当前视频播放完成
onPlayerEnded() { },
open() {
this.mediaUrl =
'api/web/media/m3u8/' +
(this.form.links[0].m3u8_url.match(RegExp(/.m3u8/))
? this.form.links[0].m3u8_url
: this.form.links[0].m3u8_url + '.m3u8')
// this.$nextTick(function () {
// document.getElementById("media-box").innerHTML =
// '<video id="my-video" class="video-js vjs-default-skin" controls preload="auto" style="width:100%;height:100%; " playsinline="true"></video>';
// this.player = videojs("my-video", {
// bigPlayButton: false,
// textTrackDisplay: false,
// posterImage: true,
// errorDisplay: true,
// controlBar: true,
// playbackRates: [0.5, 1, 1.5, 2, 3, 5, 10],
// });
// this.player.src(this.mediaUrl);
// });
},
// 关闭编辑
close() {
if (this.player) {
this.player.dispose()
}
this.$emit('close')
}
}
}
</script>
<style lang="scss">
.el-dialog {
display: flex;
flex-direction: column;
margin: 0 !important;
position: absolute;
top: 50%;
left: 50%;
transform: translate(-50%, -50%);
/*height:600px;*/
max-height: calc(100% - 30px);
max-width: calc(100% - 30px);
}
.el-dialog .el-dialog__body {
flex: 1;
overflow: auto;
}
.videoBox {
display: flex;
justify-content: center;
overflow: hidden;
}
.el-textarea.is-disabled.ti .el-textarea__inner {
color: red;
}
.media-box {
width: 100%;
height: 400px;
text-align: center;
overflow: hidden;
img {
height: 100%;
max-width: 100%;
}
#my-video {
width: 100% !important;
height: 100% !important;
border: none !important;
}
}
.check_upload {
position: relative;
padding: 10px;
overflow: hidden;
border: 1px dashed #ccc;
background-color: #f5f5f5;
div {
display: inline-block;
position: relative;
padding: 4px 8px;
font-size: 100%;
line-height: 1.4;
color: #666;
border: 1px solid #666;
cursor: pointer;
border-radius: 2px;
background: none;
outline: none;
}
}</style>
@@ -0,0 +1,401 @@
<template>
<div class="pf-warpper avlist">
<el-row class="table-form">
<el-form :inline="true" :model="searchData" class="form-inline" size="mini">
<el-form-item>
<el-input placeholder="请输入ID" clearable v-model="searchData.ids" @clear="onClear('ids')" />
</el-form-item>
<el-form-item>
<el-input placeholder="请输入up主id" clearable v-model="searchData.home_id" @clear="onClear('home_id')" />
</el-form-item>
<el-form-item>
<el-input placeholder="请输入关键字" clearable v-model="searchData.keywords" @clear="onClear('keywords')" />
</el-form-item>
<el-form-item>
<el-select placeholder="请选择更新状态" clearable v-model="searchData.update_status" @clear="onClear('update_status')">
<el-option label="已完结" value="1" />
<el-option label="未完结" value="0" />
</el-select>
</el-form-item>
<el-form-item>
<el-input placeholder="请输入mid,多个用,分开" clearable v-model="searchData.mid" @clear="onClear('mid')" />
</el-form-item>
<el-form-item>
<el-select
placeholder="请选择视频分类类型"
clearable
v-model="searchData.cat_id"
@clear="onClear('cat_id')">
<el-option v-for="item in videoTypeList" :key="item.value" :label="item.value" :value="item.label" />
</el-select>
</el-form-item>
<el-form-item>
<el-select placeholder="请选择内容类型" clearable v-model="searchData.position" @clear="onClear('position')">
<el-option v-for="item in positionList" :key="item.value" :label="item.label" :value="item.value" />
</el-select>
</el-form-item>
<el-form-item>
<el-date-picker
v-model="time"
type="daterange"
range-separator=""
value-format="yyyy-MM-dd HH:mm:ss"
start-placeholder="开始日期"
end-placeholder="结束日期">
</el-date-picker>
</el-form-item>
<el-form-item>
<el-button @click="onSeach" icon="el-icon-search" plain type="primary">搜索</el-button>
<!-- <el-button @click="add" icon="el-icon-circle-plus-outline" plain type="success">新增</el-button> -->
<el-button
@click="addAudioArray"
icon="el-icon-circle-plus-outline"
plain
type="warning">批量加入音频视频库</el-button>
<el-button
@click="addVideoArray"
icon="el-icon-circle-plus-outline"
plain
type="warning">批量加入后台视频库</el-button>
<el-button @click="addOutside" icon="el-icon-circle-plus-outline" plain type="warning">批量加入外用列表</el-button>
</el-form-item>
</el-form>
</el-row>
<el-row>
<el-col>
<el-table
:data="resData"
element-loading-text="拼命加载中"
border
height="735"
highlight-current-row
style="width: 100%; font-size: 10px"
v-loading="loading"
:row-style="{ height: '30px' }"
:cell-style="{ padding: '5px' }"
@selection-change="handleSelectionChange">
<el-table-column type="selection" width="50"> </el-table-column>
<el-table-column align="center" label="视频ID" width="190px">
<template slot-scope="scope">{{ scope.row.id }}</template>
</el-table-column>
<el-table-column align="center" label="视频标题" width="190px" show-overflow-tooltip>
<template slot-scope="scope">{{ scope.row.name }}</template>
</el-table-column>
<el-table-column align="center" label="视频描述" width="190px" show-overflow-tooltip>
<template slot-scope="scope">{{ scope.row.description }}</template>
</el-table-column>
<el-table-column align="center" label="视频定位">
<template slot-scope="scope">{{
scope.row.position | changePosition
}}</template>
</el-table-column>
<el-table-column align="center" label="up主名称">
<template slot-scope="scope">{{
scope.row.up_user
}}</template>
</el-table-column>
<el-table-column align="center" label="视频分类ID">
<template slot-scope="scope">{{
scope.row.cat_id
}}</template>
</el-table-column>
<el-table-column align="center" label="视频分类名称">
<template slot-scope="scope">{{
scope.row.cat_name
}}</template>
</el-table-column>
<el-table-column align="center" label="视频封面类型">
<template slot-scope="scope">{{ scope.row.img_type==='long'?'横图':'竖图'}}</template>
</el-table-column>
<el-table-column align="center" label="视频横版封面" width="80px">
<template slot-scope="scope">
<ShowImg style="width: 30px; height: 30px; margin: 0 auto" :noNeedDoamin="true" :urls="scope.row.img_x"></ShowImg>
</template>
</el-table-column>
<el-table-column align="center" label="视频竖版封面" width="80px">
<template slot-scope="scope">
<ShowImg style="width: 30px; height: 30px; margin: 0 auto" :noNeedDoamin="true" :urls="scope.row.img_y"></ShowImg>
</template>
</el-table-column>
<el-table-column align="center" label="标签" width="300px">
<template slot-scope="scope">
<el-tag :key="index + 'tagData'" style="margin: 2px" v-for="(item, index) in scope.row.tags" size="mini">
{{ item.name }}
</el-tag>
</template>
</el-table-column>
<el-table-column align="center" label="视频导演">
<template slot-scope="scope">{{ scope.row.director }}</template>
</el-table-column>
<el-table-column align="center" label="上架状态" width="110px">
<template slot-scope="scope">
<el-button plain size="mini">{{
scope.row.status_text }}</el-button>
</template>
</el-table-column>
<el-table-column align="center" width="120px" label="上架时间">
<template slot-scope="scope">{{ scope.row.issue_date | BeiJingTime }}</template>
</el-table-column>
<el-table-column align="center" width="120px" label="更新状态">
<template slot-scope="scope">{{ scope.row.update_status==='0'?'更新中':'已完结'}}</template>
</el-table-column>
<el-table-column align="center" fixed="right" label="操作" width="300">
<template slot-scope="scope">
<el-button
v-if="scope.row.type == 'MP3'"
@click="audioListFn(scope.$index, scope.row)"
type="success"
size="mini">加入后台MP3库</el-button>
<el-button
v-else
@click="addVideo(scope.$index, scope.row)"
size="mini"
:type="scope.row.isAdd ? 'info' : 'primary'"
:disabled="scope.row.isAdd ? true : false">{{
`${scope.row.isAdd ? '已加入后台视频库' : '加入后台视频库'}` }}</el-button>
<el-button @click="handleEdit(scope.$index, scope.row)" size="mini" type="primary">查看详情</el-button>
<!-- <el-button @click="handleDelete(scope.$index, scope.row)" size="mini" type="danger">删除</el-button> -->
</template>
</el-table-column>
</el-table>
</el-col>
</el-row>
<div class="table-pagination">
<el-pagination
:current-page="page"
:page-size="page_size"
:page-sizes="[10, 20, 30, 50, 100]"
:total="total"
@current-change="handleCurrentChange"
@size-change="handleSizeChange"
layout="total, sizes, prev, pager, next, jumper" />
</div>
<!-- 查看详情 -->
<Edit :data="editData" v-if="editVisible" @close="closeEdit" />
<ShowVideo ref="showvideo"></ShowVideo>
</div>
</template>
<script>
// 引入模块
import ShowImg from '@/components/ShowImg/index.vue'
import Edit from './components/AddOrEdit'
// import EditShowLocation from './components/editShowLocation'
import { lsjVideoList, lsjVideoDel,lsjVideoAdd } from '@/api/lsjMediaLibrary/videoList.js'
import ShowVideo from '@/components/ShowVideo/index.vue'
import {
positionList, videoTypeList,statusList
} from '@/filters/lsjMediaLibrary/videoList.js'
import { audioAdd } from '@/api/novelsManagement/audio.js'
import { isNumber } from 'mathjs/lib/entry/typeChecks'
export default {
name: 'MediaCat',
components: {
ShowImg,
ShowVideo,
Edit
},
data() {
return {
videoTypeList: videoTypeList(),
positionList: positionList(),
statusList: statusList(),
page: 1,
page_size: 20,
// 请求列表参数
searchData: {
position: 'guochan', // 番号
id: undefined,
name: undefined, // 外用状态
status: undefined, // "string",当前状态
cat_id: undefined // 视频归类
},
time: undefined,
resData: [], // el-table表格数据
total: 0, // 数据总条数
selectArray: undefined,
editShowLocationVisible: undefined,
loading: true, // 列表加载状态
// 编辑数据
editVisible: false, // 新增或编辑弹出框
editData: {
title: '查看详情',
data: {}
}
}
},
filters: {
changeFormat(val) {
switch (val) {
case 1:
return '长视频'
case 2:
return '短视频'
case 3:
return '预览'
}
},
changeContentType(val) {
switch (val) {
case 1:
return 'AV(日本)'
case 2:
return '短视频(国产)'
case 3:
return '动漫'
}
}
},
mounted() {
this.getMediaSearch()
},
methods: {
addOutside() {
this.editShowLocationVisible = true
this.editData = {
title: '',
data: this.selectArray
}
},
// TODO:加入后台视频库
addVideo(index, row) {
lsjVideoAdd({ id: row.id }).then((res) => {
if (res.code === 200) {
this.$message.success('加入成功!')
this.getMediaSearch()
} else {
this.$message.error('加入失败!')
}
})
},
// 加入后台音频库
addAudioArray() {
Object.keys(this.selectArray).forEach((key) => {
if (!this.selectArray[key].isAdd) {
this.audioListFn(key, this.selectArray[key])
}
})
},
// TODO:加入音频视频库
audioListFn(index, row) {
audioAdd({ id: row.id }).then((res) => {
if (res.code === 200) {
this.$message.success('加入成功!')
this.getMediaSearch()
} else {
this.$message.error('加入失败!')
}
})
},
// TODO:请求影片列表数据
getMediaSearch() {
this.loading = true
if(isNumber(this.page)|| isNumber(this.page_size)){
this.searchData.page = this.page + ''
this.searchData.page_size = this.page_size + ''
}
if (this.time) {
this.searchData.start_time = this.time[0]
this.searchData.end_time = this.time[1]
} else {
this.searchData.start_time = undefined
this.searchData.end_time = undefined
}
lsjVideoList(this.searchData).then((res) => {
if (res.code === 200) {
this.resData = res.data.data
this.total = Number(res.data.total)
} else {
this.$message.error('请求列表失败!')
this.resData = []
this.total = 0
}
this.loading = false
})
},
// TODO:删除影片列表数据
handleDelete(index, row) {
this.$confirm('确定删除?', '警告', {
confirmButtonText: '确定',
cancelButtonText: '取消',
type: 'warning'
}).then(() => {
lsjVideoDel({ id: row.id }).then((res) => {
if (res.code === 200) {
this.getMediaSearch()
this.$message.success('成功删除!')
} else {
this.$message.error(res.tip)
}
})
})
},
addVideoArray() {
Object.keys(this.selectArray).forEach((key) => {
if (!this.selectArray[key].isAdd) {
this.addVideo(key, this.selectArray[key])
}
})
},
onSeach() {
this.page = 1
this.page_size = 20
this.getMediaSearch()
},
// 切换每页数据量
handleSizeChange(val) {
this.page_size = val
this.getMediaSearch()
},
// 切换页数
handleCurrentChange(val) {
this.page = val
this.getMediaSearch()
},
handleSelectionChange(val) {
this.selectArray = val
},
// 新增按钮
add() {
this.editVisible = true // 新增或编辑弹出框
this.editData = {
title: '新增',
data: {}
}
},
// 编辑按钮
handleEdit(index, row) {
this.editVisible = true // 新增或编辑弹出框
this.editData = {
title: '查看详情',
data: row
}
},
// 关闭编辑弹窗
closeEdit() {
this.editVisible = false
this.editShowLocationVisible = false
this.getMediaSearch()
},
// 清空某一项筛选列表
onClear(key) {
this.searchData[key] = undefined
this.getMediaSearch()
}
}
}
</script>