Skip to content

Instantly share code, notes, and snippets.

Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save JayachandraA/603f2040b1ec1d38167e77d84c8fe8c0 to your computer and use it in GitHub Desktop.
Save JayachandraA/603f2040b1ec1d38167e77d84c8fe8c0 to your computer and use it in GitHub Desktop.
extension UITextField {
// OPTION - 1
struct Instance {
static var floating: Bool = false
}
var floating: Bool{
set{
Instance.floating = newValue
initializePlaceholder()
}
get{
return Instance.floating
}
}
// OPTION - 2
struct AssociatedKeys {
static var placeholderColor: String = "placeholderColor"
}
var placeholderColor: UIColor? {
set {
objc_setAssociatedObject(self, &AssociatedKeys.placeholderColor, newValue, objc_AssociationPolicy.OBJC_ASSOCIATION_RETAIN)
updatePlaceholderAppearance()
}
get {
guard let value = objc_getAssociatedObject(self, &AssociatedKeys.placeholderColor) as? UIColor else { return nil }
return value
}
}
// MARK: - Helper functions
func initializePlaceholder(){
guard floating == true else {
return
}
if let _ = placeholderLabel(){
return
}
addObserver(self, forKeyPath: "placeholder", options: NSKeyValueObservingOptions.new, context: nil)
NotificationCenter.default.addObserver(self, selector: #selector(handleKeyboard), name: NSNotification.Name.UIKeyboardWillHide, object: nil)
let label = UILabel(frame: CGRect(origin: CGPoint(x: 5, y: 0), size: bounds.size))
label.text = placeholder
label.font = font
addSubview(label)
placeholder = ""
let gesture = UITapGestureRecognizer(target: self, action: #selector(animatePlaceholderLabel))
label.isUserInteractionEnabled = true
label.tag = 765678
label.addGestureRecognizer(gesture)
}
func placeholderLabel() ->UILabel? {
if let label = viewWithTag(765678) as? UILabel{
return label
}
return nil
}
fileprivate func fontSize() ->CGFloat? {
return font?.pointSize
}
fileprivate func fontName() ->String? {
return font?.familyName
}
fileprivate func updatePlaceholder() {
guard let label = placeholderLabel() else { return }
label.text = placeholder
attributedPlaceholder = NSAttributedString(string: placeholder!, attributes: [NSAttributedStringKey.foregroundColor : UIColor.clear])
}
fileprivate func updatePlaceholderAppearance() {
guard let label = placeholderLabel() else { return }
label.font = self.font
label.textColor = placeholderColor
}
@objc private func animatePlaceholderLabel() {
becomeFirstResponder()
guard let label = placeholderLabel() else { return }
UIView.animate(withDuration: 0.5, animations: {
label.frame = CGRect(origin: CGPoint(x: 5, y: -(self.bounds.size.height * 0.5 + 3)), size: CGSize(width: self.bounds.size.width * 0.5, height: self.bounds.size.height * 0.5))
})
}
@objc func handleKeyboard() {
if let count = text?.count, count > 0 { return }
guard let label = placeholderLabel() else { return }
UIView.animate(withDuration: 0.3, animations: {
label.frame = CGRect(origin: CGPoint(x: 5, y: 0), size: self.bounds.size)
if let name = self.fontName(), let size = self.fontSize(){
label.font = UIFont(name: name, size: size)
}
})
}
open override func observeValue(forKeyPath keyPath: String?, of object: Any?, change: [NSKeyValueChangeKey : Any]?, context: UnsafeMutableRawPointer?) {
if let path = keyPath, path == "placeholder" {
updatePlaceholder()
}
}
/*
// Only override draw() if you perform custom drawing.
// An empty implementation adversely affects performance during animation.
override func draw(_ rect: CGRect) {
// Drawing code
}
*/
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment