Compare commits

..

No commits in common. "ff97b0f76deb4303d7076731082749961eba68b7" and "3aa5aa1bc01782274228cbf9156e6dcb56a50fd1" have entirely different histories.

10 changed files with 158 additions and 165 deletions

View File

@ -156,9 +156,10 @@
D67C57B221E28FAD00C3118B /* ComposeStatusReplyView.xib in Resources */ = {isa = PBXBuildFile; fileRef = D67C57B121E28FAD00C3118B /* ComposeStatusReplyView.xib */; }; D67C57B221E28FAD00C3118B /* ComposeStatusReplyView.xib in Resources */ = {isa = PBXBuildFile; fileRef = D67C57B121E28FAD00C3118B /* ComposeStatusReplyView.xib */; };
D67C57B421E2910700C3118B /* ComposeStatusReplyView.swift in Sources */ = {isa = PBXBuildFile; fileRef = D67C57B321E2910700C3118B /* ComposeStatusReplyView.swift */; }; D67C57B421E2910700C3118B /* ComposeStatusReplyView.swift in Sources */ = {isa = PBXBuildFile; fileRef = D67C57B321E2910700C3118B /* ComposeStatusReplyView.swift */; };
D68FEC4F232C5BC300C84F23 /* SegmentedPageViewController.swift in Sources */ = {isa = PBXBuildFile; fileRef = D68FEC4E232C5BC300C84F23 /* SegmentedPageViewController.swift */; }; D68FEC4F232C5BC300C84F23 /* SegmentedPageViewController.swift in Sources */ = {isa = PBXBuildFile; fileRef = D68FEC4E232C5BC300C84F23 /* SegmentedPageViewController.swift */; };
D6945C2F23AC47C3005C403C /* SavedDataManager.swift in Sources */ = {isa = PBXBuildFile; fileRef = D6945C2E23AC47C3005C403C /* SavedDataManager.swift */; }; D6945C2F23AC47C3005C403C /* SavedHashtagsManager.swift in Sources */ = {isa = PBXBuildFile; fileRef = D6945C2E23AC47C3005C403C /* SavedHashtagsManager.swift */; };
D6945C3223AC4D36005C403C /* HashtagTimelineViewController.swift in Sources */ = {isa = PBXBuildFile; fileRef = D6945C3123AC4D36005C403C /* HashtagTimelineViewController.swift */; }; D6945C3223AC4D36005C403C /* HashtagTimelineViewController.swift in Sources */ = {isa = PBXBuildFile; fileRef = D6945C3123AC4D36005C403C /* HashtagTimelineViewController.swift */; };
D6945C3423AC6431005C403C /* AddSavedHashtagViewController.swift in Sources */ = {isa = PBXBuildFile; fileRef = D6945C3323AC6431005C403C /* AddSavedHashtagViewController.swift */; }; D6945C3423AC6431005C403C /* AddSavedHashtagViewController.swift in Sources */ = {isa = PBXBuildFile; fileRef = D6945C3323AC6431005C403C /* AddSavedHashtagViewController.swift */; };
D6945C3623AC6C09005C403C /* SavedInstancesManager.swift in Sources */ = {isa = PBXBuildFile; fileRef = D6945C3523AC6C09005C403C /* SavedInstancesManager.swift */; };
D6945C3823AC739F005C403C /* InstanceTimelineViewController.swift in Sources */ = {isa = PBXBuildFile; fileRef = D6945C3723AC739F005C403C /* InstanceTimelineViewController.swift */; }; D6945C3823AC739F005C403C /* InstanceTimelineViewController.swift in Sources */ = {isa = PBXBuildFile; fileRef = D6945C3723AC739F005C403C /* InstanceTimelineViewController.swift */; };
D6945C3A23AC75E2005C403C /* FindInstanceViewController.swift in Sources */ = {isa = PBXBuildFile; fileRef = D6945C3923AC75E2005C403C /* FindInstanceViewController.swift */; }; D6945C3A23AC75E2005C403C /* FindInstanceViewController.swift in Sources */ = {isa = PBXBuildFile; fileRef = D6945C3923AC75E2005C403C /* FindInstanceViewController.swift */; };
D6A3BC7723218E1300FD64D5 /* TimelineSegment.swift in Sources */ = {isa = PBXBuildFile; fileRef = D6A3BC7323218C6E00FD64D5 /* TimelineSegment.swift */; }; D6A3BC7723218E1300FD64D5 /* TimelineSegment.swift in Sources */ = {isa = PBXBuildFile; fileRef = D6A3BC7323218C6E00FD64D5 /* TimelineSegment.swift */; };
@ -431,9 +432,10 @@
D67C57B121E28FAD00C3118B /* ComposeStatusReplyView.xib */ = {isa = PBXFileReference; lastKnownFileType = file.xib; path = ComposeStatusReplyView.xib; sourceTree = "<group>"; }; D67C57B121E28FAD00C3118B /* ComposeStatusReplyView.xib */ = {isa = PBXFileReference; lastKnownFileType = file.xib; path = ComposeStatusReplyView.xib; sourceTree = "<group>"; };
D67C57B321E2910700C3118B /* ComposeStatusReplyView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = ComposeStatusReplyView.swift; sourceTree = "<group>"; }; D67C57B321E2910700C3118B /* ComposeStatusReplyView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = ComposeStatusReplyView.swift; sourceTree = "<group>"; };
D68FEC4E232C5BC300C84F23 /* SegmentedPageViewController.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = SegmentedPageViewController.swift; sourceTree = "<group>"; }; D68FEC4E232C5BC300C84F23 /* SegmentedPageViewController.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = SegmentedPageViewController.swift; sourceTree = "<group>"; };
D6945C2E23AC47C3005C403C /* SavedDataManager.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = SavedDataManager.swift; sourceTree = "<group>"; }; D6945C2E23AC47C3005C403C /* SavedHashtagsManager.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = SavedHashtagsManager.swift; sourceTree = "<group>"; };
D6945C3123AC4D36005C403C /* HashtagTimelineViewController.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = HashtagTimelineViewController.swift; sourceTree = "<group>"; }; D6945C3123AC4D36005C403C /* HashtagTimelineViewController.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = HashtagTimelineViewController.swift; sourceTree = "<group>"; };
D6945C3323AC6431005C403C /* AddSavedHashtagViewController.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = AddSavedHashtagViewController.swift; sourceTree = "<group>"; }; D6945C3323AC6431005C403C /* AddSavedHashtagViewController.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = AddSavedHashtagViewController.swift; sourceTree = "<group>"; };
D6945C3523AC6C09005C403C /* SavedInstancesManager.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = SavedInstancesManager.swift; sourceTree = "<group>"; };
D6945C3723AC739F005C403C /* InstanceTimelineViewController.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = InstanceTimelineViewController.swift; sourceTree = "<group>"; }; D6945C3723AC739F005C403C /* InstanceTimelineViewController.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = InstanceTimelineViewController.swift; sourceTree = "<group>"; };
D6945C3923AC75E2005C403C /* FindInstanceViewController.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; name = FindInstanceViewController.swift; path = Tusker/Screens/FindInstanceViewController.swift; sourceTree = SOURCE_ROOT; }; D6945C3923AC75E2005C403C /* FindInstanceViewController.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; name = FindInstanceViewController.swift; path = Tusker/Screens/FindInstanceViewController.swift; sourceTree = SOURCE_ROOT; };
D6A3BC7323218C6E00FD64D5 /* TimelineSegment.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = TimelineSegment.swift; sourceTree = "<group>"; }; D6A3BC7323218C6E00FD64D5 /* TimelineSegment.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = TimelineSegment.swift; sourceTree = "<group>"; };
@ -1191,7 +1193,8 @@
D6AC956623C4347E008C9946 /* SceneDelegate.swift */, D6AC956623C4347E008C9946 /* SceneDelegate.swift */,
D64D0AAC2128D88B005A6F37 /* LocalData.swift */, D64D0AAC2128D88B005A6F37 /* LocalData.swift */,
D627FF75217E923E00CC0648 /* DraftsManager.swift */, D627FF75217E923E00CC0648 /* DraftsManager.swift */,
D6945C2E23AC47C3005C403C /* SavedDataManager.swift */, D6945C2E23AC47C3005C403C /* SavedHashtagsManager.swift */,
D6945C3523AC6C09005C403C /* SavedInstancesManager.swift */,
D6028B9A2150811100F223B9 /* MastodonCache.swift */, D6028B9A2150811100F223B9 /* MastodonCache.swift */,
D6C693EE216192C2007D6A6D /* TuskerNavigationDelegate.swift */, D6C693EE216192C2007D6A6D /* TuskerNavigationDelegate.swift */,
D6F1F84E2193B9BE00F5FE67 /* Caching */, D6F1F84E2193B9BE00F5FE67 /* Caching */,
@ -1638,6 +1641,7 @@
D68FEC4F232C5BC300C84F23 /* SegmentedPageViewController.swift in Sources */, D68FEC4F232C5BC300C84F23 /* SegmentedPageViewController.swift in Sources */,
0450531F22B0097E00100BA2 /* Timline+UI.swift in Sources */, 0450531F22B0097E00100BA2 /* Timline+UI.swift in Sources */,
D667E5F52135BCD50057A976 /* ConversationTableViewController.swift in Sources */, D667E5F52135BCD50057A976 /* ConversationTableViewController.swift in Sources */,
D6945C3623AC6C09005C403C /* SavedInstancesManager.swift in Sources */,
D6C7D27D22B6EBF800071952 /* AttachmentsContainerView.swift in Sources */, D6C7D27D22B6EBF800071952 /* AttachmentsContainerView.swift in Sources */,
D620483823D38190008A63EF /* StatusContentTextView.swift in Sources */, D620483823D38190008A63EF /* StatusContentTextView.swift in Sources */,
D6F953F021251A2900CF0F2B /* MastodonController.swift in Sources */, D6F953F021251A2900CF0F2B /* MastodonController.swift in Sources */,
@ -1693,7 +1697,7 @@
0427033822B30F5F000D31B6 /* BehaviorPrefsView.swift in Sources */, 0427033822B30F5F000D31B6 /* BehaviorPrefsView.swift in Sources */,
D627943923A553B600D38C68 /* UnbookmarkStatusActivity.swift in Sources */, D627943923A553B600D38C68 /* UnbookmarkStatusActivity.swift in Sources */,
D64D0AAD2128D88B005A6F37 /* LocalData.swift in Sources */, D64D0AAD2128D88B005A6F37 /* LocalData.swift in Sources */,
D6945C2F23AC47C3005C403C /* SavedDataManager.swift in Sources */, D6945C2F23AC47C3005C403C /* SavedHashtagsManager.swift in Sources */,
D6C94D892139E6EC00CB5196 /* AttachmentView.swift in Sources */, D6C94D892139E6EC00CB5196 /* AttachmentView.swift in Sources */,
D6B053AE23BD322B00A066FA /* AssetPickerSheetContainerViewController.swift in Sources */, D6B053AE23BD322B00A066FA /* AssetPickerSheetContainerViewController.swift in Sources */,
D6C693EF216192C2007D6A6D /* TuskerNavigationDelegate.swift in Sources */, D6C693EF216192C2007D6A6D /* TuskerNavigationDelegate.swift in Sources */,

