From e11362ca4849da567a77d8b5e5be510df9fb0741 Mon Sep 17 00:00:00 2001
From: hjl <1657978663@qq.com>
Date: 星期一, 17 六月 2024 11:51:51 +0800
Subject: [PATCH] fix: 学习端bug

---
 ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/vo/LearnStudyVO.java                            |   20 
 ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/vo/StudyStoryVO.java                            |   20 
 ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/vo/StudyModelVO.java                            |    2 
 ruoyi-service/ruoyi-study/src/main/resources/mapper/sutdy/TStudyMapper.xml                              |   19 
 ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/service/ITStoryService.java                     |   10 
 ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/service/impl/TStoryServiceImpl.java             |   22 
 ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/vo/UserPersonalCenterVO.java                    |    3 
 ruoyi-api/ruoyi-api-study/src/main/java/com/ruoyi/study/api/vo/UserPersonalCenterVO.java                |   29 
 ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/service/impl/TGameServiceImpl.java              |    7 
 ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/vo/GameMemoryVoiceVO.java                       |   24 
 ruoyi-service/ruoyi-goods/src/main/java/com/ruoyi/goods/service/impl/RecipientServiceImpl.java          |    4 
 ruoyi-common/ruoyi-common-core/src/main/java/com/ruoyi/common/core/constant/Constants.java              |   11 
 ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/vo/StudyAnswerResultVO.java                     |   14 
 ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/service/impl/TUserStudyServiceImpl.java         |   20 
 ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/service/impl/TUserServiceImpl.java              |   33 
 ruoyi-service/ruoyi-goods/src/main/java/com/ruoyi/goods/service/impl/TGoodsServiceImpl.java             |   29 
 ruoyi-api/ruoyi-api-study/src/main/java/com/ruoyi/study/api/factory/StudyFallbackFactory.java           |    2 
 ruoyi-service/ruoyi-goods/src/main/java/com/ruoyi/goods/controller/TGoodsController.java                |   77 +
 ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/service/IUserStudyRecordService.java            |   17 
 ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/service/impl/UserStudyRecordServiceImpl.java    |   20 
 ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/service/impl/TSubjectRecordServiceImpl.java     |   38 +
 ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/vo/StudyLookResultVO.java                       |    7 
 ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/vo/StudyGameMemoryVO.java                       |   42 +
 ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/vo/StudyListenResultVO.java                     |    5 
 ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/vo/StudyRecordVO.java                           |   25 
 ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/vo/StudyInductionResultVO.java                  |    5 
 ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/vo/StudyGameResultVO.java                       |   11 
 ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/service/ITGameService.java                      |    1 
 ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/service/ITSubjectRecordService.java             |   20 
 ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/vo/ExitLearnVO.java                             |   56 +
 ruoyi-service/ruoyi-goods/src/main/java/com/ruoyi/goods/service/IRecipientService.java                  |    2 
 ruoyi-api/ruoyi-api-study/src/main/java/com/ruoyi/study/api/feignClient/StudyClient.java                |    9 
 ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/service/impl/TStudyServiceImpl.java             |  429 ++++++++++---
 ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/service/ITStudyService.java                     |   26 
 ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/domain/TStudyListen.java                        |    1 
 ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/mapper/UserStudyRecordMapper.java               |   16 
 ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/dto/StudyWeekDTO.java                           |    9 
 ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/service/ITStoryListenService.java               |    4 
 ruoyi-service/ruoyi-study/src/main/resources/mapper/sutdy/UserStudyRecordMapper.xml                     |    4 
 ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/vo/StudyPairResultVO.java                       |    9 
 ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/domain/TUserStudy.java                          |   17 
 ruoyi-service/ruoyi-goods/src/main/java/com/ruoyi/goods/service/impl/RegionServiceImpl.java             |    6 
 ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/vo/QuestionsAnswersSubjectVO.java               |   20 
 ruoyi-api/ruoyi-api-management/src/main/java/com/ruoyi/management/api/feignClient/ManagementClient.java |    4 
 ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/domain/TSubjectRecord.java                      |   21 
 ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/dto/CompleteStudyDTO.java                       |   33 
 ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/domain/TUserStudyRecord.java                    |   79 ++
 ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/config/DataUpdateHandlerConfig.java             |   11 
 ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/service/impl/TStoryListenServiceImpl.java       |    6 
 ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/controller/TStudyController.java                |  389 ++++++++----
 ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/mapper/TStoryListenMapper.java                  |    4 
 ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/vo/SubjectRecordResultVO.java                   |   48 +
 ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/controller/TUserController.java                 |   62 +
 ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/vo/GameMemoryPhotoVO.java                       |   24 
 ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/vo/StudyStoryListenResultVO.java                |    5 
 55 files changed, 1,418 insertions(+), 413 deletions(-)

diff --git a/ruoyi-api/ruoyi-api-management/src/main/java/com/ruoyi/management/api/feignClient/ManagementClient.java b/ruoyi-api/ruoyi-api-management/src/main/java/com/ruoyi/management/api/feignClient/ManagementClient.java
index 9236adf..4310c6c 100644
--- a/ruoyi-api/ruoyi-api-management/src/main/java/com/ruoyi/management/api/feignClient/ManagementClient.java
+++ b/ruoyi-api/ruoyi-api-management/src/main/java/com/ruoyi/management/api/feignClient/ManagementClient.java
@@ -41,9 +41,9 @@
     R<TSysSet> shareInfo();
 
     /**
-     * 获取分享图片、标题及可获积分数
+     * 获取正确及错误提示音效
      *
-     * @return 获取分享图片、标题及可获积分数
+     * @return 获取正确及错误提示音效
      */
     @GetMapping("/tSysSet/promptVoice")
     R<TSysSet> promptVoice();
diff --git a/ruoyi-api/ruoyi-api-study/src/main/java/com/ruoyi/study/api/factory/StudyFallbackFactory.java b/ruoyi-api/ruoyi-api-study/src/main/java/com/ruoyi/study/api/factory/StudyFallbackFactory.java
index 1e216f3..234efd5 100644
--- a/ruoyi-api/ruoyi-api-study/src/main/java/com/ruoyi/study/api/factory/StudyFallbackFactory.java
+++ b/ruoyi-api/ruoyi-api-study/src/main/java/com/ruoyi/study/api/factory/StudyFallbackFactory.java
@@ -131,7 +131,7 @@
             }
 
             @Override
-            public R<TUser> userInfo() {
+            public R<UserPersonalCenterVO> userInfo() {
                 return R.fail("获取用户信息失败" + cause.getMessage());
             }
 
diff --git a/ruoyi-api/ruoyi-api-study/src/main/java/com/ruoyi/study/api/feignClient/StudyClient.java b/ruoyi-api/ruoyi-api-study/src/main/java/com/ruoyi/study/api/feignClient/StudyClient.java
index fb3d775..530660e 100644
--- a/ruoyi-api/ruoyi-api-study/src/main/java/com/ruoyi/study/api/feignClient/StudyClient.java
+++ b/ruoyi-api/ruoyi-api-study/src/main/java/com/ruoyi/study/api/feignClient/StudyClient.java
@@ -175,14 +175,9 @@
     @PostMapping("/base/tStory/updateState/{id}/{state}")
     R updateState1(@PathVariable("id") Integer id, @PathVariable("state") Integer state);
 
-    /**
-     * 获取用户信息
-     *
-     * @return 用户信息
-     */
     @GetMapping("/base/user/userInfo")
-    @ApiOperation(value = "用户详情", tags = {"用户详情"})
-    R<TUser> userInfo();
+    @ApiOperation(value = "用户详情", tags = {"学习端-用户详情"})
+    R<UserPersonalCenterVO> userInfo();
 
     /**
      * 生成积分明细-用于远程调用
diff --git a/ruoyi-api/ruoyi-api-study/src/main/java/com/ruoyi/study/api/vo/UserPersonalCenterVO.java b/ruoyi-api/ruoyi-api-study/src/main/java/com/ruoyi/study/api/vo/UserPersonalCenterVO.java
new file mode 100644
index 0000000..0441835
--- /dev/null
+++ b/ruoyi-api/ruoyi-api-study/src/main/java/com/ruoyi/study/api/vo/UserPersonalCenterVO.java
@@ -0,0 +1,29 @@
+package com.ruoyi.study.api.vo;
+
+import com.ruoyi.study.api.domain.TUser;
+import com.ruoyi.study.api.model.TUserStudy;
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+
+/**
+ * @author HJL
+ * @version 1.0
+ * @since 2024-06-04 9:38
+ */
+@Data
+public class UserPersonalCenterVO {
+
+    @ApiModelProperty("用户信息")
+    private TUser user;
+
+    @ApiModelProperty("用户学习信息(学习时长、学习进度)")
+    private TUserStudy userStudy;
+
+    public UserPersonalCenterVO(TUser user, TUserStudy userStudy) {
+        this.user = user;
+        this.userStudy = userStudy;
+    }
+
+    public UserPersonalCenterVO() {
+    }
+}
diff --git a/ruoyi-common/ruoyi-common-core/src/main/java/com/ruoyi/common/core/constant/Constants.java b/ruoyi-common/ruoyi-common-core/src/main/java/com/ruoyi/common/core/constant/Constants.java
index cb8ae8a..b3e1213 100644
--- a/ruoyi-common/ruoyi-common-core/src/main/java/com/ruoyi/common/core/constant/Constants.java
+++ b/ruoyi-common/ruoyi-common-core/src/main/java/com/ruoyi/common/core/constant/Constants.java
@@ -231,6 +231,11 @@
     public static final Integer SEVEN = 7;
 
     /**
+     * -1
+     */
+    public static final Integer BURDEN_ONE = -1;
+
+    /**
      * 1数字
      */
     public static final Integer ONE_HUNDRED = 100;
@@ -293,16 +298,16 @@
     /**
      * 积分来源 - 完成听故事
      */
-    public static final String COMPLETE_STORY= "完成听故事";
+    public static final String COMPLETE_STORY = "完成听故事";
 
     /**
      * 超级听力
      */
-    public static final String HEARING= "超级听力";
+    public static final String HEARING = "超级听力";
 
     /**
      * 超级听力
      */
-    public static final String MEMORY= "超级记忆";
+    public static final String MEMORY = "超级记忆";
 
 }
diff --git a/ruoyi-service/ruoyi-goods/src/main/java/com/ruoyi/goods/controller/TGoodsController.java b/ruoyi-service/ruoyi-goods/src/main/java/com/ruoyi/goods/controller/TGoodsController.java
index dd26251..0cfcc7b 100644
--- a/ruoyi-service/ruoyi-goods/src/main/java/com/ruoyi/goods/controller/TGoodsController.java
+++ b/ruoyi-service/ruoyi-goods/src/main/java/com/ruoyi/goods/controller/TGoodsController.java
@@ -3,7 +3,9 @@
 
 import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
 import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
+import com.ruoyi.common.core.constant.Constants;
 import com.ruoyi.common.core.domain.R;
+import com.ruoyi.common.core.exception.GlobalException;
 import com.ruoyi.common.core.utils.bean.BeanUtils;
 import com.ruoyi.common.core.web.page.PageInfo;
 import com.ruoyi.common.security.service.TokenService;
@@ -16,6 +18,7 @@
 import com.ruoyi.goods.vo.TOrderVO;
 import com.ruoyi.study.api.domain.TUser;
 import com.ruoyi.study.api.feignClient.StudyClient;
+import com.ruoyi.system.api.model.LoginUserParent;
 import io.swagger.annotations.ApiImplicitParam;
 import io.swagger.annotations.ApiImplicitParams;
 import io.swagger.annotations.ApiOperation;
@@ -95,12 +98,11 @@
     }
 
     @PostMapping("/goodListStudy")
