UITextView clear attributedText before setting new text - ios

Hi I am trying to replace the attributedText of a UITextView subclass. I want to change the coloring of the text. to do so the following code is used:
AMR_ANSIEscapeHelper *ansiEscapeHelper = [[AMR_ANSIEscapeHelper alloc] init];
[ansiEscapeHelper setDefaultStringColor:[receiveView.highlightColor objectForKey:#"text"]];
NSMutableAttributedString *resultString = [receiveView.attributedText copy];
[receiveView setAttributedText:[ansiEscapeHelper attributedStringWithANSIEscapedString:[ansiEscapeHelper ansiEscapedStringWithAttributedString:resultString]]];
Problem is: The text does not get replaced; it just seem to add another layer of text, making the text color very strange. Do i need to assert some clearing before i set the Attributed Text the second time?
Here is how it looks: (The text should not be black, dark green and red)
)

The subclass RegexHighlightView contains another method of coloring the text, therefore multiple colors are painted to the fonts!

Related

Xcode UILabel bug? Line spacing cropping text with a UILabel

I have some designs I'm following for an iOS project. The font used is Avenir with relatively tight line spacing.
Some of these labels will have dynamic text, so I can't just make the label's size larger since the size should be determined by the content.
By default line spacing for a UILabel ends up pretty large.
If I adjust the Line Height Multiple or the Max Height, the text along the top ends up cropped.
It should behave like this (Affinity Designer)...
Is there a way to handle this?
Thanks for your help!
This works for me. By adding
minimumLineHeight
let string = NSMutableAttributedString(string: venue.name)
let style = NSMutableParagraphStyle()
style.lineHeightMultiple = 0.68
style.minimumLineHeight = nameLabel.font.lineHeight
string.addAttribute(NSAttributedString.Key.paragraphStyle,
value: style,
range: NSMakeRange(0, venue.name.count))
nameLabel.attributedText = string
Unfortunately the UILabel has several quirks when it comes to vertical adjustments. A somewhat hacky solution is to move the baseline of the first line down as needed. Depending on if your string ends with a newline, and the amount of tightening you do, you might need to add one or two extra newlines also, otherwise the rendering engine will clip the last line.
The code snippet assumes that self.label already has an attributed string assigned to it, and that it has line separator character 0x2028 between the lines. This is usually true when entering multi-line text in IB.
// 0x2028 is the unicode line separator character
// Use \n instead if it is what you have
// or calculate the length of the first line in some other way
NSInteger lengthOfFirstLine = [self.label.text componentsSeparatedByString:#"\u2028"][0].length;
NSMutableAttributedString *s = [[NSMutableAttributedString alloc] initWithAttributedString:self.label.attributedText];
// Add two more blank lines so that the rendering engine doesn't clip the last line
[s appendAttributedString:[[NSAttributedString alloc] initWithString:#"\n\n"]];
// Move the baseline offset for the first line down
// the other lines will adjust to this
// 50 is a value you will have to find what looks best for you
[s addAttribute:NSBaselineOffsetAttributeName value:#(-50) range:NSMakeRange(0, lengthOfFirstLine)];
self.label.attributedText = s;

How can I add a custom view to an attributed string or text view?

I'm trying to get a custom view in an attributed string to be displayed on a textView. I am able to add an image with an NSTextAttachment, but it isn't what I want. I have a custom view that supports Gif's and Animated PNGs that I'd like to display between text.
Example:
text text text [customView] text [customView] text. <- In text view, preferably in attributed string
I would love some guidance as to where I should search specifically. So far I've seen related issues...
Subclass NSTextAttachment: How to subclass NSTextAttachment?
Use NSTextAttachmentContainer..?
NSTextAttachmentCell - Only OSX
Do manipulation in the text view
First, use NSAttributedString or NSMutableAttributedString to show your RichText in subviews (such as UITextView/UILabel)
Then, use NSTextAttachment to replace your image-script in text.
NSString *egText = #"hello [this_is_an_img_script]";
NSMutableAttributedString * destStr = [[NSMutableAttributedString alloc] initWithString:egText];
NSTextAttachment *attachment = [[NSTextAttachment alloc] initWithData:nil ofType:nil];
attachment.image = [UIImage imageNamed:[this_is_an_img_script]];
NSAttributedString *textAttachmentString = [NSAttributedString attributedStringWithAttachment:attachment]; //make your image to an attributedString
[destStr replaceCharactersInRange:range withAttributedString:textAttachmentString];
at last: [YourLabel(or YourTextView) setAttributedString:destStr];
BTW: if you use the YYkit for the RichText, you cannot use the YYAttachMentString to replace NSAttachMentString, these are different things, the UITextView(UILabel) cannot load the YYAttachMentString.
I'm looking for some way to show my gifs with the UITextView (because YYKit cannot load and preview netimage with a url, YYKit always show empty which should be a netImage, cripes!)

iOS Swift Wrapping Text Around Image

I have a UILabel that will contain various lengths of text. I need to place an image in the upper left corner of the text and have the text wrap around it. How can I do this? All I could find was using a UITextView which I don't want to use since it's static text.
This is a perfectly reasonable use of a UITextView. Your reasons for hesitation to use it are unclear. You can make the UITextView non-editable and non-selectable; the user will not know that it is a UITextView as opposed to to a UILabel.
If you don't like that solution, then what I would do is use, instead of a UILabel, a custom view that draws the text. You can draw the text with Text Kit and thus you can take complete charge of how the text draws. In particular, you can cause it to wrap however you like, including not drawing the text in the corner (exclusion path on the text container).
You can achieve this using NSTextAttachment and attributed text.
NSMutableAttributedString *myText = [[NSMutableAttributedString alloc] initWithString:labelStr];
NSTextAttachment *attachment = [[NSTextAttachment alloc] init]
attachment.image = yourImage;
NSAttributedString *attachmentLock = [NSAttributedString attributedStringWithAttachment:attachment];
NSMutableAttributedString *lockString = [[NSMutableAttributedString alloc] initWithAttributedString:myText];
//set your image range within the text. modify it till you get it right.
NSRange range = NSMakeRange(0,[labelStr length]);
[lockString replaceCharactersInRange:NSMakeRange(range.location, 1) withAttributedString:attachmentLock];
yourLabel.attributedText = lockString;

How can I horizontally center a single line of text in UITextView?

I have a UITextView which displays a fair amount of text. I need to horizontally center some, but not all, of the lines of text in the text view.
I've tried setting the NSParagraphStyleAttributeName with an NSParagraphStyle instance whose alignment property is NSTextAlignmentCenter on the range of the line to be centered. I'm also setting the font so the centered line is bold. When I do this using the code below, the relevant line is bolded, but remains left aligned.
if (shouldCenterLine) {
NSMutableParagraphStyle *centerStyle = [[NSMutableParagraphStyle alloc] init];
centerStyle.alignment = NSTextAlignmentCenter;
NSDictionary *attributes = #{NSParagraphStyleAttributeName : centerStyle,
NSFontAttributeName : boldFont};
[attributedString setAttributes:attributes range:lineRange];
}
If I apply this same paragraph style attribute to the entire contents of the text view, the text ends up centered as expected.
Is it possible to convince UITextView to center specific subranges of its text? Is the only solution to move to a UIWebView rendering generated HTML? Note that this is for an app still supporting iOS 6, so unfortunately I'm not able to use Text Kit.
Try including the line returns around the the line that you'd like centered within the range that you apply the style to.

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.

Resources