DolphinEnglishLearnStudent/Config/VoicePlayer.swift
@@ -60,7 +60,9 @@ self.player = try? AVAudioPlayer(contentsOf: fileURL!) self.player?.delegate = self self.player?.play() self.delegate?.playing() DispatchQueue.main.async { self.delegate?.playing() } }else{ //文件不存在:执行下载 let downloadTask = URLSession.shared.downloadTask(with: URL(string: u)!) { tempLocalUrl, response, error in @@ -71,7 +73,9 @@ self.player = try? AVAudioPlayer(contentsOf: finalCacheUrl) self.player?.delegate = self self.player?.play() self.delegate?.playing() DispatchQueue.main.async { self.delegate?.playing() } } catch { print("视频缓存失败:catch") } @@ -176,8 +180,10 @@ extension VoicePlayer:AVAudioPlayerDelegate{ func audioPlayerDidFinishPlaying(_ player: AVAudioPlayer, successfully flag: Bool) { VoicePlayer.share().playComplete?() delegate?.playComplete() DispatchQueue.main.async { VoicePlayer.share().playComplete?() self.delegate?.playComplete() } } func audioPlayerDecodeErrorDidOccur(_ player: AVAudioPlayer, error: (any Error)?) { DolphinEnglishLearnStudent/Moudle/Home/HomeListenFight_lesson_1_VC.swift
@@ -82,6 +82,7 @@ func restore(){ isAnsterDone = false isAnsterModel.removeAll() isAnsterComplete = false viewModel.answerType.accept(.none) @@ -94,7 +95,21 @@ private func getNextAnswer(){ isListen = false if isAnsterModel.count == 4{ print("答题答满了");return if !isAnsterDone{ let v = rootViewModel.answerCount.value rootViewModel.answerCount.accept(v + 1) } isAnsterDone = true DispatchQueue.main.asyncAfter(deadline: .now()+3){[weak self] in guard let weakSelf = self else { return } NotificationCenter.default.post(name: NextLession_Noti, object: nil) weakSelf.viewModel.answerType.accept(.none) weakSelf.viewModel.selectIndex.accept(nil) weakSelf.rootViewModel.answerItems[weakSelf.page] = weakSelf.listenNewModel.subjectList[weakSelf.page] weakSelf.isListen = false } return } randomElement = listenNewModel.subjectList[page].randomElement() @@ -252,28 +267,13 @@ } extension HomeListenFight_lesson_1_VC:VoicePlayerDelegate{ func playing() {} func playing() { isListen = false } func playComplete() { isListen = true self.menuView?.resetView() if isAnsterModel.count == 4{ if !isAnsterDone{ let v = rootViewModel.answerCount.value rootViewModel.answerCount.accept(v + 1) } isAnsterDone = true DispatchQueue.main.asyncAfter(deadline: .now()+3){[weak self] in guard let weakSelf = self else { return } NotificationCenter.default.post(name: NextLession_Noti, object: nil) weakSelf.viewModel.answerType.accept(.none) weakSelf.viewModel.selectIndex.accept(nil) weakSelf.rootViewModel.answerItems[weakSelf.page] = weakSelf.listenNewModel.subjectList[weakSelf.page] weakSelf.isListen = false } } if isAnsterComplete{ getNextAnswer() DolphinEnglishLearnStudent/Moudle/Home/Listen/VC/HomeListenFightVC.swift
@@ -48,6 +48,7 @@ /// 当前页数 var currentPage = BehaviorRelay<Int>(value: 0) var subPage = BehaviorRelay<Int>(value: 1) //小题目角标 var maxPage = BehaviorRelay<Int>(value: 5) var listenType = BehaviorRelay<ListenType>(value:.lesson1) var times:Int = 0 @@ -204,6 +205,8 @@ },onError: { _ in weakSelf.showGameLevel() }).disposed(by: weakSelf.disposeBag) } cancelClouse: {[weak self] in self?.navigationController?.popViewController(animated: true) } } @@ -294,8 +297,10 @@ private func setPages(){ switch viewModel.listenType.value{ case .lesson1,.lesson2,.lesson3,.lesson5: case .lesson1,.lesson2,.lesson5: label_pageNum.text = "已完成:\(viewModel.answerCount.value)/\((data as! ListenNewModel).subjectList.flatMap({$0}).count)" case .lesson3: label_pageNum.text = "已完成:\(viewModel.currentPage.value + 1)/\((data as! ListenNewModel).subjectList.count)" case .lesson4: //两题为一组:需要/2 label_pageNum.text = "已完成:\(viewModel.answerCount.value)/\((data as! ListenNewModel).subjectList.flatMap({$0}).count / 2)" @@ -329,20 +334,10 @@ default:break } //正确率 let accracy = Int(Double(viewModel.correctNum) / Double(viewModel.correctNum + viewModel.errorNum) * 100) //有答题过程 //完成进度 var isComplete = false switch viewModel.listenType.value { case .lesson1:isComplete = studyScheduleModel?.listen == 100 case .lesson2:isComplete = studyScheduleModel?.look == 100 case .lesson3:isComplete = studyScheduleModel?.induction == 100 case .lesson4:isComplete = studyScheduleModel?.answer == 100 case .lesson5:isComplete = studyScheduleModel?.pair == 100 default:isComplete = false } Services.completeLearing(type: viewModel.listenType.value.rawValue, studyTime: viewModel.times, studyIds: ids, isComplete: isComplete).subscribe(onNext: {data in Services.completeLearing(type: viewModel.listenType.value.rawValue, studyTime: viewModel.times, studyIds: ids, quarter: viewModel.quarter.value!, week: viewModel.week.value!, day: viewModel.day.value!, accracy: accracy).subscribe(onNext: {data in NotificationCenter.default.post(name: Refresh_ListenSchedule_Noti, object: nil) }).disposed(by: disposeBag) @@ -440,7 +435,15 @@ @objc func beforeAction(){ listenFightLine = .before var beforePage = max(0, viewModel.currentPage.value - 1) let beforePage = max(0, viewModel.currentPage.value - 1) switch viewModel.listenType.value { case .lesson1,.lesson2: let temp = (beforePage * 4) + 1 viewModel.answerCount.accept(max(1,temp)) default:break } pageVC.scroll(toPage: beforePage, animation: true) viewModel.currentPage.accept(beforePage) DolphinEnglishLearnStudent/Moudle/Home/Listen/VC/HomeListenFight_lesson_2_VC.swift
@@ -152,6 +152,10 @@ handleView.chooseClouse {[weak self] btn in guard let weakSelf = self else { return } if weakSelf.playedIndex.count != 3{ handleView.btn_choose.isSelected = false alertError(msg: "请听完");return } handleView.view_choose.alpha = 1 var lessionType:Fight_lessonType = .none if handleView.vioceSoundUrl == weakSelf.listenNewModel.subjectList[weakSelf.page][row].correct{ @@ -290,11 +294,21 @@ } extension HomeListenFight_lesson_2_VC:VoicePlayerDelegate{ func playing() {} func playing() { print("正在播放") //正在播放中,其他播放按钮先禁止 for sub in stackView.arrangedSubviews as! [StudyHandleView]{ sub.btn_pay.isEnabled = false sub.btn_choose.isEnabled = false } } func playComplete() { //对已经播放过的View,进行刷新 for sub in stackView.arrangedSubviews as! [StudyHandleView]{ sub.btn_pay.isEnabled = true sub.btn_choose.isEnabled = true if playedIndex.contains(sub.tag){ sub.resetView() sub.view_choose.alpha = playedIndex.contains(sub.tag) ? 1:0 DolphinEnglishLearnStudent/Moudle/Home/Listen/VC/HomeListenFight_lesson_3_VC.swift
@@ -38,6 +38,7 @@ private var voicePlayer = VoicePlayer.share() private var playIndex = Set<IndexPath>() //顺序播放 private var isPlayingIndex:IndexPath? //正在播放中 private var islisten:Bool = false required init(page:Int,listenNewModel:ListenNewModel){ super.init(nibName: nil, bundle: nil) @@ -64,7 +65,6 @@ super.viewDidLoad() navigationItem.titleView = UIView() playIndex.insert(IndexPath(row: 0, section: 0)) // setAnswerStackView() } func restore(){ @@ -101,63 +101,73 @@ } private func setAnswerStackView(){ private func setAnswerStackView(force:Bool = false){ stackView.removeArrangedSubviews() var tempImageArray = [String]() tempImageArray.append(listenNewModel.subjectList[page][2].img) tempImageArray.append(listenNewModel.subjectList[page][4].img) tempImageArray.append(listenNewModel.subjectList[page][5].img) view.addSubview(stackView) stackView.snp.makeConstraints { make in make.right.equalToSuperview().offset(-82) make.centerY.equalToSuperview() make.height.equalTo(52) for v in stackView.arrangedSubviews{ v.removeFromSuperview() } var tempAnswerViews = [Lesson_3_AnswerView]() for i in 0...2{ let answerView = Lesson_3_AnswerView.jq_loadNibView() answerView.alpha = 0 answerView.btn_choose.addTarget(self, action: #selector(chooseAnswerAction), for: .touchUpInside) answerView.btn_fullscreen.addTarget(self, action: #selector(fullscreenAction), for: .touchUpInside) answerView.img_cover.contentMode = .scaleToFill answerView.btn_choose.tag = 10+i answerView.btn_fullscreen.tag = 20+i answerView.imageUrl = tempImageArray[i] answerView.img_cover.sd_setImage(with: URL(string: tempImageArray[i])) answerView.snp.makeConstraints { make in make.width.equalTo(85) if isPlayingIndex == IndexPath(row: 2, section: 0) || isPlayingIndex == IndexPath(row: 1, section: 1) || isPlayingIndex == IndexPath(row: 2, section: 1) || !force{ var tempImageArray = [String]() tempImageArray.append(listenNewModel.subjectList[page][2].img) tempImageArray.append(listenNewModel.subjectList[page][4].img) tempImageArray.append(listenNewModel.subjectList[page][5].img) view.addSubview(stackView) stackView.snp.makeConstraints { make in make.right.equalToSuperview().offset(-82) make.centerY.equalToSuperview() make.height.equalTo(52) } UIView.animate(withDuration: 0.05 + Double(i)) { answerView.alpha = 1 var tempAnswerViews = [Lesson_3_AnswerView]() for i in 0...2{ let answerView = Lesson_3_AnswerView.jq_loadNibView() answerView.alpha = 0 answerView.btn_choose.addTarget(self, action: #selector(chooseAnswerAction), for: .touchUpInside) answerView.btn_fullscreen.addTarget(self, action: #selector(fullscreenAction), for: .touchUpInside) answerView.img_cover.contentMode = .scaleToFill answerView.btn_choose.tag = 10+i answerView.btn_fullscreen.tag = 20+i answerView.imageUrl = tempImageArray[i] answerView.img_cover.sd_setImage(with: URL(string: tempImageArray[i])) answerView.snp.makeConstraints { make in make.width.equalTo(85) make.height.equalTo(52) } UIView.animate(withDuration: 0.05 + Double(i)) { answerView.alpha = 1 } tempAnswerViews.append(answerView) } tempAnswerViews.append(answerView) tempAnswerViews.shuffle() stackView.addArrangedSubviews(tempAnswerViews) } tempAnswerViews.shuffle() stackView.addArrangedSubviews(tempAnswerViews) } @objc private func chooseAnswerAction(btn:UIButton){ if !islisten{ alertError(msg: "请先听题");return } if isPlayingIndex != nil { alertError(msg: "请先听题");return } if rootViewModel.correctNum == 0 && !playIndex.contains(IndexPath(row: 2, section: 0)){ if answterCount == 0 && !playIndex.contains(IndexPath(row: 2, section: 0)){ alertError(msg: "请先听题");return } if rootViewModel.correctNum == 1 && !playIndex.contains(IndexPath(row: 1, section: 1)){ if answterCount == 1 && !playIndex.contains(IndexPath(row: 1, section: 1)){ alertError(msg: "请先听题");return } if rootViewModel.correctNum == 2 && !playIndex.contains(IndexPath(row: 2, section: 1)){ if answterCount == 2 && !playIndex.contains(IndexPath(row: 2, section: 1)){ alertError(msg: "请先听题");return } @@ -244,7 +254,7 @@ subV?.btn_fullscreen.alpha = 0 }completion: { _ in DispatchQueue.main.asyncAfter(deadline: .now()+1.5) { self.setAnswerStackView() self.setAnswerStackView(force: true) } } default:break @@ -283,14 +293,16 @@ weakSelf.isPlayingIndex = index weakSelf.voicePlayer.playerEnd() weakSelf.voicePlayer.playerAt(url: weakSelf.listenNewModel.subjectList[weakSelf.page][indexPath.row].correct) if indexPath.section == 1{ weakSelf.voicePlayer.playerAt(url: weakSelf.listenNewModel.subjectList[weakSelf.page][indexPath.row + 3].correct) }else{ weakSelf.voicePlayer.playerAt(url: weakSelf.listenNewModel.subjectList[weakSelf.page][indexPath.row].correct) } weakSelf.viewModel.selectIndex.accept(index) //点击答案,就显示 if (index.section == 0 && index.row == 2) || (index.section == 1 && index.row > 0){ weakSelf.viewModel.selectIndex.accept(index) weakSelf.setAnswerStackView() } weakSelf.setAnswerStackView() collectionView.reloadItems(at: [index]) } @@ -335,7 +347,7 @@ extension HomeListenFight_lesson_3_VC:VoicePlayerDelegate{ func playComplete() { isPlayingIndex = nil islisten = true var nextRow = (viewModel.selectIndex.value?.row ?? 0) + 1 var section = (viewModel.selectIndex.value?.section ?? 0) + 0 @@ -359,6 +371,6 @@ } func playing() { islisten = false } } DolphinEnglishLearnStudent/Moudle/Home/Listen/View/ChooseLevelView.swift
@@ -15,6 +15,7 @@ @IBOutlet weak var tackView_level: UIStackView! private var clouseLevel:((Int)->Void)! private var cancelClouse:(()->Void)! private var level:Int = 0 override func awakeFromNib() { @@ -24,7 +25,7 @@ layoutIfNeeded() } static func show(clouse:@escaping (Int)->Void){ static func show(clouse:@escaping (Int)->Void,cancelClouse:@escaping()->Void){ var needLoad:Bool = true for v in sceneDelegate?.window?.subviews ?? []{ @@ -35,6 +36,7 @@ let levelView = ChooseLevelView.jq_loadNibView() levelView.clouseLevel = clouse levelView.cancelClouse = cancelClouse sceneDelegate?.window?.addSubview(levelView) levelView.frame = sceneDelegate?.window?.frame ?? .zero @@ -59,6 +61,7 @@ self.alpha = 0 } completion: { _ in self.removeFromSuperview() self.cancelClouse() } } DolphinEnglishLearnStudent/Services/Services.swift
@@ -83,13 +83,16 @@ } /// 完成学习 class func completeLearing(type:Int,studyTime:Int,studyIds:String,isComplete:Bool)->Observable<BaseResponse<SimpleModel>>{ class func completeLearing(type:Int,studyTime:Int,studyIds:String,quarter:Int,week:Int,day:Int,accracy:Int)->Observable<BaseResponse<SimpleModel>>{ let params = ParamsAppender.build(url: All_Url) params.interface(url: "/study/base/study/completeLearning") .append(key: "type", value: type) .append(key: "studyTime", value: studyTime) .append(key: "studyIds", value: studyIds) .append(key: "isComplete", value: isComplete) .append(key: "week", value: week) .append(key: "day", value: day) .append(key: "quarter", value: quarter) .append(key: "accuracy", value: accracy) return NetworkRequest.request(params: params, method: .post,encoding: JSONEncoding.default, progress: true) }