Formatting UITableView Cells in iphone - ios

I am developing an iphone app. In the image below I want the first name to be in plain font and the last name to be bold.. How can I do that? Please suggest me.. Please check this image:
Another questio..Now I think the reverse way but the problem here is the first line and second line you see are part of the same string. I want the first line to be bold and the second line to be in plain font. I am storing this in a dictionary. So my dictionary has a key and the value is a string of names and departments. I am unable to set the font. I tried to create two labels and tried to split the string according to the index and assign it to the labels I created. But, in this case the index keeps on changing as there might be a first name for a contact or there might not be any name.
In this case Prinicipal should be in plain font and name should be in bold
Please see the below image:

Starting OS 6.0 there is a property on the UILabel called attributedText which has NSAttributedString type (Available in iOS 3.2 and later.).
Here it is how I am using it:
NSDictionary *firstNameAttributes = #{ NSFontAttributeName : [UIFont fontWithName:#"Helvetica" size:18.0],
NSStrokeColorAttributeName : [UIColor blackColor]};
NSDictionary *lastNameAttributes = #{NSFontAttributeName : [UIFont fontWithName:#"Helvetica-Bold" size:20.0],
NSStrokeColorAttributeName : [UIColor blackColor]};
NSString* first = ... first name ..;
NSString* last = [NSString stringWithFormat:#" %#",... last name ....];
NSMutableAttributedString * name =
[[NSMutableAttributedString alloc] initWithString:first attributes:firstNameAttributes];
NSMutableAttributedString * lastName =
[[NSMutableAttributedString alloc] initWithString:last attributes:lastNameAttributes];
[name appendAttributedString:lastName];
[[cell textLabel] setAttributedText:name];
See also Introduction to Attributed String Programming Guide.

Since the label that you're showing the name string in defines the formatting and style, if you want to have different styles you need to have a different uilabel for each each style you want. Specifically, you will need a uilabel for the firstname: firstNameLabel.font = [UIFont systemFontOfSize:12]; and one for the lastname: lastNameLabel.font = [UIFont boldSystemFontOfSize:12];.
First place the first name string is the firstNameLabel then call [firstNameLabel sizeToFit] to fit the label text within it. Then use the frame of the firstNameLabel to place the lastNameLabel directly after it.
UILabel * firstNameLabel = [[UILabel alloc] initWithFrame:CGRectMake(10,10,100,25)];
firstNameLabel.tag = firstNameLabelTag //This should be a constant probably
firstNameLabel.font = [UIFont systemFontOfSize:12];
firstNameLabel.text = theStringRepresentingTheFirstName;
[firstNameLabel sizeToFit];
UILabel * lastNameLabel = [[UILabel alloc] initWithFrame:
CGRectMake(10+firstNameLabel.frame.size.width+2, 10, 100, 25)];
lastNameLabel.tag = lastNameLabelTag //This should be a constant probably
lastNameLabel.font = [UIFont boldSystemFontOfSize:12];
lastNameLabel.text = theLastNameString;.
[cell.contentView addSubview:firstNameLabel];
[cell.contentView addSubview:lastNameLabel];
And as for splitting the name string, you're probably pretty limited there. I would split on the first space and assume the first string is the last name (as in your first picture).
The principle case is similar, you need a label for each style that you want to present.

- (IBAction)buttonPressed:(UIButton *)sender {
NSString *title = [sender titleForState:UIControlStateNormal];
NSString *plainText = [NSString stringWithFormat:#"%# button pressed.", title];
NSMutableAttributedString *styledText = [[NSMutableAttributedString alloc] initWithString:plainText];
NSDictionary *attributes = #{ NSFontAttributeName : [UIFont boldSystemFontOfSize:self.statusLabel.font.pointSize]};
NSRange nameRange = [plainText rangeOfString:title];
[styledText setAttributes:attributes range:nameRange];
self.statusLabel.attributedText = styledText;
}

You have to create a custom UITableViewCell. http://icodeblog.com/2009/05/24/custom-uitableviewcell-using-interface-builder/

Related

How to size a symbol image in an attributed string

I have a label where I am trying to put a symbol image at the start of the label and then some text after it. This works, but the symbol image never changes size. It doesn't matter what size I provide in the UIImageSymbolConfiguration, it stays small. If I take this code and put the image in a UIImageView, then the image gets larger as expected. Is there something wrong with anything I am doing here related to the symbol image configuration?
UILabel *label = [[UILabel alloc] init];
NSString *title = #"Some Text";
label.adjustsFontForContentSizeCategory = YES;
NSMutableAttributedString *string = [[NSMutableAttributedString alloc] initWithString:[NSString stringWithFormat:#" %#", title] attributes:#{
NSFontAttributeName: [UIFont preferredFontForTextStyle:UIFontTextStyleBody],
NSForegroundColorAttributeName: [UIColor labelColor]
}];
UIImageSymbolConfiguration *configuration = [UIImageSymbolConfiguration configurationWithFont:[UIFont preferredFontForTextStyle:UIFontTextStyleLargeTitle]];
UIImage *squareImage = [[UIImage systemImageNamed:#"square.fill" withConfiguration:configuration] imageWithTintColor:[UIColor systemBlueColor]];
NSTextAttachment *imageAttachment = [NSTextAttachment textAttachmentWithImage:squareImage];
[string insertAttributedString:[NSAttributedString attributedStringWithAttachment:imageAttachment] atIndex:0];
label.attributedText = string;
I stumbled upon the same issue as I was building a similar feature today. It seems that symbols work slightly differently when embedded in text attachments: it's the font set on the attributed string that determines the size, not the configuration of the symbol itself.
With this in mind, you simply need to make sure the range of the icon in the attributed string has a font set:
UIFont *font = [UIFont preferredFontForTextStyle:UIFontTextStyleBody];
[string addAttribute:NSFontAttributeName value:font range:NSMakeRange(0, 1)];
Note that you'll still need to configure the symbol if you intend to render using a different color. In this case, attributed strings will ignore the NSForegroundColorAttributeName attribute when rendering the symbol (resulting in a blank, zero-width symbol). I suspect this is because symbols have hierarchical colors, but I might be wrong.

WatchKit, AttributedString formatting not working

I am building my first WatchKit App and am having troubles with NSAttributedString formatting as it does not seem to work as I'd expect ;)
This is my code:
UIFont *textFont = [UIFont fontWithName:#"Menlo" size:30];
UIFont *hlFont = [UIFont fontWithName:#"Menlo-Bold" size:30];
NSMutableAttributedString *information = [[NSMutableAttributedString alloc]initWithString:#"ADDED AN ENTRY OF " attributes:#{NSFontAttributeName : textFont}];
NSString *amountString = [NSString stringWithFormat:#"%.2f",(-1)*handler.amount.floatValue];
NSNumber *underline = [NSNumber numberWithInt:NSUnderlineStyleSingle];
NSAttributedString *amount = [[NSAttributedString alloc]initWithString:amountString attributes:#{NSFontAttributeName : hlFont, NSUnderlineStyleAttributeName : underline }];
NSAttributedString *to = [[NSMutableAttributedString alloc]initWithString:#" TO " attributes:#{NSFontAttributeName : textFont}];
NSString *categoryString = handler.category;
NSAttributedString *category = [[NSAttributedString alloc]initWithString:categoryString attributes:#{NSFontAttributeName : hlFont, NSUnderlineStyleAttributeName : underline }];
[information appendAttributedString:amount];
[information appendAttributedString:to];
[information appendAttributedString:category];
[_informationLabel setAttributedText:information];
and this the result:
Expectation
10.00 and Stuff should be underlined and in boldface.
Is there something fundamentally different to how attributed strings work on the watch than on iOS? What am I missing?
read through this: https://developer.apple.com/library/ios/documentation/General/Conceptual/WatchKitProgrammingGuide/TextandLabels.html
Solved it, the problem were the fonts #"Menlo".
By using
UIFont *textFont = [UIFont systemFontOfSize:20];
UIFont *hlFont = [UIFont systemFontOfSize:20];
the formatting with underlines works fine.
I don't believe you can programmatically set a label to be bold, italic, underlined....this has to be done through the actual interface in the storyboard.
According to this link
The attributes you can configure are
text
text color
font
min scale
alignment
lines
a potential workaround is to incorporate multiple labels, and set the ones you need to the right format (bold, underlined)

NSMutableAttributedString UILabel is not retaining its attributes when selected

I am having issues with retaining an attributed NSMutableString. I have a UITableView who's each UITableViewCell has an attributed text. Setting the attributed text is no problem, but upon selection, the UITableViewCell's attributes is lost. This is my code in cellForRowAtIndexPath that sets the attribute:
NSMutableAttributedString *changesStyleString_h = [[NSMutableAttributedString alloc] initWithString:#"Attributes change!" attributes:#{NSFontAttributeName: [UIFont boldSystemFontOfSize:20], NSForegroundColorAttributeName:[UIColor yellowColor]}];
[changesStyleString_h addAttributes:#{ NSUnderlineStyleAttributeName:#(1)} range:NSMakeRange(11, 6)];
cell.mainLabel.attributedText = changesStyleString
might i point out that mainLabel is also a UILabel, no customization there. Any help in the right direction would be greatly appreciated!
I found that I needed to set attributes on the ENTIRE string, or it would do funky things.
NSString* string = #"1 - some string"
NSMutableAttributedString* string = [[NSMutableAttributedString alloc] initWithString:string];
[string setAttributes:#{NSForegroundColorAttributeName: accent, NSFontAttributeName: [UIFont fontWithName:#"HelveticaNeue-Bold" size:13.f]} range:NSMakeRange(0, 1)];
This would cause weird behavior when highlighting the cell.
However, when I did this:
[string setAttributes:#{NSForegroundColorAttributeName: [UIColor blackColor]} range:NSMakeRange(1, [labelTwo length] - 1)];
Everything seemed to work as expected.
Hope that helps!

Attribute for Multiple Text

I have this code and it's working (answer from https://stackoverflow.com/a/3586943/1187014), but I want try modify it a little bit :
NSString *text = #"Forgot password?";
if ([_labelForgotPassword respondsToSelector:#selector(setAttributedText:)])
{
// iOS6 and above : Use NSAttributedStrings
const CGFloat fontSize = 13;
UIFont *boldFont = [UIFont boldSystemFontOfSize:fontSize];
UIFont *regularFont = [UIFont systemFontOfSize:fontSize];
UIColor *foregroundColor = [UIColor whiteColor];
// Create the attributes
NSDictionary *attrs = [NSDictionary dictionaryWithObjectsAndKeys:
boldFont, NSFontAttributeName,
foregroundColor, NSForegroundColorAttributeName, nil];
NSDictionary *subAttrs = [NSDictionary dictionaryWithObjectsAndKeys:
regularFont, NSFontAttributeName, nil];
const NSRange range = NSMakeRange(16,0);
// Create the attributed string (text + attributes)
NSMutableAttributedString *attributedText =
[[NSMutableAttributedString alloc] initWithString:text
attributes:attrs];
[attributedText setAttributes:subAttrs range:range];
// Set it in our UILabel and we are done!
[_labelForgotPassword setAttributedText:attributedText];
} else {
// iOS5 and below
// Here we have some options too. The first one is to do something
// less fancy and show it just as plain text without attributes.
// The second is to use CoreText and get similar results with a bit
// more of code. Interested people please look down the old answer.
// Now I am just being lazy so :p
[_labelForgotPassword setText:text];
}
What if I have multiple text, let's say :
NSString *text1 = #"Forgot password?"; // relates with UILabel _labelForgotPassword
NSString *text2 = #"I agree with terms and condition"; // relates with UILabel _labelTerms
NSString *text3 = #"Your country is not listed yet?"; // relates with UILabel _labelCountry
First method that came into my mind is by having nested IF, but nested IF will be very ugly when I have lots of text which need to be attributed, right?
So, how to create that code into a method so that I can just supply the string, name of _label, range, etc and return the result to specific UILabel. and it's all triggered under viewDidLoad. Not by button pressed, or something else.
thank you.
What i am understanding is you want the same attributed logic to be applied to all labels. You can create a category on UILabel if you want to use it for only UILabels.
Syntax of the category should be something like this:
+(NSMutableAttributedString *) convertToAttributedText: (NSString *) text withFont: (UIFont *) font
{
// write the above logic here
//return the attributed text;
}
You can pass the text1 / text2 / text3 whatever to this api and you will get the attributed text.
label.attributedtext = [NSString convertToAttributedText: text withFont:font];
You can configure this API parameters based on your need.
Hope this helps.

UILabel with different fonts

I have this string that I want to display in a label:
NSString *criticsScore=[NSString stringWithFormat:#"%#\%%",[dict objectForKey:#"critics_score"]];
_criticRating.text=criticsScore;
I want to set a small font for \%% and a large font for [dict objectForKey:#"critics_score"]];
Is this possible?
You Need to use your own control for drawing an NSAttributedString, like TTTAttributedLabel.
NSMutableAttributedString *str = [[NSMutableAttributedString alloc] initWithString:[NSString stringWithFormat:#"Blah1:blah-blah%d. Blah2:-%d%%", [currentCoupon.couponPrice intValue],[currentCoupon.couponDiscountPercent intValue]];
[str addAttribute:NSBackgroundColorAttributeName value:[UIColor clearColor] range:NSMakeRange(0,30)];/// Define Range here and also BackGround color which you want
[str addAttribute:NSForegroundColorAttributeName value:[UIColor blackColor] range:NSMakeRange(0,30)];/// Define Range here and also TextColor color which you want
[str addAttribute:NSFontAttributeName value:[UIFont fontWithName:#"HelveticaNeue-Bold" size:20.0] range:NSMakeRange(20, 10)];
lblWithText.attributedText = str;
Above Code I got From How to use multiple font stylings on a single string inside a label?
Read this post. It is about NSAttributedStrings. I think that is what you need.
You would have to do it with two UILabels. You would set the first label to be all of the text excpt the \%%, and get the size of that label using sizeWithFont: on the text that goes in that label. Then set the second label to start at the end of that label's frame.
So, it would look something like this, changing the coordinates based on where you want the labels:
NSString *criticsScore = [NSString stringWithFormat:#"%#",[dict objectForKey:#"critics_score"]];
NSString *str2 = #"\%%";
UIFont *criticsFont = [UIFont systemFontOfSize:[UIFont systemFontSize]];
UIFont *font2 = [UIFont systemFontOfSize:12.0];
//Get the sizes of each text string based on their font sizes.
CGSize criticsSize = [criticsScore sizeWithFont:criticsFont];
CGSize size2 = [str2 sizeWithFont:font2];
int x = 0;
int y = 0;
//The first label will start at whatever x and y are.
UILabel *label1 = [[UILabel alloc] initWithFrame:CGRectMake(x,y,criticsSize.width,criticsSize.height)];
[label1 setFont:criticsFont];
//Create a second label with the x starting at x+criticsSize.width;
//The y will start at y+criticsSize.height-size2.height, so that it will be aligned with the bottom.
//Change these to align it differently.
UILabel *label2 = [[UILabel alloc] initWithFrame:CGRectMake(x+criticsSize.width,y+criticsSize.height-size2.height,size2.width,size2.height)];
[label2 setFont:font2];
[self.view addSubview:label1];
[self.view addSubview:label2];

Resources