Commit 5365d0be by Daniel Dahan

performance updates and animation updates

parent bf717d93
......@@ -52,13 +52,13 @@ class AppMenuViewController: MenuViewController {
override func openMenu(completion: (() -> Void)? = nil) {
super.openMenu(completion)
sideNavigationViewController?.enabled = false
(menuView.menu.views?.first as? MaterialButton)?.animate(MaterialAnimation.rotate(0.125))
(menuView.menu.views?.first as? MaterialButton)?.animate(MaterialAnimation.rotate(angle: 45))
}
override func closeMenu(completion: (() -> Void)? = nil) {
super.closeMenu(completion)
sideNavigationViewController?.enabled = true
(menuView.menu.views?.first as? MaterialButton)?.animate(MaterialAnimation.rotate(-0.125))
(menuView.menu.views?.first as? MaterialButton)?.animate(MaterialAnimation.rotate(angle: 0))
}
/// Handler for blue button.
......
......@@ -76,8 +76,8 @@ class ViewController: UIViewController {
view.layer.addSublayer(materialLayer)
// Add a rotate animation.
MaterialAnimation.delay(3) {
materialLayer.animate(MaterialAnimation.rotate(3, duration: 3))
MaterialAnimation.delay(1) {
materialLayer.animate(MaterialAnimation.rotate(rotation: 3, duration: 3))
}
}
}
......
......@@ -7,8 +7,6 @@
objects = {
/* Begin PBXBuildFile section */
965626761C88C218004ADEF7 /* Material.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = 965626751C88C218004ADEF7 /* Material.framework */; };
965626771C88C218004ADEF7 /* Material.framework in Embed Frameworks */ = {isa = PBXBuildFile; fileRef = 965626751C88C218004ADEF7 /* Material.framework */; settings = {ATTRIBUTES = (CodeSignOnCopy, RemoveHeadersOnCopy, ); }; };
96DB1C5F1C14AA2800825BE6 /* AppDelegate.swift in Sources */ = {isa = PBXBuildFile; fileRef = 96DB1C5E1C14AA2800825BE6 /* AppDelegate.swift */; };
96DB1C611C14AA2800825BE6 /* ViewController.swift in Sources */ = {isa = PBXBuildFile; fileRef = 96DB1C601C14AA2800825BE6 /* ViewController.swift */; };
96DB1C661C14AA2800825BE6 /* Assets.xcassets in Resources */ = {isa = PBXBuildFile; fileRef = 96DB1C651C14AA2800825BE6 /* Assets.xcassets */; };
......@@ -22,7 +20,6 @@
dstPath = "";
dstSubfolderSpec = 10;
files = (
965626771C88C218004ADEF7 /* Material.framework in Embed Frameworks */,
);
name = "Embed Frameworks";
runOnlyForDeploymentPostprocessing = 0;
......@@ -30,7 +27,6 @@
/* End PBXCopyFilesBuildPhase section */
/* Begin PBXFileReference section */
965626751C88C218004ADEF7 /* Material.framework */ = {isa = PBXFileReference; explicitFileType = wrapper.framework; name = Material.framework; path = "/Users/danieldahan/Library/Developer/Xcode/DerivedData/Material-hbpnflxhoouqxebjcyhbbhqyesjd/Build/Products/Debug-iphoneos/Material.framework"; sourceTree = "<absolute>"; };
96DB1C5B1C14AA2800825BE6 /* MaterialPulseView.app */ = {isa = PBXFileReference; explicitFileType = wrapper.application; includeInIndex = 0; path = MaterialPulseView.app; sourceTree = BUILT_PRODUCTS_DIR; };
96DB1C5E1C14AA2800825BE6 /* AppDelegate.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = AppDelegate.swift; sourceTree = "<group>"; };
96DB1C601C14AA2800825BE6 /* ViewController.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = ViewController.swift; sourceTree = "<group>"; };
......@@ -44,7 +40,6 @@
isa = PBXFrameworksBuildPhase;
buildActionMask = 2147483647;
files = (
965626761C88C218004ADEF7 /* Material.framework in Frameworks */,
);
runOnlyForDeploymentPostprocessing = 0;
};
......@@ -54,7 +49,6 @@
96DB1C521C14AA2800825BE6 = {
isa = PBXGroup;
children = (
965626751C88C218004ADEF7 /* Material.framework */,
96DB1C5D1C14AA2800825BE6 /* MaterialPulseView */,
96DB1C5C1C14AA2800825BE6 /* Products */,
);
......
......@@ -68,8 +68,9 @@ class ViewController: UIViewController {
}
pulseView.animate(MaterialAnimation.animationGroup([
MaterialAnimation.rotate(4.5),
MaterialAnimation.translateY(300)
MaterialAnimation.rotate(angle: 45),
MaterialAnimation.rotateX(rotation: 2),
MaterialAnimation.translateY(200)
], duration: 4))
}
}
......
......@@ -90,7 +90,7 @@ class ViewController: UIViewController {
// Add a nice rotation animation to the base button.
let first: MaterialButton? = fabMenu.views?.first as? MaterialButton
first?.animate(MaterialAnimation.rotate(1))
first?.animate(MaterialAnimation.rotate(rotation: 1))
first?.setImage(image, forState: .Normal)
first?.setImage(image, forState: .Highlighted)
}
......
......@@ -59,12 +59,12 @@ class ViewController: UIViewController {
internal func handleMenu() {
if menuView.menu.opened {
menuView.menu.close()
(menuView.menu.views?.first as? MaterialButton)?.animate(MaterialAnimation.rotate(-0.125))
(menuView.menu.views?.first as? MaterialButton)?.animate(MaterialAnimation.rotate(rotation: 0))
} else {
menuView.menu.open() { (v: UIView) in
(v as? MaterialButton)?.pulse()
}
(menuView.menu.views?.first as? MaterialButton)?.animate(MaterialAnimation.rotate(0.125))
(menuView.menu.views?.first as? MaterialButton)?.animate(MaterialAnimation.rotate(rotation: 0.125))
}
}
......
Pod::Spec.new do |s|
s.name = 'Material'
s.version = '1.35.2'
s.version = '1.35.3'
s.license = 'BSD'
s.summary = 'Express your creativity with Material, an animation and graphics framework for Google\'s Material Design and Apple\'s Flat UI in Swift.'
s.homepage = 'http://cosmicmind.io'
......
......@@ -910,7 +910,6 @@
FRAMEWORK_SEARCH_PATHS = "";
INFOPLIST_FILE = Sources/Info.plist;
INSTALL_PATH = "$(LOCAL_LIBRARY_DIR)/Frameworks";
IPHONEOS_DEPLOYMENT_TARGET = 8.0;
LD_RUNPATH_SEARCH_PATHS = "$(inherited) @executable_path/Frameworks @loader_path/Frameworks";
PRODUCT_BUNDLE_IDENTIFIER = io.cosmicmind.Material;
PRODUCT_NAME = Material;
......@@ -933,7 +932,6 @@
FRAMEWORK_SEARCH_PATHS = "";
INFOPLIST_FILE = Sources/Info.plist;
INSTALL_PATH = "$(LOCAL_LIBRARY_DIR)/Frameworks";
IPHONEOS_DEPLOYMENT_TARGET = 8.0;
LD_RUNPATH_SEARCH_PATHS = "$(inherited) @executable_path/Frameworks @loader_path/Frameworks";
PRODUCT_BUNDLE_IDENTIFIER = io.cosmicmind.Material;
PRODUCT_NAME = Material;
......
......@@ -15,7 +15,7 @@
<key>CFBundlePackageType</key>
<string>FMWK</string>
<key>CFBundleShortVersionString</key>
<string>1.35.2</string>
<string>1.35.3</string>
<key>CFBundleSignature</key>
<string>????</string>
<key>CFBundleVersion</key>
......
......@@ -43,7 +43,7 @@ public extension UIImage {
let g: UIImage?
let t: CGRect = CGRectMake(0, 0, w, h)
UIGraphicsBeginImageContextWithOptions(t.size, false, UIScreen.mainScreen().scale)
UIGraphicsBeginImageContextWithOptions(t.size, false, MaterialDevice.scale)
drawInRect(t, blendMode: .Normal, alpha: 1)
g = UIGraphicsGetImageFromCurrentImageContext()
UIGraphicsEndImageContext()
......
......@@ -79,9 +79,13 @@ public extension MaterialAnimation {
/**
:name: rotate
*/
public static func rotate(rotations: Double = 1, duration: CFTimeInterval? = nil) -> CABasicAnimation {
public static func rotate(angle angle: CGFloat? = nil, rotation: CGFloat? = nil, duration: CFTimeInterval? = nil) -> CABasicAnimation {
let animation: CABasicAnimation = CABasicAnimation(keyPath: "transform.rotation")
animation.byValue = (M_PI * 2 * rotations) as NSNumber
if let v: CGFloat = angle {
animation.toValue = (CGFloat(M_PI) * v / 180) as NSNumber
} else if let v: CGFloat = rotation {
animation.toValue = (CGFloat(M_PI * 2) * v) as NSNumber
}
animation.fillMode = MaterialAnimationFillModeToValue(.Forwards)
animation.removedOnCompletion = false
animation.timingFunction = CAMediaTimingFunction(name: kCAMediaTimingFunctionEaseInEaseOut)
......@@ -94,9 +98,13 @@ public extension MaterialAnimation {
/**
:name: rotateX
*/
public static func rotateX(rotations: Double = 1, duration: CFTimeInterval? = nil) -> CABasicAnimation {
public static func rotateX(angle angle: CGFloat? = nil, rotation: CGFloat? = nil, duration: CFTimeInterval? = nil) -> CABasicAnimation {
let animation: CABasicAnimation = CABasicAnimation(keyPath: "transform.rotation.x")
animation.byValue = (M_PI * 2 * rotations) as NSNumber
if let v: CGFloat = angle {
animation.toValue = (CGFloat(M_PI) * v / 180) as NSNumber
} else if let v: CGFloat = rotation {
animation.toValue = (CGFloat(M_PI * 2) * v) as NSNumber
}
animation.fillMode = MaterialAnimationFillModeToValue(.Forwards)
animation.removedOnCompletion = false
animation.timingFunction = CAMediaTimingFunction(name: kCAMediaTimingFunctionEaseInEaseOut)
......@@ -109,9 +117,13 @@ public extension MaterialAnimation {
/**
:name: rotateY
*/
public static func rotateY(rotations: Double = 1, duration: CFTimeInterval? = nil) -> CABasicAnimation {
public static func rotateY(angle angle: CGFloat? = nil, rotation: CGFloat? = nil, duration: CFTimeInterval? = nil) -> CABasicAnimation {
let animation: CABasicAnimation = CABasicAnimation(keyPath: "transform.rotation.y")
animation.byValue = (M_PI * 2 * rotations) as NSNumber
if let v: CGFloat = angle {
animation.toValue = (CGFloat(M_PI) * v / 180) as NSNumber
} else if let v: CGFloat = rotation {
animation.toValue = (CGFloat(M_PI * 2) * v) as NSNumber
}
animation.fillMode = MaterialAnimationFillModeToValue(.Forwards)
animation.removedOnCompletion = false
animation.timingFunction = CAMediaTimingFunction(name: kCAMediaTimingFunctionEaseInEaseOut)
......@@ -124,9 +136,13 @@ public extension MaterialAnimation {
/**
:name: rotateZ
*/
public static func rotateZ(rotations: Double = 1, duration: CFTimeInterval? = nil) -> CABasicAnimation {
public static func rotateZ(angle angle: CGFloat? = nil, rotation: CGFloat? = nil, duration: CFTimeInterval? = nil) -> CABasicAnimation {
let animation: CABasicAnimation = CABasicAnimation(keyPath: "transform.rotation.z")
animation.byValue = (M_PI_4 * rotations) as NSNumber
if let v: CGFloat = angle {
animation.toValue = (CGFloat(M_PI) * v / 180) as NSNumber
} else if let v: CGFloat = rotation {
animation.toValue = (CGFloat(M_PI * 2) * v) as NSNumber
}
animation.fillMode = MaterialAnimationFillModeToValue(.Forwards)
animation.removedOnCompletion = false
animation.timingFunction = CAMediaTimingFunction(name: kCAMediaTimingFunctionEaseInEaseOut)
......
......@@ -468,14 +468,16 @@ public class MaterialButton : UIButton {
/// Manages the layout for the visualLayer property.
internal func layoutVisualLayer() {
visualLayer.frame = bounds
visualLayer.position = CGPointMake(width / 2, height / 2)
visualLayer.cornerRadius = cornerRadius
}
/// Manages the layout for the shape of the view instance.
internal func layoutShape() {
if .Circle == shape {
layer.cornerRadius = width / 2
let w: CGFloat = (width / 2)
if w != cornerRadius {
cornerRadius = w
}
}
}
......
......@@ -522,14 +522,16 @@ public class MaterialCollectionViewCell : UICollectionViewCell {
/// Manages the layout for the visualLayer property.
internal func layoutVisualLayer() {
visualLayer.frame = bounds
visualLayer.position = CGPointMake(width / 2, height / 2)
visualLayer.cornerRadius = cornerRadius
}
/// Manages the layout for the shape of the view instance.
internal func layoutShape() {
if .Circle == shape {
layer.cornerRadius = width / 2
let w: CGFloat = (width / 2)
if w != cornerRadius {
cornerRadius = w
}
}
}
......
......@@ -71,4 +71,9 @@ public struct MaterialDevice {
public static var height: CGFloat {
return bounds.height
}
/// Retrieves the device scale.
public static var scale: CGFloat {
return UIScreen.mainScreen().scale
}
}
\ No newline at end of file
......@@ -113,7 +113,7 @@ public class MaterialLabel : UILabel {
*/
public required init?(coder aDecoder: NSCoder) {
wrapped = true
contentsScale = UIScreen.mainScreen().scale
contentsScale = MaterialDevice.scale
super.init(coder: aDecoder)
}
......@@ -122,7 +122,7 @@ public class MaterialLabel : UILabel {
*/
public override init(frame: CGRect) {
wrapped = true
contentsScale = UIScreen.mainScreen().scale
contentsScale = MaterialDevice.scale
super.init(frame: frame)
prepareView()
}
......
......@@ -135,8 +135,7 @@ public class MaterialLayer : CAShapeLayer {
/**
A floating point value that defines a ratio between the pixel
dimensions of the visualLayer's contents property and the size
of the layer. By default, this value is set to the UIScreen's
scale value, UIScreen.mainScreen().scale.
of the layer. By default, this value is set to the MaterialDevice.scale.
*/
public override var contentsScale: CGFloat {
didSet {
......@@ -336,14 +335,16 @@ public class MaterialLayer : CAShapeLayer {
/// Manages the layout for the visualLayer property.
internal func layoutVisualLayer() {
visualLayer.frame = bounds
visualLayer.position = CGPointMake(width / 2, height / 2)
visualLayer.cornerRadius = cornerRadius
}
/// Manages the layout for the shape of the layer instance.
internal func layoutShape() {
if .Circle == shape {
cornerRadius = width / 2
let w: CGFloat = (width / 2)
if w != cornerRadius {
cornerRadius = w
}
}
}
......
......@@ -428,7 +428,6 @@ public class MaterialTableViewCell: UITableViewCell {
/// Manages the layout for the visualLayer property.
internal func layoutVisualLayer() {
visualLayer.frame = bounds
visualLayer.position = CGPointMake(width / 2, height / 2)
visualLayer.cornerRadius = cornerRadius
}
......
......@@ -211,7 +211,7 @@ public class MaterialTextLayer : CATextLayer {
textColor = MaterialColor.black
textAlignment = .Left
wrapped = true
contentsScale = UIScreen.mainScreen().scale
contentsScale = MaterialDevice.scale
lineBreakMode = .ByWordWrapping
}
}
......@@ -81,8 +81,7 @@ public class MaterialView : UIView {
/**
A floating point value that defines a ratio between the pixel
dimensions of the visualLayer's contents property and the size
of the view. By default, this value is set to the UIScreen's
scale value, UIScreen.mainScreen().scale.
of the view. By default, this value is set to the MaterialDevice.scale.
*/
public var contentsScale: CGFloat {
didSet {
......@@ -347,7 +346,7 @@ public class MaterialView : UIView {
public required init?(coder aDecoder: NSCoder) {
contentsRect = CGRectMake(0, 0, 1, 1)
contentsCenter = CGRectMake(0, 0, 1, 1)
contentsScale = UIScreen.mainScreen().scale
contentsScale = MaterialDevice.scale
contentsGravity = .ResizeAspectFill
super.init(coder: aDecoder)
prepareView()
......@@ -362,7 +361,7 @@ public class MaterialView : UIView {
public override init(frame: CGRect) {
contentsRect = CGRectMake(0, 0, 1, 1)
contentsCenter = CGRectMake(0, 0, 1, 1)
contentsScale = UIScreen.mainScreen().scale
contentsScale = MaterialDevice.scale
contentsGravity = .ResizeAspectFill
super.init(frame: frame)
prepareView()
......@@ -435,7 +434,6 @@ public class MaterialView : UIView {
animationDidStop(x, finished: true)
}
}
layoutVisualLayer()
}
/**
......@@ -460,14 +458,16 @@ public class MaterialView : UIView {
/// Manages the layout for the visualLayer property.
internal func layoutVisualLayer() {
visualLayer.frame = bounds
visualLayer.position = CGPointMake(width / 2, height / 2)
visualLayer.cornerRadius = cornerRadius
}
/// Manages the layout for the shape of the view instance.
internal func layoutShape() {
if .Circle == shape {
layer.cornerRadius = width / 2
let w: CGFloat = (width / 2)
if w != cornerRadius {
cornerRadius = w
}
}
}
......
......@@ -130,9 +130,7 @@ public class MenuViewController: UIViewController {
public func openMenu(completion: (() -> Void)? = nil) {
if true == userInteractionEnabled {
userInteractionEnabled = false
UIView.animateWithDuration(0.25, animations: { [unowned self] in
self.mainViewController.view.alpha = 0.5
})
mainViewController.view.alpha = 0.5
menuView.open(completion)
}
}
......@@ -144,12 +142,11 @@ public class MenuViewController: UIViewController {
*/
public func closeMenu(completion: (() -> Void)? = nil) {
if false == userInteractionEnabled {
UIView.animateWithDuration(0.25, animations: { [unowned self] in
self.mainViewController.view.alpha = 1
}) { [weak self] _ in
mainViewController.view.alpha = 1
menuView.close({ [weak self] in
self?.userInteractionEnabled = true
}
menuView.close(completion)
completion?()
})
}
}
......
......@@ -111,6 +111,8 @@ public class NavigationBarViewController: StatusBarViewController {
}
set(value) {
if let v: UIViewController = internalFloatingViewController {
v.view.layer.rasterizationScale = MaterialDevice.scale
v.view.layer.shouldRasterize = true
delegate?.navigationBarViewControllerWillCloseFloatingViewController?(self)
internalFloatingViewController = nil
UIView.animateWithDuration(0.5,
......@@ -122,6 +124,7 @@ public class NavigationBarViewController: StatusBarViewController {
v.willMoveToParentViewController(nil)
v.view.removeFromSuperview()
v.removeFromParentViewController()
v.view.layer.shouldRasterize = false
self.userInteractionEnabled = true
self.navigationBarView.userInteractionEnabled = true
dispatch_async(dispatch_get_main_queue()) { [unowned self] in
......@@ -142,6 +145,10 @@ public class NavigationBarViewController: StatusBarViewController {
// Animate the noteButton out and the noteViewController! in.
v.view.hidden = false
v.view.layer.rasterizationScale = MaterialDevice.scale
v.view.layer.shouldRasterize = true
view.layer.rasterizationScale = MaterialDevice.scale
view.layer.shouldRasterize = true
internalFloatingViewController = v
userInteractionEnabled = false
navigationBarView.userInteractionEnabled = false
......@@ -152,6 +159,8 @@ public class NavigationBarViewController: StatusBarViewController {
self.navigationBarView.alpha = 0.5
self.mainViewController.view.alpha = 0.5
}) { [unowned self] _ in
v.view.layer.shouldRasterize = false
self.view.layer.shouldRasterize = false
dispatch_async(dispatch_get_main_queue()) { [unowned self] in
self.delegate?.navigationBarViewControllerDidOpenFloatingViewController?(self)
}
......
......@@ -516,11 +516,11 @@ public class SideNavigationViewController: UIViewController, UIGestureRecognizer
showView(v)
delegate?.sideNavigationViewWillOpen?(self, position: .Left)
mainViewController.view.alpha = 0.5
UIView.animateWithDuration(Double(0 == velocity ? animationDuration : fmax(0.1, fmin(1, Double(v.x / velocity)))),
animations: { [unowned self] in
animations: {
v.position.x = v.width / 2
self.mainViewController.view.alpha = 0.5
}) { _ in
}) { [unowned self] _ in
self.delegate?.sideNavigationViewDidOpen?(self, position: .Left)
}
}
......@@ -540,11 +540,11 @@ public class SideNavigationViewController: UIViewController, UIGestureRecognizer
showView(v)
delegate?.sideNavigationViewWillOpen?(self, position: .Right)
mainViewController.view.alpha = 0.5
UIView.animateWithDuration(Double(0 == velocity ? animationDuration : fmax(0.1, fmin(1, Double(v.x / velocity)))),
animations: { [unowned self] in
v.position.x = self.view.bounds.width - v.width / 2
self.mainViewController.view.alpha = 0.5
}) { _ in
}) { [unowned self] _ in
self.delegate?.sideNavigationViewDidOpen?(self, position: .Right)
}
}
......@@ -561,11 +561,11 @@ public class SideNavigationViewController: UIViewController, UIGestureRecognizer
if enabledLeftView {
if let v: MaterialView = leftView {
delegate?.sideNavigationViewWillClose?(self, position: .Left)
mainViewController.view.alpha = 1
UIView.animateWithDuration(Double(0 == velocity ? animationDuration : fmax(0.1, fmin(1, Double(v.x / velocity)))),
animations: { [unowned self] in
animations: {
v.position.x = -v.width / 2
self.mainViewController.view.alpha = 1
}) { _ in
}) { [unowned self] _ in
self.toggleStatusBar()
self.hideView(v)
self.delegate?.sideNavigationViewDidClose?(self, position: .Left)
......@@ -584,11 +584,11 @@ public class SideNavigationViewController: UIViewController, UIGestureRecognizer
if enabledRightView {
if let v: MaterialView = rightView {
delegate?.sideNavigationViewWillClose?(self, position: .Right)
mainViewController.view.alpha = 1
UIView.animateWithDuration(Double(0 == velocity ? animationDuration : fmax(0.1, fmin(1, Double(v.x / velocity)))),
animations: { [unowned self] in
v.position.x = self.view.bounds.width + v.width / 2
self.mainViewController.view.alpha = 1
}) { _ in
}) { [unowned self] _ in
self.toggleStatusBar()
self.hideView(v)
self.delegate?.sideNavigationViewDidClose?(self, position: .Right)
......@@ -900,6 +900,14 @@ public class SideNavigationViewController: UIViewController, UIGestureRecognizer
userInteractionEnabled = false
container.depth = depth
container.hidden = false
container.layer.shouldRasterize = true
container.layer.rasterizationScale = MaterialDevice.scale
mainViewController.view.layer.shouldRasterize = true
mainViewController.view.layer.rasterizationScale = MaterialDevice.scale
leftViewController?.view.layer.shouldRasterize = true
leftViewController?.view.layer.rasterizationScale = MaterialDevice.scale
rightViewController?.view.layer.shouldRasterize = true
rightViewController?.view.layer.rasterizationScale = MaterialDevice.scale
}
/**
......@@ -910,6 +918,10 @@ public class SideNavigationViewController: UIViewController, UIGestureRecognizer
userInteractionEnabled = true
container.depth = .None
container.hidden = true
container.layer.shouldRasterize = false
mainViewController.view.layer.shouldRasterize = false
leftViewController?.view.layer.shouldRasterize = false
rightViewController?.view.layer.shouldRasterize = false
}
/// Layout subviews.
......
......@@ -574,7 +574,10 @@ public class TextField : UITextField {
/// Manages the layout for the shape of the view instance.
internal func layoutShape() {
if .Circle == shape {
layer.cornerRadius = width / 2
let w: CGFloat = (width / 2)
if w != cornerRadius {
cornerRadius = w
}
}
}
......
......@@ -491,7 +491,10 @@ public class TextView: UITextView {
/// Manages the layout for the shape of the view instance.
internal func layoutShape() {
if .Circle == shape {
layer.cornerRadius = width / 2
let w: CGFloat = (width / 2)
if w != cornerRadius {
cornerRadius = w
}
}
}
......
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