NetNewsWire/Mac/Inspector/FeedInspectorViewController...

223 lines
6.5 KiB
Swift
Raw Normal View History

//
// FeedInspectorViewController.swift
2018-08-29 07:18:24 +02:00
// NetNewsWire
//
// Created by Brent Simmons on 1/20/18.
// Copyright © 2018 Ranchero Software. All rights reserved.
//
import AppKit
import Articles
import Account
2020-08-01 17:50:57 +02:00
import UserNotifications
2024-03-20 07:05:30 +01:00
@MainActor final class FeedInspectorViewController: NSViewController, Inspector {
@IBOutlet weak var iconView: IconView!
@IBOutlet weak var nameTextField: NSTextField?
@IBOutlet weak var homePageURLTextField: NSTextField?
@IBOutlet weak var urlTextField: NSTextField?
@IBOutlet weak var isNotifyAboutNewArticlesCheckBox: NSButton!
@IBOutlet weak var isReaderViewAlwaysOnCheckBox: NSButton?
2024-02-26 06:41:18 +01:00
private var feed: Feed? {
2018-01-22 06:01:18 +01:00
didSet {
2018-01-22 06:24:25 +01:00
if feed != oldValue {
updateUI()
}
2018-01-22 06:01:18 +01:00
}
}
2020-08-01 17:50:57 +02:00
private var userNotificationSettings: UNNotificationSettings?
2018-01-22 06:01:18 +01:00
// MARK: Inspector
2018-01-21 07:36:17 +01:00
let isFallbackInspector = false
var objects: [Any]? {
didSet {
renameFeedIfNecessary()
2018-01-22 06:01:18 +01:00
updateFeed()
}
}
var windowTitle: String = NSLocalizedString("Feed Inspector", comment: "Feed Inspector window title")
2018-01-21 07:36:17 +01:00
func canInspect(_ objects: [Any]) -> Bool {
2024-02-26 06:41:18 +01:00
return objects.count == 1 && objects.first is Feed
2018-01-21 07:36:17 +01:00
}
2018-01-22 06:01:18 +01:00
// MARK: NSViewController
override func viewDidLoad() {
updateUI()
NotificationCenter.default.addObserver(self, selector: #selector(imageDidBecomeAvailable(_:)), name: .ImageDidBecomeAvailable, object: nil)
NotificationCenter.default.addObserver(self, selector: #selector(updateUI), name: .DidUpdateFeedPreferencesFromContextMenu, object: nil)
2018-01-22 06:01:18 +01:00
}
override func viewDidAppear() {
updateNotificationSettings()
}
override func viewDidDisappear() {
renameFeedIfNecessary()
}
// MARK: Actions
@IBAction func isNotifyAboutNewArticlesChanged(_ sender: Any) {
guard userNotificationSettings != nil else {
DispatchQueue.main.async {
self.isNotifyAboutNewArticlesCheckBox.setNextState()
}
return
}
UNUserNotificationCenter.current().getNotificationSettings { (settings) in
self.updateNotificationSettings()
if settings.authorizationStatus == .denied {
DispatchQueue.main.async {
self.isNotifyAboutNewArticlesCheckBox.setNextState()
self.showNotificationsDeniedError()
}
} else if settings.authorizationStatus == .authorized {
DispatchQueue.main.async {
self.feed?.isNotifyAboutNewArticles = (self.isNotifyAboutNewArticlesCheckBox?.state ?? .off) == .on ? true : false
}
} else {
UNUserNotificationCenter.current().requestAuthorization(options: [.badge, .sound, .alert]) { (granted, error) in
self.updateNotificationSettings()
if granted {
DispatchQueue.main.async {
self.feed?.isNotifyAboutNewArticles = (self.isNotifyAboutNewArticlesCheckBox?.state ?? .off) == .on ? true : false
NSApplication.shared.registerForRemoteNotifications()
}
} else {
DispatchQueue.main.async {
self.isNotifyAboutNewArticlesCheckBox.setNextState()
}
}
}
}
}
}
@IBAction func isReaderViewAlwaysOnChanged(_ sender: Any) {
feed?.isArticleExtractorAlwaysOn = (isReaderViewAlwaysOnCheckBox?.state ?? .off) == .on ? true : false
}
2018-01-22 06:01:18 +01:00
// MARK: Notifications
@objc func imageDidBecomeAvailable(_ note: Notification) {
updateImage()
}
}
extension FeedInspectorViewController: NSTextFieldDelegate {
func controlTextDidEndEditing(_ note: Notification) {
renameFeedIfNecessary()
}
}
private extension FeedInspectorViewController {
2018-01-22 06:01:18 +01:00
func updateFeed() {
2024-02-26 06:41:18 +01:00
guard let objects = objects, objects.count == 1, let singleFeed = objects.first as? Feed else {
2018-01-22 06:01:18 +01:00
feed = nil
return
}
2018-01-22 06:01:18 +01:00
feed = singleFeed
}
@objc func updateUI() {
2018-01-22 06:01:18 +01:00
updateImage()
updateName()
updateHomePageURL()
updateFeedURL()
updateNotifyAboutNewArticles()
updateIsReaderViewAlwaysOn()
windowTitle = feed?.nameForDisplay ?? NSLocalizedString("Feed Inspector", comment: "Feed Inspector window title")
2023-06-26 01:15:21 +02:00
isReaderViewAlwaysOnCheckBox?.isEnabled = true
2018-01-22 06:01:18 +01:00
view.needsLayout = true
}
2018-01-22 06:01:18 +01:00
func updateImage() {
guard let feed = feed, let iconView = iconView else {
2018-01-22 06:01:18 +01:00
return
}
iconView.iconImage = IconImageCache.shared.imageForFeed(feed)
}
2018-01-22 06:01:18 +01:00
func updateName() {
guard let nameTextField = nameTextField else {
return
}
let name = feed?.editedName ?? feed?.name ?? ""
if nameTextField.stringValue != name {
nameTextField.stringValue = name
}
}
2018-01-22 06:01:18 +01:00
func updateHomePageURL() {
2020-07-06 17:06:12 +02:00
homePageURLTextField?.stringValue = feed?.homePageURL?.decodedURLString ?? ""
}
2018-01-22 06:01:18 +01:00
func updateFeedURL() {
2020-07-06 17:06:12 +02:00
urlTextField?.stringValue = feed?.url.decodedURLString ?? ""
2018-01-21 07:36:17 +01:00
}
func updateNotifyAboutNewArticles() {
2021-04-19 05:21:00 +02:00
isNotifyAboutNewArticlesCheckBox?.title = feed?.notificationDisplayName ?? NSLocalizedString("Show notifications for new articles", comment: "Show notifications for new articles")
isNotifyAboutNewArticlesCheckBox?.state = (feed?.isNotifyAboutNewArticles ?? false) ? .on : .off
}
func updateIsReaderViewAlwaysOn() {
isReaderViewAlwaysOnCheckBox?.state = (feed?.isArticleExtractorAlwaysOn ?? false) ? .on : .off
}
func updateNotificationSettings() {
UNUserNotificationCenter.current().getNotificationSettings { (settings) in
self.userNotificationSettings = settings
if settings.authorizationStatus == .authorized {
DispatchQueue.main.async {
NSApplication.shared.registerForRemoteNotifications()
}
}
}
}
func showNotificationsDeniedError() {
let updateAlert = NSAlert()
updateAlert.alertStyle = .informational
updateAlert.messageText = NSLocalizedString("Enable Notifications", comment: "Notifications")
updateAlert.informativeText = NSLocalizedString("To enable notifications, open Notifications in System Preferences, then find NetNewsWire in the list.", comment: "To enable notifications, open Notifications in System Preferences, then find NetNewsWire in the list.")
updateAlert.addButton(withTitle: NSLocalizedString("Open System Preferences", comment: "Open System Preferences"))
updateAlert.addButton(withTitle: NSLocalizedString("Close", comment: "Close"))
let modalResponse = updateAlert.runModal()
if modalResponse == .alertFirstButtonReturn {
NSWorkspace.shared.open(URL(string: "x-apple.systempreferences:com.apple.preference.notifications")!)
}
}
func renameFeedIfNecessary() {
guard let feed = feed,
let account = feed.account,
let nameTextField = nameTextField,
feed.nameForDisplay != nameTextField.stringValue else {
return
}
account.renameFeed(feed, to: nameTextField.stringValue) { [weak self] result in
if case .failure(let error) = result {
self?.presentError(error)
} else {
self?.windowTitle = feed.nameForDisplay
}
}
}
2018-01-21 06:35:59 +01:00
}