web-dev-qa-db-ja.com

iOS 10.3:NSMutableAttributedStringのサブ範囲に適用された場合、NSStrikethroughStyleAttributeNameはレンダリングされません

適用範囲が文字列範囲全体ではない場合、NSMutableAttributedStringのインスタンスに属性として追加された取り消し線(シングル、ダブル、...)はレンダリングされません。

これは、addAttribute(_ name: String, value: Any, range: NSRange)insert(_ attrString: NSAttributedString, at loc: Int)append(_ attrString: NSAttributedString)、...を使用して発生します.

壊れたApple初期のiOS 10.3ベータ版で、10.3最終版では修正されていません。

クレジット: https://openradar.appspot.com/3103468

46
rshev

here で説明したように、属性付き文字列にNSBaselineOffsetAttributeNameを追加すると、取り消し線が戻ります。 drawText:in:のオーバーライドは、特にコレクションビューまたはテーブルビューセルで遅くなる可能性があります。

24
Mugunth

ベースラインオフセットを設定すると、修正されるようです。

[attributedStr addAttribute:NSBaselineOffsetAttributeName value:@0 range:NSMakeRange(0, 10)];
[attributedStr addAttribute:NSStrikethroughStyleAttributeName value:@2 range:NSMakeRange(0, 10)];

これは既知の バグ iOS 10.3で

88
tommybananas

特定のシナリオの回避策が見つかりました(UILabelのプロパティではスタイルを指定せず、すべてNSAttributedString属性で指定します)。

/// This UILabel subclass accomodates conditional fix for NSAttributedString rendering broken by Apple in iOS 10.3
final class PriceLabel: UILabel {

    override func drawText(in rect: CGRect) {
        guard let attributedText = attributedText else {
            super.drawText(in: rect)
            return
        }

        if #available(iOS 10.3, *) {
            attributedText.draw(in: rect)
        } else {
            super.drawText(in: rect)
        }
    }
}

注:UILabelのスタイリングプロパティとNSAttributedString属性を混在させる場合、レンダリングする前に新しい属性付き文字列を作成し、UILabelのスタイリングを適用してから、attributedTextのすべての属性を再適用することを検討してください。

14
rshev

スイフト4

let text = "Hello World"
let textRange = NSMakeRange(0, text.count)
let attributedText = NSMutableAttributedString(string: text)
attributedText.addAttribute(NSAttributedStringKey.strikethroughStyle,
                            value: NSUnderlineStyle.styleSingle.rawValue,
                            range: textRange)
myLabel.attributedText = attributedText
10
Yuchen Zhong

10.3でテストされたSwift 3作業コード

let attributeString: NSMutableAttributedString = NSMutableAttributedString(string: "₹3500")
attributeString.addAttribute(NSBaselineOffsetAttributeName, value: 0, range: NSMakeRange(0, attributeString.length))
attributeString.addAttribute(NSStrikethroughStyleAttributeName, value: 1, range: NSMakeRange(0, attributeString.length))
productPriceLabel.attributedText = attributeString
10
Velu Loganathan

その回避策はXcode 8.3(8E3004b)/ iOS 10.3であり、この回避策では追加のコード行は不要で、NSMutableAttributedString()を宣言するときに[NSBaselineOffsetAttributeName:0]を追加するだけです。

let attrStr = NSMutableAttributedString(string: YOUR_STRING_HERE, attributes: [NSBaselineOffsetAttributeName : 0])

// Now if you add the strike-through attribute to a range, it will work
attrStr.addAttributes([
    NSFontAttributeName: UIFont.boldSystemFont(ofSize: 24),
    NSStrikethroughStyleAttributeName: 1
], range: NSRange)
4
AamirR