Files
learning-system-mobile/pages/resource/microDetail.vue
2022-05-29 18:59:24 +08:00

1619 lines
48 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>
<!--微课详情页-->
<view><watermark></watermark>
<u-toast ref="messager"></u-toast>
<page-title :showBack="true">{{courseInfo.name}}</page-title>
<view class="tabbar">
<view class="tabbar-item" @click="clicktab(0)" :class="{'active':tabIndex==0}">课件</view>
<view v-if="homeworkInfo.has" class="tabbar-item" @click="clicktab(1)" :class="{'active':tabIndex==1}">作业</view>
<view v-if="examInfo.has" class="tabbar-item" @click="clicktab(2)" :class="{'active':tabIndex==2}">考试</view>
<view v-if="assessInfo.has" class="tabbar-item" @click="clicktab(3)" :class="{'active':tabIndex==3}">评估</view>
<view class="tabbar-item" @click="clicktab(4)" :class="{'active':tabIndex==4}">评论</view>
</view>
<view>
<view v-if="tabIndex==0">
<!--视频-->
<view style="background-color: #FFFFFF;min-height: 230px;">
<view v-if="studyId==''" >
<view style="width: 100%;height: 500upx;">
<course-image v-if="courseInfo.id!=''" :course="courseInfo"></course-image>
</view>
<!-- <view style="position: absolute;top: 150upx;z-index: 90;width: 100%;">
<view class="bm-button" style="text-align: center;">
<u-button class="u-but" @click="submitSignup" text="报名后即刻开始学习" type="warning"></u-button>
</view>
</view> -->
</view>
<view v-else style="min-height: 210px;">
<view v-if="coursewareInfo.content.contentType==10">
<!--视频-->
<view style="position: relative;">
<video v-if="curriculumData.url"
@touchend="doubleClick"
id="myVideo"
style="width: 100%;"
ref="videoone"
:src="fileBaseUrl+curriculumData.url"
@error="videoErrorCallback"
:initial-time="videoPlayingTime"
@play="onPlayerPlay"
@pause="onPlayerPause"
@ended="onPlayerEnded"
@timeupdate="onPlayerPlaying"
@fullscreenchange="onFullScreen"
controls>
</video>
<!--倍速度-->
<view id="myVideoSpeed" class="player-controls-btn cursor-pointer btn-speed">
<view style="margin-top: 10px;" @click="showSpeedCtrl">{{videoSpeed === 1 ? '倍速' : `${videoSpeed}x`}}</view>
<view class="speed-control" v-if="speedListShow">
<view class="speed-control-list">
<view class="li"
v-for="item in speedList"
:key="item"
@click="changeSpeed(item)"
:data-value="item"
:class="{'current': videoSpeed === Number(item)}">
{{ item }}x
</view>
</view>
</view>
</view>
<view class="player-box" v-if="playerBoxShow">
<view class="player-praise">
<view @click="praiseContent" style="cursor: pointer;">
<image class="icon-small" v-if="isPraise" src="/static/images/icon/praise-active.png" />
<image class="icon-small" v-else src="/static/images/icon/praise1.png" />
<!-- {{ courseInfo.praises }} -->
<view style="color:#fff;cursor: pointer;"></view>
</view>
<view style="margin-left: 15px;cursor: pointer;" @click="treadContent">
<image class="icon-small" v-if="isTrample" src="/static/images/icon/trample-active.png" />
<image class="icon-small" v-else src="/static/images/icon/trample.png" />
<!-- {{ courseInfo.trampleCount }} -->
<view style="color:#fff;cursor: pointer;"></view>
</view>
</view>
<view v-if="!scoreInfo.has" class="player-rate">
<u-rate v-model="scoreInfo.score" active-color="#f7ba2a" text-color="#ff9900" score-template="{value}" void-color="#fff" @change="addScore"></u-rate>
</view>
<view v-if="scoreInfo.has" style="padding-top: 5px;display: flex;">
<view class="player-rate" style="padding-left: 5px;">
<u-rate active-color="#f7ba2a" readonly v-model="courseInfo.score" :allow-half="true" ></u-rate>
</view>
<view class="score-text" style="margin-top:20px">
<text style="color:#ffb30f;">{{ toScore(courseInfo.score) }}</text>
<text style="font-size: 12px;color: #fff"></text>
</view>
</view>
</view>
</view>
</view>
<view v-else-if="coursewareInfo.content.contentType==20">
<!--音频播放-->
<audio-player
:src="fileBaseUrl+curriculumData.url"
:name="courseInfo.name"
:drag="curriculumData.isDrag"
@onPlay="audioPlay"
@onPause="audioPause"
@onPlaying="audioPlaying"
@onEnded="audioEnd">
</audio-player>
</view>
<view v-else-if="coursewareInfo.content.contentType==30">
<image :src="fileBaseUrl+coursewareInfo.content.content" style="width: 100%;"></image>
</view>
<view v-else-if="coursewareInfo.content.contentType==40">
<!--pdf文档-->
<view style="min-height: 500px;position: relative;">
<pdf-preview v-if="coursewareInfo.content.content && coursewareInfo.content.content!=''" :src="coursewareInfo.content.content ? fileBaseUrl+coursewareInfo.content.content : ''"></pdf-preview>
</view>
</view>
<view v-else-if="coursewareInfo.content.contentType==41" style="padding: 10upx;">
<view style="position: relative; word-break:break-all;">
<u-parse :content="coursewareInfo.content.content"></u-parse>
</view>
</view>
<view v-else-if="coursewareInfo.content.contentType==52">
<view v-if="conLink.url!=''" style="min-height: 400px;position: relative;">
<web-view :src="conLink.url"></web-view>
</view>
</view>
</view>
<view>
<!-- 评分赞和踩 -->
<u-popup :show="scoreInfo.dlgShow" mode="top" @close="closeScore" @open="openScore">
<view style="text-align: center;padding: 50upx;">
<view style="text-align: center;">给课程打分</view>
<view style="padding-top: 100upx;display: flex;justify-content: center;">
<u-rate :count="5" :size="25" v-model="scoreInfo.score"></u-rate>
</view>
<view style="padding-top: 100upx;height: 100upx;">
<u-button type="primary" @click="addScore()" text="提交评分"></u-button>
</view>
</view>
</u-popup>
<view class="main-footer" v-if="studyId !==''">
<view style="padding-top: 10px;height: 32px;">
<u-rate v-if="!scoreInfo.has" :count="5" :size="25" active-color="#f7ba2a" v-model="scoreInfo.score" @change="addScore()"></u-rate>
<u-rate v-else :size="25" active-color="#f7ba2a" :value="scoreInfo.score" readonly ></u-rate>
<!-- <text v-if="!scoreInfo.has" @click="openScore()" class="main-scroe">去评分</text>
<text class="main-praise" v-else style="color: #ffaa00;font-size: 32upx;">{{changeScore(scoreInfo.score)}} </text> -->
<!-- <u-rate class="star-rate" :disabled="true" activeColor="#FA3534" :allowHalf="true" v-show="isPraise" :count="5" :size="25" v-model="courseInfo.score"></u-rate> -->
</view>
<view style="display: flex;justify-content: flex-end;padding-top: 13px">
<view @click="praiseContent()">
<image :src="'/static/images/icon/'+(isPraise? 'praise-active.png':'praise1.png')" style="width:35upx;height: 35upx;margin-right: 5px;"></image> {{courseInfo.praises}}
</view>
<view @click="treadContent()">
<image :src="'/static/images/icon/'+(isTrample? 'trample-active.png':'trample.png')" style="width:35upx;height: 35upx;margin-left: 30upx;margin-right: 5px;"></image> {{ courseInfo.trampleCount }}
</view>
</view>
</view>
</view>
</view>
<view class="content" style="margin-top: 20upx;">
<view class="content-tit" style="margin-top: 16rpx">{{courseInfo.name}}</view>
<view class="content_top" >
<view class="top_top">
<view class="item-author" style="display: flex;flex-wrap: wrap;">
<!-- <view><u-avatar :size="25" :src="avatar"></u-avatar></view> -->
<!-- <view style="padding-left: 10upx;padding-top: 6upx;display: flex;line-height: 45upx;">
<u-avatar v-if="authorInfo.avatar==''" :size="25" shape="square" icon="account"></u-avatar>
<u-avatar v-else :size="25" shape="square" :src="authorInfo.avatar"></u-avatar>
<text style="margin-left: 10upx;"> {{courseInfo.sysCreateBy}}</text>
<text style="margin-left: 10upx;"> ({{authorInfo.code}})</text>
</view> -->
<!-- <author v-if="authorInfo" :showInfo="true" :data="authorInfo"></author> -->
<!-- <view v-for="(item, idx) in teachers" :key="idx" > -->
<!-- <view> -->
<!-- <u-avatar v-if="item.authorInfo.avatar && item.authorInfo.avatar!=''" shape="square" :size="25"
:src="$config.fileUrl+item.authorInfo.avatar" ></u-avatar> -->
<!-- <u-avatar v-else :size="25" icon="account" shape="square"></u-avatar> -->
<!-- <view v-else class="uavatar"><view class="uavatar-scale"> {{avatarText(item.teacherName)}}</view> </view> -->
<!-- </view> -->
<view v-for="(item, idx) in teachers" :key="idx">
<text style="font-size: 32upx;color: #787878;padding-right: 20upx;">{{ item.teacherName }}</text>
<!-- <text style="margin-left: 15upx;font-size: 26upx;color: #444444;">授课老师</text> -->
</view>
<!-- </view> -->
</view>
</view>
<view>
<!-- <view class="share-btn" @click="openShare">
<view class="share-btn-icon"><image style="width: 30upx;height: 30upx;" :src="'/static/images/icon/share.png'" alt=""></image></view>
<view class="share-btn-name">分享</view>
</view> -->
</view>
</view>
</view>
<!--属性-->
<view>
<view class="content">
<!-- <view class="tags">
<view v-for="(tag,tidx) in tags" :key="tidx" class="tags-item">{{tag}}</view>
</view> -->
<!-- style="display: flex;justify-content: space-between;" -->
<view>
<view class="cfield">
<!-- <view class="cfield-lable">资源归属:
<text class="cfield-value">{{courseInfo.resOwner1}}</text>
<text class="cfield-value">/{{courseInfo.resOwner2}}</text>
<text v-if="courseInfo.resOwner3!==''" class="cfield-value">/{{courseInfo.resOwner3}}</text>
</view> -->
<view class="cfield-lable"><text class="cfield-value">{{courseInfo.studys}}人学习</text></view>
</view>
<!-- <view class="cscore"> -->
<!-- <text class="cscore-value">{{changeScore(courseInfo.score)}}</text> -->
<!-- <text class="cscore-unit"></text> -->
<!-- </view> -->
</view>
</view>
<view class="content" style="margin-top: 10px;min-height: 300upx;margin-bottom: 40upx;">
<view class="consultant">
<view class="content-title">目标人群</view>
<view class="content-text">{{courseInfo.forUsers}}</view>
</view>
<view v-if="courseInfo.value!=''" class="consultant">
<view class="content-title">课程价值</view>
<view class="content-text">{{courseInfo.value}}</view>
</view>
<view v-if="courseInfo.summary!=''" class="consultant">
<view class="content-title">课程详情</view>
<view class="content-text"><u-parse :content="courseInfo.summary"></u-parse></view>
</view>
</view>
<!-- <view class="cinfo">
<view>
<u-parse :content="courseInfo.overview"></u-parse>
</view>
</view> -->
</view>
</view>
<!--作业-->
<view v-if="tabIndex==1">
<course-homework ref="homework" v-if="homeworkInfo.content.id" :content="homeworkInfo.content" :studyId="studyId"></course-homework>
</view>
<!--考试-->
<view v-show="tabIndex==2">
<course-exam v-if="examInfo.content.id" :courseType="courseInfo.type" :content="examInfo.content" :studyId="studyId"></course-exam>
</view>
<!--评估-->
<view v-show="tabIndex==3">
<course-assess v-if="assessInfo.content.id" :content="assessInfo.content" :studyId="studyId"></course-assess>
</view>
<!--评论-->
<view v-show="tabIndex==4">
<comments ref="comments" v-if="courseId && courseId!=''" :objType="1" :objId="courseId"></comments>
</view>
</view>
<!--底部-->
<interact-fixed ref="fiexdbar" :type="1" :users="teachers" :data="courseInfo" :comments="isComments" :praises="false" @handle-comment="handleComment" @comment-success="refreshComments" @share-success="shareSuccess">
<view v-if="studyId==''">
<!-- <view class="btn" @click="submitSignup()">立即报名</view> -->
</view>
<!--评论-->
<view v-else class="fixed-field" @click="openComment()">
<u-icon name="edit-pen-fill" size="18" class="fixed-field-icon"></u-icon>
<text class="fixed-field-text">说点什么..</text>
</view>
</interact-fixed>
</view>
</template>
<script>
import apiCoursePortal from '@/api/modules/coursePortal.js'
import apiCourseFile from '@/api/modules/courseFile.js'
import apiCourseStudy from '@/api/modules/courseStudy.js'
import apiVideoStudy from "@/api/modules/videoStudy.js";
import apiCourseGrade from "@/api/modules/courseGrade.js";
import apiUser from '@/api/system/user.js'
import apiResOwner from '@/api/modules/resowner.js'
import apiPraises from "@/api/modules/praises.js";
import apiTrample from "@/api/modules/trample.js";
import studyUtil from '@/utils/study.js';
import {toScore} from '@/utils/tools.js';
import { mapGetters } from 'vuex'
export default {
computed: {
...mapGetters(['userInfo']),
},
props:{
avatar:{
type:String,
default:''
},
name:{
type:String,
default:''
},
showInfo:{
type:Boolean,
default:false
},
showCode:{
type:Boolean,
default:false
},
info:{
type:String,
default:''
}
},
data() {
return {
isPlaying:false,
onplay:false,
touchNum : 0,
playerBoxShow:false,
isComments: true,
toScore:toScore,
isShow: false,
courseId:'',
studyId:'',
fileBaseUrl:this.$config.fileUrl,
courseInfo:{
id:'',
type:1,
answers:0,
favorites:0,
comments:0,
shares:0,
praises:0,
views:0,
},
authorInfo:{aid:'',name:'',code:'',orgInfo:''},
tags:[],
teachers:[],
totalContent:4,
conLink:{
openType:1,
url:''
},
curriculumData:{url:'',isDrag:true,completeSetup:1,setupTage:0,second:0},// 课件内容
coursewareInfo:{
content:{},
process:0,
status:1,
finish:false,
studyItemId:''
},
homeworkInfo:{
has:false,
content:{},
info:{},
studyItemId:'',
filePath:'',
answer:'',
close:false,
records:[]//作业记录
},
examInfo:{
has:false,
content:{},
info:{},
paper:[],
studyItemId:'',
records:[] ,//考试记录
allowSubmit:true,//是否允许考试,尝试次数达到后不能再考试
startTime:'',
detailShow:false,
detailItems:[]
},
assessInfo:{
has:false,
allowSubmit:true,
content:{},
info:{},
studyItemId:'',
},
tabIndex:0,
videoScore:3,
videoPlayer:null,
speedListShow:false,
speedList:["2.0", "1.5", "1.25", "1.0", "0.75", "0.5"],
videoSpeed: 1.0, // 当前倍速:
scoreInfo:{
dlgShow:false,
score:5,
has:false,
},
isPraise:false,
isTrample:false,
interactRuning:false,
handleTimeout:null,
isAppendTime:true,
appendStartTime: null, //记录追加的开始时间
appendHandle:null,
appentId:'',//当前追加的学习时长的id
appentInterval:30000,//追加学习时间的间隔 30秒加一次
videoPlayingTime:0,
preTime:-1,
userAvatar:'',
}
},
onLoad(options) {
this.courseId = options.id;
if(options.exam === '1') {
this.tabIndex = 2;
}
//console.log(this.courseId)
if(!this.courseId){
//this.$refs.messager.show({message:'未指定课程参数',type:'error'});
//在这个阶段中,上面的代码不起作用
uni.showToast({
title:'未指定课程'
})
}else{
this.loadDetail(this.courseId);
}
},
onShow(){
//实时渲染当前的播放状态
uni.setNavigationBarTitle({ title:'\u200E' })
},
onReady() {
this.videoPlayer=uni.createVideoContext("myVideo", this);
},
methods: {
videoErrorCallback(e){
console.log(e);
},
doubleClick(e){
this.touchNum ++
setTimeout(()=>{
if(this.touchNum == 1){
// console.log('单击')
}else if(this.touchNum >= 2){
if(this.isPlaying){
this.onPlayerPause()
} else {
this.onPlayerPlay()
}
}
this.touchNum = 0
},250)
},
handleComment() {
this.tabIndex=4;
this.isComments = false;
},
avatarText(name){
let text=name;
if(text){
let len=text.length;
if(text.length>2){
text=text.substring(len-2);
}
}
return text;
},
jupeRoute(route) {
window.location.href = route.content.content;
},
loadDetail(id){
let $this=this;
apiCoursePortal.detail(id).then(rs=>{
if(rs.status==200){
this.courseInfo=rs.result.course;
this.teachers=rs.result.teachers;
this.totalContent=rs.result.contents.length;//计算总内容数
// this.loadUserInfo(this.courseInfo.sysCreateAid);
if(rs.result.teachers && rs.result.teachers.length > 0) {
let userIds = [];
let ctoUsers = [];
rs.result.teachers.forEach(item => {
// item.authorInfo = { aid: '', name: '', orgInfo: '', avatar: '', code: '',sex:null };
item.name='';
item.orgInfo= '';
item.avatar= '';
item.code= '';
item.sex=null;
userIds.push(item.teacherId);
ctoUsers.push({ aid: item.teacherId, name: item.teacherName });
});
// this.toUsers = ctoUsers;
this.loadAuthorInfo(rs.result.teachers, userIds);
}
this.loadResOwner();
if(this.courseInfo.tags!=''){
this.tags=this.courseInfo.tags.split(',');
}
rs.result.contents.forEach(con=>{
if(con.sortIndex==1){
$this.coursewareInfo.content=con;
if(con.contentType == 40) {
if(con.content!='' && con.content.indexOf('.pdf')==-1){
// 先置空,否则会有延迟
$this.coursewareInfo.content.content = '';
apiCourseFile.detail($this.coursewareInfo.content.contentRefId).then(cfrs=>{
if(cfrs.status==200){
$this.coursewareInfo.content.content=cfrs.result.previewFilePath;
}else{
$this.$message.error('加载pdf课件文件失败');
}
});
}
}else if(con.contentType==52){
if(con.content.startsWith('\{')){
this.conLink=JSON.parse(con.content);
}else{
this.conLink.url=con.content;
this.conLink.openType=1;
}
} else if(con.contentType==10 || con.contentType==20) {
if(con.content.startsWith('\{')){
this.curriculumData=JSON.parse(con.content);
}else{
this.curriculumData.url=con.content;
}
}
}else if(con.sortIndex==2){
$this.homeworkInfo.content=con;
$this.homeworkInfo.has=true;
//查询作业信息,并显示
//$this.loadHomeworkInfo();
}else if(con.sortIndex==3){
$this.examInfo.has=true;
$this.examInfo.content=con;
//查询考试信息并显示
//$this.loadExamInfo();
}else if(con.sortIndex==4){
$this.assessInfo.has=true;
$this.assessInfo.content=con;
//转化文本为json内容
//$this.loadAssessInfo();
}
})
//study info
this.loadStudyInfo();
}else{
this.$refs.messager.show({message:rs.message,type:'error'});
}
})
},
loadAuthorInfo(list, ids) {
//加载作者信息,头像,机构信息
if (ids.length == 0) {
return;
}
apiUser.getByIds(ids).then(res => {
if (res.status == 200) {
list.forEach((item, index) => {
res.result.some(author => {
if (author.aid == item.teacherId) {
// item.authorInfo = author;
item.name= author.name;
item.orgInfo= author.orgInfo;
item.avatar= author.avatar;
item.code= author.code;
item.sex=author.sex;
if(author.avatar != '') {
item.avatar=this.$config.fileUrl + author.avatar;
}
return true;
} else {
return false;
}
});
});
} else {
//console.log('加载课程信息失败:'+res.error);
//this.$message.error(res.message);
}
});
},
loadStudyInfo() {
//获取学习信息
let $this = this;
apiCourseStudy.studyInfo(this.courseId).then(res => {
if(res.status == 200){
// console.log(res);
//this.playCourseware();
if(res.result.signup) {
this.loadScorePraiseAndTrample();
//this.appendStudyTime();
// console.log(res.result,'result11111');
this.studyId = res.result.studyId; //设置学习id
//需要判断此内容是否已学习完成,如果已学习完成,不需要再请不说了
res.result.contents.forEach(con => {
if(con.contentId == $this.coursewareInfo.content.id) {
$this.coursewareInfo.finish = true; //课件已学习
$this.coursewareInfo.studyItemId=con.id;
$this.videoPlayingTime=con.lastStudyTime;
} else if (con.contentId == $this.homeworkInfo.content.id) {
$this.homeworkInfo.studyItemId = con.id;
} else if (con.contentId == $this.examInfo.content.id) {
$this.examInfo.studyItemId = con.id;
} else if (con.contentId == $this.assessInfo.content.id) {
$this.assessInfo.studyItemId = con.id;
}
});
this.playCourseware();
}else{
this.submitSignup();
}
} else {
this.$refs.messager.show({message:res.message,type:'error'});
}
});
},
loadResOwner(){
let c=this.courseInfo;
apiResOwner.list(1,'').then(rs=>{
rs.result.forEach(item=>{
if(item.code==c.resOwner1){
c.resOwner1=item.name;
}
if(item.code==c.resOwner2){
c.resOwner2=item.name;
}
if(item.code==c.resOwner3){
c.resOwner3=item.name;
}
})
});
},
saveStudyItem(){ //先保存学习的内容,针对于音视频的内容
if(this.coursewareInfo.finish || this.coursewareInfo.studyItemId) {
return;//已记录学习记录的不再保存
}
let params = {
studyId: this.studyId, //学习id,
courseId: this.courseId, //课程id,
contentId: this.coursewareInfo.content.id, //内容id,
contentType:this.coursewareInfo.content.contentType, //内容id,
contentName: this.coursewareInfo.content.contentName, //内容名称
progress: 0,
lastStudyTime:0,
status:2,
studyDuration:0,
contentTotal: this.totalContent
};
apiVideoStudy.saveStudyItem(params).then(res=>{
if(res.status == 200){
this.coursewareInfo.studyItemId=res.result.id;
this.coursewareInfo.finish = false;
this.coursewareInfo.status = 2;
this.coursewareInfo.progress = 1;
}else{
console.log("记录学习失败:" + res.message + "" + res.error);
}
});
},
finishStudyItem(){ //设置完成学习的内容,针对于音视频的内容
let params={
itemId:this.coursewareInfo.studyItemId,
studyId:this.studyId,
courseId:this.courseId,
cnum:this.totalContent
}
apiVideoStudy.finishStudyItem(params).then(res=>{
if(res.status == 200){
this.coursewareInfo.finish = true;
this.coursewareInfo.status = 9;
this.coursewareInfo.progress = 100;
}else{
console.log("记录完成学习失败:" + res.message + "" + res.error);
}
});
},
onFullScreen(e){
console.log(e,'e');
let full=e.detail.fullScreen;
let divId='videowatermark';
setTimeout(() => {
var div = document.getElementById('myVideo')
var div1 = div.firstChild;
var speedDiv=div1.querySelector("#myVideoSpeed");
if(full){
var div3 = document.createElement("div");
div3.id =divId;
div3.setAttribute("class", "fullmark");
div3.innerHTML='';
// 从父组件传过来的水印内容
//div3.innerText =this.userInfo.name+this.userInfo.code;
for(var i=0;i<4;i++){
div3.innerHTML+='<div style="color:#ffffff;width: 40%;height: 155px;padding-left:60px;padding-top:50px; display: flex;justify-content: center; transform: rotate(-36deg);font-size:20px;">'+this.userInfo.name+this.userInfo.code+'</div>';
}
div3.style.cssText = "position:absolute;pointer-events: none; width: 100%;height: 100%;top:0;left:0;bottom: 0;right: 0; display: flex;justify-content: center;flex-wrap: wrap;overflow: hidden; opacity:0.3;padding-top:10px";
//console.log(div3,'div3');
div1.appendChild(div3);
if(!speedDiv){
var speedDiv=document.getElementById('myVideoSpeed');
div1.appendChild(speedDiv)
}
}else{
var markDiv=div1.querySelector("#"+divId);
//var speedDiv=div1.querySelector("#myVideoSpeed");
if(markDiv){
div1.removeChild(markDiv);
}
if(speedDiv){
//div1.removeChild(speedDiv);
}
}
}, 200);
},
onPlayerPlay(){
this.isPlaying = true;
//console.log("开始播放");
this.playerBoxShow = false;
this.isAppendTime=false;
this.videoSpeed=studyUtil.getVideoSpeed();
this.videoPlayer.playbackRate(this.videoSpeed);
this.$refs.videoone.play();
let $this=this;
if(!$this.coursewareInfo.finish){
let completeType=this.curriculumData.completeSetup;
if(completeType==0){
//默认5秒后学习完成.
this.handleTimeout= setTimeout(() => {$this.saveStudyInfo();}, 5000);
}else{
//先记录进行中的学习内容
this.saveStudyItem();
}
}
},
onPlayerPause(){
this.isPlaying = false;
this.$refs.videoone.pause();
//console.log("暂停");
},
onPlayerEnded(){
this.playerBoxShow = true;
//console.log("播放结束");
//this.isAppendTime=true;//开启追加学习时间
if(!this.coursewareInfo.finish && this.coursewareInfo.studyItemId){
this.finishStudyItem();
}
},
changeSpeed(e) {
// 获取选择的倍速
let value = e;
// 标记变更后的倍速,用于显示文字
this.videoSpeed = Number(value);
this.videoPlayer.playbackRate(this.videoSpeed);
studyUtil.setVideoSpeed(this.videoSpeed);
this.speedListShow=false;
},
showSpeedCtrl(){
if(this.speedListShow){
this.speedListShow=false;
}else{
this.speedListShow=true;
}
},
onPlayerPlaying(e){
//console.log("当前播放11",itme);
this.isAppendTime=false;//禁止追加学习时间
//console.log("当前播放11"+itme);
let intTime=parseInt(e.detail.currentTime);
//判断是否完成
let completeType=this.curriculumData.completeSetup;
let completeSecond=this.curriculumData.second;
if(!completeSecond){
completeSecond=5;//如果没有就采用默认的时间了
}
if(completeType>0 && !this.coursewareInfo.finish){ //因为1按进度2按时长都是计算时间所以这里直接大于0处理
if(completeType==1){
let finishPercent=this.curriculumData.setupTage;
let videDuration=this.coursewareInfo.content.duration;
let percent =intTime*100/videDuration;
if(percent>=finishPercent){
this.finishStudyItem();
}
}else if(completeType==2){
if(intTime>completeSecond){
this.finishStudyItem();
}
}
}
let saveTime=Math.floor(intTime%10);
//console.log(intTime,saveTime,'aa',this.coursewareInfo.studyItemId)
if(this.preTime!=intTime && saveTime==0 && this.coursewareInfo.studyItemId!=''){
this.preTime=intTime;
this.videoPlayingTime=intTime;
//记录播放时间
//console.log('记录播放时间:'+intTime);
let postData={
itemId:this.coursewareInfo.studyItemId,
videoTime:intTime
}
apiCourseStudy.studyVideoTime(postData).then(rs=>{
if(rs.status!=200){
console.log('记录播放时间错误');
}
})
}
},
audioPlay(){
//console.log('audioPlay');
let $this=this;
if(!$this.coursewareInfo.finish){
let completeType=this.curriculumData.completeSetup;
if(completeType==0){
//默认5秒后学习完成.
this.handleTimeout= setTimeout(() => {$this.saveStudyInfo();}, 5000);
}else{
//先记录进行中的学习内容
this.saveStudyItem();
}
}
},
audioEnd(){
//console.log('audioEnd');
if(!this.coursewareInfo.finish && this.coursewareInfo.studyItemId){
this.finishStudyItem();
}
},
audioPause(){
//console.log('audioPause');
},
audioPlaying(e,second){
// console.log(e,'e');
// console.log(e.currentTime,'currentTime');
// console.log(second,'second');
this.isAppendTime=false;//禁止追加学习时间
let videDuration=e.duration;
//let videDuration=this.coursewareInfo.content.duration;
let intTime=second;
//判断是否完成
let completeType=this.curriculumData.completeSetup;
let completeSecond=this.curriculumData.second;
if(!completeSecond){
completeSecond=5;//如果没有就采用默认的时间了
}
if(completeType>0 && !this.coursewareInfo.finish){ //因为1按进度2按时长都是计算时间所以这里直接大于0处理
if(completeType==1){
let finishPercent=this.curriculumData.setupTage;
let percent =intTime*100/videDuration;
if(percent>=finishPercent){
this.finishStudyItem();
}
}else if(completeType==2){
if(intTime>completeSecond){
this.finishStudyItem();
}
}
}
let saveTime=Math.floor(intTime%10);
//console.log(intTime,saveTime,'aa',this.coursewareInfo.studyItemId)
if(this.preTime!=intTime && saveTime==0 && this.coursewareInfo.studyItemId!=''){
this.preTime=intTime;
this.videoPlayingTime=intTime;
//记录播放时间
//console.log('记录播放时间:'+intTime);
let postData={
itemId:this.coursewareInfo.studyItemId,
videoTime:intTime
}
apiCourseStudy.studyVideoTime(postData).then(rs=>{
if(rs.status!=200){
console.log('记录播放时间错误');
}
})
}
},
saveStudyInfo() {
//记录课件学习信息
if (this.tabIndex != 0) {
//只有在课件页面停留超过5秒才会记录
return;
}
if (this.coursewareInfo.finish) {
return;
}
let params = {
studyId: this.studyId, //学习id,
courseId: this.courseId, //课程id,
contentId: this.coursewareInfo.content.id, //内容id,
contentName: this.coursewareInfo.content.contentName, //内容名称
progress: 100,
contentTotal: this.totalContent
};
apiCourseStudy.studyContent(params).then(res => {
if (res.status == 200) {
this.coursewareInfo.finish = true; //课件内容已学习,记录状态
} else {
console.log("记录学习失败:" + res.message + "" + res.error);
}
});
},
submitSignup(){ //报名
let pamars = {
courseId: this.courseId,
courseName: this.courseInfo.name,
courseType: this.courseInfo.type,
signType: 1,
signInfo: "自主报名"
};
let $this = this;
apiCourseStudy.signup(pamars).then(res => {
if (res.status == 200) {
//this.$refs.messager.show({message:'报名成功',type:'success'});
this.studyId =res.result.studyId;//设置学习id
//this.appendStudyTime(); //报名成功记录开始时间
//报名成功后就直接记录课件学习情况5秋后
this.playCourseware();
} else {
this.$refs.messager.show({message:res.message,type:'error'});
}
});
},
playCourseware(){ //播放课件内容
let ctype=this.coursewareInfo.content.contentType;
let $this=this;
if(ctype==10){
//视频播放
}else if(ctype==20){
//音频处理
}else{
if(!$this.coursewareInfo.finish){
this.handleTimeout=setTimeout(() => {$this.saveStudyInfo();}, 5000);
}
}
},
loadScorePraiseAndTrample(){
//加载是否请过分
apiCourseGrade.has(this.courseId).then(rs=>{
if(rs.status==200 && rs.result){
this.scoreInfo.has=true;
}
});
apiPraises.has(1,this.courseId).then(rs=>{
if(rs.status==200 && rs.result){
this.isPraise=true;
}
});
apiTrample.has(this.courseId).then(rs=>{
if(rs.status==200 && rs.result){
this.isTrample=true;
}
});
},
closeScore(){
this.scoreInfo.dlgShow=false;
},
openScore(){
if(this.studyId==''){
this.$refs.messager.show({message:'学习后才可评分',type:'error'});
return;
}
if(this.scoreInfo.has){
this.$refs.messager.show({message:'您已评过分',type:'error'});
return;
}
this.scoreInfo.dlgShow=true;
},
addScore(){
if(this.studyId==''){
this.$refs.messager.show({message:'学习后才可评分',type:'error'});
return;
}
if(this.scoreInfo.has){
this.$refs.messager.show({message:'您已评过分',type:'error'});
this.scoreInfo.dlgShow=false;
return;
}
let postData={
courseId:this.courseInfo.id,
studyId:this.studyId,
score:this.scoreInfo.score
}
if(this.scoreInfo.score>0){
apiCourseGrade.grade(postData).then(rs=>{
if(rs.status==200){
this.scoreInfo.dlgShow=false;
this.scoreInfo.has=true;
this.$refs.messager.show({message:'评分成功谢谢您的评分',type:'success'});
}else{
this.$refs.messager.show({message:'评分分处理失败请稍后再试',type:'error'});
}
});
}
},
praiseContent(){
if(this.studyId==''){
this.$refs.messager.show({message:'学习后才可点赞',type:'error'});
return;
}
//赞和踩只能是一个
if(this.isTrample){
this.$refs.messager.show({message:'踩过了不能再赞了',type:'error'});
return;
}
let postData={
objType:1,
objId:this.courseInfo.id,
title:this.courseInfo.name
}
if(this.interactRuning){
return;
}
this.interactRuning=true;
if(this.isPraise){
apiPraises.remove(1,this.courseInfo.id).then(rs=>{
this.interactRuning=false;
if(rs.status==200){
this.$refs.messager.show({message:'已取消点赞',type:'success'});
this.isPraise=false;
this.courseInfo.praises--;
}else{
this.$refs.messager.show({message:'取消点赞失败,请稍后再试',type:'success'});
}
})
}else{
apiPraises.save(postData).then(rs=>{
this.interactRuning=false;
if(rs.status==200){
this.$refs.messager.show({message:'点赞成功',type:'success'});
this.isPraise=true;
this.courseInfo.praises++;
}else{
this.$refs.messager.show({message:'点赞失败,请稍后再试',type:'success'});
}
})
}
},
treadContent(){
if(this.studyId==''){
this.$refs.messager.show({message:'学习后才能踩吆',type:'error'});
return;
}
//赞和踩只能是一个
if(this.isPraise){
this.$refs.messager.show({message:'赞过了不能再踩了',type:'error'});
return;
}
if(this.interactRuning){
return;
}
this.interactRuning=true;
if(this.isTrample){
apiTrample.remove(this.courseInfo.id).then(rs=>{
this.interactRuning=false;
if(rs.status==200){
this.$refs.messager.show({message:'已取消踩',type:'success'});
this.isTrample=false;
this.courseInfo.trampleCount--;
}else{
this.$refs.messager.show({message:'取消踩失败,请稍后再试',type:'error'});
}
})
}else{
apiTrample.trample(this.courseInfo.id).then(rs=>{
this.interactRuning=false;
if(rs.status==200){
this.$refs.messager.show({message:'已踩',type:'success'});
this.isTrample=true;
this.courseInfo.trampleCount++;
}else{
this.$refs.messager.show({message:'踩失败,请稍后再试',type:'error'});
}
})
}
},
changeScore(score){
if(!score){
return '0.0'
}
score=String(score)
if(score.indexOf('.')!=-1){
score=score.toFixed(1)
}else{
score=score+'.0'
}
return score
},
openComment(){
//打开评论窗口,调用组件内事件
this.$refs.fiexdbar.openInput();
},
refreshComments(){
this.$refs.comments.loadData(false);
},
openShare(){
this.$refs.fiexdbar.addShare();
},
shareSuccess(rs){
this.$refs.messager.show({message:'分享成功',type:'success'});
},
clicktab(idx) {
if(idx==1 || idx==2 || idx==3){
if(this.studyId==''){
uni.showToast({title:'报名后可以查看'})
return;
}
}
this.playerBoxShow = false;
this.tabIndex=idx;
if(idx == 4) {
this.isComments = false;
} else {
this.isComments = true;
}
}
}
}
</script>
<style lang="scss" scoped>
// .fullmark{
// position: fixed;
// width: 100%;
// height: 100%;
// top:0;
// left: 0;
// bottom: 0;
// right: 0;
// pointer-events: none;
// z-index: 9999999;
// display: flex;
// flex-wrap: wrap;
// overflow: hidden;
// .fullmark-text{
// width: 375upx;
// height: 375upx;
// display: flex;
// justify-content: center;
// align-items: center;
// transform: rotate(-36deg);
// color: #d4d4d4;
// font-size: 32upx;
// white-space: nowrap;
// }
// }
.player-box{
position: absolute;
// top: 62px;
// left: 184px;
width: 200px;
left: 50%;
top: 50%;
transform: translate(-50%, -50%);
height: 147px;
background:#a9abb3;
border-radius: 33px;
text-align: center;
padding: 20px;
box-sizing: border-box;
image{
width: 40px;
height: 40px;
margin: 0px 10px;
}
.player-praise{
margin-top: 5px;
display: flex;
// justify-items: center;
justify-content: center;
}
.player-rate{
margin-top: 20px;
text-align: center;
display: flex;
justify-content: center;
}
}
.uavatar{
border:1px solid #73adfe;
background-color: #d9e9ff;
color:#73adfe;
font-size: 12px;
width: 25px;
height: 25px;
display: flex;
justify-content: center;
align-items: center;
.uavatar-scale{
transform:scale(0.8);
}
}
.bm-button{
text-align: center;
//padding: 158upx 100%;
.u-but{
width: 320rpx;
height: 64rpx;
background-color: #2F2F2F;
opacity: 0.4;
border-radius: 10rpx;
border-color:#2F2F2F;
margin: 158rpx auto;
}
}
.player-controls-btn {
position: absolute;
right: 10px;
top: 0px;
display: inline-block;
color: #e5e5e5;
padding: 0 0.4rem;
transition: color 0.3s;
height: 22px;
}
.btn-speed:hover .speed-control {
// visibility: visible;
}
.speed-control {
position: absolute;
top: 180px;
right: -20px;
transition: visibility 0.3s;
transform: translate(-50%, -100%);
}
.speed-control .speed-control-list {
list-style: none;
color: #e5e5e5;
width: 50px;
font-size: 12px;
text-align: left;
padding: 0px 0px 0px 5px;
margin: 0;
overflow: hidden;
border-radius: 4px;
background: rgba(21, 21, 21, 0.8);
}
.speed-control .speed-control-list .li {
position: relative;
display: block;
height: 25px;
line-height: 25px;
}
.speed-control .speed-control-list .li:hover {
color: #fff;
background: rgba(99, 99, 99, 0.8);
}
.speed-control .speed-control-list .li.current {
color: var(--primaryColor);
}
.consultant{
border-bottom: 2px solid #fafafa;
padding: 20upx 0;
.content-title{
font-size: 32upx;
font-family: PingFang SC;
font-weight: 650;
color: #444444;
margin-top: 30upx;
// line-height: 24upx;
}
.content-text{
font-size: 28upx;
font-family: PingFang SC;
font-weight: 400;
color: #787878;
line-height: 33upx;
word-break:break-all;
margin-top: 20upx;
}
}
.main-footer{
background-color: #FFFFFF;
padding: 5px 18px;
display: flex;
justify-content: space-between;
.main-scroe{
display: inline-block;
width: 130rpx;
line-height: 68rpx;
text-align: center;
margin-top: -15rpx;
height: 68rpx;
// padding:20upx 30upx;
background-color: #E5E5E5;
border-radius: 10upx;
font-size: 24upx;
}
.main-praise{
line-height: 30rpx;
}
}
.main-cata{
margin-top: 20upx;
.main-cata-top{
display: flex;
padding: 20upx;
background-color: #FFFFFF;
border-bottom: 1px solid #ececec;
}
.main-cata-active{
background-color: #FFFFFF;
padding: 20upx 20upx 20upx 20upx;
}
}
.tabbar{
height: 50px;
line-height: 50px;
background-color: #FFFFFF;
display: flex;
justify-content: space-around;
color: #575757;
.tabbar-item{
text-align: center;
line-height: 40px;
height: 40px;
}
.active{
border-bottom: 2px solid #00aaff;
color: #00aaff;
}
}
.content-tit{
font-size: 36upx;
font-weight: 700;
word-break:break-all;
// margin-left: 10px;
}
.tags{
margin-top: 5px;
padding-bottom: 10upx;
.tags-item{
display: inline-block;
background: #F6FAFD;
border-radius: 14px;
padding: 8upx 20upx;
margin: 6upx;
color: #6D99FC;
font-size: 28upx;
}
}
.cfield{
line-height: 30upx;
font-size: 28upx;
.cfield-lable{
color: #767676;
}
.cfield-value{
color: #767676;
// margin-left: 10upx;
} font-size: 26rpx;
}
.cscore{
font-size: 24upx;
.cscore-value{
font-size: 38upx;
color: #FFB30F;
}
.cscore-unit{
}
}
.text-row{
margin-top: 6upx;
color: #494949;
line-height: 30px;
font-size: 26upx;
.text-row-label{
margin-left: 10px;
}
}
.btn{
width: 88px;
height: 34px;
background: #5BA2FC;
font-size: 12px;
color: #FFFFFF;
text-align: center;
line-height: 34px;
border-radius: 4px;
margin-left: 10px;
}
.video-div{
position: absolute;
z-index: 999999999;
top: 0;
left: 0;
width: 100%;
height: 100%;
background: #bcbcbc;
}
.paperinfo{
padding-top: 10px;
.paperinfo-title{
text-align: center;
font-size: 30upx;
font-weight: 600;
padding: 10px;
}
.paperinfo-item{
background-color: #FFFFFF;
}
}
.course-title{
text-align: center;
padding: 15px;
}
.endurance{
height: 90px;
background: #FFFFFF;
margin-top: 10px;
.exam{
font-size: 15px;
color: #5EB6A4;
padding-top: 15px;
margin-left: 15px;
}
.endurance-cen{
display: flex;
justify-content: space-between;
margin-right: 11px;
.schedule{
font-size: 12px;
color: #868686;
margin-left: 16px;
}
.schedules{
font-size: 2px;
color: #000000;
margin-left: 13px;
}
.patiently{
font-size: 12px;
color: #868686;
margin-left: 16px;
}
.patientlys{
font-size: 12px;
color: #000000;
margin-left: 13px;
}
}
}
.query{
width: 71px;
height: 27px;
background: #FFB30F;
font-size: 12px;
color: #FFFFFF;
text-align: center;
line-height: 27px;
margin-top: 18px;
}
/deep/.content{
border-radius: 0px;
padding: 2px 20px 10px 15px;
}
.content_top{
display: flex;
justify-content: space-between;
margin-top: 20rpx;
.top_top{
display: flex;
}
.imgs{
width: 30px;
height: 30px;
border-radius: 50%;
}
.teaters{
display: flex;
.top_top{
font-size: 18px;
color: #696969;
margin-top: 12px;
font-weight: bold;
}
.top_bot{
font-size: 15px;
color: #787878;
margin-top: 15px;
font-weight: bold;
margin-left: 2px;
}
}
.share{
width: 64px;
height: 27px;
background: #F8F7FC;
margin-right: 10px;
margin-top: 10px;
.share-img{
width: 16px;
height: 14px;
margin-left: 11px;
}
.session{
font-size: 14px;
text-align: center;
line-height: 28px;
}
}
}
.cinfo{
background: #FFFFFF;
min-height: 800upx;
padding: 20upx;
.cinfo-top{
width: 90%;
height: 58px;
margin-left: 5%;
border-bottom: 2px solid #FAFAFA;
padding-bottom: 10px;
.demar{
font-size: 32upx;
color: #666666;
margin-top: 10px;
padding-top: 18px;
}
.identity{
font-size: 28upx;
color: #787878;
margin-left: 12px;
margin-top: 6px;
}
}
.cinfo-center{
width: 90%;
height: 58px;
margin-left: 5%;
border-bottom: 2px solid #FAFAFA;
.worth{
font-size: 32upx;
color: #666666;
margin-top: 18px;
}
.details{
font-size: 28upx;
color: #787878;
margin-left: 12px;
margin-top: 6px;
}
}
.consultant{
width: 90%;
height: 58px;
margin-left: 5%;
border-bottom: 2px solid #FAFAFA;
.particulars{
font-size: 32upx;
color: #666666;
margin-top: 18px;
}
.matter{
font-size: 28upx;
color: #787878;
margin-left: 12px;
margin-top: 6px;
word-break:break-all;
}
}
}
.fixed-field{
width: 200px;
height: 40px;
line-height: 30px;
background: rgb(247,247,249);
border-radius: 10upx;
display: flex;
.fixed-field-icon{
margin-top: 2px;
margin-left: 10px;
}
.fixed-field-text{
font-size: 12px;
color: #000000;
margin-left: 2px;
margin-top: 5px;
}
}
</style>