围绕UILabel的每个字边界

时间:2015-12-02 09:36:43

标签: ios swift uilabel nsattributedstring

有没有办法可以在UILabel的每个单词周围绘制边框。假设UILabel包含字符串“This is the Line 1”。

我想要5个不同的边框,大约5个字

  
      
  1. 这个
  2.   
  3.   
  4.   
  5.   
  6. 1
  7.   

4 个答案:

答案 0 :(得分:6)

我不知道UILabel的易用代码,但对于UITextView:

Swift playground

设置:

import UIKit

let string = "Lorem ipsum dolor sit amet"

let textView = UITextView(frame: CGRect(x: 0, y: 0, width: 100, height: 100))
textView.text = string

使用正则表达式得到每个单词的匹配:

let pattern = "[a-zA-Z0-9]+"
let regex = try! NSRegularExpression(pattern: pattern, options: [])
let matches = regex.matchesInString(string, options: [], range: NSMakeRange(0, string.characters.count))

函数为每个匹配获取一个矩形(从this answer移植):

func frameOfTextInRange(range:NSRange, inTextView textView:UITextView) -> CGRect {
    let beginning = textView.beginningOfDocument
    let start = textView.positionFromPosition(beginning, offset: range.location)!
    let end = textView.positionFromPosition(start, offset: range.length)!
    let textRange = textView.textRangeFromPosition(start, toPosition: end)!
    let rect = textView.firstRectForRange(textRange)
    return textView.convertRect(rect, fromView: textView)
}

遍历每个匹配,获取其框架,使用它创建背景视图,将其添加到文本视图中:

for m in matches {
    let range = m.range
    let frame = frameOfTextInRange(range, inTextView: textView)
    let v = UIView(frame: frame)
    v.layer.borderWidth = 1
    v.layer.borderColor = UIColor.blueColor().CGColor
    textView.addSubview(v)

}

result

但可能这并没有给出你期望的结果。要获得更好的控件,可以使用属性字符串。

这里使用属性字符串

的代码相同
import UIKit

let string = "Lorem ipsum dolor sit amet"

let textView = UITextView(frame: CGRect(x: 0, y: 0, width: 100, height: 100))

let attributedString = NSMutableAttributedString(string: string)
let paragraphStyle = NSMutableParagraphStyle()
paragraphStyle.lineHeightMultiple = 1.25
attributedString.addAttribute(NSParagraphStyleAttributeName, value: paragraphStyle, range: NSMakeRange(0, string.characters.count))

textView.attributedText = attributedString

let pattern = "[a-zA-Z0-9]+"
let regex = try! NSRegularExpression(pattern: pattern, options: [])
let matches = regex.matchesInString(string, options: [], range: NSMakeRange(0, string.characters.count))

func frameOfTextInRange(range:NSRange, inTextView textView:UITextView) -> CGRect {
    let beginning = textView.beginningOfDocument
    let start = textView.positionFromPosition(beginning, offset: range.location)!
    let end = textView.positionFromPosition(start, offset: range.length)!
    let textRange = textView.textRangeFromPosition(start, toPosition: end)!
    let rect = textView.firstRectForRange(textRange)
    return textView.convertRect(rect, fromView: textView)
}

for m in matches {
    let range = m.range
    var frame = frameOfTextInRange(range, inTextView: textView)
    frame = CGRectInset(frame, CGFloat(-1.2), CGFloat(2))
    frame = CGRectOffset(frame, CGFloat(0), CGFloat(2))
    let v = UIView(frame: frame)
    v.layer.borderWidth = 1
    v.layer.borderColor = UIColor.blueColor().CGColor
    textView.addSubview(v)

}

result

创建漂亮样式的另一个好处是将视图添加到背景视图并在顶部添加该textview

import UIKit

let string = "Lorem ipsum dolor sit amet"

let textView = UITextView(frame: CGRect(x: 0, y: 0, width: 100, height: 100))
let textViewBG = UIView(frame: textView.bounds)
textViewBG.backgroundColor = UIColor.whiteColor()
let attributedString = NSMutableAttributedString(string: string)
let paragraphStyle = NSMutableParagraphStyle()
paragraphStyle.lineHeightMultiple = 1.25
attributedString.addAttribute(NSParagraphStyleAttributeName, value: paragraphStyle, range: NSMakeRange(0, string.characters.count))
attributedString.addAttribute(NSForegroundColorAttributeName, value: UIColor.whiteColor(), range: NSMakeRange(0, string.characters.count))
textView.attributedText = attributedString
textView.backgroundColor = UIColor.clearColor()