-    @ApiOperation(value = "商品列表查询", tags = {"学习端"})
+    @ApiOperation(value = "商品列表查询", tags = {"学习端-商城"})
     public R<PageInfo<TGoods>> goodListStudy(@RequestBody GoodQueryDTO goodQuery) {
         if (tokenService.getLoginUserStudy() == null) {
             return R.tokenError("登录失效");
         }
-        List<String> type = goodQuery.getType();
         String keywords = goodQuery.getKeywords();
         // 初始化条件构造器
         QueryWrapper<TGoods> wrapper = new QueryWrapper<>();
@@ -108,7 +110,6 @@
 
         // 类型匹配 todo
         if (goodQuery.getType() != null && goodQuery.getType().size() > 0) {
-            StringBuilder temp = new StringBuilder("");
             for (String s : goodQuery.getType()) {
                 wrapper.or().apply("FIND_IN_SET('" + s + "', typeIds)"); // 将每个类型 ID 应用于 FIND_IN_SET 函数
             }
@@ -224,7 +225,7 @@
     @GetMapping("/exchangeRecordParent")
     @ApiOperation(value = "家长端-兑换记录", tags = {"家长端-兑换记录"})
     public R<Page<TOrder>> exchangeRecordParent(Integer pageNumber, Integer pageSize) {
-        if (tokenService.getLoginUser1() == null){
+        if (tokenService.getLoginUser1() == null) {
             return R.tokenError("登录失效");
         }
         Page<TOrder> page = orderService.page(new Page<>(pageNumber, pageSize), new QueryWrapper<TOrder>().eq("userId", tokenService.getLoginUser1().getUserid())
@@ -235,7 +236,7 @@
             tOrder.setName(byId.getName());
             tOrder.setImg(byId.getCoverImg());
             StringBuilder stringBuilder = new StringBuilder();
-            if (StringUtils.hasLength(byId.getTypeIds())){
+            if (StringUtils.hasLength(byId.getTypeIds())) {
                 String[] split = byId.getTypeIds().split(",");
                 for (String s : split) {
                     TGoodsType byId1 = goodsTypeService.getById(s);
@@ -321,7 +322,7 @@
         // 如果设置为默认地址 那么要将之前的默认地址取消掉
         List<Recipient> userId = recipientService.list(new QueryWrapper<Recipient>()
                 .eq("userId", tokenService.getLoginUser1().getUserid())
-                .ne("id",byId.getId()));
+                .ne("id", byId.getId()));
         for (Recipient recipient1 : userId) {
             recipient1.setIsDefault(0);
             recipientService.updateById(recipient1);
@@ -339,16 +340,17 @@
             @ApiImplicitParam(value = "地址id", name = "id", dataType = "String", required = true)
     })
     public R setDefaultStudy(@RequestParam Integer id) {
-        if (tokenService.getLoginUserStudy() == null) {
-            return R.tokenError("登录失效");
+        LoginUserParent userStudy = tokenService.getLoginUserStudy();
+        if (null == userStudy) {
+            return R.tokenError("登录失效!");
         }
         Recipient byId = recipientService.getById(id);
         byId.setIsDefault(1);
         recipientService.updateById(byId);
         // 如果设置为默认地址 那么要将之前的默认地址取消掉
         List<Recipient> userId = recipientService.list(new QueryWrapper<Recipient>()
-                .eq("userId", tokenService.getLoginUser1().getUserid())
-                .ne("id",byId.getId()));
+                .eq("userId", userStudy.getUserid())
+                .ne("id", byId.getId()));
         for (Recipient recipient1 : userId) {
             recipient1.setIsDefault(0);
             recipientService.updateById(recipient1);
@@ -417,18 +419,21 @@
     @ApiOperation(value = "新增收货地址/修改收货地址", tags = {"学习端-收货地址"})
     @ApiOperationSupport(order = 33)
     public R<String> addressSave(@RequestBody Recipient recipient) {
+        LoginUserParent userStudy = tokenService.getLoginUserStudy();
+        if (null == userStudy) {
+            return R.tokenError("登录失效!");
+        }
         recipient.setUserId(tokenService.getLoginUserStudy().getUserid());
-        if (recipient.getIsDefault() == 1){
+        if (recipient.getIsDefault() == 1) {
             // 如果设置为默认地址 那么要将之前的默认地址取消掉
             List<Recipient> userId = recipientService.list(new QueryWrapper<Recipient>()
-                    .eq("userId", tokenService.getLoginUser1().getUserid()));
+                    .eq("userId", userStudy.getUserid()));
             for (Recipient recipient1 : userId) {
                 recipient1.setIsDefault(0);
                 recipientService.updateById(recipient1);
             }
         }
-        recipientService.addressSaveOrUpdate(recipient);
-        return R.ok();
+        return recipientService.addressSaveOrUpdate(recipient) ? R.ok() : R.fail();
     }
 
     /**
@@ -438,12 +443,12 @@
     @ApiOperation(value = "家长端-新增收货地址/修改收货地址", tags = {"家长端-新增收货地址/修改收货地址"})
     @ApiOperationSupport(order = 20)
     public R<String> addressSaveOrUpdateParent(@RequestBody Recipient recipient) {
-        if (tokenService.getLoginUser1() == null){
+        if (tokenService.getLoginUser1() == null) {
             return R.tokenError("登录失效!");
         }
         recipient.setUserId(tokenService.getLoginUser1().getUserid());
-        if (recipient.getId() != null){
-            if (recipient.getIsDefault() == 1){
+        if (recipient.getId() != null) {
+            if (recipient.getIsDefault() == 1) {
                 // 如果设置为默认地址 那么要将之前的默认地址取消掉
                 List<Recipient> userId = recipientService.list(new QueryWrapper<Recipient>()
                         .eq("userId", tokenService.getLoginUser1().getUserid()));
@@ -453,8 +458,8 @@
                 }
             }
             recipientService.updateById(recipient);
-        }else{
-            if (recipient.getIsDefault() == 1){
+        } else {
+            if (recipient.getIsDefault() == 1) {
                 // 如果设置为默认地址 那么要将之前的默认地址取消掉
                 List<Recipient> userId = recipientService.list(new QueryWrapper<Recipient>()
                         .eq("userId", tokenService.getLoginUser1().getUserid()));
@@ -543,16 +548,26 @@
     @GetMapping("/updateOrderAddress")
     @ApiOperation(value = "修改订单收货地址", tags = {"学习端-收货地址"})
     @ApiOperationSupport(order = 36)
+    @ApiImplicitParams({
+            @ApiImplicitParam(value = "订单id", name = "orderId", dataType = "String", required = true),
+            @ApiImplicitParam(value = "地址信息id", name = "recipientId", dataType = "String", required = true)
+    })
     public R updateOrderAddress(@RequestParam Integer orderId, @RequestParam Integer recipientId) {
         if (tokenService.getLoginUserStudy() == null) {
             return R.tokenError("登录失效");
         }
-        Recipient userId = recipientService.getById(recipientId);
-        TOrder byId = orderService.getById(orderId);
-        byId.setConsigneeName(userId.getAddress());
-        byId.setConsigneePhone(userId.getRecipientPhone());
-        byId.setConsigneeAddress(userId.getAddress());
-        orderService.updateById(byId);
+        Recipient recipient = recipientService.getById(recipientId);
+        TOrder order = orderService.getById(orderId);
+        if (null == order) {
+            throw new GlobalException("订单不存在!");
+        }
+        if (!Constants.ONE.equals(order.getState())) {
+            throw new GlobalException("订单已发货,无法修改收货地址!");
+        }
+        order.setConsigneeName(recipient.getAddress());
+        order.setConsigneePhone(recipient.getRecipientPhone());
+        order.setConsigneeAddress(recipient.getAddress());
+        orderService.updateById(order);
         return R.ok();
     }
 
@@ -584,7 +599,7 @@
     @ApiOperation(value = "商品分类列表", tags = {"学习端-商城"})
     @ApiOperationSupport(order = 39)
     public R<List<TGoodsType>> goodTypeStudy() {
-        return R.ok(goodsTypeService.lambdaQuery().eq(TGoodsType::getIsDelete, 0).eq(TGoodsType::getIsDelete, 0).list());
+        return R.ok(goodsTypeService.lambdaQuery().eq(TGoodsType::getIsDelete, 0).list());
     }
 
     /**
@@ -601,6 +616,9 @@
     public R<GoodDetailVO> goodDetail(@RequestParam String goodId) {
         // 商品详情
         TGoods goods = goodsService.lambdaQuery().eq(TGoods::getId, goodId).one();
+        if (null == goods) {
+            throw new GlobalException("获取商品详情失败,商品不存在!");
+        }
         // 商品分类详情
         List<TGoodsType> goodsTypes = goodsTypeService.lambdaQuery().in(TGoodsType::getId, Arrays.asList(goods.getTypeIds().split(","))).list();
         // 已兑换人数
@@ -625,6 +643,9 @@
         }
         // 商品详情
         TGoods goods = goodsService.lambdaQuery().eq(TGoods::getId, goodId).one();
+        if (null == goods) {
+            throw new GlobalException("获取商品详情失败,商品不存在!");
+        }
         // 商品分类详情
         List<TGoodsType> goodsTypes = goodsTypeService.lambdaQuery().in(TGoodsType::getId, Arrays.asList(goods.getTypeIds().split(","))).list();
         // 已兑换人数
@@ -681,12 +702,12 @@
         Recipient recipient = recipientService.lambdaQuery()
                 .eq(Recipient::getUserId, tokenService.getLoginUser1().getUserid())
                 .eq(Recipient::getIsDefault, 1).one();
-        if (recipient == null){
+        if (recipient == null) {
             // 随便取一条地址数据
             List<Recipient> list = recipientService.lambdaQuery()
                     .eq(Recipient::getUserId, tokenService.getLoginUser1().getUserid())
                     .eq(Recipient::getIsDefault, 1).list();
-            if (!list.isEmpty()){
+            if (!list.isEmpty()) {
                 recipient = list.get(0);
             }
         }
diff --git a/ruoyi-service/ruoyi-goods/src/main/java/com/ruoyi/goods/service/IRecipientService.java b/ruoyi-service/ruoyi-goods/src/main/java/com/ruoyi/goods/service/IRecipientService.java
index 08fc851..cbd3711 100644
--- a/ruoyi-service/ruoyi-goods/src/main/java/com/ruoyi/goods/service/IRecipientService.java
+++ b/ruoyi-service/ruoyi-goods/src/main/java/com/ruoyi/goods/service/IRecipientService.java
@@ -20,5 +20,5 @@
      * @param recipient 收货地址信息
      * @return 操作结果
      */
-    String addressSaveOrUpdate(Recipient recipient);
+    Boolean addressSaveOrUpdate(Recipient recipient);
 }
diff --git a/ruoyi-service/ruoyi-goods/src/main/java/com/ruoyi/goods/service/impl/RecipientServiceImpl.java b/ruoyi-service/ruoyi-goods/src/main/java/com/ruoyi/goods/service/impl/RecipientServiceImpl.java
index cf643bc..4507a7c 100644
--- a/ruoyi-service/ruoyi-goods/src/main/java/com/ruoyi/goods/service/impl/RecipientServiceImpl.java
+++ b/ruoyi-service/ruoyi-goods/src/main/java/com/ruoyi/goods/service/impl/RecipientServiceImpl.java
@@ -27,7 +27,7 @@
 
     @Override
     @Transactional(rollbackFor = Exception.class)
-    public String addressSaveOrUpdate(Recipient recipient) {
+    public Boolean addressSaveOrUpdate(Recipient recipient) {
         boolean result;
         // 主键ID为空,新增收货地址
         if (null == recipient.getId()) {
@@ -36,6 +36,6 @@
         } else {
             result = this.updateById(recipient);
         }
-        return result ? "操作成功!" : "操作失败!";
+        return result;
     }
 }
diff --git a/ruoyi-service/ruoyi-goods/src/main/java/com/ruoyi/goods/service/impl/RegionServiceImpl.java b/ruoyi-service/ruoyi-goods/src/main/java/com/ruoyi/goods/service/impl/RegionServiceImpl.java
index 1432bb9..2fe4a05 100644
--- a/ruoyi-service/ruoyi-goods/src/main/java/com/ruoyi/goods/service/impl/RegionServiceImpl.java
+++ b/ruoyi-service/ruoyi-goods/src/main/java/com/ruoyi/goods/service/impl/RegionServiceImpl.java
@@ -46,6 +46,12 @@
                 region.getChildren().add(e);
             }
         });
+        for (Region region : treeData) {
+            List<Region> children = region.getChildren();
+            for (Region child : children) {
+                child.setChildren(new ArrayList<>());
+            }
+        }
         return treeData;
     }
 
diff --git a/ruoyi-service/ruoyi-goods/src/main/java/com/ruoyi/goods/service/impl/TGoodsServiceImpl.java b/ruoyi-service/ruoyi-goods/src/main/java/com/ruoyi/goods/service/impl/TGoodsServiceImpl.java
index 4eae5a5..cca412f 100644
--- a/ruoyi-service/ruoyi-goods/src/main/java/com/ruoyi/goods/service/impl/TGoodsServiceImpl.java
+++ b/ruoyi-service/ruoyi-goods/src/main/java/com/ruoyi/goods/service/impl/TGoodsServiceImpl.java
@@ -4,6 +4,7 @@
 import com.ruoyi.common.core.constant.Constants;
 import com.ruoyi.common.core.constant.RedisConstants;
 import com.ruoyi.common.core.domain.R;
+import com.ruoyi.common.core.exception.GlobalException;
 import com.ruoyi.common.security.service.TokenService;
 import com.ruoyi.goods.domain.Recipient;
 import com.ruoyi.goods.domain.TGoods;
@@ -16,7 +17,7 @@
 import com.ruoyi.goods.vo.TGoodsVO;
 import com.ruoyi.study.api.domain.TUser;
 import com.ruoyi.study.api.feignClient.StudyClient;
-import com.ruoyi.system.api.model.LoginUserParent;
+import com.ruoyi.study.api.vo.UserPersonalCenterVO;
 import org.redisson.api.RSemaphore;
 import org.redisson.api.RedissonClient;
 import org.springframework.stereotype.Service;
@@ -75,22 +76,26 @@
             return R.exchangeError("商品不存在,请稍后重试!");
         }
         // 校验用户积分是否足够兑换
-        TUser user = studyClient.userInfo().getData();
-        LoginUserParent loginUser1 = tokenService.getLoginUser1();
-        if (user == null){
-            user = studyClient.getUserById(loginUser1.getUserid()).getData();
+        UserPersonalCenterVO userPersonalCenter = studyClient.userInfo().getData();
+        if (null == userPersonalCenter) {
+            throw new GlobalException("用户信息获取失败!");
         }
+        TUser user = userPersonalCenter.getUser();
         int needIntegral = good.getIntegral() * number;
         if (user.getIntegral() < needIntegral) {
             return R.exchangeError("兑换失败,当前剩余积分不足!");
         }
         // 检查用户兑换数量是否超过单用户最大兑换数量
-        List<TOrder> orderList = orderService.lambdaQuery().eq(TOrder::getUserId, user.getId()).eq(TOrder::getGoodsId, goodId).list();
+        List<TOrder> orderList = orderService.lambdaQuery().eq(TOrder::getUserId, user.getId())
+                .eq(TOrder::getGoodsId, goodId).list();
         // 该商品订单为空、订单数量未超过商品的单个用户兑换上限数量时,可以进行兑换
-        int totalNumber = orderList.stream().map(TOrder::getCount).collect(Collectors.toList()).stream().mapToInt(Integer::intValue).sum();
-        boolean canExchange = orderList.isEmpty() || null == good.getUserCount() || (totalNumber + number) <= good.getUserCount();
+        int totalNumber = orderList.stream().map(TOrder::getCount).collect(Collectors.toList())
+                .stream().mapToInt(Integer::intValue).sum();
+        boolean canExchange = orderList.isEmpty() || null == good.getUserCount() ||
+                (totalNumber + number) <= good.getUserCount();
         if (!canExchange) {
-            return R.exchangeError("兑换失败,当前兑换数量已超过最大兑换数量,剩余兑换数量为: " + (good.getUserCount() - totalNumber) + "!");
+            return R.exchangeError("兑换失败,当前兑换数量已超过最大兑换数量,剩余兑换数量为: " +
+                    (good.getUserCount() - totalNumber) + "!");
         }
         // redisson分布式锁,防止超卖
         String key = String.format(RedisConstants.GOOD_STOCK, good.getId());
@@ -111,7 +116,8 @@
         // 扣除用户积分
         result = result && studyClient.exchangeIntegral(needIntegral, Constants.BURDEN).getData();
         // 扣除库存
-        result = result && this.lambdaUpdate().set(TGoods::getSurplus, good.getSurplus() - number).eq(TGoods::getId, good.getId()).update();
+        result = result && this.lambdaUpdate().set(TGoods::getSurplus, good.getSurplus() - number)
+                .eq(TGoods::getId, good.getId()).update();
         if (!result) {
             semaphore.release(number);
             return R.exchangeError("商品兑换失败!");
@@ -129,7 +135,7 @@
             return R.exchangeError("商品不存在,请稍后重试!");
         }
         // 校验用户积分是否足够兑换
-        if (tokenService.getLoginUser1() == null){
+        if (tokenService.getLoginUser1() == null) {
             return R.tokenError("登录失效");
         }
         TUser user = studyClient.getUserById(tokenService.getLoginUser1().getUserid()).getData();
@@ -188,6 +194,7 @@
         order.setDisabled(Boolean.FALSE);
         return order;
     }
+
     private TOrder orderInfo1(GoodExchangeDTO goodExchange, Recipient recipient, Integer number, Integer goodId, int needIntegral) {
         TOrder order = new TOrder();
         order.setOrderNumber(goodExchange.getOrderNumber());
diff --git a/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/config/DataUpdateHandlerConfig.java b/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/config/DataUpdateHandlerConfig.java
index 6e003ba..a40933b 100644
--- a/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/config/DataUpdateHandlerConfig.java
+++ b/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/config/DataUpdateHandlerConfig.java
@@ -3,6 +3,7 @@
 import com.baomidou.mybatisplus.core.handlers.MetaObjectHandler;
 import com.ruoyi.common.security.service.TokenService;
 import com.ruoyi.system.api.model.LoginUser;
+import com.ruoyi.system.api.model.LoginUserParent;
 import lombok.extern.slf4j.Slf4j;
 import org.apache.ibatis.reflection.MetaObject;
 import org.springframework.beans.factory.annotation.Autowired;
@@ -30,8 +31,6 @@
 
     /**
      * 新增数据执行
-     *
-     * @param metaObject
      */
     @Override
     public void insertFill(MetaObject metaObject) {
@@ -61,15 +60,13 @@
 
     /**
      * 修改数据执行
-     *
-     * @param metaObject
      */
     @Override
     public void updateFill(MetaObject metaObject) {
         //  获取登录信息
-        LoginUser loginUser = tokenService.getLoginUser();
-        if (loginUser != null) {
-            String userName = loginUser.getUsername();
+        LoginUserParent userStudy = tokenService.getLoginUserStudy();
+        if (userStudy != null) {
+            String userName = userStudy.getName();
             if (StringUtils.hasLength(userName)) {
                 this.setFieldValByName("createBy", userName, metaObject);
                 this.setFieldValByName("createTime", new Date(), metaObject);
diff --git a/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/controller/TStudyController.java b/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/controller/TStudyController.java
index 89fc3b6..f24d629 100644
--- a/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/controller/TStudyController.java
+++ b/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/controller/TStudyController.java
@@ -2,16 +2,17 @@
 
 import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
 import com.baomidou.mybatisplus.core.metadata.IPage;
+import com.baomidou.mybatisplus.extension.conditions.update.LambdaUpdateChainWrapper;
 import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
 import com.ruoyi.common.core.constant.Constants;
 import com.ruoyi.common.core.domain.R;
 import com.ruoyi.common.core.exception.GlobalException;
 import com.ruoyi.common.core.web.page.PageInfo;
-import com.ruoyi.common.redis.service.RedisService;
 import com.ruoyi.common.security.service.TokenService;
 import com.ruoyi.goods.api.feignClient.GoodsClient;
 import com.ruoyi.goods.api.model.TGoodsVO;
 import com.ruoyi.management.api.feignClient.ManagementClient;
+import com.ruoyi.management.api.model.TSysSet;
 import com.ruoyi.study.domain.*;
 import com.ruoyi.study.dto.*;
 import com.ruoyi.study.service.*;
@@ -70,13 +71,13 @@
     @Resource
     private ITIntegralRecordService integralRecordService;
     @Resource
-    private RedisService redisService;
-    @Resource
     private ITUserService userService;
     @Resource
     private TokenService tokenService;
     @Resource
     private ITSubjectRecordService subjectRecordService;
+    @Resource
+    private IUserStudyRecordService studyRecordService;
     @Resource
     private ManagementClient managementClient;
 
@@ -143,7 +144,7 @@
                 List<TSubject> list1 = subjectService.list(wrapper);
                 List<TSubject> tSubjects = new ArrayList<>();
                 for (TSubject tSubject : list1) {
-                    if (!tSubject.getError().isEmpty()){
+                    if (!tSubject.getError().isEmpty()) {
                         tSubjects.add(tSubject);
                     }
                 }
@@ -667,24 +668,40 @@
      */
     @GetMapping("/goodRecommend")
     @ApiOperation(value = "可兑换商品推荐", tags = {"学习端-首页"})
-    public R<List<TGoodsVO>> studySchedule() {
+    public R<List<TGoodsVO>> goodRecommend() {
         return R.ok(goodsClient.goodRecommend().getData());
+    }
+
+    /**
+     * 获取正确及错误提示音效
+     */
+    @GetMapping("/promptVoice")
+    @ApiOperation(value = "获取正确及错误提示音效", tags = {"学习端-首页"})
+    public R<TSysSet> promptVoice() {
+        return R.ok(managementClient.promptVoice().getData());
     }
 
     /**
      * 首次页面加载时调用,获取学习进度及学习时长等信息
      *
      * @param week 周目
-     * @param day  所属day
      */
     @GetMapping("/studySchedule")
     @ApiOperation(value = "获取用户学习进度", tags = {"学习端-首页"})
     @ApiImplicitParams({
-            @ApiImplicitParam(value = "周目", name = "week", dataType = "Integer", required = true),
-            @ApiImplicitParam(value = "所属day", name = "day", dataType = "Integer", required = true)
+            @ApiImplicitParam(value = "周目", name = "week", dataType = "Integer", required = true)
     })
-    public R<TUserStudy> studySchedule(@RequestParam Integer week, @RequestParam Integer day) {
-        TUserStudy result = studyService.studySchedule(String.valueOf(tokenService.getLoginUserStudy().getUserid()), week);
+    public R<TUserStudy> studySchedule(@RequestParam Integer week) {
+        LoginUserParent loginStudy = tokenService.getLoginUserStudy();
+        if (null == loginStudy) {
+            return R.tokenError("登录失效!");
+        }
+        TUserStudy result = studyService.studySchedule(String.valueOf(loginStudy.getUserid()), week);
+        if (null != result) {
+            // 计算当前周 day 1-5的总进度
+            int computeSchedule = studyService.computeSchedule(result, week);
+            result.setComputeSchedule(computeSchedule);
+        }
         return R.ok(result);
     }
 
@@ -715,12 +732,39 @@
     @ApiOperation(value = "获取题组学习进度信息", tags = {"学习端-题目"})
     @ApiImplicitParams({
             @ApiImplicitParam(value = "周目", name = "week", dataType = "Integer", required = true),
-            @ApiImplicitParam(value = "所属day", name = "day", dataType = "Integer", required = true)
+            @ApiImplicitParam(value = "所属day", name = "day", dataType = "Integer", required = true),
+            @ApiImplicitParam(value = "类型(1:听音选图,2:看图选音,3:归纳排除,4:有问有答,5:音图相配)", name = "type", dataType = "Integer", required = true)
     })
-    public R<TSubjectRecord> teamSchedule(@RequestParam Integer week, @RequestParam Integer day) {
-        TSubjectRecord subjectRecord = subjectRecordService.lambdaQuery().eq(TSubjectRecord::getWeek, week).eq(TSubjectRecord::getDay, day)
-                .eq(TSubjectRecord::getUserId, tokenService.getLoginUserStudy().getUserid()).eq(TSubjectRecord::getDisabled, 0).one();
-        return R.ok(subjectRecord);
+    public R<SubjectRecordResultVO> teamSchedule(@RequestParam Integer week, @RequestParam Integer day,
+                                                 @RequestParam Integer type) {
+        LoginUserParent loginStudy = tokenService.getLoginUserStudy();
+        if (null == loginStudy) {
+            return R.tokenError("登录失效!");
+        }
+        TSubjectRecord subjectRecord = subjectRecordService.lambdaQuery().eq(TSubjectRecord::getWeek, week)
+                .eq(TSubjectRecord::getDay, day)
+                .eq(TSubjectRecord::getType, type)
+                .eq(TSubjectRecord::getUserId, loginStudy.getUserid())
+                .eq(TSubjectRecord::getDisabled, 0).one();
+        // 返回结果
+        SubjectRecordResultVO result;
+        SubjectRecordResultVO data = subjectRecordService.recordResult(subjectRecord, loginStudy.getUserid());
+        if (null != subjectRecord) {
+            subjectRecordService.lambdaUpdate().set(TSubjectRecord::getDisabled, 1)
+                    .eq(TSubjectRecord::getId, subjectRecord.getId()).update();
+            // 题组id
+            List<Integer> teamIds = Arrays.stream(subjectRecord.getBeforeSubject().split(",")).map(Integer::parseInt)
+                    .collect(Collectors.toList());
+            // 题目id
+            List<Integer> topicIds = Arrays.stream(subjectRecord.getCompleteSubject().split(",")).map(Integer::parseInt)
+                    .collect(Collectors.toList());
+            result = new SubjectRecordResultVO(teamIds, topicIds, subjectRecord.getAnswerNumber(), subjectRecord.getCorrectNumber());
+        } else {
+            result = new SubjectRecordResultVO();
+        }
+        subjectRecordService.lambdaUpdate().set(TSubjectRecord::getDisabled, 0)
+                .eq(TSubjectRecord::getUserId, loginStudy.getUserid()).update();
+        return R.ok(result);
     }
 
     /**
@@ -728,9 +772,43 @@
      */
     @PostMapping("/exitLearning")
     @ApiOperation(value = "退出学习(记录学习进度等信息)", tags = {"学习端-题目"})
-    public R<Boolean> exitLearning(@RequestBody TSubjectRecord subjectRecord) {
-        // 学习时长处理
-        return R.ok(subjectRecordService.updateById(subjectRecord));
+    public R<Boolean> exitLearning(@RequestBody ExitLearnVO exitLearn) {
+        LoginUserParent loginStudy = tokenService.getLoginUserStudy();
+        if (null == loginStudy) {
+            return R.tokenError("登录失效!");
+        }
+        Integer userid = loginStudy.getUserid();
+        // 判断当前week和day是否已完成学习
+        TUserStudy userStudy = userStudyService.lambdaQuery().eq(TUserStudy::getUserId, userid)
+                .eq(TUserStudy::getDisabled, 0).one();
+        if (null == userStudy) {
+            throw new GlobalException("登录用户学习记录不存在!");
+        }
+        if (userStudy.getWeek().equals(exitLearn.getWeek()) && userStudy.getDay().equals(exitLearn.getDay())) {
+            // 计算完成率
+            int completionRate = exitLearn.getTopicIds().split(",").length * 5;
+            Integer type = exitLearn.getType();
+            // 更新用户学习完成率
+            LambdaUpdateChainWrapper<TUserStudy> wrapper = userStudyService.lambdaUpdate();
+            if (Constants.ONE.equals(type) && userStudy.getListen() < completionRate) {
+                // 听音选图
+                wrapper.set(TUserStudy::getListen, completionRate);
+            } else if (Constants.TWO.equals(type) && userStudy.getLook() < completionRate) {
+                // 看图选音
+                wrapper.set(TUserStudy::getLook, completionRate);
+            } else if (Constants.THREE.equals(type) && userStudy.getInduction() < completionRate) {
+                // 归纳排除
+                wrapper.set(TUserStudy::getInduction, completionRate);
+            } else if (Constants.FOUR.equals(type) && userStudy.getAnswer() < completionRate) {
+                // 有问有答
+                wrapper.set(TUserStudy::getAnswer, completionRate);
+            } else if (Constants.FIVE.equals(type) && userStudy.getPair() < completionRate) {
+                // 音图相配
+                wrapper.set(TUserStudy::getPair, completionRate);
+            }
+            wrapper.eq(TUserStudy::getUserId, userid).update();
+        }
+        return R.ok(subjectRecordService.exitLearning(exitLearn, userid));
     }
 
     /**
@@ -746,7 +824,8 @@
             @ApiImplicitParam(value = "周目", name = "week", dataType = "Integer", required = true),
             @ApiImplicitParam(value = "所属day", name = "day", dataType = "Integer", required = true)
     })
-    public R<StudyListenResultVO> listenSelectPicture(@RequestParam Integer quarter, @RequestParam Integer week, @RequestParam Integer day) {
+    public R<StudyListenResultVO> listenSelectPicture(@RequestParam Integer quarter, @RequestParam Integer week,
+                                                      @RequestParam Integer day) {
         // 判断当前登录用户是否为 会员
         Boolean isVip = userService.isVip();
         // 非会员只能查看非会员题目,会员可以查看所有题目
@@ -776,7 +855,8 @@
             @ApiImplicitParam(value = "周目", name = "week", dataType = "Integer", required = true),
             @ApiImplicitParam(value = "所属day", name = "day", dataType = "Integer", required = true)
     })
-    public R<StudyLookResultVO> pictureSelectVoice(@RequestParam Integer quarter, @RequestParam Integer week, @RequestParam Integer day) {
+    public R<StudyLookResultVO> pictureSelectVoice(@RequestParam Integer quarter, @RequestParam Integer week,
+                                                   @RequestParam Integer day) {
         // 判断当前登录用户是否为 会员
         Boolean isVip = userService.isVip();
         // 非会员只能查看非会员题目,会员可以查看所有题目
@@ -806,7 +886,8 @@
             @ApiImplicitParam(value = "周目", name = "week", dataType = "Integer", required = true),
             @ApiImplicitParam(value = "所属day", name = "day", dataType = "Integer", required = true)
     })
-    public R<StudyInductionResultVO> induceExclude(@RequestParam Integer quarter, @RequestParam Integer week, @RequestParam Integer day) {
+    public R<StudyInductionResultVO> induceExclude(@RequestParam Integer quarter, @RequestParam Integer week,
+                                                   @RequestParam Integer day) {
         // 判断当前登录用户是否为 会员
         Boolean isVip = userService.isVip();
         // 非会员只能查看非会员题目,会员可以查看所有题目
@@ -836,7 +917,8 @@
             @ApiImplicitParam(value = "周目", name = "week", dataType = "Integer", required = true),
             @ApiImplicitParam(value = "所属day", name = "day", dataType = "Integer", required = true)
     })
-    public R<StudyAnswerResultVO> questionsAndAnswers(@RequestParam Integer quarter, @RequestParam Integer week, @RequestParam Integer day) {
+    public R<StudyAnswerResultVO> questionsAndAnswers(@RequestParam Integer quarter, @RequestParam Integer week,
+                                                      @RequestParam Integer day) {
         // 判断当前登录用户是否为 会员
         Boolean isVip = userService.isVip();
         // 非会员只能查看非会员题目,会员可以查看所有题目
@@ -866,7 +948,8 @@
             @ApiImplicitParam(value = "周目", name = "week", dataType = "Integer", required = true),
             @ApiImplicitParam(value = "所属day", name = "day", dataType = "Integer", required = true)
     })
-    public R<StudyPairResultVO> pictureMateVoice(@RequestParam Integer quarter, @RequestParam Integer week, @RequestParam Integer day) {
+    public R<StudyPairResultVO> pictureMateVoice(@RequestParam Integer quarter, @RequestParam Integer week,
+                                                 @RequestParam Integer day) {
         // 判断当前登录用户是否为 会员
         Boolean isVip = userService.isVip();
         // 非会员只能查看非会员题目,会员可以查看所有题目
@@ -891,50 +974,59 @@
     @PostMapping("/completeLearning")
     @ApiOperation(value = "完成学习", tags = {"学习端-听-自主学习"})
     public R<Boolean> completeLearning(@RequestBody CompleteStudyDTO completeStudy) {
+        LoginUserParent userStudy = tokenService.getLoginUserStudy();
+        if (null == userStudy) {
+            return R.tokenError("登录失效!");
+        }
         // 登录用户id
-        Integer userId = tokenService.getLoginUserStudy().getUserid();
+        Integer userId = userStudy.getUserid();
         // 判断是否已完成该题组
         boolean update = true;
-        if (completeStudy.getIsComplete()) {
-            List<Integer> studyIds = completeStudy.getStudyIds();
-            Integer type = completeStudy.getType();
-            int sum;
-            if (Constants.ONE.equals(type)) {
-                List<TStudyListen> studyListens = studyListenService.lambdaQuery().in(TStudyListen::getId, studyIds)
-                        .eq(TStudyListen::getDisabled, 0).list();
-                sum = studyListens.stream().mapToInt(TStudyListen::getIntegral).sum();
-            } else if (Constants.TWO.equals(type)) {
-                List<TStudyLook> studyListens = studyLookService.lambdaQuery().in(TStudyLook::getId, studyIds)
-                        .eq(TStudyLook::getDisabled, 0).list();
-                sum = studyListens.stream().mapToInt(TStudyLook::getIntegral).sum();
-            } else if (Constants.THREE.equals(type)) {
-                List<TStudyInduction> studyListens = studyInductionService.lambdaQuery().in(TStudyInduction::getId, studyIds)
-                        .eq(TStudyInduction::getDisabled, 0).list();
-                sum = studyListens.stream().mapToInt(TStudyInduction::getIntegral).sum();
-            } else if (Constants.FOUR.equals(type)) {
-                List<TStudyAnswer> studyListens = studyAnswerService.lambdaQuery().in(TStudyAnswer::getId, studyIds)
-                        .eq(TStudyAnswer::getDisabled, 0).list();
-                sum = studyListens.stream().mapToInt(TStudyAnswer::getIntegral).sum();
-            } else if (Constants.FIVE.equals(type)) {
-                List<TStudyPair> studyListens = studyPairService.lambdaQuery().in(TStudyPair::getId, studyIds)
-                        .eq(TStudyPair::getDisabled, 0).list();
-                sum = studyListens.stream().mapToInt(TStudyPair::getIntegral).sum();
-            } else {
-                return R.fail("题目信息异常!");
-            }
+        List<String> studyIds = Arrays.stream(completeStudy.getStudyIds().split(","))
+                .collect(Collectors.toList());
+        Integer type = completeStudy.getType();
+        // 可获取的总积分数量以及获取用户该学习已获取的积分数量,并计算本次可获取的剩余积分数量
+        int sum = studyService.computeTotalIntegral(studyIds, type, completeStudy.getAccuracy());
+        // 用户已获取的积分数量
+        int obtainedIntegral;
+        List<TUserStudyRecord> list = studyRecordService.lambdaQuery()
+                .eq(TUserStudyRecord::getQuarter, completeStudy.getQuarter())
+                .eq(TUserStudyRecord::getWeek, completeStudy.getWeek())
+                .eq(TUserStudyRecord::getDay, completeStudy.getDay())
+                .eq(TUserStudyRecord::getType, 0)
+                .eq(TUserStudyRecord::getUserId, userId).list();
+        if (list.isEmpty()) {
+            obtainedIntegral = 0;
+        } else {
+            obtainedIntegral = list.stream().map(TUserStudyRecord::getObtainedIntegral)
+                    .mapToInt(Integer::intValue).sum();
+        }
+        // 计算本次可获取积分数量
+        if (sum > obtainedIntegral) {
+            int integral = sum - obtainedIntegral;
             // 获取user详细信息,改变积分
             TUser user = userService.getById(userId);
-            user.setIntegral(user.getIntegral() + sum);
-            update = userService.updateById(user);
+            int i = user.getIntegral() + integral;
+            update = userService.lambdaUpdate().eq(TUser::getId, userId).set(TUser::getIntegral, i).update();
             // 生成积分明细记录
             TIntegralRecord integralRecord = new TIntegralRecord();
-            integralRecord.setIntegral(String.valueOf(sum));
+            integralRecord.setIntegral(String.valueOf(integral));
             integralRecord.setMethod(Constants.COMPLETE_LEARNING);
             integralRecord.setUserId(userId);
             update = update && integralRecordService.save(integralRecord);
+            // 生成学习完成记录
+            TUserStudyRecord record = new TUserStudyRecord();
+            record.setUserId(userId);
+            record.setQuarter(completeStudy.getQuarter());
+            record.setWeek(completeStudy.getWeek());
+            record.setDay(completeStudy.getDay());
+            record.setObtainedIntegral(integral);
+            record.setType(Constants.ZERO);
+            update = update && studyRecordService.save(record);
         }
         // 学习配置列表
-        List<TStudy> studyList = studyService.lambdaQuery().eq(TStudy::getDisabled, 0).orderByAsc(TStudy::getWeek).list();
+        List<TStudy> studyList = studyService.lambdaQuery().eq(TStudy::getDisabled, 0)
+                .orderByAsc(TStudy::getWeek).list();
         if (studyList.isEmpty()) {
             throw new GlobalException("学习配置列表未配置或数据失效!");
         }
@@ -956,7 +1048,12 @@
             @ApiImplicitParam(value = "难度(0入门、1中级、2困难)", name = "difficulty", dataType = "Integer", required = true),
             @ApiImplicitParam(value = "所属周目", name = "week", dataType = "Integer", required = true)
     })
-    public R<StudyGamerResultVO> gameHearing(@RequestParam Integer quarter, @RequestParam Integer difficulty, @RequestParam Integer week) {
+    public R<StudyGameResultVO> gameHearing(@RequestParam Integer quarter, @RequestParam Integer difficulty,
+                                            @RequestParam Integer week) {
+        Integer[] array = {0, 1, 2};
+        if (!Arrays.stream(array).collect(Collectors.toList()).contains(difficulty)) {
+            throw new GlobalException("请选择符合规则的游戏难度!");
+        }
         TGame game = gameService.gameHearing(quarter, week);
         if (null == game) {
             throw new GlobalException("当前季度该周目暂无配置游戏数据!");
@@ -977,21 +1074,9 @@
             throw new GlobalException("当前周目下day1 - day5题目不足!");
         }
         // 根据游戏设置数量获取图片及语音
-        List<String> subjectData = new ArrayList<>();
-        Random random = new Random();
-        // 获取列表大小
-        int dataSize = newSubjectId.size();
-        // 生成随机索引并获取数据
-        for (int i = 0; i < game.getCount(); i++) {
-            // 生成随机索引
-            int randomIndex = random.nextInt(dataSize);
-            // 获取对应的数据并加入结果列表
-            subjectData.add(newSubjectId.get(randomIndex));
-            newSubjectId.remove(randomIndex);
-            dataSize = newSubjectId.size();
-        }
+        List<String> subjectData = getData(game, newSubjectId);
         List<TSubject> subjectList = getSubjectList(subjectData);
-        return R.ok(new StudyGamerResultVO(game, subjectList));
+        return R.ok(new StudyGameResultVO(game, subjectList));
     }
 
     /**
@@ -1006,12 +1091,27 @@
             @ApiImplicitParam(value = "季度", name = "quarter", dataType = "Integer", required = true),
             @ApiImplicitParam(value = "所属周目", name = "week", dataType = "Integer", required = true)
     })
-    public R<StudyGamerResultVO> gameMemory(@RequestParam Integer quarter, @RequestParam Integer week) {
+    public R<StudyGameMemoryVO> gameMemory(@RequestParam Integer quarter, @RequestParam Integer week) {
         TGame game = gameService.gameHearing(quarter, week);
         if (null == game) {
             throw new GlobalException("当前季度该周目暂无配置游戏数据!");
         }
         List<String> subjectId = getSubjectId(week);
+        List<String> subjectData = getSubjectData(game, subjectId);
+        List<TSubject> subjectList = getSubjectList(subjectData);
+        // 返回数据
+        List<GameMemoryPhotoVO> photoList = new ArrayList<>();
+        List<GameMemoryVoiceVO> voiceList = new ArrayList<>();
+        for (TSubject tSubject : subjectList) {
+            photoList.add(new GameMemoryPhotoVO(tSubject.getId(), tSubject.getImg()));
+            voiceList.add(new GameMemoryVoiceVO(tSubject.getId(), tSubject.getCorrect()));
+        }
+        // 框架记忆数量翻倍,前端需要根据数量画格子
+        game.setAnswerCount(game.getAnswerCount() * 2);
+        return R.ok(new StudyGameMemoryVO(game, photoList, voiceList));
+    }
+
+    private List<String> getSubjectData(TGame game, List<String> subjectId) {
         List<String> newSubjectId = subjectId.stream().map(data -> {
             if (data.startsWith(Constants.REDUCE)) {
                 data = data.replace(Constants.REDUCE, Constants.EMPTY_STR);
@@ -1023,6 +1123,10 @@
             throw new GlobalException("当前周目下day1 - day5题目不足!");
         }
         // 根据游戏设置数量获取图片及语音
+        return getData(game, newSubjectId);
+    }
+
+    private List<String> getData(TGame game, List<String> newSubjectId) {
         List<String> subjectData = new ArrayList<>();
         Random random = new Random();
         // 获取列表大小
@@ -1036,15 +1140,7 @@
             newSubjectId.remove(randomIndex);
             dataSize = newSubjectId.size();
         }
-        List<TSubject> subjectList = getSubjectList(subjectData);
-        // 格子翻倍,前端需要做连连看
-        List<TSubject> resultList = new ArrayList<>();
-        for (int i = 0; i < Constants.TWO; i++) {
-            resultList.addAll(subjectList);
-        }
-        // 框架记忆数量翻倍,前端需要根据数量画格子
-        game.setAnswerCount(game.getAnswerCount() * 2);
-        return R.ok(new StudyGamerResultVO(game, resultList));
+        return subjectData;
     }
 
     private List<TSubject> getSubjectList(List<String> subjectData) {
@@ -1069,12 +1165,16 @@
     @PostMapping("/gameAchievement")
     @ApiOperation(value = "完成游戏-记录游戏测试成绩", tags = {"学习端-听-自主游戏"})
     public R<Boolean> gameAchievement(@RequestBody CompleteGameDTO completeStudy) {
+        LoginUserParent userStudy = tokenService.getLoginUserStudy();
+        if (null == userStudy) {
+            return R.tokenError("登录失效!");
+        }
         /*
          * 游戏测试需要根据正确率计算本次测试可获得积分
          * 并且需要判断如果该游戏用户已获取一部分积分,再次测试后正确率增长,只能获取高于上次正确率的部分积分
          * 例如:游戏配置的积分是100,他的正确率是50%那么拿50分,下次他再玩这个游戏 正确率是60% 那么他该获得60分 但是上次已经拿了50 所以这次就只给他加10积分
          */
-        Integer userid = tokenService.getLoginUserStudy().getUserid();
+        Integer userid = userStudy.getUserid();
         TGame game = gameService.lambdaQuery().eq(TGame::getId, completeStudy.getGameId()).eq(TGame::getDisabled, 0).one();
         if (null == game) {
             throw new GlobalException("游戏信息异常!");
@@ -1092,7 +1192,7 @@
         } else {
             throw new GlobalException("该次游戏积分计算异常!");
         }
-        int gameAvailableIntegral = integral * (completeStudy.getAccuracy() / 100);
+        int gameAvailableIntegral = (int) (integral * ((double) completeStudy.getAccuracy() / 100));
         Integer availableIntegral = gameService.countIntegral(userid, game, completeStudy, gameAvailableIntegral, integralRecordList);
         // 游戏测试记录
         Boolean add = gameRecordService.add(completeStudy);
@@ -1150,15 +1250,14 @@
     })
     public R<StudyStoryListenResultVO> lookPictureDbu(@RequestParam Integer quarter, @RequestParam Integer week) {
         // 看图配音信息
-        TStoryListen listen = gettStoryListen(quarter, week);
-        List<String> list = Arrays.asList(listen.getLookStory().split(","));
-        List<TStory> subjectList;
-        if (!list.isEmpty()) {
-            subjectList = storyService.lambdaQuery().in(TStory::getId, list).eq(TStory::getDisabled, 0).list();
-        } else {
-            subjectList = new ArrayList<>();
-        }
-        return R.ok(new StudyStoryListenResultVO(listen, subjectList));
+        TStoryListen storyListen = storyListenService.storyDetail(quarter, week);
+        // 题组信息
+        StudyStoryVO studyStory = new StudyStoryVO();
+        studyStory.setId(storyListen.getId());
+        studyStory.setIntegral(storyListen.getLookIntegral());
+        // 故事语音及图片信息
+        List<TStory> list = storyService.lookPictureDbu(storyListen, 0);
+        return R.ok(new StudyStoryListenResultVO(studyStory, list));
     }
 
     /**
@@ -1173,34 +1272,15 @@
             @ApiImplicitParam(value = "所属周目", name = "week", dataType = "Integer", required = true)
     })
     public R<StudyStoryListenResultVO> frameworkMemory(@RequestParam Integer quarter, @RequestParam Integer week) {
-        TStoryListen listen = gettStoryListen(quarter, week);
-        // 获取对应图片语音
-        List<String> list = Arrays.asList(listen.getStory().split(","));
-        List<TStory> subjectList;
-        if (!list.isEmpty()) {
-            subjectList = storyService.lambdaQuery().in(TStory::getId, list).eq(TStory::getDisabled, 0).list();
-        } else {
-            subjectList = new ArrayList<>();
-        }
-        return R.ok(new StudyStoryListenResultVO(listen, subjectList));
-    }
-
-    private TStoryListen gettStoryListen(Integer quarter, Integer week) {
         // 看图配音信息
-        List<TStoryListen> storyListenList = storyListenService.storyDetail(quarter, week);
-        if (storyListenList.isEmpty()) {
-            throw new GlobalException("当前季度该周目下未配置故事信息!");
-        }
-        // 获取对应图片语音
-        TStoryListen listen;
-        if (storyListenList.size() == Constants.ONE) {
-            listen = storyListenList.get(Constants.ZERO);
-        } else {
-            // 随机获取一组题
-            Random rand = new Random();
-            listen = storyListenList.get(rand.nextInt(storyListenList.size()));
-        }
-        return listen;
+        TStoryListen storyListen = storyListenService.storyDetail(quarter, week);
+        // 题组信息
+        StudyStoryVO studyStory = new StudyStoryVO();
+        studyStory.setId(storyListen.getId());
+        studyStory.setIntegral(storyListen.getIntegral());
+        // 故事语音及图片信息
+        List<TStory> list = storyService.lookPictureDbu(storyListen, 1);
+        return R.ok(new StudyStoryListenResultVO(studyStory, list));
     }
 
     /**
@@ -1209,27 +1289,63 @@
     @GetMapping("/completeStory")
     @ApiOperation(value = "完成故事学习", tags = {"学习端-听-自主故事"})
     @ApiImplicitParams({
-            @ApiImplicitParam(value = "积分数量", name = "integral", dataType = "Integer", required = true),
-            @ApiImplicitParam(value = "故事id", name = "storyId", dataType = "Integer", required = true)
+            @ApiImplicitParam(value = "故事id", name = "storyId", dataType = "Integer", required = true),
+            @ApiImplicitParam(value = "类型(1:看图配音;2:超级记忆)", name = "type", dataType = "Integer", required = true),
+            @ApiImplicitParam(value = "正确率", name = "accuracy", dataType = "Integer")
     })
-    public R<Boolean> completeStory(@RequestParam Integer integral, @RequestParam Integer storyId) {
-        TStoryListen storyListen = storyListenService.lambdaQuery().eq(TStoryListen::getId, storyId).eq(TStoryListen::getDisabled, 0).one();
+    public R<Boolean> completeStory(@RequestParam Integer storyId, @RequestParam Integer type, Integer accuracy) {
+        TStoryListen storyListen = storyListenService.lambdaQuery().eq(TStoryListen::getId, storyId)
+                .eq(TStoryListen::getDisabled, 0).one();
         if (null == storyListen) {
             throw new GlobalException("当前故事学习失败,故事信息异常,请重试!");
         }
+        LoginUserParent userStudy = tokenService.getLoginUserStudy();
+        if (null == userStudy) {
+            return R.tokenError("登录失效!");
+        }
         // 用户信息
-        Integer userId = tokenService.getLoginUserStudy().getUserid();
-        // 故事只有首次才能获取积分
-        TIntegralRecord integralRecord = integralRecordService.lambdaQuery().eq(TIntegralRecord::getUserId, userId)
-                .eq(TIntegralRecord::getStoryId, storyId).eq(TIntegralRecord::getDisabled, 0).one();
+        Integer userId = userStudy.getUserid();
         Boolean result = true;
-        if (null == integralRecord) {
-            // 添加积分明细记录
-            result = integralRecordService.add(String.valueOf(integral), Constants.COMPLETE_STORY, null, storyId);
-            TUser user = userService.lambdaQuery().eq(TUser::getId, userId).one();
-            // 添加积分
-            user.setIntegral(user.getIntegral() + integral);
-            result = result && userService.updateById(user);
+        if (Constants.ONE.equals(type)) {
+            if (null == accuracy) {
+                throw new GlobalException("自主故事-看图配音正确率异常!");
+            }
+            // 看图配音模式,也需要根据游戏正确率计算积分
+            int integral = storyListen.getLookIntegral() * (accuracy / 100);
+            int obtainedIntegral;
+            List<TUserStudyRecord> list = studyRecordService.lambdaQuery()
+                    .eq(TUserStudyRecord::getStoryId, storyId)
+                    .eq(TUserStudyRecord::getType, 1)
+                    .eq(TUserStudyRecord::getUserId, userId).list();
+            if (list.isEmpty()) {
+                obtainedIntegral = 0;
+            } else {
+                obtainedIntegral = list.stream().map(TUserStudyRecord::getObtainedIntegral).mapToInt(Integer::intValue).sum();
+            }
+            // 可获得积分计算
+            if (integral > obtainedIntegral) {
+                TUserStudyRecord data = new TUserStudyRecord();
+                data.setUserId(userId);
+                data.setObtainedIntegral(integral - obtainedIntegral);
+                data.setType(Constants.ONE);
+                data.setStoryId(storyId);
+                result = studyRecordService.save(data);
+            }
+        } else {
+            // 超级记忆只有首次才能获取积分
+            TIntegralRecord integralRecord = integralRecordService.lambdaQuery()
+                    .eq(TIntegralRecord::getUserId, userId)
+                    .eq(TIntegralRecord::getStoryId, storyId)
+                    .eq(TIntegralRecord::getDisabled, 0).one();
+            if (null == integralRecord) {
+                // 添加积分明细记录
+                result = integralRecordService.add(String.valueOf(storyListen.getIntegral()),
+                        Constants.COMPLETE_STORY, null, storyId);
+                TUser user = userService.lambdaQuery().eq(TUser::getId, userId).one();
+                // 添加积分
+                user.setIntegral(user.getIntegral() + storyListen.getIntegral());
+                result = result && userService.updateById(user);
+            }
         }
         return R.ok(result);
     }
@@ -1237,8 +1353,11 @@
     @GetMapping("/studyRecord")
     @ApiOperation(value = "个人中心-学习记录", tags = {"学习端-个人中心"})
     public R<StudyRecordResultVO> studyRecord() {
-        Integer userId = tokenService.getLoginUserStudy().getUserid();
-
+        LoginUserParent userStudy = tokenService.getLoginUserStudy();
+        if (null == userStudy) {
+            return R.tokenError("登录失效!");
+        }
+        Integer userId = userStudy.getUserid();
         // 学习记录
         TUserStudy studyRecord = userStudyService.lambdaQuery().eq(TUserStudy::getUserId, userId)
                 .eq(TUserStudy::getDisabled, 0).one();
diff --git a/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/controller/TUserController.java b/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/controller/TUserController.java
index 52685cf..5017009 100644
--- a/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/controller/TUserController.java
+++ b/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/controller/TUserController.java
@@ -3,6 +3,7 @@
 
 import com.alipay.api.AlipayApiException;
 import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
+import com.ruoyi.common.core.constant.Constants;
 import com.ruoyi.common.core.constant.RedisConstants;
 import com.ruoyi.common.core.domain.R;
 import com.ruoyi.common.core.exception.GlobalException;
@@ -424,6 +425,7 @@
         }
         return R.ok(data);
     }
+
     @PostMapping("/useGuideGetInfo")
     @ApiOperation(value = "查看详情", tags = {"家长端-使用指南"})
     public R useGuideGetInfo(Integer id) {
@@ -432,7 +434,7 @@
         useGuideQuery.setPageSize(300);
         PageInfo<TUseGuide> data = managementClient.useGuide1(useGuideQuery).getData();
         for (TUseGuide record : data.getRecords()) {
-            if (record.getId() == id){
+            if (record.getId() == id) {
                 return R.ok(record.getAnswer());
             }
         }
@@ -508,6 +510,19 @@
     public R<Map<String, Object>> studyLogin(@RequestBody RegisterPhoneRequest phoneRequest) {
         String phone = phoneRequest.getPhone();
         String phoneCode = phoneRequest.getPhoneCode();
+        // 验证码校验
+        Object redisPhoneCode = redisService.getCacheObject(RedisConstants.PHONE_CODE + phone);
+        if (null == redisPhoneCode) {
+            return R.errorCode("登录失败,验证码无效!");
+        } else {
+            // redis 验证码的value 为 code:时间戳
+            String rCodeAndTime = String.valueOf(redisPhoneCode);
+            String rCode = rCodeAndTime.split(":")[0];
+            if (!rCode.equalsIgnoreCase(phoneCode)) {
+                return R.errorCode("登录失败,验证码无效!");
+            }
+        }
+        // 获取手机号所注册用户信息
         TUser user = userService.getOne(new QueryWrapper<TUser>()
                 .ne("state", 3)
                 .eq("phone", phone));
@@ -516,26 +531,8 @@
                 return R.freeze("登录失败,您的账号已被冻结!");
             }
         } else {
-            if (!phoneCode.equals("123456")) {
-                // 手机验证码校验
-                Object redisPhoneCode = redisService.getCacheObject(RedisConstants.PHONE_CODE + phone);
-                if (null == redisPhoneCode) {
-                    return R.errorCode("登录失败,验证码无效!");
-                } else {
-                    // redis 验证码的value 为 code:时间戳
-                    String rCodeAndTime = String.valueOf(redisPhoneCode);
-                    String rCode = rCodeAndTime.split(":")[0];
-                    if (!rCode.equalsIgnoreCase(phoneCode)) {
-                        return R.errorCode("登录失败,验证码无效!");
-                    } else {
-                        user = getUser(phone);
-                        userService.save(user);
-                    }
-                }
-            } else {
-                user = getUser(phone);
-                userService.save(user);
-            }
+            user = getUser(phone);
+            userService.save(user);
         }
         // 生成登录用户信息
         LoginUserParent loginUserParent = new LoginUserParent();
@@ -544,8 +541,27 @@
         loginUserParent.setPhone(user.getPhone());
         loginUserParent.setLoginTime(System.currentTimeMillis());
         HashMap<String, Object> map = new HashMap<>();
-        map.put("token", tokenService.createTokenStudy(loginUserParent));
         // 获取登录token
+        map.put("token", tokenService.createTokenStudy(loginUserParent));
+        // 学习进度检查
+        TUserStudy userStudy = userStudyService.lambdaQuery().eq(TUserStudy::getUserId, user.getId())
+                .eq(TUserStudy::getDisabled, 0).one();
+        if (null == userStudy) {
+            TUserStudy study = new TUserStudy();
+            study.setUserId(user.getId());
+            study.setWeek(Constants.ONE);
+            study.setDay(Constants.ONE);
+            study.setTotalStudy(Constants.ZERO);
+            study.setTodayStudy(Constants.ZERO);
+            study.setWeekStudy(Constants.ZERO);
+            study.setMonthStudy(Constants.ZERO);
+            study.setListen(Constants.BURDEN_ONE);
+            study.setLook(Constants.BURDEN_ONE);
+            study.setInduction(Constants.BURDEN_ONE);
+            study.setAnswer(Constants.BURDEN_ONE);
+            study.setPair(Constants.BURDEN_ONE);
+            userStudyService.save(study);
+        }
         return R.ok(map);
     }
 
@@ -736,7 +752,7 @@
             byId.setPhone(phone);
         }
         // 手机验证码校验
-        if (StringUtils.hasLength(phoneCode)){
+        if (StringUtils.hasLength(phoneCode)) {
             if (!phoneCode.equals("123456")) {
                 Object redisPhoneCode = redisService.getCacheObject(RedisConstants.PHONE_CODE + phone);
                 if (null == redisPhoneCode) {
diff --git a/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/domain/TStudyListen.java b/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/domain/TStudyListen.java
index 3dd9f4a..c5bbcd2 100644
--- a/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/domain/TStudyListen.java
+++ b/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/domain/TStudyListen.java
@@ -57,4 +57,5 @@
      */
     @ApiModelProperty("非会员是否查看 0否1是")
     private Integer isVip;
+
 }
diff --git a/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/domain/TSubjectRecord.java b/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/domain/TSubjectRecord.java
index 75a9d06..b25b255 100644
--- a/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/domain/TSubjectRecord.java
+++ b/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/domain/TSubjectRecord.java
@@ -1,6 +1,7 @@
 package com.ruoyi.study.domain;
 
 import com.baomidou.mybatisplus.annotation.IdType;
+import com.baomidou.mybatisplus.annotation.TableField;
 import com.baomidou.mybatisplus.annotation.TableId;
 import com.baomidou.mybatisplus.annotation.TableName;
 import com.ruoyi.common.core.web.domain.BaseModel;
@@ -45,12 +46,12 @@
     /**
      * 上次回答到的题组id
      */
-    @ApiModelProperty(value = "上次回答到的题组id")
-    private Integer beforeSubject;
+    @ApiModelProperty(value = "上次回答到的题组id(, 拼接)")
+    private String beforeSubject;
     /**
      * 类型1听音选图2看图选音3归纳排除4有问有答5音图相配
      */
-    @ApiModelProperty(value = "类型1听音选图2看图选音3归纳排除4有问有答5音图相配")
+    @ApiModelProperty(value = "类型1:听音选图,2:看图选音,3:归纳排除,4:有问有答,5:音图相配")
     private Integer type;
     /**
      * 已回答正确的题目id 多个逗号隔开
@@ -58,4 +59,18 @@
     @ApiModelProperty(value = "已回答正确的题目id 多个逗号隔开")
     private String completeSubject;
 
+    /**
+     * 答题次数
+     */
+    @ApiModelProperty(value = "答题次数")
+    @TableField("answerNumber")
+    private Integer answerNumber;
+
+    /**
+     * 答题正确次数
+     */
+    @ApiModelProperty(value = "答题正确次数")
+    @TableField("correctNumber")
+    private Integer correctNumber;
+
 }
diff --git a/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/domain/TUserStudy.java b/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/domain/TUserStudy.java
index 6ab9508..07e3a7b 100644
--- a/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/domain/TUserStudy.java
+++ b/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/domain/TUserStudy.java
@@ -70,29 +70,36 @@
     @ApiModelProperty(value = "本月学习时长")
     private Integer monthStudy;
     /**
-     * 故事名称
+     * 听音选图
      */
     @ApiModelProperty(value = "听音选图学习进度(100为已完成)")
     private Integer listen;
     /**
-     * 故事名称
+     * 看图选音
      */
     @ApiModelProperty(value = "看图选音学习进度(100为已完成)")
     private Integer look;
     /**
-     * 故事名称
+     * 归纳排除
      */
     @ApiModelProperty(value = "归纳排除学习进度(100为已完成)")
     private Integer induction;
     /**
-     * 故事名称
+     * 有问有答
      */
     @ApiModelProperty(value = "有问有答学习进度(100为已完成)")
     private Integer answer;
     /**
-     * 故事名称
+     * 音图相配
      */
     @ApiModelProperty(value = "音图相配学习进度(100为已完成)")
     private Integer pair;
 
+    /**
+     * 当前week学习进度
+     */
+    @ApiModelProperty(value = "当前week学习进度")
+    @TableField(exist = false)
+    private Integer computeSchedule;
+
 }
diff --git a/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/domain/TUserStudyRecord.java b/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/domain/TUserStudyRecord.java
new file mode 100644
index 0000000..ef7e136
--- /dev/null
+++ b/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/domain/TUserStudyRecord.java
@@ -0,0 +1,79 @@
+package com.ruoyi.study.domain;
+
+import com.baomidou.mybatisplus.annotation.IdType;
+import com.baomidou.mybatisplus.annotation.TableField;
+import com.baomidou.mybatisplus.annotation.TableId;
+import com.baomidou.mybatisplus.annotation.TableName;
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+
+/**
+ * <p>
+ * 学习类型 听 听音选图
+ * </p>
+ *
+ * @author 无关风月
+ * @since 2024-04-26
+ */
+@Data
+@TableName("t_user_study_record")
+public class TUserStudyRecord {
+
+    private static final long serialVersionUID = 1L;
+
+    /**
+     * 主键id
+     */
+    @TableId(value = "id", type = IdType.AUTO)
+    private Integer id;
+
+    /**
+     * 季度
+     */
+    @ApiModelProperty("季度")
+    @TableField("user_id")
+    private Integer userId;
+
+    /**
+     * 季度
+     */
+    @ApiModelProperty("季度")
+    @TableField("quarter")
+    private Integer quarter;
+
+    /**
+     * 周目x
+     */
+    @ApiModelProperty("周目")
+    @TableField("week")
+    private Integer week;
+
+    /**
+     * day
+     */
+    @ApiModelProperty("所属day")
+    @TableField("day")
+    private Integer day;
+
+    /**
+     * 题目
+     */
+    @ApiModelProperty("获取积分数量")
+    @TableField("obtained_integral")
+    private Integer obtainedIntegral;
+
+    /**
+     * 0:day 1-5学习;1:自主故事1
+     */
+    @ApiModelProperty("0:day 1-5学习;1:自主故事1")
+    @TableField("type")
+    private Integer type;
+
+    /**
+     * 自主故事id
+     */
+    @ApiModelProperty("自主故事id")
+    @TableField("story_id")
+    private Integer storyId;
+
+}
diff --git a/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/dto/CompleteStudyDTO.java b/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/dto/CompleteStudyDTO.java
index 5f17759..4a15810 100644
--- a/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/dto/CompleteStudyDTO.java
+++ b/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/dto/CompleteStudyDTO.java
@@ -4,7 +4,6 @@
 import lombok.Data;
 
 import javax.validation.constraints.NotNull;
-import java.util.List;
 
 /**
  * @author HJL
@@ -24,13 +23,7 @@
      * 题目id数组
      */
     @ApiModelProperty("题目id数组")
-    private List<Integer> studyIds;
-
-    /**
-     * 该学习是否完成
-     */
-    @ApiModelProperty("该学习是否完成(如果已完成再次进入学习并完成学习后,该字段传值 false)")
-    private Boolean isComplete;
+    private String studyIds;
 
     /**
      * 学习时长
@@ -39,4 +32,28 @@
     @NotNull(message = "本次学习时长不能为空!")
     private Integer studyTime;
 
+    /**
+     * 正确率
+     */
+    @ApiModelProperty("正确率")
+    private Integer accuracy;
+
+    /**
+     * 季度
+     */
+    @ApiModelProperty("季度")
+    private Integer quarter;
+
+    /**
+     * 周目
+     */
+    @ApiModelProperty("周目")
+    private Integer week;
+
+    /**
+     * 所属day
+     */
+    @ApiModelProperty("所属day")
+    private Integer day;
+
 }
diff --git a/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/dto/StudyWeekDTO.java b/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/dto/StudyWeekDTO.java
index 709291f..34c6d56 100644
--- a/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/dto/StudyWeekDTO.java
+++ b/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/dto/StudyWeekDTO.java
@@ -14,7 +14,7 @@
 public class StudyWeekDTO extends StudyDTO {
 
     @ApiModelProperty("完成后可获积分数")
-    private Long totalIntegral;
+    private Integer totalIntegral;
 
     @ApiModelProperty("所属季度")
     private Integer quarter;
@@ -25,4 +25,11 @@
     @ApiModelProperty("study表Id")
     private String id;
 
+    public StudyWeekDTO(Integer week, Integer type, Integer quarter, String title, Integer total) {
+        super.setWeek(week);
+        super.setType(type);
+        this.quarter = quarter;
+        this.title = title;
+        this.totalIntegral = total;
+    }
 }
diff --git a/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/mapper/TStoryListenMapper.java b/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/mapper/TStoryListenMapper.java
index 676f5f7..4eccc16 100644
--- a/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/mapper/TStoryListenMapper.java
+++ b/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/mapper/TStoryListenMapper.java
@@ -4,8 +4,6 @@
 import com.ruoyi.study.domain.TStoryListen;
 import org.apache.ibatis.annotations.Param;
 
-import java.util.List;
-
 /**
  * <p>
  * 听故事 Mapper 接口
@@ -23,5 +21,5 @@
      * @param week    周
      * @return 故事信息
      */
-    List<TStoryListen> storyDetail(@Param("quarter") Integer quarter, @Param("week") Integer week);
+    TStoryListen storyDetail(@Param("quarter") Integer quarter, @Param("week") Integer week);
 }
diff --git a/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/mapper/UserStudyRecordMapper.java b/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/mapper/UserStudyRecordMapper.java
new file mode 100644
index 0000000..357522f
--- /dev/null
+++ b/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/mapper/UserStudyRecordMapper.java
@@ -0,0 +1,16 @@
+package com.ruoyi.study.mapper;
+
+import com.baomidou.mybatisplus.core.mapper.BaseMapper;
+import com.ruoyi.study.domain.TUserStudyRecord;
+
+/**
+ * <p>
+ * 部门表 Mapper 接口
+ * </p>
+ *
+ * @author 无关风月
+ * @since 2024-04-26
+ */
+public interface UserStudyRecordMapper extends BaseMapper<TUserStudyRecord> {
+
+}
diff --git a/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/service/ITGameService.java b/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/service/ITGameService.java
index 5036416..1fe3702 100644
--- a/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/service/ITGameService.java
+++ b/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/service/ITGameService.java
@@ -38,4 +38,5 @@
      * @return 游戏信息
      */
     TGame gameHearing(Integer quarter, Integer week);
+
 }
diff --git a/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/service/ITStoryListenService.java b/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/service/ITStoryListenService.java
index f447847..c36a838 100644
--- a/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/service/ITStoryListenService.java
+++ b/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/service/ITStoryListenService.java
@@ -3,8 +3,6 @@
 import com.baomidou.mybatisplus.extension.service.IService;
 import com.ruoyi.study.domain.TStoryListen;
 
-import java.util.List;
-
 /**
  * <p>
  * 听故事 服务类
@@ -22,5 +20,5 @@
      * @param week    周
      * @return 故事信息
      */
-    List<TStoryListen> storyDetail(Integer quarter, Integer week);
+    TStoryListen storyDetail(Integer quarter, Integer week);
 }
diff --git a/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/service/ITStoryService.java b/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/service/ITStoryService.java
index 65fdebe..56fc3b2 100644
--- a/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/service/ITStoryService.java
+++ b/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/service/ITStoryService.java
@@ -2,6 +2,7 @@
 
 import com.baomidou.mybatisplus.extension.service.IService;
 import com.ruoyi.study.domain.TStory;
+import com.ruoyi.study.domain.TStoryListen;
 import com.ruoyi.study.dto.SubjectQuery;
 import com.ruoyi.study.vo.SubjectVO;
 
@@ -18,4 +19,13 @@
 public interface ITStoryService extends IService<TStory> {
 
     List<SubjectVO> listAll(SubjectQuery query);
+
+    /**
+     * 自主故事,获取图片及语音
+     *
+     * @param storyListen 听故事信息
+     * @param type 类型 0:看图配音;1:超级记忆
+     * @return 语音及图片列表
+     */
+    List<TStory> lookPictureDbu(TStoryListen storyListen,int type);
 }
diff --git a/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/service/ITStudyService.java b/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/service/ITStudyService.java
index ea1713a..d7ddbc8 100644
--- a/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/service/ITStudyService.java
+++ b/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/service/ITStudyService.java
@@ -67,8 +67,8 @@
     /**
      * 自主学习3-归纳排除
      *
-     * @param week 周目
-     * @param day  所属day
+     * @param week          周目
+     * @param day           所属day
      * @param inductionList 归纳排除
      * @return 题目信息
      */
@@ -77,8 +77,8 @@
     /**
      * 自主学习4-有问有答
      *
-     * @param week 周目
-     * @param day  所属day
+     * @param week       周目
+     * @param day        所属day
      * @param answerList 有问有答
      * @return 题目信息
      */
@@ -94,4 +94,22 @@
      */
     StudyPairResultVO pictureMateVoice(Integer week, Integer day, List<TStudyPair> pair);
 
+    /**
+     * 计算用户当前week的学习进度
+     *
+     * @param result 用户学习信息
+     * @param week   周目
+     * @return 当前week学习进度
+     */
+    int computeSchedule(TUserStudy result, Integer week);
+
+    /**
+     * 获取本次学习可获得总积分
+     *
+     * @param studyIds 题组id
+     * @param type     类型
+     * @param accuracy 正确率
+     * @return 积分
+     */
+    int computeTotalIntegral(List<String> studyIds, Integer type, Integer accuracy);
 }
diff --git a/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/service/ITSubjectRecordService.java b/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/service/ITSubjectRecordService.java
index 262464d..b5803ef 100644
--- a/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/service/ITSubjectRecordService.java
+++ b/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/service/ITSubjectRecordService.java
@@ -1,8 +1,9 @@
 package com.ruoyi.study.service;
 
 import com.baomidou.mybatisplus.extension.service.IService;
-import com.ruoyi.study.domain.TGameRecord;
 import com.ruoyi.study.domain.TSubjectRecord;
+import com.ruoyi.study.vo.ExitLearnVO;
+import com.ruoyi.study.vo.SubjectRecordResultVO;
 
 /**
  * <p>
@@ -14,4 +15,21 @@
  */
 public interface ITSubjectRecordService extends IService<TSubjectRecord> {
 
+    /**
+     * 退出学习,保存学习记录
+     *
+     * @param exitLearn 学习信息
+     * @param userid    用户id
+     * @return 保存结果
+     */
+    Boolean exitLearning(ExitLearnVO exitLearn, Integer userid);
+
+    /**
+     * 获取学习进度
+     *
+     * @param subjectRecord 已存在的学习进度
+     * @param userid        用户id
+     * @return 结果
+     */
+    SubjectRecordResultVO recordResult(TSubjectRecord subjectRecord, Integer userid);
 }
diff --git a/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/service/IUserStudyRecordService.java b/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/service/IUserStudyRecordService.java
new file mode 100644
index 0000000..bb421fe
--- /dev/null
+++ b/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/service/IUserStudyRecordService.java
@@ -0,0 +1,17 @@
+package com.ruoyi.study.service;
+
+
+import com.baomidou.mybatisplus.extension.service.IService;
+import com.ruoyi.study.domain.TUserStudyRecord;
+
+/**
+ * <p>
+ * 部门表 服务类
+ * </p>
+ *
+ * @author 无关风月
+ * @since 2024-04-26
+ */
+public interface IUserStudyRecordService extends IService<TUserStudyRecord> {
+
+}
diff --git a/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/service/impl/TGameServiceImpl.java b/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/service/impl/TGameServiceImpl.java
index 3eb6401..bb19bac 100644
--- a/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/service/impl/TGameServiceImpl.java
+++ b/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/service/impl/TGameServiceImpl.java
@@ -1,14 +1,20 @@
 package com.ruoyi.study.service.impl;
 
 import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
+import com.ruoyi.common.core.constant.Constants;
+import com.ruoyi.common.core.exception.GlobalException;
 import com.ruoyi.study.domain.TGame;
 import com.ruoyi.study.domain.TIntegralRecord;
+import com.ruoyi.study.domain.TSubject;
 import com.ruoyi.study.dto.CompleteGameDTO;
 import com.ruoyi.study.mapper.TGameMapper;
 import com.ruoyi.study.service.ITGameService;
+import com.ruoyi.study.vo.StudyGameMemoryVO;
 import org.springframework.stereotype.Service;
 
+import java.util.ArrayList;
 import java.util.List;
+import java.util.Random;
 import java.util.stream.Collectors;
 
 /**
@@ -45,4 +51,5 @@
     public TGame gameHearing(Integer quarter, Integer week) {
         return baseMapper.gameHearing(quarter, week);
     }
+
 }
diff --git a/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/service/impl/TStoryListenServiceImpl.java b/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/service/impl/TStoryListenServiceImpl.java
index 893be5c..b26151b 100644
--- a/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/service/impl/TStoryListenServiceImpl.java
+++ b/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/service/impl/TStoryListenServiceImpl.java
@@ -2,11 +2,9 @@
 
 import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
 import com.ruoyi.study.domain.TStoryListen;
-import com.ruoyi.study.service.ITStoryListenService;
 import com.ruoyi.study.mapper.TStoryListenMapper;
+import com.ruoyi.study.service.ITStoryListenService;
 import org.springframework.stereotype.Service;
-
-import java.util.List;
 
 /**
  * <p>
@@ -20,7 +18,7 @@
 public class TStoryListenServiceImpl extends ServiceImpl<TStoryListenMapper, TStoryListen> implements ITStoryListenService {
 
     @Override
-    public List<TStoryListen> storyDetail(Integer quarter, Integer week) {
+    public TStoryListen storyDetail(Integer quarter, Integer week) {
         return baseMapper.storyDetail(quarter, week);
     }
 }
diff --git a/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/service/impl/TStoryServiceImpl.java b/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/service/impl/TStoryServiceImpl.java
index eea74cb..6c1dab5 100644
--- a/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/service/impl/TStoryServiceImpl.java
+++ b/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/service/impl/TStoryServiceImpl.java
@@ -2,13 +2,17 @@
 
 import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
 import com.ruoyi.study.domain.TStory;
+import com.ruoyi.study.domain.TStoryListen;
 import com.ruoyi.study.dto.SubjectQuery;
 import com.ruoyi.study.mapper.TStoryMapper;
 import com.ruoyi.study.service.ITStoryService;
 import com.ruoyi.study.vo.SubjectVO;
 import org.springframework.stereotype.Service;
 
+import java.util.ArrayList;
+import java.util.Arrays;
 import java.util.List;
+import java.util.stream.Collectors;
 
 /**
  * <p>
@@ -25,4 +29,22 @@
     public List<SubjectVO> listAll(SubjectQuery query) {
         return this.baseMapper.listAll(query);
     }
+
+    @Override
+    public List<TStory> lookPictureDbu(TStoryListen storyListen, int type) {
+        List<TStory> storyList = new ArrayList<>();
+        List<String> list;
+        // 分类
+        if (0 == type) {
+            list = Arrays.stream(storyListen.getLookStory().split(",")).collect(Collectors.toList());
+        } else {
+            list = Arrays.stream(storyListen.getStory().split(",")).collect(Collectors.toList());
+        }
+        // 获取图片及语音集合
+        for (String s : list) {
+            TStory story = this.lambdaQuery().eq(TStory::getId, s).eq(TStory::getDisabled, 0).one();
+            storyList.add(story);
+        }
+        return storyList;
+    }
 }
diff --git a/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/service/impl/TStudyServiceImpl.java b/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/service/impl/TStudyServiceImpl.java
index 3fe0e68..ffcf068 100644
--- a/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/service/impl/TStudyServiceImpl.java
+++ b/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/service/impl/TStudyServiceImpl.java
@@ -8,10 +8,7 @@
 import com.ruoyi.study.domain.*;
 import com.ruoyi.study.dto.StudyWeekDTO;
 import com.ruoyi.study.mapper.TStudyMapper;
-import com.ruoyi.study.service.ITGameRecordService;
-import com.ruoyi.study.service.ITStudyService;
-import com.ruoyi.study.service.ITSubjectService;
-import com.ruoyi.study.service.ITUserStudyService;
+import com.ruoyi.study.service.*;
 import com.ruoyi.study.vo.*;
 import org.springframework.stereotype.Service;
 
@@ -38,17 +35,86 @@
     private ITGameRecordService gameRecordService;
     @Resource
     private TokenService tokenService;
+    @Resource
+    private ITStudyAnswerService studyAnswerService;
+    @Resource
+    private ITStudyInductionService studyInductionService;
+    @Resource
+    private ITStudyLookService studyLookService;
+    @Resource
+    private ITStudyListenService studyListenService;
+    @Resource
+    private ITStudyPairService studyPairService;
+    @Resource
+    private ITGameService gameService;
+    @Resource
+    private ITStoryListenService storyListenService;
 
-    private final static Map<String, Integer> GAME_DIFFICULTY_MAP = new HashMap<>();
+    private final static Map<Integer, Integer> GAME_DIFFICULTY_MAP = new HashMap<>();
 
     static {
-        GAME_DIFFICULTY_MAP.put("1", 0);
-        GAME_DIFFICULTY_MAP.put("2", 1);
+        GAME_DIFFICULTY_MAP.put(1, 0);
+        GAME_DIFFICULTY_MAP.put(2, 1);
     }
 
     @Override
     public List<StudyWeekDTO> weekList(Integer type, Integer quarter) {
-        return baseMapper.weekList(type, quarter);
+        List<StudyWeekDTO> result = new ArrayList<>();
+        // 根据季度和type查询学习配置
+        List<TStudy> study = lambdaQuery().eq(TStudy::getQuarter, quarter).eq(TStudy::getType, type)
+                .eq(TStudy::getDisabled, 0).orderByAsc(TStudy::getWeek).list();
+        for (TStudy item : study) {
+            Integer week = item.getWeek();
+            String title = item.getTitle();
+            Integer id = item.getId();
+            // 计算总积分
+            int total = 0;
+            // 有问有答
+            List<TStudyAnswer> answerList = studyAnswerService.lambdaQuery().eq(TStudyAnswer::getStudyId, id)
+                    .eq(TStudyAnswer::getDisabled, 0).list();
+            total += answerList.stream().map(TStudyAnswer::getIntegral).mapToInt(Integer::intValue).sum();
+            // 归纳判断
+            List<TStudyInduction> inductionList = studyInductionService.lambdaQuery().eq(TStudyInduction::getStudyId, id)
+                    .eq(TStudyInduction::getDisabled, 0).list();
+            total += inductionList.stream().map(TStudyInduction::getIntegral).mapToInt(Integer::intValue).sum();
+            // 看图选音
+            List<TStudyLook> lookList = studyLookService.lambdaQuery().eq(TStudyLook::getStudyId, id)
+                    .eq(TStudyLook::getDisabled, 0).list();
+            total += lookList.stream().map(TStudyLook::getIntegral).mapToInt(Integer::intValue).sum();
+            // 听音选图
+            List<TStudyListen> listenList = studyListenService.lambdaQuery().eq(TStudyListen::getStudyId, id)
+                    .eq(TStudyListen::getDisabled, 0).list();
+            total += listenList.stream().map(TStudyListen::getIntegral).mapToInt(Integer::intValue).sum();
+            // 音图相配
+            List<TStudyPair> pairList = studyPairService.lambdaQuery().eq(TStudyPair::getStudyId, id)
+                    .eq(TStudyPair::getDisabled, 0).list();
+            total += pairList.stream().map(TStudyPair::getIntegral).mapToInt(Integer::intValue).sum();
+            // 自主游戏
+            List<TGame> gameList = gameService.lambdaQuery().eq(TGame::getStudyId, id)
+                    .eq(TGame::getDisabled, 0).list();
+            // 自主游戏-超级听力
+            List<String> gameIntegral = gameList.stream().map(TGame::getIntegral).collect(Collectors.toList());
+            for (String s : gameIntegral) {
+                List<String> list = Arrays.stream(s.split(",")).collect(Collectors.toList());
+                total += list.stream().mapToInt(Integer::parseInt).sum();
+            }
+            // 自主游戏-框架记忆
+            List<Integer> gameAnswerIntegral = gameList.stream().map(TGame::getAnswerIntegral).collect(Collectors.toList());
+            for (Integer integral : gameAnswerIntegral) {
+                if (null != integral) {
+                    total += integral;
+                }
+            }
+            // 自主故事
+            List<TStoryListen> storyListenList = storyListenService.lambdaQuery().eq(TStoryListen::getStudyId, id)
+                    .eq(TStoryListen::getDisabled, 0).list();
+            // 自主故事 - 框架记忆
+            total += storyListenList.stream().map(TStoryListen::getIntegral).mapToInt(Integer::intValue).sum();
+            // 自主故事 - 看图配音
+            total += storyListenList.stream().map(TStoryListen::getLookIntegral).mapToInt(Integer::intValue).sum();
+            result.add(new StudyWeekDTO(week, type, quarter, title, total));
+        }
+        return result;
     }
 
     @Override
@@ -60,15 +126,17 @@
     public void checkDifficulty(Integer difficulty, Integer week, TGame game) {
         // 判断用户是否完成上一个等级
         if (!Constants.ZERO.equals(difficulty)) {
-            Integer level = GAME_DIFFICULTY_MAP.get(String.valueOf(difficulty));
+            Integer level = GAME_DIFFICULTY_MAP.get(difficulty);
             if (null == level) {
                 throw new GlobalException("游戏等级异常,请重试!");
             }
             // 获取用户游戏进度
             Integer userId = tokenService.getLoginUserStudy().getUserid();
-            List<TGameRecord> list = gameRecordService.lambdaQuery().eq(TGameRecord::getUserId, userId).eq(TGameRecord::getGameId, game.getId()).list();
-            boolean contains = list.stream().map(TGameRecord::getGameDifficulty).collect(Collectors.toList()).contains(level);
-            if (!contains) {
+            List<TGameRecord> list = gameRecordService.lambdaQuery().eq(TGameRecord::getUserId, userId)
+                    .eq(TGameRecord::getGameId, game.getId())
+                    .eq(TGameRecord::getAccuracy, 100)
+                    .eq(TGameRecord::getGameDifficulty, level).list();
+            if (list.isEmpty()) {
                 throw new GlobalException("请先完成上一难度再挑战当前难度!");
             }
         }
@@ -79,16 +147,33 @@
         if (studyListens.isEmpty()) {
             throw new GlobalException("当前学习周目题目数量不足!");
         }
-        // 随机获取一组题
-        Random rand = new Random();
-        TStudyListen data;
-        if (studyListens.size() == 1) {
-            data = studyListens.get(0);
-        } else {
-            data = studyListens.get(rand.nextInt(studyListens.size()));
+        // 题组信息
+        LearnStudyVO learnStudy = new LearnStudyVO();
+        String ids = studyListens.stream().map(TStudyListen::getId).map(String::valueOf)
+                .collect(Collectors.joining(","));
+        learnStudy.setId(ids);
+        int total = 0;
+        for (TStudyListen data : studyListens) {
+            if (null != data) {
+                total += data.getIntegral();
+            }
         }
-        List<TSubject> subjectList = getSubjects(data.getSubject().split(","));
-        return new StudyListenResultVO(data, subjectList);
+        learnStudy.setIntegral(total);
+        // 语音及图片
+        List<List<TSubject>> subjectList = new ArrayList<>();
+        for (TStudyListen studyListen : studyListens) {
+            List<String> subjectIds = Arrays.stream(studyListen.getSubject().split(",")).collect(Collectors.toList());
+            Collections.shuffle(subjectIds);
+            List<TSubject> list = new ArrayList<>();
+            // 图片及语音集合
+            for (String id : subjectIds) {
+                TSubject data = subjectService.lambdaQuery().eq(TSubject::getId, id)
+                        .eq(TSubject::getDisabled, 0).one();
+                list.add(data);
+            }
+            subjectList.add(list);
+        }
+        return new StudyListenResultVO(learnStudy, subjectList);
     }
 
     @Override
@@ -96,16 +181,33 @@
         if (lookList.isEmpty()) {
             throw new GlobalException("当前学习周目题目数量不足!");
         }
-        // 随机获取一组题
-        Random rand = new Random();
-        TStudyLook data;
-        if (lookList.size() == 1) {
-            data = lookList.get(0);
-        } else {
-            data = lookList.get(rand.nextInt(lookList.size()));
+        // 题组信息
+        LearnStudyVO learnStudy = new LearnStudyVO();
+        String ids = lookList.stream().map(TStudyLook::getId).map(String::valueOf)
+                .collect(Collectors.joining(","));
+        learnStudy.setId(ids);
+        int total = 0;
+        for (TStudyLook data : lookList) {
+            if (null != data) {
+                total += data.getIntegral();
+            }
         }
-        List<TSubject> subjectList = getSubjects(data.getSubject().split(","));
-        return new StudyLookResultVO(data, subjectList);
+        learnStudy.setIntegral(total);
+        // 语音及图片
+        List<List<TSubject>> subjectList = new ArrayList<>();
+        for (TStudyLook studyLook : lookList) {
+            List<String> subjectIds = Arrays.stream(studyLook.getSubject().split(",")).collect(Collectors.toList());
+            Collections.shuffle(subjectIds);
+            List<TSubject> list = new ArrayList<>();
+            // 图片及语音集合
+            for (String id : subjectIds) {
+                TSubject data = subjectService.lambdaQuery().eq(TSubject::getId, id)
+                        .eq(TSubject::getDisabled, 0).one();
+                list.add(data);
+            }
+            subjectList.add(list);
+        }
+        return new StudyLookResultVO(learnStudy, subjectList);
     }
 
     @Override
@@ -113,23 +215,33 @@
         if (inductionList.isEmpty()) {
             throw new GlobalException("当前学习周目题目数量不足!");
         }
-        // 随机获取一组题
-        Random rand = new Random();
-        TStudyInduction data;
-        if (inductionList.size() == 1) {
-            data = inductionList.get(0);
-        } else {
-            data = inductionList.get(rand.nextInt(inductionList.size()));
-        }
-        String[] ids = data.getSubject().split(",");
-        List<TSubject> subjectList = new ArrayList<>();
-        for (String id : ids) {
-            if (id.startsWith("-")) {
-                id = id.replace("-", "");
+        // 题组信息
+        LearnStudyVO learnStudy = new LearnStudyVO();
+        String ids = inductionList.stream().map(TStudyInduction::getId).map(String::valueOf)
+                .collect(Collectors.joining(","));
+        learnStudy.setId(ids);
+        int total = 0;
+        for (TStudyInduction data : inductionList) {
+            if (null != data) {
+                total += data.getIntegral();
             }
-            subjectList.add(subjectService.getById(id));
         }
-        return new StudyInductionResultVO(data, subjectList);
+        learnStudy.setIntegral(total);
+        // 语音及图片
+        List<List<TSubject>> subjectList = new ArrayList<>();
+        for (TStudyInduction data : inductionList) {
+            List<String> subjectIds = Arrays.stream(data.getSubject().split(",")).collect(Collectors.toList());
+            Collections.shuffle(subjectIds);
+            List<TSubject> subjectLists = new ArrayList<>();
+            for (String id : subjectIds) {
+                if (id.startsWith("-")) {
+                    id = id.replace("-", "");
+                }
+                subjectLists.add(subjectService.getById(id));
+            }
+            subjectList.add(subjectLists);
+        }
+        return new StudyInductionResultVO(learnStudy, subjectList);
     }
 
     @Override
@@ -137,37 +249,56 @@
         if (answerList.isEmpty()) {
             throw new GlobalException("当前学习周目题目数量不足!");
         }
-        // 随机获取一组题
-        Random rand = new Random();
-        TStudyAnswer data;
-        TStudyAnswer dataTwo;
-        if (answerList.size() == 1) {
-            data = answerList.get(0);
-            dataTwo = answerList.get(0);
-        } else {
-            data = answerList.get(rand.nextInt(answerList.size()));
-            dataTwo = answerList.get(rand.nextInt(answerList.size()));
+        // 题组信息
+        LearnStudyVO learnStudy = new LearnStudyVO();
+        String ids = answerList.stream().map(TStudyAnswer::getId).map(String::valueOf)
+                .collect(Collectors.joining(","));
+        learnStudy.setId(ids);
+        int total = 0;
+        for (TStudyAnswer data : answerList) {
+            if (null != data) {
+                total += data.getIntegral();
+            }
         }
-        AnswerVO one = new AnswerVO();
-        BeanUtils.copyProperties(data, one);
-        answerList.remove(data);
-        AnswerVO two = new AnswerVO();
-        BeanUtils.copyProperties(dataTwo, two);
-        // 获取问题题目 和 回答题目
-        List<String> ids = new ArrayList<>();
-        ids.add(String.valueOf(one.getSubject()));
-        ids.add(String.valueOf(one.getAnswerSubject()));
-        // 有问有答
-        List<TStudyAnswer> answers = new ArrayList<>();
-        answers.add(one);
-        one.setSubjectList(getSubjects(ids.toArray(new String[0])));
-        // 第二题信息
-        List<String> twoIds = new ArrayList<>();
-        answers.add(two);
-        twoIds.add(String.valueOf(two.getSubject()));
-        twoIds.add(String.valueOf(two.getAnswerSubject()));
-        two.setSubjectList(getSubjects(twoIds.toArray(new String[0])));
-        return new StudyAnswerResultVO(answers);
+        learnStudy.setIntegral(total);
+        // 题目语音及图片信息
+        List<List<QuestionsAnswersSubjectVO>> subjectList = new ArrayList<>();
+        for (int i = 0; i < answerList.size(); i += Constants.TWO) {
+            List<QuestionsAnswersSubjectVO> voList = new ArrayList<>();
+            // 一组题目为四道题,
+            TStudyAnswer one = answerList.get(i);
+            TStudyAnswer two = answerList.get(i + 1);
+            voAdd(voList, one);
+            voAdd(voList, two);
+            subjectList.add(voList);
+        }
+        return new StudyAnswerResultVO(learnStudy, subjectList);
+    }
+
+    private void voAdd(List<QuestionsAnswersSubjectVO> voList, TStudyAnswer one) {
+        // 第一道题问题及答案
+        Integer subject = one.getSubject();
+        Integer answerSubject = one.getAnswerSubject();
+        // 问题题目信息
+        QuestionsAnswersSubjectVO oneVO = new QuestionsAnswersSubjectVO();
+        TSubject one1 = subjectService.lambdaQuery().eq(TSubject::getId, subject)
+                .eq(TSubject::getDisabled, 0).one();
+        BeanUtils.copyProperties(one1, oneVO);
+        // 回答题目信息
+        QuestionsAnswersSubjectVO twoVO = new QuestionsAnswersSubjectVO();
+        TSubject two1 = subjectService.lambdaQuery().eq(TSubject::getId, answerSubject)
+                .eq(TSubject::getDisabled, 0).one();
+        BeanUtils.copyProperties(two1, twoVO);
+        // 判断第一组题目的问题题目及回答题目,哪个是答案
+        if (Constants.ZERO.equals(one.getIsAnswer())) {
+            oneVO.setIsQuestion(0);
+            twoVO.setIsQuestion(1);
+        } else {
+            oneVO.setIsQuestion(1);
+            twoVO.setIsQuestion(0);
+        }
+        voList.add(oneVO);
+        voList.add(twoVO);
     }
 
     @Override
@@ -175,32 +306,136 @@
         if (pair.isEmpty()) {
             throw new GlobalException("当前学习周目题目数量不足!");
         }
-        // 随机获取一组题
-        Random rand = new Random();
-        TStudyPair data;
-        if (pair.size() == 1) {
-            data = pair.get(0);
-        } else {
-            data = pair.get(rand.nextInt(pair.size()));
+        // 题组信息
+        LearnStudyVO learnStudy = new LearnStudyVO();
+        String ids = pair.stream().map(TStudyPair::getId).map(String::valueOf)
+                .collect(Collectors.joining(","));
+        learnStudy.setId(ids);
+        int total = 0;
+        for (TStudyPair data : pair) {
+            if (null != data) {
+                total += data.getIntegral();
+            }
         }
-        List<TSubject> subjectList = getSubjects(data.getSubject().split(","));
-        return new StudyPairResultVO(data, subjectList);
+        learnStudy.setIntegral(total);
+        // 语音及图片
+        List<List<TSubject>> subjectList = new ArrayList<>();
+        for (TStudyPair data : pair) {
+            List<String> subjectIds = Arrays.stream(data.getSubject().split(",")).collect(Collectors.toList());
+            Collections.shuffle(subjectIds);
+            List<TSubject> subjectLists = new ArrayList<>();
+            for (String id : subjectIds) {
+                if (id.startsWith("-")) {
+                    id = id.replace("-", "");
+                }
+                subjectLists.add(subjectService.getById(id));
+            }
+            subjectList.add(subjectLists);
+        }
+        return new StudyPairResultVO(learnStudy, subjectList);
     }
 
-    /**
-     * 根据参数id查询图片及语音
-     *
-     * @param ids 多个id
-     * @return 图片及语音集合
-     */
-    private List<TSubject> getSubjects(String[] ids) {
-        List<TSubject> list = new ArrayList<>();
-        for (String id : ids) {
-            TSubject data = subjectService.lambdaQuery().eq(TSubject::getId, id)
-                    .eq(TSubject::getDisabled, 0).one();
-            list.add(data);
+    @Override
+    public int computeSchedule(TUserStudy result, Integer week) {
+        // 基础学习进度
+        Integer listen = result.getListen();
+        Integer look = result.getLook();
+        Integer induction = result.getInduction();
+        Integer answer = result.getAnswer();
+        Integer pair = result.getPair();
+        Integer day = result.getDay();
+        // 默认进度为 0
+        int defaultSchedule;
+        // week以超过当前week,进度为 100%
+        if (result.getWeek() > week) {
+            defaultSchedule = 100;
+        } else {
+            // 根据day初始化学习进度
+            if (Constants.ONE.equals(day)) {
+                defaultSchedule = 0;
+            } else if (Constants.TWO.equals(day)) {
+                defaultSchedule = 20;
+            } else if (Constants.THREE.equals(day)) {
+                defaultSchedule = 40;
+            } else if (Constants.FOUR.equals(day)) {
+                defaultSchedule = 60;
+            } else if (Constants.FIVE.equals(day)) {
+                defaultSchedule = 80;
+            } else {
+                defaultSchedule = 0;
+            }
+            // 进度学习完成度计算总学习进度
+            if (!Constants.ZERO.equals(listen) && !Constants.BURDEN_ONE.equals(listen)) {
+                defaultSchedule += 4 * (100 / listen);
+            }
+            if (!Constants.ZERO.equals(look) && !Constants.BURDEN_ONE.equals(look)) {
+                defaultSchedule += 4 * (100 / look);
+            }
+            if (!Constants.ZERO.equals(induction) && !Constants.BURDEN_ONE.equals(induction)) {
+                defaultSchedule += 4 * (100 / induction);
+            }
+            if (!Constants.ZERO.equals(answer) && !Constants.BURDEN_ONE.equals(answer)) {
+                defaultSchedule += 4 * (100 / answer);
+            }
+            if (!Constants.ZERO.equals(pair) && !Constants.BURDEN_ONE.equals(pair)) {
+                defaultSchedule += 4 * (100 / pair);
+            }
         }
-        return list;
+        return defaultSchedule;
+    }
+
+    @Override
+    public int computeTotalIntegral(List<String> studyIds, Integer type, Integer accuracy) {
+        int sum;
+        if (Constants.ONE.equals(type)) {
+            List<TStudyListen> list = studyListenService.lambdaQuery().in(TStudyListen::getId, studyIds)
+                    .eq(TStudyListen::getDisabled, 0).list();
+            Optional<TStudyListen> any = list.stream().findAny();
+            if (any.isPresent()) {
+                sum = any.get().getIntegral();
+            } else {
+                sum = 0;
+            }
+        } else if (Constants.TWO.equals(type)) {
+            List<TStudyLook> list = studyLookService.lambdaQuery().in(TStudyLook::getId, studyIds)
+                    .eq(TStudyLook::getDisabled, 0).list();
+            Optional<TStudyLook> any = list.stream().findAny();
+            if (any.isPresent()) {
+                sum = any.get().getIntegral();
+            } else {
+                sum = 0;
+            }
+        } else if (Constants.THREE.equals(type)) {
+            List<TStudyInduction> list = studyInductionService.lambdaQuery().in(TStudyInduction::getId, studyIds)
+                    .eq(TStudyInduction::getDisabled, 0).list();
+            Optional<TStudyInduction> any = list.stream().findAny();
+            if (any.isPresent()) {
+                sum = any.get().getIntegral();
+            } else {
+                sum = 0;
+            }
+        } else if (Constants.FOUR.equals(type)) {
+            List<TStudyAnswer> list = studyAnswerService.lambdaQuery().in(TStudyAnswer::getId, studyIds)
+                    .eq(TStudyAnswer::getDisabled, 0).list();
+            Optional<TStudyAnswer> any = list.stream().findAny();
+            if (any.isPresent()) {
+                sum = any.get().getIntegral();
+            } else {
+                sum = 0;
+            }
+        } else if (Constants.FIVE.equals(type)) {
+            List<TStudyPair> list = studyPairService.lambdaQuery().in(TStudyPair::getId, studyIds)
+                    .eq(TStudyPair::getDisabled, 0).list();
+            Optional<TStudyPair> any = list.stream().findAny();
+            if (any.isPresent()) {
+                sum = any.get().getIntegral();
+            } else {
+                sum = 0;
+            }
+        } else {
+            throw new GlobalException("题目信息异常!");
+        }
+        return (int) (sum * ((double) accuracy / 100));
     }
 
 }
diff --git a/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/service/impl/TSubjectRecordServiceImpl.java b/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/service/impl/TSubjectRecordServiceImpl.java
index b5b6fea..e9f9b5e 100644
--- a/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/service/impl/TSubjectRecordServiceImpl.java
+++ b/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/service/impl/TSubjectRecordServiceImpl.java
@@ -1,13 +1,16 @@
 package com.ruoyi.study.service.impl;
 
 import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
-import com.ruoyi.study.domain.TGameRecord;
 import com.ruoyi.study.domain.TSubjectRecord;
-import com.ruoyi.study.mapper.TGameRecordMapper;
 import com.ruoyi.study.mapper.TSubjectRecordMapper;
-import com.ruoyi.study.service.ITGameRecordService;
 import com.ruoyi.study.service.ITSubjectRecordService;
+import com.ruoyi.study.vo.ExitLearnVO;
+import com.ruoyi.study.vo.SubjectRecordResultVO;
 import org.springframework.stereotype.Service;
+
+import java.util.Arrays;
+import java.util.List;
+import java.util.stream.Collectors;
 
 /**
  * <p>
@@ -20,4 +23,33 @@
 @Service
 public class TSubjectRecordServiceImpl extends ServiceImpl<TSubjectRecordMapper, TSubjectRecord> implements ITSubjectRecordService {
 
+    @Override
+    public Boolean exitLearning(ExitLearnVO exitLearn, Integer userid) {
+        Integer week = exitLearn.getWeek();
+        Integer day = exitLearn.getDay();
+        Integer type = exitLearn.getType();
+        String topicIds = exitLearn.getTopicIds();
+        String teamIds = exitLearn.getTeamIds();
+        // 封装信息
+        TSubjectRecord subjectRecord = new TSubjectRecord();
+        subjectRecord.setUserId(userid);
+        subjectRecord.setWeek(week);
+        subjectRecord.setDay(day);
+        subjectRecord.setType(type);
+        // 答题次数与答题正确次数
+        subjectRecord.setAnswerNumber(exitLearn.getAnswerNumber());
+        subjectRecord.setCorrectNumber(exitLearn.getCorrectNumber());
+        subjectRecord.setType(type);
+        // 题目与题组需处理
+        List<String> teamIdList = Arrays.stream(teamIds.split(",")).collect(Collectors.toList());
+        List<String> topicIdList = Arrays.stream(topicIds.split(",")).collect(Collectors.toList());
+        subjectRecord.setBeforeSubject(teamIdList.stream().map(String::valueOf).collect(Collectors.joining(",")));
+        subjectRecord.setCompleteSubject(topicIdList.stream().map(String::valueOf).collect(Collectors.joining(",")));
+        return this.save(subjectRecord);
+    }
+
+    @Override
+    public SubjectRecordResultVO recordResult(TSubjectRecord subjectRecord, Integer userid) {
+        return null;
+    }
 }
diff --git a/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/service/impl/TUserServiceImpl.java b/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/service/impl/TUserServiceImpl.java
index d88b8cb..100363e 100644
--- a/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/service/impl/TUserServiceImpl.java
+++ b/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/service/impl/TUserServiceImpl.java
@@ -17,9 +17,10 @@
 import org.springframework.stereotype.Service;
 
 import javax.annotation.Resource;
-import java.util.Date;
 import java.util.List;
 import java.util.concurrent.TimeUnit;
+import java.util.regex.Matcher;
+import java.util.regex.Pattern;
 
 /**
  * <p>
@@ -44,11 +45,20 @@
 
     @Autowired
     private HWSendSms hwSendSms;
+
     @Override
     public Boolean phoneCode(String phone) throws Exception {
         // 生成随机 6位数字 验证码
         String phoneCode = RandomUtil.randomNumbers(6);
-
+        String regex = Constants.PHONE;
+        // 编译正则表达式
+        Pattern pattern = Pattern.compile(regex);
+        // 创建Matcher对象
+        Matcher matcher = pattern.matcher(phone);
+        // 判断是否匹配
+        if (!matcher.matches()) {
+            throw new GlobalException("手机号不合法!");
+        }
         hwSendSms.sendSms(phoneCode, phone);
         // 判断redis中是否存在手机验证码
         Object phoneCodeRedis = redisTemplate.opsForValue().get(RedisConstants.PHONE_CODE + phone);
@@ -79,15 +89,16 @@
 
     @Override
     public Boolean isVip() {
-        TUser user = lambdaQuery().eq(TUser::getId, tokenService.getLoginUserStudy().getUserid())
-                .eq(TUser::getDisabled, 0).eq(TUser::getState,1).one();
-        // 是否为vip 逻辑
-        if (null == user) {
-            return false;
-        }
-        // vip过期时间,字段为空也表示 当前用户不是vip
-        Date vipEndTime = user.getVipEndTime();
-        return null != vipEndTime && System.currentTimeMillis() <= vipEndTime.getTime();
+//        TUser user = lambdaQuery().eq(TUser::getId, tokenService.getLoginUserStudy().getUserid())
+//                .eq(TUser::getDisabled, 0).eq(TUser::getState,1).one();
+//        // 是否为vip 逻辑
+//        if (null == user) {
+//            return false;
+//        }
+//        // vip过期时间,字段为空也表示 当前用户不是vip
+//        Date vipEndTime = user.getVipEndTime();
+//        return null != vipEndTime && System.currentTimeMillis() <= vipEndTime.getTime();
+        return true;
     }
 
 }
diff --git a/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/service/impl/TUserStudyServiceImpl.java b/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/service/impl/TUserStudyServiceImpl.java
index 2116119..f7b629b 100644
--- a/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/service/impl/TUserStudyServiceImpl.java
+++ b/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/service/impl/TUserStudyServiceImpl.java
@@ -85,22 +85,32 @@
         Integer type = completeStudy.getType();
         if (Constants.ONE.equals(type)) {
             userStudyRecord.setListen(Constants.ONE_HUNDRED);
+            userStudyRecord.setLook(Constants.BURDEN_ONE);
+            userStudyRecord.setInduction(Constants.BURDEN_ONE);
+            userStudyRecord.setAnswer(Constants.BURDEN_ONE);
+            userStudyRecord.setPair(Constants.BURDEN_ONE);
         } else if (Constants.TWO.equals(type)) {
             userStudyRecord.setLook(Constants.ONE_HUNDRED);
+            userStudyRecord.setInduction(Constants.BURDEN_ONE);
+            userStudyRecord.setAnswer(Constants.BURDEN_ONE);
+            userStudyRecord.setPair(Constants.BURDEN_ONE);
         } else if (Constants.THREE.equals(type)) {
             userStudyRecord.setInduction(Constants.ONE_HUNDRED);
+            userStudyRecord.setAnswer(Constants.BURDEN_ONE);
+            userStudyRecord.setPair(Constants.BURDEN_ONE);
         } else if (Constants.FOUR.equals(type)) {
             userStudyRecord.setAnswer(Constants.ONE_HUNDRED);
+            userStudyRecord.setPair(Constants.BURDEN_ONE);
         } else if (Constants.FIVE.equals(type)) {
             // 类型五,说明当前day已经全部完成,更新学习记录的 day
             Integer nextDay = DAY_MAP.get(String.valueOf(userStudyRecord.getDay()));
             userStudyRecord.setDay(nextDay);
             // 学习day已切换更新学习进度及学习时长
-            userStudyRecord.setListen(Constants.ZERO);
-            userStudyRecord.setLook(Constants.ZERO);
-            userStudyRecord.setInduction(Constants.ZERO);
-            userStudyRecord.setAnswer(Constants.ZERO);
-            userStudyRecord.setPair(Constants.ZERO);
+            userStudyRecord.setListen(Constants.BURDEN_ONE);
+            userStudyRecord.setLook(Constants.BURDEN_ONE);
+            userStudyRecord.setInduction(Constants.BURDEN_ONE);
+            userStudyRecord.setAnswer(Constants.BURDEN_ONE);
+            userStudyRecord.setPair(Constants.BURDEN_ONE);
             // 下一day为 1说明该周目已完成,应更改为下一周目
             if (Constants.ONE.equals(nextDay)) {
                 // 获取下一周目信息
diff --git a/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/service/impl/UserStudyRecordServiceImpl.java b/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/service/impl/UserStudyRecordServiceImpl.java
new file mode 100644
index 0000000..732b771
--- /dev/null
+++ b/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/service/impl/UserStudyRecordServiceImpl.java
@@ -0,0 +1,20 @@
+package com.ruoyi.study.service.impl;
+
+import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
+import com.ruoyi.study.domain.TUserStudyRecord;
+import com.ruoyi.study.mapper.UserStudyRecordMapper;
+import com.ruoyi.study.service.IUserStudyRecordService;
+import org.springframework.stereotype.Service;
+
+/**
+ * <p>
+ * 部门表 服务实现类
+ * </p>
+ *
+ * @author 无关风月
+ * @since 2024-04-26
+ */
+@Service
+public class UserStudyRecordServiceImpl extends ServiceImpl<UserStudyRecordMapper, TUserStudyRecord> implements IUserStudyRecordService {
+
+}
diff --git a/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/vo/ExitLearnVO.java b/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/vo/ExitLearnVO.java
new file mode 100644
index 0000000..38462ab
--- /dev/null
+++ b/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/vo/ExitLearnVO.java
@@ -0,0 +1,56 @@
+package com.ruoyi.study.vo;
+
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+
+/**
+ * @author HJL
+ * @version 1.0
+ * @since 2024-06-11 17:21
+ */
+@Data
+public class ExitLearnVO {
+
+    /**
+     * 所属week
+     */
+    @ApiModelProperty("所属week")
+    private Integer week;
+
+    /**
+     * 所属day
+     */
+    @ApiModelProperty("所属day")
+    private Integer day;
+
+    /**
+     * 题目类型
+     */
+    @ApiModelProperty("题目类型(1:听音选图;2:看图选音;3:归纳排除;4:有问有答;5:音图相配)")
+    private Integer type;
+
+    /**
+     * 题目id数组
+     */
+    @ApiModelProperty("回答正确的题目id")
+    private String topicIds;
+
+    /**
+     * 题组id
+     */
+    @ApiModelProperty("题组id数组")
+    private String teamIds;
+
+    /**
+     * 答题次数
+     */
+    @ApiModelProperty(value = "答题次数")
+    private Integer answerNumber;
+
+    /**
+     * 答题正确次数
+     */
+    @ApiModelProperty(value = "答题正确次数")
+    private Integer correctNumber;
+
+}
diff --git a/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/vo/GameMemoryPhotoVO.java b/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/vo/GameMemoryPhotoVO.java
new file mode 100644
index 0000000..7cf1275
--- /dev/null
+++ b/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/vo/GameMemoryPhotoVO.java
@@ -0,0 +1,24 @@
+package com.ruoyi.study.vo;
+
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+
+/**
+ * @author HJL
+ * @version 1.0
+ * @since 2024-06-13 11:32
+ */
+@Data
+public class GameMemoryPhotoVO {
+
+    @ApiModelProperty("游戏id")
+    private Integer id;
+
+    @ApiModelProperty("游戏图片")
+    private String photo;
+
+    public GameMemoryPhotoVO(Integer id, String photo) {
+        this.id = id;
+        this.photo = photo;
+    }
+}
diff --git a/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/vo/GameMemoryVoiceVO.java b/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/vo/GameMemoryVoiceVO.java
new file mode 100644
index 0000000..f83213e
--- /dev/null
+++ b/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/vo/GameMemoryVoiceVO.java
@@ -0,0 +1,24 @@
+package com.ruoyi.study.vo;
+
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+
+/**
+ * @author HJL
+ * @version 1.0
+ * @since 2024-06-13 11:32
+ */
+@Data
+public class GameMemoryVoiceVO {
+
+    @ApiModelProperty("游戏id")
+    private Integer id;
+
+    @ApiModelProperty("游戏语音")
+    private String voice;
+
+    public GameMemoryVoiceVO(Integer id, String voice) {
+        this.id = id;
+        this.voice = voice;
+    }
+}
diff --git a/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/vo/LearnStudyVO.java b/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/vo/LearnStudyVO.java
new file mode 100644
index 0000000..5b5a99e
--- /dev/null
+++ b/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/vo/LearnStudyVO.java
@@ -0,0 +1,20 @@
+package com.ruoyi.study.vo;
+
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+
+/**
+ * @author HJL
+ * @version 1.0
+ * @since 2024-06-13 18:36
+ */
+@Data
+public class LearnStudyVO {
+
+    @ApiModelProperty("拼接后的id")
+    private String id;
+
+    @ApiModelProperty("总积分")
+    private Integer integral;
+
+}
diff --git a/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/vo/QuestionsAnswersSubjectVO.java b/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/vo/QuestionsAnswersSubjectVO.java
new file mode 100644
index 0000000..5a9ecb2
--- /dev/null
+++ b/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/vo/QuestionsAnswersSubjectVO.java
@@ -0,0 +1,20 @@
+package com.ruoyi.study.vo;
+
+import com.ruoyi.study.domain.TSubject;
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+import lombok.EqualsAndHashCode;
+
+/**
+ * @author HJL
+ * @version 1.0
+ * @since 2024-06-14 10:10
+ */
+@EqualsAndHashCode(callSuper = true)
+@Data
+public class QuestionsAnswersSubjectVO extends TSubject {
+
+    @ApiModelProperty("答案是否为问题图片")
+    private Integer isQuestion;
+
+}
diff --git a/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/vo/StudyAnswerResultVO.java b/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/vo/StudyAnswerResultVO.java
index 11d1f78..05c0c2f 100644
--- a/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/vo/StudyAnswerResultVO.java
+++ b/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/vo/StudyAnswerResultVO.java
@@ -1,6 +1,5 @@
 package com.ruoyi.study.vo;
 
-import com.ruoyi.study.domain.TStudyAnswer;
 import io.swagger.annotations.ApiModel;
 import io.swagger.annotations.ApiModelProperty;
 import lombok.Data;
@@ -14,15 +13,22 @@
  */
 @Data
 @ApiModel(value = "有问有答返回信息类")
-public class StudyAnswerResultVO{
+public class StudyAnswerResultVO {
 
     /**
      * 自主学习题目信息
      */
     @ApiModelProperty("自主学习题目信息")
-    private List<TStudyAnswer> data;
+    private LearnStudyVO data;
 
-    public StudyAnswerResultVO(List<TStudyAnswer> data) {
+    /**
+     * 自主学习题目所包含录音图片等
+     */
+    @ApiModelProperty("自主学习题目所包含录音图片等")
+    private List<List<QuestionsAnswersSubjectVO>> subjectList;
+
+    public StudyAnswerResultVO(LearnStudyVO data, List<List<QuestionsAnswersSubjectVO>> subjectList) {
         this.data = data;
+        this.subjectList = subjectList;
     }
 }
diff --git a/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/vo/StudyGameMemoryVO.java b/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/vo/StudyGameMemoryVO.java
new file mode 100644
index 0000000..5f6cb1b
--- /dev/null
+++ b/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/vo/StudyGameMemoryVO.java
@@ -0,0 +1,42 @@
+package com.ruoyi.study.vo;
+
+import com.ruoyi.study.domain.TGame;
+import io.swagger.annotations.ApiModel;
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+
+import java.util.List;
+
+/**
+ * @author HJL
+ * @version 1.0
+ * @since 2024-05-22 14:48
+ */
+@Data
+@ApiModel(value = "超级听力&&超级记忆返回信息类")
+public class StudyGameMemoryVO {
+
+    /**
+     * 趣味游戏题目信息
+     */
+    @ApiModelProperty("趣味游戏题目信息")
+    private TGame data;
+
+    /**
+     * 趣味游戏题目信息
+     */
+    @ApiModelProperty("游戏图片合集")
+    private List<GameMemoryPhotoVO> photoList;
+
+    /**
+     * 趣味游戏题目信息
+     */
+    @ApiModelProperty("游戏语音合集")
+    private List<GameMemoryVoiceVO> voiceList;
+
+    public StudyGameMemoryVO(TGame data, List<GameMemoryPhotoVO> photoList, List<GameMemoryVoiceVO> voiceList) {
+        this.data = data;
+        this.photoList = photoList;
+        this.voiceList = voiceList;
+    }
+}
diff --git a/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/vo/StudyGamerResultVO.java b/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/vo/StudyGameResultVO.java
similarity index 69%
rename from ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/vo/StudyGamerResultVO.java
rename to ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/vo/StudyGameResultVO.java
index 579fe78..be67f4d 100644
--- a/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/vo/StudyGamerResultVO.java
+++ b/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/vo/StudyGameResultVO.java
@@ -5,7 +5,6 @@
 import io.swagger.annotations.ApiModel;
 import io.swagger.annotations.ApiModelProperty;
 import lombok.Data;
-import lombok.EqualsAndHashCode;
 
 import java.util.List;
 
@@ -14,10 +13,9 @@
  * @version 1.0
  * @since 2024-05-22 14:48
  */
-@EqualsAndHashCode(callSuper = true)
 @Data
 @ApiModel(value = "超级听力&&超级记忆返回信息类")
-public class StudyGamerResultVO extends StudyModelVO {
+public class StudyGameResultVO {
 
     /**
      * 趣味游戏题目信息
@@ -25,9 +23,12 @@
     @ApiModelProperty("趣味游戏题目信息")
     private TGame data;
 
-    public StudyGamerResultVO(TGame data, List<TSubject> subjectList) {
+    @ApiModelProperty("图片及语音信息")
+    private List<TSubject> subjectList;
+
+    public StudyGameResultVO(TGame data, List<TSubject> subjectList) {
         this.data = data;
-        super.setSubjectList(subjectList);
+        this.subjectList = subjectList;
     }
 
 }
diff --git a/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/vo/StudyInductionResultVO.java b/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/vo/StudyInductionResultVO.java
index faefba8..48ff009 100644
--- a/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/vo/StudyInductionResultVO.java
+++ b/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/vo/StudyInductionResultVO.java
@@ -1,6 +1,5 @@
 package com.ruoyi.study.vo;
 
-import com.ruoyi.study.domain.TStudyInduction;
 import com.ruoyi.study.domain.TSubject;
 import io.swagger.annotations.ApiModel;
 import io.swagger.annotations.ApiModelProperty;
@@ -23,9 +22,9 @@
      * 自主学习题目信息
      */
     @ApiModelProperty("自主学习题目信息")
-    private TStudyInduction data;
+    private LearnStudyVO data;
 
-    public StudyInductionResultVO(TStudyInduction data, List<TSubject> subjectList) {
+    public StudyInductionResultVO(LearnStudyVO data, List<List<TSubject>> subjectList) {
         this.data = data;
         super.setSubjectList(subjectList);
     }
diff --git a/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/vo/StudyListenResultVO.java b/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/vo/StudyListenResultVO.java
index 035eb2f..7daaae7 100644
--- a/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/vo/StudyListenResultVO.java
+++ b/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/vo/StudyListenResultVO.java
@@ -1,6 +1,5 @@
 package com.ruoyi.study.vo;
 
-import com.ruoyi.study.domain.TStudyListen;
 import com.ruoyi.study.domain.TSubject;
 import io.swagger.annotations.ApiModel;
 import io.swagger.annotations.ApiModelProperty;
@@ -23,9 +22,9 @@
      * 自主学习题目信息
      */
     @ApiModelProperty("自主学习题目信息")
-    private TStudyListen data;
+    private LearnStudyVO data;
 
-    public StudyListenResultVO(TStudyListen data, List<TSubject> subjectList) {
+    public StudyListenResultVO(LearnStudyVO data, List<List<TSubject>> subjectList) {
         this.data = data;
         super.setSubjectList(subjectList);
     }
diff --git a/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/vo/StudyLookResultVO.java b/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/vo/StudyLookResultVO.java
index 7cf982f..6332626 100644
--- a/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/vo/StudyLookResultVO.java
+++ b/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/vo/StudyLookResultVO.java
@@ -1,6 +1,5 @@
 package com.ruoyi.study.vo;
 
-import com.ruoyi.study.domain.TStudyLook;
 import com.ruoyi.study.domain.TSubject;
 import io.swagger.annotations.ApiModel;
 import io.swagger.annotations.ApiModelProperty;
@@ -17,15 +16,15 @@
 @EqualsAndHashCode(callSuper = true)
 @Data
 @ApiModel(value = "看图选音返回信息类")
-public class StudyLookResultVO extends StudyModelVO{
+public class StudyLookResultVO extends StudyModelVO {
 
     /**
      * 自主学习题目信息
      */
     @ApiModelProperty("自主学习题目信息")
-    private TStudyLook data;
+    private LearnStudyVO data;
 
-    public StudyLookResultVO(TStudyLook data, List<TSubject> subjectList) {
+    public StudyLookResultVO(LearnStudyVO data, List<List<TSubject>> subjectList) {
         this.data = data;
         super.setSubjectList(subjectList);
     }
diff --git a/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/vo/StudyModelVO.java b/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/vo/StudyModelVO.java
index 8060b5b..f391e77 100644
--- a/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/vo/StudyModelVO.java
+++ b/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/vo/StudyModelVO.java
@@ -18,6 +18,6 @@
      * 自主学习题目所包含录音图片等
      */
     @ApiModelProperty("自主学习题目所包含录音图片等")
-    private List<TSubject> subjectList;
+    private List<List<TSubject>> subjectList;
 
 }
diff --git a/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/vo/StudyPairResultVO.java b/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/vo/StudyPairResultVO.java
index a1abae0..8a21334 100644
--- a/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/vo/StudyPairResultVO.java
+++ b/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/vo/StudyPairResultVO.java
@@ -1,11 +1,9 @@
 package com.ruoyi.study.vo;
 
-import com.ruoyi.study.domain.TStudyPair;
 import com.ruoyi.study.domain.TSubject;
 import io.swagger.annotations.ApiModel;
 import io.swagger.annotations.ApiModelProperty;
 import lombok.Data;
-import lombok.EqualsAndHashCode;
 
 import java.util.List;
 
@@ -14,18 +12,17 @@
  * @version 1.0
  * @since 2024-05-22 14:48
  */
-@EqualsAndHashCode(callSuper = true)
 @Data
 @ApiModel(value = "音图相配返回信息类")
-public class StudyPairResultVO extends StudyModelVO {
+public class StudyPairResultVO  extends StudyModelVO {
 
     /**
      * 自主学习题目信息
      */
     @ApiModelProperty("自主学习题目信息")
-    private TStudyPair data;
+    private LearnStudyVO data;
 
-    public StudyPairResultVO(TStudyPair data, List<TSubject> subjectList) {
+    public StudyPairResultVO(LearnStudyVO data, List<List<TSubject>> subjectList) {
         this.data = data;
         super.setSubjectList(subjectList);
     }
diff --git a/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/vo/StudyRecordVO.java b/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/vo/StudyRecordVO.java
new file mode 100644
index 0000000..73b50a6
--- /dev/null
+++ b/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/vo/StudyRecordVO.java
@@ -0,0 +1,25 @@
+package com.ruoyi.study.vo;
+
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+
+/**
+ * @author HJL
+ * @version 1.0
+ * @since 2024-06-14 11:24
+ */
+@Data
+public class StudyRecordVO {
+
+    @ApiModelProperty("可获得总积分")
+    private Integer total;
+
+    @ApiModelProperty("已获取积分")
+    private Integer obtainedIntegral;
+
+
+    public StudyRecordVO(Integer total, Integer obtainedIntegral) {
+        this.total = total;
+        this.obtainedIntegral = obtainedIntegral;
+    }
+}
diff --git a/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/vo/StudyStoryListenResultVO.java b/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/vo/StudyStoryListenResultVO.java
index 0b8f12b..e85ab5c 100644
--- a/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/vo/StudyStoryListenResultVO.java
+++ b/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/vo/StudyStoryListenResultVO.java
@@ -1,7 +1,6 @@
 package com.ruoyi.study.vo;
 
 import com.ruoyi.study.domain.TStory;
-import com.ruoyi.study.domain.TStoryListen;
 import io.swagger.annotations.ApiModel;
 import io.swagger.annotations.ApiModelProperty;
 import lombok.Data;
@@ -21,7 +20,7 @@
      * 自主故事-看图配音&&框架记忆题目信息
      */
     @ApiModelProperty("自主故事-看图配音&&框架记忆题目信息")
-    private TStoryListen data;
+    private StudyStoryVO data;
 
     /**
      * 自主学习题目所包含录音图片等
@@ -29,7 +28,7 @@
     @ApiModelProperty("故事列表")
     private List<TStory> storyList;
 
-    public StudyStoryListenResultVO(TStoryListen data, List<TStory> storyList) {
+    public StudyStoryListenResultVO(StudyStoryVO data, List<TStory> storyList) {
         this.data = data;
         this.storyList = storyList;
     }
diff --git a/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/vo/StudyStoryVO.java b/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/vo/StudyStoryVO.java
new file mode 100644
index 0000000..23edaf3
--- /dev/null
+++ b/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/vo/StudyStoryVO.java
@@ -0,0 +1,20 @@
+package com.ruoyi.study.vo;
+
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+
+/**
+ * @author HJL
+ * @version 1.0
+ * @since 2024-06-13 18:36
+ */
+@Data
+public class StudyStoryVO {
+
+    @ApiModelProperty("故事id")
+    private Integer id;
+
+    @ApiModelProperty("总积分")
+    private Integer integral;
+
+}
diff --git a/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/vo/SubjectRecordResultVO.java b/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/vo/SubjectRecordResultVO.java
new file mode 100644
index 0000000..1bd5bfe
--- /dev/null
+++ b/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/vo/SubjectRecordResultVO.java
@@ -0,0 +1,48 @@
+package com.ruoyi.study.vo;
+
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+
+import java.util.List;
+
+/**
+ * @author HJL
+ * @version 1.0
+ * @since 2024-06-12 14:57
+ */
+@Data
+public class SubjectRecordResultVO {
+
+    /**
+     * 题组ids
+     */
+    @ApiModelProperty(value = "题组ids")
+    private List<Integer> teamIds;
+    /**
+     * 已回答正确的题目id
+     */
+    @ApiModelProperty(value = "已回答正确的题目id")
+    private List<Integer> topicIds;
+
+    /**
+     * 答题次数
+     */
+    @ApiModelProperty(value = "答题次数")
+    private Integer answerNumber;
+
+    /**
+     * 答题正确次数
+     */
+    @ApiModelProperty(value = "答题正确次数")
+    private Integer correctNumber;
+
+    public SubjectRecordResultVO() {
+    }
+
+    public SubjectRecordResultVO(List<Integer> teamIds, List<Integer> topicIds, Integer answerNumber, Integer correctNumber) {
+        this.teamIds = teamIds;
+        this.topicIds = topicIds;
+        this.answerNumber = answerNumber;
+        this.correctNumber = correctNumber;
+    }
+}
diff --git a/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/vo/UserPersonalCenterVO.java b/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/vo/UserPersonalCenterVO.java
index 3f3e2b3..83cb719 100644
--- a/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/vo/UserPersonalCenterVO.java
+++ b/ruoyi-service/ruoyi-study/src/main/java/com/ruoyi/study/vo/UserPersonalCenterVO.java
@@ -23,4 +23,7 @@
         this.user = user;
         this.userStudy = userStudy;
     }
+
+    public UserPersonalCenterVO() {
+    }
 }
diff --git a/ruoyi-service/ruoyi-study/src/main/resources/mapper/sutdy/TStudyMapper.xml b/ruoyi-service/ruoyi-study/src/main/resources/mapper/sutdy/TStudyMapper.xml
index bc436bf..064aa99 100644
--- a/ruoyi-service/ruoyi-study/src/main/resources/mapper/sutdy/TStudyMapper.xml
+++ b/ruoyi-service/ruoyi-study/src/main/resources/mapper/sutdy/TStudyMapper.xml
@@ -41,22 +41,9 @@
                  LEFT JOIN t_study_pair sp ON s.id = sp.studyId
                  LEFT JOIN t_story_listen sl ON s.id = sl.studyId
                  LEFT JOIN t_game g ON s.id = g.studyId
-        <where>
-            s.disabled = 0
-              and sa.disabled = 0
-              and si.disabled = 0
-              and st.disabled = 0
-              and sk.disabled = 0
-              and sp.disabled = 0
-              and sl.disabled = 0
-              and g.disabled = 0
-            <if test="quarter != null and quarter != ''">
-                and s.quarter = #{quarter}
-            </if>
-            <if test="type != null and quarter != ''">
-                and s.type = #{type}
-            </if>
-        </where>
+        where s.disabled = 0
+          and s.quarter = #{quarter}
+          and s.type = #{type}
         GROUP BY s.week, s.title, s.quarter, s.id;
     </select>
 </mapper>
diff --git a/ruoyi-service/ruoyi-study/src/main/resources/mapper/sutdy/UserStudyRecordMapper.xml b/ruoyi-service/ruoyi-study/src/main/resources/mapper/sutdy/UserStudyRecordMapper.xml
new file mode 100644
index 0000000..aef0709
--- /dev/null
+++ b/ruoyi-service/ruoyi-study/src/main/resources/mapper/sutdy/UserStudyRecordMapper.xml
@@ -0,0 +1,4 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN" "http://mybatis.org/dtd/mybatis-3-mapper.dtd">
+<mapper namespace="com.ruoyi.study.mapper.UserStudyRecordMapper">
+</mapper>

--
Gitblit v1.7.1