How to get text / String from nth line of UILabel? How to get text / String from nth line of UILabel? swift swift

How to get text / String from nth line of UILabel?


I have better way to find it.

You can get this with the help of CoreText.framework.

1.Add CoreText.framework.
2.Import #import <CoreText/CoreText.h>.
Then use below method:

- (NSArray *)getLinesArrayOfStringInLabel:(UILabel *)label {    NSString *text = [label text];    UIFont   *font = [label font];    CGRect    rect = [label frame];        CTFontRef myFont = CTFontCreateWithName((__bridge CFStringRef)([font fontName]), [font pointSize], NULL);    NSMutableAttributedString *attStr = [[NSMutableAttributedString alloc] initWithString:text];    [attStr addAttribute:(NSString *)kCTFontAttributeName value:(__bridge id)myFont range:NSMakeRange(0, attStr.length)];            CTFramesetterRef frameSetter = CTFramesetterCreateWithAttributedString((__bridge CFAttributedStringRef)attStr);        CGMutablePathRef path = CGPathCreateMutable();    CGPathAddRect(path, NULL, CGRectMake(0,0,rect.size.width,100000));        CTFrameRef frame = CTFramesetterCreateFrame(frameSetter, CFRangeMake(0, 0), path, NULL);        NSArray *lines = (__bridge NSArray *)CTFrameGetLines(frame);    NSMutableArray *linesArray = [[NSMutableArray alloc]init];        for (id line in lines)    {        CTLineRef lineRef = (__bridge CTLineRef )line;        CFRange lineRange = CTLineGetStringRange(lineRef);        NSRange range = NSMakeRange(lineRange.location, lineRange.length);                NSString *lineString = [text substringWithRange:range];        [linesArray addObject:lineString];    }    return (NSArray *)linesArray;}

Call this method :-

NSArray *linesArray = [self getLinesArrayOfStringInLabel:yourLabel];

Now you can use linesArray.

SWIFT 4 VERSION

