Separate detailTextLabel by an image - ios

Im trying to do this:
The separator needs to dynamically change with the length of the label. This is what i have now
UIImageView *separator = [[UIImageView alloc]initWithImage:[UIImage imageNamed:#"Shuffle"]];
separator.frame = CGRectMake(CGRectGetMaxX(cell.detailTextLabel.frame), CGRectGetHeight(cell.frame) / 2,200, 20);
[cell addSubview:separator];
The image is placed there but it doesn't dynamically change like I thought it would.

If you only want a •, simply set the label text to
cell.detailTextLabel.text = [NSString stringWithFormat:#"ARTIST: %# • LENGTH: %#", artistName, formattedTimeAsString];
Of course you might have to use NSLocalizedString in case you support more than one language

Related

How can I embed UIViews (or, more specifically, UITextAreas) programmatically in-line with Text?

For reasons of reusability, I'm interested in finding a way to programmatically add text and custom UITextFields to a view in an efficient manner, similar to how you can combine strings using NSString's stringWithFormat: and then assign the result to a UILabel's text attribute. Ideally, with 2-3 statements I could write text and include my UITextField Objects in a string, and get an automatically text-wrapped, nicely formatted UIView that I can embed directly into my view. Basically, it would function like a UILabel with the ability to add UIView objects. For an example of the output this image would be a combination of both text and underlined UITextFields:
If this exists, it would allow me to reuse a single UITableViewCell subclass rather than having 5-6 xibs and 3-4 subclasses. I've searched about 2 hours with no real luck for a pre-existing solution, so has anyone ever encountered this problem before and used or released a library to handle this, or is there a simple solution I'm overlooking?
Thank you!
you can use CSLinearLayoutView (https://github.com/scalessec/CSLinearLayoutView)
and create a class
#implementation LabledView
+ (UIView*)create :(CGRect) frame view:(UIView*) view labelTitle:(NSString*)labelTitle viewLinearLayoutMakePadding :(CSLinearLayoutItemPadding)viewLinearLayoutMakePadding labelLinearLayoutMakePadding :(CSLinearLayoutItemPadding)labelLinearLayoutMakePadding font:(UIFont*)font textColor:(UIColor*)textColor
{
CSLinearLayoutView *container = [[CSLinearLayoutView alloc] initWithFrame:frame];
container.orientation = CSLinearLayoutViewOrientationHorizontal;
UILabel *label = [[UILabel alloc] init];
label.textColor = textColor;
[label setText:labelTitle];
[label setFont:font];
[label sizeToFit];
CSLinearLayoutItem *itemLabel = [CSLinearLayoutItem layoutItemForView:label];
itemLabel.padding = labelLinearLayoutMakePadding;
CSLinearLayoutItem *itemView = [CSLinearLayoutItem layoutItemForView:view];
itemView.padding = viewLinearLayoutMakePadding;
[container addItem:itemLabel];
[container addItem:itemView];
return container;
}
example :
UITextField *textField = [[UITextField alloc] initWithFrame:CGRectMake(0, 0, 260, 40)];
UIView *customView = [LabledView create:CGRectMake(0, 0, 280, 40) view:textField
labelTitle:#"your label" viewLinearLayoutMakePadding:CSLinearLayoutMakePadding(0, 10, 0, 0)
labelLinearLayoutMakePadding:CSLinearLayoutMakePadding(10, 0, 0, 0)
font:[UIFont fontWithName:#"Helvetica" size:12] textColor:[UIColor blackColor]];
You can underline specific ranges of a string with NSAtttibutedString. You can setAttributedString to UILabel in ios6... So that's the way I'd do it, then it can indeed be in a single label with the desired parts underlined (or in a different font/colour/etc) only. Be careful when you look into attributed string, it's attributes dictionary uses different keys for working with UIKit (these are the ones you need here) to what it uses with CoreText

How do I put an RTLabel on an iOS image?

I am trying to use https://github.com/honcheng/RTLabel to get a rich text label, but my immediate goal is to display "Hello, world!"
My code is:
UIImageView *noteImage = [[UIImageView alloc] initWithFrame:bounds];
noteImage.image = image;
[self.view addSubview:noteImage];
CJSHCardView *noteView = [[CJSHCardView alloc] initWithImage:image];
[noteView setFrame:CGRectMake(100 * i, 20, 100 * scale, 100 * scale)];
noteView.transform = CGAffineTransformScale(noteView.transform, scale_x, scale_y);
NSString *text = #"Hello, world!";
RTLabel *label = [[RTLabel alloc] initWithFrame:CGRectMake(100 * i, 20, 100 * scale, 100 * scale)];
[noteImage addSubview:label];
[label setText:text];
I tried both noteImage and noteView in the second-to-last line. The rectangle has the same dimensions as the original image, which is displaying correctly. However, none of the approaches I've tried seem apt to display a label on top of the noteImage / noteView as backgrounds.
What is an appropriate way to get a label (preferably one that supports rich text) to display on top of an image meant to serve as background for it?
iOS 7's UILabel supports attributed strings, so unless you need to target an earlier version, I suggest simply building your UI in interface builder and setting the attributed text as needed in your code.

NSAttributeString Wrapping issue

I am trying to set attribute text to a label. The attributes seems to be a working the font as well as the color.
Only issue I am facing is the wrapping of lines. The Size of the UILabel is (200,300) with numberofLines=0. So with this it should wrap the lines, but it is not happening so.
NSMutableString *title=[[NSMutableString alloc] init];
NSRange range1;
NSRange range2;
NSRange range3;
NSString *str1=#"ABCD EFGHI klm";
[title appendString:str1];
range1=NSMakeRange(0, str1.length);
NSString *str2=#"PQRSSSS ";
[title appendString:str2];
range2=NSMakeRange(range1.length, str2.length);
NSString *str3=#"1235 2347 989034 023490234 90";
[title appendString:str3];
range3=NSMakeRange(range2.location+range2.length, str3.length);
NSMutableAttributedString *attributeText=[[NSMutableAttributedString alloc] initWithString:title];
[attributeText setAttributes:[NSDictionary dictionaryWithObjectsAndKeys:color1,NSForegroundColorAttributeName,[self getStlylishItalicFont:13.0] ,NSFontAttributeName,nil] range:range1];
[attributeText setAttributes:[NSDictionary dictionaryWithObjectsAndKeys:color2,NSForegroundColorAttributeName,[self getStylishFont:13.0] ,NSFontAttributeName,nil] range:range2];
[attributeText setAttributes:[NSDictionary dictionaryWithObjectsAndKeys:color3,NSForegroundColorAttributeName,[self getStylishBoldFont:13.0] ,NSFontAttributeName,nil] range:range3];
self.myTextLabel.attributedText=attributeText;
UILabel is displayed like this, even though the height is 300.
ABCD EFGHI klm PQRSSSS 1235 234 ...
What you need is the NSParagraphStyle attribute :
NSMutableParagraphStyle *paragraphStyle = [[NSMutableParagraphStyle alloc] init];
paragraphStyle.lineBreakMode = NSLineBreakByWordWrapping;
paragraphStyle.alignment = NSTextAlignmentLeft;
paragraphStyle.lineSpacing = 1;
//Now add this to your attributes dictionary for the key NSParagraphStyleAttributeName eg,
#{NSParagraphStyleAttributeName:paragraphStyle,...}
On an unrelated note you know its better to create dictionaries in the modern Objective-c format. Whenever I don't, my mentor get's angry. That would look something like this :
[attributeText setAttributes:#{NSForegroundColorAttributeName:color1, NSFontAttributeName:[self getStlylishItalicFont:13.0], NSParagraphStyleAttributeName:paragraphStyle, }];
//The trailing comma in the dictionary definition is not at typo it is important.
Make sure you set your UILabel's line break mode attribute to the one you desired like so:
UILabel.lineBreakMode = NSLineBreakByWordWrapping;
Or if you are using Interface Builder, you can do it there.
Why can't you set the numberoflines to 1.Because wrapping makes sense but number of lines 0 doesnt make sense.. and also you have to set proper frame for label.
I think so u are facing the problem with the uilabel increasing the height , If u need the multiple lines in label then u have to give the property of havin numberoflines=0; after that u have to resize the label frame according to the size of text u are giving to the label.
Please check the below code i may be useful to u,
NSString *someText = [NSString stringWithFormat:#"%#",[[arrFulldetails objectAtIndex:indexPath.row]valueForKey:#"MessageText"]];
CGSize constraintSize;
constraintSize.width = 300.0f;
constraintSize.height =100000;
CGSize stringSize =[someText sizeWithFont: [UIFont boldSystemFontOfSize: 17] constrainedToSize: constraintSize lineBreakMode: UILineBreakModeWordWrap];
CGRect rect ;
rect = CGRectMake(10, 150, 210, 20+stringSize.height);
along with setting:
self.myTextLabel.lineBreakMode = NSLineBreakByWordWrapping;
self.myTextLabel.numberOfLines = 0;
You might also need to set your label's layout constraints to it's superview. I ran into this when I neglected to pin my label's trailing constraint to the my label's superview.

iOS - Using TTTAttributedLabel to set two color text

I'm creating iOS app that has a label. I want to set two colors. One for first part and other color for remaining part.
I've seen some messages in Stack over flow that, TTTAttributedLabel has the ability to set more than one color to text. My text will be like "ABC > def". For "ABC", i want to set brown color and for "def", i want to set white color.
How can I set that?
NSString* text = #"ABC > def";
attributedLabel = [[[TTTAttributedLabel alloc] initWithFrame:frame] autorelease];
attributedLabel.numberOfLines = 0;
attributedLabel.lineBreakMode = UILineBreakModeWordWrap;
attributedLabel.fontColor = [UIColor brownColor];
[attributedLabel setText:text afterInheritingLabelAttributesAndConfiguringWithBlock:^(NSMutableAttributedString *mutableAttributedString) {
NSRange whiteRange = [text rangeOfString:#"def"];
if (whiteRange.location != NSNotFound) {
// Core Text APIs use C functions without a direct bridge to UIFont. See Apple's "Core Text Programming Guide" to learn how to configure string attributes.
[mutableAttributedString addAttribute:(NSString *)kCTForegroundColorAttributeName value:(id)[UIColor whiteColor].CGColor range:whiteRange];
}
return mutableAttributedString;
}];
[attributedLabel sizeToFit]; //this may not be needed if the frame provided is large enough
That searches for "def" in your string and sets the foreground color of the text to white for that range. Hope this helps. I only just learned this yesterday. Came across your question whilst trying to figure it out for myself.
You could use TTTRegexAttributedLabel available at : https://github.com/kwent/TTTRegexAttributedLabel. (TTTAttributedLabel based but more easier to use with regular expressions)
//SET FONT ONLY ON FIRST MATCH REGEX
TTTRegexAttributedLabel *label = [[TTTRegexAttributedLabel alloc] init];
label.textColor = [UIColor whiteColor];
NSString *s = #"ABC > def";
[self.label setText:s withFirstMatchRegex:#"^[a-zA-Z ]*>"
withFont:[UIFont systemFontOfSize:12]
withColor:[UIColor brownColor]];

How to add line break for UILabel?

Let see that I have a string look like this:
NSString *longStr = #"AAAAA\nBBBBB\nCCCCC";
How do I make it so that the UILabel display the message like this
AAAAA
BBBBB
CCCCC
I don't think \n is recognized by UILabel, so is there anything that I can put inside NSString so that UILabel knows that it has to create a line break there?
Use \n as you are using in your string.
Set numberOfLines to 0 to allow for any number of lines.
label.numberOfLines = 0;
Update the label frame to match the size of the text using sizeWithFont:. If you don't do this your text will be vertically centered or cut off.
UILabel *label; // set frame to largest size you want
...
CGSize labelSize = [label.text sizeWithFont:label.font
constrainedToSize:label.frame.size
lineBreakMode:label.lineBreakMode];
label.frame = CGRectMake(
label.frame.origin.x, label.frame.origin.y,
label.frame.size.width, labelSize.height);
Update : Replacement for deprecatedsizeWithFont:constrainedToSize:lineBreakMode:
Reference, Replacement for deprecated sizeWithFont: in iOS 7?
CGSize labelSize = [label.text sizeWithAttributes:#{NSFontAttributeName:label.font}];
label.frame = CGRectMake(
label.frame.origin.x, label.frame.origin.y,
label.frame.size.width, labelSize.height);
Use option-return when typing in the little box in Interface Builder to insert a line feed (\n). In Interface Builder's Label attributes, set # Lines = 0.
Select the label and then change Lines property to 0 like in the above image, and then use \n in your string for line break.
In the interface builder, you can use Ctrl + Enter to insert /n to the position you want.
This way could implement the following situation
aaaaaaaaaa
If you read a string from an XML file, the line break \n in this string will not work in UILabel text. The \n is not parsed to a line break.
Here is a little trick to solve this issue:
// correct next line \n in string from XML file
NSString *myNewLineStr = #"\n";
myLabelText = [myLabelText stringByReplacingOccurrencesOfString:#"\\n" withString:myNewLineStr];
myLabel.text = myLabelText;
So you have to replace the unparsed \n part in your string by a parsed \n in a hardcoded NSString.
Here are my other label settings:
myLabel.numberOfLines = 0;
myLabel.backgroundColor = [UIColor lightGrayColor];
myLabel.textColor = [UIColor redColor];
myLabel.font = [UIFont fontWithName:#"Helvetica Neue" size:14.0];
myLabel.textAlignment = UITextAlignmentCenter;
Most important is to set numberOfLines to 0 (= unlimited number of lines in label).
No idea why Apple has chosen to not parse \n in strings read from XML?
You have to set the numberOfLines property on the UILabel. The default is 1, if you set it to 0 it will remove all limits.
Important to note it's \n (backslash) rather than /n.
For those of you who want an easy solution, do the following in the text Label input box in Interface Builder:
Make sure your number of lines is set to 0.
Alt + Enter
(Alt is your option key)
Cheers!
In Swift 2.2, > iOS 8
I've set Lines = 0 on Storyboard, under Attribute Inspector and linked a referencing outlet to the label. Then use in controller like this:
#IBOutlet weak var listLabel: UILabel!
override func viewDidLoad() {
...
listLabel.text = "Line 1\nLine 2\nLine 3\nLine 4\nLine 5\nLine 6\nLine 7\nLine 8"
}
In xCode 11, Swift 5 the \n works fine, try the below code:
textlabel.numberOfLines = 0
textlabel.text = "This is line one \n This is line two \n This is line three"
Just do it like this
NSString * strCheck = #"A\nB";
strCheck = [strCheck stringByReplacingOccurrencesOfString:#"\\n" withString:#"\n"]; //This is to prevent for fetching string from plist or data structure
label.numberOfLines = 0;
label.lineBreakMode = NSLineBreakByWordWrapping;
label.text = strCheck;
// DO not forget to set numberOfLines to zero
UILabel* locationTitle = [[UILabel alloc] initWithFrame:CGRectMake(5, 30, 230, 40)];
locationTitle.font = [UIFont systemFontOfSize:13.0];
locationTitle.numberOfLines = 0;
locationTitle.text = [NSString stringWithFormat:#"Eaton industries pvt. Ltd \nUK Apr 12"];
[cell addSubview:locationTitle];
If your using a UILabel you have to remember that the default setting is 1 line, so it does not matter how many breaks you add (\n or \r), you need to make sure it is set to more than one line so it could be allowed to append more lines.
One alternative is to use UITextView which is really meant for multilines.
You can easily achieve this in XCode attribute section of the UILabel, see screenshot:
On Xcode 6, you can just use \n even inside a string when using word wrap. It will work. So for example:
UILabel *label = [[UILabel alloc]initWithFrame:CGRectMake(0, 100, screenRect.size.width, 50)];
label.textAlignment = NSTextAlignmentCenter;
label.text = #"This will be on the first line\nfollowed by a line under it.";
label.lineBreakMode = UILineBreakModeWordWrap;
label.numberOfLines = 0;
In my case also \n was not working, I fixed issue by keeping number of lines to 0 and copied and pasted the text with new line itself for example instead of Hello \n World i pasted
Hello
World
in the interface builder.
Just using label.numberOfLines = 0;
textLabel.text = #"\nAAAAA\nBBBBB\nCCCCC";
textLabel.numberOfLines = 3; \\As you want - AAAAA\nBBBBB\nCCCCC
textLabel.lineBreakMode = UILineBreakModeWordWrap;
NSLog(#"The textLabel text is - %#",textLabel.text);
For anyone else that might have trouble with sizeWithFont:constrainedToSize:lineBreakMode: or anyone switching to ios8 (the method is deprecated as of ios7), I adjusted my height by using sizeToFit instead.
UILabel *label;
label.numberOfLines = 0;
// Setup label with desired settings
...
[label sizeToFit];
label.frame = CGRectMake(label.frame.origin.x, // Or use any desired origin
label.frame.origin.y,
label.frame.size.width, // Or use any desired width
label.frame.size.height);
NSCharacterSet *charSet = NSCharacterSet.newlineCharacterSet;
NSString *formatted = [[unformatted componentsSeparatedByCharactersInSet:charSet] componentsJoinedByString:#"\n"];
It seems wrong to me to change the label frame sizes especially when using autolayout. Using the appendFormat method seems more appropriate. Here is my example:
NSMutableString *list = [[NSMutableString alloc] init];
NSArray *textArray = #[#"AAAA", #"BBBB"];
for (NSString *string in textArray) {
[list appendFormat:#"%#\n", string.mutableCopy];
}
self.label.text = list;
self.label.numberOfLines = 0;
If you set your UILable properties from Plain to Attributed...the UILabel will hold multiline text no matter how many paragraphs for along as your UILabel height and width are set to fit the screen area you want to display the text in.
I have faced same problem, and here is, how i solved the problem. Hope this will be helpful for someone.
// Swift 2
lblMultiline.lineBreakMode = .ByWordWrapping // or use NSLineBreakMode.ByWordWrapping
lblMultiline.numberOfLines = 0
// Objective-C
lblMultiline.lineBreakMode = NSLineBreakByWordWrapping;
lblMultiline.numberOfLines = 0;
// C# (Xamarin.iOS)
lblMultiline.LineBreakMode = UILineBreakMode.WordWrap;
lblMultiline.Lines = 0;
on Xcode 6, I can use \n without problem on swift programmatically

Resources