Bladeren bron

我的作业

Steven 3 jaren geleden
bovenliggende
commit
093733a40c
100 gewijzigde bestanden met toevoegingen van 5008 en 568 verwijderingen
  1. 176 0
      KulexiuForStudent/KulexiuForStudent.xcodeproj/project.pbxproj
  2. BIN
      KulexiuForStudent/KulexiuForStudent.xcworkspace/xcuserdata/wangzhi.xcuserdatad/UserInterfaceState.xcuserstate
  3. 6 22
      KulexiuForStudent/KulexiuForStudent.xcworkspace/xcuserdata/wangzhi.xcuserdatad/xcdebugger/Breakpoints_v2.xcbkptlist
  4. 22 0
      KulexiuForStudent/KulexiuForStudent/Assets.xcassets/Course/image_upload.imageset/Contents.json
  5. BIN
      KulexiuForStudent/KulexiuForStudent/Assets.xcassets/Course/image_upload.imageset/image_upload@2x.png
  6. BIN
      KulexiuForStudent/KulexiuForStudent/Assets.xcassets/Course/image_upload.imageset/image_upload@3x.png
  7. 22 0
      KulexiuForStudent/KulexiuForStudent/Assets.xcassets/Course/sort_down.imageset/Contents.json
  8. BIN
      KulexiuForStudent/KulexiuForStudent/Assets.xcassets/Course/sort_down.imageset/sort_down@2x.png
  9. BIN
      KulexiuForStudent/KulexiuForStudent/Assets.xcassets/Course/sort_down.imageset/sort_down@3x.png
  10. 22 0
      KulexiuForStudent/KulexiuForStudent/Assets.xcassets/Course/sort_up.imageset/Contents.json
  11. BIN
      KulexiuForStudent/KulexiuForStudent/Assets.xcassets/Course/sort_up.imageset/sort_up@2x.png
  12. BIN
      KulexiuForStudent/KulexiuForStudent/Assets.xcassets/Course/sort_up.imageset/sort_up@3x.png
  13. 22 0
      KulexiuForStudent/KulexiuForStudent/Assets.xcassets/Mine/star_grey.imageset/Contents.json
  14. BIN
      KulexiuForStudent/KulexiuForStudent/Assets.xcassets/Mine/star_grey.imageset/star_grey@2x.png
  15. BIN
      KulexiuForStudent/KulexiuForStudent/Assets.xcassets/Mine/star_grey.imageset/star_grey@3x.png
  16. 22 0
      KulexiuForStudent/KulexiuForStudent/Assets.xcassets/Mine/star_light.imageset/Contents.json
  17. BIN
      KulexiuForStudent/KulexiuForStudent/Assets.xcassets/Mine/star_light.imageset/star_light@2x.png
  18. BIN
      KulexiuForStudent/KulexiuForStudent/Assets.xcassets/Mine/star_light.imageset/star_light@3x.png
  19. 22 0
      KulexiuForStudent/KulexiuForStudent/Assets.xcassets/cancle_button.imageset/Contents.json
  20. BIN
      KulexiuForStudent/KulexiuForStudent/Assets.xcassets/cancle_button.imageset/cancle_button@2x.png
  21. BIN
      KulexiuForStudent/KulexiuForStudent/Assets.xcassets/cancle_button.imageset/cancle_button@3x.png
  22. 22 0
      KulexiuForStudent/KulexiuForStudent/Assets.xcassets/playVideo_image.imageset/Contents.json
  23. BIN
      KulexiuForStudent/KulexiuForStudent/Assets.xcassets/playVideo_image.imageset/playVideo_image@2x.png
  24. BIN
      KulexiuForStudent/KulexiuForStudent/Assets.xcassets/playVideo_image.imageset/playVideo_image@3x.png
  25. 22 0
      KulexiuForStudent/KulexiuForStudent/Assets.xcassets/video_delete.imageset/Contents.json
  26. BIN
      KulexiuForStudent/KulexiuForStudent/Assets.xcassets/video_delete.imageset/video_delete@2x.png
  27. BIN
      KulexiuForStudent/KulexiuForStudent/Assets.xcassets/video_delete.imageset/video_delete@3x.png
  28. BIN
      KulexiuForStudent/KulexiuForStudent/Assets.xcassets/video_placeholder.imageset/video_placeholder@2x.png
  29. BIN
      KulexiuForStudent/KulexiuForStudent/Assets.xcassets/video_placeholder.imageset/video_placeholder@3x.png
  30. 32 0
      KulexiuForStudent/KulexiuForStudent/Common/Base/KSNetworkingManager.h
  31. 52 0
      KulexiuForStudent/KulexiuForStudent/Common/Base/KSNetworkingManager.m
  32. 18 0
      KulexiuForStudent/KulexiuForStudent/Common/Tools/KSVideoHelper.h
  33. 68 0
      KulexiuForStudent/KulexiuForStudent/Common/Tools/KSVideoHelper.m
  34. 25 0
      KulexiuForStudent/KulexiuForStudent/Common/Tools/UIView+ExtensionForDotLine.h
  35. 41 0
      KulexiuForStudent/KulexiuForStudent/Common/Tools/UIView+ExtensionForDotLine.m
  36. 19 0
      KulexiuForStudent/KulexiuForStudent/Module/Course/AccompanyCourse/View/AccompanyArrangeCell.h
  37. 55 0
      KulexiuForStudent/KulexiuForStudent/Module/Course/AccompanyCourse/View/AccompanyArrangeCell.m
  38. 139 0
      KulexiuForStudent/KulexiuForStudent/Module/Course/AccompanyCourse/View/AccompanyArrangeCell.xib
  39. 26 0
      KulexiuForStudent/KulexiuForStudent/Module/Course/AccompanyCourse/View/AccompanyCourseInfoCell.h
  40. 85 0
      KulexiuForStudent/KulexiuForStudent/Module/Course/AccompanyCourse/View/AccompanyCourseInfoCell.m
  41. 171 0
      KulexiuForStudent/KulexiuForStudent/Module/Course/AccompanyCourse/View/AccompanyCourseInfoCell.xib
  42. 28 0
      KulexiuForStudent/KulexiuForStudent/Module/Course/AccompanyCourse/View/AccompanyHomeworkCell.h
  43. 112 0
      KulexiuForStudent/KulexiuForStudent/Module/Course/AccompanyCourse/View/AccompanyHomeworkCell.m
  44. 137 0
      KulexiuForStudent/KulexiuForStudent/Module/Course/AccompanyCourse/View/AccompanyHomeworkCell.xib
  45. 19 0
      KulexiuForStudent/KulexiuForStudent/Module/Course/AccompanyCourse/View/AccompanyRemarkCell.h
  46. 54 0
      KulexiuForStudent/KulexiuForStudent/Module/Course/AccompanyCourse/View/AccompanyRemarkCell.m
  47. 139 0
      KulexiuForStudent/KulexiuForStudent/Module/Course/AccompanyCourse/View/AccompanyRemarkCell.xib
  48. 6 2
      KulexiuForStudent/KulexiuForStudent/Module/Mine/Controller/MineViewController.m
  49. 18 0
      KulexiuForStudent/KulexiuForStudent/Module/Mine/Homework/Controller/HomeworkDetailViewController.h
  50. 377 0
      KulexiuForStudent/KulexiuForStudent/Module/Mine/Homework/Controller/HomeworkDetailViewController.m
  51. 23 0
      KulexiuForStudent/KulexiuForStudent/Module/Mine/Homework/Controller/HomeworkListViewController.h
  52. 153 0
      KulexiuForStudent/KulexiuForStudent/Module/Mine/Homework/Controller/HomeworkListViewController.m
  53. 45 0
      KulexiuForStudent/KulexiuForStudent/Module/Mine/Homework/Model/HomeworkDetailModel.h
  54. 270 0
      KulexiuForStudent/KulexiuForStudent/Module/Mine/Homework/Model/HomeworkDetailModel.m
  55. 34 0
      KulexiuForStudent/KulexiuForStudent/Module/Mine/Homework/Model/HomeworkListModel.h
  56. 193 0
      KulexiuForStudent/KulexiuForStudent/Module/Mine/Homework/Model/HomeworkListModel.m
  57. 30 0
      KulexiuForStudent/KulexiuForStudent/Module/Mine/Homework/View/AccompanyAlertView.h
  58. 101 0
      KulexiuForStudent/KulexiuForStudent/Module/Mine/Homework/View/AccompanyAlertView.m
  59. 152 0
      KulexiuForStudent/KulexiuForStudent/Module/Mine/Homework/View/AccompanyAlertView.xib
  60. 20 0
      KulexiuForStudent/KulexiuForStudent/Module/Mine/Homework/View/HomeworkAddView.h
  61. 81 0
      KulexiuForStudent/KulexiuForStudent/Module/Mine/Homework/View/HomeworkAddView.m
  62. 18 0
      KulexiuForStudent/KulexiuForStudent/Module/Mine/Homework/View/HomeworkBodyView.h
  63. 333 0
      KulexiuForStudent/KulexiuForStudent/Module/Mine/Homework/View/HomeworkBodyView.m
  64. 24 0
      KulexiuForStudent/KulexiuForStudent/Module/Mine/Homework/View/HomeworkBottomView.h
  65. 44 0
      KulexiuForStudent/KulexiuForStudent/Module/Mine/Homework/View/HomeworkBottomView.m
  66. 50 0
      KulexiuForStudent/KulexiuForStudent/Module/Mine/Homework/View/HomeworkBottomView.xib
  67. 23 0
      KulexiuForStudent/KulexiuForStudent/Module/Mine/Homework/View/HomeworkListCell.h
  68. 76 0
      KulexiuForStudent/KulexiuForStudent/Module/Mine/Homework/View/HomeworkListCell.m
  69. 166 0
      KulexiuForStudent/KulexiuForStudent/Module/Mine/Homework/View/HomeworkListCell.xib
  70. 27 0
      KulexiuForStudent/KulexiuForStudent/Module/Mine/Homework/View/HomeworkSortView.h
  71. 52 0
      KulexiuForStudent/KulexiuForStudent/Module/Mine/Homework/View/HomeworkSortView.m
  72. 61 0
      KulexiuForStudent/KulexiuForStudent/Module/Mine/Homework/View/HomeworkSortView.xib
  73. 30 0
      KulexiuForStudent/KulexiuForStudent/Module/Mine/Homework/View/HomeworkVideoView.h
  74. 68 0
      KulexiuForStudent/KulexiuForStudent/Module/Mine/Homework/View/HomeworkVideoView.m
  75. 88 0
      KulexiuForStudent/KulexiuForStudent/Module/Mine/Homework/View/HomeworkVideoView.xib
  76. 1 0
      KulexiuForStudent/KulexiuForStudent/Module/Mine/MineCourse/Controller/MyCourseViewController.m
  77. 20 0
      KulexiuForStudent/KulexiuForStudent/Module/Mine/View/KSStarView.h
  78. 126 0
      KulexiuForStudent/KulexiuForStudent/Module/Mine/View/KSStarView.m
  79. 3 3
      KulexiuForStudent/Podfile
  80. 9 9
      KulexiuForStudent/Podfile.lock
  81. 9 9
      KulexiuForStudent/Pods/Manifest.lock
  82. 354 240
      KulexiuForStudent/Pods/Pods.xcodeproj/project.pbxproj
  83. 7 7
      KulexiuForStudent/Pods/RongCloudRTC/RongCloudRTC/RongRTCLib.xcframework/Info.plist
  84. 4 4
      KulexiuForStudent/Pods/RongCloudRTC/RongCloudRTC/RongRTCLib.xcframework/ios-arm64_armv7/RongRTCLib.framework/Headers/RCRTCLocalUser.h
  85. BIN
      KulexiuForStudent/Pods/RongCloudRTC/RongCloudRTC/RongRTCLib.xcframework/ios-arm64_armv7/RongRTCLib.framework/Info.plist
  86. BIN
      KulexiuForStudent/Pods/RongCloudRTC/RongCloudRTC/RongRTCLib.xcframework/ios-arm64_armv7/RongRTCLib.framework/RongRTCLib
  87. 4 4
      KulexiuForStudent/Pods/RongCloudRTC/RongCloudRTC/RongRTCLib.xcframework/ios-arm64_armv7/RongRTCLib.framework/_CodeSignature/CodeResources
  88. 4 4
      KulexiuForStudent/Pods/RongCloudRTC/RongCloudRTC/RongRTCLib.xcframework/ios-x86_64-simulator/RongRTCLib.framework/Headers/RCRTCLocalUser.h
  89. BIN
      KulexiuForStudent/Pods/RongCloudRTC/RongCloudRTC/RongRTCLib.xcframework/ios-x86_64-simulator/RongRTCLib.framework/Info.plist
  90. BIN
      KulexiuForStudent/Pods/RongCloudRTC/RongCloudRTC/RongRTCLib.xcframework/ios-x86_64-simulator/RongRTCLib.framework/RongRTCLib
  91. 4 4
      KulexiuForStudent/Pods/RongCloudRTC/RongCloudRTC/RongRTCLib.xcframework/ios-x86_64-simulator/RongRTCLib.framework/_CodeSignature/CodeResources
  92. 1 1
      KulexiuForStudent/Pods/SDWebImage/LICENSE
  93. 264 246
      KulexiuForStudent/Pods/SDWebImage/README.md
  94. 1 1
      KulexiuForStudent/Pods/Target Support Files/Pods-KulexiuForStudent-KulexiuForStudentUITests/Pods-KulexiuForStudent-KulexiuForStudentUITests-acknowledgements.markdown
  95. 1 1
      KulexiuForStudent/Pods/Target Support Files/Pods-KulexiuForStudent-KulexiuForStudentUITests/Pods-KulexiuForStudent-KulexiuForStudentUITests-acknowledgements.plist
  96. 1 1
      KulexiuForStudent/Pods/Target Support Files/Pods-KulexiuForStudent/Pods-KulexiuForStudent-acknowledgements.markdown
  97. 1 1
      KulexiuForStudent/Pods/Target Support Files/Pods-KulexiuForStudent/Pods-KulexiuForStudent-acknowledgements.plist
  98. 7 7
      KulexiuForStudent/Pods/Target Support Files/RongCloudRTC/RongCloudRTC-xcframeworks.sh
  99. 1 1
      KulexiuForStudent/Pods/Target Support Files/SDWebImage/SDWebImage-Info.plist
  100. 45 1
      KulexiuForStudent/Pods/Target Support Files/SDWebImage/SDWebImage-umbrella.h

+ 176 - 0
KulexiuForStudent/KulexiuForStudent.xcodeproj/project.pbxproj

@@ -384,6 +384,33 @@
 		BC119241280ED9E000A716F7 /* AccompanyDetailViewController.m in Sources */ = {isa = PBXBuildFile; fileRef = BC119240280ED9E000A716F7 /* AccompanyDetailViewController.m */; };
 		BC119244280EDA2400A716F7 /* NSObject+KSDateFormatter.m in Sources */ = {isa = PBXBuildFile; fileRef = BC119243280EDA2400A716F7 /* NSObject+KSDateFormatter.m */; };
 		BC119247280EDA5800A716F7 /* kSJXCollectionView.m in Sources */ = {isa = PBXBuildFile; fileRef = BC119245280EDA5800A716F7 /* kSJXCollectionView.m */; };
+		BC11924E280EDD5500A716F7 /* HomeworkListViewController.m in Sources */ = {isa = PBXBuildFile; fileRef = BC11924D280EDD5500A716F7 /* HomeworkListViewController.m */; };
+		BC119258280FA85300A716F7 /* HomeworkListCell.xib in Resources */ = {isa = PBXBuildFile; fileRef = BC119252280FA85200A716F7 /* HomeworkListCell.xib */; };
+		BC119259280FA85300A716F7 /* HomeworkListCell.m in Sources */ = {isa = PBXBuildFile; fileRef = BC119253280FA85200A716F7 /* HomeworkListCell.m */; };
+		BC11925A280FA85300A716F7 /* HomeworkSortView.xib in Resources */ = {isa = PBXBuildFile; fileRef = BC119255280FA85300A716F7 /* HomeworkSortView.xib */; };
+		BC11925B280FA85300A716F7 /* HomeworkSortView.m in Sources */ = {isa = PBXBuildFile; fileRef = BC119257280FA85300A716F7 /* HomeworkSortView.m */; };
+		BC11925E280FA89A00A716F7 /* HomeworkBodyView.m in Sources */ = {isa = PBXBuildFile; fileRef = BC11925D280FA89A00A716F7 /* HomeworkBodyView.m */; };
+		BC119263280FA90100A716F7 /* HomeworkDetailModel.m in Sources */ = {isa = PBXBuildFile; fileRef = BC119261280FA90100A716F7 /* HomeworkDetailModel.m */; };
+		BC119264280FA90100A716F7 /* HomeworkListModel.m in Sources */ = {isa = PBXBuildFile; fileRef = BC119262280FA90100A716F7 /* HomeworkListModel.m */; };
+		BC119267280FA92700A716F7 /* HomeworkDetailViewController.m in Sources */ = {isa = PBXBuildFile; fileRef = BC119266280FA92700A716F7 /* HomeworkDetailViewController.m */; };
+		BC11926B280FAF5900A716F7 /* AccompanyAlertView.m in Sources */ = {isa = PBXBuildFile; fileRef = BC119269280FAF5800A716F7 /* AccompanyAlertView.m */; };
+		BC11926C280FAF5900A716F7 /* AccompanyAlertView.xib in Resources */ = {isa = PBXBuildFile; fileRef = BC11926A280FAF5900A716F7 /* AccompanyAlertView.xib */; };
+		BC119270280FAF7D00A716F7 /* AccompanyCourseInfoCell.xib in Resources */ = {isa = PBXBuildFile; fileRef = BC11926E280FAF7C00A716F7 /* AccompanyCourseInfoCell.xib */; };
+		BC119271280FAF7D00A716F7 /* AccompanyCourseInfoCell.m in Sources */ = {isa = PBXBuildFile; fileRef = BC11926F280FAF7C00A716F7 /* AccompanyCourseInfoCell.m */; };
+		BC119275280FB01100A716F7 /* AccompanyHomeworkCell.xib in Resources */ = {isa = PBXBuildFile; fileRef = BC119272280FB01000A716F7 /* AccompanyHomeworkCell.xib */; };
+		BC119276280FB01100A716F7 /* AccompanyHomeworkCell.m in Sources */ = {isa = PBXBuildFile; fileRef = BC119273280FB01000A716F7 /* AccompanyHomeworkCell.m */; };
+		BC11927A280FB07F00A716F7 /* AccompanyArrangeCell.m in Sources */ = {isa = PBXBuildFile; fileRef = BC119277280FB07F00A716F7 /* AccompanyArrangeCell.m */; };
+		BC11927B280FB07F00A716F7 /* AccompanyArrangeCell.xib in Resources */ = {isa = PBXBuildFile; fileRef = BC119278280FB07F00A716F7 /* AccompanyArrangeCell.xib */; };
+		BC11927F280FB10900A716F7 /* AccompanyRemarkCell.m in Sources */ = {isa = PBXBuildFile; fileRef = BC11927C280FB10700A716F7 /* AccompanyRemarkCell.m */; };
+		BC119280280FB10900A716F7 /* AccompanyRemarkCell.xib in Resources */ = {isa = PBXBuildFile; fileRef = BC11927D280FB10800A716F7 /* AccompanyRemarkCell.xib */; };
+		BC119288280FB3B100A716F7 /* KSStarView.m in Sources */ = {isa = PBXBuildFile; fileRef = BC119287280FB3B100A716F7 /* KSStarView.m */; };
+		BC11928C280FB44300A716F7 /* HomeworkVideoView.xib in Resources */ = {isa = PBXBuildFile; fileRef = BC119289280FB44200A716F7 /* HomeworkVideoView.xib */; };
+		BC11928D280FB44300A716F7 /* HomeworkVideoView.m in Sources */ = {isa = PBXBuildFile; fileRef = BC11928B280FB44300A716F7 /* HomeworkVideoView.m */; };
+		BC119290280FB46100A716F7 /* KSVideoHelper.m in Sources */ = {isa = PBXBuildFile; fileRef = BC11928F280FB46100A716F7 /* KSVideoHelper.m */; };
+		BC119293280FBC1100A716F7 /* HomeworkAddView.m in Sources */ = {isa = PBXBuildFile; fileRef = BC119292280FBC1100A716F7 /* HomeworkAddView.m */; };
+		BC119298280FBCB400A716F7 /* UIView+ExtensionForDotLine.m in Sources */ = {isa = PBXBuildFile; fileRef = BC119297280FBCB400A716F7 /* UIView+ExtensionForDotLine.m */; };
+		BC11929B280FD2E800A716F7 /* HomeworkBottomView.m in Sources */ = {isa = PBXBuildFile; fileRef = BC11929A280FD2E800A716F7 /* HomeworkBottomView.m */; };
+		BC11929D280FD2EF00A716F7 /* HomeworkBottomView.xib in Resources */ = {isa = PBXBuildFile; fileRef = BC11929C280FD2EF00A716F7 /* HomeworkBottomView.xib */; };
 		BC28582B2809036D0024697C /* StudentInfoModel.m in Sources */ = {isa = PBXBuildFile; fileRef = BC28582A2809036D0024697C /* StudentInfoModel.m */; };
 		BC50171227FC0D5600F8BCBC /* SubjectChooseViewController.m in Sources */ = {isa = PBXBuildFile; fileRef = BC50171127FC0D5600F8BCBC /* SubjectChooseViewController.m */; };
 		BC50171527FC0D8300F8BCBC /* SubjectChooseBodyView.m in Sources */ = {isa = PBXBuildFile; fileRef = BC50171427FC0D8300F8BCBC /* SubjectChooseBodyView.m */; };
@@ -1236,6 +1263,51 @@
 		BC119243280EDA2400A716F7 /* NSObject+KSDateFormatter.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = "NSObject+KSDateFormatter.m"; sourceTree = "<group>"; };
 		BC119245280EDA5800A716F7 /* kSJXCollectionView.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = kSJXCollectionView.m; sourceTree = "<group>"; };
 		BC119246280EDA5800A716F7 /* kSJXCollectionView.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = kSJXCollectionView.h; sourceTree = "<group>"; };
+		BC11924C280EDD5500A716F7 /* HomeworkListViewController.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = HomeworkListViewController.h; sourceTree = "<group>"; };
+		BC11924D280EDD5500A716F7 /* HomeworkListViewController.m */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.objc; path = HomeworkListViewController.m; sourceTree = "<group>"; };
+		BC119252280FA85200A716F7 /* HomeworkListCell.xib */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = file.xib; path = HomeworkListCell.xib; sourceTree = "<group>"; };
+		BC119253280FA85200A716F7 /* HomeworkListCell.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = HomeworkListCell.m; sourceTree = "<group>"; };
+		BC119254280FA85200A716F7 /* HomeworkListCell.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = HomeworkListCell.h; sourceTree = "<group>"; };
+		BC119255280FA85300A716F7 /* HomeworkSortView.xib */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = file.xib; path = HomeworkSortView.xib; sourceTree = "<group>"; };
+		BC119256280FA85300A716F7 /* HomeworkSortView.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = HomeworkSortView.h; sourceTree = "<group>"; };
+		BC119257280FA85300A716F7 /* HomeworkSortView.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = HomeworkSortView.m; sourceTree = "<group>"; };
+		BC11925C280FA89A00A716F7 /* HomeworkBodyView.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = HomeworkBodyView.h; sourceTree = "<group>"; };
+		BC11925D280FA89A00A716F7 /* HomeworkBodyView.m */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.objc; path = HomeworkBodyView.m; sourceTree = "<group>"; };
+		BC11925F280FA90000A716F7 /* HomeworkDetailModel.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = HomeworkDetailModel.h; sourceTree = "<group>"; };
+		BC119260280FA90000A716F7 /* HomeworkListModel.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = HomeworkListModel.h; sourceTree = "<group>"; };
+		BC119261280FA90100A716F7 /* HomeworkDetailModel.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = HomeworkDetailModel.m; sourceTree = "<group>"; };
+		BC119262280FA90100A716F7 /* HomeworkListModel.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = HomeworkListModel.m; sourceTree = "<group>"; };
+		BC119265280FA92700A716F7 /* HomeworkDetailViewController.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = HomeworkDetailViewController.h; sourceTree = "<group>"; };
+		BC119266280FA92700A716F7 /* HomeworkDetailViewController.m */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.objc; path = HomeworkDetailViewController.m; sourceTree = "<group>"; };
+		BC119268280FAF5800A716F7 /* AccompanyAlertView.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = AccompanyAlertView.h; sourceTree = "<group>"; };
+		BC119269280FAF5800A716F7 /* AccompanyAlertView.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = AccompanyAlertView.m; sourceTree = "<group>"; };
+		BC11926A280FAF5900A716F7 /* AccompanyAlertView.xib */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = file.xib; path = AccompanyAlertView.xib; sourceTree = "<group>"; };
+		BC11926D280FAF7C00A716F7 /* AccompanyCourseInfoCell.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = AccompanyCourseInfoCell.h; sourceTree = "<group>"; };
+		BC11926E280FAF7C00A716F7 /* AccompanyCourseInfoCell.xib */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = file.xib; path = AccompanyCourseInfoCell.xib; sourceTree = "<group>"; };
+		BC11926F280FAF7C00A716F7 /* AccompanyCourseInfoCell.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = AccompanyCourseInfoCell.m; sourceTree = "<group>"; };
+		BC119272280FB01000A716F7 /* AccompanyHomeworkCell.xib */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = file.xib; path = AccompanyHomeworkCell.xib; sourceTree = "<group>"; };
+		BC119273280FB01000A716F7 /* AccompanyHomeworkCell.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = AccompanyHomeworkCell.m; sourceTree = "<group>"; };
+		BC119274280FB01100A716F7 /* AccompanyHomeworkCell.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = AccompanyHomeworkCell.h; sourceTree = "<group>"; };
+		BC119277280FB07F00A716F7 /* AccompanyArrangeCell.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = AccompanyArrangeCell.m; sourceTree = "<group>"; };
+		BC119278280FB07F00A716F7 /* AccompanyArrangeCell.xib */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = file.xib; path = AccompanyArrangeCell.xib; sourceTree = "<group>"; };
+		BC119279280FB07F00A716F7 /* AccompanyArrangeCell.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = AccompanyArrangeCell.h; sourceTree = "<group>"; };
+		BC11927C280FB10700A716F7 /* AccompanyRemarkCell.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = AccompanyRemarkCell.m; sourceTree = "<group>"; };
+		BC11927D280FB10800A716F7 /* AccompanyRemarkCell.xib */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = file.xib; path = AccompanyRemarkCell.xib; sourceTree = "<group>"; };
+		BC11927E280FB10900A716F7 /* AccompanyRemarkCell.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = AccompanyRemarkCell.h; sourceTree = "<group>"; };
+		BC119286280FB3B000A716F7 /* KSStarView.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = KSStarView.h; sourceTree = "<group>"; };
+		BC119287280FB3B100A716F7 /* KSStarView.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = KSStarView.m; sourceTree = "<group>"; };
+		BC119289280FB44200A716F7 /* HomeworkVideoView.xib */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = file.xib; path = HomeworkVideoView.xib; sourceTree = "<group>"; };
+		BC11928A280FB44300A716F7 /* HomeworkVideoView.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = HomeworkVideoView.h; sourceTree = "<group>"; };
+		BC11928B280FB44300A716F7 /* HomeworkVideoView.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = HomeworkVideoView.m; sourceTree = "<group>"; };
+		BC11928E280FB46100A716F7 /* KSVideoHelper.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = KSVideoHelper.h; sourceTree = "<group>"; };
+		BC11928F280FB46100A716F7 /* KSVideoHelper.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = KSVideoHelper.m; sourceTree = "<group>"; };
+		BC119291280FBC1100A716F7 /* HomeworkAddView.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = HomeworkAddView.h; sourceTree = "<group>"; };
+		BC119292280FBC1100A716F7 /* HomeworkAddView.m */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.objc; path = HomeworkAddView.m; sourceTree = "<group>"; };
+		BC119296280FBCB300A716F7 /* UIView+ExtensionForDotLine.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = "UIView+ExtensionForDotLine.h"; sourceTree = "<group>"; };
+		BC119297280FBCB400A716F7 /* UIView+ExtensionForDotLine.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = "UIView+ExtensionForDotLine.m"; sourceTree = "<group>"; };
+		BC119299280FD2E800A716F7 /* HomeworkBottomView.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = HomeworkBottomView.h; sourceTree = "<group>"; };
+		BC11929A280FD2E800A716F7 /* HomeworkBottomView.m */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.objc; path = HomeworkBottomView.m; sourceTree = "<group>"; };
+		BC11929C280FD2EF00A716F7 /* HomeworkBottomView.xib */ = {isa = PBXFileReference; lastKnownFileType = file.xib; path = HomeworkBottomView.xib; sourceTree = "<group>"; };
 		BC2858292809036C0024697C /* StudentInfoModel.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = StudentInfoModel.h; sourceTree = "<group>"; };
 		BC28582A2809036D0024697C /* StudentInfoModel.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = StudentInfoModel.m; sourceTree = "<group>"; };
 		BC50171027FC0D5600F8BCBC /* SubjectChooseViewController.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = SubjectChooseViewController.h; sourceTree = "<group>"; };
@@ -1919,6 +1991,7 @@
 		275FA20327E7356B00CFEA2E /* Mine */ = {
 			isa = PBXGroup;
 			children = (
+				BC119248280EDD4600A716F7 /* Homework */,
 				BC1191F9280ED63C00A716F7 /* MineCourse */,
 				27F9031B27E87C2D00C08A19 /* DeviceCheck */,
 				27F9030F27E87C2C00C08A19 /* Networking */,
@@ -1957,6 +2030,8 @@
 				27F9033827E87FD500C08A19 /* MineBodyView.h */,
 				27F9033927E87FD500C08A19 /* MineBodyView.m */,
 				27F9033B27E87FE100C08A19 /* MineBodyView.xib */,
+				BC119286280FB3B000A716F7 /* KSStarView.h */,
+				BC119287280FB3B100A716F7 /* KSStarView.m */,
 			);
 			path = View;
 			sourceTree = "<group>";
@@ -2081,6 +2156,10 @@
 		2779336227E3249C0010E277 /* Tools */ = {
 			isa = PBXGroup;
 			children = (
+				BC119296280FBCB300A716F7 /* UIView+ExtensionForDotLine.h */,
+				BC119297280FBCB400A716F7 /* UIView+ExtensionForDotLine.m */,
+				BC11928E280FB46100A716F7 /* KSVideoHelper.h */,
+				BC11928F280FB46100A716F7 /* KSVideoHelper.m */,
 				275FA1AA27E734C500CFEA2E /* KSImageAlert.h */,
 				275FA1AC27E734C600CFEA2E /* KSImageAlert.m */,
 				275FA1AB27E734C600CFEA2E /* KSImageAlert.xib */,
@@ -3002,6 +3081,76 @@
 		BC11923E280ED9CC00A716F7 /* View */ = {
 			isa = PBXGroup;
 			children = (
+				BC11926D280FAF7C00A716F7 /* AccompanyCourseInfoCell.h */,
+				BC11926F280FAF7C00A716F7 /* AccompanyCourseInfoCell.m */,
+				BC11926E280FAF7C00A716F7 /* AccompanyCourseInfoCell.xib */,
+				BC119279280FB07F00A716F7 /* AccompanyArrangeCell.h */,
+				BC119277280FB07F00A716F7 /* AccompanyArrangeCell.m */,
+				BC119278280FB07F00A716F7 /* AccompanyArrangeCell.xib */,
+				BC119274280FB01100A716F7 /* AccompanyHomeworkCell.h */,
+				BC119273280FB01000A716F7 /* AccompanyHomeworkCell.m */,
+				BC119272280FB01000A716F7 /* AccompanyHomeworkCell.xib */,
+				BC11927E280FB10900A716F7 /* AccompanyRemarkCell.h */,
+				BC11927C280FB10700A716F7 /* AccompanyRemarkCell.m */,
+				BC11927D280FB10800A716F7 /* AccompanyRemarkCell.xib */,
+			);
+			path = View;
+			sourceTree = "<group>";
+		};
+		BC119248280EDD4600A716F7 /* Homework */ = {
+			isa = PBXGroup;
+			children = (
+				BC119249280EDD4600A716F7 /* Controller */,
+				BC11924A280EDD4600A716F7 /* Model */,
+				BC11924B280EDD4600A716F7 /* View */,
+			);
+			path = Homework;
+			sourceTree = "<group>";
+		};
+		BC119249280EDD4600A716F7 /* Controller */ = {
+			isa = PBXGroup;
+			children = (
+				BC11924C280EDD5500A716F7 /* HomeworkListViewController.h */,
+				BC11924D280EDD5500A716F7 /* HomeworkListViewController.m */,
+				BC119265280FA92700A716F7 /* HomeworkDetailViewController.h */,
+				BC119266280FA92700A716F7 /* HomeworkDetailViewController.m */,
+			);
+			path = Controller;
+			sourceTree = "<group>";
+		};
+		BC11924A280EDD4600A716F7 /* Model */ = {
+			isa = PBXGroup;
+			children = (
+				BC11925F280FA90000A716F7 /* HomeworkDetailModel.h */,
+				BC119261280FA90100A716F7 /* HomeworkDetailModel.m */,
+				BC119260280FA90000A716F7 /* HomeworkListModel.h */,
+				BC119262280FA90100A716F7 /* HomeworkListModel.m */,
+			);
+			path = Model;
+			sourceTree = "<group>";
+		};
+		BC11924B280EDD4600A716F7 /* View */ = {
+			isa = PBXGroup;
+			children = (
+				BC119268280FAF5800A716F7 /* AccompanyAlertView.h */,
+				BC119269280FAF5800A716F7 /* AccompanyAlertView.m */,
+				BC11926A280FAF5900A716F7 /* AccompanyAlertView.xib */,
+				BC11925C280FA89A00A716F7 /* HomeworkBodyView.h */,
+				BC11925D280FA89A00A716F7 /* HomeworkBodyView.m */,
+				BC119254280FA85200A716F7 /* HomeworkListCell.h */,
+				BC119253280FA85200A716F7 /* HomeworkListCell.m */,
+				BC119252280FA85200A716F7 /* HomeworkListCell.xib */,
+				BC119256280FA85300A716F7 /* HomeworkSortView.h */,
+				BC119257280FA85300A716F7 /* HomeworkSortView.m */,
+				BC119255280FA85300A716F7 /* HomeworkSortView.xib */,
+				BC11928A280FB44300A716F7 /* HomeworkVideoView.h */,
+				BC11928B280FB44300A716F7 /* HomeworkVideoView.m */,
+				BC119289280FB44200A716F7 /* HomeworkVideoView.xib */,
+				BC119291280FBC1100A716F7 /* HomeworkAddView.h */,
+				BC119292280FBC1100A716F7 /* HomeworkAddView.m */,
+				BC119299280FD2E800A716F7 /* HomeworkBottomView.h */,
+				BC11929A280FD2E800A716F7 /* HomeworkBottomView.m */,
+				BC11929C280FD2EF00A716F7 /* HomeworkBottomView.xib */,
 			);
 			path = View;
 			sourceTree = "<group>";
@@ -3734,15 +3883,20 @@
 				BC119235280ED97C00A716F7 /* CourseForLiveCell.xib in Resources */,
 				2723B62E27F157D500E0B90B /* GroupApplyChooseAllCell.xib in Resources */,
 				275FA23A27E7356B00CFEA2E /* VefiBodyView.xib in Resources */,
+				BC119258280FA85300A716F7 /* HomeworkListCell.xib in Resources */,
 				2723B63227F157D500E0B90B /* GroupSettingBodyView.xib in Resources */,
 				2723B5BF27F157B100E0B90B /* GroupCreateView.xib in Resources */,
 				2723B63727F157D500E0B90B /* ApplyBottomView.xib in Resources */,
 				2723B62F27F157D500E0B90B /* ChatComplainBodyView.xib in Resources */,
 				2723B62127F157D500E0B90B /* NoticeEditBodyView.xib in Resources */,
 				2723B66127F15CFB00E0B90B /* SettingBodyView.xib in Resources */,
+				BC11928C280FB44300A716F7 /* HomeworkVideoView.xib in Resources */,
 				275E8AB527E18F8B00DD3F6E /* Assets.xcassets in Resources */,
+				BC119275280FB01100A716F7 /* AccompanyHomeworkCell.xib in Resources */,
+				BC119280280FB10900A716F7 /* AccompanyRemarkCell.xib in Resources */,
 				2723B63527F157D500E0B90B /* GroupApplyChooseCell.xib in Resources */,
 				2723B5C227F157B100E0B90B /* GroupListViewCell.xib in Resources */,
+				BC11925A280FA85300A716F7 /* HomeworkSortView.xib in Resources */,
 				2723B62527F157D500E0B90B /* GroupNoticeCell.xib in Resources */,
 				275FA23D27E7356B00CFEA2E /* PasswordBodyView.xib in Resources */,
 				2723B66227F15CFC00E0B90B /* FeedbackBodyView.xib in Resources */,
@@ -3750,6 +3904,7 @@
 				BCB6353027F6D2A300ACFDCF /* SealClass.strings in Resources */,
 				BCB635AE27F6E06500ACFDCF /* LiveRoomHeadView.xib in Resources */,
 				275FA1AD27E734C600CFEA2E /* KSImageAlert.xib in Resources */,
+				BC119270280FAF7D00A716F7 /* AccompanyCourseInfoCell.xib in Resources */,
 				2723B5C427F157B100E0B90B /* KSChatListSearchView.xib in Resources */,
 				2779359B27E324A80010E277 /* TZImagePickerController.bundle in Resources */,
 				277935C327E324A90010E277 /* SDQWMaskCustomView.xib in Resources */,
@@ -3761,6 +3916,7 @@
 				27F9032D27E87C2E00C08A19 /* KSNetworkAlert.xib in Resources */,
 				275FA24527E73E0100CFEA2E /* InstrumentDescView.xib in Resources */,
 				BC11922D280ED8E800A716F7 /* CourseNavView.xib in Resources */,
+				BC11929D280FD2EF00A716F7 /* HomeworkBottomView.xib in Resources */,
 				BCB6348127F6D29600ACFDCF /* LiveSeatApplyCell.xib in Resources */,
 				2723B62D27F157D500E0B90B /* GroupApplyMemberCell.xib in Resources */,
 				BCB6347427F6D29600ACFDCF /* BaseEmoji.plist in Resources */,
@@ -3771,6 +3927,7 @@
 				27F9033C27E87FE100C08A19 /* MineBodyView.xib in Resources */,
 				27F9032B27E87C2E00C08A19 /* NetworkBodyView.xib in Resources */,
 				2779358F27E324A80010E277 /* WMPlayer.bundle in Resources */,
+				BC11926C280FAF5900A716F7 /* AccompanyAlertView.xib in Resources */,
 				2723B66F27F15CFC00E0B90B /* AboutUsBodyView.xib in Resources */,
 				275FA23827E7356B00CFEA2E /* FirstSettingBodyView.xib in Resources */,
 				2723B63927F157D500E0B90B /* GroupMemberListCell.xib in Resources */,
@@ -3783,6 +3940,7 @@
 				BC119215280ED6A900A716F7 /* MyLiveCourseCell.xib in Resources */,
 				BC50171727FC0D8E00F8BCBC /* SubjectChooseBodyView.xib in Resources */,
 				BCB6359D27F6D2AB00ACFDCF /* tock.wav in Resources */,
+				BC11927B280FB07F00A716F7 /* AccompanyArrangeCell.xib in Resources */,
 				275E8AB327E18F8800DD3F6E /* Main.storyboard in Resources */,
 				277935B127E324A90010E277 /* mss_browseLoading@2x.png in Resources */,
 				BC11922C280ED8E800A716F7 /* LTSCalendarBottomView.xib in Resources */,
@@ -3961,6 +4119,7 @@
 				BCB6346427F6D29600ACFDCF /* KSLiveChatroomSeatApply.m in Sources */,
 				BC0212FE27FC66AA0040569F /* InstrumentMessageModel.m in Sources */,
 				BCB6359F27F6D2AB00ACFDCF /* ClassTitleView.m in Sources */,
+				BC119276280FB01100A716F7 /* AccompanyHomeworkCell.m in Sources */,
 				277935AC27E324A80010E277 /* MSSBrowseBaseViewController.m in Sources */,
 				2779352427E324A60010E277 /* KSUtilities.m in Sources */,
 				2779359627E324A80010E277 /* TZVideoCropController.m in Sources */,
@@ -4015,6 +4174,7 @@
 				2779354C27E324A70010E277 /* KSGifRefreshHeader.m in Sources */,
 				2779358727E324A80010E277 /* LLCollectionViewCell.m in Sources */,
 				2779352627E324A60010E277 /* UIAlertController+Extend.m in Sources */,
+				BC11925E280FA89A00A716F7 /* HomeworkBodyView.m in Sources */,
 				275FA1EB27E7351900CFEA2E /* KSBaseWKWebViewController.m in Sources */,
 				BCB6356727F6D2A300ACFDCF /* MemberChangeMessage.m in Sources */,
 				2779353B27E324A60010E277 /* UrlDecode.m in Sources */,
@@ -4091,6 +4251,7 @@
 				2723B62927F157D500E0B90B /* KSChatComplainController.m in Sources */,
 				2779351527E324A60010E277 /* NSArray+KSSafe.m in Sources */,
 				2723B61A27F157D500E0B90B /* KSSearchResultViewCell.m in Sources */,
+				BC11927A280FB07F00A716F7 /* AccompanyArrangeCell.m in Sources */,
 				277935B827E324A90010E277 /* FSCalendar.m in Sources */,
 				BCB6356C27F6D2A300ACFDCF /* Whiteboard.m in Sources */,
 				275FA23527E7356B00CFEA2E /* UserInfoManager.m in Sources */,
@@ -4117,6 +4278,7 @@
 				BCB6353827F6D2A300ACFDCF /* TipMessageCell.m in Sources */,
 				2779352827E324A60010E277 /* UIColor+Extend.m in Sources */,
 				2779357627E324A70010E277 /* ShoppCatView.m in Sources */,
+				BC11927F280FB10900A716F7 /* AccompanyRemarkCell.m in Sources */,
 				2779357127E324A70010E277 /* SkipTextView.m in Sources */,
 				BCB6345F27F6D29600ACFDCF /* KSLiveChatroomEnter.m in Sources */,
 				BCB6355D27F6D2A300ACFDCF /* SongDownloadMessage.m in Sources */,
@@ -4137,6 +4299,7 @@
 				2779357727E324A70010E277 /* GRScanManager.m in Sources */,
 				277935D527E324A90010E277 /* ALCalendarManager.m in Sources */,
 				BC02130127FC6ADD0040569F /* UIView+SubViewExtension.m in Sources */,
+				BC11924E280EDD5500A716F7 /* HomeworkListViewController.m in Sources */,
 				2779351927E324A60010E277 /* NSMutableString+KSSafe.m in Sources */,
 				2723B5BC27F157B100E0B90B /* GroupCreateView.m in Sources */,
 				BCB6346927F6D29600ACFDCF /* KSLiveChatroomSeatResponse.m in Sources */,
@@ -4161,6 +4324,7 @@
 				2779356027E324A70010E277 /* KSRecordStatusView.m in Sources */,
 				2723B62B27F157D500E0B90B /* ApplyMemberModel.m in Sources */,
 				2779354D27E324A70010E277 /* KSGifRefreshFooter.m in Sources */,
+				BC119288280FB3B100A716F7 /* KSStarView.m in Sources */,
 				275FA22F27E7356B00CFEA2E /* ShopMallViewController.m in Sources */,
 				BCB6347227F6D29600ACFDCF /* KSChatInputView.m in Sources */,
 				275E8AAA27E18F8800DD3F6E /* AppDelegate.m in Sources */,
@@ -4173,6 +4337,7 @@
 				2779358B27E324A80010E277 /* KLTNavigationController.m in Sources */,
 				27F9033127E87C2E00C08A19 /* DeviceCheckView.m in Sources */,
 				BCB6359527F6D2AB00ACFDCF /* OnlineClassManager.m in Sources */,
+				BC119263280FA90100A716F7 /* HomeworkDetailModel.m in Sources */,
 				BCB6357127F6D2A300ACFDCF /* RTCService.m in Sources */,
 				2723B62427F157D500E0B90B /* NoticeEditBodyView.m in Sources */,
 				BCB6354327F6D2A300ACFDCF /* RecentSharedWhiteboardCell.m in Sources */,
@@ -4188,6 +4353,7 @@
 				277935C127E324A90010E277 /* FSCalendarAppearance.m in Sources */,
 				275E8ABB27E18F8B00DD3F6E /* main.m in Sources */,
 				2779359F27E324A80010E277 /* TZPhotoPreviewCell.m in Sources */,
+				BC11928D280FB44300A716F7 /* HomeworkVideoView.m in Sources */,
 				277935A227E324A80010E277 /* TZLocationManager.m in Sources */,
 				2723B62827F157D500E0B90B /* KSSelectConversationViewController.m in Sources */,
 				275FA1E827E7351900CFEA2E /* CustomNavViewController.m in Sources */,
@@ -4201,13 +4367,16 @@
 				277935B227E324A90010E277 /* UIView+MSSLayout.m in Sources */,
 				275FA1E427E7351900CFEA2E /* KSWebNavView.m in Sources */,
 				2779356D27E324A70010E277 /* StoreShopCaterview.m in Sources */,
+				BC119267280FA92700A716F7 /* HomeworkDetailViewController.m in Sources */,
 				BCB6346127F6D29600ACFDCF /* KSChatroomMessageCenter.m in Sources */,
+				BC11925B280FA85300A716F7 /* HomeworkSortView.m in Sources */,
 				277935D327E324A90010E277 /* ALCalendarPicker.m in Sources */,
 				BCB6359427F6D2AB00ACFDCF /* NewClassRoomViewController.m in Sources */,
 				BCB6356027F6D2A300ACFDCF /* WhiteboardMessage.m in Sources */,
 				2779354F27E324A70010E277 /* VoLRUManager.m in Sources */,
 				2779356727E324A70010E277 /* UIColor+Hex.m in Sources */,
 				BCB6345E27F6D29600ACFDCF /* KSLiveChatroomLeave.m in Sources */,
+				BC11929B280FD2E800A716F7 /* HomeworkBottomView.m in Sources */,
 				275FA1E727E7351900CFEA2E /* KSWebSocketManager.m in Sources */,
 				277935AE27E324A80010E277 /* MSSBrowseRemindView.m in Sources */,
 				2779356A27E324A70010E277 /* YKNodeModel.m in Sources */,
@@ -4222,6 +4391,7 @@
 				2723B68227F15D3D00E0B90B /* ModifyPhoneChangeController.m in Sources */,
 				277935C827E324A90010E277 /* TADotView.m in Sources */,
 				BC1191FF280ED64E00A716F7 /* MyCourseViewController.m in Sources */,
+				BC119298280FBCB400A716F7 /* UIView+ExtensionForDotLine.m in Sources */,
 				BCB635A927F6D93300ACFDCF /* KSChatVideoView.m in Sources */,
 				2779353027E324A60010E277 /* NSDate+Extension.m in Sources */,
 				BCB6356627F6D2A300ACFDCF /* DeviceMessage.m in Sources */,
@@ -4239,6 +4409,7 @@
 				275FA23627E7356B00CFEA2E /* LoginBodyView.m in Sources */,
 				2779355A27E324A70010E277 /* QCCountdownButton.m in Sources */,
 				275FA1E127E7351900CFEA2E /* KSTabBarViewController.m in Sources */,
+				BC11926B280FAF5900A716F7 /* AccompanyAlertView.m in Sources */,
 				277935BB27E324A90010E277 /* FSCalendarSeparatorDecorationView.m in Sources */,
 				275FA1DF27E7351900CFEA2E /* RCConnectionManager.m in Sources */,
 				275FA22B27E7356B00CFEA2E /* HomeViewController.m in Sources */,
@@ -4247,6 +4418,7 @@
 				2779355227E324A70010E277 /* VoMemoryCache.m in Sources */,
 				2779352A27E324A60010E277 /* UIView+Dealloc.m in Sources */,
 				2779352D27E324A60010E277 /* NSString+CZHSizeExtension.m in Sources */,
+				BC119259280FA85300A716F7 /* HomeworkListCell.m in Sources */,
 				2779353827E324A60010E277 /* UIView+KSExtension.m in Sources */,
 				2723B5CD27F157BE00E0B90B /* GroupListModel.m in Sources */,
 				2779354B27E324A60010E277 /* KSVideoEditor.m in Sources */,
@@ -4319,6 +4491,7 @@
 				2779352927E324A60010E277 /* zhPopupController.m in Sources */,
 				2779359527E324A80010E277 /* TZVideoEditedPreviewController.m in Sources */,
 				2723B63127F157D500E0B90B /* GroupSettingBodyView.m in Sources */,
+				BC119290280FB46100A716F7 /* KSVideoHelper.m in Sources */,
 				BCB6354827F6D2A300ACFDCF /* PersonListCell.m in Sources */,
 				BCB6354A27F6D2A300ACFDCF /* ToolPanelView.m in Sources */,
 				2779358327E324A80010E277 /* LLPhotoBrowser.m in Sources */,
@@ -4333,8 +4506,10 @@
 				2723B5C127F157B100E0B90B /* ContractListCell.m in Sources */,
 				275FA1E527E7351900CFEA2E /* KSAccompanyWebViewController.m in Sources */,
 				BC11923A280ED98E00A716F7 /* AccompanyCourseCell.m in Sources */,
+				BC119264280FA90100A716F7 /* HomeworkListModel.m in Sources */,
 				2779354A27E324A60010E277 /* UIImage+Resize.m in Sources */,
 				2723B5A327F1578300E0B90B /* KSChatListViewController.m in Sources */,
+				BC119271280FAF7D00A716F7 /* AccompanyCourseInfoCell.m in Sources */,
 				2723B68427F15D3D00E0B90B /* AddressViewController.m in Sources */,
 				2779357527E324A70010E277 /* LifeButton.m in Sources */,
 				27F9032C27E87C2E00C08A19 /* KSNetworkAlert.m in Sources */,
@@ -4344,6 +4519,7 @@
 				2723B5A427F1578300E0B90B /* KSChatConversationViewController.m in Sources */,
 				2723B62627F157D500E0B90B /* GroupApplyViewController.m in Sources */,
 				277935C427E324A90010E277 /* SDCycleScrollView.m in Sources */,
+				BC119293280FBC1100A716F7 /* HomeworkAddView.m in Sources */,
 				2723B61C27F157D500E0B90B /* KSRCSearchBar.m in Sources */,
 				277935C627E324A90010E277 /* SDQWMaskCustomModel.m in Sources */,
 				BCB6353C27F6D2A300ACFDCF /* MessageHelper.m in Sources */,

BIN
KulexiuForStudent/KulexiuForStudent.xcworkspace/xcuserdata/wangzhi.xcuserdatad/UserInterfaceState.xcuserstate


+ 6 - 22
KulexiuForStudent/KulexiuForStudent.xcworkspace/xcuserdata/wangzhi.xcuserdatad/xcdebugger/Breakpoints_v2.xcbkptlist

@@ -55,32 +55,16 @@
       <BreakpointProxy
          BreakpointExtensionID = "Xcode.Breakpoint.FileBreakpoint">
          <BreakpointContent
-            uuid = "717EAF05-8918-413E-9C75-56859D0E716D"
-            shouldBeEnabled = "Yes"
-            ignoreCount = "0"
-            continueAfterRunningActions = "No"
-            filePath = "KulexiuForStudent/Module/Course/Controller/CourseViewController.m"
-            startingColumnNumber = "9223372036854775807"
-            endingColumnNumber = "9223372036854775807"
-            startingLineNumber = "290"
-            endingLineNumber = "290"
-            landmarkName = "-loadMonthCourse:"
-            landmarkType = "7">
-         </BreakpointContent>
-      </BreakpointProxy>
-      <BreakpointProxy
-         BreakpointExtensionID = "Xcode.Breakpoint.FileBreakpoint">
-         <BreakpointContent
-            uuid = "AC09EF7E-D41B-4CB1-8763-5BA5699C3941"
-            shouldBeEnabled = "Yes"
+            uuid = "A811E03D-935E-4812-9BA4-F901FD668906"
+            shouldBeEnabled = "No"
             ignoreCount = "0"
             continueAfterRunningActions = "No"
-            filePath = "KulexiuForStudent/Module/Course/Controller/CourseViewController.m"
+            filePath = "KulexiuForStudent/Module/Mine/Homework/View/HomeworkBodyView.m"
             startingColumnNumber = "9223372036854775807"
             endingColumnNumber = "9223372036854775807"
-            startingLineNumber = "304"
-            endingLineNumber = "304"
-            landmarkName = "-loadMonthCourse:"
+            startingLineNumber = "112"
+            endingLineNumber = "112"
+            landmarkName = "-requestData"
             landmarkType = "7">
          </BreakpointContent>
       </BreakpointProxy>

+ 22 - 0
KulexiuForStudent/KulexiuForStudent/Assets.xcassets/Course/image_upload.imageset/Contents.json

@@ -0,0 +1,22 @@
+{
+  "images" : [
+    {
+      "idiom" : "universal",
+      "scale" : "1x"
+    },
+    {
+      "filename" : "image_upload@2x.png",
+      "idiom" : "universal",
+      "scale" : "2x"
+    },
+    {
+      "filename" : "image_upload@3x.png",
+      "idiom" : "universal",
+      "scale" : "3x"
+    }
+  ],
+  "info" : {
+    "author" : "xcode",
+    "version" : 1
+  }
+}

BIN
KulexiuForStudent/KulexiuForStudent/Assets.xcassets/Course/image_upload.imageset/image_upload@2x.png


BIN
KulexiuForStudent/KulexiuForStudent/Assets.xcassets/Course/image_upload.imageset/image_upload@3x.png


+ 22 - 0
KulexiuForStudent/KulexiuForStudent/Assets.xcassets/Course/sort_down.imageset/Contents.json

@@ -0,0 +1,22 @@
+{
+  "images" : [
+    {
+      "idiom" : "universal",
+      "scale" : "1x"
+    },
+    {
+      "filename" : "sort_down@2x.png",
+      "idiom" : "universal",
+      "scale" : "2x"
+    },
+    {
+      "filename" : "sort_down@3x.png",
+      "idiom" : "universal",
+      "scale" : "3x"
+    }
+  ],
+  "info" : {
+    "author" : "xcode",
+    "version" : 1
+  }
+}

BIN
KulexiuForStudent/KulexiuForStudent/Assets.xcassets/Course/sort_down.imageset/sort_down@2x.png


BIN
KulexiuForStudent/KulexiuForStudent/Assets.xcassets/Course/sort_down.imageset/sort_down@3x.png


+ 22 - 0
KulexiuForStudent/KulexiuForStudent/Assets.xcassets/Course/sort_up.imageset/Contents.json

@@ -0,0 +1,22 @@
+{
+  "images" : [
+    {
+      "idiom" : "universal",
+      "scale" : "1x"
+    },
+    {
+      "filename" : "sort_up@2x.png",
+      "idiom" : "universal",
+      "scale" : "2x"
+    },
+    {
+      "filename" : "sort_up@3x.png",
+      "idiom" : "universal",
+      "scale" : "3x"
+    }
+  ],
+  "info" : {
+    "author" : "xcode",
+    "version" : 1
+  }
+}

BIN
KulexiuForStudent/KulexiuForStudent/Assets.xcassets/Course/sort_up.imageset/sort_up@2x.png


BIN
KulexiuForStudent/KulexiuForStudent/Assets.xcassets/Course/sort_up.imageset/sort_up@3x.png


+ 22 - 0
KulexiuForStudent/KulexiuForStudent/Assets.xcassets/Mine/star_grey.imageset/Contents.json

@@ -0,0 +1,22 @@
+{
+  "images" : [
+    {
+      "idiom" : "universal",
+      "scale" : "1x"
+    },
+    {
+      "filename" : "star_grey@2x.png",
+      "idiom" : "universal",
+      "scale" : "2x"
+    },
+    {
+      "filename" : "star_grey@3x.png",
+      "idiom" : "universal",
+      "scale" : "3x"
+    }
+  ],
+  "info" : {
+    "author" : "xcode",
+    "version" : 1
+  }
+}

BIN
KulexiuForStudent/KulexiuForStudent/Assets.xcassets/Mine/star_grey.imageset/star_grey@2x.png


BIN
KulexiuForStudent/KulexiuForStudent/Assets.xcassets/Mine/star_grey.imageset/star_grey@3x.png


+ 22 - 0
KulexiuForStudent/KulexiuForStudent/Assets.xcassets/Mine/star_light.imageset/Contents.json

@@ -0,0 +1,22 @@
+{
+  "images" : [
+    {
+      "idiom" : "universal",
+      "scale" : "1x"
+    },
+    {
+      "filename" : "star_light@2x.png",
+      "idiom" : "universal",
+      "scale" : "2x"
+    },
+    {
+      "filename" : "star_light@3x.png",
+      "idiom" : "universal",
+      "scale" : "3x"
+    }
+  ],
+  "info" : {
+    "author" : "xcode",
+    "version" : 1
+  }
+}

BIN
KulexiuForStudent/KulexiuForStudent/Assets.xcassets/Mine/star_light.imageset/star_light@2x.png


BIN
KulexiuForStudent/KulexiuForStudent/Assets.xcassets/Mine/star_light.imageset/star_light@3x.png


+ 22 - 0
KulexiuForStudent/KulexiuForStudent/Assets.xcassets/cancle_button.imageset/Contents.json

@@ -0,0 +1,22 @@
+{
+  "images" : [
+    {
+      "idiom" : "universal",
+      "scale" : "1x"
+    },
+    {
+      "filename" : "cancle_button@2x.png",
+      "idiom" : "universal",
+      "scale" : "2x"
+    },
+    {
+      "filename" : "cancle_button@3x.png",
+      "idiom" : "universal",
+      "scale" : "3x"
+    }
+  ],
+  "info" : {
+    "author" : "xcode",
+    "version" : 1
+  }
+}

BIN
KulexiuForStudent/KulexiuForStudent/Assets.xcassets/cancle_button.imageset/cancle_button@2x.png


BIN
KulexiuForStudent/KulexiuForStudent/Assets.xcassets/cancle_button.imageset/cancle_button@3x.png


+ 22 - 0
KulexiuForStudent/KulexiuForStudent/Assets.xcassets/playVideo_image.imageset/Contents.json

@@ -0,0 +1,22 @@
+{
+  "images" : [
+    {
+      "idiom" : "universal",
+      "scale" : "1x"
+    },
+    {
+      "filename" : "playVideo_image@2x.png",
+      "idiom" : "universal",
+      "scale" : "2x"
+    },
+    {
+      "filename" : "playVideo_image@3x.png",
+      "idiom" : "universal",
+      "scale" : "3x"
+    }
+  ],
+  "info" : {
+    "author" : "xcode",
+    "version" : 1
+  }
+}

BIN
KulexiuForStudent/KulexiuForStudent/Assets.xcassets/playVideo_image.imageset/playVideo_image@2x.png


BIN
KulexiuForStudent/KulexiuForStudent/Assets.xcassets/playVideo_image.imageset/playVideo_image@3x.png


+ 22 - 0
KulexiuForStudent/KulexiuForStudent/Assets.xcassets/video_delete.imageset/Contents.json

@@ -0,0 +1,22 @@
+{
+  "images" : [
+    {
+      "idiom" : "universal",
+      "scale" : "1x"
+    },
+    {
+      "filename" : "video_delete@2x.png",
+      "idiom" : "universal",
+      "scale" : "2x"
+    },
+    {
+      "filename" : "video_delete@3x.png",
+      "idiom" : "universal",
+      "scale" : "3x"
+    }
+  ],
+  "info" : {
+    "author" : "xcode",
+    "version" : 1
+  }
+}

BIN
KulexiuForStudent/KulexiuForStudent/Assets.xcassets/video_delete.imageset/video_delete@2x.png


BIN
KulexiuForStudent/KulexiuForStudent/Assets.xcassets/video_delete.imageset/video_delete@3x.png


BIN
KulexiuForStudent/KulexiuForStudent/Assets.xcassets/video_placeholder.imageset/video_placeholder@2x.png


BIN
KulexiuForStudent/KulexiuForStudent/Assets.xcassets/video_placeholder.imageset/video_placeholder@3x.png


+ 32 - 0
KulexiuForStudent/KulexiuForStudent/Common/Base/KSNetworkingManager.h

@@ -362,6 +362,38 @@ NS_ASSUME_NONNULL_BEGIN
 /// @param faliure 失败
 + (void)queryCourseForDay:(NSString *)post classDate:(NSString *)classDate success:(void(^)(NSDictionary *dic))success faliure:(void(^)(NSError *error))faliure;
 
+#pragma mark ----- 课后作业
+// /api-student/homework/list
+
+/// 课后作业列表
+/// @param post post
+/// @param date 年月 格式:yyyy-MM
+/// @param submit 作业提交状态 0:否,1:是
+/// @param page 页数
+/// @param rows 条数
+/// @param success 成功
+/// @param faliure 失败
++ (void)homeworkListRequest:(NSString *)post date:(NSString *)date submit:(NSInteger)submit page:(NSInteger)page rows:(NSInteger)rows success:(void(^)(NSDictionary *dic))success faliure:(void(^)(NSError *error))faliure;
+
+// /api-student/homework/detail/{courseId}
+
+/// 陪练课课后作业信息详情
+/// @param get get
+/// @param courseId 课程信息
+/// @param success 成功
+/// @param faliure 失败
++ (void)homeworkDetailRequest:(NSString *)get courseId:(NSString *)courseId success:(void(^)(NSDictionary *dic))success faliure:(void(^)(NSError *error))faliure;
+
+// /api-student/homework/submit
+
+/// 作业提交
+/// @param post post
+/// @param courseScheduleId 作业提交
+/// @param attachment 作业内容
+/// @param success 成功
+/// @param faliure 失败
++ (void)homeSubmitAction:(NSString *)post courseScheduleId:(NSString *)courseScheduleId attachment:(NSString *)attachment success:(void(^)(NSDictionary *dic))success faliure:(void(^)(NSError *error))faliure;
+
 @end
 
 NS_ASSUME_NONNULL_END

+ 52 - 0
KulexiuForStudent/KulexiuForStudent/Common/Base/KSNetworkingManager.m

@@ -817,4 +817,56 @@
     [parm setValue:classDate forKey:@"classDate"];
     [self request:post andWithUrl:url and:parm success:success faliure:faliure];
 }
+
+#pragma mark ----- 课后作业
+// /api-student/homework/list
+
+/// 课后作业列表
+/// @param post post
+/// @param date 年月 格式:yyyy-MM
+/// @param submit 作业提交状态 0:否,1:是
+/// @param page 页数
+/// @param rows 条数
+/// @param success 成功
+/// @param faliure 失败
++ (void)homeworkListRequest:(NSString *)post date:(NSString *)date submit:(NSInteger)submit page:(NSInteger)page rows:(NSInteger)rows success:(void(^)(NSDictionary *dic))success faliure:(void(^)(NSError *error))faliure {
+    [self configRequestMethodJSON];
+    NSString *url = [NSString stringWithFormat:@"%@%@", hostURL, @"/api-student/homework/list"];
+    NSMutableDictionary *parm = [NSMutableDictionary dictionary];
+    [parm setValue:date forKey:@"date"];
+    [parm setValue:@(submit) forKey:@"submit"];
+    [parm setValue:@(page) forKey:@"page"];
+    [parm setValue:@(rows) forKey:@"rows"];
+    [self request:post andWithUrl:url and:parm success:success faliure:faliure];
+}
+
+// /api-student/homework/detail/{courseId}
+
+/// 陪练课课后作业信息详情
+/// @param get get
+/// @param courseId 课程信息
+/// @param success 成功
+/// @param faliure 失败
++ (void)homeworkDetailRequest:(NSString *)get courseId:(NSString *)courseId success:(void(^)(NSDictionary *dic))success faliure:(void(^)(NSError *error))faliure {
+    NSString *url = [NSString stringWithFormat:@"%@%@/%@",hostURL, @"/api-student/homework/detail",courseId];
+    [self request:get andWithUrl:url and:nil success:success faliure:faliure];
+}
+
+// /api-student/homework/submit
+
+/// 作业提交
+/// @param post post
+/// @param courseScheduleId 作业提交
+/// @param attachment 作业内容
+/// @param success 成功
+/// @param faliure 失败
++ (void)homeSubmitAction:(NSString *)post courseScheduleId:(NSString *)courseScheduleId attachment:(NSString *)attachment success:(void(^)(NSDictionary *dic))success faliure:(void(^)(NSError *error))faliure {
+    [self configRequestMethodJSON];
+    NSString *url = [NSString stringWithFormat:@"%@%@", hostURL, @"/api-student/homework/submit"];
+    NSMutableDictionary *parm = [NSMutableDictionary dictionary];
+    [parm setValue:courseScheduleId forKey:@"courseScheduleId"];
+    [parm setValue:attachment forKey:@"submit"];
+    [self request:post andWithUrl:url and:parm success:success faliure:faliure];
+
+}
 @end

+ 18 - 0
KulexiuForStudent/KulexiuForStudent/Common/Tools/KSVideoHelper.h

@@ -0,0 +1,18 @@
+//
+//  KSVideoHelper.h
+//  KulexiuForTeacher
+//
+//  Created by 王智 on 2022/4/12.
+//
+
+#import <Foundation/Foundation.h>
+
+NS_ASSUME_NONNULL_BEGIN
+
+@interface KSVideoHelper : NSObject
+
++ (void)getVideoPreviewImageUrl:(NSString *)videoUrl forImageView:(UIImageView *)imageView placeholder:(UIImage *)placeHolder;
+
+@end
+
+NS_ASSUME_NONNULL_END

+ 68 - 0
KulexiuForStudent/KulexiuForStudent/Common/Tools/KSVideoHelper.m

@@ -0,0 +1,68 @@
+//
+//  KSVideoHelper.m
+//  KulexiuForTeacher
+//
+//  Created by 王智 on 2022/4/12.
+//
+
+#import "KSVideoHelper.h"
+#import <AVFoundation/AVAsset.h>
+#import <AVFoundation/AVAssetImageGenerator.h>
+#import <AVFoundation/AVTime.h>
+#import <SDWebImage/SDImageCache.h>
+
+@implementation KSVideoHelper
+
++ (void)getVideoPreviewImageUrl:(NSString *)videoUrl forImageView:(UIImageView *)imageView placeholder:(UIImage *)placeHolder {
+
+    [[SDImageCache sharedImageCache] queryCacheOperationForKey:videoUrl done:^(UIImage * _Nullable image, NSData * _Nullable data, SDImageCacheType cacheType) {
+        //是否有缓存图片
+        if(image){
+            imageView.image = image;
+        }else{
+            //获取视频第一帧
+            [self getVideoFirstViewImage:videoUrl forImageView:imageView placeHolderImage:placeHolder];
+        }
+    }];
+}
+
+// 获取视频第一帧
++ (void)getVideoFirstViewImage:(NSString *)videoURL forImageView:(UIImageView *)imageView placeHolderImage:(UIImage *)placeHolder {
+   
+    NSString *url = videoURL;
+    __block UIImage *videoImage;
+    dispatch_async(dispatch_get_global_queue(0, 0), ^{
+        AVURLAsset *asset = [[AVURLAsset alloc] initWithURL:[NSURL URLWithString:url] options:nil];
+        NSParameterAssert(asset);
+        AVAssetImageGenerator *assetImageGenerator =[[AVAssetImageGenerator alloc] initWithAsset:asset];
+        assetImageGenerator.appliesPreferredTrackTransform = YES;
+        assetImageGenerator.apertureMode =AVAssetImageGeneratorApertureModeEncodedPixels;
+        CGImageRef thumbnailImageRef = NULL;
+        NSError *thumbnailImageGenerationError = nil;
+        thumbnailImageRef = [assetImageGenerator copyCGImageAtTime:CMTimeMake(0, 60)actualTime:NULL error:&thumbnailImageGenerationError];
+        if(!thumbnailImageRef)
+        NSLog(@"thumbnailImageGenerationError %@",thumbnailImageGenerationError);
+        videoImage = thumbnailImageRef ? [[UIImage alloc]initWithCGImage:thumbnailImageRef]: nil;
+        
+        dispatch_async(dispatch_get_main_queue(), ^{
+            //主线程更新UI
+            if(videoImage){
+                imageView.image = videoImage;
+                //缓存图片
+                [[SDImageCache sharedImageCache] storeImage:videoImage forKey:videoURL toDisk:NO completion:^{
+                    
+                }];
+                
+            }else{
+                //如果不是视频就设置图片
+                [imageView sd_setImageWithURL:[NSURL URLWithString:videoURL] placeholderImage:placeHolder];
+            }
+        });
+          
+    });
+
+}
+
+@end
+
+

+ 25 - 0
KulexiuForStudent/KulexiuForStudent/Common/Tools/UIView+ExtensionForDotLine.h

@@ -0,0 +1,25 @@
+//
+//  UIView+ExtensionForDotLine.h
+//  KulexiuForTeacher
+//
+//  Created by 王智 on 2022/4/11.
+//
+
+#import <UIKit/UIKit.h>
+
+NS_ASSUME_NONNULL_BEGIN
+
+@interface UIView (ExtensionForDotLine)
+
+/// 画外框虚线
+/// @param width 虚线宽带
+/// @param length 一条虚线的长度
+/// @param space 虚线艰巨
+/// @param cornerRadius 边框圆角
+/// @param lineColor 线条颜色
+- (void)drawBoardDottedLine:(double)width length:(double)length space:(double)space cornerRadius:(double)cornerRadius lineColor:(UIColor*)lineColor;
+
+
+@end
+
+NS_ASSUME_NONNULL_END

+ 41 - 0
KulexiuForStudent/KulexiuForStudent/Common/Tools/UIView+ExtensionForDotLine.m

@@ -0,0 +1,41 @@
+//
+//  UIView+ExtensionForDotLine.m
+//  KulexiuForTeacher
+//
+//  Created by 王智 on 2022/4/11.
+//
+
+#import "UIView+ExtensionForDotLine.h"
+
+@implementation UIView (ExtensionForDotLine)
+
+/// 画外框虚线
+/// @param width 虚线宽带
+/// @param length 一条虚线的长度
+/// @param space 虚线艰巨
+/// @param cornerRadius 边框圆角
+/// @param lineColor 线条颜色
+- (void)drawBoardDottedLine:(double)width length:(double)length space:(double)space cornerRadius:(double)cornerRadius lineColor:(UIColor*)lineColor {
+    self.layer.cornerRadius = cornerRadius;
+    CAShapeLayer *borderLayer = [CAShapeLayer layer];
+    borderLayer.bounds = self.bounds;
+    borderLayer.position = CGPointMake(CGRectGetMidX(self.bounds), CGRectGetMidY(self.bounds));
+    borderLayer.path = [UIBezierPath bezierPathWithRoundedRect:borderLayer.bounds cornerRadius:cornerRadius].CGPath;
+    borderLayer.lineWidth = width;
+    borderLayer.lineCap = @"square";
+    //虚线边框---小边框的长度
+    borderLayer.lineDashPattern = @[@(length),@(space)];
+    //实线边框
+    borderLayer.fillColor = [UIColor clearColor].CGColor;
+    borderLayer.strokeColor = lineColor.CGColor;
+//    [self removeAllSublayers];
+    [self.layer addSublayer :borderLayer];
+}
+
+- (void)removeAllSublayers {
+    for (CALayer *layer in self.layer.sublayers) {
+        [layer removeFromSuperlayer];
+    }
+}
+
+@end

+ 19 - 0
KulexiuForStudent/KulexiuForStudent/Module/Course/AccompanyCourse/View/AccompanyArrangeCell.h

@@ -0,0 +1,19 @@
+//
+//  AccompanyArrangeCell.h
+//  KulexiuForTeacher
+//
+//  Created by 王智 on 2022/4/6.
+//
+
+#import <UIKit/UIKit.h>
+
+
+NS_ASSUME_NONNULL_BEGIN
+
+@interface AccompanyArrangeCell : UITableViewCell
+
+- (void)configWithHomeworkContent:(NSString *)content hasArrangeHomework:(BOOL)hasArrange;
+
+@end
+
+NS_ASSUME_NONNULL_END

+ 55 - 0
KulexiuForStudent/KulexiuForStudent/Module/Course/AccompanyCourse/View/AccompanyArrangeCell.m

@@ -0,0 +1,55 @@
+//
+//  AccompanyArrangeCell.m
+//  KulexiuForTeacher
+//
+//  Created by 王智 on 2022/4/6.
+//
+
+#import "AccompanyArrangeCell.h"
+
+@interface AccompanyArrangeCell ()
+
+@property (weak, nonatomic) IBOutlet UILabel *contentLabel;
+
+@property (weak, nonatomic) IBOutlet UIView *emptyView;
+
+
+@end
+
+@implementation AccompanyArrangeCell
+
+- (void)awakeFromNib {
+    [super awakeFromNib];
+    // Initialization code
+    self.selectionStyle = UITableViewCellSelectionStyleNone;
+}
+
+- (void)configWithHomeworkContent:(NSString *)content hasArrangeHomework:(BOOL)hasArrange {
+
+    if (hasArrange) {
+        self.emptyView.hidden = YES;
+        if (![NSString isEmptyString:content]) {
+            NSMutableParagraphStyle *paragraphStyle = [[NSMutableParagraphStyle alloc] init];
+            [paragraphStyle setLineSpacing:4];//调整行间距
+            NSMutableAttributedString *attr = [[NSMutableAttributedString alloc] initWithString:content attributes:@{NSParagraphStyleAttributeName:paragraphStyle,NSFontAttributeName:[UIFont systemFontOfSize:13.0f],NSForegroundColorAttributeName:HexRGB(0x333333)}];
+            self.contentLabel.attributedText = attr;
+        }
+        else {
+            self.contentLabel.text = @"";
+        }
+    }
+    else {
+        self.emptyView.hidden = NO;
+        self.contentLabel.text = @"";
+    }
+}
+
+
+
+- (void)setSelected:(BOOL)selected animated:(BOOL)animated {
+    [super setSelected:selected animated:animated];
+
+    // Configure the view for the selected state
+}
+
+@end

+ 139 - 0
KulexiuForStudent/KulexiuForStudent/Module/Course/AccompanyCourse/View/AccompanyArrangeCell.xib

@@ -0,0 +1,139 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<document type="com.apple.InterfaceBuilder3.CocoaTouch.XIB" version="3.0" toolsVersion="20037" targetRuntime="iOS.CocoaTouch" propertyAccessControl="none" useAutolayout="YES" useTraitCollections="YES" useSafeAreas="YES" colorMatched="YES">
+    <device id="retina6_1" orientation="portrait" appearance="light"/>
+    <dependencies>
+        <deployment identifier="iOS"/>
+        <plugIn identifier="com.apple.InterfaceBuilder.IBCocoaTouchPlugin" version="20020"/>
+        <capability name="Safe area layout guides" minToolsVersion="9.0"/>
+        <capability name="System colors in document resources" minToolsVersion="11.0"/>
+        <capability name="documents saved in the Xcode 8 format" minToolsVersion="8.0"/>
+    </dependencies>
+    <objects>
+        <placeholder placeholderIdentifier="IBFilesOwner" id="-1" userLabel="File's Owner"/>
+        <placeholder placeholderIdentifier="IBFirstResponder" id="-2" customClass="UIResponder"/>
+        <tableViewCell contentMode="scaleToFill" selectionStyle="default" indentationWidth="10" rowHeight="215" id="KGk-i7-Jjw" customClass="AccompanyArrangeCell">
+            <rect key="frame" x="0.0" y="0.0" width="375" height="215"/>
+            <autoresizingMask key="autoresizingMask" flexibleMaxX="YES" flexibleMaxY="YES"/>
+            <tableViewCellContentView key="contentView" opaque="NO" clipsSubviews="YES" multipleTouchEnabled="YES" contentMode="center" tableViewCell="KGk-i7-Jjw" id="H2p-sc-9uM">
+                <rect key="frame" x="0.0" y="0.0" width="375" height="215"/>
+                <autoresizingMask key="autoresizingMask"/>
+                <subviews>
+                    <view contentMode="scaleToFill" translatesAutoresizingMaskIntoConstraints="NO" id="gA1-Yl-rTq">
+                        <rect key="frame" x="14" y="0.0" width="347" height="203"/>
+                        <subviews>
+                            <imageView clipsSubviews="YES" userInteractionEnabled="NO" contentMode="scaleAspectFit" horizontalHuggingPriority="251" verticalHuggingPriority="251" image="accell_left" translatesAutoresizingMaskIntoConstraints="NO" id="zvH-rj-MgD">
+                                <rect key="frame" x="11" y="13" width="4" height="18"/>
+                            </imageView>
+                            <label opaque="NO" userInteractionEnabled="NO" contentMode="left" horizontalHuggingPriority="251" verticalHuggingPriority="251" text="课后作业" textAlignment="natural" lineBreakMode="tailTruncation" baselineAdjustment="alignBaselines" adjustsFontSizeToFit="NO" translatesAutoresizingMaskIntoConstraints="NO" id="qyk-Yf-gN8">
+                                <rect key="frame" x="20" y="12" width="58" height="20"/>
+                                <constraints>
+                                    <constraint firstAttribute="height" constant="20" id="D64-2R-Ow8"/>
+                                </constraints>
+                                <fontDescription key="fontDescription" type="system" weight="medium" pointSize="14"/>
+                                <color key="textColor" red="0.20000000000000001" green="0.20000000000000001" blue="0.20000000000000001" alpha="1" colorSpace="calibratedRGB"/>
+                                <nil key="highlightedColor"/>
+                            </label>
+                            <view contentMode="scaleToFill" translatesAutoresizingMaskIntoConstraints="NO" id="vf1-Yo-J7O">
+                                <rect key="frame" x="11" y="40" width="327" height="153"/>
+                                <subviews>
+                                    <label opaque="NO" userInteractionEnabled="NO" contentMode="left" horizontalHuggingPriority="251" verticalHuggingPriority="251" text="" textAlignment="natural" lineBreakMode="tailTruncation" numberOfLines="0" baselineAdjustment="alignBaselines" adjustsFontSizeToFit="NO" translatesAutoresizingMaskIntoConstraints="NO" id="H1L-ao-uRw">
+                                        <rect key="frame" x="9" y="11" width="312" height="0.0"/>
+                                        <fontDescription key="fontDescription" type="system" pointSize="13"/>
+                                        <color key="textColor" red="0.20000000000000001" green="0.20000000000000001" blue="0.20000000000000001" alpha="1" colorSpace="calibratedRGB"/>
+                                        <nil key="highlightedColor"/>
+                                    </label>
+                                    <view contentMode="scaleToFill" translatesAutoresizingMaskIntoConstraints="NO" id="dU1-HN-KyM">
+                                        <rect key="frame" x="0.0" y="0.0" width="327" height="153"/>
+                                        <subviews>
+                                            <imageView clipsSubviews="YES" userInteractionEnabled="NO" contentMode="scaleAspectFit" horizontalHuggingPriority="251" verticalHuggingPriority="251" image="homework_placeholder" translatesAutoresizingMaskIntoConstraints="NO" id="XfA-4s-phL">
+                                                <rect key="frame" x="33" y="37.5" width="79" height="78"/>
+                                                <constraints>
+                                                    <constraint firstAttribute="width" constant="79" id="0hA-Du-KDq"/>
+                                                    <constraint firstAttribute="height" constant="78" id="UOp-9T-qAZ"/>
+                                                </constraints>
+                                            </imageView>
+                                            <label opaque="NO" userInteractionEnabled="NO" contentMode="left" horizontalHuggingPriority="251" verticalHuggingPriority="251" usesAttributedText="YES" lineBreakMode="tailTruncation" numberOfLines="2" baselineAdjustment="alignBaselines" adjustsFontSizeToFit="NO" translatesAutoresizingMaskIntoConstraints="NO" id="Fby-JO-ifq">
+                                                <rect key="frame" x="120" y="59.5" width="157" height="34.5"/>
+                                                <attributedString key="attributedText">
+                                                    <fragment content="课程结束后老师会布置作业喔~">
+                                                        <attributes>
+                                                            <color key="NSColor" red="0.59999999999999998" green="0.59999999999999998" blue="0.59999999999999998" alpha="1" colorSpace="calibratedRGB"/>
+                                                            <font key="NSFont" size="13" name="STSongti-SC-Regular"/>
+                                                            <paragraphStyle key="NSParagraphStyle" alignment="natural" lineBreakMode="wordWrapping" baseWritingDirection="natural" lineSpacing="4" tighteningFactorForTruncation="0.0"/>
+                                                        </attributes>
+                                                    </fragment>
+                                                </attributedString>
+                                                <nil key="highlightedColor"/>
+                                            </label>
+                                        </subviews>
+                                        <color key="backgroundColor" white="0.0" alpha="0.0" colorSpace="custom" customColorSpace="genericGamma22GrayColorSpace"/>
+                                        <constraints>
+                                            <constraint firstItem="Fby-JO-ifq" firstAttribute="centerY" secondItem="dU1-HN-KyM" secondAttribute="centerY" id="blg-fz-G9n"/>
+                                            <constraint firstItem="XfA-4s-phL" firstAttribute="leading" secondItem="dU1-HN-KyM" secondAttribute="leading" constant="33" id="dMf-ag-brp"/>
+                                            <constraint firstItem="Fby-JO-ifq" firstAttribute="leading" secondItem="XfA-4s-phL" secondAttribute="trailing" constant="8" id="hhO-vt-zAb"/>
+                                            <constraint firstItem="XfA-4s-phL" firstAttribute="centerY" secondItem="dU1-HN-KyM" secondAttribute="centerY" id="q6d-yu-I27"/>
+                                            <constraint firstAttribute="trailing" secondItem="Fby-JO-ifq" secondAttribute="trailing" constant="50" id="zxg-Qb-1UO"/>
+                                        </constraints>
+                                    </view>
+                                </subviews>
+                                <color key="backgroundColor" red="0.96862745100000003" green="0.97254901959999995" blue="0.97647058819999999" alpha="1" colorSpace="calibratedRGB"/>
+                                <constraints>
+                                    <constraint firstAttribute="trailing" secondItem="H1L-ao-uRw" secondAttribute="trailing" constant="6" id="0fj-KP-pN1"/>
+                                    <constraint firstItem="dU1-HN-KyM" firstAttribute="leading" secondItem="vf1-Yo-J7O" secondAttribute="leading" id="2gz-6H-k3O"/>
+                                    <constraint firstAttribute="bottom" secondItem="dU1-HN-KyM" secondAttribute="bottom" id="AiG-7u-Z5R"/>
+                                    <constraint firstAttribute="trailing" secondItem="dU1-HN-KyM" secondAttribute="trailing" id="CT7-rV-eTH"/>
+                                    <constraint firstItem="H1L-ao-uRw" firstAttribute="leading" secondItem="vf1-Yo-J7O" secondAttribute="leading" constant="9" id="Gn2-jW-Sqe"/>
+                                    <constraint firstAttribute="bottom" relation="greaterThanOrEqual" secondItem="H1L-ao-uRw" secondAttribute="bottom" constant="5" id="MId-4v-mP6"/>
+                                    <constraint firstAttribute="height" relation="greaterThanOrEqual" constant="88" id="Ohc-jd-ZIz"/>
+                                    <constraint firstItem="dU1-HN-KyM" firstAttribute="top" secondItem="vf1-Yo-J7O" secondAttribute="top" id="ReN-18-uf8"/>
+                                    <constraint firstItem="H1L-ao-uRw" firstAttribute="top" secondItem="vf1-Yo-J7O" secondAttribute="top" constant="11" id="ung-Zh-kpd"/>
+                                </constraints>
+                                <userDefinedRuntimeAttributes>
+                                    <userDefinedRuntimeAttribute type="number" keyPath="cornerRadius">
+                                        <real key="value" value="4"/>
+                                    </userDefinedRuntimeAttribute>
+                                </userDefinedRuntimeAttributes>
+                            </view>
+                        </subviews>
+                        <color key="backgroundColor" systemColor="systemBackgroundColor"/>
+                        <constraints>
+                            <constraint firstAttribute="trailing" secondItem="vf1-Yo-J7O" secondAttribute="trailing" constant="9" id="C9V-eH-geC"/>
+                            <constraint firstItem="vf1-Yo-J7O" firstAttribute="leading" secondItem="gA1-Yl-rTq" secondAttribute="leading" constant="11" id="NWC-5K-8kt"/>
+                            <constraint firstItem="zvH-rj-MgD" firstAttribute="top" secondItem="gA1-Yl-rTq" secondAttribute="top" constant="13" id="QHm-hW-lio"/>
+                            <constraint firstAttribute="bottom" secondItem="vf1-Yo-J7O" secondAttribute="bottom" constant="10" id="T6p-ud-tLL"/>
+                            <constraint firstItem="zvH-rj-MgD" firstAttribute="leading" secondItem="gA1-Yl-rTq" secondAttribute="leading" constant="11" id="ad3-xv-Xlz"/>
+                            <constraint firstItem="qyk-Yf-gN8" firstAttribute="centerY" secondItem="zvH-rj-MgD" secondAttribute="centerY" id="dYy-51-vic"/>
+                            <constraint firstItem="qyk-Yf-gN8" firstAttribute="leading" secondItem="zvH-rj-MgD" secondAttribute="trailing" constant="5" id="hFd-yY-LNW"/>
+                            <constraint firstItem="vf1-Yo-J7O" firstAttribute="top" secondItem="qyk-Yf-gN8" secondAttribute="bottom" constant="8" id="jc2-n6-O3G"/>
+                        </constraints>
+                        <userDefinedRuntimeAttributes>
+                            <userDefinedRuntimeAttribute type="number" keyPath="cornerRadius">
+                                <real key="value" value="10"/>
+                            </userDefinedRuntimeAttribute>
+                        </userDefinedRuntimeAttributes>
+                    </view>
+                </subviews>
+                <constraints>
+                    <constraint firstAttribute="bottom" secondItem="gA1-Yl-rTq" secondAttribute="bottom" constant="12" id="2aT-dT-NKd"/>
+                    <constraint firstAttribute="trailing" secondItem="gA1-Yl-rTq" secondAttribute="trailing" constant="14" id="HAH-m5-qkU"/>
+                    <constraint firstItem="gA1-Yl-rTq" firstAttribute="leading" secondItem="H2p-sc-9uM" secondAttribute="leading" constant="14" id="RNC-dm-lAm"/>
+                    <constraint firstItem="gA1-Yl-rTq" firstAttribute="top" secondItem="H2p-sc-9uM" secondAttribute="top" id="b2j-gd-T1S"/>
+                </constraints>
+            </tableViewCellContentView>
+            <viewLayoutGuide key="safeArea" id="aW0-zy-SZf"/>
+            <color key="backgroundColor" white="0.0" alpha="0.0" colorSpace="custom" customColorSpace="genericGamma22GrayColorSpace"/>
+            <connections>
+                <outlet property="contentLabel" destination="H1L-ao-uRw" id="YPY-n4-spk"/>
+                <outlet property="emptyView" destination="dU1-HN-KyM" id="Lep-x2-mcW"/>
+            </connections>
+            <point key="canvasLocation" x="207.97101449275365" y="134.93303571428569"/>
+        </tableViewCell>
+    </objects>
+    <resources>
+        <image name="accell_left" width="4" height="18"/>
+        <image name="homework_placeholder" width="79" height="78"/>
+        <systemColor name="systemBackgroundColor">
+            <color white="1" alpha="1" colorSpace="custom" customColorSpace="genericGamma22GrayColorSpace"/>
+        </systemColor>
+    </resources>
+</document>

+ 26 - 0
KulexiuForStudent/KulexiuForStudent/Module/Course/AccompanyCourse/View/AccompanyCourseInfoCell.h

@@ -0,0 +1,26 @@
+//
+//  AccompanyCourseInfoCell.h
+//  KulexiuForTeacher
+//
+//  Created by 王智 on 2022/4/13.
+//
+
+#import <UIKit/UIKit.h>
+
+NS_ASSUME_NONNULL_BEGIN
+
+typedef void(^AccompanyChatCallback)(void);
+
+@interface AccompanyCourseInfoCell : UITableViewCell
+
+@property (weak, nonatomic) IBOutlet UILabel *statusLabel;
+
+@property (nonatomic, assign) BOOL hideChatButton;
+
+- (void)configWithStartTime:(NSString *)beginTime endTime:(NSString *)endTime teacherAvatar:(NSString *)teacherAvatar teacherName:(NSString *)teacherName teacherId:(NSString *)teacherId courseSubject:(NSString *)courseSubject;
+
+- (void)chatCalkback:(AccompanyChatCallback)callback;
+
+@end
+
+NS_ASSUME_NONNULL_END

+ 85 - 0
KulexiuForStudent/KulexiuForStudent/Module/Course/AccompanyCourse/View/AccompanyCourseInfoCell.m

@@ -0,0 +1,85 @@
+//
+//  AccompanyCourseInfoCell.m
+//  KulexiuForTeacher
+//
+//  Created by 王智 on 2022/4/13.
+//
+
+#import "AccompanyCourseInfoCell.h"
+
+@interface AccompanyCourseInfoCell ()
+
+@property (weak, nonatomic) IBOutlet UILabel *courseTime;
+@property (weak, nonatomic) IBOutlet UIImageView *studentAvatar;
+@property (weak, nonatomic) IBOutlet UILabel *studentName;
+@property (weak, nonatomic) IBOutlet UILabel *studentSubject;
+
+@property (weak, nonatomic) IBOutlet UIButton *chatButton;
+
+@property (nonatomic, strong) NSString *userId;
+
+@property (nonatomic, strong) NSString *userName;
+
+@property (nonatomic, copy) AccompanyChatCallback callback;
+
+@end
+
+@implementation AccompanyCourseInfoCell
+
+- (void)awakeFromNib {
+    [super awakeFromNib];
+    // Initialization code
+    self.selectionStyle = UITableViewCellSelectionStyleNone;
+}
+
+- (void)configWithStartTime:(NSString *)beginTime endTime:(NSString *)endTime teacherAvatar:(NSString *)teacherAvatar teacherName:(NSString *)teacherName teacherId:(NSString *)teacherId courseSubject:(NSString *)courseSubject {
+    // time
+    NSDateFormatter *formatter = [NSObject getDateformatter];
+    [formatter setDateFormat:@"yyyy-MM-dd HH:mm:ss"];
+    NSDate *startDate = [formatter dateFromString:beginTime];
+    NSDate *endDate = [formatter dateFromString:endTime];
+    [formatter setDateFormat:@"yyyy/MM/dd HH:mm"];
+    NSString *lessonBegin = [formatter stringFromDate:startDate];
+    [formatter setDateFormat:@"HH:mm"];
+    NSString *lessonEnd = [formatter stringFromDate:endDate];
+    self.courseTime.text = [NSString stringWithFormat:@"%@~%@",[NSString returnNoNullStringWithString:lessonBegin],[NSString returnNoNullStringWithString:lessonEnd]];
+    
+    self.studentName.text = [NSString returnNoNullStringWithString:teacherName];
+    [self.studentAvatar sd_setImageWithURL:[NSURL URLWithString:teacherAvatar] placeholderImage:[UIImage imageNamed:USERDEFAULT_LOGO]];
+    self.studentSubject.text = [NSString returnNoNullStringWithString:courseSubject];
+
+    self.userId = teacherId;
+    self.userName = teacherName;
+}
+
+- (void)setHideChatButton:(BOOL)hideChatButton {
+    _hideChatButton = hideChatButton;
+    if (hideChatButton) {
+        self.chatButton.hidden = YES;
+        self.chatButton.userInteractionEnabled = NO;
+    }
+    else {
+        self.chatButton.hidden = NO;
+        self.chatButton.userInteractionEnabled = YES;
+    }
+}
+
+- (void)chatCalkback:(AccompanyChatCallback)callback {
+    if (callback) {
+        self.callback = callback;
+    }
+}
+
+- (IBAction)chatAction:(id)sender {
+    if (self.callback) {
+        self.callback();
+    }
+}
+
+- (void)setSelected:(BOOL)selected animated:(BOOL)animated {
+    [super setSelected:selected animated:animated];
+
+    // Configure the view for the selected state
+}
+
+@end

+ 171 - 0
KulexiuForStudent/KulexiuForStudent/Module/Course/AccompanyCourse/View/AccompanyCourseInfoCell.xib

@@ -0,0 +1,171 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<document type="com.apple.InterfaceBuilder3.CocoaTouch.XIB" version="3.0" toolsVersion="20037" targetRuntime="iOS.CocoaTouch" propertyAccessControl="none" useAutolayout="YES" useTraitCollections="YES" useSafeAreas="YES" colorMatched="YES">
+    <device id="retina6_1" orientation="portrait" appearance="light"/>
+    <dependencies>
+        <deployment identifier="iOS"/>
+        <plugIn identifier="com.apple.InterfaceBuilder.IBCocoaTouchPlugin" version="20020"/>
+        <capability name="Safe area layout guides" minToolsVersion="9.0"/>
+        <capability name="System colors in document resources" minToolsVersion="11.0"/>
+        <capability name="documents saved in the Xcode 8 format" minToolsVersion="8.0"/>
+    </dependencies>
+    <objects>
+        <placeholder placeholderIdentifier="IBFilesOwner" id="-1" userLabel="File's Owner"/>
+        <placeholder placeholderIdentifier="IBFirstResponder" id="-2" customClass="UIResponder"/>
+        <tableViewCell contentMode="scaleToFill" selectionStyle="default" indentationWidth="10" id="KGk-i7-Jjw" customClass="AccompanyCourseInfoCell">
+            <rect key="frame" x="0.0" y="0.0" width="367" height="145"/>
+            <autoresizingMask key="autoresizingMask" flexibleMaxX="YES" flexibleMaxY="YES"/>
+            <tableViewCellContentView key="contentView" opaque="NO" clipsSubviews="YES" multipleTouchEnabled="YES" contentMode="center" tableViewCell="KGk-i7-Jjw" id="H2p-sc-9uM">
+                <rect key="frame" x="0.0" y="0.0" width="367" height="145"/>
+                <autoresizingMask key="autoresizingMask"/>
+                <subviews>
+                    <view contentMode="scaleToFill" translatesAutoresizingMaskIntoConstraints="NO" id="Me9-vj-Fhq">
+                        <rect key="frame" x="14" y="10" width="339" height="123"/>
+                        <subviews>
+                            <view contentMode="scaleToFill" translatesAutoresizingMaskIntoConstraints="NO" id="09K-c6-xYX">
+                                <rect key="frame" x="10" y="38" width="319" height="1"/>
+                                <color key="backgroundColor" red="0.94901960780000005" green="0.94901960780000005" blue="0.94901960780000005" alpha="1" colorSpace="calibratedRGB"/>
+                                <constraints>
+                                    <constraint firstAttribute="height" constant="1" id="h3O-jJ-oio"/>
+                                </constraints>
+                            </view>
+                            <imageView clipsSubviews="YES" userInteractionEnabled="NO" contentMode="scaleAspectFit" horizontalHuggingPriority="251" verticalHuggingPriority="251" image="course_time" translatesAutoresizingMaskIntoConstraints="NO" id="Xea-2d-MhT">
+                                <rect key="frame" x="11" y="12" width="16" height="16"/>
+                                <constraints>
+                                    <constraint firstAttribute="height" constant="16" id="QJa-8k-PXn"/>
+                                    <constraint firstAttribute="width" constant="16" id="kpa-Xw-v8k"/>
+                                </constraints>
+                            </imageView>
+                            <label opaque="NO" userInteractionEnabled="NO" contentMode="left" horizontalHuggingPriority="251" verticalHuggingPriority="251" text="" textAlignment="natural" lineBreakMode="tailTruncation" baselineAdjustment="alignBaselines" adjustsFontSizeToFit="NO" translatesAutoresizingMaskIntoConstraints="NO" id="dYZ-ZA-mKb">
+                                <rect key="frame" x="34" y="11" width="0.0" height="18"/>
+                                <constraints>
+                                    <constraint firstAttribute="height" constant="18" id="Cjh-qx-oBI"/>
+                                </constraints>
+                                <fontDescription key="fontDescription" type="system" pointSize="13"/>
+                                <color key="textColor" red="0.40000000000000002" green="0.40000000000000002" blue="0.40000000000000002" alpha="1" colorSpace="calibratedRGB"/>
+                                <nil key="highlightedColor"/>
+                            </label>
+                            <label opaque="NO" userInteractionEnabled="NO" contentMode="left" horizontalHuggingPriority="251" verticalHuggingPriority="251" text="" textAlignment="center" lineBreakMode="tailTruncation" baselineAdjustment="alignBaselines" adjustsFontSizeToFit="NO" translatesAutoresizingMaskIntoConstraints="NO" id="sy0-Ds-ef0">
+                                <rect key="frame" x="278" y="20" width="50" height="0.0"/>
+                                <constraints>
+                                    <constraint firstAttribute="width" constant="50" id="hjG-kD-dSK"/>
+                                </constraints>
+                                <fontDescription key="fontDescription" type="system" weight="medium" pointSize="14"/>
+                                <color key="textColor" red="0.59999999999999998" green="0.59999999999999998" blue="0.59999999999999998" alpha="1" colorSpace="calibratedRGB"/>
+                                <nil key="highlightedColor"/>
+                            </label>
+                            <imageView clipsSubviews="YES" userInteractionEnabled="NO" contentMode="scaleAspectFill" horizontalHuggingPriority="251" verticalHuggingPriority="251" image="user_default_avatal" translatesAutoresizingMaskIntoConstraints="NO" id="s7E-Da-TcK">
+                                <rect key="frame" x="11" y="56" width="47" height="47"/>
+                                <constraints>
+                                    <constraint firstAttribute="height" constant="47" id="4Ap-gR-6vk"/>
+                                    <constraint firstAttribute="width" constant="47" id="NoH-2D-u0z"/>
+                                </constraints>
+                                <userDefinedRuntimeAttributes>
+                                    <userDefinedRuntimeAttribute type="number" keyPath="cornerRadius">
+                                        <real key="value" value="5"/>
+                                    </userDefinedRuntimeAttribute>
+                                </userDefinedRuntimeAttributes>
+                            </imageView>
+                            <label opaque="NO" userInteractionEnabled="NO" contentMode="left" horizontalHuggingPriority="251" verticalHuggingPriority="251" text="" textAlignment="natural" lineBreakMode="tailTruncation" baselineAdjustment="alignBaselines" adjustsFontSizeToFit="NO" translatesAutoresizingMaskIntoConstraints="NO" id="mNS-6d-8wr">
+                                <rect key="frame" x="68" y="56" width="0.0" height="24"/>
+                                <constraints>
+                                    <constraint firstAttribute="height" constant="24" id="CXE-YJ-Psv"/>
+                                </constraints>
+                                <fontDescription key="fontDescription" type="system" weight="medium" pointSize="16"/>
+                                <color key="textColor" red="0.1019607843" green="0.1019607843" blue="0.1019607843" alpha="1" colorSpace="calibratedRGB"/>
+                                <nil key="highlightedColor"/>
+                            </label>
+                            <view contentMode="scaleToFill" translatesAutoresizingMaskIntoConstraints="NO" id="2RD-hr-hLB">
+                                <rect key="frame" x="68" y="83" width="10" height="20"/>
+                                <subviews>
+                                    <label opaque="NO" userInteractionEnabled="NO" contentMode="left" horizontalHuggingPriority="251" verticalHuggingPriority="251" text="" textAlignment="natural" lineBreakMode="tailTruncation" baselineAdjustment="alignBaselines" adjustsFontSizeToFit="NO" translatesAutoresizingMaskIntoConstraints="NO" id="g0Z-7O-ahT">
+                                        <rect key="frame" x="5" y="0.0" width="0.0" height="20"/>
+                                        <fontDescription key="fontDescription" type="system" pointSize="11"/>
+                                        <color key="textColor" red="1" green="0.54901960780000003" blue="0.0" alpha="1" colorSpace="calibratedRGB"/>
+                                        <nil key="highlightedColor"/>
+                                    </label>
+                                </subviews>
+                                <color key="backgroundColor" red="1" green="0.94509803920000002" blue="0.87058823529999996" alpha="1" colorSpace="calibratedRGB"/>
+                                <constraints>
+                                    <constraint firstAttribute="bottom" secondItem="g0Z-7O-ahT" secondAttribute="bottom" id="D38-fw-jAX"/>
+                                    <constraint firstAttribute="trailing" secondItem="g0Z-7O-ahT" secondAttribute="trailing" constant="5" id="N3Z-Rs-lL1"/>
+                                    <constraint firstItem="g0Z-7O-ahT" firstAttribute="top" secondItem="2RD-hr-hLB" secondAttribute="top" id="df1-Vz-7wk"/>
+                                    <constraint firstAttribute="height" constant="20" id="dx5-We-4wH"/>
+                                    <constraint firstItem="g0Z-7O-ahT" firstAttribute="leading" secondItem="2RD-hr-hLB" secondAttribute="leading" constant="5" id="liU-VW-wo4"/>
+                                </constraints>
+                                <userDefinedRuntimeAttributes>
+                                    <userDefinedRuntimeAttribute type="number" keyPath="cornerRadius">
+                                        <real key="value" value="4"/>
+                                    </userDefinedRuntimeAttribute>
+                                </userDefinedRuntimeAttributes>
+                            </view>
+                            <button opaque="NO" contentMode="scaleToFill" contentHorizontalAlignment="center" contentVerticalAlignment="center" lineBreakMode="middleTruncation" translatesAutoresizingMaskIntoConstraints="NO" id="dZv-fL-5CE">
+                                <rect key="frame" x="68" y="48" width="40" height="40"/>
+                                <constraints>
+                                    <constraint firstAttribute="height" constant="40" id="DSU-U0-FpE"/>
+                                    <constraint firstAttribute="width" constant="40" id="PGx-kW-17W"/>
+                                </constraints>
+                                <inset key="imageEdgeInsets" minX="0.0" minY="0.0" maxX="2.2250738585072014e-308" maxY="0.0"/>
+                                <state key="normal" image="course_chat"/>
+                                <connections>
+                                    <action selector="chatAction:" destination="KGk-i7-Jjw" eventType="touchUpInside" id="Mja-PS-NEH"/>
+                                </connections>
+                            </button>
+                        </subviews>
+                        <color key="backgroundColor" systemColor="systemBackgroundColor"/>
+                        <constraints>
+                            <constraint firstItem="2RD-hr-hLB" firstAttribute="bottom" secondItem="s7E-Da-TcK" secondAttribute="bottom" id="4j8-NG-p8a"/>
+                            <constraint firstAttribute="trailing" secondItem="sy0-Ds-ef0" secondAttribute="trailing" constant="11" id="8bf-XE-uBd"/>
+                            <constraint firstItem="dYZ-ZA-mKb" firstAttribute="leading" secondItem="Xea-2d-MhT" secondAttribute="trailing" constant="7" id="AaW-vX-a8p"/>
+                            <constraint firstItem="Xea-2d-MhT" firstAttribute="leading" secondItem="Me9-vj-Fhq" secondAttribute="leading" constant="11" id="CBa-w0-UOa"/>
+                            <constraint firstItem="s7E-Da-TcK" firstAttribute="top" secondItem="09K-c6-xYX" secondAttribute="bottom" constant="17" id="Ft4-re-ZDx"/>
+                            <constraint firstItem="Xea-2d-MhT" firstAttribute="top" secondItem="Me9-vj-Fhq" secondAttribute="top" constant="12" id="Nhv-BT-RCR"/>
+                            <constraint firstItem="09K-c6-xYX" firstAttribute="leading" secondItem="Me9-vj-Fhq" secondAttribute="leading" constant="10" id="Oye-BS-j2I"/>
+                            <constraint firstItem="dYZ-ZA-mKb" firstAttribute="centerY" secondItem="Xea-2d-MhT" secondAttribute="centerY" id="P1s-2G-pny"/>
+                            <constraint firstItem="sy0-Ds-ef0" firstAttribute="centerY" secondItem="dYZ-ZA-mKb" secondAttribute="centerY" id="X9X-7C-53D"/>
+                            <constraint firstItem="dZv-fL-5CE" firstAttribute="leading" secondItem="mNS-6d-8wr" secondAttribute="trailing" id="XgQ-6M-AZe"/>
+                            <constraint firstItem="sy0-Ds-ef0" firstAttribute="leading" relation="greaterThanOrEqual" secondItem="dYZ-ZA-mKb" secondAttribute="trailing" constant="10" id="YVK-XV-hev"/>
+                            <constraint firstAttribute="bottom" secondItem="s7E-Da-TcK" secondAttribute="bottom" constant="20" id="a6x-Et-6cK"/>
+                            <constraint firstItem="s7E-Da-TcK" firstAttribute="leading" secondItem="Me9-vj-Fhq" secondAttribute="leading" constant="11" id="dAu-VP-8Cy"/>
+                            <constraint firstItem="mNS-6d-8wr" firstAttribute="leading" secondItem="s7E-Da-TcK" secondAttribute="trailing" constant="10" id="dm3-Jc-bB0"/>
+                            <constraint firstItem="2RD-hr-hLB" firstAttribute="leading" secondItem="mNS-6d-8wr" secondAttribute="leading" id="iOB-o4-an5"/>
+                            <constraint firstItem="dZv-fL-5CE" firstAttribute="centerY" secondItem="mNS-6d-8wr" secondAttribute="centerY" id="iZq-rI-A9M"/>
+                            <constraint firstAttribute="trailing" secondItem="09K-c6-xYX" secondAttribute="trailing" constant="10" id="p00-p1-Cqn"/>
+                            <constraint firstItem="mNS-6d-8wr" firstAttribute="top" secondItem="s7E-Da-TcK" secondAttribute="top" id="u91-Cd-N1a"/>
+                            <constraint firstItem="09K-c6-xYX" firstAttribute="top" secondItem="Xea-2d-MhT" secondAttribute="bottom" constant="10" id="uTr-wS-3kK"/>
+                        </constraints>
+                        <userDefinedRuntimeAttributes>
+                            <userDefinedRuntimeAttribute type="number" keyPath="cornerRadius">
+                                <real key="value" value="10"/>
+                            </userDefinedRuntimeAttribute>
+                        </userDefinedRuntimeAttributes>
+                    </view>
+                </subviews>
+                <constraints>
+                    <constraint firstAttribute="bottom" secondItem="Me9-vj-Fhq" secondAttribute="bottom" constant="12" id="Xsc-EO-bGL"/>
+                    <constraint firstItem="Me9-vj-Fhq" firstAttribute="top" secondItem="H2p-sc-9uM" secondAttribute="top" constant="10" id="YXp-RV-zfk"/>
+                    <constraint firstAttribute="trailing" secondItem="Me9-vj-Fhq" secondAttribute="trailing" constant="14" id="atd-gk-0m1"/>
+                    <constraint firstItem="Me9-vj-Fhq" firstAttribute="leading" secondItem="H2p-sc-9uM" secondAttribute="leading" constant="14" id="g3f-25-gGV"/>
+                </constraints>
+            </tableViewCellContentView>
+            <viewLayoutGuide key="safeArea" id="aW0-zy-SZf"/>
+            <color key="backgroundColor" white="0.0" alpha="0.0" colorSpace="custom" customColorSpace="genericGamma22GrayColorSpace"/>
+            <connections>
+                <outlet property="chatButton" destination="dZv-fL-5CE" id="AJN-Du-3LN"/>
+                <outlet property="courseTime" destination="dYZ-ZA-mKb" id="JjR-Me-4kj"/>
+                <outlet property="statusLabel" destination="sy0-Ds-ef0" id="0IK-l7-I3g"/>
+                <outlet property="studentAvatar" destination="s7E-Da-TcK" id="Hat-QP-4o3"/>
+                <outlet property="studentName" destination="mNS-6d-8wr" id="DZl-me-T26"/>
+                <outlet property="studentSubject" destination="g0Z-7O-ahT" id="SsG-hN-q6S"/>
+            </connections>
+            <point key="canvasLocation" x="165.94202898550725" y="108.48214285714285"/>
+        </tableViewCell>
+    </objects>
+    <resources>
+        <image name="course_chat" width="19" height="18"/>
+        <image name="course_time" width="16" height="16"/>
+        <image name="user_default_avatal" width="52" height="52"/>
+        <systemColor name="systemBackgroundColor">
+            <color white="1" alpha="1" colorSpace="custom" customColorSpace="genericGamma22GrayColorSpace"/>
+        </systemColor>
+    </resources>
+</document>

+ 28 - 0
KulexiuForStudent/KulexiuForStudent/Module/Course/AccompanyCourse/View/AccompanyHomeworkCell.h

@@ -0,0 +1,28 @@
+//
+//  AccompanyHomeworkCell.h
+//  KulexiuForTeacher
+//
+//  Created by 王智 on 2022/4/13.
+//
+
+#import <UIKit/UIKit.h>
+#import "HomeworkVideoView.h"
+
+typedef NS_ENUM(NSInteger, HOMEWORKACTION) {
+    HOMEWORKACTION_PLAY,   // 播放
+    HOMEWORKACTION_DELETE, // 删除
+    HOMEWORKACTION_ADD,    // 上传新作业
+};
+typedef void(^HomeworkCellAction)(HOMEWORKACTION action, NSInteger viewIndex);
+
+NS_ASSUME_NONNULL_BEGIN
+
+@interface AccompanyHomeworkCell : UITableViewCell
+
+@property (nonatomic, assign) BOOL canSubmit;
+
+- (void)configWithAttachmentArray:(NSMutableArray *)fileArray canDisplaySubmitView:(BOOL)canDisplay callback:(HomeworkCellAction)callback;
+
+@end
+
+NS_ASSUME_NONNULL_END

+ 112 - 0
KulexiuForStudent/KulexiuForStudent/Module/Course/AccompanyCourse/View/AccompanyHomeworkCell.m

@@ -0,0 +1,112 @@
+//
+//  AccompanyHomeworkCell.m
+//  KulexiuForTeacher
+//
+//  Created by 王智 on 2022/4/13.
+//
+
+#import "AccompanyHomeworkCell.h"
+#import "HomeworkAddView.h"
+
+@interface AccompanyHomeworkCell ()
+
+@property (weak, nonatomic) IBOutlet UIView *emptyView;
+
+@property (weak, nonatomic) IBOutlet UIView *videoContainer;
+
+@property (nonatomic, copy) HomeworkCellAction callback;
+
+@end
+
+@implementation AccompanyHomeworkCell
+
+- (void)awakeFromNib {
+    [super awakeFromNib];
+    // Initialization code
+    self.selectionStyle = UITableViewCellSelectionStyleNone;
+}
+
+- (void)configWithAttachmentArray:(NSMutableArray *)fileArray canDisplaySubmitView:(BOOL)canDisplay callback:(nonnull HomeworkCellAction)callback {
+    if (callback) {
+        self.callback = callback;
+    }
+    [self.videoContainer removeAllSubViews];
+    if (canDisplay) {
+        self.emptyView.hidden = YES;
+        [self configVideoViewWithSource:fileArray];
+    }
+    else {
+        self.emptyView.hidden = NO;
+    }
+}
+
+- (void)configVideoViewWithSource:(NSMutableArray *)fileArray {
+    CGFloat maxWidth = kScreenWidth - 24 - 11;
+    CGFloat space = 0;
+    CGFloat width = (maxWidth - space * 2) / 3.0f;
+    CGFloat height = 92.0f;
+    for (NSInteger i = 0; i < fileArray.count; i++) {
+        if (i > 2) {
+            return;
+        }
+        CGFloat positionX = i * (width + space);
+        NSString *videoUrl = fileArray[i];
+        HomeworkVideoView *videoView = [HomeworkVideoView shareInstance];
+        videoView.frame = CGRectMake(positionX, 0, width, height);
+        if (self.canSubmit == NO) {
+            videoView.hideDeleteButton = YES;
+        }
+        videoView.tag = i+1000;
+        MJWeakSelf
+        [videoView displayVideoUrl:videoUrl callback:^(VIDEOVIEWACTION action, NSInteger viewIndex) {
+            if (action == VIDEOVIEWACTION_PLAY) {
+                [weakSelf playVideoIndex:viewIndex];
+            }
+            else {
+                [weakSelf deleteVideoIndex:viewIndex];
+            }
+        }];
+
+        [self.videoContainer addSubview:videoView];
+    }
+    if (fileArray.count < 3 && self.canSubmit) { // 添加上传按钮
+        CGFloat positionX = fileArray.count * (width + space);
+        HomeworkAddView *addView = [[HomeworkAddView alloc] initWithFrame:CGRectMake(positionX, 0, width, height)];
+        [self.videoContainer addSubview:addView];
+        MJWeakSelf;
+        [addView chooseCallback:^{
+            [weakSelf chooseVideo];
+        }];
+    }
+}
+
+- (void)chooseVideo {
+    if (self.callback) {
+        self.callback(HOMEWORKACTION_ADD,0);
+    }
+}
+
+// 播放
+- (void)playVideoIndex:(NSInteger)index {
+    if (self.callback) {
+        self.callback(HOMEWORKACTION_PLAY,index);
+    }
+}
+// 删除
+- (void)deleteVideoIndex:(NSInteger)index {
+    if (self.callback) {
+        self.callback(HOMEWORKACTION_DELETE, index);
+    }
+}
+
+- (void)setCanSubmit:(BOOL)canSubmit {
+    _canSubmit = canSubmit;
+}
+
+- (void)setSelected:(BOOL)selected animated:(BOOL)animated {
+    [super setSelected:selected animated:animated];
+
+    // Configure the view for the selected state
+}
+
+@end

+ 137 - 0
KulexiuForStudent/KulexiuForStudent/Module/Course/AccompanyCourse/View/AccompanyHomeworkCell.xib

@@ -0,0 +1,137 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<document type="com.apple.InterfaceBuilder3.CocoaTouch.XIB" version="3.0" toolsVersion="20037" targetRuntime="iOS.CocoaTouch" propertyAccessControl="none" useAutolayout="YES" useTraitCollections="YES" useSafeAreas="YES" colorMatched="YES">
+    <device id="retina6_1" orientation="portrait" appearance="light"/>
+    <dependencies>
+        <deployment identifier="iOS"/>
+        <plugIn identifier="com.apple.InterfaceBuilder.IBCocoaTouchPlugin" version="20020"/>
+        <capability name="Safe area layout guides" minToolsVersion="9.0"/>
+        <capability name="System colors in document resources" minToolsVersion="11.0"/>
+        <capability name="documents saved in the Xcode 8 format" minToolsVersion="8.0"/>
+    </dependencies>
+    <objects>
+        <placeholder placeholderIdentifier="IBFilesOwner" id="-1" userLabel="File's Owner"/>
+        <placeholder placeholderIdentifier="IBFirstResponder" id="-2" customClass="UIResponder"/>
+        <tableViewCell contentMode="scaleToFill" selectionStyle="default" indentationWidth="10" rowHeight="204" id="KGk-i7-Jjw" customClass="AccompanyHomeworkCell">
+            <rect key="frame" x="0.0" y="0.0" width="364" height="204"/>
+            <autoresizingMask key="autoresizingMask" flexibleMaxX="YES" flexibleMaxY="YES"/>
+            <tableViewCellContentView key="contentView" opaque="NO" clipsSubviews="YES" multipleTouchEnabled="YES" contentMode="center" tableViewCell="KGk-i7-Jjw" id="H2p-sc-9uM">
+                <rect key="frame" x="0.0" y="0.0" width="364" height="204"/>
+                <autoresizingMask key="autoresizingMask"/>
+                <subviews>
+                    <view contentMode="scaleToFill" translatesAutoresizingMaskIntoConstraints="NO" id="dtq-Yd-b5t">
+                        <rect key="frame" x="14" y="0.0" width="336" height="192"/>
+                        <subviews>
+                            <imageView clipsSubviews="YES" userInteractionEnabled="NO" contentMode="scaleAspectFit" horizontalHuggingPriority="251" verticalHuggingPriority="251" image="accell_left" translatesAutoresizingMaskIntoConstraints="NO" id="1fO-1K-g2U">
+                                <rect key="frame" x="11" y="13" width="4" height="18"/>
+                            </imageView>
+                            <label opaque="NO" userInteractionEnabled="NO" contentMode="left" horizontalHuggingPriority="251" verticalHuggingPriority="251" text="视频作业" textAlignment="natural" lineBreakMode="tailTruncation" baselineAdjustment="alignBaselines" adjustsFontSizeToFit="NO" translatesAutoresizingMaskIntoConstraints="NO" id="sJu-iK-25U">
+                                <rect key="frame" x="20" y="12" width="58" height="20"/>
+                                <constraints>
+                                    <constraint firstAttribute="height" constant="20" id="3jD-tp-tJm"/>
+                                </constraints>
+                                <fontDescription key="fontDescription" type="system" weight="medium" pointSize="14"/>
+                                <color key="textColor" red="0.20000000000000001" green="0.20000000000000001" blue="0.20000000000000001" alpha="1" colorSpace="calibratedRGB"/>
+                                <nil key="highlightedColor"/>
+                            </label>
+                            <view contentMode="scaleToFill" translatesAutoresizingMaskIntoConstraints="NO" id="EwC-zg-aiZ">
+                                <rect key="frame" x="11" y="40" width="316" height="142"/>
+                                <color key="backgroundColor" white="0.0" alpha="0.0" colorSpace="custom" customColorSpace="genericGamma22GrayColorSpace"/>
+                            </view>
+                            <view contentMode="scaleToFill" translatesAutoresizingMaskIntoConstraints="NO" id="0zy-PX-mCI">
+                                <rect key="frame" x="11" y="40" width="316" height="142"/>
+                                <subviews>
+                                    <view contentMode="scaleToFill" translatesAutoresizingMaskIntoConstraints="NO" id="O89-iL-xU2">
+                                        <rect key="frame" x="0.0" y="0.0" width="316" height="142"/>
+                                        <subviews>
+                                            <imageView clipsSubviews="YES" userInteractionEnabled="NO" contentMode="scaleAspectFit" horizontalHuggingPriority="251" verticalHuggingPriority="251" image="homeworkVideo_placeholder" translatesAutoresizingMaskIntoConstraints="NO" id="bLX-aR-bAP">
+                                                <rect key="frame" x="33" y="32" width="79" height="78"/>
+                                                <constraints>
+                                                    <constraint firstAttribute="height" constant="78" id="Hpe-hS-lAP"/>
+                                                    <constraint firstAttribute="width" constant="79" id="aWC-Pr-Ddt"/>
+                                                </constraints>
+                                            </imageView>
+                                            <label opaque="NO" userInteractionEnabled="NO" contentMode="left" horizontalHuggingPriority="251" verticalHuggingPriority="251" usesAttributedText="YES" lineBreakMode="tailTruncation" numberOfLines="2" baselineAdjustment="alignBaselines" adjustsFontSizeToFit="NO" translatesAutoresizingMaskIntoConstraints="NO" id="xV1-w2-nqO">
+                                                <rect key="frame" x="120" y="54.5" width="146" height="33"/>
+                                                <attributedString key="attributedText">
+                                                    <fragment content="课程结束之后课上传视频作业">
+                                                        <attributes>
+                                                            <color key="NSColor" red="0.59999999999999998" green="0.59999999999999998" blue="0.59999999999999998" alpha="1" colorSpace="calibratedRGB"/>
+                                                            <font key="NSFont" size="13" name=".PingFangSC-Regular"/>
+                                                            <paragraphStyle key="NSParagraphStyle" alignment="natural" lineBreakMode="wordWrapping" baseWritingDirection="natural" lineSpacing="4" tighteningFactorForTruncation="0.0"/>
+                                                        </attributes>
+                                                    </fragment>
+                                                </attributedString>
+                                                <nil key="highlightedColor"/>
+                                            </label>
+                                        </subviews>
+                                        <color key="backgroundColor" white="0.0" alpha="0.0" colorSpace="custom" customColorSpace="genericGamma22GrayColorSpace"/>
+                                        <constraints>
+                                            <constraint firstAttribute="trailing" secondItem="xV1-w2-nqO" secondAttribute="trailing" constant="50" id="8Iy-eb-oui"/>
+                                            <constraint firstItem="bLX-aR-bAP" firstAttribute="centerY" secondItem="O89-iL-xU2" secondAttribute="centerY" id="hrH-63-pil"/>
+                                            <constraint firstItem="bLX-aR-bAP" firstAttribute="leading" secondItem="O89-iL-xU2" secondAttribute="leading" constant="33" id="o6S-TQ-YzT"/>
+                                            <constraint firstItem="xV1-w2-nqO" firstAttribute="leading" secondItem="bLX-aR-bAP" secondAttribute="trailing" constant="8" id="r6Y-hX-87F"/>
+                                            <constraint firstItem="xV1-w2-nqO" firstAttribute="centerY" secondItem="O89-iL-xU2" secondAttribute="centerY" id="tJl-Zn-ULW"/>
+                                        </constraints>
+                                    </view>
+                                </subviews>
+                                <color key="backgroundColor" red="0.96862745100000003" green="0.97254901959999995" blue="0.97647058819999999" alpha="1" colorSpace="calibratedRGB"/>
+                                <constraints>
+                                    <constraint firstAttribute="trailing" secondItem="O89-iL-xU2" secondAttribute="trailing" id="HQp-bb-AtX"/>
+                                    <constraint firstItem="O89-iL-xU2" firstAttribute="leading" secondItem="0zy-PX-mCI" secondAttribute="leading" id="S2b-yI-RdW"/>
+                                    <constraint firstAttribute="height" relation="greaterThanOrEqual" constant="88" id="ZyR-89-1K1"/>
+                                    <constraint firstItem="O89-iL-xU2" firstAttribute="top" secondItem="0zy-PX-mCI" secondAttribute="top" id="bRR-gO-HrZ"/>
+                                    <constraint firstAttribute="bottom" secondItem="O89-iL-xU2" secondAttribute="bottom" id="lUa-1z-WaZ"/>
+                                </constraints>
+                                <userDefinedRuntimeAttributes>
+                                    <userDefinedRuntimeAttribute type="number" keyPath="cornerRadius">
+                                        <real key="value" value="4"/>
+                                    </userDefinedRuntimeAttribute>
+                                </userDefinedRuntimeAttributes>
+                            </view>
+                        </subviews>
+                        <color key="backgroundColor" systemColor="systemBackgroundColor"/>
+                        <constraints>
+                            <constraint firstItem="0zy-PX-mCI" firstAttribute="trailing" secondItem="EwC-zg-aiZ" secondAttribute="trailing" id="70p-E3-NeF"/>
+                            <constraint firstAttribute="bottom" secondItem="0zy-PX-mCI" secondAttribute="bottom" constant="10" id="F6N-7x-aaL"/>
+                            <constraint firstItem="sJu-iK-25U" firstAttribute="leading" secondItem="1fO-1K-g2U" secondAttribute="trailing" constant="5" id="eUo-qr-eCq"/>
+                            <constraint firstItem="0zy-PX-mCI" firstAttribute="leading" secondItem="dtq-Yd-b5t" secondAttribute="leading" constant="11" id="hOV-oC-FPR"/>
+                            <constraint firstItem="1fO-1K-g2U" firstAttribute="leading" secondItem="dtq-Yd-b5t" secondAttribute="leading" constant="11" id="hrI-hU-381"/>
+                            <constraint firstItem="0zy-PX-mCI" firstAttribute="leading" secondItem="EwC-zg-aiZ" secondAttribute="leading" id="j8s-Lv-sdz"/>
+                            <constraint firstItem="0zy-PX-mCI" firstAttribute="bottom" secondItem="EwC-zg-aiZ" secondAttribute="bottom" id="jr8-M4-buE"/>
+                            <constraint firstItem="1fO-1K-g2U" firstAttribute="top" secondItem="dtq-Yd-b5t" secondAttribute="top" constant="13" id="oA4-Nz-L8o"/>
+                            <constraint firstItem="sJu-iK-25U" firstAttribute="centerY" secondItem="1fO-1K-g2U" secondAttribute="centerY" id="pIn-T0-aBu"/>
+                            <constraint firstItem="0zy-PX-mCI" firstAttribute="top" secondItem="sJu-iK-25U" secondAttribute="bottom" constant="8" id="rcZ-bR-wHe"/>
+                            <constraint firstItem="0zy-PX-mCI" firstAttribute="top" secondItem="EwC-zg-aiZ" secondAttribute="top" id="w8p-y6-gXb"/>
+                            <constraint firstAttribute="trailing" secondItem="0zy-PX-mCI" secondAttribute="trailing" constant="9" id="wuB-Na-rgf"/>
+                        </constraints>
+                        <userDefinedRuntimeAttributes>
+                            <userDefinedRuntimeAttribute type="number" keyPath="cornerRadius">
+                                <real key="value" value="10"/>
+                            </userDefinedRuntimeAttribute>
+                        </userDefinedRuntimeAttributes>
+                    </view>
+                </subviews>
+                <constraints>
+                    <constraint firstItem="dtq-Yd-b5t" firstAttribute="top" secondItem="H2p-sc-9uM" secondAttribute="top" id="5e0-db-H4S"/>
+                    <constraint firstItem="dtq-Yd-b5t" firstAttribute="leading" secondItem="H2p-sc-9uM" secondAttribute="leading" constant="14" id="hxY-5l-lak"/>
+                    <constraint firstAttribute="bottom" secondItem="dtq-Yd-b5t" secondAttribute="bottom" constant="12" id="kKE-Bs-RqF"/>
+                    <constraint firstAttribute="trailing" secondItem="dtq-Yd-b5t" secondAttribute="trailing" constant="14" id="vAs-g4-MaY"/>
+                </constraints>
+            </tableViewCellContentView>
+            <viewLayoutGuide key="safeArea" id="aW0-zy-SZf"/>
+            <color key="backgroundColor" white="0.0" alpha="0.0" colorSpace="custom" customColorSpace="genericGamma22GrayColorSpace"/>
+            <connections>
+                <outlet property="emptyView" destination="0zy-PX-mCI" id="3KA-n7-M42"/>
+                <outlet property="videoContainer" destination="EwC-zg-aiZ" id="5RL-eg-4SG"/>
+            </connections>
+            <point key="canvasLocation" x="163.768115942029" y="128.57142857142856"/>
+        </tableViewCell>
+    </objects>
+    <resources>
+        <image name="accell_left" width="4" height="18"/>
+        <image name="homeworkVideo_placeholder" width="79" height="78"/>
+        <systemColor name="systemBackgroundColor">
+            <color white="1" alpha="1" colorSpace="custom" customColorSpace="genericGamma22GrayColorSpace"/>
+        </systemColor>
+    </resources>
+</document>

+ 19 - 0
KulexiuForStudent/KulexiuForStudent/Module/Course/AccompanyCourse/View/AccompanyRemarkCell.h

@@ -0,0 +1,19 @@
+//
+//  AccompanyRemarkCell.h
+//  KulexiuForTeacher
+//
+//  Created by 王智 on 2022/4/6.
+//
+
+#import <UIKit/UIKit.h>
+
+
+NS_ASSUME_NONNULL_BEGIN
+
+@interface AccompanyRemarkCell : UITableViewCell
+
+- (void)configWithRemarkMessage:(NSString *)remarkMessage hasEvaluate:(BOOL)hasEvaluate;
+
+@end
+
+NS_ASSUME_NONNULL_END

+ 54 - 0
KulexiuForStudent/KulexiuForStudent/Module/Course/AccompanyCourse/View/AccompanyRemarkCell.m

@@ -0,0 +1,54 @@
+//
+//  AccompanyRemarkCell.m
+//  KulexiuForTeacher
+//
+//  Created by 王智 on 2022/4/6.
+//
+
+#import "AccompanyRemarkCell.h"
+
+@interface AccompanyRemarkCell ()
+
+@property (weak, nonatomic) IBOutlet UIView *emptyView;
+
+@property (weak, nonatomic) IBOutlet UILabel *contentLabel;
+
+
+@end
+
+@implementation AccompanyRemarkCell
+
+- (void)awakeFromNib {
+    [super awakeFromNib];
+    // Initialization code
+    self.selectionStyle = UITableViewCellSelectionStyleNone;
+}
+
+- (void)configWithRemarkMessage:(NSString *)evaluateMessage hasEvaluate:(BOOL)hasEvaluate {
+
+    if (hasEvaluate) {
+        self.emptyView.hidden = YES;
+        if (![NSString isEmptyString:evaluateMessage]) {
+            NSMutableParagraphStyle *paragraphStyle = [[NSMutableParagraphStyle alloc] init];
+            [paragraphStyle setLineSpacing:4];//调整行间距
+            NSMutableAttributedString *attr = [[NSMutableAttributedString alloc] initWithString:evaluateMessage attributes:@{NSParagraphStyleAttributeName:paragraphStyle,NSFontAttributeName:[UIFont systemFontOfSize:13.0f],NSForegroundColorAttributeName:HexRGB(0x333333)}];
+            self.contentLabel.attributedText = attr;
+        }
+        else {
+            self.contentLabel.text = @"";
+        }
+    }
+    else {
+        self.emptyView.hidden = NO;
+        self.contentLabel.text = @"";
+    }
+}
+
+
+- (void)setSelected:(BOOL)selected animated:(BOOL)animated {
+    [super setSelected:selected animated:animated];
+
+    // Configure the view for the selected state
+}
+
+@end

+ 139 - 0
KulexiuForStudent/KulexiuForStudent/Module/Course/AccompanyCourse/View/AccompanyRemarkCell.xib

@@ -0,0 +1,139 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<document type="com.apple.InterfaceBuilder3.CocoaTouch.XIB" version="3.0" toolsVersion="20037" targetRuntime="iOS.CocoaTouch" propertyAccessControl="none" useAutolayout="YES" useTraitCollections="YES" useSafeAreas="YES" colorMatched="YES">
+    <device id="retina6_1" orientation="portrait" appearance="light"/>
+    <dependencies>
+        <deployment identifier="iOS"/>
+        <plugIn identifier="com.apple.InterfaceBuilder.IBCocoaTouchPlugin" version="20020"/>
+        <capability name="Safe area layout guides" minToolsVersion="9.0"/>
+        <capability name="System colors in document resources" minToolsVersion="11.0"/>
+        <capability name="documents saved in the Xcode 8 format" minToolsVersion="8.0"/>
+    </dependencies>
+    <objects>
+        <placeholder placeholderIdentifier="IBFilesOwner" id="-1" userLabel="File's Owner"/>
+        <placeholder placeholderIdentifier="IBFirstResponder" id="-2" customClass="UIResponder"/>
+        <tableViewCell contentMode="scaleToFill" selectionStyle="default" indentationWidth="10" rowHeight="221" id="KGk-i7-Jjw" customClass="AccompanyRemarkCell">
+            <rect key="frame" x="0.0" y="0.0" width="375" height="221"/>
+            <autoresizingMask key="autoresizingMask" flexibleMaxX="YES" flexibleMaxY="YES"/>
+            <tableViewCellContentView key="contentView" opaque="NO" clipsSubviews="YES" multipleTouchEnabled="YES" contentMode="center" tableViewCell="KGk-i7-Jjw" id="H2p-sc-9uM">
+                <rect key="frame" x="0.0" y="0.0" width="375" height="221"/>
+                <autoresizingMask key="autoresizingMask"/>
+                <subviews>
+                    <view contentMode="scaleToFill" translatesAutoresizingMaskIntoConstraints="NO" id="qyw-41-OgZ">
+                        <rect key="frame" x="14" y="0.0" width="347" height="209"/>
+                        <subviews>
+                            <imageView clipsSubviews="YES" userInteractionEnabled="NO" contentMode="scaleAspectFit" horizontalHuggingPriority="251" verticalHuggingPriority="251" image="accell_left" translatesAutoresizingMaskIntoConstraints="NO" id="Nmt-3B-GQh">
+                                <rect key="frame" x="11" y="13" width="4" height="18"/>
+                            </imageView>
+                            <label opaque="NO" userInteractionEnabled="NO" contentMode="left" horizontalHuggingPriority="251" verticalHuggingPriority="251" text="作业点评" textAlignment="natural" lineBreakMode="tailTruncation" baselineAdjustment="alignBaselines" adjustsFontSizeToFit="NO" translatesAutoresizingMaskIntoConstraints="NO" id="Lof-Tc-krl">
+                                <rect key="frame" x="20" y="12" width="58" height="20"/>
+                                <constraints>
+                                    <constraint firstAttribute="height" constant="20" id="FEC-1Y-gGm"/>
+                                </constraints>
+                                <fontDescription key="fontDescription" type="system" weight="medium" pointSize="14"/>
+                                <color key="textColor" red="0.20000000000000001" green="0.20000000000000001" blue="0.20000000000000001" alpha="1" colorSpace="calibratedRGB"/>
+                                <nil key="highlightedColor"/>
+                            </label>
+                            <view contentMode="scaleToFill" translatesAutoresizingMaskIntoConstraints="NO" id="ehC-4r-0Vt">
+                                <rect key="frame" x="11" y="40" width="327" height="159"/>
+                                <subviews>
+                                    <label opaque="NO" userInteractionEnabled="NO" contentMode="left" horizontalHuggingPriority="251" verticalHuggingPriority="251" text="" textAlignment="natural" lineBreakMode="tailTruncation" numberOfLines="0" baselineAdjustment="alignBaselines" adjustsFontSizeToFit="NO" translatesAutoresizingMaskIntoConstraints="NO" id="fGD-VY-opX">
+                                        <rect key="frame" x="9" y="11" width="312" height="0.0"/>
+                                        <fontDescription key="fontDescription" type="system" pointSize="13"/>
+                                        <color key="textColor" red="0.20000000000000001" green="0.20000000000000001" blue="0.20000000000000001" alpha="1" colorSpace="calibratedRGB"/>
+                                        <nil key="highlightedColor"/>
+                                    </label>
+                                    <view contentMode="scaleToFill" translatesAutoresizingMaskIntoConstraints="NO" id="W9z-ye-Ww2">
+                                        <rect key="frame" x="0.0" y="0.0" width="327" height="159"/>
+                                        <subviews>
+                                            <imageView clipsSubviews="YES" userInteractionEnabled="NO" contentMode="scaleAspectFit" horizontalHuggingPriority="251" verticalHuggingPriority="251" image="homework_placeholder" translatesAutoresizingMaskIntoConstraints="NO" id="44c-14-lXI">
+                                                <rect key="frame" x="33" y="40.5" width="79" height="78"/>
+                                                <constraints>
+                                                    <constraint firstAttribute="height" constant="78" id="3IW-Vv-GOP"/>
+                                                    <constraint firstAttribute="width" constant="79" id="bln-k4-dPI"/>
+                                                </constraints>
+                                            </imageView>
+                                            <label opaque="NO" userInteractionEnabled="NO" contentMode="left" horizontalHuggingPriority="251" verticalHuggingPriority="251" usesAttributedText="YES" lineBreakMode="tailTruncation" numberOfLines="2" baselineAdjustment="alignBaselines" adjustsFontSizeToFit="NO" translatesAutoresizingMaskIntoConstraints="NO" id="M7Y-he-HQe">
+                                                <rect key="frame" x="120" y="62.5" width="157" height="34.5"/>
+                                                <attributedString key="attributedText">
+                                                    <fragment content="课程结束后上传作业视频会得倒老师点评喔~">
+                                                        <attributes>
+                                                            <color key="NSColor" red="0.59999999999999998" green="0.59999999999999998" blue="0.59999999999999998" alpha="1" colorSpace="calibratedRGB"/>
+                                                            <font key="NSFont" size="13" name="STSongti-SC-Regular"/>
+                                                            <paragraphStyle key="NSParagraphStyle" alignment="natural" lineBreakMode="wordWrapping" baseWritingDirection="natural" lineSpacing="4" tighteningFactorForTruncation="0.0"/>
+                                                        </attributes>
+                                                    </fragment>
+                                                </attributedString>
+                                                <nil key="highlightedColor"/>
+                                            </label>
+                                        </subviews>
+                                        <color key="backgroundColor" white="0.0" alpha="0.0" colorSpace="custom" customColorSpace="genericGamma22GrayColorSpace"/>
+                                        <constraints>
+                                            <constraint firstItem="M7Y-he-HQe" firstAttribute="leading" secondItem="44c-14-lXI" secondAttribute="trailing" constant="8" id="1Ag-bV-qSy"/>
+                                            <constraint firstAttribute="trailing" secondItem="M7Y-he-HQe" secondAttribute="trailing" constant="50" id="QeU-Ah-bkP"/>
+                                            <constraint firstItem="44c-14-lXI" firstAttribute="centerY" secondItem="W9z-ye-Ww2" secondAttribute="centerY" id="bQB-oC-9NI"/>
+                                            <constraint firstItem="M7Y-he-HQe" firstAttribute="centerY" secondItem="W9z-ye-Ww2" secondAttribute="centerY" id="khM-b5-QrM"/>
+                                            <constraint firstItem="44c-14-lXI" firstAttribute="leading" secondItem="W9z-ye-Ww2" secondAttribute="leading" constant="33" id="vq5-de-jPS"/>
+                                        </constraints>
+                                    </view>
+                                </subviews>
+                                <color key="backgroundColor" red="0.96862745098039216" green="0.97254901960784312" blue="0.97647058823529409" alpha="1" colorSpace="custom" customColorSpace="calibratedRGB"/>
+                                <constraints>
+                                    <constraint firstItem="fGD-VY-opX" firstAttribute="top" secondItem="ehC-4r-0Vt" secondAttribute="top" constant="11" id="5qP-C3-ls4"/>
+                                    <constraint firstAttribute="bottom" relation="greaterThanOrEqual" secondItem="fGD-VY-opX" secondAttribute="bottom" constant="5" id="97b-0p-hN7"/>
+                                    <constraint firstItem="fGD-VY-opX" firstAttribute="leading" secondItem="ehC-4r-0Vt" secondAttribute="leading" constant="9" id="HQP-RH-aK1"/>
+                                    <constraint firstAttribute="height" relation="greaterThanOrEqual" constant="88" id="L9X-hq-5Cj"/>
+                                    <constraint firstItem="W9z-ye-Ww2" firstAttribute="top" secondItem="ehC-4r-0Vt" secondAttribute="top" id="LmU-3Z-TK6"/>
+                                    <constraint firstAttribute="trailing" secondItem="fGD-VY-opX" secondAttribute="trailing" constant="6" id="NvZ-6s-hae"/>
+                                    <constraint firstItem="W9z-ye-Ww2" firstAttribute="leading" secondItem="ehC-4r-0Vt" secondAttribute="leading" id="TG2-AT-S1D"/>
+                                    <constraint firstAttribute="trailing" secondItem="W9z-ye-Ww2" secondAttribute="trailing" id="b8y-80-QsT"/>
+                                    <constraint firstAttribute="bottom" secondItem="W9z-ye-Ww2" secondAttribute="bottom" id="eNf-PG-4d5"/>
+                                </constraints>
+                                <userDefinedRuntimeAttributes>
+                                    <userDefinedRuntimeAttribute type="number" keyPath="cornerRadius">
+                                        <real key="value" value="4"/>
+                                    </userDefinedRuntimeAttribute>
+                                </userDefinedRuntimeAttributes>
+                            </view>
+                        </subviews>
+                        <color key="backgroundColor" systemColor="systemBackgroundColor"/>
+                        <constraints>
+                            <constraint firstItem="Nmt-3B-GQh" firstAttribute="leading" secondItem="qyw-41-OgZ" secondAttribute="leading" constant="11" id="1vg-Xu-dly"/>
+                            <constraint firstItem="Lof-Tc-krl" firstAttribute="centerY" secondItem="Nmt-3B-GQh" secondAttribute="centerY" id="855-0U-TnZ"/>
+                            <constraint firstItem="Nmt-3B-GQh" firstAttribute="top" secondItem="qyw-41-OgZ" secondAttribute="top" constant="13" id="Hlw-dV-esz"/>
+                            <constraint firstItem="Lof-Tc-krl" firstAttribute="leading" secondItem="Nmt-3B-GQh" secondAttribute="trailing" constant="5" id="U3l-C1-sla"/>
+                            <constraint firstAttribute="trailing" secondItem="ehC-4r-0Vt" secondAttribute="trailing" constant="9" id="UGg-Vv-yct"/>
+                            <constraint firstItem="ehC-4r-0Vt" firstAttribute="top" secondItem="Lof-Tc-krl" secondAttribute="bottom" constant="8" id="c4A-7V-3jf"/>
+                            <constraint firstAttribute="bottom" secondItem="ehC-4r-0Vt" secondAttribute="bottom" constant="10" id="ghc-VL-2mE"/>
+                            <constraint firstItem="ehC-4r-0Vt" firstAttribute="leading" secondItem="qyw-41-OgZ" secondAttribute="leading" constant="11" id="lg4-q3-Py7"/>
+                        </constraints>
+                        <userDefinedRuntimeAttributes>
+                            <userDefinedRuntimeAttribute type="number" keyPath="cornerRadius">
+                                <real key="value" value="10"/>
+                            </userDefinedRuntimeAttribute>
+                        </userDefinedRuntimeAttributes>
+                    </view>
+                </subviews>
+                <constraints>
+                    <constraint firstAttribute="trailing" secondItem="qyw-41-OgZ" secondAttribute="trailing" constant="14" id="MJ6-BL-ggf"/>
+                    <constraint firstAttribute="bottom" secondItem="qyw-41-OgZ" secondAttribute="bottom" constant="12" id="QTx-dh-Ga2"/>
+                    <constraint firstItem="qyw-41-OgZ" firstAttribute="top" secondItem="H2p-sc-9uM" secondAttribute="top" id="jxk-Ie-3Ff"/>
+                    <constraint firstItem="qyw-41-OgZ" firstAttribute="leading" secondItem="H2p-sc-9uM" secondAttribute="leading" constant="14" id="vWY-b7-XDC"/>
+                </constraints>
+            </tableViewCellContentView>
+            <viewLayoutGuide key="safeArea" id="aW0-zy-SZf"/>
+            <color key="backgroundColor" white="0.0" alpha="0.0" colorSpace="custom" customColorSpace="genericGamma22GrayColorSpace"/>
+            <connections>
+                <outlet property="contentLabel" destination="fGD-VY-opX" id="2nt-wP-TPs"/>
+                <outlet property="emptyView" destination="W9z-ye-Ww2" id="RYX-4Q-Ecb"/>
+            </connections>
+            <point key="canvasLocation" x="131.15942028985509" y="101.45089285714285"/>
+        </tableViewCell>
+    </objects>
+    <resources>
+        <image name="accell_left" width="4" height="18"/>
+        <image name="homework_placeholder" width="79" height="78"/>
+        <systemColor name="systemBackgroundColor">
+            <color white="1" alpha="1" colorSpace="custom" customColorSpace="genericGamma22GrayColorSpace"/>
+        </systemColor>
+    </resources>
+</document>

+ 6 - 2
KulexiuForStudent/KulexiuForStudent/Module/Mine/Controller/MineViewController.m

@@ -15,6 +15,8 @@
 #import "KSEnterLiveroomManager.h"
 #import "UserInfoManager.h"
 #import "StudentInfoModel.h"
+#import "MyCourseViewController.h"
+#import "HomeworkListViewController.h"
 
 @interface MineViewController ()
 
@@ -116,12 +118,14 @@
             break;
         case MINEVIEWTYPE_COURSE:
         {
-
+            MyCourseViewController *ctrl = [[MyCourseViewController alloc] init];
+            [self.navigationController pushViewController:ctrl animated:YES];
         }
             break;
         case MINEVIEWTYPE_HOMEWORK:
         {
-            
+            HomeworkListViewController *ctrl = [[HomeworkListViewController alloc] init];
+            [self.navigationController pushViewController:ctrl animated:YES];
         }
             break;
         case MINEVIEWTYPE_MUSIC:

+ 18 - 0
KulexiuForStudent/KulexiuForStudent/Module/Mine/Homework/Controller/HomeworkDetailViewController.h

@@ -0,0 +1,18 @@
+//
+//  HomeworkDetailViewController.h
+//  KulexiuForStudent
+//
+//  Created by 王智 on 2022/4/20.
+//
+
+#import "KSBaseViewController.h"
+
+NS_ASSUME_NONNULL_BEGIN
+
+@interface HomeworkDetailViewController : KSBaseViewController
+
+@property (nonatomic, strong) NSString *courseId;
+
+@end
+
+NS_ASSUME_NONNULL_END

+ 377 - 0
KulexiuForStudent/KulexiuForStudent/Module/Mine/Homework/Controller/HomeworkDetailViewController.m

@@ -0,0 +1,377 @@
+//
+//  HomeworkDetailViewController.m
+//  KulexiuForStudent
+//
+//  Created by 王智 on 2022/4/20.
+//
+
+#import "HomeworkDetailViewController.h"
+#import "AccompanyAlertView.h"
+#import "HomeworkDetailModel.h"
+#import "WMPlayer.h"
+#import "AccompanyCourseInfoCell.h"
+#import "AccompanyArrangeCell.h"
+#import "AccompanyHomeworkCell.h"
+#import "AccompanyRemarkCell.h"
+#import "KSMediaManager.h"
+#import "HomeworkBottomView.h"
+
+@interface HomeworkDetailViewController ()<UITableViewDelegate, UITableViewDataSource,WMPlayerDelegate>
+{
+    WMPlayer *_wmPlayer;
+    CGRect _playerFrame;
+}
+@property (nonatomic, strong) UIView *bgView;
+
+@property (nonatomic, assign) BOOL isRatation;
+
+@property (nonatomic, strong) UITableView *tableView;
+
+@property (nonatomic, assign) NSInteger cellCount;
+
+@property (nonatomic, strong) AccompanyAlertView *alertView;
+
+@property (nonatomic, strong) HomeworkDetailModel *detailModel;
+
+@property (nonatomic, strong) NSMutableArray *fileArray;
+
+@property (nonatomic, strong) KSMediaManager *mediaManager;
+
+@property (strong, nonatomic) MBProgressHUD *HUD;
+
+@property (nonatomic, assign) BOOL canModify;
+
+@property (nonatomic, strong) HomeworkBottomView *bottomView;
+
+@end
+
+@implementation HomeworkDetailViewController
+
+- (void)viewDidLoad {
+    [super viewDidLoad];
+    // Do any additional setup after loading the view.
+    [self allocTitle:@"作业详情"];
+    [self setupUI];
+    [self requestCourseMessage];
+}
+
+- (void)setupUI {
+    [self.scrollView removeFromSuperview];
+    self.view.backgroundColor = HexRGB(0xf6f8f9);
+    [self.view addSubview:self.tableView];
+    [self.tableView mas_makeConstraints:^(MASConstraintMaker *make) {
+        make.left.right.top.mas_equalTo(self.view);
+        make.bottom.mas_equalTo(self.view.mas_bottom).offset(-iPhoneXSafeBottomMargin);
+    }];
+}
+
+- (void)requestCourseMessage {
+    [self showhud];
+    [KSNetworkingManager homeworkDetailRequest:KS_GET courseId:self.courseId success:^(NSDictionary * _Nonnull dic) {
+        [self removehub];
+        if ([dic integerValueForKey:@"code"] == 200 && [dic boolValueForKey:@"status"]) {
+            self.detailModel = [[HomeworkDetailModel alloc] initWithDictionary:[dic dictionaryValueForKey:@"data"]];
+            [self evaluateViewDisplay];
+        }
+        else {
+            [self MBPShow:MESSAGEKEY];
+        }
+    } faliure:^(NSError * _Nonnull error) {
+        [self removehub];
+    }];
+}
+
+- (void)evaluateViewDisplay {
+    // 判断显示
+    if (self.detailModel.decorateHomework == 0) { // 未布置
+        self.cellCount = 2;
+    }
+    else { // 已布置
+        if (self.detailModel.submitHomework == 0) { // 未提交
+            self.cellCount = 3;
+        }
+        else { // 已提交
+            self.cellCount = 4;
+            if (![NSString isEmptyString:self.detailModel.studentAttachments]) {
+                self.fileArray = [NSMutableArray arrayWithArray:[self.detailModel.studentAttachments componentsSeparatedByString:@","]];
+            }
+        }
+    }
+    // 老师布置过作业且没有点评 可以点击
+    if (self.detailModel.reviewHomework == 1 || self.detailModel.decorateHomework == 0) {
+        self.bottomView.sureButton.userInteractionEnabled = NO;
+        self.bottomView.sureButton.backgroundColor = HexRGB(0xe5e5e5);
+        [self.bottomView.sureButton setTitleColor:HexRGB(0x666666) forState:UIControlStateNormal];
+    }
+    else {
+        self.bottomView.sureButton.userInteractionEnabled = YES;
+        self.bottomView.sureButton.backgroundColor = THEMECOLOR;
+        [self.bottomView.sureButton setTitleColor:[UIColor whiteColor] forState:UIControlStateNormal];
+    }
+    
+    [self.tableView reloadData];
+}
+
+#pragma mark ----- table data source
+- (NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section {
+    return self.cellCount;
+}
+
+- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath {
+    if (indexPath.row == 0) { // 课程信息
+        AccompanyCourseInfoCell *cell = [tableView dequeueReusableCellWithIdentifier:@"AccompanyCourseInfoCell"];
+        cell.statusLabel.text = @"已结束";
+        cell.statusLabel.textColor = HexRGB(0x999999);
+        [cell configWithStartTime:self.detailModel.startTime endTime:self.detailModel.endTime teacherAvatar:self.detailModel.teacherAvatar teacherName:self.detailModel.teacherName teacherId:self.detailModel.teacherId courseSubject:self.detailModel.subjectName];
+        cell.hideChatButton = YES;
+        return cell;
+    }
+    else if (indexPath.row == 1) { // 布置作业
+        AccompanyArrangeCell *cell  = [tableView dequeueReusableCellWithIdentifier:@"AccompanyArrangeCell"];
+        BOOL hasArrange = self.detailModel.decorateHomework == 1 ? YES : NO;
+        [cell configWithHomeworkContent:self.detailModel.content hasArrangeHomework:hasArrange];
+        return cell;
+    }
+    else if (indexPath.row == 2) { // 作业视频
+        // studentAttachments
+        BOOL canDisplay = self.detailModel.decorateHomework == 1 ? YES : NO;
+        AccompanyHomeworkCell *cell = [tableView dequeueReusableCellWithIdentifier:@"AccompanyHomeworkCell"];
+        MJWeakSelf;
+        [cell configWithAttachmentArray:self.fileArray canDisplaySubmitView:canDisplay callback:^(HOMEWORKACTION action, NSInteger viewIndex) {
+            [weakSelf operationActionWithType:action index:viewIndex];
+        }];
+        
+        return cell;
+    }
+    else { // 老师点评
+        AccompanyRemarkCell *cell = [tableView dequeueReusableCellWithIdentifier:@"AccompanyRemarkCell"];
+        BOOL hasEvaluate = self.detailModel.reviewHomework == 1? YES : NO;
+        [cell configWithRemarkMessage:self.detailModel.teacherReplied hasEvaluate:hasEvaluate];
+        return cell;
+    }
+}
+
+- (void)operationActionWithType:(HOMEWORKACTION)action index:(NSInteger)viewIndex {
+    switch (action) {
+        case HOMEWORKACTION_PLAY:
+        {
+            [self playVideoIndex:viewIndex];
+        }
+            break;
+        case HOMEWORKACTION_DELETE:
+        {
+            [self deleteVideoIndex:viewIndex];
+        }
+            break;
+        case HOMEWORKACTION_ADD: // 选择曲目
+        {
+            // 调用相册
+            self.mediaManager = [[KSMediaManager alloc] init];
+            self.mediaManager.mediaType = MEDIATYPE_VIDEO;
+            self.mediaManager.maxPhotoNumber = 1;
+            self.mediaManager.baseCtrl = self;
+            self.mediaManager.needCropImage = NO;
+            MJWeakSelf;
+            [self.mediaManager noAlertCallback:^(NSString * _Nullable videoUrl, NSMutableArray * _Nullable imageArray, NSMutableArray * _Nullable imageAsset) {
+                NSLog(@"%@", videoUrl);
+                // 上传视频
+                [weakSelf uploadVideoWithUrl:videoUrl];
+            }];
+            [self.mediaManager pushImagePickerController];
+        }
+        default:
+            break;
+    }
+}
+
+#pragma mark --- 上传视频文件
+- (void)uploadVideoWithUrl:(NSString *)videoUrl {
+    [self hudTipWillShow:YES];
+    NSData *fileData = [NSData dataWithContentsOfURL:[NSURL fileURLWithPath:videoUrl]];
+    [KSNetworkingManager videoFileUpload:KS_POST fileData:fileData progress:^(int64_t bytesWritten, int64_t totalBytes) {
+        dispatch_main_async_safe(^{
+            // 显示进度
+            if (self.HUD) {
+                self.HUD.progress = bytesWritten / totalBytes;// progress是回调进度
+            }
+        });
+    } success:^(NSDictionary * _Nonnull dic) {
+        [self hudTipWillShow:NO];
+        if ([dic integerValueForKey:@"code"] == 200 && [dic boolValueForKey:@"status"]) {
+            NSString *fileUrl = [[dic dictionaryValueForKey:@"data"] stringValueForKey:@"url"];
+            // 删除文件
+            [self removeVideoWithPath:videoUrl];
+            [self.fileArray addObject:fileUrl];
+            [self.tableView reloadData];
+        }
+        else {
+            [self MBPShow:MESSAGEKEY];
+            
+        }
+    } faliure:^(NSError * _Nonnull error) {
+        [self hudTipWillShow:NO];
+    }];
+}
+
+- (void)removeVideoWithPath:(NSString *)videoUrl {
+    NSFileManager *fileMamager = [NSFileManager defaultManager];
+    if ([fileMamager fileExistsAtPath:videoUrl]) {
+        [fileMamager removeItemAtPath:videoUrl error:nil];
+    }
+}
+
+// 播放
+- (void)playVideoIndex:(NSInteger)index {
+    if (self.fileArray.count > index) {
+        NSString *fileUrl = self.fileArray[index];
+        [self playVideoWithUrl:fileUrl];
+    }
+}
+// 删除
+- (void)deleteVideoIndex:(NSInteger)index {
+    if (self.fileArray.count > index) {
+        [self.fileArray removeObjectAtIndex:index];
+        [self.tableView reloadData];
+    }
+}
+
+#pragma mark ------ WMPlayer
+- (void)playVideoWithUrl:(NSString *)fileUrl {
+    fileUrl = [fileUrl stringByAddingPercentEncodingWithAllowedCharacters:[NSCharacterSet URLQueryAllowedCharacterSet]];
+    _playerFrame = CGRectMake(0, iPhoneXSafeTopMargin, kScreenWidth, kScreenHeight - iPhoneXSafeTopMargin - iPhoneXSafeBottomMargin);
+    _wmPlayer = [[WMPlayer alloc] initWithFrame:_playerFrame];
+    WMPlayerModel *playModel = [[WMPlayerModel alloc] init];
+    playModel.videoURL = [NSURL URLWithString:fileUrl];
+    _wmPlayer.playerModel = playModel;
+    _wmPlayer.delegate = self;
+    _bgView = [[UIView alloc] initWithFrame:CGRectMake(0, 0, kScreenWidth, kScreenHeight)];
+    _bgView.backgroundColor = [UIColor blackColor];
+    [[UIApplication sharedApplication].keyWindow addSubview:_bgView];
+    [[UIApplication sharedApplication].keyWindow addSubview:_wmPlayer];
+    [[UIApplication sharedApplication].keyWindow bringSubviewToFront:_wmPlayer];
+    
+    [_wmPlayer play];
+}
+
+- (void)wmplayer:(WMPlayer *)wmplayer clickedCloseButton:(UIButton *)backBtn {
+    [wmplayer removePlayer];
+    [_bgView removeFromSuperview];
+    [self setNeedsStatusBarAppearanceUpdate];
+}
+
+- (void)wmplayer:(WMPlayer *)wmplayer clickedFullScreenButton:(UIButton *)fullScreenBtn {
+    self.isRatation = !self.isRatation;
+    
+    if (self.isRatation) {
+        [wmplayer removeFromSuperview];
+        [UIView animateWithDuration:1.0f animations:^{
+            wmplayer.transform = CGAffineTransformMakeRotation(M_PI_2);
+            
+        } completion:^(BOOL finished) {
+            wmplayer.frame = CGRectMake(0, iPhoneXSafeTopMargin, kScreenWidth, kScreenHeight - iPhoneXSafeTopMargin - iPhoneXSafeBottomMargin);
+            [[UIApplication sharedApplication].keyWindow addSubview:wmplayer];
+            [[UIApplication sharedApplication].keyWindow bringSubviewToFront:wmplayer];
+        }];
+    }
+    else {
+        [wmplayer removeFromSuperview];
+        
+        [UIView animateWithDuration:1.0f animations:^{
+            //        复原
+            wmplayer.transform = CGAffineTransformIdentity;
+            
+        } completion:^(BOOL finished) {
+            wmplayer.frame = CGRectMake(0, iPhoneXSafeTopMargin, kScreenWidth, kScreenHeight - iPhoneXSafeTopMargin - iPhoneXSafeBottomMargin);
+            [[UIApplication sharedApplication].keyWindow addSubview:wmplayer];
+            [[UIApplication sharedApplication].keyWindow bringSubviewToFront:wmplayer];
+        }];
+    }
+}
+
+- (void)submitHomeworkAction {
+    if (self.fileArray.count == 0) {
+        [self MBPShow:@"请选择作业视频"];
+        return;
+    }
+    NSString *attachment = [self.fileArray componentsJoinedByString:@","];
+    [self showhud];
+    [KSNetworkingManager homeSubmitAction:KS_POST courseScheduleId:self.courseId attachment:attachment success:^(NSDictionary * _Nonnull dic) {
+        [self removehub];
+        if ([dic integerValueForKey:@"code"] == 200 && [dic boolValueForKey:@"status"]) {
+            [self MBPShow:@"作业提交成功"];
+            [self requestCourseMessage];
+        }
+        else {
+            [self MBPShow:MESSAGEKEY];
+        }
+    } faliure:^(NSError * _Nonnull error) {
+        [self removehub];
+    }];
+}
+
+#pragma mark --- lazying
+- (HomeworkBottomView *)bottomView {
+    if (!_bottomView) {
+        _bottomView = [HomeworkBottomView shareInstance];
+        _bottomView.frame = CGRectMake(0, 0, kScreenWidth, 70);
+        MJWeakSelf;
+        [_bottomView sureAction:^{
+            [weakSelf submitHomeworkAction];
+        }];
+    }
+    return _bottomView;
+}
+
+- (UITableView *)tableView {
+    if (!_tableView) {
+        _tableView = [[UITableView alloc] initWithFrame:CGRectZero style:UITableViewStylePlain];
+        _tableView.backgroundColor = [UIColor clearColor];
+        _tableView.delegate = self;
+        _tableView.dataSource = self;
+        _tableView.separatorStyle = UITableViewCellSeparatorStyleNone;
+        _tableView.showsHorizontalScrollIndicator = NO;
+        _tableView.showsVerticalScrollIndicator = NO;
+        _tableView.rowHeight = UITableViewAutomaticDimension;
+        _tableView.estimatedRowHeight = 136.0f;
+        [_tableView registerNib:[UINib nibWithNibName:@"AccompanyCourseInfoCell" bundle:[NSBundle mainBundle]] forCellReuseIdentifier:@"AccompanyCourseInfoCell"];
+        [_tableView registerNib:[UINib nibWithNibName:@"AccompanyArrangeCell" bundle:[NSBundle mainBundle]] forCellReuseIdentifier:@"AccompanyArrangeCell"];
+        [_tableView registerNib:[UINib nibWithNibName:@"AccompanyHomeworkCell" bundle:[NSBundle mainBundle]] forCellReuseIdentifier:@"AccompanyHomeworkCell"];
+        [_tableView registerNib:[UINib nibWithNibName:@"AccompanyRemarkCell" bundle:[NSBundle mainBundle]] forCellReuseIdentifier:@"AccompanyRemarkCell"];
+        _tableView.tableFooterView = self.bottomView;
+        
+    }
+    return _tableView;
+}
+
+- (void)hudTipWillShow:(BOOL)willShow{
+    if (willShow) {
+        [self resignFirstResponder];
+        UIWindow *keyWindow = [UIApplication sharedApplication].keyWindow;
+        if (!_HUD) {
+            _HUD = [MBProgressHUD showHUDAddedTo:keyWindow animated:YES];
+            _HUD.removeFromSuperViewOnHide = YES;
+            _HUD.mode = MBProgressHUDModeDeterminateHorizontalBar;
+            _HUD.label.text = @"正在上传视频文件...";
+            _HUD.contentColor = [UIColor whiteColor];
+            _HUD.bezelView.style = MBProgressHUDBackgroundStyleSolidColor;
+            _HUD.bezelView.backgroundColor = [UIColor colorWithHexString:@"#000000" alpha:0.8];
+        }else{
+            _HUD.progress = 0;
+            [keyWindow addSubview:_HUD];
+            [_HUD showAnimated:YES];
+        }
+    }else{
+        [_HUD hideAnimated:YES];
+    }
+}
+/*
+#pragma mark - Navigation
+
+// In a storyboard-based application, you will often want to do a little preparation before navigation
+- (void)prepareForSegue:(UIStoryboardSegue *)segue sender:(id)sender {
+    // Get the new view controller using [segue destinationViewController].
+    // Pass the selected object to the new view controller.
+}
+*/
+
+@end

+ 23 - 0
KulexiuForStudent/KulexiuForStudent/Module/Mine/Homework/Controller/HomeworkListViewController.h

@@ -0,0 +1,23 @@
+//
+//  HomeworkListViewController.h
+//  KulexiuForStudent
+//
+//  Created by 王智 on 2022/4/19.
+//
+
+#import "KSBaseViewController.h"
+#import "JXCategoryView.h"
+#import "JXPagerView.h"
+
+NS_ASSUME_NONNULL_BEGIN
+
+@interface HomeworkListViewController : KSBaseViewController
+
+@property (nonatomic, strong) JXPagerView *pagerView;
+@property (nonatomic, strong, readonly) JXCategoryTitleView *categoryView;
+@property (nonatomic, strong) NSArray <NSString *> *titles;
+
+@end
+
+
+NS_ASSUME_NONNULL_END

+ 153 - 0
KulexiuForStudent/KulexiuForStudent/Module/Mine/Homework/Controller/HomeworkListViewController.m

@@ -0,0 +1,153 @@
+//
+//  HomeworkListViewController.m
+//  KulexiuForStudent
+//
+//  Created by 王智 on 2022/4/19.
+//
+
+#import "HomeworkListViewController.h"
+#import "JXCategoryView.h"
+#import "JXPagerListRefreshView.h"
+#import "HomeworkBodyView.h"
+
+
+@interface HomeworkListViewController ()<JXPagerViewDelegate, JXPagerMainTableViewGestureDelegate,JXCategoryViewDelegate>
+
+@property (nonatomic, assign) NSInteger selectedIndex;
+
+@property (nonatomic, strong) NSMutableArray *listViewArray;
+
+@property (nonatomic, assign) CGFloat headHeight;
+
+
+@end
+
+@implementation HomeworkListViewController
+
+- (void)viewDidLoad {
+    [super viewDidLoad];
+    // Do any additional setup after loading the view.
+    [self allocTitle:@"我的作业"];
+    self.titles = @[@"未提交",@"已提交"];
+    [self setupUI];
+}
+
+- (void)setupUI {
+    self.headHeight = 64.0f;
+    [self.scrollView removeFromSuperview];
+    self.view.backgroundColor = HexRGB(0xf6f8f9);
+    
+    _categoryView = [[JXCategoryTitleView alloc] initWithFrame:CGRectMake(0, 0, kScreenWidth, self.headHeight)];
+    self.categoryView.titles = self.titles;
+    self.categoryView.delegate = self;
+    self.categoryView.titleFont = [UIFont systemFontOfSize:17.0f];
+    self.categoryView.titleSelectedFont = [UIFont systemFontOfSize:17.0f weight:UIFontWeightMedium];
+    self.categoryView.titleSelectedColor = HexRGB(0x333333);
+    self.categoryView.titleColor = HexRGB(0x666666);
+    self.categoryView.titleColorGradientEnabled = YES;
+    self.categoryView.backgroundColor = [UIColor whiteColor];
+    
+    JXCategoryIndicatorLineView *lineView = [[JXCategoryIndicatorLineView alloc] init];
+    lineView.indicatorColor = THEMECOLOR;
+    lineView.indicatorWidth = 28;
+    self.categoryView.indicators = @[lineView];
+    
+    _pagerView = [self preferredPagingView];
+    self.pagerView.frame = CGRectMake(0, 0, kScreenWidth, kScreenHeight - kNaviBarHeight - iPhoneXSafeBottomMargin);
+    self.pagerView.backgroundColor = [UIColor clearColor];
+    self.pagerView.mainTableView.backgroundColor = [UIColor clearColor];
+    self.pagerView.listContainerView.backgroundColor = [UIColor clearColor];
+    self.pagerView.mainTableView.gestureDelegate = self;
+    self.categoryView.listContainer = (id<JXCategoryViewListContainer>)self.pagerView.listContainerView;
+    self.pagerView.listContainerView.listCellBackgroundColor = [UIColor clearColor];
+    [self.view addSubview:self.pagerView];
+}
+
+- (void)viewWillAppear:(BOOL)animated {
+    [super viewWillAppear:animated];
+    self.navigationController.interactivePopGestureRecognizer.enabled = YES;
+    if (self.listViewArray.count > self.categoryView.selectedIndex) {
+        id value = self.listViewArray[self.categoryView.selectedIndex];
+        if ([value isKindOfClass:[HomeworkBodyView class]]) {
+            HomeworkBodyView *listView = (HomeworkBodyView *)value;
+            [listView beginFirstRefresh];
+        }
+    }
+}
+
+- (void)viewDidAppear:(BOOL)animated {
+    [super viewDidAppear:animated];
+    self.navigationController.interactivePopGestureRecognizer.enabled = (self.categoryView.selectedIndex == 0);
+}
+
+- (JXPagerView *)preferredPagingView {
+    return [[JXPagerListRefreshView alloc] initWithDelegate:self];
+}
+
+#pragma mark - JXPagerViewDelegate
+
+- (UIView *)tableHeaderViewInPagerView:(JXPagerView *)pagerView {
+    return [UIView new];
+}
+
+- (NSUInteger)tableHeaderViewHeightInPagerView:(JXPagerView *)pagerView {
+    return CGFLOAT_MIN;
+}
+
+- (NSUInteger)heightForPinSectionHeaderInPagerView:(JXPagerView *)pagerView {
+    return self.headHeight;
+}
+
+- (UIView *)viewForPinSectionHeaderInPagerView:(JXPagerView *)pagerView {
+    return self.categoryView;
+}
+
+- (NSInteger)numberOfListsInPagerView:(JXPagerView *)pagerView {
+    //和categoryView的item数量一致
+    return self.titles.count;
+}
+
+- (id<JXPagerViewListViewDelegate>)pagerView:(JXPagerView *)pagerView initListAtIndex:(NSInteger)index {
+    HomeworkBodyView *listView = [[HomeworkBodyView alloc] init];
+    listView.naviController = self.navigationController;
+    [self.listViewArray replaceObjectAtIndex:index withObject:listView];
+    self.listViewArray[index] = listView;
+    listView.selectIndex = index;
+    [listView beginFirstRefresh];
+    return listView;
+}
+
+#pragma mark - JXCategoryViewDelegate
+- (void)categoryView:(JXCategoryBaseView *)categoryView didSelectedItemAtIndex:(NSInteger)index {
+    self.navigationController.interactivePopGestureRecognizer.enabled = (index == 0);
+}
+
+
+#pragma mark - JXPagerMainTableViewGestureDelegate
+
+- (BOOL)mainTableViewGestureRecognizer:(UIGestureRecognizer *)gestureRecognizer shouldRecognizeSimultaneouslyWithGestureRecognizer:(UIGestureRecognizer *)otherGestureRecognizer {
+    //禁止categoryView左右滑动的时候,上下和左右都可以滚动
+    if (otherGestureRecognizer == self.categoryView.collectionView.panGestureRecognizer) {
+        return NO;
+    }
+    return [gestureRecognizer isKindOfClass:[UIPanGestureRecognizer class]] && [otherGestureRecognizer isKindOfClass:[UIPanGestureRecognizer class]];
+}
+
+
+- (NSMutableArray *)listViewArray {
+    if (!_listViewArray) {
+        _listViewArray = [NSMutableArray arrayWithArray:@[@"",@""]];
+    }
+    return _listViewArray;
+}
+/*
+#pragma mark - Navigation
+
+// In a storyboard-based application, you will often want to do a little preparation before navigation
+- (void)prepareForSegue:(UIStoryboardSegue *)segue sender:(id)sender {
+    // Get the new view controller using [segue destinationViewController].
+    // Pass the selected object to the new view controller.
+}
+*/
+
+@end

+ 45 - 0
KulexiuForStudent/KulexiuForStudent/Module/Mine/Homework/Model/HomeworkDetailModel.h

@@ -0,0 +1,45 @@
+//
+//  HomeworkDetailModel.h
+//
+//  Created by Steven  on 2022/4/18
+//  Copyright (c) 2022 __MyCompanyName__. All rights reserved.
+//
+
+#import <Foundation/Foundation.h>
+
+
+
+@interface HomeworkDetailModel : NSObject <NSCoding, NSCopying>
+
+@property (nonatomic, strong) NSString *courseStatus;
+@property (nonatomic, strong) NSString *content;
+@property (nonatomic, strong) NSString *studentName;
+@property (nonatomic, strong) NSString *courseScheduleId;
+@property (nonatomic, strong) NSString *title;
+@property (nonatomic, assign) double submitHomework;
+@property (nonatomic, assign) double studentHomeworkId;
+@property (nonatomic, strong) NSString *teacherName;
+@property (nonatomic, strong) NSString *decorateTime;
+@property (nonatomic, strong) NSString *endTime;
+@property (nonatomic, strong) NSString *teacherReplied;
+@property (nonatomic, strong) NSString *subjectName;
+@property (nonatomic, strong) NSString *internalBaseClassIdentifier;
+@property (nonatomic, strong) NSString *submitTime;
+@property (nonatomic, strong) NSString *studentAttachments;
+@property (nonatomic, strong) NSString *courseType;
+@property (nonatomic, assign) double decorateHomework;
+@property (nonatomic, strong) NSString *attachments;
+@property (nonatomic, strong) NSString *courseGroupId;
+@property (nonatomic, strong) NSString *studentAvatar;
+@property (nonatomic, strong) NSString *startTime;
+@property (nonatomic, strong) NSString *classDate;
+@property (nonatomic, strong) NSString *teacherAvatar;
+@property (nonatomic, assign) double reviewHomework;
+@property (nonatomic, strong) NSString *studentId;
+@property (nonatomic, strong) NSString *teacherId;
+
++ (instancetype)modelObjectWithDictionary:(NSDictionary *)dict;
+- (instancetype)initWithDictionary:(NSDictionary *)dict;
+- (NSDictionary *)dictionaryRepresentation;
+
+@end

+ 270 - 0
KulexiuForStudent/KulexiuForStudent/Module/Mine/Homework/Model/HomeworkDetailModel.m

@@ -0,0 +1,270 @@
+//
+//  HomeworkDetailModel.m
+//
+//  Created by Steven  on 2022/4/18
+//  Copyright (c) 2022 __MyCompanyName__. All rights reserved.
+//
+
+#import "HomeworkDetailModel.h"
+
+
+NSString *const kHomeworkDetailModelCourseStatus = @"courseStatus";
+NSString *const kHomeworkDetailModelContent = @"content";
+NSString *const kHomeworkDetailModelStudentName = @"studentName";
+NSString *const kHomeworkDetailModelCourseScheduleId = @"courseScheduleId";
+NSString *const kHomeworkDetailModelTitle = @"title";
+NSString *const kHomeworkDetailModelSubmitHomework = @"submitHomework";
+NSString *const kHomeworkDetailModelStudentHomeworkId = @"studentHomeworkId";
+NSString *const kHomeworkDetailModelTeacherName = @"teacherName";
+NSString *const kHomeworkDetailModelDecorateTime = @"decorateTime";
+NSString *const kHomeworkDetailModelEndTime = @"endTime";
+NSString *const kHomeworkDetailModelTeacherReplied = @"teacherReplied";
+NSString *const kHomeworkDetailModelSubjectName = @"subjectName";
+NSString *const kHomeworkDetailModelId = @"id";
+NSString *const kHomeworkDetailModelSubmitTime = @"submitTime";
+NSString *const kHomeworkDetailModelStudentAttachments = @"studentAttachments";
+NSString *const kHomeworkDetailModelCourseType = @"courseType";
+NSString *const kHomeworkDetailModelDecorateHomework = @"decorateHomework";
+NSString *const kHomeworkDetailModelAttachments = @"attachments";
+NSString *const kHomeworkDetailModelCourseGroupId = @"courseGroupId";
+NSString *const kHomeworkDetailModelStudentAvatar = @"studentAvatar";
+NSString *const kHomeworkDetailModelStartTime = @"startTime";
+NSString *const kHomeworkDetailModelClassDate = @"classDate";
+NSString *const kHomeworkDetailModelTeacherAvatar = @"teacherAvatar";
+NSString *const kHomeworkDetailModelReviewHomework = @"reviewHomework";
+NSString *const kHomeworkDetailModelStudentId = @"studentId";
+NSString *const kHomeworkDetailModelTeacherId = @"teacherId";
+
+@interface HomeworkDetailModel ()
+
+- (id)objectOrNilForKey:(id)aKey fromDictionary:(NSDictionary *)dict;
+
+@end
+
+@implementation HomeworkDetailModel
+
+@synthesize courseStatus = _courseStatus;
+@synthesize content = _content;
+@synthesize studentName = _studentName;
+@synthesize courseScheduleId = _courseScheduleId;
+@synthesize title = _title;
+@synthesize submitHomework = _submitHomework;
+@synthesize studentHomeworkId = _studentHomeworkId;
+@synthesize teacherName = _teacherName;
+@synthesize decorateTime = _decorateTime;
+@synthesize endTime = _endTime;
+@synthesize teacherReplied = _teacherReplied;
+@synthesize subjectName = _subjectName;
+@synthesize internalBaseClassIdentifier = _internalBaseClassIdentifier;
+@synthesize submitTime = _submitTime;
+@synthesize studentAttachments = _studentAttachments;
+@synthesize courseType = _courseType;
+@synthesize decorateHomework = _decorateHomework;
+@synthesize attachments = _attachments;
+@synthesize courseGroupId = _courseGroupId;
+@synthesize studentAvatar = _studentAvatar;
+@synthesize startTime = _startTime;
+@synthesize classDate = _classDate;
+@synthesize teacherAvatar = _teacherAvatar;
+@synthesize reviewHomework = _reviewHomework;
+@synthesize studentId = _studentId;
+@synthesize teacherId = _teacherId;
+
++ (instancetype)modelObjectWithDictionary:(NSDictionary *)dict
+{
+    return [[self alloc] initWithDictionary:dict];
+}
+
+- (instancetype)initWithDictionary:(NSDictionary *)dict
+{
+    self = [super init];
+    
+    // This check serves to make sure that a non-NSDictionary object
+    // passed into the model class doesn't break the parsing.
+    if(self && [dict isKindOfClass:[NSDictionary class]]) {
+            self.courseStatus = [self objectOrNilForKey:kHomeworkDetailModelCourseStatus fromDictionary:dict];
+            self.content = [self objectOrNilForKey:kHomeworkDetailModelContent fromDictionary:dict];
+            self.studentName = [self objectOrNilForKey:kHomeworkDetailModelStudentName fromDictionary:dict];
+            self.courseScheduleId = [self objectOrNilForKey:kHomeworkDetailModelCourseScheduleId fromDictionary:dict];
+            self.title = [self objectOrNilForKey:kHomeworkDetailModelTitle fromDictionary:dict];
+            self.submitHomework = [[self objectOrNilForKey:kHomeworkDetailModelSubmitHomework fromDictionary:dict] doubleValue];
+            self.studentHomeworkId = [[self objectOrNilForKey:kHomeworkDetailModelStudentHomeworkId fromDictionary:dict] doubleValue];
+            self.teacherName = [self objectOrNilForKey:kHomeworkDetailModelTeacherName fromDictionary:dict];
+            self.decorateTime = [self objectOrNilForKey:kHomeworkDetailModelDecorateTime fromDictionary:dict];
+            self.endTime = [self objectOrNilForKey:kHomeworkDetailModelEndTime fromDictionary:dict];
+            self.teacherReplied = [self objectOrNilForKey:kHomeworkDetailModelTeacherReplied fromDictionary:dict];
+            self.subjectName = [self objectOrNilForKey:kHomeworkDetailModelSubjectName fromDictionary:dict];
+            self.internalBaseClassIdentifier = [self objectOrNilForKey:kHomeworkDetailModelId fromDictionary:dict];
+            self.submitTime = [self objectOrNilForKey:kHomeworkDetailModelSubmitTime fromDictionary:dict];
+            self.studentAttachments = [self objectOrNilForKey:kHomeworkDetailModelStudentAttachments fromDictionary:dict];
+            self.courseType = [self objectOrNilForKey:kHomeworkDetailModelCourseType fromDictionary:dict];
+            self.decorateHomework = [[self objectOrNilForKey:kHomeworkDetailModelDecorateHomework fromDictionary:dict] doubleValue];
+            self.attachments = [self objectOrNilForKey:kHomeworkDetailModelAttachments fromDictionary:dict];
+            self.courseGroupId = [self objectOrNilForKey:kHomeworkDetailModelCourseGroupId fromDictionary:dict];
+            self.studentAvatar = [self objectOrNilForKey:kHomeworkDetailModelStudentAvatar fromDictionary:dict];
+            self.startTime = [self objectOrNilForKey:kHomeworkDetailModelStartTime fromDictionary:dict];
+            self.classDate = [self objectOrNilForKey:kHomeworkDetailModelClassDate fromDictionary:dict];
+            self.teacherAvatar = [self objectOrNilForKey:kHomeworkDetailModelTeacherAvatar fromDictionary:dict];
+            self.reviewHomework = [[self objectOrNilForKey:kHomeworkDetailModelReviewHomework fromDictionary:dict] doubleValue];
+        self.studentId = [self objectOrNilForKey:kHomeworkDetailModelStudentId fromDictionary:dict];
+        self.teacherId = [self objectOrNilForKey:kHomeworkDetailModelTeacherId fromDictionary:dict];
+    }
+    
+    return self;
+    
+}
+
+- (NSDictionary *)dictionaryRepresentation
+{
+    NSMutableDictionary *mutableDict = [NSMutableDictionary dictionary];
+    [mutableDict setValue:self.courseStatus forKey:kHomeworkDetailModelCourseStatus];
+    [mutableDict setValue:self.content forKey:kHomeworkDetailModelContent];
+    [mutableDict setValue:self.studentName forKey:kHomeworkDetailModelStudentName];
+    [mutableDict setValue:self.courseScheduleId forKey:kHomeworkDetailModelCourseScheduleId];
+    [mutableDict setValue:self.title forKey:kHomeworkDetailModelTitle];
+    [mutableDict setValue:[NSNumber numberWithDouble:self.submitHomework] forKey:kHomeworkDetailModelSubmitHomework];
+    [mutableDict setValue:[NSNumber numberWithDouble:self.studentHomeworkId] forKey:kHomeworkDetailModelStudentHomeworkId];
+    [mutableDict setValue:self.teacherName forKey:kHomeworkDetailModelTeacherName];
+    [mutableDict setValue:self.decorateTime forKey:kHomeworkDetailModelDecorateTime];
+    [mutableDict setValue:self.endTime forKey:kHomeworkDetailModelEndTime];
+    [mutableDict setValue:self.teacherReplied forKey:kHomeworkDetailModelTeacherReplied];
+    [mutableDict setValue:self.subjectName forKey:kHomeworkDetailModelSubjectName];
+    [mutableDict setValue:self.internalBaseClassIdentifier forKey:kHomeworkDetailModelId];
+    [mutableDict setValue:self.submitTime forKey:kHomeworkDetailModelSubmitTime];
+    [mutableDict setValue:self.studentAttachments forKey:kHomeworkDetailModelStudentAttachments];
+    [mutableDict setValue:self.courseType forKey:kHomeworkDetailModelCourseType];
+    [mutableDict setValue:[NSNumber numberWithDouble:self.decorateHomework] forKey:kHomeworkDetailModelDecorateHomework];
+    [mutableDict setValue:self.attachments forKey:kHomeworkDetailModelAttachments];
+    [mutableDict setValue:self.courseGroupId forKey:kHomeworkDetailModelCourseGroupId];
+    [mutableDict setValue:self.studentAvatar forKey:kHomeworkDetailModelStudentAvatar];
+    [mutableDict setValue:self.startTime forKey:kHomeworkDetailModelStartTime];
+    [mutableDict setValue:self.classDate forKey:kHomeworkDetailModelClassDate];
+    [mutableDict setValue:self.teacherAvatar forKey:kHomeworkDetailModelTeacherAvatar];
+    [mutableDict setValue:[NSNumber numberWithDouble:self.reviewHomework] forKey:kHomeworkDetailModelReviewHomework];
+    [mutableDict setValue:self.studentId forKey:kHomeworkDetailModelStudentId];
+    [mutableDict setValue:self.teacherId forKey:kHomeworkDetailModelTeacherId];
+    return [NSDictionary dictionaryWithDictionary:mutableDict];
+}
+
+- (NSString *)description 
+{
+    return [NSString stringWithFormat:@"%@", [self dictionaryRepresentation]];
+}
+
+#pragma mark - Helper Method
+- (id)objectOrNilForKey:(id)aKey fromDictionary:(NSDictionary *)dict
+{
+    id object = [dict objectForKey:aKey];
+    if ([object isKindOfClass:[NSNumber class]]) {
+        NSNumber *number = object;
+        object = [number stringValue];
+    }
+    return [object isEqual:[NSNull null]] ? nil : object;
+}
+
+
+#pragma mark - NSCoding Methods
+
+- (id)initWithCoder:(NSCoder *)aDecoder
+{
+    self = [super init];
+
+    self.courseStatus = [aDecoder decodeObjectForKey:kHomeworkDetailModelCourseStatus];
+    self.content = [aDecoder decodeObjectForKey:kHomeworkDetailModelContent];
+    self.studentName = [aDecoder decodeObjectForKey:kHomeworkDetailModelStudentName];
+    self.courseScheduleId = [aDecoder decodeObjectForKey:kHomeworkDetailModelCourseScheduleId];
+    self.title = [aDecoder decodeObjectForKey:kHomeworkDetailModelTitle];
+    self.submitHomework = [aDecoder decodeDoubleForKey:kHomeworkDetailModelSubmitHomework];
+    self.studentHomeworkId = [aDecoder decodeDoubleForKey:kHomeworkDetailModelStudentHomeworkId];
+    self.teacherName = [aDecoder decodeObjectForKey:kHomeworkDetailModelTeacherName];
+    self.decorateTime = [aDecoder decodeObjectForKey:kHomeworkDetailModelDecorateTime];
+    self.endTime = [aDecoder decodeObjectForKey:kHomeworkDetailModelEndTime];
+    self.teacherReplied = [aDecoder decodeObjectForKey:kHomeworkDetailModelTeacherReplied];
+    self.subjectName = [aDecoder decodeObjectForKey:kHomeworkDetailModelSubjectName];
+    self.internalBaseClassIdentifier = [aDecoder decodeObjectForKey:kHomeworkDetailModelId];
+    self.submitTime = [aDecoder decodeObjectForKey:kHomeworkDetailModelSubmitTime];
+    self.studentAttachments = [aDecoder decodeObjectForKey:kHomeworkDetailModelStudentAttachments];
+    self.courseType = [aDecoder decodeObjectForKey:kHomeworkDetailModelCourseType];
+    self.decorateHomework = [aDecoder decodeDoubleForKey:kHomeworkDetailModelDecorateHomework];
+    self.attachments = [aDecoder decodeObjectForKey:kHomeworkDetailModelAttachments];
+    self.courseGroupId = [aDecoder decodeObjectForKey:kHomeworkDetailModelCourseGroupId];
+    self.studentAvatar = [aDecoder decodeObjectForKey:kHomeworkDetailModelStudentAvatar];
+    self.startTime = [aDecoder decodeObjectForKey:kHomeworkDetailModelStartTime];
+    self.classDate = [aDecoder decodeObjectForKey:kHomeworkDetailModelClassDate];
+    self.teacherAvatar = [aDecoder decodeObjectForKey:kHomeworkDetailModelTeacherAvatar];
+    self.reviewHomework = [aDecoder decodeDoubleForKey:kHomeworkDetailModelReviewHomework];
+    self.studentId = [aDecoder decodeObjectForKey:kHomeworkDetailModelStudentId];
+    self.teacherId = [aDecoder decodeObjectForKey:kHomeworkDetailModelTeacherId];
+    return self;
+}
+
+- (void)encodeWithCoder:(NSCoder *)aCoder
+{
+
+    [aCoder encodeObject:_courseStatus forKey:kHomeworkDetailModelCourseStatus];
+    [aCoder encodeObject:_content forKey:kHomeworkDetailModelContent];
+    [aCoder encodeObject:_studentName forKey:kHomeworkDetailModelStudentName];
+    [aCoder encodeObject:_courseScheduleId forKey:kHomeworkDetailModelCourseScheduleId];
+    [aCoder encodeObject:_title forKey:kHomeworkDetailModelTitle];
+    [aCoder encodeDouble:_submitHomework forKey:kHomeworkDetailModelSubmitHomework];
+    [aCoder encodeDouble:_studentHomeworkId forKey:kHomeworkDetailModelStudentHomeworkId];
+    [aCoder encodeObject:_teacherName forKey:kHomeworkDetailModelTeacherName];
+    [aCoder encodeObject:_decorateTime forKey:kHomeworkDetailModelDecorateTime];
+    [aCoder encodeObject:_endTime forKey:kHomeworkDetailModelEndTime];
+    [aCoder encodeObject:_teacherReplied forKey:kHomeworkDetailModelTeacherReplied];
+    [aCoder encodeObject:_subjectName forKey:kHomeworkDetailModelSubjectName];
+    [aCoder encodeObject:_internalBaseClassIdentifier forKey:kHomeworkDetailModelId];
+    [aCoder encodeObject:_submitTime forKey:kHomeworkDetailModelSubmitTime];
+    [aCoder encodeObject:_studentAttachments forKey:kHomeworkDetailModelStudentAttachments];
+    [aCoder encodeObject:_courseType forKey:kHomeworkDetailModelCourseType];
+    [aCoder encodeDouble:_decorateHomework forKey:kHomeworkDetailModelDecorateHomework];
+    [aCoder encodeObject:_attachments forKey:kHomeworkDetailModelAttachments];
+    [aCoder encodeObject:_courseGroupId forKey:kHomeworkDetailModelCourseGroupId];
+    [aCoder encodeObject:_studentAvatar forKey:kHomeworkDetailModelStudentAvatar];
+    [aCoder encodeObject:_startTime forKey:kHomeworkDetailModelStartTime];
+    [aCoder encodeObject:_classDate forKey:kHomeworkDetailModelClassDate];
+    [aCoder encodeObject:_teacherAvatar forKey:kHomeworkDetailModelTeacherAvatar];
+    [aCoder encodeDouble:_reviewHomework forKey:kHomeworkDetailModelReviewHomework];
+    [aCoder encodeObject:_studentId forKey:kHomeworkDetailModelStudentId];
+    [aCoder encodeObject:_teacherId forKey:kHomeworkDetailModelTeacherId];
+}
+
+- (id)copyWithZone:(NSZone *)zone
+{
+    HomeworkDetailModel *copy = [[HomeworkDetailModel alloc] init];
+    
+    if (copy) {
+
+        copy.courseStatus = [self.courseStatus copyWithZone:zone];
+        copy.content = [self.content copyWithZone:zone];
+        copy.studentName = [self.studentName copyWithZone:zone];
+        copy.courseScheduleId = [self.courseScheduleId copyWithZone:zone];
+        copy.title = [self.title copyWithZone:zone];
+        copy.submitHomework = self.submitHomework;
+        copy.studentHomeworkId = self.studentHomeworkId;
+        copy.teacherName = [self.teacherName copyWithZone:zone];
+        copy.decorateTime = [self.decorateTime copyWithZone:zone];
+        copy.endTime = [self.endTime copyWithZone:zone];
+        copy.teacherReplied = [self.teacherReplied copyWithZone:zone];
+        copy.subjectName = [self.subjectName copyWithZone:zone];
+        copy.internalBaseClassIdentifier = [self.internalBaseClassIdentifier copyWithZone:zone];
+        copy.submitTime = [self.submitTime copyWithZone:zone];
+        copy.studentAttachments = [self.studentAttachments copyWithZone:zone];
+        copy.courseType = [self.courseType copyWithZone:zone];
+        copy.decorateHomework = self.decorateHomework;
+        copy.attachments = [self.attachments copyWithZone:zone];
+        copy.courseGroupId = [self.courseGroupId copyWithZone:zone];
+        copy.studentAvatar = [self.studentAvatar copyWithZone:zone];
+        copy.startTime = [self.startTime copyWithZone:zone];
+        copy.classDate = [self.classDate copyWithZone:zone];
+        copy.teacherAvatar = [self.teacherAvatar copyWithZone:zone];
+        copy.reviewHomework = self.reviewHomework;
+        copy.studentId = [self.studentId copyWithZone:zone];
+        copy.teacherId = [self.teacherId copyWithZone:zone];
+    }
+    
+    return copy;
+}
+
+
+@end

+ 34 - 0
KulexiuForStudent/KulexiuForStudent/Module/Mine/Homework/Model/HomeworkListModel.h

@@ -0,0 +1,34 @@
+//
+//  HomeworkListModel.h
+//
+//  Created by Steven  on 2022/4/18
+//  Copyright (c) 2022 __MyCompanyName__. All rights reserved.
+//
+
+#import <Foundation/Foundation.h>
+
+
+
+@interface HomeworkListModel : NSObject <NSCoding, NSCopying>
+
+@property (nonatomic, strong) NSString *courseGroupId;
+@property (nonatomic, strong) NSString *classDate;
+@property (nonatomic, strong) NSString *teacherAvatar;
+@property (nonatomic, strong) NSString *decorateTime;
+@property (nonatomic, assign) double absenteeism;
+@property (nonatomic, strong) NSString *courseId;
+@property (nonatomic, strong) NSString *teacherName;
+@property (nonatomic, strong) NSString *studentId;
+@property (nonatomic, strong) NSString *studentName;
+@property (nonatomic, strong) NSString *subjectName;
+@property (nonatomic, strong) NSString *endTime;
+@property (nonatomic, strong) NSString *studentAvatar;
+@property (nonatomic, strong) NSString *submitTime;
+@property (nonatomic, strong) NSString *startTime;
+@property (nonatomic, strong) NSString *teacherId;
+
++ (instancetype)modelObjectWithDictionary:(NSDictionary *)dict;
+- (instancetype)initWithDictionary:(NSDictionary *)dict;
+- (NSDictionary *)dictionaryRepresentation;
+
+@end

+ 193 - 0
KulexiuForStudent/KulexiuForStudent/Module/Mine/Homework/Model/HomeworkListModel.m

@@ -0,0 +1,193 @@
+//
+//  HomeworkListModel.m
+//
+//  Created by Steven  on 2022/4/18
+//  Copyright (c) 2022 __MyCompanyName__. All rights reserved.
+//
+
+#import "HomeworkListModel.h"
+
+
+NSString *const kHomeworkListModelCourseGroupId = @"courseGroupId";
+NSString *const kHomeworkListModelClassDate = @"classDate";
+NSString *const kHomeworkListModelTeacherAvatar = @"teacherAvatar";
+NSString *const kHomeworkListModelDecorateTime = @"decorateTime";
+NSString *const kHomeworkListModelAbsenteeism = @"absenteeism";
+NSString *const kHomeworkListModelCourseId = @"courseId";
+NSString *const kHomeworkListModelTeacherName = @"teacherName";
+NSString *const kHomeworkListModelStudentName = @"studentName";
+NSString *const kHomeworkListModelSubjectName = @"subjectName";
+NSString *const kHomeworkListModelEndTime = @"endTime";
+NSString *const kHomeworkListModelStudentAvatar = @"studentAvatar";
+NSString *const kHomeworkListModelSubmitTime = @"submitTime";
+NSString *const kHomeworkListModelStartTime = @"startTime";
+NSString *const kHomeworkListModelStudentId = @"studentId";
+NSString *const kHomeworkListModelTeacherId = @"teacherId";
+
+@interface HomeworkListModel ()
+
+- (id)objectOrNilForKey:(id)aKey fromDictionary:(NSDictionary *)dict;
+
+@end
+
+@implementation HomeworkListModel
+
+@synthesize courseGroupId = _courseGroupId;
+@synthesize classDate = _classDate;
+@synthesize teacherAvatar = _teacherAvatar;
+@synthesize decorateTime = _decorateTime;
+@synthesize absenteeism = _absenteeism;
+@synthesize courseId = _courseId;
+@synthesize teacherName = _teacherName;
+@synthesize studentName = _studentName;
+@synthesize subjectName = _subjectName;
+@synthesize endTime = _endTime;
+@synthesize studentAvatar = _studentAvatar;
+@synthesize submitTime = _submitTime;
+@synthesize startTime = _startTime;
+@synthesize studentId = _studentId;
+@synthesize teacherId = _teacherId;
+
++ (instancetype)modelObjectWithDictionary:(NSDictionary *)dict
+{
+    return [[self alloc] initWithDictionary:dict];
+}
+
+- (instancetype)initWithDictionary:(NSDictionary *)dict
+{
+    self = [super init];
+    
+    // This check serves to make sure that a non-NSDictionary object
+    // passed into the model class doesn't break the parsing.
+    if(self && [dict isKindOfClass:[NSDictionary class]]) {
+            self.courseGroupId = [self objectOrNilForKey:kHomeworkListModelCourseGroupId fromDictionary:dict];
+            self.classDate = [self objectOrNilForKey:kHomeworkListModelClassDate fromDictionary:dict];
+            self.teacherAvatar = [self objectOrNilForKey:kHomeworkListModelTeacherAvatar fromDictionary:dict];
+            self.decorateTime = [self objectOrNilForKey:kHomeworkListModelDecorateTime fromDictionary:dict];
+            self.absenteeism = [[self objectOrNilForKey:kHomeworkListModelAbsenteeism fromDictionary:dict] doubleValue];
+            self.courseId = [self objectOrNilForKey:kHomeworkListModelCourseId fromDictionary:dict];
+            self.teacherName = [self objectOrNilForKey:kHomeworkListModelTeacherName fromDictionary:dict];
+            self.studentName = [self objectOrNilForKey:kHomeworkListModelStudentName fromDictionary:dict];
+            self.subjectName = [self objectOrNilForKey:kHomeworkListModelSubjectName fromDictionary:dict];
+            self.endTime = [self objectOrNilForKey:kHomeworkListModelEndTime fromDictionary:dict];
+            self.studentAvatar = [self objectOrNilForKey:kHomeworkListModelStudentAvatar fromDictionary:dict];
+            self.submitTime = [self objectOrNilForKey:kHomeworkListModelSubmitTime fromDictionary:dict];
+            self.startTime = [self objectOrNilForKey:kHomeworkListModelStartTime fromDictionary:dict];
+            self.studentId = [self objectOrNilForKey:kHomeworkListModelStudentId fromDictionary:dict];
+            self.teacherId = [self objectOrNilForKey:kHomeworkListModelTeacherId fromDictionary:dict];
+    }
+    
+    return self;
+    
+}
+
+- (NSDictionary *)dictionaryRepresentation
+{
+    NSMutableDictionary *mutableDict = [NSMutableDictionary dictionary];
+    [mutableDict setValue:self.courseGroupId forKey:kHomeworkListModelCourseGroupId];
+    [mutableDict setValue:self.classDate forKey:kHomeworkListModelClassDate];
+    [mutableDict setValue:self.teacherAvatar forKey:kHomeworkListModelTeacherAvatar];
+    [mutableDict setValue:self.decorateTime forKey:kHomeworkListModelDecorateTime];
+    [mutableDict setValue:[NSNumber numberWithDouble:self.absenteeism] forKey:kHomeworkListModelAbsenteeism];
+    [mutableDict setValue:self.courseId forKey:kHomeworkListModelCourseId];
+    [mutableDict setValue:self.teacherName forKey:kHomeworkListModelTeacherName];
+    [mutableDict setValue:self.studentName forKey:kHomeworkListModelStudentName];
+    [mutableDict setValue:self.subjectName forKey:kHomeworkListModelSubjectName];
+    [mutableDict setValue:self.endTime forKey:kHomeworkListModelEndTime];
+    [mutableDict setValue:self.studentAvatar forKey:kHomeworkListModelStudentAvatar];
+    [mutableDict setValue:self.submitTime forKey:kHomeworkListModelSubmitTime];
+    [mutableDict setValue:self.startTime forKey:kHomeworkListModelStartTime];
+    [mutableDict setValue:self.studentId forKey:kHomeworkListModelStudentId];
+    [mutableDict setValue:self.teacherId forKey:kHomeworkListModelTeacherId];
+    return [NSDictionary dictionaryWithDictionary:mutableDict];
+}
+
+- (NSString *)description 
+{
+    return [NSString stringWithFormat:@"%@", [self dictionaryRepresentation]];
+}
+
+#pragma mark - Helper Method
+- (id)objectOrNilForKey:(id)aKey fromDictionary:(NSDictionary *)dict
+{
+    id object = [dict objectForKey:aKey];
+    if ([object isKindOfClass:[NSNumber class]]) {
+        NSNumber *number = object;
+        object = [number stringValue];
+    }
+    return [object isEqual:[NSNull null]] ? nil : object;
+}
+
+
+#pragma mark - NSCoding Methods
+
+- (id)initWithCoder:(NSCoder *)aDecoder
+{
+    self = [super init];
+
+    self.courseGroupId = [aDecoder decodeObjectForKey:kHomeworkListModelCourseGroupId];
+    self.classDate = [aDecoder decodeObjectForKey:kHomeworkListModelClassDate];
+    self.teacherAvatar = [aDecoder decodeObjectForKey:kHomeworkListModelTeacherAvatar];
+    self.decorateTime = [aDecoder decodeObjectForKey:kHomeworkListModelDecorateTime];
+    self.absenteeism = [aDecoder decodeDoubleForKey:kHomeworkListModelAbsenteeism];
+    self.courseId = [aDecoder decodeObjectForKey:kHomeworkListModelCourseId];
+    self.teacherName = [aDecoder decodeObjectForKey:kHomeworkListModelTeacherName];
+    self.studentName = [aDecoder decodeObjectForKey:kHomeworkListModelStudentName];
+    self.subjectName = [aDecoder decodeObjectForKey:kHomeworkListModelSubjectName];
+    self.endTime = [aDecoder decodeObjectForKey:kHomeworkListModelEndTime];
+    self.studentAvatar = [aDecoder decodeObjectForKey:kHomeworkListModelStudentAvatar];
+    self.submitTime = [aDecoder decodeObjectForKey:kHomeworkListModelSubmitTime];
+    self.startTime = [aDecoder decodeObjectForKey:kHomeworkListModelStartTime];
+    self.studentId = [aDecoder decodeObjectForKey:kHomeworkListModelStudentId];
+    self.teacherId = [aDecoder decodeObjectForKey:kHomeworkListModelTeacherId];
+    return self;
+}
+
+- (void)encodeWithCoder:(NSCoder *)aCoder
+{
+
+    [aCoder encodeObject:_courseGroupId forKey:kHomeworkListModelCourseGroupId];
+    [aCoder encodeObject:_classDate forKey:kHomeworkListModelClassDate];
+    [aCoder encodeObject:_teacherAvatar forKey:kHomeworkListModelTeacherAvatar];
+    [aCoder encodeObject:_decorateTime forKey:kHomeworkListModelDecorateTime];
+    [aCoder encodeDouble:_absenteeism forKey:kHomeworkListModelAbsenteeism];
+    [aCoder encodeObject:_courseId forKey:kHomeworkListModelCourseId];
+    [aCoder encodeObject:_teacherName forKey:kHomeworkListModelTeacherName];
+    [aCoder encodeObject:_studentName forKey:kHomeworkListModelStudentName];
+    [aCoder encodeObject:_subjectName forKey:kHomeworkListModelSubjectName];
+    [aCoder encodeObject:_endTime forKey:kHomeworkListModelEndTime];
+    [aCoder encodeObject:_studentAvatar forKey:kHomeworkListModelStudentAvatar];
+    [aCoder encodeObject:_submitTime forKey:kHomeworkListModelSubmitTime];
+    [aCoder encodeObject:_startTime forKey:kHomeworkListModelStartTime];
+    [aCoder encodeObject:_studentId forKey:kHomeworkListModelStudentId];
+    [aCoder encodeObject:_teacherId forKey:kHomeworkListModelTeacherId];
+}
+
+- (id)copyWithZone:(NSZone *)zone
+{
+    HomeworkListModel *copy = [[HomeworkListModel alloc] init];
+    
+    if (copy) {
+
+        copy.courseGroupId = [self.courseGroupId copyWithZone:zone];
+        copy.classDate = [self.classDate copyWithZone:zone];
+        copy.teacherAvatar = [self.teacherAvatar copyWithZone:zone];
+        copy.decorateTime = [self.decorateTime copyWithZone:zone];
+        copy.absenteeism = self.absenteeism;
+        copy.courseId = [self.courseId copyWithZone:zone];
+        copy.teacherName = [self.teacherName copyWithZone:zone];
+        copy.studentName = [self.studentName copyWithZone:zone];
+        copy.subjectName = [self.subjectName copyWithZone:zone];
+        copy.endTime = [self.endTime copyWithZone:zone];
+        copy.studentAvatar = [self.studentAvatar copyWithZone:zone];
+        copy.submitTime = [self.submitTime copyWithZone:zone];
+        copy.startTime = [self.startTime copyWithZone:zone];
+        copy.studentId = [self.studentId copyWithZone:zone];
+        copy.teacherId = [self.teacherId copyWithZone:zone];
+    }
+    
+    return copy;
+}
+
+
+@end

+ 30 - 0
KulexiuForStudent/KulexiuForStudent/Module/Mine/Homework/View/AccompanyAlertView.h

@@ -0,0 +1,30 @@
+//
+//  AccompanyAlertView.h
+//  KulexiuForTeacher
+//
+//  Created by 王智 on 2022/4/11.
+//
+
+#import <UIKit/UIKit.h>
+
+typedef void(^AccompanyAlertCallback)(NSString * _Nonnull content, NSInteger starNum);
+
+NS_ASSUME_NONNULL_BEGIN
+
+@interface AccompanyAlertView : UIView
+
+@property (weak, nonatomic) IBOutlet UILabel *alertTitle;
+
+@property (weak, nonatomic) IBOutlet UITextView *inputView;
+
+@property (weak, nonatomic) IBOutlet UILabel *tipsLabel;
+
++ (instancetype)shareInstance;
+
+- (void)showInView:(UIView *)displayView showStarView:(BOOL)showStarView;
+
+- (void)sureCallback:(AccompanyAlertCallback)callback;
+
+@end
+
+NS_ASSUME_NONNULL_END

+ 101 - 0
KulexiuForStudent/KulexiuForStudent/Module/Mine/Homework/View/AccompanyAlertView.m

@@ -0,0 +1,101 @@
+//
+//  AccompanyAlertView.m
+//  KulexiuForTeacher
+//
+//  Created by 王智 on 2022/4/11.
+//
+
+#import "AccompanyAlertView.h"
+#import "KSStarView.h"
+
+@interface AccompanyAlertView ()<UITextViewDelegate>
+
+@property (weak, nonatomic) IBOutlet KSStarView *starView;
+
+@property (nonatomic, copy) AccompanyAlertCallback callback;
+
+@end
+
+@implementation AccompanyAlertView
+
+- (void)awakeFromNib {
+    [super awakeFromNib];
+    self.inputView.delegate = self;
+    self.starView.hidden = YES;
+    self.starView.allowMark = YES;
+}
+
++ (instancetype)shareInstance {
+    AccompanyAlertView *view = [[[NSBundle mainBundle] loadNibNamed:@"AccompanyAlertView" owner:nil options:nil] firstObject];
+    view.frame = CGRectMake(0, 0, kScreen_Width, kScreen_Height);
+    return view;
+}
+- (void)showInView:(UIView *)displayView showStarView:(BOOL)showStarView {
+    if (showStarView) {
+        self.starView.hidden = NO;
+    }
+    [displayView addSubview:self];
+}
+
+- (void)sureCallback:(AccompanyAlertCallback)callback {
+    if (callback) {
+        self.callback = callback;
+    }
+}
+
+- (IBAction)cancelAction:(id)sender {
+    [self removeFromSuperview];
+}
+
+- (IBAction)sureAction:(id)sender {
+    NSInteger starNum = self.starView.rate * 5;
+    if (self.callback) {
+        self.callback(self.inputView.text, starNum);
+    }
+    [self removeFromSuperview];
+}
+
+
+#pragma mark ---- text view delegate
+
+- (void)textViewDidBeginEditing:(UITextView *)textView {
+    self.tipsLabel.hidden = YES;
+}
+- (void)textViewDidEndEditing:(UITextView *)textView {
+    if ([NSString isEmptyString:textView.text]) {
+        self.tipsLabel.hidden = NO;
+    }
+}
+
+- (BOOL)textViewShouldEndEditing:(UITextView *)textView {
+    [self endEditing:YES];
+    return YES;
+}
+
+- (void)touchesBegan:(NSSet<UITouch *> *)touches withEvent:(UIEvent *)event {
+    [self endEditing:YES];
+}
+
+- (BOOL)textView:(UITextView *)textView shouldChangeTextInRange:(NSRange)range replacementText:(NSString *)text {
+    if ([text isEqualToString:@""]) {
+        return YES;
+    }
+    
+    // 输入控制
+    NSString *newString = [textView.text stringByReplacingCharactersInRange:range withString:text];
+    if (newString.length > 200) {
+        return NO;
+    }
+
+    return YES;
+}
+
+/*
+// Only override drawRect: if you perform custom drawing.
+// An empty implementation adversely affects performance during animation.
+- (void)drawRect:(CGRect)rect {
+    // Drawing code
+}
+*/
+
+@end

+ 152 - 0
KulexiuForStudent/KulexiuForStudent/Module/Mine/Homework/View/AccompanyAlertView.xib

@@ -0,0 +1,152 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<document type="com.apple.InterfaceBuilder3.CocoaTouch.XIB" version="3.0" toolsVersion="20037" targetRuntime="iOS.CocoaTouch" propertyAccessControl="none" useAutolayout="YES" useTraitCollections="YES" colorMatched="YES">
+    <device id="retina6_1" orientation="portrait" appearance="light"/>
+    <dependencies>
+        <deployment identifier="iOS"/>
+        <plugIn identifier="com.apple.InterfaceBuilder.IBCocoaTouchPlugin" version="20020"/>
+        <capability name="System colors in document resources" minToolsVersion="11.0"/>
+        <capability name="documents saved in the Xcode 8 format" minToolsVersion="8.0"/>
+    </dependencies>
+    <objects>
+        <placeholder placeholderIdentifier="IBFilesOwner" id="-1" userLabel="File's Owner"/>
+        <placeholder placeholderIdentifier="IBFirstResponder" id="-2" customClass="UIResponder"/>
+        <view contentMode="scaleToFill" id="iN0-l3-epB" customClass="AccompanyAlertView">
+            <rect key="frame" x="0.0" y="0.0" width="414" height="896"/>
+            <autoresizingMask key="autoresizingMask" widthSizable="YES" heightSizable="YES"/>
+            <subviews>
+                <view contentMode="scaleToFill" translatesAutoresizingMaskIntoConstraints="NO" id="kJz-jy-Enw">
+                    <rect key="frame" x="32" y="322" width="350" height="252"/>
+                    <subviews>
+                        <imageView clipsSubviews="YES" userInteractionEnabled="NO" contentMode="scaleAspectFit" horizontalHuggingPriority="251" verticalHuggingPriority="251" image="accell_left" translatesAutoresizingMaskIntoConstraints="NO" id="g5U-zt-jhG">
+                            <rect key="frame" x="19" y="27" width="4" height="14"/>
+                        </imageView>
+                        <label opaque="NO" userInteractionEnabled="NO" contentMode="left" horizontalHuggingPriority="251" verticalHuggingPriority="251" text="评价学员" textAlignment="natural" lineBreakMode="tailTruncation" baselineAdjustment="alignBaselines" adjustsFontSizeToFit="NO" translatesAutoresizingMaskIntoConstraints="NO" id="Biv-dK-fGb">
+                            <rect key="frame" x="29" y="23" width="74" height="22"/>
+                            <fontDescription key="fontDescription" type="system" weight="medium" pointSize="18"/>
+                            <color key="textColor" red="0.20000000000000001" green="0.20000000000000001" blue="0.20000000000000001" alpha="1" colorSpace="custom" customColorSpace="sRGB"/>
+                            <nil key="highlightedColor"/>
+                        </label>
+                        <button opaque="NO" contentMode="scaleToFill" contentHorizontalAlignment="center" contentVerticalAlignment="center" lineBreakMode="middleTruncation" translatesAutoresizingMaskIntoConstraints="NO" id="sjo-db-uX7">
+                            <rect key="frame" x="310" y="0.0" width="40" height="40"/>
+                            <constraints>
+                                <constraint firstAttribute="height" constant="40" id="TQQ-uo-INP"/>
+                                <constraint firstAttribute="width" constant="40" id="mp9-0N-gC4"/>
+                            </constraints>
+                            <inset key="imageEdgeInsets" minX="0.0" minY="0.0" maxX="2.2250738585072014e-308" maxY="0.0"/>
+                            <state key="normal" image="check_cancle"/>
+                            <connections>
+                                <action selector="cancelAction:" destination="iN0-l3-epB" eventType="touchUpInside" id="PIg-Q4-17H"/>
+                            </connections>
+                        </button>
+                        <view contentMode="scaleToFill" translatesAutoresizingMaskIntoConstraints="NO" id="pIM-1F-iXG" customClass="KSStarView">
+                            <rect key="frame" x="111" y="24.5" width="90" height="19"/>
+                            <color key="backgroundColor" systemColor="systemBackgroundColor"/>
+                            <constraints>
+                                <constraint firstAttribute="width" constant="90" id="VfG-pE-0iO"/>
+                                <constraint firstAttribute="height" constant="19" id="zCf-FD-G74"/>
+                            </constraints>
+                        </view>
+                        <button opaque="NO" contentMode="scaleToFill" contentHorizontalAlignment="center" contentVerticalAlignment="center" lineBreakMode="middleTruncation" translatesAutoresizingMaskIntoConstraints="NO" id="G0I-PQ-FQA">
+                            <rect key="frame" x="26" y="193" width="298" height="44"/>
+                            <color key="backgroundColor" red="0.1764705882352941" green="0.7803921568627451" blue="0.66666666666666663" alpha="1" colorSpace="calibratedRGB"/>
+                            <constraints>
+                                <constraint firstAttribute="height" constant="44" id="E0O-u9-1AP"/>
+                            </constraints>
+                            <fontDescription key="fontDescription" type="system" pointSize="16"/>
+                            <inset key="imageEdgeInsets" minX="0.0" minY="0.0" maxX="2.2250738585072014e-308" maxY="0.0"/>
+                            <state key="normal" title="提交"/>
+                            <userDefinedRuntimeAttributes>
+                                <userDefinedRuntimeAttribute type="number" keyPath="cornerRadius">
+                                    <real key="value" value="22"/>
+                                </userDefinedRuntimeAttribute>
+                            </userDefinedRuntimeAttributes>
+                            <connections>
+                                <action selector="sureAction:" destination="iN0-l3-epB" eventType="touchUpInside" id="Dyw-XX-Ggo"/>
+                            </connections>
+                        </button>
+                        <view contentMode="scaleToFill" translatesAutoresizingMaskIntoConstraints="NO" id="MLc-UI-hJt">
+                            <rect key="frame" x="18" y="63" width="314" height="115"/>
+                            <subviews>
+                                <textView clipsSubviews="YES" multipleTouchEnabled="YES" contentMode="scaleToFill" textAlignment="natural" translatesAutoresizingMaskIntoConstraints="NO" id="7gT-5S-Mnm">
+                                    <rect key="frame" x="0.0" y="0.0" width="314" height="115"/>
+                                    <color key="backgroundColor" white="0.0" alpha="0.0" colorSpace="custom" customColorSpace="genericGamma22GrayColorSpace"/>
+                                    <color key="textColor" red="0.40000000000000002" green="0.40000000000000002" blue="0.40000000000000002" alpha="1" colorSpace="calibratedRGB"/>
+                                    <fontDescription key="fontDescription" type="system" pointSize="14"/>
+                                    <textInputTraits key="textInputTraits" autocapitalizationType="sentences"/>
+                                </textView>
+                                <label opaque="NO" userInteractionEnabled="NO" contentMode="left" horizontalHuggingPriority="251" verticalHuggingPriority="251" text="请输入您对本次课程学员表现的评价" textAlignment="natural" lineBreakMode="tailTruncation" numberOfLines="0" baselineAdjustment="alignBaselines" adjustsFontSizeToFit="NO" translatesAutoresizingMaskIntoConstraints="NO" id="4Yk-u1-WFH">
+                                    <rect key="frame" x="11" y="11" width="292" height="17"/>
+                                    <fontDescription key="fontDescription" type="system" pointSize="14"/>
+                                    <color key="textColor" red="0.59999999999999998" green="0.59999999999999998" blue="0.59999999999999998" alpha="1" colorSpace="calibratedRGB"/>
+                                    <nil key="highlightedColor"/>
+                                </label>
+                            </subviews>
+                            <color key="backgroundColor" red="0.96862745098039216" green="0.97254901960784312" blue="0.97647058823529409" alpha="1" colorSpace="calibratedRGB"/>
+                            <constraints>
+                                <constraint firstAttribute="trailing" secondItem="4Yk-u1-WFH" secondAttribute="trailing" constant="11" id="0MB-PA-Aa5"/>
+                                <constraint firstAttribute="bottom" secondItem="7gT-5S-Mnm" secondAttribute="bottom" id="43J-6J-HH9"/>
+                                <constraint firstItem="4Yk-u1-WFH" firstAttribute="leading" secondItem="MLc-UI-hJt" secondAttribute="leading" constant="11" id="Coy-Mj-2Xf"/>
+                                <constraint firstItem="4Yk-u1-WFH" firstAttribute="top" secondItem="MLc-UI-hJt" secondAttribute="top" constant="11" id="d9n-1a-LAI"/>
+                                <constraint firstItem="7gT-5S-Mnm" firstAttribute="leading" secondItem="MLc-UI-hJt" secondAttribute="leading" id="e5S-8l-apw"/>
+                                <constraint firstAttribute="trailing" secondItem="7gT-5S-Mnm" secondAttribute="trailing" id="fZD-0W-Y2B"/>
+                                <constraint firstItem="7gT-5S-Mnm" firstAttribute="top" secondItem="MLc-UI-hJt" secondAttribute="top" id="nJo-xj-WnT"/>
+                            </constraints>
+                            <userDefinedRuntimeAttributes>
+                                <userDefinedRuntimeAttribute type="number" keyPath="cornerRadius">
+                                    <real key="value" value="4"/>
+                                </userDefinedRuntimeAttribute>
+                            </userDefinedRuntimeAttributes>
+                        </view>
+                    </subviews>
+                    <color key="backgroundColor" systemColor="systemBackgroundColor"/>
+                    <constraints>
+                        <constraint firstAttribute="trailing" secondItem="sjo-db-uX7" secondAttribute="trailing" id="A3M-Sl-J6R"/>
+                        <constraint firstAttribute="trailing" secondItem="MLc-UI-hJt" secondAttribute="trailing" constant="18" id="CtM-Jg-oJD"/>
+                        <constraint firstItem="G0I-PQ-FQA" firstAttribute="leading" secondItem="kJz-jy-Enw" secondAttribute="leading" constant="26" id="GHy-tP-tdG"/>
+                        <constraint firstItem="Biv-dK-fGb" firstAttribute="centerY" secondItem="g5U-zt-jhG" secondAttribute="centerY" id="Ki2-YG-6lh"/>
+                        <constraint firstAttribute="height" constant="252" id="M9C-HQ-gB4"/>
+                        <constraint firstItem="g5U-zt-jhG" firstAttribute="top" secondItem="kJz-jy-Enw" secondAttribute="top" constant="27" id="OKg-sG-RdM"/>
+                        <constraint firstItem="g5U-zt-jhG" firstAttribute="leading" secondItem="kJz-jy-Enw" secondAttribute="leading" constant="19" id="Pa0-MX-aqP"/>
+                        <constraint firstItem="pIM-1F-iXG" firstAttribute="centerY" secondItem="Biv-dK-fGb" secondAttribute="centerY" id="Syz-BX-BWg"/>
+                        <constraint firstItem="MLc-UI-hJt" firstAttribute="leading" secondItem="kJz-jy-Enw" secondAttribute="leading" constant="18" id="ZBZ-un-Lnm"/>
+                        <constraint firstItem="pIM-1F-iXG" firstAttribute="leading" secondItem="Biv-dK-fGb" secondAttribute="trailing" constant="8" id="ZHm-tN-Tgv"/>
+                        <constraint firstItem="sjo-db-uX7" firstAttribute="top" secondItem="kJz-jy-Enw" secondAttribute="top" id="gHV-ix-oRX"/>
+                        <constraint firstItem="MLc-UI-hJt" firstAttribute="top" secondItem="Biv-dK-fGb" secondAttribute="bottom" constant="18" id="kn9-CM-VIU"/>
+                        <constraint firstAttribute="trailing" secondItem="G0I-PQ-FQA" secondAttribute="trailing" constant="26" id="lga-IR-Xi5"/>
+                        <constraint firstItem="G0I-PQ-FQA" firstAttribute="top" secondItem="MLc-UI-hJt" secondAttribute="bottom" constant="15" id="qfK-wZ-o3X"/>
+                        <constraint firstAttribute="bottom" secondItem="G0I-PQ-FQA" secondAttribute="bottom" constant="15" id="wvD-8g-GL1"/>
+                        <constraint firstItem="Biv-dK-fGb" firstAttribute="leading" secondItem="g5U-zt-jhG" secondAttribute="trailing" constant="6" id="yLW-be-98P"/>
+                    </constraints>
+                    <userDefinedRuntimeAttributes>
+                        <userDefinedRuntimeAttribute type="number" keyPath="cornerRadius">
+                            <real key="value" value="8"/>
+                        </userDefinedRuntimeAttribute>
+                    </userDefinedRuntimeAttributes>
+                </view>
+            </subviews>
+            <color key="backgroundColor" red="0.0" green="0.0" blue="0.0" alpha="0.5" colorSpace="custom" customColorSpace="sRGB"/>
+            <constraints>
+                <constraint firstItem="kJz-jy-Enw" firstAttribute="centerY" secondItem="iN0-l3-epB" secondAttribute="centerY" id="Yh6-BB-9g3"/>
+                <constraint firstAttribute="trailing" secondItem="kJz-jy-Enw" secondAttribute="trailing" constant="32" id="nGG-8u-ImK"/>
+                <constraint firstItem="kJz-jy-Enw" firstAttribute="leading" secondItem="iN0-l3-epB" secondAttribute="leading" constant="32" id="wiJ-hM-0Kt"/>
+            </constraints>
+            <nil key="simulatedTopBarMetrics"/>
+            <nil key="simulatedBottomBarMetrics"/>
+            <freeformSimulatedSizeMetrics key="simulatedDestinationMetrics"/>
+            <connections>
+                <outlet property="alertTitle" destination="Biv-dK-fGb" id="JYe-yN-jwF"/>
+                <outlet property="inputView" destination="7gT-5S-Mnm" id="cmg-Lm-Mx1"/>
+                <outlet property="starView" destination="pIM-1F-iXG" id="Ezw-4e-Vew"/>
+                <outlet property="tipsLabel" destination="4Yk-u1-WFH" id="Tbg-vh-eGE"/>
+            </connections>
+            <point key="canvasLocation" x="131.8840579710145" y="75.669642857142847"/>
+        </view>
+    </objects>
+    <resources>
+        <image name="accell_left" width="4" height="14"/>
+        <image name="check_cancle" width="14" height="14"/>
+        <systemColor name="systemBackgroundColor">
+            <color white="1" alpha="1" colorSpace="custom" customColorSpace="genericGamma22GrayColorSpace"/>
+        </systemColor>
+    </resources>
+</document>

+ 20 - 0
KulexiuForStudent/KulexiuForStudent/Module/Mine/Homework/View/HomeworkAddView.h

@@ -0,0 +1,20 @@
+//
+//  HomeworkAddView.h
+//  KulexiuForStudent
+//
+//  Created by 王智 on 2022/4/20.
+//
+
+#import <UIKit/UIKit.h>
+#import "UIView+ExtensionForDotLine.h"
+
+NS_ASSUME_NONNULL_BEGIN
+typedef void(^HomeworkChooseCallback)(void);
+
+@interface HomeworkAddView : UIView
+
+- (void)chooseCallback:(HomeworkChooseCallback)callback;
+
+@end
+
+NS_ASSUME_NONNULL_END

+ 81 - 0
KulexiuForStudent/KulexiuForStudent/Module/Mine/Homework/View/HomeworkAddView.m

@@ -0,0 +1,81 @@
+//
+//  HomeworkAddView.m
+//  KulexiuForStudent
+//
+//  Created by 王智 on 2022/4/20.
+//
+
+#import "HomeworkAddView.h"
+
+@interface HomeworkAddView ()
+
+@property (nonatomic, copy) HomeworkChooseCallback callback;
+
+@end
+
+@implementation HomeworkAddView
+
+- (instancetype)initWithFrame:(CGRect)frame {
+    self = [super initWithFrame:frame];
+    if (self) {
+        [self configUI];
+    }
+    return self;
+}
+
+- (void)configUI {
+    
+    UIView *bgView = [[UIView alloc] initWithFrame:CGRectMake(0, 11, self.bounds.size.width - 11, self.bounds.size.height -22)];
+    [self addSubview:bgView];
+    [bgView drawBoardDottedLine:1.0f length:4 space:4 cornerRadius:8.0f lineColor:THEMECOLOR];
+    
+    UIImageView *imgView = [[UIImageView alloc] initWithImage:[UIImage imageNamed:@"image_upload"]];
+    [bgView addSubview:imgView];
+    
+    [imgView mas_makeConstraints:^(MASConstraintMaker *make) {
+        make.centerX.mas_equalTo(bgView.mas_centerX);
+        make.width.mas_equalTo(32);
+        make.height.mas_equalTo(32);
+        make.top.mas_equalTo(bgView.mas_top).offset(13);
+    }];
+    
+    UILabel *label = [[UILabel alloc] init];
+    label.textAlignment = NSTextAlignmentCenter;
+    label.text = @"上传视频";
+    label.font = [UIFont systemFontOfSize:10.0f];
+    label.textColor = THEMECOLOR;
+    [bgView addSubview:label];
+    [label mas_makeConstraints:^(MASConstraintMaker *make) {
+        make.left.right.mas_equalTo(bgView);
+        make.top.mas_equalTo(imgView.mas_bottom).offset(1);
+        make.height.mas_equalTo(17);
+    }];
+    UIButton *actionButton = [UIButton buttonWithType:UIButtonTypeCustom];
+    [actionButton addTarget:self action:@selector(buttonClickAction:) forControlEvents:UIControlEventTouchUpInside];
+    [bgView addSubview:actionButton];
+    [actionButton mas_makeConstraints:^(MASConstraintMaker *make) {
+        make.left.right.top.bottom.mas_equalTo(bgView);
+    }];
+}
+
+
+- (void)chooseCallback:(HomeworkChooseCallback)callback {
+    if (callback) {
+        self.callback = callback;
+    }
+}
+
+- (void)buttonClickAction:(UIButton *)sender {
+    if (self.callback) {
+        self.callback();
+    }
+}
+/*
+// Only override drawRect: if you perform custom drawing.
+// An empty implementation adversely affects performance during animation.
+- (void)drawRect:(CGRect)rect {
+    // Drawing code
+}
+*/
+
+@end

+ 18 - 0
KulexiuForStudent/KulexiuForStudent/Module/Mine/Homework/View/HomeworkBodyView.h

@@ -0,0 +1,18 @@
+//
+//  HomeworkBodyView.h
+//  KulexiuForStudent
+//
+//  Created by 王智 on 2022/4/20.
+//
+
+#import "KSJXBodyView.h"
+#import "StateView.h"
+#import "Reachability.h"
+
+NS_ASSUME_NONNULL_BEGIN
+
+@interface HomeworkBodyView : KSJXBodyView
+
+@end
+
+NS_ASSUME_NONNULL_END

+ 333 - 0
KulexiuForStudent/KulexiuForStudent/Module/Mine/Homework/View/HomeworkBodyView.m

@@ -0,0 +1,333 @@
+//
+//  HomeworkBodyView.m
+//  KulexiuForStudent
+//
+//  Created by 王智 on 2022/4/20.
+//
+
+#import "HomeworkBodyView.h"
+#import "HomeworkListCell.h"
+#import "KSChatConversationViewController.h"
+#import "HomeworkSortView.h"
+#import "KSFullDatePicker.h"
+#import "HomeworkDetailViewController.h"
+#import "HomeworkListModel.h"
+
+@interface HomeworkBodyView ()<UITableViewDelegate,UITableViewDataSource>
+
+@property (nonatomic, strong) NSDateFormatter *dateFormatter;
+
+@property (nonatomic, strong) NSMutableArray *dataArray;
+
+@property (nonatomic, strong) StateView *promptView;
+@property (nonatomic, strong) UIView *promptPlaceView;
+
+@property (nonatomic, assign) BOOL networkAvaiable; // 网络是否可用
+
+@property (nonatomic, assign) BOOL isLoadMore;
+@property (nonatomic, assign) NSInteger rows;
+@property (nonatomic, assign) NSInteger pages;
+
+@property (nonatomic, strong) HomeworkSortView *sortView;
+
+@property (nonatomic, strong) NSString *chooseDate;
+
+@end
+
+@implementation HomeworkBodyView
+
+- (instancetype)initWithFrame:(CGRect)frame {
+    self = [super initWithFrame:frame];
+    if (self) {
+        self.backgroundColor = HexRGB(0xf6f8f9);
+        self.tableView = [[UITableView alloc] initWithFrame:CGRectMake(0, 0, frame.size.width, frame.size.height) style:UITableViewStylePlain];
+        self.tableView.backgroundColor = HexRGB(0xf6f8f9);
+        self.tableView.showsVerticalScrollIndicator = NO;
+        self.tableView.showsHorizontalScrollIndicator = NO;
+        self.tableView.dataSource = self;
+        self.tableView.delegate = self;
+        self.tableView.separatorStyle = UITableViewCellSeparatorStyleNone;
+        self.tableView.rowHeight = 132;
+        [self addSubview:self.tableView];
+        
+        
+        UIView *headView = [[UIView alloc] initWithFrame:CGRectMake(0, 0, kScreenWidth, 10)];
+        headView.backgroundColor = HexRGB(0xf6f8f9);
+        self.tableView.tableHeaderView = headView;
+        
+        UIView *bottomView = [[UIView alloc] initWithFrame:CGRectMake(0, 0, kScreenWidth, 10)];
+        bottomView.backgroundColor = HexRGB(0xf6f8f9);
+        self.tableView.tableFooterView = bottomView;
+        
+        [self.tableView registerNib:[UINib nibWithNibName:@"HomeworkListCell" bundle:[NSBundle mainBundle]] forCellReuseIdentifier:@"HomeworkListCell"];
+
+        [self.dateFormatter setDateFormat:@"yyyy-MM"];
+        NSDate *currentDate = [NSDate date];
+        self.chooseDate = [self.dateFormatter stringFromDate:currentDate];
+        
+        MJWeakSelf;
+        self.tableView.mj_header = [KSGifRefreshHeader headerWithRefreshingBlock:^{
+            [weakSelf resetParamenter];
+            [weakSelf requestData];
+        }];
+        self.tableView.mj_footer = [KSGifRefreshFooter footerWithRefreshingBlock:^{
+            if (weakSelf.isLoadMore) {
+                weakSelf.pages += 1;
+                [weakSelf requestData];
+            }
+            else {
+                [weakSelf.tableView.mj_footer endRefreshingWithNoMoreData];
+            }
+        }];
+    }
+    return self;
+}
+
+- (void)endRefresh {
+    dispatch_after(dispatch_time(DISPATCH_TIME_NOW, (int64_t)(0.5 * NSEC_PER_SEC)), dispatch_get_main_queue(), ^{
+        [self.tableView.mj_header endRefreshing];
+        [self.tableView.mj_footer endRefreshing];
+    });
+}
+
+- (void)refreshAndRequestData {
+    [self resetParamenter];
+    [self requestData];
+    
+}
+
+- (void)resetParamenter {
+    self.isLoadMore = YES;
+    self.pages = 1;
+    self.rows = 10;
+    self.dataArray = [NSMutableArray array];
+    [self.tableView.mj_footer resetNoMoreData];
+    [self setPromptString:@"暂无内容" imageName:@"wd_img_zwsj" inView:self.tableView];
+    [self.tableView reloadData];
+}
+
+- (void)requestData {
+    NSInteger hasSubmit = self.selectIndex == 0 ? 0 : 1;
+    [KSNetworkingManager homeworkListRequest:KS_POST date:self.chooseDate submit:hasSubmit page:self.pages rows:self.rows success:^(NSDictionary * _Nonnull dic) {
+        [self endRefresh];
+        if ([dic integerValueForKey:@"code"] == 200 && [dic boolValueForKey:@"status"]) {
+            NSArray *sourceArray = [[dic dictionaryValueForKey:@"data"] arrayValueForKey:@"rows"];
+            for (NSDictionary *parm in sourceArray) {
+                HomeworkListModel *model = [[HomeworkListModel alloc] initWithDictionary:parm];
+                [self.dataArray addObject:model];
+            }
+            
+            if (sourceArray.count < self.rows) {
+                self.isLoadMore = NO;
+            }
+        }
+        else {
+            [self MBPShow:MESSAGEKEY];
+        }
+        [self.tableView reloadData];
+        [self changePromptLabelStateWithArray:self.dataArray];
+    } faliure:^(NSError * _Nonnull error) {
+        [self endRefresh];
+        if (self.networkAvaiable == NO) {
+            [self setPromptString:@"暂无网络" imageName:@"no_networking" inView:self.tableView];
+        }
+        [self.dataArray removeAllObjects];
+        [self.tableView reloadData];
+        [self changePromptLabelStateWithArray:self.dataArray];
+    }];
+}
+
+- (void)beginRefreshImmediately {
+    [self.tableView.mj_header beginRefreshing];
+}
+
+- (void)selectCellAtIndexPath:(NSIndexPath *)indexPath {
+    
+    if (self.lastSelectedIndexPath == indexPath) {
+        return;
+    }
+    if (self.lastSelectedIndexPath != nil) {
+        UITableViewCell *cell = [self.tableView cellForRowAtIndexPath:self.lastSelectedIndexPath];
+        [cell setSelected:NO animated:NO];
+    }
+    UITableViewCell *cell = [self.tableView cellForRowAtIndexPath:indexPath];
+    [cell setSelected:YES animated:NO];
+    self.lastSelectedIndexPath = indexPath;
+}
+
+- (void)layoutSubviews {
+    [super layoutSubviews];
+    CGFloat topHeight = 50.0f;
+    self.tableView.frame = CGRectMake(0, topHeight, self.bounds.size.width, self.bounds.size.height - topHeight);
+    if (!_sortView) {
+        self.sortView.frame = CGRectMake(0, 0, kScreenWidth, topHeight);
+        [self addSubview:self.sortView];
+        [self.dateFormatter setDateFormat:@"yyyy年MM月"];
+        NSDate *currentDate = [NSDate date];
+        self.sortView.sortTitleLabel.text = [NSString returnNoNullStringWithString:[self.dateFormatter stringFromDate:currentDate]];
+    }
+}
+
+- (void)beginFirstRefresh {
+    if (!self.isHeaderRefreshed) {
+        [self beginRefreshImmediately];
+    }
+}
+
+#pragma mark - UITableViewDataSource
+- (NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section {
+    return self.dataArray.count;
+}
+
+- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath {
+    HomeworkListModel *model = self.dataArray[indexPath.row];
+    HomeworkListCell *cell = [tableView dequeueReusableCellWithIdentifier:@"HomeworkListCell"];
+    [cell configWithSource:model];
+    MJWeakSelf;
+    [cell chatWithStudent:^(NSString * _Nonnull userId, NSString * _Nonnull userName) {
+        [weakSelf chatStudent:userId name:userName];
+    }];
+    return cell;
+}
+
+- (void)chatStudent:(NSString *)studentId name:(NSString *)name {
+    KSChatConversationViewController *conversationVC = [[KSChatConversationViewController alloc] init];
+    conversationVC.targetId = studentId;
+    conversationVC.title = name;
+    conversationVC.conversationType = ConversationType_PRIVATE;
+    [self.naviController pushViewController:conversationVC animated:YES];
+}
+
+- (void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath {
+    // 进入作业详情
+    HomeworkListModel *model = self.dataArray[indexPath.row];
+    HomeworkDetailViewController *detailVC = [[HomeworkDetailViewController alloc] init];
+    detailVC.courseId = model.courseId;
+    [self.naviController pushViewController:detailVC animated:YES];
+}
+
+/**
+ 设置没有数据时的显示
+ 
+ @param promptString 提示语
+ @param imgName 图片名称
+ @param view 显示在什么地方
+ */
+- (void)setPromptString:(NSString *)promptString imageName:(NSString *)imgName inView:(UIView *)view {
+    if (self.promptView != nil) {
+        [self.promptView removeFromSuperview];
+    }
+    else {
+        self.promptView = [[StateView alloc]init];
+        self.promptView.frame = CGRectMake(0, 0, kScreenWidth, kScreenHeight - 300);
+    }
+    _promptPlaceView = view;
+    //当请求不到数据时 ,自定义提示view 将会出现;
+    self.promptView.imageName = imgName;
+    self.promptView.alpha = 0.0f;
+    [self.promptView setText:promptString];
+    [view addSubview:self.promptView];
+}
+
+// 结束刷新后调用方法
+- (void)changePromptLabelStateWithArray:(NSMutableArray *)array {
+    NSInteger count;
+    if (array.count) {
+        count = array.count;
+    } else {
+        count = 0;
+    }
+    
+    [UIView animateWithDuration:0.1 animations:^{
+        [[self promptView] setAlpha:count ? 0.0f :1.0f ] ;
+        
+    }] ;
+    
+}
+
+- (BOOL)networkAvaiable {
+    return [self checkNetworkAvaiable];
+}
+
+- (BOOL)checkNetworkAvaiable {
+    BOOL isExistenceNetwork = YES;
+    Reachability *reach = [Reachability reachabilityWithHostName:@"www.apple.com"];
+    switch ([reach currentReachabilityStatus]) {
+        case NotReachable:
+            isExistenceNetwork = NO;
+            //NSLog(@"notReachable");
+            break;
+        case ReachableViaWiFi:
+            isExistenceNetwork = YES;
+            //NSLog(@"WIFI");
+            break;
+        case ReachableViaWWAN:
+            isExistenceNetwork = YES;
+            //NSLog(@"3G");
+            break;
+    }
+    return isExistenceNetwork;
+}
+
+
+#pragma mark ---- lazying
+- (NSDateFormatter *)dateFormatter {
+    if (!_dateFormatter) {
+        _dateFormatter = [NSObject getDateformatter];
+    }
+    return _dateFormatter;
+}
+- (NSMutableArray *)dataArray {
+    if (!_dataArray) {
+        _dataArray = [NSMutableArray array];
+    }
+    return _dataArray;
+}
+
+- (HomeworkSortView *)sortView {
+    if (!_sortView) {
+        _sortView = [HomeworkSortView shareInstance];
+        MJWeakSelf;
+        [_sortView sortAction:^{
+            [weakSelf timeChooseAction];
+        }];
+    }
+    return _sortView;
+}
+
+- (void)timeChooseAction {
+    KSFullDatePicker *picker = [[KSFullDatePicker alloc] initWithTitle:@"" date:[NSDate date] pickMode:KSDATEPICKER_MODE_YEAR_MONTH selectDateBlock:^(NSString *date) {
+
+        self.chooseDate = date;
+        NSString *displayTime = [self getTimeDisplay:date];
+        [self.sortView.sortTitleLabel setText:displayTime];
+        [self resetPickerStatus];
+        // 请求数据
+        [self refreshAndRequestData];
+    } cancleBlock:^{
+        [self resetPickerStatus];
+    }];
+    [picker show];
+}
+
+- (void)resetPickerStatus {
+    self.sortView.arrowUp = NO;
+}
+
+- (NSString *)getTimeDisplay:(NSString *)chooseMonth {
+    [self.dateFormatter setDateFormat:@"yyyy-MM"];
+    NSDate *chooseDate = [self.dateFormatter dateFromString:chooseMonth];
+    [self.dateFormatter setDateFormat:@"yyyy年MM月"];
+    NSString *displayTime = [self.dateFormatter stringFromDate:chooseDate];
+    return displayTime;
+}
+
+/*
+// Only override drawRect: if you perform custom drawing.
+// An empty implementation adversely affects performance during animation.
+- (void)drawRect:(CGRect)rect {
+    // Drawing code
+}
+*/
+
+@end

+ 24 - 0
KulexiuForStudent/KulexiuForStudent/Module/Mine/Homework/View/HomeworkBottomView.h

@@ -0,0 +1,24 @@
+//
+//  HomeworkBottomView.h
+//  KulexiuForStudent
+//
+//  Created by 王智 on 2022/4/20.
+//
+
+#import <UIKit/UIKit.h>
+
+NS_ASSUME_NONNULL_BEGIN
+
+typedef void(^HomeworkSureAction)(void);
+
+@interface HomeworkBottomView : UIView
+
+@property (weak, nonatomic) IBOutlet UIButton *sureButton;
+
++ (instancetype)shareInstance;
+
+- (void)sureAction:(HomeworkSureAction)callback;
+
+@end
+
+NS_ASSUME_NONNULL_END

+ 44 - 0
KulexiuForStudent/KulexiuForStudent/Module/Mine/Homework/View/HomeworkBottomView.m

@@ -0,0 +1,44 @@
+//
+//  HomeworkBottomView.m
+//  KulexiuForStudent
+//
+//  Created by 王智 on 2022/4/20.
+//
+
+#import "HomeworkBottomView.h"
+
+@interface HomeworkBottomView ()
+
+@property (nonatomic, copy) HomeworkSureAction callback;
+
+@end
+
+
+@implementation HomeworkBottomView
+
++ (instancetype)shareInstance {
+    HomeworkBottomView *view = [[[NSBundle mainBundle] loadNibNamed:@"HomeworkBottomView" owner:nil options:nil] firstObject];
+    return view;
+}
+
+- (void)sureAction:(HomeworkSureAction)callback {
+    if (callback) {
+        self.callback = callback;
+    }
+}
+
+- (IBAction)sureSubmitAction:(id)sender {
+    if (self.callback) {
+        self.callback();
+    }
+}
+
+/*
+// Only override drawRect: if you perform custom drawing.
+// An empty implementation adversely affects performance during animation.
+- (void)drawRect:(CGRect)rect {
+    // Drawing code
+}
+*/
+
+@end

+ 50 - 0
KulexiuForStudent/KulexiuForStudent/Module/Mine/Homework/View/HomeworkBottomView.xib

@@ -0,0 +1,50 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<document type="com.apple.InterfaceBuilder3.CocoaTouch.XIB" version="3.0" toolsVersion="20037" targetRuntime="iOS.CocoaTouch" propertyAccessControl="none" useAutolayout="YES" useTraitCollections="YES" colorMatched="YES">
+    <device id="retina6_1" orientation="portrait" appearance="light"/>
+    <dependencies>
+        <deployment identifier="iOS"/>
+        <plugIn identifier="com.apple.InterfaceBuilder.IBCocoaTouchPlugin" version="20020"/>
+        <capability name="documents saved in the Xcode 8 format" minToolsVersion="8.0"/>
+    </dependencies>
+    <objects>
+        <placeholder placeholderIdentifier="IBFilesOwner" id="-1" userLabel="File's Owner"/>
+        <placeholder placeholderIdentifier="IBFirstResponder" id="-2" customClass="UIResponder"/>
+        <view contentMode="scaleToFill" id="iN0-l3-epB" customClass="HomeworkBottomView">
+            <rect key="frame" x="0.0" y="0.0" width="414" height="105"/>
+            <autoresizingMask key="autoresizingMask"/>
+            <subviews>
+                <button opaque="NO" contentMode="scaleToFill" contentHorizontalAlignment="center" contentVerticalAlignment="center" lineBreakMode="middleTruncation" translatesAutoresizingMaskIntoConstraints="NO" id="ZKa-bu-ujx">
+                    <rect key="frame" x="113.5" y="15" width="187" height="44"/>
+                    <color key="backgroundColor" red="0.1764705882" green="0.78039215689999997" blue="0.66666666669999997" alpha="1" colorSpace="calibratedRGB"/>
+                    <constraints>
+                        <constraint firstAttribute="height" constant="44" id="ZZm-hJ-tfL"/>
+                        <constraint firstAttribute="width" constant="187" id="o3w-qW-8mx"/>
+                    </constraints>
+                    <fontDescription key="fontDescription" type="system" pointSize="16"/>
+                    <inset key="imageEdgeInsets" minX="0.0" minY="0.0" maxX="2.2250738585072014e-308" maxY="0.0"/>
+                    <state key="normal" title="确认提交"/>
+                    <userDefinedRuntimeAttributes>
+                        <userDefinedRuntimeAttribute type="number" keyPath="cornerRadius">
+                            <real key="value" value="22"/>
+                        </userDefinedRuntimeAttribute>
+                    </userDefinedRuntimeAttributes>
+                    <connections>
+                        <action selector="sureSubmitAction:" destination="iN0-l3-epB" eventType="touchUpInside" id="woa-Fw-moE"/>
+                    </connections>
+                </button>
+            </subviews>
+            <color key="backgroundColor" white="0.0" alpha="0.0" colorSpace="custom" customColorSpace="genericGamma22GrayColorSpace"/>
+            <constraints>
+                <constraint firstItem="ZKa-bu-ujx" firstAttribute="centerX" secondItem="iN0-l3-epB" secondAttribute="centerX" id="ifA-KQ-41t"/>
+                <constraint firstItem="ZKa-bu-ujx" firstAttribute="top" secondItem="iN0-l3-epB" secondAttribute="top" constant="15" id="n4I-zV-EXt"/>
+            </constraints>
+            <nil key="simulatedTopBarMetrics"/>
+            <nil key="simulatedBottomBarMetrics"/>
+            <freeformSimulatedSizeMetrics key="simulatedDestinationMetrics"/>
+            <connections>
+                <outlet property="sureButton" destination="ZKa-bu-ujx" id="eBK-Dv-3Zc"/>
+            </connections>
+            <point key="canvasLocation" x="131.8840579710145" y="-117.52232142857142"/>
+        </view>
+    </objects>
+</document>

+ 23 - 0
KulexiuForStudent/KulexiuForStudent/Module/Mine/Homework/View/HomeworkListCell.h

@@ -0,0 +1,23 @@
+//
+//  HomeworkListCell.h
+//  KulexiuForTeacher
+//
+//  Created by 王智 on 2022/4/13.
+//
+
+#import <UIKit/UIKit.h>
+#import "HomeworkListModel.h"
+
+typedef void(^HomeworkChatCallback)(NSString * _Nonnull userId, NSString * _Nonnull userName);
+
+NS_ASSUME_NONNULL_BEGIN
+
+@interface HomeworkListCell : UITableViewCell
+
+- (void)configWithSource:(HomeworkListModel *)sourceModel;
+
+- (void)chatWithStudent:(HomeworkChatCallback)callback;
+
+@end
+
+NS_ASSUME_NONNULL_END

+ 76 - 0
KulexiuForStudent/KulexiuForStudent/Module/Mine/Homework/View/HomeworkListCell.m

@@ -0,0 +1,76 @@
+//
+//  HomeworkListCell.m
+//  KulexiuForTeacher
+//
+//  Created by 王智 on 2022/4/13.
+//
+
+#import "HomeworkListCell.h"
+
+@interface HomeworkListCell ()
+
+@property (weak, nonatomic) IBOutlet UILabel *courseTime;
+
+@property (weak, nonatomic) IBOutlet UIImageView *studentAvatal;
+
+@property (weak, nonatomic) IBOutlet UILabel *studentNameLabel;
+
+@property (weak, nonatomic) IBOutlet UILabel *subjectLabel;
+
+@property (weak, nonatomic) IBOutlet UILabel *statusLabel;
+
+@property (nonatomic, copy) HomeworkChatCallback callback;
+
+@property (nonatomic, strong) NSString *userId;
+
+@property (nonatomic, strong) NSString *userName;
+
+@end
+
+@implementation HomeworkListCell
+
+- (void)awakeFromNib {
+    [super awakeFromNib];
+    // Initialization code
+    self.selectionStyle = UITableViewCellSelectionStyleNone;
+}
+
+- (void)configWithSource:(HomeworkListModel *)sourceModel {
+    // time
+    NSDateFormatter *formatter = [NSObject getDateformatter];
+    [formatter setDateFormat:@"yyyy-MM-dd HH:mm:ss"];
+    NSDate *startDate = [formatter dateFromString:sourceModel.startTime];
+    NSDate *endDate = [formatter dateFromString:sourceModel.endTime];
+    [formatter setDateFormat:@"yyyy/MM/dd HH:mm"];
+    NSString *lessonBegin = [formatter stringFromDate:startDate];
+    [formatter setDateFormat:@"HH:mm"];
+    NSString *lessonEnd = [formatter stringFromDate:endDate];
+    self.courseTime.text = [NSString stringWithFormat:@"%@~%@",[NSString returnNoNullStringWithString:lessonBegin],[NSString returnNoNullStringWithString:lessonEnd]];
+    
+    self.studentNameLabel.text = [NSString returnNoNullStringWithString:sourceModel.teacherName];
+    [self.studentAvatal sd_setImageWithURL:[NSURL URLWithString:sourceModel.teacherAvatar] placeholderImage:[UIImage imageNamed:USERDEFAULT_LOGO]];
+    self.subjectLabel.text = [NSString returnNoNullStringWithString:sourceModel.subjectName];
+
+    self.userId = sourceModel.studentId;
+    self.userName = sourceModel.studentName;
+}
+
+- (void)chatWithStudent:(HomeworkChatCallback)callback {
+    if (callback) {
+        self.callback = callback;
+    }
+}
+
+- (IBAction)chatAction:(id)sender {
+    if (self.callback) {
+        self.callback(self.userId, self.userName);
+    }
+}
+
+- (void)setSelected:(BOOL)selected animated:(BOOL)animated {
+    [super setSelected:selected animated:animated];
+
+    // Configure the view for the selected state
+}
+
+@end

+ 166 - 0
KulexiuForStudent/KulexiuForStudent/Module/Mine/Homework/View/HomeworkListCell.xib

@@ -0,0 +1,166 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<document type="com.apple.InterfaceBuilder3.CocoaTouch.XIB" version="3.0" toolsVersion="20037" targetRuntime="iOS.CocoaTouch" propertyAccessControl="none" useAutolayout="YES" useTraitCollections="YES" useSafeAreas="YES" colorMatched="YES">
+    <device id="retina6_1" orientation="portrait" appearance="light"/>
+    <dependencies>
+        <deployment identifier="iOS"/>
+        <plugIn identifier="com.apple.InterfaceBuilder.IBCocoaTouchPlugin" version="20020"/>
+        <capability name="Safe area layout guides" minToolsVersion="9.0"/>
+        <capability name="System colors in document resources" minToolsVersion="11.0"/>
+        <capability name="documents saved in the Xcode 8 format" minToolsVersion="8.0"/>
+    </dependencies>
+    <objects>
+        <placeholder placeholderIdentifier="IBFilesOwner" id="-1" userLabel="File's Owner"/>
+        <placeholder placeholderIdentifier="IBFirstResponder" id="-2" customClass="UIResponder"/>
+        <tableViewCell contentMode="scaleToFill" selectionStyle="default" indentationWidth="10" rowHeight="87" id="KGk-i7-Jjw" customClass="HomeworkListCell">
+            <rect key="frame" x="0.0" y="0.0" width="468" height="138"/>
+            <autoresizingMask key="autoresizingMask" flexibleMaxX="YES" flexibleMaxY="YES"/>
+            <tableViewCellContentView key="contentView" opaque="NO" clipsSubviews="YES" multipleTouchEnabled="YES" contentMode="center" tableViewCell="KGk-i7-Jjw" id="H2p-sc-9uM">
+                <rect key="frame" x="0.0" y="0.0" width="468" height="138"/>
+                <autoresizingMask key="autoresizingMask"/>
+                <subviews>
+                    <view contentMode="scaleToFill" translatesAutoresizingMaskIntoConstraints="NO" id="7PV-kN-jHP">
+                        <rect key="frame" x="14" y="0.0" width="440" height="126"/>
+                        <subviews>
+                            <view contentMode="scaleToFill" translatesAutoresizingMaskIntoConstraints="NO" id="8DG-NN-Big">
+                                <rect key="frame" x="10" y="38" width="420" height="1"/>
+                                <color key="backgroundColor" red="0.94901960780000005" green="0.94901960780000005" blue="0.94901960780000005" alpha="1" colorSpace="calibratedRGB"/>
+                                <constraints>
+                                    <constraint firstAttribute="height" constant="1" id="J5x-mn-Xjj"/>
+                                </constraints>
+                            </view>
+                            <imageView clipsSubviews="YES" userInteractionEnabled="NO" contentMode="scaleAspectFit" horizontalHuggingPriority="251" verticalHuggingPriority="251" image="course_time" translatesAutoresizingMaskIntoConstraints="NO" id="tGm-S4-F4x">
+                                <rect key="frame" x="11" y="12" width="16" height="16"/>
+                                <constraints>
+                                    <constraint firstAttribute="height" constant="16" id="JtY-7v-IEx"/>
+                                    <constraint firstAttribute="width" constant="16" id="eRH-xo-J70"/>
+                                </constraints>
+                            </imageView>
+                            <label opaque="NO" userInteractionEnabled="NO" contentMode="left" horizontalHuggingPriority="251" verticalHuggingPriority="251" text="2021/09/17 14:00~14:25" textAlignment="natural" lineBreakMode="tailTruncation" baselineAdjustment="alignBaselines" adjustsFontSizeToFit="NO" translatesAutoresizingMaskIntoConstraints="NO" id="pXr-41-D0m">
+                                <rect key="frame" x="34" y="12" width="147" height="16"/>
+                                <fontDescription key="fontDescription" type="system" pointSize="13"/>
+                                <color key="textColor" red="0.40000000000000002" green="0.40000000000000002" blue="0.40000000000000002" alpha="1" colorSpace="calibratedRGB"/>
+                                <nil key="highlightedColor"/>
+                            </label>
+                            <label opaque="NO" userInteractionEnabled="NO" contentMode="left" horizontalHuggingPriority="251" verticalHuggingPriority="251" text="已结束" textAlignment="center" lineBreakMode="tailTruncation" baselineAdjustment="alignBaselines" adjustsFontSizeToFit="NO" translatesAutoresizingMaskIntoConstraints="NO" id="1qw-WH-Jvr">
+                                <rect key="frame" x="379" y="11.5" width="50" height="17"/>
+                                <constraints>
+                                    <constraint firstAttribute="width" constant="50" id="E6U-2d-Wcf"/>
+                                </constraints>
+                                <fontDescription key="fontDescription" type="system" weight="medium" pointSize="14"/>
+                                <color key="textColor" red="0.59999999999999998" green="0.59999999999999998" blue="0.59999999999999998" alpha="1" colorSpace="calibratedRGB"/>
+                                <nil key="highlightedColor"/>
+                            </label>
+                            <imageView clipsSubviews="YES" userInteractionEnabled="NO" contentMode="scaleAspectFill" horizontalHuggingPriority="251" verticalHuggingPriority="251" image="user_default_avatal" translatesAutoresizingMaskIntoConstraints="NO" id="RUc-4R-w37">
+                                <rect key="frame" x="11" y="56" width="47" height="47"/>
+                                <constraints>
+                                    <constraint firstAttribute="width" constant="47" id="ERa-d0-RjJ"/>
+                                    <constraint firstAttribute="height" constant="47" id="b7T-Sz-cr8"/>
+                                </constraints>
+                                <userDefinedRuntimeAttributes>
+                                    <userDefinedRuntimeAttribute type="number" keyPath="cornerRadius">
+                                        <real key="value" value="5"/>
+                                    </userDefinedRuntimeAttribute>
+                                </userDefinedRuntimeAttributes>
+                            </imageView>
+                            <label opaque="NO" userInteractionEnabled="NO" contentMode="left" horizontalHuggingPriority="251" verticalHuggingPriority="251" text="孙老师" textAlignment="natural" lineBreakMode="tailTruncation" baselineAdjustment="alignBaselines" adjustsFontSizeToFit="NO" translatesAutoresizingMaskIntoConstraints="NO" id="FpP-hs-iFV">
+                                <rect key="frame" x="68" y="56" width="49" height="24"/>
+                                <constraints>
+                                    <constraint firstAttribute="height" constant="24" id="EnM-36-tXQ"/>
+                                </constraints>
+                                <fontDescription key="fontDescription" type="system" weight="medium" pointSize="16"/>
+                                <color key="textColor" red="0.1019607843" green="0.1019607843" blue="0.1019607843" alpha="1" colorSpace="calibratedRGB"/>
+                                <nil key="highlightedColor"/>
+                            </label>
+                            <view contentMode="scaleToFill" translatesAutoresizingMaskIntoConstraints="NO" id="6lL-kM-wkw">
+                                <rect key="frame" x="68" y="83" width="44" height="20"/>
+                                <subviews>
+                                    <label opaque="NO" userInteractionEnabled="NO" contentMode="left" horizontalHuggingPriority="251" verticalHuggingPriority="251" text="单簧管" textAlignment="natural" lineBreakMode="tailTruncation" baselineAdjustment="alignBaselines" adjustsFontSizeToFit="NO" translatesAutoresizingMaskIntoConstraints="NO" id="N2M-qy-lji">
+                                        <rect key="frame" x="5" y="0.0" width="34" height="20"/>
+                                        <fontDescription key="fontDescription" type="system" pointSize="11"/>
+                                        <color key="textColor" red="1" green="0.54901960780000003" blue="0.0" alpha="1" colorSpace="calibratedRGB"/>
+                                        <nil key="highlightedColor"/>
+                                    </label>
+                                </subviews>
+                                <color key="backgroundColor" red="1" green="0.94509803920000002" blue="0.87058823529999996" alpha="1" colorSpace="calibratedRGB"/>
+                                <constraints>
+                                    <constraint firstAttribute="height" constant="20" id="0Bh-JX-Emk"/>
+                                    <constraint firstAttribute="bottom" secondItem="N2M-qy-lji" secondAttribute="bottom" id="W9B-0Z-WhX"/>
+                                    <constraint firstAttribute="trailing" secondItem="N2M-qy-lji" secondAttribute="trailing" constant="5" id="gCN-fa-45e"/>
+                                    <constraint firstItem="N2M-qy-lji" firstAttribute="leading" secondItem="6lL-kM-wkw" secondAttribute="leading" constant="5" id="mBQ-WO-UKp"/>
+                                    <constraint firstItem="N2M-qy-lji" firstAttribute="top" secondItem="6lL-kM-wkw" secondAttribute="top" id="yfs-2E-vzh"/>
+                                </constraints>
+                                <userDefinedRuntimeAttributes>
+                                    <userDefinedRuntimeAttribute type="number" keyPath="cornerRadius">
+                                        <real key="value" value="4"/>
+                                    </userDefinedRuntimeAttribute>
+                                </userDefinedRuntimeAttributes>
+                            </view>
+                            <button opaque="NO" contentMode="scaleToFill" contentHorizontalAlignment="center" contentVerticalAlignment="center" lineBreakMode="middleTruncation" translatesAutoresizingMaskIntoConstraints="NO" id="p4E-9g-vYI">
+                                <rect key="frame" x="117" y="48" width="40" height="40"/>
+                                <constraints>
+                                    <constraint firstAttribute="width" constant="40" id="NEW-y5-Oa7"/>
+                                    <constraint firstAttribute="height" constant="40" id="zmM-0I-BZc"/>
+                                </constraints>
+                                <inset key="imageEdgeInsets" minX="0.0" minY="0.0" maxX="2.2250738585072014e-308" maxY="0.0"/>
+                                <state key="normal" image="course_chat"/>
+                                <connections>
+                                    <action selector="chatAction:" destination="KGk-i7-Jjw" eventType="touchUpInside" id="SHA-Sd-33P"/>
+                                </connections>
+                            </button>
+                        </subviews>
+                        <color key="backgroundColor" systemColor="systemBackgroundColor"/>
+                        <constraints>
+                            <constraint firstAttribute="trailing" secondItem="1qw-WH-Jvr" secondAttribute="trailing" constant="11" id="18O-zO-GbD"/>
+                            <constraint firstItem="tGm-S4-F4x" firstAttribute="top" secondItem="7PV-kN-jHP" secondAttribute="top" constant="12" id="4GN-CO-nq1"/>
+                            <constraint firstItem="8DG-NN-Big" firstAttribute="top" secondItem="tGm-S4-F4x" secondAttribute="bottom" constant="10" id="6Ws-sC-rr1"/>
+                            <constraint firstItem="8DG-NN-Big" firstAttribute="leading" secondItem="7PV-kN-jHP" secondAttribute="leading" constant="10" id="ABd-pR-d50"/>
+                            <constraint firstItem="6lL-kM-wkw" firstAttribute="leading" secondItem="FpP-hs-iFV" secondAttribute="leading" id="AMW-R9-Bcq"/>
+                            <constraint firstItem="1qw-WH-Jvr" firstAttribute="leading" relation="greaterThanOrEqual" secondItem="pXr-41-D0m" secondAttribute="trailing" constant="10" id="Cot-6G-AkF"/>
+                            <constraint firstItem="RUc-4R-w37" firstAttribute="top" secondItem="8DG-NN-Big" secondAttribute="bottom" constant="17" id="Ex9-cF-vet"/>
+                            <constraint firstItem="p4E-9g-vYI" firstAttribute="leading" secondItem="FpP-hs-iFV" secondAttribute="trailing" id="Gpq-6F-6J4"/>
+                            <constraint firstItem="RUc-4R-w37" firstAttribute="leading" secondItem="7PV-kN-jHP" secondAttribute="leading" constant="11" id="LyQ-fd-Lkg"/>
+                            <constraint firstAttribute="trailing" secondItem="8DG-NN-Big" secondAttribute="trailing" constant="10" id="Mzo-e4-Gx1"/>
+                            <constraint firstItem="p4E-9g-vYI" firstAttribute="centerY" secondItem="FpP-hs-iFV" secondAttribute="centerY" id="TMh-aj-iKs"/>
+                            <constraint firstItem="FpP-hs-iFV" firstAttribute="top" secondItem="RUc-4R-w37" secondAttribute="top" id="Vs4-cN-QKB"/>
+                            <constraint firstItem="pXr-41-D0m" firstAttribute="leading" secondItem="tGm-S4-F4x" secondAttribute="trailing" constant="7" id="gdm-De-jDR"/>
+                            <constraint firstItem="6lL-kM-wkw" firstAttribute="bottom" secondItem="RUc-4R-w37" secondAttribute="bottom" id="grq-IE-FpO"/>
+                            <constraint firstItem="tGm-S4-F4x" firstAttribute="leading" secondItem="7PV-kN-jHP" secondAttribute="leading" constant="11" id="h4I-tZ-hfV"/>
+                            <constraint firstItem="FpP-hs-iFV" firstAttribute="leading" secondItem="RUc-4R-w37" secondAttribute="trailing" constant="10" id="ktR-vp-74U"/>
+                            <constraint firstItem="pXr-41-D0m" firstAttribute="centerY" secondItem="tGm-S4-F4x" secondAttribute="centerY" id="rTa-Wu-PAv"/>
+                            <constraint firstItem="1qw-WH-Jvr" firstAttribute="centerY" secondItem="pXr-41-D0m" secondAttribute="centerY" id="yWK-wY-KLq"/>
+                        </constraints>
+                        <userDefinedRuntimeAttributes>
+                            <userDefinedRuntimeAttribute type="number" keyPath="cornerRadius">
+                                <real key="value" value="10"/>
+                            </userDefinedRuntimeAttribute>
+                        </userDefinedRuntimeAttributes>
+                    </view>
+                </subviews>
+                <constraints>
+                    <constraint firstItem="7PV-kN-jHP" firstAttribute="leading" secondItem="H2p-sc-9uM" secondAttribute="leading" constant="14" id="J8J-il-NaF"/>
+                    <constraint firstItem="7PV-kN-jHP" firstAttribute="top" secondItem="H2p-sc-9uM" secondAttribute="top" id="QRL-Nt-LjS"/>
+                    <constraint firstAttribute="bottom" secondItem="7PV-kN-jHP" secondAttribute="bottom" constant="12" id="dAT-MI-rz7"/>
+                    <constraint firstAttribute="trailing" secondItem="7PV-kN-jHP" secondAttribute="trailing" constant="14" id="inf-74-qqm"/>
+                </constraints>
+            </tableViewCellContentView>
+            <viewLayoutGuide key="safeArea" id="aW0-zy-SZf"/>
+            <color key="backgroundColor" white="0.0" alpha="0.0" colorSpace="custom" customColorSpace="genericGamma22GrayColorSpace"/>
+            <connections>
+                <outlet property="courseTime" destination="pXr-41-D0m" id="P4z-qr-Sz2"/>
+                <outlet property="statusLabel" destination="1qw-WH-Jvr" id="Ft9-cT-Ndb"/>
+                <outlet property="studentAvatal" destination="RUc-4R-w37" id="ZyZ-wJ-Xmv"/>
+                <outlet property="studentNameLabel" destination="FpP-hs-iFV" id="nao-Cd-xgS"/>
+                <outlet property="subjectLabel" destination="N2M-qy-lji" id="GVs-Ed-0bm"/>
+            </connections>
+            <point key="canvasLocation" x="263.768115942029" y="109.82142857142857"/>
+        </tableViewCell>
+    </objects>
+    <resources>
+        <image name="course_chat" width="19" height="18"/>
+        <image name="course_time" width="16" height="16"/>
+        <image name="user_default_avatal" width="52" height="52"/>
+        <systemColor name="systemBackgroundColor">
+            <color white="1" alpha="1" colorSpace="custom" customColorSpace="genericGamma22GrayColorSpace"/>
+        </systemColor>
+    </resources>
+</document>

+ 27 - 0
KulexiuForStudent/KulexiuForStudent/Module/Mine/Homework/View/HomeworkSortView.h

@@ -0,0 +1,27 @@
+//
+//  HomeworkSortView.h
+//  KulexiuForTeacher
+//
+//  Created by 王智 on 2022/4/13.
+//
+
+#import <UIKit/UIKit.h>
+
+NS_ASSUME_NONNULL_BEGIN
+
+typedef void(^TimeSortCallback)(void);
+
+@interface HomeworkSortView : UIView
+
+@property (weak, nonatomic) IBOutlet UILabel *sortTitleLabel;
+
+@property (nonatomic, assign) BOOL arrowUp;
+
++ (instancetype)shareInstance;
+
+- (void)sortAction:(TimeSortCallback)callback;
+
+
+@end
+
+NS_ASSUME_NONNULL_END

+ 52 - 0
KulexiuForStudent/KulexiuForStudent/Module/Mine/Homework/View/HomeworkSortView.m

@@ -0,0 +1,52 @@
+//
+//  HomeworkSortView.m
+//  KulexiuForTeacher
+//
+//  Created by 王智 on 2022/4/13.
+//
+
+#import "HomeworkSortView.h"
+
+@interface HomeworkSortView ()
+
+@property (weak, nonatomic) IBOutlet UIImageView *arrowImage;
+
+@property (nonatomic, copy) TimeSortCallback callback;
+
+@end
+
+@implementation HomeworkSortView
+
++ (instancetype)shareInstance {
+    HomeworkSortView *view = [[[NSBundle mainBundle] loadNibNamed:@"HomeworkSortView" owner:nil options:nil] firstObject];
+    return view;
+}
+
+- (void)sortAction:(TimeSortCallback)callback {
+    if (callback) {
+        self.callback = callback;
+    }
+}
+
+- (IBAction)sortButtonAction:(id)sender {
+    self.arrowUp = YES;
+    if (self.callback) {
+        self.callback();
+    }
+}
+
+- (void)setArrowUp:(BOOL)arrowUp {
+    _arrowUp = arrowUp;
+    NSString *imageName = arrowUp ? @"sort_up" : @"sort_down";
+    [self.arrowImage setImage:[UIImage imageNamed:imageName]];
+}
+
+/*
+// Only override drawRect: if you perform custom drawing.
+// An empty implementation adversely affects performance during animation.
+- (void)drawRect:(CGRect)rect {
+    // Drawing code
+}
+*/
+
+@end

+ 61 - 0
KulexiuForStudent/KulexiuForStudent/Module/Mine/Homework/View/HomeworkSortView.xib

@@ -0,0 +1,61 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<document type="com.apple.InterfaceBuilder3.CocoaTouch.XIB" version="3.0" toolsVersion="20037" targetRuntime="iOS.CocoaTouch" propertyAccessControl="none" useAutolayout="YES" useTraitCollections="YES" colorMatched="YES">
+    <device id="retina6_1" orientation="portrait" appearance="light"/>
+    <dependencies>
+        <deployment identifier="iOS"/>
+        <plugIn identifier="com.apple.InterfaceBuilder.IBCocoaTouchPlugin" version="20020"/>
+        <capability name="documents saved in the Xcode 8 format" minToolsVersion="8.0"/>
+    </dependencies>
+    <objects>
+        <placeholder placeholderIdentifier="IBFilesOwner" id="-1" userLabel="File's Owner"/>
+        <placeholder placeholderIdentifier="IBFirstResponder" id="-2" customClass="UIResponder"/>
+        <view contentMode="scaleToFill" id="iN0-l3-epB" customClass="HomeworkSortView">
+            <rect key="frame" x="0.0" y="0.0" width="414" height="71"/>
+            <autoresizingMask key="autoresizingMask"/>
+            <subviews>
+                <label opaque="NO" userInteractionEnabled="NO" contentMode="left" horizontalHuggingPriority="251" verticalHuggingPriority="251" text="2021年9月" textAlignment="natural" lineBreakMode="tailTruncation" baselineAdjustment="alignBaselines" adjustsFontSizeToFit="NO" translatesAutoresizingMaskIntoConstraints="NO" id="t4D-yi-OH7">
+                    <rect key="frame" x="14" y="25.5" width="69" height="20"/>
+                    <constraints>
+                        <constraint firstAttribute="height" constant="20" id="Wp2-fJ-Nhg"/>
+                    </constraints>
+                    <fontDescription key="fontDescription" type="system" pointSize="14"/>
+                    <color key="textColor" red="0.20000000000000001" green="0.20000000000000001" blue="0.20000000000000001" alpha="1" colorSpace="calibratedRGB"/>
+                    <nil key="highlightedColor"/>
+                </label>
+                <imageView clipsSubviews="YES" userInteractionEnabled="NO" contentMode="scaleAspectFit" horizontalHuggingPriority="251" verticalHuggingPriority="251" image="sort_down" translatesAutoresizingMaskIntoConstraints="NO" id="dxn-Em-1xD">
+                    <rect key="frame" x="86" y="32.5" width="8" height="6"/>
+                </imageView>
+                <button opaque="NO" contentMode="scaleToFill" contentHorizontalAlignment="center" contentVerticalAlignment="center" lineBreakMode="middleTruncation" translatesAutoresizingMaskIntoConstraints="NO" id="0zE-tr-Z1O">
+                    <rect key="frame" x="14" y="0.0" width="80" height="71"/>
+                    <inset key="imageEdgeInsets" minX="0.0" minY="0.0" maxX="2.2250738585072014e-308" maxY="0.0"/>
+                    <connections>
+                        <action selector="sortButtonAction:" destination="iN0-l3-epB" eventType="touchUpInside" id="rWv-0j-Xxb"/>
+                    </connections>
+                </button>
+            </subviews>
+            <color key="backgroundColor" white="0.0" alpha="0.0" colorSpace="custom" customColorSpace="genericGamma22GrayColorSpace"/>
+            <constraints>
+                <constraint firstItem="0zE-tr-Z1O" firstAttribute="top" secondItem="iN0-l3-epB" secondAttribute="top" id="3A4-LV-UX8"/>
+                <constraint firstItem="t4D-yi-OH7" firstAttribute="leading" secondItem="0zE-tr-Z1O" secondAttribute="leading" id="IEw-nx-7uA"/>
+                <constraint firstItem="dxn-Em-1xD" firstAttribute="centerY" secondItem="0zE-tr-Z1O" secondAttribute="centerY" id="bQb-1X-2bN"/>
+                <constraint firstItem="dxn-Em-1xD" firstAttribute="centerY" secondItem="t4D-yi-OH7" secondAttribute="centerY" id="plf-sU-8TP"/>
+                <constraint firstAttribute="bottom" secondItem="0zE-tr-Z1O" secondAttribute="bottom" id="qyE-Vi-A46"/>
+                <constraint firstItem="dxn-Em-1xD" firstAttribute="leading" secondItem="t4D-yi-OH7" secondAttribute="trailing" constant="3" id="rdB-Cz-jgk"/>
+                <constraint firstItem="dxn-Em-1xD" firstAttribute="trailing" secondItem="0zE-tr-Z1O" secondAttribute="trailing" id="uMM-8g-Iey"/>
+                <constraint firstItem="t4D-yi-OH7" firstAttribute="leading" secondItem="iN0-l3-epB" secondAttribute="leading" constant="14" id="xba-oZ-dqJ"/>
+                <constraint firstItem="t4D-yi-OH7" firstAttribute="centerY" secondItem="iN0-l3-epB" secondAttribute="centerY" id="yPk-Hn-IMF"/>
+            </constraints>
+            <nil key="simulatedTopBarMetrics"/>
+            <nil key="simulatedBottomBarMetrics"/>
+            <freeformSimulatedSizeMetrics key="simulatedDestinationMetrics"/>
+            <connections>
+                <outlet property="arrowImage" destination="dxn-Em-1xD" id="9IA-4h-Loj"/>
+                <outlet property="sortTitleLabel" destination="t4D-yi-OH7" id="aJ4-rZ-EMq"/>
+            </connections>
+            <point key="canvasLocation" x="131.8840579710145" y="41.852678571428569"/>
+        </view>
+    </objects>
+    <resources>
+        <image name="sort_down" width="8" height="6"/>
+    </resources>
+</document>

+ 30 - 0
KulexiuForStudent/KulexiuForStudent/Module/Mine/Homework/View/HomeworkVideoView.h

@@ -0,0 +1,30 @@
+//
+//  HomeworkVideoView.h
+//  KulexiuForTeacher
+//
+//  Created by 王智 on 2022/4/18.
+//
+
+#import <UIKit/UIKit.h>
+@class HomeworkVideoView;
+
+typedef NS_ENUM(NSInteger, VIDEOVIEWACTION) {
+    VIDEOVIEWACTION_PLAY,
+    VIDEOVIEWACTION_DELETE,
+};
+
+NS_ASSUME_NONNULL_BEGIN
+
+typedef void(^VideoViewCallback)(VIDEOVIEWACTION action,NSInteger viewIndex);
+
+@interface HomeworkVideoView : UIView
+
+@property (nonatomic,assign) BOOL hideDeleteButton;
+
++ (instancetype)shareInstance;
+
+- (void)displayVideoUrl:(NSString *)videoUrl callback:(VideoViewCallback)callback;
+
+@end
+
+NS_ASSUME_NONNULL_END

+ 68 - 0
KulexiuForStudent/KulexiuForStudent/Module/Mine/Homework/View/HomeworkVideoView.m

@@ -0,0 +1,68 @@
+//
+//  HomeworkVideoView.m
+//  KulexiuForTeacher
+//
+//  Created by 王智 on 2022/4/18.
+//
+
+#import "HomeworkVideoView.h"
+#import "KSVideoHelper.h"
+
+@interface HomeworkVideoView ()
+
+@property (weak, nonatomic) IBOutlet UIImageView *videoImage;
+
+@property (weak, nonatomic) IBOutlet UIButton *deleteButton;
+
+@property (nonatomic, copy) VideoViewCallback callback;
+
+@end
+
+@implementation HomeworkVideoView
+
++ (instancetype)shareInstance {
+    HomeworkVideoView *view = [[[NSBundle mainBundle] loadNibNamed:@"HomeworkVideoView" owner:nil options:nil] firstObject];
+    return view;
+}
+
+- (void)displayVideoUrl:(NSString *)videoUrl callback:(VideoViewCallback)callback {
+    if (callback) {
+        self.callback = callback;
+    }
+    [KSVideoHelper getVideoPreviewImageUrl:videoUrl forImageView:self.videoImage placeholder:[UIImage imageNamed:@"video_placeholder"]];
+}
+
+- (void)setHideDeleteButton:(BOOL)hideDeleteButton {
+    _hideDeleteButton = hideDeleteButton;
+    if (hideDeleteButton) {
+        self.deleteButton.hidden = YES;
+        self.deleteButton.userInteractionEnabled = NO;
+    }
+    else {
+        self.deleteButton.hidden = NO;
+        self.deleteButton.userInteractionEnabled = YES;
+    }
+}
+
+- (IBAction)playButtonAction:(id)sender {
+    if (self.callback) {
+        self.callback(VIDEOVIEWACTION_PLAY, self.tag-1000);
+    }
+}
+
+- (IBAction)deleteAction:(id)sender {
+    if (self.callback) {
+        self.callback(VIDEOVIEWACTION_DELETE, self.tag-1000);
+    }
+}
+
+
+/*
+// Only override drawRect: if you perform custom drawing.
+// An empty implementation adversely affects performance during animation.
+- (void)drawRect:(CGRect)rect {
+    // Drawing code
+}
+*/
+
+@end

+ 88 - 0
KulexiuForStudent/KulexiuForStudent/Module/Mine/Homework/View/HomeworkVideoView.xib

@@ -0,0 +1,88 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<document type="com.apple.InterfaceBuilder3.CocoaTouch.XIB" version="3.0" toolsVersion="20037" targetRuntime="iOS.CocoaTouch" propertyAccessControl="none" useAutolayout="YES" useTraitCollections="YES" colorMatched="YES">
+    <device id="retina6_1" orientation="portrait" appearance="light"/>
+    <dependencies>
+        <deployment identifier="iOS"/>
+        <plugIn identifier="com.apple.InterfaceBuilder.IBCocoaTouchPlugin" version="20020"/>
+        <capability name="documents saved in the Xcode 8 format" minToolsVersion="8.0"/>
+    </dependencies>
+    <objects>
+        <placeholder placeholderIdentifier="IBFilesOwner" id="-1" userLabel="File's Owner"/>
+        <placeholder placeholderIdentifier="IBFirstResponder" id="-2" customClass="UIResponder"/>
+        <view contentMode="scaleToFill" id="iN0-l3-epB" customClass="HomeworkVideoView">
+            <rect key="frame" x="0.0" y="0.0" width="269" height="144"/>
+            <autoresizingMask key="autoresizingMask"/>
+            <subviews>
+                <view contentMode="scaleToFill" translatesAutoresizingMaskIntoConstraints="NO" id="rO5-WR-JIz">
+                    <rect key="frame" x="0.0" y="11" width="258" height="122"/>
+                    <subviews>
+                        <imageView clipsSubviews="YES" userInteractionEnabled="NO" contentMode="scaleAspectFill" horizontalHuggingPriority="251" verticalHuggingPriority="251" image="video_placeholder" translatesAutoresizingMaskIntoConstraints="NO" id="gHr-CE-99d">
+                            <rect key="frame" x="0.0" y="0.0" width="258" height="122"/>
+                            <color key="backgroundColor" white="0.0" alpha="0.0" colorSpace="custom" customColorSpace="genericGamma22GrayColorSpace"/>
+                        </imageView>
+                        <button opaque="NO" contentMode="scaleToFill" contentHorizontalAlignment="center" contentVerticalAlignment="center" lineBreakMode="middleTruncation" translatesAutoresizingMaskIntoConstraints="NO" id="PPM-pp-KPh">
+                            <rect key="frame" x="107" y="39" width="44" height="44"/>
+                            <constraints>
+                                <constraint firstAttribute="width" constant="44" id="34f-sk-BQa"/>
+                                <constraint firstAttribute="height" constant="44" id="Yfs-VJ-ptv"/>
+                            </constraints>
+                            <inset key="imageEdgeInsets" minX="0.0" minY="0.0" maxX="2.2250738585072014e-308" maxY="0.0"/>
+                            <state key="normal" image="playVideo_image"/>
+                            <connections>
+                                <action selector="playButtonAction:" destination="iN0-l3-epB" eventType="touchUpInside" id="AB0-aS-CaM"/>
+                            </connections>
+                        </button>
+                    </subviews>
+                    <color key="backgroundColor" white="0.0" alpha="0.0" colorSpace="custom" customColorSpace="genericGamma22GrayColorSpace"/>
+                    <constraints>
+                        <constraint firstItem="PPM-pp-KPh" firstAttribute="centerX" secondItem="rO5-WR-JIz" secondAttribute="centerX" id="JHL-B3-1f2"/>
+                        <constraint firstAttribute="trailing" secondItem="gHr-CE-99d" secondAttribute="trailing" id="JWt-TI-hBz"/>
+                        <constraint firstItem="gHr-CE-99d" firstAttribute="top" secondItem="rO5-WR-JIz" secondAttribute="top" id="KnA-ig-rMW"/>
+                        <constraint firstAttribute="bottom" secondItem="gHr-CE-99d" secondAttribute="bottom" id="MSH-Fc-g7W"/>
+                        <constraint firstItem="PPM-pp-KPh" firstAttribute="centerY" secondItem="rO5-WR-JIz" secondAttribute="centerY" id="rV7-EE-BTr"/>
+                        <constraint firstItem="gHr-CE-99d" firstAttribute="leading" secondItem="rO5-WR-JIz" secondAttribute="leading" id="xN9-EC-NeB"/>
+                    </constraints>
+                    <userDefinedRuntimeAttributes>
+                        <userDefinedRuntimeAttribute type="number" keyPath="cornerRadius">
+                            <real key="value" value="10"/>
+                        </userDefinedRuntimeAttribute>
+                    </userDefinedRuntimeAttributes>
+                </view>
+                <button opaque="NO" contentMode="scaleToFill" contentHorizontalAlignment="center" contentVerticalAlignment="center" lineBreakMode="middleTruncation" translatesAutoresizingMaskIntoConstraints="NO" id="ISP-Z6-g0a">
+                    <rect key="frame" x="247" y="0.0" width="22" height="22"/>
+                    <constraints>
+                        <constraint firstAttribute="width" constant="22" id="6uC-Rk-yxh"/>
+                        <constraint firstAttribute="height" constant="22" id="t7e-qc-N6I"/>
+                    </constraints>
+                    <inset key="imageEdgeInsets" minX="0.0" minY="0.0" maxX="2.2250738585072014e-308" maxY="0.0"/>
+                    <state key="normal" image="video_delete"/>
+                    <connections>
+                        <action selector="deleteAction:" destination="iN0-l3-epB" eventType="touchUpInside" id="8yK-yg-qlh"/>
+                    </connections>
+                </button>
+            </subviews>
+            <color key="backgroundColor" white="0.0" alpha="0.0" colorSpace="custom" customColorSpace="genericGamma22GrayColorSpace"/>
+            <constraints>
+                <constraint firstAttribute="bottom" secondItem="rO5-WR-JIz" secondAttribute="bottom" constant="11" id="e4v-r6-cOI"/>
+                <constraint firstItem="rO5-WR-JIz" firstAttribute="top" secondItem="iN0-l3-epB" secondAttribute="top" constant="11" id="iHL-C1-ymd"/>
+                <constraint firstAttribute="trailing" secondItem="rO5-WR-JIz" secondAttribute="trailing" constant="11" id="pPg-Wq-ZA1"/>
+                <constraint firstItem="ISP-Z6-g0a" firstAttribute="top" secondItem="iN0-l3-epB" secondAttribute="top" id="qio-LT-SbC"/>
+                <constraint firstAttribute="trailing" secondItem="ISP-Z6-g0a" secondAttribute="trailing" id="sTY-Iv-Pnz"/>
+                <constraint firstItem="rO5-WR-JIz" firstAttribute="leading" secondItem="iN0-l3-epB" secondAttribute="leading" id="xK9-L4-zph"/>
+            </constraints>
+            <nil key="simulatedTopBarMetrics"/>
+            <nil key="simulatedBottomBarMetrics"/>
+            <freeformSimulatedSizeMetrics key="simulatedDestinationMetrics"/>
+            <connections>
+                <outlet property="deleteButton" destination="ISP-Z6-g0a" id="rlS-hF-AEJ"/>
+                <outlet property="videoImage" destination="gHr-CE-99d" id="RPL-3x-Poj"/>
+            </connections>
+            <point key="canvasLocation" x="236.95652173913047" y="-174.10714285714286"/>
+        </view>
+    </objects>
+    <resources>
+        <image name="playVideo_image" width="26" height="26"/>
+        <image name="video_delete" width="22" height="22"/>
+        <image name="video_placeholder" width="103" height="72"/>
+    </resources>
+</document>

+ 1 - 0
KulexiuForStudent/KulexiuForStudent/Module/Mine/MineCourse/Controller/MyCourseViewController.m

@@ -17,6 +17,7 @@
     [super viewDidLoad];
     // Do any additional setup after loading the view.
     [self allocTitle:@"我的课程"];
+    self.titles = @[@"陪练课",@"直播课",@"视频课"];
 }
 
 /*

+ 20 - 0
KulexiuForStudent/KulexiuForStudent/Module/Mine/View/KSStarView.h

@@ -0,0 +1,20 @@
+//
+//  KSStarView.h
+//  KulexiuForTeacher
+//
+//  Created by Kyle on 2022/3/28.
+//
+
+#import <UIKit/UIKit.h>
+
+NS_ASSUME_NONNULL_BEGIN
+
+@interface KSStarView : UIView
+
+@property (nonatomic, assign) CGFloat rate;     //比例0~1
+
+@property (nonatomic, assign) BOOL allowMark;//是否允许评分
+
+@end
+
+NS_ASSUME_NONNULL_END

+ 126 - 0
KulexiuForStudent/KulexiuForStudent/Module/Mine/View/KSStarView.m

@@ -0,0 +1,126 @@
+//
+//  KSStarView.m
+//  KulexiuForTeacher
+//
+//  Created by Kyle on 2022/3/28.
+//
+
+#import "KSStarView.h"
+
+#define kStarMaxCount 5
+#define kGrayImgName   @"star_grey"
+#define kYellowImgName  @"star_light"
+
+
+@interface KSStarView ()
+
+@property (nonatomic, strong) UIView *grayView;
+@property (nonatomic, strong) UIView *yellowView;
+
+@property (nonatomic, assign) CGFloat realWidth;
+@property (nonatomic, assign) CGFloat realHeight;
+
+@end
+
+@implementation KSStarView
+
+- (instancetype)initWithFrame:(CGRect)frame {
+    if (self = [super initWithFrame:frame]) {
+        [self initUI];
+    }
+    return self;
+}
+
+-(instancetype)initWithCoder:(NSCoder *)aDecoder
+{
+    if (self = [super initWithCoder:aDecoder]) {
+        [self initUI];
+    }
+    return self;
+}
+
+-(void)initUI {
+    UIImage *grayImg = [UIImage imageNamed:kGrayImgName];
+    if (grayImg.size.width*kStarMaxCount/grayImg.size.height < self.bounds.size.width/self.bounds.size.height)
+    {
+        //视图过长
+        self.realHeight = self.bounds.size.height;
+        self.realWidth = (grayImg.size.width*kStarMaxCount)/grayImg.size.height * self.realHeight;
+    }
+    else
+    {
+        self.realWidth = self.bounds.size.width;
+        self.realHeight = grayImg.size.height / (grayImg.size.width*kStarMaxCount) * self.realWidth;
+    }
+    
+    CGFloat scale = self.realHeight / grayImg.size.height;
+    
+    //灰底
+    self.grayView = [[UIView alloc] initWithFrame:CGRectMake(0, 0, grayImg.size.width*kStarMaxCount, grayImg.size.height)];
+    self.grayView.center = CGPointMake(self.bounds.size.width/2.0, self.bounds.size.height/2.0);
+    self.grayView.clipsToBounds = YES;
+    self.grayView.backgroundColor = [UIColor colorWithPatternImage:[UIImage imageNamed:kGrayImgName]];
+    self.grayView.transform = CGAffineTransformMakeScale(scale, scale);
+    [self addSubview:self.grayView];
+    
+    //星星
+    self.yellowView = [[UIView alloc] initWithFrame:self.grayView.bounds];
+    self.yellowView.center = self.grayView.center;
+    self.yellowView.clipsToBounds = YES;
+    self.yellowView.backgroundColor = [UIColor colorWithPatternImage:[UIImage imageNamed:kYellowImgName]];
+    self.yellowView.transform = CGAffineTransformMakeScale(scale, scale);
+    [self addSubview:self.yellowView];
+    
+    UITapGestureRecognizer *tapGesture = [[UITapGestureRecognizer alloc] initWithTarget:self action:@selector(gestureAction:)];
+    [self addGestureRecognizer:tapGesture];
+}
+
+-(void)setRate:(CGFloat)rate
+{
+    _rate = rate;
+    
+    if (rate > 1) {
+        _rate = 1;
+    }
+    else if (rate < 0){
+        _rate = 0;
+    }
+    
+    [self setNeedsLayout];
+}
+
+
+-(void)layoutSubviews
+{
+    [super layoutSubviews];
+    
+    self.yellowView.frame = CGRectMake(self.grayView.frame.origin.x, self.grayView.frame.origin.y, self.realWidth * self.rate, self.realHeight);
+}
+
+
+
+-(void)gestureAction:(UITapGestureRecognizer *)gesture
+{
+    if (!self.allowMark) {
+        return;
+    }
+    
+    CGPoint point = [gesture locationInView:self];
+    double num = (point.x - self.grayView.frame.origin.x) / (self.realWidth/5);
+    if (num < 0) {
+        num = 0;
+    }
+    
+    self.rate = ceil(num) / kStarMaxCount < 1.0/kStarMaxCount ? 1.0 / kStarMaxCount : ceil(num) / kStarMaxCount;
+}
+
+
+/*
+// Only override drawRect: if you perform custom drawing.
+// An empty implementation adversely affects performance during animation.
+- (void)drawRect:(CGRect)rect {
+    // Drawing code
+}
+*/
+
+@end

+ 3 - 3
KulexiuForStudent/Podfile

@@ -12,7 +12,7 @@ target 'KulexiuForStudent' do
   pod 'AFNetworking', '~> 4.0'
   pod 'Masonry', '~> 1.1.0'
   pod 'MBProgressHUD', '~> 1.2.0'
-  pod 'SDWebImage', '~> 3.8.2'
+  pod 'SDWebImage', '~> 5.12.5'
   pod 'MJRefresh', '~> 3.1.12'
   pod 'IQKeyboardManager'
   pod 'Reachability', '~> 3.2'
@@ -35,8 +35,8 @@ target 'KulexiuForStudent' do
   pod 'RongCloudIM/IMLib',  '~> 5.2.0'
   pod 'RongCloudIM/IMKit',  '~> 5.2.0'
   pod 'RongCloudIM/Sight',  '~> 5.2.0'
-  pod 'RongCloudRTC/RongRTCLib','~> 5.2.0'
-#  pod 'RongCloudRTC/RongFaceBeautifier','~> 5.2.0'
+  pod 'RongCloudRTC/RongRTCLib','~> 5.2.1'
+
   # Pods for KulexiuForStudent
 
   target 'KulexiuForStudentTests' do

+ 9 - 9
KulexiuForStudent/Podfile.lock

@@ -66,12 +66,12 @@ PODS:
     - RongCloudIM/IMLibCore
   - RongCloudIM/Sight (5.2.0.1):
     - RongCloudIM/IMKit
-  - RongCloudRTC/RongRTCLib (5.2.0):
+  - RongCloudRTC/RongRTCLib (5.2.1):
     - RongCloudIM/IMLibCore (>= 5.1.3)
   - RSKImageCropper (3.0.2)
-  - SDWebImage (3.8.3):
-    - SDWebImage/Core (= 3.8.3)
-  - SDWebImage/Core (3.8.3)
+  - SDWebImage (5.12.5):
+    - SDWebImage/Core (= 5.12.5)
+  - SDWebImage/Core (5.12.5)
   - SocketRocket (0.6.0)
   - SSZipArchive (2.4.3)
   - UMAPM (1.5.6)
@@ -121,9 +121,9 @@ DEPENDENCIES:
   - RongCloudIM/IMKit (~> 5.2.0)
   - RongCloudIM/IMLib (~> 5.2.0)
   - RongCloudIM/Sight (~> 5.2.0)
-  - RongCloudRTC/RongRTCLib (~> 5.2.0)
+  - RongCloudRTC/RongRTCLib (~> 5.2.1)
   - RSKImageCropper
-  - SDWebImage (~> 3.8.2)
+  - SDWebImage (~> 5.12.5)
   - SocketRocket
   - SSZipArchive
   - UMAPM
@@ -177,9 +177,9 @@ SPEC CHECKSUMS:
   MJRefresh: ee5b68f639775462faba4db0fd243baf4d42c2cf
   Reachability: 33e18b67625424e47b6cde6d202dce689ad7af96
   RongCloudIM: 92b53cd215a397fba7413220411b49179043022d
-  RongCloudRTC: d68b5b91a51d378036d7de0b5fe836e1a93ede9f
+  RongCloudRTC: 0bda17440186a6174fe5871ba30030466cc19c3a
   RSKImageCropper: 1ac71e9a82e3f41eea3eedfff8eacb0d3821c9ec
-  SDWebImage: a72e880a8fe0f7fc31efe15aaed443c074d2a80c
+  SDWebImage: 0905f1b7760fc8ac4198cae0036600d67478751e
   SocketRocket: fccef3f9c5cedea1353a9ef6ada904fde10d6608
   SSZipArchive: fe6a26b2a54d5a0890f2567b5cc6de5caa600aef
   UMAPM: 5ab988b8bedfd090ee2307cb80530ba79b8ac264
@@ -189,6 +189,6 @@ SPEC CHECKSUMS:
   YYModel: 2a7fdd96aaa4b86a824e26d0c517de8928c04b30
   ZKCycleScrollView: 4b353d17b7f469b245a1c606d5a977e72b940895
 
-PODFILE CHECKSUM: 04b96d3c9cef2ea6f6f511a9ef671b6b80141144
+PODFILE CHECKSUM: d1525614cc0e9f425131238bd58c1c5c566c494b
 
 COCOAPODS: 1.11.3

+ 9 - 9
KulexiuForStudent/Pods/Manifest.lock

@@ -66,12 +66,12 @@ PODS:
     - RongCloudIM/IMLibCore
   - RongCloudIM/Sight (5.2.0.1):
     - RongCloudIM/IMKit
-  - RongCloudRTC/RongRTCLib (5.2.0):
+  - RongCloudRTC/RongRTCLib (5.2.1):
     - RongCloudIM/IMLibCore (>= 5.1.3)
   - RSKImageCropper (3.0.2)
-  - SDWebImage (3.8.3):
-    - SDWebImage/Core (= 3.8.3)
-  - SDWebImage/Core (3.8.3)
+  - SDWebImage (5.12.5):
+    - SDWebImage/Core (= 5.12.5)
+  - SDWebImage/Core (5.12.5)
   - SocketRocket (0.6.0)
   - SSZipArchive (2.4.3)
   - UMAPM (1.5.6)
@@ -121,9 +121,9 @@ DEPENDENCIES:
   - RongCloudIM/IMKit (~> 5.2.0)
   - RongCloudIM/IMLib (~> 5.2.0)
   - RongCloudIM/Sight (~> 5.2.0)
-  - RongCloudRTC/RongRTCLib (~> 5.2.0)
+  - RongCloudRTC/RongRTCLib (~> 5.2.1)
   - RSKImageCropper
-  - SDWebImage (~> 3.8.2)
+  - SDWebImage (~> 5.12.5)
   - SocketRocket
   - SSZipArchive
   - UMAPM
@@ -177,9 +177,9 @@ SPEC CHECKSUMS:
   MJRefresh: ee5b68f639775462faba4db0fd243baf4d42c2cf
   Reachability: 33e18b67625424e47b6cde6d202dce689ad7af96
   RongCloudIM: 92b53cd215a397fba7413220411b49179043022d
-  RongCloudRTC: d68b5b91a51d378036d7de0b5fe836e1a93ede9f
+  RongCloudRTC: 0bda17440186a6174fe5871ba30030466cc19c3a
   RSKImageCropper: 1ac71e9a82e3f41eea3eedfff8eacb0d3821c9ec
-  SDWebImage: a72e880a8fe0f7fc31efe15aaed443c074d2a80c
+  SDWebImage: 0905f1b7760fc8ac4198cae0036600d67478751e
   SocketRocket: fccef3f9c5cedea1353a9ef6ada904fde10d6608
   SSZipArchive: fe6a26b2a54d5a0890f2567b5cc6de5caa600aef
   UMAPM: 5ab988b8bedfd090ee2307cb80530ba79b8ac264
@@ -189,6 +189,6 @@ SPEC CHECKSUMS:
   YYModel: 2a7fdd96aaa4b86a824e26d0c517de8928c04b30
   ZKCycleScrollView: 4b353d17b7f469b245a1c606d5a977e72b940895
 
-PODFILE CHECKSUM: 04b96d3c9cef2ea6f6f511a9ef671b6b80141144
+PODFILE CHECKSUM: d1525614cc0e9f425131238bd58c1c5c566c494b
 
 COCOAPODS: 1.11.3

File diff suppressed because it is too large
+ 354 - 240
KulexiuForStudent/Pods/Pods.xcodeproj/project.pbxproj


+ 7 - 7
KulexiuForStudent/Pods/RongCloudRTC/RongCloudRTC/RongRTCLib.xcframework/Info.plist

@@ -6,30 +6,30 @@
 	<array>
 		<dict>
 			<key>LibraryIdentifier</key>
-			<string>ios-x86_64-simulator</string>
+			<string>ios-arm64_armv7</string>
 			<key>LibraryPath</key>
 			<string>RongRTCLib.framework</string>
 			<key>SupportedArchitectures</key>
 			<array>
-				<string>x86_64</string>
+				<string>arm64</string>
+				<string>armv7</string>
 			</array>
 			<key>SupportedPlatform</key>
 			<string>ios</string>
-			<key>SupportedPlatformVariant</key>
-			<string>simulator</string>
 		</dict>
 		<dict>
 			<key>LibraryIdentifier</key>
-			<string>ios-arm64_armv7</string>
+			<string>ios-x86_64-simulator</string>
 			<key>LibraryPath</key>
 			<string>RongRTCLib.framework</string>
 			<key>SupportedArchitectures</key>
 			<array>
-				<string>arm64</string>
-				<string>armv7</string>
+				<string>x86_64</string>
 			</array>
 			<key>SupportedPlatform</key>
 			<string>ios</string>
+			<key>SupportedPlatformVariant</key>
+			<string>simulator</string>
 		</dict>
 	</array>
 	<key>CFBundlePackageType</key>

+ 4 - 4
KulexiuForStudent/Pods/RongCloudRTC/RongCloudRTC/RongRTCLib.xcframework/ios-arm64_armv7/RongRTCLib.framework/Headers/RCRTCLocalUser.h

@@ -283,7 +283,7 @@ NS_ASSUME_NONNULL_BEGIN
  
  @param inviteeRoomId 被邀请人所在房间号
  @param inviteeUserId 被邀请人userId
- @param autoMix 是否将邀请人音视频资源发送到被邀请人房间中合流
+ @param autoMix 是否将被邀请人音视频资源合流到邀请人房间中
  @param extra 附加信息, 可随消息发送给被邀请人
  @param completion 完成的回调
  @discussion
@@ -302,7 +302,7 @@ NS_ASSUME_NONNULL_BEGIN
  
  @param inviteeRoomId 被邀请人所在房间号
  @param inviteeUserId 被邀请人userId
- @param autoMix 是否将邀请人音视频资源发送到被邀请人房间中合流
+ @param autoMix 是否将被邀请人音视频资源合流到邀请人房间中
  @param extra 附加信息, 可随消息发送给被邀请人
  @param completion 完成的回调
  @discussion
@@ -356,7 +356,7 @@ NS_ASSUME_NONNULL_BEGIN
  @param inviterRoomId 邀请人所在的房间号
  @param inviterUserId 邀请人userId
  @param agree 是否同意加入副房间
- @param autoMix 是否将被邀请人音视频资源发送到邀请人房间中合流
+ @param autoMix 是否将邀请人音视频资源合流到被邀请人(响应邀请的人)房间中
  @param extra 附加信息, 可随消息发送给邀请人
  @param completion 完成的回调
  @discussion
@@ -377,7 +377,7 @@ NS_ASSUME_NONNULL_BEGIN
  @param inviterRoomId 邀请人所在的房间号
  @param inviterUserId 邀请人userId
  @param agree 是否同意加入副房间
- @param autoMix 是否将被邀请人音视频资源发送到邀请人房间中合流
+ @param autoMix 是否将邀请人音视频资源合流到被邀请人(响应邀请的人)房间中
  @param extra 附加信息, 可随消息发送给邀请人
  @param completion 完成的回调
  @discussion

BIN
KulexiuForStudent/Pods/RongCloudRTC/RongCloudRTC/RongRTCLib.xcframework/ios-arm64_armv7/RongRTCLib.framework/Info.plist


BIN
KulexiuForStudent/Pods/RongCloudRTC/RongCloudRTC/RongRTCLib.xcframework/ios-arm64_armv7/RongRTCLib.framework/RongRTCLib


+ 4 - 4
KulexiuForStudent/Pods/RongCloudRTC/RongCloudRTC/RongRTCLib.xcframework/ios-arm64_armv7/RongRTCLib.framework/_CodeSignature/CodeResources

@@ -106,7 +106,7 @@
 		</data>
 		<key>Headers/RCRTCLocalUser.h</key>
 		<data>
-		eeARQ+eAF+NjCgK5RLu9c9nCoZI=
+		V07gqERBiW4MPIvcwZJKJyrpboU=
 		</data>
 		<key>Headers/RCRTCLocalVideoView.h</key>
 		<data>
@@ -246,7 +246,7 @@
 		</data>
 		<key>Info.plist</key>
 		<data>
-		VWKBhaPYqsG4AXHsh5ZVULyiHPI=
+		9i3znfKB1CrQjld4q6mkWjzhWjQ=
 		</data>
 		<key>Modules/module.modulemap</key>
 		<data>
@@ -534,11 +534,11 @@
 		<dict>
 			<key>hash</key>
 			<data>
-			eeARQ+eAF+NjCgK5RLu9c9nCoZI=
+			V07gqERBiW4MPIvcwZJKJyrpboU=
 			</data>
 			<key>hash2</key>
 			<data>
-			hR0ZatH0x0wLiTWNLts01Yq70YRDIrBr3GoywXDjy0U=
+			5WBg6Wc7ObbRvCtLmiw6ndqVbeNNHjAvB92/8mqmDDI=
 			</data>
 		</dict>
 		<key>Headers/RCRTCLocalVideoView.h</key>

+ 4 - 4
KulexiuForStudent/Pods/RongCloudRTC/RongCloudRTC/RongRTCLib.xcframework/ios-x86_64-simulator/RongRTCLib.framework/Headers/RCRTCLocalUser.h

@@ -283,7 +283,7 @@ NS_ASSUME_NONNULL_BEGIN
  
  @param inviteeRoomId 被邀请人所在房间号
  @param inviteeUserId 被邀请人userId
- @param autoMix 是否将邀请人音视频资源发送到被邀请人房间中合流
+ @param autoMix 是否将被邀请人音视频资源合流到邀请人房间中
  @param extra 附加信息, 可随消息发送给被邀请人
  @param completion 完成的回调
  @discussion
@@ -302,7 +302,7 @@ NS_ASSUME_NONNULL_BEGIN
  
  @param inviteeRoomId 被邀请人所在房间号
  @param inviteeUserId 被邀请人userId
- @param autoMix 是否将邀请人音视频资源发送到被邀请人房间中合流
+ @param autoMix 是否将被邀请人音视频资源合流到邀请人房间中
  @param extra 附加信息, 可随消息发送给被邀请人
  @param completion 完成的回调
  @discussion
@@ -356,7 +356,7 @@ NS_ASSUME_NONNULL_BEGIN
  @param inviterRoomId 邀请人所在的房间号
  @param inviterUserId 邀请人userId
  @param agree 是否同意加入副房间
- @param autoMix 是否将被邀请人音视频资源发送到邀请人房间中合流
+ @param autoMix 是否将邀请人音视频资源合流到被邀请人(响应邀请的人)房间中
  @param extra 附加信息, 可随消息发送给邀请人
  @param completion 完成的回调
  @discussion
@@ -377,7 +377,7 @@ NS_ASSUME_NONNULL_BEGIN
  @param inviterRoomId 邀请人所在的房间号
  @param inviterUserId 邀请人userId
  @param agree 是否同意加入副房间
- @param autoMix 是否将被邀请人音视频资源发送到邀请人房间中合流
+ @param autoMix 是否将邀请人音视频资源合流到被邀请人(响应邀请的人)房间中
  @param extra 附加信息, 可随消息发送给邀请人
  @param completion 完成的回调
  @discussion

BIN
KulexiuForStudent/Pods/RongCloudRTC/RongCloudRTC/RongRTCLib.xcframework/ios-x86_64-simulator/RongRTCLib.framework/Info.plist


BIN
KulexiuForStudent/Pods/RongCloudRTC/RongCloudRTC/RongRTCLib.xcframework/ios-x86_64-simulator/RongRTCLib.framework/RongRTCLib


+ 4 - 4
KulexiuForStudent/Pods/RongCloudRTC/RongCloudRTC/RongRTCLib.xcframework/ios-x86_64-simulator/RongRTCLib.framework/_CodeSignature/CodeResources

@@ -106,7 +106,7 @@
 		</data>
 		<key>Headers/RCRTCLocalUser.h</key>
 		<data>
-		eeARQ+eAF+NjCgK5RLu9c9nCoZI=
+		V07gqERBiW4MPIvcwZJKJyrpboU=
 		</data>
 		<key>Headers/RCRTCLocalVideoView.h</key>
 		<data>
@@ -246,7 +246,7 @@
 		</data>
 		<key>Info.plist</key>
 		<data>
-		rJX3vb1/BBToTqI1Lhe+IuYPWEc=
+		vdR1KhEmLmhWIGXM7NCSgjaFmgA=
 		</data>
 		<key>Modules/module.modulemap</key>
 		<data>
@@ -534,11 +534,11 @@
 		<dict>
 			<key>hash</key>
 			<data>
-			eeARQ+eAF+NjCgK5RLu9c9nCoZI=
+			V07gqERBiW4MPIvcwZJKJyrpboU=
 			</data>
 			<key>hash2</key>
 			<data>
-			hR0ZatH0x0wLiTWNLts01Yq70YRDIrBr3GoywXDjy0U=
+			5WBg6Wc7ObbRvCtLmiw6ndqVbeNNHjAvB92/8mqmDDI=
 			</data>
 		</dict>
 		<key>Headers/RCRTCLocalVideoView.h</key>

+ 1 - 1
KulexiuForStudent/Pods/SDWebImage/LICENSE

@@ -1,4 +1,4 @@
-Copyright (c) 2016 Olivier Poitrey rs@dailymotion.com
+Copyright (c) 2009-2020 Olivier Poitrey rs@dailymotion.com
  
 Permission is hereby granted, free of charge, to any person obtaining a copy
 of this software and associated documentation files (the "Software"), to deal

+ 264 - 246
KulexiuForStudent/Pods/SDWebImage/README.md

@@ -1,334 +1,352 @@
-Web Image
-=========
-[![Build Status](http://img.shields.io/travis/rs/SDWebImage/master.svg?style=flat)](https://travis-ci.org/rs/SDWebImage)
+<p align="center" >
+  <img src="https://raw.githubusercontent.com/SDWebImage/SDWebImage/master/SDWebImage_logo.png" title="SDWebImage logo" float=left>
+</p>
+
+
+[![Build Status](http://img.shields.io/travis/SDWebImage/SDWebImage/master.svg?style=flat)](https://travis-ci.org/SDWebImage/SDWebImage)
 [![Pod Version](http://img.shields.io/cocoapods/v/SDWebImage.svg?style=flat)](http://cocoadocs.org/docsets/SDWebImage/)
 [![Pod Platform](http://img.shields.io/cocoapods/p/SDWebImage.svg?style=flat)](http://cocoadocs.org/docsets/SDWebImage/)
 [![Pod License](http://img.shields.io/cocoapods/l/SDWebImage.svg?style=flat)](https://www.apache.org/licenses/LICENSE-2.0.html)
-[![Dependency Status](https://www.versioneye.com/objective-c/sdwebimage/3.3/badge.svg?style=flat)](https://www.versioneye.com/objective-c/sdwebimage/3.3)
-[![Reference Status](https://www.versioneye.com/objective-c/sdwebimage/reference_badge.svg?style=flat)](https://www.versioneye.com/objective-c/sdwebimage/references)
-[![Carthage compatible](https://img.shields.io/badge/Carthage-compatible-4BC51D.svg?style=flat)](https://github.com/rs/SDWebImage)
-
-This library provides a category for UIImageView with support for remote images coming from the web.
-
-It provides:
-
-- An `UIImageView` category adding web image and cache management to the Cocoa Touch framework
-- An asynchronous image downloader
-- An asynchronous memory + disk image caching with automatic cache expiration handling
-- Animated GIF support
-- WebP format support
-- A background image decompression
-- A guarantee that the same URL won't be downloaded several times
-- A guarantee that bogus URLs won't be retried again and again
-- A guarantee that main thread will never be blocked
-- Performances!
-- Use GCD and ARC
-- Arm64 support
-
-NOTE: Version 3.8 of SDWebImage requires iOS 7 or later (because of NSURLSession). 
-Versions 3.7 to 3.0 requires iOS 5.1.1. If you need iOS < 5.0 support, please use the last [2.0 version](https://github.com/rs/SDWebImage/tree/2.0-compat).
+[![Carthage compatible](https://img.shields.io/badge/Carthage-compatible-brightgreen.svg)](https://github.com/SDWebImage/SDWebImage)
+[![SwiftPM compatible](https://img.shields.io/badge/SwiftPM-compatible-brightgreen.svg)](https://swift.org/package-manager/)
+[![Mac Catalyst compatible](https://img.shields.io/badge/Catalyst-compatible-brightgreen.svg)](https://developer.apple.com/documentation/xcode/creating_a_mac_version_of_your_ipad_app/)
+[![codecov](https://codecov.io/gh/SDWebImage/SDWebImage/branch/master/graph/badge.svg)](https://codecov.io/gh/SDWebImage/SDWebImage)
+
+This library provides an async image downloader with cache support. For convenience, we added categories for UI elements like `UIImageView`, `UIButton`, `MKAnnotationView`.
+
+## Features
+
+- [x] Categories for `UIImageView`, `UIButton`, `MKAnnotationView` adding web image and cache management
+- [x] An asynchronous image downloader
+- [x] An asynchronous memory + disk image caching with automatic cache expiration handling
+- [x] A background image decompression to avoid frame rate drop
+- [x] [Progressive image loading](https://github.com/SDWebImage/SDWebImage/wiki/Advanced-Usage#progressive-animation) (including animated image, like GIF showing in Web browser)
+- [x] [Thumbnail image decoding](https://github.com/SDWebImage/SDWebImage/wiki/Advanced-Usage#thumbnail-decoding-550) to save CPU && Memory for large images
+- [x] [Extendable image coder](https://github.com/SDWebImage/SDWebImage/wiki/Advanced-Usage#custom-coder-420) to support massive image format, like WebP
+- [x] [Full-stack solution for animated images](https://github.com/SDWebImage/SDWebImage/wiki/Advanced-Usage#animated-image-50) which keep a balance between CPU && Memory
+- [x] [Customizable and composable transformations](https://github.com/SDWebImage/SDWebImage/wiki/Advanced-Usage#transformer-50) can be applied to the images right after download
+- [x] [Customizable and multiple caches system](https://github.com/SDWebImage/SDWebImage/wiki/Advanced-Usage#custom-cache-50)
+- [x] [Customizable and multiple loaders system](https://github.com/SDWebImage/SDWebImage/wiki/Advanced-Usage#custom-loader-50) to expand the capabilities, like [Photos Library](https://github.com/SDWebImage/SDWebImagePhotosPlugin)
+- [x] [Image loading indicators](https://github.com/SDWebImage/SDWebImage/wiki/How-to-use#use-view-indicator-50)
+- [x] [Image loading transition animation](https://github.com/SDWebImage/SDWebImage/wiki/Advanced-Usage#image-transition-430)
+- [x] A guarantee that the same URL won't be downloaded several times
+- [x] A guarantee that bogus URLs won't be retried again and again
+- [x] A guarantee that main thread will never be blocked
+- [x] Modern Objective-C and better Swift support 
+- [x] Performances!
+
+## Supported Image Formats
+
+- Image formats supported by Apple system (JPEG, PNG, TIFF, BMP, ...), including [GIF](https://github.com/SDWebImage/SDWebImage/wiki/Advanced-Usage#gif-coder)/[APNG](https://github.com/SDWebImage/SDWebImage/wiki/Advanced-Usage#apng-coder) animated image
+- HEIC format from iOS 11/macOS 10.13, including animated HEIC from iOS 13/macOS 10.15 via [SDWebImageHEICCoder](https://github.com/SDWebImage/SDWebImage/wiki/Advanced-Usage#heic-coder). For lower firmware, use coder plugin [SDWebImageHEIFCoder](https://github.com/SDWebImage/SDWebImageHEIFCoder)
+- WebP format from iOS 14/macOS 11.0 via [SDWebImageAWebPCoder](https://github.com/SDWebImage/SDWebImage/wiki/Advanced-Usage#awebp-coder). For lower firmware, use coder plugin [SDWebImageWebPCoder](https://github.com/SDWebImage/SDWebImageWebPCoder)
+- Support extendable coder plugins for new image formats like BPG, AVIF. And vector format like PDF, SVG. See all the list in [Image coder plugin List](https://github.com/SDWebImage/SDWebImage/wiki/Coder-Plugin-List)
+
+## Additional modules and Ecosystem
+
+In order to keep SDWebImage focused and limited to the core features, but also allow extensibility and custom behaviors, during the 5.0 refactoring we focused on modularizing the library.
+As such, we have moved/built new modules to [SDWebImage org](https://github.com/SDWebImage).
+
+#### SwiftUI
+[SwiftUI](https://developer.apple.com/xcode/swiftui/) is an innovative UI framework written in Swift to build user interfaces across all Apple platforms.
+
+We support SwiftUI by building a brand new framework called [SDWebImageSwiftUI](https://github.com/SDWebImage/SDWebImageSwiftUI), which is built on top of SDWebImage core functions (caching, loading and animation).
+
+The new framework introduce two View structs `WebImage` and `AnimatedImage` for SwiftUI world, `ImageIndicator` modifier for any View, `ImageManager` observable object for data source. Supports iOS 13+/macOS 10.15+/tvOS 13+/watchOS 6+ and Swift 5.1. Have a nice try and provide feedback!
+
+#### Coders for additional image formats
+- [SDWebImageWebPCoder](https://github.com/SDWebImage/SDWebImageWebPCoder) - coder for WebP format. iOS 8+/macOS 10.10+. Based on [libwebp](https://chromium.googlesource.com/webm/libwebp)
+- [SDWebImageHEIFCoder](https://github.com/SDWebImage/SDWebImageHEIFCoder) - coder for HEIF format, iOS 8+/macOS 10.10+ support. Based on [libheif](https://github.com/strukturag/libheif)
+- [SDWebImageBPGCoder](https://github.com/SDWebImage/SDWebImageBPGCoder) - coder for BPG format. Based on [libbpg](https://github.com/mirrorer/libbpg)
+- [SDWebImageFLIFCoder](https://github.com/SDWebImage/SDWebImageFLIFCoder) - coder for FLIF format. Based on [libflif](https://github.com/FLIF-hub/FLIF)
+- [SDWebImageAVIFCoder](https://github.com/SDWebImage/SDWebImageAVIFCoder) - coder for AVIF (AV1-based) format. Based on [libavif](https://github.com/AOMediaCodec/libavif)
+- [SDWebImagePDFCoder](https://github.com/SDWebImage/SDWebImagePDFCoder) - coder for PDF vector format. Using built-in frameworks
+- [SDWebImageSVGCoder](https://github.com/SDWebImage/SDWebImageSVGCoder) - coder for SVG vector format. Using built-in frameworks
+- [SDWebImageLottieCoder](https://github.com/SDWebImage/SDWebImageLottieCoder) - coder for Lottie animation format. Based on [rlottie](https://github.com/Samsung/rlottie)
+- and more from community!
+
+#### Custom Caches
+- [SDWebImageYYPlugin](https://github.com/SDWebImage/SDWebImageYYPlugin) - plugin to support caching images with [YYCache](https://github.com/ibireme/YYCache)
+- [SDWebImagePINPlugin](https://github.com/SDWebImage/SDWebImagePINPlugin) - plugin to support caching images with [PINCache](https://github.com/pinterest/PINCache)
+
+#### Custom Loaders
+- [SDWebImagePhotosPlugin](https://github.com/SDWebImage/SDWebImagePhotosPlugin) - plugin to support loading images from Photos (using `Photos.framework`) 
+- [SDWebImageLinkPlugin](https://github.com/SDWebImage/SDWebImageLinkPlugin) - plugin to support loading images from rich link url, as well as `LPLinkView` (using `LinkPresentation.framework`) 
+
+#### Integration with 3rd party libraries
+- [SDWebImageLottiePlugin](https://github.com/SDWebImage/SDWebImageLottiePlugin) - plugin to support [Lottie-iOS](https://github.com/airbnb/lottie-ios), vector animation rending with remote JSON files
+- [SDWebImageSVGKitPlugin](https://github.com/SDWebImage/SDWebImageSVGKitPlugin) - plugin to support [SVGKit](https://github.com/SVGKit/SVGKit), SVG rendering using Core Animation, iOS 8+/macOS 10.10+ support
+- [SDWebImageFLPlugin](https://github.com/SDWebImage/SDWebImageFLPlugin) - plugin to support [FLAnimatedImage](https://github.com/Flipboard/FLAnimatedImage) as the engine for animated GIFs
+- [SDWebImageYYPlugin](https://github.com/SDWebImage/SDWebImageYYPlugin) - plugin to integrate [YYImage](https://github.com/ibireme/YYImage) & [YYCache](https://github.com/ibireme/YYCache) for image rendering & caching
+
+#### Community driven popular libraries
+- [FirebaseUI](https://github.com/firebase/FirebaseUI-iOS) - Firebase Storage binding for query images, based on SDWebImage loader system
+- [react-native-fast-image](https://github.com/DylanVann/react-native-fast-image) - React Native fast image component, based on SDWebImage Animated Image solution
+- [flutter_image_compress](https://github.com/OpenFlutter/flutter_image_compress) - Flutter compresses image plugin, based on SDWebImage WebP coder plugin
+
+#### Make our lives easier
+- [libwebp-Xcode](https://github.com/SDWebImage/libwebp-Xcode) - A wrapper for [libwebp](https://chromium.googlesource.com/webm/libwebp) + an Xcode project.
+- [libheif-Xcode](https://github.com/SDWebImage/libheif-Xcode) - A wrapper for [libheif](https://github.com/strukturag/libheif) + an Xcode project.
+- [libavif-Xcode](https://github.com/SDWebImage/libavif-Xcode) - A wrapper for [libavif](https://github.com/AOMediaCodec/libavif) + an Xcode project.
+- and more third-party C/C++ image codec libraries with CocoaPods/Carthage/SwiftPM support.
+
+You can use those directly, or create similar components of your own, by using the customizable architecture of SDWebImage.
+
+## Requirements
+
+- iOS 9.0 or later
+- tvOS 9.0 or later
+- watchOS 2.0 or later
+- macOS 10.11 or later (10.15 for Catalyst)
+- Xcode 11.0 or later
+
+#### Backwards compatibility
+
+- For iOS 8, macOS 10.10 or Xcode < 11, use [any 5.x version up to 5.9.5](https://github.com/SDWebImage/SDWebImage/releases/tag/5.9.5)
+- For iOS 7, macOS 10.9 or Xcode < 8, use [any 4.x version up to 4.4.6](https://github.com/SDWebImage/SDWebImage/releases/tag/4.4.6)
+- For macOS 10.8, use [any 4.x version up to 4.3.0](https://github.com/SDWebImage/SDWebImage/releases/tag/4.3.0)
+- For iOS 5 and 6, use [any 3.x version up to 3.7.6](https://github.com/SDWebImage/SDWebImage/releases/tag/3.7.6)
+- For iOS < 5.0, please use the last [2.0 version](https://github.com/SDWebImage/SDWebImage/tree/2.0-compat).
+
+## Getting Started
+
+- Read this Readme doc
+- Read the [How to use section](https://github.com/SDWebImage/SDWebImage#how-to-use)
+- Read the [Latest Documentation](https://sdwebimage.github.io/) and [CocoaDocs for old version](http://cocoadocs.org/docsets/SDWebImage/)
+- Try the example by downloading the project from Github or even easier using CocoaPods try `pod try SDWebImage`
+- Read the [Installation Guide](https://github.com/SDWebImage/SDWebImage/wiki/Installation-Guide)
+- Read the [SDWebImage 5.0 Migration Guide](https://github.com/SDWebImage/SDWebImage/blob/master/Docs/SDWebImage-5.0-Migration-guide.md) to get an idea of the changes from 4.x to 5.x
+- Read the [SDWebImage 4.0 Migration Guide](https://github.com/SDWebImage/SDWebImage/blob/master/Docs/SDWebImage-4.0-Migration-guide.md) to get an idea of the changes from 3.x to 4.x
+- Read the [Common Problems](https://github.com/SDWebImage/SDWebImage/wiki/Common-Problems) to find the solution for common problems 
+- Go to the [Wiki Page](https://github.com/SDWebImage/SDWebImage/wiki) for more information such as [Advanced Usage](https://github.com/SDWebImage/SDWebImage/wiki/Advanced-Usage)
+
+## Who Uses It
+- Find out [who uses SDWebImage](https://github.com/SDWebImage/SDWebImage/wiki/Who-Uses-SDWebImage) and add your app to the list.
+
+## Communication
+
+- If you **need help**, use [Stack Overflow](http://stackoverflow.com/questions/tagged/sdwebimage). (Tag 'sdwebimage')
+- If you'd like to **ask a general question**, use [Stack Overflow](http://stackoverflow.com/questions/tagged/sdwebimage).
+- If you **found a bug**, open an issue.
+- If you **have a feature request**, open an issue.
+- If you **need IRC channel**, use [Gitter](https://gitter.im/SDWebImage/community).
 
-[How is SDWebImage better than X?](https://github.com/rs/SDWebImage/wiki/How-is-SDWebImage-better-than-X%3F)
+## Contribution
 
-Who Uses It
-----------
+- If you **want to contribute**, read the [Contributing Guide](https://github.com/SDWebImage/SDWebImage/blob/master/.github/CONTRIBUTING.md)
+- For **development contribution guide**, read the [How-To-Contribute](https://github.com/SDWebImage/SDWebImage/wiki/How-to-Contribute)
+- For **understanding code architecture**, read the [Code Architecture Analysis](https://github.com/SDWebImage/SDWebImage/wiki/5.6-Code-Architecture-Analysis)
 
-Find out [who uses SDWebImage](https://github.com/rs/SDWebImage/wiki/Who-Uses-SDWebImage) and add your app to the list.
+## How To Use
 
-How To Use
-----------
-
-API documentation is available at [CocoaDocs - SDWebImage](http://cocoadocs.org/docsets/SDWebImage/)
-
-### Using UIImageView+WebCache category with UITableView
-
-Just #import the UIImageView+WebCache.h header, and call the sd_setImageWithURL:placeholderImage:
-method from the tableView:cellForRowAtIndexPath: UITableViewDataSource method. Everything will be
-handled for you, from async downloads to caching management.
+* Objective-C
 
 ```objective-c
-#import <SDWebImage/UIImageView+WebCache.h>
-
+#import <SDWebImage/SDWebImage.h>
 ...
-
-- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath {
-    static NSString *MyIdentifier = @"MyIdentifier";
-
-    UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:MyIdentifier];
-    if (cell == nil) {
-        cell = [[[UITableViewCell alloc] initWithStyle:UITableViewCellStyleDefault
-                                       reuseIdentifier:MyIdentifier] autorelease];
-    }
-
-    // Here we use the new provided sd_setImageWithURL: method to load the web image
-    [cell.imageView sd_setImageWithURL:[NSURL URLWithString:@"http://www.domain.com/path/to/image.jpg"]
-                      placeholderImage:[UIImage imageNamed:@"placeholder.png"]];
-
-    cell.textLabel.text = @"My Text";
-    return cell;
-}
+[imageView sd_setImageWithURL:[NSURL URLWithString:@"http://www.domain.com/path/to/image.jpg"]
+             placeholderImage:[UIImage imageNamed:@"placeholder.png"]];
 ```
 
-### Using blocks
+* Swift
 
-With blocks, you can be notified about the image download progress and whenever the image retrieval
-has completed with success or not:
+```swift
+import SDWebImage
 
-```objective-c
-// Here we use the new provided sd_setImageWithURL: method to load the web image
-[cell.imageView sd_setImageWithURL:[NSURL URLWithString:@"http://www.domain.com/path/to/image.jpg"]
-                      placeholderImage:[UIImage imageNamed:@"placeholder.png"]
-                             completed:^(UIImage *image, NSError *error, SDImageCacheType cacheType, NSURL *imageURL) {
-                                ... completion code here ...
-                             }];
+imageView.sd_setImage(with: URL(string: "http://www.domain.com/path/to/image.jpg"), placeholderImage: UIImage(named: "placeholder.png"))
 ```
 
-Note: neither your success nor failure block will be call if your image request is canceled before completion.
+- For details about how to use the library and clear examples, see [The detailed How to use](https://github.com/SDWebImage/SDWebImage/blob/master/Docs/HowToUse.md)
 
-### Using SDWebImageManager
+## Animated Images (GIF) support
 
-The SDWebImageManager is the class behind the UIImageView+WebCache category. It ties the
-asynchronous downloader with the image cache store. You can use this class directly to benefit
-from web image downloading with caching in another context than a UIView (ie: with Cocoa).
+In 5.0, we introduced a brand new mechanism for supporting animated images. This includes animated image loading, rendering, decoding, and also supports customizations (for advanced users).
 
-Here is a simple example of how to use SDWebImageManager:
+This animated image solution is available for `iOS`/`tvOS`/`macOS`. The `SDAnimatedImage` is subclass of `UIImage/NSImage`, and `SDAnimatedImageView` is subclass of `UIImageView/NSImageView`, to make them compatible with the common frameworks APIs.
 
-```objective-c
-SDWebImageManager *manager = [SDWebImageManager sharedManager];
-[manager downloadImageWithURL:imageURL
-                      options:0
-                     progress:^(NSInteger receivedSize, NSInteger expectedSize) {
-                         // progression tracking code
-                     }
-                     completed:^(UIImage *image, NSError *error, SDImageCacheType cacheType, BOOL finished, NSURL *imageURL) {
-                         if (image) {
-                             // do something with image
-                         }
-                     }];
-```
-
-### Using Asynchronous Image Downloader Independently
-
-It's also possible to use the async image downloader independently:
-
-```objective-c
-SDWebImageDownloader *downloader = [SDWebImageDownloader sharedDownloader];
-[downloader downloadImageWithURL:imageURL
-                         options:0
-                        progress:^(NSInteger receivedSize, NSInteger expectedSize) {
-                            // progression tracking code
-                        }
-                       completed:^(UIImage *image, NSData *data, NSError *error, BOOL finished) {
-                            if (image && finished) {
-                                // do something with image
-                            }
-                        }];
-```
+The `SDAnimatedImageView` supports the familiar image loading category methods, works like drop-in replacement for `UIImageView/NSImageView`.
 
-### Using Asynchronous Image Caching Independently
+Don't have `UIView` (like `WatchKit` or `CALayer`)? you can still use `SDAnimatedPlayer` the player engine for advanced playback and rendering.
 
-It is also possible to use the async based image cache store independently. SDImageCache
-maintains a memory cache and an optional disk cache. Disk cache write operations are performed
-asynchronous so it doesn't add unnecessary latency to the UI.
+See [Animated Image](https://github.com/SDWebImage/SDWebImage/wiki/Advanced-Usage#animated-image-50) for more detailed information.
 
-The SDImageCache class provides a singleton instance for convenience but you can create your own
-instance if you want to create separated cache namespace.
-
-To lookup the cache, you use the `queryDiskCacheForKey:done:` method. If the method returns nil, it means the cache
-doesn't currently own the image. You are thus responsible for generating and caching it. The cache
-key is an application unique identifier for the image to cache. It is generally the absolute URL of
-the image.
+* Objective-C
 
 ```objective-c
-SDImageCache *imageCache = [[SDImageCache alloc] initWithNamespace:@"myNamespace"];
-[imageCache queryDiskCacheForKey:myCacheKey done:^(UIImage *image) {
-    // image is not nil if image was found
-}];
+SDAnimatedImageView *imageView = [SDAnimatedImageView new];
+SDAnimatedImage *animatedImage = [SDAnimatedImage imageNamed:@"image.gif"];
+imageView.image = animatedImage;
 ```
 
-By default SDImageCache will lookup the disk cache if an image can't be found in the memory cache.
-You can prevent this from happening by calling the alternative method `imageFromMemoryCacheForKey:`.
-
-To store an image into the cache, you use the storeImage:forKey: method:
+* Swift
 
-```objective-c
-[[SDImageCache sharedImageCache] storeImage:myImage forKey:myCacheKey];
+```swift
+let imageView = SDAnimatedImageView()
+let animatedImage = SDAnimatedImage(named: "image.gif")
+imageView.image = animatedImage
 ```
 
-By default, the image will be stored in memory cache as well as on disk cache (asynchronously). If
-you want only the memory cache, use the alternative method storeImage:forKey:toDisk: with a negative
-third argument.
-
-### Using cache key filter
-
-Sometime, you may not want to use the image URL as cache key because part of the URL is dynamic
-(i.e.: for access control purpose). SDWebImageManager provides a way to set a cache key filter that
-takes the NSURL as input, and output a cache key NSString.
-
-The following example sets a filter in the application delegate that will remove any query-string from
-the URL before to use it as a cache key:
-
-```objective-c
-- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions {
-    SDWebImageManager.sharedManager.cacheKeyFilter = ^(NSURL *url) {
-        url = [[NSURL alloc] initWithScheme:url.scheme host:url.host path:url.path];
-        return [url absoluteString];
-    };
-
-    // Your app init code...
-    return YES;
-}
-```
-
-
-Common Problems
----------------
+#### FLAnimatedImage integration has its own dedicated repo
+In order to clean up things and make our core project do less things, we decided that the `FLAnimatedImage` integration does not belong here. From 5.0, this will still be available, but under a dedicated repo [SDWebImageFLPlugin](https://github.com/SDWebImage/SDWebImageFLPlugin).
 
-### Using dynamic image size with UITableViewCell
+## Installation
 
-UITableView determines the size of the image by the first image set for a cell. If your remote images
-don't have the same size as your placeholder image, you may experience strange anamorphic scaling issue.
-The following article gives a way to workaround this issue:
-
-[http://www.wrichards.com/blog/2011/11/sdwebimage-fixed-width-cell-images/](http://www.wrichards.com/blog/2011/11/sdwebimage-fixed-width-cell-images/)
-
-
-### Handle image refresh
+There are four ways to use SDWebImage in your project:
+- using CocoaPods
+- using Carthage
+- using Swift Package Manager
+- manual install (build frameworks or embed Xcode Project)
 
-SDWebImage does very aggressive caching by default. It ignores all kind of caching control header returned by the HTTP server and cache the returned images with no time restriction. It implies your images URLs are static URLs pointing to images that never change. If the pointed image happen to change, some parts of the URL should change accordingly.
+### Installation with CocoaPods
 
-If you don't control the image server you're using, you may not be able to change the URL when its content is updated. This is the case for Facebook avatar URLs for instance. In such case, you may use the `SDWebImageRefreshCached` flag. This will slightly degrade the performance but will respect the HTTP caching control headers:
+[CocoaPods](http://cocoapods.org/) is a dependency manager for Objective-C, which automates and simplifies the process of using 3rd-party libraries in your projects. See the [Get Started](http://cocoapods.org/#get_started) section for more details.
 
-``` objective-c
-[imageView sd_setImageWithURL:[NSURL URLWithString:@"https://graph.facebook.com/olivier.poitrey/picture"]
-                 placeholderImage:[UIImage imageNamed:@"avatar-placeholder.png"]
-                          options:SDWebImageRefreshCached];
+#### Podfile
+```
+platform :ios, '8.0'
+pod 'SDWebImage', '~> 5.0'
 ```
 
-### Add a progress indicator
-
-See this category: https://github.com/JJSaccolo/UIActivityIndicator-for-SDWebImage
-
-Installation
-------------
-
-There are three ways to use SDWebImage in your project:
-- using CocoaPods
-- copying all the files into your project
-- importing the project as a static library
+##### Swift and static framework
 
-### Installation with CocoaPods
+Swift project previously had to use `use_frameworks!` to make all Pods into dynamic framework to let CocoaPods work.
 
-[CocoaPods](http://cocoapods.org/) is a dependency manager for Objective-C, which automates and simplifies the process of using 3rd-party libraries in your projects. See the [Get Started](http://cocoapods.org/#get_started) section for more details.
+However, starting with `CocoaPods 1.5.0+` (with `Xcode 9+`), which supports to build both Objective-C && Swift code into static framework. You can use modular headers to use SDWebImage as static framework, without the need of `use_frameworks!`:
 
-#### Podfile
 ```
-platform :ios, '7.0'
-pod 'SDWebImage', '~>3.8'
+platform :ios, '8.0'
+# Uncomment the next line when you want all Pods as static framework
+# use_modular_headers!
+pod 'SDWebImage', :modular_headers => true
 ```
 
-If you are using Swift, be sure to add `use_frameworks!` and set your target to iOS 8+:
+See more on [CocoaPods 1.5.0 — Swift Static Libraries](http://blog.cocoapods.org/CocoaPods-1.5.0/)
+
+If not, you still need to add `use_frameworks!` to use SDWebImage as dynamic framework:
+
 ```
 platform :ios, '8.0'
 use_frameworks!
+pod 'SDWebImage'
 ```
 
 #### Subspecs
 
-There are 3 subspecs available now: `Core`, `MapKit` and `WebP` (this means you can install only some of the SDWebImage modules. By default, you get just `Core`, so if you need `WebP`, you need to specify it). 
+There are 2 subspecs available now: `Core` and `MapKit` (this means you can install only some of the SDWebImage modules. By default, you get just `Core`, so if you need `MapKit`, you need to specify it). 
 
 Podfile example:
+
 ```
-pod 'SDWebImage/WebP'
+pod 'SDWebImage/MapKit'
 ```
 
-### Installation with Carthage (iOS 8+)
+### Installation with Carthage
 
 [Carthage](https://github.com/Carthage/Carthage) is a lightweight dependency manager for Swift and Objective-C. It leverages CocoaTouch modules and is less invasive than CocoaPods.
 
 To install with carthage, follow the instruction on [Carthage](https://github.com/Carthage/Carthage)
 
-#### Cartfile
-```
-github "rs/SDWebImage"
-```
+Carthage users can point to this repository and use whichever generated framework they'd like: SDWebImage, SDWebImageMapKit or both.
 
-#### Usage
-Swift
+Make the following entry in your Cartfile: `github "SDWebImage/SDWebImage"`
+Then run `carthage update`
+If this is your first time using Carthage in the project, you'll need to go through some additional steps as explained [over at Carthage](https://github.com/Carthage/Carthage#adding-frameworks-to-an-application).
 
-If you installed using CocoaPods:
-```
-import SDWebImage
-```
+> NOTE: At this time, Carthage does not provide a way to build only specific repository subcomponents (or equivalent of CocoaPods's subspecs). All components and their dependencies will be built with the above command. However, you don't need to copy frameworks you aren't using into your project. For instance, if you aren't using `SDWebImageMapKit`, feel free to delete that framework from the Carthage Build directory after `carthage update` completes.
 
-If you installed manually:
-```
-import WebImage
-```
+### Installation with Swift Package Manager (Xcode 11+)
 
-Objective-C
+[Swift Package Manager](https://swift.org/package-manager/) (SwiftPM) is a tool for managing the distribution of Swift code as well as C-family dependency. From Xcode 11, SwiftPM got natively integrated with Xcode.
 
+SDWebImage support SwiftPM from version 5.1.0. To use SwiftPM, you should use Xcode 11 to open your project. Click `File` -> `Swift Packages` -> `Add Package Dependency`, enter [SDWebImage repo's URL](https://github.com/SDWebImage/SDWebImage.git). Or you can login Xcode with your GitHub account and just type `SDWebImage` to search.
+
+After select the package, you can choose the dependency type (tagged version, branch or commit). Then Xcode will setup all the stuff for you.
+
+If you're a framework author and use SDWebImage as a dependency, update your `Package.swift` file:
+
+```swift
+let package = Package(
+    // 5.1.0 ..< 6.0.0
+    dependencies: [
+        .package(url: "https://github.com/SDWebImage/SDWebImage.git", from: "5.1.0")
+    ],
+    // ...
+)
 ```
-@import WebImage;
-```
 
-### Installation by cloning the repository
+### Manual Installation Guide
+
+See more on [Manual install Guide](https://github.com/SDWebImage/SDWebImage/wiki/Installation-Guide#manual-installation-guide)
+
+### Import headers in your source files
+
+In the source files where you need to use the library, import the umbrella header file:
 
-In order to gain access to all the files from the repository, you should clone it.
+```objective-c
+#import <SDWebImage/SDWebImage.h>
 ```
-git clone --recursive https://github.com/rs/SDWebImage.git
+
+It's also recommend to use the module import syntax, available for CocoaPods(enable `modular_headers`)/Carthage/SwiftPM.
+
+```objecitivec
+@import SDWebImage;
 ```
 
-### Add the SDWebImage project to your project
+### Build Project
 
-- Download and unzip the last version of the framework from the [download page](https://github.com/rs/SDWebImage/releases)
-- Right-click on the project navigator and select "Add Files to "Your Project":
-- In the dialog, select SDWebImage.framework:
-- Check the "Copy items into destination group's folder (if needed)" checkbox
+At this point your workspace should build without error. If you are having problem, post to the Issue and the
+community can help you solve it.
 
-### Add dependencies
+## Data Collection Practices
+As required by the [App privacy details on the App Store](https://developer.apple.com/app-store/app-privacy-details/), here's SDWebImage's list of [Data Collection Practices](https://sdwebimage.github.io/DataCollection/index.html).
 
-- In you application project app’s target settings, find the "Build Phases" section and open the "Link Binary With Libraries" block:
-- Click the "+" button again and select the "ImageIO.framework", this is needed by the progressive download feature:
+## Author
+- [Olivier Poitrey](https://github.com/rs)
 
-### Add Linker Flag
+## Collaborators
+- [Konstantinos K.](https://github.com/mythodeia)
+- [Bogdan Poplauschi](https://github.com/bpoplauschi)
+- [Chester Liu](https://github.com/skyline75489)
+- [DreamPiggy](https://github.com/dreampiggy)
+- [Wu Zhong](https://github.com/zhongwuzw)
 
-Open the "Build Settings" tab, in the "Linking" section, locate the "Other Linker Flags" setting and add the "-ObjC" flag:
+## Credits
 
-![Other Linker Flags](http://dl.dropbox.com/u/123346/SDWebImage/10_other_linker_flags.jpg)
+Thank you to all the people who have already contributed to SDWebImage.
 
-Alternatively, if this causes compilation problems with frameworks that extend optional libraries, such as Parse,  RestKit or opencv2, instead of the -ObjC flag use:
-```
--force_load SDWebImage.framework/Versions/Current/SDWebImage
-```
+[![Contributors](https://opencollective.com/SDWebImage/contributors.svg?width=890)](https://github.com/SDWebImage/SDWebImage/graphs/contributors)
 
-If you're using Cocoa Pods and have any frameworks that extend optional libraries, such as Parsen RestKit or opencv2, instead of the -ObjC flag use:
-```
--force_load $(TARGET_BUILD_DIR)/libPods.a
-```
-and this:
-```
-$(inherited)
-```
+## Licenses
 
-### Import headers in your source files
+All source code is licensed under the [MIT License](https://github.com/SDWebImage/SDWebImage/blob/master/LICENSE).
 
-In the source files where you need to use the library, import the header file:
+## Architecture
 
-```objective-c
-#import <SDWebImage/UIImageView+WebCache.h>
-```
+To learn about SDWebImage's architecture design for contribution, read [The Core of SDWebImage v5.6 Architecture](https://github.com/SDWebImage/SDWebImage/wiki/5.6-Code-Architecture-Analysis). Thanks @looseyi for the post and translation.
 
-### Build Project
+#### High Level Diagram
+<p align="center" >
+    <img src="https://raw.githubusercontent.com/SDWebImage/SDWebImage/master/Docs/Diagrams/SDWebImageHighLevelDiagram.jpeg" title="SDWebImage high level diagram">
+</p>
 
-At this point your workspace should build without error. If you are having problem, post to the Issue and the
-community can help you solve it.
+#### Overall Class Diagram
+<p align="center" >
+    <img src="https://raw.githubusercontent.com/SDWebImage/SDWebImage/master/Docs/Diagrams/SDWebImageClassDiagram.png" title="SDWebImage overall class diagram">
+</p>
 
-Future Enhancements
--------------------
+#### Top Level API Diagram
+<p align="center" >
+    <img src="https://raw.githubusercontent.com/SDWebImage/SDWebImage/master/Docs/Diagrams/SDWebImageTopLevelClassDiagram.png" title="SDWebImage top level API diagram">
+</p>
 
-- LRU memory cache cleanup instead of reset on memory warning
+#### Main Sequence Diagram
+<p align="center" >
+    <img src="https://raw.githubusercontent.com/SDWebImage/SDWebImage/master/Docs/Diagrams/SDWebImageSequenceDiagram.png" title="SDWebImage sequence diagram">
+</p>
 
-## Licenses
+#### More detailed diagrams
+- [Manager API Diagram](https://raw.githubusercontent.com/SDWebImage/SDWebImage/master/Docs/Diagrams/SDWebImageManagerClassDiagram.png)
+- [Coders API Diagram](https://raw.githubusercontent.com/SDWebImage/SDWebImage/master/Docs/Diagrams/SDWebImageCodersClassDiagram.png)
+- [Loader API Diagram](https://raw.githubusercontent.com/SDWebImage/SDWebImage/master/Docs/Diagrams/SDWebImageLoaderClassDiagram.png)
+- [Cache API Diagram](https://raw.githubusercontent.com/SDWebImage/SDWebImage/master/Docs/Diagrams/SDWebImageCacheClassDiagram.png)
 
-All source code is licensed under the [MIT License](https://raw.github.com/rs/SDWebImage/master/LICENSE).

+ 1 - 1
KulexiuForStudent/Pods/Target Support Files/Pods-KulexiuForStudent-KulexiuForStudentUITests/Pods-KulexiuForStudent-KulexiuForStudentUITests-acknowledgements.markdown

@@ -273,7 +273,7 @@ Copyright 2021 RongCloud
 
 ## SDWebImage
 
-Copyright (c) 2016 Olivier Poitrey rs@dailymotion.com
+Copyright (c) 2009-2020 Olivier Poitrey rs@dailymotion.com
  
 Permission is hereby granted, free of charge, to any person obtaining a copy
 of this software and associated documentation files (the "Software"), to deal

+ 1 - 1
KulexiuForStudent/Pods/Target Support Files/Pods-KulexiuForStudent-KulexiuForStudentUITests/Pods-KulexiuForStudent-KulexiuForStudentUITests-acknowledgements.plist

@@ -380,7 +380,7 @@ THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
 		</dict>
 		<dict>
 			<key>FooterText</key>
-			<string>Copyright (c) 2016 Olivier Poitrey rs@dailymotion.com
+			<string>Copyright (c) 2009-2020 Olivier Poitrey rs@dailymotion.com
  
 Permission is hereby granted, free of charge, to any person obtaining a copy
 of this software and associated documentation files (the "Software"), to deal

+ 1 - 1
KulexiuForStudent/Pods/Target Support Files/Pods-KulexiuForStudent/Pods-KulexiuForStudent-acknowledgements.markdown

@@ -273,7 +273,7 @@ Copyright 2021 RongCloud
 
 ## SDWebImage
 
-Copyright (c) 2016 Olivier Poitrey rs@dailymotion.com
+Copyright (c) 2009-2020 Olivier Poitrey rs@dailymotion.com
  
 Permission is hereby granted, free of charge, to any person obtaining a copy
 of this software and associated documentation files (the "Software"), to deal

+ 1 - 1
KulexiuForStudent/Pods/Target Support Files/Pods-KulexiuForStudent/Pods-KulexiuForStudent-acknowledgements.plist

@@ -380,7 +380,7 @@ THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
 		</dict>
 		<dict>
 			<key>FooterText</key>
-			<string>Copyright (c) 2016 Olivier Poitrey rs@dailymotion.com
+			<string>Copyright (c) 2009-2020 Olivier Poitrey rs@dailymotion.com
  
 Permission is hereby granted, free of charge, to any person obtaining a copy
 of this software and associated documentation files (the "Software"), to deal

+ 7 - 7
KulexiuForStudent/Pods/Target Support Files/RongCloudRTC/RongCloudRTC-xcframeworks.sh

@@ -17,24 +17,24 @@ RSYNC_PROTECT_TMP_FILES=(--filter "P .*.??????")
 variant_for_slice()
 {
   case "$1" in
-  "RongRTCLib.xcframework/ios-x86_64-simulator")
-    echo "simulator"
-    ;;
   "RongRTCLib.xcframework/ios-arm64_armv7")
     echo ""
     ;;
+  "RongRTCLib.xcframework/ios-x86_64-simulator")
+    echo "simulator"
+    ;;
   esac
 }
 
 archs_for_slice()
 {
   case "$1" in
-  "RongRTCLib.xcframework/ios-x86_64-simulator")
-    echo "x86_64"
-    ;;
   "RongRTCLib.xcframework/ios-arm64_armv7")
     echo "arm64 armv7"
     ;;
+  "RongRTCLib.xcframework/ios-x86_64-simulator")
+    echo "x86_64"
+    ;;
   esac
 }
 
@@ -117,5 +117,5 @@ install_xcframework() {
   echo "Copied $source to $destination"
 }
 
-install_xcframework "${PODS_ROOT}/RongCloudRTC/RongCloudRTC/RongRTCLib.xcframework" "RongCloudRTC/RongRTCLib" "framework" "ios-x86_64-simulator" "ios-arm64_armv7"
+install_xcframework "${PODS_ROOT}/RongCloudRTC/RongCloudRTC/RongRTCLib.xcframework" "RongCloudRTC/RongRTCLib" "framework" "ios-arm64_armv7" "ios-x86_64-simulator"
 

+ 1 - 1
KulexiuForStudent/Pods/Target Support Files/SDWebImage/SDWebImage-Info.plist

@@ -15,7 +15,7 @@
   <key>CFBundlePackageType</key>
   <string>FMWK</string>
   <key>CFBundleShortVersionString</key>
-  <string>3.8.3</string>
+  <string>5.12.5</string>
   <key>CFBundleSignature</key>
   <string>????</string>
   <key>CFBundleVersion</key>

+ 45 - 1
KulexiuForStudent/Pods/Target Support Files/SDWebImage/SDWebImage-umbrella.h

@@ -10,21 +10,65 @@
 #endif
 #endif
 
+#import "NSButton+WebCache.h"
 #import "NSData+ImageContentType.h"
+#import "NSImage+Compatibility.h"
+#import "SDAnimatedImage.h"
+#import "SDAnimatedImagePlayer.h"
+#import "SDAnimatedImageRep.h"
+#import "SDAnimatedImageView+WebCache.h"
+#import "SDAnimatedImageView.h"
+#import "SDDiskCache.h"
+#import "SDGraphicsImageRenderer.h"
+#import "SDImageAPNGCoder.h"
+#import "SDImageAWebPCoder.h"
 #import "SDImageCache.h"
+#import "SDImageCacheConfig.h"
+#import "SDImageCacheDefine.h"
+#import "SDImageCachesManager.h"
+#import "SDImageCoder.h"
+#import "SDImageCoderHelper.h"
+#import "SDImageCodersManager.h"
+#import "SDImageFrame.h"
+#import "SDImageGIFCoder.h"
+#import "SDImageGraphics.h"
+#import "SDImageHEICCoder.h"
+#import "SDImageIOAnimatedCoder.h"
+#import "SDImageIOCoder.h"
+#import "SDImageLoader.h"
+#import "SDImageLoadersManager.h"
+#import "SDImageTransformer.h"
+#import "SDMemoryCache.h"
+#import "SDWebImageCacheKeyFilter.h"
+#import "SDWebImageCacheSerializer.h"
 #import "SDWebImageCompat.h"
-#import "SDWebImageDecoder.h"
+#import "SDWebImageDefine.h"
 #import "SDWebImageDownloader.h"
+#import "SDWebImageDownloaderConfig.h"
+#import "SDWebImageDownloaderDecryptor.h"
 #import "SDWebImageDownloaderOperation.h"
+#import "SDWebImageDownloaderRequestModifier.h"
+#import "SDWebImageDownloaderResponseModifier.h"
+#import "SDWebImageError.h"
+#import "SDWebImageIndicator.h"
 #import "SDWebImageManager.h"
 #import "SDWebImageOperation.h"
+#import "SDWebImageOptionsProcessor.h"
 #import "SDWebImagePrefetcher.h"
+#import "SDWebImageTransition.h"
 #import "UIButton+WebCache.h"
+#import "UIImage+ExtendedCacheData.h"
+#import "UIImage+ForceDecode.h"
 #import "UIImage+GIF.h"
+#import "UIImage+MemoryCacheCost.h"
+#import "UIImage+Metadata.h"
 #import "UIImage+MultiFormat.h"
+#import "UIImage+Transform.h"
 #import "UIImageView+HighlightedWebCache.h"
 #import "UIImageView+WebCache.h"
+#import "UIView+WebCache.h"
 #import "UIView+WebCacheOperation.h"
+#import "SDWebImage.h"
 
 FOUNDATION_EXPORT double SDWebImageVersionNumber;
 FOUNDATION_EXPORT const unsigned char SDWebImageVersionString[];

Some files were not shown because too many files changed in this diff