chickenparm chickenparm - 19 days ago 4
Swift Question

text draw on image extending off the image

I'm using the answer here to draw text on an image. The issue I am having is when the CGPoint is set near the right edge of the image, the text extends off of the image. I'm trying to figure out a way to draw left instead of right from the CGPoint or somehow calculate the size in points of the text that will be drawn then then move the draw point to accommodate for this size.

Here is the code I am using.

func textToImage(drawText text: NSString, inImage image: UIImage, atPoint point: CGPoint) -> UIImage {

let color = UserDefaults.standard.colorForKey(key: "color")!
let font = UserDefaults.standard.value(forKey: "font") as! String
let size = UserDefaults.standard.value(forKey: "size") as! Int
let fontAndSize = UIFont(name: font, size: CGFloat(size))!

let scale = UIScreen.main.scale
UIGraphicsBeginImageContextWithOptions(image.size, false, scale)

let textFontAttributes = [
NSFontAttributeName: fontAndSize,
NSForegroundColorAttributeName: color,
] as [String : Any]
image.draw(in: CGRect(origin: CGPoint.zero, size: image.size))

let rect = CGRect(origin: point, size: image.size)
text.draw(in: rect, withAttributes: textFontAttributes)

let newImage = UIGraphicsGetImageFromCurrentImageContext()
UIGraphicsEndImageContext()

return newImage!
}

func imagePickerController(_ picker: UIImagePickerController, didFinishPickingMediaWithInfo info: [String : Any]) {
if let mediaType = info[UIImagePickerControllerMediaType] as? String {
if mediaType.isEqual((kUTTypeImage as String)) {
if let pickedImage = info[UIImagePickerControllerOriginalImage] as? UIImage {
let width = pickedImage.size.width
let height = pickedImage.size.height
// this puts the point in the bottom right of the image which then causes the text drawn to extend off of the image
let point = CGPoint(x: width - 20, y: height - 50)
let timestampText = getTimestampText() as NSString
let timestampImage = textToImage(drawText: timestampText, inImage: pickedImage, atPoint: point)
if newMedia {
UIImageWriteToSavedPhotosAlbum(timestampImage, nil, nil, nil)
}
}

Answer

If you want to draw to the left, you can in fact "calculate the size in points of the text that will be drawn then move the draw point to accommodate for this size" by using boundingRectWithSize:options:attributes:context:. Ex:

func textToImage(drawText text: NSString, inImage image: UIImage, atPoint point: CGPoint) -> UIImage {

    let color = UserDefaults.standard.colorForKey(key: "color")!
    let font = UserDefaults.standard.value(forKey: "font") as! String
    let size = UserDefaults.standard.value(forKey: "size") as! Int
    let fontAndSize = UIFont(name: font, size: CGFloat(size))!

    let scale = UIScreen.main.scale
    UIGraphicsBeginImageContextWithOptions(image.size, false, scale)

    let textFontAttributes = [
        NSFontAttributeName: fontAndSize,
        NSForegroundColorAttributeName: color,
        ] as [String : Any]

    // Calculate text size
    let rectSize = text.boundingRect(with: CGSize(width:CGFloat(MAXFLOAT), height: CGFloat(MAXFLOAT)), options: NSStringDrawingOptions.usesLineFragmentOrigin, attributes: textFontAttributes, context: nil).size

    // Subtract the text width from the x origin
    let rect = CGRect(x:point.x-rectSize.width, y:point.y, width:rectSize.width, height: rectSize.height)
    text.draw(in: rect, withAttributes: textFontAttributes)
}