Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How to correct UIView and UILabel text scaling with pixelation?

When I add a UILabel with text to a UIView and then scale the UIView, the contents is displayed with pixelation. The greater the scale factor, the greater the pixelation.

I understand using a CATextLayer might be able to assist and could display the scaled UIView and UILabel text without pixelation but I don't know how to implement it.

This is how I create a triangle and scale it with no pixelation. It scales with perfect sharp edges.

How can I ensure the same when scaling a UILabel ?

func drawTriangle() {
    let path = UIBezierPath()
    path.moveToPoint(CGPoint(x: 0, y: 100))
    path.addLineToPoint(CGPoint(x: 100, y: 100))
    path.addLineToPoint(CGPoint(x: 50, y: 0))
    path.closePath()

    let shape = CAShapeLayer()
    shape.path = path.CGPath
    shape.fillColor = UIColor.blackColor().CGColor

    viewTriangle.layer.insertSublayer(shape, atIndex: 0)
}

func scaleTriangle() {
    viewTriangle.transform = CGAffineTransformMakeScale(5, 5)
}

Question:

In Swift code, how do I convert the below to use a CATextLayer so that it scales with no pixelation?


Problem code:

func drawLetter() { // pixelated when scaled ?
    let labelLetter = UILabel(frame: CGRect(x: 0, y: 0, width: 100, height: 100))
    labelLetter.text = "A"
    labelLetter.backgroundColor = UIColor.clearColor()
    labelLetter.textColor = UIColor.blackColor()
    labelLetter.font = UIFont(name: labelLetter.font.fontName, size: 144)
    labelLetter.textAlignment = .Center
    viewLetter.addSubview(labelLetter)
    }
}

func scaleView() {
    let scaleValue: CGFloat = 5
    self.viewLetter.transform = CGAffineTransformMakeScale(scaleValue, scaleValue)
}

Image:

enter image description here

like image 353
user4806509 Avatar asked Oct 30 '22 01:10

user4806509


2 Answers

I understand using a CATextLayer uses paths for drawing and will display the scaled UIView and UILabel text without pixelation.

You understand wrong. A CATextLayer draws text and scales its text. This is an either-or thing: use CATextLayer or a UILabel.

It's easy to get more detail in a scaled view: that is what a view's contentScaleFactor is for. Simply increase it, taking into account the existing scale due to the resolution of the screen, to match your scale transform.

like image 171
matt Avatar answered Nov 15 '22 07:11

matt


This scales up the view 5x and sets the content's scale as well

func scaleView() {
    let scaleValue: CGFloat = 5
    self.viewLetter.transform = CGAffineTransformMakeScale(scaleValue, scaleValue)
    self.labelLetter.contentScaleFactor = scaleValue * x //scaleValue * native content scale  (2 on iPhone 8 and 3 on iPhone 8 plus)
}
like image 23
Mars Avatar answered Nov 15 '22 06:11

Mars