UILabel Text with Multiple Font Colors - ios

Is there a way to have the textColor property of a UILabel be two different UIColors? Basically I'm trying to make the first character in the UILabel text property to be greenColor and the rest be blackColor. I would like to avoid using two different UILabels because I may want to change the position in the text of the green character.

Starting from ios 6 you can do the following :
NSMutableAttributedString *attributedString = [[NSMutableAttributedString alloc] initWithString:string];
[attributedString addAttribute:NSBackgroundColorAttributeName value:[UIColor redColor] range:NSMakeRange(0,3)];
[attributedString addAttribute:NSForegroundColorAttributeName value:[UIColor blackColor] range:NSMakeRange(4,9)];
cell.label.attributedText = attributedString;

UILabel doesnot supprt this property...
Use should use NSAttributedString... and use controllers for drawing NSAttributesString...
Controller for NSAttributedString
UPDATE:
From iOS 6 you can do the following :
label.attributedText = attributedString;

Swift 3:
extension NSMutableAttributedString {
func setColorForText(textToFind: String, withColor color: UIColor) {
let range: NSRange = self.mutableString.range(of: textToFind, options: .caseInsensitive)
if range != nil {
self.addAttribute(NSAttributedStringKey.foregroundColor, value: color, range: range)
}
}
}
func setColoredLabel() {
var string: NSMutableAttributedString = NSMutableAttributedString(string: "My label with red blue and green colored text")
string.setColorForText(textToFind: "red", withColor: UIColor.red)
string.setColorForText(textToFind: "blue", withColor: UIColor.blue)
string.setColorForText(textToFind: "green", withColor: UIColor.green)
mylabel.attributedText = string
}
Result:

NSAttributedStrings support mixed fonts, styles, and colors in the same string, but aren't currently supported by any standard UIKit controls. That said, you should check out TTTAttributedLabel. It's a simple, performant replacement for UILabel that will allow you to display rich text really easily.

No - Apple say you should use HTML in a UIWebView if you need formatted text. (See the note in the overview section of the UITextView API docs.)

Another alternative way is to create multiple labels with difference color and layout them next to each other. Try to make the label's background color transparent. It may be tedious but should work.

No, that's not possible - you need to draw on your own or compose using several labels.
If you can accept 3.2 compatibility, you might have a look at NSAttributedString.

not currently possible, usually you would use an NSAttributedString, but to use this on iOS you would need to roll your own label. you may be able to work round this using a UIWebView, but I don't like to do that, it seems heavy handed.

Related

NSAttributedString: How to mimic opacity or alpha equivalent using color

I am using NSAttributedString for a button title and would like to be able to "grey out" or lower the alpha or capacity of certain text. NSAttributedString does not appear to allow you to modify the opacity or alpha value of the text but does let you adjust the color using:
NSMutableAttributedString *text =
[[NSMutableAttributedString alloc]
initWithAttributedString: label.attributedText];
[text addAttribute:NSForegroundColorAttributeName
value:[UIColor redColor]
range:NSMakeRange(10, 1)];
or:
let range = (mainString as NSString).range(of: stringToColor)
let mutableAttributedString = NSMutableAttributedString.init(string: mainString)
mutableAttributedString.addAttribute(NSAttributedString.Key.foregroundColor, value: UIColor.red, range: range)
In this case, the starting color is System Blue. Is there any formula that would allow me to modify the system color to the equivalent of an alpha value (or opacity) of 0.5?
Thanks for any suggestions.
You can change any color alpha using
UIColor.red.withAlphaComponent(0.5)
Of course, you have to know the original color.
There is no universal alpha modifier.

Swift iOS. Multi line UILabel background color to follow the text

I have a multi line UILabel which I want to set the background color exactly the same as when you highlight the text on a web browser with your mouse but cannot seem to find a solution.
This is what I got in my storyboard:
And this is what I am aiming to achieve:
This is the browser example I was mentioned above:
Yes, use attribute text. Here for swift
let textBgColor = UIColor.greenColor()
let attributes = [
NSBackgroundColorAttributeName : textBgColor
]
let attributedString = NSAttributedString(string: Constant.kDescriptionArray[0], attributes: attributes)
descriptionLabel.attributedText = attributedString
Try using attributed string
NSMutableAttributedString *string = [[NSMutableAttributedString alloc]
initWithString:#"Some text line Some text line\nSome text line"];
[string addAttribute:NSBackgroundColorAttributeName value:[UIColor redColor] range:NSMakeRange(0, string.length)];
titleLabel.attributedText = string;
EDIT:
Eric needed help to write swift codes. I just posted the code I had, and anyone with simple Swift knowledge should be able to write the Swift code :). Its all about learning after all :)
But any way here is the swift code.
let string = NSMutableAttributedString(string: "blah blah", attributes: [NSBackgroundColorAttributeName: UIColor.redColor()])
label.attributedText = string

