move behavior

This commit is contained in:
Pfeil, Scott Robert 2021-02-10 12:40:23 -05:00
parent c473177832
commit d333e449fe
5 changed files with 76 additions and 102 deletions

View File

@ -16,10 +16,6 @@ open class Video: View {
/// Used to track the state and respond..
private var stateKVOToken: NSKeyValueObservation?
private weak var pauseBehavior: BlockPageVisibilityBehavior?
private weak var scrollBehavior: BlockPageScrolledBehavior?
private var visible = true
open override func setupView() {
@ -54,9 +50,8 @@ open class Video: View {
}
// Handle pause behavior
addVisibleBehavoir(to: model, delegateObject: delegateObject)
addScrolledBehavoir(to: model, delegateObject: delegateObject)
// addForegroundCheck()
model.addVisibleBehavoir(for: self, delegateObject: delegateObject)
model.addScrollBehavoir(for: self, delegateObject: delegateObject)
}
/// Listens and responds to video loading state changes.
@ -102,62 +97,4 @@ open class Video: View {
deinit {
removeStateObserver()
}
/// Adds a behavoir to pause the video on page hidden behavoir and unpause if necessary on page shown.
open func addVisibleBehavoir(to model: VideoModel, delegateObject: MVMCoreUIDelegateObject?) {
let onShow = { [weak self] in
guard self?.visible == true,
let model = self?.model as? VideoModel,
model.autoPlay else { return }
model.videoDataManager.player?.play()
}
let onHide: () -> Void = { [weak self] in
guard self?.visible == true,
let model = self?.model as? VideoModel else { return }
model.videoDataManager.player?.pause()
}
if pauseBehavior != nil {
pauseBehavior?.pageShownHandler = onShow
pauseBehavior?.pageHiddenHandler = onHide
} else {
guard let delegate = delegateObject?.moleculeDelegate,
let page = delegate as? PageProtocol,
var pageModel = page.pageModel as? PageBehaviorsTemplateProtocol else { return }
var behavoirs = pageModel.behaviors ?? []
let pauseBehavior = BlockPageVisibilityBehavior(with: onShow, onPageHiddenHandler: onHide)
behavoirs.append(pauseBehavior)
pageModel.behaviors = behavoirs
self.pauseBehavior = pauseBehavior
}
}
open func addScrolledBehavoir(to model: VideoModel, delegateObject: MVMCoreUIDelegateObject?) {
let onScroll = { [weak self] (scrollView: UIScrollView) in
// If visible to not visible, pause video.
// If not visible to visible, unpause if needed, add visible behavior
// visible ==
// if !visible {
// pause
// } else {
// let model = self?.model as? VideoModel,
// model.autoPlay else { return }
// model.videoDataManager.player?.play()
// }
}
if scrollBehavior != nil {
scrollBehavior?.pageScrolledHandler = onScroll
} else {
guard let delegate = delegateObject?.moleculeDelegate,
let page = delegate as? PageProtocol,
var pageModel = page.pageModel as? PageBehaviorsTemplateProtocol else { return }
var behavoirs = pageModel.behaviors ?? []
let scrollBehavior = BlockPageScrolledBehavior(with: onScroll)
behavoirs.append(scrollBehavior)
pageModel.behaviors = behavoirs
self.scrollBehavior = scrollBehavior
}
}
}

View File

@ -127,6 +127,8 @@ import Foundation
}
private func removeMemoryWarningListener() {
guard let observer = memoryWarningListener else { return }
NotificationCenter.default.removeObserver(observer)
memoryWarningListener = nil
}

View File

