Having issue with CTFontRef - iphone

Hi I need using a couple of fonts with CTFontRef for an iPad application , I need use this method because my font is not English . so I found this code from this site
but compiler gives me some error :
CTFontRef font = CTFontCreateWithName(CFSTR("myfont"), 12,NULL);
NSMutableAttributedStringRef attrString = [[NSMutableAttributedString alloc] initWithString:textView.text];
[attrString addAttribute:(NSString*)kCTFontAttributeName
value:(id)font
range: NSMakeRange(0, textView.text.length)];
I would be grateful if you help me to solve the problem

Just see this. may be useful for you :
CTFontRef font = CTFontCreateWithName(CFSTR("GujaratiSangamMN-Bold"),12.0f, NULL);
NSDictionary *attrs = [NSDictionary dictionaryWithObjectsAndKeys:
(id)font, kCTFontAttributeName,
nil];
NSAttributedString *attrString = [[NSAttributedString alloc] initWithString:textView.text
attributes:attrs];

The problem with your code is with the NSMutableAttributedStringRef. Use an NSMutableAttributedString instead:
NSString *myString = #"Hello World!!";
CTFontRef futura = CTFontCreateWithName( CFSTR("Futura"), 24.0, NULL);
NSMutableAttributedString *attString = [[NSMutableAttributedString alloc]
initWithString:myString];
[attString addAttribute:(NSString *)kCTFontAttributeName
value:(id)futura
range:NSMakeRange(0, 4)];

Related

UILabel is not displaying its correct value even if it is giving the newly assigned value in console

I have a UILabel which is displayed as a question. Its successfully displaying the question text which has been assigned to it programmatically. But later according to one if else condition, I have to change text in the label.Specifically I want to display an asterik(*) mark at the end of the string if that is a mandatory question.The * should be in red color and rest of the text should be in black.But it displays only the question not the * mark.If I try to print the questLabel.text it is giving the question with * mark at the end.Here is the code that I am trying
questText = questLabel.text;
questText = [questText stringByAppendingString:#"✶"];
NSMutableAttributedString * str = [[NSMutableAttributedString alloc] initWithString:questText];
NSMutableAttributedString *text =
[[NSMutableAttributedString alloc]
initWithAttributedString: str];
int length = (int)text.length;
[text addAttribute:NSForegroundColorAttributeName
value:[UIColor redColor]
range:NSMakeRange(length-1, 1)];
[questLabel setAttributedText: text];
If I try to print the value of questLabel.attributedText :
Question{
}✶{
NSColor = "UIDeviceRGBColorSpace 1 0 0 1";
}
And the value for questLabel.text is :Question✶
Please help me out with this..Thanks in advance..
You should change your code to this.
NSString *questText = questLabel.text;
questText = [questText stringByAppendingString:#"✶"];
NSMutableAttributedString *text =
[[NSMutableAttributedString alloc] initWithString:questText];
int length = (int)text.length;
[text addAttribute:NSForegroundColorAttributeName value:[UIColor blackColor] range:NSMakeRange(0, length-1)];
[text addAttribute:NSForegroundColorAttributeName value:[UIColor redColor] range:NSMakeRange(length-1, 1)];
[questLabel setAttributedText: text];
You can also try this
NSMutableAttributedString *string = [[NSMutableAttributedString alloc] initWithString:self.questLabel.text attributes:#{NSForegroundColorAttributeName:[UIColor blackColor]}];
NSMutableAttributedString *starString = [[NSMutableAttributedString alloc] initWithString:#"✶" attributes:#{NSForegroundColorAttributeName:[UIColor redColor]}];
[string appendAttributedString:starString];
[self.questLabel setAttributedText:string];

Letter spacing in IOS 6

I would like to know that how can i set Letter spacing in iOS 6? It's working fine for iOS 7 using below code, now need to do for iOS 6 :
NSMutableAttributedString *attributedString = [[NSMutableAttributedString alloc] initWithString:[arraySettings objectAtIndex:indexPath.row]];
float spacing = 0.2f;
[attributedString addAttribute:NSKernAttributeName
value:#(spacing)
range:NSMakeRange(0, [[arraySettings objectAtIndex:indexPath.row] length])];
cell.textLabel.attributedText = attributedString;
error image after crashing above code in iOS 6 :
Thanks.
My guess is that you have some sort of memory related issue with your arraySettings ivar.
I've slightly modified the code you provided in a test project and it seemed to work fine for me when run on both the iOS 6.1 and 7.1 simulator.
Could you try using the following code and see what happens?
NSString *string = [[arraySettings objectAtIndex:indexPath.row] copy];
NSMutableAttributedString *attributedString = [[NSMutableAttributedString alloc] initWithString:string];
CGFloat spacing = 0.2f;
[attributedString addAttribute:NSKernAttributeName value:#(spacing) range:NSMakeRange(0, string.length)];
cell.textLabel.attributedText = attributedString;
If you are still getting a crash then you will need to provide more info about what you are doing with the arraySettings object.
I had to do same thing in one of my project and used this same code. It was working fine for me.
NSMutableAttributedString *attributedString =
[[NSMutableAttributedString alloc] initWithString:#"hi this is my testing string"];
float spacing = 1.0f;
[attributedString addAttribute:NSKernAttributeName
value:#(spacing)
range:NSMakeRange(0, [#"hi this is my testing string" length])];
mylbl.attributedText = attributedString;

Core Foundation Memory Leak

For this bit of code:
CTFontRef font = CTFontCreateWithName((__bridge CFStringRef)self.fontName, self.paragraphSpacing, NULL);
[self.text insertAttributedString: [[NSAttributedString alloc] initWithString: #" \n" attributes: [NSDictionary dictionaryWithObjectsAndKeys: (__bridge id)font, (id)kCTFontAttributeName, (id)[self paragraphStyle], (id)kCTParagraphStyleAttributeName, nil]] atIndex: 0];
[self.text appendAttributedString: [[NSAttributedString alloc] initWithString: #"\n " attributes: [NSDictionary dictionaryWithObjectsAndKeys: (__bridge id)font, (id)kCTFontAttributeName, (id)[self paragraphStyle], (id)kCTParagraphStyleAttributeName, nil]]];
CFRelease(font);
For the middle two lines am getting "potential leak of an object" yet I'm not really seeing the problem.
I should mention that the static analyzer is pointing at [self paragraphStyle] which is:
- (CTParagraphStyleRef) paragraphStyle
{
CTTextAlignment alignment = self.alignment;
CGFloat lineSpacing = self.lineSpacing;
CGFloat firstLineHeadIndent = self.indent;
CGFloat headIndent = self.indent;
CGFloat tailIndent = -self.indent;
CTParagraphStyleSetting paragraphSettings[] =
{
{kCTParagraphStyleSpecifierAlignment, sizeof(alignment), &alignment},
{kCTParagraphStyleSpecifierLineSpacing, sizeof(lineSpacing), &lineSpacing},
{kCTParagraphStyleSpecifierFirstLineHeadIndent, sizeof(firstLineHeadIndent), &firstLineHeadIndent},
{kCTParagraphStyleSpecifierHeadIndent, sizeof(headIndent), &headIndent},
{kCTParagraphStyleSpecifierTailIndent, sizeof(tailIndent), &tailIndent},
};
return CTParagraphStyleCreate(paragraphSettings, 5);
}
after the edit it becomes clear. you method is CREATING paragrah styles and those are never released
a) the method should be renamed so it becomes clearer that it creates new objects
b) you have to CFRelease them
what would be enough:
CTFontRef font = CTFontCreateWithName((__bridge CFStringRef)self.fontName, self.paragraphSpacing, NULL);
assert(font); //may not be nil
CTParagraphStyleRef paragraph = self.paragraphStyle;
assert(paragraph); //may not be nil
[self.text insertAttributedString: [[NSAttributedString alloc] initWithString: #" \n" attributes: [NSDictionary dictionaryWithObjectsAndKeys: (__bridge id)font, (id)kCTFontAttributeName, (id)paragraph, (id)kCTParagraphStyleAttributeName, nil]] atIndex: 0];
[self.text appendAttributedString: [[NSAttributedString alloc] initWithString: #"\n " attributes: [NSDictionary dictionaryWithObjectsAndKeys: (__bridge id)font, (id)kCTFontAttributeName, (id)paragraph, (id)kCTParagraphStyleAttributeName, nil]]];
CFRelease(font);
CFRelease(paragraph); //!!!
*the asserts are bonus

Color String in the Label

If I want to create some strings having format as these:
the string is the text property of a label.
some characters in this string have color different from other characters.
some characters are underlined and have a link, and when I hit the characters, and other views pop up.
Could somebody tell me how can I realize this effect?
If you support iOS < 6, better use 3rd party component e.g. TTTAttributedLabel. Else use attributedText property of UILabel.
NSDictionary *colors = [[NSDictionary alloc] initWithObjectsAndKeys: [UIColor blueColor], #"Hyd", [UIColor brownColor], #"Bang", [UIColor orangeColor], #"Delhi", [UIColor yellowColor], #"Gujarat", nil];
NSMutableAttributedString *attributeString = [[NSMutableAttributedString alloc] initWithString:#""];
for (NSString *word in colors) {
UIColor *color = [colors objectForKey:word];
NSDictionary *attributes = [NSDictionary dictionaryWithObject:color forKey:NSForegroundColorAttributeName];
NSAttributedString *substring = [[NSAttributedString alloc] initWithString:word attributes:attributes];
[attributeString appendAttributedString:substring];
}

Combining Attributed Strings

As an example, say I had an array of 10 NSAttributedStrings, what is the best method for combining them all into one string? I know of the appendAttributedString method, but this only allows for one to be combined at a time, meaning a loop is needed.
Or is there any need to combine them if theyre just going into a textview - just have a loop to add them to that view? Im just trying to get my head around how a lot of text in different formats is added to a textview!
Please, try:
NSRange range = NSMakeRange(0, 1);
NSString *space = #" ";
NSMutableAttributedString *attSpace = [[NSMutableAttributedString alloc] initWithString:space];
[attSpace addAttribute:NSForegroundColorAttributeName value:[UIColor grayColor] range:range];
[attSpace addAttribute:NSFontAttributeName value:[UIFont fontWithName:#"HelveticaNeue-Light"
size:11.f] range:range];
range = NSMakeRange(0, [string1 length]);
NSMutableAttributedString *att1 = [[NSMutableAttributedString alloc] initWithString:string1];
[att1 addAttribute:NSForegroundColorAttributeName value:[UIColor grayColor] range:range];
[att1 addAttribute:NSFontAttributeName value:[UIFont fontWithName:#"HelveticaNeue-Light"
size:11.f] range:range];
range = NSMakeRange(0, [string2 length]);
NSMutableAttributedString *att2 = [[NSMutableAttributedString alloc] initWithString:string2];
[att2 addAttribute:NSForegroundColorAttributeName value:[UIColor grayColor] range:range];
[att2 addAttribute:NSFontAttributeName value:[UIFont fontWithName:#"HelveticaNeue-Light"
size:11.f] range:range];
[att1 appendAttributedString:attSpace];
[att1 appendAttributedString:att2];
I'll share a kind of complex combination I've made mixing plain, striked and bold text in a resultant attributed string over the title of UIButton.
// Monthly button
NSMutableAttributedString *strikedOutPrice = [[NSMutableAttributedString alloc] initWithString:#"6,99"];
[strikedOutPrice setAttributes:#{ NSForegroundColorAttributeName : [UIColor whiteColor], NSStrikethroughStyleAttributeName: #2 } range:NSMakeRange(0, [strikedOutPrice length])];
NSMutableAttributedString *boldPrice = [[NSMutableAttributedString alloc] initWithString:#"4,99"];
[boldPrice setAttributes:#{ NSFontAttributeName:[UIFont boldSystemFontOfSize:16.0f], NSForegroundColorAttributeName : [UIColor whiteColor] } range:NSMakeRange(0, [boldPrice length])];
NSMutableAttributedString* titleStringMonthly = [[NSMutableAttributedString alloc] initWithString:[NSString stringWithFormat:#"%# %# %#" , [[LocalizationSystem sharedLocalSystem] localizedStringForKey:#"1 Month for" value:#"1 Mes por"], #"6,99", #"4,99"]];
[titleStringMonthly setAttributes:#{ NSForegroundColorAttributeName : [UIColor whiteColor] } range:NSMakeRange(0, [titleStringMonthly length])];
NSString *language = [Utils getAppLanguage];
if([language isEqualToString:#"es"])
{
[titleStringMonthly replaceCharactersInRange:NSMakeRange(10, 4) withAttributedString:strikedOutPrice];
[titleStringMonthly replaceCharactersInRange:NSMakeRange(15, 4) withAttributedString:boldPrice];
}
else
{
[titleStringMonthly replaceCharactersInRange:NSMakeRange(12, 4) withAttributedString:strikedOutPrice];
[titleStringMonthly replaceCharactersInRange:NSMakeRange(17, 4) withAttributedString:boldPrice];
}
[_oneMonthButton setAttributedTitle:titleStringMonthly forState:UIControlStateNormal];
I imagine that for this case you could have a couple of dynamic counters that keeps track of the index and length of the next range and make the replacements over a NSMutableAttributedString (like I do with my titleStringMonthly on the example)
Hope It helps someone.
You could do something like this
NSString *attr = [NSString stringWithFormat:#"%#%#%#", attributedString1, string2, string3];
Doing so will result in one attr string variable with all 10 of the strings put together, and you could do [textView setText:attr]; :)