Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

chore: 재생 로직 구조 변경 #342

Closed
wants to merge 16 commits into from
Closed
Show file tree
Hide file tree
Changes from 6 commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
21 changes: 20 additions & 1 deletion iOS/Layover/Layover.xcodeproj/project.pbxproj
Original file line number Diff line number Diff line change
Expand Up @@ -145,6 +145,9 @@
835A61A22B068115002F22A5 /* PlaybackInteractor.swift in Sources */ = {isa = PBXBuildFile; fileRef = 835A619C2B068115002F22A5 /* PlaybackInteractor.swift */; };
835A61A62B0B4DDD002F22A5 /* Dashboard-Regular.ttf in Resources */ = {isa = PBXBuildFile; fileRef = 835A61A52B0B4DDD002F22A5 /* Dashboard-Regular.ttf */; };
835A61A92B0B5A31002F22A5 /* LoginConfigurator.swift in Sources */ = {isa = PBXBuildFile; fileRef = 835A61A82B0B5A31002F22A5 /* LoginConfigurator.swift */; };
8363A32D2B4C1CBB00772DDF /* PlaybackPresenterTests.swift in Sources */ = {isa = PBXBuildFile; fileRef = 8363A32C2B4C1CBA00772DDF /* PlaybackPresenterTests.swift */; };
8363A32F2B4C329100772DDF /* PlaybackInteractorTests.swift in Sources */ = {isa = PBXBuildFile; fileRef = 8363A32E2B4C329100772DDF /* PlaybackInteractorTests.swift */; };
8363A3332B4D6E9B00772DDF /* MockPlaybackWorker.swift in Sources */ = {isa = PBXBuildFile; fileRef = 8363A3322B4D6E9B00772DDF /* MockPlaybackWorker.swift */; };
836C33872B15A29600ECAFB0 /* Toast.swift in Sources */ = {isa = PBXBuildFile; fileRef = 836C33862B15A29600ECAFB0 /* Toast.swift */; };
836C338B2B15D22C00ECAFB0 /* PlaybackConfigurator.swift in Sources */ = {isa = PBXBuildFile; fileRef = 836C338A2B15D22C00ECAFB0 /* PlaybackConfigurator.swift */; };
836C33912B17629400ECAFB0 /* MapRouter.swift in Sources */ = {isa = PBXBuildFile; fileRef = 836C33902B17629400ECAFB0 /* MapRouter.swift */; };
Expand Down Expand Up @@ -402,6 +405,9 @@
835A61A52B0B4DDD002F22A5 /* Dashboard-Regular.ttf */ = {isa = PBXFileReference; lastKnownFileType = file; path = "Dashboard-Regular.ttf"; sourceTree = "<group>"; };
835A61A82B0B5A31002F22A5 /* LoginConfigurator.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = LoginConfigurator.swift; sourceTree = "<group>"; };
835A61AA2B0B85FD002F22A5 /* en */ = {isa = PBXFileReference; lastKnownFileType = text.plist.strings; name = en; path = en.lproj/LaunchScreen.strings; sourceTree = "<group>"; };
8363A32C2B4C1CBA00772DDF /* PlaybackPresenterTests.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; name = PlaybackPresenterTests.swift; path = LayoverTests/Mocks/Workers/PlaybackPresenterTests.swift; sourceTree = SOURCE_ROOT; };
8363A32E2B4C329100772DDF /* PlaybackInteractorTests.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; name = PlaybackInteractorTests.swift; path = LayoverTests/Mocks/Workers/PlaybackInteractorTests.swift; sourceTree = SOURCE_ROOT; };
8363A3322B4D6E9B00772DDF /* MockPlaybackWorker.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = MockPlaybackWorker.swift; sourceTree = "<group>"; };
836C33862B15A29600ECAFB0 /* Toast.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = Toast.swift; sourceTree = "<group>"; };
836C338A2B15D22C00ECAFB0 /* PlaybackConfigurator.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = PlaybackConfigurator.swift; sourceTree = "<group>"; };
836C33902B17629400ECAFB0 /* MapRouter.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = MapRouter.swift; sourceTree = "<group>"; };
Expand Down Expand Up @@ -619,6 +625,7 @@
194C21C72B1DF09B00C62645 /* Scenes */ = {
isa = PBXGroup;
children = (
8363A32B2B4C1C6900772DDF /* Playback */,
19AE481D2B29D02700DD4612 /* EditProfile */,
19AE48122B28C2A800DD4612 /* Setting */,
192513632B26F7BB001533FA /* TagPlayList */,
Expand Down Expand Up @@ -647,6 +654,7 @@
1925136C2B26F84E001533FA /* MockTagPlayListWorker.swift */,
192513842B27852C001533FA /* MockUserWorker.swift */,
19AE481B2B28C53800DD4612 /* MockSettingWorker.swift */,
8363A3322B4D6E9B00772DDF /* MockPlaybackWorker.swift */,
);
path = Workers;
sourceTree = "<group>";
Expand Down Expand Up @@ -869,6 +877,15 @@
path = Playback;
sourceTree = "<group>";
};
8363A32B2B4C1C6900772DDF /* Playback */ = {
isa = PBXGroup;
children = (
8363A32C2B4C1CBA00772DDF /* PlaybackPresenterTests.swift */,
8363A32E2B4C329100772DDF /* PlaybackInteractorTests.swift */,
);
path = Playback;
sourceTree = "<group>";
};
836C33922B18436A00ECAFB0 /* Setting */ = {
isa = PBXGroup;
children = (
Expand Down Expand Up @@ -1436,7 +1453,6 @@
FC2511AB2B04EA6B004717BC /* MapConfigurator.swift in Sources */,
1945523B2B05258200299768 /* HomeConfigurator.swift in Sources */,
FCF19BE22B2A4088003002E0 /* AVFileType+.swift in Sources */,
FC5BE11D2B148D160036366D /* EditProfileWorker.swift in Sources */,
19A1693A2B17BCC400DB34C0 /* MemberDTO.swift in Sources */,
194551F62B037F2D00299768 /* LoginViewController.swift in Sources */,
FC767FA52B125F430088CF9B /* UIViewController+.swift in Sources */,
Expand Down Expand Up @@ -1589,18 +1605,21 @@
192513682B26F7CE001533FA /* TagPlayListViewControllerTests.swift in Sources */,
1925136A2B26F7CE001533FA /* TagPlayListWorkerTests.swift in Sources */,
19AE48182B28C2B700DD4612 /* SettingInteractorTests.swift in Sources */,
8363A3332B4D6E9B00772DDF /* MockPlaybackWorker.swift in Sources */,
192513A72B278BB3001533FA /* Seeds.swift in Sources */,
194C21C52B1DEE6B00C62645 /* HomeWorkerTests.swift in Sources */,
19AE481C2B28C53800DD4612 /* MockSettingWorker.swift in Sources */,
19AE48252B29D03D00DD4612 /* EditProfilePresenterTests.swift in Sources */,
192513802B277CD7001533FA /* ProfileViewControllerTests.swift in Sources */,
194C21C62B1DEE6B00C62645 /* HomePresenterTests.swift in Sources */,
FC4E0C202B28B4C500152596 /* MockLocationFetcher.swift in Sources */,
8363A32D2B4C1CBB00772DDF /* PlaybackPresenterTests.swift in Sources */,
1925137A2B273D98001533FA /* StubAuthManager.swift in Sources */,
1925136D2B26F84E001533FA /* MockTagPlayListWorker.swift in Sources */,
19AE481A2B28C2B700DD4612 /* SettingPresenterTests.swift in Sources */,
19AE48172B28C2B700DD4612 /* SettingViewControllerTests.swift in Sources */,
194C21C32B1DEE6B00C62645 /* HomeViewControllerTests.swift in Sources */,
8363A32F2B4C329100772DDF /* PlaybackInteractorTests.swift in Sources */,
192513692B26F7CE001533FA /* TagPlayListInteractorTests.swift in Sources */,
19AE48232B29D03D00DD4612 /* EditProfileInteractorTests.swift in Sources */,
194C21CC2B1DF39200C62645 /* MockHomeWorker.swift in Sources */,
Expand Down
8 changes: 4 additions & 4 deletions iOS/Layover/Layover/Network/Mock/MockData/PostList.json
Original file line number Diff line number Diff line change
Expand Up @@ -81,8 +81,8 @@
{
"member" : {
"id" : 5,
"username" : "layover",
"introduce" : "Hi, my name is hwani",
"username" : "layover2",
"introduce" : "Hi, my name is hwani2",
"profile_image_url" : "profile_image_link"
},
"board" : {
Expand All @@ -91,8 +91,8 @@
"video_thumbnail_url" : "https://res.heraldm.com/content/image/2023/04/16/20230416000040_0.jpg",
"longitude" : 37.0532156213,
"latitude" : 127.060123123,
"title" : "아이즈원",
"content" : "게시글 설명2",
"title" : "아이즈원2",
"content" : "게시글 설명3",
"status": "COMPLETE"
},
"tag" : ["해시태그1", "해시태그6"]
Expand Down
130 changes: 58 additions & 72 deletions iOS/Layover/Layover/Scenes/Playback/PlaybackInteractor.swift
Original file line number Diff line number Diff line change
Expand Up @@ -9,8 +9,7 @@
import UIKit

protocol PlaybackBusinessLogic {
@discardableResult
func displayVideoList() -> Task<Bool, Never>
func displayVideoList() async
func moveInitialPlaybackCell()
func setInitialPlaybackCell()
func leavePlaybackView()
Expand All @@ -31,10 +30,8 @@ protocol PlaybackBusinessLogic {
func resumeVideo()
func moveToProfile(with request: PlaybackModels.MoveToRelativeView.Request)
func moveToTagPlay(with request: PlaybackModels.MoveToRelativeView.Request)
@discardableResult
func fetchPosts() -> Task<Bool, Never>
@discardableResult
func loadProfileImageAndLocation(with request: PlaybackModels.LoadProfileImageAndLocation.Request) -> Task<Bool, Never>
func fetchPosts() async
func loadProfileImageAndLocation(with request: PlaybackModels.LoadProfileImageAndLocation.Request) async
}

protocol PlaybackDataStore: AnyObject {
Expand Down Expand Up @@ -80,26 +77,23 @@ final class PlaybackInteractor: PlaybackBusinessLogic, PlaybackDataStore {

private var currentPage: Int = 1

private var playbackVideoInfos: [Models.PlaybackInfo] = []
var playbackVideoInfos: [Models.PlaybackInfo] = []

// MARK: - UseCase Load Video List

func displayVideoList() -> Task<Bool, Never> {
Task {
guard let parentView: Models.ParentView,
var posts: [Post],
let worker: PlaybackWorkerProtocol else { return false }
if parentView == .map {
posts = worker.makeInfiniteScroll(posts: posts)
self.posts = posts
}
let videos: [Models.PlaybackVideo]
(videos, playbackVideoInfos) = transPostToVideo(posts)
let response: Models.LoadPlaybackVideoList.Response = Models.LoadPlaybackVideoList.Response(videos: videos)
await MainActor.run {
presenter?.presentVideoList(with: response)
}
return true
func displayVideoList() async {
guard let parentView: Models.ParentView,
var posts: [Post],
let worker: PlaybackWorkerProtocol else { return }
if parentView == .map {
posts = worker.makeInfiniteScroll(posts: posts)
self.posts = posts
}
let videos: [Models.PlaybackVideo]
(videos, playbackVideoInfos) = transPostToVideo(posts)
let response: Models.LoadPlaybackVideoList.Response = Models.LoadPlaybackVideoList.Response(videos: videos)
await MainActor.run {
presenter?.presentVideoList(with: response)
}
}

Expand Down Expand Up @@ -284,7 +278,7 @@ final class PlaybackInteractor: PlaybackBusinessLogic, PlaybackDataStore {
isNeedReplace: true)
playbackVideoInfos.append(playbackVideoInfos[request.indexPathRow - 1])
if let posts {
self.posts?.append((posts[2]))
self.posts?.append(posts[request.indexPathRow - 1])
}
} else {
response = Models.DeletePlaybackVideo.Response(
Expand Down Expand Up @@ -359,59 +353,51 @@ final class PlaybackInteractor: PlaybackBusinessLogic, PlaybackDataStore {
presenter?.presentTagPlay()
}

func fetchPosts() -> Task<Bool, Never> {
Task {
if !isFetchReqeust {
isFetchReqeust = true
var page: Int = 0
if parentView != .home {
page = playbackVideoInfos.count / Models.fetchPostCount + 1
if page == currentPage {
return false
}
}
currentPage = page
var newPosts: [Post]?
switch parentView {
case .home:
newPosts = await worker?.fetchHomePosts()
case .map:
return false
case .myProfile, .otherProfile:
newPosts = await worker?.fetchProfilePosts(profileID: memberID, page: page)
case .tag:
guard let selectedTag else { return false }
newPosts = await worker?.fetchTagPosts(selectedTag: selectedTag, page: page)
default:
return false
}
guard let newPosts else { return false }
posts?.append(contentsOf: newPosts)
let videos: [Models.PlaybackVideo]
let newInfos: [Models.PlaybackInfo]
(videos, newInfos) = transPostToVideo(newPosts)
self.playbackVideoInfos.append(contentsOf: newInfos)
let response: Models.LoadPlaybackVideoList.Response = Models.LoadPlaybackVideoList.Response(videos: videos)
await MainActor.run {
presenter?.presentLoadFetchVideos(with: response)
isFetchReqeust = false
func fetchPosts() async {
if !isFetchReqeust {
isFetchReqeust = true
var page: Int = 0
if parentView != .home {
page = playbackVideoInfos.count / Models.fetchPostCount + 1
if page == currentPage {
return
}
return true
}
return false
currentPage = page
var newPosts: [Post]?
switch parentView {
case .home:
newPosts = await worker?.fetchHomePosts()
case .map:
return
case .myProfile, .otherProfile:
newPosts = await worker?.fetchProfilePosts(profileID: memberID, page: page)
case .tag:
guard let selectedTag else { return }
newPosts = await worker?.fetchTagPosts(selectedTag: selectedTag, page: page)
default:
return
}
guard let newPosts else { return }
posts?.append(contentsOf: newPosts)
let videos: [Models.PlaybackVideo]
let newInfos: [Models.PlaybackInfo]
(videos, newInfos) = transPostToVideo(newPosts)
self.playbackVideoInfos.append(contentsOf: newInfos)
let response: Models.LoadPlaybackVideoList.Response = Models.LoadPlaybackVideoList.Response(videos: videos)
await MainActor.run {
presenter?.presentLoadFetchVideos(with: response)
isFetchReqeust = false
}
}
}

func loadProfileImageAndLocation(with request: PlaybackModels.LoadProfileImageAndLocation.Request) -> Task<Bool, Never> {
Task {
async let profileImageData = self.worker?.fetchImageData(with: request.profileImageURL)
async let location: String? = self.worker?.transLocation(latitude: request.latitude, longitude: request.longitude)
let response: Models.LoadProfileImageAndLocation.Response = Models.LoadProfileImageAndLocation.Response(curCell: request.curCell, profileImageData: await profileImageData, location: await location)
await MainActor.run {
presenter?.presentLoadProfileImageAndLocation(with: response)
return true
}
return false
func loadProfileImageAndLocation(with request: PlaybackModels.LoadProfileImageAndLocation.Request) async {
async let profileImageData = self.worker?.fetchImageData(with: request.profileImageURL)
async let location: String? = self.worker?.transLocation(latitude: request.latitude, longitude: request.longitude)
let response: Models.LoadProfileImageAndLocation.Response = Models.LoadProfileImageAndLocation.Response(curCell: request.curCell, profileImageData: await profileImageData, location: await location)
await MainActor.run {
presenter?.presentLoadProfileImageAndLocation(with: response)
}
}
}
5 changes: 0 additions & 5 deletions iOS/Layover/Layover/Scenes/Playback/PlaybackPresenter.swift
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,6 @@ import Foundation
protocol PlaybackPresentationLogic {
func presentVideoList(with response: PlaybackModels.LoadPlaybackVideoList.Response)
func presentLoadFetchVideos(with response: PlaybackModels.LoadPlaybackVideoList.Response)
func presentSetCellIfInfinite(with response: PlaybackModels.SetInitialPlaybackCell.Response)
func presentMoveCellNext(with response: PlaybackModels.DisplayPlaybackVideo.Response)
func presentSetInitialPlaybackCell(with response: PlaybackModels.SetInitialPlaybackCell.Response)
func presentMoveInitialPlaybackCell(with response: PlaybackModels.SetInitialPlaybackCell.Response)
Expand Down Expand Up @@ -50,10 +49,6 @@ final class PlaybackPresenter: PlaybackPresentationLogic {
viewController?.loadFetchVideos(viewModel: viewModel)
}

func presentSetCellIfInfinite(with response: PlaybackModels.SetInitialPlaybackCell.Response) {
viewController?.displayMoveCellIfinfinite(viewModel: Models.SetInitialPlaybackCell.ViewModel(indexPathRow: response.indexPathRow))
}

// MARK: - UseCase Set Init Playback Scene

func presentSetInitialPlaybackCell(with response: PlaybackModels.SetInitialPlaybackCell.Response) {
Expand Down
25 changes: 13 additions & 12 deletions iOS/Layover/Layover/Scenes/Playback/PlaybackViewController.swift
Original file line number Diff line number Diff line change
Expand Up @@ -19,7 +19,6 @@ protocol PlaybackViewControllerDelegate: AnyObject {
protocol PlaybackDisplayLogic: AnyObject {
func displayVideoList(viewModel: PlaybackModels.LoadPlaybackVideoList.ViewModel)
func loadFetchVideos(viewModel: PlaybackModels.LoadPlaybackVideoList.ViewModel)
func displayMoveCellIfinfinite(viewModel: PlaybackModels.SetInitialPlaybackCell.ViewModel)
func stopPrevPlayerAndPlayCurPlayer(viewModel: PlaybackModels.DisplayPlaybackVideo.ViewModel)
func setInitialPlaybackCell(viewModel: PlaybackModels.SetInitialPlaybackCell.ViewModel)
func moveInitialPlaybackCell(viewModel: PlaybackModels.SetInitialPlaybackCell.ViewModel)
Expand Down Expand Up @@ -92,7 +91,9 @@ final class PlaybackViewController: BaseViewController {

override func viewDidLoad() {
super.viewDidLoad()
interactor?.displayVideoList()
Task {
await interactor?.displayVideoList()
}
interactor?.configurePlaybackCell()
playbackCollectionView.delegate = self
playbackCollectionView.contentInsetAdjustmentBehavior = .never
Expand Down Expand Up @@ -213,10 +214,6 @@ extension PlaybackViewController: PlaybackDisplayLogic {
dataSource?.apply(currentSnapshot, animatingDifferences: true)
}

func displayMoveCellIfinfinite(viewModel: Models.SetInitialPlaybackCell.ViewModel) {
playbackCollectionView.setContentOffset(.init(x: playbackCollectionView.contentOffset.x, y: playbackCollectionView.bounds.height * CGFloat(viewModel.indexPathRow)), animated: false)
}

func stopPrevPlayerAndPlayCurPlayer(viewModel: PlaybackModels.DisplayPlaybackVideo.ViewModel) {
guard let tabBarHeight: CGFloat = self.tabBarController?.tabBar.frame.height else { return }
if let previousCell = viewModel.previousCell {
Expand Down Expand Up @@ -270,11 +267,13 @@ extension PlaybackViewController: PlaybackDisplayLogic {
}
}
cell.addAVPlayer(url: playbackVideo.displayedPost.board.videoURL)
self.interactor?.loadProfileImageAndLocation(with: Models.LoadProfileImageAndLocation.Request(
curCell: cell,
profileImageURL: playbackVideo.displayedPost.member.profileImageURL,
latitude: playbackVideo.displayedPost.board.latitude,
longitude: playbackVideo.displayedPost.board.longitude))
Task {
await self.interactor?.loadProfileImageAndLocation(with: Models.LoadProfileImageAndLocation.Request(
curCell: cell,
profileImageURL: playbackVideo.displayedPost.member.profileImageURL,
latitude: playbackVideo.displayedPost.board.latitude,
longitude: playbackVideo.displayedPost.board.longitude))
}
cell.delegate = self
return cell
}
Expand Down Expand Up @@ -402,7 +401,9 @@ extension PlaybackViewController: UICollectionViewDelegate {
let currentOffset = scrollView.contentOffset.y
let maximumOffset = scrollView.contentSize.height - scrollView.frame.size.height
if maximumOffset < currentOffset {
interactor?.fetchPosts()
Task {
await interactor?.fetchPosts()
}
}
}
}
Expand Down
Loading