获取UILabel中的每一行文本

我试图将UILabel中的每一行添加到一个数组,但我使用的代码似乎并不准确。

 func getLinesArrayOfStringInLabel(label:UILabel) -> [String] { guard let text: NSString = label.text as? NSString else { return [] } 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(NSAttributedStringKey.font, 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 } let label = UILabel() label.numberOfLines = 0 label.frame = CGRect(x: 40, y: 237, width: 265, height: 53) label.font = UIFont.systemFont(ofSize: 22, weight: UIFont.Weight.regular) label.text = "Hey there how's it going today?" label.backgroundColor = .red bg.addSubview(label) print(getLinesArrayOfStringInLabel(label: label)) 

这打印

 ["Hey there how\'s it going ", "today?"] 

但标签看起来像这样:

在这里输入图像说明

我期望得到["Hey there how\'s it ", "going today?"] 。 这是怎么回事?

所以它似乎是UILabel的东西,而不是你正在使用的function有问题。 我怀疑一个CATextLayer会如何从这个方法返回它们,我悲伤地发现:(我是对的。

这是我的结果图片: 在这里输入图像说明

红色是您用来创buildUILabel的确切代码。

绿色是一个CATextLayer,具有与上面UILabel相同的特征,包括字体,字体大小和帧大小。

黄色是一个子类UIView,它正在replace它自己的图层并返回一个CATextLayer。 我附在下面。 您可以继续构build它以满足您的需求,但是我认为这是真正的解决scheme,并且是唯一一个将获得的线条与用户看到的可见线条匹配的线条。 如果你想出一个更好的解决scheme,请让我知道。

 import UIKit class AGLabel: UIView { var alignment : String = kCAAlignmentLeft{ didSet{ configureText() } } var font : UIFont = UIFont.systemFont(ofSize: 16){ didSet{ configureText() } } var fontSize : CGFloat = 16.0{ didSet{ configureText() } } var textColor : UIColor = UIColor.black{ didSet{ configureText() } } var text : String = ""{ didSet{ configureText() } } override class var layerClass: AnyClass { get { return CATextLayer.self } } func configureText(){ if let textLayer = self.layer as? CATextLayer{ textLayer.foregroundColor = textColor.cgColor textLayer.font = font textLayer.fontSize = fontSize textLayer.string = text textLayer.contentsScale = UIScreen.main.scale textLayer.contentsGravity = kCAGravityCenter textLayer.isWrapped = true } } } 

您还应该在GitHub上签出Core-Text-Label 。 它完全像CATextLayers一样呈现,并且会匹配get行的返回值。 它不会为我的特殊需要工作,因为我需要我的可resize,它崩溃,但如果不需要resize,那么我会检查出来。

最后,我又回来了,看起来这可能是一个在iOS 11中开始的单词换行问题,他们不会在一行中留下一个孤儿词。