Search code examples
cocoansstringdrawrectnsimagensbutton

Drawing artifacts when drawing a NSString in a NSButton


I am using drawRect to draw a NSString inside a custom view, which is a subview of NSButton. The drawRect of the NSButton is also drawing an NSImage, which appears to the be the problem. If I remove the drawRect code for the NSImage, it no longer happens (but then I don't have a background).

Here is the custom view drawRect (shortened):

override func drawRect(dirtyRect: NSRect) {
    super.drawRect(dirtyRect)

    let string: NSString = NSString(string: thermostat.displayTargetTemperature())
    string.drawAtPoint(NSMakePoint(CGFloat(width), CGFloat(y)), withAttributes: self.attributes)

}

Here is the NSButton drawRect:

override func drawRect(dirtyRect: NSRect) {
    var image = NSImage(named: FILDarkManager.enabled ? "preferences-statusbar-bg-dark" : "preferences-statusbar-bg-light")

    if (self.state == NSOnState) {
        image?.drawInRect(dirtyRect, fromRect: NSZeroRect, operation: NSCompositingOperation.CompositeSourceOver, fraction: 1.0, respectFlipped: true, hints: nil)
    }
    else {
        image?.drawInRect(dirtyRect, fromRect: NSZeroRect, operation: NSCompositingOperation.CompositeSourceOver, fraction: 0.8, respectFlipped: true, hints: nil)
    }

    super.drawRect(dirtyRect)
}

Perhaps it is something to do with the operation when drawing the NSImage?

The strange thing is that if I hover over the view, it draws correctly.

Screenshot


Solution

  • Try drawing the image into [self bounds] rather than into dirtyRect.

    Drawing the string probably dirties part of your button, causing your code to draw the image into that dirtyRect.