View File

@ -1,113 +0,0 @@
//
// SavedDataManager.swift
// Tusker
//
// Created by Shadowfacts on 12/19/19.
// Copyright © 2019 Shadowfacts. All rights reserved.
//
import Foundation
import Pachyderm
class SavedDataManager: Codable {
private(set) static var shared: SavedDataManager = load()
private static var documentsDirectory = FileManager.default.urls(for: .documentDirectory, in: .userDomainMask).first!
private static var archiveURL = SavedDataManager.documentsDirectory.appendingPathComponent("saved_data").appendingPathExtension("plist")
static func save() {
DispatchQueue.global(qos: .utility).async {
let encoder = PropertyListEncoder()
let data = try? encoder.encode(shared)
try? data?.write(to: archiveURL, options: .noFileProtection)
}
}
static func load() -> SavedDataManager {
let decoder = PropertyListDecoder()
if let data = try? Data(contentsOf: archiveURL),
let savedHashtagsManager = try? decoder.decode(Self.self, from: data) {
return savedHashtagsManager
}
return SavedDataManager()
}
private init() {}
private var savedHashtags: [String: [Hashtag]] = [:] {
didSet {
SavedDataManager.save()
NotificationCenter.default.post(name: .savedHashtagsChanged, object: nil)
}
}
private var savedInstances: [String: [URL]] = [:] {
didSet {
SavedDataManager.save()
NotificationCenter.default.post(name: .savedInstancesChanged, object: nil)
}
}
func sortedHashtags(for account: LocalData.UserAccountInfo) -> [Hashtag] {
if let hashtags = savedHashtags[account.id] {
return hashtags.sorted(by: { $0.name < $1.name })
} else {
return []
}
}
func isSaved(hashtag: Hashtag, for account: LocalData.UserAccountInfo) -> Bool {
return savedHashtags[account.id]?.contains(hashtag) ?? false
}
func add(hashtag: Hashtag, for account: LocalData.UserAccountInfo) {
if isSaved(hashtag: hashtag, for: account) {
return
}
if var saved = savedHashtags[account.id] {
saved.append(hashtag)
savedHashtags[account.id] = saved
} else {
savedHashtags[account.id] = [hashtag]
}
}
func remove(hashtag: Hashtag, for account: LocalData.UserAccountInfo) {
guard isSaved(hashtag: hashtag, for: account) else { return }
if var saved = savedHashtags[account.id] {
saved.removeAll(where: { $0.name == hashtag.name })
savedHashtags[account.id] = saved
}
}
func savedInstances(for account: LocalData.UserAccountInfo) -> [URL] {
return savedInstances[account.id] ?? []
}
func isSaved(instance url: URL, for account: LocalData.UserAccountInfo) -> Bool {
return savedInstances[account.id]?.contains(url) ?? false
}
func add(instance url: URL, for account: LocalData.UserAccountInfo) {
if isSaved(instance: url, for: account) { return }
if var saved = savedInstances[account.id] {
saved.append(url)
savedInstances[account.id] = saved
} else {
savedInstances[account.id] = [url]
}
}
func remove(instance url: URL, for account: LocalData.UserAccountInfo) {
guard isSaved(instance: url, for: account) else { return }
if var saved = savedInstances[account.id] {
saved.removeAll(where: { $0 == url })
savedInstances[account.id] = saved
}
}
}
extension Foundation.Notification.Name {
static let savedHashtagsChanged = Notification.Name("savedHashtagsChanged")
static let savedInstancesChanged = Notification.Name("savedInstancesChanged")
}