@ -18,6 +18,9 @@ open class VideoModel: MoleculeModelProtocol {
/// Keeps a reference to the video data.
public var videoDataManager: VideoDataManager
private weak var visibleBehavior: BlockPageVisibilityBehavior?
private weak var scrollBehavior: BlockPageScrolledBehavior?
private enum CodingKeys: String, CodingKey {
case moleculeName
@ -35,7 +38,6 @@ open class VideoModel: MoleculeModelProtocol {
required public init(from decoder: Decoder) throws {
let typeContainer = try decoder.container(keyedBy: CodingKeys.self)
video = try typeContainer.decode(String.self, forKey:.video)
videoDataManager = VideoDataManager(with: video)
if let showControls = try typeContainer.decodeIfPresent(Bool.self, forKey: .showControls) {
self.showControls = showControls
}
@ -45,6 +47,7 @@ open class VideoModel: MoleculeModelProtocol {
if let alwaysReset = try typeContainer.decodeIfPresent(Bool.self, forKey: .alwaysReset) {
self.alwaysReset = alwaysReset
}
videoDataManager = VideoDataManager(with: video)
}
open func encode(to encoder: Encoder) throws {
@ -55,4 +58,63 @@ open class VideoModel: MoleculeModelProtocol {
try container.encode(autoPlay, forKey: .autoPlay)
try container.encode(alwaysReset, forKey: .alwaysReset)
}
// Temporary
func isVisible(view: UIView) -> Bool {
return true
}
/// Adds a behavoir to pause the video on page hidden behavoir and unpause if necessary on page shown.
open func addVisibleBehavoir(for view: Video, delegateObject: MVMCoreUIDelegateObject?) {
let onShow = { [weak self] in
guard let self = self,
self.isVisible(view: view),
self.autoPlay else { return }
self.videoDataManager.player?.play()
}
let onHide: () -> Void = { [weak self] in
guard let self = self else { return }
self.videoDataManager.player?.pause()
}
guard visibleBehavior == nil else {
visibleBehavior?.pageShownHandler = onShow
visibleBehavior?.pageHiddenHandler = onHide
return
}
guard let delegate = delegateObject?.moleculeDelegate,
let page = delegate as? PageProtocol,
var pageModel = page.pageModel as? PageBehaviorsTemplateProtocol else { return }
let pauseBehavior = BlockPageVisibilityBehavior(with: onShow, onPageHiddenHandler: onHide)
pageModel.add(behavior: pauseBehavior)
self.visibleBehavior = pauseBehavior
}
/// Adds a behavoir to pause the video if scrolled off of the page and unpause if necessary if scrolled on.
open func addScrollBehavoir(for view: Video, delegateObject: MVMCoreUIDelegateObject?) {
let onScroll = { [weak self] (scrollView: UIScrollView) in
// If visible to not visible, pause video.
// If not visible to visible, unpause if needed, add visible behavior
guard let self = self else { return }
if !self.isVisible(view: view) {
self.videoDataManager.player?.pause()
} else if self.autoPlay {
self.videoDataManager.player?.play()
}
}
guard scrollBehavior == nil else {
scrollBehavior?.pageScrolledHandler = onScroll
return
}
guard let delegate = delegateObject?.moleculeDelegate,
let page = delegate as? PageProtocol,
var pageModel = page.pageModel as? PageBehaviorsTemplateProtocol else { return }
let scrollBehavior = BlockPageScrolledBehavior(with: onScroll)
pageModel.add(behavior: scrollBehavior)
self.scrollBehavior = scrollBehavior
}
}

View File

@ -73,38 +73,3 @@ public class BlockPageScrolledBehavior: PageScrolledBehavior {
pageScrolledHandler(scrollView)
}
}
public class VideoPauseBehavior: PageVisibilityBehavior {
public static var identifier = "videoPause"
public weak var videoModel: VideoModel?
public init(with videoModel: VideoModel) {
self.videoModel = videoModel
}
private enum CodingKeys: String, CodingKey {
case behaviorName
}
//MARK:- PageVisibilityBehavior
public func onPageShown() {
// TODO: Only do this if attached to a visible view...
if videoModel?.autoPlay == true {
videoModel?.videoDataManager.player?.play()
}
}
public func onPageHidden() {
videoModel?.videoDataManager.player?.pause()
}
public required init(from decoder: Decoder) throws {}
public func encode(to encoder: Encoder) throws {
var container = encoder.container(keyedBy: CodingKeys.self)
try container.encode(behaviorName, forKey: .behaviorName)
}
}

View File

@ -43,5 +43,13 @@ public protocol PageScrolledBehavior: PageBehaviorProtocol {
public protocol PageBehaviorsTemplateProtocol {
var behaviors: [PageBehaviorProtocol]? { get set }
}
public extension PageBehaviorsTemplateProtocol {
mutating func add(behavior: PageBehaviorProtocol) {
var behavoirs = behaviors ?? []
behavoirs.append(behavior)
self.behaviors = behavoirs
}
}