// // Created by Jesse Squires // http://www.hexedbits.com // // // Documentation // http://cocoadocs.org/docsets/JSMessagesViewController // // // The MIT License // Copyright (c) 2013 Jesse Squires // http://opensource.org/licenses/MIT // #import "JSMessageTextView.h" #import "JSBubbleView.h" #import "NSString+JSMessagesView.h" @interface JSMessageTextView () - (void)setup; - (void)addTextViewNotificationObservers; - (void)removeTextViewNotificationObservers; - (void)didReceiveTextViewNotification:(NSNotification *)notification; @end @implementation JSMessageTextView #pragma mark - Initialization - (void)setup { _placeHolderTextColor = [UIColor lightGrayColor]; self.autoresizingMask = UIViewAutoresizingFlexibleWidth; self.scrollIndicatorInsets = UIEdgeInsetsMake(10.0f, 0.0f, 10.0f, 8.0f); self.contentInset = UIEdgeInsetsZero; self.scrollEnabled = YES; self.scrollsToTop = NO; self.userInteractionEnabled = YES; self.font = [UIFont systemFontOfSize:16.0f]; self.textColor = [UIColor blackColor]; self.backgroundColor = [UIColor whiteColor]; self.keyboardAppearance = UIKeyboardAppearanceDefault; self.keyboardType = UIKeyboardTypeDefault; self.returnKeyType = UIReturnKeyDefault; self.textAlignment = NSTextAlignmentLeft; [self addTextViewNotificationObservers]; } - (instancetype)initWithFrame:(CGRect)frame { self = [super initWithFrame:frame]; if (self) { [self setup]; } return self; } - (instancetype)initWithCoder:(NSCoder *)aDecoder { self = [super initWithCoder:aDecoder]; if (self) { [self setup]; } return self; } - (void)dealloc { [self removeTextViewNotificationObservers]; _placeHolder = nil; _placeHolderTextColor = nil; } #pragma mark - Setters - (void)setPlaceHolder:(NSString *)placeHolder { if ([placeHolder isEqualToString:_placeHolder]) { return; } NSUInteger maxChars = [JSMessageTextView maxCharactersPerLine]; if ([placeHolder length] > maxChars) { placeHolder = [placeHolder substringToIndex:maxChars - 8]; placeHolder = [[placeHolder js_stringByTrimingWhitespace] stringByAppendingFormat:@"..."]; } _placeHolder = placeHolder; [self setNeedsDisplay]; } - (void)setPlaceHolderTextColor:(UIColor *)placeHolderTextColor { if ([placeHolderTextColor isEqual:_placeHolderTextColor]) { return; } _placeHolderTextColor = placeHolderTextColor; [self setNeedsDisplay]; } #pragma mark - Message text view - (NSUInteger)numberOfLinesOfText { return [JSMessageTextView numberOfLinesForMessage:self.text]; } + (NSUInteger)maxCharactersPerLine { return ([UIDevice currentDevice].userInterfaceIdiom == UIUserInterfaceIdiomPhone) ? 33 : 109; } + (NSUInteger)numberOfLinesForMessage:(NSString *)text { return (text.length / [JSMessageTextView maxCharactersPerLine]) + 1; } #pragma mark - Text view overrides - (void)setText:(NSString *)text { [super setText:text]; [self setNeedsDisplay]; } - (void)setAttributedText:(NSAttributedString *)attributedText { [super setAttributedText:attributedText]; [self setNeedsDisplay]; } - (void)setFont:(UIFont *)font { [super setFont:font]; [self setNeedsDisplay]; } - (void)setTextAlignment:(NSTextAlignment)textAlignment { [super setTextAlignment:textAlignment]; [self setNeedsDisplay]; } #pragma mark - Drawing - (void)drawRect:(CGRect)rect { [super drawRect:rect]; if ([self.text length] == 0 && self.placeHolder) { CGRect placeHolderRect = CGRectMake(10.0f, 7.0f, rect.size.width, rect.size.height); [self.placeHolderTextColor set]; if (NSFoundationVersionNumber > NSFoundationVersionNumber_iOS_6_0) { NSMutableParagraphStyle *paragraphStyle = [[NSMutableParagraphStyle alloc] init]; paragraphStyle.lineBreakMode = NSLineBreakByTruncatingTail; paragraphStyle.alignment = self.textAlignment; [self.placeHolder drawInRect:placeHolderRect withAttributes:@{ NSFontAttributeName : self.font, NSForegroundColorAttributeName : self.placeHolderTextColor, NSParagraphStyleAttributeName : paragraphStyle }]; } else { [self.placeHolder drawInRect:placeHolderRect withFont:self.font lineBreakMode:NSLineBreakByTruncatingTail alignment:self.textAlignment]; } } } #pragma mark - Notifications - (void)addTextViewNotificationObservers { [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(didReceiveTextViewNotification:) name:UITextViewTextDidChangeNotification object:self]; [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(didReceiveTextViewNotification:) name:UITextViewTextDidBeginEditingNotification object:self]; [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(didReceiveTextViewNotification:) name:UITextViewTextDidEndEditingNotification object:self]; } - (void)removeTextViewNotificationObservers { [[NSNotificationCenter defaultCenter] removeObserver:self name:UITextViewTextDidChangeNotification object:self]; [[NSNotificationCenter defaultCenter] removeObserver:self name:UITextViewTextDidBeginEditingNotification object:self]; [[NSNotificationCenter defaultCenter] removeObserver:self name:UITextViewTextDidEndEditingNotification object:self]; } - (void)didReceiveTextViewNotification:(NSNotification *)notification { [self setNeedsDisplay]; } @end