Maciek
Maciek

Reputation: 211

swift image resize and save resolution issue

I have a problem with image size.

Initially I have image with any size which I crop to square

func cropToSquare() -> NSImage? {
    let dimensions = [self.width, self.height]
    let lessValue = dimensions.min()
    let x = floor((self.width - lessValue!) / 2)
    let y = floor((self.height - lessValue!) / 2)
    let frame = NSMakeRect(x, y, lessValue!, lessValue!)
    guard let rep = self.bestRepresentation(for: frame, context: nil, hints: nil) else {
        return nil
    }
    let img = NSImage(size: NSSize(width: lessValue!, height: lessValue!))
    img.lockFocus()
    defer { img.unlockFocus() }
    if rep.draw(in: NSMakeRect(0, 0, lessValue!, lessValue!),
                from: frame,
                operation: NSCompositingOperation.copy,
                fraction: 1.0,
                respectFlipped: false,
                hints: [:]) {
        return img
    }
    return nil
}

Next I resize image

func copyWithSize(size: NSSize) -> NSImage? {
    let frame = NSMakeRect(0, 0, size.width, size.height)
    guard let rep = self.bestRepresentation(for: frame, context: nil, hints: nil) else {
        return nil
    }
    let img = NSImage(size: size)
    img.lockFocus()
    defer { img.unlockFocus() }
    if rep.draw(in: frame) {
        print(size, frame)
        return img
    }
    return nil
}

finally saving image to file using the png extension from this answer

Generally everything working OK ... except image size. When I start with some size and resize to let say 100x100 my saved image has a double size (200x200).

What's wrong with my code ?

Upvotes: 1

Views: 702

Answers (1)

Oskar
Oskar

Reputation: 3702

The image is drawing in @2x because you have a Mac with a Retina display.

Using lockFocus creates a new image for displaying on the screen, which is impractical if you want to save it to a file.

You could get the scaling factor using:

NSScreen.main.backingScaleFactor

and adjust your resize accordingly.

But the best solution is to create a NSBitmapImageRep and manually set it's size to the size you want the image.

Upvotes: 2

Related Questions