2017-07-03 19:29:44 +02:00
|
|
|
//
|
|
|
|
// Container.swift
|
|
|
|
// Evergreen
|
|
|
|
//
|
|
|
|
// Created by Brent Simmons on 4/17/16.
|
|
|
|
// Copyright © 2016 Ranchero Software, LLC. All rights reserved.
|
|
|
|
//
|
|
|
|
|
|
|
|
import Foundation
|
|
|
|
import RSCore
|
2017-09-17 21:08:50 +02:00
|
|
|
import Data
|
2017-07-03 19:29:44 +02:00
|
|
|
|
|
|
|
public typealias VisitBlock = (_ obj: AnyObject) -> Bool // Return true to stop
|
|
|
|
|
|
|
|
extension NSNotification.Name {
|
|
|
|
|
|
|
|
public static let ChildrenDidChange = Notification.Name("ChildrenDidChangeNotification")
|
|
|
|
}
|
|
|
|
|
2017-09-17 21:08:50 +02:00
|
|
|
public protocol Container {
|
2017-07-03 19:29:44 +02:00
|
|
|
|
|
|
|
//Recursive
|
|
|
|
func hasAtLeastOneFeed() -> Bool
|
|
|
|
func flattenedFeeds() -> Set<Feed>
|
|
|
|
func existingFeed(with feedID: String) -> Feed?
|
|
|
|
func existingFeed(withURL url: String) -> Feed?
|
|
|
|
|
|
|
|
func isChild(_ obj: AnyObject) -> Bool
|
|
|
|
|
|
|
|
// visitBlock should return true to stop visiting.
|
|
|
|
// visitObjects returns true if a visitBlock returned true.
|
|
|
|
func visitObjects(_ recurse: Bool, _ visitBlock: VisitBlock) -> Bool
|
|
|
|
}
|
|
|
|
|
|
|
|
public extension Container {
|
|
|
|
|
|
|
|
func hasAtLeastOneFeed() -> Bool {
|
|
|
|
|
|
|
|
let foundObject = findObject(true, visitBlock: { (oneDescendant) -> Bool in
|
|
|
|
return oneDescendant is Feed
|
|
|
|
})
|
|
|
|
return foundObject != nil
|
|
|
|
}
|
|
|
|
|
|
|
|
func existingFeed(with feedID: String) -> Feed? {
|
|
|
|
|
|
|
|
let foundObject = findObject(true) { (oneDescendant) -> Bool in
|
|
|
|
if let oneFeed = oneDescendant as? Feed, oneFeed.feedID == feedID {
|
|
|
|
return true
|
|
|
|
}
|
|
|
|
return false
|
|
|
|
}
|
|
|
|
return foundObject as! Feed?
|
|
|
|
}
|
|
|
|
|
|
|
|
func existingFeed(withURL url: String) -> Feed? {
|
|
|
|
|
|
|
|
let foundObject = findObject(true) { (oneDescendant) -> Bool in
|
|
|
|
if let oneFeed = oneDescendant as? Feed, oneFeed.url == url {
|
|
|
|
return true
|
|
|
|
}
|
|
|
|
return false
|
|
|
|
}
|
|
|
|
return foundObject as! Feed?
|
|
|
|
}
|
|
|
|
|
|
|
|
func visitChildren(visitBlock: VisitBlock) -> Bool {
|
|
|
|
|
|
|
|
return visitObjects(false, visitBlock)
|
|
|
|
}
|
|
|
|
|
|
|
|
func findObject(_ recurse: Bool, visitBlock: @escaping VisitBlock) -> AnyObject? {
|
|
|
|
|
|
|
|
var foundObject: AnyObject?
|
|
|
|
|
|
|
|
let _ = visitObjects(recurse) { (oneObject) in
|
|
|
|
|
|
|
|
if let _ = foundObject {
|
|
|
|
return true
|
|
|
|
}
|
|
|
|
|
|
|
|
if visitBlock(oneObject) {
|
|
|
|
foundObject = oneObject
|
|
|
|
return true
|
|
|
|
}
|
|
|
|
|
|
|
|
return false
|
|
|
|
}
|
|
|
|
|
|
|
|
return foundObject
|
|
|
|
}
|
|
|
|
|
|
|
|
func objectIsChild(_ obj: AnyObject) -> Bool {
|
|
|
|
|
|
|
|
return visitObjects(false) { (oneObject) in
|
|
|
|
return obj === oneObject
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
func objectIsDescendant(_ obj: AnyObject) -> Bool {
|
|
|
|
|
|
|
|
return visitObjects(true) { (oneObject) in
|
|
|
|
return obj === oneObject
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
func existingFolderWithName(_ name: String) -> Folder? {
|
|
|
|
|
|
|
|
let foundObject = findObject(false) { (oneObject) in
|
|
|
|
if let oneFolder = oneObject as? Folder, oneFolder.nameForDisplay == name {
|
|
|
|
return true
|
|
|
|
}
|
|
|
|
return false
|
|
|
|
}
|
|
|
|
return foundObject as! Folder?
|
|
|
|
}
|
|
|
|
|
|
|
|
public func postChildrenDidChangeNotification() {
|
|
|
|
|
|
|
|
NotificationCenter.default.post(name: .ChildrenDidChange, object: self)
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|