let pattern = "[a-zA-Z0-9]+"
let regex = try! NSRegularExpression(pattern: pattern, options: [])
let matches = regex.matchesInString(string, options: [], range: NSMakeRange(0, string.characters.count))

func frameOfTextInRange(range:NSRange, inTextView textView:UITextView) -> CGRect {
    let beginning = textView.beginningOfDocument
    let start = textView.positionFromPosition(beginning, offset: range.location)!
    let end = textView.positionFromPosition(start, offset: range.length)!
    let textRange = textView.textRangeFromPosition(start, toPosition: end)!
    let rect = textView.firstRectForRange(textRange)
    return textView.convertRect(rect, fromView: textView)
}

for m in matches {
    let range = m.range
    var frame = frameOfTextInRange(range, inTextView: textView)
    frame = CGRectInset(frame, CGFloat(-1.2), CGFloat(2))
    frame = CGRectOffset(frame, CGFloat(0), CGFloat(2))
    let v = UIView(frame: frame)
    v.layer.cornerRadius = 2
    v.backgroundColor = UIColor(hue: 0.66, saturation: 0.6, brightness: 1, alpha: 1)
    textViewBG.addSubview(v)

}
textViewBG.addSubview(textView)

enter image description here

增加单词之间的空格,我们可以改变空格的字距

import UIKit

func frameOfTextInRange(range:NSRange, inTextView textView:UITextView) -> CGRect {
    let beginning = textView.beginningOfDocument
    let start = textView.positionFromPosition(beginning, offset: range.location)!
    let end = textView.positionFromPosition(start, offset: range.length)!
    let textRange = textView.textRangeFromPosition(start, toPosition: end)!
    let rect = textView.firstRectForRange(textRange)
    return textView.convertRect(rect, fromView: textView)
}

let string = "Lorem ipsum dolor sit amet"

let textView = UITextView(frame: CGRect(x: 0, y: 0, width: 100, height: 100))
textView.backgroundColor = UIColor.clearColor()

textView.attributedText = {
    let attributedString = NSMutableAttributedString(string: string)
    let paragraphStyle = NSMutableParagraphStyle()
    paragraphStyle.lineHeightMultiple = 1.25
    attributedString.addAttribute(NSParagraphStyleAttributeName, value: paragraphStyle, range: NSMakeRange(0, string.characters.count))
    attributedString.addAttribute(NSForegroundColorAttributeName, value: UIColor.whiteColor(), range: NSMakeRange(0, string.characters.count))

    let regex = try! NSRegularExpression(pattern: "\\s", options: [])
    let matches = regex.matchesInString(string, options: [], range: NSMakeRange(0, string.characters.count))
    for m in matches {
        attributedString.addAttribute(NSKernAttributeName, value: 6, range: m.range)
    }
    return NSAttributedString(attributedString: attributedString)
}()

let textViewBG = UIView(frame: textView.bounds)
textViewBG.backgroundColor = UIColor.whiteColor()


let pattern = "[^ ]+"
let regex = try! NSRegularExpression(pattern: pattern, options: [])
let matches = regex.matchesInString(string, options: [], range: NSMakeRange(0, string.characters.count))

for m in matches {
    textViewBG.addSubview({
        let range = m.range
        var frame = frameOfTextInRange(range, inTextView: textView)
        frame = CGRectInset(frame, CGFloat(-3), CGFloat(2))
        frame = CGRectOffset(frame, CGFloat(0), CGFloat(3))
        let v = UIView(frame: frame)
        v.layer.cornerRadius = 2
        v.backgroundColor = UIColor(hue: 211.0/360.0, saturation: 0.35, brightness: 0.78    , alpha: 1)
        return v
    }())
}

textViewBG.addSubview(textView)

result

答案 1 :(得分:2)

SWIFT 4版本

这是Swift 4版本 vikingosegundo Answer 使用UITextView包括其他一些调整,包括:
•来自数组的单词列表
•在textView中居中
•可调字数限制
•自定义字体

//: Playground - noun: a place where people can play

import UIKit

var array = [String]()

array = ["WORD1", "WORD2", "WORD3", "WORD4", "WORD4", "LOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOONGWORD", "WORD5"]

