mirror of
https://github.com/cranci1/Sora.git
synced 2026-03-11 17:45:37 +00:00
what was this monster 😭
This commit is contained in:
parent
bca07c9c46
commit
5607ec70ff
1 changed files with 78 additions and 110 deletions
|
|
@ -189,12 +189,12 @@ struct MediaInfoView: View {
|
||||||
UserDefaults.standard.set(true, forKey: "isMediaInfoActive")
|
UserDefaults.standard.set(true, forKey: "isMediaInfoActive")
|
||||||
// swipe back
|
// swipe back
|
||||||
/*
|
/*
|
||||||
if let windowScene = UIApplication.shared.connectedScenes.first as? UIWindowScene,
|
if let windowScene = UIApplication.shared.connectedScenes.first as? UIWindowScene,
|
||||||
let window = windowScene.windows.first,
|
let window = windowScene.windows.first,
|
||||||
let navigationController = window.rootViewController?.children.first as? UINavigationController {
|
let navigationController = window.rootViewController?.children.first as? UINavigationController {
|
||||||
navigationController.interactivePopGestureRecognizer?.isEnabled = false
|
navigationController.interactivePopGestureRecognizer?.isEnabled = false
|
||||||
}
|
}
|
||||||
*/
|
*/
|
||||||
}
|
}
|
||||||
.onChange(of: selectedRange) { newValue in
|
.onChange(of: selectedRange) { newValue in
|
||||||
UserDefaults.standard.set(newValue.lowerBound, forKey: selectedRangeKey)
|
UserDefaults.standard.set(newValue.lowerBound, forKey: selectedRangeKey)
|
||||||
|
|
@ -404,7 +404,7 @@ struct MediaInfoView: View {
|
||||||
.foregroundColor(.secondary)
|
.foregroundColor(.secondary)
|
||||||
.lineLimit(showFullSynopsis ? nil : 3)
|
.lineLimit(showFullSynopsis ? nil : 3)
|
||||||
.animation(nil, value: showFullSynopsis)
|
.animation(nil, value: showFullSynopsis)
|
||||||
|
|
||||||
HStack {
|
HStack {
|
||||||
Spacer()
|
Spacer()
|
||||||
Text(showFullSynopsis ? NSLocalizedString("LESS", comment: "") : NSLocalizedString("MORE", comment: ""))
|
Text(showFullSynopsis ? NSLocalizedString("LESS", comment: "") : NSLocalizedString("MORE", comment: ""))
|
||||||
|
|
@ -487,7 +487,7 @@ struct MediaInfoView: View {
|
||||||
.cornerRadius(15)
|
.cornerRadius(15)
|
||||||
.gradientOutline()
|
.gradientOutline()
|
||||||
}
|
}
|
||||||
|
|
||||||
Button(action: { openSafariViewController(with: href) }) {
|
Button(action: { openSafariViewController(with: href) }) {
|
||||||
Image(systemName: "safari")
|
Image(systemName: "safari")
|
||||||
.resizable()
|
.resizable()
|
||||||
|
|
@ -557,7 +557,7 @@ struct MediaInfoView: View {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ViewBuilder
|
@ViewBuilder
|
||||||
private var seasonSelectorStyled: some View {
|
private var seasonSelectorStyled: some View {
|
||||||
let seasons = groupedEpisodes()
|
let seasons = groupedEpisodes()
|
||||||
|
|
@ -581,7 +581,7 @@ struct MediaInfoView: View {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ViewBuilder
|
@ViewBuilder
|
||||||
private var rangeSelectorStyled: some View {
|
private var rangeSelectorStyled: some View {
|
||||||
Menu {
|
Menu {
|
||||||
|
|
@ -719,17 +719,17 @@ struct MediaInfoView: View {
|
||||||
menuButton
|
menuButton
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if chapters.count > chapterChunkSize {
|
if chapters.count > chapterChunkSize {
|
||||||
HStack {
|
HStack {
|
||||||
Spacer()
|
Spacer()
|
||||||
chapterRangeSelectorStyled
|
chapterRangeSelectorStyled
|
||||||
}
|
|
||||||
.padding(.bottom, 0)
|
|
||||||
}
|
}
|
||||||
LazyVStack(spacing: 15) {
|
.padding(.bottom, 0)
|
||||||
ForEach(chapters.indices.filter { selectedChapterRange.contains($0) }, id: \..self) { i in
|
}
|
||||||
let chapter = chapters[i]
|
LazyVStack(spacing: 15) {
|
||||||
let _ = refreshTrigger
|
ForEach(chapters.indices.filter { selectedChapterRange.contains($0) }, id: \..self) { i in
|
||||||
|
let chapter = chapters[i]
|
||||||
|
let _ = refreshTrigger
|
||||||
if let href = chapter["href"] as? String,
|
if let href = chapter["href"] as? String,
|
||||||
let number = chapter["number"] as? Int,
|
let number = chapter["number"] as? Int,
|
||||||
let title = chapter["title"] as? String {
|
let title = chapter["title"] as? String {
|
||||||
|
|
@ -792,7 +792,7 @@ struct MediaInfoView: View {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ViewBuilder
|
@ViewBuilder
|
||||||
private var chapterRangeSelectorStyled: some View {
|
private var chapterRangeSelectorStyled: some View {
|
||||||
Menu {
|
Menu {
|
||||||
|
|
@ -952,7 +952,7 @@ struct MediaInfoView: View {
|
||||||
UserDefaults.standard.set(imageUrl, forKey: "mediaInfoImageUrl_\(module.id.uuidString)")
|
UserDefaults.standard.set(imageUrl, forKey: "mediaInfoImageUrl_\(module.id.uuidString)")
|
||||||
Logger.shared.log("Saved MediaInfoView image URL: \(imageUrl) for module \(module.id.uuidString)", type: "Debug")
|
Logger.shared.log("Saved MediaInfoView image URL: \(imageUrl) for module \(module.id.uuidString)", type: "Debug")
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
if module.metadata.novel == true {
|
if module.metadata.novel == true {
|
||||||
if !hasFetched {
|
if !hasFetched {
|
||||||
|
|
@ -969,11 +969,11 @@ struct MediaInfoView: View {
|
||||||
if let jsContent = jsContent {
|
if let jsContent = jsContent {
|
||||||
jsController.loadScript(jsContent)
|
jsController.loadScript(jsContent)
|
||||||
}
|
}
|
||||||
|
|
||||||
await withTaskGroup(of: Void.self) { group in
|
await withTaskGroup(of: Void.self) { group in
|
||||||
var chaptersLoaded = false
|
var chaptersLoaded = false
|
||||||
var detailsLoaded = false
|
var detailsLoaded = false
|
||||||
|
|
||||||
group.addTask {
|
group.addTask {
|
||||||
let fetchedChapters = try? await JSController.shared.extractChapters(moduleId: module.id.uuidString, href: href)
|
let fetchedChapters = try? await JSController.shared.extractChapters(moduleId: module.id.uuidString, href: href)
|
||||||
await MainActor.run {
|
await MainActor.run {
|
||||||
|
|
@ -1429,7 +1429,6 @@ struct MediaInfoView: View {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
func fetchDetails() {
|
func fetchDetails() {
|
||||||
Logger.shared.log("fetchDetails: called", type: "Debug")
|
Logger.shared.log("fetchDetails: called", type: "Debug")
|
||||||
DispatchQueue.main.asyncAfter(deadline: .now() + 0.5) {
|
DispatchQueue.main.asyncAfter(deadline: .now() + 0.5) {
|
||||||
|
|
@ -1437,88 +1436,15 @@ struct MediaInfoView: View {
|
||||||
do {
|
do {
|
||||||
let jsContent = try moduleManager.getModuleContent(module)
|
let jsContent = try moduleManager.getModuleContent(module)
|
||||||
jsController.loadScript(jsContent)
|
jsController.loadScript(jsContent)
|
||||||
|
|
||||||
|
let completion: (Any?, [EpisodeLink]) -> Void = { items, episodes in
|
||||||
|
self.handleFetchDetailsResponse(items: items, episodes: episodes)
|
||||||
|
}
|
||||||
|
|
||||||
if module.metadata.asyncJS == true {
|
if module.metadata.asyncJS == true {
|
||||||
jsController.fetchDetailsJS(url: href) { items, episodes in
|
jsController.fetchDetailsJS(url: href, completion: completion)
|
||||||
Logger.shared.log("fetchDetails: items = \(items)", type: "Debug")
|
|
||||||
Logger.shared.log("fetchDetails: episodes = \(episodes)", type: "Debug")
|
|
||||||
|
|
||||||
if let mediaItems = items as? [MediaItem], let item = mediaItems.first {
|
|
||||||
self.synopsis = item.description
|
|
||||||
self.aliases = item.aliases
|
|
||||||
self.airdate = item.airdate
|
|
||||||
} else if let str = items as? String {
|
|
||||||
if let data = str.data(using: .utf8),
|
|
||||||
let arr = try? JSONSerialization.jsonObject(with: data) as? [[String: Any]],
|
|
||||||
let dict = arr.first {
|
|
||||||
self.synopsis = dict["description"] as? String ?? ""
|
|
||||||
self.aliases = dict["aliases"] as? String ?? ""
|
|
||||||
self.airdate = dict["airdate"] as? String ?? ""
|
|
||||||
}
|
|
||||||
} else if let dict = items as? [String: Any] {
|
|
||||||
self.synopsis = dict["description"] as? String ?? ""
|
|
||||||
self.aliases = dict["aliases"] as? String ?? ""
|
|
||||||
self.airdate = dict["airdate"] as? String ?? ""
|
|
||||||
} else if let arr = items as? [[String: Any]], let dict = arr.first {
|
|
||||||
self.synopsis = dict["description"] as? String ?? ""
|
|
||||||
self.aliases = dict["aliases"] as? String ?? ""
|
|
||||||
self.airdate = dict["airdate"] as? String ?? ""
|
|
||||||
} else {
|
|
||||||
Logger.shared.log("Failed to process items of type: \(type(of: items))", type: "Error")
|
|
||||||
}
|
|
||||||
|
|
||||||
if self.module.metadata.novel ?? false {
|
|
||||||
Logger.shared.log("fetchDetails: (novel) chapters count = \(self.chapters.count)", type: "Debug")
|
|
||||||
self.isLoading = false
|
|
||||||
self.isRefetching = false
|
|
||||||
} else {
|
|
||||||
Logger.shared.log("fetchDetails: (episodes) episodes count = \(episodes.count)", type: "Debug")
|
|
||||||
self.episodeLinks = episodes
|
|
||||||
self.restoreSelectionState()
|
|
||||||
self.isLoading = false
|
|
||||||
self.isRefetching = false
|
|
||||||
}
|
|
||||||
}
|
|
||||||
} else {
|
} else {
|
||||||
jsController.fetchDetails(url: href) { items, episodes in
|
jsController.fetchDetails(url: href, completion: completion)
|
||||||
Logger.shared.log("fetchDetails: items = \(items)", type: "Debug")
|
|
||||||
Logger.shared.log("fetchDetails: episodes = \(episodes)", type: "Debug")
|
|
||||||
|
|
||||||
if let mediaItems = items as? [MediaItem], let item = mediaItems.first {
|
|
||||||
self.synopsis = item.description
|
|
||||||
self.aliases = item.aliases
|
|
||||||
self.airdate = item.airdate
|
|
||||||
} else if let str = items as? String {
|
|
||||||
if let data = str.data(using: .utf8),
|
|
||||||
let arr = try? JSONSerialization.jsonObject(with: data) as? [[String: Any]],
|
|
||||||
let dict = arr.first {
|
|
||||||
self.synopsis = dict["description"] as? String ?? ""
|
|
||||||
self.aliases = dict["aliases"] as? String ?? ""
|
|
||||||
self.airdate = dict["airdate"] as? String ?? ""
|
|
||||||
}
|
|
||||||
} else if let dict = items as? [String: Any] {
|
|
||||||
self.synopsis = dict["description"] as? String ?? ""
|
|
||||||
self.aliases = dict["aliases"] as? String ?? ""
|
|
||||||
self.airdate = dict["airdate"] as? String ?? ""
|
|
||||||
} else if let arr = items as? [[String: Any]], let dict = arr.first {
|
|
||||||
self.synopsis = dict["description"] as? String ?? ""
|
|
||||||
self.aliases = dict["aliases"] as? String ?? ""
|
|
||||||
self.airdate = dict["airdate"] as? String ?? ""
|
|
||||||
} else {
|
|
||||||
Logger.shared.log("Failed to process items of type: \(type(of: items))", type: "Error")
|
|
||||||
}
|
|
||||||
|
|
||||||
if self.module.metadata.novel ?? false {
|
|
||||||
Logger.shared.log("fetchDetails: (novel) chapters count = \(self.chapters.count)", type: "Debug")
|
|
||||||
self.isLoading = false
|
|
||||||
self.isRefetching = false
|
|
||||||
} else {
|
|
||||||
Logger.shared.log("fetchDetails: (episodes) episodes count = \(episodes.count)", type: "Debug")
|
|
||||||
self.episodeLinks = episodes
|
|
||||||
self.restoreSelectionState()
|
|
||||||
self.isLoading = false
|
|
||||||
self.isRefetching = false
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
} catch {
|
} catch {
|
||||||
Logger.shared.log("Error loading module: \(error)", type: "Error")
|
Logger.shared.log("Error loading module: \(error)", type: "Error")
|
||||||
|
|
@ -1529,6 +1455,53 @@ struct MediaInfoView: View {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private func handleFetchDetailsResponse(items: Any?, episodes: [EpisodeLink]) {
|
||||||
|
Logger.shared.log("fetchDetails: items = \(items)", type: "Debug")
|
||||||
|
Logger.shared.log("fetchDetails: episodes = \(episodes)", type: "Debug")
|
||||||
|
|
||||||
|
processItemsResponse(items)
|
||||||
|
|
||||||
|
if module.metadata.novel ?? false {
|
||||||
|
Logger.shared.log("fetchDetails: (novel) chapters count = \(chapters.count)", type: "Debug")
|
||||||
|
} else {
|
||||||
|
Logger.shared.log("fetchDetails: (episodes) episodes count = \(episodes.count)", type: "Debug")
|
||||||
|
episodeLinks = episodes
|
||||||
|
restoreSelectionState()
|
||||||
|
}
|
||||||
|
|
||||||
|
isLoading = false
|
||||||
|
isRefetching = false
|
||||||
|
}
|
||||||
|
|
||||||
|
private func processItemsResponse(_ items: Any?) {
|
||||||
|
if let mediaItems = items as? [MediaItem], let item = mediaItems.first {
|
||||||
|
synopsis = item.description
|
||||||
|
aliases = item.aliases
|
||||||
|
airdate = item.airdate
|
||||||
|
} else if let str = items as? String {
|
||||||
|
parseStringResponse(str)
|
||||||
|
} else if let dict = items as? [String: Any] {
|
||||||
|
extractMetadataFromDict(dict)
|
||||||
|
} else if let arr = items as? [[String: Any]], let dict = arr.first {
|
||||||
|
extractMetadataFromDict(dict)
|
||||||
|
} else {
|
||||||
|
Logger.shared.log("Failed to process items of type: \(type(of: items))", type: "Error")
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private func parseStringResponse(_ str: String) {
|
||||||
|
guard let data = str.data(using: .utf8),
|
||||||
|
let arr = try? JSONSerialization.jsonObject(with: data) as? [[String: Any]],
|
||||||
|
let dict = arr.first else { return }
|
||||||
|
extractMetadataFromDict(dict)
|
||||||
|
}
|
||||||
|
|
||||||
|
private func extractMetadataFromDict(_ dict: [String: Any]) {
|
||||||
|
synopsis = dict["description"] as? String ?? ""
|
||||||
|
aliases = dict["aliases"] as? String ?? ""
|
||||||
|
airdate = dict["airdate"] as? String ?? ""
|
||||||
|
}
|
||||||
|
|
||||||
private func fetchAniListPosterImageAndSet() {
|
private func fetchAniListPosterImageAndSet() {
|
||||||
guard let listID = itemID, listID > 0 else { return }
|
guard let listID = itemID, listID > 0 else { return }
|
||||||
AniListMutation().fetchCoverImage(animeId: listID) { result in
|
AniListMutation().fetchCoverImage(animeId: listID) { result in
|
||||||
|
|
@ -1709,7 +1682,6 @@ struct MediaInfoView: View {
|
||||||
}.resume()
|
}.resume()
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
func fetchStream(href: String) {
|
func fetchStream(href: String) {
|
||||||
let fetchID = UUID()
|
let fetchID = UUID()
|
||||||
activeFetchID = fetchID
|
activeFetchID = fetchID
|
||||||
|
|
@ -1954,7 +1926,6 @@ struct MediaInfoView: View {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
private func downloadSingleEpisodeDirectly(episode: EpisodeLink) {
|
private func downloadSingleEpisodeDirectly(episode: EpisodeLink) {
|
||||||
if isSingleEpisodeDownloading { return }
|
if isSingleEpisodeDownloading { return }
|
||||||
|
|
||||||
|
|
@ -2240,7 +2211,6 @@ struct MediaInfoView: View {
|
||||||
}.resume()
|
}.resume()
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
private func presentAlert(_ alert: UIAlertController) {
|
private func presentAlert(_ alert: UIAlertController) {
|
||||||
if let windowScene = UIApplication.shared.connectedScenes.first as? UIWindowScene,
|
if let windowScene = UIApplication.shared.connectedScenes.first as? UIWindowScene,
|
||||||
let window = windowScene.windows.first,
|
let window = windowScene.windows.first,
|
||||||
|
|
@ -2342,5 +2312,3 @@ struct MediaInfoView: View {
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
|
||||||
Loading…
Reference in a new issue