Reputation: 807
This is the code inside my custom view class:
func drawTestingPoint(_ point: CGPoint, target: Int, output: Int) {
let path = NSBezierPath()
path.appendArc(withCenter: point, radius: 5, startAngle: 0, endAngle: 360)
NSColor.black.setStroke()
if target == output {
NSColor.green.setFill()
} else {
NSColor.red.setFill()
}
path.lineWidth = 3
path.fill()
path.stroke()
}
override func draw(_ dirtyRect: NSRect) {
//If I call the drawTestingPoint function here it works
}
Inside my viewDidLoad
method in my NSViewController
class I set up the custom view and try to draw the testing point:
let size = getDataViewSize()
let origin = CGPoint(x: view.frame.width/2-size.width/2, y: view.frame.height/2-size.height/2)
dataView = DataView(frame: CGRect(origin: origin, size: size))
view.addSubview(dataView)
dataView.drawTestingPoint(CGPoint(x: view.frame.width/2 y: view.frame.height/2), target: target, output: output)
dataView.needsDisplay = true
My problem is that no point is getting drawn. I think there can't be anything wrong with my drawTestingPoint
function because when I call it inside my draw(_ dirtyRect: NSRect)
function in my custom NSView
class, it works. What can I do so I can call this function inside my viewDidLoad
function how you can see in the codes snippets above so my point gets drawn
Upvotes: 0
Views: 212
Reputation: 131398
You can't just draw any time you want. Normally you set up a view and implement draw(_:)
as you've done. The system calls the draw method when it needs the view to draw its contents. Before calling your draw(_:)
method it sets up the drawing context correctly to draw inside your view and clip if you draw outside of the view. That's the bit you're missing.
As a general rule you should NOT draw outside of the view's draw(_:)
method. I've done drawing outside of the draw(_:)
method so infrequently that I don't remember what you'd need to do to set up the drawing context correctly. (To be fair I do mostly iOS development these days and my MacOS is getting rusty.)
So the short answer is "Don't do that."
Instead, set up your custom view to save the information it needs to draw itself. As others have suggested, when you make changes to the view, set needsDisplay=true
on the view. That will cause the system to call the view's draw(_:)
method on the next pass through the event loop
Upvotes: 1