How to set kerning in iPhone UILabel

后端 未结 9 1082
Happy的楠姐
Happy的楠姐 2020-11-30 01:12

I am developing an iPhone app, and I want to set kerning in UILabel. The code I\'ve written (possibly around kCTKernAttributeName) seems to be in error. How mig

相关标签:
9条回答
  • 2020-11-30 01:38

    Before:

    After:

    Here's a Swift 3 extension that let's you set a UILabel's kerning via code or storyboard:

    extension UILabel {
    
        @IBInspectable var kerning: Float {
            get {
                var range = NSMakeRange(0, (text ?? "").count)
                guard let kern = attributedText?.attribute(NSAttributedStringKey.kern, at: 0, effectiveRange: &range),
                    let value = kern as? NSNumber
                    else {
                        return 0
                }
                return value.floatValue
            }
            set {
                var attText:NSMutableAttributedString
    
                if let attributedText = attributedText {
                    attText = NSMutableAttributedString(attributedString: attributedText)
                } else if let text = text {
                    attText = NSMutableAttributedString(string: text)
                } else {
                    attText = NSMutableAttributedString(string: "")
                }
    
                let range = NSMakeRange(0, attText.length)
                attText.addAttribute(NSAttributedStringKey.kern, value: NSNumber(value: newValue), range: range)
                self.attributedText = attText
            }
        }
    }
    

    Demo usage:

    myLabel.kerning = 3.0
    

    or

    The demo uses 3.0 kerning for drama, but I've found 0.1 - 0.8 tends to work well in practice.

    0 讨论(0)
  • 2020-11-30 01:47

    Swift 4 and 5

    extension NSAttributedString {
    
        /// Returns a new instance of NSAttributedString with same contents and attributes with kerning added.
        /// - Parameter kerning: a kerning you want to assign to the text.
        /// - Returns: a new instance of NSAttributedString with given kerning.
        func withKerning(_ kerning: CGFloat) -> NSAttributedString {
            let attributedString = NSMutableAttributedString(attributedString: self)
            attributedString.addAttributes([.kern: kerning],
                                           range: NSRange(location: 0, length: string.count))
            return NSAttributedString(attributedString: attributedString)
        }
     ]
    
    0 讨论(0)
  • 2020-11-30 01:48

    In Swift 2.0...

    Add an extension:

    extension UIView {
        func attributes(font: String, color: UIColor, fontSize: CGFloat, kern: Double) -> [String: NSObject] {
            let attribute = [
                NSForegroundColorAttributeName: color,
                NSKernAttributeName: kern,
                NSFontAttributeName : UIFont(name: font, size: fontSize)!
            ]
            return attribute
        }
    }
    

    Now, just set your UILabel as attributedText:

    self.label.attributedText = NSMutableAttributedString(string: "SwiftExample", attributes: attributes("SourceSans-Regular", color: UIColor.whiteColor(), fontSize: 20, kern: 2.0))   
    

    Obviously, I added a bunch of parameters that you may not need. Play around -- feel free to rewrite the method -- I was looking for this on a bunch of different answers so figured I'd post the whole extension in case it helps someone out there... -rab

    0 讨论(0)
  • 2020-11-30 01:49

    Just to be up-to-date here, iOS 6 introduced attributedText for UILabel and UITextView!

    UILabel reference:
    http://developer.apple.com/library/ios/#documentation/uikit/reference/UILabel_Class/Reference/UILabel.html#//apple_ref/occ/instp/UILabel/attributedText

    0 讨论(0)
  • 2020-11-30 01:51

    As far as I am aware, UILabel will not render the characteristics of NSAttributedString. There are a couple of nice open source solutions. I recently used TTTAttributedLabel as a swap in replacement for UILabel that accepts NSAttributedString.

    DTCoreText (former NSAttributedString+HTML) is also getting a bit of buzz lately.

    0 讨论(0)
  • 2020-11-30 01:59

    An example using IBDesignables and IBInspectables where you can manage to set the kerning value through storyboard only. I found it very practical and I thought to share it with you.

    UILabelKerning.h

    #import <UIKit/UIKit.h>
    
    IB_DESIGNABLE
    
    @interface UILabelKerning : UILabel
    @property (assign, nonatomic) IBInspectable int kerning;
    @end
    

    UILabelKerning.m

    #import "UILabelKerning.h"
    
    @implementation UILabelKerning
    
    
    -(void)awakeFromNib {
    
        [self setTheAttributes];
    }
    
    - (id)initWithCoder:(NSCoder*)aDecoder
    {
        self = [super initWithCoder:aDecoder];
        if (self)
        {
            // Initialization code
        }
    
        return self;
    }
    -(void)setTheAttributes{
        NSMutableAttributedString *attributedString =[[NSMutableAttributedString alloc] initWithAttributedString:self.attributedText];
        [attributedString addAttribute:NSKernAttributeName
                                 value:[NSNumber numberWithFloat:self.kerning]
                                 range:NSMakeRange(0, [self.text length])];
        [self setAttributedText:attributedString];
    }
    @end
    

    0 讨论(0)
提交回复
热议问题