Files
fe-manage/src/views/courselibrary/CourseRecommended.vue
2023-09-26 10:54:02 +08:00

931 lines
23 KiB
Vue
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
<!-- 课程推荐页面 -->
<template>
<div class="recommend">
<!-- 搜索框及按钮 -->
<div class="filter">
<div class="filterItems">
<div class="select">
<a-input v-model:value="searchData.recommendName" style="width: 106px; height: 40px; border-radius: 5px"
placeholder="请输入姓名" />
</div>
<div class="select">
<div class="select addTimeBox">
<div class="addTime">创建时间</div>
<a-range-picker v-model:value="recommendTimeList" style="width: 420px" @change="timeChange"
format="YYYY-MM-DD" valueFormat="YYYY-MM-DD" separator="至" :placeholder="[' 开始时间', ' 结束时间']" />
</div>
</div>
<div style="display: flex; margin-bottom: 20px">
<div class="btn btn1" @click="getList(1)">
<div class="search"></div>
<div class="btnText">搜索</div>
</div>
<div class="btn btn2" @click="handleRest" style="width: 105px">
<div class="search"></div>
<div class="btnText">重置</div>
</div>
</div>
</div>
<div class="btns">
<div class="btn btn3" @click="handleNew">
<div class="search"></div>
<div class="btnText">发起推荐</div>
</div>
</div>
</div>
<!-- 搜索框及按钮 -->
<!-- 表格 -->
<div class="tableBox">
<a-table style="border: 1px solid #f2f6fe" :columns="column" :data-source="state.data" :loading="!loading"
:scroll="{ x: 1100 }" :pagination="false">
<template #operation="{ record }">
<a-space style="padding-right: 10px">
<a-button @click="downloadInfo(record)" type="link">信息下载
</a-button>
<a-button
@click="() => handleLook(record, String(record.courseform))"
type="link"
>查看
</a-button>
<a-button @click="() => handleOper(record, 'withdraw', record.pushProgress)" type="link">
{{ state.status[record.pushProgress] }}
</a-button>
<a-button @click="handleOper(record, 'del')" danger type="link">删除
</a-button>
</a-space>
</template>
</a-table>
</div>
<div class="modalMain">
<div class="onlinemanage" :style="{ display: om_1 ? 'block' : 'none' }">
<div class="om_main">
<div class="om_body">
<div class="b_sub">
<div class="b_title">课程{{ newCourseName }}</div>
<div class="bs_type" style="margin-left: 20px">类型</div>
<div class="bs_right">{{ faceType }}</div>
<div class="bs_left">内容分类</div>
<div class="bs_right">{{ faceClassification }}</div>
<div class="bs_left">状态</div>
<div class="bs_right">
{{ faceStatus == 1 ? "已启用" : "已停用" }}
</div>
</div>
<a-tabs
class="b_menu"
v-model:activeKey="faceManageTab"
size="large"
:tabBarStyle="{ marginLeft: '10px' }"
@change="faceManageChange"
>
<a-tab-pane key="1" tab="学习记录">
<div class="b_menunav">
<div class="bm_select">
<a-select
class="select"
ref="select"
placeholder="请选择状态"
v-model:value="gl_selectV2"
style="width: 200px"
:options="options11"
allowClear
@focus="focus"
@change="handleChange"
>
</a-select>
</div>
<div class="bm_input">
<a-input
v-model:value="gl_inputV2"
style="width: 200px; height: 40px; border-radius: 8px"
placeholder="姓名"
/>
</div>
<div class="bm_btn">
<div class="btn btn1" @click="handleSearchTable3">
<div class="search"></div>
<div class="btnText">搜索</div>
</div>
<div class="btn btn2" @click="reseatSearchTable3">
<div class="search"></div>
<div class="btnText">重置</div>
</div>
</div>
</div>
<div class="bm_table" style="margin-bottom: 20px">
<a-table
:columns="columns2"
:data-source="tableData3"
:loading="manageStuLoading"
:pagination="false"
>
<template #bodyCell="{ column }">
<template v-if="column.key === 'opacation'">
<a @click="ckxq_hs">查看详情</a>
</template>
</template>
</a-table>
<div class="tableBox" style="margin-top: 50px">
<div class="pa">
<a-pagination
:showSizeChanger="false"
showQuickJumper="true"
hideOnSinglePage="true"
:pageSize="pageSize222"
:current="currentPage222"
:total="tableDataTotal222"
class="pagination"
@change="handelChangePage222"
/>
</div>
</div>
</div>
</a-tab-pane>
</a-tabs>
</div>
</div>
</div>
</div>
<div class="pa" style="display: flex; justify-content: flex-end; padding: 0 38px">
<a-pagination show-quick-jumper :pageSize="searchData.pageSize" :current="searchData.pageIndex" :total="state.total"
class="pagination" @change="handelChangePage" show-size-changer />
</div>
<RecommendedCourse v-model:visible="newNext" :title="推荐课程"></RecommendedCourse>
<SeeModal
:visible="lookCourseModal"
:detail="faceDetailObj"
@cancel="ft_exit_see"
/>
</div>
</template>
<script setup lang="jsx">
import { ref, onMounted, reactive, watch, toRefs } from "vue";
import { Form, message,} from "ant-design-vue";
import { boeRequest } from "@/api/request";
import useDownload from '@/hooks/useDownload'
import {
RECOMMEND_PAGE,
deleteResearch,
caseInfoDownload,
rePushOrWithdraw,
} from "@/api/case";
import dialog from "@/utils/dialog";
import RecommendedCourse from "@/components/drawers/RecommendedCourse.vue";
import { checkMenu } from "@/utils/utils";
import SeeModal from "@/components/courserecommended/CourseRecommended.vue";
const column = [
{
title: "推荐人",
dataIndex: "recommendBy",
key: "recommendBy",
width: "10%",
align: "center",
ellipsis: true,
className: "h",
customRender: ({ text }) => {
return text ? text : "-";
},
},
{
title: "列表包名称",
dataIndex: "listPageName",
key: "listPageName",
width: "20%",
align: "center",
className: "h",
customRender: ({ text }) => {
return text ? text : "-";
},
},
{
title: "推荐时间",
dataIndex: "recommendTime",
key: "recommendTime",
width: "20%",
align: "center",
className: "h",
customRender: ({ text }) => {
return text ? text : "-";
},
},
{
title: "课程数",
dataIndex: "courseCount",
key: "courseCount",
width: "10%",
align: "center",
className: "h",
customRender: ({ text }) => {
return text ? text : "-";
},
},
{
title: "用户数",
dataIndex: "userCount",
key: "userCount",
width: "10%",
align: "center",
className: "h",
customRender: ({ text }) => {
return text ? text : "-";
},
},
{
title: "推送进度",
dataIndex: "pushProgress",
key: "pushProgress",
width: "15%",
align: "center",
className: "h",
customRender: ({ text }) => {
switch (text) {
case 1:
return <span>推送中</span>;
case 2:
return <span>推送中</span>;
case 3:
return <span>已完成</span>;
case 4:
return <span style={{ color: "red" }}>推送失败</span>;
case 5:
return <span>推送撤回</span>;
default:
return <span>-</span>;
}
},
},
{
title: "查看率",
dataIndex: "viewRate",
key: "viewRate",
width: "10%",
align: "center",
className: "h",
customRender: ({ text }) => {
return text ? text : "0%";
},
},
{
title: "完成比",
dataIndex: "viewRate",
key: "viewRate",
width: "10%",
align: "center",
className: "h",
customRender: ({ text }) => {
return text ? text : "0%";
},
},
];
//查看
// 预览弹框 开启和关闭
const ft_exit_see = () => {
lookCourseModal.value = false;
};
const handleLook = async (itm, type) => {
// // if (type === "1") {
// // return;
// // }
// // state.offcourseId = itm.id;
// // const item = await detail({
// // offcourseId: Number(state.offcourseId),
// // }).then((res) => {
// // if (res.data.code === 200) return res.data.data;
// // });
lookCourseModal.value = true;
// // item.attach = item.attach == "" ? [] : item.attach.split(",");
// // state.faceDetailObj = item;
// // console.log("获取查看信息", item);
};
const authenticationColumn = {
title: "操作",
width: "30%",
className: "h",
dataIndex: "id",
key: "id",
fixed: "right",
align: "center",
slots: { customRender: "operation" },
}
const lookCourseModal = ref(false)
const faceDetailObj = ref({})
const state = reactive({
data: [],
total: 0,
status: {
1: "撤回",
2: "撤回",
3: "撤回",
4: "重新推送",
5: "重新推送",
},
});
// 查询数据
const searchData = ref({
pageIndex: 1,
pageSize: 10,
recommendName: "",
recommendTimeList: [],
});
const newNext = ref(false);
const recommendTimeList = ref([]);
const loading = ref(false);
watch(newNext, (value) => {
if (!value) {
searchData.value.pageIndex = 1;
getList()
}
})
const getList = (num) => {
if (num === 1) searchData.value.pageIndex = 1;
boeRequest(RECOMMEND_PAGE, searchData.value)
.then((res) => {
loading.value = true;
state.data = res?.result?.list || [];
state.total = res?.result?.count || 0;
})
.catch(() => {
loading.value = false;
});
};
// 获取列表数据
getList();
onMounted(() => {
// 是否需要触发新建弹框
let str = location.href;
let isOpen = str.includes("openCreate=true");
if (isOpen) {
newNext.value = true;
}
column.push(authenticationColumn)
});
const { resetFields } = Form.useForm(searchData, {});
const handle = (record) => ({
withdraw: async () => {
try {
// editReleaseStatus({ assessmentId: record.id, releaseStatus: 1 });
await rePushOrWithdraw({ casesRecommendId: record.id });
getList();
} catch (error) {
message.info("推送失败!");
}
},
del: async () => {
loading.value = true;
await deleteResearch({ id: record.id })
.then(() => {
message.info("删除成功!");
getList();
})
.catch(() => (loading.value = false));
},
});
const handleMsg = {
del: "你确定要删除这条记录吗?",
withdraw1: "你确认要撤回此次推送吗?",
withdraw2: "你确认要撤回此次推送吗?",
withdraw3: "你确认要撤回此次推送吗?",
withdraw4: "您确定要重新推送此案例吗?",
withdraw5: "您确定要重新推送此案例吗?",
};
function handleOper(record, type, status = '') {
dialog({ content: handleMsg[status ? type + status : type], ok: handle(record)[type] });
}
// 信息下载
const downloadInfo = (record) => {
try {
useDownload('/xboe/m/boe/cases/recommend/info_download', { casesRecommendId: record.id }, '案例信息')
} catch (error) {
console.log(error);
}
};
const handelChangePage = (page, pageSize) => {
loading.value = false;
searchData.value.pageSize = pageSize;
searchData.value.pageIndex = page;
getList();
};
function timeChange(time, timeStr) {
searchData.value.recommendTimeList = time ? time : [];
}
const handleRest = () => {
recommendTimeList.value = [];
resetFields();
getList();
};
const handleNew = () => {
newNext.value = true;
};
</script>
<style lang="scss" scoped>
.clearfix:before,
.clearfix:after {
content: " ";
display: block;
clear: both;
}
.addTimeBox {
position: relative;
display: flex;
align-items: center;
.addTime {
position: absolute;
z-index: 10;
margin-left: 10px;
color: rgba(0, 0, 0, 0.4);
}
.ant-picker {
padding-left: 85px;
}
.ant-picker-range .ant-picker-active-bar {
margin-left: 85px;
}
}
.out {
//display: flex;
display: block;
position: absolute;
width: 680px;
// height: 525px;
background-color: #fff;
box-shadow: 0 0 10px rgba(118, 136, 166, 0.21);
left: 50%;
top: 50%;
transform: translate(-50%, -50%);
.top {
width: 100%;
height: 68px;
background: linear-gradient(rgba(78, 166, 255, 0.2) 0%,
rgba(78, 166, 255, 0) 100%);
display: flex;
align-items: center;
.topimg {
width: 18px;
height: 18px;
margin-left: 27px;
}
.topc {
color: #000000;
font-size: 16px;
margin-left: 8px;
}
}
.mid {
width: 100%;
height: 100%;
background-color: #fff;
display: flex;
flex-direction: column;
align-items: center;
.d {
// margin-top: 8px;
// color: #ff4e4e;
margin-left: -5px;
}
.name {
width: 78%;
// background-color: lightcoral;
display: flex;
margin-top: 20px;
align-items: center;
height: 40px;
// border: 1px solid black;
.inname {
color: #6f6f6f;
font-size: 14px;
margin-left: 7px;
}
.in {
margin-left: 14px;
width: 81%;
.ant-input {
border-radius: 5px;
// height: 120%;
width: 100%;
height: 30px;
}
.showcount {
position: absolute;
right: 10px;
color: #c7cbd2;
bottom: 5px;
}
}
}
.btn {
width: 33%;
margin-top: 30px;
display: flex;
justify-content: space-between;
margin-bottom: 30px;
.samtn {
width: 100px;
height: 40px;
font-size: 14px;
border: 1px solid #4ea6ff;
border-radius: 8px;
cursor: pointer;
}
.btn1 {
background-color: #fff;
color: #4ea6ff;
}
.btn2 {
margin-left: 10px;
background-color: #4ea6ff;
color: #fff;
}
}
}
}
.recommend {
width: 100%;
height: 100%;
display: flex;
flex-direction: column;
position: relative;
.filter {
margin-left: 38px;
margin-right: 38px;
margin-top: 30px;
display: flex;
justify-content: space-between;
flex-wrap: wrap;
.filterItems {
display: flex;
flex-wrap: wrap;
.select {
margin-right: 20px;
margin-bottom: 20px;
}
.btn {
padding: 0 26px 0 26px;
height: 38px;
background: #4ea6ff;
border-radius: 8px;
display: flex;
align-items: center;
justify-content: center;
margin-right: 14px;
flex-shrink: 0;
cursor: pointer;
.search {
background-size: 100%;
}
.btnText {
font-size: 14px;
font-weight: 400;
color: #ffffff;
line-height: 36px;
margin-left: 5px;
}
}
.btnn {
padding: 0 26px 0 26px;
height: 38px;
background: #4ea6ff;
border-radius: 8px;
border: 1px solid rgba(64, 158, 255, 1);
display: flex;
align-items: center;
justify-content: center;
margin-right: 14px;
flex-shrink: 0;
cursor: pointer;
.search {
background-size: 100%;
}
.btnText {
font-size: 14px;
font-weight: 400;
color: #fff;
line-height: 36px;
margin-left: 5px;
}
}
.btn1 {
.search {
width: 15px;
height: 17px;
background-image: url("../../assets/images/courseManage/search0.png");
}
}
.btn2 {
.search {
width: 16px;
height: 18px;
background-image: url("../../assets/images/courseManage/reset0.png");
}
}
// .btn1:hover {
// background: rgba(64, 158, 255, 0.76);
// .search {
// background-image: url("../../assets/images/courseManage/search0.png");
// }
// .btnText {
// color: #ffffff;
// }
// }
.btn1:active {
background: #0982ff;
}
// .btn2:hover {
// background: rgba(64, 158, 255, 0.1);
// }
.btn2:active {
background: rgba(64, 158, 255, 0.2);
}
}
.btns {
display: flex;
.btn {
padding: 0 26px;
height: 38px;
background: #4ea6ff;
border-radius: 8px;
//border: 1px solid rgba(64, 158, 255, 1);
display: flex;
align-items: center;
justify-content: center;
margin-right: 14px;
flex-shrink: 0;
cursor: pointer;
.search {
background-size: 100%;
}
.btnText {
font-size: 14px;
font-weight: 400;
color: #ffffff;
line-height: 36px;
margin-left: 5px;
}
}
.btn3 {
margin-right: 0;
.search {
width: 17px;
height: 18px;
background-image: url("../../assets/images/courseManage/add0.png");
}
}
// .btn3:hover {
// background: rgba(64, 158, 255, 0.76);
// .search {
// background-image: url("../../assets/images/courseManage/add0.png");
// }
// .btnText {
// color: #ffffff;
// }
// }
.btn3:active {
background: #0982ff;
}
}
}
.tableBox {
margin: 20px 38px 30px;
display: flex;
flex: 1;
flex-direction: column;
th.ant-table-cell {
background-color: #eff4fc !important;
text-align: center;
color: #999ba3;
}
td.ant-table-cell {
text-align: center;
}
}
.pa {
width: 100%;
display: flex;
justify-content: center;
margin-bottom: 20px;
.pagination {
margin-bottom: 20px;
}
.ant-pagination-item-link,
.ant-pagination-item,
.ant-select-selector,
.ant-pagination-options-quick-jumper input {
border-radius: 8px;
}
}
.unout {
display: none;
}
.operation {
display: flex;
justify-content: right;
.fb {
display: flex;
margin-right: 20px;
.jc {
color: #4ea6ff;
font-size: 14px;
margin-left: 20px;
white-space: nowrap;
cursor: pointer;
}
}
}
}
.DelModal {
.ant-modal {
.ant-modal-content {
width: 424px !important;
.ant-modal-body {
.delete {
z-index: 9999;
width: 424px;
background: #ffffff;
box-shadow: 0 1px 35px 0 rgba(118, 136, 166, 0.21);
border-radius: 4px;
position: absolute;
left: 50%;
top: 10%;
transform: translate(-50%, -50%);
.del_header {
position: absolute;
width: calc(100%);
height: 40px;
background: linear-gradient(rgba(78, 166, 255, 0.2) 0%,
rgba(78, 166, 255, 0) 100%);
}
.del_main {
width: 100%;
position: relative;
.header {
display: flex;
align-items: center;
padding-top: 20px;
padding-left: 26px;
font-size: 16px;
.del-icon {
width: 16px;
height: 16px;
position: relative;
margin-right: 10px;
img {
width: 100%;
height: 100%;
position: absolute;
top: 0;
left: 0;
background-size: 100% 100%;
}
}
.icon {
width: 16px;
height: 16px;
margin-right: 10px;
background-image: url(@/assets/images/coursewareManage/QR.png);
background-size: 100% 100%;
}
.close_exit {
position: absolute;
right: 42px;
cursor: pointer;
width: 20px;
height: 20px;
background-image: url(@/assets/images/coursewareManage/close.png);
background-size: 100% 100%;
}
}
.body {
width: 100%;
margin: 34px auto 56px auto;
display: flex;
justify-content: center;
align-items: center;
}
.del_btnbox {
display: flex;
margin: 30px auto;
justify-content: center;
.del_btn {
width: 100px;
height: 40px;
background: rgba(64, 158, 255, 0);
border-radius: 8px;
display: flex;
align-items: center;
justify-content: center;
margin-right: 14px;
flex-shrink: 0;
cursor: pointer;
.btnText {
font-size: 14px;
font-weight: 400;
line-height: 40px;
}
}
.btn1 {
border: 1px solid rgba(64, 158, 255, 1);
color: #4ea6ff;
}
.btn2 {
background-color: #4ea6ff;
color: #ffffff;
}
}
}
}
}
}
}
}
</style>