I've been researching this question but the answer I found does not work.
[myImageView addSubview:myTextView];
I want the text to become part of the image, so if I saved myImageView to the camera roll, the text would be included.
Am I doing something wrong or is there another way to do this?
Suppose you've already got a UIImage img, then use the following code to add texts
-(void)drawText:(NSString *)text onImage:(UIImage *)img
{
UIFont *font = yourTextViewFont;
UIGraphicsBeginImageContext(img.size);
[img drawAtPoint:CGPointZero];
CGContextSetRGBFillColor(UIGraphicsGetCurrentContext(), 1.0, 1.0, 1.0, 1);
[text drawAtPoint: CGPointMake(20, 20) withFont: font];
UIImage *ret = UIGraphicsGetImageFromCurrentImageContext();
UIGraphicsEndImageContext();
return ret;
}
Related
I want to add text on an image programmatically, but I can't seem to find how to do it. I've found one solution on here, but a lot of things are deprecated so it doesn't work...
Please help!
EDIT:
Here's my code:
UIImage *backgroundImage = image;
NSMutableDictionary *stringAttributes = [NSMutableDictionary dictionary];
[stringAttributes setObject: [UIFont fontWithName:#"Helvetica" size:20] forKey: NSFontAttributeName];
[stringAttributes setObject: [UIColor whiteColor] forKey: NSForegroundColorAttributeName];
[stringAttributes setObject: [NSNumber numberWithFloat: 2.0] forKey: NSStrokeWidthAttributeName];
[stringAttributes setObject: [UIColor blackColor] forKey: NSStrokeColorAttributeName];
[backgroundImage drawInRect:CGRectMake(0, 0, backgroundImage.size.width, backgroundImage.size.height)];
NSString *myString = [NSString stringWithFormat:#"Yolo"];
[myString drawInRect:CGRectMake(0, 0, 200, 50) withAttributes:stringAttributes];
UIImage *result = UIGraphicsGetImageFromCurrentImageContext();
UIGraphicsEndImageContext();
self.imageView.image = result;
NEW EDIT:
I'd like to clearify some things to understand the question better. My app lets the user send a photo that they have taken themselves via text messaging or by email, and I want to add some pre-written text from strings, on the photo.
So my question is: How do I get the text from the strings, on to the photo?
It took forever, but I figured it out.
Code:
NSMutableDictionary *stringAttributes = [NSMutableDictionary dictionary];
[stringAttributes setObject: [UIFont fontWithName:#"Avenir Book" size:250] forKey: NSFontAttributeName];
[stringAttributes setObject: [UIColor whiteColor] forKey: NSForegroundColorAttributeName];
NSString *placeString = [NSString stringWithFormat:#"Text here."];
CGSize size = [placeString sizeWithAttributes:stringAttributes];
//Create a bitmap context into which the text will be rendered.
UIGraphicsBeginImageContext(size);
//Render the text.
[placeString drawAtPoint:CGPointMake(0.0, 0.0) withAttributes:stringAttributes];
//Retrieve the image.
UIImage *imagene = UIGraphicsGetImageFromCurrentImageContext();
UIImage *mergedImage = _imageView.image;
CGSize newSize = image.size;
UIGraphicsBeginImageContext(newSize);
//Use existing opacity as is.
[mergedImage drawInRect:CGRectMake(0, 0, newSize.width, newSize.height)];
//Apply supplied opacity if applicable.
CGRect drawingRect = (CGRect) {.size = size};
drawingRect.origin.x = (newSize.width - size.width) * 0.01;
drawingRect.origin.y = (newSize.height - size.height) * 0.03;
[imagene drawInRect:drawingRect blendMode:kCGBlendModeNormal alpha:1];
UIImage *newImage = UIGraphicsGetImageFromCurrentImageContext();
UIGraphicsEndImageContext();
[_imageView setImage:newImage];
self.imageView.image = newImage;
Here's a general approach, code is likely missing but it gives you the important bits.
CGContextRef ctx = CGBitmapContextCreate(...)
CGContextDrawImage (gtx, myContextRect, myimage);
CGContextSelectFont(ctx, "Helvetica", 10.0, kCGEncodingMacRoman);
CGContextSetCharacterSpacing(ctx, 1.7);
CGContextSetTextDrawingMode(ctx, kCGTextFill);
CGContextShowTextAtPoint(ctx, 100.0, 100.0, "SOME TEXT", 9);
CGImageRef imageRef = CGBitmapContextCreateImage(ctx);
UIImage *finalImage = [UIImage imageWithCGImage:imageRef];
This will give you an image you can put in a view, or share via UIActivityViewController. I'm sure you can work out the bits.
The approach is:
1) Create bitmap context.
2) Render image
3) Add text
4) Save context to image
Simply place a UILabel on top of a UIImageView in IB and position them as desired using constraints. Then set the text into the label as desired.
EDIT:
Now that I know you want to be able to save I'd suggest using UIGraphicsBeginImageContextWithOptions to create an off-screen graphics context. I find that easier to deal with than CGContext and Core Graphics calls.
Draw into the context and the fetch and image from it.
Make the context the size of your image, and pass in a scale of 0 to use the device's native scale.
Your code might look something like this:
//Create an off-screen graphics context for drawing.
CGSize imageSize = myImage.size;
UIGraphicsBeginImageContextWithOptions(imageSize, false, 0);
//draw your image using drawAtPoint(CGPointmake(0,0));
//draw your string using one of the drawAtPoint or drawInRect methods
//available in NSString UIKit additions
//Fetch the resulting image from the context.
UIImage *maskImage = UIGraphicsGetImageFromCurrentImageContext();
//End the off-screen context
UIGraphicsEndImageContext();
Basically I have a main UIImage, which acts as a background/border. Within that UIImage I have 2 more UIImages, vertically split with a gap around them so you can still see a border of the main background UIImage. On each side I have a UILabel, to describe the images. Below is a picture of what I mean to help put into context.
What I want to achieve is to make this into 1 image, but keeping all of the current positions, layouts, image layouts (Aspect Fill) and label sizes and label background colours the same. I also want this image to be the same quality so it still looks good.
I have looked at many other stackoverflow questions and have so far come up with the follow, but it has the following problems:
Doesn't position the image labels to their correct places and sizes
Doesn't have the background colour for the labels or main image
Doesn't have the images as Aspect Fill (like the UIImageViews) so the outside of each picture is shown as well and isn't cropped properly, like in the above example.
Below is my code so far, can anyone help me achieve it like the image above please? I am fairly new to iOS development and am struggling a bit:
-(UIImage *)renderImagesForSharing{
CGSize newImageSize = CGSizeMake(640, 640);
NSLog(#"CGSize %#",NSStringFromCGSize(newImageSize));
UIGraphicsBeginImageContextWithOptions(newImageSize, NO, 0.0);
[self.mainImage.layer renderInContext:UIGraphicsGetCurrentContext()];
[self.beforeImageSide.image drawInRect:CGRectMake(0,0,(newImageSize.width/2),newImageSize.height)];
[self.afterImageSize.image drawInRect:CGRectMake(320,0,(newImageSize.width/2),newImageSize.height) blendMode:kCGBlendModeNormal alpha:1.0];
[self.beforeLabel drawTextInRect:CGRectMake(60.0f, 0.0f, 200.0f, 50.0f)];
[self.afterLabel drawTextInRect:CGRectMake(0.0f, 0.0f, 100.0f, 50.0f)];
UIImage *image = UIGraphicsGetImageFromCurrentImageContext();
NSData *imgData = UIImageJPEGRepresentation(image, 0.9);
UIImage * imagePNG = [UIImage imageWithData:imgData]; //wrap UIImage around PNG representation
UIGraphicsEndImageContext();
return imagePNG;
}
Thank you in advance for any help guys!
I don't understand why you want use drawInRect: to accomplish this task.
Since you have the images and everything with you, you can easily create a view as you have shown in the image. Then take a screenshot of it like this:
UIGraphicsBeginImageContextWithOptions(self.view.bounds.size, self.view.opaque, 0.0);
[self.view.layer renderInContext:UIGraphicsGetCurrentContext()];
UIImage*theImage=UIGraphicsGetImageFromCurrentImageContext();
UIGraphicsEndImageContext();
NSData*theImageData=UIImageJPEGRepresentation(theImage, 1.0 ); //you can use PNG too
[theImageData writeToFile:#"example.jpeg" atomically:YES];
Change the self.view to the view just created
It will give some idea.
UIGraphicsBeginImageContextWithOptions(DiagnosisView.bounds.size, DiagnosisView.opaque, 0.0);
CGContextRef ctx = UIGraphicsGetCurrentContext();
[[UIColor redColor] set];
CGContextFillRect(ctx, DiagnosisView.frame);
[DiagnosisView.layer renderInContext:ctx];
UIImage * img = UIGraphicsGetImageFromCurrentImageContext();
UIGraphicsEndImageContext();
NSString *imagePath = [KdiagnosisFolderPath stringByAppendingPathComponent:FileName];
NSData *pngData = UIImagePNGRepresentation(img);
[pngData writeToFile:imagePath atomically:YES];
pngData = nil,imagePath = nil;
So the text of my playingCardLabel is #"A \u2663"
- (IBAction)flipCardButtonTapped:(UIButton *)sender
{
if([self.playingCardLabel.textColor isEqual:[UIColor whiteColor]])
self.playingCardLabel.textColor = [UIColor blackColor];
else
self.playingCardLabel.textColor = [UIColor whiteColor];
}
How come when I tap the button, only the A changes to white, the spade (or whatever it is called) remains black no matter what?
Those symbols appear to be fixed in color. Use \U2663 for the black club (♣︎) and use \U2667 for the white club (♧). There are similar black or white version of the spade, heart, and diamond.
create image from symbol of unicode using your colour. use UIImageView instead UILabel, or use UILabel with NSAttributedString + NSTextAttachment (image inside).
#implementation NSString (OSExt)
- (UIImage *)toImageWithAttributes:(NSDictionary*)attributes
{
CGSize size = [self sizeWithAttributes:attributes];
UIGraphicsBeginImageContextWithOptions(size, NO, 0.0);
[self drawAtPoint:CGPointZero withAttributes:attributes];
CGContextRef imgctx = UIGraphicsGetCurrentContext();
// use blend mode to fill symbols like #"♣︎"
CGContextSetBlendMode(imgctx, kCGBlendModeSourceAtop);
CGContextSetFillColorWithColor(imgctx, [attributes[NSForegroundColorAttributeName] CGColor]);
CGContextFillRect(imgctx, (CGRect){CGPointZero, size});
UIImage *image = UIGraphicsGetImageFromCurrentImageContext();
UIGraphicsEndImageContext();
return image;
}
#end
// use
id attrs = #{NSForegroundColorAttributeName:[UIColor greenColor]};
UIImage *image = [#"♣︎" toImageWithAttributes:attrs];
I've tried setting the title text attributes. The Button is set by using an icon and then setting the title property. The icon is properly tinted. The title remains 'untinted'
Screenshot attached.
If tintColor does not affect the text color, the only solution I know of is to essentially create a composite image of the icon and text, then use that as your button image:
UIGraphicsBeginImageContextWithOptions(someSize, NO, 0);
CGContextRef context = UIGraphicsGetCurrentContext();
// draw the image
// Use UIKit NSString additions to draw the text
UIImage *image = UIGraphicsGetImageFromCurrentImageContext();
UIGraphicsEndImageContext();
David's suggestion works. Here is sample code:
+ (UIImage *) image:(NSString *) imageName withTitle:(NSString *)title {
UIFont *titleFont = [UIFont boldSystemFontOfSize:10];
CGSize textSize = [title sizeWithFont:titleFont];
CGFloat width = MAX(35, textSize.width);
UIGraphicsBeginImageContextWithOptions(CGSizeMake(width, 35), NO, 0);
CGContextRef context = UIGraphicsGetCurrentContext();
UIImage *toolbarImage = [UIImage imageNamed:imageName];
CGContextSaveGState(context); {
CGContextTranslateCTM(context, 0, 35);
CGContextScaleCTM(context, 1.0, -1.0);
CGContextDrawImage(context, CGRectMake((width - toolbarImage.size.width) / 2, 14, toolbarImage.size.width, toolbarImage.size.height), toolbarImage.CGImage);
}
CGContextRestoreGState(context);
[title drawInRect:CGRectMake((width - textSize.width) / 2, 22, textSize.width, textSize.height) withFont:titleFont];
UIImage *image = UIGraphicsGetImageFromCurrentImageContext();
UIGraphicsEndImageContext();
return image;
}
Tweak some of the frame parameters to fit your images.
I'm quite new to ios development
and I'm trying to write text on an image and rotate the text
I wrote the text but I'm trying to rotate it around its center
the idea is to translate the text to put its origin on the center then rotate then retranslate to the original position
Here's my code :
context = UIGraphicsGetCurrentContext();
txt = #"Hello";
[[UIColor redColor] set];
CGSize sz = [txt sizeWithFont:font];
rect= CGRectMake(tpoint.x,tpoint.y,sz.width, sz.height);
CGContextTranslateCTM(context, sz.width/2, sz.height/2);
CGContextRotateCTM(context, 0.3);
CGContextTranslateCTM(context, -sz.width/2, -sz.height/2);
[txt drawAtPoint:tpoint withFont:font];
UIImage *newImage = UIGraphicsGetImageFromCurrentImageContext();
UIGraphicsEndImageContext();
imageView.image = newImage;