func getLinesArrayOfString(in label: UILabel) -> [String] {                /// An empty string's array        var linesArray = [String]()                guard let text = label.text, let font = label.font else {return linesArray}                let rect = label.frame                let myFont = CTFontCreateWithFontDescriptor(font.fontDescriptor, 0, nil)        let attStr = NSMutableAttributedString(string: text)        attStr.addAttribute(kCTFontAttributeName as NSAttributedString.Key, value: myFont, range: NSRange(location: 0, length: attStr.length))                let frameSetter: CTFramesetter = CTFramesetterCreateWithAttributedString(attStr as CFAttributedString)        let path: CGMutablePath = CGMutablePath()        path.addRect(CGRect(x: 0, y: 0, width: rect.size.width, height: 100000), transform: .identity)                let frame: CTFrame = CTFramesetterCreateFrame(frameSetter, CFRangeMake(0, 0), path, nil)        guard let lines = CTFrameGetLines(frame) as? [Any] else {return linesArray}                for line in lines {            let lineRef = line as! CTLine            let lineRange: CFRange = CTLineGetStringRange(lineRef)            let range = NSRange(location: lineRange.location, length: lineRange.length)            let lineString: String = (text as NSString).substring(with: range)            linesArray.append(lineString)        }        return linesArray }

Use:

let lines: [String] = getLinesArrayOfString(in: label)


Swift 3

func getLinesArrayFromLabel(label:UILabel) -> [String] {  let text:NSString = label.text! as NSString // TODO: Make safe?  let font:UIFont = label.font  let rect:CGRect = label.frame      let myFont:CTFont = CTFontCreateWithName(font.fontName as CFString, font.pointSize, nil)  let attStr:NSMutableAttributedString = NSMutableAttributedString(string: text as String)  attStr.addAttribute(String(kCTFontAttributeName), value:myFont, range: NSMakeRange(0, attStr.length))  let frameSetter:CTFramesetter = CTFramesetterCreateWithAttributedString(attStr as CFAttributedString)  let path:CGMutablePath = CGMutablePath()  path.addRect(CGRect(x:0, y:0, width:rect.size.width, height:100000))      let frame:CTFrame = CTFramesetterCreateFrame(frameSetter, CFRangeMake(0, 0), path, nil)  let lines = CTFrameGetLines(frame) as NSArray  var linesArray = [String]()      for line in lines {    let lineRange = CTLineGetStringRange(line as! CTLine)    let range:NSRange = NSMakeRange(lineRange.location, lineRange.length)    let lineString = text.substring(with: range)    linesArray.append(lineString as String)  }  return linesArray}

Swift 2 (Xcode 7) version (tested, and re-edited from the Swift 1 answer)

func getLinesArrayOfStringInLabel(label:UILabel) -> [String] {    let text:NSString = label.text! // TODO: Make safe?  let font:UIFont = label.font  let rect:CGRect = label.frame      let myFont:CTFontRef = CTFontCreateWithName(font.fontName, font.pointSize, nil)  let attStr:NSMutableAttributedString = NSMutableAttributedString(string: text as String)  attStr.addAttribute(String(kCTFontAttributeName), value:myFont, range: NSMakeRange(0, attStr.length))  let frameSetter:CTFramesetterRef = CTFramesetterCreateWithAttributedString(attStr as CFAttributedStringRef)  let path:CGMutablePathRef = CGPathCreateMutable()  CGPathAddRect(path, nil, CGRectMake(0, 0, rect.size.width, 100000))  let frame:CTFrameRef = CTFramesetterCreateFrame(frameSetter, CFRangeMake(0, 0), path, nil)  let lines = CTFrameGetLines(frame) as NSArray  var linesArray = [String]()      for line in lines {    let lineRange = CTLineGetStringRange(line as! CTLine)    let range:NSRange = NSMakeRange(lineRange.location, lineRange.length)    let lineString = text.substringWithRange(range)    linesArray.append(lineString as String)  }  return linesArray}


Answer with Proper release !!!!

-(NSArray *)getLinesArrayOfStringInLabel:(UILabel *)label{    NSString *text = [label text];    UIFont   *font = [label font];    CGRect    rect = [label frame];    CTFontRef myFont = CTFontCreateWithName(( CFStringRef)([font fontName]), [font pointSize], NULL);    NSMutableAttributedString *attStr = [[NSMutableAttributedString alloc] initWithString:text];    [attStr addAttribute:(NSString *)kCTFontAttributeName value:( id)myFont range:NSMakeRange(0, attStr.length)];    CFRelease(myFont);    CTFramesetterRef frameSetter = CTFramesetterCreateWithAttributedString(( CFAttributedStringRef)attStr);    CGMutablePathRef path = CGPathCreateMutable();    CGPathAddRect(path, NULL, CGRectMake(0,0,rect.size.width,100000));    CTFrameRef frame = CTFramesetterCreateFrame(frameSetter, CFRangeMake(0, 0), path, NULL);    NSArray *lines = ( NSArray *)CTFrameGetLines(frame);    NSMutableArray *linesArray = [[NSMutableArray alloc]init];    for (id line in lines)    {        CTLineRef lineRef = ( CTLineRef )line;        CFRange lineRange = CTLineGetStringRange(lineRef);        NSRange range = NSMakeRange(lineRange.location, lineRange.length);        NSString *lineString = [text substringWithRange:range];        CFAttributedStringSetAttribute((CFMutableAttributedStringRef)attStr, lineRange, kCTKernAttributeName, (CFTypeRef)([NSNumber numberWithFloat:0.0]));        CFAttributedStringSetAttribute((CFMutableAttributedStringRef)attStr, lineRange, kCTKernAttributeName, (CFTypeRef)([NSNumber numberWithInt:0.0]));        //NSLog(@"''''''''''''''''''%@",lineString);        [linesArray addObject:lineString];    }    [attStr release];    CGPathRelease(path);    CFRelease( frame );    CFRelease(frameSetter);    return (NSArray *)linesArray;}