Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Drawing text over Core Graphics in Swift 3

Background: I am drawing on a UIImageView with Core Graphics. I would like to ultimately draw a text string over the core graphics drawing.

This (hackingwithswift.com) method i used to draw the text to an image, set my imageView to that image, and then draw over with core graphics. But I want the text to overlay the core graphics drawing.

Now I have moved to this https://stackoverflow.com/a/35574171/6337391 but it still isnt allowing me to write on top of my drawing.

class MapViewController: UIViewController {

    @IBOutlet var imageView: UIImageView!

    func drawScale() {
        // establish 6 points to draw a little bar with
        let length = CGFloat(80.0)
        let bottom = imageView.bounds.size.height - 15.0
        let left = CGFloat(20.0)
        let top = bottom - 20.0
        let middle = top + 10.0
        let right = left + length
        let topLeft = CGPoint(x: left, y: top)
        let topRight = CGPoint(x: right, y: top)
        let bottomRight = CGPoint(x: right, y: bottom)
        let bottomLeft = CGPoint(x: left, y: bottom)
        let middleLeft = CGPoint(x: left, y: middle)
        let middleRight = CGPoint(x: right, y: middle)

        // draw the bar
        drawLineFrom(fromPoint: topLeft, toPoint: bottomLeft, color: UIColor.red.cgColor, width: 1.0, alias: false)
        drawLineFrom(fromPoint: topRight, toPoint: bottomRight, color: UIColor.red.cgColor, width: 1.0, alias: false)
        drawLineFrom(fromPoint: middleLeft, toPoint: middleRight, color: UIColor.red.cgColor, width: 1.0, alias: false)

        // draw a text string
        UIGraphicsBeginImageContext(self.imageView.frame.size)

        let paragraphStyle = NSMutableParagraphStyle()
        paragraphStyle.alignment = .center

        let attrs = [
            NSFontAttributeName: UIFont.systemFont(ofSize: 12),
            NSParagraphStyleAttributeName: paragraphStyle,
            NSForegroundColorAttributeName: UIColor.red]

        let scaleString = "45 feet"
        scaleString.draw(at: CGPoint(x: 0, y: 50), withAttributes: attrs)

        let newImage = UIGraphicsGetImageFromCurrentImageContext()
        UIGraphicsEndImageContext()
    }

    /* Stroke a line between two CGPoints. Color, width, anti-alias options. */
    func drawLineFrom(fromPoint: CGPoint, toPoint: CGPoint, color: CGColor, width: CGFloat, alias: Bool) {
        // 1
        UIGraphicsBeginImageContext(self.imageView.frame.size)
        let context = UIGraphicsGetCurrentContext()!
        context.setShouldAntialias(alias)
        self.imageView.image?.draw(in: CGRect(x: 0, y: 0, width: self.imageView.frame.size.width, height: self.imageView.frame.size.height))

        // 2
        context.move(to: fromPoint)
        context.addLine(to: toPoint)

        // 3
        context.setLineWidth(width)
        context.setStrokeColor(color)

        // 4
        context.strokePath()

        // 5
        self.imageView.image = UIGraphicsGetImageFromCurrentImageContext()
        self.imageView.alpha = 1.0
        UIGraphicsEndImageContext()
    }
}

Doesnt work. Drawing the text string completely erases the bar. If move the bar drawing code under the string drawing code, then both are visible, but of course the bar is then over the string.

like image 202
Harry Netzer Avatar asked Feb 28 '17 01:02

Harry Netzer


2 Answers

Using Swift 4:

let paragraphStyle = NSMutableParagraphStyle()
paragraphStyle.alignment = .center

let attributes = [
    NSAttributedStringKey.paragraphStyle: paragraphStyle,
    NSAttributedStringKey.font: UIFont.systemFont(ofSize: 12.0),
    NSAttributedStringKey.foregroundColor: UIColor.blue
]

let myText = "HELLO"
let attributedString = NSAttributedString(string: myText, attributes: attributes)

let stringRect = CGRect(x: W/2 - 50, y: border, width: 100, height: H)
attributedString.draw(in: stringRect)

For Swift 4.2, change the above attributes to:

let attributes: [NSAttributedString.Key : Any] = [
    .paragraphStyle: paragraphStyle,
    .font: UIFont.systemFont(ofSize: 12.0),
    .foregroundColor: UIColor.blue
]
like image 163
ingconti Avatar answered Oct 05 '22 07:10

ingconti


Swift 3.0 : to draw text

   func drawMyText(myText:String,textColor:UIColor, FontName:String, FontSize:CGFloat, inRect:CGRect){

     let textFont = UIFont(name: FontName, size: FontSize)!
    let textFontAttributes = [
        NSFontAttributeName: textFont,
        NSForegroundColorAttributeName: textColor,
        ] as [String : Any]

    myText.draw(in: inRect, withAttributes: textFontAttributes)
}

call this function , below is e.g.

let _rect = CGRect(x: 40, y: 100, width: 40, height: 40)

 drawMyText(myText: "Hello", textColor: UIColor.black, FontName: "Helvetica Bold", FontSize: 11 , inRect:_rect)
like image 40
Devesh Avatar answered Oct 05 '22 06:10

Devesh