View File

@ -0,0 +1,65 @@
//
// SavedHashtagsManager.swift
// Tusker
//
// Created by Shadowfacts on 12/19/19.
// Copyright © 2019 Shadowfacts. All rights reserved.
//
import Foundation
import Pachyderm
class SavedHashtagsManager: Codable {
private(set) static var shared: SavedHashtagsManager = load()
private static var documentsDirectory = FileManager.default.urls(for: .documentDirectory, in: .userDomainMask).first!
private static var archiveURL = SavedHashtagsManager.documentsDirectory.appendingPathComponent("saved_hashtags").appendingPathExtension("plist")
static func save() {
DispatchQueue.global(qos: .utility).async {
let encoder = PropertyListEncoder()
let data = try? encoder.encode(shared)
try? data?.write(to: archiveURL, options: .noFileProtection)
}
}
static func load() -> SavedHashtagsManager {
let decoder = PropertyListDecoder()
if let data = try? Data(contentsOf: archiveURL),
let savedHashtagsManager = try? decoder.decode(Self.self, from: data) {
return savedHashtagsManager
}
return SavedHashtagsManager()
}
private init() {}
private var savedHashtags: [Hashtag] = []
var sorted: [Hashtag] {
return savedHashtags.sorted(by: { $0.name < $1.name })
}
func isSaved(_ hashtag: Hashtag) -> Bool {
return savedHashtags.contains(hashtag)
}
func add(_ hashtag: Hashtag) {
if isSaved(hashtag) {
return
}
savedHashtags.append(hashtag)
SavedHashtagsManager.save()
NotificationCenter.default.post(name: .savedHashtagsChanged, object: nil)
}
func remove(_ hashtag: Hashtag) {
guard isSaved(hashtag) else { return }
savedHashtags.removeAll(where: { $0.name == hashtag.name })
SavedHashtagsManager.save()
NotificationCenter.default.post(name: .savedHashtagsChanged, object: nil)
}
}
extension Foundation.Notification.Name {
static let savedHashtagsChanged = Notification.Name("savedHashtagsChanged")
}

