UILable

2016-07-26  本文已影响317人  Laughingg

UILable 是一个只读的文本视图,使用这个类绘制单行或者多行的静态文本。你可以将 UILable 作为你界面的一部分。UILable 提供了简单文本和复合样式文本的支持。你能够控制文本的外观,比如文本是否有阴影是否高亮。如果需要,你可以通过子类进行深度的定制。
UILable 的默认的内容模式是 重绘,在这个模式下,每次 lable 的 bounds 发生改变的时候就会对 Lable 的内容进行重新绘制。(通过触发 setNeedsDisplay() 方法进行重绘)你可以改变这个模式,通过修改继承过来的 contentMode 属性。

lable 对象是默认忽略用户事件并切除子 view 。 如果你想在自定义的子类中控制用户事件,你必须明确的修改 lable 的 isUserInteractionEnabled 属性值为 ture。如果你需去扩展 lable 的 bounds 的区域,你必须修改 clipsToBounds 属性的值为 false

**注意点: **

  1. UILable 默认是不能响应用户事件, 只用 isUserInteractionEnabled = ture 的时候可以。
  2. 超出 UILable 部分的内容默认情况下是被切除的。 (clipsToBounds = ture)
  3. UILable 默认情况下只能显示单行文字,只用在 numberOfLines = 0 的时候才显示多行文本

1. 简单文本的显示

let lable = UILabel()
lable.text = "我是一个文本"
lable.frame = CGRect(x: 10, y: 74, width: 200, height: 50)
view.addSubview(lable)
Snip20160726_1.png

2. 文本的换行模式

public enum NSLineBreakMode : Int {

    case byWordWrapping // Wrap at word boundaries, default

    case byCharWrapping // Wrap at character boundaries

    case byClipping // Simply clip

    case byTruncatingHead // Truncate at head of line: "...wxyz"

    case byTruncatingTail // Truncate at tail of line: "abcd..."

    case byTruncatingMiddle // Truncate middle of line:  "ab...yz"
}

默认的换行模式 NSLineBreakByTruncatingTail

public var lineBreakMode: NSLineBreakMode 
// default is NSLineBreakByTruncatingTail. used for single and multiple lines of text
Snip20160726_3.png

3. 阴影设置

// 设置阴影的颜色
lable.shadowColor = UIColor.red()

// 设置了阴影的偏移
lable.shadowOffset = CGSize(width: 10, height: 10)

width : 表示左右偏移。 + 向右,-向左
height: 表示上下偏移。 + 向上,- 向下

1.gif

4. isEnabled

表示一个文本是否可用。 只决定了 text 如何绘制。

 lable.isEnabled = false

文本默认会变成灰色

Snip20160726_4.png

5. 文本的高亮

//        lable.isEnabled = false    // 这个属性会影响文本高亮
lable.highlightedTextColor = UIColor.red()    // 这个值只会在   isHighlighted = true 的时候自动显示


lable.isHighlighted = true       // 文本是否进行高亮

/*
Button 中 的 lable 在用户进行按压操作的时候 。 text 会进入高亮状态。
*/
Snip20160726_5.png

6. lable 自带 API 文本尺寸的处理

**文本 fit矩形区域 去调整字体 **

public var adjustsFontSizeToFitWidth: Bool // default is NO

这个属性是表明,是否调整 lable 字体的大小去适应给定的 矩形范围。

通常情况下,lable 的文本绘制会按照 font 指定的进行绘制。 如果 adjustsFontSizeToFitWidth 设置为 true , 无论怎样,只要 lable 的文本超过 lable 的矩形范围,这个 lable 就会调整字体的大小去适应矩形区域。直到达到最小字体。在 iOS6 之前的版本中只用 numberOfLines 为 1 的时候才是有效的。

如果你 设置 了 adjustsFontSizeToFitWidth = true ,也应该同时设置 minimumFontSize 属性。

self.lable = UILabel()
self.lable!.frame = CGRect(x: 10, y: 75, width: 100, height: 100)

