下划线覆盖NSAttributedString中的文本

时间:2017-05-04 14:27:35

标签: ios swift nsattributedstring

我试图创建一个属性字符串,但下划线覆盖了我的文字,而不是出现在它后面:

enter image description here

有没有办法解决这个问题?我使用以下代码:

let paragraphStyle = NSMutableParagraphStyle()
paragraphStyle.lineSpacing = 10.0

let attributes = [NSForegroundColorAttributeName: UIColor.white,
                  NSUnderlineStyleAttributeName: NSUnderlineStyle.styleThick.rawValue,
                  NSUnderlineColorAttributeName: UIColor.red,
                  NSParagraphStyleAttributeName: paragraphStyle]

let attributedString = NSAttributedString(string: "Story", attributes: attributes)

谢谢!

编辑:

提供更多背景信息:

我在放置在.xib文件中的UILabel上显示属性字符串:

view.textLabel.attributedText = attributedString

标签有以下字体: 系统大胆32.0

我在iPhone 6上运行代码 - iOS 10.3模拟器。

编辑2:

我应该提到标签可能在某些时候包含多行文本。这就是numberOfLines设置为0的原因。

编辑3: 如果有人遇到这个问题 - 似乎在iOS 9 vs 10以及UILabel vs UITextView上绘制下划线有很多不同。我最终不得不通过子类化NSLayoutManager来绘制下划线。

4 个答案:

答案 0 :(得分:4)

是的,存在您所描述的问题。它会在您使用多行UILabel时显示,因此不仅要将numberOfLines设置为0,还要在其中键入多行。

示例

let selectedStringAttributes: [String: Any]
    = [NSFontAttributeName: UIFont.boldSystemFont(ofSize: 28),
       NSForegroundColorAttributeName: UIColor.green,
       NSUnderlineStyleAttributeName: NSUnderlineStyle.styleSingle.rawValue,
       NSUnderlineColorAttributeName: UIColor.green]

let label = UILabel(frame: CGRect(x: 100, y: 100, width: 500, height: 100))
label.numberOfLines = 0

label.attributedText = NSAttributedString(string: "String to test underline", attributes: selectedStringAttributes)

一切看起来都不错。

但是如果你想使用这样的文字:

label.attributedText = NSAttributedString(string: "String to\ntest underline", attributes: selectedStringAttributes)

或标签的宽度太短,而不是:

Not so good

因此NSAttributedString中出现这种行为的原因当然是bug。正如它在雷达中所提到的,有一个解决方法

您应该将此属性添加到NSAttributedString

NSBaselineOffsetAttributeName: 0

魔法将会发生。

答案 1 :(得分:2)

在我的机器上,在黑色背景的UILabel中显示你的属性字符串,它显示了一个非常漂亮的显示:

enter image description here

红色粗下划线与文本很好地分开,并被中断以允许" y"通过它。

注意您无法将UILabel的font(在Interface Builder中设置)与其attributedText组合在一起。您必须在attributedText中设置整个标签的文字格式。所以,我的代码看起来像这样:

    let attributes : [String:Any] = [NSForegroundColorAttributeName: UIColor.white,
                      NSUnderlineStyleAttributeName: NSUnderlineStyle.styleThick.rawValue,
                      NSUnderlineColorAttributeName: UIColor.red,
                      NSFontAttributeName: UIFont.boldSystemFont(ofSize: 32)]
    let attributedString = NSAttributedString(string: "Story", attributes: attributes)
    lab.backgroundColor = .black
    lab.attributedText = attributedString

(你会注意到我删除了段落行间距的规定;只有一行,所以这个规定什么也没有增加。但是,即使我恢复它也会得到相同的结果。)

答案 2 :(得分:2)

使用此方法,您可以使用x空格在标签下方绘制边框,而不是使用NSAttributedString。

let space:CGFloat = 10

let border = CALayer()
border.backgroundColor = UIColor.red.cgColor
border.frame = CGRect(x: 0, y: (label?.frame.size.height)! + space, width: (label?.frame.size.width)!, height: 1)
label?.layer.addSublayer(border)

答案 3 :(得分:2)

所以这是我对这个问题的解决方案。 我认为它“更清洁”,更容易。 发贴我如果你不明白:)

<div id="book1" class="book">
        <ul class="hardcover_front">
            <li></li>
            <li>Tri</li>
        </ul>
        <ul class="hardcover_back">
            <li>shy</li>
            <li></li>
        </ul>
        <ul class="book_spine">
        </ul>
</div>