Commit 0209d364 by Daniel Dahan

working TextView

parent 808a1ae4
...@@ -21,7 +21,7 @@ import MaterialKit ...@@ -21,7 +21,7 @@ import MaterialKit
class ViewController: UIViewController, TextDelegate, TextViewDelegate { class ViewController: UIViewController, TextDelegate, TextViewDelegate {
lazy var text: Text = Text() lazy var text: Text = Text()
var textView: TextView? var textView: TextView!
override func viewDidLoad() { override func viewDidLoad() {
super.viewDidLoad() super.viewDidLoad()
...@@ -42,18 +42,23 @@ class ViewController: UIViewController, TextDelegate, TextViewDelegate { ...@@ -42,18 +42,23 @@ class ViewController: UIViewController, TextDelegate, TextViewDelegate {
text.textStorage.addLayoutManager(layoutManager) text.textStorage.addLayoutManager(layoutManager)
textView = TextView(frame: CGRectNull, textContainer: textContainer) textView = TextView(frame: CGRectNull, textContainer: textContainer)
textView?.delegate = self textView.delegate = self
textView!.editable = true textView.editable = true
textView!.selectable = true textView.selectable = true
textView!.font = RobotoFont.regular textView.font = RobotoFont.regular
textView!.placeholderLabel = UILabel() textView.placeholderLabel = UILabel()
textView!.placeholderLabel!.textColor = MaterialColor.grey.base textView.placeholderLabel!.textColor = MaterialColor.grey.base
textView!.placeholderLabel!.text = "MaterialKit TextView" textView.placeholderLabel!.text = "Description"
view.addSubview(textView!) textView.titleLabel = UILabel()
textView.titleLabel!.font = RobotoFont.mediumWithSize(12)
textView.titleLabelNormalColor = MaterialColor.grey.lighten2
textView.titleLabelHighlightedColor = MaterialColor.blue.accent3
view.addSubview(textView)
textView!.translatesAutoresizingMaskIntoConstraints = false textView!.translatesAutoresizingMaskIntoConstraints = false
MaterialLayout.alignToParent(view, child: textView!, top: 24, left: 24, bottom: 24, right: 24) MaterialLayout.alignToParent(view, child: textView!, top: 124, left: 24, bottom: 24, right: 24)
} }
func textWillProcessEdit(text: Text, textStorage: TextStorage, string: String, range: NSRange) { func textWillProcessEdit(text: Text, textStorage: TextStorage, string: String, range: NSRange) {
......
...@@ -21,6 +21,26 @@ import UIKit ...@@ -21,6 +21,26 @@ import UIKit
public protocol TextViewDelegate : UITextViewDelegate {} public protocol TextViewDelegate : UITextViewDelegate {}
public class TextView: UITextView { public class TextView: UITextView {
public var titleLabel: UILabel? {
didSet {
prepareTitleLabel()
}
}
/**
:name: titleLabelNormalColor
*/
public var titleLabelNormalColor: UIColor? {
didSet {
titleLabel?.textColor = titleLabelNormalColor
}
}
/**
:name: titleLabelHighlightedColor
*/
public var titleLabelHighlightedColor: UIColor?
/** /**
:name: init :name: init
*/ */
...@@ -41,24 +61,15 @@ public class TextView: UITextView { ...@@ -41,24 +61,15 @@ public class TextView: UITextView {
// :name: deinit // :name: deinit
// //
deinit { deinit {
NSNotificationCenter.defaultCenter().removeObserver(self, name: UITextViewTextDidChangeNotification, object: nil) removeNotificationHandlers()
} }
/** /**
:name: placeholder :name: placeholderLabel
*/ */
public var placeholderLabel: UILabel? { public var placeholderLabel: UILabel? {
didSet { didSet {
if let p = placeholderLabel { preparePlaceholderLabel()
p.translatesAutoresizingMaskIntoConstraints = false
p.font = font
p.textAlignment = textAlignment
p.numberOfLines = 0
p.backgroundColor = .clearColor()
addSubview(p)
updateLabelConstraints()
textViewTextDidChange()
}
} }
} }
...@@ -68,7 +79,7 @@ public class TextView: UITextView { ...@@ -68,7 +79,7 @@ public class TextView: UITextView {
*/ */
public override var text: String! { public override var text: String! {
didSet { didSet {
textViewTextDidChange() handleTextViewTextDidChange()
} }
} }
...@@ -77,7 +88,7 @@ public class TextView: UITextView { ...@@ -77,7 +88,7 @@ public class TextView: UITextView {
*/ */
public override var attributedText: NSAttributedString! { public override var attributedText: NSAttributedString! {
didSet { didSet {
textViewTextDidChange() handleTextViewTextDidChange()
} }
} }
...@@ -86,43 +97,150 @@ public class TextView: UITextView { ...@@ -86,43 +97,150 @@ public class TextView: UITextView {
*/ */
public override var textContainerInset: UIEdgeInsets { public override var textContainerInset: UIEdgeInsets {
didSet { didSet {
updateLabelConstraints() reloadView()
} }
} }
public override func layoutSubviews() { public override func layoutSubviews() {
super.layoutSubviews() super.layoutSubviews()
placeholderLabel?.preferredMaxLayoutWidth = textContainer.size.width - textContainer.lineFragmentPadding * 2 placeholderLabel?.preferredMaxLayoutWidth = textContainer.size.width - textContainer.lineFragmentPadding * 2
titleLabel?.frame.size.width = bounds.width
} }
/** /**
:name: updateLabelConstraints :name: reloadView
*/ */
internal func updateLabelConstraints() { internal func reloadView() {
if let p = placeholderLabel { if let p = placeholderLabel {
removeConstraints(constraints) removeConstraints(constraints)
addConstraints(NSLayoutConstraint.constraintsWithVisualFormat("H:|-(left)-[placeholderLabel]-(right)-|", options: [], metrics: ["left": textContainerInset.left + textContainer.lineFragmentPadding, "right": textContainerInset.right + textContainer.lineFragmentPadding], views: ["placeholderLabel": p])) MaterialLayout.alignToParent(self,
addConstraints(NSLayoutConstraint.constraintsWithVisualFormat("V:|-(top)-[placeholderLabel]-(bottom)-|", options: [], metrics: ["top": textContainerInset.top, "bottom": textContainerInset.bottom], views: ["placeholderLabel": p])) child: p,
top: textContainerInset.top,
left: textContainerInset.left + textContainer.lineFragmentPadding,
bottom: textContainerInset.bottom,
right: textContainerInset.right + textContainer.lineFragmentPadding)
} }
} }
// /**
// :name: textViewTextDidChange :name: textFieldDidBegin
// */
internal func textViewTextDidChange() { internal func handleTextViewTextDidBegin() {
titleLabel?.text = placeholderLabel?.text
if 0 == text?.utf16.count {
titleLabel?.textColor = titleLabelNormalColor
} else {
titleLabel?.textColor = titleLabelHighlightedColor
}
}
/**
:name: textFieldDidChange
*/
internal func handleTextViewTextDidChange() {
if let p = placeholderLabel { if let p = placeholderLabel {
p.hidden = !text.isEmpty p.hidden = !text.isEmpty
} }
if 0 < text?.utf16.count {
showTitleLabel()
titleLabel?.textColor = titleLabelHighlightedColor
} else if 0 == text?.utf16.count {
hideTitleLabel()
}
}
/**
:name: textFieldDidEnd
*/
internal func handleTextViewTextDidEnd() {
if 0 < text?.utf16.count {
showTitleLabel()
} else if 0 == text?.utf16.count {
hideTitleLabel()
}
titleLabel?.textColor = titleLabelNormalColor
} }
// //
// :name: prepareView // :name: prepareView
// //
private func prepareView() { private func prepareView() {
textContainerInset = UIEdgeInsetsMake(16, 16, 16, 16) textContainerInset = UIEdgeInsets(top: 24, left: 0, bottom: 24, right: 0)
backgroundColor = .clearColor() backgroundColor = MaterialColor.clear
clipsToBounds = false
removeNotificationHandlers()
prepareNotificationHandlers()
reloadView()
}
private func preparePlaceholderLabel() {
if let v: UILabel = placeholderLabel {
v.translatesAutoresizingMaskIntoConstraints = false
v.font = font
v.textAlignment = textAlignment
v.numberOfLines = 0
v.backgroundColor = .clearColor()
titleLabel?.text = placeholderLabel?.text
addSubview(v)
reloadView()
handleTextViewTextDidChange()
}
}
/**
:name: prepareTitleLabel
*/
private func prepareTitleLabel() {
if let v: UILabel = titleLabel {
MaterialAnimation.animationDisabled {
v.hidden = true
v.alpha = 0
}
titleLabel?.text = placeholderLabel?.text
let h: CGFloat = v.font.pointSize
v.frame = CGRectMake(0, -h, bounds.width, h)
addSubview(v)
}
}
/**
:name: showTitleLabel
*/
private func showTitleLabel() {
if let v: UILabel = titleLabel {
v.frame.size.height = v.font.pointSize
v.hidden = false
UIView.animateWithDuration(0.25, animations: {
v.alpha = 1
v.frame.origin.y = -v.frame.height - 4
})
}
}
/**
:name: hideTitleLabel
*/
private func hideTitleLabel() {
if let v: UILabel = titleLabel {
UIView.animateWithDuration(0.25, animations: {
v.alpha = 0
v.frame.origin.y = -v.frame.height
}) { _ in
v.hidden = true
}
}
}
private func prepareNotificationHandlers() {
NSNotificationCenter.defaultCenter().addObserver(self, selector: "handleTextViewTextDidBegin", name: UITextViewTextDidBeginEditingNotification, object: nil)
NSNotificationCenter.defaultCenter().addObserver(self, selector: "handleTextViewTextDidChange", name: UITextViewTextDidChangeNotification, object: nil)
NSNotificationCenter.defaultCenter().addObserver(self, selector: "handleTextViewTextDidEnd", name: UITextViewTextDidEndEditingNotification, object: nil)
}
private func removeNotificationHandlers() {
NSNotificationCenter.defaultCenter().removeObserver(self, name: UITextViewTextDidBeginEditingNotification, object: nil)
NSNotificationCenter.defaultCenter().removeObserver(self, name: UITextViewTextDidChangeNotification, object: nil) NSNotificationCenter.defaultCenter().removeObserver(self, name: UITextViewTextDidChangeNotification, object: nil)
NSNotificationCenter.defaultCenter().addObserver(self, selector: "textViewTextDidChange", name: UITextViewTextDidChangeNotification, object: nil) NSNotificationCenter.defaultCenter().removeObserver(self, name: UITextViewTextDidEndEditingNotification, object: nil)
updateLabelConstraints()
} }
} }
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