// 设置背景颜色主要是为了看清楚 lable 的范围
lable?.backgroundColor = UIColor.gray()

// 让文本多行显示        
lable?.numberOfLines = 0
lable?.adjustsFontSizeToFitWidth = true
lable?.minimumScaleFactor = 0.5   // minimumFontSize 是等效的
view.addSubview(lable!)
1.gif

允许由于截断的原因进行默认的收缩处理

 public var adjustsFontSizeToFitWidth: Bool // default is NO

默认值为 false

在设置为 true 的时候,文本在进行截断之前会收缩字符空间。
这个最大的收缩量有字体,行宽,换行模式,和另一些相关的信息决定。
(测试的效果不是太明显)

基准线调整

public var baselineAdjustment: UIBaselineAdjustment // default is UIBaselineAdjustmentAlignBaselines

这个属性 只有 numberOfLines = 1 的时候才有效果
(测试的效果不是很明显)

adjustsFontSizeToFitWidth = true ,text 在文字在进行缩放的时候调整文本的基准线。

** 文本行数的处理 **

public var numberOfLines: Int

这个是用来控制 文本 矩形区域中能够显示的最大行数。
当 numberOfLines = 0 的时候表示没有行数限制。
当最大行数显示的内容超过 文本矩形区域显示的范围,不能显示后就以换行模式进行处理。

当 lable 调用 sizeToFit() 方法后,numberOfLines 的值就会进行计算并进行存储。

7. 文本绘制的处理

/*
子类进重载:
   1. 想要在完成一些计算之前去改变文本的矩形区域, 使用 返回值可以现在文本的高度

这个方法是在调用 sizeToFit() 或者 sizeThatFits(_:)  之前进行调用。
*/
public func textRect(forBounds bounds: CGRect, limitedToNumberOfLines numberOfLines: Int) -> CGRect


// 需要修改默认的文本绘制行为的时候进行重载
/*
Lable 根据默认的图形上下文环境进行配置后会调用这个方法。

重载: 
 自己进行图形上下配置,调用父类进行真实的绘制行为,或者进行一些自己的绘制行为。
 如果进行自行渲染文本就不需要调用父类
*/
public func drawText(in rect: CGRect)

这两个方法都是用来给子类进行重载操作的。

8. 文本 size 的计算

**1. 单行文本的计算 **

public func size(attributes attrs: [String : AnyObject]? = [:]) -> CGSize
// 1. 单行文本计算
let str = "1234567890"

let label = UILabel()
self.label = label
label.backgroundColor = UIColor.red()
label.textColor = UIColor.white()
label.text = str

// 根据 label 的属性来计算文本的尺寸
let size = (str as NSString).size(attributes: [NSFontAttributeName : label.font])
// 默认情况下,这种方式和上一种方式一样的效果
// let size = (str as NSString).size(attributes: [NSFontAttributeName : UIFont.systemFont(ofSize: 17)])

print(size)
label.frame = CGRect(x: 10, y: 74, width: size.width, height: size.height)
view.addSubview(label)
Snip20160727_8.png

这种计算的 size 和 label 是否是 多行没有关系。

动态计算文本

var label: UILabel?

