added iOS source code
[wl-app.git] / iOS / Pods / FolioReaderKit / Source / FolioReaderContainer.swift
1 //
2 //  FolioReaderContainer.swift
3 //  FolioReaderKit
4 //
5 //  Created by Heberti Almeida on 15/04/15.
6 //  Copyright (c) 2015 Folio Reader. All rights reserved.
7 //
8
9 import UIKit
10 import FontBlaster
11
12 /// Reader container
13 open class FolioReaderContainer: UIViewController {
14     var shouldHideStatusBar = true
15     var shouldRemoveEpub = true
16     
17     // Mark those property as public so they can accessed from other classes/subclasses.
18     public var epubPath: String
19         public var unzipPath: String?
20     public var book: FRBook
21     
22     public var centerNavigationController: UINavigationController?
23     public var centerViewController: FolioReaderCenter?
24     public var audioPlayer: FolioReaderAudioPlayer?
25     
26     public var readerConfig: FolioReaderConfig
27     public var folioReader: FolioReader
28
29     fileprivate var errorOnLoad = false
30
31     // MARK: - Init
32
33     /// Init a Folio Reader Container
34     ///
35     /// - Parameters:
36     ///   - config: Current Folio Reader configuration
37     ///   - folioReader: Current instance of the FolioReader kit.
38     ///   - path: The ePub path on system. Must not be nil nor empty string.
39         ///   - unzipPath: Path to unzip the compressed epub.
40     ///   - removeEpub: Should delete the original file after unzip? Default to `true` so the ePub will be unziped only once.
41     public init(withConfig config: FolioReaderConfig, folioReader: FolioReader, epubPath path: String, unzipPath: String? = nil, removeEpub: Bool = true) {
42         self.readerConfig = config
43         self.folioReader = folioReader
44         self.epubPath = path
45                 self.unzipPath = unzipPath
46         self.shouldRemoveEpub = removeEpub
47         self.book = FRBook()
48
49         super.init(nibName: nil, bundle: Bundle.frameworkBundle())
50
51         // Configure the folio reader.
52         self.folioReader.readerContainer = self
53
54         // Initialize the default reader options.
55         if self.epubPath != "" {
56             self.initialization()
57         }
58     }
59
60     required public init?(coder aDecoder: NSCoder) {
61         // When a FolioReaderContainer object is instantiated from the storyboard this function is called before.
62         // At this moment, we need to initialize all non-optional objects with default values.
63         // The function `setupConfig(config:epubPath:removeEpub:)` MUST be called afterward.
64         // See the ExampleFolioReaderContainer.swift for more information?
65         self.readerConfig = FolioReaderConfig()
66         self.folioReader = FolioReader()
67         self.epubPath = ""
68         self.shouldRemoveEpub = false
69         self.book = FRBook()
70
71         super.init(coder: aDecoder)
72
73         // Configure the folio reader.
74         self.folioReader.readerContainer = self
75     }
76
77     /// Common Initialization
78     fileprivate func initialization() {
79         // Register custom fonts
80         FontBlaster.blast(bundle: Bundle.frameworkBundle())
81
82         // Register initial defaults
83         self.folioReader.register(defaults: [
84             kCurrentFontFamily: FolioReaderFont.andada.rawValue,
85             kNightMode: false,
86             kCurrentFontSize: 2,
87             kCurrentMarginSize: 2,
88             kCurrentInterlineSize: 2,
89             kCurrentAudioRate: 1,
90             kCurrentHighlightStyle: 0,
91             kCurrentTOCMenu: 0,
92             kCurrentMediaOverlayStyle: MediaOverlayStyle.default.rawValue,
93             kCurrentScrollDirection: FolioReaderScrollDirection.defaultVertical.rawValue
94             ])
95     }
96
97     /// Set the `FolioReaderConfig` and epubPath.
98     ///
99     /// - Parameters:
100     ///   - config: Current Folio Reader configuration
101     ///   - path: The ePub path on system. Must not be nil nor empty string.
102         ///   - unzipPath: Path to unzip the compressed epub.
103     ///   - removeEpub: Should delete the original file after unzip? Default to `true` so the ePub will be unziped only once.
104     open func setupConfig(_ config: FolioReaderConfig, epubPath path: String, unzipPath: String? = nil, removeEpub: Bool = true) {
105         self.readerConfig = config
106         self.folioReader = FolioReader()
107         self.folioReader.readerContainer = self
108         self.epubPath = path
109                 self.unzipPath = unzipPath
110         self.shouldRemoveEpub = removeEpub
111     }
112
113     // MARK: - View life cicle
114
115     override open func viewDidLoad() {
116         super.viewDidLoad()
117
118         let canChangeScrollDirection = self.readerConfig.canChangeScrollDirection
119         self.readerConfig.canChangeScrollDirection = self.readerConfig.isDirection(canChangeScrollDirection, canChangeScrollDirection, false)
120
121         // If user can change scroll direction use the last saved
122         if self.readerConfig.canChangeScrollDirection == true {
123             var scrollDirection = FolioReaderScrollDirection(rawValue: self.folioReader.currentScrollDirection) ?? .vertical
124             if (scrollDirection == .defaultVertical && self.readerConfig.scrollDirection != .defaultVertical) {
125                 scrollDirection = self.readerConfig.scrollDirection
126             }
127
128             self.readerConfig.scrollDirection = scrollDirection
129         }
130
131         let hideBars = readerConfig.hideBars
132         self.readerConfig.shouldHideNavigationOnTap = ((hideBars == true) ? true : self.readerConfig.shouldHideNavigationOnTap)
133
134         self.centerViewController = FolioReaderCenter(withContainer: self)
135
136         if let rootViewController = self.centerViewController {
137             self.centerNavigationController = UINavigationController(rootViewController: rootViewController)
138         }
139
140         self.centerNavigationController?.setNavigationBarHidden(self.readerConfig.shouldHideNavigationOnTap, animated: false)
141         if let _centerNavigationController = self.centerNavigationController {
142             self.view.addSubview(_centerNavigationController.view)
143             self.addChildViewController(_centerNavigationController)
144         }
145         self.centerNavigationController?.didMove(toParentViewController: self)
146
147         if (self.readerConfig.hideBars == true) {
148             self.readerConfig.shouldHideNavigationOnTap = false
149             self.navigationController?.navigationBar.isHidden = true
150             self.centerViewController?.pageIndicatorHeight = 0
151         }
152
153         // Read async book
154         guard (self.epubPath.isEmpty == false) else {
155             print("Epub path is nil.")
156             self.errorOnLoad = true
157             return
158         }
159
160         DispatchQueue.global(qos: .userInitiated).async {
161
162             do {
163                 let parsedBook = try FREpubParser().readEpub(epubPath: self.epubPath, removeEpub: self.shouldRemoveEpub, unzipPath: self.unzipPath)
164                 self.book = parsedBook
165                 self.folioReader.isReaderOpen = true
166
167                 // Reload data
168                 DispatchQueue.main.async {
169                     // Add audio player if needed
170                     if self.book.hasAudio || self.readerConfig.enableTTS {
171                         self.addAudioPlayer()
172                     }
173                     self.centerViewController?.reloadData()
174                     self.folioReader.isReaderReady = true
175                     self.folioReader.delegate?.folioReader?(self.folioReader, didFinishedLoading: self.book)
176                 }
177             } catch {
178                 self.errorOnLoad = true
179                 self.alert(message: error.localizedDescription)
180             }
181         }
182     }
183
184     override open func viewDidAppear(_ animated: Bool) {
185         super.viewDidAppear(animated)
186
187         if (self.errorOnLoad == true) {
188             self.dismiss()
189         }
190     }
191
192     /**
193      Initialize the media player
194      */
195     func addAudioPlayer() {
196         self.audioPlayer = FolioReaderAudioPlayer(withFolioReader: self.folioReader, book: self.book)
197         self.folioReader.readerAudioPlayer = audioPlayer
198     }
199
200     // MARK: - Status Bar
201
202     override open var prefersStatusBarHidden: Bool {
203         return (self.readerConfig.shouldHideNavigationOnTap == false ? false : self.shouldHideStatusBar)
204     }
205
206     override open var preferredStatusBarUpdateAnimation: UIStatusBarAnimation {
207         return UIStatusBarAnimation.slide
208     }
209
210     override open var preferredStatusBarStyle: UIStatusBarStyle {
211         return .lightContent // self.folioReader.isNight(.lightContent, .default)
212     }
213 }
214
215 extension FolioReaderContainer {
216     func alert(message: String) {
217         let alertController = UIAlertController(
218             title: "Error",
219             message: message,
220             preferredStyle: UIAlertControllerStyle.alert
221         )
222         let action = UIAlertAction(title: "OK", style: UIAlertActionStyle.cancel) { [weak self]
223             (result : UIAlertAction) -> Void in
224             self?.dismiss()
225         }
226         alertController.addAction(action)
227         self.present(alertController, animated: true, completion: nil)
228     }
229 }