diff --git a/Example.xcodeproj/project.pbxproj b/Example.xcodeproj/project.pbxproj index 3ce5ed2..d128177 100644 --- a/Example.xcodeproj/project.pbxproj +++ b/Example.xcodeproj/project.pbxproj @@ -8,6 +8,8 @@ /* Begin PBXBuildFile section */ 4D137EB819C1BE5700AC1050 /* LaunchScreen.xib in Resources */ = {isa = PBXBuildFile; fileRef = 4D137EB619C1BE5700AC1050 /* LaunchScreen.xib */; }; + 4D4ECAD51CBE8B32000CF6FA /* StatefulPlaceholderView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 4D4ECAD31CBE89EA000CF6FA /* StatefulPlaceholderView.swift */; }; + 4D4ECAD61CBE8B33000CF6FA /* StatefulPlaceholderView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 4D4ECAD31CBE89EA000CF6FA /* StatefulPlaceholderView.swift */; }; 4D64514B1A64079200108EA3 /* StatefulViewController.h in Headers */ = {isa = PBXBuildFile; fileRef = 4D64514A1A64079200108EA3 /* StatefulViewController.h */; settings = {ATTRIBUTES = (Public, ); }; }; 4D6451511A64079300108EA3 /* StatefulViewController.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = 4D6451461A64079200108EA3 /* StatefulViewController.framework */; }; 4D64515A1A64079300108EA3 /* StatefulViewControllerTests.swift in Sources */ = {isa = PBXBuildFile; fileRef = 4D6451591A64079300108EA3 /* StatefulViewControllerTests.swift */; }; @@ -70,6 +72,7 @@ /* Begin PBXFileReference section */ 4D137EB719C1BE5700AC1050 /* Base */ = {isa = PBXFileReference; lastKnownFileType = file.xib; name = Base; path = Base.lproj/LaunchScreen.xib; sourceTree = ""; }; + 4D4ECAD31CBE89EA000CF6FA /* StatefulPlaceholderView.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = StatefulPlaceholderView.swift; sourceTree = ""; }; 4D6451461A64079200108EA3 /* StatefulViewController.framework */ = {isa = PBXFileReference; explicitFileType = wrapper.framework; includeInIndex = 0; path = StatefulViewController.framework; sourceTree = BUILT_PRODUCTS_DIR; }; 4D6451491A64079200108EA3 /* Info.plist */ = {isa = PBXFileReference; lastKnownFileType = text.plist.xml; path = Info.plist; sourceTree = ""; }; 4D64514A1A64079200108EA3 /* StatefulViewController.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = StatefulViewController.h; sourceTree = ""; }; @@ -132,6 +135,7 @@ 4D6451661A64089800108EA3 /* StatefulViewController.swift */, 4DC230DC1BB5BA810083B95A /* StatefulViewControllerImplementation.swift */, 4D6451671A64089800108EA3 /* ViewStateMachine.swift */, + 4D4ECAD31CBE89EA000CF6FA /* StatefulPlaceholderView.swift */, 4D64514A1A64079200108EA3 /* StatefulViewController.h */, 4D6451481A64079200108EA3 /* Supporting Files */, ); @@ -401,6 +405,7 @@ files = ( 4DC230DD1BB5BA810083B95A /* StatefulViewControllerImplementation.swift in Sources */, 4D6451691A64089800108EA3 /* ViewStateMachine.swift in Sources */, + 4D4ECAD51CBE8B32000CF6FA /* StatefulPlaceholderView.swift in Sources */, 4D6451681A64089800108EA3 /* StatefulViewController.swift in Sources */, ); runOnlyForDeploymentPostprocessing = 0; @@ -432,6 +437,7 @@ files = ( 523646921C6F88CF00392180 /* StatefulViewControllerImplementation.swift in Sources */, 523646931C6F88CF00392180 /* ViewStateMachine.swift in Sources */, + 4D4ECAD61CBE8B33000CF6FA /* StatefulPlaceholderView.swift in Sources */, 523646911C6F88CF00392180 /* StatefulViewController.swift in Sources */, ); runOnlyForDeploymentPostprocessing = 0; diff --git a/Example/PlaceholderViews/LoadingView.swift b/Example/PlaceholderViews/LoadingView.swift index 1211b97..f8ed028 100644 --- a/Example/PlaceholderViews/LoadingView.swift +++ b/Example/PlaceholderViews/LoadingView.swift @@ -7,15 +7,16 @@ // import UIKit +import StatefulViewController -class LoadingView: BasicPlaceholderView { +class LoadingView: BasicPlaceholderView, StatefulPlaceholderView { let label = UILabel() override func setupView() { super.setupView() - backgroundColor = UIColor.whiteColor() + backgroundColor = UIColor.redColor() label.text = "Loading..." label.translatesAutoresizingMaskIntoConstraints = false @@ -36,4 +37,8 @@ class LoadingView: BasicPlaceholderView { centerView.addConstraints(vConstraintsActivity) } + func placeholderViewInsets() -> UIEdgeInsets { + return UIEdgeInsets(top: 100, left: 10, bottom: 200, right: 50) + } + } diff --git a/README.md b/README.md index 114e04a..06a2feb 100644 --- a/README.md +++ b/README.md @@ -98,7 +98,24 @@ func handleErrorWhenContentAvailable(error: ErrorType) { } ``` + + +### Custom Placeholder View insets + +Per default, StatefulViewController presents all configured placeholder views fullscreen (i.e. with 0 insets from top, bottom, left & right from the superview). In case a placeholder view should have custom insets the configured placeholderview may conform to the `StatefulPlaceholderView` protocol and override the `placeholderViewInsets` method to return custom edge insets. + +```swift +class MyPlaceholderView: UIView, StatefulPlaceholderView { + func placeholderViewInsets() -> UIEdgeInsets { + return UIEdgeInsets(top: 20, left: 20, bottom: 20, right: 20) + } +} +``` + + + + ### View State Machine > Note: The following section is only intended for those, who want to create a stateful controller that differs from the flow described above. diff --git a/StatefulViewController/StatefulPlaceholderView.swift b/StatefulViewController/StatefulPlaceholderView.swift new file mode 100644 index 0000000..a1bf5b2 --- /dev/null +++ b/StatefulViewController/StatefulPlaceholderView.swift @@ -0,0 +1,24 @@ +// +// StatefulPlaceholderView.swift +// Example +// +// Created by Alexander Schuch on 13/04/16. +// Copyright © 2016 Alexander Schuch. All rights reserved. +// + +import UIKit + +public protocol StatefulPlaceholderView { + /// Defines the insets to apply when presented via the `StatefulViewController` + /// Return insets here in order to inset the current placeholder view from the edges + /// of the parent view. + func placeholderViewInsets() -> UIEdgeInsets +} + +extension StatefulPlaceholderView { + + public func placeholderViewInsets() -> UIEdgeInsets { + return UIEdgeInsets() + } + +} diff --git a/StatefulViewController/ViewStateMachine.swift b/StatefulViewController/ViewStateMachine.swift index 09d5101..1e83fab 100644 --- a/StatefulViewController/ViewStateMachine.swift +++ b/StatefulViewController/ViewStateMachine.swift @@ -149,10 +149,13 @@ public class ViewStateMachine { newView.alpha = animated ? 0.0 : 1.0 newView.translatesAutoresizingMaskIntoConstraints = false self.view.addSubview(newView) - + + let insets = (newView as? StatefulPlaceholderView)?.placeholderViewInsets() ?? UIEdgeInsets() + let metrics = ["top": insets.top, "bottom": insets.bottom, "left": insets.left, "right": insets.right] let views = ["view": newView] - let hConstraints = NSLayoutConstraint.constraintsWithVisualFormat("|[view]|", options: [], metrics: nil, views: views) - let vConstraints = NSLayoutConstraint.constraintsWithVisualFormat("V:|[view]|", options: [], metrics: nil, views: views) + + let hConstraints = NSLayoutConstraint.constraintsWithVisualFormat("|-left-[view]-right-|", options: [], metrics: metrics, views: views) + let vConstraints = NSLayoutConstraint.constraintsWithVisualFormat("V:|-top-[view]-bottom-|", options: [], metrics: metrics, views: views) self.view.addConstraints(hConstraints) self.view.addConstraints(vConstraints) }