var stringarr = String()

for i in 0...(array.count-1) {

if array[i].count > 20 {
    let count = array[i].count
    let dropCount = count-20
    let dropCharacters = array[i].dropLast(dropCount)
    var shortenedWord = "\(dropCharacters)"
    shortenedWord = "\(shortenedWord)..."
    print(shortenedWord)
    array[i] = shortenedWord

    }
}

stringarr = array.joined(separator: " ")


func frameOfTextInRange(range:NSRange, inTextView textView:UITextView) -> CGRect {
    let beginning = textView.beginningOfDocument
    let start = textView.position(from: beginning, offset: range.location)
    let end = textView.position(from: start!, offset: range.length)
    let textRange = textView.textRange(from: start!, to: end!)
    let rect = textView.firstRect(for: textRange!)

    return textView.convert(rect, from: textView)
}

let textView = UITextView(frame: CGRect(x: 0, y: 0, width: 375, height: 200))
textView.backgroundColor = UIColor.clear

let lineSpacing: CGFloat = 0.0

textView.attributedText = {
    let attributedString = NSMutableAttributedString(string: stringarr)
    let paragraphStyle = NSMutableParagraphStyle()
    paragraphStyle.lineHeightMultiple = 1.5
    paragraphStyle.lineSpacing = lineSpacing
    attributedString.addAttribute(.paragraphStyle, value: paragraphStyle, range: NSRange(location: 0, length: stringarr.count))
    attributedString.addAttribute(.foregroundColor, value: UIColor.white, range: NSRange(location: 0, length: stringarr.count))
    attributedString.addAttribute(.font, value: UIFont(name: "AvenirNext-Regular", size: 10.0)!, range: NSRange(location: 0, length: stringarr.count))


let regex = try! NSRegularExpression(pattern: "\\s", options: [])
let matches = regex.matches(in: stringarr, options: [], range: NSRange(location: 0, length: stringarr.count))

for m in matches {
    attributedString.addAttribute(.kern, value: 6, range: m.range)
}

return NSAttributedString(attributedString: attributedString)
}()


textView.textAlignment = .center

let textViewBG = UIView(frame: textView.bounds)
textViewBG.backgroundColor = UIColor.white

let pattern = "[^ ]+"
let regex = try! NSRegularExpression(pattern: pattern, options: [])
 let matches = regex.matches(in: stringarr, options: [], range: NSRange(location: 0, length: stringarr.count))

for m in matches {
textViewBG.addSubview({
    let range = m.range
    let frame = frameOfTextInRange(range: range, inTextView: textView).insetBy(dx: CGFloat(-2), dy: CGFloat(3)).offsetBy(dx: CGFloat(0), dy: CGFloat(3))
    let v = UIView(frame: frame)
    v.layer.cornerRadius = 0
    v.backgroundColor = UIColor.black
    return v
    }())
}

textViewBG.addSubview(textView)

//: End of playground



Result

希望有帮助!

答案 2 :(得分:1)

您必须为每个单词创建一个标签....以编程方式执行!我现在做了,请测试!希望你喜欢: - )

导入UIKit

class ViewController: UIViewController {

var arrayStrings = [String]()
var x : CGFloat = 0
var labelReference = 0

override func viewDidLoad() {
    super.viewDidLoad()


    let space = " "
    let string = "This is the line 1"
    var word = string.componentsSeparatedByString(space)
    print (word[0]) // prints "This"
    print(word[1]) // print "is"

    for var i = 0; i < word.count ; i++ {


        arrayStrings.append(word[i])


        let characteresCount = word[i].characters.count


        // change de "9" based on your font size
        let label = UILabel(frame: CGRectMake(CGFloat(32 + x), 30, CGFloat(characteresCount * 9), 25))
        x += label.frame.size.width + 2
        label.text = word[i]
        label.layer
        label.layer.borderWidth = 1.0
        label.layer.cornerRadius = 10
        view.addSubview(label)


      }

   }

}

答案 3 :(得分:0)

SWIFT5。替代解决方案

解决方案逻辑

  1. 将字符串转换为标签
  2. 自定义标签
  3. 将标签转换为图像
  4. 将图像转换为属性文本
  5. 创建TextView
  6. 将属性文本设置为TextView

Final TextView

您可以在此处找到实现:

https://github.com/vivatum/WordsAsTagLabels-Example