View File

@ -0,0 +1,61 @@
//
// SavedInstancesManager.swift
// Tusker
//
// Created by Shadowfacts on 12/19/19.
// Copyright © 2019 Shadowfacts. All rights reserved.
//
import Foundation
class SavedInstanceManager: Codable {
private(set) static var shared: SavedInstanceManager = load()
private static var documentsDirectory = FileManager.default.urls(for: .documentDirectory, in: .userDomainMask).first!
private static var archiveURL = SavedInstanceManager.documentsDirectory.appendingPathComponent("saved_instances").appendingPathExtension("plist")
static func save() {
DispatchQueue.global(qos: .utility).async {
let encoder = PropertyListEncoder()
let data = try? encoder.encode(shared)
try? data?.write(to: archiveURL, options: .noFileProtection)
}
}
static func load() -> SavedInstanceManager {
let decoder = PropertyListDecoder()
if let data = try? Data(contentsOf: archiveURL),
let savedInstanceManager = try? decoder.decode(Self.self, from: data) {
return savedInstanceManager
}
return SavedInstanceManager()
}
private init() {}
private(set) var savedInstances: [URL] = []
func isSaved(_ url: URL) -> Bool {
return savedInstances.contains(url)
}
func add(_ url: URL) {
if isSaved(url) {
return
}
savedInstances.append(url)
SavedInstanceManager.save()
NotificationCenter.default.post(name: .savedInstancesChanged, object: nil)
}
func remove(_ url: URL) {
guard isSaved(url) else { return }
savedInstances.removeAll(where: { $0 == url })
SavedInstanceManager.save()
NotificationCenter.default.post(name: .savedInstancesChanged, object: nil)
}
}
extension Notification.Name {
static let savedInstancesChanged = Notification.Name("savedInstancesChanged")
}

