UILabel、UITextView中的attributedText

问题描述

给UILabel设置了highlightedTextColor属性,在执行label.highlighted = YES后,label并不显示highlightedTextColor对应的颜色。

发现问题

翻阅代码,发现此label并非用text来赋值显示的文本,而是使用attributedText。经过尝试,发现导致问题的原因是初始化attributedTextNSForegroundColorAttributeName对应的UIColor跟此label的textColor不一致,当两者一样的时,highlightedTextColor才有作用。

挖掘问题

查找文档,UILabelattributedText属性,有如下解释

Discussion

This property is nil by default.

Assigning a new value to this property also replaces the value of the text property with the same string data, although without any formatting information. In addition, assigning a new a value updates the values in the font, textColor, and other style-related properties so that they reflect the style information starting at location 0 in the attributed string.

当给attributedText属性赋值的时候,会影响到textfonttextColor等属性,本文主要对textColor做一些深入的了解。

写些代码来验证一下

代码如下:

- (void)attributedStringOfInputUI {
    UILabel *label = [UILabel new];
    label.textColor = [UIColor blueColor];
    label.highlightedTextColor = [UIColor redColor];
    label.attributedText = ({
        NSMutableAttributedString *attributedString = [[NSMutableAttributedString alloc]
                                                       initWithString:@"Hello,World!"
                                                       attributes:@{
                                                                    NSForegroundColorAttributeName : [UIColor grayColor]
                                                                    }];
        [attributedString appendAttributedString:[[NSAttributedString alloc]
                                                  initWithString:@"Again!"
                                                  attributes:@{
                                                               NSForegroundColorAttributeName : [UIColor blueColor]
                                                               }]];
        [attributedString appendAttributedString:[[NSAttributedString alloc]
                                                  initWithString:@"Again!"
                                                  attributes:@{
                                                               NSForegroundColorAttributeName : [UIColor blueColor]
                                                               }]];
        attributedString;
    });
    label.highlighted = YES;
    [self.view addSubview:label];
    [label mas_makeConstraints:^(MASConstraintMaker *make) {
        make.center.equalTo(self.view);
    }];
    
    self.label = label;

    UIButton *button = [UIButton buttonWithType:UIButtonTypeSystem];
    [button setTitle:@"添加文本" forState:UIControlStateNormal];
    [button addTarget:self action:@selector(appendString) forControlEvents:UIControlEventTouchUpInside];
    [self.view addSubview:button];
    [button mas_makeConstraints:^(MASConstraintMaker *make) {
        make.centerX.equalTo(self.view);
        make.bottom.equalTo(self.view).offset(-90);
    }];
    
    UIButton *button2 = [UIButton buttonWithType:UIButtonTypeSystem];
    [button2 setTitle:@"改变highlightedTextColor" forState:UIControlStateNormal];
    [button2 addTarget:self action:@selector(changeHighlightedTextColor) forControlEvents:UIControlEventTouchUpInside];
    [self.view addSubview:button2];
    [button2 mas_makeConstraints:^(MASConstraintMaker *make) {
        make.centerX.equalTo(self.view);
        make.bottom.equalTo(self.view).offset(-60);
    }];
    
    UIButton *button3 = [UIButton buttonWithType:UIButtonTypeSystem];
    [button3 setTitle:@"改变TextColor" forState:UIControlStateNormal];
    [button3 addTarget:self action:@selector(changeTextColor) forControlEvents:UIControlEventTouchUpInside];
    [self.view addSubview:button3];
    [button3 mas_makeConstraints:^(MASConstraintMaker *make) {
        make.centerX.equalTo(self.view);
        make.bottom.equalTo(self.view).offset(-30);
    }];
}
- (void)appendString {
    NSMutableAttributedString *attributedString = self.label.attributedText.mutableCopy;

    [attributedString appendAttributedString:[[NSAttributedString alloc]
                                              initWithString:@"Again!"
                                              attributes:@{
                                                           NSForegroundColorAttributeName : self.label.textColor
                                                           }]];
    [attributedString appendAttributedString:[[NSAttributedString alloc]
                                              initWithString:@"Again!"
                                              attributes:@{
                                                           NSForegroundColorAttributeName : [UIColor blueColor]
                                                           }]];
    self.label.attributedText = attributedString;
}

- (void)changeHighlightedTextColor {
    self.label.highlightedTextColor = [UIColor greenColor];
}
- (void)changeTextColor {
    self.label.textColor = [UIColor grayColor];
    self.label.highlighted = !self.label.highlighted;
}
  • 初始化UILabel,设置textColor[UIColor blueColor],设置highlightedTextColor[UIColor redColor],然后给attributedText赋值,并设置highlightedYES,运行之后,结果界面如下:

    UILabel、UITextView中的attributedText_第1张图片

    可以看到,attributedText中颜色值为[UIColor blueColor]的字段,颜色变成了highlightedTextColor的颜色,即颜色跟textColor一样的字段会响应highlighted属性的变化。
    attributedText被赋了新值,此时,label的textColor会收到影响,值会跟attributedText开头字段(此处为Hello,Wolrd!)的样式统一,即[UIColor grayColor]

  • 那此时,再给attributedText赋值时,是否是颜色值为[UIColor grayColor]的字段会响应highlighted属性,点击按钮,执行appendString来验证一下,结果界面如下:

    UILabel、UITextView中的attributedText_第2张图片

    跟设想的不一样,依然是颜色为[UIColor blueColor]的字段响应了highlighted属性,不过验证了textColor确实变成了[UIColor grayColor]
    此处猜想,在设置textColor时,UILabel内部有个私有属性保存了这个值,当设置attributedText时,只会改变textColor,不会改变这个私有属性,这个私有属性来判断attributedText中哪些字段需要响应highlighted

  • 改变highlightedTextColor,又会有什么影响,点击按钮,运行changeHighlightedTextColor,效果界面如下:

    UILabel、UITextView中的attributedText_第3张图片

    由此可见,只是改变了highlightedTextColor,没有其他事先没有预想到的问题。

  • 改变textColor,从文档可以看出,将会改变attributedText中所有字段的颜色显示,也可以预料,改变之后,attributedText中的所有字段都会响应highlighted

If you are using styled text, assigning a new value to this property causes the color to be applied to the entirety of the string in the attributedText property. If you want to apply the color to only a portion of the text, create a new attributed string with the desired style information and associate it with the label. If you are not using styled text, this property applies to the entire text string in the text property.

点击按钮,第一次运行changeTextColor,效果界面如下:

UILabel、UITextView中的attributedText_第4张图片

点击按钮,第二次运行changeTextColor,效果界面如下:

UILabel、UITextView中的attributedText_第5张图片

运行结果跟设想的一样。

总结

到此,本次对attributedText的探索就结束了,fonttextColorattributedText都会互相影响,当只是给文本添加段落格式,或者实现统一字体颜色的文本和图片的混合显示,这种情况下,不建议通过NSFontAttributeNameNSForegroundColorAttributeName来定义字体大小和颜色显示,应该直接设置fonttextColor,个人见解,欢迎讨论。

你可能感兴趣的:(UILabel、UITextView中的attributedText)