Commit 9df090fa authored by wangzhengwen's avatar wangzhengwen

5.12

parent b2df69b1
......@@ -86,20 +86,32 @@ class Course extends BaseController
}
//关联教师
public function teacher()
/**获取课时详情
* @param Request $request
* @return \app\html|\think\response\Json|true
*/
public function getCourseDetail(Request $request)
{
return $this->hasOne(CourseTeacher::class, 'teacher_id', 'id')->field('id,nickname,description');
}
$vo = (new CourseValidate())->goCheck(['course_id']);
if ($vo !== true) {
return $vo;
}
$data = $request->param();
//关联章节
// public function sections()
// {
// return $this->hasMany(Course::class, 'course_id');
// }
$data = (new CourseModel())
// ->with(['getTeacher','getSections'=>['getCourseClass'],'getCourseClass'])
->getCouresDetail($data['course_id']);
return $this->returnMsg('success',1,$data);
public function getCourseDetail(Request $request)
}
/**获取课程章节目录课时
* @param Request $request
* @return \app\html|\think\response\Json|true
*/
public function getCoureseClassList(Request $request)
{
$vo = (new CourseValidate())->goCheck(['course_id']);
if ($vo !== true) {
......@@ -107,9 +119,17 @@ class Course extends BaseController
}
$data = $request->param();
$data = (new CourseModel())->getCouresDetail($data['course_id']);
$data = (new CourseModel())
->with(['getTeacher','getSections'=>['getCourseClass'],'getCourseClass'])
->where('id',$data['course_id'])
->field('id,thumb,title,createtime,description,price,content,teacher_id,tvclick,click')
->find();
return $this->returnMsg('success',1,$data);
}
public function coureseStudy()
{
}
......
<?php
namespace app\api\controller;
use app\api\middleware\Auth;
use app\api\service\UserService;
use app\BaseController;
use think\facade\Request;
use app\api\service\CourseProgressService;
class CourseProgress extends BaseController
{
protected $middleware = [
Auth::class,
];
/**
* 上报学习进度API
*/
public function reportProgress()
{
$data = Request::only(['course_id', 'class_id', 'current_time']);
$token = Request::header('token');
$userId = UserService::getUserInfo($token)['id'];
$result = CourseProgressService::updateProgress(
$userId,
$data['course_id'],
$data['class_id'],
$data['current_time'],
);
if (!$result) {
return $this->returnMsg('视频不存在',0);
}
return $this->returnMsg('操作成功',1,$result);
}
/**
* 获取课程进度API
*/
public function getProgress()
{
$token = Request::header('token');
$userId = UserService::getUserInfo($token)['id'];
$data = Request::only(['course_id','page','pageSize']);
$progress = CourseProgressService::getUserAllCoursesProgress($userId, $data['page'], $data['pageSize']);
return $this->returnMsg('操作成功',1,$progress);
}
/**
* 获取最后学习位置API
*/
public function getLastLearn()
{
$token = Request::header('token');
$userId = UserService::getUserInfo($token)['id'];
$data = Request::only(['course_id']);
$lastLearn = CourseProgressService::getLearnedClasses($userId, $data['course_id']);
return $this->returnMsg('操作成功',1,$lastLearn);
}
}
\ No newline at end of file
<?php
namespace app\api\service;
use app\model\Course;
use app\model\CourseClass;
use app\model\CourseProgress;
class CourseProgressService
{
/**
* 更新学习进度
* @param int $userId 用户ID
* @param int $courseId 课程ID
* @param int $classId 课时ID
* @param int $currentTime 当前观看位置(秒)
* @param int $duration 视频总时长(秒)
* @return array
*/
public static function updateProgress($userId, $courseId, $classId, $currentTime)
{
$duration = CourseClass::where('id',$classId)->value('tvtime');
// $duration = 50;
if (!$duration) {
return false;
}
// 判断是否看完(观看进度超过95%或最后10秒)
$isFinished = ($currentTime >= $duration - 10) || ($currentTime >= $duration * 0.95);
// 查找或创建记录
$progress = CourseProgress::where([
'user_id' => $userId,
'course_id' => $courseId,
'class_id' => $classId
])->findOrEmpty();
if ($progress->isEmpty()) {
// 新记录
$progress = CourseProgress::create([
'user_id' => $userId,
'course_id' => $courseId,
'class_id' => $classId,
'tvtime' => $duration,
'look_tvtime' => $currentTime,
'is_wc_look' => $isFinished ? 1 : 0
]);
} else {
// 更新记录(只更新必要字段)
$updateData = [
'look_tvtime' => $currentTime,
'is_wc_look' => $isFinished ? 1 : $progress->is_wc_look
];
// 如果视频总时长有变化才更新
if ($duration != $progress->tvtime) {
$updateData['tvtime'] = $duration;
}
$progress->save($updateData);
}
return [
'progress' => $progress->look_tvtime,
'duration' => $progress->tvtime,
'is_finished' => $progress->is_wc_look
];
}
/** 获取当前用户所有课程进度统计
* @param $userId
* @return void
*/
public static function getUserAllCoursesProgress($userId, $page = 1, $pageSize = 10)
{
// 获取用户学习过的所有课程ID(去重)
$courseIds = CourseProgress::where('user_id', $userId)
->distinct(true)
->column('course_id');
// 如果没有学习记录,返回空分页
if (empty($courseIds)) {
return [
'total' => 0,
'per_page' => $pageSize,
'current_page' => $page,
'data' => []
];
}
// 分页查询课程基本信息
$query = Course::where('id', 'in', $courseIds)
->field('id,title,description,thumb');
$paginator = $query->paginate([
'list_rows' => $pageSize,
'page' => $page
]);
// 获取分页数据
$list = $paginator->items();
// 为每个课程添加进度信息
foreach ($list as $k => $v) {
$list[$k]['progress'] = self::getCourseProgress($userId, $v['id']);
}
return [
'total' => $paginator->total(),
'per_page' => $paginator->listRows(),
'current_page' => $paginator->currentPage(),
'last_page' => $paginator->lastPage(),
'data' => $list
];
}
/**
* 获取用户课程进度统计
* @param int $userId 用户ID
* @param int $courseId 课程ID
* @return array
*/
public static function getCourseProgress($userId, $courseId)
{
// 获取所有课时进度
$progressList = CourseProgress::with(['class'])
->where('user_id', $userId)
->where('course_id', $courseId)
->select();
// 统计计算
$finishedCount = 0;
$totalDuration = 0;
$learnedDuration = 0;
$classProgress = [];
foreach ($progressList as $item) {
if ($item->is_wc_look) {
$finishedCount++;
}
$totalDuration += $item->tvtime;
$learnedDuration += min($item->look_tvtime, $item->tvtime);
$classProgress[$item->class_id] = [
'progress' => $item->look_tvtime,
'duration' => $item->tvtime,
'is_finished' => $item->is_wc_look,
'last_learn' => $item->createtime
];
}
return [
'finished_count' => $finishedCount,
'total_classes' => count($progressList),
'progress_percent' => $totalDuration > 0 ? round($learnedDuration / $totalDuration * 100) : 0,
'classes' => $classProgress
];
}
/**
* 获取课程最后学习时间
*/
private static function getLastLearnTime($userId, $courseId)
{
$lastProgress = CourseProgress::where('user_id', $userId)
->where('course_id', $courseId)
->order('createtime', 'desc')
->value('createtime');
return $lastProgress ? date('Y-m-d H:i', $lastProgress) : '未学习';
}
/**
* 获取用户最后学习的课时
* @param int $userId 用户ID
* @param int $courseId 课程ID
* @return array|null
*/
public static function getLastLearnedClass($userId, $courseId)
{
$progress = CourseProgress::with(['class'])
->where('user_id', $userId)
->where('course_id', $courseId)
->where('look_tvtime', '>', 0)
->order('createtime', 'desc')
->find();
return $progress ? [
'class_id' => $progress->class_id,
'progress' => $progress->look_tvtime,
'duration' => $progress->tvtime,
'last_time' => $progress->createtime,
'is_finished' => $progress->is_wc_look
] : null;
}
/**多条
* 获取用户最后学习的课时
* @param int $userId 用户ID
* @param int $courseId 课程ID
* @return array|null
*/
public static function getLearnedClasses($userId, $courseId)
{
$progressList = CourseProgress::with(['class'])
->where('user_id', $userId)
->where('course_id', $courseId)
->where('look_tvtime', '>', 0)
->order('createtime', 'desc')
->select()
->toArray();
if (empty($progressList)) {
return [];
}
// 返回所有记录(按时间倒序)
return array_map(function ($progress) {
return [
'class_id' => $progress['class_id'],
'progress' => $progress['look_tvtime'],
'duration' => $progress['tvtime'],
'last_time' => $progress['createtime'],
'is_wc_look' => $progress['is_wc_look']
];
}, $progressList);
}
/**用户课程学习情况看板
* @param $userId
* @return array
* @throws \think\db\exception\DataNotFoundException
* @throws \think\db\exception\DbException
* @throws \think\db\exception\ModelNotFoundException
*/
public static function getUserLearningReport($userId)
{
// 已学习课程数
$learnedCourses = CourseProgress::where('user_id', $userId)
->group('course_id')
->count();
// 总学习时长(小时)
$totalHours = CourseProgress::where('user_id', $userId)
->sum('look_tvtime') / 3600;
// 最近学习记录
$recent = CourseProgress::with(['course', 'class'])
->where('user_id', $userId)
->order('createtime', 'desc')
->limit(5)
->select();
return [
'learned_courses' => $learnedCourses,
'total_hours' => round($totalHours, 1),
'recent_learning' => $recent
];
}
}
\ No newline at end of file
......@@ -56,10 +56,10 @@ class Course extends Model
public function getCouresDetail($course_id = 0)
{
$where = ['status'=>3,'is_sell'=>1,'is_del'=>0];
// $where = ['status'=>3,'is_sell'=>1,'is_del'=>0];
if ($course_id)
{
$where['course_id'] = $course_id;
$where['id'] = $course_id;
}
return self::where($where)
......@@ -68,5 +68,29 @@ class Course extends Model
}
//关联教师
public function getTeacher()
{
return $this->hasOne(CourseTeacher::class, 'id', 'teacher_id')
->field('id,nickname,description');
}
//关联章节
public function getSections()
{
return $this->hasMany(CourseClassCategory::class, 'course_id','id')
->where('is_del',0)
->order('sort','asc')
->field('id,title,course_id');
}
//关联课时
public function getCourseClass()
{
return $this->hasMany(\app\model\CourseClass::class, 'course_id','id')
->where('is_del',0)
->order('sort','asc');
}
}
\ No newline at end of file
<?php
namespace app\model;
use think\Model;
class CourseClass extends Model
{
}
\ No newline at end of file
<?php
namespace app\model;
use think\Model;
class CourseClassCategory extends Model
{
//关联课时
public function getCourseClass()
{
return $this->hasMany(\app\model\CourseClass::class, 'cate_id','id')
// ->where('is_del',0)
->order('sort','asc');
// ->field('id,title,cate_id');
}
}
\ No newline at end of file
<?php
namespace app\model;
use app\model\project\User;
use think\Model;
class CourseProgress extends Model
{
// 设置完整表名
protected $table = 'fj_course_progress';
// 自动时间戳(将createtime转换为时间戳自动管理)
protected $autoWriteTimestamp = true;
protected $createTime = 'createtime';
protected $updateTime = 'updatetime'; // 不需要更新时间字段
// 关联课程
public function course()
{
return $this->belongsTo(Course::class, 'course_id');
}
// 关联章节(课时)
public function class()
{
return $this->belongsTo(CourseClass::class, 'class_id');
}
// 关联用户
public function user()
{
return $this->belongsTo(User::class, 'user_id');
}
}
\ No newline at end of file
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment