Reputation: 13
I am trying to generate a pdf inside my app. To draw a string I'm calculating the size of the bounding rect for that string using boundingRectWithSize and then drawing the string inside a rect of that size.
The code works fine in iOS 7.1 and above but in iOS 7.0.3 the text is not drawn at all if it's width is more than the rectangle's width (400). According to Apple's docs the string should have been wrapped to a new line and clipped if it cannot fit the rect, which is happening in iOS 7.1 and above, but not in iOS 7.0.3.
Here is my code snippet:
-(void)drawText:(NSString *)string
{
CGContextRef context = UIGraphicsGetCurrentContext();
CGContextSetFillColorWithColor(context, [UIColor blackColor].CGColor);
NSDictionary *attrsDictionary = [NSDictionary dictionaryWithObjectsAndKeys:
myFontForContentBold, NSFontAttributeName,
[NSNumber numberWithFloat:1.0], NSBaselineOffsetAttributeName, nil];
CGRect textRect = [string boundingRectWithSize:CGSizeMake(400, CGFLOAT_MAX) options:NSStringDrawingUsesLineFragmentOrigin|NSStringDrawingUsesFontLeading attributes:attributes context:nil]
textRect = CGRectMake(130, 80, 400, textRect.size.height);
[string drawInRect:textRect withAttributes:attrsDictionary];
}
I am not able to figure out what the problem might be. Please help.
Upvotes: 1
Views: 3071
Reputation: 1154
Try this:
-(void)drawText:(NSString *)string {
// this method must be called after a valid graphic context
// is configured, it can be called in drawRect:, or a bitmap or pdf context is configured.
CGContextRef context = UIGraphicsGetCurrentContext();
CGContextSetFillColorWithColor(context, [UIColor blackColor].CGColor);
NSDictionary *attrsDictionary = [NSDictionary dictionaryWithObjectsAndKeys:
myFontForContentBold, NSFontAttributeName,
[NSNumber numberWithFloat:1.0], NSBaselineOffsetAttributeName, nil];
NSAttributedString *richText = [[NSAttributedString alloc] initWithString:string attributes:attrsDictionary];
CGRect textRect = [richText boundingRectWithSize:CGSizeMake(400, CGFLOAT_MAX)
options:NSStringDrawingUsesLineFragmentOrigin | NSStringDrawingUsesFontLeading
context:nil];
textRect = CGRectMake(130, 80, 400, textRect.size.height);
[richText drawInRect:textRect];
}
If you need to draw large chunk of text, consider Text Kit
.
The Text Kit
approach:
- (void)drawAddressList:(NSArray *)list atPoint:(CGPoint)point {
NSTextStorage *textStorage = [[NSTextStorage alloc] init];
NSLayoutManager *layoutManager = [[NSLayoutManager alloc] init];
NSTextContainer *textContainer = [[NSTextContainer alloc] initWithSize:CGSizeMake(400.0f, FLT_MAX)];
[textStorage addLayoutManager:layoutManager];
[layoutManager addTextContainer:textContainer];
textContainer.lineFragmentPadding = 0.0f;
NSDictionary *attributes = @{NSFontAttributeName:[UIFont preferredFontForTextStyle:UIFontTextStyleBody]};
// it's a simple attributes for illustration
for (NSString *address in list) {
NSString *buffer = [NSString stringWithFormat:@"%@\n", address];
[textStorage appendAttributedString:[[NSAttributedString alloc] initWithString:buffer attributes:attributes]];
}
[layoutManager ensureLayoutForTextContainer:textContainer];
CGRect rect = [layoutManager usedRectForTextContainer:textContainer];
rect.size.width = 400.0f;
rect.size.height = ceilf(rect.size.height);
rect.origin = point; // this is the frame needed to draw the address list
[layoutManager drawGlyphsForGlyphRange:NSMakeRange(0, textStorage.length) atPoint:point];
}
Upvotes: 1