Commit ffaaea85 by Daniel Dahan

development: added BottomSheetController and BottomSheet

parent 4b8a39b8
...@@ -9,6 +9,8 @@ ...@@ -9,6 +9,8 @@
/* Begin PBXBuildFile section */ /* Begin PBXBuildFile section */
961730361E0E156400A9A297 /* SpringMotion.swift in Sources */ = {isa = PBXBuildFile; fileRef = 961730351E0E156400A9A297 /* SpringMotion.swift */; }; 961730361E0E156400A9A297 /* SpringMotion.swift in Sources */ = {isa = PBXBuildFile; fileRef = 961730351E0E156400A9A297 /* SpringMotion.swift */; };
9617305A1E145DE900A9A297 /* CollectionViewCard.swift in Sources */ = {isa = PBXBuildFile; fileRef = 961730591E145DE900A9A297 /* CollectionViewCard.swift */; }; 9617305A1E145DE900A9A297 /* CollectionViewCard.swift in Sources */ = {isa = PBXBuildFile; fileRef = 961730591E145DE900A9A297 /* CollectionViewCard.swift */; };
961730701E16EFFF00A9A297 /* BottomSheet.swift in Sources */ = {isa = PBXBuildFile; fileRef = 9617306F1E16EFFF00A9A297 /* BottomSheet.swift */; };
961730721E16F00C00A9A297 /* BottomSheetController.swift in Sources */ = {isa = PBXBuildFile; fileRef = 961730711E16F00C00A9A297 /* BottomSheetController.swift */; };
9617B07D1DFCA8CF00410F8F /* Application.swift in Headers */ = {isa = PBXBuildFile; fileRef = 961E6BDE1DDA2A95004E6C93 /* Application.swift */; settings = {ATTRIBUTES = (Public, ); }; }; 9617B07D1DFCA8CF00410F8F /* Application.swift in Headers */ = {isa = PBXBuildFile; fileRef = 961E6BDE1DDA2A95004E6C93 /* Application.swift */; settings = {ATTRIBUTES = (Public, ); }; };
9617B07E1DFCA8CF00410F8F /* Card.swift in Headers */ = {isa = PBXBuildFile; fileRef = 96BCB75D1CB40DC500C806FE /* Card.swift */; settings = {ATTRIBUTES = (Public, ); }; }; 9617B07E1DFCA8CF00410F8F /* Card.swift in Headers */ = {isa = PBXBuildFile; fileRef = 96BCB75D1CB40DC500C806FE /* Card.swift */; settings = {ATTRIBUTES = (Public, ); }; };
9617B07F1DFCA8CF00410F8F /* ImageCard.swift in Headers */ = {isa = PBXBuildFile; fileRef = 96BCB7621CB40DC500C806FE /* ImageCard.swift */; settings = {ATTRIBUTES = (Public, ); }; }; 9617B07F1DFCA8CF00410F8F /* ImageCard.swift in Headers */ = {isa = PBXBuildFile; fileRef = 96BCB7621CB40DC500C806FE /* ImageCard.swift */; settings = {ATTRIBUTES = (Public, ); }; };
...@@ -228,6 +230,8 @@ ...@@ -228,6 +230,8 @@
961276621DCD8B1800A7D920 /* CharacterAttribute.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = CharacterAttribute.swift; sourceTree = "<group>"; }; 961276621DCD8B1800A7D920 /* CharacterAttribute.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = CharacterAttribute.swift; sourceTree = "<group>"; };
961730351E0E156400A9A297 /* SpringMotion.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = SpringMotion.swift; sourceTree = "<group>"; }; 961730351E0E156400A9A297 /* SpringMotion.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = SpringMotion.swift; sourceTree = "<group>"; };
961730591E145DE900A9A297 /* CollectionViewCard.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = CollectionViewCard.swift; sourceTree = "<group>"; }; 961730591E145DE900A9A297 /* CollectionViewCard.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = CollectionViewCard.swift; sourceTree = "<group>"; };
9617306F1E16EFFF00A9A297 /* BottomSheet.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = BottomSheet.swift; sourceTree = "<group>"; };
961730711E16F00C00A9A297 /* BottomSheetController.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = BottomSheetController.swift; sourceTree = "<group>"; };
961DED451DCC40C500F425B6 /* Editor.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = Editor.swift; sourceTree = "<group>"; }; 961DED451DCC40C500F425B6 /* Editor.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = Editor.swift; sourceTree = "<group>"; };
961DED4A1DCC546100F425B6 /* EditorController.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = EditorController.swift; sourceTree = "<group>"; }; 961DED4A1DCC546100F425B6 /* EditorController.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = EditorController.swift; sourceTree = "<group>"; };
961E6BDE1DDA2A95004E6C93 /* Application.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = Application.swift; sourceTree = "<group>"; }; 961E6BDE1DDA2A95004E6C93 /* Application.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = Application.swift; sourceTree = "<group>"; };
...@@ -386,6 +390,15 @@ ...@@ -386,6 +390,15 @@
name = TextField; name = TextField;
sourceTree = "<group>"; sourceTree = "<group>";
}; };
9617306E1E16EFE300A9A297 /* BottomSheet */ = {
isa = PBXGroup;
children = (
9617306F1E16EFFF00A9A297 /* BottomSheet.swift */,
961730711E16F00C00A9A297 /* BottomSheetController.swift */,
);
name = BottomSheet;
sourceTree = "<group>";
};
961DED441DCC40AC00F425B6 /* Editor */ = { 961DED441DCC40AC00F425B6 /* Editor */ = {
isa = PBXGroup; isa = PBXGroup;
children = ( children = (
...@@ -627,6 +640,7 @@ ...@@ -627,6 +640,7 @@
children = ( children = (
961E6BDD1DDA2A7E004E6C93 /* Application */, 961E6BDD1DDA2A7E004E6C93 /* Application */,
96264BE41D833C8400576F37 /* Bar */, 96264BE41D833C8400576F37 /* Bar */,
9617306E1E16EFE300A9A297 /* BottomSheet */,
962DDD081D6FBBD0001C307C /* BottomTabBar */, 962DDD081D6FBBD0001C307C /* BottomTabBar */,
96BCB8031CB40F4B00C806FE /* Button */, 96BCB8031CB40F4B00C806FE /* Button */,
96BCB8021CB40F3B00C806FE /* Card */, 96BCB8021CB40F3B00C806FE /* Card */,
...@@ -1200,6 +1214,7 @@ ...@@ -1200,6 +1214,7 @@
965E80E51DD4C53300D61E4B /* PulseMotion.swift in Sources */, 965E80E51DD4C53300D61E4B /* PulseMotion.swift in Sources */,
965E80FE1DD4D59500D61E4B /* ToolbarController.swift in Sources */, 965E80FE1DD4D59500D61E4B /* ToolbarController.swift in Sources */,
96328B971E05C0BB009A4C90 /* TableView.swift in Sources */, 96328B971E05C0BB009A4C90 /* TableView.swift in Sources */,
961730701E16EFFF00A9A297 /* BottomSheet.swift in Sources */,
965E80C81DD4C50600D61E4B /* Motion.swift in Sources */, 965E80C81DD4C50600D61E4B /* Motion.swift in Sources */,
965E80C91DD4C50600D61E4B /* TransitionMotion.swift in Sources */, 965E80C91DD4C50600D61E4B /* TransitionMotion.swift in Sources */,
965E80CA1DD4C50600D61E4B /* KeyframeMotion.swift in Sources */, 965E80CA1DD4C50600D61E4B /* KeyframeMotion.swift in Sources */,
...@@ -1222,6 +1237,7 @@ ...@@ -1222,6 +1237,7 @@
965E80D51DD4C50600D61E4B /* Grid.swift in Sources */, 965E80D51DD4C50600D61E4B /* Grid.swift in Sources */,
965E80D61DD4C50600D61E4B /* HeightPreset.swift in Sources */, 965E80D61DD4C50600D61E4B /* HeightPreset.swift in Sources */,
961E6BDF1DDA2A95004E6C93 /* Application.swift in Sources */, 961E6BDF1DDA2A95004E6C93 /* Application.swift in Sources */,
961730721E16F00C00A9A297 /* BottomSheetController.swift in Sources */,
965E80D71DD4C50600D61E4B /* Icon.swift in Sources */, 965E80D71DD4C50600D61E4B /* Icon.swift in Sources */,
965E80FC1DD4D59500D61E4B /* SearchBarController.swift in Sources */, 965E80FC1DD4D59500D61E4B /* SearchBarController.swift in Sources */,
965E80D81DD4C50600D61E4B /* Layer.swift in Sources */, 965E80D81DD4C50600D61E4B /* Layer.swift in Sources */,
......
/*
* Copyright (C) 2015 - 2016, Daniel Dahan and CosmicMind, Inc. <http://cosmicmind.com>.
* All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions are met:
*
* * Redistributions of source code must retain the above copyright notice, this
* list of conditions and the following disclaimer.
*
* * Redistributions in binary form must reproduce the above copyright notice,
* this list of conditions and the following disclaimer in the documentation
* and/or other materials provided with the distribution.
*
* * Neither the name of CosmicMind nor the names of its
* contributors may be used to endorse or promote products derived from
* this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
* DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
* SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
* CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
* OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
* OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
import UIKit
class BottomSheet: CollectionViewCard {
}
...@@ -175,7 +175,7 @@ open class Menu: Button { ...@@ -175,7 +175,7 @@ open class Menu: Button {
open override func prepare() { open override func prepare() {
super.prepare() super.prepare()
prepareCard() prepareCollectionViewCard()
prepareHandler() prepareHandler()
} }
...@@ -187,8 +187,8 @@ open class Menu: Button { ...@@ -187,8 +187,8 @@ open class Menu: Button {
} }
extension Menu { extension Menu {
/// Prepares the card. /// Prepares the collectionViewCard.
fileprivate func prepareCard() { fileprivate func prepareCollectionViewCard() {
collectionViewCard.collectionView.delegate = self collectionViewCard.collectionView.delegate = self
collectionViewCard.collectionView.dataSource = self collectionViewCard.collectionView.dataSource = self
collectionViewCard.collectionView.register(MenuCollectionViewCell.self, forCellWithReuseIdentifier: "MenuCollectionViewCell") collectionViewCard.collectionView.register(MenuCollectionViewCell.self, forCellWithReuseIdentifier: "MenuCollectionViewCell")
......
...@@ -181,7 +181,8 @@ open class NavigationDrawerController: RootController { ...@@ -181,7 +181,8 @@ open class NavigationDrawerController: RootController {
the leftView is opened, if it is below the threshold, the the leftView is opened, if it is below the threshold, the
leftView is closed. leftView is closed.
*/ */
@IBInspectable public var leftThreshold: CGFloat = 64 @IBInspectable
open var leftThreshold: CGFloat = 64
fileprivate var leftViewThreshold: CGFloat = 0 fileprivate var leftViewThreshold: CGFloat = 0
/** /**
...@@ -191,7 +192,8 @@ open class NavigationDrawerController: RootController { ...@@ -191,7 +192,8 @@ open class NavigationDrawerController: RootController {
the rightView is closed, if it is below the threshold, the the rightView is closed, if it is below the threshold, the
rightView is opened. rightView is opened.
*/ */
@IBInspectable public var rightThreshold: CGFloat = 64 @IBInspectable
open var rightThreshold: CGFloat = 64
fileprivate var rightViewThreshold: CGFloat = 0 fileprivate var rightViewThreshold: CGFloat = 0
/** /**
...@@ -505,36 +507,45 @@ open class NavigationDrawerController: RootController { ...@@ -505,36 +507,45 @@ open class NavigationDrawerController: RootController {
if hide { if hide {
UIView.animate(withDuration: duration, UIView.animate(withDuration: duration,
animations: { [weak self] in animations: { [weak self] in
if let s = self { guard let s = self else {
return
}
v.bounds.size.width = width v.bounds.size.width = width
v.position.x = -width / 2 v.position.x = -width / 2
s.rootViewController.view.alpha = 1 s.rootViewController.view.alpha = 1
}
}) { [weak self] _ in }) { [weak self] _ in
if let s = self { guard let s = self else {
return
}
v.isShadowPathAutoSizing = true v.isShadowPathAutoSizing = true
s.layoutSubviews() s.layoutSubviews()
s.hideView(container: v) s.hideView(container: v)
} }
}
} else { } else {
UIView.animate(withDuration: duration, UIView.animate(withDuration: duration,
animations: { [weak self] in animations: { [weak self] in
if let s = self { guard let s = self else {
return
}
v.bounds.size.width = width v.bounds.size.width = width
v.position.x = width / 2 v.position.x = width / 2
s.rootViewController.view.alpha = 0.5 s.rootViewController.view.alpha = 0.5
}
}) { [weak self] _ in }) { [weak self] _ in
if let s = self { guard let s = self else {
return
}
v.isShadowPathAutoSizing = true v.isShadowPathAutoSizing = true
s.layoutSubviews() s.layoutSubviews()
s.showView(container: v) s.showView(container: v)
} }
} }
}
} else { } else {
v.bounds.size.width = width v.bounds.size.width = width
if hide { if hide {
hideView(container: v) hideView(container: v)
v.position.x = -v.width / 2 v.position.x = -v.width / 2
...@@ -547,6 +558,7 @@ open class NavigationDrawerController: RootController { ...@@ -547,6 +558,7 @@ open class NavigationDrawerController: RootController {
rootViewController.view.alpha = 0.5 rootViewController.view.alpha = 0.5
v.isShadowPathAutoSizing = true v.isShadowPathAutoSizing = true
} }
layoutSubviews() layoutSubviews()
} }
} }
...@@ -580,36 +592,45 @@ open class NavigationDrawerController: RootController { ...@@ -580,36 +592,45 @@ open class NavigationDrawerController: RootController {
if hide { if hide {
UIView.animate(withDuration: duration, UIView.animate(withDuration: duration,
animations: { [weak self] in animations: { [weak self] in
if let s = self { guard let s = self else {
return
}
v.bounds.size.width = width v.bounds.size.width = width
v.position.x = s.view.bounds.width + width / 2 v.position.x = s.view.bounds.width + width / 2
s.rootViewController.view.alpha = 1 s.rootViewController.view.alpha = 1
}
}) { [weak self] _ in }) { [weak self] _ in
if let s = self { guard let s = self else {
return
}
v.isShadowPathAutoSizing = true v.isShadowPathAutoSizing = true
s.layoutSubviews() s.layoutSubviews()
s.hideView(container: v) s.hideView(container: v)
} }
}
} else { } else {
UIView.animate(withDuration: duration, UIView.animate(withDuration: duration,
animations: { [weak self] in animations: { [weak self] in
if let s = self { guard let s = self else {
return
}
v.bounds.size.width = width v.bounds.size.width = width
v.position.x = s.view.bounds.width - width / 2 v.position.x = s.view.bounds.width - width / 2
s.rootViewController.view.alpha = 0.5 s.rootViewController.view.alpha = 0.5
}
}) { [weak self] _ in }) { [weak self] _ in
if let s = self { guard let s = self else {
return
}
v.isShadowPathAutoSizing = true v.isShadowPathAutoSizing = true
s.layoutSubviews() s.layoutSubviews()
s.showView(container: v) s.showView(container: v)
} }
} }
}
} else { } else {
v.bounds.size.width = width v.bounds.size.width = width
if hide { if hide {
hideView(container: v) hideView(container: v)
v.position.x = view.bounds.width + v.width / 2 v.position.x = view.bounds.width + v.width / 2
...@@ -622,6 +643,7 @@ open class NavigationDrawerController: RootController { ...@@ -622,6 +643,7 @@ open class NavigationDrawerController: RootController {
rootViewController.view.alpha = 0.5 rootViewController.view.alpha = 0.5
v.isShadowPathAutoSizing = true v.isShadowPathAutoSizing = true
} }
layoutSubviews() layoutSubviews()
} }
} }
...@@ -1088,15 +1110,19 @@ extension NavigationDrawerController: UIGestureRecognizerDelegate { ...@@ -1088,15 +1110,19 @@ extension NavigationDrawerController: UIGestureRecognizerDelegate {
if !isRightViewOpened && gestureRecognizer == leftPanGesture && (isLeftViewOpened || isPointContainedWithinLeftThreshold(point: touch.location(in: view))) { if !isRightViewOpened && gestureRecognizer == leftPanGesture && (isLeftViewOpened || isPointContainedWithinLeftThreshold(point: touch.location(in: view))) {
return true return true
} }
if !isLeftViewOpened && gestureRecognizer == rightPanGesture && (isRightViewOpened || isPointContainedWithinRighThreshold(point: touch.location(in: view))) { if !isLeftViewOpened && gestureRecognizer == rightPanGesture && (isRightViewOpened || isPointContainedWithinRighThreshold(point: touch.location(in: view))) {
return true return true
} }
if isLeftViewOpened && gestureRecognizer == leftTapGesture { if isLeftViewOpened && gestureRecognizer == leftTapGesture {
return true return true
} }
if isRightViewOpened && gestureRecognizer == rightTapGesture { if isRightViewOpened && gestureRecognizer == rightTapGesture {
return true return true
} }
return false return false
} }
...@@ -1108,7 +1134,10 @@ extension NavigationDrawerController: UIGestureRecognizerDelegate { ...@@ -1108,7 +1134,10 @@ extension NavigationDrawerController: UIGestureRecognizerDelegate {
*/ */
@objc @objc
fileprivate func handleLeftViewPanGesture(recognizer: UIPanGestureRecognizer) { fileprivate func handleLeftViewPanGesture(recognizer: UIPanGestureRecognizer) {
if isLeftViewEnabled && (isLeftViewOpened || !isRightViewOpened && isPointContainedWithinLeftThreshold(point: recognizer.location(in: view))) { guard isLeftViewEnabled && (isLeftViewOpened || !isRightViewOpened && isPointContainedWithinLeftThreshold(point: recognizer.location(in: view))) else {
return
}
guard let v = leftView else { guard let v = leftView else {
return return
} }
...@@ -1150,7 +1179,6 @@ extension NavigationDrawerController: UIGestureRecognizerDelegate { ...@@ -1150,7 +1179,6 @@ extension NavigationDrawerController: UIGestureRecognizerDelegate {
case .possible:break case .possible:break
} }
} }
}
/** /**
A method that is fired when the pan gesture is recognized A method that is fired when the pan gesture is recognized
...@@ -1160,7 +1188,10 @@ extension NavigationDrawerController: UIGestureRecognizerDelegate { ...@@ -1160,7 +1188,10 @@ extension NavigationDrawerController: UIGestureRecognizerDelegate {
*/ */
@objc @objc
fileprivate func handleRightViewPanGesture(recognizer: UIPanGestureRecognizer) { fileprivate func handleRightViewPanGesture(recognizer: UIPanGestureRecognizer) {
if isRightViewEnabled && (isRightViewOpened || !isLeftViewOpened && isPointContainedWithinRighThreshold(point: recognizer.location(in: view))) { guard isRightViewEnabled && (isRightViewOpened || !isLeftViewOpened && isPointContainedWithinRighThreshold(point: recognizer.location(in: view))) else {
return
}
guard let v = rightView else { guard let v = rightView else {
return return
} }
...@@ -1202,7 +1233,6 @@ extension NavigationDrawerController: UIGestureRecognizerDelegate { ...@@ -1202,7 +1233,6 @@ extension NavigationDrawerController: UIGestureRecognizerDelegate {
case .possible:break case .possible:break
} }
} }
}
/** /**
A method that is fired when the tap gesture is recognized A method that is fired when the tap gesture is recognized
...@@ -1222,9 +1252,11 @@ extension NavigationDrawerController: UIGestureRecognizerDelegate { ...@@ -1222,9 +1252,11 @@ extension NavigationDrawerController: UIGestureRecognizerDelegate {
delegate?.navigationDrawerController?(navigationDrawerController: self, didTapAt: recognizer.location(in: view), position: .left) delegate?.navigationDrawerController?(navigationDrawerController: self, didTapAt: recognizer.location(in: view), position: .left)
if isLeftViewEnabled && isLeftViewOpened && !isPointContainedWithinView(container: v, point: recognizer.location(in: v)) { guard isLeftViewEnabled && isLeftViewOpened && !isPointContainedWithinView(container: v, point: recognizer.location(in: v)) else {
closeLeftView() return
} }
closeLeftView()
} }
/** /**
...@@ -1245,8 +1277,10 @@ extension NavigationDrawerController: UIGestureRecognizerDelegate { ...@@ -1245,8 +1277,10 @@ extension NavigationDrawerController: UIGestureRecognizerDelegate {
delegate?.navigationDrawerController?(navigationDrawerController: self, didTapAt: recognizer.location(in: view), position: .right) delegate?.navigationDrawerController?(navigationDrawerController: self, didTapAt: recognizer.location(in: view), position: .right)
if isRightViewEnabled && isRightViewOpened && !isPointContainedWithinView(container: v, point: recognizer.location(in: v)) { guard isRightViewEnabled && isRightViewOpened && !isPointContainedWithinView(container: v, point: recognizer.location(in: v)) else {
closeRightView() return
} }
closeRightView()
} }
} }
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment