UItextViewでプレースホルダーを使えるようにする方法。
昔からやりつくされていますが、必要に迫られたので @himara2 先輩が過去に書いた記事を参考に、SwiftかつIBInspectableを使えるようにしました。
import UIKit
class UIPlaceHolderTextView: UITextView {
lazy var placeHolderLabel: UILabel = UILabel()
@IBInspectable var placeHolderColor: UIColor = UIColor.lightGrayColor()
@IBInspectable var placeHolder: String = ""
required init?(coder aDecoder: NSCoder) {
super.init(coder: aDecoder)
}
override init(frame: CGRect, textContainer: NSTextContainer?) {
super.init(frame: frame, textContainer: textContainer)
NSNotificationCenter.defaultCenter().addObserver(self, selector: "textChanged:", name: UITextViewTextDidChangeNotification, object: self)
}
override func awakeFromNib() {
super.awakeFromNib()
NSNotificationCenter.defaultCenter().addObserver(self, selector: "textChanged:", name: UITextViewTextDidChangeNotification, object: self)
}
deinit {
NSNotificationCenter.defaultCenter().removeObserver(self)
}
override func drawRect(rect: CGRect) {
if(self.placeHolder.characters.count > 0) {
self.placeHolderLabel.frame = CGRectMake(4,8,self.bounds.size.width - 16,0)
self.placeHolderLabel.lineBreakMode = NSLineBreakMode.ByWordWrapping
self.placeHolderLabel.numberOfLines = 0
self.placeHolderLabel.font = self.font
self.placeHolderLabel.backgroundColor = UIColor.clearColor()
self.placeHolderLabel.textColor = self.placeHolderColor
self.placeHolderLabel.alpha = 0
self.placeHolderLabel.tag = 999
self.placeHolderLabel.text = self.placeHolder
self.placeHolderLabel.sizeToFit()
self.addSubview(placeHolderLabel)
}
self.sendSubviewToBack(placeHolderLabel)
if self.text.characters.count == 0 && self.placeHolder.characters.count > 0 {
self.viewWithTag(999)?.alpha = 1
}
super.drawRect(rect)
}
func textChanged(notification: NSNotification?) {
if self.placeHolder.characters.count == 0 {
return
}
if self.text.characters.count == 0 {
self.viewWithTag(999)?.alpha = 1.0
} else {
self.viewWithTag(999)?.alpha = 0.0
}
}
}
Storyboard上でUITextViewを配置し、クラスをUIPlaceHolderTextViewに変更します。
変更すると、Place HolderColorとPlaceHolderの値をInterfaceBuilderから変更することができます。
便利ですね。
一点、自分の環境ではBackgroundColorをClearにしないとTextViewの背景が黒くなってしまいました。
そこで、IB上でClearColorに設定しています。