How to provide different font color in same label programatically involving dynamic text

Hi Below is the kind of view I need to achieve using UILabel. I have heard about NSAttributedString but not sure how to use it for dynamic text loading.
Here the whole text font is Roboto-Light. However, I have to replace text 'Dr Andrew Murphy, John Smith' from the API response for first two doctors and get the count for '23 doctors' from API so that it adjusts in this label accordingly. Text color as you can see depends upon if text is constant or dynamic. I am not sure how to achieve it. Hence some code snippets are really welcome.
Thanks!
You can use NSMutableAttributeString with addAttribute:value:range like that;
//Your entry string
NSString *myString = #"I have to replace text 'Dr Andrew Murphy, John Smith' ";
//Create mutable string from original one
NSMutableAttributedString *attString = [[NSMutableAttributedString alloc] initWithString:myString];
//Fing range of the string you want to change colour
//If you need to change colour in more that one place just repeat it
NSRange range = [myString rangeOfString:#"John Smith"];
[attString addAttribute:NSForegroundColorAttributeName value:[UIColor yellowColor] range:range];
//Add it to the label - notice its not text property but it's attributeText
label.attributedText = attString;
Hope this help
Create an NSMutableAttributedString with the raw text.
Then find the range of a string you wish to color. Use that range with the NSMutableAttributedString setAttributes:range: method.
Repeat for each bit of text you wish to color.

Letter spacing in iOS

I have the following code:
[[cancelButton titleLabel] setFont:[UIFont fontWithName:#"ProximaNova-Regular" size:15]];
How would I set the letter-spacing as well?
You can't change the letter spacing in the abstract, which means that you can't change it at all under iOS 5 and below.
As of iOS 6, you can push an attributed string rather than a vanilla one to a UILabel. The process for pushing an attributed string works slightly differently from the process for pushing an ordinary one — the font, text colour and a bunch of other properties are all set on the string rather than on the label. The reason is that attributed strings allow different attributes to be set for different regions of the string. So you can set a string that combines multiple fonts, text colours, etc.
One of the supported Core Text attributes is kCTKernAttributeName, which as of iOS 6 is easier to take advantage of via the UIKit addition NSKernAttributeName. You can use kerning to adjust the horizontal spacing of glyphs.
Under iOS 5 and earlier you used to have to do a lot of mental jumping back and forth between Core Foundation C-style objects and Objective-C UIKit objects. As of 6 that's no longer necessary. But be wary if you search the 'net that things got a lot easier under 6 — if you see lots of __bridge casts and manual CFReleases then you're probably looking at older code.
Anyway, supposing you currently have something like:
UILabel *label = [cancelButton titleLabel];
UIFont *font = <whatever>;
UIColor *textColour = <whatever>;
NSString *string = <whatever>;
label.text = string;
label.font = font;
label.textColor = textColour;
You'd instead do something more like:
NSAttributedString *attributedString =
[[NSAttributedString alloc]
initWithString:string
attributes:
#{
NSFontAttributeName : font,
NSForegroundColorAttributeName : textColour
}];
label.attributedText = attributedString;
In your case, also to adjust the overall kerning you'd add:
NSAttributedString *attributedString =
[[NSAttributedString alloc]
initWithString:string
attributes:
#{
NSFontAttributeName : font,
NSForegroundColorAttributeName : textColour,
NSKernAttributeName : #(-1.3f)
}];
label.attributedText = attributedString;
Or whatever kerning value you want to apply. See the various constants at the bottom of the NSAttributedString UIKit Additions Reference for the various other attributes you can apply and which version of iOS they first became available on.
Much later addendum: while still being one of the least Swifty people you'll meet, I think this is the equivalent in Swift:
button.titleLabel?.attributedText =
NSAttributedString(
string: string,
attributes:
[
NSFontAttributeName: font,
NSForegroundColorAttributeName: textColour,
NSKernAttributeName: -1.3
])
NSAttributedString *cancelButtonAttributedString = [[NSAttributedString alloc]
initWithString:#"Hello"
attributes:
#{
NSKernAttributeName: #(1.5)
}];
[cancelButton setAttributedTitle:cancelButtonAttributedString forState:UIControlStateNormal];
This is only simple answer for above question
One of the supported Core Text attributes is kCTKernAttributeName, which as of iOS 6 is easier to take advantage of via the UIKit addition NSKernAttributeName. You can use kerning to adjust the horizontal spacing of glyphs.
Kerning is the adjustment of space between two unique letters. Kerning varies between different character pairs. For example, a combination like 'AVA' would have a different kerning between characters than something like 'VVV'
By using NSKernAttributeName, you're actually overriding that custom space adjustment that is built into the font file, setting all the various character pair kern values to the same number, thus breaking the optimal kerning. When applied to an entire string of text, small amounts of kerning the broken spacing is more noticeable. However, high kerning values could push the letter far enough apart to the point that the poor spacing will not be as noticeable.
What you're looking for is Tracking (aka letter spacing), which is the spacing between all the letters in a given block of text. Unfortunately, iOS does not seem to let you control that attribute.

