From 14bec27dab5431907c865690649c9449b8025d06 Mon Sep 17 00:00:00 2001 From: Kevin Delord Date: Tue, 28 Mar 2017 17:34:05 +0200 Subject: [PATCH 001/110] Storyboard example now full screen. Update podfile --- .../xcshareddata/xcschemes/Example.xcscheme | 7 +++++++ Example/Podfile.lock | 2 +- .../Base.lproj/Main.storyboard | 18 +++++++++++------- 3 files changed, 19 insertions(+), 8 deletions(-) diff --git a/Example/Example.xcodeproj/xcshareddata/xcschemes/Example.xcscheme b/Example/Example.xcodeproj/xcshareddata/xcschemes/Example.xcscheme index d78b6713e..949d39375 100644 --- a/Example/Example.xcodeproj/xcshareddata/xcschemes/Example.xcscheme +++ b/Example/Example.xcodeproj/xcshareddata/xcschemes/Example.xcscheme @@ -71,6 +71,13 @@ ReferencedContainer = "container:Example.xcodeproj"> + + + + diff --git a/Example/Podfile.lock b/Example/Podfile.lock index e80456442..dd8730030 100644 --- a/Example/Podfile.lock +++ b/Example/Podfile.lock @@ -45,4 +45,4 @@ SPEC CHECKSUMS: PODFILE CHECKSUM: 591559c46a2b0a49e687795b8ae46fadbddf8fd4 -COCOAPODS: 1.1.1 +COCOAPODS: 1.2.0 diff --git a/Example/StoryboardExample/Base.lproj/Main.storyboard b/Example/StoryboardExample/Base.lproj/Main.storyboard index f9cff5f1a..1e83f1ce9 100644 --- a/Example/StoryboardExample/Base.lproj/Main.storyboard +++ b/Example/StoryboardExample/Base.lproj/Main.storyboard @@ -1,8 +1,11 @@ - - + + + + + - + @@ -20,6 +23,7 @@ + @@ -29,12 +33,12 @@ - + - + - + @@ -67,7 +71,7 @@ - + From 1b8f38944e22ca4e2e142cb5c010b21ee7491e28 Mon Sep 17 00:00:00 2001 From: Kevin Delord Date: Tue, 28 Mar 2017 17:34:14 +0200 Subject: [PATCH 002/110] Update gitignore --- .gitignore | 49 +++++++++++++++++++++++++++++++++++++++++++------ 1 file changed, 43 insertions(+), 6 deletions(-) diff --git a/.gitignore b/.gitignore index 48fa0839c..63004da4f 100644 --- a/.gitignore +++ b/.gitignore @@ -1,6 +1,12 @@ # Xcode # +# gitignore contributors: remember to update Global/Xcode.gitignore, Objective-C.gitignore & Swift.gitignore + +## Build generated build/ +DerivedData/ + +## Various settings *.pbxuser !default.pbxuser *.mode1v3 @@ -9,25 +15,56 @@ build/ !default.mode2v3 *.perspectivev3 !default.perspectivev3 -xcuserdata -*.xccheckout +xcuserdata/ + +## Other *.moved-aside -DerivedData +*.xcuserstate +*.DS_Store + +## SMF Specific +.swiftlint.yml + +## Obj-C/Swift specific *.hmap *.ipa -*.xcuserstate +*.dSYM.zip +*.dSYM + +## Playgrounds +timeline.xctimeline +playground.xcworkspace + +# Swift Package Manager +# +# Add this line if you want to avoid checking in source code from Swift Package Manager dependencies. +# Packages/ +.build/ # CocoaPods # # We recommend against adding the Pods directory to your .gitignore. However # you should judge for yourself, the pros and cons are mentioned at: -# http://guides.cocoapods.org/using/using-cocoapods.html#should-i-ignore-the-pods-directory-in-source-control +# https://guides.cocoapods.org/using/using-cocoapods.html#should-i-check-the-pods-directory-into-source-control # Pods/ +Example/Pods/ # Carthage # # Add this line if you want to avoid checking in source code from Carthage dependencies. -Carthage/Checkouts +# Carthage/Checkouts Carthage/Build + +# fastlane +# +# It is recommended to not store the screenshots in the git repo. Instead, use fastlane to re-generate the +# screenshots whenever they are needed. +# For more information about the recommended setup visit: +# https://github.com/fastlane/fastlane/blob/master/fastlane/docs/Gitignore.md + +fastlane/report.xml +fastlane/Preview.html +fastlane/screenshots +fastlane/test_output From 9bbe04f1a7dcc8d9e654a2b48239955b9eb679e4 Mon Sep 17 00:00:00 2001 From: Kevin Delord Date: Tue, 28 Mar 2017 18:46:23 +0200 Subject: [PATCH 003/110] Add TODOs and replace the shared instance in the FolioReaderKit class --- Example/Example/ViewController.swift | 3 +- Source/FolioReaderAudioPlayer.swift | 4 +- Source/FolioReaderContainer.swift | 86 +++++----- Source/FolioReaderKit.swift | 241 ++++++++++++++++++++------- Source/Models/Highlight+Helper.swift | 49 +++--- Source/Models/Highlight.swift | 2 + 6 files changed, 254 insertions(+), 131 deletions(-) diff --git a/Example/Example/ViewController.swift b/Example/Example/ViewController.swift index fda2fbd06..582682401 100755 --- a/Example/Example/ViewController.swift +++ b/Example/Example/ViewController.swift @@ -13,6 +13,7 @@ class ViewController: UIViewController { @IBOutlet var bookOne: UIButton! @IBOutlet var bookTwo: UIButton! + let epubSampleFiles = [ "The Silver Chair", // standard eBook "The Adventures Of Sherlock Holmes - Adventure I", // audio-eBook @@ -55,7 +56,7 @@ class ViewController: UIViewController { // Epub file let epubName = epubSampleFiles[sampleNum-1]; let bookPath = Bundle.main.path(forResource: epubName, ofType: "epub") - FolioReader.presentReader(parentViewController: self, withEpubPath: bookPath!, andConfig: config, shouldRemoveEpub: false) + _ = FolioReader.presentReader(parentViewController: self, withEpubPath: bookPath!, andConfig: config, shouldRemoveEpub: false) } func setCover(_ button: UIButton, index: Int) { diff --git a/Source/FolioReaderAudioPlayer.swift b/Source/FolioReaderAudioPlayer.swift index 4412a0614..a9ca572b1 100644 --- a/Source/FolioReaderAudioPlayer.swift +++ b/Source/FolioReaderAudioPlayer.swift @@ -34,8 +34,8 @@ open class FolioReaderAudioPlayer: NSObject { // this is needed to the audio can play even when the "silent/vibrate" toggle is on let session:AVAudioSession = AVAudioSession.sharedInstance() - try! session.setCategory(AVAudioSessionCategoryPlayback) - try! session.setActive(true) + try? session.setCategory(AVAudioSessionCategoryPlayback) + try? session.setActive(true) updateNowPlayingInfo() } diff --git a/Source/FolioReaderContainer.swift b/Source/FolioReaderContainer.swift index 4999b0916..c1aaef0e7 100755 --- a/Source/FolioReaderContainer.swift +++ b/Source/FolioReaderContainer.swift @@ -9,18 +9,23 @@ import UIKit import FontBlaster +// TODO_SMF: remove static variables var readerConfig: FolioReaderConfig! var book: FRBook! /// Reader container -open class FolioReaderContainer: UIViewController { - var centerNavigationController: UINavigationController! - var centerViewController: FolioReaderCenter! - var audioPlayer: FolioReaderAudioPlayer! - var shouldHideStatusBar = true - var shouldRemoveEpub = true - var epubPath: String! - fileprivate var errorOnLoad = false +open class FolioReaderContainer : UIViewController { + + // TODO_SMF: remove `!` + var centerNavigationController : UINavigationController! + var centerViewController : FolioReaderCenter! + var audioPlayer : FolioReaderAudioPlayer? + var shouldHideStatusBar = true + var shouldRemoveEpub = true + var epubPath : String! + + fileprivate var folioReader : FolioReader? + fileprivate var errorOnLoad = false // MARK: - Init @@ -33,28 +38,27 @@ open class FolioReaderContainer: UIViewController { - returns: `self`, initialized using the `FolioReaderConfig`. */ - public init(withConfig config: FolioReaderConfig, epubPath path: String, removeEpub: Bool = true) { + public init(withConfig config: FolioReaderConfig, folioReader: FolioReader, epubPath path: String, removeEpub: Bool = true) { super.init(nibName: nil, bundle: Bundle.frameworkBundle()) readerConfig = config - epubPath = path - shouldRemoveEpub = removeEpub + self.folioReader = folioReader + self.epubPath = path + self.shouldRemoveEpub = removeEpub - initialization() + self.initialization() } required public init?(coder aDecoder: NSCoder) { super.init(coder: aDecoder) - initialization() + self.initialization() } /** Common Initialization */ fileprivate func initialization() { - FolioReader.shared.readerContainer = self - book = FRBook() // Register custom fonts @@ -70,7 +74,7 @@ open class FolioReaderContainer: UIViewController { kCurrentTOCMenu: 0, kCurrentMediaOverlayStyle: MediaOverlayStyle.default.rawValue, kCurrentScrollDirection: FolioReaderScrollDirection.defaultVertical.rawValue - ]) + ]) } /** @@ -80,10 +84,11 @@ open class FolioReaderContainer: UIViewController { - parameter path: The ePub path on system - parameter removeEpub: Should delete the original file after unzip? Default to `true` so the ePub will be unziped only once. */ - open func setupConfig(_ config: FolioReaderConfig, epubPath path: String, removeEpub: Bool = true) { + open func setupConfig(_ config: FolioReaderConfig, folioReader: FolioReader, epubPath path: String, removeEpub: Bool = true) { readerConfig = config - epubPath = path - shouldRemoveEpub = removeEpub + self.folioReader = folioReader + self.epubPath = path + self.shouldRemoveEpub = removeEpub } // MARK: - View life cicle @@ -95,7 +100,7 @@ open class FolioReaderContainer: UIViewController { // If user can change scroll direction use the last saved if readerConfig.canChangeScrollDirection { - var scrollDirection = FolioReaderScrollDirection(rawValue: FolioReader.currentScrollDirection) ?? .vertical + var scrollDirection = (FolioReaderScrollDirection(rawValue: (self.folioReader?.currentScrollDirection ?? 0)) ?? .vertical) if (scrollDirection == .defaultVertical && readerConfig.scrollDirection != .defaultVertical) { scrollDirection = readerConfig.scrollDirection @@ -106,14 +111,14 @@ open class FolioReaderContainer: UIViewController { readerConfig.shouldHideNavigationOnTap = ((readerConfig.hideBars == true) ? true : readerConfig.shouldHideNavigationOnTap) - centerViewController = FolioReaderCenter() - FolioReader.shared.readerCenter = centerViewController + self.centerViewController = FolioReaderCenter() + self.folioReader?.readerCenter = self.centerViewController - centerNavigationController = UINavigationController(rootViewController: centerViewController) - centerNavigationController.setNavigationBarHidden(readerConfig.shouldHideNavigationOnTap, animated: false) - view.addSubview(centerNavigationController.view) - addChildViewController(centerNavigationController) - centerNavigationController.didMove(toParentViewController: self) + self.centerNavigationController = UINavigationController(rootViewController: self.centerViewController) + self.centerNavigationController.setNavigationBarHidden(readerConfig.shouldHideNavigationOnTap, animated: false) + self.view.addSubview(self.centerNavigationController.view) + self.addChildViewController(self.centerNavigationController) + self.centerNavigationController.didMove(toParentViewController: self) if (readerConfig.hideBars == true) { readerConfig.shouldHideNavigationOnTap = false @@ -122,12 +127,12 @@ open class FolioReaderContainer: UIViewController { } // Read async book - guard !epubPath.isEmpty else { + guard (self.epubPath.isEmpty == false) else { print("Epub path is nil.") - errorOnLoad = true + self.errorOnLoad = true return } - + DispatchQueue.global(qos: .userInitiated).async { if let parsedBook = FREpubParser().readEpub(epubPath: self.epubPath, removeEpub: self.shouldRemoveEpub) { book = parsedBook @@ -137,7 +142,7 @@ open class FolioReaderContainer: UIViewController { guard !self.errorOnLoad else { return } - FolioReader.isReaderOpen = true + self.folioReader?.isReaderOpen = true // Reload data DispatchQueue.main.async(execute: { @@ -149,8 +154,13 @@ open class FolioReaderContainer: UIViewController { self.centerViewController.reloadData() - FolioReader.isReaderReady = true - FolioReader.shared.delegate?.folioReader?(FolioReader.shared, didFinishedLoading: book) + self.folioReader?.isReaderReady = true + + guard let reader = self.folioReader else { + return + } + + reader.delegate?.folioReader?(reader, didFinishedLoading: book) }) } } @@ -158,8 +168,8 @@ open class FolioReaderContainer: UIViewController { override open func viewDidAppear(_ animated: Bool) { super.viewDidAppear(animated) - if errorOnLoad { - dismiss() + if (self.errorOnLoad == true) { + self.dismiss() } } @@ -167,14 +177,14 @@ open class FolioReaderContainer: UIViewController { Initialize the media player */ func addAudioPlayer() { - audioPlayer = FolioReaderAudioPlayer() - FolioReader.shared.readerAudioPlayer = audioPlayer; + self.audioPlayer = FolioReaderAudioPlayer() + self.folioReader?.readerAudioPlayer = audioPlayer } // MARK: - Status Bar override open var prefersStatusBarHidden: Bool { - return readerConfig.shouldHideNavigationOnTap == false ? false : shouldHideStatusBar + return (readerConfig.shouldHideNavigationOnTap == false ? false : shouldHideStatusBar) } override open var preferredStatusBarUpdateAnimation: UIStatusBarAnimation { diff --git a/Source/FolioReaderKit.swift b/Source/FolioReaderKit.swift index ea51f0a2d..8560ef69c 100755 --- a/Source/FolioReaderKit.swift +++ b/Source/FolioReaderKit.swift @@ -9,11 +9,15 @@ import Foundation import UIKit +// TODO_SMF: replace/remove utility function + // MARK: - Internal constants for devices internal let isPad = UIDevice.current.userInterfaceIdiom == .pad internal let isPhone = UIDevice.current.userInterfaceIdiom == .phone +// TODO_SMF: create constant file + // MARK: - Internal constants internal let kApplicationDocumentsDirectory = NSSearchPathForDirectoriesInDomains(.documentDirectory, .userDomainMask, true)[0] @@ -63,16 +67,19 @@ enum MediaOverlayStyle: Int { /** Called when reader did closed. */ - @objc optional func folioReaderDidClosed() + @objc optional func folioReaderDidClosed(_ folioReader: FolioReader) + + // TODO_SMF: make sure the following deprecated functions still work... or not.: + // TODO_SMF_KEVIN: ask the maind developer for that. + @objc optional func folioReaderDidClosed() } /** Main Library class with some useful constants and methods */ open class FolioReader: NSObject { - + /// Singleton instance - open static let shared = FolioReader() fileprivate override init() {} /// Custom unzip path @@ -80,42 +87,45 @@ open class FolioReader: NSObject { /// FolioReaderDelegate open weak var delegate: FolioReaderDelegate? - - + open weak var readerCenter: FolioReaderCenter? + // TODO_SMF: remove `!` open weak var readerContainer: FolioReaderContainer! open weak var readerAudioPlayer: FolioReaderAudioPlayer? - - static let defaults = UserDefaults.standard - - - + + // TODO_SMF: remove/rename static UserDefaults object. + class var defaults : UserDefaults { + return UserDefaults.standard + } + /// Check if reader is open - static var isReaderOpen = false + var isReaderOpen = false /// Check if reader is open and ready - static var isReaderReady = false + var isReaderReady = false /// Check if layout needs to change to fit Right To Left - static var needsRTLChange: Bool { - return book.spine.isRtl && readerConfig.scrollDirection == .horizontal + class var needsRTLChange: Bool { + return (book.spine.isRtl == true && readerConfig.scrollDirection == .horizontal) } /// Check if current theme is Night mode - open static var nightMode: Bool { + open var nightMode: Bool { get { return FolioReader.defaults.bool(forKey: kNightMode) } set (value) { FolioReader.defaults.set(value, forKey: kNightMode) FolioReader.defaults.synchronize() - if let readerCenter = FolioReader.shared.readerCenter { + if let readerCenter = self.readerCenter { UIView.animate(withDuration: 0.6, animations: { - _ = readerCenter.currentPage?.webView.js("nightMode(\(nightMode))") + // TODO_SMF: infinite loop? + _ = readerCenter.currentPage?.webView.js("nightMode(\(self.nightMode))") readerCenter.pageIndicatorView?.reloadColors() readerCenter.configureNavBar() readerCenter.scrollScrubber?.reloadColors() - readerCenter.collectionView.backgroundColor = (nightMode ? readerConfig.nightModeBackground : UIColor.white) + readerCenter.collectionView.backgroundColor = (self.nightMode ? readerConfig.nightModeBackground : UIColor.white) }, completion: { (finished: Bool) in + // TODO_SMF: add constant NotificationCenter.default.post(name: Notification.Name(rawValue: "needRefreshPageMode"), object: nil) }) } @@ -123,28 +133,32 @@ open class FolioReader: NSObject { } /// Check current font name - open static var currentFont: FolioReaderFont { + open var currentFont: FolioReaderFont { get { return FolioReaderFont(rawValue: FolioReader.defaults.value(forKey: kCurrentFontFamily) as! Int)! } set (font) { FolioReader.defaults.setValue(font.rawValue, forKey: kCurrentFontFamily) - _ = FolioReader.shared.readerCenter?.currentPage?.webView.js("setFontName('\(font.cssIdentifier)')") + _ = self.readerCenter?.currentPage?.webView.js("setFontName('\(font.cssIdentifier)')") } } /// Check current font size - open static var currentFontSize: FolioReaderFontSize { + open var currentFontSize: FolioReaderFontSize { + // TODO_SMF: remove unwrap get { return FolioReaderFontSize(rawValue: FolioReader.defaults.value(forKey: kCurrentFontSize) as! Int)! } set (value) { FolioReader.defaults.setValue(value.rawValue, forKey: kCurrentFontSize) - if let _currentPage = FolioReader.shared.readerCenter?.currentPage { - _currentPage.webView.js("setFontSize('\(currentFontSize.cssIdentifier)')") + guard let currentPage = self.readerCenter?.currentPage else { + return } + + currentPage.webView.js("setFontSize('\(currentFontSize.cssIdentifier)')") } } /// Check current audio rate, the speed of speech voice - static var currentAudioRate: Int { + var currentAudioRate: Int { + // TODO_SMF: remove unwrap get { return FolioReader.defaults.value(forKey: kCurrentAudioRate) as! Int } set (value) { FolioReader.defaults.setValue(value, forKey: kCurrentAudioRate) @@ -152,7 +166,8 @@ open class FolioReader: NSObject { } /// Check the current highlight style - static var currentHighlightStyle: Int { + var currentHighlightStyle: Int { + // TODO_SMF: remove unwrap get { return FolioReader.defaults.value(forKey: kCurrentHighlightStyle) as! Int } set (value) { FolioReader.defaults.setValue(value, forKey: kCurrentHighlightStyle) @@ -161,6 +176,7 @@ open class FolioReader: NSObject { /// Check the current Media Overlay or TTS style static var currentMediaOverlayStyle: MediaOverlayStyle { + // TODO_SMF: remove unwrap get { return MediaOverlayStyle(rawValue: FolioReader.defaults.value(forKey: kCurrentMediaOverlayStyle) as! Int)! } set (value) { FolioReader.defaults.setValue(value.rawValue, forKey: kCurrentMediaOverlayStyle) @@ -168,15 +184,15 @@ open class FolioReader: NSObject { } /// Check the current scroll direction - open static var currentScrollDirection: Int { + // TODO_SMF: value should use `FolioReaderScrollDirection` instead of `Int`? + open var currentScrollDirection: Int { + // TODO_SMF: remove unwrap get { return FolioReader.defaults.value(forKey: kCurrentScrollDirection) as! Int } set (value) { FolioReader.defaults.setValue(value, forKey: kCurrentScrollDirection) - if let _readerCenter = FolioReader.shared.readerCenter { - let direction = FolioReaderScrollDirection(rawValue: currentScrollDirection) ?? .defaultVertical - _readerCenter.setScrollDirection(direction) - } + let direction = (FolioReaderScrollDirection(rawValue: currentScrollDirection) ?? .defaultVertical) + self.readerCenter?.setScrollDirection(direction) } } @@ -204,35 +220,27 @@ open class FolioReader: NSObject { /** Present a Folio Reader for a Parent View Controller. */ - open class func presentReader(parentViewController: UIViewController, withEpubPath epubPath: String, andConfig config: FolioReaderConfig, shouldRemoveEpub: Bool = true, animated: Bool = true) { - let reader = FolioReaderContainer(withConfig: config, epubPath: epubPath, removeEpub: shouldRemoveEpub) - FolioReader.shared.readerContainer = reader - parentViewController.present(reader, animated: animated, completion: nil) - } - - // MARK: - Application State - - /** - Called when the application will resign active - */ - open class func applicationWillResignActive() { - saveReaderState() - } - - /** - Called when the application will terminate - */ - open class func applicationWillTerminate() { - saveReaderState() + open class func presentReader(parentViewController: UIViewController, withEpubPath epubPath: String, andConfig config: FolioReaderConfig, shouldRemoveEpub: Bool = true, animated: Bool = true) -> FolioReader { + let folioReader = FolioReader() + let readerContainer = FolioReaderContainer(withConfig: config, folioReader: folioReader, epubPath: epubPath, removeEpub: shouldRemoveEpub) + folioReader.readerContainer = readerContainer + parentViewController.present(readerContainer, animated: animated, completion: nil) + FolioReader.shared = folioReader + return folioReader } - +} + +// MARK: - Exit, save and close FolioReader + +extension FolioReader { + /** Save Reader state, book, page and scroll are saved */ - open class func saveReaderState() { - guard FolioReader.isReaderOpen else { return } + open func saveReaderState() { + guard self.isReaderOpen else { return } - if let currentPage = FolioReader.shared.readerCenter?.currentPage { + if let currentPage = self.readerCenter?.currentPage { let position = [ "pageNumber": currentPageNumber, "pageOffsetX": currentPage.webView.scrollView.contentOffset.x, @@ -246,20 +254,126 @@ open class FolioReader: NSObject { /** Closes and save the reader current instance */ - open class func close() { - FolioReader.saveReaderState() - FolioReader.isReaderOpen = false - FolioReader.isReaderReady = false - FolioReader.shared.readerAudioPlayer?.stop(immediate: true) + open func close() { + self.saveReaderState() + self.isReaderOpen = false + self.isReaderReady = false + self.readerAudioPlayer?.stop(immediate: true) FolioReader.defaults.set(0, forKey: kCurrentTOCMenu) - FolioReader.shared.delegate?.folioReaderDidClosed?() + self.delegate?.folioReaderDidClosed?(self) + self.delegate?.folioReaderDidClosed?() } } +// MARK: - Public shared extension. All Deprecated function + +extension FolioReader { + + // TODO_SMF: temporal variable to build and run the current state. Should be completely remove. + private static var _sharedInstance = FolioReader() + open static var shared : FolioReader { + get { return _sharedInstance } + set { + _sharedInstance = newValue + } + } + + /// Check if current theme is Night mode + open class var nightMode: Bool { + get { return FolioReader.shared.nightMode } + set (value) { + FolioReader.shared.nightMode = value + } + } + + /// Check current font name + open class var currentFont: FolioReaderFont { + get { return FolioReader.shared.currentFont } + set (font) { + FolioReader.shared.currentFont = font + } + } + + /// Check current font size + open class var currentFontSize: FolioReaderFontSize { + // TODO_SMF: remove unwrap + get { return FolioReader.shared.currentFontSize } + set (value) { + FolioReader.shared.currentFontSize = value + } + } + + /// Check the current scroll direction + // TODO_SMF: value should use `FolioReaderScrollDirection` instead of `Int`? + open class var currentScrollDirection: Int { + // TODO_SMF: remove unwrap + get { return FolioReader.shared.currentScrollDirection } + set (value) { + FolioReader.shared.currentScrollDirection = value + } + } + + open class var currentAudioRate: Int { + // TODO_SMF: remove unwrap + get { return FolioReader.shared.currentAudioRate } + set (value) { + FolioReader.shared.currentAudioRate = value + } + } + + /// Check if reader is open and ready + open class var isReaderReady : Bool { + return FolioReader.shared.isReaderReady + } + + /** + Save Reader state, book, page and scroll are saved + */ + open class func saveReaderState() { + FolioReader.shared.saveReaderState() + } + + /** + Closes and save the reader current instance + */ + open class func close() { + FolioReader.shared.close() + } + + /// Check the current highlight style + open class var currentHighlightStyle: Int { + get { return FolioReader.shared.currentHighlightStyle } + set (value) { + FolioReader.shared.currentHighlightStyle = value + } + } +} + +// MARK: - Application State + +extension FolioReader { + + // TODO_SMF: deprecate and find a replacement for those functions. + + /** + Called when the application will resign active + */ + open class func applicationWillResignActive() { + FolioReader.shared.saveReaderState() + } + + /** + Called when the application will terminate + */ + open class func applicationWillTerminate() { + FolioReader.shared.saveReaderState() + } +} + // MARK: - Global Functions func isNight (_ f: T, _ l: T) -> T { - return FolioReader.nightMode ? f : l + return (FolioReader.shared.nightMode == true ? f : l) } // MARK: - Scroll Direction Functions @@ -584,9 +698,10 @@ internal extension String { return String(format: "%02.f:%02.f", min, sec) } - } +// TODO_SMF: split files into extension files + internal extension UIImage { convenience init?(readerImageNamed: String) { self.init(named: readerImageNamed, in: Bundle.frameworkBundle(), compatibleWith: nil) @@ -687,7 +802,7 @@ internal extension UIViewController { } func dismiss() { - dismiss(nil) + self.dismiss(nil) } func dismiss(_ completion: (() -> Void)?) { diff --git a/Source/Models/Highlight+Helper.swift b/Source/Models/Highlight+Helper.swift index a289667bc..0362ac1c2 100644 --- a/Source/Models/Highlight+Helper.swift +++ b/Source/Models/Highlight+Helper.swift @@ -20,24 +20,20 @@ public enum HighlightStyle: Int { case underline public init () { self = .yellow } - + + // TODO_SMF: replace with a string enum instead. + /** Return HighlightStyle for CSS class. */ public static func styleForClass(_ className: String) -> HighlightStyle { switch className { - case "highlight-yellow": - return .yellow - case "highlight-green": - return .green - case "highlight-blue": - return .blue - case "highlight-pink": - return .pink - case "highlight-underline": - return .underline - default: - return .yellow + case "highlight-yellow": return .yellow + case "highlight-green": return .green + case "highlight-blue": return .blue + case "highlight-pink": return .pink + case "highlight-underline": return .underline + default: return .yellow } } @@ -46,25 +42,22 @@ public enum HighlightStyle: Int { */ public static func classForStyle(_ style: Int) -> String { switch style { - case HighlightStyle.yellow.rawValue: - return "highlight-yellow" - case HighlightStyle.green.rawValue: - return "highlight-green" - case HighlightStyle.blue.rawValue: - return "highlight-blue" - case HighlightStyle.pink.rawValue: - return "highlight-pink" - case HighlightStyle.underline.rawValue: - return "highlight-underline" - default: - return "highlight-yellow" + case HighlightStyle.yellow.rawValue: return "highlight-yellow" + case HighlightStyle.green.rawValue: return "highlight-green" + case HighlightStyle.blue.rawValue: return "highlight-blue" + case HighlightStyle.pink.rawValue: return "highlight-pink" + case HighlightStyle.underline.rawValue: return "highlight-underline" + default: return "highlight-yellow" } } - + + // TODO_SMF: remove default cases, add optional result. + /** Return CSS class for HighlightStyle. */ public static func colorForStyle(_ style: Int, nightMode: Bool = false) -> UIColor { + switch style { case HighlightStyle.yellow.rawValue: return UIColor(red: 255/255, green: 235/255, blue: 107/255, alpha: nightMode ? 0.9 : 1) @@ -86,7 +79,9 @@ public enum HighlightStyle: Int { public typealias Completion = (_ error: NSError?) -> () extension Highlight { - + + // TODO_SMF: replace try with a 'do-try-catch' or at least a 'try?'. + /** Save a Highlight with completion block diff --git a/Source/Models/Highlight.swift b/Source/Models/Highlight.swift index 6f3466cb0..363f606e6 100644 --- a/Source/Models/Highlight.swift +++ b/Source/Models/Highlight.swift @@ -9,6 +9,8 @@ import Foundation import RealmSwift +// TODO_SMF: Remove `!`. + /// A Highlight object open class Highlight: Object { open dynamic var bookId: String! From b16196d36e3a17e43c81f1eeadc1937e44ad2b64 Mon Sep 17 00:00:00 2001 From: Kevin Delord Date: Tue, 28 Mar 2017 19:41:43 +0200 Subject: [PATCH 004/110] Refactor the readerCenter and global book entity --- Source/FolioReaderAudioPlayer.swift | 94 ++++++++++++++++------------- Source/FolioReaderCenter.swift | 89 +++++++++++++++------------ Source/FolioReaderChapterList.swift | 32 ++++++---- Source/FolioReaderContainer.swift | 36 +++++------ Source/FolioReaderKit.swift | 12 ++-- Source/FolioReaderPage.swift | 30 ++++++--- Source/FolioReaderQuoteShare.swift | 20 ++++-- Source/FolioReaderWebView.swift | 9 ++- 8 files changed, 193 insertions(+), 129 deletions(-) diff --git a/Source/FolioReaderAudioPlayer.swift b/Source/FolioReaderAudioPlayer.swift index a9ca572b1..b7f0a357f 100644 --- a/Source/FolioReaderAudioPlayer.swift +++ b/Source/FolioReaderAudioPlayer.swift @@ -25,7 +25,12 @@ open class FolioReaderAudioPlayer: NSObject { var registeredCommands = false var completionHandler: () -> Void = {} var utteranceRate: Float = 0 - + + fileprivate var book : FRBook? { + // TODO_SMF: remove this getter + return FolioReader.shared.readerContainer?.book + } + // MARK: Init override init() { @@ -151,11 +156,11 @@ open class FolioReaderAudioPlayer: NSObject { } func play() { - if book.hasAudio() { + if (self.book?.hasAudio() == true) { guard let currentPage = FolioReader.shared.readerCenter?.currentPage else { return } currentPage.webView.js("playAudio()") } else { - readCurrentSentence() + self.readCurrentSentence() } // UIApplication.sharedApplication().idleTimerDisabled = true @@ -174,9 +179,9 @@ open class FolioReaderAudioPlayer: NSObject { func playAudio(_ href: String, fragmentID: String) { isTextToSpeech = false - stop() + self.stop() - let smilFile = book.smilFileForHref(href) + let smilFile = self.book?.smilFileForHref(href) // if no smil file for this href and the same href is being requested, we've hit the end. stop playing if smilFile == nil && currentHref != nil && href == currentHref { @@ -238,11 +243,12 @@ open class FolioReaderAudioPlayer: NSObject { Once an audio fragment begins playing, the audio clip will continue playing until the player timer detects the audio is out of the fragment timeframe. */ - @discardableResult fileprivate func _playFragment(_ smil: FRSmilElement!) -> Bool { + @discardableResult fileprivate func _playFragment(_ smil: FRSmilElement?) -> Bool { - if smil == nil { + guard let smil = smil else { + // TODO_SMF_QUESTION: disable log? print("no more parallel audio to play") - stop() + self.stop() return false } @@ -303,28 +309,28 @@ open class FolioReaderAudioPlayer: NSObject { Gets the next audio fragment in the current smil file, or moves on to the next smil file */ - fileprivate func nextAudioFragment() -> FRSmilElement! { - - let smilFile = book.smilFileForHref(currentHref) + fileprivate func nextAudioFragment() -> FRSmilElement? { - if smilFile == nil { return nil } + guard let smilFile = self.book?.smilFileForHref(currentHref) else { + return nil + } - let smil = currentFragment == nil ? smilFile?.parallelAudioForFragment(nil) : smilFile?.nextParallelAudioForFragment(currentFragment) + let smil = (self.currentFragment == nil ? smilFile.parallelAudioForFragment(nil) : smilFile.nextParallelAudioForFragment(currentFragment)) - if smil != nil { - currentFragment = smil?.textElement().attributes["src"] + if (smil != nil) { + self.currentFragment = smil?.textElement().attributes["src"] return smil } - currentHref = book.spine.nextChapter(currentHref)!.href - currentFragment = nil - currentSmilFile = smilFile + self.currentHref = self.book?.spine.nextChapter(currentHref)?.href + self.currentFragment = nil + self.currentSmilFile = smilFile - if currentHref == nil { + guard (self.currentHref != nil) else { return nil } - return nextAudioFragment() + return self.nextAudioFragment() } func playText(_ href: String, text: String) { @@ -340,7 +346,7 @@ open class FolioReaderAudioPlayer: NSObject { let utterance = AVSpeechUtterance(string: text) utterance.rate = utteranceRate - utterance.voice = AVSpeechSynthesisVoice(language: book.metadata.language) + utterance.voice = AVSpeechSynthesisVoice(language: self.book?.metadata.language) if synthesizer.isSpeaking { stopSynthesizer() @@ -353,25 +359,29 @@ open class FolioReaderAudioPlayer: NSObject { // MARK: TTS Sentence func speakSentence() { - guard let - readerCenter = FolioReader.shared.readerCenter, + guard + let readerCenter = FolioReader.shared.readerCenter, + let playbackActiveClass = self.book?.playbackActiveClass(), let currentPage = readerCenter.currentPage else { return } - let sentence = currentPage.webView.js("getSentenceWithIndex('\(book.playbackActiveClass())')") - - if sentence != nil { - let chapter = readerCenter.getCurrentChapter() - let href = chapter != nil ? chapter!.href : ""; - playText(href!, text: sentence!) - } else { - if readerCenter.isLastPage() { - stop() - } else { - readerCenter.changePageToNext() - } - } + guard let sentence = currentPage.webView.js("getSentenceWithIndex('\(playbackActiveClass)')") else { + if (readerCenter.isLastPage() == true) { + self.stop() + } else { + readerCenter.changePageToNext() + } + + return + } + + guard let href = readerCenter.getCurrentChapter()?.href else { + return + } + + // TODO_SMF_QUESTION: the previous code mde it possible for `href` to be an empty string. Was that valid? should this logic be kept? + self.playText(href, text: sentence) } func readCurrentSentence() { @@ -413,7 +423,7 @@ open class FolioReaderAudioPlayer: NSObject { guard let player = player else { return } if currentEndTime != nil && currentEndTime > 0 && player.currentTime > currentEndTime { - _playFragment(nextAudioFragment()) + _playFragment(self.nextAudioFragment()) } } @@ -428,13 +438,13 @@ open class FolioReaderAudioPlayer: NSObject { var songInfo = [String: AnyObject]() // Get book Artwork - if let coverImage = book.coverImage, let artwork = UIImage(contentsOfFile: coverImage.fullHref) { + if let coverImage = self.book?.coverImage, let artwork = UIImage(contentsOfFile: coverImage.fullHref) { let albumArt = MPMediaItemArtwork(image: artwork) songInfo[MPMediaItemPropertyArtwork] = albumArt } // Get book title - if let title = book.title() { + if let title = self.book?.title() { songInfo[MPMediaItemPropertyAlbumTitle] = title as AnyObject? } @@ -444,7 +454,7 @@ open class FolioReaderAudioPlayer: NSObject { } // Get author name - if let author = book.metadata.creators.first { + if let author = self.book?.metadata.creators.first { songInfo[MPMediaItemPropertyArtist] = author.name as AnyObject? } @@ -474,7 +484,7 @@ open class FolioReaderAudioPlayer: NSObject { currentHref = chapter.href - for item in book.flatTableOfContents { + for item in (self.book?.flatTableOfContents ?? []) { if let resource = item.resource , resource.href == currentHref { return item.title } @@ -523,6 +533,6 @@ extension FolioReaderAudioPlayer: AVSpeechSynthesizerDelegate { extension FolioReaderAudioPlayer: AVAudioPlayerDelegate { public func audioPlayerDidFinishPlaying(_ player: AVAudioPlayer, successfully flag: Bool) { - _playFragment(nextAudioFragment()) + _playFragment(self.nextAudioFragment()) } } diff --git a/Source/FolioReaderCenter.swift b/Source/FolioReaderCenter.swift index b9140287c..18abc8888 100755 --- a/Source/FolioReaderCenter.swift +++ b/Source/FolioReaderCenter.swift @@ -40,15 +40,16 @@ var isScrolling = false } /// The base reader class -open class FolioReaderCenter: UIViewController, UICollectionViewDelegate, UICollectionViewDataSource { +open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICollectionViewDataSource { /// This delegate receives the events from the current `FolioReaderPage`s delegate. - open weak var delegate: FolioReaderCenterDelegate? + open weak var delegate : FolioReaderCenterDelegate? /// This delegate receives the events from current page - open weak var pageDelegate: FolioReaderPageDelegate? + open weak var pageDelegate : FolioReaderPageDelegate? + + open weak var readerContainer : FolioReaderContainer? - /// The current visible page on reader open fileprivate(set) var currentPage: FolioReaderPage? @@ -56,7 +57,7 @@ open class FolioReaderCenter: UIViewController, UICollectionViewDelegate, UIColl let collectionViewLayout = UICollectionViewFlowLayout() var loadingView: UIActivityIndicatorView! var pages: [String]! - var totalPages: Int! + var totalPages: Int = 0 var tempFragment: String? var animator: ZFModalTransitionAnimator! var pageIndicatorView: FolioReaderPageIndicator? @@ -73,17 +74,24 @@ open class FolioReaderCenter: UIViewController, UICollectionViewDelegate, UIColl fileprivate var isFirstLoad = true fileprivate var currentWebViewScrollPositions = [Int: CGPoint]() fileprivate var currentOrientation: UIInterfaceOrientation? - + + fileprivate var book : FRBook? { + return self.readerContainer?.book + } + // MARK: - Init - init() { + init(withContainer readerContainer: FolioReaderContainer) { super.init(nibName: nil, bundle: Bundle.frameworkBundle()) - initialization() + + self.readerContainer = readerContainer + self.initialization() } required public init?(coder aDecoder: NSCoder) { super.init(coder: aDecoder) - initialization() + + self.initialization() } /** @@ -95,14 +103,14 @@ open class FolioReaderCenter: UIViewController, UICollectionViewDelegate, UIColl self.pageIndicatorHeight = 0 } - totalPages = book.spine.spineReferences.count + self.totalPages = (self.book?.spine.spineReferences.count ?? 0) // Loading indicator let style: UIActivityIndicatorViewStyle = isNight(.white, .gray) loadingView = UIActivityIndicatorView(activityIndicatorStyle: style) loadingView.hidesWhenStopped = true loadingView.startAnimating() - view.addSubview(loadingView) + self.view.addSubview(loadingView) } // MARK: - View life cicle @@ -234,7 +242,7 @@ open class FolioReaderCenter: UIViewController, UICollectionViewDelegate, UIColl rightBarIcons.append(UIBarButtonItem(image: shareIcon, style: .plain, target: self, action:#selector(shareChapter(_:)))) } - if book.hasAudio() || readerConfig.enableTTS { + if (self.book?.hasAudio() == true || readerConfig.enableTTS) { rightBarIcons.append(UIBarButtonItem(image: audioIcon, style: .plain, target: self, action:#selector(presentPlayerMenu(_:)))) } @@ -246,16 +254,16 @@ open class FolioReaderCenter: UIViewController, UICollectionViewDelegate, UIColl } func reloadData() { - loadingView.stopAnimating() - totalPages = book.spine.spineReferences.count + self.loadingView.stopAnimating() + self.totalPages = (self.book?.spine.spineReferences.count ?? 0) - collectionView.reloadData() - configureNavBarButtons() - setCollectionViewProgressiveDirection() + self.collectionView.reloadData() + self.configureNavBarButtons() + self.setCollectionViewProgressiveDirection() if let position = FolioReader.defaults.value(forKey: kBookId) as? NSDictionary, let pageNumber = position["pageNumber"] as? Int , pageNumber > 0 { - changePageWith(page: pageNumber) + self.changePageWith(page: pageNumber) currentPageNumber = pageNumber return } @@ -392,7 +400,7 @@ open class FolioReaderCenter: UIViewController, UICollectionViewDelegate, UIColl setPageProgressiveDirection(cell) // Configure the cell - if let resource = book.spine.spineReferences[(indexPath as NSIndexPath).row].resource, + if let resource = self.book?.spine.spineReferences[(indexPath as NSIndexPath).row].resource, var html = try? String(contentsOfFile: resource.fullHref, encoding: String.Encoding.utf8) { let mediaOverlayStyleColors = "\"\(readerConfig.mediaOverlayColor.hexString(false))\", \"\(readerConfig.mediaOverlayColor.highlightColor().hexString(false))\"" @@ -737,8 +745,8 @@ open class FolioReaderCenter: UIViewController, UICollectionViewDelegate, UIColl */ func findPageByResource(_ reference: FRTocReference) -> Int { var count = 0 - for item in book.spine.spineReferences { - if let resource = reference.resource , item.resource == resource { + for item in (self.book?.spine.spineReferences ?? []) { + if let resource = reference.resource, item.resource == resource { return count } count += 1 @@ -751,7 +759,7 @@ open class FolioReaderCenter: UIViewController, UICollectionViewDelegate, UIColl */ func findPageByHref(_ href: String) -> Int { var count = 0 - for item in book.spine.spineReferences { + for item in (self.book?.spine.spineReferences ?? []) { if item.resource.href == href { return count } @@ -765,8 +773,8 @@ open class FolioReaderCenter: UIViewController, UICollectionViewDelegate, UIColl */ func getCurrentChapter() -> FRResource? { if let currentPageNumber = currentPageNumber { - for item in book.flatTableOfContents { - if let reference = book.spine.spineReferences[safe: currentPageNumber-1], let resource = item.resource + for item in (self.book?.flatTableOfContents ?? []) { + if let reference = self.book?.spine.spineReferences[safe: currentPageNumber-1], let resource = item.resource , resource == reference.resource { return item.resource } @@ -780,14 +788,20 @@ open class FolioReaderCenter: UIViewController, UICollectionViewDelegate, UIColl */ func getCurrentChapterName() -> String? { if let currentPageNumber = currentPageNumber { - for item in book.flatTableOfContents { - if let reference = book.spine.spineReferences[safe: currentPageNumber-1], let resource = item.resource - , resource == reference.resource { - if let title = item.title { - return title - } - return nil - } + for item in (self.book?.flatTableOfContents ?? []) { + guard + let reference = self.book?.spine.spineReferences[safe: currentPageNumber-1], + let resource = item.resource else { + return nil + } + + guard + (resource == reference.resource), + let title = item.title else { + return nil + } + + return title } } return nil @@ -836,9 +850,10 @@ open class FolioReaderCenter: UIViewController, UICollectionViewDelegate, UIColl var chapterName = "" var authorName = "" var shareItems = [AnyObject]() - + + // TODO_SMF: refactor similar code in current functions. // Get book title - if let title = book.title() { + if let title = self.book?.title() { bookTitle = title subject += " “\(title)”" } @@ -849,7 +864,7 @@ open class FolioReaderCenter: UIViewController, UICollectionViewDelegate, UIColl } // Get author name - if let author = book.metadata.creators.first { + if let author = self.book?.metadata.creators.first { authorName = author.name } @@ -896,7 +911,7 @@ open class FolioReaderCenter: UIViewController, UICollectionViewDelegate, UIColl var shareItems = [AnyObject]() // Get book title - if let title = book.title() { + if let title = self.book?.title() { bookTitle = title subject += " “\(title)”" } @@ -907,7 +922,7 @@ open class FolioReaderCenter: UIViewController, UICollectionViewDelegate, UIColl } // Get author name - if let author = book.metadata.creators.first { + if let author = self.book?.metadata.creators.first { authorName = author.name } diff --git a/Source/FolioReaderChapterList.swift b/Source/FolioReaderChapterList.swift index c3f25d749..0d8fa702a 100755 --- a/Source/FolioReaderChapterList.swift +++ b/Source/FolioReaderChapterList.swift @@ -25,21 +25,26 @@ import UIKit class FolioReaderChapterList: UITableViewController { weak var delegate: FolioReaderChapterListDelegate? var tocItems = [FRTocReference]() - + + fileprivate var book : FRBook? { + // TODO_SMF: remove this getter + return FolioReader.shared.readerContainer?.book + } + override func viewDidLoad() { super.viewDidLoad() // Register cell classes - tableView.register(FolioReaderChapterListCell.self, forCellReuseIdentifier: reuseIdentifier) - tableView.separatorInset = UIEdgeInsets.zero - tableView.backgroundColor = isNight(readerConfig.nightModeMenuBackground, readerConfig.menuBackgroundColor) - tableView.separatorColor = isNight(readerConfig.nightModeSeparatorColor, readerConfig.menuSeparatorColor) + self.tableView.register(FolioReaderChapterListCell.self, forCellReuseIdentifier: reuseIdentifier) + self.tableView.separatorInset = UIEdgeInsets.zero + self.tableView.backgroundColor = isNight(readerConfig.nightModeMenuBackground, readerConfig.menuBackgroundColor) + self.tableView.separatorColor = isNight(readerConfig.nightModeSeparatorColor, readerConfig.menuSeparatorColor) - tableView.rowHeight = UITableViewAutomaticDimension - tableView.estimatedRowHeight = 50 + self.tableView.rowHeight = UITableViewAutomaticDimension + self.tableView.estimatedRowHeight = 50 // Create TOC list - tocItems = book.flatTableOfContents + self.tocItems = (self.book?.flatTableOfContents ?? []) } // MARK: - Table view data source @@ -63,7 +68,7 @@ class FolioReaderChapterList: UITableViewController { // Add audio duration for Media Ovelay if let resource = tocReference.resource { if let mediaOverlay = resource.mediaOverlay { - let duration = book.durationFor("#"+mediaOverlay) + let duration = self.book?.durationFor("#"+mediaOverlay) let durationFormatted = (duration != nil ? duration : "")?.clockTimeToMinutesString() cell.indexLabel.text = cell.indexLabel.text! + (duration != nil ? " - "+durationFormatted! : ""); @@ -71,9 +76,12 @@ class FolioReaderChapterList: UITableViewController { } // Mark current reading chapter - if let currentPageNumber = currentPageNumber, let reference = book.spine.spineReferences[safe: currentPageNumber-1] , tocReference.resource != nil { - let resource = reference.resource - cell.indexLabel.textColor = tocReference.resource == resource ? readerConfig.tintColor : readerConfig.menuTextColor + if + let currentPageNumber = currentPageNumber, + let reference = self.book?.spine.spineReferences[safe: currentPageNumber - 1], + (tocReference.resource != nil) { + let resource = reference.resource + cell.indexLabel.textColor = (tocReference.resource == resource ? readerConfig.tintColor : readerConfig.menuTextColor) } cell.layoutMargins = UIEdgeInsets.zero diff --git a/Source/FolioReaderContainer.swift b/Source/FolioReaderContainer.swift index c1aaef0e7..ac0ea34ba 100755 --- a/Source/FolioReaderContainer.swift +++ b/Source/FolioReaderContainer.swift @@ -11,7 +11,6 @@ import FontBlaster // TODO_SMF: remove static variables var readerConfig: FolioReaderConfig! -var book: FRBook! /// Reader container open class FolioReaderContainer : UIViewController { @@ -22,7 +21,8 @@ open class FolioReaderContainer : UIViewController { var audioPlayer : FolioReaderAudioPlayer? var shouldHideStatusBar = true var shouldRemoveEpub = true - var epubPath : String! + var epubPath : String? + var book : FRBook? fileprivate var folioReader : FolioReader? fileprivate var errorOnLoad = false @@ -111,9 +111,8 @@ open class FolioReaderContainer : UIViewController { readerConfig.shouldHideNavigationOnTap = ((readerConfig.hideBars == true) ? true : readerConfig.shouldHideNavigationOnTap) - self.centerViewController = FolioReaderCenter() - self.folioReader?.readerCenter = self.centerViewController - + self.centerViewController = FolioReaderCenter(withContainer: self) + self.centerNavigationController = UINavigationController(rootViewController: self.centerViewController) self.centerNavigationController.setNavigationBarHidden(readerConfig.shouldHideNavigationOnTap, animated: false) self.view.addSubview(self.centerNavigationController.view) @@ -127,28 +126,27 @@ open class FolioReaderContainer : UIViewController { } // Read async book - guard (self.epubPath.isEmpty == false) else { + guard let epubPath = self.epubPath, (epubPath.isEmpty == false) else { print("Epub path is nil.") self.errorOnLoad = true return } DispatchQueue.global(qos: .userInitiated).async { - if let parsedBook = FREpubParser().readEpub(epubPath: self.epubPath, removeEpub: self.shouldRemoveEpub) { - book = parsedBook - } else { - self.errorOnLoad = true - } - - guard !self.errorOnLoad else { return } - + + guard let parsedBook = FREpubParser().readEpub(epubPath: epubPath, removeEpub: self.shouldRemoveEpub) else { + self.errorOnLoad = true + return + } + + self.book = parsedBook self.folioReader?.isReaderOpen = true // Reload data DispatchQueue.main.async(execute: { // Add audio player if needed - if book.hasAudio() || readerConfig.enableTTS { + if (self.book?.hasAudio() == true || readerConfig.enableTTS) { self.addAudioPlayer() } @@ -156,11 +154,13 @@ open class FolioReaderContainer : UIViewController { self.folioReader?.isReaderReady = true - guard let reader = self.folioReader else { - return + guard + let reader = self.folioReader, + let loadedBook = self.book else { + return } - reader.delegate?.folioReader?(reader, didFinishedLoading: book) + reader.delegate?.folioReader?(reader, didFinishedLoading: loadedBook) }) } } diff --git a/Source/FolioReaderKit.swift b/Source/FolioReaderKit.swift index 8560ef69c..878c7ca72 100755 --- a/Source/FolioReaderKit.swift +++ b/Source/FolioReaderKit.swift @@ -70,7 +70,7 @@ enum MediaOverlayStyle: Int { @objc optional func folioReaderDidClosed(_ folioReader: FolioReader) // TODO_SMF: make sure the following deprecated functions still work... or not.: - // TODO_SMF_KEVIN: ask the maind developer for that. + // TODO_SMF_QUESTION: ask the main developer(s) for that. @objc optional func folioReaderDidClosed() } @@ -88,7 +88,10 @@ open class FolioReader: NSObject { /// FolioReaderDelegate open weak var delegate: FolioReaderDelegate? - open weak var readerCenter: FolioReaderCenter? + open weak var readerCenter: FolioReaderCenter? { + return self.readerContainer.centerViewController + } + // TODO_SMF: remove `!` open weak var readerContainer: FolioReaderContainer! open weak var readerAudioPlayer: FolioReaderAudioPlayer? @@ -106,7 +109,8 @@ open class FolioReader: NSObject { /// Check if layout needs to change to fit Right To Left class var needsRTLChange: Bool { - return (book.spine.isRtl == true && readerConfig.scrollDirection == .horizontal) + // TODO_SMF: after readerConfig has been migrated, use local variables instead. Plus create a static class getter. + return (FolioReader.shared.readerContainer.book?.spine.isRtl == true && readerConfig.scrollDirection == .horizontal) } /// Check if current theme is Night mode @@ -127,7 +131,7 @@ open class FolioReader: NSObject { }, completion: { (finished: Bool) in // TODO_SMF: add constant NotificationCenter.default.post(name: Notification.Name(rawValue: "needRefreshPageMode"), object: nil) - }) + }) } } } diff --git a/Source/FolioReaderPage.swift b/Source/FolioReaderPage.swift index 221138e33..86cf3b62c 100755 --- a/Source/FolioReaderPage.swift +++ b/Source/FolioReaderPage.swift @@ -32,12 +32,18 @@ import JSQWebViewController open class FolioReaderPage: UICollectionViewCell, UIWebViewDelegate, UIGestureRecognizerDelegate { weak var delegate: FolioReaderPageDelegate? + // TODO_SMF: remove `!` /// The index of the current page. Note: The index start at 1! open var pageNumber: Int! var webView: FolioReaderWebView! fileprivate var colorView: UIView! fileprivate var shouldShowBar = true fileprivate var menuIsVisible = false + + fileprivate var book: FRBook? { + // TODO_SMF: remove this getter + return FolioReader.shared.readerContainer?.book + } // MARK: - View life cicle @@ -157,7 +163,7 @@ open class FolioReaderPage: UICollectionViewCell, UIWebViewDelegate, UIGestureRe refreshPageMode() - if readerConfig.enableTTS && !book.hasAudio() { + if (readerConfig.enableTTS && self.book?.hasAudio() == false) { webView.js("wrappingSentencesWithinPTags()") if let audioPlayer = FolioReader.shared.readerAudioPlayer , audioPlayer.isPlaying() { @@ -214,10 +220,12 @@ open class FolioReaderPage: UICollectionViewCell, UIWebViewDelegate, UIGestureRe let anchorFromURL = url.fragment // Handle internal url - if (url.path as NSString).pathExtension != "" { - let base = (book.opfResource.href as NSString).deletingLastPathComponent + if ((url.path as NSString).pathExtension != "") { + var base = (self.book?.opfResource.href as? NSString)?.deletingLastPathComponent + base = ((base == nil || base?.isEmpty == true) ? kBookId : base) + let path = url.path - let splitedPath = path.components(separatedBy: base.isEmpty ? kBookId : base) + let splitedPath = path.components(separatedBy: (base ?? kBookId)) // Return to avoid crash if splitedPath.count <= 1 || splitedPath[1].isEmpty { @@ -227,7 +235,7 @@ open class FolioReaderPage: UICollectionViewCell, UIWebViewDelegate, UIGestureRe let href = splitedPath[1].trimmingCharacters(in: CharacterSet(charactersIn: "/")) let hrefPage = (FolioReader.shared.readerCenter?.findPageByHref(href) ?? 0) + 1 - if hrefPage == pageNumber { + if (hrefPage == pageNumber) { // Handle internal #anchor if anchorFromURL != nil { handleAnchor(anchorFromURL!, avoidBeginningAnchors: false, animated: true) @@ -437,11 +445,15 @@ open class FolioReaderPage: UICollectionViewCell, UIWebViewDelegate, UIGestureRe /** Audio Mark ID - marks an element with an ID with the given class and scrolls to it - - parameter ID: The ID + - parameter identifier: The identifier */ - func audioMarkID(_ ID: String) { - guard let currentPage = FolioReader.shared.readerCenter?.currentPage else { return } - currentPage.webView.js("audioMarkID('\(book.playbackActiveClass())','\(ID)')") + func audioMarkID(_ identifier: String) { + guard + let playbackActiveClass = self.book?.playbackActiveClass(), + let currentPage = FolioReader.shared.readerCenter?.currentPage else { + return + } + currentPage.webView.js("audioMarkID('\(playbackActiveClass)','\(identifier)')") } // MARK: UIMenu visibility diff --git a/Source/FolioReaderQuoteShare.swift b/Source/FolioReaderQuoteShare.swift index dc2e779be..532fe3ec9 100644 --- a/Source/FolioReaderQuoteShare.swift +++ b/Source/FolioReaderQuoteShare.swift @@ -23,7 +23,12 @@ class FolioReaderQuoteShare: UIViewController { var dataSource = [QuoteImage]() let imagePicker = UIImagePickerController() var selectedIndex = 0 - + + fileprivate var book : FRBook? { + // TODO_SMF: remove this getter + return FolioReader.shared.readerContainer?.book + } + // MARK: Init init(initWithText shareText: String) { @@ -79,8 +84,13 @@ class FolioReaderQuoteShare: UIViewController { var bookTitle = "" var authorName = "" - if let title = book.title() { bookTitle = title } - if let author = book.metadata.creators.first { authorName = author.name } + if let title = self.book?.title() { + bookTitle = title + } + + if let author = self.book?.metadata.creators.first { + authorName = author.name + } titleLabel = UILabel() titleLabel.text = bookTitle @@ -249,13 +259,13 @@ class FolioReaderQuoteShare: UIViewController { var shareItems = [AnyObject]() // Get book title - if let title = book.title() { + if let title = self.book?.title() { bookTitle = title subject += " “\(title)”" } // Get author name - if let author = book.metadata.creators.first { + if let author = self.book?.metadata.creators.first { authorName = author.name } diff --git a/Source/FolioReaderWebView.swift b/Source/FolioReaderWebView.swift index 6b8cba694..152704909 100644 --- a/Source/FolioReaderWebView.swift +++ b/Source/FolioReaderWebView.swift @@ -14,6 +14,11 @@ open class FolioReaderWebView: UIWebView { var isShare = false var isOneWord = false + fileprivate var book : FRBook? { + // TODO_SMF: remove this getter + return FolioReader.shared.readerContainer?.book + } + // MARK: - UIMenuController open override func canPerformAction(_ action: Selector, withSender sender: Any?) -> Bool { @@ -28,7 +33,7 @@ open class FolioReaderWebView: UIWebView { } else { if action == #selector(highlight(_:)) || (action == #selector(define(_:)) && isOneWord) - || (action == #selector(play(_:)) && (book.hasAudio() || readerConfig.enableTTS)) + || (action == #selector(play(_:)) && (self.book?.hasAudio() == true || readerConfig.enableTTS)) || (action == #selector(share(_:)) && readerConfig.allowSharing) || (action == #selector(copy(_:)) && readerConfig.allowSharing) { return true @@ -233,7 +238,7 @@ open class FolioReaderWebView: UIWebView { // default menu menuItems = [highlightItem, defineItem, shareItem] - if book.hasAudio() || readerConfig.enableTTS { + if (self.book?.hasAudio() == true || readerConfig.enableTTS) { menuItems.insert(playAudioItem, at: 0) } From 88da69d8bf8a33a201ae45bdedfc6cea95bad9d0 Mon Sep 17 00:00:00 2001 From: Kevin Delord Date: Tue, 28 Mar 2017 19:57:58 +0200 Subject: [PATCH 005/110] ReaderContainer: improve usage --- Source/FolioReaderAudioPlayer.swift | 2 ++ Source/FolioReaderCenter.swift | 18 ++++++++++-------- Source/FolioReaderKit.swift | 16 ++++++++-------- Source/FolioReaderWebView.swift | 4 ++-- 4 files changed, 22 insertions(+), 18 deletions(-) diff --git a/Source/FolioReaderAudioPlayer.swift b/Source/FolioReaderAudioPlayer.swift index b7f0a357f..daf4638b1 100644 --- a/Source/FolioReaderAudioPlayer.swift +++ b/Source/FolioReaderAudioPlayer.swift @@ -11,6 +11,8 @@ import AVFoundation import MediaPlayer open class FolioReaderAudioPlayer: NSObject { + + // TODO_SMF: remove `!` var isTextToSpeech = false var synthesizer: AVSpeechSynthesizer! var playing = false diff --git a/Source/FolioReaderCenter.swift b/Source/FolioReaderCenter.swift index 18abc8888..8f1c398b3 100755 --- a/Source/FolioReaderCenter.swift +++ b/Source/FolioReaderCenter.swift @@ -337,10 +337,10 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo if readerConfig.shouldHideNavigationOnTap == false { return } let shouldHide = true - FolioReader.shared.readerContainer.shouldHideStatusBar = shouldHide + self.readerContainer?.shouldHideStatusBar = shouldHide UIView.animate(withDuration: 0.25, animations: { - FolioReader.shared.readerContainer.setNeedsStatusBarAppearanceUpdate() + self.readerContainer?.setNeedsStatusBarAppearanceUpdate() // Show minutes indicator // self.pageIndicatorView.minutesLabel.alpha = 0 @@ -352,10 +352,10 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo configureNavBar() let shouldHide = false - FolioReader.shared.readerContainer.shouldHideStatusBar = shouldHide + self.readerContainer?.shouldHideStatusBar = shouldHide UIView.animate(withDuration: 0.25, animations: { - FolioReader.shared.readerContainer.setNeedsStatusBarAppearanceUpdate() + self.readerContainer?.setNeedsStatusBarAppearanceUpdate() }) navigationController?.setNavigationBarHidden(shouldHide, animated: true) } @@ -363,13 +363,15 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo func toggleBars() { if readerConfig.shouldHideNavigationOnTap == false { return } - let shouldHide = !navigationController!.isNavigationBarHidden - if !shouldHide { configureNavBar() } + let shouldHide = !self.navigationController!.isNavigationBarHidden + if (shouldHide == false) { + self.configureNavBar() + } - FolioReader.shared.readerContainer.shouldHideStatusBar = shouldHide + self.readerContainer?.shouldHideStatusBar = shouldHide UIView.animate(withDuration: 0.25, animations: { - FolioReader.shared.readerContainer.setNeedsStatusBarAppearanceUpdate() + self.readerContainer?.setNeedsStatusBarAppearanceUpdate() // Show minutes indicator // self.pageIndicatorView.minutesLabel.alpha = shouldHide ? 0 : 1 diff --git a/Source/FolioReaderKit.swift b/Source/FolioReaderKit.swift index 878c7ca72..d7b308efd 100755 --- a/Source/FolioReaderKit.swift +++ b/Source/FolioReaderKit.swift @@ -83,21 +83,21 @@ open class FolioReader: NSObject { fileprivate override init() {} /// Custom unzip path - open var unzipPath: String? + open var unzipPath : String? /// FolioReaderDelegate - open weak var delegate: FolioReaderDelegate? + open weak var delegate : FolioReaderDelegate? - open weak var readerCenter: FolioReaderCenter? { - return self.readerContainer.centerViewController + open weak var readerCenter : FolioReaderCenter? { + return self.readerContainer?.centerViewController } // TODO_SMF: remove `!` - open weak var readerContainer: FolioReaderContainer! - open weak var readerAudioPlayer: FolioReaderAudioPlayer? + open weak var readerContainer : FolioReaderContainer? + open weak var readerAudioPlayer : FolioReaderAudioPlayer? // TODO_SMF: remove/rename static UserDefaults object. - class var defaults : UserDefaults { + class var defaults : UserDefaults { return UserDefaults.standard } @@ -110,7 +110,7 @@ open class FolioReader: NSObject { /// Check if layout needs to change to fit Right To Left class var needsRTLChange: Bool { // TODO_SMF: after readerConfig has been migrated, use local variables instead. Plus create a static class getter. - return (FolioReader.shared.readerContainer.book?.spine.isRtl == true && readerConfig.scrollDirection == .horizontal) + return (FolioReader.shared.readerContainer?.book?.spine.isRtl == true && readerConfig.scrollDirection == .horizontal) } /// Check if current theme is Night mode diff --git a/Source/FolioReaderWebView.swift b/Source/FolioReaderWebView.swift index 152704909..49ed16149 100644 --- a/Source/FolioReaderWebView.swift +++ b/Source/FolioReaderWebView.swift @@ -131,13 +131,13 @@ open class FolioReaderWebView: UIWebView { func define(_ sender: UIMenuController?) { let selectedText = js("getSelectedText()") - setMenuVisible(false) + self.setMenuVisible(false) self.clearTextSelection() let vc = UIReferenceLibraryViewController(term: selectedText! ) vc.view.tintColor = readerConfig.tintColor - FolioReader.shared.readerContainer.show(vc, sender: nil) + FolioReader.shared.readerContainer?.show(vc, sender: nil) } func play(_ sender: UIMenuController?) { From e7c03222dc95982d7fae106ef1cdc041168bd999 Mon Sep 17 00:00:00 2001 From: Kevin Delord Date: Tue, 28 Mar 2017 21:07:27 +0200 Subject: [PATCH 006/110] Refactor reader config --- Source/FolioReaderCenter.swift | 142 +++++++++++++----------- Source/FolioReaderChapterList.swift | 11 +- Source/FolioReaderChapterListCell.swift | 2 +- Source/FolioReaderContainer.swift | 68 ++++++------ Source/FolioReaderFontsMenu.swift | 45 ++++---- Source/FolioReaderHighlightList.swift | 19 ++-- Source/FolioReaderKit.swift | 34 +++--- Source/FolioReaderPage.swift | 31 +++--- Source/FolioReaderPageIndicator.swift | 23 ++-- Source/FolioReaderPlayerMenu.swift | 38 ++++--- Source/FolioReaderQuoteShare.swift | 43 +++---- Source/FolioReaderWebView.swift | 37 +++--- Source/Models/Highlight+Helper.swift | 17 ++- Source/PageViewController.swift | 11 +- Source/ScrollScrubber.swift | 23 ++-- 15 files changed, 310 insertions(+), 234 deletions(-) diff --git a/Source/FolioReaderCenter.swift b/Source/FolioReaderCenter.swift index 8f1c398b3..426586462 100755 --- a/Source/FolioReaderCenter.swift +++ b/Source/FolioReaderCenter.swift @@ -48,7 +48,7 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo /// This delegate receives the events from current page open weak var pageDelegate : FolioReaderPageDelegate? - open weak var readerContainer : FolioReaderContainer? + open var readerContainer : FolioReaderContainer /// The current visible page on reader open fileprivate(set) var currentPage: FolioReaderPage? @@ -76,22 +76,27 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo fileprivate var currentOrientation: UIInterfaceOrientation? fileprivate var book : FRBook? { - return self.readerContainer?.book + // TODO_SMF: remove optional + return self.readerContainer.book + } + + fileprivate var readerConfig : FolioReaderConfig { + return self.readerContainer.readerConfig } // MARK: - Init init(withContainer readerContainer: FolioReaderContainer) { - super.init(nibName: nil, bundle: Bundle.frameworkBundle()) - self.readerContainer = readerContainer + super.init(nibName: nil, bundle: Bundle.frameworkBundle()) + + self.initialization() } - - required public init?(coder aDecoder: NSCoder) { - super.init(coder: aDecoder) - self.initialization() + required public init?(coder aDecoder: NSCoder) { + // TODO_SMF_QUESTION: is that ok? do 'we' really support NSCoding? + fatalError("This class doesn't support NSCoding.") } /** @@ -99,7 +104,7 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo */ fileprivate func initialization() { - if (readerConfig.hideBars == true) { + if (self.readerConfig.hideBars == true) { self.pageIndicatorHeight = 0 } @@ -127,7 +132,7 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo collectionViewLayout.minimumInteritemSpacing = 0 collectionViewLayout.scrollDirection = .direction() - let background = isNight(readerConfig.nightModeBackground, UIColor.white) + let background = isNight(self.readerConfig.nightModeBackground, UIColor.white) view.backgroundColor = background // CollectionView @@ -156,7 +161,7 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo configureNavBar() // Page indicator view - if !readerConfig.hidePageIndicator { + if (self.readerConfig.hidePageIndicator == false) { pageIndicatorView = FolioReaderPageIndicator(frame: self.frameForPageIndicatorView()) if let pageIndicatorView = pageIndicatorView { view.addSubview(pageIndicatorView) @@ -209,12 +214,12 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo } fileprivate func frameForScrollScrubber() -> CGRect { - let scrubberY: CGFloat = ((readerConfig.shouldHideNavigationOnTap == true || readerConfig.hideBars == true) ? 50 : 74) + let scrubberY: CGFloat = ((self.readerConfig.shouldHideNavigationOnTap == true || self.readerConfig.hideBars == true) ? 50 : 74) return CGRect(x: pageWidth + 10, y: scrubberY, width: 40, height: pageHeight - 100) } func configureNavBar() { - let navBackground = isNight(readerConfig.nightModeMenuBackground, UIColor.white) + let navBackground = isNight(self.readerConfig.nightModeMenuBackground, UIColor.white) let tintColor = readerConfig.tintColor let navText = isNight(UIColor.white, UIColor.black) let font = UIFont(name: "Avenir-Light", size: 17)! @@ -238,11 +243,11 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo var rightBarIcons = [UIBarButtonItem]() - if readerConfig.allowSharing { + if (self.readerConfig.allowSharing == true) { rightBarIcons.append(UIBarButtonItem(image: shareIcon, style: .plain, target: self, action:#selector(shareChapter(_:)))) } - if (self.book?.hasAudio() == true || readerConfig.enableTTS) { + if (self.book?.hasAudio() == true || self.readerConfig.enableTTS == true) { rightBarIcons.append(UIBarButtonItem(image: audioIcon, style: .plain, target: self, action:#selector(presentPlayerMenu(_:)))) } @@ -301,14 +306,14 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo pageOffsetRate = pageScrollView.contentOffset.forDirection() / pageScrollView.contentSize.forDirection() // Change layout - readerConfig.scrollDirection = direction - collectionViewLayout.scrollDirection = .direction() - currentPage.setNeedsLayout() - collectionView.collectionViewLayout.invalidateLayout() - collectionView.setContentOffset(frameForPage(currentPageNumber).origin, animated: false) + self.readerConfig.scrollDirection = direction + self.collectionViewLayout.scrollDirection = .direction() + self.currentPage?.setNeedsLayout() + self.collectionView.collectionViewLayout.invalidateLayout() + self.collectionView.setContentOffset(frameForPage(currentPageNumber).origin, animated: false) // Page progressive direction - setCollectionViewProgressiveDirection() + self.setCollectionViewProgressiveDirection() delay(0.2) { self.setPageProgressiveDirection(currentPage) } @@ -320,7 +325,7 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo var pageOffset = pageScrollView.contentSize.forDirection() * self.pageOffsetRate // Fix the offset for paged scroll - if readerConfig.scrollDirection == .horizontal { + if (self.readerConfig.scrollDirection == .horizontal) { let page = round(pageOffset / pageWidth) pageOffset = page * pageWidth } @@ -332,51 +337,55 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo // MARK: Status bar and Navigation bar + // TODO_SMF: refactor similar code func hideBars() { - if readerConfig.shouldHideNavigationOnTap == false { return } + guard (self.readerConfig.shouldHideNavigationOnTap == true) else { + return + } - let shouldHide = true - self.readerContainer?.shouldHideStatusBar = shouldHide + self.readerContainer.shouldHideStatusBar = true UIView.animate(withDuration: 0.25, animations: { - self.readerContainer?.setNeedsStatusBarAppearanceUpdate() + self.readerContainer.setNeedsStatusBarAppearanceUpdate() // Show minutes indicator // self.pageIndicatorView.minutesLabel.alpha = 0 }) - navigationController?.setNavigationBarHidden(shouldHide, animated: true) + navigationController?.setNavigationBarHidden(true, animated: true) } func showBars() { configureNavBar() - let shouldHide = false - self.readerContainer?.shouldHideStatusBar = shouldHide + let shouldHide = + self.readerContainer.shouldHideStatusBar = false UIView.animate(withDuration: 0.25, animations: { - self.readerContainer?.setNeedsStatusBarAppearanceUpdate() + self.readerContainer.setNeedsStatusBarAppearanceUpdate() }) - navigationController?.setNavigationBarHidden(shouldHide, animated: true) + navigationController?.setNavigationBarHidden(false, animated: true) } func toggleBars() { - if readerConfig.shouldHideNavigationOnTap == false { return } + guard (self.readerConfig.shouldHideNavigationOnTap == true) else { + return + } - let shouldHide = !self.navigationController!.isNavigationBarHidden + let shouldHide = (!self.navigationController!.isNavigationBarHidden) if (shouldHide == false) { self.configureNavBar() } - self.readerContainer?.shouldHideStatusBar = shouldHide + self.readerContainer.shouldHideStatusBar = shouldHide UIView.animate(withDuration: 0.25, animations: { - self.readerContainer?.setNeedsStatusBarAppearanceUpdate() + self.readerContainer.setNeedsStatusBarAppearanceUpdate() // Show minutes indicator // self.pageIndicatorView.minutesLabel.alpha = shouldHide ? 0 : 1 }) - navigationController?.setNavigationBarHidden(shouldHide, animated: true) + self.navigationController?.setNavigationBarHidden(shouldHide, animated: true) } // MARK: UICollectionViewDataSource @@ -402,44 +411,47 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo setPageProgressiveDirection(cell) // Configure the cell - if let resource = self.book?.spine.spineReferences[(indexPath as NSIndexPath).row].resource, - var html = try? String(contentsOfFile: resource.fullHref, encoding: String.Encoding.utf8) { - let mediaOverlayStyleColors = "\"\(readerConfig.mediaOverlayColor.hexString(false))\", \"\(readerConfig.mediaOverlayColor.highlightColor().hexString(false))\"" + guard + let resource = self.book?.spine.spineReferences[(indexPath as NSIndexPath).row].resource, + var html = try? String(contentsOfFile: resource.fullHref, encoding: String.Encoding.utf8) else { + return cell + } - // Inject CSS - let jsFilePath = Bundle.frameworkBundle().path(forResource: "Bridge", ofType: "js") - let cssFilePath = Bundle.frameworkBundle().path(forResource: "Style", ofType: "css") - let cssTag = "" - let jsTag = "" + - "" + let mediaOverlayStyleColors = "\"\(self.readerConfig.mediaOverlayColor.hexString(false))\", \"\(self.readerConfig.mediaOverlayColor.highlightColor().hexString(false))\"" - let toInject = "\n\(cssTag)\n\(jsTag)\n" - html = html.replacingOccurrences(of: "", with: toInject) + // Inject CSS + let jsFilePath = Bundle.frameworkBundle().path(forResource: "Bridge", ofType: "js") + let cssFilePath = Bundle.frameworkBundle().path(forResource: "Style", ofType: "css") + let cssTag = "" + let jsTag = "" + + "" - // Font class name - var classes = FolioReader.currentFont.cssIdentifier - classes += " "+FolioReader.currentMediaOverlayStyle.className() + let toInject = "\n\(cssTag)\n\(jsTag)\n" + html = html.replacingOccurrences(of: "", with: toInject) - // Night mode - if FolioReader.nightMode { - classes += " nightMode" - } + // Font class name + var classes = FolioReader.currentFont.cssIdentifier + classes += " "+FolioReader.currentMediaOverlayStyle.className() - // Font Size - classes += " \(FolioReader.currentFontSize.cssIdentifier)" + // Night mode + if FolioReader.nightMode { + classes += " nightMode" + } - html = html.replacingOccurrences(of: " CGSize { return CGSize(width: collectionView.frame.width, height: collectionView.frame.height) @@ -513,7 +525,7 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo var pageOffset = currentPage.webView.scrollView.contentSize.forDirection() * pageOffsetRate // Fix the offset for paged scroll - if readerConfig.scrollDirection == .horizontal { + if (self.readerConfig.scrollDirection == .horizontal && pageWidth != 0) { let page = round(pageOffset / pageWidth) pageOffset = page * pageWidth } diff --git a/Source/FolioReaderChapterList.swift b/Source/FolioReaderChapterList.swift index 0d8fa702a..70e8eabbd 100755 --- a/Source/FolioReaderChapterList.swift +++ b/Source/FolioReaderChapterList.swift @@ -31,14 +31,19 @@ class FolioReaderChapterList: UITableViewController { return FolioReader.shared.readerContainer?.book } + fileprivate var readerConfig : FolioReaderConfig { + // TODO_SMF: remove this getter + return FolioReader.shared.readerContainer!.readerConfig + } + override func viewDidLoad() { super.viewDidLoad() // Register cell classes self.tableView.register(FolioReaderChapterListCell.self, forCellReuseIdentifier: reuseIdentifier) self.tableView.separatorInset = UIEdgeInsets.zero - self.tableView.backgroundColor = isNight(readerConfig.nightModeMenuBackground, readerConfig.menuBackgroundColor) - self.tableView.separatorColor = isNight(readerConfig.nightModeSeparatorColor, readerConfig.menuSeparatorColor) + self.tableView.backgroundColor = isNight(self.readerConfig.nightModeMenuBackground, self.readerConfig.menuBackgroundColor) + self.tableView.separatorColor = isNight(self.readerConfig.nightModeSeparatorColor, self.readerConfig.menuSeparatorColor) self.tableView.rowHeight = UITableViewAutomaticDimension self.tableView.estimatedRowHeight = 50 @@ -81,7 +86,7 @@ class FolioReaderChapterList: UITableViewController { let reference = self.book?.spine.spineReferences[safe: currentPageNumber - 1], (tocReference.resource != nil) { let resource = reference.resource - cell.indexLabel.textColor = (tocReference.resource == resource ? readerConfig.tintColor : readerConfig.menuTextColor) + cell.indexLabel.textColor = (tocReference.resource == resource ? self.readerConfig.tintColor : self.readerConfig.menuTextColor) } cell.layoutMargins = UIEdgeInsets.zero diff --git a/Source/FolioReaderChapterListCell.swift b/Source/FolioReaderChapterListCell.swift index b6c88e11a..87afceedb 100755 --- a/Source/FolioReaderChapterListCell.swift +++ b/Source/FolioReaderChapterListCell.swift @@ -18,7 +18,7 @@ class FolioReaderChapterListCell: UITableViewCell { indexLabel.numberOfLines = 0 indexLabel.translatesAutoresizingMaskIntoConstraints = false indexLabel.font = UIFont(name: "Avenir-Light", size: 17) - indexLabel.textColor = readerConfig.menuTextColor + indexLabel.textColor = FolioReader.shared.readerContainer?.readerConfig.menuTextColor contentView.addSubview(indexLabel) // Configure cell contraints diff --git a/Source/FolioReaderContainer.swift b/Source/FolioReaderContainer.swift index ac0ea34ba..f1543afe1 100755 --- a/Source/FolioReaderContainer.swift +++ b/Source/FolioReaderContainer.swift @@ -9,20 +9,17 @@ import UIKit import FontBlaster -// TODO_SMF: remove static variables -var readerConfig: FolioReaderConfig! - /// Reader container open class FolioReaderContainer : UIViewController { - // TODO_SMF: remove `!` - var centerNavigationController : UINavigationController! - var centerViewController : FolioReaderCenter! + var centerNavigationController : UINavigationController? + var centerViewController : FolioReaderCenter? var audioPlayer : FolioReaderAudioPlayer? var shouldHideStatusBar = true var shouldRemoveEpub = true var epubPath : String? var book : FRBook? + var readerConfig : FolioReaderConfig fileprivate var folioReader : FolioReader? fileprivate var errorOnLoad = false @@ -39,20 +36,19 @@ open class FolioReaderContainer : UIViewController { - returns: `self`, initialized using the `FolioReaderConfig`. */ public init(withConfig config: FolioReaderConfig, folioReader: FolioReader, epubPath path: String, removeEpub: Bool = true) { - super.init(nibName: nil, bundle: Bundle.frameworkBundle()) - - readerConfig = config + self.readerConfig = config self.folioReader = folioReader self.epubPath = path self.shouldRemoveEpub = removeEpub - + + super.init(nibName: nil, bundle: Bundle.frameworkBundle()) + self.initialization() } required public init?(coder aDecoder: NSCoder) { - super.init(coder: aDecoder) - - self.initialization() + // TODO_SMF_QUESTION: is that ok? do 'we' really support NSCoding? + fatalError("This class doesn't support NSCoding.") } /** @@ -85,7 +81,7 @@ open class FolioReaderContainer : UIViewController { - parameter removeEpub: Should delete the original file after unzip? Default to `true` so the ePub will be unziped only once. */ open func setupConfig(_ config: FolioReaderConfig, folioReader: FolioReader, epubPath path: String, removeEpub: Bool = true) { - readerConfig = config + self.readerConfig = config self.folioReader = folioReader self.epubPath = path self.shouldRemoveEpub = removeEpub @@ -95,34 +91,42 @@ open class FolioReaderContainer : UIViewController { override open func viewDidLoad() { super.viewDidLoad() - - readerConfig.canChangeScrollDirection = isDirection(readerConfig.canChangeScrollDirection, readerConfig.canChangeScrollDirection, false) + + // TODO_SMF: wtf + let canChangeScrollDirection = self.readerConfig.canChangeScrollDirection + self.readerConfig.canChangeScrollDirection = isDirection(canChangeScrollDirection, canChangeScrollDirection, false) // If user can change scroll direction use the last saved - if readerConfig.canChangeScrollDirection { + if (self.readerConfig.canChangeScrollDirection == true) { var scrollDirection = (FolioReaderScrollDirection(rawValue: (self.folioReader?.currentScrollDirection ?? 0)) ?? .vertical) - if (scrollDirection == .defaultVertical && readerConfig.scrollDirection != .defaultVertical) { - scrollDirection = readerConfig.scrollDirection + if (scrollDirection == .defaultVertical && self.readerConfig.scrollDirection != .defaultVertical) { + scrollDirection = self.readerConfig.scrollDirection } - readerConfig.scrollDirection = scrollDirection + self.readerConfig.scrollDirection = scrollDirection } - readerConfig.shouldHideNavigationOnTap = ((readerConfig.hideBars == true) ? true : readerConfig.shouldHideNavigationOnTap) + let hideBars = (self.readerConfig.hideBars ?? false) + self.readerConfig.shouldHideNavigationOnTap = ((hideBars == true) ? true : self.readerConfig.shouldHideNavigationOnTap) self.centerViewController = FolioReaderCenter(withContainer: self) - self.centerNavigationController = UINavigationController(rootViewController: self.centerViewController) - self.centerNavigationController.setNavigationBarHidden(readerConfig.shouldHideNavigationOnTap, animated: false) - self.view.addSubview(self.centerNavigationController.view) - self.addChildViewController(self.centerNavigationController) - self.centerNavigationController.didMove(toParentViewController: self) + if let rootViewController = self.centerViewController { + self.centerNavigationController = UINavigationController(rootViewController: rootViewController) + } + + self.centerNavigationController?.setNavigationBarHidden(self.readerConfig.shouldHideNavigationOnTap, animated: false) + if let _centerNavigationController = self.centerNavigationController { + self.view.addSubview(_centerNavigationController.view) + self.addChildViewController(_centerNavigationController) + } + self.centerNavigationController?.didMove(toParentViewController: self) - if (readerConfig.hideBars == true) { - readerConfig.shouldHideNavigationOnTap = false + if (self.readerConfig.hideBars == true) { + self.readerConfig.shouldHideNavigationOnTap = false self.navigationController?.navigationBar.isHidden = true - self.centerViewController.pageIndicatorHeight = 0 + self.centerViewController?.pageIndicatorHeight = 0 } // Read async book @@ -146,11 +150,11 @@ open class FolioReaderContainer : UIViewController { DispatchQueue.main.async(execute: { // Add audio player if needed - if (self.book?.hasAudio() == true || readerConfig.enableTTS) { + if (self.book?.hasAudio() == true || self.readerConfig.enableTTS == true) { self.addAudioPlayer() } - self.centerViewController.reloadData() + self.centerViewController?.reloadData() self.folioReader?.isReaderReady = true @@ -184,7 +188,7 @@ open class FolioReaderContainer : UIViewController { // MARK: - Status Bar override open var prefersStatusBarHidden: Bool { - return (readerConfig.shouldHideNavigationOnTap == false ? false : shouldHideStatusBar) + return (self.readerConfig.shouldHideNavigationOnTap == false ? false : self.shouldHideStatusBar) } override open var preferredStatusBarUpdateAnimation: UIStatusBarAnimation { diff --git a/Source/FolioReaderFontsMenu.swift b/Source/FolioReaderFontsMenu.swift index b61f261bb..c78924bda 100644 --- a/Source/FolioReaderFontsMenu.swift +++ b/Source/FolioReaderFontsMenu.swift @@ -70,6 +70,11 @@ public enum FolioReaderFontSize: Int { class FolioReaderFontsMenu: UIViewController, SMSegmentViewDelegate, UIGestureRecognizerDelegate { var menuView: UIView! + + fileprivate var readerConfig : FolioReaderConfig { + // TODO_SMF: remove this getter + return FolioReader.shared.readerContainer!.readerConfig + } override func viewDidLoad() { super.viewDidLoad() @@ -84,9 +89,9 @@ class FolioReaderFontsMenu: UIViewController, SMSegmentViewDelegate, UIGestureRe view.addGestureRecognizer(tapGesture) // Menu view - let visibleHeight: CGFloat = readerConfig.canChangeScrollDirection ? 222 : 170 + let visibleHeight: CGFloat = self.readerConfig.canChangeScrollDirection ? 222 : 170 menuView = UIView(frame: CGRect(x: 0, y: view.frame.height-visibleHeight, width: view.frame.width, height: view.frame.height)) - menuView.backgroundColor = isNight(readerConfig.nightModeMenuBackground, UIColor.white) + menuView.backgroundColor = isNight(self.readerConfig.nightModeMenuBackground, UIColor.white) menuView.autoresizingMask = .flexibleWidth menuView.layer.shadowColor = UIColor.black.cgColor menuView.layer.shadowOffset = CGSize(width: 0, height: 0) @@ -98,7 +103,7 @@ class FolioReaderFontsMenu: UIViewController, SMSegmentViewDelegate, UIGestureRe view.addSubview(menuView) let normalColor = UIColor(white: 0.5, alpha: 0.7) - let selectedColor = readerConfig.tintColor + let selectedColor = self.readerConfig.tintColor let sun = UIImage(readerImageNamed: "icon-sun") let moon = UIImage(readerImageNamed: "icon-moon") let fontSmall = UIImage(readerImageNamed: "icon-font-small") @@ -114,7 +119,7 @@ class FolioReaderFontsMenu: UIViewController, SMSegmentViewDelegate, UIGestureRe // Day night mode let dayNight = SMSegmentView(frame: CGRect(x: 0, y: 0, width: view.frame.width, height: 55), - separatorColour: readerConfig.nightModeSeparatorColor, + separatorColour: self.readerConfig.nightModeSeparatorColor, separatorWidth: 1, segmentProperties: [ keySegmentTitleFont: UIFont(name: "Avenir-Light", size: 17)!, @@ -126,15 +131,15 @@ class FolioReaderFontsMenu: UIViewController, SMSegmentViewDelegate, UIGestureRe ]) dayNight.delegate = self dayNight.tag = 1 - dayNight.addSegmentWithTitle(readerConfig.localizedFontMenuDay, onSelectionImage: sunSelected, offSelectionImage: sunNormal) - dayNight.addSegmentWithTitle(readerConfig.localizedFontMenuNight, onSelectionImage: moonSelected, offSelectionImage: moonNormal) + dayNight.addSegmentWithTitle(self.readerConfig.localizedFontMenuDay, onSelectionImage: sunSelected, offSelectionImage: sunNormal) + dayNight.addSegmentWithTitle(self.readerConfig.localizedFontMenuNight, onSelectionImage: moonSelected, offSelectionImage: moonNormal) dayNight.selectSegmentAtIndex(FolioReader.nightMode.hashValue) menuView.addSubview(dayNight) // Separator let line = UIView(frame: CGRect(x: 0, y: dayNight.frame.height+dayNight.frame.origin.y, width: view.frame.width, height: 1)) - line.backgroundColor = readerConfig.nightModeSeparatorColor + line.backgroundColor = self.readerConfig.nightModeSeparatorColor menuView.addSubview(line) // Fonts adjust @@ -164,7 +169,7 @@ class FolioReaderFontsMenu: UIViewController, SMSegmentViewDelegate, UIGestureRe // Separator 2 let line2 = UIView(frame: CGRect(x: 0, y: fontName.frame.height+fontName.frame.origin.y, width: view.frame.width, height: 1)) - line2.backgroundColor = readerConfig.nightModeSeparatorColor + line2.backgroundColor = self.readerConfig.nightModeSeparatorColor menuView.addSubview(line2) // Font slider size @@ -180,7 +185,7 @@ class FolioReaderFontsMenu: UIViewController, SMSegmentViewDelegate, UIGestureRe slider.thumbColor = selectedColor slider.backgroundColor = UIColor.clear - slider.tintColor = readerConfig.nightModeSeparatorColor + slider.tintColor = self.readerConfig.nightModeSeparatorColor slider.minimumValue = 0 slider.value = CGFloat(FolioReader.currentFontSize.rawValue) slider.addTarget(self, action: #selector(FolioReaderFontsMenu.sliderValueChanged(_:)), for: UIControlEvents.valueChanged) @@ -204,11 +209,13 @@ class FolioReaderFontsMenu: UIViewController, SMSegmentViewDelegate, UIGestureRe menuView.addSubview(fontBigView) // Only continues if user can change scroll direction - guard readerConfig.canChangeScrollDirection else { return } + guard (self.readerConfig.canChangeScrollDirection == true) else { + return + } // Separator 3 let line3 = UIView(frame: CGRect(x: 0, y: line2.frame.origin.y+56, width: view.frame.width, height: 1)) - line3.backgroundColor = readerConfig.nightModeSeparatorColor + line3.backgroundColor = self.readerConfig.nightModeSeparatorColor menuView.addSubview(line3) let vertical = UIImage(readerImageNamed: "icon-menu-vertical") @@ -220,7 +227,7 @@ class FolioReaderFontsMenu: UIViewController, SMSegmentViewDelegate, UIGestureRe // Layout direction let layoutDirection = SMSegmentView(frame: CGRect(x: 0, y: line3.frame.origin.y, width: view.frame.width, height: 55), - separatorColour: readerConfig.nightModeSeparatorColor, + separatorColour: self.readerConfig.nightModeSeparatorColor, separatorWidth: 1, segmentProperties: [ keySegmentTitleFont: UIFont(name: "Avenir-Light", size: 17)!, @@ -232,13 +239,13 @@ class FolioReaderFontsMenu: UIViewController, SMSegmentViewDelegate, UIGestureRe ]) layoutDirection.delegate = self layoutDirection.tag = 3 - layoutDirection.addSegmentWithTitle(readerConfig.localizedLayoutVertical, onSelectionImage: verticalSelected, offSelectionImage: verticalNormal) - layoutDirection.addSegmentWithTitle(readerConfig.localizedLayoutHorizontal, onSelectionImage: horizontalSelected, offSelectionImage: horizontalNormal) + layoutDirection.addSegmentWithTitle(self.readerConfig.localizedLayoutVertical, onSelectionImage: verticalSelected, offSelectionImage: verticalNormal) + layoutDirection.addSegmentWithTitle(self.readerConfig.localizedLayoutHorizontal, onSelectionImage: horizontalSelected, offSelectionImage: horizontalNormal) var scrollDirection = FolioReaderScrollDirection(rawValue: FolioReader.currentScrollDirection) - if scrollDirection == .defaultVertical && readerConfig.scrollDirection != .defaultVertical { - scrollDirection = readerConfig.scrollDirection + if scrollDirection == .defaultVertical && self.readerConfig.scrollDirection != .defaultVertical { + scrollDirection = self.readerConfig.scrollDirection } layoutDirection.selectSegmentAtIndex(scrollDirection?.rawValue ?? 0) @@ -255,7 +262,7 @@ class FolioReaderFontsMenu: UIViewController, SMSegmentViewDelegate, UIGestureRe FolioReader.nightMode = Bool(index == 1) UIView.animate(withDuration: 0.6, animations: { - self.menuView.backgroundColor = (FolioReader.nightMode ?readerConfig.nightModeBackground : UIColor.white) + self.menuView.backgroundColor = (FolioReader.nightMode ? self.readerConfig.nightModeBackground : UIColor.white) }) } else if segmentView.tag == 2 { @@ -286,7 +293,7 @@ class FolioReaderFontsMenu: UIViewController, SMSegmentViewDelegate, UIGestureRe func tapGesture() { dismiss() - if readerConfig.shouldHideNavigationOnTap == false { + if (self.readerConfig.shouldHideNavigationOnTap == false) { FolioReader.shared.readerCenter?.showBars() } } @@ -301,6 +308,6 @@ class FolioReaderFontsMenu: UIViewController, SMSegmentViewDelegate, UIGestureRe // MARK: - Status Bar override var prefersStatusBarHidden : Bool { - return readerConfig.shouldHideNavigationOnTap == true + return (self.readerConfig.shouldHideNavigationOnTap == true) } } diff --git a/Source/FolioReaderHighlightList.swift b/Source/FolioReaderHighlightList.swift index 6dfade28d..acc924fd3 100644 --- a/Source/FolioReaderHighlightList.swift +++ b/Source/FolioReaderHighlightList.swift @@ -11,14 +11,19 @@ import UIKit class FolioReaderHighlightList: UITableViewController { var highlights: [Highlight]! - + + fileprivate var readerConfig : FolioReaderConfig { + // TODO_SMF: remove this getter + return FolioReader.shared.readerContainer!.readerConfig + } + override func viewDidLoad() { super.viewDidLoad() - tableView.register(UITableViewCell.self, forCellReuseIdentifier: reuseIdentifier) - tableView.separatorInset = UIEdgeInsets.zero - tableView.backgroundColor = isNight(readerConfig.nightModeMenuBackground, readerConfig.menuBackgroundColor) - tableView.separatorColor = isNight(readerConfig.nightModeSeparatorColor, readerConfig.menuSeparatorColor) + self.tableView.register(UITableViewCell.self, forCellReuseIdentifier: reuseIdentifier) + self.tableView.separatorInset = UIEdgeInsets.zero + self.tableView.backgroundColor = isNight(self.readerConfig.nightModeMenuBackground, self.readerConfig.menuBackgroundColor) + self.tableView.separatorColor = isNight(self.readerConfig.nightModeSeparatorColor, self.readerConfig.menuSeparatorColor) highlights = Highlight.allByBookId((kBookId as NSString).deletingPathExtension) } @@ -41,7 +46,7 @@ class FolioReaderHighlightList: UITableViewController { // Format date let dateFormatter = DateFormatter() - dateFormatter.dateFormat = readerConfig.localizedHighlightsDateFormat + dateFormatter.dateFormat = self.readerConfig.localizedHighlightsDateFormat let dateString = dateFormatter.string(from: highlight.date) // Date @@ -66,7 +71,7 @@ class FolioReaderHighlightList: UITableViewController { let range = NSRange(location: 0, length: text.length) let paragraph = NSMutableParagraphStyle() paragraph.lineSpacing = 3 - let textColor = isNight(readerConfig.menuTextColor, UIColor.black) + let textColor = isNight(self.readerConfig.menuTextColor, UIColor.black) text.addAttribute(NSParagraphStyleAttributeName, value: paragraph, range: range) text.addAttribute(NSFontAttributeName, value: UIFont(name: "Avenir-Light", size: 16)!, range: range) diff --git a/Source/FolioReaderKit.swift b/Source/FolioReaderKit.swift index d7b308efd..24458bdc3 100755 --- a/Source/FolioReaderKit.swift +++ b/Source/FolioReaderKit.swift @@ -13,8 +13,8 @@ import UIKit // MARK: - Internal constants for devices -internal let isPad = UIDevice.current.userInterfaceIdiom == .pad -internal let isPhone = UIDevice.current.userInterfaceIdiom == .phone +internal let isPad = (UIDevice.current.userInterfaceIdiom == .pad) +internal let isPhone = (UIDevice.current.userInterfaceIdiom == .phone) // TODO_SMF: create constant file @@ -88,14 +88,13 @@ open class FolioReader: NSObject { /// FolioReaderDelegate open weak var delegate : FolioReaderDelegate? + // TODO_SMF_QUESTION: male those fileprivate (or internal) to avoid public access from other class? + open weak var readerContainer : FolioReaderContainer? + open weak var readerAudioPlayer : FolioReaderAudioPlayer? open weak var readerCenter : FolioReaderCenter? { return self.readerContainer?.centerViewController } - // TODO_SMF: remove `!` - open weak var readerContainer : FolioReaderContainer? - open weak var readerAudioPlayer : FolioReaderAudioPlayer? - // TODO_SMF: remove/rename static UserDefaults object. class var defaults : UserDefaults { return UserDefaults.standard @@ -108,9 +107,8 @@ open class FolioReader: NSObject { var isReaderReady = false /// Check if layout needs to change to fit Right To Left - class var needsRTLChange: Bool { - // TODO_SMF: after readerConfig has been migrated, use local variables instead. Plus create a static class getter. - return (FolioReader.shared.readerContainer?.book?.spine.isRtl == true && readerConfig.scrollDirection == .horizontal) + var needsRTLChange: Bool { + return (self.readerContainer?.book?.spine.isRtl == true && self.readerContainer?.readerConfig.scrollDirection == .horizontal) } /// Check if current theme is Night mode @@ -127,7 +125,7 @@ open class FolioReader: NSObject { readerCenter.pageIndicatorView?.reloadColors() readerCenter.configureNavBar() readerCenter.scrollScrubber?.reloadColors() - readerCenter.collectionView.backgroundColor = (self.nightMode ? readerConfig.nightModeBackground : UIColor.white) + readerCenter.collectionView.backgroundColor = (self.nightMode ? self.readerContainer?.readerConfig.nightModeBackground : UIColor.white) }, completion: { (finished: Bool) in // TODO_SMF: add constant NotificationCenter.default.post(name: Notification.Name(rawValue: "needRefreshPageMode"), object: nil) @@ -351,6 +349,11 @@ extension FolioReader { FolioReader.shared.currentHighlightStyle = value } } + + /// Check if layout needs to change to fit Right To Left + open class var needsRTLChange: Bool { + return FolioReader.shared.needsRTLChange + } } // MARK: - Application State @@ -404,10 +407,11 @@ func isNight (_ f: T, _ l: T) -> T { - returns: The right value based on direction. */ func isDirection (_ vertical: T, _ horizontal: T, _ horizontalContentVertical: T? = nil) -> T { - switch readerConfig.scrollDirection { - case .vertical, .defaultVertical: return vertical - case .horizontal: return horizontal - case .horizontalWithVerticalContent: return horizontalContentVertical ?? vertical + let direction = (FolioReader.shared.readerContainer?.readerConfig.scrollDirection ?? .defaultVertical) + switch direction { + case .vertical, .defaultVertical: return vertical + case .horizontal: return horizontal + case .horizontalWithVerticalContent: return (horizontalContentVertical ?? vertical) } } @@ -717,7 +721,7 @@ internal extension UIImage { - returns: Returns a colored image */ func ignoreSystemTint() -> UIImage { - return self.imageTintColor(readerConfig.tintColor).withRenderingMode(.alwaysOriginal) + return self.imageTintColor(FolioReader.shared.readerContainer!.readerConfig.tintColor).withRenderingMode(.alwaysOriginal) } /** diff --git a/Source/FolioReaderPage.swift b/Source/FolioReaderPage.swift index 86cf3b62c..f1a333417 100755 --- a/Source/FolioReaderPage.swift +++ b/Source/FolioReaderPage.swift @@ -30,7 +30,12 @@ import JSQWebViewController } open class FolioReaderPage: UICollectionViewCell, UIWebViewDelegate, UIGestureRecognizerDelegate { - + + fileprivate var readerConfig : FolioReaderConfig { + // TODO_SMF: remove this getter + return FolioReader.shared.readerContainer!.readerConfig + } + weak var delegate: FolioReaderPageDelegate? // TODO_SMF: remove `!` /// The index of the current page. Note: The index start at 1! @@ -68,7 +73,7 @@ open class FolioReaderPage: UICollectionViewCell, UIWebViewDelegate, UIGestureRe if colorView == nil { colorView = UIView() - colorView.backgroundColor = readerConfig.nightModeBackground + colorView.backgroundColor = self.readerConfig.nightModeBackground webView.scrollView.addSubview(colorView) } @@ -95,13 +100,13 @@ open class FolioReaderPage: UICollectionViewCell, UIWebViewDelegate, UIGestureRe } func webViewFrame() -> CGRect { - guard readerConfig.hideBars == false else { + guard (self.readerConfig.hideBars == false) else { return bounds } let statusbarHeight = UIApplication.shared.statusBarFrame.size.height let navBarHeight = FolioReader.shared.readerCenter?.navigationController?.navigationBar.frame.size.height ?? CGFloat(0) - let navTotal = readerConfig.shouldHideNavigationOnTap ? 0 : statusbarHeight + navBarHeight + let navTotal = self.readerConfig.shouldHideNavigationOnTap ? 0 : statusbarHeight + navBarHeight let paddingTop: CGFloat = 20 let paddingBottom: CGFloat = 30 @@ -163,7 +168,7 @@ open class FolioReaderPage: UICollectionViewCell, UIWebViewDelegate, UIGestureRe refreshPageMode() - if (readerConfig.enableTTS && self.book?.hasAudio() == false) { + if (self.readerConfig.enableTTS == true && self.book?.hasAudio() == false) { webView.js("wrappingSentencesWithinPTags()") if let audioPlayer = FolioReader.shared.readerAudioPlayer , audioPlayer.isPlaying() { @@ -173,7 +178,7 @@ open class FolioReaderPage: UICollectionViewCell, UIWebViewDelegate, UIGestureRe let direction: ScrollDirection = FolioReader.needsRTLChange ? .positive() : .negative() - if pageScrollDirection == direction && isScrolling && readerConfig.scrollDirection != .horizontalWithVerticalContent { + if pageScrollDirection == direction && isScrolling && self.readerConfig.scrollDirection != .horizontalWithVerticalContent { scrollPageToBottom() } @@ -262,19 +267,19 @@ open class FolioReaderPage: UICollectionViewCell, UIWebViewDelegate, UIGestureRe if #available(iOS 9.0, *) { let safariVC = SFSafariViewController(url: request.url!) - safariVC.view.tintColor = readerConfig.tintColor + safariVC.view.tintColor = self.readerConfig.tintColor FolioReader.shared.readerCenter?.present(safariVC, animated: true, completion: nil) } else { let webViewController = WebViewController(url: request.url!) let nav = UINavigationController(rootViewController: webViewController) - nav.view.tintColor = readerConfig.tintColor + nav.view.tintColor = self.readerConfig.tintColor FolioReader.shared.readerCenter?.present(nav, animated: true, completion: nil) } return false } else { // Check if the url is a custom class based onClick listerner var isClassBasedOnClickListenerScheme = false - for listener in readerConfig.classBasedOnClickListeners { + for listener in self.readerConfig.classBasedOnClickListeners { if (scheme == listener.schemeName), @@ -359,7 +364,7 @@ open class FolioReaderPage: UICollectionViewCell, UIWebViewDelegate, UIGestureRe self.shouldShowBar = true }) } - } else if readerConfig.shouldHideNavigationOnTap == true { + } else if self.readerConfig.shouldHideNavigationOnTap == true { FolioReader.shared.readerCenter?.hideBars() } @@ -408,7 +413,7 @@ open class FolioReaderPage: UICollectionViewCell, UIWebViewDelegate, UIGestureRe if !anchor.isEmpty { let offset = getAnchorOffset(anchor) - switch readerConfig.scrollDirection { + switch self.readerConfig.scrollDirection { case .vertical, .defaultVertical: let isBeginning = offset < frame.forDirection()/2 @@ -432,7 +437,7 @@ open class FolioReaderPage: UICollectionViewCell, UIWebViewDelegate, UIGestureRe - returns: The element offset ready to scroll */ func getAnchorOffset(_ anchor: String) -> CGFloat { - let horizontal = readerConfig.scrollDirection == .horizontal + let horizontal = self.readerConfig.scrollDirection == .horizontal if let strOffset = webView.js("getAnchorOffset('\(anchor)', \(horizontal.description))") { return CGFloat((strOffset as NSString).floatValue) } @@ -494,7 +499,7 @@ open class FolioReaderPage: UICollectionViewCell, UIWebViewDelegate, UIGestureRe fileprivate func setupClassBasedOnClickListeners() { - for listener in readerConfig.classBasedOnClickListeners { + for listener in self.readerConfig.classBasedOnClickListeners { self.webView.js("addClassBasedOnClickListener(\"\(listener.schemeName)\", \"\(listener.querySelector)\", \"\(listener.attributeName)\", \"\(listener.selectAll)\")"); } } diff --git a/Source/FolioReaderPageIndicator.swift b/Source/FolioReaderPageIndicator.swift index bc07c798b..493a618b1 100644 --- a/Source/FolioReaderPageIndicator.swift +++ b/Source/FolioReaderPageIndicator.swift @@ -16,11 +16,16 @@ class FolioReaderPageIndicator: UIView { var currentPage: Int = 1 { didSet { self.reloadViewWithPage(self.currentPage) } } - + + fileprivate var readerConfig : FolioReaderConfig { + // TODO_SMF: remove this getter + return FolioReader.shared.readerContainer!.readerConfig + } + override init(frame: CGRect) { super.init(frame: frame) - let color = isNight(readerConfig.nightModeBackground, UIColor.white) + let color = isNight(self.readerConfig.nightModeBackground, UIColor.white) backgroundColor = color layer.shadowColor = color.cgColor layer.shadowOffset = CGSize(width: 0, height: -6) @@ -61,7 +66,7 @@ class FolioReaderPageIndicator: UIView { } func reloadColors() { - let color = isNight(readerConfig.nightModeBackground, UIColor.white) + let color = isNight(self.readerConfig.nightModeBackground, UIColor.white) backgroundColor = color // Animate the shadow color change @@ -84,19 +89,19 @@ class FolioReaderPageIndicator: UIView { let pagesRemaining = FolioReader.needsRTLChange ? totalPages-(totalPages-page+1) : totalPages-page if pagesRemaining == 1 { - pagesLabel.text = " "+readerConfig.localizedReaderOnePageLeft + pagesLabel.text = " " + self.readerConfig.localizedReaderOnePageLeft } else { - pagesLabel.text = " \(pagesRemaining) "+readerConfig.localizedReaderManyPagesLeft + pagesLabel.text = " \(pagesRemaining) " + self.readerConfig.localizedReaderManyPagesLeft } let minutesRemaining = Int(ceil(CGFloat((pagesRemaining * totalMinutes)/totalPages))) if minutesRemaining > 1 { - minutesLabel.text = "\(minutesRemaining) "+readerConfig.localizedReaderManyMinutes+" ·" + minutesLabel.text = "\(minutesRemaining) " + self.readerConfig.localizedReaderManyMinutes+" ·" } else if minutesRemaining == 1 { - minutesLabel.text = readerConfig.localizedReaderOneMinute+" ·" + minutesLabel.text = self.readerConfig.localizedReaderOneMinute+" ·" } else { - minutesLabel.text = readerConfig.localizedReaderLessThanOneMinute+" ·" + minutesLabel.text = self.readerConfig.localizedReaderLessThanOneMinute+" ·" } reloadView(updateShadow: false) @@ -107,7 +112,7 @@ extension FolioReaderPageIndicator: CAAnimationDelegate { func animationDidStop(_ anim: CAAnimation, finished flag: Bool) { // Set the shadow color to the final value of the animation is done if let keyPath = anim.value(forKeyPath: "keyPath") as? String , keyPath == "shadowColor" { - let color = isNight(readerConfig.nightModeBackground, UIColor.white) + let color = isNight(self.readerConfig.nightModeBackground, UIColor.white) layer.shadowColor = color.cgColor } } diff --git a/Source/FolioReaderPlayerMenu.swift b/Source/FolioReaderPlayerMenu.swift index bf7d1eaa7..b926c8022 100644 --- a/Source/FolioReaderPlayerMenu.swift +++ b/Source/FolioReaderPlayerMenu.swift @@ -15,6 +15,11 @@ class FolioReaderPlayerMenu: UIViewController, SMSegmentViewDelegate, UIGestureR var styleOptionBtns = [UIButton]() var viewDidAppear = false + fileprivate var readerConfig : FolioReaderConfig { + // TODO_SMF: remove this getter + return FolioReader.shared.readerContainer!.readerConfig + } + override func viewDidLoad() { super.viewDidLoad() @@ -29,7 +34,7 @@ class FolioReaderPlayerMenu: UIViewController, SMSegmentViewDelegate, UIGestureR // Menu view menuView = UIView(frame: CGRect(x: 0, y: view.frame.height-165, width: view.frame.width, height: view.frame.height)) - menuView.backgroundColor = isNight(readerConfig.nightModeMenuBackground, UIColor.white) + menuView.backgroundColor = isNight(self.readerConfig.nightModeMenuBackground, UIColor.white) menuView.autoresizingMask = .flexibleWidth menuView.layer.shadowColor = UIColor.black.cgColor menuView.layer.shadowOffset = CGSize(width: 0, height: 0) @@ -39,12 +44,9 @@ class FolioReaderPlayerMenu: UIViewController, SMSegmentViewDelegate, UIGestureR menuView.layer.rasterizationScale = UIScreen.main.scale menuView.layer.shouldRasterize = true view.addSubview(menuView) - - - let normalColor = UIColor(white: 0.5, alpha: 0.7) - let selectedColor = readerConfig.tintColor + let selectedColor = self.readerConfig.tintColor let size = 55 let padX = 32 // @NOTE: could this be improved/simplified with autolayout? @@ -96,7 +98,7 @@ class FolioReaderPlayerMenu: UIViewController, SMSegmentViewDelegate, UIGestureR // Separator let line = UIView(frame: CGRect(x: 0, y: playPauseBtn.frame.height+playPauseBtn.frame.origin.y, width: view.frame.width, height: 1)) - line.backgroundColor = readerConfig.nightModeSeparatorColor + line.backgroundColor = self.readerConfig.nightModeSeparatorColor menuView.addSubview(line) // audio playback rate adjust @@ -123,7 +125,7 @@ class FolioReaderPlayerMenu: UIViewController, SMSegmentViewDelegate, UIGestureR // Separator let line2 = UIView(frame: CGRect(x: 0, y: playbackRate.frame.height+playbackRate.frame.origin.y, width: view.frame.width, height: 1)) - line2.backgroundColor = readerConfig.nightModeSeparatorColor + line2.backgroundColor = self.readerConfig.nightModeSeparatorColor menuView.addSubview(line2) @@ -131,9 +133,9 @@ class FolioReaderPlayerMenu: UIViewController, SMSegmentViewDelegate, UIGestureR let style0 = UIButton(frame: CGRect(x: 0, y: line2.frame.height+line2.frame.origin.y, width: view.frame.width/3, height: 55)) style0.titleLabel!.textAlignment = .center style0.titleLabel!.font = UIFont(name: "Avenir-Light", size: 17) - style0.setTitleColor(isNight(readerConfig.nightModeMenuBackground, UIColor.white), for: UIControlState()) - style0.setTitleColor(isNight(readerConfig.nightModeMenuBackground, UIColor.white), for: .selected) - style0.setTitle(readerConfig.localizedPlayerMenuStyle, for: UIControlState()) + style0.setTitleColor(isNight(self.readerConfig.nightModeMenuBackground, UIColor.white), for: UIControlState()) + style0.setTitleColor(isNight(self.readerConfig.nightModeMenuBackground, UIColor.white), for: .selected) + style0.setTitle(self.readerConfig.localizedPlayerMenuStyle, for: UIControlState()) menuView.addSubview(style0); style0.titleLabel?.sizeToFit() let style0Bgd = UIView(frame: style0.titleLabel!.frame) @@ -154,7 +156,7 @@ class FolioReaderPlayerMenu: UIViewController, SMSegmentViewDelegate, UIGestureR NSUnderlineStyleAttributeName: NSUnderlineStyle.patternDot.rawValue|NSUnderlineStyle.styleSingle.rawValue, NSUnderlineColorAttributeName: normalColor ]), for: UIControlState()) - style1.setAttributedTitle(NSAttributedString(string: readerConfig.localizedPlayerMenuStyle, attributes: [ + style1.setAttributedTitle(NSAttributedString(string: self.readerConfig.localizedPlayerMenuStyle, attributes: [ NSForegroundColorAttributeName: isNight(UIColor.white, UIColor.black), NSUnderlineStyleAttributeName: NSUnderlineStyle.patternDot.rawValue|NSUnderlineStyle.styleSingle.rawValue, NSUnderlineColorAttributeName: selectedColor @@ -166,15 +168,15 @@ class FolioReaderPlayerMenu: UIViewController, SMSegmentViewDelegate, UIGestureR style2.titleLabel!.font = UIFont(name: "Avenir-Light", size: 17) style2.setTitleColor(normalColor, for: UIControlState()) style2.setTitleColor(selectedColor, for: .selected) - style2.setTitle(readerConfig.localizedPlayerMenuStyle, for: UIControlState()) + style2.setTitle(self.readerConfig.localizedPlayerMenuStyle, for: UIControlState()) menuView.addSubview(style2); // add line dividers between style buttons let style1line = UIView(frame: CGRect(x: style1.frame.origin.x, y: style1.frame.origin.y, width: 1, height: style1.frame.height)) - style1line.backgroundColor = readerConfig.nightModeSeparatorColor + style1line.backgroundColor = self.readerConfig.nightModeSeparatorColor menuView.addSubview(style1line) let style2line = UIView(frame: CGRect(x: style2.frame.origin.x, y: style2.frame.origin.y, width: 1, height: style2.frame.height)) - style2line.backgroundColor = readerConfig.nightModeSeparatorColor + style2line.backgroundColor = self.readerConfig.nightModeSeparatorColor menuView.addSubview(style2line) // select the current style @@ -214,7 +216,7 @@ class FolioReaderPlayerMenu: UIViewController, SMSegmentViewDelegate, UIGestureR // MARK: - Status Bar override var prefersStatusBarHidden : Bool { - return readerConfig.shouldHideNavigationOnTap == true + return (self.readerConfig.shouldHideNavigationOnTap == true) } // MARK: - SMSegmentView delegate @@ -250,7 +252,7 @@ class FolioReaderPlayerMenu: UIViewController, SMSegmentViewDelegate, UIGestureR btn.isSelected = btn == sender if btn.tag == MediaOverlayStyle.default.rawValue { - btn.subviews.first?.backgroundColor = btn.isSelected ? readerConfig.tintColor : UIColor(white: 0.5, alpha: 0.7) + btn.subviews.first?.backgroundColor = (btn.isSelected ? self.readerConfig.tintColor : UIColor(white: 0.5, alpha: 0.7)) } } @@ -261,9 +263,9 @@ class FolioReaderPlayerMenu: UIViewController, SMSegmentViewDelegate, UIGestureR } func closeView() { - dismiss() + self.dismiss() - if readerConfig.shouldHideNavigationOnTap == false { + if (self.readerConfig.shouldHideNavigationOnTap == false) { FolioReader.shared.readerCenter?.showBars() } } diff --git a/Source/FolioReaderQuoteShare.swift b/Source/FolioReaderQuoteShare.swift index 532fe3ec9..f55fdd53f 100644 --- a/Source/FolioReaderQuoteShare.swift +++ b/Source/FolioReaderQuoteShare.swift @@ -29,6 +29,11 @@ class FolioReaderQuoteShare: UIViewController { return FolioReader.shared.readerContainer?.book } + fileprivate var readerConfig : FolioReaderConfig { + // TODO_SMF: remove this getter + return FolioReader.shared.readerContainer!.readerConfig + } + // MARK: Init init(initWithText shareText: String) { @@ -50,8 +55,8 @@ class FolioReaderQuoteShare: UIViewController { setCloseButton() configureNavBar() - let titleAttrs = [NSForegroundColorAttributeName: readerConfig.tintColor] - let share = UIBarButtonItem(title: readerConfig.localizedShare, style: .plain, target: self, action: #selector(shareQuote(_:))) + let titleAttrs = [NSForegroundColorAttributeName: self.readerConfig.tintColor] + let share = UIBarButtonItem(title: self.readerConfig.localizedShare, style: .plain, target: self, action: #selector(shareQuote(_:))) share.setTitleTextAttributes(titleAttrs, for: UIControlState()) navigationItem.rightBarButtonItem = share @@ -61,9 +66,9 @@ class FolioReaderQuoteShare: UIViewController { } let screenBounds = isPad ? preferredContentSize : UIScreen.main.bounds.size - filterImage = UIView(frame: CGRect(x: 0, y: 0, width: screenBounds.width, height: screenBounds.width)) - filterImage.backgroundColor = readerConfig.menuSeparatorColor - view.addSubview(filterImage) + self.filterImage = UIView(frame: CGRect(x: 0, y: 0, width: screenBounds.width, height: screenBounds.width)) + self.filterImage.backgroundColor = self.readerConfig.menuSeparatorColor + view.addSubview(self.filterImage) imageView = UIImageView(frame: filterImage.bounds) filterImage.addSubview(imageView) @@ -106,7 +111,7 @@ class FolioReaderQuoteShare: UIViewController { // Attributed author let attrs = [NSFontAttributeName: UIFont(name: "Lato-Italic", size: 15)!] - let attributedString = NSMutableAttributedString(string:"\(readerConfig.localizedShareBy) ", attributes: attrs) + let attributedString = NSMutableAttributedString(string:"\(self.readerConfig.localizedShareBy) ", attributes: attrs) let attrs1 = [NSFontAttributeName: UIFont(name: "Lato-Regular", size: 15)!] let boldString = NSMutableAttributedString(string: authorName, attributes:attrs1) @@ -122,7 +127,7 @@ class FolioReaderQuoteShare: UIViewController { authorLabel.minimumScaleFactor = 0.5 filterImage.addSubview(authorLabel) - let logoImage = readerConfig.quoteCustomLogoImage + let logoImage = self.readerConfig.quoteCustomLogoImage let logoHeight = logoImage?.size.height ?? 0 logoImageView = UIImageView(image: logoImage) logoImageView.contentMode = .center @@ -155,7 +160,7 @@ class FolioReaderQuoteShare: UIViewController { collectionViewLayout.minimumInteritemSpacing = 0 collectionViewLayout.scrollDirection = .horizontal - let background = isNight(readerConfig.nightModeBackground, UIColor.white) + let background = isNight(self.readerConfig.nightModeBackground, UIColor.white) view.backgroundColor = background // CollectionView @@ -176,8 +181,8 @@ class FolioReaderQuoteShare: UIViewController { collectionView!.register(UICollectionViewCell.self, forCellWithReuseIdentifier: reuseIdentifier) // Create images - dataSource = readerConfig.quoteCustomBackgrounds - if readerConfig.quotePreserveDefaultBackgrounds { + dataSource = self.readerConfig.quoteCustomBackgrounds + if (self.readerConfig.quotePreserveDefaultBackgrounds == true) { createDefaultImages() } @@ -189,8 +194,8 @@ class FolioReaderQuoteShare: UIViewController { } func configureNavBar() { - let navBackground = isNight(readerConfig.nightModeMenuBackground, UIColor.white) - let tintColor = readerConfig.tintColor + let navBackground = isNight(self.readerConfig.nightModeMenuBackground, UIColor.white) + let tintColor = self.readerConfig.tintColor let navText = isNight(UIColor.white, UIColor.black) let font = UIFont(name: "Avenir-Light", size: 17)! setTranslucentNavigation(false, color: navBackground, tintColor: tintColor, titleColor: navText, andFont: font) @@ -252,7 +257,7 @@ class FolioReaderQuoteShare: UIViewController { // MARK: Share func shareQuote(_ sender: UIBarButtonItem) { - var subject = readerConfig.localizedShareHighlightSubject + var subject = self.readerConfig.localizedShareHighlightSubject var text = "" var bookTitle = "" var authorName = "" @@ -269,12 +274,12 @@ class FolioReaderQuoteShare: UIViewController { authorName = author.name } - text = "\(bookTitle) \n\(readerConfig.localizedShareBy) \(authorName)" + text = "\(bookTitle) \n\(self.readerConfig.localizedShareBy) \(authorName)" let imageQuote = UIImage.imageWithView(filterImage) shareItems.append(imageQuote) - if let bookShareLink = readerConfig.localizedShareWebLink { + if let bookShareLink = self.readerConfig.localizedShareWebLink { text += "\n\(bookShareLink.absoluteString)" } @@ -347,7 +352,7 @@ extension FolioReaderQuoteShare: UICollectionViewDataSource { } if selectedIndex == (indexPath as NSIndexPath).row { - cell.contentView.layer.borderColor = readerConfig.tintColor.cgColor + cell.contentView.layer.borderColor = self.readerConfig.tintColor.cgColor cell.contentView.layer.borderWidth = 3 } else { cell.contentView.layer.borderColor = UIColor(white: 0.5, alpha: 0.2).cgColor @@ -374,19 +379,19 @@ extension FolioReaderQuoteShare: UICollectionViewDelegate { guard (indexPath as NSIndexPath).row > 0 else { let alertController = UIAlertController(title: nil, message: nil, preferredStyle: .actionSheet) - let takePhoto = UIAlertAction(title: readerConfig.localizedTakePhoto, style: .default, handler: { (action) -> Void in + let takePhoto = UIAlertAction(title: self.readerConfig.localizedTakePhoto, style: .default, handler: { (action) -> Void in self.imagePicker.sourceType = .camera self.imagePicker.allowsEditing = true self.present(self.imagePicker, animated: true, completion: nil) }) - let existingPhoto = UIAlertAction(title: readerConfig.localizedChooseExisting, style: .default) { (action) -> Void in + let existingPhoto = UIAlertAction(title: self.readerConfig.localizedChooseExisting, style: .default) { (action) -> Void in self.imagePicker.sourceType = .photoLibrary self.imagePicker.allowsEditing = true self.present(self.imagePicker, animated: true, completion: nil) } - let cancel = UIAlertAction(title: readerConfig.localizedCancel, style: .cancel, handler: nil) + let cancel = UIAlertAction(title: self.readerConfig.localizedCancel, style: .cancel, handler: nil) alertController.addAction(takePhoto) alertController.addAction(existingPhoto) diff --git a/Source/FolioReaderWebView.swift b/Source/FolioReaderWebView.swift index 49ed16149..397ca32b1 100644 --- a/Source/FolioReaderWebView.swift +++ b/Source/FolioReaderWebView.swift @@ -19,10 +19,15 @@ open class FolioReaderWebView: UIWebView { return FolioReader.shared.readerContainer?.book } + fileprivate var readerConfig : FolioReaderConfig { + // TODO_SMF: remove this getter + return FolioReader.shared.readerContainer!.readerConfig + } + // MARK: - UIMenuController open override func canPerformAction(_ action: Selector, withSender sender: Any?) -> Bool { - guard readerConfig != nil && readerConfig.useReaderMenuController == true else { + guard (self.readerConfig.useReaderMenuController == true) else { return super.canPerformAction(action, withSender: sender) } @@ -33,9 +38,9 @@ open class FolioReaderWebView: UIWebView { } else { if action == #selector(highlight(_:)) || (action == #selector(define(_:)) && isOneWord) - || (action == #selector(play(_:)) && (self.book?.hasAudio() == true || readerConfig.enableTTS)) - || (action == #selector(share(_:)) && readerConfig.allowSharing) - || (action == #selector(copy(_:)) && readerConfig.allowSharing) { + || (action == #selector(play(_:)) && (self.book?.hasAudio() == true || self.readerConfig.enableTTS == true)) + || (action == #selector(share(_:)) && self.readerConfig.allowSharing == true) + || (action == #selector(copy(_:)) && self.readerConfig.allowSharing == true) { return true } return false @@ -47,7 +52,7 @@ open class FolioReaderWebView: UIWebView { func share(_ sender: UIMenuController) { let alertController = UIAlertController(title: nil, message: nil, preferredStyle: .actionSheet) - let shareImage = UIAlertAction(title: readerConfig.localizedShareImageQuote, style: .default, handler: { (action) -> Void in + let shareImage = UIAlertAction(title: self.readerConfig.localizedShareImageQuote, style: .default, handler: { (action) -> Void in if self.isShare { if let textToShare = self.js("getHighlightContent()") { FolioReader.shared.readerCenter?.presentQuoteShare(textToShare) @@ -62,7 +67,7 @@ open class FolioReaderWebView: UIWebView { self.setMenuVisible(false) }) - let shareText = UIAlertAction(title: readerConfig.localizedShareTextQuote, style: .default) { (action) -> Void in + let shareText = UIAlertAction(title: self.readerConfig.localizedShareTextQuote, style: .default) { (action) -> Void in if self.isShare { if let textToShare = self.js("getHighlightContent()") { FolioReader.shared.readerCenter?.shareHighlight(textToShare, rect: sender.menuFrame) @@ -75,7 +80,7 @@ open class FolioReaderWebView: UIWebView { self.setMenuVisible(false) } - let cancel = UIAlertAction(title: readerConfig.localizedCancel, style: .cancel, handler: nil) + let cancel = UIAlertAction(title: self.readerConfig.localizedCancel, style: .cancel, handler: nil) alertController.addAction(shareImage) alertController.addAction(shareText) @@ -136,7 +141,7 @@ open class FolioReaderWebView: UIWebView { self.clearTextSelection() let vc = UIReferenceLibraryViewController(term: selectedText! ) - vc.view.tintColor = readerConfig.tintColor + vc.view.tintColor = self.readerConfig.tintColor FolioReader.shared.readerContainer?.show(vc, sender: nil) } @@ -178,7 +183,7 @@ open class FolioReaderWebView: UIWebView { // MARK: - Create and show menu func createMenu(options: Bool) { - guard readerConfig.useReaderMenuController else { + guard (self.readerConfig.useReaderMenuController == true) else { return } @@ -195,9 +200,9 @@ open class FolioReaderWebView: UIWebView { let menuController = UIMenuController.shared - let highlightItem = UIMenuItem(title: readerConfig.localizedHighlightMenu, action: #selector(highlight(_:))) - let playAudioItem = UIMenuItem(title: readerConfig.localizedPlayMenu, action: #selector(play(_:))) - let defineItem = UIMenuItem(title: readerConfig.localizedDefineMenu, action: #selector(define(_:))) + let highlightItem = UIMenuItem(title: self.readerConfig.localizedHighlightMenu, action: #selector(highlight(_:))) + let playAudioItem = UIMenuItem(title: self.readerConfig.localizedPlayMenu, action: #selector(play(_:))) + let defineItem = UIMenuItem(title: self.readerConfig.localizedDefineMenu, action: #selector(define(_:))) let colorsItem = UIMenuItem(title: "C", image: colors) { [weak self] _ in self?.colors(menuController) } @@ -228,7 +233,7 @@ open class FolioReaderWebView: UIWebView { // menu on existing highlight if isShare { menuItems = [colorsItem, removeItem] - if readerConfig.allowSharing { + if (self.readerConfig.allowSharing == true) { menuItems.append(shareItem) } } else if isColors { @@ -238,11 +243,11 @@ open class FolioReaderWebView: UIWebView { // default menu menuItems = [highlightItem, defineItem, shareItem] - if (self.book?.hasAudio() == true || readerConfig.enableTTS) { + if (self.book?.hasAudio() == true || self.readerConfig.enableTTS == true) { menuItems.insert(playAudioItem, at: 0) } - if !readerConfig.allowSharing { + if (self.readerConfig.allowSharing == false) { menuItems.removeLast() } } @@ -284,7 +289,7 @@ open class FolioReaderWebView: UIWebView { } func setupScrollDirection() { - switch readerConfig.scrollDirection { + switch self.readerConfig.scrollDirection { case .vertical, .defaultVertical, .horizontalWithVerticalContent: scrollView.isPagingEnabled = false paginationMode = .unpaginated diff --git a/Source/Models/Highlight+Helper.swift b/Source/Models/Highlight+Helper.swift index 0362ac1c2..bde0a936d 100644 --- a/Source/Models/Highlight+Helper.swift +++ b/Source/Models/Highlight+Helper.swift @@ -80,6 +80,11 @@ public typealias Completion = (_ error: NSError?) -> () extension Highlight { + fileprivate static var readerConfig : FolioReaderConfig { + // TODO_SMF: remove this getter + return FolioReader.shared.readerContainer!.readerConfig + } + // TODO_SMF: replace try with a 'do-try-catch' or at least a 'try?'. /** @@ -89,7 +94,7 @@ extension Highlight { */ public func persist(_ completion: Completion? = nil) { do { - let realm = try! Realm(configuration: readerConfig.realmConfiguration) + let realm = try! Realm(configuration: Highlight.readerConfig.realmConfiguration) realm.beginWrite() realm.add(self, update: true) try realm.commitWrite() @@ -105,7 +110,7 @@ extension Highlight { */ public func remove() { do { - let realm = try! Realm(configuration: readerConfig.realmConfiguration) + let realm = try! Realm(configuration: Highlight.readerConfig.realmConfiguration) realm.beginWrite() realm.delete(self) try realm.commitWrite() @@ -123,7 +128,7 @@ extension Highlight { var highlight: Highlight? let predicate = NSPredicate(format:"highlightId = %@", highlightId) - let realm = try! Realm(configuration: readerConfig.realmConfiguration) + let realm = try! Realm(configuration: self.readerConfig.realmConfiguration) highlight = realm.objects(Highlight.self).filter(predicate).toArray(Highlight.self).first highlight?.remove() } @@ -138,7 +143,7 @@ extension Highlight { var highlight: Highlight? let predicate = NSPredicate(format:"highlightId = %@", highlightId) do { - let realm = try! Realm(configuration: readerConfig.realmConfiguration) + let realm = try! Realm(configuration: self.readerConfig.realmConfiguration) highlight = realm.objects(Highlight.self).filter(predicate).toArray(Highlight.self).first realm.beginWrite() @@ -162,7 +167,7 @@ extension Highlight { public static func allByBookId(_ bookId: String, andPage page: NSNumber? = nil) -> [Highlight] { var highlights: [Highlight]? let predicate = (page != nil) ? NSPredicate(format: "bookId = %@ && page = %@", bookId, page!) : NSPredicate(format: "bookId = %@", bookId) - let realm = try! Realm(configuration: readerConfig.realmConfiguration) + let realm = try! Realm(configuration: self.readerConfig.realmConfiguration) highlights = realm.objects(Highlight.self).filter(predicate).toArray(Highlight.self) return highlights! } @@ -174,7 +179,7 @@ extension Highlight { */ public static func all() -> [Highlight] { var highlights: [Highlight]? - let realm = try! Realm(configuration: readerConfig.realmConfiguration) + let realm = try! Realm(configuration: self.readerConfig.realmConfiguration) highlights = realm.objects(Highlight.self).toArray(Highlight.self) return highlights! } diff --git a/Source/PageViewController.swift b/Source/PageViewController.swift index e5c8ec632..d4382cae6 100644 --- a/Source/PageViewController.swift +++ b/Source/PageViewController.swift @@ -15,7 +15,12 @@ class PageViewController: UIPageViewController { var viewControllerOne: UIViewController! var viewControllerTwo: UIViewController! var index = FolioReader.defaults.integer(forKey: kCurrentTOCMenu) - + + fileprivate var readerConfig : FolioReaderConfig { + // TODO_SMF: remove this getter + return FolioReader.shared.readerContainer!.readerConfig + } + // MARK: Init override init(transitionStyle style: UIPageViewControllerTransitionStyle, navigationOrientation: UIPageViewControllerNavigationOrientation, options: [String : Any]?) { @@ -67,8 +72,8 @@ class PageViewController: UIPageViewController { } func configureNavBar() { - let navBackground = isNight(readerConfig.nightModeMenuBackground, UIColor.white) - let tintColor = readerConfig.tintColor + let navBackground = isNight(self.readerConfig.nightModeMenuBackground, UIColor.white) + let tintColor = self.readerConfig.tintColor let navText = isNight(UIColor.white, UIColor.black) let font = UIFont(name: "Avenir-Light", size: 17)! setTranslucentNavigation(false, color: navBackground, tintColor: tintColor, titleColor: navText, andFont: font) diff --git a/Source/ScrollScrubber.swift b/Source/ScrollScrubber.swift index 8f1b6b34d..35539a643 100644 --- a/Source/ScrollScrubber.swift +++ b/Source/ScrollScrubber.swift @@ -54,6 +54,11 @@ class ScrollScrubber: NSObject, UIScrollViewDelegate { var scrollDelta: CGFloat! var scrollDeltaTimer: Timer! + fileprivate var readerConfig : FolioReaderConfig { + // TODO_SMF: remove this getter + return FolioReader.shared.readerContainer!.readerConfig + } + var frame: CGRect! { didSet { self.slider.frame = frame @@ -74,7 +79,7 @@ class ScrollScrubber: NSObject, UIScrollViewDelegate { // less obtrusive knob and fixes jump: http://stackoverflow.com/a/22301039/484780 let thumbImg = UIImage(readerImageNamed: "knob") - let thumbImgColor = thumbImg!.imageTintColor(readerConfig.tintColor).withRenderingMode(.alwaysOriginal) + let thumbImgColor = thumbImg!.imageTintColor(self.readerConfig.tintColor).withRenderingMode(.alwaysOriginal) slider.setThumbImage(thumbImgColor, for: UIControlState()) slider.setThumbImage(thumbImgColor, for: .selected) slider.setThumbImage(thumbImgColor, for: .highlighted) @@ -86,8 +91,8 @@ class ScrollScrubber: NSObject, UIScrollViewDelegate { } func reloadColors() { - slider.minimumTrackTintColor = readerConfig.tintColor - slider.maximumTrackTintColor = isNight(readerConfig.nightModeSeparatorColor, readerConfig.menuSeparatorColor) + slider.minimumTrackTintColor = self.readerConfig.tintColor + slider.maximumTrackTintColor = isNight(self.readerConfig.nightModeSeparatorColor, self.readerConfig.menuSeparatorColor) } // MARK: - slider events @@ -171,11 +176,13 @@ class ScrollScrubber: NSObject, UIScrollViewDelegate { } } - func scrollViewDidScroll(_ scrollView: UIScrollView) { - guard readerConfig.scrollDirection == .vertical || readerConfig.scrollDirection == .defaultVertical || readerConfig.scrollDirection == .horizontalWithVerticalContent else { - return - } - + func scrollViewDidScroll(_ scrollView: UIScrollView) { + guard (self.readerConfig.scrollDirection == .vertical || + self.readerConfig.scrollDirection == .defaultVertical || + self.readerConfig.scrollDirection == .horizontalWithVerticalContent) else { + return + } + if visible && usingSlider == false { setSliderVal() } From 6460b636d13012e65473b04ffca721ee29c56fe1 Mon Sep 17 00:00:00 2001 From: Kevin Delord Date: Wed, 29 Mar 2017 17:54:22 +0200 Subject: [PATCH 007/110] Improve isDirection functions to use current readerConfig --- Source/EPUBCore/FREpubParser.swift | 16 ++-- Source/FolioReaderCenter.swift | 86 ++++++++++-------- Source/FolioReaderConfig.swift | 30 ++++++ Source/FolioReaderContainer.swift | 24 +++-- Source/FolioReaderKit.swift | 126 ++++++++++++++++++++++---- Source/FolioReaderPageIndicator.swift | 23 ++--- Source/ScrollScrubber.swift | 32 +++---- 7 files changed, 232 insertions(+), 105 deletions(-) diff --git a/Source/EPUBCore/FREpubParser.swift b/Source/EPUBCore/FREpubParser.swift index 976604b81..5363fed46 100755 --- a/Source/EPUBCore/FREpubParser.swift +++ b/Source/EPUBCore/FREpubParser.swift @@ -25,9 +25,12 @@ class FREpubParser: NSObject, SSZipArchiveDelegate { Parse the Cover Image from an epub file. Returns an UIImage. */ - func parseCoverImage(_ epubPath: String) -> UIImage? { - guard let book = readEpub(epubPath: epubPath, removeEpub: false), let coverImage = book.coverImage else { - return nil + // TODO_SMF_DOC: new function signature change + func parseCoverImage(_ epubPath: String, unzipPath: String? = nil) -> UIImage? { + guard + let book = readEpub(epubPath: epubPath, removeEpub: false, unzipPath: unzipPath), + let coverImage = book.coverImage else { + return nil } return UIImage(contentsOfFile: coverImage.fullHref) } @@ -47,9 +50,6 @@ class FREpubParser: NSObject, SSZipArchiveDelegate { return authorName } - - - /** Unzip, delete and read an epub file. Returns a FRBook. @@ -62,8 +62,8 @@ class FREpubParser: NSObject, SSZipArchiveDelegate { let fileManager = FileManager.default let bookName = (withEpubPath as NSString).lastPathComponent - if let bookUnzipPath = FolioReader.shared.unzipPath, fileManager.fileExists(atPath: bookUnzipPath) { - bookBasePath = bookUnzipPath + if let path = unzipPath, (fileManager.fileExists(atPath: path) == true) { + bookBasePath = path } else { bookBasePath = kApplicationDocumentsDirectory } diff --git a/Source/FolioReaderCenter.swift b/Source/FolioReaderCenter.swift index 426586462..e69d451aa 100755 --- a/Source/FolioReaderCenter.swift +++ b/Source/FolioReaderCenter.swift @@ -111,7 +111,7 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo self.totalPages = (self.book?.spine.spineReferences.count ?? 0) // Loading indicator - let style: UIActivityIndicatorViewStyle = isNight(.white, .gray) + let style: UIActivityIndicatorViewStyle = self.readerContainer.folioReader.isNight(UIActivityIndicatorViewStyle.white, UIActivityIndicatorViewStyle.gray) loadingView = UIActivityIndicatorView(activityIndicatorStyle: style) loadingView.hidesWhenStopped = true loadingView.startAnimating() @@ -130,9 +130,9 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo collectionViewLayout.sectionInset = UIEdgeInsets.zero collectionViewLayout.minimumLineSpacing = 0 collectionViewLayout.minimumInteritemSpacing = 0 - collectionViewLayout.scrollDirection = .direction() + collectionViewLayout.scrollDirection = .direction(withConfiguration: self.readerConfig) - let background = isNight(self.readerConfig.nightModeBackground, UIColor.white) + let background = self.readerContainer.folioReader.isNight(self.readerConfig.nightModeBackground, UIColor.white) view.backgroundColor = background // CollectionView @@ -162,14 +162,15 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo // Page indicator view if (self.readerConfig.hidePageIndicator == false) { - pageIndicatorView = FolioReaderPageIndicator(frame: self.frameForPageIndicatorView()) + let frame = self.frameForPageIndicatorView() + pageIndicatorView = FolioReaderPageIndicator(frame: frame, readerConfig: self.readerConfig, folioReader: self.readerContainer.folioReader) if let pageIndicatorView = pageIndicatorView { view.addSubview(pageIndicatorView) } } - scrollScrubber = ScrollScrubber(frame: self.frameForScrollScrubber()) - scrollScrubber?.delegate = self + self.scrollScrubber = ScrollScrubber(frame: self.frameForScrollScrubber(), withReaderContainer: self.readerContainer) + self.scrollScrubber?.delegate = self if let scrollScrubber = scrollScrubber { view.addSubview(scrollScrubber.slider) } @@ -219,9 +220,9 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo } func configureNavBar() { - let navBackground = isNight(self.readerConfig.nightModeMenuBackground, UIColor.white) + let navBackground = self.readerContainer.folioReader.isNight(self.readerConfig.nightModeMenuBackground, UIColor.white) let tintColor = readerConfig.tintColor - let navText = isNight(UIColor.white, UIColor.black) + let navText = self.readerContainer.folioReader.isNight(UIColor.white, UIColor.black) let font = UIFont(name: "Avenir-Light", size: 17)! setTranslucentNavigation(color: navBackground, tintColor: tintColor, titleColor: navText, andFont: font) } @@ -303,11 +304,12 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo // Get internal page offset before layout change let pageScrollView = currentPage.webView.scrollView - pageOffsetRate = pageScrollView.contentOffset.forDirection() / pageScrollView.contentSize.forDirection() + // TODO_SMF: check not divided by 0 + pageOffsetRate = (pageScrollView.contentOffset.forDirection(withConfiguration: self.readerConfig) / pageScrollView.contentSize.forDirection(withConfiguration: self.readerConfig)) // Change layout self.readerConfig.scrollDirection = direction - self.collectionViewLayout.scrollDirection = .direction() + self.collectionViewLayout.scrollDirection = .direction(withConfiguration: self.readerConfig) self.currentPage?.setNeedsLayout() self.collectionView.collectionViewLayout.invalidateLayout() self.collectionView.setContentOffset(frameForPage(currentPageNumber).origin, animated: false) @@ -322,7 +324,7 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo * so the delay wait until layout finished the changes. */ delay(0.1) { - var pageOffset = pageScrollView.contentSize.forDirection() * self.pageOffsetRate + var pageOffset = (pageScrollView.contentSize.forDirection(withConfiguration: self.readerConfig) * self.pageOffsetRate) // Fix the offset for paged scroll if (self.readerConfig.scrollDirection == .horizontal) { @@ -330,7 +332,7 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo pageOffset = page * pageWidth } - let pageOffsetPoint = isDirection(CGPoint(x: 0, y: pageOffset), CGPoint(x: pageOffset, y: 0)) + let pageOffsetPoint = self.readerConfig.isDirection(CGPoint(x: 0, y: pageOffset), CGPoint(x: pageOffset, y: 0)) pageScrollView.setContentOffset(pageOffsetPoint, animated: true) } } @@ -504,7 +506,8 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo // Adjust internal page offset guard let currentPage = self.currentPage else { return } let pageScrollView = currentPage.webView.scrollView - self.pageOffsetRate = pageScrollView.contentOffset.forDirection() / pageScrollView.contentSize.forDirection() + // TODO_SMF: check not divided by 0 + self.pageOffsetRate = (pageScrollView.contentOffset.forDirection(withConfiguration: self.readerConfig) / pageScrollView.contentSize.forDirection(withConfiguration: self.readerConfig)) }) } @@ -522,7 +525,7 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo scrollScrubber?.setSliderVal() // After rotation fix internal page offset - var pageOffset = currentPage.webView.scrollView.contentSize.forDirection() * pageOffsetRate + var pageOffset = (currentPage.webView.scrollView.contentSize.forDirection(withConfiguration: self.readerConfig) * pageOffsetRate) // Fix the offset for paged scroll if (self.readerConfig.scrollDirection == .horizontal && pageWidth != 0) { @@ -617,7 +620,8 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo guard let page = page else { return } let pageSize = isDirection(pageHeight, pageWidth) - pageIndicatorView?.totalPages = Int(ceil(page.webView.scrollView.contentSize.forDirection()/pageSize!)) + // TODO_SMF: remove unwrap + pageIndicatorView?.totalPages = Int(ceil(page.webView.scrollView.contentSize.forDirection(withConfiguration: self.readerConfig)/pageSize!)) let pageOffSet = isDirection(page.webView.scrollView.contentOffset.x, page.webView.scrollView.contentOffset.x, page.webView.scrollView.contentOffset.y) let webViewPage = pageForOffset(pageOffSet, pageHeight: pageSize!) @@ -718,7 +722,7 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo } UIView.animate(withDuration: animated ? 0.3 : 0, delay: 0, options: UIViewAnimationOptions(), animations: { () -> Void in - self.collectionView.scrollToItem(at: indexPath, at: .direction(), animated: false) + self.collectionView.scrollToItem(at: indexPath, at: .direction(withConfiguration: self.readerConfig), animated: false) }) { (finished: Bool) -> Void in completion?() } @@ -996,35 +1000,43 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo scrollScrubber?.scrollViewDidScroll(scrollView) // Update current reading page - if scrollView is UICollectionView {} else { - let pageSize = isDirection(pageHeight, pageWidth) - - if let page = currentPage - , page.webView.scrollView.contentOffset.forDirection()+pageSize! <= page.webView.scrollView.contentSize.forDirection() { + if scrollView is UICollectionView { + // Do nothing? + } else { + if let page = currentPage, + let pageSize = isDirection(pageHeight, pageWidth) { - let webViewPage = pageForOffset(page.webView.scrollView.contentOffset.forDirection(), pageHeight: pageSize!) + if (page.webView.scrollView.contentOffset.forDirection(withConfiguration: self.readerConfig)+pageSize <= page.webView.scrollView.contentSize.forDirection(withConfiguration: self.readerConfig)) { - if (readerConfig.scrollDirection == .horizontalWithVerticalContent), - let cell = ((scrollView.superview as? UIWebView)?.delegate as? FolioReaderPage) { + let webViewPage = pageForOffset(page.webView.scrollView.contentOffset.forDirection(withConfiguration: self.readerConfig), pageHeight: pageSize) - let currentIndexPathRow = cell.pageNumber - 1 + if (readerConfig.scrollDirection == .horizontalWithVerticalContent), + let cell = ((scrollView.superview as? UIWebView)?.delegate as? FolioReaderPage) { - // if the cell reload don't save the top position offset - if let oldOffSet = self.currentWebViewScrollPositions[currentIndexPathRow] - , (abs(oldOffSet.y - scrollView.contentOffset.y) > 100) {} else { - self.currentWebViewScrollPositions[currentIndexPathRow] = scrollView.contentOffset + let currentIndexPathRow = cell.pageNumber - 1 + + // if the cell reload don't save the top position offset + if let oldOffSet = self.currentWebViewScrollPositions[currentIndexPathRow], (abs(oldOffSet.y - scrollView.contentOffset.y) > 100) { + // DO nothing? + } else { + self.currentWebViewScrollPositions[currentIndexPathRow] = scrollView.contentOffset + } + } + + if pageIndicatorView?.currentPage != webViewPage { + pageIndicatorView?.currentPage = webViewPage } } + } + } - if pageIndicatorView?.currentPage != webViewPage { - pageIndicatorView?.currentPage = webViewPage - } - } - } - - pageScrollDirection = scrollView.contentOffset.forDirection() < pointNow.forDirection() ? .negative() : .positive() + if (scrollView.contentOffset.forDirection(withConfiguration: self.readerConfig) < pointNow.forDirection(withConfiguration: self.readerConfig)) { + pageScrollDirection = .negative(withConfiguration: self.readerConfig) + } else { + pageScrollDirection = .positive(withConfiguration: self.readerConfig) + } } - + open func scrollViewDidEndDecelerating(_ scrollView: UIScrollView) { isScrolling = false diff --git a/Source/FolioReaderConfig.swift b/Source/FolioReaderConfig.swift index 1aacebc11..1e90d1dbe 100755 --- a/Source/FolioReaderConfig.swift +++ b/Source/FolioReaderConfig.swift @@ -205,4 +205,34 @@ open class FolioReaderConfig: NSObject { open var localizedTakePhoto = NSLocalizedString("Take Photo", comment: "") open var localizedShareImageQuote = NSLocalizedString("Share image quote", comment: "") open var localizedShareTextQuote = NSLocalizedString("Share text quote", comment: "") + + + /** + Simplify attibution of values based on direction, basically is to avoid too much usage of `switch`, + `if` and `else` statements to check. So basically this is like a shorthand version of the `switch` verification. + + For example: + ``` + let pageOffsetPoint = isDirection(CGPoint(x: 0, y: pageOffset), CGPoint(x: pageOffset, y: 0), CGPoint(x: 0, y: pageOffset)) + ``` + + As usually the `vertical` direction and `horizontalContentVertical` has similar statements you can basically hide the last + value and it will assume the value from `vertical` as fallback. + ``` + let pageOffsetPoint = isDirection(CGPoint(x: 0, y: pageOffset), CGPoint(x: pageOffset, y: 0)) + ``` + + - parameter vertical: Value for `vertical` direction + - parameter horizontal: Value for `horizontal` direction + - parameter horizontalContentVertical: Value for `horizontalWithVerticalContent` direction, if nil will fallback to `vertical` value + + - returns: The right value based on direction. + */ + func isDirection (_ vertical: T, _ horizontal: T, _ horizontalContentVertical: T? = nil) -> T { + switch self.scrollDirection { + case .vertical, .defaultVertical: return vertical + case .horizontal: return horizontal + case .horizontalWithVerticalContent: return (horizontalContentVertical ?? vertical) + } + } } diff --git a/Source/FolioReaderContainer.swift b/Source/FolioReaderContainer.swift index f1543afe1..a97475456 100755 --- a/Source/FolioReaderContainer.swift +++ b/Source/FolioReaderContainer.swift @@ -20,8 +20,8 @@ open class FolioReaderContainer : UIViewController { var epubPath : String? var book : FRBook? var readerConfig : FolioReaderConfig + var folioReader : FolioReader - fileprivate var folioReader : FolioReader? fileprivate var errorOnLoad = false // MARK: - Init @@ -55,7 +55,7 @@ open class FolioReaderContainer : UIViewController { Common Initialization */ fileprivate func initialization() { - book = FRBook() + self.book = FRBook() // Register custom fonts FontBlaster.blast(bundle: Bundle.frameworkBundle()) @@ -94,11 +94,11 @@ open class FolioReaderContainer : UIViewController { // TODO_SMF: wtf let canChangeScrollDirection = self.readerConfig.canChangeScrollDirection - self.readerConfig.canChangeScrollDirection = isDirection(canChangeScrollDirection, canChangeScrollDirection, false) + self.readerConfig.canChangeScrollDirection = self.readerConfig.isDirection(canChangeScrollDirection, canChangeScrollDirection, false) // If user can change scroll direction use the last saved if (self.readerConfig.canChangeScrollDirection == true) { - var scrollDirection = (FolioReaderScrollDirection(rawValue: (self.folioReader?.currentScrollDirection ?? 0)) ?? .vertical) + var scrollDirection = (FolioReaderScrollDirection(rawValue: self.folioReader.currentScrollDirection) ?? .vertical) if (scrollDirection == .defaultVertical && self.readerConfig.scrollDirection != .defaultVertical) { scrollDirection = self.readerConfig.scrollDirection @@ -144,7 +144,7 @@ open class FolioReaderContainer : UIViewController { } self.book = parsedBook - self.folioReader?.isReaderOpen = true + self.folioReader.isReaderOpen = true // Reload data DispatchQueue.main.async(execute: { @@ -156,15 +156,13 @@ open class FolioReaderContainer : UIViewController { self.centerViewController?.reloadData() - self.folioReader?.isReaderReady = true + self.folioReader.isReaderReady = true - guard - let reader = self.folioReader, - let loadedBook = self.book else { - return + guard let loadedBook = self.book else { + return } - reader.delegate?.folioReader?(reader, didFinishedLoading: loadedBook) + self.folioReader.delegate?.folioReader?(self.folioReader, didFinishedLoading: loadedBook) }) } } @@ -182,7 +180,7 @@ open class FolioReaderContainer : UIViewController { */ func addAudioPlayer() { self.audioPlayer = FolioReaderAudioPlayer() - self.folioReader?.readerAudioPlayer = audioPlayer + self.folioReader.readerAudioPlayer = audioPlayer } // MARK: - Status Bar @@ -196,6 +194,6 @@ open class FolioReaderContainer : UIViewController { } override open var preferredStatusBarStyle: UIStatusBarStyle { - return isNight(.lightContent, .default) + return self.folioReader.isNight(.lightContent, .default) } } diff --git a/Source/FolioReaderKit.swift b/Source/FolioReaderKit.swift index 24458bdc3..8cd9dc2c0 100755 --- a/Source/FolioReaderKit.swift +++ b/Source/FolioReaderKit.swift @@ -71,6 +71,7 @@ enum MediaOverlayStyle: Int { // TODO_SMF: make sure the following deprecated functions still work... or not.: // TODO_SMF_QUESTION: ask the main developer(s) for that. + // TODO_SMF_DOC: new function signature change @objc optional func folioReaderDidClosed() } @@ -110,7 +111,11 @@ open class FolioReader: NSObject { var needsRTLChange: Bool { return (self.readerContainer?.book?.spine.isRtl == true && self.readerContainer?.readerConfig.scrollDirection == .horizontal) } - + + func isNight(_ f: T, _ l: T) -> T { + return (self.nightMode == true ? f : l) + } + /// Check if current theme is Night mode open var nightMode: Bool { get { return FolioReader.defaults.bool(forKey: kNightMode) } @@ -125,7 +130,7 @@ open class FolioReader: NSObject { readerCenter.pageIndicatorView?.reloadColors() readerCenter.configureNavBar() readerCenter.scrollScrubber?.reloadColors() - readerCenter.collectionView.backgroundColor = (self.nightMode ? self.readerContainer?.readerConfig.nightModeBackground : UIColor.white) + readerCenter.collectionView.backgroundColor = (self.nightMode == true ? self.readerContainer?.readerConfig.nightModeBackground : UIColor.white) }, completion: { (finished: Bool) in // TODO_SMF: add constant NotificationCenter.default.post(name: Notification.Name(rawValue: "needRefreshPageMode"), object: nil) @@ -203,11 +208,13 @@ open class FolioReader: NSObject { /** Read Cover Image and Return an `UIImage` */ - open class func getCoverImage(_ epubPath: String) -> UIImage? { - return FREpubParser().parseCoverImage(epubPath) + // TODO_SMF_DOC: new function signature change + open class func getCoverImage(_ epubPath: String, unzipPath: String? = nil) -> UIImage? { + // TODO_SMF_QUESTION: this used the shared instance before and ignore the parameter. + // Should we properly implement the parameter or change the API to use the current FolioReader? + return FREpubParser().parseCoverImage(epubPath, unzipPath: unzipPath) } - // MARK: - Get Title open class func getTitle(_ epubPath: String) -> String? { return FREpubParser().parseTitle(epubPath) @@ -274,7 +281,9 @@ extension FolioReader { // TODO_SMF: temporal variable to build and run the current state. Should be completely remove. private static var _sharedInstance = FolioReader() open static var shared : FolioReader { - get { return _sharedInstance } + get { + return _sharedInstance + } set { _sharedInstance = newValue } @@ -380,6 +389,9 @@ extension FolioReader { // MARK: - Global Functions func isNight (_ f: T, _ l: T) -> T { + fatalError("should not use that function.") + // TODO_SMF: remove that function + // TODO_SMF_DOC: notify change return (FolioReader.shared.nightMode == true ? f : l) } @@ -407,7 +419,8 @@ func isNight (_ f: T, _ l: T) -> T { - returns: The right value based on direction. */ func isDirection (_ vertical: T, _ horizontal: T, _ horizontalContentVertical: T? = nil) -> T { - let direction = (FolioReader.shared.readerContainer?.readerConfig.scrollDirection ?? .defaultVertical) + fatalError("should not use that function.") + let direction = (FolioReader.shared.readerContainer!.readerConfig.scrollDirection) switch direction { case .vertical, .defaultVertical: return vertical case .horizontal: return horizontal @@ -416,47 +429,120 @@ func isDirection (_ vertical: T, _ horizontal: T, _ horizontalContentVertical } extension UICollectionViewScrollDirection { - static func direction() -> UICollectionViewScrollDirection { - return isDirection(.vertical, .horizontal, .horizontal) + + static func direction() -> UICollectionViewScrollDirection { + // TODO_SMF: deprecate + guard let readerConfig = FolioReader.shared.readerContainer?.readerConfig else { + return .vertical + } + + return UICollectionViewScrollDirection.direction(withConfiguration: readerConfig) + } + + static func direction(withConfiguration readerConfig: FolioReaderConfig) -> UICollectionViewScrollDirection { + return readerConfig.isDirection(.vertical, .horizontal, .horizontal) } } extension UICollectionViewScrollPosition { - static func direction() -> UICollectionViewScrollPosition { - return isDirection(.top, .left, .left) - } + + static func direction() -> UICollectionViewScrollPosition { + // TODO_SMF: deprecate + guard let readerConfig = FolioReader.shared.readerContainer?.readerConfig else { + return .top + } + + return UICollectionViewScrollPosition.direction(withConfiguration: readerConfig) + } + + static func direction(withConfiguration readerConfig: FolioReaderConfig) -> UICollectionViewScrollPosition { + return readerConfig.isDirection(.top, .left, .left) + } } extension CGPoint { func forDirection() -> CGFloat { - return isDirection(y, x, y) + // TODO_SMF: deprecate + guard let readerConfig = FolioReader.shared.readerContainer?.readerConfig else { + return self.y + } + + return self.forDirection(withConfiguration: readerConfig) } + + func forDirection(withConfiguration readerConfig: FolioReaderConfig) -> CGFloat { + return readerConfig.isDirection(self.y, self.x, self.y) + } } extension CGSize { func forDirection() -> CGFloat { - return isDirection(height, width, height) + // TODO_SMF: deprecate + guard let readerConfig = FolioReader.shared.readerContainer?.readerConfig else { + return self.height + } + return self.forDirection(withConfiguration: readerConfig) } - + + func forDirection(withConfiguration readerConfig: FolioReaderConfig) -> CGFloat { + return readerConfig.isDirection(height, width, height) + } + func forReverseDirection() -> CGFloat { - return isDirection(width, height, width) + // TODO_SMF: deprecate + guard let readerConfig = FolioReader.shared.readerContainer?.readerConfig else { + return self.width + } + + return self.forReverseDirection(withConfiguration: readerConfig) } + + func forReverseDirection(withConfiguration readerConfig: FolioReaderConfig) -> CGFloat { + return readerConfig.isDirection(width, height, width) + } } extension CGRect { func forDirection() -> CGFloat { - return isDirection(height, width, height) + // TODO_SMF: deprecate + guard let readerConfig = FolioReader.shared.readerContainer?.readerConfig else { + return self.height + } + + return self.forDirection(withConfiguration: readerConfig) } + + func forDirection(withConfiguration readerConfig: FolioReaderConfig) -> CGFloat { + return readerConfig.isDirection(height, width, height) + } } extension ScrollDirection { static func negative() -> ScrollDirection { - return isDirection(.down, .right, .right) + // TODO_SMF: deprecate + guard let readerConfig = FolioReader.shared.readerContainer?.readerConfig else { + return self.down + } + + return self.negative(withConfiguration: readerConfig) } - + + static func negative(withConfiguration readerConfig: FolioReaderConfig) -> ScrollDirection { + return readerConfig.isDirection(.down, .right, .right) + } + static func positive() -> ScrollDirection { - return isDirection(.up, .left, .left) + // TODO_SMF: deprecate + guard let readerConfig = FolioReader.shared.readerContainer?.readerConfig else { + return self.up + } + + return self.positive(withConfiguration: readerConfig) } + + static func positive(withConfiguration readerConfig: FolioReaderConfig) -> ScrollDirection { + return readerConfig.isDirection(.up, .left, .left) + } } // MARK: Helpers diff --git a/Source/FolioReaderPageIndicator.swift b/Source/FolioReaderPageIndicator.swift index 493a618b1..f78fd0062 100644 --- a/Source/FolioReaderPageIndicator.swift +++ b/Source/FolioReaderPageIndicator.swift @@ -17,15 +17,16 @@ class FolioReaderPageIndicator: UIView { didSet { self.reloadViewWithPage(self.currentPage) } } - fileprivate var readerConfig : FolioReaderConfig { - // TODO_SMF: remove this getter - return FolioReader.shared.readerContainer!.readerConfig - } + fileprivate var readerConfig : FolioReaderConfig + fileprivate var folioReader : FolioReader + + init(frame: CGRect, readerConfig: FolioReaderConfig, folioReader: FolioReader) { + self.readerConfig = readerConfig + self.folioReader = folioReader - override init(frame: CGRect) { super.init(frame: frame) - let color = isNight(self.readerConfig.nightModeBackground, UIColor.white) + let color = self.folioReader.isNight(self.readerConfig.nightModeBackground, UIColor.white) backgroundColor = color layer.shadowColor = color.cgColor layer.shadowOffset = CGSize(width: 0, height: -6) @@ -61,12 +62,12 @@ class FolioReaderPageIndicator: UIView { if updateShadow { layer.shadowPath = UIBezierPath(rect: bounds).cgPath - reloadColors() + self.reloadColors() } } func reloadColors() { - let color = isNight(self.readerConfig.nightModeBackground, UIColor.white) + let color = self.folioReader.isNight(self.readerConfig.nightModeBackground, UIColor.white) backgroundColor = color // Animate the shadow color change @@ -81,8 +82,8 @@ class FolioReaderPageIndicator: UIView { animation.timingFunction = CAMediaTimingFunction(name: kCAMediaTimingFunctionEaseInEaseOut) layer.add(animation, forKey: "shadowColor") - minutesLabel.textColor = isNight(UIColor(white: 1, alpha: 0.3), UIColor(white: 0, alpha: 0.6)) - pagesLabel.textColor = isNight(UIColor(white: 1, alpha: 0.6), UIColor(white: 0, alpha: 0.9)) + minutesLabel.textColor = self.folioReader.isNight(UIColor(white: 1, alpha: 0.3), UIColor(white: 0, alpha: 0.6)) + pagesLabel.textColor = self.folioReader.isNight(UIColor(white: 1, alpha: 0.6), UIColor(white: 0, alpha: 0.9)) } fileprivate func reloadViewWithPage(_ page: Int) { @@ -112,7 +113,7 @@ extension FolioReaderPageIndicator: CAAnimationDelegate { func animationDidStop(_ anim: CAAnimation, finished flag: Bool) { // Set the shadow color to the final value of the animation is done if let keyPath = anim.value(forKeyPath: "keyPath") as? String , keyPath == "shadowColor" { - let color = isNight(self.readerConfig.nightModeBackground, UIColor.white) + let color = self.folioReader.isNight(self.readerConfig.nightModeBackground, UIColor.white) layer.shadowColor = color.cgColor } } diff --git a/Source/ScrollScrubber.swift b/Source/ScrollScrubber.swift index 35539a643..13892d928 100644 --- a/Source/ScrollScrubber.swift +++ b/Source/ScrollScrubber.swift @@ -54,32 +54,30 @@ class ScrollScrubber: NSObject, UIScrollViewDelegate { var scrollDelta: CGFloat! var scrollDeltaTimer: Timer! - fileprivate var readerConfig : FolioReaderConfig { - // TODO_SMF: remove this getter - return FolioReader.shared.readerContainer!.readerConfig - } - var frame: CGRect! { + fileprivate var readerContainer : FolioReaderContainer + + var frame: CGRect { didSet { self.slider.frame = frame } } - init(frame:CGRect) { + init(frame:CGRect, withReaderContainer readerContainer: FolioReaderContainer) { + self.frame = frame + self.readerContainer = readerContainer + super.init() slider = UISlider() slider.layer.anchorPoint = CGPoint(x: 0, y: 0) slider.transform = CGAffineTransform(rotationAngle: CGFloat(M_PI_2)) slider.alpha = 0 - - self.frame = frame - - reloadColors() + self.reloadColors() // less obtrusive knob and fixes jump: http://stackoverflow.com/a/22301039/484780 let thumbImg = UIImage(readerImageNamed: "knob") - let thumbImgColor = thumbImg!.imageTintColor(self.readerConfig.tintColor).withRenderingMode(.alwaysOriginal) + let thumbImgColor = thumbImg!.imageTintColor(self.readerContainer.readerConfig.tintColor).withRenderingMode(.alwaysOriginal) slider.setThumbImage(thumbImgColor, for: UIControlState()) slider.setThumbImage(thumbImgColor, for: .selected) slider.setThumbImage(thumbImgColor, for: .highlighted) @@ -91,8 +89,9 @@ class ScrollScrubber: NSObject, UIScrollViewDelegate { } func reloadColors() { - slider.minimumTrackTintColor = self.readerConfig.tintColor - slider.maximumTrackTintColor = isNight(self.readerConfig.nightModeSeparatorColor, self.readerConfig.menuSeparatorColor) + let readerConfig = self.readerContainer.readerConfig + slider.minimumTrackTintColor = readerConfig.tintColor + slider.maximumTrackTintColor = self.readerContainer.folioReader.isNight(readerConfig.nightModeSeparatorColor, readerConfig.menuSeparatorColor) } // MARK: - slider events @@ -177,9 +176,10 @@ class ScrollScrubber: NSObject, UIScrollViewDelegate { } func scrollViewDidScroll(_ scrollView: UIScrollView) { - guard (self.readerConfig.scrollDirection == .vertical || - self.readerConfig.scrollDirection == .defaultVertical || - self.readerConfig.scrollDirection == .horizontalWithVerticalContent) else { + let readerConfig = self.readerContainer.readerConfig + guard (readerConfig.scrollDirection == .vertical || + readerConfig.scrollDirection == .defaultVertical || + readerConfig.scrollDirection == .horizontalWithVerticalContent) else { return } From 1d59fc9d2def34bb10d1d35378014d60f622b136 Mon Sep 17 00:00:00 2001 From: Kevin Delord Date: Wed, 29 Mar 2017 18:36:44 +0200 Subject: [PATCH 008/110] PageScrubbler: improve init logic and remove few optional unwrap --- Source/FolioReaderCenter.swift | 27 +++++++++++++++-------- Source/FolioReaderPage.swift | 39 +++++++++++++++++----------------- Source/ScrollScrubber.swift | 25 ++++++++++++++-------- 3 files changed, 54 insertions(+), 37 deletions(-) diff --git a/Source/FolioReaderCenter.swift b/Source/FolioReaderCenter.swift index e69d451aa..da6e45ccc 100755 --- a/Source/FolioReaderCenter.swift +++ b/Source/FolioReaderCenter.swift @@ -401,8 +401,17 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo } open func collectionView(_ collectionView: UICollectionView, cellForItemAt indexPath: IndexPath) -> UICollectionViewCell { - let cell = collectionView.dequeueReusableCell(withReuseIdentifier: reuseIdentifier, for: indexPath) as! FolioReaderPage - + var reuseableCell = collectionView.dequeueReusableCell(withReuseIdentifier: reuseIdentifier, for: indexPath) as? FolioReaderPage + guard let pageCell = reuseableCell else { + return UICollectionViewCell() + } + + return self.configure(readerPageCell: pageCell, atIndexPath: indexPath) + } + + private func configure(readerPageCell cell: FolioReaderPage, atIndexPath indexPath: IndexPath) -> FolioReaderPage { + + cell.setup(withReaderConfig: self.readerConfig, book: self.book) cell.pageNumber = (indexPath as NSIndexPath).row+1 cell.webView.scrollView.delegate = self cell.webView.setupScrollDirection() @@ -495,7 +504,7 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo } // Adjust collectionView - self.collectionView.contentSize = isDirection( + self.collectionView.contentSize = self.readerConfig.isDirection( CGSize(width: pageWidth, height: pageHeight * CGFloat(self.totalPages)), CGSize(width: pageWidth * CGFloat(self.totalPages), height: pageHeight), CGSize(width: pageWidth * CGFloat(self.totalPages), height: pageHeight) @@ -533,7 +542,7 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo pageOffset = page * pageWidth } - let pageOffsetPoint = isDirection(CGPoint(x: 0, y: pageOffset), CGPoint(x: pageOffset, y: 0)) + let pageOffsetPoint = self.readerConfig.isDirection(CGPoint(x: 0, y: pageOffset), CGPoint(x: pageOffset, y: 0)) currentPage.webView.scrollView.setContentOffset(pageOffsetPoint, animated: true) } @@ -619,11 +628,11 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo func pagesForCurrentPage(_ page: FolioReaderPage?) { guard let page = page else { return } - let pageSize = isDirection(pageHeight, pageWidth) + let pageSize = self.readerConfig.isDirection(pageHeight, pageWidth) // TODO_SMF: remove unwrap pageIndicatorView?.totalPages = Int(ceil(page.webView.scrollView.contentSize.forDirection(withConfiguration: self.readerConfig)/pageSize!)) - let pageOffSet = isDirection(page.webView.scrollView.contentOffset.x, page.webView.scrollView.contentOffset.x, page.webView.scrollView.contentOffset.y) + let pageOffSet = self.readerConfig.isDirection(page.webView.scrollView.contentOffset.x, page.webView.scrollView.contentOffset.x, page.webView.scrollView.contentOffset.y) let webViewPage = pageForOffset(pageOffSet, pageHeight: pageSize!) pageIndicatorView?.currentPage = webViewPage @@ -664,7 +673,7 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo } func frameForPage(_ page: Int) -> CGRect { - return isDirection( + return self.readerConfig.isDirection( CGRect(x: 0, y: pageHeight * CGFloat(page-1), width: pageWidth, height: pageHeight), CGRect(x: pageWidth * CGFloat(page-1), y: 0, width: pageWidth, height: pageHeight) ) @@ -1004,7 +1013,7 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo // Do nothing? } else { if let page = currentPage, - let pageSize = isDirection(pageHeight, pageWidth) { + let pageSize = self.readerConfig.isDirection(pageHeight, pageWidth) { if (page.webView.scrollView.contentOffset.forDirection(withConfiguration: self.readerConfig)+pageSize <= page.webView.scrollView.contentSize.forDirection(withConfiguration: self.readerConfig)) { @@ -1164,7 +1173,7 @@ extension FolioReaderCenter: FolioReaderPageDelegate { if let position = FolioReader.defaults.value(forKey: kBookId) as? NSDictionary { let pageNumber = position["pageNumber"]! as! Int - let offset = isDirection(position["pageOffsetY"], position["pageOffsetX"]) as? CGFloat + let offset = self.readerConfig.isDirection(position["pageOffsetY"], position["pageOffsetX"]) as? CGFloat let pageOffset = offset if isFirstLoad { diff --git a/Source/FolioReaderPage.swift b/Source/FolioReaderPage.swift index f1a333417..8342dd4a7 100755 --- a/Source/FolioReaderPage.swift +++ b/Source/FolioReaderPage.swift @@ -31,11 +31,6 @@ import JSQWebViewController open class FolioReaderPage: UICollectionViewCell, UIWebViewDelegate, UIGestureRecognizerDelegate { - fileprivate var readerConfig : FolioReaderConfig { - // TODO_SMF: remove this getter - return FolioReader.shared.readerContainer!.readerConfig - } - weak var delegate: FolioReaderPageDelegate? // TODO_SMF: remove `!` /// The index of the current page. Note: The index start at 1! @@ -45,15 +40,21 @@ open class FolioReaderPage: UICollectionViewCell, UIWebViewDelegate, UIGestureRe fileprivate var shouldShowBar = true fileprivate var menuIsVisible = false - fileprivate var book: FRBook? { - // TODO_SMF: remove this getter - return FolioReader.shared.readerContainer?.book - } - + fileprivate var readerConfig: FolioReaderConfig + fileprivate var book: FRBook? + // MARK: - View life cicle - - override public init(frame: CGRect) { - super.init(frame: frame) + + public override init(frame: CGRect) { + // Init reader config with a default one. Later the current one must be configured through the setup function. + self.readerConfig = FolioReaderConfig() + super.init(frame: frame) + } + + public func setup(withReaderConfig readerConfig: FolioReaderConfig, book: FRBook?) { + self.readerConfig = readerConfig + self.book = book + self.backgroundColor = UIColor.clear // TODO: Put the notification name in a Constants file @@ -86,7 +87,7 @@ open class FolioReaderPage: UICollectionViewCell, UIWebViewDelegate, UIGestureRe required public init?(coder aDecoder: NSCoder) { fatalError("storyboards are incompatible with truth and beauty") } - + deinit { webView.scrollView.delegate = nil NotificationCenter.default.removeObserver(self) @@ -112,9 +113,9 @@ open class FolioReaderPage: UICollectionViewCell, UIWebViewDelegate, UIGestureRe return CGRect( x: bounds.origin.x, - y: isDirection(bounds.origin.y + navTotal, bounds.origin.y + navTotal + paddingTop), + y: self.readerConfig.isDirection(bounds.origin.y + navTotal, bounds.origin.y + navTotal + paddingTop), width: bounds.width, - height: isDirection(bounds.height - navTotal, bounds.height - navTotal - paddingTop - paddingBottom) + height: self.readerConfig.isDirection(bounds.height - navTotal, bounds.height - navTotal - paddingTop - paddingBottom) ) } @@ -176,7 +177,7 @@ open class FolioReaderPage: UICollectionViewCell, UIWebViewDelegate, UIGestureRe } } - let direction: ScrollDirection = FolioReader.needsRTLChange ? .positive() : .negative() + let direction: ScrollDirection = FolioReader.needsRTLChange ? .positive(withConfiguration: self.readerConfig) : .negative(withConfiguration: self.readerConfig) if pageScrollDirection == direction && isScrolling && self.readerConfig.scrollDirection != .horizontalWithVerticalContent { scrollPageToBottom() @@ -381,7 +382,7 @@ open class FolioReaderPage: UICollectionViewCell, UIWebViewDelegate, UIGestureRe - parameter animated: Enable or not scrolling animation */ open func scrollPageToOffset(_ offset: CGFloat, animated: Bool) { - let pageOffsetPoint = isDirection(CGPoint(x: 0, y: offset), CGPoint(x: offset, y: 0)) + let pageOffsetPoint = self.readerConfig.isDirection(CGPoint(x: 0, y: offset), CGPoint(x: offset, y: 0)) webView.scrollView.setContentOffset(pageOffsetPoint, animated: animated) } @@ -389,7 +390,7 @@ open class FolioReaderPage: UICollectionViewCell, UIWebViewDelegate, UIGestureRe Scrolls the page to bottom */ open func scrollPageToBottom() { - let bottomOffset = isDirection( + let bottomOffset = self.readerConfig.isDirection( CGPoint(x: 0, y: webView.scrollView.contentSize.height - webView.scrollView.bounds.height), CGPoint(x: webView.scrollView.contentSize.width - webView.scrollView.bounds.width, y: 0), CGPoint(x: webView.scrollView.contentSize.width - webView.scrollView.bounds.width, y: 0) diff --git a/Source/ScrollScrubber.swift b/Source/ScrollScrubber.swift index 13892d928..d4dab3baf 100644 --- a/Source/ScrollScrubber.swift +++ b/Source/ScrollScrubber.swift @@ -54,7 +54,6 @@ class ScrollScrubber: NSObject, UIScrollViewDelegate { var scrollDelta: CGFloat! var scrollDeltaTimer: Timer! - fileprivate var readerContainer : FolioReaderContainer var frame: CGRect { @@ -109,7 +108,7 @@ class ScrollScrubber: NSObject, UIScrollViewDelegate { func sliderChange(_ slider:UISlider) { let movePosition = height()*CGFloat(slider.value) let offset = isDirection(CGPoint(x: 0, y: movePosition), CGPoint(x: movePosition, y: 0)) - scrollView().setContentOffset(offset, animated: false) + scrollView()?.setContentOffset(offset, animated: false) } // MARK: - show / hide @@ -171,7 +170,7 @@ class ScrollScrubber: NSObject, UIScrollViewDelegate { } if scrollStart == nil { - scrollStart = scrollView.contentOffset.forDirection() + scrollStart = scrollView.contentOffset.forDirection(withConfiguration: self.readerContainer.readerConfig) } } @@ -192,7 +191,7 @@ class ScrollScrubber: NSObject, UIScrollViewDelegate { show() } else if delegate.currentPage != nil && scrollStart != nil { - scrollDelta = scrollView.contentOffset.forDirection() - scrollStart + scrollDelta = scrollView.contentOffset.forDirection(withConfiguration: self.readerContainer.readerConfig) - scrollStart if scrollDeltaTimer == nil && scrollDelta > (pageHeight * 0.2 ) || (scrollDelta * -1) > (pageHeight * 0.2) { show() @@ -216,7 +215,7 @@ class ScrollScrubber: NSObject, UIScrollViewDelegate { scrollDeltaTimer = nil } - scrollStart = scrollView().contentOffset.forDirection() + scrollStart = (scrollView()?.contentOffset.forDirection(withConfiguration: self.readerContainer.readerConfig) ?? 0) scrollDelta = 0 } @@ -227,15 +226,23 @@ class ScrollScrubber: NSObject, UIScrollViewDelegate { // MARK: - utility methods - fileprivate func scrollView() -> UIScrollView { - return delegate.currentPage!.webView.scrollView + fileprivate func scrollView() -> UIScrollView? { + return delegate.currentPage?.webView.scrollView } fileprivate func height() -> CGFloat { - return delegate.currentPage!.webView.scrollView.contentSize.height - pageHeight + 44 + guard let currentPage = delegate.currentPage else { + return 0 + } + + return currentPage.webView.scrollView.contentSize.height - pageHeight + 44 } fileprivate func scrollTop() -> CGFloat { - return delegate.currentPage!.webView.scrollView.contentOffset.forDirection() + guard let currentPage = delegate.currentPage else { + return 0 + } + + return currentPage.webView.scrollView.contentOffset.forDirection(withConfiguration: self.readerContainer.readerConfig) } } From 4604a5316a9ad17421d58ffdd3a4f4a0dd310762 Mon Sep 17 00:00:00 2001 From: Kevin Delord Date: Thu, 30 Mar 2017 16:10:19 +0200 Subject: [PATCH 009/110] Refactor highlightlist, scrollscrubber and chapter list --- Source/FolioReaderCenter.swift | 9 ++++----- Source/FolioReaderChapterList.swift | 23 ++++++++++++++++------- Source/FolioReaderConfig.swift | 4 ++-- Source/FolioReaderHighlightList.swift | 24 +++++++++++++++++------- Source/FolioReaderKit.swift | 6 ++++-- Source/FolioReaderPage.swift | 4 ++-- Source/PageViewController.swift | 21 +++++++++++---------- Source/ScrollScrubber.swift | 6 +++--- 8 files changed, 59 insertions(+), 38 deletions(-) diff --git a/Source/FolioReaderCenter.swift b/Source/FolioReaderCenter.swift index da6e45ccc..6d41239fd 100755 --- a/Source/FolioReaderCenter.swift +++ b/Source/FolioReaderCenter.swift @@ -1093,11 +1093,10 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo func presentChapterList(_ sender: UIBarButtonItem) { FolioReader.saveReaderState() - let chapter = FolioReaderChapterList() - chapter.delegate = self - let highlight = FolioReaderHighlightList() - - let pageController = PageViewController(transitionStyle: .scroll, navigationOrientation: .horizontal, options:nil) + let chapter = FolioReaderChapterList(folioReader: self.readerContainer.folioReader, readerConfig: self.readerConfig, delegate: self) + let highlight = FolioReaderHighlightList(folioReader: self.readerContainer.folioReader, readerConfig: self.readerConfig) + let pageController = PageViewController(folioReader: self.readerContainer.folioReader, readerConfig: self.readerConfig) + pageController.viewControllerOne = chapter pageController.viewControllerTwo = highlight pageController.segmentedControlItems = [readerConfig.localizedContentsTitle, readerConfig.localizedHighlightsTitle] diff --git a/Source/FolioReaderChapterList.swift b/Source/FolioReaderChapterList.swift index 70e8eabbd..d0a23c4e9 100755 --- a/Source/FolioReaderChapterList.swift +++ b/Source/FolioReaderChapterList.swift @@ -27,13 +27,22 @@ class FolioReaderChapterList: UITableViewController { var tocItems = [FRTocReference]() fileprivate var book : FRBook? { - // TODO_SMF: remove this getter - return FolioReader.shared.readerContainer?.book + return self.folioReader.readerContainer?.book } - fileprivate var readerConfig : FolioReaderConfig { - // TODO_SMF: remove this getter - return FolioReader.shared.readerContainer!.readerConfig + fileprivate var readerConfig : FolioReaderConfig + fileprivate var folioReader : FolioReader + + init(folioReader: FolioReader, readerConfig: FolioReaderConfig, delegate: FolioReaderChapterListDelegate?) { + self.readerConfig = readerConfig + self.folioReader = folioReader + self.delegate = delegate + + super.init(style: UITableViewStyle.plain) + } + + required init?(coder aDecoder: NSCoder) { + fatalError("init with coder not supported") } override func viewDidLoad() { @@ -42,8 +51,8 @@ class FolioReaderChapterList: UITableViewController { // Register cell classes self.tableView.register(FolioReaderChapterListCell.self, forCellReuseIdentifier: reuseIdentifier) self.tableView.separatorInset = UIEdgeInsets.zero - self.tableView.backgroundColor = isNight(self.readerConfig.nightModeMenuBackground, self.readerConfig.menuBackgroundColor) - self.tableView.separatorColor = isNight(self.readerConfig.nightModeSeparatorColor, self.readerConfig.menuSeparatorColor) + self.tableView.backgroundColor = self.folioReader.isNight(self.readerConfig.nightModeMenuBackground, self.readerConfig.menuBackgroundColor) + self.tableView.separatorColor = self.folioReader.isNight(self.readerConfig.nightModeSeparatorColor, self.readerConfig.menuSeparatorColor) self.tableView.rowHeight = UITableViewAutomaticDimension self.tableView.estimatedRowHeight = 50 diff --git a/Source/FolioReaderConfig.swift b/Source/FolioReaderConfig.swift index 1e90d1dbe..4eeedced5 100755 --- a/Source/FolioReaderConfig.swift +++ b/Source/FolioReaderConfig.swift @@ -213,13 +213,13 @@ open class FolioReaderConfig: NSObject { For example: ``` - let pageOffsetPoint = isDirection(CGPoint(x: 0, y: pageOffset), CGPoint(x: pageOffset, y: 0), CGPoint(x: 0, y: pageOffset)) + let pageOffsetPoint = readerConfig.isDirection(CGPoint(x: 0, y: pageOffset), CGPoint(x: pageOffset, y: 0), CGPoint(x: 0, y: pageOffset)) ``` As usually the `vertical` direction and `horizontalContentVertical` has similar statements you can basically hide the last value and it will assume the value from `vertical` as fallback. ``` - let pageOffsetPoint = isDirection(CGPoint(x: 0, y: pageOffset), CGPoint(x: pageOffset, y: 0)) + let pageOffsetPoint = readerConfig.isDirection(CGPoint(x: 0, y: pageOffset), CGPoint(x: pageOffset, y: 0)) ``` - parameter vertical: Value for `vertical` direction diff --git a/Source/FolioReaderHighlightList.swift b/Source/FolioReaderHighlightList.swift index acc924fd3..64ef9c016 100644 --- a/Source/FolioReaderHighlightList.swift +++ b/Source/FolioReaderHighlightList.swift @@ -12,18 +12,28 @@ class FolioReaderHighlightList: UITableViewController { var highlights: [Highlight]! - fileprivate var readerConfig : FolioReaderConfig { - // TODO_SMF: remove this getter - return FolioReader.shared.readerContainer!.readerConfig + fileprivate var readerConfig : FolioReaderConfig + fileprivate var folioReader : FolioReader + + init(folioReader: FolioReader, readerConfig: FolioReaderConfig) { + self.readerConfig = readerConfig + self.folioReader = folioReader + + super.init(style: UITableViewStyle.plain) } + required init?(coder aDecoder: NSCoder) { + fatalError("init with coder not supported") + } + + override func viewDidLoad() { super.viewDidLoad() self.tableView.register(UITableViewCell.self, forCellReuseIdentifier: reuseIdentifier) self.tableView.separatorInset = UIEdgeInsets.zero - self.tableView.backgroundColor = isNight(self.readerConfig.nightModeMenuBackground, self.readerConfig.menuBackgroundColor) - self.tableView.separatorColor = isNight(self.readerConfig.nightModeSeparatorColor, self.readerConfig.menuSeparatorColor) + self.tableView.backgroundColor = self.folioReader.isNight(self.readerConfig.nightModeMenuBackground, self.readerConfig.menuBackgroundColor) + self.tableView.separatorColor = self.folioReader.isNight(self.readerConfig.nightModeSeparatorColor, self.readerConfig.menuSeparatorColor) highlights = Highlight.allByBookId((kBookId as NSString).deletingPathExtension) } @@ -62,7 +72,7 @@ class FolioReaderHighlightList: UITableViewController { } dateLabel.text = dateString.uppercased() - dateLabel.textColor = isNight(UIColor(white: 5, alpha: 0.3), UIColor.lightGray) + dateLabel.textColor = self.folioReader.isNight(UIColor(white: 5, alpha: 0.3), UIColor.lightGray) dateLabel.frame = CGRect(x: 20, y: 20, width: view.frame.width-40, height: dateLabel.frame.height) // Text @@ -71,7 +81,7 @@ class FolioReaderHighlightList: UITableViewController { let range = NSRange(location: 0, length: text.length) let paragraph = NSMutableParagraphStyle() paragraph.lineSpacing = 3 - let textColor = isNight(self.readerConfig.menuTextColor, UIColor.black) + let textColor = self.folioReader.isNight(self.readerConfig.menuTextColor, UIColor.black) text.addAttribute(NSParagraphStyleAttributeName, value: paragraph, range: range) text.addAttribute(NSFontAttributeName, value: UIFont(name: "Avenir-Light", size: 16)!, range: range) diff --git a/Source/FolioReaderKit.swift b/Source/FolioReaderKit.swift index 8cd9dc2c0..5bcb1f109 100755 --- a/Source/FolioReaderKit.swift +++ b/Source/FolioReaderKit.swift @@ -30,6 +30,8 @@ internal var kCurrentScrollDirection = "com.folioreader.kCurrentScrollDirection" internal let kNightMode = "com.folioreader.kNightMode" internal let kCurrentTOCMenu = "com.folioreader.kCurrentTOCMenu" internal let kHighlightRange = 30 + +// TODO_SMF: remove kBookId internal var kBookId: String! /** @@ -403,13 +405,13 @@ func isNight (_ f: T, _ l: T) -> T { For example: ``` - let pageOffsetPoint = isDirection(CGPoint(x: 0, y: pageOffset), CGPoint(x: pageOffset, y: 0), CGPoint(x: 0, y: pageOffset)) + let pageOffsetPoint = readerConfig.isDirection(CGPoint(x: 0, y: pageOffset), CGPoint(x: pageOffset, y: 0), CGPoint(x: 0, y: pageOffset)) ``` As usually the `vertical` direction and `horizontalContentVertical` has similar statements you can basically hide the last value and it will assume the value from `vertical` as fallback. ``` - let pageOffsetPoint = isDirection(CGPoint(x: 0, y: pageOffset), CGPoint(x: pageOffset, y: 0)) + let pageOffsetPoint = readerConfig.isDirection(CGPoint(x: 0, y: pageOffset), CGPoint(x: pageOffset, y: 0)) ``` - parameter vertical: Value for `vertical` direction diff --git a/Source/FolioReaderPage.swift b/Source/FolioReaderPage.swift index 8342dd4a7..7c63fe824 100755 --- a/Source/FolioReaderPage.swift +++ b/Source/FolioReaderPage.swift @@ -396,7 +396,7 @@ open class FolioReaderPage: UICollectionViewCell, UIWebViewDelegate, UIGestureRe CGPoint(x: webView.scrollView.contentSize.width - webView.scrollView.bounds.width, y: 0) ) - if bottomOffset.forDirection() >= 0 { + if bottomOffset.forDirection(withConfiguration: self.readerConfig) >= 0 { DispatchQueue.main.async(execute: { self.webView.scrollView.setContentOffset(bottomOffset, animated: false) }) @@ -416,7 +416,7 @@ open class FolioReaderPage: UICollectionViewCell, UIWebViewDelegate, UIGestureRe switch self.readerConfig.scrollDirection { case .vertical, .defaultVertical: - let isBeginning = offset < frame.forDirection()/2 + let isBeginning = (offset < frame.forDirection(withConfiguration: self.readerConfig) * 0.5) if !avoidBeginningAnchors { scrollPageToOffset(offset, animated: animated) diff --git a/Source/PageViewController.swift b/Source/PageViewController.swift index d4382cae6..46ec91b1e 100644 --- a/Source/PageViewController.swift +++ b/Source/PageViewController.swift @@ -9,6 +9,7 @@ import UIKit class PageViewController: UIPageViewController { + var segmentedControl: UISegmentedControl! var viewList = [UIViewController]() var segmentedControlItems = [String]() @@ -16,15 +17,15 @@ class PageViewController: UIPageViewController { var viewControllerTwo: UIViewController! var index = FolioReader.defaults.integer(forKey: kCurrentTOCMenu) - fileprivate var readerConfig : FolioReaderConfig { - // TODO_SMF: remove this getter - return FolioReader.shared.readerContainer!.readerConfig - } + fileprivate var readerConfig : FolioReaderConfig + fileprivate var folioReader : FolioReader // MARK: Init - - override init(transitionStyle style: UIPageViewControllerTransitionStyle, navigationOrientation: UIPageViewControllerNavigationOrientation, options: [String : Any]?) { - super.init(transitionStyle: style, navigationOrientation: navigationOrientation, options: options) + + init(folioReader: FolioReader, readerConfig: FolioReaderConfig) { + self.folioReader = folioReader + self.readerConfig = readerConfig + super.init(transitionStyle: .scroll, navigationOrientation: .horizontal, options: nil) self.edgesForExtendedLayout = UIRectEdge() self.extendedLayoutIncludesOpaqueBars = true @@ -72,9 +73,9 @@ class PageViewController: UIPageViewController { } func configureNavBar() { - let navBackground = isNight(self.readerConfig.nightModeMenuBackground, UIColor.white) + let navBackground = self.folioReader.isNight(self.readerConfig.nightModeMenuBackground, UIColor.white) let tintColor = self.readerConfig.tintColor - let navText = isNight(UIColor.white, UIColor.black) + let navText = self.folioReader.isNight(UIColor.white, UIColor.black) let font = UIFont(name: "Avenir-Light", size: 17)! setTranslucentNavigation(false, color: navBackground, tintColor: tintColor, titleColor: navText, andFont: font) } @@ -91,7 +92,7 @@ class PageViewController: UIPageViewController { // MARK: - Status Bar override var preferredStatusBarStyle : UIStatusBarStyle { - return isNight(.lightContent, .default) + return self.folioReader.isNight(.lightContent, .default) } } diff --git a/Source/ScrollScrubber.swift b/Source/ScrollScrubber.swift index d4dab3baf..510143f54 100644 --- a/Source/ScrollScrubber.swift +++ b/Source/ScrollScrubber.swift @@ -106,8 +106,8 @@ class ScrollScrubber: NSObject, UIScrollViewDelegate { } func sliderChange(_ slider:UISlider) { - let movePosition = height()*CGFloat(slider.value) - let offset = isDirection(CGPoint(x: 0, y: movePosition), CGPoint(x: movePosition, y: 0)) + let movePosition = (height() * CGFloat(slider.value)) + let offset = self.readerContainer.readerConfig.isDirection(CGPoint(x: 0, y: movePosition), CGPoint(x: movePosition, y: 0)) scrollView()?.setContentOffset(offset, animated: false) } @@ -235,7 +235,7 @@ class ScrollScrubber: NSObject, UIScrollViewDelegate { return 0 } - return currentPage.webView.scrollView.contentSize.height - pageHeight + 44 + return (currentPage.webView.scrollView.contentSize.height - pageHeight + 44) } fileprivate func scrollTop() -> CGFloat { From 063bd93f6ac05d5fdc5b6177226b32b3ec82c7b4 Mon Sep 17 00:00:00 2001 From: Kevin Delord Date: Thu, 30 Mar 2017 16:41:57 +0200 Subject: [PATCH 010/110] Refactor FolioReaderFontsMenu --- Source/FolioReaderCenter.swift | 4 ++-- Source/FolioReaderFontsMenu.swift | 23 ++++++++++++++++------- Source/FolioReaderHighlightList.swift | 2 +- 3 files changed, 19 insertions(+), 10 deletions(-) diff --git a/Source/FolioReaderCenter.swift b/Source/FolioReaderCenter.swift index 6d41239fd..dc72c94ae 100755 --- a/Source/FolioReaderCenter.swift +++ b/Source/FolioReaderCenter.swift @@ -1112,7 +1112,7 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo FolioReader.saveReaderState() hideBars() - let menu = FolioReaderFontsMenu() + let menu = FolioReaderFontsMenu(folioReader: self.readerContainer.folioReader, readerConfig: self.readerConfig) menu.modalPresentationStyle = .custom animator = ZFModalTransitionAnimator(modalViewController: menu) @@ -1124,7 +1124,7 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo animator.direction = ZFModalTransitonDirection.bottom menu.transitioningDelegate = animator - present(menu, animated: true, completion: nil) + self.present(menu, animated: true, completion: nil) } /** diff --git a/Source/FolioReaderFontsMenu.swift b/Source/FolioReaderFontsMenu.swift index c78924bda..44ebd2760 100644 --- a/Source/FolioReaderFontsMenu.swift +++ b/Source/FolioReaderFontsMenu.swift @@ -67,15 +67,24 @@ public enum FolioReaderFontSize: Int { } } -class FolioReaderFontsMenu: UIViewController, SMSegmentViewDelegate, UIGestureRecognizerDelegate { +class FolioReaderFontsMenu : UIViewController, SMSegmentViewDelegate, UIGestureRecognizerDelegate { - var menuView: UIView! + var menuView : UIView! - fileprivate var readerConfig : FolioReaderConfig { - // TODO_SMF: remove this getter - return FolioReader.shared.readerContainer!.readerConfig + fileprivate var readerConfig : FolioReaderConfig + fileprivate var folioReader : FolioReader + + init(folioReader: FolioReader, readerConfig: FolioReaderConfig) { + self.readerConfig = readerConfig + self.folioReader = folioReader + + super.init(nibName: nil, bundle: nil) } - + + required init?(coder aDecoder: NSCoder) { + fatalError("init(coder:) has not been implemented") + } + override func viewDidLoad() { super.viewDidLoad() @@ -91,7 +100,7 @@ class FolioReaderFontsMenu: UIViewController, SMSegmentViewDelegate, UIGestureRe // Menu view let visibleHeight: CGFloat = self.readerConfig.canChangeScrollDirection ? 222 : 170 menuView = UIView(frame: CGRect(x: 0, y: view.frame.height-visibleHeight, width: view.frame.width, height: view.frame.height)) - menuView.backgroundColor = isNight(self.readerConfig.nightModeMenuBackground, UIColor.white) + menuView.backgroundColor = self.folioReader.isNight(self.readerConfig.nightModeMenuBackground, UIColor.white) menuView.autoresizingMask = .flexibleWidth menuView.layer.shadowColor = UIColor.black.cgColor menuView.layer.shadowOffset = CGSize(width: 0, height: 0) diff --git a/Source/FolioReaderHighlightList.swift b/Source/FolioReaderHighlightList.swift index 64ef9c016..395e83728 100644 --- a/Source/FolioReaderHighlightList.swift +++ b/Source/FolioReaderHighlightList.swift @@ -35,7 +35,7 @@ class FolioReaderHighlightList: UITableViewController { self.tableView.backgroundColor = self.folioReader.isNight(self.readerConfig.nightModeMenuBackground, self.readerConfig.menuBackgroundColor) self.tableView.separatorColor = self.folioReader.isNight(self.readerConfig.nightModeSeparatorColor, self.readerConfig.menuSeparatorColor) - highlights = Highlight.allByBookId((kBookId as NSString).deletingPathExtension) + self.highlights = Highlight.allByBookId((kBookId as NSString).deletingPathExtension) } // MARK: - Table view data source From a9dbb414c150d4558a98b78b9c28240d7226bc91 Mon Sep 17 00:00:00 2001 From: Kevin Delord Date: Thu, 30 Mar 2017 16:59:51 +0200 Subject: [PATCH 011/110] Refactor FolioReaderPlayerMenu --- Source/FolioReaderCenter.swift | 6 +++-- Source/FolioReaderContainer.swift | 3 ++- Source/FolioReaderHighlightList.swift | 1 - Source/FolioReaderPlayerMenu.swift | 33 +++++++++++++++++---------- 4 files changed, 27 insertions(+), 16 deletions(-) diff --git a/Source/FolioReaderCenter.swift b/Source/FolioReaderCenter.swift index dc72c94ae..09049521d 100755 --- a/Source/FolioReaderCenter.swift +++ b/Source/FolioReaderCenter.swift @@ -825,7 +825,9 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo guard (resource == reference.resource), let title = item.title else { - return nil + // TODO_SMF: check if this really works fine (or if it was working anyway). + // Select text -> share. + return nil } return title @@ -1134,7 +1136,7 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo FolioReader.saveReaderState() hideBars() - let menu = FolioReaderPlayerMenu() + let menu = FolioReaderPlayerMenu(folioReader: self.readerContainer.folioReader, readerConfig: self.readerConfig) menu.modalPresentationStyle = .custom animator = ZFModalTransitionAnimator(modalViewController: menu) diff --git a/Source/FolioReaderContainer.swift b/Source/FolioReaderContainer.swift index a97475456..45b515986 100755 --- a/Source/FolioReaderContainer.swift +++ b/Source/FolioReaderContainer.swift @@ -17,7 +17,8 @@ open class FolioReaderContainer : UIViewController { var audioPlayer : FolioReaderAudioPlayer? var shouldHideStatusBar = true var shouldRemoveEpub = true - var epubPath : String? + // TODO_SMF: remove optional for book and epubPath + var epubPath : String? var book : FRBook? var readerConfig : FolioReaderConfig var folioReader : FolioReader diff --git a/Source/FolioReaderHighlightList.swift b/Source/FolioReaderHighlightList.swift index 395e83728..3be178aa2 100644 --- a/Source/FolioReaderHighlightList.swift +++ b/Source/FolioReaderHighlightList.swift @@ -26,7 +26,6 @@ class FolioReaderHighlightList: UITableViewController { fatalError("init with coder not supported") } - override func viewDidLoad() { super.viewDidLoad() diff --git a/Source/FolioReaderPlayerMenu.swift b/Source/FolioReaderPlayerMenu.swift index b926c8022..4ee45b1bc 100644 --- a/Source/FolioReaderPlayerMenu.swift +++ b/Source/FolioReaderPlayerMenu.swift @@ -8,16 +8,25 @@ import UIKit -class FolioReaderPlayerMenu: UIViewController, SMSegmentViewDelegate, UIGestureRecognizerDelegate { +class FolioReaderPlayerMenu : UIViewController, SMSegmentViewDelegate, UIGestureRecognizerDelegate { - var menuView: UIView! - var playPauseBtn: UIButton! - var styleOptionBtns = [UIButton]() - var viewDidAppear = false + var menuView : UIView! + var playPauseBtn : UIButton! + var styleOptionBtns = [UIButton]() + var viewDidAppear = false - fileprivate var readerConfig : FolioReaderConfig { - // TODO_SMF: remove this getter - return FolioReader.shared.readerContainer!.readerConfig + fileprivate var readerConfig : FolioReaderConfig + fileprivate var folioReader : FolioReader + + init(folioReader: FolioReader, readerConfig: FolioReaderConfig) { + self.readerConfig = readerConfig + self.folioReader = folioReader + + super.init(nibName: nil, bundle: nil) + } + + required init?(coder aDecoder: NSCoder) { + fatalError("init(coder:) has not been implemented") } override func viewDidLoad() { @@ -34,7 +43,7 @@ class FolioReaderPlayerMenu: UIViewController, SMSegmentViewDelegate, UIGestureR // Menu view menuView = UIView(frame: CGRect(x: 0, y: view.frame.height-165, width: view.frame.width, height: view.frame.height)) - menuView.backgroundColor = isNight(self.readerConfig.nightModeMenuBackground, UIColor.white) + menuView.backgroundColor = self.folioReader.isNight(self.readerConfig.nightModeMenuBackground, UIColor.white) menuView.autoresizingMask = .flexibleWidth menuView.layer.shadowColor = UIColor.black.cgColor menuView.layer.shadowOffset = CGSize(width: 0, height: 0) @@ -133,8 +142,8 @@ class FolioReaderPlayerMenu: UIViewController, SMSegmentViewDelegate, UIGestureR let style0 = UIButton(frame: CGRect(x: 0, y: line2.frame.height+line2.frame.origin.y, width: view.frame.width/3, height: 55)) style0.titleLabel!.textAlignment = .center style0.titleLabel!.font = UIFont(name: "Avenir-Light", size: 17) - style0.setTitleColor(isNight(self.readerConfig.nightModeMenuBackground, UIColor.white), for: UIControlState()) - style0.setTitleColor(isNight(self.readerConfig.nightModeMenuBackground, UIColor.white), for: .selected) + style0.setTitleColor(self.folioReader.isNight(self.readerConfig.nightModeMenuBackground, UIColor.white), for: UIControlState()) + style0.setTitleColor(self.folioReader.isNight(self.readerConfig.nightModeMenuBackground, UIColor.white), for: .selected) style0.setTitle(self.readerConfig.localizedPlayerMenuStyle, for: UIControlState()) menuView.addSubview(style0); style0.titleLabel?.sizeToFit() @@ -157,7 +166,7 @@ class FolioReaderPlayerMenu: UIViewController, SMSegmentViewDelegate, UIGestureR NSUnderlineColorAttributeName: normalColor ]), for: UIControlState()) style1.setAttributedTitle(NSAttributedString(string: self.readerConfig.localizedPlayerMenuStyle, attributes: [ - NSForegroundColorAttributeName: isNight(UIColor.white, UIColor.black), + NSForegroundColorAttributeName: self.folioReader.isNight(UIColor.white, UIColor.black), NSUnderlineStyleAttributeName: NSUnderlineStyle.patternDot.rawValue|NSUnderlineStyle.styleSingle.rawValue, NSUnderlineColorAttributeName: selectedColor ]), for: .selected) From 81b2e75786323755d00a4926923f9fa8239daed5 Mon Sep 17 00:00:00 2001 From: Kevin Delord Date: Thu, 30 Mar 2017 17:10:03 +0200 Subject: [PATCH 012/110] Refactor FolioReaderQuoteShare --- Source/FolioReaderCenter.swift | 2 +- Source/FolioReaderContainer.swift | 1 - Source/FolioReaderKit.swift | 2 +- Source/FolioReaderQuoteShare.swift | 27 +++++++++++++-------------- 4 files changed, 15 insertions(+), 17 deletions(-) diff --git a/Source/FolioReaderCenter.swift b/Source/FolioReaderCenter.swift index 09049521d..7499ff4b0 100755 --- a/Source/FolioReaderCenter.swift +++ b/Source/FolioReaderCenter.swift @@ -1155,7 +1155,7 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo Present Quote Share */ func presentQuoteShare(_ string: String) { - let quoteShare = FolioReaderQuoteShare(initWithText: string) + let quoteShare = FolioReaderQuoteShare(initWithText: string, readerConfig: self.readerConfig, folioReader: self.readerContainer.folioReader) let nav = UINavigationController(rootViewController: quoteShare) if isPad { diff --git a/Source/FolioReaderContainer.swift b/Source/FolioReaderContainer.swift index 45b515986..fb2502521 100755 --- a/Source/FolioReaderContainer.swift +++ b/Source/FolioReaderContainer.swift @@ -93,7 +93,6 @@ open class FolioReaderContainer : UIViewController { override open func viewDidLoad() { super.viewDidLoad() - // TODO_SMF: wtf let canChangeScrollDirection = self.readerConfig.canChangeScrollDirection self.readerConfig.canChangeScrollDirection = self.readerConfig.isDirection(canChangeScrollDirection, canChangeScrollDirection, false) diff --git a/Source/FolioReaderKit.swift b/Source/FolioReaderKit.swift index 5bcb1f109..2c195f97d 100755 --- a/Source/FolioReaderKit.swift +++ b/Source/FolioReaderKit.swift @@ -91,7 +91,7 @@ open class FolioReader: NSObject { /// FolioReaderDelegate open weak var delegate : FolioReaderDelegate? - // TODO_SMF_QUESTION: male those fileprivate (or internal) to avoid public access from other class? + // TODO_SMF_QUESTION: make those fileprivate (or internal) to avoid public access from other class? open weak var readerContainer : FolioReaderContainer? open weak var readerAudioPlayer : FolioReaderAudioPlayer? open weak var readerCenter : FolioReaderCenter? { diff --git a/Source/FolioReaderQuoteShare.swift b/Source/FolioReaderQuoteShare.swift index f55fdd53f..260a225fc 100644 --- a/Source/FolioReaderQuoteShare.swift +++ b/Source/FolioReaderQuoteShare.swift @@ -8,7 +8,6 @@ import UIKit - class FolioReaderQuoteShare: UIViewController { var quoteText: String! var filterImage: UIView! @@ -24,21 +23,21 @@ class FolioReaderQuoteShare: UIViewController { let imagePicker = UIImagePickerController() var selectedIndex = 0 - fileprivate var book : FRBook? { - // TODO_SMF: remove this getter - return FolioReader.shared.readerContainer?.book + fileprivate var book: FRBook? { + return self.folioReader.readerContainer?.book } - fileprivate var readerConfig : FolioReaderConfig { - // TODO_SMF: remove this getter - return FolioReader.shared.readerContainer!.readerConfig - } + fileprivate var folioReader : FolioReader + fileprivate var readerConfig : FolioReaderConfig // MARK: Init - init(initWithText shareText: String) { + init(initWithText shareText: String, readerConfig: FolioReaderConfig, folioReader: FolioReader) { + self.folioReader = folioReader + self.readerConfig = readerConfig + self.quoteText = shareText.stripLineBreaks().stripHtml() + super.init(nibName: nil, bundle: Bundle.frameworkBundle()) - self.quoteText = shareText.stripLineBreaks().stripHtml() } required init?(coder aDecoder: NSCoder) { @@ -160,7 +159,7 @@ class FolioReaderQuoteShare: UIViewController { collectionViewLayout.minimumInteritemSpacing = 0 collectionViewLayout.scrollDirection = .horizontal - let background = isNight(self.readerConfig.nightModeBackground, UIColor.white) + let background = self.folioReader.isNight(self.readerConfig.nightModeBackground, UIColor.white) view.backgroundColor = background // CollectionView @@ -194,9 +193,9 @@ class FolioReaderQuoteShare: UIViewController { } func configureNavBar() { - let navBackground = isNight(self.readerConfig.nightModeMenuBackground, UIColor.white) + let navBackground = self.folioReader.isNight(self.readerConfig.nightModeMenuBackground, UIColor.white) let tintColor = self.readerConfig.tintColor - let navText = isNight(UIColor.white, UIColor.black) + let navText = self.folioReader.isNight(UIColor.white, UIColor.black) let font = UIFont(name: "Avenir-Light", size: 17)! setTranslucentNavigation(false, color: navBackground, tintColor: tintColor, titleColor: navText, andFont: font) } @@ -300,7 +299,7 @@ class FolioReaderQuoteShare: UIViewController { // MARK: Status Bar override var preferredStatusBarStyle : UIStatusBarStyle { - return isNight(.lightContent, .default) + return self.folioReader.isNight(.lightContent, .default) } override var supportedInterfaceOrientations : UIInterfaceOrientationMask { From d13cf98258831cc9f93212c5b35448ccd896bf2e Mon Sep 17 00:00:00 2001 From: Kevin Delord Date: Thu, 30 Mar 2017 17:12:56 +0200 Subject: [PATCH 013/110] Refactor FolioReaderAudioPlayer --- Source/FolioReaderAudioPlayer.swift | 8 +++----- Source/FolioReaderContainer.swift | 2 +- 2 files changed, 4 insertions(+), 6 deletions(-) diff --git a/Source/FolioReaderAudioPlayer.swift b/Source/FolioReaderAudioPlayer.swift index daf4638b1..fcdc2ccfe 100644 --- a/Source/FolioReaderAudioPlayer.swift +++ b/Source/FolioReaderAudioPlayer.swift @@ -28,15 +28,13 @@ open class FolioReaderAudioPlayer: NSObject { var completionHandler: () -> Void = {} var utteranceRate: Float = 0 - fileprivate var book : FRBook? { - // TODO_SMF: remove this getter - return FolioReader.shared.readerContainer?.book - } + fileprivate var book : FRBook? // MARK: Init - override init() { + init(withBook book: FRBook?) { super.init() + self.book = book UIApplication.shared.beginReceivingRemoteControlEvents() // this is needed to the audio can play even when the "silent/vibrate" toggle is on diff --git a/Source/FolioReaderContainer.swift b/Source/FolioReaderContainer.swift index fb2502521..f25fbc6aa 100755 --- a/Source/FolioReaderContainer.swift +++ b/Source/FolioReaderContainer.swift @@ -179,7 +179,7 @@ open class FolioReaderContainer : UIViewController { Initialize the media player */ func addAudioPlayer() { - self.audioPlayer = FolioReaderAudioPlayer() + self.audioPlayer = FolioReaderAudioPlayer(withBook: self.book) self.folioReader.readerAudioPlayer = audioPlayer } From b3876c8ce9be75ec41eb02255ced7754c62eeb62 Mon Sep 17 00:00:00 2001 From: Kevin Delord Date: Thu, 30 Mar 2017 17:21:02 +0200 Subject: [PATCH 014/110] Refactor FolioReaderWebView.swift --- Source/FolioReaderPage.swift | 2 +- Source/FolioReaderWebView.swift | 30 +++++++++++++++++++----------- 2 files changed, 20 insertions(+), 12 deletions(-) diff --git a/Source/FolioReaderPage.swift b/Source/FolioReaderPage.swift index 7c63fe824..1c9fd2353 100755 --- a/Source/FolioReaderPage.swift +++ b/Source/FolioReaderPage.swift @@ -61,7 +61,7 @@ open class FolioReaderPage: UICollectionViewCell, UIWebViewDelegate, UIGestureRe NotificationCenter.default.addObserver(self, selector: #selector(refreshPageMode), name: NSNotification.Name(rawValue: "needRefreshPageMode"), object: nil) if webView == nil { - webView = FolioReaderWebView(frame: webViewFrame()) + webView = FolioReaderWebView(frame: webViewFrame(), readerConfig: self.readerConfig, book: self.book) webView.autoresizingMask = [.flexibleWidth, .flexibleHeight] webView.dataDetectorTypes = .link webView.scrollView.showsVerticalScrollIndicator = false diff --git a/Source/FolioReaderWebView.swift b/Source/FolioReaderWebView.swift index 397ca32b1..078d20a98 100644 --- a/Source/FolioReaderWebView.swift +++ b/Source/FolioReaderWebView.swift @@ -9,19 +9,27 @@ import UIKit /// The custom WebView used in each page -open class FolioReaderWebView: UIWebView { - var isColors = false - var isShare = false - var isOneWord = false - - fileprivate var book : FRBook? { - // TODO_SMF: remove this getter - return FolioReader.shared.readerContainer?.book +open class FolioReaderWebView : UIWebView { + var isColors = false + var isShare = false + var isOneWord = false + + fileprivate var book : FRBook? + fileprivate var readerConfig : FolioReaderConfig + + override init(frame: CGRect) { + fatalError("use init(frame:readerConfig:book:) instead.") } - fileprivate var readerConfig : FolioReaderConfig { - // TODO_SMF: remove this getter - return FolioReader.shared.readerContainer!.readerConfig + init(frame: CGRect, readerConfig: FolioReaderConfig, book: FRBook?) { + self.readerConfig = readerConfig + self.book = book + + super.init(frame: frame) + } + + required public init?(coder aDecoder: NSCoder) { + fatalError("init(coder:) has not been implemented") } // MARK: - UIMenuController From f0e19e6ede52519c4800188ed698ff7167e317da Mon Sep 17 00:00:00 2001 From: Kevin Delord Date: Thu, 30 Mar 2017 18:01:53 +0200 Subject: [PATCH 015/110] Highlight: remove explicit try! --- Source/FolioReaderWebView.swift | 11 +- Source/Models/Highlight+Helper.swift | 415 ++++++++++++++------------- Source/Models/Highlight.swift | 2 - 3 files changed, 224 insertions(+), 204 deletions(-) diff --git a/Source/FolioReaderWebView.swift b/Source/FolioReaderWebView.swift index 078d20a98..018e21b43 100644 --- a/Source/FolioReaderWebView.swift +++ b/Source/FolioReaderWebView.swift @@ -132,10 +132,15 @@ open class FolioReaderWebView : UIWebView { setMenuVisible(true, andRect: rect) // Persist - let html = js("getHTML()") - if let highlight = Highlight.matchHighlight(html, andId: dic["id"]!, startOffset: startOffset, endOffset: endOffset) { - highlight.persist() + guard + let html = js("getHTML()"), + let identifier = dic["id"], + let highlight = Highlight.matchHighlight(html, andId: identifier, startOffset: startOffset, endOffset: endOffset) else { + return } + + highlight.persist() + } catch { print("Could not receive JSON") } diff --git a/Source/Models/Highlight+Helper.swift b/Source/Models/Highlight+Helper.swift index bde0a936d..ee848090d 100644 --- a/Source/Models/Highlight+Helper.swift +++ b/Source/Models/Highlight+Helper.swift @@ -85,204 +85,221 @@ extension Highlight { return FolioReader.shared.readerContainer!.readerConfig } - // TODO_SMF: replace try with a 'do-try-catch' or at least a 'try?'. + /** + Save a Highlight with completion block - /** - Save a Highlight with completion block - - - parameter completion: Completion block - */ - public func persist(_ completion: Completion? = nil) { - do { - let realm = try! Realm(configuration: Highlight.readerConfig.realmConfiguration) - realm.beginWrite() - realm.add(self, update: true) - try realm.commitWrite() - completion?(nil) - } catch let error as NSError { - print("Error on persist highlight: \(error)") - completion?(error) - } - } - - /** - Remove a Highlight - */ - public func remove() { - do { - let realm = try! Realm(configuration: Highlight.readerConfig.realmConfiguration) - realm.beginWrite() - realm.delete(self) - try realm.commitWrite() - } catch let error as NSError { - print("Error on remove highlight: \(error)") - } - } - - /** - Remove a Highlight by ID - - - parameter highlightId: The ID to be removed - */ - public static func removeById(_ highlightId: String) { - var highlight: Highlight? - let predicate = NSPredicate(format:"highlightId = %@", highlightId) - - let realm = try! Realm(configuration: self.readerConfig.realmConfiguration) - highlight = realm.objects(Highlight.self).filter(predicate).toArray(Highlight.self).first - highlight?.remove() - } - - /** - Update a Highlight by ID - - - parameter highlightId: The ID to be removed - - parameter type: The `HighlightStyle` - */ - public static func updateById(_ highlightId: String, type: HighlightStyle) { - var highlight: Highlight? - let predicate = NSPredicate(format:"highlightId = %@", highlightId) - do { - let realm = try! Realm(configuration: self.readerConfig.realmConfiguration) - highlight = realm.objects(Highlight.self).filter(predicate).toArray(Highlight.self).first - realm.beginWrite() - - highlight?.type = type.hashValue - - try realm.commitWrite() - } catch let error as NSError { - print("Error on updateById : \(error)") - } - - } - - /** - Return a list of Highlights with a given ID - - - parameter bookId: Book ID - - parameter page: Page number - - - returns: Return a list of Highlights - */ - public static func allByBookId(_ bookId: String, andPage page: NSNumber? = nil) -> [Highlight] { - var highlights: [Highlight]? - let predicate = (page != nil) ? NSPredicate(format: "bookId = %@ && page = %@", bookId, page!) : NSPredicate(format: "bookId = %@", bookId) - let realm = try! Realm(configuration: self.readerConfig.realmConfiguration) - highlights = realm.objects(Highlight.self).filter(predicate).toArray(Highlight.self) - return highlights! - } - - /** - Return all Highlights - - - returns: Return all Highlights - */ - public static func all() -> [Highlight] { - var highlights: [Highlight]? - let realm = try! Realm(configuration: self.readerConfig.realmConfiguration) - highlights = realm.objects(Highlight.self).toArray(Highlight.self) - return highlights! - } - - // MARK: HTML Methods - - /** - Match a highlight on string. - */ - public static func matchHighlight(_ text: String!, andId id: String, startOffset: String, endOffset: String) -> Highlight? { - let pattern = "((.|\\s)*?)" - let regex = try! NSRegularExpression(pattern: pattern, options: []) - let matches = regex.matches(in: text, options: [], range: NSRange(location: 0, length: text.utf16.count)) - let str = (text as NSString) - - let mapped = matches.map { (match) -> Highlight in - var contentPre = str.substring(with: NSRange(location: match.range.location-kHighlightRange, length: kHighlightRange)) - var contentPost = str.substring(with: NSRange(location: match.range.location + match.range.length, length: kHighlightRange)) - - // Normalize string before save - - if contentPre.range(of: ">") != nil { - let regex = try! NSRegularExpression(pattern: "((?=[^>]*$)(.|\\s)*$)", options: []) - let searchString = regex.firstMatch(in: contentPre, options: .reportProgress, range: NSRange(location: 0, length: contentPre.characters.count)) - - if searchString!.range.location != NSNotFound { - contentPre = (contentPre as NSString).substring(with: searchString!.range) - } - } - - if contentPost.range(of: "<") != nil { - let regex = try! NSRegularExpression(pattern: "^((.|\\s)*?)(?=<)", options: []) - let searchString = regex.firstMatch(in: contentPost, options: .reportProgress, range: NSRange(location: 0, length: contentPost.characters.count)) - - if searchString!.range.location != NSNotFound { - contentPost = (contentPost as NSString).substring(with: searchString!.range) - } - } - - let highlight = Highlight() - highlight.highlightId = id - highlight.type = HighlightStyle.styleForClass(str.substring(with: match.rangeAt(1))).rawValue - highlight.date = Foundation.Date() - highlight.content = Highlight.removeSentenceSpam(str.substring(with: match.rangeAt(2))) - highlight.contentPre = Highlight.removeSentenceSpam(contentPre) - highlight.contentPost = Highlight.removeSentenceSpam(contentPost) - highlight.page = currentPageNumber - highlight.bookId = (kBookId as NSString).deletingPathExtension - highlight.startOffset = Int(startOffset) ?? -1 - highlight.endOffset = Int(endOffset) ?? -1 - - return highlight - } - return mapped.first - } - - /** - Remove a Highlight from HTML by ID - - - parameter highlightId: The ID to be removed - - returns: The removed id - */ - @discardableResult public static func removeFromHTMLById(_ highlightId: String) -> String? { - guard let currentPage = FolioReader.shared.readerCenter?.currentPage else { return nil } - - if let removedId = currentPage.webView.js("removeHighlightById('\(highlightId)')") { - return removedId - } else { - print("Error removing Higlight from page") - return nil - } - } - - /** - Remove span tag before store the highlight, this span is added on JavaScript. - - - - parameter text: Text to analise - - returns: Striped text - */ - public static func removeSentenceSpam(_ text: String) -> String { - - // Remove from text - func removeFrom(_ text: String, withPattern pattern: String) -> String { - var locator = text - let regex = try! NSRegularExpression(pattern: pattern, options: []) - let matches = regex.matches(in: locator, options: [], range: NSRange(location: 0, length: locator.utf16.count)) - let str = (locator as NSString) - - var newLocator = "" - for match in matches { - newLocator += str.substring(with: match.rangeAt(1)) - } - - if matches.count > 0 && !newLocator.isEmpty { - locator = newLocator - } - - return locator - } - - let pattern = "((.|\\s)*?)" - let cleanText = removeFrom(text, withPattern: pattern) - return cleanText - } + - parameter completion: Completion block + */ + public func persist(_ completion: Completion? = nil) { + do { + let realm = try Realm(configuration: Highlight.readerConfig.realmConfiguration) + realm.beginWrite() + realm.add(self, update: true) + try realm.commitWrite() + completion?(nil) + } catch let error as NSError { + print("Error on persist highlight: \(error)") + completion?(error) + } + } + + /** + Remove a Highlight + */ + public func remove() { + do { + let realm = try Realm(configuration: Highlight.readerConfig.realmConfiguration) + realm.beginWrite() + realm.delete(self) + try realm.commitWrite() + } catch let error as NSError { + print("Error on remove highlight: \(error)") + } + } + + /** + Remove a Highlight by ID + + - parameter highlightId: The ID to be removed + */ + public static func removeById(_ highlightId: String) { + var highlight: Highlight? + let predicate = NSPredicate(format:"highlightId = %@", highlightId) + + do { + let realm = try Realm(configuration: self.readerConfig.realmConfiguration) + highlight = realm.objects(Highlight.self).filter(predicate).toArray(Highlight.self).first + highlight?.remove() + } catch let error as NSError { + print("Error on remove highlight by id: \(error)") + } + } + + /** + Update a Highlight by ID + + - parameter highlightId: The ID to be removed + - parameter type: The `HighlightStyle` + */ + public static func updateById(_ highlightId: String, type: HighlightStyle) { + var highlight: Highlight? + let predicate = NSPredicate(format:"highlightId = %@", highlightId) + do { + let realm = try Realm(configuration: self.readerConfig.realmConfiguration) + highlight = realm.objects(Highlight.self).filter(predicate).toArray(Highlight.self).first + realm.beginWrite() + + highlight?.type = type.hashValue + + try realm.commitWrite() + } catch let error as NSError { + print("Error on updateById: \(error)") + } + + } + + /** + Return a list of Highlights with a given ID + + - parameter bookId: Book ID + - parameter page: Page number + + - returns: Return a list of Highlights + */ + public static func allByBookId(_ bookId: String, andPage page: NSNumber? = nil) -> [Highlight] { + var highlights: [Highlight]? + var predicate = NSPredicate(format: "bookId = %@", bookId) + if let page = page { + predicate = NSPredicate(format: "bookId = %@ && page = %@", bookId, page) + } + + do { + let realm = try Realm(configuration: self.readerConfig.realmConfiguration) + highlights = realm.objects(Highlight.self).filter(predicate).toArray(Highlight.self) + return (highlights ?? []) + } catch let error as NSError { + print("Error on fetch all by book Id: \(error)") + return [] + } + } + + /** + Return all Highlights + + - returns: Return all Highlights + */ + public static func all() -> [Highlight] { + var highlights: [Highlight]? + do { + let realm = try Realm(configuration: self.readerConfig.realmConfiguration) + highlights = realm.objects(Highlight.self).toArray(Highlight.self) + return (highlights ?? []) + } catch let error as NSError { + print("Error on fetch all: \(error)") + return [] + } + } + + // MARK: HTML Methods + + /** + Match a highlight on string. + */ + public static func matchHighlight(_ text: String, andId id: String, startOffset: String, endOffset: String) -> Highlight? { + let pattern = "((.|\\s)*?)" + let regex = try? NSRegularExpression(pattern: pattern, options: []) + let matches = regex?.matches(in: text, options: [], range: NSRange(location: 0, length: text.utf16.count)) + let str = (text as NSString) + + let mapped = matches?.map { (match) -> Highlight in + var contentPre = str.substring(with: NSRange(location: match.range.location-kHighlightRange, length: kHighlightRange)) + var contentPost = str.substring(with: NSRange(location: match.range.location + match.range.length, length: kHighlightRange)) + + // Normalize string before save + contentPre = Highlight.subString(ofContent: contentPre, fromRangeOfString: ">", withPattern: "((?=[^>]*$)(.|\\s)*$)") + contentPost = Highlight.subString(ofContent: contentPost, fromRangeOfString: "<", withPattern: "^((.|\\s)*?)(?=<)") + + let highlight = Highlight() + highlight.highlightId = id + highlight.type = HighlightStyle.styleForClass(str.substring(with: match.rangeAt(1))).rawValue + highlight.date = Foundation.Date() + highlight.content = Highlight.removeSentenceSpam(str.substring(with: match.rangeAt(2))) + highlight.contentPre = Highlight.removeSentenceSpam(contentPre) + highlight.contentPost = Highlight.removeSentenceSpam(contentPost) + highlight.page = currentPageNumber + highlight.bookId = (kBookId as NSString).deletingPathExtension + highlight.startOffset = (Int(startOffset) ?? -1) + highlight.endOffset = (Int(endOffset) ?? -1) + + return highlight + } + + return mapped?.first + } + + private static func subString(ofContent content: String, fromRangeOfString rangeString: String, withPattern pattern: String) -> String { + + var updatedContent = content + if updatedContent.range(of: rangeString) != nil { + let regex = try? NSRegularExpression(pattern: pattern, options: []) + let searchString = regex?.firstMatch(in: updatedContent, options: .reportProgress, range: NSRange(location: 0, length: updatedContent.characters.count)) + + if let string = searchString, (string.range.location != NSNotFound) { + updatedContent = (updatedContent as NSString).substring(with: string.range) + } + } + + return updatedContent + } + + /** + Remove a Highlight from HTML by ID + + - parameter highlightId: The ID to be removed + - returns: The removed id + */ + @discardableResult public static func removeFromHTMLById(_ highlightId: String) -> String? { + guard let currentPage = FolioReader.shared.readerCenter?.currentPage else { return nil } + + if let removedId = currentPage.webView.js("removeHighlightById('\(highlightId)')") { + return removedId + } else { + print("Error removing Higlight from page") + return nil + } + } + + /** + Remove span tag before store the highlight, this span is added on JavaScript. + + + - parameter text: Text to analise + - returns: Striped text + */ + public static func removeSentenceSpam(_ text: String) -> String { + + // Remove from text + func removeFrom(_ text: String, withPattern pattern: String) -> String { + var locator = text + let regex = try? NSRegularExpression(pattern: pattern, options: []) + let matches = regex?.matches(in: locator, options: [], range: NSRange(location: 0, length: locator.utf16.count)) + let str = (locator as NSString) + + var newLocator = "" + // TODO_SMF: check this and add match type + matches?.forEach( { match in + newLocator += str.substring(with: match.rangeAt(1)) + }) + + if (matches?.count > 0 && newLocator.isEmpty == false) { + locator = newLocator + } + + return locator + } + + let pattern = "((.|\\s)*?)" + let cleanText = removeFrom(text, withPattern: pattern) + return cleanText + } } diff --git a/Source/Models/Highlight.swift b/Source/Models/Highlight.swift index 363f606e6..6f3466cb0 100644 --- a/Source/Models/Highlight.swift +++ b/Source/Models/Highlight.swift @@ -9,8 +9,6 @@ import Foundation import RealmSwift -// TODO_SMF: Remove `!`. - /// A Highlight object open class Highlight: Object { open dynamic var bookId: String! From 9634542c56ab00f7e3079bb31c0acef1ed67c60c Mon Sep 17 00:00:00 2001 From: Kevin Delord Date: Thu, 30 Mar 2017 18:31:57 +0200 Subject: [PATCH 016/110] Database method: integrate dynamic reader configuration --- Source/FolioReaderHighlightList.swift | 13 ++- Source/FolioReaderKit.swift | 4 +- Source/FolioReaderPage.swift | 2 +- Source/FolioReaderWebView.swift | 6 +- Source/Models/Highlight+Helper.swift | 141 ++++++++++++++++++-------- 5 files changed, 108 insertions(+), 58 deletions(-) diff --git a/Source/FolioReaderHighlightList.swift b/Source/FolioReaderHighlightList.swift index 3be178aa2..676cba59e 100644 --- a/Source/FolioReaderHighlightList.swift +++ b/Source/FolioReaderHighlightList.swift @@ -8,12 +8,11 @@ import UIKit -class FolioReaderHighlightList: UITableViewController { +class FolioReaderHighlightList : UITableViewController { - var highlights: [Highlight]! - - fileprivate var readerConfig : FolioReaderConfig - fileprivate var folioReader : FolioReader + fileprivate var highlights = [Highlight]() + fileprivate var readerConfig : FolioReaderConfig + fileprivate var folioReader : FolioReader init(folioReader: FolioReader, readerConfig: FolioReaderConfig) { self.readerConfig = readerConfig @@ -34,7 +33,7 @@ class FolioReaderHighlightList: UITableViewController { self.tableView.backgroundColor = self.folioReader.isNight(self.readerConfig.nightModeMenuBackground, self.readerConfig.menuBackgroundColor) self.tableView.separatorColor = self.folioReader.isNight(self.readerConfig.nightModeSeparatorColor, self.readerConfig.menuSeparatorColor) - self.highlights = Highlight.allByBookId((kBookId as NSString).deletingPathExtension) + self.highlights = Highlight.allByBookId(withConfiguration: self.readerConfig, bookId: (kBookId as NSString).deletingPathExtension) } // MARK: - Table view data source @@ -151,7 +150,7 @@ class FolioReaderHighlightList: UITableViewController { Highlight.removeFromHTMLById(highlight.highlightId) // Remove from HTML } - highlight.remove() // Remove from Database + highlight.remove(withConfiguration: self.readerConfig) // Remove from Database highlights.remove(at: (indexPath as NSIndexPath).row) tableView.deleteRows(at: [indexPath], with: .fade) } diff --git a/Source/FolioReaderKit.swift b/Source/FolioReaderKit.swift index 2c195f97d..81e1c25c7 100755 --- a/Source/FolioReaderKit.swift +++ b/Source/FolioReaderKit.swift @@ -25,8 +25,8 @@ internal let kCurrentFontFamily = "com.folioreader.kCurrentFontFamily" internal let kCurrentFontSize = "com.folioreader.kCurrentFontSize" internal let kCurrentAudioRate = "com.folioreader.kCurrentAudioRate" internal let kCurrentHighlightStyle = "com.folioreader.kCurrentHighlightStyle" -internal var kCurrentMediaOverlayStyle = "com.folioreader.kMediaOverlayStyle" -internal var kCurrentScrollDirection = "com.folioreader.kCurrentScrollDirection" +internal let kCurrentMediaOverlayStyle = "com.folioreader.kMediaOverlayStyle" +internal let kCurrentScrollDirection = "com.folioreader.kCurrentScrollDirection" internal let kNightMode = "com.folioreader.kNightMode" internal let kCurrentTOCMenu = "com.folioreader.kCurrentTOCMenu" internal let kHighlightRange = 30 diff --git a/Source/FolioReaderPage.swift b/Source/FolioReaderPage.swift index 1c9fd2353..05b431f5a 100755 --- a/Source/FolioReaderPage.swift +++ b/Source/FolioReaderPage.swift @@ -132,7 +132,7 @@ open class FolioReaderPage: UICollectionViewCell, UIWebViewDelegate, UIGestureRe fileprivate func htmlContentWithInsertHighlights(_ htmlContent: String) -> String { var tempHtmlContent = htmlContent as NSString // Restore highlights - let highlights = Highlight.allByBookId((kBookId as NSString).deletingPathExtension, andPage: pageNumber as NSNumber?) + let highlights = Highlight.allByBookId(withConfiguration: self.readerConfig, bookId: (kBookId as NSString).deletingPathExtension, andPage: pageNumber as NSNumber?) if highlights.count > 0 { for item in highlights { diff --git a/Source/FolioReaderWebView.swift b/Source/FolioReaderWebView.swift index 018e21b43..e469928a2 100644 --- a/Source/FolioReaderWebView.swift +++ b/Source/FolioReaderWebView.swift @@ -110,7 +110,7 @@ open class FolioReaderWebView : UIWebView { func remove(_ sender: UIMenuController?) { if let removedId = js("removeThisHighlight()") { - Highlight.removeById(removedId) + Highlight.removeById(withConfiguration: self.readerConfig, highlightId: removedId) } setMenuVisible(false) } @@ -139,7 +139,7 @@ open class FolioReaderWebView : UIWebView { return } - highlight.persist() + highlight.persist(withConfiguration: self.readerConfig) } catch { print("Could not receive JSON") @@ -188,7 +188,7 @@ open class FolioReaderWebView : UIWebView { FolioReader.currentHighlightStyle = style.rawValue if let updateId = js("setHighlightStyle('\(HighlightStyle.classForStyle(style.rawValue))')") { - Highlight.updateById(updateId, type: style) + Highlight.updateById(withConfiguration: self.readerConfig, highlightId: updateId, type: style) } colors(sender) } diff --git a/Source/Models/Highlight+Helper.swift b/Source/Models/Highlight+Helper.swift index ee848090d..dbe83eddf 100644 --- a/Source/Models/Highlight+Helper.swift +++ b/Source/Models/Highlight+Helper.swift @@ -80,19 +80,27 @@ public typealias Completion = (_ error: NSError?) -> () extension Highlight { - fileprivate static var readerConfig : FolioReaderConfig { - // TODO_SMF: remove this getter + private static var readerConfig : FolioReaderConfig { + // TODO_SMF: deprecate return FolioReader.shared.readerContainer!.readerConfig } - /** - Save a Highlight with completion block - - - parameter completion: Completion block - */ + /// Save a Highlight with completion block + /// + /// - Parameter completion: Completion block public func persist(_ completion: Completion? = nil) { + // TODO_SMF: deprecate + self.persist(withConfiguration: Highlight.readerConfig, completion: completion) + } + + /// Save a Highlight with completion block + /// + /// - Parameters: + /// - readerConfig: Current folio reader configuration. + /// - completion: Completion block. + public func persist(withConfiguration readerConfig: FolioReaderConfig, completion: Completion? = nil) { do { - let realm = try Realm(configuration: Highlight.readerConfig.realmConfiguration) + let realm = try Realm(configuration: readerConfig.realmConfiguration) realm.beginWrite() realm.add(self, update: true) try realm.commitWrite() @@ -103,12 +111,18 @@ extension Highlight { } } - /** - Remove a Highlight - */ + /// Remove a Highlight public func remove() { + // TODO_SMF: deprecate + self.remove(withConfiguration: Highlight.readerConfig) + } + + /// Remove a Highlight + /// + /// - Parameter readerConfig: Current folio reader configuration. + public func remove(withConfiguration readerConfig: FolioReaderConfig) { do { - let realm = try Realm(configuration: Highlight.readerConfig.realmConfiguration) + let realm = try Realm(configuration: readerConfig.realmConfiguration) realm.beginWrite() realm.delete(self) try realm.commitWrite() @@ -117,35 +131,53 @@ extension Highlight { } } - /** - Remove a Highlight by ID - - - parameter highlightId: The ID to be removed - */ + /// Remove a Highlight by ID + /// + /// - Parameter highlightId: The ID to be removed public static func removeById(_ highlightId: String) { + // TODO_SMF: deprecate + Highlight.removeById(withConfiguration: Highlight.readerConfig, highlightId: highlightId) + } + + /// Remove a Highlight by ID + /// + /// - Parameters: + /// - readerConfig: Current folio reader configuration. + /// - highlightId: The ID to be removed + public static func removeById(withConfiguration readerConfig: FolioReaderConfig, highlightId: String) { var highlight: Highlight? let predicate = NSPredicate(format:"highlightId = %@", highlightId) do { - let realm = try Realm(configuration: self.readerConfig.realmConfiguration) + let realm = try Realm(configuration: readerConfig.realmConfiguration) highlight = realm.objects(Highlight.self).filter(predicate).toArray(Highlight.self).first - highlight?.remove() + highlight?.remove(withConfiguration: readerConfig) } catch let error as NSError { print("Error on remove highlight by id: \(error)") } } - /** - Update a Highlight by ID - - - parameter highlightId: The ID to be removed - - parameter type: The `HighlightStyle` - */ + /// Update a Highlight by ID + /// + /// - Parameters: + /// - highlightId: The ID to be removed + /// - type: The `HighlightStyle` public static func updateById(_ highlightId: String, type: HighlightStyle) { + // TODO_SMF: deprecate + Highlight.updateById(withConfiguration: Highlight.readerConfig, highlightId: highlightId, type: type) + } + + /// Update a Highlight by ID + /// + /// - Parameters: + /// - readerConfig: Current folio reader configuration. + /// - highlightId: The ID to be removed + /// - type: The `HighlightStyle` + public static func updateById(withConfiguration readerConfig: FolioReaderConfig, highlightId: String, type: HighlightStyle) { var highlight: Highlight? let predicate = NSPredicate(format:"highlightId = %@", highlightId) do { - let realm = try Realm(configuration: self.readerConfig.realmConfiguration) + let realm = try Realm(configuration: readerConfig.realmConfiguration) highlight = realm.objects(Highlight.self).filter(predicate).toArray(Highlight.self).first realm.beginWrite() @@ -158,15 +190,25 @@ extension Highlight { } - /** - Return a list of Highlights with a given ID - - - parameter bookId: Book ID - - parameter page: Page number - - - returns: Return a list of Highlights - */ + /// Return a list of Highlights with a given ID + /// + /// - Parameters: + /// - bookId: Book ID + /// - page: Page number + /// - Returns: Return a list of Highlights public static func allByBookId(_ bookId: String, andPage page: NSNumber? = nil) -> [Highlight] { + // TODO_SMF: deprecate + return Highlight.allByBookId(withConfiguration: Highlight.readerConfig, bookId: bookId, andPage: page) + } + + /// Return a list of Highlights with a given ID + /// + /// - Parameters: + /// - readerConfig: Current folio reader configuration. + /// - bookId: Book ID + /// - page: Page number + /// - Returns: Return a list of Highlights + public static func allByBookId(withConfiguration readerConfig: FolioReaderConfig, bookId: String, andPage page: NSNumber? = nil) -> [Highlight] { var highlights: [Highlight]? var predicate = NSPredicate(format: "bookId = %@", bookId) if let page = page { @@ -174,7 +216,7 @@ extension Highlight { } do { - let realm = try Realm(configuration: self.readerConfig.realmConfiguration) + let realm = try Realm(configuration: readerConfig.realmConfiguration) highlights = realm.objects(Highlight.self).filter(predicate).toArray(Highlight.self) return (highlights ?? []) } catch let error as NSError { @@ -183,15 +225,22 @@ extension Highlight { } } - /** - Return all Highlights - - - returns: Return all Highlights - */ + /// Return all Highlights + /// + /// - Returns: Return all Highlights public static func all() -> [Highlight] { + // TODO_SMF: deprecate + return Highlight.all(withConfiguration: Highlight.readerConfig) + } + + /// Return all Highlights + /// + /// - Parameter readerConfig: - readerConfig: Current folio reader configuration. + /// - Returns: Return all Highlights + public static func all(withConfiguration readerConfig: FolioReaderConfig) -> [Highlight] { var highlights: [Highlight]? do { - let realm = try Realm(configuration: self.readerConfig.realmConfiguration) + let realm = try Realm(configuration: readerConfig.realmConfiguration) highlights = realm.objects(Highlight.self).toArray(Highlight.self) return (highlights ?? []) } catch let error as NSError { @@ -199,8 +248,11 @@ extension Highlight { return [] } } +} - // MARK: HTML Methods +// MARK: - HTML Methods + +extension Highlight { /** Match a highlight on string. @@ -264,7 +316,7 @@ extension Highlight { if let removedId = currentPage.webView.js("removeHighlightById('\(highlightId)')") { return removedId } else { - print("Error removing Higlight from page") + print("Error removing Highlight from page") return nil } } @@ -286,8 +338,7 @@ extension Highlight { let str = (locator as NSString) var newLocator = "" - // TODO_SMF: check this and add match type - matches?.forEach( { match in + matches?.forEach({ (match: NSTextCheckingResult) in newLocator += str.substring(with: match.rangeAt(1)) }) From c6f0e6ea0a0484ee4db026f16596f82735722ea0 Mon Sep 17 00:00:00 2001 From: Kevin Delord Date: Thu, 30 Mar 2017 18:47:03 +0200 Subject: [PATCH 017/110] Refactor HighlightStyle --- Source/Models/Highlight+Helper.swift | 53 ++++++++++++++-------------- 1 file changed, 27 insertions(+), 26 deletions(-) diff --git a/Source/Models/Highlight+Helper.swift b/Source/Models/Highlight+Helper.swift index dbe83eddf..ea0d83e44 100644 --- a/Source/Models/Highlight+Helper.swift +++ b/Source/Models/Highlight+Helper.swift @@ -19,9 +19,10 @@ public enum HighlightStyle: Int { case pink case underline - public init () { self = .yellow } - - // TODO_SMF: replace with a string enum instead. + public init () { + // Default style is `.yellow` + self = .yellow + } /** Return HighlightStyle for CSS class. @@ -41,37 +42,37 @@ public enum HighlightStyle: Int { Return CSS class for HighlightStyle. */ public static func classForStyle(_ style: Int) -> String { - switch style { - case HighlightStyle.yellow.rawValue: return "highlight-yellow" - case HighlightStyle.green.rawValue: return "highlight-green" - case HighlightStyle.blue.rawValue: return "highlight-blue" - case HighlightStyle.pink.rawValue: return "highlight-pink" - case HighlightStyle.underline.rawValue: return "highlight-underline" - default: return "highlight-yellow" + + let enumStyle = (HighlightStyle(rawValue: style) ?? HighlightStyle()) + switch enumStyle { + case .yellow: return "highlight-yellow" + case .green: return "highlight-green" + case .blue: return "highlight-blue" + case .pink: return "highlight-pink" + case .underline: return "highlight-underline" } } - // TODO_SMF: remove default cases, add optional result. + /// Color components for the style + /// + /// - Returns: Tuple of all color compnonents. + private func colorComponents() -> (red: CGFloat, green: CGFloat, blue: CGFloat, alpha: CGFloat) { + switch self { + case .yellow: return (red: 255, green: 235, blue: 107, alpha: 0.9) + case .green: return (red: 192, green: 237, blue: 114, alpha: 0.9) + case .blue: return (red: 173, green: 216, blue: 255, alpha: 0.9) + case .pink: return (red: 255, green: 176, blue: 202, alpha: 0.9) + case .underline: return (red: 240, green: 40, blue: 20, alpha: 0.6) + } + } /** Return CSS class for HighlightStyle. */ public static func colorForStyle(_ style: Int, nightMode: Bool = false) -> UIColor { - - switch style { - case HighlightStyle.yellow.rawValue: - return UIColor(red: 255/255, green: 235/255, blue: 107/255, alpha: nightMode ? 0.9 : 1) - case HighlightStyle.green.rawValue: - return UIColor(red: 192/255, green: 237/255, blue: 114/255, alpha: nightMode ? 0.9 : 1) - case HighlightStyle.blue.rawValue: - return UIColor(red: 173/255, green: 216/255, blue: 255/255, alpha: nightMode ? 0.9 : 1) - case HighlightStyle.pink.rawValue: - return UIColor(red: 255/255, green: 176/255, blue: 202/255, alpha: nightMode ? 0.9 : 1) - case HighlightStyle.underline.rawValue: - return UIColor(red: 240/255, green: 40/255, blue: 20/255, alpha: nightMode ? 0.6 : 1) - default: - return UIColor(red: 255/255, green: 235/255, blue: 107/255, alpha: nightMode ? 0.9 : 1) - } + let enumStyle = (HighlightStyle(rawValue: style) ?? HighlightStyle()) + let colors = enumStyle.colorComponents() + return UIColor(red: colors.red/255, green: colors.green/255, blue: colors.blue/255, alpha: (nightMode ? colors.alpha : 1)) } } From 89528a727b233aea33230a4a557cf6ebcbbf2a6c Mon Sep 17 00:00:00 2001 From: Kevin Delord Date: Thu, 30 Mar 2017 18:51:46 +0200 Subject: [PATCH 018/110] Remove few todos and minor code improvment --- Source/FolioReaderCenter.swift | 2 +- Source/FolioReaderKit.swift | 11 ----------- Source/FolioReaderQuoteShare.swift | 10 +++++----- 3 files changed, 6 insertions(+), 17 deletions(-) diff --git a/Source/FolioReaderCenter.swift b/Source/FolioReaderCenter.swift index 7499ff4b0..6fed0e8ae 100755 --- a/Source/FolioReaderCenter.swift +++ b/Source/FolioReaderCenter.swift @@ -1158,7 +1158,7 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo let quoteShare = FolioReaderQuoteShare(initWithText: string, readerConfig: self.readerConfig, folioReader: self.readerContainer.folioReader) let nav = UINavigationController(rootViewController: quoteShare) - if isPad { + if (UIDevice.current.userInterfaceIdiom == .pad) { nav.modalPresentationStyle = .formSheet } diff --git a/Source/FolioReaderKit.swift b/Source/FolioReaderKit.swift index 81e1c25c7..76356078a 100755 --- a/Source/FolioReaderKit.swift +++ b/Source/FolioReaderKit.swift @@ -9,15 +9,6 @@ import Foundation import UIKit -// TODO_SMF: replace/remove utility function - -// MARK: - Internal constants for devices - -internal let isPad = (UIDevice.current.userInterfaceIdiom == .pad) -internal let isPhone = (UIDevice.current.userInterfaceIdiom == .phone) - -// TODO_SMF: create constant file - // MARK: - Internal constants internal let kApplicationDocumentsDirectory = NSSearchPathForDirectoriesInDomains(.documentDirectory, .userDomainMask, true)[0] @@ -134,7 +125,6 @@ open class FolioReader: NSObject { readerCenter.scrollScrubber?.reloadColors() readerCenter.collectionView.backgroundColor = (self.nightMode == true ? self.readerContainer?.readerConfig.nightModeBackground : UIColor.white) }, completion: { (finished: Bool) in - // TODO_SMF: add constant NotificationCenter.default.post(name: Notification.Name(rawValue: "needRefreshPageMode"), object: nil) }) } @@ -317,7 +307,6 @@ extension FolioReader { } /// Check the current scroll direction - // TODO_SMF: value should use `FolioReaderScrollDirection` instead of `Int`? open class var currentScrollDirection: Int { // TODO_SMF: remove unwrap get { return FolioReader.shared.currentScrollDirection } diff --git a/Source/FolioReaderQuoteShare.swift b/Source/FolioReaderQuoteShare.swift index 260a225fc..502b1ee07 100644 --- a/Source/FolioReaderQuoteShare.swift +++ b/Source/FolioReaderQuoteShare.swift @@ -58,12 +58,12 @@ class FolioReaderQuoteShare: UIViewController { let share = UIBarButtonItem(title: self.readerConfig.localizedShare, style: .plain, target: self, action: #selector(shareQuote(_:))) share.setTitleTextAttributes(titleAttrs, for: UIControlState()) navigationItem.rightBarButtonItem = share - - // - if isPad { + + let isPad = (UIDevice.current.userInterfaceIdiom == .pad) + if (isPad == true) { preferredContentSize = CGSize(width: 400, height: 600) } - let screenBounds = isPad ? preferredContentSize : UIScreen.main.bounds.size + let screenBounds = (isPad == true ? preferredContentSize : UIScreen.main.bounds.size) self.filterImage = UIView(frame: CGRect(x: 0, y: 0, width: screenBounds.width, height: screenBounds.width)) self.filterImage.backgroundColor = self.readerConfig.menuSeparatorColor @@ -172,7 +172,7 @@ class FolioReaderQuoteShare: UIViewController { collectionView.decelerationRate = UIScrollViewDecelerationRateFast view.addSubview(collectionView) - if isPhone { + if (UIDevice.current.userInterfaceIdiom == .phone) { collectionView.autoresizingMask = [.flexibleWidth] } From 3e514d2834d3e08fb635602610f3459290822325 Mon Sep 17 00:00:00 2001 From: Kevin Delord Date: Thu, 30 Mar 2017 19:08:45 +0200 Subject: [PATCH 019/110] remove optional for book and epubPath --- Source/FolioReaderCenter.swift | 30 +++++++-------- Source/FolioReaderContainer.swift | 62 +++++++++++++------------------ Source/FolioReaderKit.swift | 2 +- 3 files changed, 41 insertions(+), 53 deletions(-) diff --git a/Source/FolioReaderCenter.swift b/Source/FolioReaderCenter.swift index 6fed0e8ae..c8f31c1b9 100755 --- a/Source/FolioReaderCenter.swift +++ b/Source/FolioReaderCenter.swift @@ -75,7 +75,7 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo fileprivate var currentWebViewScrollPositions = [Int: CGPoint]() fileprivate var currentOrientation: UIInterfaceOrientation? - fileprivate var book : FRBook? { + fileprivate var book : FRBook { // TODO_SMF: remove optional return self.readerContainer.book } @@ -108,7 +108,7 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo self.pageIndicatorHeight = 0 } - self.totalPages = (self.book?.spine.spineReferences.count ?? 0) + self.totalPages = self.book.spine.spineReferences.count // Loading indicator let style: UIActivityIndicatorViewStyle = self.readerContainer.folioReader.isNight(UIActivityIndicatorViewStyle.white, UIActivityIndicatorViewStyle.gray) @@ -248,7 +248,7 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo rightBarIcons.append(UIBarButtonItem(image: shareIcon, style: .plain, target: self, action:#selector(shareChapter(_:)))) } - if (self.book?.hasAudio() == true || self.readerConfig.enableTTS == true) { + if (self.book.hasAudio() == true || self.readerConfig.enableTTS == true) { rightBarIcons.append(UIBarButtonItem(image: audioIcon, style: .plain, target: self, action:#selector(presentPlayerMenu(_:)))) } @@ -261,7 +261,7 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo func reloadData() { self.loadingView.stopAnimating() - self.totalPages = (self.book?.spine.spineReferences.count ?? 0) + self.totalPages = (self.book.spine.spineReferences.count ?? 0) self.collectionView.reloadData() self.configureNavBarButtons() @@ -423,7 +423,7 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo // Configure the cell guard - let resource = self.book?.spine.spineReferences[(indexPath as NSIndexPath).row].resource, + let resource = self.book.spine.spineReferences[(indexPath as NSIndexPath).row].resource, var html = try? String(contentsOfFile: resource.fullHref, encoding: String.Encoding.utf8) else { return cell } @@ -772,7 +772,7 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo */ func findPageByResource(_ reference: FRTocReference) -> Int { var count = 0 - for item in (self.book?.spine.spineReferences ?? []) { + for item in self.book.spine.spineReferences { if let resource = reference.resource, item.resource == resource { return count } @@ -786,7 +786,7 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo */ func findPageByHref(_ href: String) -> Int { var count = 0 - for item in (self.book?.spine.spineReferences ?? []) { + for item in self.book.spine.spineReferences { if item.resource.href == href { return count } @@ -800,8 +800,8 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo */ func getCurrentChapter() -> FRResource? { if let currentPageNumber = currentPageNumber { - for item in (self.book?.flatTableOfContents ?? []) { - if let reference = self.book?.spine.spineReferences[safe: currentPageNumber-1], let resource = item.resource + for item in self.book.flatTableOfContents { + if let reference = self.book.spine.spineReferences[safe: currentPageNumber-1], let resource = item.resource , resource == reference.resource { return item.resource } @@ -815,9 +815,9 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo */ func getCurrentChapterName() -> String? { if let currentPageNumber = currentPageNumber { - for item in (self.book?.flatTableOfContents ?? []) { + for item in self.book.flatTableOfContents { guard - let reference = self.book?.spine.spineReferences[safe: currentPageNumber-1], + let reference = self.book.spine.spineReferences[safe: currentPageNumber-1], let resource = item.resource else { return nil } @@ -882,7 +882,7 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo // TODO_SMF: refactor similar code in current functions. // Get book title - if let title = self.book?.title() { + if let title = self.book.title() { bookTitle = title subject += " “\(title)”" } @@ -893,7 +893,7 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo } // Get author name - if let author = self.book?.metadata.creators.first { + if let author = self.book.metadata.creators.first { authorName = author.name } @@ -940,7 +940,7 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo var shareItems = [AnyObject]() // Get book title - if let title = self.book?.title() { + if let title = self.book.title() { bookTitle = title subject += " “\(title)”" } @@ -951,7 +951,7 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo } // Get author name - if let author = self.book?.metadata.creators.first { + if let author = self.book.metadata.creators.first { authorName = author.name } diff --git a/Source/FolioReaderContainer.swift b/Source/FolioReaderContainer.swift index f25fbc6aa..023bc3393 100755 --- a/Source/FolioReaderContainer.swift +++ b/Source/FolioReaderContainer.swift @@ -17,30 +17,28 @@ open class FolioReaderContainer : UIViewController { var audioPlayer : FolioReaderAudioPlayer? var shouldHideStatusBar = true var shouldRemoveEpub = true - // TODO_SMF: remove optional for book and epubPath - var epubPath : String? - var book : FRBook? + var epubPath : String + var book : FRBook var readerConfig : FolioReaderConfig var folioReader : FolioReader fileprivate var errorOnLoad = false // MARK: - Init - - /** - Init a Container - - - parameter config: A instance of `FolioReaderConfig` - - parameter path: The ePub path on system - - parameter removeEpub: Should delete the original file after unzip? Default to `true` so the ePub will be unziped only once. - - - returns: `self`, initialized using the `FolioReaderConfig`. - */ + + /// Init a Folio Reader Container + /// + /// - Parameters: + /// - config: Current Folio Reader configuration + /// - folioReader: Current instance of the FolioReader kit. + /// - path: The ePub path on system + /// - removeEpub: Should delete the original file after unzip? Default to `true` so the ePub will be unziped only once. public init(withConfig config: FolioReaderConfig, folioReader: FolioReader, epubPath path: String, removeEpub: Bool = true) { self.readerConfig = config self.folioReader = folioReader self.epubPath = path self.shouldRemoveEpub = removeEpub + self.book = FRBook() super.init(nibName: nil, bundle: Bundle.frameworkBundle()) @@ -51,13 +49,9 @@ open class FolioReaderContainer : UIViewController { // TODO_SMF_QUESTION: is that ok? do 'we' really support NSCoding? fatalError("This class doesn't support NSCoding.") } - - /** - Common Initialization - */ + + /// Common Initialization fileprivate func initialization() { - self.book = FRBook() - // Register custom fonts FontBlaster.blast(bundle: Bundle.frameworkBundle()) @@ -73,14 +67,14 @@ open class FolioReaderContainer : UIViewController { kCurrentScrollDirection: FolioReaderScrollDirection.defaultVertical.rawValue ]) } - - /** - Set the `FolioReaderConfig` and epubPath. - - - parameter config: A instance of `FolioReaderConfig` - - parameter path: The ePub path on system - - parameter removeEpub: Should delete the original file after unzip? Default to `true` so the ePub will be unziped only once. - */ + + /// Set the `FolioReaderConfig` and epubPath. + /// + /// - Parameters: + /// - config: Current Folio Reader configuration + /// - folioReader: Current instance of the FolioReader kit. + /// - path: The ePub path on system + /// - removeEpub: Should delete the original file after unzip? Default to `true` so the ePub will be unziped only once. open func setupConfig(_ config: FolioReaderConfig, folioReader: FolioReader, epubPath path: String, removeEpub: Bool = true) { self.readerConfig = config self.folioReader = folioReader @@ -130,7 +124,7 @@ open class FolioReaderContainer : UIViewController { } // Read async book - guard let epubPath = self.epubPath, (epubPath.isEmpty == false) else { + guard (self.epubPath.isEmpty == false) else { print("Epub path is nil.") self.errorOnLoad = true return @@ -138,7 +132,7 @@ open class FolioReaderContainer : UIViewController { DispatchQueue.global(qos: .userInitiated).async { - guard let parsedBook = FREpubParser().readEpub(epubPath: epubPath, removeEpub: self.shouldRemoveEpub) else { + guard let parsedBook = FREpubParser().readEpub(epubPath: self.epubPath, removeEpub: self.shouldRemoveEpub) else { self.errorOnLoad = true return } @@ -150,19 +144,13 @@ open class FolioReaderContainer : UIViewController { DispatchQueue.main.async(execute: { // Add audio player if needed - if (self.book?.hasAudio() == true || self.readerConfig.enableTTS == true) { + if (self.book.hasAudio() == true || self.readerConfig.enableTTS == true) { self.addAudioPlayer() } self.centerViewController?.reloadData() - self.folioReader.isReaderReady = true - - guard let loadedBook = self.book else { - return - } - - self.folioReader.delegate?.folioReader?(self.folioReader, didFinishedLoading: loadedBook) + self.folioReader.delegate?.folioReader?(self.folioReader, didFinishedLoading: self.book) }) } } diff --git a/Source/FolioReaderKit.swift b/Source/FolioReaderKit.swift index 76356078a..66966d0eb 100755 --- a/Source/FolioReaderKit.swift +++ b/Source/FolioReaderKit.swift @@ -102,7 +102,7 @@ open class FolioReader: NSObject { /// Check if layout needs to change to fit Right To Left var needsRTLChange: Bool { - return (self.readerContainer?.book?.spine.isRtl == true && self.readerContainer?.readerConfig.scrollDirection == .horizontal) + return (self.readerContainer?.book.spine.isRtl == true && self.readerContainer?.readerConfig.scrollDirection == .horizontal) } func isNight(_ f: T, _ l: T) -> T { From 276a370c779725434221c36aded1a73c7a0524bd Mon Sep 17 00:00:00 2001 From: Kevin Delord Date: Thu, 30 Mar 2017 19:21:48 +0200 Subject: [PATCH 020/110] Remove unnecessary optional for FRBook --- Source/FolioReaderAudioPlayer.swift | 32 +++++++++++++++-------------- Source/FolioReaderCenter.swift | 5 ++--- Source/FolioReaderChapterList.swift | 24 ++++++++++------------ Source/FolioReaderPage.swift | 20 ++++++++++-------- Source/FolioReaderQuoteShare.swift | 16 +++++++-------- Source/FolioReaderWebView.swift | 8 ++++---- 6 files changed, 52 insertions(+), 53 deletions(-) diff --git a/Source/FolioReaderAudioPlayer.swift b/Source/FolioReaderAudioPlayer.swift index fcdc2ccfe..7102ed99d 100644 --- a/Source/FolioReaderAudioPlayer.swift +++ b/Source/FolioReaderAudioPlayer.swift @@ -28,21 +28,23 @@ open class FolioReaderAudioPlayer: NSObject { var completionHandler: () -> Void = {} var utteranceRate: Float = 0 - fileprivate var book : FRBook? + fileprivate var book : FRBook // MARK: Init - init(withBook book: FRBook?) { - super.init() + init(withBook book: FRBook) { self.book = book + + super.init() + UIApplication.shared.beginReceivingRemoteControlEvents() // this is needed to the audio can play even when the "silent/vibrate" toggle is on - let session:AVAudioSession = AVAudioSession.sharedInstance() + let session = AVAudioSession.sharedInstance() try? session.setCategory(AVAudioSessionCategoryPlayback) try? session.setActive(true) - updateNowPlayingInfo() + self.updateNowPlayingInfo() } deinit { @@ -156,7 +158,7 @@ open class FolioReaderAudioPlayer: NSObject { } func play() { - if (self.book?.hasAudio() == true) { + if (self.book.hasAudio() == true) { guard let currentPage = FolioReader.shared.readerCenter?.currentPage else { return } currentPage.webView.js("playAudio()") } else { @@ -181,7 +183,7 @@ open class FolioReaderAudioPlayer: NSObject { self.stop() - let smilFile = self.book?.smilFileForHref(href) + let smilFile = self.book.smilFileForHref(href) // if no smil file for this href and the same href is being requested, we've hit the end. stop playing if smilFile == nil && currentHref != nil && href == currentHref { @@ -311,7 +313,7 @@ open class FolioReaderAudioPlayer: NSObject { */ fileprivate func nextAudioFragment() -> FRSmilElement? { - guard let smilFile = self.book?.smilFileForHref(currentHref) else { + guard let smilFile = self.book.smilFileForHref(currentHref) else { return nil } @@ -322,7 +324,7 @@ open class FolioReaderAudioPlayer: NSObject { return smil } - self.currentHref = self.book?.spine.nextChapter(currentHref)?.href + self.currentHref = self.book.spine.nextChapter(currentHref)?.href self.currentFragment = nil self.currentSmilFile = smilFile @@ -346,7 +348,7 @@ open class FolioReaderAudioPlayer: NSObject { let utterance = AVSpeechUtterance(string: text) utterance.rate = utteranceRate - utterance.voice = AVSpeechSynthesisVoice(language: self.book?.metadata.language) + utterance.voice = AVSpeechSynthesisVoice(language: self.book.metadata.language) if synthesizer.isSpeaking { stopSynthesizer() @@ -361,11 +363,11 @@ open class FolioReaderAudioPlayer: NSObject { func speakSentence() { guard let readerCenter = FolioReader.shared.readerCenter, - let playbackActiveClass = self.book?.playbackActiveClass(), let currentPage = readerCenter.currentPage else { return } + let playbackActiveClass = self.book.playbackActiveClass() guard let sentence = currentPage.webView.js("getSentenceWithIndex('\(playbackActiveClass)')") else { if (readerCenter.isLastPage() == true) { self.stop() @@ -438,13 +440,13 @@ open class FolioReaderAudioPlayer: NSObject { var songInfo = [String: AnyObject]() // Get book Artwork - if let coverImage = self.book?.coverImage, let artwork = UIImage(contentsOfFile: coverImage.fullHref) { + if let coverImage = self.book.coverImage, let artwork = UIImage(contentsOfFile: coverImage.fullHref) { let albumArt = MPMediaItemArtwork(image: artwork) songInfo[MPMediaItemPropertyArtwork] = albumArt } // Get book title - if let title = self.book?.title() { + if let title = self.book.title() { songInfo[MPMediaItemPropertyAlbumTitle] = title as AnyObject? } @@ -454,7 +456,7 @@ open class FolioReaderAudioPlayer: NSObject { } // Get author name - if let author = self.book?.metadata.creators.first { + if let author = self.book.metadata.creators.first { songInfo[MPMediaItemPropertyArtist] = author.name as AnyObject? } @@ -484,7 +486,7 @@ open class FolioReaderAudioPlayer: NSObject { currentHref = chapter.href - for item in (self.book?.flatTableOfContents ?? []) { + for item in (self.book.flatTableOfContents ?? []) { if let resource = item.resource , resource.href == currentHref { return item.title } diff --git a/Source/FolioReaderCenter.swift b/Source/FolioReaderCenter.swift index c8f31c1b9..bdd162588 100755 --- a/Source/FolioReaderCenter.swift +++ b/Source/FolioReaderCenter.swift @@ -76,7 +76,6 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo fileprivate var currentOrientation: UIInterfaceOrientation? fileprivate var book : FRBook { - // TODO_SMF: remove optional return self.readerContainer.book } @@ -1095,7 +1094,7 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo func presentChapterList(_ sender: UIBarButtonItem) { FolioReader.saveReaderState() - let chapter = FolioReaderChapterList(folioReader: self.readerContainer.folioReader, readerConfig: self.readerConfig, delegate: self) + let chapter = FolioReaderChapterList(folioReader: self.readerContainer.folioReader, readerConfig: self.readerConfig, book: self.readerContainer.book, delegate: self) let highlight = FolioReaderHighlightList(folioReader: self.readerContainer.folioReader, readerConfig: self.readerConfig) let pageController = PageViewController(folioReader: self.readerContainer.folioReader, readerConfig: self.readerConfig) @@ -1155,7 +1154,7 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo Present Quote Share */ func presentQuoteShare(_ string: String) { - let quoteShare = FolioReaderQuoteShare(initWithText: string, readerConfig: self.readerConfig, folioReader: self.readerContainer.folioReader) + let quoteShare = FolioReaderQuoteShare(initWithText: string, readerConfig: self.readerConfig, folioReader: self.readerContainer.folioReader, book: self.readerContainer.book) let nav = UINavigationController(rootViewController: quoteShare) if (UIDevice.current.userInterfaceIdiom == .pad) { diff --git a/Source/FolioReaderChapterList.swift b/Source/FolioReaderChapterList.swift index d0a23c4e9..aad76cf79 100755 --- a/Source/FolioReaderChapterList.swift +++ b/Source/FolioReaderChapterList.swift @@ -22,21 +22,19 @@ import UIKit func chapterList(didDismissedChapterList chapterList: FolioReaderChapterList) } -class FolioReaderChapterList: UITableViewController { - weak var delegate: FolioReaderChapterListDelegate? - var tocItems = [FRTocReference]() +class FolioReaderChapterList : UITableViewController { - fileprivate var book : FRBook? { - return self.folioReader.readerContainer?.book - } - - fileprivate var readerConfig : FolioReaderConfig - fileprivate var folioReader : FolioReader + weak var delegate : FolioReaderChapterListDelegate? + fileprivate var tocItems = [FRTocReference]() + fileprivate var book : FRBook + fileprivate var readerConfig : FolioReaderConfig + fileprivate var folioReader : FolioReader - init(folioReader: FolioReader, readerConfig: FolioReaderConfig, delegate: FolioReaderChapterListDelegate?) { + init(folioReader: FolioReader, readerConfig: FolioReaderConfig, book: FRBook, delegate: FolioReaderChapterListDelegate?) { self.readerConfig = readerConfig self.folioReader = folioReader self.delegate = delegate + self.book = book super.init(style: UITableViewStyle.plain) } @@ -58,7 +56,7 @@ class FolioReaderChapterList: UITableViewController { self.tableView.estimatedRowHeight = 50 // Create TOC list - self.tocItems = (self.book?.flatTableOfContents ?? []) + self.tocItems = self.book.flatTableOfContents } // MARK: - Table view data source @@ -82,7 +80,7 @@ class FolioReaderChapterList: UITableViewController { // Add audio duration for Media Ovelay if let resource = tocReference.resource { if let mediaOverlay = resource.mediaOverlay { - let duration = self.book?.durationFor("#"+mediaOverlay) + let duration = self.book.durationFor("#"+mediaOverlay) let durationFormatted = (duration != nil ? duration : "")?.clockTimeToMinutesString() cell.indexLabel.text = cell.indexLabel.text! + (duration != nil ? " - "+durationFormatted! : ""); @@ -92,7 +90,7 @@ class FolioReaderChapterList: UITableViewController { // Mark current reading chapter if let currentPageNumber = currentPageNumber, - let reference = self.book?.spine.spineReferences[safe: currentPageNumber - 1], + let reference = self.book.spine.spineReferences[safe: currentPageNumber - 1], (tocReference.resource != nil) { let resource = reference.resource cell.indexLabel.textColor = (tocReference.resource == resource ? self.readerConfig.tintColor : self.readerConfig.menuTextColor) diff --git a/Source/FolioReaderPage.swift b/Source/FolioReaderPage.swift index 05b431f5a..28564f239 100755 --- a/Source/FolioReaderPage.swift +++ b/Source/FolioReaderPage.swift @@ -41,17 +41,19 @@ open class FolioReaderPage: UICollectionViewCell, UIWebViewDelegate, UIGestureRe fileprivate var menuIsVisible = false fileprivate var readerConfig: FolioReaderConfig - fileprivate var book: FRBook? + fileprivate var book: FRBook // MARK: - View life cicle public override init(frame: CGRect) { - // Init reader config with a default one. Later the current one must be configured through the setup function. + // Init explicit attributes with a default value. The `setup` function MUST be called to configure the current object with valid attributes. self.readerConfig = FolioReaderConfig() + self.book = FRBook() + super.init(frame: frame) } - public func setup(withReaderConfig readerConfig: FolioReaderConfig, book: FRBook?) { + public func setup(withReaderConfig readerConfig: FolioReaderConfig, book: FRBook) { self.readerConfig = readerConfig self.book = book @@ -169,7 +171,7 @@ open class FolioReaderPage: UICollectionViewCell, UIWebViewDelegate, UIGestureRe refreshPageMode() - if (self.readerConfig.enableTTS == true && self.book?.hasAudio() == false) { + if (self.readerConfig.enableTTS == true && self.book.hasAudio() == false) { webView.js("wrappingSentencesWithinPTags()") if let audioPlayer = FolioReader.shared.readerAudioPlayer , audioPlayer.isPlaying() { @@ -227,7 +229,7 @@ open class FolioReaderPage: UICollectionViewCell, UIWebViewDelegate, UIGestureRe // Handle internal url if ((url.path as NSString).pathExtension != "") { - var base = (self.book?.opfResource.href as? NSString)?.deletingLastPathComponent + var base = (self.book.opfResource.href as? NSString)?.deletingLastPathComponent base = ((base == nil || base?.isEmpty == true) ? kBookId : base) let path = url.path @@ -454,11 +456,11 @@ open class FolioReaderPage: UICollectionViewCell, UIWebViewDelegate, UIGestureRe - parameter identifier: The identifier */ func audioMarkID(_ identifier: String) { - guard - let playbackActiveClass = self.book?.playbackActiveClass(), - let currentPage = FolioReader.shared.readerCenter?.currentPage else { - return + guard let currentPage = FolioReader.shared.readerCenter?.currentPage else { + return } + + let playbackActiveClass = self.book.playbackActiveClass() currentPage.webView.js("audioMarkID('\(playbackActiveClass)','\(identifier)')") } diff --git a/Source/FolioReaderQuoteShare.swift b/Source/FolioReaderQuoteShare.swift index 502b1ee07..13fe0c2c2 100644 --- a/Source/FolioReaderQuoteShare.swift +++ b/Source/FolioReaderQuoteShare.swift @@ -23,19 +23,17 @@ class FolioReaderQuoteShare: UIViewController { let imagePicker = UIImagePickerController() var selectedIndex = 0 - fileprivate var book: FRBook? { - return self.folioReader.readerContainer?.book - } - + fileprivate var book : FRBook fileprivate var folioReader : FolioReader fileprivate var readerConfig : FolioReaderConfig // MARK: Init - init(initWithText shareText: String, readerConfig: FolioReaderConfig, folioReader: FolioReader) { + init(initWithText shareText: String, readerConfig: FolioReaderConfig, folioReader: FolioReader, book: FRBook) { self.folioReader = folioReader self.readerConfig = readerConfig self.quoteText = shareText.stripLineBreaks().stripHtml() + self.book = book super.init(nibName: nil, bundle: Bundle.frameworkBundle()) } @@ -88,11 +86,11 @@ class FolioReaderQuoteShare: UIViewController { var bookTitle = "" var authorName = "" - if let title = self.book?.title() { + if let title = self.book.title() { bookTitle = title } - if let author = self.book?.metadata.creators.first { + if let author = self.book.metadata.creators.first { authorName = author.name } @@ -263,13 +261,13 @@ class FolioReaderQuoteShare: UIViewController { var shareItems = [AnyObject]() // Get book title - if let title = self.book?.title() { + if let title = self.book.title() { bookTitle = title subject += " “\(title)”" } // Get author name - if let author = self.book?.metadata.creators.first { + if let author = self.book.metadata.creators.first { authorName = author.name } diff --git a/Source/FolioReaderWebView.swift b/Source/FolioReaderWebView.swift index e469928a2..ced9239ff 100644 --- a/Source/FolioReaderWebView.swift +++ b/Source/FolioReaderWebView.swift @@ -14,14 +14,14 @@ open class FolioReaderWebView : UIWebView { var isShare = false var isOneWord = false - fileprivate var book : FRBook? + fileprivate var book : FRBook fileprivate var readerConfig : FolioReaderConfig override init(frame: CGRect) { fatalError("use init(frame:readerConfig:book:) instead.") } - init(frame: CGRect, readerConfig: FolioReaderConfig, book: FRBook?) { + init(frame: CGRect, readerConfig: FolioReaderConfig, book: FRBook) { self.readerConfig = readerConfig self.book = book @@ -46,7 +46,7 @@ open class FolioReaderWebView : UIWebView { } else { if action == #selector(highlight(_:)) || (action == #selector(define(_:)) && isOneWord) - || (action == #selector(play(_:)) && (self.book?.hasAudio() == true || self.readerConfig.enableTTS == true)) + || (action == #selector(play(_:)) && (self.book.hasAudio() == true || self.readerConfig.enableTTS == true)) || (action == #selector(share(_:)) && self.readerConfig.allowSharing == true) || (action == #selector(copy(_:)) && self.readerConfig.allowSharing == true) { return true @@ -256,7 +256,7 @@ open class FolioReaderWebView : UIWebView { // default menu menuItems = [highlightItem, defineItem, shareItem] - if (self.book?.hasAudio() == true || self.readerConfig.enableTTS == true) { + if (self.book.hasAudio() == true || self.readerConfig.enableTTS == true) { menuItems.insert(playAudioItem, at: 0) } From 23f1188b73d61ef267ec05001e9c30778712e584 Mon Sep 17 00:00:00 2001 From: Kevin Delord Date: Thu, 30 Mar 2017 19:27:58 +0200 Subject: [PATCH 021/110] Update todos --- Source/FolioReaderAudioPlayer.swift | 1 + Source/FolioReaderCenter.swift | 2 +- Source/FolioReaderKit.swift | 50 ++++++++++------------------ Source/Models/Highlight+Helper.swift | 14 ++++---- 4 files changed, 26 insertions(+), 41 deletions(-) diff --git a/Source/FolioReaderAudioPlayer.swift b/Source/FolioReaderAudioPlayer.swift index 7102ed99d..53ca65fdf 100644 --- a/Source/FolioReaderAudioPlayer.swift +++ b/Source/FolioReaderAudioPlayer.swift @@ -361,6 +361,7 @@ open class FolioReaderAudioPlayer: NSObject { // MARK: TTS Sentence func speakSentence() { + // TODO_SMF_CHECK: does it work fine? guard let readerCenter = FolioReader.shared.readerCenter, let currentPage = readerCenter.currentPage else { diff --git a/Source/FolioReaderCenter.swift b/Source/FolioReaderCenter.swift index bdd162588..9be6d48ec 100755 --- a/Source/FolioReaderCenter.swift +++ b/Source/FolioReaderCenter.swift @@ -824,7 +824,7 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo guard (resource == reference.resource), let title = item.title else { - // TODO_SMF: check if this really works fine (or if it was working anyway). + // TODO_SMF_CHECK: check if this really works fine (or if it was working anyway). // Select text -> share. return nil } diff --git a/Source/FolioReaderKit.swift b/Source/FolioReaderKit.swift index 66966d0eb..030f0aa10 100755 --- a/Source/FolioReaderKit.swift +++ b/Source/FolioReaderKit.swift @@ -62,7 +62,7 @@ enum MediaOverlayStyle: Int { */ @objc optional func folioReaderDidClosed(_ folioReader: FolioReader) - // TODO_SMF: make sure the following deprecated functions still work... or not.: + // TODO_SMF_CHECK: make sure the following deprecated functions still work... or not.: // TODO_SMF_QUESTION: ask the main developer(s) for that. // TODO_SMF_DOC: new function signature change @objc optional func folioReaderDidClosed() @@ -118,7 +118,7 @@ open class FolioReader: NSObject { if let readerCenter = self.readerCenter { UIView.animate(withDuration: 0.6, animations: { - // TODO_SMF: infinite loop? + // TODO_SMF_CHECK: infinite loop? _ = readerCenter.currentPage?.webView.js("nightMode(\(self.nightMode))") readerCenter.pageIndicatorView?.reloadColors() readerCenter.configureNavBar() @@ -183,7 +183,6 @@ open class FolioReader: NSObject { } /// Check the current scroll direction - // TODO_SMF: value should use `FolioReaderScrollDirection` instead of `Int`? open var currentScrollDirection: Int { // TODO_SMF: remove unwrap get { return FolioReader.defaults.value(forKey: kCurrentScrollDirection) as! Int } @@ -284,43 +283,30 @@ extension FolioReader { /// Check if current theme is Night mode open class var nightMode: Bool { get { return FolioReader.shared.nightMode } - set (value) { - FolioReader.shared.nightMode = value - } + set { FolioReader.shared.nightMode = newValue } } /// Check current font name open class var currentFont: FolioReaderFont { get { return FolioReader.shared.currentFont } - set (font) { - FolioReader.shared.currentFont = font - } + set { FolioReader.shared.currentFont = newValue } } /// Check current font size open class var currentFontSize: FolioReaderFontSize { - // TODO_SMF: remove unwrap get { return FolioReader.shared.currentFontSize } - set (value) { - FolioReader.shared.currentFontSize = value - } + set { FolioReader.shared.currentFontSize = newValue } } /// Check the current scroll direction open class var currentScrollDirection: Int { - // TODO_SMF: remove unwrap get { return FolioReader.shared.currentScrollDirection } - set (value) { - FolioReader.shared.currentScrollDirection = value - } + set { FolioReader.shared.currentScrollDirection = newValue } } open class var currentAudioRate: Int { - // TODO_SMF: remove unwrap get { return FolioReader.shared.currentAudioRate } - set (value) { - FolioReader.shared.currentAudioRate = value - } + set { FolioReader.shared.currentAudioRate = newValue } } /// Check if reader is open and ready @@ -345,9 +331,7 @@ extension FolioReader { /// Check the current highlight style open class var currentHighlightStyle: Int { get { return FolioReader.shared.currentHighlightStyle } - set (value) { - FolioReader.shared.currentHighlightStyle = value - } + set { FolioReader.shared.currentHighlightStyle = newValue } } /// Check if layout needs to change to fit Right To Left @@ -360,7 +344,7 @@ extension FolioReader { extension FolioReader { - // TODO_SMF: deprecate and find a replacement for those functions. + // TODO_SMF_DEPRECATE and find a replacement for those functions. /** Called when the application will resign active @@ -422,7 +406,7 @@ func isDirection (_ vertical: T, _ horizontal: T, _ horizontalContentVertical extension UICollectionViewScrollDirection { static func direction() -> UICollectionViewScrollDirection { - // TODO_SMF: deprecate + // TODO_SMF_DEPRECATE guard let readerConfig = FolioReader.shared.readerContainer?.readerConfig else { return .vertical } @@ -438,7 +422,7 @@ extension UICollectionViewScrollDirection { extension UICollectionViewScrollPosition { static func direction() -> UICollectionViewScrollPosition { - // TODO_SMF: deprecate + // TODO_SMF_DEPRECATE guard let readerConfig = FolioReader.shared.readerContainer?.readerConfig else { return .top } @@ -453,7 +437,7 @@ extension UICollectionViewScrollPosition { extension CGPoint { func forDirection() -> CGFloat { - // TODO_SMF: deprecate + // TODO_SMF_DEPRECATE guard let readerConfig = FolioReader.shared.readerContainer?.readerConfig else { return self.y } @@ -468,7 +452,7 @@ extension CGPoint { extension CGSize { func forDirection() -> CGFloat { - // TODO_SMF: deprecate + // TODO_SMF_DEPRECATE guard let readerConfig = FolioReader.shared.readerContainer?.readerConfig else { return self.height } @@ -480,7 +464,7 @@ extension CGSize { } func forReverseDirection() -> CGFloat { - // TODO_SMF: deprecate + // TODO_SMF_DEPRECATE guard let readerConfig = FolioReader.shared.readerContainer?.readerConfig else { return self.width } @@ -495,7 +479,7 @@ extension CGSize { extension CGRect { func forDirection() -> CGFloat { - // TODO_SMF: deprecate + // TODO_SMF_DEPRECATE guard let readerConfig = FolioReader.shared.readerContainer?.readerConfig else { return self.height } @@ -510,7 +494,7 @@ extension CGRect { extension ScrollDirection { static func negative() -> ScrollDirection { - // TODO_SMF: deprecate + // TODO_SMF_DEPRECATE guard let readerConfig = FolioReader.shared.readerContainer?.readerConfig else { return self.down } @@ -523,7 +507,7 @@ extension ScrollDirection { } static func positive() -> ScrollDirection { - // TODO_SMF: deprecate + // TODO_SMF_DEPRECATE guard let readerConfig = FolioReader.shared.readerContainer?.readerConfig else { return self.up } diff --git a/Source/Models/Highlight+Helper.swift b/Source/Models/Highlight+Helper.swift index ea0d83e44..e3401bd80 100644 --- a/Source/Models/Highlight+Helper.swift +++ b/Source/Models/Highlight+Helper.swift @@ -82,7 +82,7 @@ public typealias Completion = (_ error: NSError?) -> () extension Highlight { private static var readerConfig : FolioReaderConfig { - // TODO_SMF: deprecate + // TODO_SMF_DEPRECATE return FolioReader.shared.readerContainer!.readerConfig } @@ -90,7 +90,7 @@ extension Highlight { /// /// - Parameter completion: Completion block public func persist(_ completion: Completion? = nil) { - // TODO_SMF: deprecate + // TODO_SMF_DEPRECATE self.persist(withConfiguration: Highlight.readerConfig, completion: completion) } @@ -114,7 +114,7 @@ extension Highlight { /// Remove a Highlight public func remove() { - // TODO_SMF: deprecate + // TODO_SMF_DEPRECATE self.remove(withConfiguration: Highlight.readerConfig) } @@ -136,7 +136,7 @@ extension Highlight { /// /// - Parameter highlightId: The ID to be removed public static func removeById(_ highlightId: String) { - // TODO_SMF: deprecate + // TODO_SMF_DEPRECATE Highlight.removeById(withConfiguration: Highlight.readerConfig, highlightId: highlightId) } @@ -164,7 +164,7 @@ extension Highlight { /// - highlightId: The ID to be removed /// - type: The `HighlightStyle` public static func updateById(_ highlightId: String, type: HighlightStyle) { - // TODO_SMF: deprecate + // TODO_SMF_DEPRECATE: deprecate Highlight.updateById(withConfiguration: Highlight.readerConfig, highlightId: highlightId, type: type) } @@ -198,7 +198,7 @@ extension Highlight { /// - page: Page number /// - Returns: Return a list of Highlights public static func allByBookId(_ bookId: String, andPage page: NSNumber? = nil) -> [Highlight] { - // TODO_SMF: deprecate + // TODO_SMF_DEPRECATE return Highlight.allByBookId(withConfiguration: Highlight.readerConfig, bookId: bookId, andPage: page) } @@ -230,7 +230,7 @@ extension Highlight { /// /// - Returns: Return all Highlights public static func all() -> [Highlight] { - // TODO_SMF: deprecate + // TODO_SMF_DEPRECATE return Highlight.all(withConfiguration: Highlight.readerConfig) } From 8e995c2a9e2dc39805a69d192b01ee6a0d362751 Mon Sep 17 00:00:00 2001 From: Kevin Delord Date: Thu, 30 Mar 2017 19:51:09 +0200 Subject: [PATCH 022/110] PR: add doc and TODOs --- Source/EPUBCore/FREpubParser.swift | 26 ++++++++------- Source/FolioReaderAudioPlayer.swift | 1 + Source/FolioReaderCenter.swift | 14 ++++---- Source/FolioReaderFontsMenu.swift | 1 + Source/FolioReaderHighlightList.swift | 3 +- Source/FolioReaderKit.swift | 47 +++++++-------------------- Source/FolioReaderPage.swift | 2 ++ Source/FolioReaderPlayerMenu.swift | 1 + Source/FolioReaderWebView.swift | 1 + Source/Models/Highlight+Helper.swift | 1 + 10 files changed, 42 insertions(+), 55 deletions(-) diff --git a/Source/EPUBCore/FREpubParser.swift b/Source/EPUBCore/FREpubParser.swift index 5363fed46..fe43bd28f 100755 --- a/Source/EPUBCore/FREpubParser.swift +++ b/Source/EPUBCore/FREpubParser.swift @@ -14,19 +14,23 @@ import ZipArchive #endif import AEXML -class FREpubParser: NSObject, SSZipArchiveDelegate { - let book = FRBook() - var bookBasePath: String! - var resourcesBasePath: String! - var shouldRemoveEpub = true +class FREpubParser : NSObject, SSZipArchiveDelegate { + + let book = FRBook() + var bookBasePath : String! + var resourcesBasePath : String! + var shouldRemoveEpub = true + fileprivate var epubPathToRemove: String? - - /** - Parse the Cover Image from an epub file. - Returns an UIImage. - */ - // TODO_SMF_DOC: new function signature change + + /// Parse the Cover Image from an epub file. + /// + /// - Parameters: + /// - epubPath: Epub path on the disk + /// - unzipPath: Path to unzip the compressed epub. + /// - Returns: An UIImage object func parseCoverImage(_ epubPath: String, unzipPath: String? = nil) -> UIImage? { + // TODO_SMF_DOC: new function signature change guard let book = readEpub(epubPath: epubPath, removeEpub: false, unzipPath: unzipPath), let coverImage = book.coverImage else { diff --git a/Source/FolioReaderAudioPlayer.swift b/Source/FolioReaderAudioPlayer.swift index 53ca65fdf..5234665d4 100644 --- a/Source/FolioReaderAudioPlayer.swift +++ b/Source/FolioReaderAudioPlayer.swift @@ -231,6 +231,7 @@ open class FolioReaderAudioPlayer: NSObject { func playNextChapter() { stopPlayerTimer() // Wait for "currentPage" to update, then request to play audio + // TODO_SMF: remove call to FolioReader.shared.readerCenter FolioReader.shared.readerCenter?.changePageToNext { if self.isPlaying() { self.play() diff --git a/Source/FolioReaderCenter.swift b/Source/FolioReaderCenter.swift index 9be6d48ec..b15db38b0 100755 --- a/Source/FolioReaderCenter.swift +++ b/Source/FolioReaderCenter.swift @@ -279,7 +279,7 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo // MARK: Change page progressive direction func setCollectionViewProgressiveDirection() { - if FolioReader.needsRTLChange { + if (FolioReader.needsRTLChange == true) { collectionView.transform = CGAffineTransform(scaleX: -1, y: 1) } else { collectionView.transform = CGAffineTransform.identity @@ -287,7 +287,7 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo } func setPageProgressiveDirection(_ page: FolioReaderPage) { - if FolioReader.needsRTLChange { + if (FolioReader.needsRTLChange == true) { // if page.transform.a == -1 { return } page.transform = CGAffineTransform(scaleX: -1, y: 1) } else { @@ -295,7 +295,6 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo } } - // MARK: Change layout orientation func setScrollDirection(_ direction: FolioReaderScrollDirection) { @@ -357,9 +356,8 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo } func showBars() { - configureNavBar() - - let shouldHide = + self.configureNavBar() + self.readerContainer.shouldHideStatusBar = false UIView.animate(withDuration: 0.25, animations: { @@ -1011,7 +1009,7 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo // Update current reading page if scrollView is UICollectionView { - // Do nothing? + // TODO_SMF: refactor? } else { if let page = currentPage, let pageSize = self.readerConfig.isDirection(pageHeight, pageWidth) { @@ -1027,7 +1025,7 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo // if the cell reload don't save the top position offset if let oldOffSet = self.currentWebViewScrollPositions[currentIndexPathRow], (abs(oldOffSet.y - scrollView.contentOffset.y) > 100) { - // DO nothing? + // TODO_SMF: refactor? } else { self.currentWebViewScrollPositions[currentIndexPathRow] = scrollView.contentOffset } diff --git a/Source/FolioReaderFontsMenu.swift b/Source/FolioReaderFontsMenu.swift index 44ebd2760..afbe25445 100644 --- a/Source/FolioReaderFontsMenu.swift +++ b/Source/FolioReaderFontsMenu.swift @@ -264,6 +264,7 @@ class FolioReaderFontsMenu : UIViewController, SMSegmentViewDelegate, UIGestur // MARK: - SMSegmentView delegate func segmentView(_ segmentView: SMSegmentView, didSelectSegmentAtIndex index: Int) { + // TODO_SMF: remove call to FolioReader.shared.readerCenter guard (FolioReader.shared.readerCenter?.currentPage) != nil else { return } if segmentView.tag == 1 { diff --git a/Source/FolioReaderHighlightList.swift b/Source/FolioReaderHighlightList.swift index 676cba59e..b85134193 100644 --- a/Source/FolioReaderHighlightList.swift +++ b/Source/FolioReaderHighlightList.swift @@ -138,8 +138,9 @@ class FolioReaderHighlightList : UITableViewController { override func tableView(_ tableView: UITableView, didSelectRowAt indexPath: IndexPath) { let highlight = highlights[(indexPath as NSIndexPath).row] + // TODO_SMF: remove call to FolioReader.shared.readerCenter FolioReader.shared.readerCenter?.changePageWith(page: highlight.page, andFragment: highlight.highlightId) - dismiss() + self.dismiss() } override func tableView(_ tableView: UITableView, commit editingStyle: UITableViewCellEditingStyle, forRowAt indexPath: IndexPath) { diff --git a/Source/FolioReaderKit.swift b/Source/FolioReaderKit.swift index 030f0aa10..b36919627 100755 --- a/Source/FolioReaderKit.swift +++ b/Source/FolioReaderKit.swift @@ -272,12 +272,8 @@ extension FolioReader { // TODO_SMF: temporal variable to build and run the current state. Should be completely remove. private static var _sharedInstance = FolioReader() open static var shared : FolioReader { - get { - return _sharedInstance - } - set { - _sharedInstance = newValue - } + get { return _sharedInstance } + set { _sharedInstance = newValue } } /// Check if current theme is Night mode @@ -304,6 +300,7 @@ extension FolioReader { set { FolioReader.shared.currentScrollDirection = newValue } } + /// Check current audio rate, the speed of speech voice open class var currentAudioRate: Int { get { return FolioReader.shared.currentAudioRate } set { FolioReader.shared.currentAudioRate = newValue } @@ -314,16 +311,12 @@ extension FolioReader { return FolioReader.shared.isReaderReady } - /** - Save Reader state, book, page and scroll are saved - */ + /// Save Reader state, book, page and scroll are saved open class func saveReaderState() { FolioReader.shared.saveReaderState() } - /** - Closes and save the reader current instance - */ + /// Closes and save the reader current instance open class func close() { FolioReader.shared.close() } @@ -364,36 +357,19 @@ extension FolioReader { // MARK: - Global Functions func isNight (_ f: T, _ l: T) -> T { - fatalError("should not use that function.") - // TODO_SMF: remove that function + // TODO_SMF: remove fatal error + // TODO_SMF_DEPRECATE // TODO_SMF_DOC: notify change + fatalError("should not use that function.") return (FolioReader.shared.nightMode == true ? f : l) } // MARK: - Scroll Direction Functions -/** - Simplify attibution of values based on direction, basically is to avoid too much usage of `switch`, - `if` and `else` statements to check. So basically this is like a shorthand version of the `switch` verification. - - For example: - ``` - let pageOffsetPoint = readerConfig.isDirection(CGPoint(x: 0, y: pageOffset), CGPoint(x: pageOffset, y: 0), CGPoint(x: 0, y: pageOffset)) - ``` - - As usually the `vertical` direction and `horizontalContentVertical` has similar statements you can basically hide the last - value and it will assume the value from `vertical` as fallback. - ``` - let pageOffsetPoint = readerConfig.isDirection(CGPoint(x: 0, y: pageOffset), CGPoint(x: pageOffset, y: 0)) - ``` - - - parameter vertical: Value for `vertical` direction - - parameter horizontal: Value for `horizontal` direction - - parameter horizontalContentVertical: Value for `horizontalWithVerticalContent` direction, if nil will fallback to `vertical` value - - - returns: The right value based on direction. - */ func isDirection (_ vertical: T, _ horizontal: T, _ horizontalContentVertical: T? = nil) -> T { + // TODO_SMF_DEPRECATE + // TODO_SMF: remove fatal error + // TODO_SMF_DOC: notify change fatalError("should not use that function.") let direction = (FolioReader.shared.readerContainer!.readerConfig.scrollDirection) switch direction { @@ -782,6 +758,7 @@ internal extension UIImage { - returns: Returns a colored image */ func ignoreSystemTint() -> UIImage { + // TODO_SMF: replace shared readerContainer return self.imageTintColor(FolioReader.shared.readerContainer!.readerConfig.tintColor).withRenderingMode(.alwaysOriginal) } diff --git a/Source/FolioReaderPage.swift b/Source/FolioReaderPage.swift index 28564f239..cebbab9d3 100755 --- a/Source/FolioReaderPage.swift +++ b/Source/FolioReaderPage.swift @@ -271,6 +271,7 @@ open class FolioReaderPage: UICollectionViewCell, UIWebViewDelegate, UIGestureRe if #available(iOS 9.0, *) { let safariVC = SFSafariViewController(url: request.url!) safariVC.view.tintColor = self.readerConfig.tintColor + // TODO_SMF: remove call to FolioReader.shared.readerCenter FolioReader.shared.readerCenter?.present(safariVC, animated: true, completion: nil) } else { let webViewController = WebViewController(url: request.url!) @@ -456,6 +457,7 @@ open class FolioReaderPage: UICollectionViewCell, UIWebViewDelegate, UIGestureRe - parameter identifier: The identifier */ func audioMarkID(_ identifier: String) { + // TODO_SMF: replace shared readerContainer guard let currentPage = FolioReader.shared.readerCenter?.currentPage else { return } diff --git a/Source/FolioReaderPlayerMenu.swift b/Source/FolioReaderPlayerMenu.swift index 4ee45b1bc..c666c8fae 100644 --- a/Source/FolioReaderPlayerMenu.swift +++ b/Source/FolioReaderPlayerMenu.swift @@ -266,6 +266,7 @@ class FolioReaderPlayerMenu : UIViewController, SMSegmentViewDelegate, UIGestu } // update the current page style + // TODO_SMF: remove call to FolioReader.shared.readerCenter if let currentPage = FolioReader.shared.readerCenter?.currentPage { currentPage.webView.js("setMediaOverlayStyle(\"\(FolioReader.currentMediaOverlayStyle.className())\")") } diff --git a/Source/FolioReaderWebView.swift b/Source/FolioReaderWebView.swift index ced9239ff..31fba7209 100644 --- a/Source/FolioReaderWebView.swift +++ b/Source/FolioReaderWebView.swift @@ -67,6 +67,7 @@ open class FolioReaderWebView : UIWebView { } } else { if let textToShare = self.js("getSelectedText()") { + // TODO_SMF: remove call to FolioReader.shared.readerCenter FolioReader.shared.readerCenter?.presentQuoteShare(textToShare) self.clearTextSelection() diff --git a/Source/Models/Highlight+Helper.swift b/Source/Models/Highlight+Helper.swift index e3401bd80..8afa18abd 100644 --- a/Source/Models/Highlight+Helper.swift +++ b/Source/Models/Highlight+Helper.swift @@ -312,6 +312,7 @@ extension Highlight { - returns: The removed id */ @discardableResult public static func removeFromHTMLById(_ highlightId: String) -> String? { + // TODO_SMF: remove call to FolioReader.shared.readerCenter guard let currentPage = FolioReader.shared.readerCenter?.currentPage else { return nil } if let removedId = currentPage.webView.js("removeHighlightById('\(highlightId)')") { From db0ed102e2a9d612c3c1ef383fe058af71787ed3 Mon Sep 17 00:00:00 2001 From: Kevin Delord Date: Thu, 30 Mar 2017 20:39:59 +0200 Subject: [PATCH 023/110] ignoreSystemTint: remove shared readerContainer and many optional unwrapping --- Source/FolioReaderCenter.swift | 2 +- Source/FolioReaderChapterListCell.swift | 1 + Source/FolioReaderFontsMenu.swift | 20 +++--- Source/FolioReaderKit.swift | 86 ++++++++++++++++--------- Source/FolioReaderPage.swift | 18 +++--- Source/FolioReaderPlayerMenu.swift | 12 ++-- Source/FolioReaderQuoteShare.swift | 24 +++---- Source/FolioReaderWebView.swift | 19 ++++-- Source/ScrollScrubber.swift | 2 +- 9 files changed, 108 insertions(+), 76 deletions(-) diff --git a/Source/FolioReaderCenter.swift b/Source/FolioReaderCenter.swift index b15db38b0..ebb6cb1b9 100755 --- a/Source/FolioReaderCenter.swift +++ b/Source/FolioReaderCenter.swift @@ -408,7 +408,7 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo private func configure(readerPageCell cell: FolioReaderPage, atIndexPath indexPath: IndexPath) -> FolioReaderPage { - cell.setup(withReaderConfig: self.readerConfig, book: self.book) + cell.setup(withReaderConfig: self.readerConfig, readerContainer: self.readerContainer) cell.pageNumber = (indexPath as NSIndexPath).row+1 cell.webView.scrollView.delegate = self cell.webView.setupScrollDirection() diff --git a/Source/FolioReaderChapterListCell.swift b/Source/FolioReaderChapterListCell.swift index 87afceedb..d623ef662 100755 --- a/Source/FolioReaderChapterListCell.swift +++ b/Source/FolioReaderChapterListCell.swift @@ -18,6 +18,7 @@ class FolioReaderChapterListCell: UITableViewCell { indexLabel.numberOfLines = 0 indexLabel.translatesAutoresizingMaskIntoConstraints = false indexLabel.font = UIFont(name: "Avenir-Light", size: 17) + // TODO_SMF: replace shared readerContainer indexLabel.textColor = FolioReader.shared.readerContainer?.readerConfig.menuTextColor contentView.addSubview(indexLabel) diff --git a/Source/FolioReaderFontsMenu.swift b/Source/FolioReaderFontsMenu.swift index afbe25445..b9901f59c 100644 --- a/Source/FolioReaderFontsMenu.swift +++ b/Source/FolioReaderFontsMenu.swift @@ -118,13 +118,13 @@ class FolioReaderFontsMenu : UIViewController, SMSegmentViewDelegate, UIGestur let fontSmall = UIImage(readerImageNamed: "icon-font-small") let fontBig = UIImage(readerImageNamed: "icon-font-big") - let sunNormal = sun!.imageTintColor(normalColor).withRenderingMode(.alwaysOriginal) - let moonNormal = moon!.imageTintColor(normalColor).withRenderingMode(.alwaysOriginal) - let fontSmallNormal = fontSmall!.imageTintColor(normalColor).withRenderingMode(.alwaysOriginal) - let fontBigNormal = fontBig!.imageTintColor(normalColor).withRenderingMode(.alwaysOriginal) + let sunNormal = sun?.imageTintColor(normalColor)?.withRenderingMode(.alwaysOriginal) + let moonNormal = moon?.imageTintColor(normalColor)?.withRenderingMode(.alwaysOriginal) + let fontSmallNormal = fontSmall?.imageTintColor(normalColor)?.withRenderingMode(.alwaysOriginal) + let fontBigNormal = fontBig?.imageTintColor(normalColor)?.withRenderingMode(.alwaysOriginal) - let sunSelected = sun!.imageTintColor(selectedColor).withRenderingMode(.alwaysOriginal) - let moonSelected = moon!.imageTintColor(selectedColor).withRenderingMode(.alwaysOriginal) + let sunSelected = sun?.imageTintColor(selectedColor)?.withRenderingMode(.alwaysOriginal) + let moonSelected = moon?.imageTintColor(selectedColor)?.withRenderingMode(.alwaysOriginal) // Day night mode let dayNight = SMSegmentView(frame: CGRect(x: 0, y: 0, width: view.frame.width, height: 55), @@ -229,10 +229,10 @@ class FolioReaderFontsMenu : UIViewController, SMSegmentViewDelegate, UIGestur let vertical = UIImage(readerImageNamed: "icon-menu-vertical") let horizontal = UIImage(readerImageNamed: "icon-menu-horizontal") - let verticalNormal = vertical!.imageTintColor(normalColor).withRenderingMode(.alwaysOriginal) - let horizontalNormal = horizontal!.imageTintColor(normalColor).withRenderingMode(.alwaysOriginal) - let verticalSelected = vertical!.imageTintColor(selectedColor).withRenderingMode(.alwaysOriginal) - let horizontalSelected = horizontal!.imageTintColor(selectedColor).withRenderingMode(.alwaysOriginal) + let verticalNormal = vertical?.imageTintColor(normalColor)?.withRenderingMode(.alwaysOriginal) + let horizontalNormal = horizontal?.imageTintColor(normalColor)?.withRenderingMode(.alwaysOriginal) + let verticalSelected = vertical?.imageTintColor(selectedColor)?.withRenderingMode(.alwaysOriginal) + let horizontalSelected = horizontal?.imageTintColor(selectedColor)?.withRenderingMode(.alwaysOriginal) // Layout direction let layoutDirection = SMSegmentView(frame: CGRect(x: 0, y: line3.frame.origin.y, width: view.frame.width, height: 55), diff --git a/Source/FolioReaderKit.swift b/Source/FolioReaderKit.swift index b36919627..bc8ab284e 100755 --- a/Source/FolioReaderKit.swift +++ b/Source/FolioReaderKit.swift @@ -25,13 +25,11 @@ internal let kHighlightRange = 30 // TODO_SMF: remove kBookId internal var kBookId: String! -/** - Defines the media overlay and TTS selection - - - Default: The background is colored - - Underline: The underlined is colored - - TextColor: The text is colored - */ +/// Defines the media overlay and TTS selection +/// +/// - `default`: The background is colored +/// - underline: The underlined is colored +/// - textColor: The text is colored enum MediaOverlayStyle: Int { case `default` case underline @@ -73,9 +71,6 @@ enum MediaOverlayStyle: Int { */ open class FolioReader: NSObject { - /// Singleton instance - fileprivate override init() {} - /// Custom unzip path open var unzipPath : String? @@ -391,6 +386,7 @@ extension UICollectionViewScrollDirection { } static func direction(withConfiguration readerConfig: FolioReaderConfig) -> UICollectionViewScrollDirection { + // TODO_SMF_DOC return readerConfig.isDirection(.vertical, .horizontal, .horizontal) } } @@ -407,11 +403,13 @@ extension UICollectionViewScrollPosition { } static func direction(withConfiguration readerConfig: FolioReaderConfig) -> UICollectionViewScrollPosition { + // TODO_SMF_DOC return readerConfig.isDirection(.top, .left, .left) } } extension CGPoint { + func forDirection() -> CGFloat { // TODO_SMF_DEPRECATE guard let readerConfig = FolioReader.shared.readerContainer?.readerConfig else { @@ -422,11 +420,13 @@ extension CGPoint { } func forDirection(withConfiguration readerConfig: FolioReaderConfig) -> CGFloat { + // TODO_SMF_DOC return readerConfig.isDirection(self.y, self.x, self.y) } } extension CGSize { + func forDirection() -> CGFloat { // TODO_SMF_DEPRECATE guard let readerConfig = FolioReader.shared.readerContainer?.readerConfig else { @@ -436,6 +436,7 @@ extension CGSize { } func forDirection(withConfiguration readerConfig: FolioReaderConfig) -> CGFloat { + // TODO_SMF_DOC return readerConfig.isDirection(height, width, height) } @@ -449,11 +450,13 @@ extension CGSize { } func forReverseDirection(withConfiguration readerConfig: FolioReaderConfig) -> CGFloat { + // TODO_SMF_DOC return readerConfig.isDirection(width, height, width) } } extension CGRect { + func forDirection() -> CGFloat { // TODO_SMF_DEPRECATE guard let readerConfig = FolioReader.shared.readerContainer?.readerConfig else { @@ -464,11 +467,13 @@ extension CGRect { } func forDirection(withConfiguration readerConfig: FolioReaderConfig) -> CGFloat { + // TODO_SMF_DOC return readerConfig.isDirection(height, width, height) } } extension ScrollDirection { + static func negative() -> ScrollDirection { // TODO_SMF_DEPRECATE guard let readerConfig = FolioReader.shared.readerContainer?.readerConfig else { @@ -479,6 +484,7 @@ extension ScrollDirection { } static func negative(withConfiguration readerConfig: FolioReaderConfig) -> ScrollDirection { + // TODO_SMF_DOC return readerConfig.isDirection(.down, .right, .right) } @@ -492,6 +498,7 @@ extension ScrollDirection { } static func positive(withConfiguration readerConfig: FolioReaderConfig) -> ScrollDirection { + // TODO_SMF_DOC return readerConfig.isDirection(.up, .left, .left) } } @@ -748,42 +755,57 @@ internal extension String { // TODO_SMF: split files into extension files internal extension UIImage { - convenience init?(readerImageNamed: String) { + + convenience init?(readerImageNamed: String) { self.init(named: readerImageNamed, in: Bundle.frameworkBundle(), compatibleWith: nil) } - - /** - Forces the image to be colored with Reader Config tintColor - - - returns: Returns a colored image - */ - func ignoreSystemTint() -> UIImage { - // TODO_SMF: replace shared readerContainer - return self.imageTintColor(FolioReader.shared.readerContainer!.readerConfig.tintColor).withRenderingMode(.alwaysOriginal) + + /// Forces the image to be colored with Reader Config tintColor + /// + /// - Returns: Returns a colored image + func ignoreSystemTint() -> UIImage? { + // TODO_SMF_DEPRECATE + guard let readerConfig = FolioReader.shared.readerContainer?.readerConfig else { + return nil + } + + return self.ignoreSystemTint(withConfiguration: readerConfig) + } + + /// Forces the image to be colored with Reader Config tintColor + /// + /// - Parameter readerConfig: Current folio reader configuration. + /// - Returns: Returns a colored image + func ignoreSystemTint(withConfiguration readerConfig: FolioReaderConfig) -> UIImage? { + // TODO_SMF_DOC + return self.imageTintColor(readerConfig.tintColor)?.withRenderingMode(.alwaysOriginal) } - + /** Colorize the image with a color - parameter tintColor: The input color - returns: Returns a colored image */ - func imageTintColor(_ tintColor: UIColor) -> UIImage { + func imageTintColor(_ tintColor: UIColor) -> UIImage? { UIGraphicsBeginImageContextWithOptions(self.size, false, self.scale) - let context = UIGraphicsGetCurrentContext()! as CGContext - context.translateBy(x: 0, y: self.size.height) - context.scaleBy(x: 1.0, y: -1.0) - context.setBlendMode(CGBlendMode.normal) - + let context = UIGraphicsGetCurrentContext() + context?.translateBy(x: 0, y: self.size.height) + context?.scaleBy(x: 1.0, y: -1.0) + context?.setBlendMode(CGBlendMode.normal) + let rect = CGRect(x: 0, y: 0, width: self.size.width, height: self.size.height) as CGRect - context.clip(to: rect, mask: self.cgImage!) + if let cgImage = self.cgImage { + context?.clip(to: rect, mask: cgImage) + } + tintColor.setFill() - context.fill(rect) - - let newImage = UIGraphicsGetImageFromCurrentImageContext()! as UIImage + context?.fill(rect) + + let newImage = UIGraphicsGetImageFromCurrentImageContext() UIGraphicsEndImageContext() - + return newImage } diff --git a/Source/FolioReaderPage.swift b/Source/FolioReaderPage.swift index cebbab9d3..ee1cf1934 100755 --- a/Source/FolioReaderPage.swift +++ b/Source/FolioReaderPage.swift @@ -40,30 +40,32 @@ open class FolioReaderPage: UICollectionViewCell, UIWebViewDelegate, UIGestureRe fileprivate var shouldShowBar = true fileprivate var menuIsVisible = false - fileprivate var readerConfig: FolioReaderConfig - fileprivate var book: FRBook + fileprivate var readerConfig : FolioReaderConfig + fileprivate var readerContainer : FolioReaderContainer + fileprivate var book : FRBook { + return self.readerContainer.book + } // MARK: - View life cicle public override init(frame: CGRect) { // Init explicit attributes with a default value. The `setup` function MUST be called to configure the current object with valid attributes. self.readerConfig = FolioReaderConfig() - self.book = FRBook() + self.readerContainer = FolioReaderContainer(withConfig: self.readerConfig, folioReader: FolioReader(), epubPath: "") super.init(frame: frame) } - public func setup(withReaderConfig readerConfig: FolioReaderConfig, book: FRBook) { + public func setup(withReaderConfig readerConfig: FolioReaderConfig, readerContainer: FolioReaderContainer) { self.readerConfig = readerConfig - self.book = book + self.readerContainer = readerContainer self.backgroundColor = UIColor.clear - - // TODO: Put the notification name in a Constants file + NotificationCenter.default.addObserver(self, selector: #selector(refreshPageMode), name: NSNotification.Name(rawValue: "needRefreshPageMode"), object: nil) if webView == nil { - webView = FolioReaderWebView(frame: webViewFrame(), readerConfig: self.readerConfig, book: self.book) + webView = FolioReaderWebView(frame: webViewFrame(), readerConfig: self.readerConfig, readerContainer: self.readerContainer) webView.autoresizingMask = [.flexibleWidth, .flexibleHeight] webView.dataDetectorTypes = .link webView.scrollView.showsVerticalScrollIndicator = false diff --git a/Source/FolioReaderPlayerMenu.swift b/Source/FolioReaderPlayerMenu.swift index c666c8fae..68fd00e21 100644 --- a/Source/FolioReaderPlayerMenu.swift +++ b/Source/FolioReaderPlayerMenu.swift @@ -68,13 +68,13 @@ class FolioReaderPlayerMenu : UIViewController, SMSegmentViewDelegate, UIGestu let pause = UIImage(readerImageNamed: "pause-icon") let prev = UIImage(readerImageNamed: "prev-icon") let next = UIImage(readerImageNamed: "next-icon") - let playSelected = play!.imageTintColor(selectedColor).withRenderingMode(.alwaysOriginal) - let pauseSelected = pause!.imageTintColor(selectedColor).withRenderingMode(.alwaysOriginal) + let playSelected = play?.imageTintColor(selectedColor)?.withRenderingMode(.alwaysOriginal) + let pauseSelected = pause?.imageTintColor(selectedColor)?.withRenderingMode(.alwaysOriginal) - let prevNormal = prev!.imageTintColor(normalColor).withRenderingMode(.alwaysOriginal) - let nextNormal = next!.imageTintColor(normalColor).withRenderingMode(.alwaysOriginal) - let prevSelected = prev!.imageTintColor(selectedColor).withRenderingMode(.alwaysOriginal) - let nextSelected = next!.imageTintColor(selectedColor).withRenderingMode(.alwaysOriginal) + let prevNormal = prev?.imageTintColor(normalColor)?.withRenderingMode(.alwaysOriginal) + let nextNormal = next?.imageTintColor(normalColor)?.withRenderingMode(.alwaysOriginal) + let prevSelected = prev?.imageTintColor(selectedColor)?.withRenderingMode(.alwaysOriginal) + let nextSelected = next?.imageTintColor(selectedColor)?.withRenderingMode(.alwaysOriginal) // prev button let prevBtn = UIButton(frame: CGRect(x: gutterX + padX, y: 0, width: size, height: size)) diff --git a/Source/FolioReaderQuoteShare.swift b/Source/FolioReaderQuoteShare.swift index 13fe0c2c2..48b9ac170 100644 --- a/Source/FolioReaderQuoteShare.swift +++ b/Source/FolioReaderQuoteShare.swift @@ -332,23 +332,25 @@ extension FolioReaderQuoteShare: UICollectionViewDataSource { imageView.tag = tag cell.contentView.addSubview(imageView) } - - // Image color - let normalColor = UIColor(white: 0.5, alpha: 0.7) - let camera = UIImage(readerImageNamed: "icon-camera") - let dash = UIImage(readerImageNamed: "border-dashed-pattern") - let cameraNormal = camera!.imageTintColor(normalColor) - let dashNormal = dash!.imageTintColor(normalColor) - + // Camera - guard (indexPath as NSIndexPath).row > 0 else { + guard ((indexPath as NSIndexPath).row > 0) else { + + // Image color + let normalColor = UIColor(white: 0.5, alpha: 0.7) + let camera = UIImage(readerImageNamed: "icon-camera") + let dash = UIImage(readerImageNamed: "border-dashed-pattern") + let cameraNormal = camera?.imageTintColor(normalColor) + imageView.contentMode = .center imageView.image = cameraNormal - cell.contentView.layer.borderColor = UIColor(patternImage: dashNormal).cgColor + if let dashNormal = dash?.imageTintColor(normalColor) { + cell.contentView.layer.borderColor = UIColor(patternImage: dashNormal).cgColor + } return cell } - if selectedIndex == (indexPath as NSIndexPath).row { + if (selectedIndex == (indexPath as NSIndexPath).row) { cell.contentView.layer.borderColor = self.readerConfig.tintColor.cgColor cell.contentView.layer.borderWidth = 3 } else { diff --git a/Source/FolioReaderWebView.swift b/Source/FolioReaderWebView.swift index 31fba7209..1354c09dd 100644 --- a/Source/FolioReaderWebView.swift +++ b/Source/FolioReaderWebView.swift @@ -14,16 +14,19 @@ open class FolioReaderWebView : UIWebView { var isShare = false var isOneWord = false - fileprivate var book : FRBook fileprivate var readerConfig : FolioReaderConfig + fileprivate var readerContainer : FolioReaderContainer + fileprivate var book : FRBook { + return self.readerContainer.book + } override init(frame: CGRect) { fatalError("use init(frame:readerConfig:book:) instead.") } - init(frame: CGRect, readerConfig: FolioReaderConfig, book: FRBook) { + init(frame: CGRect, readerConfig: FolioReaderConfig, readerContainer: FolioReaderContainer) { self.readerConfig = readerConfig - self.book = book + self.readerContainer = readerContainer super.init(frame: frame) } @@ -148,15 +151,17 @@ open class FolioReaderWebView : UIWebView { } func define(_ sender: UIMenuController?) { - let selectedText = js("getSelectedText()") - self.setMenuVisible(false) + guard let selectedText = js("getSelectedText()") else { + return + } + self.setMenuVisible(false) self.clearTextSelection() - let vc = UIReferenceLibraryViewController(term: selectedText! ) + let vc = UIReferenceLibraryViewController(term: selectedText) vc.view.tintColor = self.readerConfig.tintColor - FolioReader.shared.readerContainer?.show(vc, sender: nil) + self.readerContainer.show(vc, sender: nil) } func play(_ sender: UIMenuController?) { diff --git a/Source/ScrollScrubber.swift b/Source/ScrollScrubber.swift index 510143f54..6f1c7897b 100644 --- a/Source/ScrollScrubber.swift +++ b/Source/ScrollScrubber.swift @@ -76,7 +76,7 @@ class ScrollScrubber: NSObject, UIScrollViewDelegate { // less obtrusive knob and fixes jump: http://stackoverflow.com/a/22301039/484780 let thumbImg = UIImage(readerImageNamed: "knob") - let thumbImgColor = thumbImg!.imageTintColor(self.readerContainer.readerConfig.tintColor).withRenderingMode(.alwaysOriginal) + let thumbImgColor = thumbImg?.imageTintColor(self.readerContainer.readerConfig.tintColor)?.withRenderingMode(.alwaysOriginal) slider.setThumbImage(thumbImgColor, for: UIControlState()) slider.setThumbImage(thumbImgColor, for: .selected) slider.setThumbImage(thumbImgColor, for: .highlighted) From 5d875479080a79b643e27426dc0241b9c6f6ac83 Mon Sep 17 00:00:00 2001 From: Kevin Delord Date: Thu, 30 Mar 2017 20:57:54 +0200 Subject: [PATCH 024/110] Reafactor FolioReaderChapterListCell --- Source/FolioReaderChapterList.swift | 13 ++-- Source/FolioReaderChapterListCell.swift | 80 +++++++++++++++---------- 2 files changed, 56 insertions(+), 37 deletions(-) diff --git a/Source/FolioReaderChapterList.swift b/Source/FolioReaderChapterList.swift index aad76cf79..6893ff88c 100755 --- a/Source/FolioReaderChapterList.swift +++ b/Source/FolioReaderChapterList.swift @@ -71,19 +71,22 @@ class FolioReaderChapterList : UITableViewController { override func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell { let cell = tableView.dequeueReusableCell(withIdentifier: reuseIdentifier, for: indexPath) as! FolioReaderChapterListCell - + + cell.setup(withConfiguration: self.readerConfig) let tocReference = tocItems[(indexPath as NSIndexPath).row] let isSection = tocReference.children.count > 0 - cell.indexLabel.text = tocReference.title.trimmingCharacters(in: .whitespacesAndNewlines) + cell.indexLabel?.text = tocReference.title.trimmingCharacters(in: .whitespacesAndNewlines) // Add audio duration for Media Ovelay if let resource = tocReference.resource { if let mediaOverlay = resource.mediaOverlay { let duration = self.book.durationFor("#"+mediaOverlay) - let durationFormatted = (duration != nil ? duration : "")?.clockTimeToMinutesString() - cell.indexLabel.text = cell.indexLabel.text! + (duration != nil ? " - "+durationFormatted! : ""); + if let durationFormatted = (duration != nil ? duration : "")?.clockTimeToMinutesString() { + let text = (cell.indexLabel?.text ?? "") + cell.indexLabel?.text = text + (duration != nil ? (" - " + durationFormatted) : "") + } } } @@ -93,7 +96,7 @@ class FolioReaderChapterList : UITableViewController { let reference = self.book.spine.spineReferences[safe: currentPageNumber - 1], (tocReference.resource != nil) { let resource = reference.resource - cell.indexLabel.textColor = (tocReference.resource == resource ? self.readerConfig.tintColor : self.readerConfig.menuTextColor) + cell.indexLabel?.textColor = (tocReference.resource == resource ? self.readerConfig.tintColor : self.readerConfig.menuTextColor) } cell.layoutMargins = UIEdgeInsets.zero diff --git a/Source/FolioReaderChapterListCell.swift b/Source/FolioReaderChapterListCell.swift index d623ef662..c6834d454 100755 --- a/Source/FolioReaderChapterListCell.swift +++ b/Source/FolioReaderChapterListCell.swift @@ -8,36 +8,52 @@ import UIKit -class FolioReaderChapterListCell: UITableViewCell { - var indexLabel = UILabel() - - override init(style: UITableViewCellStyle, reuseIdentifier: String?) { - super.init(style: style, reuseIdentifier: reuseIdentifier) - - indexLabel.lineBreakMode = .byWordWrapping - indexLabel.numberOfLines = 0 - indexLabel.translatesAutoresizingMaskIntoConstraints = false - indexLabel.font = UIFont(name: "Avenir-Light", size: 17) - // TODO_SMF: replace shared readerContainer - indexLabel.textColor = FolioReader.shared.readerContainer?.readerConfig.menuTextColor - contentView.addSubview(indexLabel) - - // Configure cell contraints - var constraints = [NSLayoutConstraint]() - let views = ["label": self.indexLabel] - - NSLayoutConstraint.constraints(withVisualFormat: "H:|-15-[label]-15-|", options: [], metrics: nil, views: views).forEach { - constraints.append($0 as NSLayoutConstraint) - } - - NSLayoutConstraint.constraints(withVisualFormat: "V:|-16-[label]-16-|", options: [], metrics: nil, views: views).forEach { - constraints.append($0 as NSLayoutConstraint) - } - - contentView.addConstraints(constraints) - } - - required init?(coder aDecoder: NSCoder) { - fatalError("storyboards are incompatible with truth and beauty") - } +class FolioReaderChapterListCell : UITableViewCell { + + var indexLabel : UILabel? + + override init(style: UITableViewCellStyle, reuseIdentifier: String?) { + super.init(style: style, reuseIdentifier: reuseIdentifier) + + self.indexLabel = UILabel() + } + + func setup(withConfiguration readerConfig: FolioReaderConfig) { + + self.indexLabel?.lineBreakMode = .byWordWrapping + self.indexLabel?.numberOfLines = 0 + self.indexLabel?.translatesAutoresizingMaskIntoConstraints = false + self.indexLabel?.font = UIFont(name: "Avenir-Light", size: 17) + self.indexLabel?.textColor = readerConfig.menuTextColor + + if let label = self.indexLabel { + contentView.addSubview(label) + + // TODO_SMF_CHECK + // Configure cell contraints + var constraints = [NSLayoutConstraint]() + let views = ["label": label] + + NSLayoutConstraint.constraints(withVisualFormat: "H:|-15-[label]-15-|", options: [], metrics: nil, views: views).forEach { + constraints.append($0 as NSLayoutConstraint) + } + + NSLayoutConstraint.constraints(withVisualFormat: "V:|-16-[label]-16-|", options: [], metrics: nil, views: views).forEach { + constraints.append($0 as NSLayoutConstraint) + } + + contentView.addConstraints(constraints) + } + } + + required init?(coder aDecoder: NSCoder) { + fatalError("storyboards are incompatible with truth and beauty") + } + + override func prepareForReuse() { + super.prepareForReuse() + + // As the `setup` is called at each reuse, make sure the label is added only once to the view hierarchy. + self.indexLabel?.removeFromSuperview() + } } From c9275669f7fba9405dff95d91757049604029381 Mon Sep 17 00:00:00 2001 From: Kevin Delord Date: Thu, 30 Mar 2017 20:59:45 +0200 Subject: [PATCH 025/110] Remove todo --- Source/FolioReaderChapterListCell.swift | 5 ++--- 1 file changed, 2 insertions(+), 3 deletions(-) diff --git a/Source/FolioReaderChapterListCell.swift b/Source/FolioReaderChapterListCell.swift index c6834d454..5be26bfcb 100755 --- a/Source/FolioReaderChapterListCell.swift +++ b/Source/FolioReaderChapterListCell.swift @@ -27,9 +27,8 @@ class FolioReaderChapterListCell : UITableViewCell { self.indexLabel?.textColor = readerConfig.menuTextColor if let label = self.indexLabel { - contentView.addSubview(label) + self.contentView.addSubview(label) - // TODO_SMF_CHECK // Configure cell contraints var constraints = [NSLayoutConstraint]() let views = ["label": label] @@ -42,7 +41,7 @@ class FolioReaderChapterListCell : UITableViewCell { constraints.append($0 as NSLayoutConstraint) } - contentView.addConstraints(constraints) + self.contentView.addConstraints(constraints) } } From 44cd61283ab178de7fcc887806dee6024b670a22 Mon Sep 17 00:00:00 2001 From: Kevin Delord Date: Thu, 30 Mar 2017 21:35:57 +0200 Subject: [PATCH 026/110] Carthage; Update gitignore --- .gitignore | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/.gitignore b/.gitignore index 63004da4f..0b8810f0e 100644 --- a/.gitignore +++ b/.gitignore @@ -53,8 +53,7 @@ Example/Pods/ # Carthage # # Add this line if you want to avoid checking in source code from Carthage dependencies. -# Carthage/Checkouts - +Carthage/Checkouts Carthage/Build # fastlane From b5fdb3f224f2aa98b1649d340cf9f1a0ff03c49d Mon Sep 17 00:00:00 2001 From: Kevin Delord Date: Thu, 30 Mar 2017 22:29:39 +0200 Subject: [PATCH 027/110] FolioReader: convert convenience init to internal --- Source/FolioReaderKit.swift | 3 +++ 1 file changed, 3 insertions(+) diff --git a/Source/FolioReaderKit.swift b/Source/FolioReaderKit.swift index bc8ab284e..2c3181f0a 100755 --- a/Source/FolioReaderKit.swift +++ b/Source/FolioReaderKit.swift @@ -71,6 +71,9 @@ enum MediaOverlayStyle: Int { */ open class FolioReader: NSObject { + /// Internal init function to disable the creation of `FolioReader` objects outside the current scope. + internal override init() { } + /// Custom unzip path open var unzipPath : String? From 5bc3bb3087840a5265bf1dffa858dd356e224caa Mon Sep 17 00:00:00 2001 From: Kevin Delord Date: Thu, 30 Mar 2017 23:12:09 +0200 Subject: [PATCH 028/110] Highlight: create extension with all static deprecated functions inside --- Source/Models/Highlight+Helper.swift | 117 ++++++++++++++------------- 1 file changed, 61 insertions(+), 56 deletions(-) diff --git a/Source/Models/Highlight+Helper.swift b/Source/Models/Highlight+Helper.swift index 8afa18abd..2eb53fd4b 100644 --- a/Source/Models/Highlight+Helper.swift +++ b/Source/Models/Highlight+Helper.swift @@ -81,19 +81,6 @@ public typealias Completion = (_ error: NSError?) -> () extension Highlight { - private static var readerConfig : FolioReaderConfig { - // TODO_SMF_DEPRECATE - return FolioReader.shared.readerContainer!.readerConfig - } - - /// Save a Highlight with completion block - /// - /// - Parameter completion: Completion block - public func persist(_ completion: Completion? = nil) { - // TODO_SMF_DEPRECATE - self.persist(withConfiguration: Highlight.readerConfig, completion: completion) - } - /// Save a Highlight with completion block /// /// - Parameters: @@ -112,12 +99,6 @@ extension Highlight { } } - /// Remove a Highlight - public func remove() { - // TODO_SMF_DEPRECATE - self.remove(withConfiguration: Highlight.readerConfig) - } - /// Remove a Highlight /// /// - Parameter readerConfig: Current folio reader configuration. @@ -132,14 +113,6 @@ extension Highlight { } } - /// Remove a Highlight by ID - /// - /// - Parameter highlightId: The ID to be removed - public static func removeById(_ highlightId: String) { - // TODO_SMF_DEPRECATE - Highlight.removeById(withConfiguration: Highlight.readerConfig, highlightId: highlightId) - } - /// Remove a Highlight by ID /// /// - Parameters: @@ -158,16 +131,6 @@ extension Highlight { } } - /// Update a Highlight by ID - /// - /// - Parameters: - /// - highlightId: The ID to be removed - /// - type: The `HighlightStyle` - public static func updateById(_ highlightId: String, type: HighlightStyle) { - // TODO_SMF_DEPRECATE: deprecate - Highlight.updateById(withConfiguration: Highlight.readerConfig, highlightId: highlightId, type: type) - } - /// Update a Highlight by ID /// /// - Parameters: @@ -191,17 +154,6 @@ extension Highlight { } - /// Return a list of Highlights with a given ID - /// - /// - Parameters: - /// - bookId: Book ID - /// - page: Page number - /// - Returns: Return a list of Highlights - public static func allByBookId(_ bookId: String, andPage page: NSNumber? = nil) -> [Highlight] { - // TODO_SMF_DEPRECATE - return Highlight.allByBookId(withConfiguration: Highlight.readerConfig, bookId: bookId, andPage: page) - } - /// Return a list of Highlights with a given ID /// /// - Parameters: @@ -226,14 +178,6 @@ extension Highlight { } } - /// Return all Highlights - /// - /// - Returns: Return all Highlights - public static func all() -> [Highlight] { - // TODO_SMF_DEPRECATE - return Highlight.all(withConfiguration: Highlight.readerConfig) - } - /// Return all Highlights /// /// - Parameter readerConfig: - readerConfig: Current folio reader configuration. @@ -251,6 +195,67 @@ extension Highlight { } } +// MARK: - Static functions + +extension Highlight { + + private static var readerConfig : FolioReaderConfig { + // TODO_SMF_DEPRECATE + return FolioReader.shared.readerContainer!.readerConfig + } + + /// Save a Highlight with completion block + /// + /// - Parameter completion: Completion block + public func persist(_ completion: Completion? = nil) { + // TODO_SMF_DEPRECATE + self.persist(withConfiguration: Highlight.readerConfig, completion: completion) + } + + /// Return all Highlights + /// + /// - Returns: Return all Highlights + public static func all() -> [Highlight] { + // TODO_SMF_DEPRECATE + return Highlight.all(withConfiguration: Highlight.readerConfig) + } + + /// Return a list of Highlights with a given ID + /// + /// - Parameters: + /// - bookId: Book ID + /// - page: Page number + /// - Returns: Return a list of Highlights + public static func allByBookId(_ bookId: String, andPage page: NSNumber? = nil) -> [Highlight] { + // TODO_SMF_DEPRECATE + return Highlight.allByBookId(withConfiguration: Highlight.readerConfig, bookId: bookId, andPage: page) + } + + /// Update a Highlight by ID + /// + /// - Parameters: + /// - highlightId: The ID to be removed + /// - type: The `HighlightStyle` + public static func updateById(_ highlightId: String, type: HighlightStyle) { + // TODO_SMF_DEPRECATE: deprecate + Highlight.updateById(withConfiguration: Highlight.readerConfig, highlightId: highlightId, type: type) + } + + /// Remove a Highlight by ID + /// + /// - Parameter highlightId: The ID to be removed + public static func removeById(_ highlightId: String) { + // TODO_SMF_DEPRECATE + Highlight.removeById(withConfiguration: Highlight.readerConfig, highlightId: highlightId) + } + + /// Remove a Highlight + public func remove() { + // TODO_SMF_DEPRECATE + self.remove(withConfiguration: Highlight.readerConfig) + } +} + // MARK: - HTML Methods extension Highlight { From 2e3f4b848cd565f2cb70e659ee04d92e8c4621f6 Mon Sep 17 00:00:00 2001 From: Kevin Delord Date: Thu, 30 Mar 2017 23:32:24 +0200 Subject: [PATCH 029/110] Remove kBookId global variable --- Source/EPUBCore/FRBook.swift | 1 + Source/EPUBCore/FREpubParser.swift | 6 +++--- Source/FolioReaderCenter.swift | 23 ++++++++++++--------- Source/FolioReaderHighlightList.swift | 9 +++++++-- Source/FolioReaderKit.swift | 29 ++++++++++++++------------- Source/FolioReaderPage.swift | 19 ++++++++++++------ Source/FolioReaderWebView.swift | 3 ++- Source/Models/Highlight+Helper.swift | 4 ++-- 8 files changed, 57 insertions(+), 37 deletions(-) diff --git a/Source/EPUBCore/FRBook.swift b/Source/EPUBCore/FRBook.swift index 11c5df740..9d2e911ac 100755 --- a/Source/EPUBCore/FRBook.swift +++ b/Source/EPUBCore/FRBook.swift @@ -21,6 +21,7 @@ open class FRBook: NSObject { var coverImage: FRResource? var version: Double? var uniqueIdentifier: String? + var name: String? func hasAudio() -> Bool { return smils.smils.count > 0 ? true : false diff --git a/Source/EPUBCore/FREpubParser.swift b/Source/EPUBCore/FREpubParser.swift index fe43bd28f..1efc74f6c 100755 --- a/Source/EPUBCore/FREpubParser.swift +++ b/Source/EPUBCore/FREpubParser.swift @@ -93,11 +93,11 @@ class FREpubParser : NSObject, SSZipArchiveDelegate { // Skip from backup this folder addSkipBackupAttributeToItemAtURL(URL(fileURLWithPath: bookBasePath, isDirectory: true)) - - kBookId = bookName + + self.book.name = bookName readContainer() readOpf() - return book + return self.book } /** diff --git a/Source/FolioReaderCenter.swift b/Source/FolioReaderCenter.swift index ebb6cb1b9..481c1df06 100755 --- a/Source/FolioReaderCenter.swift +++ b/Source/FolioReaderCenter.swift @@ -266,14 +266,17 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo self.configureNavBarButtons() self.setCollectionViewProgressiveDirection() - if let position = FolioReader.defaults.value(forKey: kBookId) as? NSDictionary, - let pageNumber = position["pageNumber"] as? Int , pageNumber > 0 { - self.changePageWith(page: pageNumber) - currentPageNumber = pageNumber - return - } - - currentPageNumber = 1 + guard + let bookId = self.book.name, + let position = FolioReader.defaults.value(forKey: bookId) as? NSDictionary, + let pageNumber = position["pageNumber"] as? Int, + (pageNumber > 0) else { + currentPageNumber = 1 + return + } + + self.changePageWith(page: pageNumber) + currentPageNumber = pageNumber } // MARK: Change page progressive direction @@ -1169,7 +1172,9 @@ extension FolioReaderCenter: FolioReaderPageDelegate { public func pageDidLoad(_ page: FolioReaderPage) { - if let position = FolioReader.defaults.value(forKey: kBookId) as? NSDictionary { + if + let bookId = self.book.name, + let position = FolioReader.defaults.value(forKey: bookId) as? NSDictionary { let pageNumber = position["pageNumber"]! as! Int let offset = self.readerConfig.isDirection(position["pageOffsetY"], position["pageOffsetX"]) as? CGFloat let pageOffset = offset diff --git a/Source/FolioReaderHighlightList.swift b/Source/FolioReaderHighlightList.swift index b85134193..0fb8bd201 100644 --- a/Source/FolioReaderHighlightList.swift +++ b/Source/FolioReaderHighlightList.swift @@ -32,8 +32,13 @@ class FolioReaderHighlightList : UITableViewController { self.tableView.separatorInset = UIEdgeInsets.zero self.tableView.backgroundColor = self.folioReader.isNight(self.readerConfig.nightModeMenuBackground, self.readerConfig.menuBackgroundColor) self.tableView.separatorColor = self.folioReader.isNight(self.readerConfig.nightModeSeparatorColor, self.readerConfig.menuSeparatorColor) - - self.highlights = Highlight.allByBookId(withConfiguration: self.readerConfig, bookId: (kBookId as NSString).deletingPathExtension) + + guard let bookId = (self.folioReader.readerContainer?.book.name as? NSString)?.deletingPathExtension else { + self.highlights = [] + return + } + + self.highlights = Highlight.allByBookId(withConfiguration: self.readerConfig, bookId: bookId) } // MARK: - Table view data source diff --git a/Source/FolioReaderKit.swift b/Source/FolioReaderKit.swift index 2c3181f0a..2d2c0003c 100755 --- a/Source/FolioReaderKit.swift +++ b/Source/FolioReaderKit.swift @@ -22,9 +22,6 @@ internal let kNightMode = "com.folioreader.kNightMode" internal let kCurrentTOCMenu = "com.folioreader.kCurrentTOCMenu" internal let kHighlightRange = 30 -// TODO_SMF: remove kBookId -internal var kBookId: String! - /// Defines the media overlay and TTS selection /// /// - `default`: The background is colored @@ -238,17 +235,21 @@ extension FolioReader { open func saveReaderState() { guard self.isReaderOpen else { return } - if let currentPage = self.readerCenter?.currentPage { - let position = [ - "pageNumber": currentPageNumber, - "pageOffsetX": currentPage.webView.scrollView.contentOffset.x, - "pageOffsetY": currentPage.webView.scrollView.contentOffset.y - ] as [String : Any] - - FolioReader.defaults.set(position, forKey: kBookId) - } - } - + guard + let bookId = self.readerContainer?.book.name, + let currentPage = self.readerCenter?.currentPage else { + return + } + + let position = [ + "pageNumber": currentPageNumber, + "pageOffsetX": currentPage.webView.scrollView.contentOffset.x, + "pageOffsetY": currentPage.webView.scrollView.contentOffset.y + ] as [String : Any] + + FolioReader.defaults.set(position, forKey: bookId) + } + /** Closes and save the reader current instance */ diff --git a/Source/FolioReaderPage.swift b/Source/FolioReaderPage.swift index ee1cf1934..c587f7973 100755 --- a/Source/FolioReaderPage.swift +++ b/Source/FolioReaderPage.swift @@ -136,9 +136,13 @@ open class FolioReaderPage: UICollectionViewCell, UIWebViewDelegate, UIGestureRe fileprivate func htmlContentWithInsertHighlights(_ htmlContent: String) -> String { var tempHtmlContent = htmlContent as NSString // Restore highlights - let highlights = Highlight.allByBookId(withConfiguration: self.readerConfig, bookId: (kBookId as NSString).deletingPathExtension, andPage: pageNumber as NSNumber?) + guard let bookId = (self.book.name as? NSString)?.deletingPathExtension else { + return tempHtmlContent as String + } + + let highlights = Highlight.allByBookId(withConfiguration: self.readerConfig, bookId: bookId, andPage: pageNumber as NSNumber?) - if highlights.count > 0 { + if (highlights.count > 0) { for item in highlights { let style = HighlightStyle.classForStyle(item.type) let tag = "\(item.content!)" @@ -231,14 +235,17 @@ open class FolioReaderPage: UICollectionViewCell, UIWebViewDelegate, UIGestureRe // Handle internal url if ((url.path as NSString).pathExtension != "") { - var base = (self.book.opfResource.href as? NSString)?.deletingLastPathComponent - base = ((base == nil || base?.isEmpty == true) ? kBookId : base) + + var pathComponent = (self.book.opfResource.href as? NSString)?.deletingLastPathComponent + guard let base = ((pathComponent == nil || pathComponent?.isEmpty == true) ? self.book.name : pathComponent) else { + return true + } let path = url.path - let splitedPath = path.components(separatedBy: (base ?? kBookId)) + let splitedPath = path.components(separatedBy: base) // Return to avoid crash - if splitedPath.count <= 1 || splitedPath[1].isEmpty { + if (splitedPath.count <= 1 || splitedPath[1].isEmpty) { return true } diff --git a/Source/FolioReaderWebView.swift b/Source/FolioReaderWebView.swift index 1354c09dd..1d802c8e2 100644 --- a/Source/FolioReaderWebView.swift +++ b/Source/FolioReaderWebView.swift @@ -139,7 +139,8 @@ open class FolioReaderWebView : UIWebView { guard let html = js("getHTML()"), let identifier = dic["id"], - let highlight = Highlight.matchHighlight(html, andId: identifier, startOffset: startOffset, endOffset: endOffset) else { + let bookId = (self.book.name as? NSString)?.deletingPathExtension, + let highlight = Highlight.matchHighlight(html, andId: identifier, startOffset: startOffset, endOffset: endOffset, bookId: bookId) else { return } diff --git a/Source/Models/Highlight+Helper.swift b/Source/Models/Highlight+Helper.swift index 2eb53fd4b..51cb03e8c 100644 --- a/Source/Models/Highlight+Helper.swift +++ b/Source/Models/Highlight+Helper.swift @@ -263,7 +263,7 @@ extension Highlight { /** Match a highlight on string. */ - public static func matchHighlight(_ text: String, andId id: String, startOffset: String, endOffset: String) -> Highlight? { + public static func matchHighlight(_ text: String, andId id: String, startOffset: String, endOffset: String, bookId: String) -> Highlight? { let pattern = "((.|\\s)*?)" let regex = try? NSRegularExpression(pattern: pattern, options: []) let matches = regex?.matches(in: text, options: [], range: NSRange(location: 0, length: text.utf16.count)) @@ -285,7 +285,7 @@ extension Highlight { highlight.contentPre = Highlight.removeSentenceSpam(contentPre) highlight.contentPost = Highlight.removeSentenceSpam(contentPost) highlight.page = currentPageNumber - highlight.bookId = (kBookId as NSString).deletingPathExtension + highlight.bookId = bookId highlight.startOffset = (Int(startOffset) ?? -1) highlight.endOffset = (Int(endOffset) ?? -1) From 791d421f71f87d5d30011c45c0d43fd25abaf12c Mon Sep 17 00:00:00 2001 From: Kevin Delord Date: Fri, 31 Mar 2017 00:02:59 +0200 Subject: [PATCH 030/110] Remove calls to FolioReader.shared.ReaderCenter --- Source/FolioReaderAudioPlayer.swift | 21 ++++++++-------- Source/FolioReaderContainer.swift | 2 +- Source/FolioReaderFontsMenu.swift | 16 ++++++------ Source/FolioReaderHighlightList.swift | 13 +++++----- Source/FolioReaderPage.swift | 28 +++++++++++---------- Source/FolioReaderPlayerMenu.swift | 15 ++++++------ Source/FolioReaderWebView.swift | 18 ++++++++------ Source/Models/Highlight+Helper.swift | 35 +++++++++++++++++++-------- 8 files changed, 84 insertions(+), 64 deletions(-) diff --git a/Source/FolioReaderAudioPlayer.swift b/Source/FolioReaderAudioPlayer.swift index 5234665d4..01529fa72 100644 --- a/Source/FolioReaderAudioPlayer.swift +++ b/Source/FolioReaderAudioPlayer.swift @@ -28,12 +28,14 @@ open class FolioReaderAudioPlayer: NSObject { var completionHandler: () -> Void = {} var utteranceRate: Float = 0 - fileprivate var book : FRBook + fileprivate var book : FRBook + fileprivate var folioReader : FolioReader // MARK: Init - init(withBook book: FRBook) { + init(withFolioReader folioReader: FolioReader, book: FRBook) { self.book = book + self.folioReader = folioReader super.init() @@ -159,7 +161,7 @@ open class FolioReaderAudioPlayer: NSObject { func play() { if (self.book.hasAudio() == true) { - guard let currentPage = FolioReader.shared.readerCenter?.currentPage else { return } + guard let currentPage = self.folioReader.readerCenter?.currentPage else { return } currentPage.webView.js("playAudio()") } else { self.readCurrentSentence() @@ -219,7 +221,7 @@ open class FolioReaderAudioPlayer: NSObject { func playPrevChapter() { stopPlayerTimer() // Wait for "currentPage" to update, then request to play audio - FolioReader.shared.readerCenter?.changePageToPrevious { + self.folioReader.readerCenter?.changePageToPrevious { if self.isPlaying() { self.play() } else { @@ -231,8 +233,7 @@ open class FolioReaderAudioPlayer: NSObject { func playNextChapter() { stopPlayerTimer() // Wait for "currentPage" to update, then request to play audio - // TODO_SMF: remove call to FolioReader.shared.readerCenter - FolioReader.shared.readerCenter?.changePageToNext { + self.folioReader.readerCenter?.changePageToNext { if self.isPlaying() { self.play() } @@ -302,7 +303,7 @@ open class FolioReaderAudioPlayer: NSObject { // get the fragment ID so we can "mark" it in the webview let textParts = textFragment!.components(separatedBy: "#") let fragmentID = textParts[1]; - FolioReader.shared.readerCenter?.audioMark(href: currentHref, fragmentID: fragmentID) + self.folioReader.readerCenter?.audioMark(href: currentHref, fragmentID: fragmentID) return true } @@ -364,7 +365,7 @@ open class FolioReaderAudioPlayer: NSObject { func speakSentence() { // TODO_SMF_CHECK: does it work fine? guard - let readerCenter = FolioReader.shared.readerCenter, + let readerCenter = self.folioReader.readerCenter, let currentPage = readerCenter.currentPage else { return } @@ -397,7 +398,7 @@ open class FolioReaderAudioPlayer: NSObject { } else { if synthesizer.isSpeaking { stopSynthesizer(immediate: false, completion: { - if let currentPage = FolioReader.shared.readerCenter?.currentPage { + if let currentPage = self.folioReader.readerCenter?.currentPage { currentPage.webView.js("resetCurrentSentenceIndex()") } self.speakSentence() @@ -482,7 +483,7 @@ open class FolioReaderAudioPlayer: NSObject { the `currentPage` in ReaderCenter may not have updated just yet */ func getCurrentChapterName() -> String? { - guard let chapter = FolioReader.shared.readerCenter?.getCurrentChapter() else { + guard let chapter = self.folioReader.readerCenter?.getCurrentChapter() else { return nil } diff --git a/Source/FolioReaderContainer.swift b/Source/FolioReaderContainer.swift index 023bc3393..cf6b711e1 100755 --- a/Source/FolioReaderContainer.swift +++ b/Source/FolioReaderContainer.swift @@ -167,7 +167,7 @@ open class FolioReaderContainer : UIViewController { Initialize the media player */ func addAudioPlayer() { - self.audioPlayer = FolioReaderAudioPlayer(withBook: self.book) + self.audioPlayer = FolioReaderAudioPlayer(withFolioReader: self.folioReader, book: self.book) self.folioReader.readerAudioPlayer = audioPlayer } diff --git a/Source/FolioReaderFontsMenu.swift b/Source/FolioReaderFontsMenu.swift index b9901f59c..f404b005d 100644 --- a/Source/FolioReaderFontsMenu.swift +++ b/Source/FolioReaderFontsMenu.swift @@ -264,8 +264,7 @@ class FolioReaderFontsMenu : UIViewController, SMSegmentViewDelegate, UIGestur // MARK: - SMSegmentView delegate func segmentView(_ segmentView: SMSegmentView, didSelectSegmentAtIndex index: Int) { - // TODO_SMF: remove call to FolioReader.shared.readerCenter - guard (FolioReader.shared.readerCenter?.currentPage) != nil else { return } + guard (self.folioReader.readerCenter?.currentPage) != nil else { return } if segmentView.tag == 1 { @@ -290,12 +289,13 @@ class FolioReaderFontsMenu : UIViewController, SMSegmentViewDelegate, UIGestur // MARK: - Font slider changed func sliderValueChanged(_ sender: HADiscreteSlider) { - guard (FolioReader.shared.readerCenter?.currentPage) != nil else { return } - let index = Int(sender.value) - - if let _fontSize = FolioReaderFontSize(rawValue: index) { - FolioReader.currentFontSize = _fontSize + guard + (self.folioReader.readerCenter?.currentPage != nil), + let fontSize = FolioReaderFontSize(rawValue: Int(sender.value)) else { + return } + + FolioReader.currentFontSize = fontSize } // MARK: - Gestures @@ -304,7 +304,7 @@ class FolioReaderFontsMenu : UIViewController, SMSegmentViewDelegate, UIGestur dismiss() if (self.readerConfig.shouldHideNavigationOnTap == false) { - FolioReader.shared.readerCenter?.showBars() + self.folioReader.readerCenter?.showBars() } } diff --git a/Source/FolioReaderHighlightList.swift b/Source/FolioReaderHighlightList.swift index 0fb8bd201..d5aedb8eb 100644 --- a/Source/FolioReaderHighlightList.swift +++ b/Source/FolioReaderHighlightList.swift @@ -141,19 +141,20 @@ class FolioReaderHighlightList : UITableViewController { // MARK: - Table view delegate override func tableView(_ tableView: UITableView, didSelectRowAt indexPath: IndexPath) { - let highlight = highlights[(indexPath as NSIndexPath).row] + guard let highlight = highlights[safe: (indexPath as NSIndexPath).row] else { + return + } - // TODO_SMF: remove call to FolioReader.shared.readerCenter - FolioReader.shared.readerCenter?.changePageWith(page: highlight.page, andFragment: highlight.highlightId) + self.folioReader.readerCenter?.changePageWith(page: highlight.page, andFragment: highlight.highlightId) self.dismiss() } override func tableView(_ tableView: UITableView, commit editingStyle: UITableViewCellEditingStyle, forRowAt indexPath: IndexPath) { if editingStyle == .delete { let highlight = highlights[(indexPath as NSIndexPath).row] - - if highlight.page == currentPageNumber { - Highlight.removeFromHTMLById(highlight.highlightId) // Remove from HTML + + if (highlight.page == currentPageNumber), let page = self.folioReader.readerCenter?.currentPage { + Highlight.removeFromHTMLById(withinPage: page, highlightId: highlight.highlightId) // Remove from HTML } highlight.remove(withConfiguration: self.readerConfig) // Remove from Database diff --git a/Source/FolioReaderPage.swift b/Source/FolioReaderPage.swift index c587f7973..1bcaa0ebd 100755 --- a/Source/FolioReaderPage.swift +++ b/Source/FolioReaderPage.swift @@ -45,6 +45,9 @@ open class FolioReaderPage: UICollectionViewCell, UIWebViewDelegate, UIGestureRe fileprivate var book : FRBook { return self.readerContainer.book } + fileprivate var folioReader : FolioReader { + return self.readerContainer.folioReader + } // MARK: - View life cicle @@ -110,7 +113,7 @@ open class FolioReaderPage: UICollectionViewCell, UIWebViewDelegate, UIGestureRe } let statusbarHeight = UIApplication.shared.statusBarFrame.size.height - let navBarHeight = FolioReader.shared.readerCenter?.navigationController?.navigationBar.frame.size.height ?? CGFloat(0) + let navBarHeight = self.folioReader.readerCenter?.navigationController?.navigationBar.frame.size.height ?? CGFloat(0) let navTotal = self.readerConfig.shouldHideNavigationOnTap ? 0 : statusbarHeight + navBarHeight let paddingTop: CGFloat = 20 let paddingBottom: CGFloat = 30 @@ -180,7 +183,7 @@ open class FolioReaderPage: UICollectionViewCell, UIWebViewDelegate, UIGestureRe if (self.readerConfig.enableTTS == true && self.book.hasAudio() == false) { webView.js("wrappingSentencesWithinPTags()") - if let audioPlayer = FolioReader.shared.readerAudioPlayer , audioPlayer.isPlaying() { + if let audioPlayer = self.folioReader.readerAudioPlayer, (audioPlayer.isPlaying() == true) { audioPlayer.readCurrentSentence() } } @@ -224,9 +227,9 @@ open class FolioReaderPage: UICollectionViewCell, UIWebViewDelegate, UIGestureRe guard let decoded = url.absoluteString.removingPercentEncoding else { return false } let playID = decoded.substring(from: decoded.index(decoded.startIndex, offsetBy: 13)) - let chapter = FolioReader.shared.readerCenter?.getCurrentChapter() + let chapter = self.folioReader.readerCenter?.getCurrentChapter() let href = chapter?.href ?? "" - FolioReader.shared.readerAudioPlayer?.playAudio(href, fragmentID: playID) + self.folioReader.readerAudioPlayer?.playAudio(href, fragmentID: playID) return false } else if scheme == "file" { @@ -250,7 +253,7 @@ open class FolioReaderPage: UICollectionViewCell, UIWebViewDelegate, UIGestureRe } let href = splitedPath[1].trimmingCharacters(in: CharacterSet(charactersIn: "/")) - let hrefPage = (FolioReader.shared.readerCenter?.findPageByHref(href) ?? 0) + 1 + let hrefPage = (self.folioReader.readerCenter?.findPageByHref(href) ?? 0) + 1 if (hrefPage == pageNumber) { // Handle internal #anchor @@ -259,7 +262,7 @@ open class FolioReaderPage: UICollectionViewCell, UIWebViewDelegate, UIGestureRe return false } } else { - FolioReader.shared.readerCenter?.changePageWith(href: href, animated: true) + self.folioReader.readerCenter?.changePageWith(href: href, animated: true) } return false @@ -280,13 +283,12 @@ open class FolioReaderPage: UICollectionViewCell, UIWebViewDelegate, UIGestureRe if #available(iOS 9.0, *) { let safariVC = SFSafariViewController(url: request.url!) safariVC.view.tintColor = self.readerConfig.tintColor - // TODO_SMF: remove call to FolioReader.shared.readerCenter - FolioReader.shared.readerCenter?.present(safariVC, animated: true, completion: nil) + self.folioReader.readerCenter?.present(safariVC, animated: true, completion: nil) } else { let webViewController = WebViewController(url: request.url!) let nav = UINavigationController(rootViewController: webViewController) nav.view.tintColor = self.readerConfig.tintColor - FolioReader.shared.readerCenter?.present(nav, animated: true, completion: nil) + self.folioReader.readerCenter?.present(nav, animated: true, completion: nil) } return false } else { @@ -359,7 +361,7 @@ open class FolioReaderPage: UICollectionViewCell, UIWebViewDelegate, UIGestureRe open func handleTapGesture(_ recognizer: UITapGestureRecognizer) { // webView.setMenuVisible(false) - if let _navigationController = FolioReader.shared.readerCenter?.navigationController , _navigationController.isNavigationBarHidden { + if let _navigationController = self.folioReader.readerCenter?.navigationController , _navigationController.isNavigationBarHidden { let menuIsVisibleRef = menuIsVisible let selected = webView.js("getSelectedText()") @@ -372,13 +374,13 @@ open class FolioReaderPage: UICollectionViewCell, UIWebViewDelegate, UIGestureRe DispatchQueue.main.asyncAfter(deadline: dispatchTime, execute: { if self.shouldShowBar && !menuIsVisibleRef { - FolioReader.shared.readerCenter?.toggleBars() + self.folioReader.readerCenter?.toggleBars() } self.shouldShowBar = true }) } } else if self.readerConfig.shouldHideNavigationOnTap == true { - FolioReader.shared.readerCenter?.hideBars() + self.folioReader.readerCenter?.hideBars() } // Reset menu @@ -467,7 +469,7 @@ open class FolioReaderPage: UICollectionViewCell, UIWebViewDelegate, UIGestureRe */ func audioMarkID(_ identifier: String) { // TODO_SMF: replace shared readerContainer - guard let currentPage = FolioReader.shared.readerCenter?.currentPage else { + guard let currentPage = self.folioReader.readerCenter?.currentPage else { return } diff --git a/Source/FolioReaderPlayerMenu.swift b/Source/FolioReaderPlayerMenu.swift index 68fd00e21..575698472 100644 --- a/Source/FolioReaderPlayerMenu.swift +++ b/Source/FolioReaderPlayerMenu.swift @@ -93,7 +93,7 @@ class FolioReaderPlayerMenu : UIViewController, SMSegmentViewDelegate, UIGestu playPauseBtn.addTarget(self, action: #selector(FolioReaderPlayerMenu.togglePlay(_:)), for: .touchUpInside) menuView.addSubview(playPauseBtn) - if let audioPlayer = FolioReader.shared.readerAudioPlayer , audioPlayer.isPlaying() { + if let audioPlayer = self.folioReader.readerAudioPlayer , audioPlayer.isPlaying() { playPauseBtn.isSelected = true } @@ -233,23 +233,23 @@ class FolioReaderPlayerMenu : UIViewController, SMSegmentViewDelegate, UIGestu func segmentView(_ segmentView: SMSegmentView, didSelectSegmentAtIndex index: Int) { guard viewDidAppear else { return } - if let audioPlayer = FolioReader.shared.readerAudioPlayer , segmentView.tag == 2 { + if let audioPlayer = self.folioReader.readerAudioPlayer , segmentView.tag == 2 { audioPlayer.setRate(index) FolioReader.currentAudioRate = index } } func prevChapter(_ sender: UIButton!) { - FolioReader.shared.readerAudioPlayer?.playPrevChapter() + self.folioReader.readerAudioPlayer?.playPrevChapter() } func nextChapter(_ sender: UIButton!) { - FolioReader.shared.readerAudioPlayer?.playNextChapter() + self.folioReader.readerAudioPlayer?.playNextChapter() } func togglePlay(_ sender: UIButton!) { sender.isSelected = sender.isSelected != true - FolioReader.shared.readerAudioPlayer?.togglePlay() + self.folioReader.readerAudioPlayer?.togglePlay() closeView() } @@ -266,8 +266,7 @@ class FolioReaderPlayerMenu : UIViewController, SMSegmentViewDelegate, UIGestu } // update the current page style - // TODO_SMF: remove call to FolioReader.shared.readerCenter - if let currentPage = FolioReader.shared.readerCenter?.currentPage { + if let currentPage = self.folioReader.readerCenter?.currentPage { currentPage.webView.js("setMediaOverlayStyle(\"\(FolioReader.currentMediaOverlayStyle.className())\")") } } @@ -276,7 +275,7 @@ class FolioReaderPlayerMenu : UIViewController, SMSegmentViewDelegate, UIGestu self.dismiss() if (self.readerConfig.shouldHideNavigationOnTap == false) { - FolioReader.shared.readerCenter?.showBars() + self.folioReader.readerCenter?.showBars() } } diff --git a/Source/FolioReaderWebView.swift b/Source/FolioReaderWebView.swift index 1d802c8e2..6a4d26b90 100644 --- a/Source/FolioReaderWebView.swift +++ b/Source/FolioReaderWebView.swift @@ -19,6 +19,9 @@ open class FolioReaderWebView : UIWebView { fileprivate var book : FRBook { return self.readerContainer.book } + fileprivate var folioReader : FolioReader { + return self.readerContainer.folioReader + } override init(frame: CGRect) { fatalError("use init(frame:readerConfig:book:) instead.") @@ -66,12 +69,11 @@ open class FolioReaderWebView : UIWebView { let shareImage = UIAlertAction(title: self.readerConfig.localizedShareImageQuote, style: .default, handler: { (action) -> Void in if self.isShare { if let textToShare = self.js("getHighlightContent()") { - FolioReader.shared.readerCenter?.presentQuoteShare(textToShare) + self.folioReader.readerCenter?.presentQuoteShare(textToShare) } } else { if let textToShare = self.js("getSelectedText()") { - // TODO_SMF: remove call to FolioReader.shared.readerCenter - FolioReader.shared.readerCenter?.presentQuoteShare(textToShare) + self.folioReader.readerCenter?.presentQuoteShare(textToShare) self.clearTextSelection() } @@ -82,11 +84,11 @@ open class FolioReaderWebView : UIWebView { let shareText = UIAlertAction(title: self.readerConfig.localizedShareTextQuote, style: .default) { (action) -> Void in if self.isShare { if let textToShare = self.js("getHighlightContent()") { - FolioReader.shared.readerCenter?.shareHighlight(textToShare, rect: sender.menuFrame) + self.folioReader.readerCenter?.shareHighlight(textToShare, rect: sender.menuFrame) } } else { if let textToShare = self.js("getSelectedText()") { - FolioReader.shared.readerCenter?.shareHighlight(textToShare, rect: sender.menuFrame) + self.folioReader.readerCenter?.shareHighlight(textToShare, rect: sender.menuFrame) } } self.setMenuVisible(false) @@ -99,11 +101,11 @@ open class FolioReaderWebView : UIWebView { alertController.addAction(cancel) if let alert = alertController.popoverPresentationController { - alert.sourceView = FolioReader.shared.readerCenter?.currentPage + alert.sourceView = self.folioReader.readerCenter?.currentPage alert.sourceRect = sender.menuFrame } - FolioReader.shared.readerCenter?.present(alertController, animated: true, completion: nil) + self.folioReader.readerCenter?.present(alertController, animated: true, completion: nil) } func colors(_ sender: UIMenuController?) { @@ -166,7 +168,7 @@ open class FolioReaderWebView : UIWebView { } func play(_ sender: UIMenuController?) { - FolioReader.shared.readerAudioPlayer?.play() + self.folioReader.readerAudioPlayer?.play() self.clearTextSelection() } diff --git a/Source/Models/Highlight+Helper.swift b/Source/Models/Highlight+Helper.swift index 51cb03e8c..27b21d583 100644 --- a/Source/Models/Highlight+Helper.swift +++ b/Source/Models/Highlight+Helper.swift @@ -87,6 +87,7 @@ extension Highlight { /// - readerConfig: Current folio reader configuration. /// - completion: Completion block. public func persist(withConfiguration readerConfig: FolioReaderConfig, completion: Completion? = nil) { + // TODO_SMF_DOC do { let realm = try Realm(configuration: readerConfig.realmConfiguration) realm.beginWrite() @@ -103,6 +104,7 @@ extension Highlight { /// /// - Parameter readerConfig: Current folio reader configuration. public func remove(withConfiguration readerConfig: FolioReaderConfig) { + // TODO_SMF_DOC do { let realm = try Realm(configuration: readerConfig.realmConfiguration) realm.beginWrite() @@ -119,6 +121,7 @@ extension Highlight { /// - readerConfig: Current folio reader configuration. /// - highlightId: The ID to be removed public static func removeById(withConfiguration readerConfig: FolioReaderConfig, highlightId: String) { + // TODO_SMF_DOC var highlight: Highlight? let predicate = NSPredicate(format:"highlightId = %@", highlightId) @@ -138,6 +141,7 @@ extension Highlight { /// - highlightId: The ID to be removed /// - type: The `HighlightStyle` public static func updateById(withConfiguration readerConfig: FolioReaderConfig, highlightId: String, type: HighlightStyle) { + // TODO_SMF_DOC var highlight: Highlight? let predicate = NSPredicate(format:"highlightId = %@", highlightId) do { @@ -162,6 +166,7 @@ extension Highlight { /// - page: Page number /// - Returns: Return a list of Highlights public static func allByBookId(withConfiguration readerConfig: FolioReaderConfig, bookId: String, andPage page: NSNumber? = nil) -> [Highlight] { + // TODO_SMF_DOC var highlights: [Highlight]? var predicate = NSPredicate(format: "bookId = %@", bookId) if let page = page { @@ -183,6 +188,7 @@ extension Highlight { /// - Parameter readerConfig: - readerConfig: Current folio reader configuration. /// - Returns: Return all Highlights public static func all(withConfiguration readerConfig: FolioReaderConfig) -> [Highlight] { + // TODO_SMF_DOC var highlights: [Highlight]? do { let realm = try Realm(configuration: readerConfig.realmConfiguration) @@ -254,6 +260,16 @@ extension Highlight { // TODO_SMF_DEPRECATE self.remove(withConfiguration: Highlight.readerConfig) } + + /// Remove a Highlight from HTML by ID + /// + /// - Parameter highlightId: The ID to be removed + /// - Returns: The removed id + @discardableResult public static func removeFromHTMLById(_ highlightId: String) -> String? { + // TODO_SMF_DEPRECATE + let page = FolioReader.shared.readerCenter?.currentPage + return self.removeFromHTMLById(withinPage: page, highlightId: highlightId) + } } // MARK: - HTML Methods @@ -296,7 +312,6 @@ extension Highlight { } private static func subString(ofContent content: String, fromRangeOfString rangeString: String, withPattern pattern: String) -> String { - var updatedContent = content if updatedContent.range(of: rangeString) != nil { let regex = try? NSRegularExpression(pattern: pattern, options: []) @@ -310,15 +325,15 @@ extension Highlight { return updatedContent } - /** - Remove a Highlight from HTML by ID - - - parameter highlightId: The ID to be removed - - returns: The removed id - */ - @discardableResult public static func removeFromHTMLById(_ highlightId: String) -> String? { - // TODO_SMF: remove call to FolioReader.shared.readerCenter - guard let currentPage = FolioReader.shared.readerCenter?.currentPage else { return nil } + /// Remove a Highlight from HTML by ID + /// + /// - Parameters: + /// - page: The page containing the HTML. + /// - highlightId: The ID to be removed + /// - Returns: The removed id + @discardableResult public static func removeFromHTMLById(withinPage page: FolioReaderPage?, highlightId: String) -> String? { + // TODO_SMF_DOC + guard let currentPage = page else { return nil } if let removedId = currentPage.webView.js("removeHighlightById('\(highlightId)')") { return removedId From ffdbc2d81330e5f66ec9af1356a74236d68f5843 Mon Sep 17 00:00:00 2001 From: Kevin Delord Date: Fri, 31 Mar 2017 00:55:46 +0200 Subject: [PATCH 031/110] Example app: integrate new API and refactor code --- Example/Example/AppDelegate.swift | 15 ++- Example/Example/ViewController.swift | 160 +++++++++++++++++++-------- 2 files changed, 122 insertions(+), 53 deletions(-) diff --git a/Example/Example/AppDelegate.swift b/Example/Example/AppDelegate.swift index 790600ccf..a177baf35 100644 --- a/Example/Example/AppDelegate.swift +++ b/Example/Example/AppDelegate.swift @@ -10,9 +10,11 @@ import UIKit import FolioReaderKit @UIApplicationMain -class AppDelegate: UIResponder, UIApplicationDelegate { +class AppDelegate : UIResponder, UIApplicationDelegate { - var window: UIWindow? + var window : UIWindow? + var standardEpub : FolioReader? + var audioEpub : FolioReader? func application(_ application: UIApplication, didFinishLaunchingWithOptions launchOptions: [UIApplicationLaunchOptionsKey: Any]?) -> Bool { // Override point for customization after application launch. @@ -20,11 +22,14 @@ class AppDelegate: UIResponder, UIApplicationDelegate { } func applicationWillResignActive(_ application: UIApplication) { - FolioReader.applicationWillResignActive() + /// Save Reader state, book, page and scroll offset. + self.standardEpub?.saveReaderState() + self.audioEpub?.saveReaderState() } func applicationWillTerminate(_ application: UIApplication) { - FolioReader.applicationWillTerminate() + /// Save Reader state, book, page and scroll offset. + self.standardEpub?.saveReaderState() + self.audioEpub?.saveReaderState() } } - diff --git a/Example/Example/ViewController.swift b/Example/Example/ViewController.swift index 582682401..8d6db86ad 100755 --- a/Example/Example/ViewController.swift +++ b/Example/Example/ViewController.swift @@ -9,62 +9,126 @@ import UIKit import FolioReaderKit -class ViewController: UIViewController { +enum Epub: Int { + case bookOne = 0 + case bookTwo - @IBOutlet var bookOne: UIButton! - @IBOutlet var bookTwo: UIButton! + var name: String { + switch self { + case .bookOne: return "The Silver Chair" // standard eBook + case .bookTwo: return "The Adventures Of Sherlock Holmes - Adventure I" // audio-eBook + } + } - let epubSampleFiles = [ - "The Silver Chair", // standard eBook - "The Adventures Of Sherlock Holmes - Adventure I", // audio-eBook - ] + var shouldHideNavigationOnTap: Bool { + switch self { + case .bookOne: return false + case .bookTwo: return true + } + } + + var scrollDirection: FolioReaderScrollDirection { + switch self { + case .bookOne: return .vertical + case .bookTwo: return .horizontal + } + } + + var bookPath: String? { + return Bundle.main.path(forResource: self.name, ofType: "epub") + } + + func retain(folioReader: FolioReader) { + let appDelegate = (UIApplication.shared.delegate as? AppDelegate) + + switch self { + case .bookOne: appDelegate?.standardEpub = folioReader + case .bookTwo: appDelegate?.audioEpub = folioReader + } + } +} + +class ViewController : UIViewController { + + @IBOutlet var bookOne : UIButton? + @IBOutlet var bookTwo : UIButton? override func viewDidLoad() { super.viewDidLoad() - - setCover(bookOne, index: 0) - setCover(bookTwo, index: 1) - } - @IBAction func didOpen(_ sender: AnyObject) { - openEpub(sender.tag); + self.bookOne?.tag = Epub.bookOne.rawValue + self.bookTwo?.tag = Epub.bookTwo.rawValue + + self.setCover(self.bookOne, index: 0) + self.setCover(self.bookTwo, index: 1) } - - func openEpub(_ sampleNum: Int) { - let config = FolioReaderConfig() - config.shouldHideNavigationOnTap = sampleNum == 1 ? true : false - config.scrollDirection = sampleNum == 1 ? .horizontal : .vertical - - // See more at FolioReaderConfig.swift -// config.canChangeScrollDirection = false -// config.enableTTS = false -// config.allowSharing = false -// config.tintColor = UIColor.blueColor() -// config.toolBarTintColor = UIColor.redColor() -// config.toolBarBackgroundColor = UIColor.purpleColor() -// config.menuTextColor = UIColor.brownColor() -// config.menuBackgroundColor = UIColor.lightGrayColor() -// config.hidePageIndicator = true -// config.realmConfiguration = Realm.Configuration(fileURL: FileManager.default.urls(for: .documentDirectory, in: .userDomainMask).first?.appendingPathComponent("highlights.realm")) - - // Custom sharing quote background - let customImageQuote = QuoteImage(withImage: UIImage(named: "demo-bg")!, alpha: 0.6, backgroundColor: UIColor.black) - let customQuote = QuoteImage(withColor: UIColor(red:0.30, green:0.26, blue:0.20, alpha:1.0), alpha: 1.0, textColor: UIColor(red:0.86, green:0.73, blue:0.70, alpha:1.0)) - - config.quoteCustomBackgrounds = [customImageQuote, customQuote] - - // Epub file - let epubName = epubSampleFiles[sampleNum-1]; - let bookPath = Bundle.main.path(forResource: epubName, ofType: "epub") - _ = FolioReader.presentReader(parentViewController: self, withEpubPath: bookPath!, andConfig: config, shouldRemoveEpub: false) + + private func readerConfiguration(forEpub epub: Epub) -> FolioReaderConfig { + + let config = FolioReaderConfig() + config.shouldHideNavigationOnTap = epub.shouldHideNavigationOnTap + config.scrollDirection = epub.scrollDirection + + // See more at FolioReaderConfig.swift + // config.canChangeScrollDirection = false + // config.enableTTS = false + // config.allowSharing = false + // config.tintColor = UIColor.blueColor() + // config.toolBarTintColor = UIColor.redColor() + // config.toolBarBackgroundColor = UIColor.purpleColor() + // config.menuTextColor = UIColor.brownColor() + // config.menuBackgroundColor = UIColor.lightGrayColor() + // config.hidePageIndicator = true + // config.realmConfiguration = Realm.Configuration(fileURL: FileManager.default.urls(for: .documentDirectory, in: .userDomainMask).first?.appendingPathComponent("highlights.realm")) + + // Custom sharing quote background + config.quoteCustomBackgrounds = [] + if let image = UIImage(named: "demo-bg") { + let customImageQuote = QuoteImage(withImage: image, alpha: 0.6, backgroundColor: UIColor.black) + config.quoteCustomBackgrounds.append(customImageQuote) + } + + let textColor = UIColor(red:0.86, green:0.73, blue:0.70, alpha:1.0) + let customColor = UIColor(red:0.30, green:0.26, blue:0.20, alpha:1.0) + let customQuote = QuoteImage(withColor: customColor, alpha: 1.0, textColor: textColor) + config.quoteCustomBackgrounds.append(customQuote) + + return config + } + + fileprivate func open(epub: Epub) { + + guard let bookPath = epub.bookPath else { + return + } + + let readerConfiguration = self.readerConfiguration(forEpub: epub) + let folioReader = FolioReader.presentReader(parentViewController: self, withEpubPath: bookPath, andConfig: readerConfiguration, shouldRemoveEpub: false) + + epub.retain(folioReader: folioReader) } - func setCover(_ button: UIButton, index: Int) { - let epubName = epubSampleFiles[index]; - let bookPath = Bundle.main.path(forResource: epubName, ofType: "epub") - - if let image = FolioReader.getCoverImage(bookPath!) { - button.setBackgroundImage(image, for: .normal) - } + private func setCover(_ button: UIButton?, index: Int) { + guard + let epub = Epub(rawValue: index), + let bookPath = epub.bookPath, + let image = FolioReader.getCoverImage(bookPath) else { + return + } + + button?.setBackgroundImage(image, for: .normal) } } + +// MARK: - IBAction + +extension ViewController { + + @IBAction func didOpen(_ sender: AnyObject) { + guard let epub = Epub(rawValue: sender.tag) else { + return + } + + self.open(epub: epub) + } +} From 9f36b97764bf9f20456b1ebe638cdb5814a93f1b Mon Sep 17 00:00:00 2001 From: Kevin Delord Date: Fri, 31 Mar 2017 01:03:57 +0200 Subject: [PATCH 032/110] FolioReader: remove all use of FolioReader.shared attribute. --- Source/FolioReaderAudioPlayer.swift | 4 +- Source/FolioReaderCenter.swift | 47 +++---- Source/FolioReaderFontsMenu.swift | 22 ++-- Source/FolioReaderHighlightList.swift | 6 +- Source/FolioReaderKit.swift | 172 +++++++++++++++----------- Source/FolioReaderPage.swift | 4 +- Source/FolioReaderPageIndicator.swift | 2 +- Source/FolioReaderPlayerMenu.swift | 14 +-- Source/FolioReaderQuoteShare.swift | 3 +- Source/FolioReaderWebView.swift | 4 +- Source/PageViewController.swift | 2 +- 11 files changed, 157 insertions(+), 123 deletions(-) diff --git a/Source/FolioReaderAudioPlayer.swift b/Source/FolioReaderAudioPlayer.swift index 01529fa72..5de5d03d7 100644 --- a/Source/FolioReaderAudioPlayer.swift +++ b/Source/FolioReaderAudioPlayer.swift @@ -276,7 +276,7 @@ open class FolioReaderAudioPlayer: NSObject { guard let player = player else { return false } - setRate(FolioReader.currentAudioRate) + setRate(self.folioReader.currentAudioRate) player.enableRate = true player.prepareToPlay() player.delegate = self @@ -345,7 +345,7 @@ open class FolioReaderAudioPlayer: NSObject { if synthesizer == nil { synthesizer = AVSpeechSynthesizer() synthesizer.delegate = self - setRate(FolioReader.currentAudioRate) + setRate(self.folioReader.currentAudioRate) } let utterance = AVSpeechUtterance(string: text) diff --git a/Source/FolioReaderCenter.swift b/Source/FolioReaderCenter.swift index 481c1df06..978c0529a 100755 --- a/Source/FolioReaderCenter.swift +++ b/Source/FolioReaderCenter.swift @@ -229,11 +229,11 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo func configureNavBarButtons() { // Navbar buttons - let shareIcon = UIImage(readerImageNamed: "icon-navbar-share")?.ignoreSystemTint() - let audioIcon = UIImage(readerImageNamed: "icon-navbar-tts")?.ignoreSystemTint() //man-speech-icon - let closeIcon = UIImage(readerImageNamed: "icon-navbar-close")?.ignoreSystemTint() - let tocIcon = UIImage(readerImageNamed: "icon-navbar-toc")?.ignoreSystemTint() - let fontIcon = UIImage(readerImageNamed: "icon-navbar-font")?.ignoreSystemTint() + let shareIcon = UIImage(readerImageNamed: "icon-navbar-share")?.ignoreSystemTint(withConfiguration: self.readerConfig) + let audioIcon = UIImage(readerImageNamed: "icon-navbar-tts")?.ignoreSystemTint(withConfiguration: self.readerConfig) //man-speech-icon + let closeIcon = UIImage(readerImageNamed: "icon-navbar-close")?.ignoreSystemTint(withConfiguration: self.readerConfig) + let tocIcon = UIImage(readerImageNamed: "icon-navbar-toc")?.ignoreSystemTint(withConfiguration: self.readerConfig) + let fontIcon = UIImage(readerImageNamed: "icon-navbar-font")?.ignoreSystemTint(withConfiguration: self.readerConfig) let space = 70 as CGFloat let menu = UIBarButtonItem(image: closeIcon, style: .plain, target: self, action:#selector(closeReader(_:))) @@ -282,7 +282,7 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo // MARK: Change page progressive direction func setCollectionViewProgressiveDirection() { - if (FolioReader.needsRTLChange == true) { + if (self.readerContainer.folioReader.needsRTLChange == true) { collectionView.transform = CGAffineTransform(scaleX: -1, y: 1) } else { collectionView.transform = CGAffineTransform.identity @@ -290,7 +290,7 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo } func setPageProgressiveDirection(_ page: FolioReaderPage) { - if (FolioReader.needsRTLChange == true) { + if (self.readerContainer.folioReader.needsRTLChange == true) { // if page.transform.a == -1 { return } page.transform = CGAffineTransform(scaleX: -1, y: 1) } else { @@ -441,16 +441,16 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo html = html.replacingOccurrences(of: "", with: toInject) // Font class name - var classes = FolioReader.currentFont.cssIdentifier - classes += " "+FolioReader.currentMediaOverlayStyle.className() + var classes = self.readerContainer.folioReader.currentFont.cssIdentifier + classes += " " + self.readerContainer.folioReader.currentMediaOverlayStyle.className() // Night mode - if FolioReader.nightMode { + if (self.readerContainer.folioReader.nightMode == true) { classes += " nightMode" } // Font Size - classes += " \(FolioReader.currentFontSize.cssIdentifier)" + classes += " \(self.readerContainer.folioReader.currentFontSize.cssIdentifier)" html = html.replacingOccurrences(of: "= totalPages { @@ -1086,14 +1091,14 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo func closeReader(_ sender: UIBarButtonItem) { dismiss() - FolioReader.close() + self.readerContainer.folioReader.close() } /** Present chapter list */ func presentChapterList(_ sender: UIBarButtonItem) { - FolioReader.saveReaderState() + self.readerContainer.folioReader.saveReaderState() let chapter = FolioReaderChapterList(folioReader: self.readerContainer.folioReader, readerConfig: self.readerConfig, book: self.readerContainer.book, delegate: self) let highlight = FolioReaderHighlightList(folioReader: self.readerContainer.folioReader, readerConfig: self.readerConfig) @@ -1111,7 +1116,7 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo Present fonts and settings menu */ func presentFontsMenu() { - FolioReader.saveReaderState() + self.readerContainer.folioReader.saveReaderState() hideBars() let menu = FolioReaderFontsMenu(folioReader: self.readerContainer.folioReader, readerConfig: self.readerConfig) @@ -1133,7 +1138,7 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo Present audio player menu */ func presentPlayerMenu(_ sender: UIBarButtonItem) { - FolioReader.saveReaderState() + self.readerContainer.folioReader.saveReaderState() hideBars() let menu = FolioReaderPlayerMenu(folioReader: self.readerContainer.folioReader, readerConfig: self.readerConfig) @@ -1186,7 +1191,7 @@ extension FolioReaderCenter: FolioReaderPageDelegate { if currentPageNumber == pageNumber && pageOffset > 0 { page.scrollPageToOffset(pageOffset!, animated: false) } - } else if !isScrolling && FolioReader.needsRTLChange { + } else if !isScrolling && self.readerContainer.folioReader.needsRTLChange { page.scrollPageToBottom() } } else if isFirstLoad { diff --git a/Source/FolioReaderFontsMenu.swift b/Source/FolioReaderFontsMenu.swift index f404b005d..71c78a6b2 100644 --- a/Source/FolioReaderFontsMenu.swift +++ b/Source/FolioReaderFontsMenu.swift @@ -142,7 +142,7 @@ class FolioReaderFontsMenu : UIViewController, SMSegmentViewDelegate, UIGestur dayNight.tag = 1 dayNight.addSegmentWithTitle(self.readerConfig.localizedFontMenuDay, onSelectionImage: sunSelected, offSelectionImage: sunNormal) dayNight.addSegmentWithTitle(self.readerConfig.localizedFontMenuNight, onSelectionImage: moonSelected, offSelectionImage: moonNormal) - dayNight.selectSegmentAtIndex(FolioReader.nightMode.hashValue) + dayNight.selectSegmentAtIndex(self.folioReader.nightMode.hashValue) menuView.addSubview(dayNight) @@ -173,7 +173,7 @@ class FolioReaderFontsMenu : UIViewController, SMSegmentViewDelegate, UIGestur fontName.segments[2].titleFont = UIFont(name: "Lora-Regular", size: 18)! fontName.segments[3].titleFont = UIFont(name: "Raleway-Regular", size: 18)! - fontName.selectSegmentAtIndex(FolioReader.currentFont.rawValue) + fontName.selectSegmentAtIndex(self.folioReader.currentFont.rawValue) menuView.addSubview(fontName) // Separator 2 @@ -196,7 +196,7 @@ class FolioReaderFontsMenu : UIViewController, SMSegmentViewDelegate, UIGestur slider.backgroundColor = UIColor.clear slider.tintColor = self.readerConfig.nightModeSeparatorColor slider.minimumValue = 0 - slider.value = CGFloat(FolioReader.currentFontSize.rawValue) + slider.value = CGFloat(self.folioReader.currentFontSize.rawValue) slider.addTarget(self, action: #selector(FolioReaderFontsMenu.sliderValueChanged(_:)), for: UIControlEvents.valueChanged) // Force remove fill color @@ -251,7 +251,7 @@ class FolioReaderFontsMenu : UIViewController, SMSegmentViewDelegate, UIGestur layoutDirection.addSegmentWithTitle(self.readerConfig.localizedLayoutVertical, onSelectionImage: verticalSelected, offSelectionImage: verticalNormal) layoutDirection.addSegmentWithTitle(self.readerConfig.localizedLayoutHorizontal, onSelectionImage: horizontalSelected, offSelectionImage: horizontalNormal) - var scrollDirection = FolioReaderScrollDirection(rawValue: FolioReader.currentScrollDirection) + var scrollDirection = FolioReaderScrollDirection(rawValue: self.folioReader.currentScrollDirection) if scrollDirection == .defaultVertical && self.readerConfig.scrollDirection != .defaultVertical { scrollDirection = self.readerConfig.scrollDirection @@ -268,21 +268,23 @@ class FolioReaderFontsMenu : UIViewController, SMSegmentViewDelegate, UIGestur if segmentView.tag == 1 { - FolioReader.nightMode = Bool(index == 1) + self.folioReader.nightMode = Bool(index == 1) UIView.animate(withDuration: 0.6, animations: { - self.menuView.backgroundColor = (FolioReader.nightMode ? self.readerConfig.nightModeBackground : UIColor.white) + self.menuView.backgroundColor = (self.folioReader.nightMode ? self.readerConfig.nightModeBackground : UIColor.white) }) } else if segmentView.tag == 2 { - FolioReader.currentFont = FolioReaderFont(rawValue: index)! + self.folioReader.currentFont = FolioReaderFont(rawValue: index)! } else if segmentView.tag == 3 { - guard FolioReader.currentScrollDirection != index else { return } + guard self.folioReader.currentScrollDirection != index else { + return + } - FolioReader.currentScrollDirection = index + self.folioReader.currentScrollDirection = index } } @@ -295,7 +297,7 @@ class FolioReaderFontsMenu : UIViewController, SMSegmentViewDelegate, UIGestur return } - FolioReader.currentFontSize = fontSize + self.folioReader.currentFontSize = fontSize } // MARK: - Gestures diff --git a/Source/FolioReaderHighlightList.swift b/Source/FolioReaderHighlightList.swift index d5aedb8eb..4737d0883 100644 --- a/Source/FolioReaderHighlightList.swift +++ b/Source/FolioReaderHighlightList.swift @@ -90,12 +90,12 @@ class FolioReaderHighlightList : UITableViewController { text.addAttribute(NSFontAttributeName, value: UIFont(name: "Avenir-Light", size: 16)!, range: range) text.addAttribute(NSForegroundColorAttributeName, value: textColor, range: range) - if highlight.type == HighlightStyle.underline.rawValue { + if (highlight.type == HighlightStyle.underline.rawValue) { text.addAttribute(NSBackgroundColorAttributeName, value: UIColor.clear, range: range) - text.addAttribute(NSUnderlineColorAttributeName, value: HighlightStyle.colorForStyle(highlight.type, nightMode: FolioReader.nightMode), range: range) + text.addAttribute(NSUnderlineColorAttributeName, value: HighlightStyle.colorForStyle(highlight.type, nightMode: self.folioReader.nightMode), range: range) text.addAttribute(NSUnderlineStyleAttributeName, value: NSNumber(value: NSUnderlineStyle.styleSingle.rawValue as Int), range: range) } else { - text.addAttribute(NSBackgroundColorAttributeName, value: HighlightStyle.colorForStyle(highlight.type, nightMode: FolioReader.nightMode), range: range) + text.addAttribute(NSBackgroundColorAttributeName, value: HighlightStyle.colorForStyle(highlight.type, nightMode: self.folioReader.nightMode), range: range) } // Text diff --git a/Source/FolioReaderKit.swift b/Source/FolioReaderKit.swift index 2d2c0003c..56e183cdc 100755 --- a/Source/FolioReaderKit.swift +++ b/Source/FolioReaderKit.swift @@ -43,18 +43,17 @@ enum MediaOverlayStyle: Int { /// FolioReader actions delegate @objc public protocol FolioReaderDelegate: class { - - /** - Did finished loading book. - - - parameter folioReader: The FolioReader instance - - parameter book: The Book instance - */ + + /// Did finished loading book. + /// + /// - Parameters: + /// - folioReader: The FolioReader instance + /// - book: The Book instance @objc optional func folioReader(_ folioReader: FolioReader, didFinishedLoading book: FRBook) - - /** - Called when reader did closed. - */ + + /// Called when reader did closed. + /// + /// - Parameter folioReader: The FolioReader instance @objc optional func folioReaderDidClosed(_ folioReader: FolioReader) // TODO_SMF_CHECK: make sure the following deprecated functions still work... or not.: @@ -169,7 +168,7 @@ open class FolioReader: NSObject { } /// Check the current Media Overlay or TTS style - static var currentMediaOverlayStyle: MediaOverlayStyle { + var currentMediaOverlayStyle: MediaOverlayStyle { // TODO_SMF: remove unwrap get { return MediaOverlayStyle(rawValue: FolioReader.defaults.value(forKey: kCurrentMediaOverlayStyle) as! Int)! } set (value) { @@ -188,50 +187,56 @@ open class FolioReader: NSObject { self.readerCenter?.setScrollDirection(direction) } } +} - // MARK: - Get Cover Image - - /** - Read Cover Image and Return an `UIImage` - */ - // TODO_SMF_DOC: new function signature change - open class func getCoverImage(_ epubPath: String, unzipPath: String? = nil) -> UIImage? { - // TODO_SMF_QUESTION: this used the shared instance before and ignore the parameter. - // Should we properly implement the parameter or change the API to use the current FolioReader? - return FREpubParser().parseCoverImage(epubPath, unzipPath: unzipPath) - } - - // MARK: - Get Title - open class func getTitle(_ epubPath: String) -> String? { - return FREpubParser().parseTitle(epubPath) - } +// MARK: - Present Folio Reader - open class func getAuthorName(_ epubPath: String) -> String? { - return FREpubParser().parseAuthorName(epubPath) - } +extension FolioReader { - // MARK: - Present Folio Reader - /** Present a Folio Reader for a Parent View Controller. + // TODO_SMF_DOC */ open class func presentReader(parentViewController: UIViewController, withEpubPath epubPath: String, andConfig config: FolioReaderConfig, shouldRemoveEpub: Bool = true, animated: Bool = true) -> FolioReader { let folioReader = FolioReader() let readerContainer = FolioReaderContainer(withConfig: config, folioReader: folioReader, epubPath: epubPath, removeEpub: shouldRemoveEpub) folioReader.readerContainer = readerContainer parentViewController.present(readerContainer, animated: animated, completion: nil) + // TODO_SMF_DOC FolioReader.shared = folioReader return folioReader } } +// MARK: - Image Cover + +extension FolioReader { + + // TODO_SMF_QUESTION: this used the shared instance before and ignore the parameter. + // Should we properly implement the parameter or change the API to use the current FolioReader? + + /** + Read Cover Image and Return an `UIImage` + */ + // TODO_SMF_DOC: new function signature change + open class func getCoverImage(_ epubPath: String, unzipPath: String? = nil) -> UIImage? { + return FREpubParser().parseCoverImage(epubPath, unzipPath: unzipPath) + } + + open class func getTitle(_ epubPath: String) -> String? { + return FREpubParser().parseTitle(epubPath) + } + + open class func getAuthorName(_ epubPath: String) -> String? { + return FREpubParser().parseAuthorName(epubPath) + } +} + // MARK: - Exit, save and close FolioReader extension FolioReader { - /** - Save Reader state, book, page and scroll are saved - */ + /// Save Reader state, book, page and scroll offset. open func saveReaderState() { guard self.isReaderOpen else { return } @@ -250,9 +255,7 @@ extension FolioReader { FolioReader.defaults.set(position, forKey: bookId) } - /** - Closes and save the reader current instance - */ + /// Closes and save the reader current instance. open func close() { self.saveReaderState() self.isReaderOpen = false @@ -264,70 +267,86 @@ extension FolioReader { } } -// MARK: - Public shared extension. All Deprecated function +// MARK: - Public static functions. All Deprecated function extension FolioReader { - // TODO_SMF: temporal variable to build and run the current state. Should be completely remove. + // TODO_SMF_DEPRECATE private static var _sharedInstance = FolioReader() open static var shared : FolioReader { get { return _sharedInstance } set { _sharedInstance = newValue } } + /// Check the current Media Overlay or TTS style + static var currentMediaOverlayStyle: MediaOverlayStyle { + // TODO_SMF_DEPRECATE + return FolioReader.shared.currentMediaOverlayStyle + } + /// Check if current theme is Night mode open class var nightMode: Bool { + // TODO_SMF_DEPRECATE get { return FolioReader.shared.nightMode } set { FolioReader.shared.nightMode = newValue } } /// Check current font name open class var currentFont: FolioReaderFont { + // TODO_SMF_DEPRECATE get { return FolioReader.shared.currentFont } set { FolioReader.shared.currentFont = newValue } } /// Check current font size open class var currentFontSize: FolioReaderFontSize { + // TODO_SMF_DEPRECATE get { return FolioReader.shared.currentFontSize } set { FolioReader.shared.currentFontSize = newValue } } /// Check the current scroll direction open class var currentScrollDirection: Int { + // TODO_SMF_DEPRECATE get { return FolioReader.shared.currentScrollDirection } set { FolioReader.shared.currentScrollDirection = newValue } } /// Check current audio rate, the speed of speech voice open class var currentAudioRate: Int { + // TODO_SMF_DEPRECATE get { return FolioReader.shared.currentAudioRate } set { FolioReader.shared.currentAudioRate = newValue } } /// Check if reader is open and ready open class var isReaderReady : Bool { + // TODO_SMF_DEPRECATE return FolioReader.shared.isReaderReady } /// Save Reader state, book, page and scroll are saved open class func saveReaderState() { + // TODO_SMF_DEPRECATE FolioReader.shared.saveReaderState() } /// Closes and save the reader current instance open class func close() { + // TODO_SMF_DEPRECATE FolioReader.shared.close() } /// Check the current highlight style open class var currentHighlightStyle: Int { + // TODO_SMF_DEPRECATE get { return FolioReader.shared.currentHighlightStyle } set { FolioReader.shared.currentHighlightStyle = newValue } } /// Check if layout needs to change to fit Right To Left open class var needsRTLChange: Bool { + // TODO_SMF_DEPRECATE return FolioReader.shared.needsRTLChange } } @@ -338,17 +357,17 @@ extension FolioReader { // TODO_SMF_DEPRECATE and find a replacement for those functions. - /** - Called when the application will resign active - */ + /// Called when the application will resign active open class func applicationWillResignActive() { + // TODO_SMF_DEPRECATE + // TODO_DOC: no replacement required. Call `aFolioReader.saveReaderState()` instead FolioReader.shared.saveReaderState() } - /** - Called when the application will terminate - */ + /// Called when the application will terminate open class func applicationWillTerminate() { + // TODO_SMF_DEPRECATE + // TODO_DOC: no replacement required. Call `aFolioReader.saveReaderState()` instead FolioReader.shared.saveReaderState() } } @@ -356,10 +375,8 @@ extension FolioReader { // MARK: - Global Functions func isNight (_ f: T, _ l: T) -> T { - // TODO_SMF: remove fatal error // TODO_SMF_DEPRECATE // TODO_SMF_DOC: notify change - fatalError("should not use that function.") return (FolioReader.shared.nightMode == true ? f : l) } @@ -367,9 +384,7 @@ func isNight (_ f: T, _ l: T) -> T { func isDirection (_ vertical: T, _ horizontal: T, _ horizontalContentVertical: T? = nil) -> T { // TODO_SMF_DEPRECATE - // TODO_SMF: remove fatal error // TODO_SMF_DOC: notify change - fatalError("should not use that function.") let direction = (FolioReader.shared.readerContainer!.readerConfig.scrollDirection) switch direction { case .vertical, .defaultVertical: return vertical @@ -579,25 +594,26 @@ internal extension UIColor { self.init(red:red, green:green, blue:blue, alpha:alpha) } - /** - Hex string of a UIColor instance. - - - parameter rgba: Whether the alpha should be included. - */ - // from: https://github.com/yeahdongcn/UIColor-Hex-Swift - func hexString(_ includeAlpha: Bool) -> String { - var r: CGFloat = 0 - var g: CGFloat = 0 - var b: CGFloat = 0 - var a: CGFloat = 0 - self.getRed(&r, green: &g, blue: &b, alpha: &a) - - if (includeAlpha) { - return String(format: "#%02X%02X%02X%02X", Int(r * 255), Int(g * 255), Int(b * 255), Int(a * 255)) - } else { - return String(format: "#%02X%02X%02X", Int(r * 255), Int(g * 255), Int(b * 255)) - } - } + // + /// Hex string of a UIColor instance. + /// + /// from: https://github.com/yeahdongcn/UIColor-Hex-Swift + /// + /// - Parameter includeAlpha: Whether the alpha should be included. + /// - Returns: Hexa string + func hexString(_ includeAlpha: Bool) -> String { + var r: CGFloat = 0 + var g: CGFloat = 0 + var b: CGFloat = 0 + var a: CGFloat = 0 + self.getRed(&r, green: &g, blue: &b, alpha: &a) + + if (includeAlpha == true) { + return String(format: "#%02X%02X%02X%02X", Int(r * 255), Int(g * 255), Int(b * 255), Int(a * 255)) + } else { + return String(format: "#%02X%02X%02X", Int(r * 255), Int(g * 255), Int(b * 255)) + } + } // MARK: - color shades // https://gist.github.com/mbigatti/c6be210a6bbc0ff25972 @@ -867,9 +883,19 @@ internal extension UIImage { } internal extension UIViewController { - - func setCloseButton() { - let closeImage = UIImage(readerImageNamed: "icon-navbar-close")?.ignoreSystemTint() + + func setCloseButton() { + // TODO_SMF_DEPRECATE + guard let config = FolioReader.shared.readerContainer?.readerConfig else { + return + } + + self.setCloseButton(withConfiguration: config) + } + + func setCloseButton(withConfiguration readerConfig: FolioReaderConfig) { + // TODO_SMF_DOC + let closeImage = UIImage(readerImageNamed: "icon-navbar-close")?.ignoreSystemTint(withConfiguration: readerConfig) self.navigationItem.leftBarButtonItem = UIBarButtonItem(image: closeImage, style: .plain, target: self, action: #selector(dismiss as (Void) -> Void)) } diff --git a/Source/FolioReaderPage.swift b/Source/FolioReaderPage.swift index 1bcaa0ebd..956385e8f 100755 --- a/Source/FolioReaderPage.swift +++ b/Source/FolioReaderPage.swift @@ -188,7 +188,7 @@ open class FolioReaderPage: UICollectionViewCell, UIWebViewDelegate, UIGestureRe } } - let direction: ScrollDirection = FolioReader.needsRTLChange ? .positive(withConfiguration: self.readerConfig) : .negative(withConfiguration: self.readerConfig) + let direction: ScrollDirection = self.folioReader.needsRTLChange ? .positive(withConfiguration: self.readerConfig) : .negative(withConfiguration: self.readerConfig) if pageScrollDirection == direction && isScrolling && self.readerConfig.scrollDirection != .horizontalWithVerticalContent { scrollPageToBottom() @@ -499,7 +499,7 @@ open class FolioReaderPage: UICollectionViewCell, UIWebViewDelegate, UIGestureRe // MARK: ColorView fix for horizontal layout func refreshPageMode() { - if FolioReader.nightMode { + if (self.folioReader.nightMode == true) { // omit create webView and colorView let script = "document.documentElement.offsetHeight" let contentHeight = webView.stringByEvaluatingJavaScript(from: script) diff --git a/Source/FolioReaderPageIndicator.swift b/Source/FolioReaderPageIndicator.swift index f78fd0062..e4c53cd53 100644 --- a/Source/FolioReaderPageIndicator.swift +++ b/Source/FolioReaderPageIndicator.swift @@ -87,7 +87,7 @@ class FolioReaderPageIndicator: UIView { } fileprivate func reloadViewWithPage(_ page: Int) { - let pagesRemaining = FolioReader.needsRTLChange ? totalPages-(totalPages-page+1) : totalPages-page + let pagesRemaining = self.folioReader.needsRTLChange ? totalPages-(totalPages-page+1) : totalPages-page if pagesRemaining == 1 { pagesLabel.text = " " + self.readerConfig.localizedReaderOnePageLeft diff --git a/Source/FolioReaderPlayerMenu.swift b/Source/FolioReaderPlayerMenu.swift index 575698472..0148a1416 100644 --- a/Source/FolioReaderPlayerMenu.swift +++ b/Source/FolioReaderPlayerMenu.swift @@ -128,7 +128,7 @@ class FolioReaderPlayerMenu : UIViewController, SMSegmentViewDelegate, UIGestu playbackRate.addSegmentWithTitle("1½x", onSelectionImage: nil, offSelectionImage: nil) playbackRate.addSegmentWithTitle("2x", onSelectionImage: nil, offSelectionImage: nil) playbackRate.segmentTitleFont = UIFont(name: "Avenir-Light", size: 17)! - playbackRate.selectSegmentAtIndex(Int(FolioReader.currentAudioRate)) + playbackRate.selectSegmentAtIndex(Int(self.folioReader.currentAudioRate)) menuView.addSubview(playbackRate) @@ -189,9 +189,9 @@ class FolioReaderPlayerMenu : UIViewController, SMSegmentViewDelegate, UIGestu menuView.addSubview(style2line) // select the current style - style0.isSelected = (FolioReader.currentMediaOverlayStyle == .default) - style1.isSelected = (FolioReader.currentMediaOverlayStyle == .underline) - style2.isSelected = (FolioReader.currentMediaOverlayStyle == .textColor) + style0.isSelected = (self.folioReader.currentMediaOverlayStyle == .default) + style1.isSelected = (self.folioReader.currentMediaOverlayStyle == .underline) + style2.isSelected = (self.folioReader.currentMediaOverlayStyle == .textColor) if style0.isSelected { style0Bgd.backgroundColor = selectedColor } // hook up button actions @@ -235,7 +235,7 @@ class FolioReaderPlayerMenu : UIViewController, SMSegmentViewDelegate, UIGestu if let audioPlayer = self.folioReader.readerAudioPlayer , segmentView.tag == 2 { audioPlayer.setRate(index) - FolioReader.currentAudioRate = index + self.folioReader.currentAudioRate = index } } @@ -254,7 +254,7 @@ class FolioReaderPlayerMenu : UIViewController, SMSegmentViewDelegate, UIGestu } func changeStyle(_ sender: UIButton!) { - FolioReader.currentMediaOverlayStyle = MediaOverlayStyle(rawValue: sender.tag)! + self.folioReader.currentMediaOverlayStyle = MediaOverlayStyle(rawValue: sender.tag)! // select the proper style button for btn in styleOptionBtns { @@ -267,7 +267,7 @@ class FolioReaderPlayerMenu : UIViewController, SMSegmentViewDelegate, UIGestu // update the current page style if let currentPage = self.folioReader.readerCenter?.currentPage { - currentPage.webView.js("setMediaOverlayStyle(\"\(FolioReader.currentMediaOverlayStyle.className())\")") + currentPage.webView.js("setMediaOverlayStyle(\"\(self.folioReader.currentMediaOverlayStyle.className())\")") } } diff --git a/Source/FolioReaderQuoteShare.swift b/Source/FolioReaderQuoteShare.swift index 48b9ac170..e87f0a184 100644 --- a/Source/FolioReaderQuoteShare.swift +++ b/Source/FolioReaderQuoteShare.swift @@ -49,7 +49,8 @@ class FolioReaderQuoteShare: UIViewController { override func viewDidLoad() { super.viewDidLoad() - setCloseButton() + + self.setCloseButton(withConfiguration: self.readerConfig) configureNavBar() let titleAttrs = [NSForegroundColorAttributeName: self.readerConfig.tintColor] diff --git a/Source/FolioReaderWebView.swift b/Source/FolioReaderWebView.swift index 6a4d26b90..375f854e8 100644 --- a/Source/FolioReaderWebView.swift +++ b/Source/FolioReaderWebView.swift @@ -122,7 +122,7 @@ open class FolioReaderWebView : UIWebView { } func highlight(_ sender: UIMenuController?) { - let highlightAndReturn = js("highlightString('\(HighlightStyle.classForStyle(FolioReader.currentHighlightStyle))')") + let highlightAndReturn = js("highlightString('\(HighlightStyle.classForStyle(self.folioReader.currentHighlightStyle))')") let jsonData = highlightAndReturn?.data(using: String.Encoding.utf8) do { @@ -194,7 +194,7 @@ open class FolioReaderWebView : UIWebView { } func changeHighlightStyle(_ sender: UIMenuController?, style: HighlightStyle) { - FolioReader.currentHighlightStyle = style.rawValue + self.folioReader.currentHighlightStyle = style.rawValue if let updateId = js("setHighlightStyle('\(HighlightStyle.classForStyle(style.rawValue))')") { Highlight.updateById(withConfiguration: self.readerConfig, highlightId: updateId, type: style) diff --git a/Source/PageViewController.swift b/Source/PageViewController.swift index 46ec91b1e..3d563e2d7 100644 --- a/Source/PageViewController.swift +++ b/Source/PageViewController.swift @@ -64,7 +64,7 @@ class PageViewController: UIPageViewController { } } - setCloseButton() + self.setCloseButton(withConfiguration: self.readerConfig) } override func viewWillAppear(_ animated: Bool) { From 98554447bc795fe665bb2084e4f733c736f957e2 Mon Sep 17 00:00:00 2001 From: Kevin Delord Date: Fri, 31 Mar 2017 01:04:56 +0200 Subject: [PATCH 033/110] Remove todo --- Source/FolioReaderPage.swift | 1 - 1 file changed, 1 deletion(-) diff --git a/Source/FolioReaderPage.swift b/Source/FolioReaderPage.swift index 956385e8f..095794a86 100755 --- a/Source/FolioReaderPage.swift +++ b/Source/FolioReaderPage.swift @@ -468,7 +468,6 @@ open class FolioReaderPage: UICollectionViewCell, UIWebViewDelegate, UIGestureRe - parameter identifier: The identifier */ func audioMarkID(_ identifier: String) { - // TODO_SMF: replace shared readerContainer guard let currentPage = self.folioReader.readerCenter?.currentPage else { return } From d878439ecd2ebd3b9bf50f909ad49f38b566ff6a Mon Sep 17 00:00:00 2001 From: Kevin Delord Date: Fri, 31 Mar 2017 18:20:42 +0200 Subject: [PATCH 034/110] Add TODO --- Source/FolioReaderCenter.swift | 1 + Source/FolioReaderSharingProvider.swift | 4 ---- 2 files changed, 1 insertion(+), 4 deletions(-) diff --git a/Source/FolioReaderCenter.swift b/Source/FolioReaderCenter.swift index 978c0529a..62cd8ca78 100755 --- a/Source/FolioReaderCenter.swift +++ b/Source/FolioReaderCenter.swift @@ -9,6 +9,7 @@ import UIKit import ZFDragableModalTransition +// TODO_SMF: remove global variables let reuseIdentifier = "Cell" var pageWidth: CGFloat! var pageHeight: CGFloat! diff --git a/Source/FolioReaderSharingProvider.swift b/Source/FolioReaderSharingProvider.swift index d853d418b..f390995e0 100644 --- a/Source/FolioReaderSharingProvider.swift +++ b/Source/FolioReaderSharingProvider.swift @@ -38,8 +38,4 @@ class FolioReaderSharingProvider: UIActivityItemProvider { return text } - -// func activityViewController(activityViewController: UIActivityViewController, thumbnailImageForActivityType activityType: String?, suggestedSize size: CGSize) -> UIImage? { -// -// } } From 5ed89780b61038a56972f76452c5dfbf1a627794 Mon Sep 17 00:00:00 2001 From: Kevin Delord Date: Fri, 31 Mar 2017 18:30:47 +0200 Subject: [PATCH 035/110] PR: refactor guard --- Source/FolioReaderCenter.swift | 6 +----- Source/FolioReaderPage.swift | 2 +- Source/FolioReaderWebView.swift | 7 ++++--- 3 files changed, 6 insertions(+), 9 deletions(-) diff --git a/Source/FolioReaderCenter.swift b/Source/FolioReaderCenter.swift index ebb6cb1b9..5b4a480c6 100755 --- a/Source/FolioReaderCenter.swift +++ b/Source/FolioReaderCenter.swift @@ -815,11 +815,7 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo for item in self.book.flatTableOfContents { guard let reference = self.book.spine.spineReferences[safe: currentPageNumber-1], - let resource = item.resource else { - return nil - } - - guard + let resource = item.resource, (resource == reference.resource), let title = item.title else { // TODO_SMF_CHECK: check if this really works fine (or if it was working anyway). diff --git a/Source/FolioReaderPage.swift b/Source/FolioReaderPage.swift index ee1cf1934..68495692f 100755 --- a/Source/FolioReaderPage.swift +++ b/Source/FolioReaderPage.swift @@ -65,7 +65,7 @@ open class FolioReaderPage: UICollectionViewCell, UIWebViewDelegate, UIGestureRe NotificationCenter.default.addObserver(self, selector: #selector(refreshPageMode), name: NSNotification.Name(rawValue: "needRefreshPageMode"), object: nil) if webView == nil { - webView = FolioReaderWebView(frame: webViewFrame(), readerConfig: self.readerConfig, readerContainer: self.readerContainer) + webView = FolioReaderWebView(frame: webViewFrame(), readerContainer: self.readerContainer) webView.autoresizingMask = [.flexibleWidth, .flexibleHeight] webView.dataDetectorTypes = .link webView.scrollView.showsVerticalScrollIndicator = false diff --git a/Source/FolioReaderWebView.swift b/Source/FolioReaderWebView.swift index 1354c09dd..6bec20087 100644 --- a/Source/FolioReaderWebView.swift +++ b/Source/FolioReaderWebView.swift @@ -14,7 +14,9 @@ open class FolioReaderWebView : UIWebView { var isShare = false var isOneWord = false - fileprivate var readerConfig : FolioReaderConfig + fileprivate var readerConfig : FolioReaderConfig { + return self.readerContainer.readerConfig + } fileprivate var readerContainer : FolioReaderContainer fileprivate var book : FRBook { return self.readerContainer.book @@ -24,8 +26,7 @@ open class FolioReaderWebView : UIWebView { fatalError("use init(frame:readerConfig:book:) instead.") } - init(frame: CGRect, readerConfig: FolioReaderConfig, readerContainer: FolioReaderContainer) { - self.readerConfig = readerConfig + init(frame: CGRect, readerContainer: FolioReaderContainer) { self.readerContainer = readerContainer super.init(frame: frame) From c256dfc7189ab1e76682e31f4b51f0ad1d11fdd3 Mon Sep 17 00:00:00 2001 From: Kevin Delord Date: Fri, 31 Mar 2017 18:34:31 +0200 Subject: [PATCH 036/110] Refactor: isScrolling --- Source/FolioReaderCenter.swift | 8 ++++---- Source/FolioReaderPage.swift | 2 +- 2 files changed, 5 insertions(+), 5 deletions(-) diff --git a/Source/FolioReaderCenter.swift b/Source/FolioReaderCenter.swift index f04550cae..d8a1b0059 100755 --- a/Source/FolioReaderCenter.swift +++ b/Source/FolioReaderCenter.swift @@ -17,7 +17,6 @@ var previousPageNumber: Int! var currentPageNumber: Int! var nextPageNumber: Int! var pageScrollDirection = ScrollDirection() -var isScrolling = false /// Protocol which is used from `FolioReaderCenter`s. @objc public protocol FolioReaderCenterDelegate: class { @@ -67,6 +66,7 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo var recentlyScrolledDelay = 2.0 // 2 second delay until we clear recentlyScrolled var recentlyScrolledTimer: Timer! var scrollScrubber: ScrollScrubber? + var isScrolling = false fileprivate var screenBounds: CGRect! fileprivate var pointNow = CGPoint.zero @@ -991,7 +991,7 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo // MARK: - ScrollView Delegate open func scrollViewWillBeginDragging(_ scrollView: UIScrollView) { - isScrolling = true + self.isScrolling = true clearRecentlyScrolled() recentlyScrolled = true pointNow = scrollView.contentOffset @@ -1051,7 +1051,7 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo } open func scrollViewDidEndDecelerating(_ scrollView: UIScrollView) { - isScrolling = false + self.isScrolling = false if (readerConfig.scrollDirection == .horizontalWithVerticalContent), let cell = ((scrollView.superview as? UIWebView)?.delegate as? FolioReaderPage) { @@ -1188,7 +1188,7 @@ extension FolioReaderCenter: FolioReaderPageDelegate { if currentPageNumber == pageNumber && pageOffset > 0 { page.scrollPageToOffset(pageOffset!, animated: false) } - } else if !isScrolling && self.readerContainer.folioReader.needsRTLChange { + } else if (self.isScrolling == false && self.readerContainer.folioReader.needsRTLChange == true) { page.scrollPageToBottom() } } else if isFirstLoad { diff --git a/Source/FolioReaderPage.swift b/Source/FolioReaderPage.swift index 4082fa344..a8460b389 100755 --- a/Source/FolioReaderPage.swift +++ b/Source/FolioReaderPage.swift @@ -190,7 +190,7 @@ open class FolioReaderPage: UICollectionViewCell, UIWebViewDelegate, UIGestureRe let direction: ScrollDirection = self.folioReader.needsRTLChange ? .positive(withConfiguration: self.readerConfig) : .negative(withConfiguration: self.readerConfig) - if pageScrollDirection == direction && isScrolling && self.readerConfig.scrollDirection != .horizontalWithVerticalContent { + if (pageScrollDirection == direction && self.folioReader.readerCenter?.isScrolling == true && self.readerConfig.scrollDirection != .horizontalWithVerticalContent) { scrollPageToBottom() } From f6f509ce1945f859a3e502a53dce6a93559fc687 Mon Sep 17 00:00:00 2001 From: Kevin Delord Date: Fri, 31 Mar 2017 18:36:34 +0200 Subject: [PATCH 037/110] Refactor: pageScrollDirection --- Source/FolioReaderCenter.swift | 8 ++++---- Source/FolioReaderPage.swift | 2 +- 2 files changed, 5 insertions(+), 5 deletions(-) diff --git a/Source/FolioReaderCenter.swift b/Source/FolioReaderCenter.swift index d8a1b0059..54230a7ef 100755 --- a/Source/FolioReaderCenter.swift +++ b/Source/FolioReaderCenter.swift @@ -16,7 +16,6 @@ var pageHeight: CGFloat! var previousPageNumber: Int! var currentPageNumber: Int! var nextPageNumber: Int! -var pageScrollDirection = ScrollDirection() /// Protocol which is used from `FolioReaderCenter`s. @objc public protocol FolioReaderCenterDelegate: class { @@ -67,6 +66,7 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo var recentlyScrolledTimer: Timer! var scrollScrubber: ScrollScrubber? var isScrolling = false + var pageScrollDirection = ScrollDirection() fileprivate var screenBounds: CGRect! fileprivate var pointNow = CGPoint.zero @@ -657,7 +657,7 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo let first = indexPaths.first! as IndexPath let last = indexPaths.last! as IndexPath - switch pageScrollDirection { + switch self.pageScrollDirection { case .up: if (first as NSIndexPath).compare(last) == .orderedAscending { indexPath = last @@ -1044,9 +1044,9 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo } if (scrollView.contentOffset.forDirection(withConfiguration: self.readerConfig) < pointNow.forDirection(withConfiguration: self.readerConfig)) { - pageScrollDirection = .negative(withConfiguration: self.readerConfig) + self.pageScrollDirection = .negative(withConfiguration: self.readerConfig) } else { - pageScrollDirection = .positive(withConfiguration: self.readerConfig) + self.pageScrollDirection = .positive(withConfiguration: self.readerConfig) } } diff --git a/Source/FolioReaderPage.swift b/Source/FolioReaderPage.swift index a8460b389..9d3b7e462 100755 --- a/Source/FolioReaderPage.swift +++ b/Source/FolioReaderPage.swift @@ -190,7 +190,7 @@ open class FolioReaderPage: UICollectionViewCell, UIWebViewDelegate, UIGestureRe let direction: ScrollDirection = self.folioReader.needsRTLChange ? .positive(withConfiguration: self.readerConfig) : .negative(withConfiguration: self.readerConfig) - if (pageScrollDirection == direction && self.folioReader.readerCenter?.isScrolling == true && self.readerConfig.scrollDirection != .horizontalWithVerticalContent) { + if (self.folioReader.readerCenter?.pageScrollDirection == direction && self.folioReader.readerCenter?.isScrolling == true && self.readerConfig.scrollDirection != .horizontalWithVerticalContent) { scrollPageToBottom() } From 63a7aad40547b41a3757f1f97b700e220c01698d Mon Sep 17 00:00:00 2001 From: Kevin Delord Date: Fri, 31 Mar 2017 19:21:59 +0200 Subject: [PATCH 038/110] Refactor: currentPageNumber --- Source/FolioReaderCenter.swift | 91 +++++++++++++-------------- Source/FolioReaderChapterList.swift | 2 +- Source/FolioReaderHighlightList.swift | 5 +- Source/FolioReaderKit.swift | 2 +- Source/FolioReaderWebView.swift | 8 ++- Source/Models/Highlight+Helper.swift | 29 ++++++--- 6 files changed, 74 insertions(+), 63 deletions(-) diff --git a/Source/FolioReaderCenter.swift b/Source/FolioReaderCenter.swift index 54230a7ef..d3b994510 100755 --- a/Source/FolioReaderCenter.swift +++ b/Source/FolioReaderCenter.swift @@ -13,9 +13,6 @@ import ZFDragableModalTransition let reuseIdentifier = "Cell" var pageWidth: CGFloat! var pageHeight: CGFloat! -var previousPageNumber: Int! -var currentPageNumber: Int! -var nextPageNumber: Int! /// Protocol which is used from `FolioReaderCenter`s. @objc public protocol FolioReaderCenterDelegate: class { @@ -67,6 +64,9 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo var scrollScrubber: ScrollScrubber? var isScrolling = false var pageScrollDirection = ScrollDirection() + var nextPageNumber: Int = 0 + var previousPageNumber: Int = 0 + var currentPageNumber: Int = 0 fileprivate var screenBounds: CGRect! fileprivate var pointNow = CGPoint.zero @@ -272,12 +272,12 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo let position = FolioReader.defaults.value(forKey: bookId) as? NSDictionary, let pageNumber = position["pageNumber"] as? Int, (pageNumber > 0) else { - currentPageNumber = 1 + self.currentPageNumber = 1 return } self.changePageWith(page: pageNumber) - currentPageNumber = pageNumber + self.currentPageNumber = pageNumber } // MARK: Change page progressive direction @@ -314,7 +314,7 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo self.collectionViewLayout.scrollDirection = .direction(withConfiguration: self.readerConfig) self.currentPage?.setNeedsLayout() self.collectionView.collectionViewLayout.invalidateLayout() - self.collectionView.setContentOffset(frameForPage(currentPageNumber).origin, animated: false) + self.collectionView.setContentOffset(frameForPage(self.currentPageNumber).origin, animated: false) // Page progressive direction self.setCollectionViewProgressiveDirection() @@ -510,7 +510,7 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo CGSize(width: pageWidth * CGFloat(self.totalPages), height: pageHeight), CGSize(width: pageWidth * CGFloat(self.totalPages), height: pageHeight) ) - self.collectionView.setContentOffset(self.frameForPage(currentPageNumber).origin, animated: false) + self.collectionView.setContentOffset(self.frameForPage(self.currentPageNumber).origin, animated: false) self.collectionView.collectionViewLayout.invalidateLayout() // Adjust internal page offset @@ -555,10 +555,10 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo return } - self.collectionView.scrollToItem(at: IndexPath(row: currentPageNumber - 1, section: 0), at: UICollectionViewScrollPosition(), animated: false) - if currentPageNumber+1 >= totalPages { + self.collectionView.scrollToItem(at: IndexPath(row: self.currentPageNumber - 1, section: 0), at: UICollectionViewScrollPosition(), animated: false) + if ((self.currentPageNumber + 1) >= totalPages) { UIView.animate(withDuration: duration, animations: { - self.collectionView.setContentOffset(self.frameForPage(currentPageNumber).origin, animated: false) + self.collectionView.setContentOffset(self.frameForPage(self.currentPageNumber).origin, animated: false) }) } } @@ -594,17 +594,17 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo func updateCurrentPage(_ page: FolioReaderPage? = nil, completion: (() -> Void)? = nil) { if let page = page { currentPage = page - previousPageNumber = page.pageNumber-1 - currentPageNumber = page.pageNumber + self.previousPageNumber = page.pageNumber-1 + self.currentPageNumber = page.pageNumber } else { let currentIndexPath = getCurrentIndexPath() currentPage = collectionView.cellForItem(at: currentIndexPath) as? FolioReaderPage - previousPageNumber = (currentIndexPath as NSIndexPath).row - currentPageNumber = (currentIndexPath as NSIndexPath).row+1 + self.previousPageNumber = (currentIndexPath as NSIndexPath).row + self.currentPageNumber = (currentIndexPath as NSIndexPath).row+1 } - nextPageNumber = currentPageNumber+1 <= totalPages ? currentPageNumber+1 : currentPageNumber + self.nextPageNumber = (((self.currentPageNumber + 1) <= totalPages) ? (self.currentPageNumber + 1) : self.currentPageNumber) // // Set navigation title // if let chapterName = getCurrentChapterName() { @@ -686,7 +686,7 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo } func changePageWith(page: Int, andFragment fragment: String, animated: Bool = false, completion: (() -> Void)? = nil) { - if currentPageNumber == page { + if (self.currentPageNumber == page) { if let currentPage = currentPage , fragment != "" { currentPage.handleAnchor(fragment, avoidBeginningAnchors: true, animated: animated) } @@ -758,17 +758,17 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo } func isLastPage() -> Bool{ - return currentPageNumber == nextPageNumber + return (currentPageNumber == self.nextPageNumber) } func changePageToNext(_ completion: (() -> Void)? = nil) { - changePageWith(page: nextPageNumber, animated: true) { () -> Void in + changePageWith(page: self.nextPageNumber, animated: true) { () -> Void in completion?() } } func changePageToPrevious(_ completion: (() -> Void)? = nil) { - changePageWith(page: previousPageNumber, animated: true) { () -> Void in + changePageWith(page: self.previousPageNumber, animated: true) { () -> Void in completion?() } } @@ -804,39 +804,38 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo /** Find and return the current chapter resource. */ - func getCurrentChapter() -> FRResource? { - if let currentPageNumber = currentPageNumber { - for item in self.book.flatTableOfContents { - if let reference = self.book.spine.spineReferences[safe: currentPageNumber-1], let resource = item.resource - , resource == reference.resource { - return item.resource - } - } - } + func getCurrentChapter() -> FRResource? { + for item in self.book.flatTableOfContents { + if + let reference = self.book.spine.spineReferences[safe: (self.currentPageNumber - 1)], + let resource = item.resource, + (resource == reference.resource) { + return item.resource + } + } return nil } /** Find and return the current chapter name. */ - func getCurrentChapterName() -> String? { - if let currentPageNumber = currentPageNumber { - for item in self.book.flatTableOfContents { - guard - let reference = self.book.spine.spineReferences[safe: currentPageNumber-1], - let resource = item.resource, - (resource == reference.resource), - let title = item.title else { - // TODO_SMF_CHECK: check if this really works fine (or if it was working anyway). - // Select text -> share. - return nil - } + func getCurrentChapterName() -> String? { + for item in self.book.flatTableOfContents { + guard + let reference = self.book.spine.spineReferences[safe: (self.currentPageNumber - 1)], + let resource = item.resource, + (resource == reference.resource), + let title = item.title else { + // TODO_SMF_CHECK: check if this really works fine (or if it was working anyway). + // Select text -> share. + return nil + } - return title - } - } - return nil - } + return title + } + + return nil + } // MARK: Public page methods @@ -1185,7 +1184,7 @@ extension FolioReaderCenter: FolioReaderPageDelegate { updateCurrentPage(page) isFirstLoad = false - if currentPageNumber == pageNumber && pageOffset > 0 { + if (self.currentPageNumber == pageNumber && pageOffset > 0) { page.scrollPageToOffset(pageOffset!, animated: false) } } else if (self.isScrolling == false && self.readerContainer.folioReader.needsRTLChange == true) { diff --git a/Source/FolioReaderChapterList.swift b/Source/FolioReaderChapterList.swift index 6893ff88c..65e8a8ab1 100755 --- a/Source/FolioReaderChapterList.swift +++ b/Source/FolioReaderChapterList.swift @@ -92,7 +92,7 @@ class FolioReaderChapterList : UITableViewController { // Mark current reading chapter if - let currentPageNumber = currentPageNumber, + let currentPageNumber = self.folioReader.readerCenter?.currentPageNumber, let reference = self.book.spine.spineReferences[safe: currentPageNumber - 1], (tocReference.resource != nil) { let resource = reference.resource diff --git a/Source/FolioReaderHighlightList.swift b/Source/FolioReaderHighlightList.swift index 4737d0883..667960d55 100644 --- a/Source/FolioReaderHighlightList.swift +++ b/Source/FolioReaderHighlightList.swift @@ -153,8 +153,9 @@ class FolioReaderHighlightList : UITableViewController { if editingStyle == .delete { let highlight = highlights[(indexPath as NSIndexPath).row] - if (highlight.page == currentPageNumber), let page = self.folioReader.readerCenter?.currentPage { - Highlight.removeFromHTMLById(withinPage: page, highlightId: highlight.highlightId) // Remove from HTML + if (highlight.page == self.folioReader.readerCenter?.currentPageNumber), + let page = self.folioReader.readerCenter?.currentPage { + Highlight.removeFromHTMLById(withinPage: page, highlightId: highlight.highlightId) // Remove from HTML } highlight.remove(withConfiguration: self.readerConfig) // Remove from Database diff --git a/Source/FolioReaderKit.swift b/Source/FolioReaderKit.swift index 56e183cdc..5ef0036d8 100755 --- a/Source/FolioReaderKit.swift +++ b/Source/FolioReaderKit.swift @@ -247,7 +247,7 @@ extension FolioReader { } let position = [ - "pageNumber": currentPageNumber, + "pageNumber": (self.readerCenter?.currentPageNumber ?? 0), "pageOffsetX": currentPage.webView.scrollView.contentOffset.x, "pageOffsetY": currentPage.webView.scrollView.contentOffset.y ] as [String : Any] diff --git a/Source/FolioReaderWebView.swift b/Source/FolioReaderWebView.swift index 72eefe4fd..64fa6e12b 100644 --- a/Source/FolioReaderWebView.swift +++ b/Source/FolioReaderWebView.swift @@ -142,12 +142,14 @@ open class FolioReaderWebView : UIWebView { guard let html = js("getHTML()"), let identifier = dic["id"], - let bookId = (self.book.name as? NSString)?.deletingPathExtension, - let highlight = Highlight.matchHighlight(html, andId: identifier, startOffset: startOffset, endOffset: endOffset, bookId: bookId) else { + let bookId = (self.book.name as? NSString)?.deletingPathExtension else { return } - highlight.persist(withConfiguration: self.readerConfig) + let pageNumber = (self.readerContainer.folioReader.readerCenter?.currentPageNumber ?? 0) + let match = Highlight.MatchingHighlight(text: html, id: identifier, startOffset: startOffset, endOffset: endOffset, bookId: bookId, currentPage: pageNumber) + let highlight = Highlight.matchHighlight(match) + highlight?.persist(withConfiguration: self.readerConfig) } catch { print("Could not receive JSON") diff --git a/Source/Models/Highlight+Helper.swift b/Source/Models/Highlight+Helper.swift index 27b21d583..dc5d89c89 100644 --- a/Source/Models/Highlight+Helper.swift +++ b/Source/Models/Highlight+Helper.swift @@ -276,34 +276,43 @@ extension Highlight { extension Highlight { + public struct MatchingHighlight { + var text: String + var id: String + var startOffset: String + var endOffset: String + var bookId: String + var currentPage: Int + } + /** Match a highlight on string. */ - public static func matchHighlight(_ text: String, andId id: String, startOffset: String, endOffset: String, bookId: String) -> Highlight? { - let pattern = "((.|\\s)*?)" + public static func matchHighlight(_ matchingHighlight: MatchingHighlight) -> Highlight? { + let pattern = "((.|\\s)*?)" let regex = try? NSRegularExpression(pattern: pattern, options: []) - let matches = regex?.matches(in: text, options: [], range: NSRange(location: 0, length: text.utf16.count)) - let str = (text as NSString) + let matches = regex?.matches(in: matchingHighlight.text, options: [], range: NSRange(location: 0, length: matchingHighlight.text.utf16.count)) + let str = (matchingHighlight.text as NSString) let mapped = matches?.map { (match) -> Highlight in var contentPre = str.substring(with: NSRange(location: match.range.location-kHighlightRange, length: kHighlightRange)) var contentPost = str.substring(with: NSRange(location: match.range.location + match.range.length, length: kHighlightRange)) // Normalize string before save - contentPre = Highlight.subString(ofContent: contentPre, fromRangeOfString: ">", withPattern: "((?=[^>]*$)(.|\\s)*$)") + contentPre = Highlight.subString(ofContent: contentPre, fromRangeOfString: ">", withPattern: "((?=[^>]*$)(.|\\s)*$)") contentPost = Highlight.subString(ofContent: contentPost, fromRangeOfString: "<", withPattern: "^((.|\\s)*?)(?=<)") let highlight = Highlight() - highlight.highlightId = id + highlight.highlightId = matchingHighlight.id highlight.type = HighlightStyle.styleForClass(str.substring(with: match.rangeAt(1))).rawValue highlight.date = Foundation.Date() highlight.content = Highlight.removeSentenceSpam(str.substring(with: match.rangeAt(2))) highlight.contentPre = Highlight.removeSentenceSpam(contentPre) highlight.contentPost = Highlight.removeSentenceSpam(contentPost) - highlight.page = currentPageNumber - highlight.bookId = bookId - highlight.startOffset = (Int(startOffset) ?? -1) - highlight.endOffset = (Int(endOffset) ?? -1) + highlight.page = matchingHighlight.currentPage + highlight.bookId = matchingHighlight.bookId + highlight.startOffset = (Int(matchingHighlight.startOffset) ?? -1) + highlight.endOffset = (Int(matchingHighlight.endOffset) ?? -1) return highlight } From 17c35b8a1396e349ca38d03ab92a888c6e8cc2db Mon Sep 17 00:00:00 2001 From: Kevin Delord Date: Fri, 31 Mar 2017 19:25:03 +0200 Subject: [PATCH 039/110] Refactor: reuseIdentifier --- Source/FolioReaderCenter.swift | 5 ++--- Source/FolioReaderChapterList.swift | 5 ++--- Source/FolioReaderHighlightList.swift | 4 ++-- Source/FolioReaderKit.swift | 1 + Source/FolioReaderQuoteShare.swift | 4 ++-- 5 files changed, 9 insertions(+), 10 deletions(-) diff --git a/Source/FolioReaderCenter.swift b/Source/FolioReaderCenter.swift index d3b994510..69fd105d1 100755 --- a/Source/FolioReaderCenter.swift +++ b/Source/FolioReaderCenter.swift @@ -10,7 +10,6 @@ import UIKit import ZFDragableModalTransition // TODO_SMF: remove global variables -let reuseIdentifier = "Cell" var pageWidth: CGFloat! var pageHeight: CGFloat! @@ -153,7 +152,7 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo } // Register cell classes - collectionView!.register(FolioReaderPage.self, forCellWithReuseIdentifier: reuseIdentifier) + collectionView!.register(FolioReaderPage.self, forCellWithReuseIdentifier: kReuseCellIdentifier) // Configure navigation bar and layout automaticallyAdjustsScrollViewInsets = false @@ -402,7 +401,7 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo } open func collectionView(_ collectionView: UICollectionView, cellForItemAt indexPath: IndexPath) -> UICollectionViewCell { - var reuseableCell = collectionView.dequeueReusableCell(withReuseIdentifier: reuseIdentifier, for: indexPath) as? FolioReaderPage + var reuseableCell = collectionView.dequeueReusableCell(withReuseIdentifier: kReuseCellIdentifier, for: indexPath) as? FolioReaderPage guard let pageCell = reuseableCell else { return UICollectionViewCell() } diff --git a/Source/FolioReaderChapterList.swift b/Source/FolioReaderChapterList.swift index 65e8a8ab1..b53b6e65a 100755 --- a/Source/FolioReaderChapterList.swift +++ b/Source/FolioReaderChapterList.swift @@ -8,7 +8,6 @@ import UIKit - /// Table Of Contents delegate @objc protocol FolioReaderChapterListDelegate: class { /** @@ -47,7 +46,7 @@ class FolioReaderChapterList : UITableViewController { super.viewDidLoad() // Register cell classes - self.tableView.register(FolioReaderChapterListCell.self, forCellReuseIdentifier: reuseIdentifier) + self.tableView.register(FolioReaderChapterListCell.self, forCellReuseIdentifier: kReuseCellIdentifier) self.tableView.separatorInset = UIEdgeInsets.zero self.tableView.backgroundColor = self.folioReader.isNight(self.readerConfig.nightModeMenuBackground, self.readerConfig.menuBackgroundColor) self.tableView.separatorColor = self.folioReader.isNight(self.readerConfig.nightModeSeparatorColor, self.readerConfig.menuSeparatorColor) @@ -70,7 +69,7 @@ class FolioReaderChapterList : UITableViewController { } override func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell { - let cell = tableView.dequeueReusableCell(withIdentifier: reuseIdentifier, for: indexPath) as! FolioReaderChapterListCell + let cell = tableView.dequeueReusableCell(withIdentifier: kReuseCellIdentifier, for: indexPath) as! FolioReaderChapterListCell cell.setup(withConfiguration: self.readerConfig) let tocReference = tocItems[(indexPath as NSIndexPath).row] diff --git a/Source/FolioReaderHighlightList.swift b/Source/FolioReaderHighlightList.swift index 667960d55..470b5b438 100644 --- a/Source/FolioReaderHighlightList.swift +++ b/Source/FolioReaderHighlightList.swift @@ -28,7 +28,7 @@ class FolioReaderHighlightList : UITableViewController { override func viewDidLoad() { super.viewDidLoad() - self.tableView.register(UITableViewCell.self, forCellReuseIdentifier: reuseIdentifier) + self.tableView.register(UITableViewCell.self, forCellReuseIdentifier: kReuseCellIdentifier) self.tableView.separatorInset = UIEdgeInsets.zero self.tableView.backgroundColor = self.folioReader.isNight(self.readerConfig.nightModeMenuBackground, self.readerConfig.menuBackgroundColor) self.tableView.separatorColor = self.folioReader.isNight(self.readerConfig.nightModeSeparatorColor, self.readerConfig.menuSeparatorColor) @@ -52,7 +52,7 @@ class FolioReaderHighlightList : UITableViewController { } override func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell { - let cell = tableView.dequeueReusableCell(withIdentifier: reuseIdentifier, for: indexPath) + let cell = tableView.dequeueReusableCell(withIdentifier: kReuseCellIdentifier, for: indexPath) cell.backgroundColor = UIColor.clear let highlight = highlights[(indexPath as NSIndexPath).row] diff --git a/Source/FolioReaderKit.swift b/Source/FolioReaderKit.swift index 5ef0036d8..79b766142 100755 --- a/Source/FolioReaderKit.swift +++ b/Source/FolioReaderKit.swift @@ -21,6 +21,7 @@ internal let kCurrentScrollDirection = "com.folioreader.kCurrentScrollDirection" internal let kNightMode = "com.folioreader.kNightMode" internal let kCurrentTOCMenu = "com.folioreader.kCurrentTOCMenu" internal let kHighlightRange = 30 +internal let kReuseCellIdentifier = "com.folioreader.Cell.ReuseIdentifier" /// Defines the media overlay and TTS selection /// diff --git a/Source/FolioReaderQuoteShare.swift b/Source/FolioReaderQuoteShare.swift index e87f0a184..961ec16dd 100644 --- a/Source/FolioReaderQuoteShare.swift +++ b/Source/FolioReaderQuoteShare.swift @@ -176,7 +176,7 @@ class FolioReaderQuoteShare: UIViewController { } // Register cell classes - collectionView!.register(UICollectionViewCell.self, forCellWithReuseIdentifier: reuseIdentifier) + collectionView?.register(UICollectionViewCell.self, forCellWithReuseIdentifier: kReuseCellIdentifier) // Create images dataSource = self.readerConfig.quoteCustomBackgrounds @@ -318,7 +318,7 @@ extension FolioReaderQuoteShare: UICollectionViewDataSource { } func collectionView(_ collectionView: UICollectionView, cellForItemAt indexPath: IndexPath) -> UICollectionViewCell { - let cell = collectionView.dequeueReusableCell(withReuseIdentifier: reuseIdentifier, for: indexPath) + let cell = collectionView.dequeueReusableCell(withReuseIdentifier: kReuseCellIdentifier, for: indexPath) let imageView: UIImageView! let tag = 9999 From a843c8178f5dc21fa5b6f40ecf8e1760920ee5f5 Mon Sep 17 00:00:00 2001 From: Kevin Delord Date: Fri, 31 Mar 2017 19:39:45 +0200 Subject: [PATCH 040/110] Refactor: pageheight and pageWidth --- Source/FolioReaderCenter.swift | 111 +++++++++++++++------------------ Source/ScrollScrubber.swift | 36 ++++++----- 2 files changed, 72 insertions(+), 75 deletions(-) diff --git a/Source/FolioReaderCenter.swift b/Source/FolioReaderCenter.swift index 69fd105d1..dbbb46efe 100755 --- a/Source/FolioReaderCenter.swift +++ b/Source/FolioReaderCenter.swift @@ -9,28 +9,20 @@ import UIKit import ZFDragableModalTransition -// TODO_SMF: remove global variables -var pageWidth: CGFloat! -var pageHeight: CGFloat! - /// Protocol which is used from `FolioReaderCenter`s. @objc public protocol FolioReaderCenterDelegate: class { - /** - Notifies that a page appeared. This is triggered is a page is chosen and displayed. - - - parameter page: The appeared page - */ + /// Notifies that a page appeared. This is triggered is a page is chosen and displayed. + /// + /// - Parameter page: The appeared page @objc optional func pageDidAppear(_ page: FolioReaderPage) - /** - Passes and returns the HTML content as `String`. Implement this method if you want to modify the HTML content of a `FolioReaderPage`. - - - parameter page: The `FolioReaderPage` - - parameter htmlContent: The current HTML content as `String` - - - returns: The adjusted HTML content as `String`. This is the content which will be loaded into the given `FolioReaderPage` - */ + /// Passes and returns the HTML content as `String`. Implement this method if you want to modify the HTML content of a `FolioReaderPage`. + /// + /// - Parameters: + /// - page: The `FolioReaderPage`. + /// - htmlContent: The current HTML content as `String`. + /// - Returns: The adjusted HTML content as `String`. This is the content which will be loaded into the given `FolioReaderPage`. @objc optional func htmlContentForPage(_ page: FolioReaderPage, htmlContent: String) -> String } @@ -66,6 +58,8 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo var nextPageNumber: Int = 0 var previousPageNumber: Int = 0 var currentPageNumber: Int = 0 + var pageWidth: CGFloat = 0.0 + var pageHeight: CGFloat = 0.0 fileprivate var screenBounds: CGRect! fileprivate var pointNow = CGPoint.zero @@ -215,7 +209,7 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo fileprivate func frameForScrollScrubber() -> CGRect { let scrubberY: CGFloat = ((self.readerConfig.shouldHideNavigationOnTap == true || self.readerConfig.hideBars == true) ? 50 : 74) - return CGRect(x: pageWidth + 10, y: scrubberY, width: 40, height: pageHeight - 100) + return CGRect(x: self.pageWidth + 10, y: scrubberY, width: 40, height: (self.pageHeight - 100)) } func configureNavBar() { @@ -328,9 +322,9 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo var pageOffset = (pageScrollView.contentSize.forDirection(withConfiguration: self.readerConfig) * self.pageOffsetRate) // Fix the offset for paged scroll - if (self.readerConfig.scrollDirection == .horizontal) { - let page = round(pageOffset / pageWidth) - pageOffset = page * pageWidth + if (self.readerConfig.scrollDirection == .horizontal && self.pageWidth != 0) { + let page = round(pageOffset / self.pageWidth) + pageOffset = (page * self.pageWidth) } let pageOffsetPoint = self.readerConfig.isDirection(CGPoint(x: 0, y: pageOffset), CGPoint(x: pageOffset, y: 0)) @@ -505,9 +499,9 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo // Adjust collectionView self.collectionView.contentSize = self.readerConfig.isDirection( - CGSize(width: pageWidth, height: pageHeight * CGFloat(self.totalPages)), - CGSize(width: pageWidth * CGFloat(self.totalPages), height: pageHeight), - CGSize(width: pageWidth * CGFloat(self.totalPages), height: pageHeight) + CGSize(width: self.pageWidth, height: self.pageHeight * CGFloat(self.totalPages)), + CGSize(width: self.pageWidth * CGFloat(self.totalPages), height: self.pageHeight), + CGSize(width: self.pageWidth * CGFloat(self.totalPages), height: self.pageHeight) ) self.collectionView.setContentOffset(self.frameForPage(self.currentPageNumber).origin, animated: false) self.collectionView.collectionViewLayout.invalidateLayout() @@ -540,9 +534,9 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo var pageOffset = (currentPage.webView.scrollView.contentSize.forDirection(withConfiguration: self.readerConfig) * pageOffsetRate) // Fix the offset for paged scroll - if (self.readerConfig.scrollDirection == .horizontal && pageWidth != 0) { - let page = round(pageOffset / pageWidth) - pageOffset = page * pageWidth + if (self.readerConfig.scrollDirection == .horizontal && self.pageWidth != 0) { + let page = round(pageOffset / self.pageWidth) + pageOffset = page * self.pageWidth } let pageOffsetPoint = self.readerConfig.isDirection(CGPoint(x: 0, y: pageOffset), CGPoint(x: pageOffset, y: 0)) @@ -566,20 +560,20 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo func setPageSize(_ orientation: UIInterfaceOrientation) { if orientation.isPortrait { - if screenBounds.size.width < screenBounds.size.height { - pageWidth = self.view.frame.width - pageHeight = self.view.frame.height + if (screenBounds.size.width < screenBounds.size.height) { + self.pageWidth = self.view.frame.width + self.pageHeight = self.view.frame.height } else { - pageWidth = self.view.frame.height - pageHeight = self.view.frame.width + self.pageWidth = self.view.frame.height + self.pageHeight = self.view.frame.width } } else { - if screenBounds.size.width > screenBounds.size.height { - pageWidth = self.view.frame.width - pageHeight = self.view.frame.height + if (screenBounds.size.width > screenBounds.size.height) { + self.pageWidth = self.view.frame.width + self.pageHeight = self.view.frame.height } else { - pageWidth = self.view.frame.height - pageHeight = self.view.frame.width + self.pageWidth = self.view.frame.height + self.pageHeight = self.view.frame.width } } } @@ -633,12 +627,13 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo func pagesForCurrentPage(_ page: FolioReaderPage?) { guard let page = page else { return } - let pageSize = self.readerConfig.isDirection(pageHeight, pageWidth) + let pageSize = self.readerConfig.isDirection(pageHeight, self.pageWidth) + let contentSize = page.webView.scrollView.contentSize.forDirection(withConfiguration: self.readerConfig) // TODO_SMF: remove unwrap - pageIndicatorView?.totalPages = Int(ceil(page.webView.scrollView.contentSize.forDirection(withConfiguration: self.readerConfig)/pageSize!)) + pageIndicatorView?.totalPages = ((pageSize != 0) ? Int(ceil(contentSize / pageSize)) : 0) let pageOffSet = self.readerConfig.isDirection(page.webView.scrollView.contentOffset.x, page.webView.scrollView.contentOffset.x, page.webView.scrollView.contentOffset.y) - let webViewPage = pageForOffset(pageOffSet, pageHeight: pageSize!) + let webViewPage = pageForOffset(pageOffSet, pageHeight: pageSize) pageIndicatorView?.currentPage = webViewPage } @@ -679,8 +674,8 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo func frameForPage(_ page: Int) -> CGRect { return self.readerConfig.isDirection( - CGRect(x: 0, y: pageHeight * CGFloat(page-1), width: pageWidth, height: pageHeight), - CGRect(x: pageWidth * CGFloat(page-1), y: 0, width: pageWidth, height: pageHeight) + CGRect(x: 0, y: self.pageHeight * CGFloat(page-1), width: self.pageWidth, height: self.pageHeight), + CGRect(x: self.pageWidth * CGFloat(page-1), y: 0, width: self.pageWidth, height: self.pageHeight) ) } @@ -1013,30 +1008,28 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo // Update current reading page if scrollView is UICollectionView { // TODO_SMF: refactor? - } else { - if let page = currentPage, - let pageSize = self.readerConfig.isDirection(pageHeight, pageWidth) { + } else if let page = currentPage { + let pageSize = self.readerConfig.isDirection(self.pageHeight, self.pageWidth) - if (page.webView.scrollView.contentOffset.forDirection(withConfiguration: self.readerConfig)+pageSize <= page.webView.scrollView.contentSize.forDirection(withConfiguration: self.readerConfig)) { + if (page.webView.scrollView.contentOffset.forDirection(withConfiguration: self.readerConfig)+pageSize <= page.webView.scrollView.contentSize.forDirection(withConfiguration: self.readerConfig)) { - let webViewPage = pageForOffset(page.webView.scrollView.contentOffset.forDirection(withConfiguration: self.readerConfig), pageHeight: pageSize) + let webViewPage = pageForOffset(page.webView.scrollView.contentOffset.forDirection(withConfiguration: self.readerConfig), pageHeight: pageSize) - if (readerConfig.scrollDirection == .horizontalWithVerticalContent), - let cell = ((scrollView.superview as? UIWebView)?.delegate as? FolioReaderPage) { + if (readerConfig.scrollDirection == .horizontalWithVerticalContent), + let cell = ((scrollView.superview as? UIWebView)?.delegate as? FolioReaderPage) { - let currentIndexPathRow = cell.pageNumber - 1 + let currentIndexPathRow = cell.pageNumber - 1 - // if the cell reload don't save the top position offset - if let oldOffSet = self.currentWebViewScrollPositions[currentIndexPathRow], (abs(oldOffSet.y - scrollView.contentOffset.y) > 100) { - // TODO_SMF: refactor? - } else { - self.currentWebViewScrollPositions[currentIndexPathRow] = scrollView.contentOffset - } + // if the cell reload don't save the top position offset + if let oldOffSet = self.currentWebViewScrollPositions[currentIndexPathRow], (abs(oldOffSet.y - scrollView.contentOffset.y) > 100) { + // TODO_SMF: refactor? + } else { + self.currentWebViewScrollPositions[currentIndexPathRow] = scrollView.contentOffset } + } - if pageIndicatorView?.currentPage != webViewPage { - pageIndicatorView?.currentPage = webViewPage - } + if pageIndicatorView?.currentPage != webViewPage { + pageIndicatorView?.currentPage = webViewPage } } } diff --git a/Source/ScrollScrubber.swift b/Source/ScrollScrubber.swift index 6f1c7897b..c1e86499f 100644 --- a/Source/ScrollScrubber.swift +++ b/Source/ScrollScrubber.swift @@ -186,20 +186,22 @@ class ScrollScrubber: NSObject, UIScrollViewDelegate { setSliderVal() } - if( slider.alpha > 0 ){ - - show() - - } else if delegate.currentPage != nil && scrollStart != nil { - scrollDelta = scrollView.contentOffset.forDirection(withConfiguration: self.readerContainer.readerConfig) - scrollStart - - if scrollDeltaTimer == nil && scrollDelta > (pageHeight * 0.2 ) || (scrollDelta * -1) > (pageHeight * 0.2) { - show() - resetScrollDelta() - } - } - } - + if (slider.alpha > 0) { + self.show() + + } else if delegate.currentPage != nil && scrollStart != nil { + scrollDelta = scrollView.contentOffset.forDirection(withConfiguration: self.readerContainer.readerConfig) - scrollStart + + guard let pageHeight = self.readerContainer.folioReader.readerCenter?.pageHeight, + (scrollDeltaTimer == nil && scrollDelta > (pageHeight * 0.2 ) || (scrollDelta * -1) > (pageHeight * 0.2)) else { + return + } + + self.show() + self.resetScrollDelta() + } + } + func scrollViewDidEndDecelerating(_ scrollView: UIScrollView) { resetScrollDelta() } @@ -231,8 +233,10 @@ class ScrollScrubber: NSObject, UIScrollViewDelegate { } fileprivate func height() -> CGFloat { - guard let currentPage = delegate.currentPage else { - return 0 + guard + let currentPage = delegate.currentPage, + let pageHeight = self.readerContainer.folioReader.readerCenter?.pageHeight else { + return 0 } return (currentPage.webView.scrollView.contentSize.height - pageHeight + 44) From 2d915d6fdf886b6b1c02e98cb09745992ebc5ce5 Mon Sep 17 00:00:00 2001 From: Kevin Delord Date: Fri, 31 Mar 2017 19:47:58 +0200 Subject: [PATCH 041/110] Refactor: remove possible division by 0 --- Source/FolioReaderAudioPlayer.swift | 1 - Source/FolioReaderCenter.swift | 38 +++++++++++++++++------------ Source/FolioReaderKit.swift | 2 +- Source/FolioReaderPage.swift | 2 +- 4 files changed, 25 insertions(+), 18 deletions(-) diff --git a/Source/FolioReaderAudioPlayer.swift b/Source/FolioReaderAudioPlayer.swift index 5de5d03d7..e630f6cef 100644 --- a/Source/FolioReaderAudioPlayer.swift +++ b/Source/FolioReaderAudioPlayer.swift @@ -12,7 +12,6 @@ import MediaPlayer open class FolioReaderAudioPlayer: NSObject { - // TODO_SMF: remove `!` var isTextToSpeech = false var synthesizer: AVSpeechSynthesizer! var playing = false diff --git a/Source/FolioReaderCenter.swift b/Source/FolioReaderCenter.swift index dbbb46efe..4583a1702 100755 --- a/Source/FolioReaderCenter.swift +++ b/Source/FolioReaderCenter.swift @@ -293,15 +293,27 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo } // MARK: Change layout orientation - + + /// Get internal page offset before layout change + private func updatePageOffsetRate() { + guard let currentPage = self.currentPage else { + return + } + + let pageScrollView = currentPage.webView.scrollView + let contentSize = pageScrollView.contentSize.forDirection(withConfiguration: self.readerConfig) + let contentOffset = pageScrollView.contentOffset.forDirection(withConfiguration: self.readerConfig) + self.pageOffsetRate = (contentSize != 0 ? (contentOffset / contentSize) : 0) + } + func setScrollDirection(_ direction: FolioReaderScrollDirection) { - guard let currentPage = currentPage else { return } - - // Get internal page offset before layout change - let pageScrollView = currentPage.webView.scrollView - // TODO_SMF: check not divided by 0 - pageOffsetRate = (pageScrollView.contentOffset.forDirection(withConfiguration: self.readerConfig) / pageScrollView.contentSize.forDirection(withConfiguration: self.readerConfig)) - + guard let currentPage = self.currentPage else { + return + } + let pageScrollView = currentPage.webView.scrollView + + // Get internal page offset before layout change + self.updatePageOffsetRate() // Change layout self.readerConfig.scrollDirection = direction self.collectionViewLayout.scrollDirection = .direction(withConfiguration: self.readerConfig) @@ -507,10 +519,7 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo self.collectionView.collectionViewLayout.invalidateLayout() // Adjust internal page offset - guard let currentPage = self.currentPage else { return } - let pageScrollView = currentPage.webView.scrollView - // TODO_SMF: check not divided by 0 - self.pageOffsetRate = (pageScrollView.contentOffset.forDirection(withConfiguration: self.readerConfig) / pageScrollView.contentSize.forDirection(withConfiguration: self.readerConfig)) + self.updatePageOffsetRate() }) } @@ -629,13 +638,12 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo let pageSize = self.readerConfig.isDirection(pageHeight, self.pageWidth) let contentSize = page.webView.scrollView.contentSize.forDirection(withConfiguration: self.readerConfig) - // TODO_SMF: remove unwrap - pageIndicatorView?.totalPages = ((pageSize != 0) ? Int(ceil(contentSize / pageSize)) : 0) + self.pageIndicatorView?.totalPages = ((pageSize != 0) ? Int(ceil(contentSize / pageSize)) : 0) let pageOffSet = self.readerConfig.isDirection(page.webView.scrollView.contentOffset.x, page.webView.scrollView.contentOffset.x, page.webView.scrollView.contentOffset.y) let webViewPage = pageForOffset(pageOffSet, pageHeight: pageSize) - pageIndicatorView?.currentPage = webViewPage + self.pageIndicatorView?.currentPage = webViewPage } func pageForOffset(_ offset: CGFloat, pageHeight height: CGFloat) -> Int { diff --git a/Source/FolioReaderKit.swift b/Source/FolioReaderKit.swift index 79b766142..8db3c54de 100755 --- a/Source/FolioReaderKit.swift +++ b/Source/FolioReaderKit.swift @@ -84,7 +84,7 @@ open class FolioReader: NSObject { return self.readerContainer?.centerViewController } - // TODO_SMF: remove/rename static UserDefaults object. + // TODO_SMF: USERDEFAULT class var defaults : UserDefaults { return UserDefaults.standard } diff --git a/Source/FolioReaderPage.swift b/Source/FolioReaderPage.swift index 9d3b7e462..54c58db73 100755 --- a/Source/FolioReaderPage.swift +++ b/Source/FolioReaderPage.swift @@ -32,7 +32,7 @@ import JSQWebViewController open class FolioReaderPage: UICollectionViewCell, UIWebViewDelegate, UIGestureRecognizerDelegate { weak var delegate: FolioReaderPageDelegate? - // TODO_SMF: remove `!` + /// The index of the current page. Note: The index start at 1! open var pageNumber: Int! var webView: FolioReaderWebView! From e466ed0ae99bf438bd5a22b1cd030bc207efe9ec Mon Sep 17 00:00:00 2001 From: Kevin Delord Date: Fri, 31 Mar 2017 20:03:16 +0200 Subject: [PATCH 042/110] Refactor: remove some optional unwrappings --- Source/FolioReaderKit.swift | 57 +++++++++++++++++++++--------- Source/FolioReaderPlayerMenu.swift | 2 +- 2 files changed, 42 insertions(+), 17 deletions(-) diff --git a/Source/FolioReaderKit.swift b/Source/FolioReaderKit.swift index 8db3c54de..9b2c5d012 100755 --- a/Source/FolioReaderKit.swift +++ b/Source/FolioReaderKit.swift @@ -126,19 +126,34 @@ open class FolioReader: NSObject { } } - /// Check current font name + /// Check current font name. Default .andada open var currentFont: FolioReaderFont { - get { return FolioReaderFont(rawValue: FolioReader.defaults.value(forKey: kCurrentFontFamily) as! Int)! } + get { + guard + let rawValue = FolioReader.defaults.value(forKey: kCurrentFontFamily) as? Int, + let font = FolioReaderFont(rawValue: rawValue) else { + return .andada + } + + return font + } set (font) { FolioReader.defaults.setValue(font.rawValue, forKey: kCurrentFontFamily) _ = self.readerCenter?.currentPage?.webView.js("setFontName('\(font.cssIdentifier)')") } } - /// Check current font size + /// Check current font size. Default .m open var currentFontSize: FolioReaderFontSize { - // TODO_SMF: remove unwrap - get { return FolioReaderFontSize(rawValue: FolioReader.defaults.value(forKey: kCurrentFontSize) as! Int)! } + get { + guard + let rawValue = FolioReader.defaults.value(forKey: kCurrentFontSize) as? Int, + let size = FolioReaderFontSize(rawValue: rawValue) else { + return .m + } + + return size + } set (value) { FolioReader.defaults.setValue(value.rawValue, forKey: kCurrentFontSize) @@ -150,19 +165,17 @@ open class FolioReader: NSObject { } } - /// Check current audio rate, the speed of speech voice + /// Check current audio rate, the speed of speech voice. Default 0 var currentAudioRate: Int { - // TODO_SMF: remove unwrap - get { return FolioReader.defaults.value(forKey: kCurrentAudioRate) as! Int } + get { return (FolioReader.defaults.value(forKey: kCurrentAudioRate) as? Int ?? 0) } set (value) { FolioReader.defaults.setValue(value, forKey: kCurrentAudioRate) } } - /// Check the current highlight style + /// Check the current highlight style.Default 0 var currentHighlightStyle: Int { - // TODO_SMF: remove unwrap - get { return FolioReader.defaults.value(forKey: kCurrentHighlightStyle) as! Int } + get { return (FolioReader.defaults.value(forKey: kCurrentHighlightStyle) as? Int ?? 0) } set (value) { FolioReader.defaults.setValue(value, forKey: kCurrentHighlightStyle) } @@ -170,17 +183,29 @@ open class FolioReader: NSObject { /// Check the current Media Overlay or TTS style var currentMediaOverlayStyle: MediaOverlayStyle { - // TODO_SMF: remove unwrap - get { return MediaOverlayStyle(rawValue: FolioReader.defaults.value(forKey: kCurrentMediaOverlayStyle) as! Int)! } + get { + guard + let rawValue = FolioReader.defaults.value(forKey: kCurrentMediaOverlayStyle) as? Int, + let style = MediaOverlayStyle(rawValue: rawValue) else { + return MediaOverlayStyle.default + } + + return style + } set (value) { FolioReader.defaults.setValue(value.rawValue, forKey: kCurrentMediaOverlayStyle) } } - /// Check the current scroll direction + /// Check the current scroll direction. Default .defaultVertical open var currentScrollDirection: Int { - // TODO_SMF: remove unwrap - get { return FolioReader.defaults.value(forKey: kCurrentScrollDirection) as! Int } + get { + guard let value = FolioReader.defaults.value(forKey: kCurrentScrollDirection) as? Int else { + return FolioReaderScrollDirection.defaultVertical.rawValue + } + + return value + } set (value) { FolioReader.defaults.setValue(value, forKey: kCurrentScrollDirection) diff --git a/Source/FolioReaderPlayerMenu.swift b/Source/FolioReaderPlayerMenu.swift index 0148a1416..2a194b510 100644 --- a/Source/FolioReaderPlayerMenu.swift +++ b/Source/FolioReaderPlayerMenu.swift @@ -233,7 +233,7 @@ class FolioReaderPlayerMenu : UIViewController, SMSegmentViewDelegate, UIGestu func segmentView(_ segmentView: SMSegmentView, didSelectSegmentAtIndex index: Int) { guard viewDidAppear else { return } - if let audioPlayer = self.folioReader.readerAudioPlayer , segmentView.tag == 2 { + if let audioPlayer = self.folioReader.readerAudioPlayer, (segmentView.tag == 2) { audioPlayer.setRate(index) self.folioReader.currentAudioRate = index } From b3612f8e011cad9775f18c7a3b7f246597e0da3f Mon Sep 17 00:00:00 2001 From: Kevin Delord Date: Fri, 31 Mar 2017 20:10:19 +0200 Subject: [PATCH 043/110] Refactor: function with bad structure --- Source/FolioReaderCenter.swift | 25 ++++++++++++------------- 1 file changed, 12 insertions(+), 13 deletions(-) diff --git a/Source/FolioReaderCenter.swift b/Source/FolioReaderCenter.swift index 4583a1702..89c412366 100755 --- a/Source/FolioReaderCenter.swift +++ b/Source/FolioReaderCenter.swift @@ -883,7 +883,6 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo var authorName = "" var shareItems = [AnyObject]() - // TODO_SMF: refactor similar code in current functions. // Get book title if let title = self.book.title() { bookTitle = title @@ -1007,21 +1006,21 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo open func scrollViewDidScroll(_ scrollView: UIScrollView) { - if !navigationController!.isNavigationBarHidden { - toggleBars() + if (navigationController?.isNavigationBarHidden == false) { + self.toggleBars() } scrollScrubber?.scrollViewDidScroll(scrollView) - - // Update current reading page - if scrollView is UICollectionView { - // TODO_SMF: refactor? - } else if let page = currentPage { - let pageSize = self.readerConfig.isDirection(self.pageHeight, self.pageWidth) - if (page.webView.scrollView.contentOffset.forDirection(withConfiguration: self.readerConfig)+pageSize <= page.webView.scrollView.contentSize.forDirection(withConfiguration: self.readerConfig)) { + // Update current reading page + if ((scrollView is UICollectionView) == false), let page = currentPage { + + let pageSize = self.readerConfig.isDirection(self.pageHeight, self.pageWidth) + let contentOffset = page.webView.scrollView.contentOffset.forDirection(withConfiguration: self.readerConfig) + let contentSize = page.webView.scrollView.contentSize.forDirection(withConfiguration: self.readerConfig) + if (contentOffset + pageSize <= contentSize) { - let webViewPage = pageForOffset(page.webView.scrollView.contentOffset.forDirection(withConfiguration: self.readerConfig), pageHeight: pageSize) + let webViewPage = pageForOffset(contentOffset, pageHeight: pageSize) if (readerConfig.scrollDirection == .horizontalWithVerticalContent), let cell = ((scrollView.superview as? UIWebView)?.delegate as? FolioReaderPage) { @@ -1030,13 +1029,13 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo // if the cell reload don't save the top position offset if let oldOffSet = self.currentWebViewScrollPositions[currentIndexPathRow], (abs(oldOffSet.y - scrollView.contentOffset.y) > 100) { - // TODO_SMF: refactor? + // Do nothing } else { self.currentWebViewScrollPositions[currentIndexPathRow] = scrollView.contentOffset } } - if pageIndicatorView?.currentPage != webViewPage { + if (pageIndicatorView?.currentPage != webViewPage) { pageIndicatorView?.currentPage = webViewPage } } From 9d397403519dc01912bbcdcc62f27eb74d8857cb Mon Sep 17 00:00:00 2001 From: Kevin Delord Date: Fri, 31 Mar 2017 20:29:20 +0200 Subject: [PATCH 044/110] Refactor: duplicated code --- Source/FolioReaderCenter.swift | 77 ++++++++++++++++------------------ 1 file changed, 35 insertions(+), 42 deletions(-) diff --git a/Source/FolioReaderCenter.swift b/Source/FolioReaderCenter.swift index 89c412366..13993354f 100755 --- a/Source/FolioReaderCenter.swift +++ b/Source/FolioReaderCenter.swift @@ -274,22 +274,21 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo } // MARK: Change page progressive direction - + + private func transformViewForRTL(_ view: UIView?) { + if (self.readerContainer.folioReader.needsRTLChange == true) { + view?.transform = CGAffineTransform(scaleX: -1, y: 1) + } else { + view?.transform = CGAffineTransform.identity + } + } + func setCollectionViewProgressiveDirection() { - if (self.readerContainer.folioReader.needsRTLChange == true) { - collectionView.transform = CGAffineTransform(scaleX: -1, y: 1) - } else { - collectionView.transform = CGAffineTransform.identity - } + self.transformViewForRTL(self.collectionView) } func setPageProgressiveDirection(_ page: FolioReaderPage) { - if (self.readerContainer.folioReader.needsRTLChange == true) { -// if page.transform.a == -1 { return } - page.transform = CGAffineTransform(scaleX: -1, y: 1) - } else { - page.transform = CGAffineTransform.identity - } + self.transformViewForRTL(page) } // MARK: Change layout orientation @@ -310,6 +309,7 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo guard let currentPage = self.currentPage else { return } + let pageScrollView = currentPage.webView.scrollView // Get internal page offset before layout change @@ -346,33 +346,18 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo // MARK: Status bar and Navigation bar - // TODO_SMF: refactor similar code func hideBars() { guard (self.readerConfig.shouldHideNavigationOnTap == true) else { return } - self.readerContainer.shouldHideStatusBar = true - - UIView.animate(withDuration: 0.25, animations: { - self.readerContainer.setNeedsStatusBarAppearanceUpdate() - - // Show minutes indicator -// self.pageIndicatorView.minutesLabel.alpha = 0 - }) - navigationController?.setNavigationBarHidden(true, animated: true) + self.updateBarsStatus(true) } func showBars() { self.configureNavBar() - - self.readerContainer.shouldHideStatusBar = false - - UIView.animate(withDuration: 0.25, animations: { - self.readerContainer.setNeedsStatusBarAppearanceUpdate() - }) - navigationController?.setNavigationBarHidden(false, animated: true) + self.updateBarsStatus(false) } func toggleBars() { @@ -384,20 +369,28 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo if (shouldHide == false) { self.configureNavBar() } - - self.readerContainer.shouldHideStatusBar = shouldHide - - UIView.animate(withDuration: 0.25, animations: { - self.readerContainer.setNeedsStatusBarAppearanceUpdate() - - // Show minutes indicator -// self.pageIndicatorView.minutesLabel.alpha = shouldHide ? 0 : 1 - }) - self.navigationController?.setNavigationBarHidden(shouldHide, animated: true) + + self.updateBarsStatus(shouldHide) } - + + private func updateBarsStatus(_ shouldHide: Bool, shouldShowIndicator: Bool = false) { + + self.readerContainer.shouldHideStatusBar = shouldHide + + UIView.animate(withDuration: 0.25, animations: { + self.readerContainer.setNeedsStatusBarAppearanceUpdate() + + // Show minutes indicator + if (shouldShowIndicator == true) { + self.pageIndicatorView?.minutesLabel.alpha = (shouldHide == true ? 0 : 1) + } + }) + + self.navigationController?.setNavigationBarHidden(shouldHide, animated: true) + } + // MARK: UICollectionViewDataSource - + open func numberOfSections(in collectionView: UICollectionView) -> Int { return 1 } @@ -1027,7 +1020,7 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo let currentIndexPathRow = cell.pageNumber - 1 - // if the cell reload don't save the top position offset + // if the cell reload doesn't save the top position offset if let oldOffSet = self.currentWebViewScrollPositions[currentIndexPathRow], (abs(oldOffSet.y - scrollView.contentOffset.y) > 100) { // Do nothing } else { From ed5c6bc166bb38f00d3d34d7b32290081df20c18 Mon Sep 17 00:00:00 2001 From: Kevin Delord Date: Fri, 31 Mar 2017 20:34:58 +0200 Subject: [PATCH 045/110] Remove optional unwrapping --- Source/FolioReaderCenter.swift | 2 +- Source/FolioReaderQuoteShare.swift | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/Source/FolioReaderCenter.swift b/Source/FolioReaderCenter.swift index 13993354f..75813fe79 100755 --- a/Source/FolioReaderCenter.swift +++ b/Source/FolioReaderCenter.swift @@ -146,7 +146,7 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo } // Register cell classes - collectionView!.register(FolioReaderPage.self, forCellWithReuseIdentifier: kReuseCellIdentifier) + collectionView?.register(FolioReaderPage.self, forCellWithReuseIdentifier: kReuseCellIdentifier) // Configure navigation bar and layout automaticallyAdjustsScrollViewInsets = false diff --git a/Source/FolioReaderQuoteShare.swift b/Source/FolioReaderQuoteShare.swift index 961ec16dd..d6c19a9e3 100644 --- a/Source/FolioReaderQuoteShare.swift +++ b/Source/FolioReaderQuoteShare.swift @@ -177,7 +177,7 @@ class FolioReaderQuoteShare: UIViewController { // Register cell classes collectionView?.register(UICollectionViewCell.self, forCellWithReuseIdentifier: kReuseCellIdentifier) - + // Create images dataSource = self.readerConfig.quoteCustomBackgrounds if (self.readerConfig.quotePreserveDefaultBackgrounds == true) { From 3769df65bd58f04656f0ce8eb4c64c77f73f8e69 Mon Sep 17 00:00:00 2001 From: Kevin Delord Date: Fri, 31 Mar 2017 21:08:06 +0200 Subject: [PATCH 046/110] Fix and better integrate the storyboard support. --- Example/StoryboardExample/AppDelegate.swift | 11 ++++---- .../ExampleFolioReaderContainer.swift | 2 ++ Source/FolioReaderConfig.swift | 25 +++++++----------- Source/FolioReaderContainer.swift | 26 ++++++++++++++----- Source/FolioReaderKit.swift | 5 ++-- 5 files changed, 39 insertions(+), 30 deletions(-) diff --git a/Example/StoryboardExample/AppDelegate.swift b/Example/StoryboardExample/AppDelegate.swift index 964e3ff6e..e7c3e3854 100644 --- a/Example/StoryboardExample/AppDelegate.swift +++ b/Example/StoryboardExample/AppDelegate.swift @@ -10,21 +10,22 @@ import UIKit import FolioReaderKit @UIApplicationMain -class AppDelegate: UIResponder, UIApplicationDelegate { - - var window: UIWindow? +class AppDelegate : UIResponder, UIApplicationDelegate { + var window : UIWindow? + var epubReader : FolioReader? + func application(_ application: UIApplication, didFinishLaunchingWithOptions launchOptions: [UIApplicationLaunchOptionsKey: Any]?) -> Bool { // Override point for customization after application launch. return true } func applicationWillResignActive(_ application: UIApplication) { - FolioReader.applicationWillResignActive() + self.epubReader?.saveReaderState() } func applicationWillTerminate(_ application: UIApplication) { - FolioReader.applicationWillTerminate() + self.epubReader?.saveReaderState() } } diff --git a/Example/StoryboardExample/ExampleFolioReaderContainer.swift b/Example/StoryboardExample/ExampleFolioReaderContainer.swift index e975b508c..43939fd1e 100644 --- a/Example/StoryboardExample/ExampleFolioReaderContainer.swift +++ b/Example/StoryboardExample/ExampleFolioReaderContainer.swift @@ -28,5 +28,7 @@ class ExampleFolioReaderContainer: FolioReaderContainer { guard let bookPath = Bundle.main.path(forResource: "The Silver Chair", ofType: "epub") else { return } setupConfig(config, epubPath: bookPath) + + (UIApplication.shared.delegate as? AppDelegate)?.epubReader = self.folioReader } } diff --git a/Source/FolioReaderConfig.swift b/Source/FolioReaderConfig.swift index 4eeedced5..cb173137d 100755 --- a/Source/FolioReaderConfig.swift +++ b/Source/FolioReaderConfig.swift @@ -12,28 +12,21 @@ import RealmSwift // MARK: - FolioReaderScrollDirection -/** - Defines the Reader scrolling direction - */ +/// Defines the Reader scrolling direction +/// +/// - vertical: Section and content scroll on vertical. +/// - horizontal: Section and content scroll on horizontal. +/// - horizontalWithVerticalContent: Sections scroll horizontal and content scroll on vertical. +/// - defaultVertical: The default scroll direction, if not overridden; works as .vertical. public enum FolioReaderScrollDirection: Int { - - /// Section and content scroll on vertical case vertical - - /// Section and content scroll on horizontal case horizontal - - /// Sections scroll horizontal and content scroll on vertical case horizontalWithVerticalContent - - /// The default scroll direction, if not overridden; works as .vertical case defaultVertical - /** - The current scroll direction - - - returns: Returns `UICollectionViewScrollDirection` - */ + /// The current scroll direction + /// + /// - Returns: Returns `UICollectionViewScrollDirection` func collectionViewScrollDirection() -> UICollectionViewScrollDirection { switch self { case .vertical, .defaultVertical: diff --git a/Source/FolioReaderContainer.swift b/Source/FolioReaderContainer.swift index cf6b711e1..3a7109676 100755 --- a/Source/FolioReaderContainer.swift +++ b/Source/FolioReaderContainer.swift @@ -19,8 +19,9 @@ open class FolioReaderContainer : UIViewController { var shouldRemoveEpub = true var epubPath : String var book : FRBook - var readerConfig : FolioReaderConfig - var folioReader : FolioReader + // Mark those property as public so they can accessed from other classes/subclasses. + public var readerConfig : FolioReaderConfig + public var folioReader : FolioReader fileprivate var errorOnLoad = false @@ -46,8 +47,19 @@ open class FolioReaderContainer : UIViewController { } required public init?(coder aDecoder: NSCoder) { - // TODO_SMF_QUESTION: is that ok? do 'we' really support NSCoding? - fatalError("This class doesn't support NSCoding.") + // When a FolioReaderContainer object is instantiated from the storyboard this function is called before. + // At this moment, we need to initialize all non-optional objects with default values. + // The function `setupConfig(config:epubPath:removeEpub:)` MUST be called afterward. + // See the ExampleFolioReaderContainer.swift for more information? + self.readerConfig = FolioReaderConfig() + self.folioReader = FolioReader() + self.epubPath = "" + self.shouldRemoveEpub = false + self.book = FRBook() + + super.init(coder: aDecoder) + + self.folioReader.readerContainer = self } /// Common Initialization @@ -72,12 +84,12 @@ open class FolioReaderContainer : UIViewController { /// /// - Parameters: /// - config: Current Folio Reader configuration - /// - folioReader: Current instance of the FolioReader kit. /// - path: The ePub path on system /// - removeEpub: Should delete the original file after unzip? Default to `true` so the ePub will be unziped only once. - open func setupConfig(_ config: FolioReaderConfig, folioReader: FolioReader, epubPath path: String, removeEpub: Bool = true) { + open func setupConfig(_ config: FolioReaderConfig, epubPath path: String, removeEpub: Bool = true) { self.readerConfig = config - self.folioReader = folioReader + self.folioReader = FolioReader() + self.folioReader.readerContainer = self self.epubPath = path self.shouldRemoveEpub = removeEpub } diff --git a/Source/FolioReaderKit.swift b/Source/FolioReaderKit.swift index 9b2c5d012..5882af617 100755 --- a/Source/FolioReaderKit.swift +++ b/Source/FolioReaderKit.swift @@ -221,9 +221,10 @@ extension FolioReader { /** Present a Folio Reader for a Parent View Controller. - // TODO_SMF_DOC */ - open class func presentReader(parentViewController: UIViewController, withEpubPath epubPath: String, andConfig config: FolioReaderConfig, shouldRemoveEpub: Bool = true, animated: Bool = true) -> FolioReader { + open class func presentReader(parentViewController: UIViewController, withEpubPath epubPath: String, andConfig config: FolioReaderConfig, shouldRemoveEpub: Bool = true, animated: + Bool = true) -> FolioReader { + // TODO_SMF_DOC let folioReader = FolioReader() let readerContainer = FolioReaderContainer(withConfig: config, folioReader: folioReader, epubPath: epubPath, removeEpub: shouldRemoveEpub) folioReader.readerContainer = readerContainer From 12d26b15607130cf0c07a2a5b95a5d77ec568d6b Mon Sep 17 00:00:00 2001 From: Kevin Delord Date: Fri, 31 Mar 2017 21:08:58 +0200 Subject: [PATCH 047/110] Add todo check --- Source/FolioReaderAudioPlayer.swift | 2 ++ Source/FolioReaderCenter.swift | 3 +++ Source/FolioReaderKit.swift | 1 + 3 files changed, 6 insertions(+) diff --git a/Source/FolioReaderAudioPlayer.swift b/Source/FolioReaderAudioPlayer.swift index e630f6cef..ef0f0d07a 100644 --- a/Source/FolioReaderAudioPlayer.swift +++ b/Source/FolioReaderAudioPlayer.swift @@ -372,8 +372,10 @@ open class FolioReaderAudioPlayer: NSObject { let playbackActiveClass = self.book.playbackActiveClass() guard let sentence = currentPage.webView.js("getSentenceWithIndex('\(playbackActiveClass)')") else { if (readerCenter.isLastPage() == true) { + // TODO_SMF_CHECK: when do this happen? self.stop() } else { + // TODO_SMF_CHECK: when do this happen? readerCenter.changePageToNext() } diff --git a/Source/FolioReaderCenter.swift b/Source/FolioReaderCenter.swift index 75813fe79..a4b4f4ed9 100755 --- a/Source/FolioReaderCenter.swift +++ b/Source/FolioReaderCenter.swift @@ -277,6 +277,7 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo private func transformViewForRTL(_ view: UIView?) { if (self.readerContainer.folioReader.needsRTLChange == true) { + // TODO_SMF_CHECK: when do this happen? view?.transform = CGAffineTransform(scaleX: -1, y: 1) } else { view?.transform = CGAffineTransform.identity @@ -826,9 +827,11 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo return nil } + // TODO_SMF_CHECK: when do this happen? return title } + // TODO_SMF_CHECK: when do this happen? return nil } diff --git a/Source/FolioReaderKit.swift b/Source/FolioReaderKit.swift index 5882af617..4661483ff 100755 --- a/Source/FolioReaderKit.swift +++ b/Source/FolioReaderKit.swift @@ -200,6 +200,7 @@ open class FolioReader: NSObject { /// Check the current scroll direction. Default .defaultVertical open var currentScrollDirection: Int { get { + // TODO_SMF_CHECK: when do this happen? guard let value = FolioReader.defaults.value(forKey: kCurrentScrollDirection) as? Int else { return FolioReaderScrollDirection.defaultVertical.rawValue } From 384d9dc223af83af033aa99e9e4a75a4078f4b4f Mon Sep 17 00:00:00 2001 From: Kevin Delord Date: Fri, 31 Mar 2017 21:16:05 +0200 Subject: [PATCH 048/110] Update API logic to return FolioReaderContainer --- Example/Example/AppDelegate.swift | 4 ++-- Example/Example/ViewController.swift | 10 +++++----- Example/StoryboardExample/AppDelegate.swift | 2 +- .../ExampleFolioReaderContainer.swift | 2 +- Source/FolioReaderContainer.swift | 7 ++++++- Source/FolioReaderKit.swift | 6 ++---- Source/FolioReaderPage.swift | 1 + 7 files changed, 18 insertions(+), 14 deletions(-) diff --git a/Example/Example/AppDelegate.swift b/Example/Example/AppDelegate.swift index a177baf35..a6c471909 100644 --- a/Example/Example/AppDelegate.swift +++ b/Example/Example/AppDelegate.swift @@ -13,8 +13,8 @@ import FolioReaderKit class AppDelegate : UIResponder, UIApplicationDelegate { var window : UIWindow? - var standardEpub : FolioReader? - var audioEpub : FolioReader? + var standardEpub : FolioReaderContainer? + var audioEpub : FolioReaderContainer? func application(_ application: UIApplication, didFinishLaunchingWithOptions launchOptions: [UIApplicationLaunchOptionsKey: Any]?) -> Bool { // Override point for customization after application launch. diff --git a/Example/Example/ViewController.swift b/Example/Example/ViewController.swift index 8d6db86ad..c6d20b920 100755 --- a/Example/Example/ViewController.swift +++ b/Example/Example/ViewController.swift @@ -38,12 +38,12 @@ enum Epub: Int { return Bundle.main.path(forResource: self.name, ofType: "epub") } - func retain(folioReader: FolioReader) { + func retain(folioReaderContainer: FolioReaderContainer) { let appDelegate = (UIApplication.shared.delegate as? AppDelegate) switch self { - case .bookOne: appDelegate?.standardEpub = folioReader - case .bookTwo: appDelegate?.audioEpub = folioReader + case .bookOne: appDelegate?.standardEpub = folioReaderContainer + case .bookTwo: appDelegate?.audioEpub = folioReaderContainer } } } @@ -103,9 +103,9 @@ class ViewController : UIViewController { } let readerConfiguration = self.readerConfiguration(forEpub: epub) - let folioReader = FolioReader.presentReader(parentViewController: self, withEpubPath: bookPath, andConfig: readerConfiguration, shouldRemoveEpub: false) + let folioReaderContainer = FolioReader.presentReader(parentViewController: self, withEpubPath: bookPath, andConfig: readerConfiguration, shouldRemoveEpub: false) - epub.retain(folioReader: folioReader) + epub.retain(folioReaderContainer: folioReaderContainer) } private func setCover(_ button: UIButton?, index: Int) { diff --git a/Example/StoryboardExample/AppDelegate.swift b/Example/StoryboardExample/AppDelegate.swift index e7c3e3854..1a1ba7b72 100644 --- a/Example/StoryboardExample/AppDelegate.swift +++ b/Example/StoryboardExample/AppDelegate.swift @@ -13,7 +13,7 @@ import FolioReaderKit class AppDelegate : UIResponder, UIApplicationDelegate { var window : UIWindow? - var epubReader : FolioReader? + var epubReader : FolioReaderContainer? func application(_ application: UIApplication, didFinishLaunchingWithOptions launchOptions: [UIApplicationLaunchOptionsKey: Any]?) -> Bool { // Override point for customization after application launch. diff --git a/Example/StoryboardExample/ExampleFolioReaderContainer.swift b/Example/StoryboardExample/ExampleFolioReaderContainer.swift index 43939fd1e..cd5ca508b 100644 --- a/Example/StoryboardExample/ExampleFolioReaderContainer.swift +++ b/Example/StoryboardExample/ExampleFolioReaderContainer.swift @@ -29,6 +29,6 @@ class ExampleFolioReaderContainer: FolioReaderContainer { guard let bookPath = Bundle.main.path(forResource: "The Silver Chair", ofType: "epub") else { return } setupConfig(config, epubPath: bookPath) - (UIApplication.shared.delegate as? AppDelegate)?.epubReader = self.folioReader + (UIApplication.shared.delegate as? AppDelegate)?.epubReader = self } } diff --git a/Source/FolioReaderContainer.swift b/Source/FolioReaderContainer.swift index 3a7109676..53f4ae6e9 100755 --- a/Source/FolioReaderContainer.swift +++ b/Source/FolioReaderContainer.swift @@ -174,7 +174,12 @@ open class FolioReaderContainer : UIViewController { self.dismiss() } } - + + /// Save Reader state, book, page and scroll offset. + open func saveReaderState() { + self.folioReader.saveReaderState() + } + /** Initialize the media player */ diff --git a/Source/FolioReaderKit.swift b/Source/FolioReaderKit.swift index 4661483ff..05cd46ef2 100755 --- a/Source/FolioReaderKit.swift +++ b/Source/FolioReaderKit.swift @@ -224,7 +224,7 @@ extension FolioReader { Present a Folio Reader for a Parent View Controller. */ open class func presentReader(parentViewController: UIViewController, withEpubPath epubPath: String, andConfig config: FolioReaderConfig, shouldRemoveEpub: Bool = true, animated: - Bool = true) -> FolioReader { + Bool = true) -> FolioReaderContainer { // TODO_SMF_DOC let folioReader = FolioReader() let readerContainer = FolioReaderContainer(withConfig: config, folioReader: folioReader, epubPath: epubPath, removeEpub: shouldRemoveEpub) @@ -232,7 +232,7 @@ extension FolioReader { parentViewController.present(readerContainer, animated: animated, completion: nil) // TODO_SMF_DOC FolioReader.shared = folioReader - return folioReader + return readerContainer } } @@ -800,8 +800,6 @@ internal extension String { } } -// TODO_SMF: split files into extension files - internal extension UIImage { convenience init?(readerImageNamed: String) { diff --git a/Source/FolioReaderPage.swift b/Source/FolioReaderPage.swift index 54c58db73..d34c5a328 100755 --- a/Source/FolioReaderPage.swift +++ b/Source/FolioReaderPage.swift @@ -159,6 +159,7 @@ open class FolioReaderPage: UICollectionViewCell, UIWebViewDelegate, UIGestureRe tempHtmlContent = tempHtmlContent.replacingCharacters(in: newRange, with: tag) as NSString } else { + // TODO_SMF_CHECK: this might not be normal. print("highlight range not found") } } From 34926db0334354e326abb3127c45c7a3bfcb15b3 Mon Sep 17 00:00:00 2001 From: Kevin Delord Date: Sat, 1 Apr 2017 22:40:37 +0200 Subject: [PATCH 049/110] Wrap all store values in dicionaries --- .../ExampleFolioReaderContainer.swift | 2 +- Source/FolioReaderCenter.swift | 6 +- Source/FolioReaderContainer.swift | 9 +- Source/FolioReaderKit.swift | 130 ++++++++++++------ Source/FolioReaderPage.swift | 13 +- Source/FolioReaderUserDefaults.swift | 82 +++++++++++ Source/PageViewController.swift | 10 +- 7 files changed, 190 insertions(+), 62 deletions(-) create mode 100644 Source/FolioReaderUserDefaults.swift diff --git a/Example/StoryboardExample/ExampleFolioReaderContainer.swift b/Example/StoryboardExample/ExampleFolioReaderContainer.swift index cd5ca508b..370dcb405 100644 --- a/Example/StoryboardExample/ExampleFolioReaderContainer.swift +++ b/Example/StoryboardExample/ExampleFolioReaderContainer.swift @@ -20,7 +20,7 @@ class ExampleFolioReaderContainer: FolioReaderContainer { // Print the chapter ID if one was clicked // A chapter in "The Silver Chair" looks like this "
" - // To knwo if a user tapped on a chapter we can listen to events on the class "chapter" and receive the id value + // To know if a user tapped on a chapter we can listen to events on the class "chapter" and receive the id value let listener = ClassBasedOnClickListener(schemeName: "chaptertapped", querySelector: ".chapter", attributeName: "id", onClickAction: { (attributeContent: String?, touchPointRelativeToWebView: CGPoint?) in print("chapter with id: " + (attributeContent ?? "-") + " clicked") }) diff --git a/Source/FolioReaderCenter.swift b/Source/FolioReaderCenter.swift index a4b4f4ed9..2f9a9da09 100755 --- a/Source/FolioReaderCenter.swift +++ b/Source/FolioReaderCenter.swift @@ -262,7 +262,7 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo guard let bookId = self.book.name, - let position = FolioReader.defaults.value(forKey: bookId) as? NSDictionary, + let position = self.readerContainer.folioReader.savedPositionForCurrentBook as? NSDictionary, let pageNumber = position["pageNumber"] as? Int, (pageNumber > 0) else { self.currentPageNumber = 1 @@ -411,7 +411,7 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo private func configure(readerPageCell cell: FolioReaderPage, atIndexPath indexPath: IndexPath) -> FolioReaderPage { - cell.setup(withReaderConfig: self.readerConfig, readerContainer: self.readerContainer) + cell.setup(withReaderContainer: self.readerContainer) cell.pageNumber = (indexPath as NSIndexPath).row+1 cell.webView.scrollView.delegate = self cell.webView.setupScrollDirection() @@ -1170,7 +1170,7 @@ extension FolioReaderCenter: FolioReaderPageDelegate { if let bookId = self.book.name, - let position = FolioReader.defaults.value(forKey: bookId) as? NSDictionary { + let position = self.readerContainer.folioReader.savedPositionForCurrentBook as? NSDictionary { let pageNumber = position["pageNumber"]! as! Int let offset = self.readerConfig.isDirection(position["pageOffsetY"], position["pageOffsetX"]) as? CGFloat let pageOffset = offset diff --git a/Source/FolioReaderContainer.swift b/Source/FolioReaderContainer.swift index 53f4ae6e9..ed9bc9efc 100755 --- a/Source/FolioReaderContainer.swift +++ b/Source/FolioReaderContainer.swift @@ -42,8 +42,11 @@ open class FolioReaderContainer : UIViewController { self.book = FRBook() super.init(nibName: nil, bundle: Bundle.frameworkBundle()) - - self.initialization() + + self.folioReader.readerContainer = self + if (self.epubPath != "") { + self.initialization() + } } required public init?(coder aDecoder: NSCoder) { @@ -68,7 +71,7 @@ open class FolioReaderContainer : UIViewController { FontBlaster.blast(bundle: Bundle.frameworkBundle()) // Register initial defaults - FolioReader.defaults.register(defaults: [ + self.folioReader.register(defaults: [ kCurrentFontFamily: FolioReaderFont.andada.rawValue, kNightMode: false, kCurrentFontSize: 2, diff --git a/Source/FolioReaderKit.swift b/Source/FolioReaderKit.swift index 05cd46ef2..afb29504f 100755 --- a/Source/FolioReaderKit.swift +++ b/Source/FolioReaderKit.swift @@ -63,9 +63,7 @@ enum MediaOverlayStyle: Int { @objc optional func folioReaderDidClosed() } -/** - Main Library class with some useful constants and methods - */ +/// Main Library class with some useful constants and methods open class FolioReader: NSObject { /// Internal init function to disable the creation of `FolioReader` objects outside the current scope. @@ -84,17 +82,12 @@ open class FolioReader: NSObject { return self.readerContainer?.centerViewController } - // TODO_SMF: USERDEFAULT - class var defaults : UserDefaults { - return UserDefaults.standard - } - /// Check if reader is open var isReaderOpen = false /// Check if reader is open and ready var isReaderReady = false - + /// Check if layout needs to change to fit Right To Left var needsRTLChange: Bool { return (self.readerContainer?.book.spine.isRtl == true && self.readerContainer?.readerConfig.scrollDirection == .horizontal) @@ -104,16 +97,57 @@ open class FolioReader: NSObject { return (self.nightMode == true ? f : l) } + fileprivate var defaults: FolioReaderUserDefaults { + + guard + let path = self.readerContainer?.epubPath, + (path.isEmpty == false), + let identifier = (path as? NSString)?.lastPathComponent, + (identifier.isEmpty == false) else { + fatalError("invalid user default unique identifier") + return FolioReaderUserDefaults(withIdentifier: "") + } + + return FolioReaderUserDefaults(withIdentifier: identifier) + } +} + +// MARK: - Present Folio Reader + +extension FolioReader { + + /** + Present a Folio Reader for a Parent View Controller. + */ + open class func presentReader(parentViewController: UIViewController, withEpubPath epubPath: String, andConfig config: FolioReaderConfig, shouldRemoveEpub: Bool = true, animated: + Bool = true) -> FolioReaderContainer { + // TODO_SMF_DOC + let folioReader = FolioReader() + let readerContainer = FolioReaderContainer(withConfig: config, folioReader: folioReader, epubPath: epubPath, removeEpub: shouldRemoveEpub) + folioReader.readerContainer = readerContainer + parentViewController.present(readerContainer, animated: animated, completion: nil) + // TODO_SMF_DOC + FolioReader.shared = folioReader + return readerContainer + } +} + +// MARK: - Getters and setters for stored values + +extension FolioReader { + + public func register(defaults: [String: Any]) { + self.defaults.register(defaults: defaults) + } + /// Check if current theme is Night mode open var nightMode: Bool { - get { return FolioReader.defaults.bool(forKey: kNightMode) } + get { return self.defaults.bool(forKey: kNightMode) } set (value) { - FolioReader.defaults.set(value, forKey: kNightMode) - FolioReader.defaults.synchronize() + self.defaults.set(value, forKey: kNightMode) if let readerCenter = self.readerCenter { UIView.animate(withDuration: 0.6, animations: { - // TODO_SMF_CHECK: infinite loop? _ = readerCenter.currentPage?.webView.js("nightMode(\(self.nightMode))") readerCenter.pageIndicatorView?.reloadColors() readerCenter.configureNavBar() @@ -130,7 +164,7 @@ open class FolioReader: NSObject { open var currentFont: FolioReaderFont { get { guard - let rawValue = FolioReader.defaults.value(forKey: kCurrentFontFamily) as? Int, + let rawValue = self.defaults.value(forKey: kCurrentFontFamily) as? Int, let font = FolioReaderFont(rawValue: rawValue) else { return .andada } @@ -138,7 +172,7 @@ open class FolioReader: NSObject { return font } set (font) { - FolioReader.defaults.setValue(font.rawValue, forKey: kCurrentFontFamily) + self.defaults.set(font.rawValue, forKey: kCurrentFontFamily) _ = self.readerCenter?.currentPage?.webView.js("setFontName('\(font.cssIdentifier)')") } } @@ -147,7 +181,7 @@ open class FolioReader: NSObject { open var currentFontSize: FolioReaderFontSize { get { guard - let rawValue = FolioReader.defaults.value(forKey: kCurrentFontSize) as? Int, + let rawValue = self.defaults.value(forKey: kCurrentFontSize) as? Int, let size = FolioReaderFontSize(rawValue: rawValue) else { return .m } @@ -155,7 +189,7 @@ open class FolioReader: NSObject { return size } set (value) { - FolioReader.defaults.setValue(value.rawValue, forKey: kCurrentFontSize) + self.defaults.set(value.rawValue, forKey: kCurrentFontSize) guard let currentPage = self.readerCenter?.currentPage else { return @@ -167,17 +201,17 @@ open class FolioReader: NSObject { /// Check current audio rate, the speed of speech voice. Default 0 var currentAudioRate: Int { - get { return (FolioReader.defaults.value(forKey: kCurrentAudioRate) as? Int ?? 0) } + get { return self.defaults.integer(forKey: kCurrentAudioRate) } set (value) { - FolioReader.defaults.setValue(value, forKey: kCurrentAudioRate) + self.defaults.set(value, forKey: kCurrentAudioRate) } } /// Check the current highlight style.Default 0 var currentHighlightStyle: Int { - get { return (FolioReader.defaults.value(forKey: kCurrentHighlightStyle) as? Int ?? 0) } + get { return self.defaults.integer(forKey: kCurrentHighlightStyle) } set (value) { - FolioReader.defaults.setValue(value, forKey: kCurrentHighlightStyle) + self.defaults.set(value, forKey: kCurrentHighlightStyle) } } @@ -185,7 +219,7 @@ open class FolioReader: NSObject { var currentMediaOverlayStyle: MediaOverlayStyle { get { guard - let rawValue = FolioReader.defaults.value(forKey: kCurrentMediaOverlayStyle) as? Int, + let rawValue = self.defaults.value(forKey: kCurrentMediaOverlayStyle) as? Int, let style = MediaOverlayStyle(rawValue: rawValue) else { return MediaOverlayStyle.default } @@ -193,7 +227,7 @@ open class FolioReader: NSObject { return style } set (value) { - FolioReader.defaults.setValue(value.rawValue, forKey: kCurrentMediaOverlayStyle) + self.defaults.set(value.rawValue, forKey: kCurrentMediaOverlayStyle) } } @@ -201,39 +235,43 @@ open class FolioReader: NSObject { open var currentScrollDirection: Int { get { // TODO_SMF_CHECK: when do this happen? - guard let value = FolioReader.defaults.value(forKey: kCurrentScrollDirection) as? Int else { + guard let value = self.defaults.integer(forKey: kCurrentScrollDirection) as? Int else { return FolioReaderScrollDirection.defaultVertical.rawValue } return value } set (value) { - FolioReader.defaults.setValue(value, forKey: kCurrentScrollDirection) + self.defaults.set(value, forKey: kCurrentScrollDirection) let direction = (FolioReaderScrollDirection(rawValue: currentScrollDirection) ?? .defaultVertical) self.readerCenter?.setScrollDirection(direction) } } -} -// MARK: - Present Folio Reader + open var currentMenuIndex: Int { + get { return self.defaults.integer(forKey: kCurrentTOCMenu) } + set (value) { + self.defaults.set(value, forKey: kCurrentTOCMenu) + } + } -extension FolioReader { + open var savedPositionForCurrentBook: [String: Any]? { + get { + guard let bookId = self.readerContainer?.book.name else { + return nil + } - /** - Present a Folio Reader for a Parent View Controller. - */ - open class func presentReader(parentViewController: UIViewController, withEpubPath epubPath: String, andConfig config: FolioReaderConfig, shouldRemoveEpub: Bool = true, animated: - Bool = true) -> FolioReaderContainer { - // TODO_SMF_DOC - let folioReader = FolioReader() - let readerContainer = FolioReaderContainer(withConfig: config, folioReader: folioReader, epubPath: epubPath, removeEpub: shouldRemoveEpub) - folioReader.readerContainer = readerContainer - parentViewController.present(readerContainer, animated: animated, completion: nil) - // TODO_SMF_DOC - FolioReader.shared = folioReader - return readerContainer - } + return self.defaults.value(forKey: bookId) as? [String : Any] + } + set { + guard let bookId = self.readerContainer?.book.name else { + return + } + + self.defaults.set(newValue, forKey: bookId) + } + } } // MARK: - Image Cover @@ -266,7 +304,9 @@ extension FolioReader { /// Save Reader state, book, page and scroll offset. open func saveReaderState() { - guard self.isReaderOpen else { return } + guard (self.isReaderOpen == true) else { + return + } guard let bookId = self.readerContainer?.book.name, @@ -280,7 +320,7 @@ extension FolioReader { "pageOffsetY": currentPage.webView.scrollView.contentOffset.y ] as [String : Any] - FolioReader.defaults.set(position, forKey: bookId) + self.savedPositionForCurrentBook = position } /// Closes and save the reader current instance. @@ -289,7 +329,7 @@ extension FolioReader { self.isReaderOpen = false self.isReaderReady = false self.readerAudioPlayer?.stop(immediate: true) - FolioReader.defaults.set(0, forKey: kCurrentTOCMenu) + self.defaults.set(0, forKey: kCurrentTOCMenu) self.delegate?.folioReaderDidClosed?(self) self.delegate?.folioReaderDidClosed?() } diff --git a/Source/FolioReaderPage.swift b/Source/FolioReaderPage.swift index d34c5a328..f91336d60 100755 --- a/Source/FolioReaderPage.swift +++ b/Source/FolioReaderPage.swift @@ -40,11 +40,16 @@ open class FolioReaderPage: UICollectionViewCell, UIWebViewDelegate, UIGestureRe fileprivate var shouldShowBar = true fileprivate var menuIsVisible = false - fileprivate var readerConfig : FolioReaderConfig fileprivate var readerContainer : FolioReaderContainer + + fileprivate var readerConfig : FolioReaderConfig { + return readerContainer.readerConfig + } + fileprivate var book : FRBook { return self.readerContainer.book } + fileprivate var folioReader : FolioReader { return self.readerContainer.folioReader } @@ -53,14 +58,12 @@ open class FolioReaderPage: UICollectionViewCell, UIWebViewDelegate, UIGestureRe public override init(frame: CGRect) { // Init explicit attributes with a default value. The `setup` function MUST be called to configure the current object with valid attributes. - self.readerConfig = FolioReaderConfig() - self.readerContainer = FolioReaderContainer(withConfig: self.readerConfig, folioReader: FolioReader(), epubPath: "") + self.readerContainer = FolioReaderContainer(withConfig: FolioReaderConfig(), folioReader: FolioReader(), epubPath: "") super.init(frame: frame) } - public func setup(withReaderConfig readerConfig: FolioReaderConfig, readerContainer: FolioReaderContainer) { - self.readerConfig = readerConfig + public func setup(withReaderContainer readerContainer: FolioReaderContainer) { self.readerContainer = readerContainer self.backgroundColor = UIColor.clear diff --git a/Source/FolioReaderUserDefaults.swift b/Source/FolioReaderUserDefaults.swift new file mode 100644 index 000000000..e71b47d84 --- /dev/null +++ b/Source/FolioReaderUserDefaults.swift @@ -0,0 +1,82 @@ +// +// FolioReaderUserDefaults.swift +// Pods +// +// Created by Kevin Delord on 01/04/17. +// +// + +import Foundation + +class FolioReaderUserDefaults { + + fileprivate var userDefaults : [String: Any] + fileprivate var identifier : String + + init(withIdentifier identifier: String) { + self.identifier = identifier + + guard let defaults = UserDefaults.standard.value(forKey: identifier) as? [String: Any] else { + let emptyDefaults = [String: Any]() + UserDefaults.standard.set(emptyDefaults, forKey: identifier) + UserDefaults.standard.synchronize() + self.userDefaults = emptyDefaults + return + } + + self.userDefaults = defaults + } + + public func synchronize() { + guard (self.identifier != "") else { + fatalError("invalid user default unique identifier") + return + } + + UserDefaults.standard.set(self.userDefaults, forKey: self.identifier) + UserDefaults.standard.synchronize() + } +} + +// MARK: - Getter + +extension FolioReaderUserDefaults { + + internal func bool(forKey key: String) -> Bool { + guard let value = self.userDefaults[key] as? Bool else { + return false + } + + return value + } + + internal func integer(forKey key: String) -> Int { + guard let value = self.userDefaults[key] as? Int else { + return 0 + } + + return value + } + + internal func value(forKey key: String) -> Any? { + return self.userDefaults[key] + } +} + +// MARK: - Setter + +extension FolioReaderUserDefaults { + + internal func register(defaults: [String: Any]) { + for (key, value) in defaults { + self.userDefaults[key] = value + } + + self.synchronize() + } + + internal func set(_ value: Any?, forKey key: String) { + self.userDefaults[key] = value + self.synchronize() + } +} diff --git a/Source/PageViewController.swift b/Source/PageViewController.swift index 3d563e2d7..5fd99d90e 100644 --- a/Source/PageViewController.swift +++ b/Source/PageViewController.swift @@ -15,8 +15,7 @@ class PageViewController: UIPageViewController { var segmentedControlItems = [String]() var viewControllerOne: UIViewController! var viewControllerTwo: UIViewController! - var index = FolioReader.defaults.integer(forKey: kCurrentTOCMenu) - + var index : Int fileprivate var readerConfig : FolioReaderConfig fileprivate var folioReader : FolioReader @@ -25,6 +24,7 @@ class PageViewController: UIPageViewController { init(folioReader: FolioReader, readerConfig: FolioReaderConfig) { self.folioReader = folioReader self.readerConfig = readerConfig + self.index = self.folioReader.currentMenuIndex super.init(transitionStyle: .scroll, navigationOrientation: .horizontal, options: nil) self.edgesForExtendedLayout = UIRectEdge() @@ -83,10 +83,10 @@ class PageViewController: UIPageViewController { // MARK: - Segmented control changes func didSwitchMenu(_ sender: UISegmentedControl) { - index = sender.selectedSegmentIndex - let direction: UIPageViewControllerNavigationDirection = index == 0 ? .reverse : .forward + self.index = sender.selectedSegmentIndex + let direction: UIPageViewControllerNavigationDirection = (index == 0 ? .reverse : .forward) setViewControllers([viewList[index]], direction: direction, animated: true, completion: nil) - FolioReader.defaults.set(index, forKey: kCurrentTOCMenu) + self.folioReader.currentMenuIndex = index } // MARK: - Status Bar From 626ad07f8ac36d858f0862465b57048214a827e4 Mon Sep 17 00:00:00 2001 From: Kevin Delord Date: Sat, 1 Apr 2017 22:55:32 +0200 Subject: [PATCH 050/110] Add documentation --- Source/FolioReaderContainer.swift | 8 ++++++-- Source/FolioReaderKit.swift | 13 ++++++++++--- 2 files changed, 16 insertions(+), 5 deletions(-) diff --git a/Source/FolioReaderContainer.swift b/Source/FolioReaderContainer.swift index ed9bc9efc..3fdd115e1 100755 --- a/Source/FolioReaderContainer.swift +++ b/Source/FolioReaderContainer.swift @@ -32,7 +32,7 @@ open class FolioReaderContainer : UIViewController { /// - Parameters: /// - config: Current Folio Reader configuration /// - folioReader: Current instance of the FolioReader kit. - /// - path: The ePub path on system + /// - path: The ePub path on system. Must not be nil nor empty string. /// - removeEpub: Should delete the original file after unzip? Default to `true` so the ePub will be unziped only once. public init(withConfig config: FolioReaderConfig, folioReader: FolioReader, epubPath path: String, removeEpub: Bool = true) { self.readerConfig = config @@ -43,7 +43,10 @@ open class FolioReaderContainer : UIViewController { super.init(nibName: nil, bundle: Bundle.frameworkBundle()) + // Configure the folio reader. self.folioReader.readerContainer = self + + // Initialize the default reader options. if (self.epubPath != "") { self.initialization() } @@ -62,6 +65,7 @@ open class FolioReaderContainer : UIViewController { super.init(coder: aDecoder) + // Configure the folio reader. self.folioReader.readerContainer = self } @@ -87,7 +91,7 @@ open class FolioReaderContainer : UIViewController { /// /// - Parameters: /// - config: Current Folio Reader configuration - /// - path: The ePub path on system + /// - path: The ePub path on system. Must not be nil nor empty string. /// - removeEpub: Should delete the original file after unzip? Default to `true` so the ePub will be unziped only once. open func setupConfig(_ config: FolioReaderConfig, epubPath path: String, removeEpub: Bool = true) { self.readerConfig = config diff --git a/Source/FolioReaderKit.swift b/Source/FolioReaderKit.swift index afb29504f..77788d0fe 100755 --- a/Source/FolioReaderKit.swift +++ b/Source/FolioReaderKit.swift @@ -97,6 +97,7 @@ open class FolioReader: NSObject { return (self.nightMode == true ? f : l) } + /// UserDefault for the current ePub file. fileprivate var defaults: FolioReaderUserDefaults { guard @@ -116,9 +117,15 @@ open class FolioReader: NSObject { extension FolioReader { - /** - Present a Folio Reader for a Parent View Controller. - */ + /// Present a Folio Reader Container modally on a Parent View Controller. + /// + /// - Parameters: + /// - parentViewController: View Controller that will present the reader container. + /// - epubPath: String representing the path on the disk of the ePub file. Must not be nil nor empty string. + /// - config: FolioReader configuration. + /// - shouldRemoveEpub: Boolean to remove the epub or not. Default true. + /// - animated: Pass true to animate the presentation; otherwise, pass false. + /// - Returns: The new and presented FolioReaderContainer instance. open class func presentReader(parentViewController: UIViewController, withEpubPath epubPath: String, andConfig config: FolioReaderConfig, shouldRemoveEpub: Bool = true, animated: Bool = true) -> FolioReaderContainer { // TODO_SMF_DOC From c9b16f406d74aa66690b26d20b21cd02a7ed9c97 Mon Sep 17 00:00:00 2001 From: Kevin Delord Date: Sat, 1 Apr 2017 23:09:57 +0200 Subject: [PATCH 051/110] Fix typo in delegate function name --- Source/FolioReaderCenter.swift | 1 - Source/FolioReaderKit.swift | 7 ++----- 2 files changed, 2 insertions(+), 6 deletions(-) diff --git a/Source/FolioReaderCenter.swift b/Source/FolioReaderCenter.swift index 2f9a9da09..07a15f3f1 100755 --- a/Source/FolioReaderCenter.swift +++ b/Source/FolioReaderCenter.swift @@ -88,7 +88,6 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo } required public init?(coder aDecoder: NSCoder) { - // TODO_SMF_QUESTION: is that ok? do 'we' really support NSCoding? fatalError("This class doesn't support NSCoding.") } diff --git a/Source/FolioReaderKit.swift b/Source/FolioReaderKit.swift index 77788d0fe..e11241a55 100755 --- a/Source/FolioReaderKit.swift +++ b/Source/FolioReaderKit.swift @@ -55,10 +55,9 @@ enum MediaOverlayStyle: Int { /// Called when reader did closed. /// /// - Parameter folioReader: The FolioReader instance - @objc optional func folioReaderDidClosed(_ folioReader: FolioReader) + @objc optional func folioReaderDidClose(_ folioReader: FolioReader) // TODO_SMF_CHECK: make sure the following deprecated functions still work... or not.: - // TODO_SMF_QUESTION: ask the main developer(s) for that. // TODO_SMF_DOC: new function signature change @objc optional func folioReaderDidClosed() } @@ -337,7 +336,7 @@ extension FolioReader { self.isReaderReady = false self.readerAudioPlayer?.stop(immediate: true) self.defaults.set(0, forKey: kCurrentTOCMenu) - self.delegate?.folioReaderDidClosed?(self) + self.delegate?.folioReaderDidClose?(self) self.delegate?.folioReaderDidClosed?() } } @@ -430,8 +429,6 @@ extension FolioReader { extension FolioReader { - // TODO_SMF_DEPRECATE and find a replacement for those functions. - /// Called when the application will resign active open class func applicationWillResignActive() { // TODO_SMF_DEPRECATE From 04bf4733c70f7e9e38efda67fc4864a2bd645087 Mon Sep 17 00:00:00 2001 From: Kevin Delord Date: Sat, 1 Apr 2017 23:26:32 +0200 Subject: [PATCH 052/110] FolioReader: mark functions as deprecated --- Source/FolioReaderKit.swift | 40 +++++++++++++------------------------ 1 file changed, 14 insertions(+), 26 deletions(-) diff --git a/Source/FolioReaderKit.swift b/Source/FolioReaderKit.swift index e11241a55..96a601087 100755 --- a/Source/FolioReaderKit.swift +++ b/Source/FolioReaderKit.swift @@ -343,9 +343,9 @@ extension FolioReader { // MARK: - Public static functions. All Deprecated function +@available(*, deprecated, message: "Shared instance removed. Use a local instance instead.") extension FolioReader { - // TODO_SMF_DEPRECATE private static var _sharedInstance = FolioReader() open static var shared : FolioReader { get { return _sharedInstance } @@ -354,91 +354,79 @@ extension FolioReader { /// Check the current Media Overlay or TTS style static var currentMediaOverlayStyle: MediaOverlayStyle { - // TODO_SMF_DEPRECATE return FolioReader.shared.currentMediaOverlayStyle } /// Check if current theme is Night mode open class var nightMode: Bool { - // TODO_SMF_DEPRECATE get { return FolioReader.shared.nightMode } set { FolioReader.shared.nightMode = newValue } } /// Check current font name open class var currentFont: FolioReaderFont { - // TODO_SMF_DEPRECATE get { return FolioReader.shared.currentFont } set { FolioReader.shared.currentFont = newValue } } /// Check current font size open class var currentFontSize: FolioReaderFontSize { - // TODO_SMF_DEPRECATE get { return FolioReader.shared.currentFontSize } set { FolioReader.shared.currentFontSize = newValue } } /// Check the current scroll direction open class var currentScrollDirection: Int { - // TODO_SMF_DEPRECATE get { return FolioReader.shared.currentScrollDirection } set { FolioReader.shared.currentScrollDirection = newValue } } /// Check current audio rate, the speed of speech voice open class var currentAudioRate: Int { - // TODO_SMF_DEPRECATE get { return FolioReader.shared.currentAudioRate } set { FolioReader.shared.currentAudioRate = newValue } } /// Check if reader is open and ready open class var isReaderReady : Bool { - // TODO_SMF_DEPRECATE return FolioReader.shared.isReaderReady } /// Save Reader state, book, page and scroll are saved open class func saveReaderState() { - // TODO_SMF_DEPRECATE FolioReader.shared.saveReaderState() } /// Closes and save the reader current instance open class func close() { - // TODO_SMF_DEPRECATE FolioReader.shared.close() } /// Check the current highlight style open class var currentHighlightStyle: Int { - // TODO_SMF_DEPRECATE get { return FolioReader.shared.currentHighlightStyle } set { FolioReader.shared.currentHighlightStyle = newValue } } /// Check if layout needs to change to fit Right To Left open class var needsRTLChange: Bool { - // TODO_SMF_DEPRECATE return FolioReader.shared.needsRTLChange } } // MARK: - Application State +@available(*, deprecated, message: "Use 'saveReaderState' on a FolioReaderContainer object instead.") extension FolioReader { /// Called when the application will resign active open class func applicationWillResignActive() { - // TODO_SMF_DEPRECATE // TODO_DOC: no replacement required. Call `aFolioReader.saveReaderState()` instead FolioReader.shared.saveReaderState() } /// Called when the application will terminate open class func applicationWillTerminate() { - // TODO_SMF_DEPRECATE // TODO_DOC: no replacement required. Call `aFolioReader.saveReaderState()` instead FolioReader.shared.saveReaderState() } @@ -446,16 +434,16 @@ extension FolioReader { // MARK: - Global Functions +@available(*, deprecated, message: "Shared instance removed. Use a local instance instead.") func isNight (_ f: T, _ l: T) -> T { - // TODO_SMF_DEPRECATE // TODO_SMF_DOC: notify change return (FolioReader.shared.nightMode == true ? f : l) } // MARK: - Scroll Direction Functions +@available(*, deprecated, message: "Shared instance removed. Use a local instance instead.") func isDirection (_ vertical: T, _ horizontal: T, _ horizontalContentVertical: T? = nil) -> T { - // TODO_SMF_DEPRECATE // TODO_SMF_DOC: notify change let direction = (FolioReader.shared.readerContainer!.readerConfig.scrollDirection) switch direction { @@ -467,8 +455,8 @@ func isDirection (_ vertical: T, _ horizontal: T, _ horizontalContentVertical extension UICollectionViewScrollDirection { + @available(*, deprecated, message: "Use 'direction(withConfiguration:)' instead.") static func direction() -> UICollectionViewScrollDirection { - // TODO_SMF_DEPRECATE guard let readerConfig = FolioReader.shared.readerContainer?.readerConfig else { return .vertical } @@ -484,8 +472,8 @@ extension UICollectionViewScrollDirection { extension UICollectionViewScrollPosition { + @available(*, deprecated, message: "Use 'direction(withConfiguration:)' instead.") static func direction() -> UICollectionViewScrollPosition { - // TODO_SMF_DEPRECATE guard let readerConfig = FolioReader.shared.readerContainer?.readerConfig else { return .top } @@ -501,8 +489,8 @@ extension UICollectionViewScrollPosition { extension CGPoint { + @available(*, deprecated, message: "Use 'forDirection(withConfiguration:)' instead.") func forDirection() -> CGFloat { - // TODO_SMF_DEPRECATE guard let readerConfig = FolioReader.shared.readerContainer?.readerConfig else { return self.y } @@ -518,8 +506,8 @@ extension CGPoint { extension CGSize { + @available(*, deprecated, message: "Use 'forDirection(withConfiguration:)' instead.") func forDirection() -> CGFloat { - // TODO_SMF_DEPRECATE guard let readerConfig = FolioReader.shared.readerContainer?.readerConfig else { return self.height } @@ -531,8 +519,8 @@ extension CGSize { return readerConfig.isDirection(height, width, height) } + @available(*, deprecated, message: "Use 'forReverseDirection(withConfiguration:)' instead.") func forReverseDirection() -> CGFloat { - // TODO_SMF_DEPRECATE guard let readerConfig = FolioReader.shared.readerContainer?.readerConfig else { return self.width } @@ -548,8 +536,8 @@ extension CGSize { extension CGRect { + @available(*, deprecated, message: "Use 'forDirection(withConfiguration:)' instead.") func forDirection() -> CGFloat { - // TODO_SMF_DEPRECATE guard let readerConfig = FolioReader.shared.readerContainer?.readerConfig else { return self.height } @@ -565,8 +553,8 @@ extension CGRect { extension ScrollDirection { + @available(*, deprecated, message: "Use 'negative(withConfiguration:)' instead.") static func negative() -> ScrollDirection { - // TODO_SMF_DEPRECATE guard let readerConfig = FolioReader.shared.readerContainer?.readerConfig else { return self.down } @@ -579,8 +567,8 @@ extension ScrollDirection { return readerConfig.isDirection(.down, .right, .right) } + @available(*, deprecated, message: "Use 'positive(withConfiguration:)' instead.") static func positive() -> ScrollDirection { - // TODO_SMF_DEPRECATE guard let readerConfig = FolioReader.shared.readerContainer?.readerConfig else { return self.up } @@ -853,8 +841,8 @@ internal extension UIImage { /// Forces the image to be colored with Reader Config tintColor /// /// - Returns: Returns a colored image + @available(*, deprecated, message: "Use 'ignoreSystemTint(withConfiguration:)' instead.") func ignoreSystemTint() -> UIImage? { - // TODO_SMF_DEPRECATE guard let readerConfig = FolioReader.shared.readerContainer?.readerConfig else { return nil } @@ -954,8 +942,8 @@ internal extension UIImage { internal extension UIViewController { + @available(*, deprecated, message: "Use 'setCloseButton(withConfiguration:)' instead.") func setCloseButton() { - // TODO_SMF_DEPRECATE guard let config = FolioReader.shared.readerContainer?.readerConfig else { return } From 7bb0b6880aba5c82d9e2994a6d5f86d76876f61f Mon Sep 17 00:00:00 2001 From: Kevin Delord Date: Sat, 1 Apr 2017 23:32:44 +0200 Subject: [PATCH 053/110] Highlight: mark functions as deprecated --- Source/Models/Highlight+Helper.swift | 16 ++++++++-------- 1 file changed, 8 insertions(+), 8 deletions(-) diff --git a/Source/Models/Highlight+Helper.swift b/Source/Models/Highlight+Helper.swift index dc5d89c89..414a25866 100644 --- a/Source/Models/Highlight+Helper.swift +++ b/Source/Models/Highlight+Helper.swift @@ -205,24 +205,24 @@ extension Highlight { extension Highlight { + @available(*, deprecated, message: "Shared instance removed. Use a local instance instead.") private static var readerConfig : FolioReaderConfig { - // TODO_SMF_DEPRECATE return FolioReader.shared.readerContainer!.readerConfig } /// Save a Highlight with completion block /// /// - Parameter completion: Completion block + @available(*, deprecated, message: "Use 'persist(withConfiguration:completion:)' instead.") public func persist(_ completion: Completion? = nil) { - // TODO_SMF_DEPRECATE self.persist(withConfiguration: Highlight.readerConfig, completion: completion) } /// Return all Highlights /// /// - Returns: Return all Highlights + @available(*, deprecated, message: "Use 'all(withConfiguration:)' instead.") public static func all() -> [Highlight] { - // TODO_SMF_DEPRECATE return Highlight.all(withConfiguration: Highlight.readerConfig) } @@ -232,8 +232,8 @@ extension Highlight { /// - bookId: Book ID /// - page: Page number /// - Returns: Return a list of Highlights + @available(*, deprecated, message: "Use 'allByBookId(withConfiguration:bookId:andPage:)' instead.") public static func allByBookId(_ bookId: String, andPage page: NSNumber? = nil) -> [Highlight] { - // TODO_SMF_DEPRECATE return Highlight.allByBookId(withConfiguration: Highlight.readerConfig, bookId: bookId, andPage: page) } @@ -242,22 +242,22 @@ extension Highlight { /// - Parameters: /// - highlightId: The ID to be removed /// - type: The `HighlightStyle` + @available(*, deprecated, message: "Use 'updateById(withConfiguration:highlightId:type:)' instead.") public static func updateById(_ highlightId: String, type: HighlightStyle) { - // TODO_SMF_DEPRECATE: deprecate Highlight.updateById(withConfiguration: Highlight.readerConfig, highlightId: highlightId, type: type) } /// Remove a Highlight by ID /// /// - Parameter highlightId: The ID to be removed + @available(*, deprecated, message: "Use 'removeById(withConfiguration:highlightId:)' instead.") public static func removeById(_ highlightId: String) { - // TODO_SMF_DEPRECATE Highlight.removeById(withConfiguration: Highlight.readerConfig, highlightId: highlightId) } /// Remove a Highlight + @available(*, deprecated, message: "Use 'remove(withConfiguration:)' instead.") public func remove() { - // TODO_SMF_DEPRECATE self.remove(withConfiguration: Highlight.readerConfig) } @@ -265,8 +265,8 @@ extension Highlight { /// /// - Parameter highlightId: The ID to be removed /// - Returns: The removed id + @available(*, deprecated, message: "Use 'removeFromHTMLById(withinPage:highlightId:)' instead.") @discardableResult public static func removeFromHTMLById(_ highlightId: String) -> String? { - // TODO_SMF_DEPRECATE let page = FolioReader.shared.readerCenter?.currentPage return self.removeFromHTMLById(withinPage: page, highlightId: highlightId) } From 9a73d5eab60bf58bf03c673cd74a720108d6588a Mon Sep 17 00:00:00 2001 From: Kevin Delord Date: Sat, 1 Apr 2017 23:53:44 +0200 Subject: [PATCH 054/110] Remove TODO_SMF_DOCs and create new extensions file --- Source/EPUBCore/FREpubParser.swift | 1 - Source/Extensions.swift | 605 ++++++++++++++++++++++++++ Source/FolioReaderKit.swift | 607 +-------------------------- Source/Models/Highlight+Helper.swift | 7 - migration.md | 44 ++ 5 files changed, 650 insertions(+), 614 deletions(-) create mode 100644 Source/Extensions.swift create mode 100644 migration.md diff --git a/Source/EPUBCore/FREpubParser.swift b/Source/EPUBCore/FREpubParser.swift index 1efc74f6c..5fc20b044 100755 --- a/Source/EPUBCore/FREpubParser.swift +++ b/Source/EPUBCore/FREpubParser.swift @@ -30,7 +30,6 @@ class FREpubParser : NSObject, SSZipArchiveDelegate { /// - unzipPath: Path to unzip the compressed epub. /// - Returns: An UIImage object func parseCoverImage(_ epubPath: String, unzipPath: String? = nil) -> UIImage? { - // TODO_SMF_DOC: new function signature change guard let book = readEpub(epubPath: epubPath, removeEpub: false, unzipPath: unzipPath), let coverImage = book.coverImage else { diff --git a/Source/Extensions.swift b/Source/Extensions.swift new file mode 100644 index 000000000..179469795 --- /dev/null +++ b/Source/Extensions.swift @@ -0,0 +1,605 @@ +// +// Extensions.swift +// Pods +// +// Created by Kevin Delord on 01/04/17. +// +// + +import Foundation +import UIKit + +extension UICollectionViewScrollDirection { + + @available(*, deprecated, message: "Use 'direction(withConfiguration:)' instead.") + static func direction() -> UICollectionViewScrollDirection { + guard let readerConfig = FolioReader.shared.readerContainer?.readerConfig else { + return .vertical + } + + return UICollectionViewScrollDirection.direction(withConfiguration: readerConfig) + } + + static func direction(withConfiguration readerConfig: FolioReaderConfig) -> UICollectionViewScrollDirection { + return readerConfig.isDirection(.vertical, .horizontal, .horizontal) + } +} + +extension UICollectionViewScrollPosition { + + @available(*, deprecated, message: "Use 'direction(withConfiguration:)' instead.") + static func direction() -> UICollectionViewScrollPosition { + guard let readerConfig = FolioReader.shared.readerContainer?.readerConfig else { + return .top + } + + return UICollectionViewScrollPosition.direction(withConfiguration: readerConfig) + } + + static func direction(withConfiguration readerConfig: FolioReaderConfig) -> UICollectionViewScrollPosition { + return readerConfig.isDirection(.top, .left, .left) + } +} + +extension CGPoint { + + @available(*, deprecated, message: "Use 'forDirection(withConfiguration:)' instead.") + func forDirection() -> CGFloat { + guard let readerConfig = FolioReader.shared.readerContainer?.readerConfig else { + return self.y + } + + return self.forDirection(withConfiguration: readerConfig) + } + + func forDirection(withConfiguration readerConfig: FolioReaderConfig) -> CGFloat { + return readerConfig.isDirection(self.y, self.x, self.y) + } +} + +extension CGSize { + + @available(*, deprecated, message: "Use 'forDirection(withConfiguration:)' instead.") + func forDirection() -> CGFloat { + guard let readerConfig = FolioReader.shared.readerContainer?.readerConfig else { + return self.height + } + return self.forDirection(withConfiguration: readerConfig) + } + + func forDirection(withConfiguration readerConfig: FolioReaderConfig) -> CGFloat { + return readerConfig.isDirection(height, width, height) + } + + @available(*, deprecated, message: "Use 'forReverseDirection(withConfiguration:)' instead.") + func forReverseDirection() -> CGFloat { + guard let readerConfig = FolioReader.shared.readerContainer?.readerConfig else { + return self.width + } + + return self.forReverseDirection(withConfiguration: readerConfig) + } + + func forReverseDirection(withConfiguration readerConfig: FolioReaderConfig) -> CGFloat { + return readerConfig.isDirection(width, height, width) + } +} + +extension CGRect { + + @available(*, deprecated, message: "Use 'forDirection(withConfiguration:)' instead.") + func forDirection() -> CGFloat { + guard let readerConfig = FolioReader.shared.readerContainer?.readerConfig else { + return self.height + } + + return self.forDirection(withConfiguration: readerConfig) + } + + func forDirection(withConfiguration readerConfig: FolioReaderConfig) -> CGFloat { + return readerConfig.isDirection(height, width, height) + } +} + +extension ScrollDirection { + + @available(*, deprecated, message: "Use 'negative(withConfiguration:)' instead.") + static func negative() -> ScrollDirection { + guard let readerConfig = FolioReader.shared.readerContainer?.readerConfig else { + return self.down + } + + return self.negative(withConfiguration: readerConfig) + } + + static func negative(withConfiguration readerConfig: FolioReaderConfig) -> ScrollDirection { + return readerConfig.isDirection(.down, .right, .right) + } + + @available(*, deprecated, message: "Use 'positive(withConfiguration:)' instead.") + static func positive() -> ScrollDirection { + guard let readerConfig = FolioReader.shared.readerContainer?.readerConfig else { + return self.up + } + + return self.positive(withConfiguration: readerConfig) + } + + static func positive(withConfiguration readerConfig: FolioReaderConfig) -> ScrollDirection { + return readerConfig.isDirection(.up, .left, .left) + } +} + +// MARK: Helpers + +/** +Delay function +From: http://stackoverflow.com/a/24318861/517707 + +- parameter delay: Delay in seconds +- parameter closure: Closure +*/ +func delay(_ delay:Double, closure:@escaping ()->()) { + DispatchQueue.main.asyncAfter( + deadline: DispatchTime.now() + Double(Int64(delay * Double(NSEC_PER_SEC))) / Double(NSEC_PER_SEC), execute: closure) +} + + +// MARK: - Extensions + +internal extension Bundle { + class func frameworkBundle() -> Bundle { + return Bundle(for: FolioReader.self) + } +} + +internal extension UIColor { + convenience init(rgba: String) { + var red: CGFloat = 0.0 + var green: CGFloat = 0.0 + var blue: CGFloat = 0.0 + var alpha: CGFloat = 1.0 + + if rgba.hasPrefix("#") { + let index = rgba.characters.index(rgba.startIndex, offsetBy: 1) + let hex = rgba.substring(from: index) + let scanner = Scanner(string: hex) + var hexValue: CUnsignedLongLong = 0 + if scanner.scanHexInt64(&hexValue) { + switch (hex.characters.count) { + case 3: + red = CGFloat((hexValue & 0xF00) >> 8) / 15.0 + green = CGFloat((hexValue & 0x0F0) >> 4) / 15.0 + blue = CGFloat(hexValue & 0x00F) / 15.0 + break + case 4: + red = CGFloat((hexValue & 0xF000) >> 12) / 15.0 + green = CGFloat((hexValue & 0x0F00) >> 8) / 15.0 + blue = CGFloat((hexValue & 0x00F0) >> 4) / 15.0 + alpha = CGFloat(hexValue & 0x000F) / 15.0 + break + case 6: + red = CGFloat((hexValue & 0xFF0000) >> 16) / 255.0 + green = CGFloat((hexValue & 0x00FF00) >> 8) / 255.0 + blue = CGFloat(hexValue & 0x0000FF) / 255.0 + break + case 8: + red = CGFloat((hexValue & 0xFF000000) >> 24) / 255.0 + green = CGFloat((hexValue & 0x00FF0000) >> 16) / 255.0 + blue = CGFloat((hexValue & 0x0000FF00) >> 8) / 255.0 + alpha = CGFloat(hexValue & 0x000000FF) / 255.0 + break + default: + print("Invalid RGB string, number of characters after '#' should be either 3, 4, 6 or 8", terminator: "") + break + } + } else { + print("Scan hex error") + } + } else { + print("Invalid RGB string, missing '#' as prefix", terminator: "") + } + self.init(red:red, green:green, blue:blue, alpha:alpha) + } + + // + /// Hex string of a UIColor instance. + /// + /// from: https://github.com/yeahdongcn/UIColor-Hex-Swift + /// + /// - Parameter includeAlpha: Whether the alpha should be included. + /// - Returns: Hexa string + func hexString(_ includeAlpha: Bool) -> String { + var r: CGFloat = 0 + var g: CGFloat = 0 + var b: CGFloat = 0 + var a: CGFloat = 0 + self.getRed(&r, green: &g, blue: &b, alpha: &a) + + if (includeAlpha == true) { + return String(format: "#%02X%02X%02X%02X", Int(r * 255), Int(g * 255), Int(b * 255), Int(a * 255)) + } else { + return String(format: "#%02X%02X%02X", Int(r * 255), Int(g * 255), Int(b * 255)) + } + } + + // MARK: - color shades + // https://gist.github.com/mbigatti/c6be210a6bbc0ff25972 + + func highlightColor() -> UIColor { + + var hue : CGFloat = 0 + var saturation : CGFloat = 0 + var brightness : CGFloat = 0 + var alpha : CGFloat = 0 + + if getHue(&hue, saturation: &saturation, brightness: &brightness, alpha: &alpha) { + return UIColor(hue: hue, saturation: 0.30, brightness: 1, alpha: alpha) + } else { + return self; + } + + } + + /** + Returns a lighter color by the provided percentage + + :param: lighting percent percentage + :returns: lighter UIColor + */ + func lighterColor(_ percent : Double) -> UIColor { + return colorWithBrightnessFactor(CGFloat(1 + percent)); + } + + /** + Returns a darker color by the provided percentage + + :param: darking percent percentage + :returns: darker UIColor + */ + func darkerColor(_ percent : Double) -> UIColor { + return colorWithBrightnessFactor(CGFloat(1 - percent)); + } + + /** + Return a modified color using the brightness factor provided + + :param: factor brightness factor + :returns: modified color + */ + func colorWithBrightnessFactor(_ factor: CGFloat) -> UIColor { + var hue : CGFloat = 0 + var saturation : CGFloat = 0 + var brightness : CGFloat = 0 + var alpha : CGFloat = 0 + + if getHue(&hue, saturation: &saturation, brightness: &brightness, alpha: &alpha) { + return UIColor(hue: hue, saturation: saturation, brightness: brightness * factor, alpha: alpha) + } else { + return self; + } + } +} + +internal extension String { + /// Truncates the string to length number of characters and + /// appends optional trailing string if longer + func truncate(_ length: Int, trailing: String? = nil) -> String { + if self.characters.count > length { + return self.substring(to: self.characters.index(self.startIndex, offsetBy: length)) + (trailing ?? "") + } else { + return self + } + } + + func stripHtml() -> String { + return self.replacingOccurrences(of: "<[^>]+>", with: "", options: .regularExpression) + } + + func stripLineBreaks() -> String { + return self.replacingOccurrences(of: "\n", with: "", options: .regularExpression) + } + + /** + Converts a clock time such as `0:05:01.2` to seconds (`Double`) + + Looks for media overlay clock formats as specified [here][1] + + - Note: this may not be the most efficient way of doing this. It can be improved later on. + + - Returns: seconds as `Double` + + [1]: http://www.idpf.org/epub/301/spec/epub-mediaoverlays.html#app-clock-examples + */ + func clockTimeToSeconds() -> Double { + + let val = self.trimmingCharacters(in: CharacterSet.whitespaces) + + if( val.isEmpty ){ return 0 } + + let formats = [ + "HH:mm:ss.SSS" : "^\\d{1,2}:\\d{2}:\\d{2}\\.\\d{1,3}$", + "HH:mm:ss" : "^\\d{1,2}:\\d{2}:\\d{2}$", + "mm:ss.SSS" : "^\\d{1,2}:\\d{2}\\.\\d{1,3}$", + "mm:ss" : "^\\d{1,2}:\\d{2}$", + "ss.SSS" : "^\\d{1,2}\\.\\d{1,3}$", + ] + + // search for normal duration formats such as `00:05:01.2` + for (format, pattern) in formats { + + if val.range(of: pattern, options: .regularExpression) != nil { + + let formatter = DateFormatter() + formatter.dateFormat = format + let time = formatter.date(from: val) + + if( time == nil ){ return 0 } + + formatter.dateFormat = "ss.SSS" + let seconds = (formatter.string(from: time!) as NSString).doubleValue + + formatter.dateFormat = "mm" + let minutes = (formatter.string(from: time!) as NSString).doubleValue + + formatter.dateFormat = "HH" + let hours = (formatter.string(from: time!) as NSString).doubleValue + + return seconds + (minutes*60) + (hours*60*60) + } + } + + // if none of the more common formats match, check for other possible formats + + // 2345ms + if val.range(of: "^\\d+ms$", options: .regularExpression) != nil{ + return (val as NSString).doubleValue / 1000.0 + } + + // 7.25h + if val.range(of: "^\\d+(\\.\\d+)?h$", options: .regularExpression) != nil { + return (val as NSString).doubleValue * 60 * 60 + } + + // 13min + if val.range(of: "^\\d+(\\.\\d+)?min$", options: .regularExpression) != nil { + return (val as NSString).doubleValue * 60 + } + + return 0 + } + + func clockTimeToMinutesString() -> String { + + let val = clockTimeToSeconds() + + let min = floor(val / 60) + let sec = floor(val.truncatingRemainder(dividingBy: 60)) + + return String(format: "%02.f:%02.f", min, sec) + } +} + +internal extension UIImage { + + convenience init?(readerImageNamed: String) { + self.init(named: readerImageNamed, in: Bundle.frameworkBundle(), compatibleWith: nil) + } + + /// Forces the image to be colored with Reader Config tintColor + /// + /// - Returns: Returns a colored image + @available(*, deprecated, message: "Use 'ignoreSystemTint(withConfiguration:)' instead.") + func ignoreSystemTint() -> UIImage? { + guard let readerConfig = FolioReader.shared.readerContainer?.readerConfig else { + return nil + } + + return self.ignoreSystemTint(withConfiguration: readerConfig) + } + + /// Forces the image to be colored with Reader Config tintColor + /// + /// - Parameter readerConfig: Current folio reader configuration. + /// - Returns: Returns a colored image + func ignoreSystemTint(withConfiguration readerConfig: FolioReaderConfig) -> UIImage? { + return self.imageTintColor(readerConfig.tintColor)?.withRenderingMode(.alwaysOriginal) + } + + /** + Colorize the image with a color + + - parameter tintColor: The input color + - returns: Returns a colored image + */ + func imageTintColor(_ tintColor: UIColor) -> UIImage? { + UIGraphicsBeginImageContextWithOptions(self.size, false, self.scale) + + let context = UIGraphicsGetCurrentContext() + context?.translateBy(x: 0, y: self.size.height) + context?.scaleBy(x: 1.0, y: -1.0) + context?.setBlendMode(CGBlendMode.normal) + + let rect = CGRect(x: 0, y: 0, width: self.size.width, height: self.size.height) as CGRect + if let cgImage = self.cgImage { + context?.clip(to: rect, mask: cgImage) + } + + tintColor.setFill() + context?.fill(rect) + + let newImage = UIGraphicsGetImageFromCurrentImageContext() + UIGraphicsEndImageContext() + + return newImage + } + + /** + Generate a image with a color + + - parameter color: The input color + - returns: Returns a colored image + */ + class func imageWithColor(_ color: UIColor?) -> UIImage { + let rect = CGRect(x: 0.0, y: 0.0, width: 1.0, height: 1.0) + UIGraphicsBeginImageContextWithOptions(rect.size, false, 0) + let context = UIGraphicsGetCurrentContext() + + if let color = color { + color.setFill() + } else { + UIColor.white.setFill() + } + + context!.fill(rect) + let image = UIGraphicsGetImageFromCurrentImageContext() + UIGraphicsEndImageContext() + + return image! + } + + /** + Generates a image with a `CALayer` + + - parameter layer: The input `CALayer` + - returns: Return a rendered image + */ + class func imageWithLayer(_ layer: CALayer) -> UIImage { + UIGraphicsBeginImageContextWithOptions(layer.bounds.size, layer.isOpaque, 0.0) + layer.render(in: UIGraphicsGetCurrentContext()!) + let img = UIGraphicsGetImageFromCurrentImageContext() + UIGraphicsEndImageContext() + return img! + } + + /** + Generates a image from a `UIView` + + - parameter view: The input `UIView` + - returns: Return a rendered image + */ + class func imageWithView(_ view: UIView) -> UIImage { + UIGraphicsBeginImageContextWithOptions(view.bounds.size, view.isOpaque, 0.0) + view.drawHierarchy(in: view.bounds, afterScreenUpdates: true) + let img = UIGraphicsGetImageFromCurrentImageContext() + UIGraphicsEndImageContext() + return img! + } +} + +internal extension UIViewController { + + @available(*, deprecated, message: "Use 'setCloseButton(withConfiguration:)' instead.") + func setCloseButton() { + guard let config = FolioReader.shared.readerContainer?.readerConfig else { + return + } + + self.setCloseButton(withConfiguration: config) + } + + func setCloseButton(withConfiguration readerConfig: FolioReaderConfig) { + let closeImage = UIImage(readerImageNamed: "icon-navbar-close")?.ignoreSystemTint(withConfiguration: readerConfig) + self.navigationItem.leftBarButtonItem = UIBarButtonItem(image: closeImage, style: .plain, target: self, action: #selector(dismiss as (Void) -> Void)) + } + + func dismiss() { + self.dismiss(nil) + } + + func dismiss(_ completion: (() -> Void)?) { + DispatchQueue.main.async { + self.dismiss(animated: true, completion: { + completion?() + }) + } + } + + // MARK: - NavigationBar + + func setTransparentNavigation() { + let navBar = self.navigationController?.navigationBar + navBar?.setBackgroundImage(UIImage(), for: UIBarMetrics.default) + navBar?.hideBottomHairline() + navBar?.isTranslucent = true + } + + func setTranslucentNavigation(_ translucent: Bool = true, color: UIColor, tintColor: UIColor = UIColor.white, titleColor: UIColor = UIColor.black, andFont font: UIFont = UIFont.systemFont(ofSize: 17)) { + let navBar = self.navigationController?.navigationBar + navBar?.setBackgroundImage(UIImage.imageWithColor(color), for: UIBarMetrics.default) + navBar?.showBottomHairline() + navBar?.isTranslucent = translucent + navBar?.tintColor = tintColor + navBar?.titleTextAttributes = [NSForegroundColorAttributeName: titleColor, NSFontAttributeName: font] + } +} + +internal extension UINavigationBar { + + func hideBottomHairline() { + let navigationBarImageView = hairlineImageViewInNavigationBar(self) + navigationBarImageView!.isHidden = true + } + + func showBottomHairline() { + let navigationBarImageView = hairlineImageViewInNavigationBar(self) + navigationBarImageView!.isHidden = false + } + + fileprivate func hairlineImageViewInNavigationBar(_ view: UIView) -> UIImageView? { + if view.isKind(of: UIImageView.self) && view.bounds.height <= 1.0 { + return (view as! UIImageView) + } + + let subviews = (view.subviews ) + for subview: UIView in subviews { + if let imageView: UIImageView = hairlineImageViewInNavigationBar(subview) { + return imageView + } + } + return nil + } +} + +extension UINavigationController { + + open override var preferredStatusBarStyle : UIStatusBarStyle { + guard let viewController = visibleViewController else { return .default } + return viewController.preferredStatusBarStyle + } + + open override var supportedInterfaceOrientations : UIInterfaceOrientationMask { + guard let viewController = visibleViewController else { return .portrait } + return viewController.supportedInterfaceOrientations + } + + open override var shouldAutorotate : Bool { + guard let viewController = visibleViewController else { return false } + return viewController.shouldAutorotate + } +} + +/** +This fixes iOS 9 crash +http://stackoverflow.com/a/32010520/517707 +*/ +extension UIAlertController { + open override var supportedInterfaceOrientations : UIInterfaceOrientationMask { + return .portrait + } + + open override var shouldAutorotate : Bool { + return false + } +} + +extension Array { + + /** + Return index if is safe, if not return nil + http://stackoverflow.com/a/30593673/517707 + */ + subscript(safe index: Int) -> Element? { + return indices ~= index ? self[index] : nil + } +} diff --git a/Source/FolioReaderKit.swift b/Source/FolioReaderKit.swift index 96a601087..2d5357eb1 100755 --- a/Source/FolioReaderKit.swift +++ b/Source/FolioReaderKit.swift @@ -132,7 +132,7 @@ extension FolioReader { let readerContainer = FolioReaderContainer(withConfig: config, folioReader: folioReader, epubPath: epubPath, removeEpub: shouldRemoveEpub) folioReader.readerContainer = readerContainer parentViewController.present(readerContainer, animated: animated, completion: nil) - // TODO_SMF_DOC + // Set the shared instance to support old version. FolioReader.shared = folioReader return readerContainer } @@ -452,608 +452,3 @@ func isDirection (_ vertical: T, _ horizontal: T, _ horizontalContentVertical case .horizontalWithVerticalContent: return (horizontalContentVertical ?? vertical) } } - -extension UICollectionViewScrollDirection { - - @available(*, deprecated, message: "Use 'direction(withConfiguration:)' instead.") - static func direction() -> UICollectionViewScrollDirection { - guard let readerConfig = FolioReader.shared.readerContainer?.readerConfig else { - return .vertical - } - - return UICollectionViewScrollDirection.direction(withConfiguration: readerConfig) - } - - static func direction(withConfiguration readerConfig: FolioReaderConfig) -> UICollectionViewScrollDirection { - // TODO_SMF_DOC - return readerConfig.isDirection(.vertical, .horizontal, .horizontal) - } -} - -extension UICollectionViewScrollPosition { - - @available(*, deprecated, message: "Use 'direction(withConfiguration:)' instead.") - static func direction() -> UICollectionViewScrollPosition { - guard let readerConfig = FolioReader.shared.readerContainer?.readerConfig else { - return .top - } - - return UICollectionViewScrollPosition.direction(withConfiguration: readerConfig) - } - - static func direction(withConfiguration readerConfig: FolioReaderConfig) -> UICollectionViewScrollPosition { - // TODO_SMF_DOC - return readerConfig.isDirection(.top, .left, .left) - } -} - -extension CGPoint { - - @available(*, deprecated, message: "Use 'forDirection(withConfiguration:)' instead.") - func forDirection() -> CGFloat { - guard let readerConfig = FolioReader.shared.readerContainer?.readerConfig else { - return self.y - } - - return self.forDirection(withConfiguration: readerConfig) - } - - func forDirection(withConfiguration readerConfig: FolioReaderConfig) -> CGFloat { - // TODO_SMF_DOC - return readerConfig.isDirection(self.y, self.x, self.y) - } -} - -extension CGSize { - - @available(*, deprecated, message: "Use 'forDirection(withConfiguration:)' instead.") - func forDirection() -> CGFloat { - guard let readerConfig = FolioReader.shared.readerContainer?.readerConfig else { - return self.height - } - return self.forDirection(withConfiguration: readerConfig) - } - - func forDirection(withConfiguration readerConfig: FolioReaderConfig) -> CGFloat { - // TODO_SMF_DOC - return readerConfig.isDirection(height, width, height) - } - - @available(*, deprecated, message: "Use 'forReverseDirection(withConfiguration:)' instead.") - func forReverseDirection() -> CGFloat { - guard let readerConfig = FolioReader.shared.readerContainer?.readerConfig else { - return self.width - } - - return self.forReverseDirection(withConfiguration: readerConfig) - } - - func forReverseDirection(withConfiguration readerConfig: FolioReaderConfig) -> CGFloat { - // TODO_SMF_DOC - return readerConfig.isDirection(width, height, width) - } -} - -extension CGRect { - - @available(*, deprecated, message: "Use 'forDirection(withConfiguration:)' instead.") - func forDirection() -> CGFloat { - guard let readerConfig = FolioReader.shared.readerContainer?.readerConfig else { - return self.height - } - - return self.forDirection(withConfiguration: readerConfig) - } - - func forDirection(withConfiguration readerConfig: FolioReaderConfig) -> CGFloat { - // TODO_SMF_DOC - return readerConfig.isDirection(height, width, height) - } -} - -extension ScrollDirection { - - @available(*, deprecated, message: "Use 'negative(withConfiguration:)' instead.") - static func negative() -> ScrollDirection { - guard let readerConfig = FolioReader.shared.readerContainer?.readerConfig else { - return self.down - } - - return self.negative(withConfiguration: readerConfig) - } - - static func negative(withConfiguration readerConfig: FolioReaderConfig) -> ScrollDirection { - // TODO_SMF_DOC - return readerConfig.isDirection(.down, .right, .right) - } - - @available(*, deprecated, message: "Use 'positive(withConfiguration:)' instead.") - static func positive() -> ScrollDirection { - guard let readerConfig = FolioReader.shared.readerContainer?.readerConfig else { - return self.up - } - - return self.positive(withConfiguration: readerConfig) - } - - static func positive(withConfiguration readerConfig: FolioReaderConfig) -> ScrollDirection { - // TODO_SMF_DOC - return readerConfig.isDirection(.up, .left, .left) - } -} - -// MARK: Helpers - -/** - Delay function - From: http://stackoverflow.com/a/24318861/517707 - - - parameter delay: Delay in seconds - - parameter closure: Closure - */ -func delay(_ delay:Double, closure:@escaping ()->()) { - DispatchQueue.main.asyncAfter( - deadline: DispatchTime.now() + Double(Int64(delay * Double(NSEC_PER_SEC))) / Double(NSEC_PER_SEC), execute: closure) -} - - -// MARK: - Extensions - -internal extension Bundle { - class func frameworkBundle() -> Bundle { - return Bundle(for: FolioReader.self) - } -} - -internal extension UIColor { - convenience init(rgba: String) { - var red: CGFloat = 0.0 - var green: CGFloat = 0.0 - var blue: CGFloat = 0.0 - var alpha: CGFloat = 1.0 - - if rgba.hasPrefix("#") { - let index = rgba.characters.index(rgba.startIndex, offsetBy: 1) - let hex = rgba.substring(from: index) - let scanner = Scanner(string: hex) - var hexValue: CUnsignedLongLong = 0 - if scanner.scanHexInt64(&hexValue) { - switch (hex.characters.count) { - case 3: - red = CGFloat((hexValue & 0xF00) >> 8) / 15.0 - green = CGFloat((hexValue & 0x0F0) >> 4) / 15.0 - blue = CGFloat(hexValue & 0x00F) / 15.0 - break - case 4: - red = CGFloat((hexValue & 0xF000) >> 12) / 15.0 - green = CGFloat((hexValue & 0x0F00) >> 8) / 15.0 - blue = CGFloat((hexValue & 0x00F0) >> 4) / 15.0 - alpha = CGFloat(hexValue & 0x000F) / 15.0 - break - case 6: - red = CGFloat((hexValue & 0xFF0000) >> 16) / 255.0 - green = CGFloat((hexValue & 0x00FF00) >> 8) / 255.0 - blue = CGFloat(hexValue & 0x0000FF) / 255.0 - break - case 8: - red = CGFloat((hexValue & 0xFF000000) >> 24) / 255.0 - green = CGFloat((hexValue & 0x00FF0000) >> 16) / 255.0 - blue = CGFloat((hexValue & 0x0000FF00) >> 8) / 255.0 - alpha = CGFloat(hexValue & 0x000000FF) / 255.0 - break - default: - print("Invalid RGB string, number of characters after '#' should be either 3, 4, 6 or 8", terminator: "") - break - } - } else { - print("Scan hex error") - } - } else { - print("Invalid RGB string, missing '#' as prefix", terminator: "") - } - self.init(red:red, green:green, blue:blue, alpha:alpha) - } - - // - /// Hex string of a UIColor instance. - /// - /// from: https://github.com/yeahdongcn/UIColor-Hex-Swift - /// - /// - Parameter includeAlpha: Whether the alpha should be included. - /// - Returns: Hexa string - func hexString(_ includeAlpha: Bool) -> String { - var r: CGFloat = 0 - var g: CGFloat = 0 - var b: CGFloat = 0 - var a: CGFloat = 0 - self.getRed(&r, green: &g, blue: &b, alpha: &a) - - if (includeAlpha == true) { - return String(format: "#%02X%02X%02X%02X", Int(r * 255), Int(g * 255), Int(b * 255), Int(a * 255)) - } else { - return String(format: "#%02X%02X%02X", Int(r * 255), Int(g * 255), Int(b * 255)) - } - } - - // MARK: - color shades - // https://gist.github.com/mbigatti/c6be210a6bbc0ff25972 - - func highlightColor() -> UIColor { - - var hue : CGFloat = 0 - var saturation : CGFloat = 0 - var brightness : CGFloat = 0 - var alpha : CGFloat = 0 - - if getHue(&hue, saturation: &saturation, brightness: &brightness, alpha: &alpha) { - return UIColor(hue: hue, saturation: 0.30, brightness: 1, alpha: alpha) - } else { - return self; - } - - } - - /** - Returns a lighter color by the provided percentage - - :param: lighting percent percentage - :returns: lighter UIColor - */ - func lighterColor(_ percent : Double) -> UIColor { - return colorWithBrightnessFactor(CGFloat(1 + percent)); - } - - /** - Returns a darker color by the provided percentage - - :param: darking percent percentage - :returns: darker UIColor - */ - func darkerColor(_ percent : Double) -> UIColor { - return colorWithBrightnessFactor(CGFloat(1 - percent)); - } - - /** - Return a modified color using the brightness factor provided - - :param: factor brightness factor - :returns: modified color - */ - func colorWithBrightnessFactor(_ factor: CGFloat) -> UIColor { - var hue : CGFloat = 0 - var saturation : CGFloat = 0 - var brightness : CGFloat = 0 - var alpha : CGFloat = 0 - - if getHue(&hue, saturation: &saturation, brightness: &brightness, alpha: &alpha) { - return UIColor(hue: hue, saturation: saturation, brightness: brightness * factor, alpha: alpha) - } else { - return self; - } - } -} - -internal extension String { - /// Truncates the string to length number of characters and - /// appends optional trailing string if longer - func truncate(_ length: Int, trailing: String? = nil) -> String { - if self.characters.count > length { - return self.substring(to: self.characters.index(self.startIndex, offsetBy: length)) + (trailing ?? "") - } else { - return self - } - } - - func stripHtml() -> String { - return self.replacingOccurrences(of: "<[^>]+>", with: "", options: .regularExpression) - } - - func stripLineBreaks() -> String { - return self.replacingOccurrences(of: "\n", with: "", options: .regularExpression) - } - - /** - Converts a clock time such as `0:05:01.2` to seconds (`Double`) - - Looks for media overlay clock formats as specified [here][1] - - - Note: this may not be the most efficient way of doing this. It can be improved later on. - - - Returns: seconds as `Double` - - [1]: http://www.idpf.org/epub/301/spec/epub-mediaoverlays.html#app-clock-examples - */ - func clockTimeToSeconds() -> Double { - - let val = self.trimmingCharacters(in: CharacterSet.whitespaces) - - if( val.isEmpty ){ return 0 } - - let formats = [ - "HH:mm:ss.SSS" : "^\\d{1,2}:\\d{2}:\\d{2}\\.\\d{1,3}$", - "HH:mm:ss" : "^\\d{1,2}:\\d{2}:\\d{2}$", - "mm:ss.SSS" : "^\\d{1,2}:\\d{2}\\.\\d{1,3}$", - "mm:ss" : "^\\d{1,2}:\\d{2}$", - "ss.SSS" : "^\\d{1,2}\\.\\d{1,3}$", - ] - - // search for normal duration formats such as `00:05:01.2` - for (format, pattern) in formats { - - if val.range(of: pattern, options: .regularExpression) != nil { - - let formatter = DateFormatter() - formatter.dateFormat = format - let time = formatter.date(from: val) - - if( time == nil ){ return 0 } - - formatter.dateFormat = "ss.SSS" - let seconds = (formatter.string(from: time!) as NSString).doubleValue - - formatter.dateFormat = "mm" - let minutes = (formatter.string(from: time!) as NSString).doubleValue - - formatter.dateFormat = "HH" - let hours = (formatter.string(from: time!) as NSString).doubleValue - - return seconds + (minutes*60) + (hours*60*60) - } - } - - // if none of the more common formats match, check for other possible formats - - // 2345ms - if val.range(of: "^\\d+ms$", options: .regularExpression) != nil{ - return (val as NSString).doubleValue / 1000.0 - } - - // 7.25h - if val.range(of: "^\\d+(\\.\\d+)?h$", options: .regularExpression) != nil { - return (val as NSString).doubleValue * 60 * 60 - } - - // 13min - if val.range(of: "^\\d+(\\.\\d+)?min$", options: .regularExpression) != nil { - return (val as NSString).doubleValue * 60 - } - - return 0 - } - - func clockTimeToMinutesString() -> String { - - let val = clockTimeToSeconds() - - let min = floor(val / 60) - let sec = floor(val.truncatingRemainder(dividingBy: 60)) - - return String(format: "%02.f:%02.f", min, sec) - } -} - -internal extension UIImage { - - convenience init?(readerImageNamed: String) { - self.init(named: readerImageNamed, in: Bundle.frameworkBundle(), compatibleWith: nil) - } - - /// Forces the image to be colored with Reader Config tintColor - /// - /// - Returns: Returns a colored image - @available(*, deprecated, message: "Use 'ignoreSystemTint(withConfiguration:)' instead.") - func ignoreSystemTint() -> UIImage? { - guard let readerConfig = FolioReader.shared.readerContainer?.readerConfig else { - return nil - } - - return self.ignoreSystemTint(withConfiguration: readerConfig) - } - - /// Forces the image to be colored with Reader Config tintColor - /// - /// - Parameter readerConfig: Current folio reader configuration. - /// - Returns: Returns a colored image - func ignoreSystemTint(withConfiguration readerConfig: FolioReaderConfig) -> UIImage? { - // TODO_SMF_DOC - return self.imageTintColor(readerConfig.tintColor)?.withRenderingMode(.alwaysOriginal) - } - - /** - Colorize the image with a color - - - parameter tintColor: The input color - - returns: Returns a colored image - */ - func imageTintColor(_ tintColor: UIColor) -> UIImage? { - UIGraphicsBeginImageContextWithOptions(self.size, false, self.scale) - - let context = UIGraphicsGetCurrentContext() - context?.translateBy(x: 0, y: self.size.height) - context?.scaleBy(x: 1.0, y: -1.0) - context?.setBlendMode(CGBlendMode.normal) - - let rect = CGRect(x: 0, y: 0, width: self.size.width, height: self.size.height) as CGRect - if let cgImage = self.cgImage { - context?.clip(to: rect, mask: cgImage) - } - - tintColor.setFill() - context?.fill(rect) - - let newImage = UIGraphicsGetImageFromCurrentImageContext() - UIGraphicsEndImageContext() - - return newImage - } - - /** - Generate a image with a color - - - parameter color: The input color - - returns: Returns a colored image - */ - class func imageWithColor(_ color: UIColor?) -> UIImage { - let rect = CGRect(x: 0.0, y: 0.0, width: 1.0, height: 1.0) - UIGraphicsBeginImageContextWithOptions(rect.size, false, 0) - let context = UIGraphicsGetCurrentContext() - - if let color = color { - color.setFill() - } else { - UIColor.white.setFill() - } - - context!.fill(rect) - let image = UIGraphicsGetImageFromCurrentImageContext() - UIGraphicsEndImageContext() - - return image! - } - - /** - Generates a image with a `CALayer` - - - parameter layer: The input `CALayer` - - returns: Return a rendered image - */ - class func imageWithLayer(_ layer: CALayer) -> UIImage { - UIGraphicsBeginImageContextWithOptions(layer.bounds.size, layer.isOpaque, 0.0) - layer.render(in: UIGraphicsGetCurrentContext()!) - let img = UIGraphicsGetImageFromCurrentImageContext() - UIGraphicsEndImageContext() - return img! - } - - /** - Generates a image from a `UIView` - - - parameter view: The input `UIView` - - returns: Return a rendered image - */ - class func imageWithView(_ view: UIView) -> UIImage { - UIGraphicsBeginImageContextWithOptions(view.bounds.size, view.isOpaque, 0.0) - view.drawHierarchy(in: view.bounds, afterScreenUpdates: true) - let img = UIGraphicsGetImageFromCurrentImageContext() - UIGraphicsEndImageContext() - return img! - } -} - -internal extension UIViewController { - - @available(*, deprecated, message: "Use 'setCloseButton(withConfiguration:)' instead.") - func setCloseButton() { - guard let config = FolioReader.shared.readerContainer?.readerConfig else { - return - } - - self.setCloseButton(withConfiguration: config) - } - - func setCloseButton(withConfiguration readerConfig: FolioReaderConfig) { - // TODO_SMF_DOC - let closeImage = UIImage(readerImageNamed: "icon-navbar-close")?.ignoreSystemTint(withConfiguration: readerConfig) - self.navigationItem.leftBarButtonItem = UIBarButtonItem(image: closeImage, style: .plain, target: self, action: #selector(dismiss as (Void) -> Void)) - } - - func dismiss() { - self.dismiss(nil) - } - - func dismiss(_ completion: (() -> Void)?) { - DispatchQueue.main.async { - self.dismiss(animated: true, completion: { - completion?() - }) - } - } - - // MARK: - NavigationBar - - func setTransparentNavigation() { - let navBar = self.navigationController?.navigationBar - navBar?.setBackgroundImage(UIImage(), for: UIBarMetrics.default) - navBar?.hideBottomHairline() - navBar?.isTranslucent = true - } - - func setTranslucentNavigation(_ translucent: Bool = true, color: UIColor, tintColor: UIColor = UIColor.white, titleColor: UIColor = UIColor.black, andFont font: UIFont = UIFont.systemFont(ofSize: 17)) { - let navBar = self.navigationController?.navigationBar - navBar?.setBackgroundImage(UIImage.imageWithColor(color), for: UIBarMetrics.default) - navBar?.showBottomHairline() - navBar?.isTranslucent = translucent - navBar?.tintColor = tintColor - navBar?.titleTextAttributes = [NSForegroundColorAttributeName: titleColor, NSFontAttributeName: font] - } -} - -internal extension UINavigationBar { - - func hideBottomHairline() { - let navigationBarImageView = hairlineImageViewInNavigationBar(self) - navigationBarImageView!.isHidden = true - } - - func showBottomHairline() { - let navigationBarImageView = hairlineImageViewInNavigationBar(self) - navigationBarImageView!.isHidden = false - } - - fileprivate func hairlineImageViewInNavigationBar(_ view: UIView) -> UIImageView? { - if view.isKind(of: UIImageView.self) && view.bounds.height <= 1.0 { - return (view as! UIImageView) - } - - let subviews = (view.subviews ) - for subview: UIView in subviews { - if let imageView: UIImageView = hairlineImageViewInNavigationBar(subview) { - return imageView - } - } - return nil - } -} - -extension UINavigationController { - - open override var preferredStatusBarStyle : UIStatusBarStyle { - guard let viewController = visibleViewController else { return .default } - return viewController.preferredStatusBarStyle - } - - open override var supportedInterfaceOrientations : UIInterfaceOrientationMask { - guard let viewController = visibleViewController else { return .portrait } - return viewController.supportedInterfaceOrientations - } - - open override var shouldAutorotate : Bool { - guard let viewController = visibleViewController else { return false } - return viewController.shouldAutorotate - } -} - -/** - This fixes iOS 9 crash - http://stackoverflow.com/a/32010520/517707 - */ -extension UIAlertController { - open override var supportedInterfaceOrientations : UIInterfaceOrientationMask { - return .portrait - } - - open override var shouldAutorotate : Bool { - return false - } -} - -extension Array { - - /** - Return index if is safe, if not return nil - http://stackoverflow.com/a/30593673/517707 - */ - subscript(safe index: Int) -> Element? { - return indices ~= index ? self[index] : nil - } -} diff --git a/Source/Models/Highlight+Helper.swift b/Source/Models/Highlight+Helper.swift index 414a25866..58396e569 100644 --- a/Source/Models/Highlight+Helper.swift +++ b/Source/Models/Highlight+Helper.swift @@ -87,7 +87,6 @@ extension Highlight { /// - readerConfig: Current folio reader configuration. /// - completion: Completion block. public func persist(withConfiguration readerConfig: FolioReaderConfig, completion: Completion? = nil) { - // TODO_SMF_DOC do { let realm = try Realm(configuration: readerConfig.realmConfiguration) realm.beginWrite() @@ -104,7 +103,6 @@ extension Highlight { /// /// - Parameter readerConfig: Current folio reader configuration. public func remove(withConfiguration readerConfig: FolioReaderConfig) { - // TODO_SMF_DOC do { let realm = try Realm(configuration: readerConfig.realmConfiguration) realm.beginWrite() @@ -121,7 +119,6 @@ extension Highlight { /// - readerConfig: Current folio reader configuration. /// - highlightId: The ID to be removed public static func removeById(withConfiguration readerConfig: FolioReaderConfig, highlightId: String) { - // TODO_SMF_DOC var highlight: Highlight? let predicate = NSPredicate(format:"highlightId = %@", highlightId) @@ -141,7 +138,6 @@ extension Highlight { /// - highlightId: The ID to be removed /// - type: The `HighlightStyle` public static func updateById(withConfiguration readerConfig: FolioReaderConfig, highlightId: String, type: HighlightStyle) { - // TODO_SMF_DOC var highlight: Highlight? let predicate = NSPredicate(format:"highlightId = %@", highlightId) do { @@ -166,7 +162,6 @@ extension Highlight { /// - page: Page number /// - Returns: Return a list of Highlights public static func allByBookId(withConfiguration readerConfig: FolioReaderConfig, bookId: String, andPage page: NSNumber? = nil) -> [Highlight] { - // TODO_SMF_DOC var highlights: [Highlight]? var predicate = NSPredicate(format: "bookId = %@", bookId) if let page = page { @@ -188,7 +183,6 @@ extension Highlight { /// - Parameter readerConfig: - readerConfig: Current folio reader configuration. /// - Returns: Return all Highlights public static func all(withConfiguration readerConfig: FolioReaderConfig) -> [Highlight] { - // TODO_SMF_DOC var highlights: [Highlight]? do { let realm = try Realm(configuration: readerConfig.realmConfiguration) @@ -341,7 +335,6 @@ extension Highlight { /// - highlightId: The ID to be removed /// - Returns: The removed id @discardableResult public static func removeFromHTMLById(withinPage page: FolioReaderPage?, highlightId: String) -> String? { - // TODO_SMF_DOC guard let currentPage = page else { return nil } if let removedId = currentPage.webView.js("removeHighlightById('\(highlightId)')") { diff --git a/migration.md b/migration.md new file mode 100644 index 000000000..fc15edfa9 --- /dev/null +++ b/migration.md @@ -0,0 +1,44 @@ +# Migration Guide to version 1.2.0 + +## Introduction + +-- + +## What changed? + +### Class: FolioReader + +### Class: Highlight + +The following functions now need a FolioReaderConfig object as parameter: + +public static func all(withConfiguration readerConfig: FolioReaderConfig) -> [Highlight] +public static func allByBookId(withConfiguration readerConfig: FolioReaderConfig, bookId: String, andPage page: NSNumber? = nil) -> [Highlight] +public static func updateById(withConfiguration readerConfig: FolioReaderConfig, highlightId: String, type: HighlightStyle) +public static func removeById(withConfiguration readerConfig: FolioReaderConfig, highlightId: String) +public func remove(withConfiguration readerConfig: FolioReaderConfig) +public func persist(withConfiguration readerConfig: FolioReaderConfig, completion: Completion? = nil) +@discardableResult public static func removeFromHTMLById(withinPage page: FolioReaderPage?, highlightId: String) -> String? + +### Class: FREpubParser + +The `parseCoverImage` function now takes an optional parameter indicating the unzip path. +Before it used the static shared instance. +Default value is the Documents directory. + +func parseCoverImage(_ epubPath: String, unzipPath: String? = nil) -> UIImage? + +### Class: UIKit classes extensions + +The following functions now need a FolioReaderConfig object as parameter: + +UICollectionViewScrollDirection.direction(withConfiguration readerConfig: FolioReaderConfig) -> UICollectionViewScrollDirection +UICollectionViewScrollPosition.direction(withConfiguration readerConfig: FolioReaderConfig) -> UICollectionViewScrollPosition +CGPoint.forDirection(withConfiguration readerConfig: FolioReaderConfig) -> CGFloat +CGSize.forDirection(withConfiguration readerConfig: FolioReaderConfig) -> CGFloat +CGSize.forReverseDirection(withConfiguration readerConfig: FolioReaderConfig) -> CGFloat +CGRect.forDirection(withConfiguration readerConfig: FolioReaderConfig) -> CGFloat +ScrollDirection.negative(withConfiguration readerConfig: FolioReaderConfig) -> ScrollDirection +ScrollDirection.positive(withConfiguration readerConfig: FolioReaderConfig) -> ScrollDirection +UIImage.ignoreSystemTint(withConfiguration readerConfig: FolioReaderConfig) -> UIImage? +UIViewController.setCloseButton(withConfiguration readerConfig: FolioReaderConfig) \ No newline at end of file From 60c1f7b336c694cdded9eb76e900cb0df356f7a2 Mon Sep 17 00:00:00 2001 From: Kevin Delord Date: Sun, 2 Apr 2017 00:06:35 +0200 Subject: [PATCH 055/110] Report more changes on the migration.md file --- Source/FolioReaderKit.swift | 16 +++------------ migration.md | 39 ++++++++++++++++++++++++++++++++++++- 2 files changed, 41 insertions(+), 14 deletions(-) diff --git a/Source/FolioReaderKit.swift b/Source/FolioReaderKit.swift index 2d5357eb1..420e81c2d 100755 --- a/Source/FolioReaderKit.swift +++ b/Source/FolioReaderKit.swift @@ -57,8 +57,7 @@ enum MediaOverlayStyle: Int { /// - Parameter folioReader: The FolioReader instance @objc optional func folioReaderDidClose(_ folioReader: FolioReader) - // TODO_SMF_CHECK: make sure the following deprecated functions still work... or not.: - // TODO_SMF_DOC: new function signature change + // TODO_SMF_CHECK: make sure the following deprecated functions still work... or not. @objc optional func folioReaderDidClosed() } @@ -127,7 +126,6 @@ extension FolioReader { /// - Returns: The new and presented FolioReaderContainer instance. open class func presentReader(parentViewController: UIViewController, withEpubPath epubPath: String, andConfig config: FolioReaderConfig, shouldRemoveEpub: Bool = true, animated: Bool = true) -> FolioReaderContainer { - // TODO_SMF_DOC let folioReader = FolioReader() let readerContainer = FolioReaderContainer(withConfig: config, folioReader: folioReader, epubPath: epubPath, removeEpub: shouldRemoveEpub) folioReader.readerContainer = readerContainer @@ -290,7 +288,6 @@ extension FolioReader { /** Read Cover Image and Return an `UIImage` */ - // TODO_SMF_DOC: new function signature change open class func getCoverImage(_ epubPath: String, unzipPath: String? = nil) -> UIImage? { return FREpubParser().parseCoverImage(epubPath, unzipPath: unzipPath) } @@ -436,19 +433,12 @@ extension FolioReader { @available(*, deprecated, message: "Shared instance removed. Use a local instance instead.") func isNight (_ f: T, _ l: T) -> T { - // TODO_SMF_DOC: notify change - return (FolioReader.shared.nightMode == true ? f : l) + return FolioReader.shared.isNight(f, l) } // MARK: - Scroll Direction Functions @available(*, deprecated, message: "Shared instance removed. Use a local instance instead.") func isDirection (_ vertical: T, _ horizontal: T, _ horizontalContentVertical: T? = nil) -> T { - // TODO_SMF_DOC: notify change - let direction = (FolioReader.shared.readerContainer!.readerConfig.scrollDirection) - switch direction { - case .vertical, .defaultVertical: return vertical - case .horizontal: return horizontal - case .horizontalWithVerticalContent: return (horizontalContentVertical ?? vertical) - } + return FolioReader.shared.readerContainer!.readerConfig.isDirection(vertical, horizontal, horizontalContentVertical) } diff --git a/migration.md b/migration.md index fc15edfa9..de8067835 100644 --- a/migration.md +++ b/migration.md @@ -8,10 +8,33 @@ ### Class: FolioReader +The function `presentReader` now returns the presented FolioReaderContainer instance. +It also initialise the depcrecated shared instance in order to support the previous versions of the library. + +``` +class func presentReader(parentViewController: UIViewController, withEpubPath epubPath: String, andConfig config: FolioReaderConfig, shouldRemoveEpub: Bool = true, animated: Bool = true) -> FolioReaderContainer +``` + +The function `getCoverImage` now has an extra parameter indicating the unzip path for the epub. + +``` +class func getCoverImage(_ epubPath: String, unzipPath: String? = nil) -> UIImage? +``` + +### Class: FolioReaderDelegate + +The function `folioReaderDidClosed` has been renamed `folioReaderDidClose`. +It also has a new FolioReader parameter. + +``` +func folioReaderDidClose(_ folioReader: FolioReader) +``` + ### Class: Highlight The following functions now need a FolioReaderConfig object as parameter: +``` public static func all(withConfiguration readerConfig: FolioReaderConfig) -> [Highlight] public static func allByBookId(withConfiguration readerConfig: FolioReaderConfig, bookId: String, andPage page: NSNumber? = nil) -> [Highlight] public static func updateById(withConfiguration readerConfig: FolioReaderConfig, highlightId: String, type: HighlightStyle) @@ -19,6 +42,7 @@ public static func removeById(withConfiguration readerConfig: FolioReaderConfig, public func remove(withConfiguration readerConfig: FolioReaderConfig) public func persist(withConfiguration readerConfig: FolioReaderConfig, completion: Completion? = nil) @discardableResult public static func removeFromHTMLById(withinPage page: FolioReaderPage?, highlightId: String) -> String? +``` ### Class: FREpubParser @@ -26,12 +50,15 @@ The `parseCoverImage` function now takes an optional parameter indicating the un Before it used the static shared instance. Default value is the Documents directory. +``` func parseCoverImage(_ epubPath: String, unzipPath: String? = nil) -> UIImage? +``` ### Class: UIKit classes extensions The following functions now need a FolioReaderConfig object as parameter: +``` UICollectionViewScrollDirection.direction(withConfiguration readerConfig: FolioReaderConfig) -> UICollectionViewScrollDirection UICollectionViewScrollPosition.direction(withConfiguration readerConfig: FolioReaderConfig) -> UICollectionViewScrollPosition CGPoint.forDirection(withConfiguration readerConfig: FolioReaderConfig) -> CGFloat @@ -41,4 +68,14 @@ CGRect.forDirection(withConfiguration readerConfig: FolioReaderConfig) -> CGFloa ScrollDirection.negative(withConfiguration readerConfig: FolioReaderConfig) -> ScrollDirection ScrollDirection.positive(withConfiguration readerConfig: FolioReaderConfig) -> ScrollDirection UIImage.ignoreSystemTint(withConfiguration readerConfig: FolioReaderConfig) -> UIImage? -UIViewController.setCloseButton(withConfiguration readerConfig: FolioReaderConfig) \ No newline at end of file +UIViewController.setCloseButton(withConfiguration readerConfig: FolioReaderConfig) +``` + +### Class: none + +The following functions have been deprecated and replaced by functions within the FolioReader and the FolioReaderConfig classes. + +``` +func isNight (_ f: T, _ l: T) -> T +func isDirection (_ vertical: T, _ horizontal: T, _ horizontalContentVertical: T? = nil) -> T +``` From e7894714b096dc2346472a277984693991ef11ea Mon Sep 17 00:00:00 2001 From: Kevin Delord Date: Sun, 2 Apr 2017 00:20:46 +0200 Subject: [PATCH 056/110] Improve question comment text --- Source/FolioReaderAudioPlayer.swift | 2 +- Source/FolioReaderKit.swift | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/Source/FolioReaderAudioPlayer.swift b/Source/FolioReaderAudioPlayer.swift index ef0f0d07a..6b34bb5a8 100644 --- a/Source/FolioReaderAudioPlayer.swift +++ b/Source/FolioReaderAudioPlayer.swift @@ -386,7 +386,7 @@ open class FolioReaderAudioPlayer: NSObject { return } - // TODO_SMF_QUESTION: the previous code mde it possible for `href` to be an empty string. Was that valid? should this logic be kept? + // TODO_SMF_QUESTION: the previous code made it possible for `href` to be an empty string. Was that valid? should this logic be kept? self.playText(href, text: sentence) } diff --git a/Source/FolioReaderKit.swift b/Source/FolioReaderKit.swift index 420e81c2d..b87e7353e 100755 --- a/Source/FolioReaderKit.swift +++ b/Source/FolioReaderKit.swift @@ -282,7 +282,7 @@ extension FolioReader { extension FolioReader { - // TODO_SMF_QUESTION: this used the shared instance before and ignore the parameter. + // TODO_SMF_QUESTION: the `getCoverImage` function used the shared instance before and ignored the parameter. // Should we properly implement the parameter or change the API to use the current FolioReader? /** From 16d2607c1d67d8bba7933db36175d2697f5b9832 Mon Sep 17 00:00:00 2001 From: Kevin Delord Date: Sun, 2 Apr 2017 00:22:19 +0200 Subject: [PATCH 057/110] Comments: fix typo --- Source/FolioReaderAudioPlayer.swift | 4 ++-- Source/FolioReaderCenter.swift | 6 +++--- Source/FolioReaderKit.swift | 2 +- 3 files changed, 6 insertions(+), 6 deletions(-) diff --git a/Source/FolioReaderAudioPlayer.swift b/Source/FolioReaderAudioPlayer.swift index 6b34bb5a8..402fbbc49 100644 --- a/Source/FolioReaderAudioPlayer.swift +++ b/Source/FolioReaderAudioPlayer.swift @@ -372,10 +372,10 @@ open class FolioReaderAudioPlayer: NSObject { let playbackActiveClass = self.book.playbackActiveClass() guard let sentence = currentPage.webView.js("getSentenceWithIndex('\(playbackActiveClass)')") else { if (readerCenter.isLastPage() == true) { - // TODO_SMF_CHECK: when do this happen? + // TODO_SMF_CHECK: when does this happen? self.stop() } else { - // TODO_SMF_CHECK: when do this happen? + // TODO_SMF_CHECK: when does this happen? readerCenter.changePageToNext() } diff --git a/Source/FolioReaderCenter.swift b/Source/FolioReaderCenter.swift index 07a15f3f1..1c67daaa8 100755 --- a/Source/FolioReaderCenter.swift +++ b/Source/FolioReaderCenter.swift @@ -276,7 +276,7 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo private func transformViewForRTL(_ view: UIView?) { if (self.readerContainer.folioReader.needsRTLChange == true) { - // TODO_SMF_CHECK: when do this happen? + // TODO_SMF_CHECK: when does this happen? view?.transform = CGAffineTransform(scaleX: -1, y: 1) } else { view?.transform = CGAffineTransform.identity @@ -826,11 +826,11 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo return nil } - // TODO_SMF_CHECK: when do this happen? + // TODO_SMF_CHECK: when does this happen? return title } - // TODO_SMF_CHECK: when do this happen? + // TODO_SMF_CHECK: when does this happen? return nil } diff --git a/Source/FolioReaderKit.swift b/Source/FolioReaderKit.swift index b87e7353e..4c18492fe 100755 --- a/Source/FolioReaderKit.swift +++ b/Source/FolioReaderKit.swift @@ -238,7 +238,7 @@ extension FolioReader { /// Check the current scroll direction. Default .defaultVertical open var currentScrollDirection: Int { get { - // TODO_SMF_CHECK: when do this happen? + // TODO_SMF_CHECK: when does this happen? guard let value = self.defaults.integer(forKey: kCurrentScrollDirection) as? Int else { return FolioReaderScrollDirection.defaultVertical.rawValue } From fa30b2aa65dfd3dc03559ff025bcc5c022255da3 Mon Sep 17 00:00:00 2001 From: Kevin Delord Date: Sun, 2 Apr 2017 00:31:24 +0200 Subject: [PATCH 058/110] Delegate: deprecate one function --- Example/Example/ViewController.swift | 1 - Source/FolioReaderKit.swift | 3 ++- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/Example/Example/ViewController.swift b/Example/Example/ViewController.swift index c6d20b920..26bec0270 100755 --- a/Example/Example/ViewController.swift +++ b/Example/Example/ViewController.swift @@ -104,7 +104,6 @@ class ViewController : UIViewController { let readerConfiguration = self.readerConfiguration(forEpub: epub) let folioReaderContainer = FolioReader.presentReader(parentViewController: self, withEpubPath: bookPath, andConfig: readerConfiguration, shouldRemoveEpub: false) - epub.retain(folioReaderContainer: folioReaderContainer) } diff --git a/Source/FolioReaderKit.swift b/Source/FolioReaderKit.swift index 4c18492fe..9f508c4a8 100755 --- a/Source/FolioReaderKit.swift +++ b/Source/FolioReaderKit.swift @@ -57,7 +57,8 @@ enum MediaOverlayStyle: Int { /// - Parameter folioReader: The FolioReader instance @objc optional func folioReaderDidClose(_ folioReader: FolioReader) - // TODO_SMF_CHECK: make sure the following deprecated functions still work... or not. + /// Called when reader did closed. + @available(*, deprecated, message: "Use 'folioReaderDidClose(_ folioReader: FolioReader)' instead.") @objc optional func folioReaderDidClosed() } From 805ee5944a346bfe19bf73cf303296d82c6033cd Mon Sep 17 00:00:00 2001 From: Kevin Delord Date: Sun, 2 Apr 2017 00:35:06 +0200 Subject: [PATCH 059/110] Add more migration documentation --- Source/FolioReaderKit.swift | 4 +--- migration.md | 9 +++++++++ 2 files changed, 10 insertions(+), 3 deletions(-) diff --git a/Source/FolioReaderKit.swift b/Source/FolioReaderKit.swift index 9f508c4a8..83ef74f1b 100755 --- a/Source/FolioReaderKit.swift +++ b/Source/FolioReaderKit.swift @@ -414,18 +414,16 @@ extension FolioReader { // MARK: - Application State -@available(*, deprecated, message: "Use 'saveReaderState' on a FolioReaderContainer object instead.") +@available(*, deprecated, message: "Use 'saveReaderState()' on a FolioReaderContainer object instead.") extension FolioReader { /// Called when the application will resign active open class func applicationWillResignActive() { - // TODO_DOC: no replacement required. Call `aFolioReader.saveReaderState()` instead FolioReader.shared.saveReaderState() } /// Called when the application will terminate open class func applicationWillTerminate() { - // TODO_DOC: no replacement required. Call `aFolioReader.saveReaderState()` instead FolioReader.shared.saveReaderState() } } diff --git a/migration.md b/migration.md index de8067835..9ce1acdcf 100644 --- a/migration.md +++ b/migration.md @@ -21,6 +21,15 @@ The function `getCoverImage` now has an extra parameter indicating the unzip pat class func getCoverImage(_ epubPath: String, unzipPath: String? = nil) -> UIImage? ``` +The functions to be called within the AppDelegate methods have been deprecated. +There is no direct replacement, use `saveReaderState` on a `FolioReaderContainer` object instead. + +Deprecated: +``` +class func applicationWillResignActive() +class func applicationWillTerminate() +``` + ### Class: FolioReaderDelegate The function `folioReaderDidClosed` has been renamed `folioReaderDidClose`. From b6730d96f3c09b962b8dc50e72aa44641e22ffac Mon Sep 17 00:00:00 2001 From: Kevin Delord Date: Sun, 2 Apr 2017 00:41:39 +0200 Subject: [PATCH 060/110] update documentation and readme --- README.md | 12 ++++++------ migration.md | 6 +++++- 2 files changed, 11 insertions(+), 7 deletions(-) diff --git a/README.md b/README.md index bd837624b..6aa6b19b1 100644 --- a/README.md +++ b/README.md @@ -103,7 +103,7 @@ import FolioReaderKit func open(sender: AnyObject) { let config = FolioReaderConfig()    let bookPath = Bundle.main.path(forResource: "book", ofType: "epub") -    FolioReader.presentReader(parentViewController: self, withEpubPath: bookPath!, andConfig: config) +    let myReaderContainer = FolioReader.presentReader(parentViewController: self, withEpubPath: bookPath!, andConfig: config) } ``` @@ -112,10 +112,10 @@ You can also use your own FolioReader View Controller like this. ```swift let config = FolioReaderConfig() let bookPath = Bundle.main.path(forResource: "book", ofType: "epub") -let epubVC = FolioReaderContainer(withConfig: config, epubPath: bookPath!, removeEpub: true) +let myReaderContainer = FolioReaderContainer(withConfig: config, epubPath: bookPath!, removeEpub: true) -// Present the epubVC view controller like every other UIViewController instance -present(epubVC, animated: true, completion: nil) +// Present the myReaderContainer view controller like every other UIViewController instance +present(myReaderContainer, animated: true, completion: nil) ``` In your `AppDelegate` call `applicationWillResignActive` and `applicationWillTerminate`. This will save the reader state even if you kill the app. @@ -124,11 +124,11 @@ In your `AppDelegate` call `applicationWillResignActive` and `applicationWillTer import FolioReaderKit func applicationWillResignActive(_ application: UIApplication) { - FolioReader.applicationWillResignActive() + myReaderContainer.saveReaderState() } func applicationWillTerminate(_ application: UIApplication) { - FolioReader.applicationWillTerminate() + myReaderContainer.saveReaderState() } ``` diff --git a/migration.md b/migration.md index 9ce1acdcf..323a6c28d 100644 --- a/migration.md +++ b/migration.md @@ -22,13 +22,17 @@ class func getCoverImage(_ epubPath: String, unzipPath: String? = nil) -> UIImag ``` The functions to be called within the AppDelegate methods have been deprecated. -There is no direct replacement, use `saveReaderState` on a `FolioReaderContainer` object instead. +There is no direct replacement, use `saveReaderState()` on a `FolioReaderContainer` object instead. Deprecated: ``` class func applicationWillResignActive() class func applicationWillTerminate() ``` +Replaced by on `FolioReaderContainer` class: +``` +open func saveReaderState() +``` ### Class: FolioReaderDelegate From 89c663259ad9b4c3c0c4ef84a902c8b2d53e33cd Mon Sep 17 00:00:00 2001 From: Kevin Delord Date: Mon, 3 Apr 2017 15:59:23 +0200 Subject: [PATCH 061/110] Add one minor 0 check --- Source/FolioReaderCenter.swift | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/Source/FolioReaderCenter.swift b/Source/FolioReaderCenter.swift index a4b4f4ed9..4370e36ec 100755 --- a/Source/FolioReaderCenter.swift +++ b/Source/FolioReaderCenter.swift @@ -641,6 +641,10 @@ open class FolioReaderCenter : UIViewController, UICollectionViewDelegate, UICo } func pageForOffset(_ offset: CGFloat, pageHeight height: CGFloat) -> Int { + guard (height != 0) else { + return 0 + } + let page = Int(ceil(offset / height))+1 return page } From 67d335d6dce0aa3b79b2ea54d1cf298544a53c8a Mon Sep 17 00:00:00 2001 From: Kevin Delord Date: Mon, 3 Apr 2017 16:59:24 +0200 Subject: [PATCH 062/110] Migrationm: add description --- migration.md | 10 +++++++++- 1 file changed, 9 insertions(+), 1 deletion(-) diff --git a/migration.md b/migration.md index 323a6c28d..9dfefc8b0 100644 --- a/migration.md +++ b/migration.md @@ -2,10 +2,18 @@ ## Introduction --- +That new version introduce a new feature that allows you to have multiple instances of a `FolioReaderContainer` at the same time in your app. +All instances now have their own stored informations and nothing is shared between them. + +Before, the library used a global static `FolioReader` that contained all relevant objects (ReaderContainer, ReaderConfig, AudioPlayer, etc). +Even though this class is still used internaly, all of its static functions have been deprecated. + +You must now use the (same) functions of a local instance (from your code) instead. ## What changed? +Here is the list of changes made to the `public` functions. + ### Class: FolioReader The function `presentReader` now returns the presented FolioReaderContainer instance. From 82d9394bc5f77552d345b0da2906da24c3543e15 Mon Sep 17 00:00:00 2001 From: Kevin Delord Date: Mon, 3 Apr 2017 17:03:25 +0200 Subject: [PATCH 063/110] Update TODO_SMF_QUESTION --- Source/FolioReaderAudioPlayer.swift | 4 ++-- Source/FolioReaderKit.swift | 6 +++--- 2 files changed, 5 insertions(+), 5 deletions(-) diff --git a/Source/FolioReaderAudioPlayer.swift b/Source/FolioReaderAudioPlayer.swift index 402fbbc49..847d7543e 100644 --- a/Source/FolioReaderAudioPlayer.swift +++ b/Source/FolioReaderAudioPlayer.swift @@ -249,7 +249,7 @@ open class FolioReaderAudioPlayer: NSObject { @discardableResult fileprivate func _playFragment(_ smil: FRSmilElement?) -> Bool { guard let smil = smil else { - // TODO_SMF_QUESTION: disable log? + // TODO_SMF_QUESTION: What about the log that the library prints in the console? shouldn’t we disable it? use another library for that or some compiler flags? print("no more parallel audio to play") self.stop() return false @@ -386,7 +386,7 @@ open class FolioReaderAudioPlayer: NSObject { return } - // TODO_SMF_QUESTION: the previous code made it possible for `href` to be an empty string. Was that valid? should this logic be kept? + // TODO_SMF_QUESTION: The previous code made it possible to call `playText` with the parameter `href` being an empty string. Was that valid? should this logic be kept? self.playText(href, text: sentence) } diff --git a/Source/FolioReaderKit.swift b/Source/FolioReaderKit.swift index 83ef74f1b..7ed9ebd84 100755 --- a/Source/FolioReaderKit.swift +++ b/Source/FolioReaderKit.swift @@ -74,7 +74,7 @@ open class FolioReader: NSObject { /// FolioReaderDelegate open weak var delegate : FolioReaderDelegate? - // TODO_SMF_QUESTION: make those fileprivate (or internal) to avoid public access from other class? + // TODO_SMF_QUESTION: Should we make those `fileprivate` (or `internal`) to avoid public access from other class? open weak var readerContainer : FolioReaderContainer? open weak var readerAudioPlayer : FolioReaderAudioPlayer? open weak var readerCenter : FolioReaderCenter? { @@ -283,8 +283,8 @@ extension FolioReader { extension FolioReader { - // TODO_SMF_QUESTION: the `getCoverImage` function used the shared instance before and ignored the parameter. - // Should we properly implement the parameter or change the API to use the current FolioReader? + // TODO_SMF_QUESTION: The static `getCoverImage` function used the shared instance before and ignored the `unzipPath` parameter. + // Should we properly implement the parameter (what has been done now) or should change the API to only use the current FolioReader instance? /** Read Cover Image and Return an `UIImage` From 908659e67c0c35507c015d33c4f2a5f8b5a0252d Mon Sep 17 00:00:00 2001 From: Kevin Delord Date: Mon, 3 Apr 2017 17:48:45 +0200 Subject: [PATCH 064/110] Update migration.md --- migration.md | 44 +++++++++++++++++++++++++++++++++++++++----- 1 file changed, 39 insertions(+), 5 deletions(-) diff --git a/migration.md b/migration.md index 9dfefc8b0..c224ce502 100644 --- a/migration.md +++ b/migration.md @@ -5,7 +5,7 @@ That new version introduce a new feature that allows you to have multiple instances of a `FolioReaderContainer` at the same time in your app. All instances now have their own stored informations and nothing is shared between them. -Before, the library used a global static `FolioReader` that contained all relevant objects (ReaderContainer, ReaderConfig, AudioPlayer, etc). +Before, the library used a global static `FolioReader` that contained all relevant objects (`ReaderContainer`, `ReaderConfig`, `AudioPlayer`, etc). Even though this class is still used internaly, all of its static functions have been deprecated. You must now use the (same) functions of a local instance (from your code) instead. @@ -16,7 +16,7 @@ Here is the list of changes made to the `public` functions. ### Class: FolioReader -The function `presentReader` now returns the presented FolioReaderContainer instance. +The function `presentReader` now returns the presented `FolioReaderContainer` instance. It also initialise the depcrecated shared instance in order to support the previous versions of the library. ``` @@ -29,6 +29,8 @@ The function `getCoverImage` now has an extra parameter indicating the unzip pat class func getCoverImage(_ epubPath: String, unzipPath: String? = nil) -> UIImage? ``` +#### AppDelegate + The functions to be called within the AppDelegate methods have been deprecated. There is no direct replacement, use `saveReaderState()` on a `FolioReaderContainer` object instead. @@ -42,10 +44,42 @@ Replaced by on `FolioReaderContainer` class: open func saveReaderState() ``` +#### Deprecated static functions + +All class/static functions have been deprecated and replaced by instance functions. Nor the static functions or the shared instances should be used anymore. + +List of all deprecated `FolioReader` static attributes and functions: + +``` +open static var shared : FolioReader +static var currentMediaOverlayStyle: MediaOverlayStyle +open class var nightMode: Bool +open class var currentFont: FolioReaderFont +open class var currentFontSize: FolioReaderFontSize +open class var currentScrollDirection: Int +open class var currentAudioRate: Int +open class var isReaderReady : Bool +open class func saveReaderState() +open class func close() +open class var currentHighlightStyle: Int +open class var needsRTLChange: Bool + +open class func applicationWillResignActive() +open class func applicationWillTerminate() +``` + +### Class: FolioReaderContainer + +The public `init` function now takes an extra `FolioReader` instance as parameter. + +``` +public init(withConfig config: FolioReaderConfig, folioReader: FolioReader, epubPath path: String, removeEpub: Bool = true) +``` + ### Class: FolioReaderDelegate The function `folioReaderDidClosed` has been renamed `folioReaderDidClose`. -It also has a new FolioReader parameter. +It also has a new `FolioReader parameter. ``` func folioReaderDidClose(_ folioReader: FolioReader) @@ -53,7 +87,7 @@ func folioReaderDidClose(_ folioReader: FolioReader) ### Class: Highlight -The following functions now need a FolioReaderConfig object as parameter: +The following functions now need a `FolioReaderConfig` object as parameter: ``` public static func all(withConfiguration readerConfig: FolioReaderConfig) -> [Highlight] @@ -94,7 +128,7 @@ UIViewController.setCloseButton(withConfiguration readerConfig: FolioReaderConfi ### Class: none -The following functions have been deprecated and replaced by functions within the FolioReader and the FolioReaderConfig classes. +The following functions have been deprecated and replaced by functions within the `FolioReader` and the `FolioReaderConfig` classes. ``` func isNight (_ f: T, _ l: T) -> T From 522226ca54ae65c29ddd34e25496d6db29b4f84f Mon Sep 17 00:00:00 2001 From: Hans Seiffert Date: Mon, 10 Apr 2017 09:07:59 +0200 Subject: [PATCH 065/110] Remove unwanted space --- Source/Extensions.swift | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Source/Extensions.swift b/Source/Extensions.swift index 179469795..6b591e397 100644 --- a/Source/Extensions.swift +++ b/Source/Extensions.swift @@ -551,7 +551,7 @@ internal extension UINavigationBar { return (view as! UIImageView) } - let subviews = (view.subviews ) + let subviews = (view.subviews) for subview: UIView in subviews { if let imageView: UIImageView = hairlineImageViewInNavigationBar(subview) { return imageView From 1cd8cd685b8cb1b9aeaa049871d22e6ad1b260a4 Mon Sep 17 00:00:00 2001 From: Hans Seiffert Date: Mon, 10 Apr 2017 09:14:04 +0200 Subject: [PATCH 066/110] Remove unneeded SMF content --- .gitignore | 3 --- Source/FolioReaderKit.swift | 1 - 2 files changed, 4 deletions(-) diff --git a/.gitignore b/.gitignore index 0b8810f0e..48b1ea00e 100644 --- a/.gitignore +++ b/.gitignore @@ -22,9 +22,6 @@ xcuserdata/ *.xcuserstate *.DS_Store -## SMF Specific -.swiftlint.yml - ## Obj-C/Swift specific *.hmap *.ipa diff --git a/Source/FolioReaderKit.swift b/Source/FolioReaderKit.swift index 7ed9ebd84..c27259bd0 100755 --- a/Source/FolioReaderKit.swift +++ b/Source/FolioReaderKit.swift @@ -74,7 +74,6 @@ open class FolioReader: NSObject { /// FolioReaderDelegate open weak var delegate : FolioReaderDelegate? - // TODO_SMF_QUESTION: Should we make those `fileprivate` (or `internal`) to avoid public access from other class? open weak var readerContainer : FolioReaderContainer? open weak var readerAudioPlayer : FolioReaderAudioPlayer? open weak var readerCenter : FolioReaderCenter? { From c1b0dd17f07ae1f1ec0aa27598b7f01fbd13d1c5 Mon Sep 17 00:00:00 2001 From: Hans Seiffert Date: Mon, 10 Apr 2017 09:16:50 +0200 Subject: [PATCH 067/110] Remove Xcode 8.1 logging workaround from the schemes --- .../xcshareddata/xcschemes/Example.xcscheme | 7 ------- 1 file changed, 7 deletions(-) diff --git a/Example/Example.xcodeproj/xcshareddata/xcschemes/Example.xcscheme b/Example/Example.xcodeproj/xcshareddata/xcschemes/Example.xcscheme index 949d39375..d78b6713e 100644 --- a/Example/Example.xcodeproj/xcshareddata/xcschemes/Example.xcscheme +++ b/Example/Example.xcodeproj/xcshareddata/xcschemes/Example.xcscheme @@ -71,13 +71,6 @@ ReferencedContainer = "container:Example.xcodeproj"> - - - - From aa67bf674045331e8d1118cfa70c5ffe56bcdf3d Mon Sep 17 00:00:00 2001 From: Hans Seiffert Date: Mon, 10 Apr 2017 10:02:09 +0200 Subject: [PATCH 068/110] Replace tabs with spaces for the indentation --- Example/Example/AppDelegate.swift | 18 +- Example/Example/ViewController.swift | 190 ++-- Example/StoryboardExample/AppDelegate.swift | 12 +- .../ExampleFolioReaderContainer.swift | 24 +- Source/EPUBCore/FRBook.swift | 50 +- Source/EPUBCore/FREpubParser.swift | 176 ++-- Source/EPUBCore/FRMediaType.swift | 42 +- Source/EPUBCore/FRMetadata.swift | 94 +- Source/EPUBCore/FRResource.swift | 12 +- Source/EPUBCore/FRResources.swift | 42 +- Source/EPUBCore/FRSmilElement.swift | 14 +- Source/EPUBCore/FRSmils.swift | 40 +- Source/EPUBCore/FRSpine.swift | 11 +- Source/EPUBCore/FRTocReference.swift | 14 +- Source/Extensions.swift | 986 +++++++++--------- Source/FolioReaderAudioPlayer.swift | 228 ++-- Source/FolioReaderCenter.swift | 909 ++++++++-------- Source/FolioReaderChapterList.swift | 66 +- Source/FolioReaderChapterListCell.swift | 72 +- Source/FolioReaderConfig.swift | 256 ++--- Source/FolioReaderContainer.swift | 172 +-- Source/FolioReaderFontsMenu.swift | 268 ++--- Source/FolioReaderHighlightList.swift | 86 +- Source/FolioReaderKit.swift | 490 ++++----- Source/FolioReaderPage.swift | 474 ++++----- Source/FolioReaderPageIndicator.swift | 74 +- Source/FolioReaderPlayerMenu.swift | 108 +- Source/FolioReaderQuoteShare.swift | 210 ++-- Source/FolioReaderSharingProvider.swift | 10 +- Source/FolioReaderUserDefaults.swift | 108 +- Source/FolioReaderWebView.swift | 528 +++++----- Source/Models/Highlight+Helper.swift | 632 +++++------ Source/Models/Highlight.swift | 22 +- Source/PageViewController.swift | 72 +- Source/QuoteImage.swift | 8 +- Source/ScrollScrubber.swift | 178 ++-- 36 files changed, 3348 insertions(+), 3348 deletions(-) diff --git a/Example/Example/AppDelegate.swift b/Example/Example/AppDelegate.swift index a6c471909..ae18383b6 100644 --- a/Example/Example/AppDelegate.swift +++ b/Example/Example/AppDelegate.swift @@ -10,11 +10,11 @@ import UIKit import FolioReaderKit @UIApplicationMain -class AppDelegate : UIResponder, UIApplicationDelegate { +class AppDelegate: UIResponder, UIApplicationDelegate { - var window : UIWindow? - var standardEpub : FolioReaderContainer? - var audioEpub : FolioReaderContainer? + var window : UIWindow? + var standardEpub : FolioReaderContainer? + var audioEpub : FolioReaderContainer? func application(_ application: UIApplication, didFinishLaunchingWithOptions launchOptions: [UIApplicationLaunchOptionsKey: Any]?) -> Bool { // Override point for customization after application launch. @@ -22,14 +22,14 @@ class AppDelegate : UIResponder, UIApplicationDelegate { } func applicationWillResignActive(_ application: UIApplication) { - /// Save Reader state, book, page and scroll offset. - self.standardEpub?.saveReaderState() - self.audioEpub?.saveReaderState() + /// Save Reader state, book, page and scroll offset. + self.standardEpub?.saveReaderState() + self.audioEpub?.saveReaderState() } func applicationWillTerminate(_ application: UIApplication) { - /// Save Reader state, book, page and scroll offset. + /// Save Reader state, book, page and scroll offset. self.standardEpub?.saveReaderState() - self.audioEpub?.saveReaderState() + self.audioEpub?.saveReaderState() } } diff --git a/Example/Example/ViewController.swift b/Example/Example/ViewController.swift index 26bec0270..bb449af5f 100755 --- a/Example/Example/ViewController.swift +++ b/Example/Example/ViewController.swift @@ -10,124 +10,124 @@ import UIKit import FolioReaderKit enum Epub: Int { - case bookOne = 0 - case bookTwo - - var name: String { - switch self { - case .bookOne: return "The Silver Chair" // standard eBook - case .bookTwo: return "The Adventures Of Sherlock Holmes - Adventure I" // audio-eBook - } - } - - var shouldHideNavigationOnTap: Bool { - switch self { - case .bookOne: return false - case .bookTwo: return true - } - } - - var scrollDirection: FolioReaderScrollDirection { - switch self { - case .bookOne: return .vertical - case .bookTwo: return .horizontal - } - } - - var bookPath: String? { - return Bundle.main.path(forResource: self.name, ofType: "epub") - } - - func retain(folioReaderContainer: FolioReaderContainer) { - let appDelegate = (UIApplication.shared.delegate as? AppDelegate) - - switch self { - case .bookOne: appDelegate?.standardEpub = folioReaderContainer - case .bookTwo: appDelegate?.audioEpub = folioReaderContainer - } - } + case bookOne = 0 + case bookTwo + + var name: String { + switch self { + case .bookOne: return "The Silver Chair" // standard eBook + case .bookTwo: return "The Adventures Of Sherlock Holmes - Adventure I" // audio-eBook + } + } + + var shouldHideNavigationOnTap: Bool { + switch self { + case .bookOne: return false + case .bookTwo: return true + } + } + + var scrollDirection: FolioReaderScrollDirection { + switch self { + case .bookOne: return .vertical + case .bookTwo: return .horizontal + } + } + + var bookPath: String? { + return Bundle.main.path(forResource: self.name, ofType: "epub") + } + + func retain(folioReaderContainer: FolioReaderContainer) { + let appDelegate = (UIApplication.shared.delegate as? AppDelegate) + + switch self { + case .bookOne: appDelegate?.standardEpub = folioReaderContainer + case .bookTwo: appDelegate?.audioEpub = folioReaderContainer + } + } } -class ViewController : UIViewController { +class ViewController: UIViewController { - @IBOutlet var bookOne : UIButton? - @IBOutlet var bookTwo : UIButton? + @IBOutlet var bookOne : UIButton? + @IBOutlet var bookTwo : UIButton? override func viewDidLoad() { super.viewDidLoad() - self.bookOne?.tag = Epub.bookOne.rawValue - self.bookTwo?.tag = Epub.bookTwo.rawValue + self.bookOne?.tag = Epub.bookOne.rawValue + self.bookTwo?.tag = Epub.bookTwo.rawValue self.setCover(self.bookOne, index: 0) self.setCover(self.bookTwo, index: 1) } - private func readerConfiguration(forEpub epub: Epub) -> FolioReaderConfig { - - let config = FolioReaderConfig() - config.shouldHideNavigationOnTap = epub.shouldHideNavigationOnTap - config.scrollDirection = epub.scrollDirection - - // See more at FolioReaderConfig.swift - // config.canChangeScrollDirection = false - // config.enableTTS = false - // config.allowSharing = false - // config.tintColor = UIColor.blueColor() - // config.toolBarTintColor = UIColor.redColor() - // config.toolBarBackgroundColor = UIColor.purpleColor() - // config.menuTextColor = UIColor.brownColor() - // config.menuBackgroundColor = UIColor.lightGrayColor() - // config.hidePageIndicator = true - // config.realmConfiguration = Realm.Configuration(fileURL: FileManager.default.urls(for: .documentDirectory, in: .userDomainMask).first?.appendingPathComponent("highlights.realm")) - - // Custom sharing quote background - config.quoteCustomBackgrounds = [] - if let image = UIImage(named: "demo-bg") { - let customImageQuote = QuoteImage(withImage: image, alpha: 0.6, backgroundColor: UIColor.black) - config.quoteCustomBackgrounds.append(customImageQuote) - } - - let textColor = UIColor(red:0.86, green:0.73, blue:0.70, alpha:1.0) - let customColor = UIColor(red:0.30, green:0.26, blue:0.20, alpha:1.0) - let customQuote = QuoteImage(withColor: customColor, alpha: 1.0, textColor: textColor) - config.quoteCustomBackgrounds.append(customQuote) - - return config - } + private func readerConfiguration(forEpub epub: Epub) -> FolioReaderConfig { + + let config = FolioReaderConfig() + config.shouldHideNavigationOnTap = epub.shouldHideNavigationOnTap + config.scrollDirection = epub.scrollDirection + + // See more at FolioReaderConfig.swift + // config.canChangeScrollDirection = false + // config.enableTTS = false + // config.allowSharing = false + // config.tintColor = UIColor.blueColor() + // config.toolBarTintColor = UIColor.redColor() + // config.toolBarBackgroundColor = UIColor.purpleColor() + // config.menuTextColor = UIColor.brownColor() + // config.menuBackgroundColor = UIColor.lightGrayColor() + // config.hidePageIndicator = true + // config.realmConfiguration = Realm.Configuration(fileURL: FileManager.default.urls(for: .documentDirectory, in: .userDomainMask).first?.appendingPathComponent("highlights.realm")) + + // Custom sharing quote background + config.quoteCustomBackgrounds = [] + if let image = UIImage(named: "demo-bg") { + let customImageQuote = QuoteImage(withImage: image, alpha: 0.6, backgroundColor: UIColor.black) + config.quoteCustomBackgrounds.append(customImageQuote) + } + + let textColor = UIColor(red:0.86, green:0.73, blue:0.70, alpha:1.0) + let customColor = UIColor(red:0.30, green:0.26, blue:0.20, alpha:1.0) + let customQuote = QuoteImage(withColor: customColor, alpha: 1.0, textColor: textColor) + config.quoteCustomBackgrounds.append(customQuote) + + return config + } fileprivate func open(epub: Epub) { - guard let bookPath = epub.bookPath else { - return - } + guard let bookPath = epub.bookPath else { + return + } - let readerConfiguration = self.readerConfiguration(forEpub: epub) + let readerConfiguration = self.readerConfiguration(forEpub: epub) let folioReaderContainer = FolioReader.presentReader(parentViewController: self, withEpubPath: bookPath, andConfig: readerConfiguration, shouldRemoveEpub: false) - epub.retain(folioReaderContainer: folioReaderContainer) + epub.retain(folioReaderContainer: folioReaderContainer) } - + private func setCover(_ button: UIButton?, index: Int) { - guard - let epub = Epub(rawValue: index), - let bookPath = epub.bookPath, - let image = FolioReader.getCoverImage(bookPath) else { - return - } - - button?.setBackgroundImage(image, for: .normal) + guard + let epub = Epub(rawValue: index), + let bookPath = epub.bookPath, + let image = FolioReader.getCoverImage(bookPath) else { + return + } + + button?.setBackgroundImage(image, for: .normal) } } // MARK: - IBAction extension ViewController { - - @IBAction func didOpen(_ sender: AnyObject) { - guard let epub = Epub(rawValue: sender.tag) else { - return - } - - self.open(epub: epub) - } + + @IBAction func didOpen(_ sender: AnyObject) { + guard let epub = Epub(rawValue: sender.tag) else { + return + } + + self.open(epub: epub) + } } diff --git a/Example/StoryboardExample/AppDelegate.swift b/Example/StoryboardExample/AppDelegate.swift index 1a1ba7b72..7821b17f6 100644 --- a/Example/StoryboardExample/AppDelegate.swift +++ b/Example/StoryboardExample/AppDelegate.swift @@ -10,20 +10,20 @@ import UIKit import FolioReaderKit @UIApplicationMain -class AppDelegate : UIResponder, UIApplicationDelegate { - - var window : UIWindow? - var epubReader : FolioReaderContainer? +class AppDelegate: UIResponder, UIApplicationDelegate { + + var window : UIWindow? + var epubReader : FolioReaderContainer? func application(_ application: UIApplication, didFinishLaunchingWithOptions launchOptions: [UIApplicationLaunchOptionsKey: Any]?) -> Bool { // Override point for customization after application launch. return true } - + func applicationWillResignActive(_ application: UIApplication) { self.epubReader?.saveReaderState() } - + func applicationWillTerminate(_ application: UIApplication) { self.epubReader?.saveReaderState() } diff --git a/Example/StoryboardExample/ExampleFolioReaderContainer.swift b/Example/StoryboardExample/ExampleFolioReaderContainer.swift index 370dcb405..3573c2e5f 100644 --- a/Example/StoryboardExample/ExampleFolioReaderContainer.swift +++ b/Example/StoryboardExample/ExampleFolioReaderContainer.swift @@ -11,24 +11,24 @@ import FolioReaderKit class ExampleFolioReaderContainer: FolioReaderContainer { - required init?(coder aDecoder: NSCoder) { + required init?(coder aDecoder: NSCoder) { super.init(coder: aDecoder) - + let config = FolioReaderConfig() config.scrollDirection = .horizontalWithVerticalContent - config.shouldHideNavigationOnTap = false + config.shouldHideNavigationOnTap = false - // Print the chapter ID if one was clicked - // A chapter in "The Silver Chair" looks like this "
" - // To know if a user tapped on a chapter we can listen to events on the class "chapter" and receive the id value - let listener = ClassBasedOnClickListener(schemeName: "chaptertapped", querySelector: ".chapter", attributeName: "id", onClickAction: { (attributeContent: String?, touchPointRelativeToWebView: CGPoint?) in - print("chapter with id: " + (attributeContent ?? "-") + " clicked") - }) - config.classBasedOnClickListeners.append(listener) + // Print the chapter ID if one was clicked + // A chapter in "The Silver Chair" looks like this "
" + // To know if a user tapped on a chapter we can listen to events on the class "chapter" and receive the id value + let listener = ClassBasedOnClickListener(schemeName: "chaptertapped", querySelector: ".chapter", attributeName: "id", onClickAction: { (attributeContent: String?, touchPointRelativeToWebView: CGPoint?) in + print("chapter with id: " + (attributeContent ?? "-") + " clicked") + }) + config.classBasedOnClickListeners.append(listener) guard let bookPath = Bundle.main.path(forResource: "The Silver Chair", ofType: "epub") else { return } setupConfig(config, epubPath: bookPath) - (UIApplication.shared.delegate as? AppDelegate)?.epubReader = self - } + (UIApplication.shared.delegate as? AppDelegate)?.epubReader = self + } } diff --git a/Source/EPUBCore/FRBook.swift b/Source/EPUBCore/FRBook.swift index 9d2e911ac..9e2fb0b56 100755 --- a/Source/EPUBCore/FRBook.swift +++ b/Source/EPUBCore/FRBook.swift @@ -10,19 +10,19 @@ import UIKit open class FRBook: NSObject { - var resources = FRResources() - var metadata = FRMetadata() - var spine = FRSpine() - var smils = FRSmils() - var tableOfContents: [FRTocReference]! - var flatTableOfContents: [FRTocReference]! - var opfResource: FRResource! - var tocResource: FRResource? - var coverImage: FRResource? - var version: Double? - var uniqueIdentifier: String? - var name: String? - + var resources = FRResources() + var metadata = FRMetadata() + var spine = FRSpine() + var smils = FRSmils() + var tableOfContents : [FRTocReference]! + var flatTableOfContents : [FRTocReference]! + var opfResource : FRResource! + var tocResource : FRResource? + var coverImage : FRResource? + var version : Double? + var uniqueIdentifier : String? + var name : String? + func hasAudio() -> Bool { return smils.smils.count > 0 ? true : false } @@ -41,49 +41,49 @@ open class FRBook: NSObject { func duration() -> String? { return metadata.findMetaByProperty("media:duration"); } - + // @NOTE: should "#" be automatically prefixed with the ID? func durationFor(_ ID: String) -> String? { return metadata.findMetaByProperty("media:duration", refinedBy: ID) } - - + + func activeClass() -> String { guard let className = metadata.findMetaByProperty("media:active-class") else { return "epub-media-overlay-active" } return className } - + func playbackActiveClass() -> String { guard let className = metadata.findMetaByProperty("media:playback-active-class") else { return "epub-media-overlay-playing" } return className } - - + + // MARK: - Media Overlay (SMIL) retrieval - + /** Get Smil File from a resource (if it has a media-overlay) - */ + */ func smilFileForResource(_ resource: FRResource!) -> FRSmilFile! { if( resource == nil || resource.mediaOverlay == nil ){ return nil } - + // lookup the smile resource to get info about the file let smilResource = resources.findById(resource.mediaOverlay) - + // use the resource to get the file return smils.findByHref( smilResource!.href ) } - + func smilFileForHref(_ href: String) -> FRSmilFile! { return smilFileForResource(resources.findByHref(href)) } - + func smilFileForId(_ ID: String) -> FRSmilFile! { return smilFileForResource(resources.findById(ID)) } diff --git a/Source/EPUBCore/FREpubParser.swift b/Source/EPUBCore/FREpubParser.swift index 5fc20b044..6465de20d 100755 --- a/Source/EPUBCore/FREpubParser.swift +++ b/Source/EPUBCore/FREpubParser.swift @@ -8,20 +8,20 @@ import UIKit #if COCOAPODS -import SSZipArchive + import SSZipArchive #else -import ZipArchive + import ZipArchive #endif import AEXML -class FREpubParser : NSObject, SSZipArchiveDelegate { +class FREpubParser: NSObject, SSZipArchiveDelegate { - let book = FRBook() - var bookBasePath : String! - var resourcesBasePath : String! - var shouldRemoveEpub = true + let book = FRBook() + var bookBasePath : String! + var resourcesBasePath : String! + var shouldRemoveEpub = true - fileprivate var epubPathToRemove: String? + fileprivate var epubPathToRemove : String? /// Parse the Cover Image from an epub file. /// @@ -31,9 +31,9 @@ class FREpubParser : NSObject, SSZipArchiveDelegate { /// - Returns: An UIImage object func parseCoverImage(_ epubPath: String, unzipPath: String? = nil) -> UIImage? { guard - let book = readEpub(epubPath: epubPath, removeEpub: false, unzipPath: unzipPath), - let coverImage = book.coverImage else { - return nil + let book = readEpub(epubPath: epubPath, removeEpub: false, unzipPath: unzipPath), + let coverImage = book.coverImage else { + return nil } return UIImage(contentsOfFile: coverImage.fullHref) } @@ -48,7 +48,7 @@ class FREpubParser : NSObject, SSZipArchiveDelegate { func parseAuthorName(_ epubPath: String) -> String? { guard let book = readEpub(epubPath: epubPath, removeEpub: false), let authorName = book.authorName() else { - return nil + return nil } return authorName } @@ -56,7 +56,7 @@ class FREpubParser : NSObject, SSZipArchiveDelegate { /** Unzip, delete and read an epub file. Returns a FRBook. - */ + */ func readEpub(epubPath withEpubPath: String, removeEpub: Bool = true, unzipPath: String? = nil) -> FRBook? { epubPathToRemove = withEpubPath shouldRemoveEpub = removeEpub @@ -77,7 +77,7 @@ class FREpubParser : NSObject, SSZipArchiveDelegate { print("Epub file does not exist.") return nil } - + // Unzip if necessary var needsUnzip = false if fileManager.fileExists(atPath: bookBasePath, isDirectory:&isDir) { @@ -85,26 +85,26 @@ class FREpubParser : NSObject, SSZipArchiveDelegate { } else { needsUnzip = true } - + if needsUnzip { SSZipArchive.unzipFile(atPath: withEpubPath, toDestination: bookBasePath, delegate: self) } - + // Skip from backup this folder addSkipBackupAttributeToItemAtURL(URL(fileURLWithPath: bookBasePath, isDirectory: true)) - self.book.name = bookName + self.book.name = bookName readContainer() readOpf() return self.book } - + /** Read and parse container.xml file. - */ + */ fileprivate func readContainer() { let containerPath = "META-INF/container.xml" - + do { let containerData = try Data(contentsOf: URL(fileURLWithPath: (bookBasePath as NSString).appendingPathComponent(containerPath)), options: .alwaysMapped) let xmlDoc = try AEXMLDocument(xml: containerData) @@ -117,27 +117,27 @@ class FREpubParser : NSObject, SSZipArchiveDelegate { print("Cannot read container.xml") } } - + /** Read and parse .opf file. - */ + */ fileprivate func readOpf() { let opfPath = (bookBasePath as NSString).appendingPathComponent(book.opfResource.href) var identifier: String? - + do { let opfData = try Data(contentsOf: URL(fileURLWithPath: opfPath), options: .alwaysMapped) let xmlDoc = try AEXMLDocument(xml: opfData) - + // Base OPF info if let package = xmlDoc.children.first { identifier = package.attributes["unique-identifier"] - + if let version = package.attributes["version"] { book.version = Double(version) } } - + // Parse and save each "manifest item" for item in xmlDoc.root["manifest"]["item"].all! { let resource = FRResource() @@ -147,20 +147,20 @@ class FREpubParser : NSObject, SSZipArchiveDelegate { resource.fullHref = (resourcesBasePath as NSString).appendingPathComponent(resource.href).removingPercentEncoding resource.mediaType = FRMediaType.mediaTypeByName(item.attributes["media-type"]!, fileName: resource.href) resource.mediaOverlay = item.attributes["media-overlay"] - + // if a .smil file is listed in resources, go parse that file now and save it on book model if (resource.mediaType != nil && resource.mediaType == FRMediaType.SMIL) { readSmilFile(resource) } - + book.resources.add(resource) } - + book.smils.basePath = resourcesBasePath - + // Read metadata book.metadata = readMetadata(xmlDoc.root["metadata"].children) - + // Read the book unique identifier if let uniqueIdentifier = book.metadata.findIdentifierById(identifier) { book.uniqueIdentifier = uniqueIdentifier @@ -173,7 +173,7 @@ class FREpubParser : NSObject, SSZipArchiveDelegate { } else if let coverResource = book.resources.findByProperties("cover-image") { book.coverImage = coverResource } - + // Specific TOC for ePub 2 and 3 // Get the first resource with the NCX mediatype if let tocResource = book.resources.findByMediaType(FRMediaType.NCX) { @@ -184,17 +184,17 @@ class FREpubParser : NSObject, SSZipArchiveDelegate { } else if let tocResource = book.resources.findByProperties("nav") { book.tocResource = tocResource } - + assert(book.tocResource != nil, "ERROR: Could not find table of contents resource. The book don't have a TOC resource.") - + // The book TOC book.tableOfContents = findTableOfContents() book.flatTableOfContents = createFlatTOC() - + // Read Spine let spine = xmlDoc.root["spine"] book.spine = readSpine(spine.children) - + // Page progress direction `ltr` or `rtl` if let pageProgressionDirection = spine.attributes["page-progression-direction"] { book.spine.pageProgressionDirection = pageProgressionDirection @@ -203,28 +203,28 @@ class FREpubParser : NSObject, SSZipArchiveDelegate { print("Cannot read .opf file.") } } - + /** Reads and parses a .smil file - */ + */ fileprivate func readSmilFile(_ resource: FRResource) { do { let smilData = try Data(contentsOf: URL(fileURLWithPath: resource.fullHref), options: .alwaysMapped) var smilFile = FRSmilFile(resource: resource) let xmlDoc = try AEXMLDocument(xml: smilData) - + let children = xmlDoc.root["body"].children if children.count > 0 { smilFile.data.append(contentsOf: readSmilFileElements(children)) } - + book.smils.add(smilFile) } catch { print("Cannot read .smil file: "+resource.href) } } - + fileprivate func readSmilFileElements(_ children:[AEXMLElement]) -> [FRSmilElement] { var data = [FRSmilElement]() @@ -246,13 +246,13 @@ class FREpubParser : NSObject, SSZipArchiveDelegate { /** Read and parse the Table of Contents. - */ + */ fileprivate func findTableOfContents() -> [FRTocReference] { var tableOfContent = [FRTocReference]() var tocItems: [AEXMLElement]? guard let tocResource = book.tocResource else { return tableOfContent } let tocPath = (resourcesBasePath as NSString).appendingPathComponent(tocResource.href) - + do { if tocResource.mediaType == FRMediaType.NCX { let ncxData = try Data(contentsOf: URL(fileURLWithPath: tocPath), options: .alwaysMapped) @@ -263,7 +263,7 @@ class FREpubParser : NSObject, SSZipArchiveDelegate { } else { let tocData = try Data(contentsOf: URL(fileURLWithPath: tocPath), options: .alwaysMapped) let xmlDoc = try AEXMLDocument(xml: tocData) - + if let nav = xmlDoc.root["body"]["nav"].first, let itemsList = nav["ol"]["li"].all { tocItems = itemsList } else if let nav = findNavTag(xmlDoc.root["body"]), let itemsList = nav["ol"]["li"].all { @@ -273,19 +273,19 @@ class FREpubParser : NSObject, SSZipArchiveDelegate { } catch { print("Cannot find Table of Contents.") } - + guard let items = tocItems else { return tableOfContent } - + for item in items { tableOfContent.append(readTOCReference(item)) } - + return tableOfContent } - + /** Recursively finds a `