View File

@ -52,7 +52,7 @@ class AddSavedHashtagViewController: SearchResultsViewController {
extension AddSavedHashtagViewController: SearchResultsViewControllerDelegate { extension AddSavedHashtagViewController: SearchResultsViewControllerDelegate {
func selectedSearchResult(hashtag: Hashtag) { func selectedSearchResult(hashtag: Hashtag) {
SavedDataManager.shared.add(hashtag: hashtag, for: mastodonController.accountInfo!) SavedHashtagsManager.shared.add(hashtag)
dismiss(animated: true) dismiss(animated: true)
} }
} }

View File

@ -81,14 +81,12 @@ class ExploreViewController: EnhancedTableViewController {
}) })
dataSource.exploreController = self dataSource.exploreController = self
let account = mastodonController.accountInfo!
var snapshot = NSDiffableDataSourceSnapshot<Section, Item>() var snapshot = NSDiffableDataSourceSnapshot<Section, Item>()
snapshot.appendSections([.bookmarks, .lists, .savedHashtags, .savedInstances]) snapshot.appendSections([.bookmarks, .lists, .savedHashtags, .savedInstances])
snapshot.appendItems([.bookmarks], toSection: .bookmarks) snapshot.appendItems([.bookmarks], toSection: .bookmarks)
snapshot.appendItems([.addList], toSection: .lists) snapshot.appendItems([.addList], toSection: .lists)
snapshot.appendItems(SavedDataManager.shared.sortedHashtags(for: account).map { .savedHashtag($0) } + [.addSavedHashtag], toSection: .savedHashtags) snapshot.appendItems(SavedHashtagsManager.shared.sorted.map { .savedHashtag($0) } + [.addSavedHashtag], toSection: .savedHashtags)
snapshot.appendItems(SavedDataManager.shared.savedInstances(for: account).map { .savedInstance($0) } + [.findInstance], toSection: .savedInstances) snapshot.appendItems(SavedInstanceManager.shared.savedInstances.map { .savedInstance($0) } + [.findInstance], toSection: .savedInstances)
// the initial, static items should not be displayed with an animation // the initial, static items should not be displayed with an animation
UIView.performWithoutAnimation { UIView.performWithoutAnimation {
dataSource.apply(snapshot) dataSource.apply(snapshot)
@ -129,18 +127,16 @@ class ExploreViewController: EnhancedTableViewController {
} }
@objc func savedHashtagsChanged() { @objc func savedHashtagsChanged() {
let account = mastodonController.accountInfo!
var snapshot = dataSource.snapshot() var snapshot = dataSource.snapshot()
snapshot.deleteItems(snapshot.itemIdentifiers(inSection: .savedHashtags)) snapshot.deleteItems(snapshot.itemIdentifiers(inSection: .savedHashtags))
snapshot.appendItems(SavedDataManager.shared.sortedHashtags(for: account).map { .savedHashtag($0) } + [.addSavedHashtag], toSection: .savedHashtags) snapshot.appendItems(SavedHashtagsManager.shared.sorted.map { .savedHashtag($0) } + [.addSavedHashtag], toSection: .savedHashtags)
dataSource.apply(snapshot) dataSource.apply(snapshot)
} }
@objc func savedInstancesChanged() { @objc func savedInstancesChanged() {
let account = mastodonController.accountInfo!
var snapshot = dataSource.snapshot() var snapshot = dataSource.snapshot()
snapshot.deleteItems(snapshot.itemIdentifiers(inSection: .savedInstances)) snapshot.deleteItems(snapshot.itemIdentifiers(inSection: .savedInstances))
snapshot.appendItems(SavedDataManager.shared.savedInstances(for: account).map { .savedInstance($0) } + [.findInstance], toSection: .savedInstances) snapshot.appendItems(SavedInstanceManager.shared.savedInstances.map { .savedInstance($0) } + [.findInstance], toSection: .savedInstances)
dataSource.apply(snapshot) dataSource.apply(snapshot)
} }
@ -167,13 +163,11 @@ class ExploreViewController: EnhancedTableViewController {
} }
func removeSavedHashtag(_ hashtag: Hashtag) { func removeSavedHashtag(_ hashtag: Hashtag) {
let account = mastodonController.accountInfo! SavedHashtagsManager.shared.remove(hashtag)
SavedDataManager.shared.remove(hashtag: hashtag, for: account)
} }
func removeSavedInstance(_ instanceURL: URL) { func removeSavedInstance(_ instanceURL: URL) {
let account = mastodonController.accountInfo! SavedInstanceManager.shared.remove(instanceURL)
SavedDataManager.shared.remove(instance: instanceURL, for: account)
} }
// MARK: - Table view delegate // MARK: - Table view delegate
@ -223,11 +217,11 @@ class ExploreViewController: EnhancedTableViewController {
present(navController, animated: true) present(navController, animated: true)
case let .savedInstance(url): case let .savedInstance(url):
show(InstanceTimelineViewController(for: url, parentMastodonController: mastodonController), sender: nil) show(InstanceTimelineViewController(for: url), sender: nil)
case .findInstance: case .findInstance:
tableView.selectRow(at: nil, animated: true, scrollPosition: .none) tableView.selectRow(at: nil, animated: true, scrollPosition: .none)
let findController = FindInstanceViewController(parentMastodonController: mastodonController) let findController = FindInstanceViewController()
findController.instanceTimelineDelegate = self findController.instanceTimelineDelegate = self
let navController = UINavigationController(rootViewController: findController) let navController = UINavigationController(rootViewController: findController)
present(navController, animated: true) present(navController, animated: true)
@ -354,7 +348,7 @@ extension ExploreViewController {
extension ExploreViewController: InstanceTimelineViewControllerDelegate { extension ExploreViewController: InstanceTimelineViewControllerDelegate {
func didSaveInstance(url: URL) { func didSaveInstance(url: URL) {
dismiss(animated: true) { dismiss(animated: true) {
self.show(InstanceTimelineViewController(for: url, parentMastodonController: self.mastodonController), sender: nil) self.show(InstanceTimelineViewController(for: url), sender: nil)
} }
} }

View File

@ -10,20 +10,8 @@ import UIKit
class FindInstanceViewController: InstanceSelectorTableViewController { class FindInstanceViewController: InstanceSelectorTableViewController {
weak var parentMastodonController: MastodonController?
var instanceTimelineDelegate: InstanceTimelineViewControllerDelegate? var instanceTimelineDelegate: InstanceTimelineViewControllerDelegate?
init(parentMastodonController: MastodonController) {
self.parentMastodonController = parentMastodonController
super.init()
}
required init?(coder: NSCoder) {
fatalError("init(coder:) has not been implemented")
}
override func viewDidLoad() { override func viewDidLoad() {
super.viewDidLoad() super.viewDidLoad()
@ -44,7 +32,7 @@ class FindInstanceViewController: InstanceSelectorTableViewController {
extension FindInstanceViewController: InstanceSelectorTableViewControllerDelegate { extension FindInstanceViewController: InstanceSelectorTableViewControllerDelegate {
func didSelectInstance(url: URL) { func didSelectInstance(url: URL) {
let instanceTimelineController = InstanceTimelineViewController(for: url, parentMastodonController: parentMastodonController!) let instanceTimelineController = InstanceTimelineViewController(for: url)
instanceTimelineController.delegate = instanceTimelineDelegate instanceTimelineController.delegate = instanceTimelineDelegate
show(instanceTimelineController, sender: self) show(instanceTimelineController, sender: self)
} }

View File

@ -55,7 +55,7 @@ class InstanceSelectorTableViewController: UITableViewController {
tableView.rowHeight = UITableView.automaticDimension tableView.rowHeight = UITableView.automaticDimension
tableView.estimatedRowHeight = 120 tableView.estimatedRowHeight = 120
dataSource = DataSource(tableView: tableView, cellProvider: { (tableView, indexPath, item) -> UITableViewCell? in dataSource = DataSource(tableView: tableView, cellProvider: { [weak self] (tableView, indexPath, item) -> UITableViewCell? in
switch item { switch item {
case let .selected(instance): case let .selected(instance):
let cell = tableView.dequeueReusableCell(withIdentifier: instanceCell, for: indexPath) as! InstanceTableViewCell let cell = tableView.dequeueReusableCell(withIdentifier: instanceCell, for: indexPath) as! InstanceTableViewCell

View File

@ -15,7 +15,7 @@ class HashtagTimelineViewController: TimelineTableViewController {
var toggleSaveButton: UIBarButtonItem! var toggleSaveButton: UIBarButtonItem!
var toggleSaveButtonTitle: String { var toggleSaveButtonTitle: String {
if SavedDataManager.shared.isSaved(hashtag: hashtag, for: mastodonController.accountInfo!) { if SavedHashtagsManager.shared.isSaved(hashtag) {
return NSLocalizedString("Unsave", comment: "unsave hashtag button") return NSLocalizedString("Unsave", comment: "unsave hashtag button")
} else { } else {
return NSLocalizedString("Save", comment: "save hashtag button") return NSLocalizedString("Save", comment: "save hashtag button")
@ -48,10 +48,10 @@ class HashtagTimelineViewController: TimelineTableViewController {
// MARK: - Interaction // MARK: - Interaction
@objc func toggleSaveButtonPressed() { @objc func toggleSaveButtonPressed() {
if SavedDataManager.shared.isSaved(hashtag: hashtag, for: mastodonController.accountInfo!) { if SavedHashtagsManager.shared.isSaved(hashtag) {
SavedDataManager.shared.remove(hashtag: hashtag, for: mastodonController.accountInfo!) SavedHashtagsManager.shared.remove(hashtag)
} else { } else {
SavedDataManager.shared.add(hashtag: hashtag, for: mastodonController.accountInfo!) SavedHashtagsManager.shared.add(hashtag)
} }
} }

View File

@ -17,29 +17,23 @@ class InstanceTimelineViewController: TimelineTableViewController {
weak var delegate: InstanceTimelineViewControllerDelegate? weak var delegate: InstanceTimelineViewControllerDelegate?
weak var parentMastodonController: MastodonController?
let instanceURL: URL let instanceURL: URL
let instanceMastodonController: MastodonController
var toggleSaveButton: UIBarButtonItem! var toggleSaveButton: UIBarButtonItem!
var toggleSaveButtonTitle: String { var toggleSaveButtonTitle: String {
if SavedDataManager.shared.isSaved(instance: instanceURL, for: parentMastodonController!.accountInfo!) { if SavedInstanceManager.shared.isSaved(instanceURL) {
return NSLocalizedString("Unsave", comment: "unsave instance button") return NSLocalizedString("Unsave", comment: "unsave instance button")
} else { } else {
return NSLocalizedString("Save", comment: "save instance button") return NSLocalizedString("Save", comment: "save instance button")
} }
} }
init(for url: URL, parentMastodonController: MastodonController) { init(for url: URL) {
self.parentMastodonController = parentMastodonController
self.instanceURL = url self.instanceURL = url
let mastodonController = MastodonController(instanceURL: url)
// the timeline VC only stores a weak reference to it, so we need to store a strong reference to make sure it's not released immediately super.init(for: .instance(instanceURL: url), mastodonController: mastodonController)
instanceMastodonController = MastodonController(instanceURL: url)
super.init(for: .instance(instanceURL: url), mastodonController: instanceMastodonController)
} }
required init?(coder aDecoder: NSCoder) { required init?(coder aDecoder: NSCoder) {
@ -76,11 +70,11 @@ class InstanceTimelineViewController: TimelineTableViewController {
// MARK: - Interaction // MARK: - Interaction
@objc func toggleSaveButtonPressed() { @objc func toggleSaveButtonPressed() {
if SavedDataManager.shared.isSaved(instance: instanceURL, for: parentMastodonController!.accountInfo!) { if SavedInstanceManager.shared.isSaved(instanceURL) {
SavedDataManager.shared.remove(instance: instanceURL, for: parentMastodonController!.accountInfo!) SavedInstanceManager.shared.remove(instanceURL)
delegate?.didUnsaveInstance(url: instanceURL) delegate?.didUnsaveInstance(url: instanceURL)
} else { } else {
SavedDataManager.shared.add(instance: instanceURL, for: parentMastodonController!.accountInfo!) SavedInstanceManager.shared.add(instanceURL)
delegate?.didSaveInstance(url: instanceURL) delegate?.didSaveInstance(url: instanceURL)
} }
} }