How to make an underlined text in UILabel?

How can I make an underlined text in UILabel?
I had tried by making a UILabel with height 0.5f and place it under the text. This line label is not visible when I am running my app in iPhone 4.3 and iPhone 4.3 simulator, but it is visible in iPhone 5.0 simulator onwards. Why?
How can I do this?
Objective-C
iOS 6.0 > version
UILabel supports NSAttributedString
NSMutableAttributedString *attributeString = [[NSMutableAttributedString alloc] initWithString:#"Hello Good Morning"];
[attributeString addAttribute:NSUnderlineStyleAttributeName
value:[NSNumber numberWithInt:1]
range:(NSRange){0,[attributeString length]}];
Swift
let attributeString: NSMutableAttributedString = NSMutableAttributedString(string: "Hello Good Morning")
attributeString.addAttribute(NSUnderlineStyleAttributeName, value: 1, range: NSMakeRange(0, attributeString.length))
Definition :
- (void)addAttribute:(NSString *)name value:(id)value range:(NSRange)aRange
Parameters List:
name : A string specifying the attribute name. Attribute keys can be supplied by another framework or can be custom ones you define. For information about where to find the system-supplied attribute keys, see the overview section in NSAttributedString Class Reference.
value : The attribute value associated with name.
aRange : The range of characters to which the specified attribute/value pair applies.
Now use like this:
yourLabel.attributedText = [attributeString copy];
iOS 5.1.1 < version
You needs 3 party attributed Label to display attributed text:
1) Refer TTTAttributedLabel link. Its best third party attributed Label to display attributed text.
2) refer OHAttributedLabel for third party attributed Label
I am using Xcode 9 and iOS 11.
To make the UILabel with an underline beneath it.
You can use both
1. Using code
2. Using xib
Using code:
NSMutableAttributedString *attributeString = [[NSMutableAttributedString alloc] initWithString:#"I am iOS Developer"];
[attributeString addAttribute:NSUnderlineStyleAttributeName
value:[NSNumber numberWithInt:1]
range:(NSRange){0,[attributeString length]}];
lblAttributed.attributedText = attributeString;
Using Xib:
We can also use for button too.
The Designer Way - Highly Customisable Version
I personally prefer to customise my design(s) as much as possible. Sometimes, you will find that using the built-in underline tool is not easily customisable.
Here is how I do it:
1 First I create a UIView for the underline. You can then choose your background color, either in IB or programmatically. Constraints are key here.
2 Then, you can customise the underline as much as you like. For example, to adapt the width of the underline for better visual effect, create an outlet connection to a constraint in Interface Builder
3 You can then easily programmatically customise your underline view. For example here, to give you an idea we will make the underline 20 px wider than the title "Breads":
var originalString: String = "Breads"
let myString: NSString = originalString as NSString
let size: CGSize = myString.size(attributes: [NSFontAttributeName: UIFont.systemFont(ofSize: 14.0)])
self.widthUnderlineTitle.constant = size.width + 20
Results:
Take a look at TTTAttributedLabel. If you're allowed to use 3d-party components just replace your UILabels with TTTAttributedLabel where you need it (drop-in replacement). Works with iOS < 6.0!
Swift extension on UILabel:
Still needs improvement, any thoughts are welcome:
extension UILabel{
func underLine(){
if let textUnwrapped = self.text{
let underlineAttribute = [NSUnderlineStyleAttributeName: NSUnderlineStyle.StyleSingle.rawValue]
let underlineAttributedString = NSAttributedString(string: textUnwrapped, attributes: underlineAttribute)
self.attributedText = underlineAttributedString
}
}
}
One of the cons i can think of right now is that it will need to be called each time text changes, and there is no actual way of turning it off...
Swift 4.0
var attributeString = NSMutableAttributedString(string: "Hello Good Morning")
attributeString.addAttribute(NSUnderlineStyleAttributeName, value: 1, range: NSRange)
Swift 5
let attributeString: NSMutableAttributedString = NSMutableAttributedString(string: yourLabel.text ?? "")
attributeString.addAttribute(NSAttributedString.Key.underlineStyle, value: 1, range: NSMakeRange(0, attributeString.length))
yourLabel.attributedText = attributeString

Resources