override func viewDidLoad() {
    super.viewDidLoad()


    
    // 1. 单行文本计算
    let str = "1234567890"

    let label = UILabel()
    self.label = label
    label.backgroundColor = UIColor.red()
    label.textColor = UIColor.white()
    label.text = str
    label.numberOfLines = 0

    // 根据 label 的属性来计算文本的尺寸
    let size = (str as NSString).size(attributes: [NSFontAttributeName : label.font])
    // 默认情况下,这种方式和上一种方式一样的效果
    // let size = (str as NSString).size(attributes: [NSFontAttributeName : UIFont.systemFont(ofSize: 17)])

    print(size)
    label.frame = CGRect(x: 10, y: 74, width: size.width, height: size.height)
    view.addSubview(label)
    
    
    // 输入框
    let textF = UITextField()
    textF.borderStyle = .roundedRect
    textF.frame = CGRect(x: 10, y: view.frame.size.height - 50, width: view.frame.size.width - 20, height: 44)
    textF.addTarget(self, action: #selector(textChange), for: .editingChanged)
    view.addSubview(textF)
}


func textChange(sender: UITextField) {
    
    // 设置 字符串
    self.label!.text = sender.text
    
    // 计算字符串大小
    let size = (sender.text! as NSString).size(attributes: [NSFontAttributeName : self.label!.font])

    // 设置字符串 frame
    label!.frame = CGRect(x: 10, y: 74, width: size.width, height: size.height)
}
2.gif

**2. 多行文本的计算 **

public func boundingRect(with size: CGSize, 
                           options: NSStringDrawingOptions = [], 
                        attributes: [String : AnyObject]? = [:],
                           context: NSStringDrawingContext?) -> CGRect



//  字符串绘制选项
public struct NSStringDrawingOptions : OptionSet {

    public init(rawValue: Int)

    // 绘制文本时使用 line fragement origin 而不是 baseline origin
    public static var usesLineFragmentOrigin: NSStringDrawingOptions { get }

    // 计算行高时使用行距。(译者注:字体大小 + 行间距=行距) 
    public static var usesFontLeading: NSStringDrawingOptions { get }

    // 计算布局时使用图元字形(而不是印刷字体)。
    public static var usesDeviceMetrics: NSStringDrawingOptions { get }

    @available(iOS 6.0, *)
    // 如果文本内容超出指定的矩形限制,文本将被截去并在最后一个字符后加上省略号。
    // 如果没有指定NSStringDrawingUsesLineFragmentOrigin选项,则该选项被忽略
    public static var truncatesLastVisibleLine: NSStringDrawingOptions { get }
}


Attributes 是文本字体的属性:该参数要设置字体的大小。
Context 是上下文对象,用于包含信息:如何调整字间距以及缩放。最终,该对象包含的信息将用于文本绘制。该参数可为 nil。 

var label: UILabel?

override func viewDidLoad() {
    super.viewDidLoad()
    
    
    
    // 1. 单行文本计算
    let str = "1234567890"
    
    let label = UILabel()
    self.label = label
    label.backgroundColor = UIColor.red()
    label.textColor = UIColor.white()
    label.text = str
    label.numberOfLines = 0
    
    let width = view.frame.size.width - 20
    let size = (str as NSString).boundingRect(with: CGSize(width: width, height: CGFloat(MAXFLOAT)), options: NSStringDrawingOptions.usesLineFragmentOrigin, attributes: [NSFontAttributeName : UIFont.systemFont(ofSize: 17)], context: nil)
    
    print(size)
    label.frame = CGRect(x: 10, y: 74, width: size.width, height: size.height)
    view.addSubview(label)
    
    
    // 输入框
    let textF = UITextField()
    textF.borderStyle = .roundedRect
    textF.frame = CGRect(x: 10, y: view.frame.size.height - 50, width: view.frame.size.width - 20, height: 44)
    textF.addTarget(self, action: #selector(textChange), for: .editingChanged)
    view.addSubview(textF)
}


func textChange(sender: UITextField) {
    
    // 设置 字符串
    self.label!.text = sender.text
    
    //  限制的文本宽度
    let width = view.frame.size.width - 20
    
    // 计算字符串大小
     let size = ((self.label?.text)! as NSString).boundingRect(with: CGSize(width: width, height: CGFloat(MAXFLOAT)), options: NSStringDrawingOptions.usesLineFragmentOrigin, attributes: [NSFontAttributeName : UIFont.systemFont(ofSize: 17)], context: nil)
    
    // 设置字符串 frame
    label!.frame = CGRect(x: 10, y: 74, width: size.width, height: size.height)
}
2.gif
上一篇下一篇

猜你喜欢

热点阅读