У меня есть кастом NSView
. Его содержимое может быть шире экрана. Я использовал Interface Builder для встраивания своего пользовательского представления в NSScrollView
. Представление прокрутки содержит горизонтальное NSScroller
и NSClipView
, содержащее мое пользовательское представление.
Я переопределяю NSView.draw(_:)
следующим образом:
var frameSet = false
override func draw(_ dirtyRect: NSRect) {
super.draw(dirtyRect)
print("bounds \(bounds)") // Always shows origin of 0.0, 0.0
if !frameSet {
frame = NSRect(x: 0, y: 0, width: bounds.width*2, height: bounds.height)
frameSet = true
}
let scrollView = enclosingScrollView
let scroller = scrollView!.horizontalScroller
scroller!.isEnabled = true // This is necessary
let context = NSGraphicsContext.current?.cgContext
// draw stuff
}
На экране появляется полоса прокрутки, и я могу перетащить его назад и вперед, но это не влияет на мой пользовательский вид Я ожидал бы следующее:
Я бы ожидал, что NSView.bounds
каким-то образом отразит состояние горизонтальной полосы прокрутки. Но прямоугольник границ всегда имеет начало 0,0 независимо от состояния полосы прокрутки.
Я ожидаю, что при перемещении полосы прокрутки будет установлен NSView.needsDisplay
в принудительное состояние перерисовка Этого не происходит.
Что я могу сделать, это запросить состояние полосы прокрутки в моем методе draw(_:)
.
var frameSet = false
override func draw(_ dirtyRect: NSRect) {
super.draw(dirtyRect)
print("bounds \(bounds)") // Shows previous setting
if !frameSet {
frame = NSRect(x: 0, y: 0, width: bounds.width*2, height: bounds.height)
frameSet = true
}
let scrollView = enclosingScrollView
let scroller = scrollView!.horizontalScroller
scroller!.isEnabled = true // This is necessary
let knobRect = scroller!.rect(for: NSScroller.Part.knob)
bounds = NSRect(x: knobRect.minX, y: bounds.minY, width: bounds.width, height: bounds.height)
print( "new bounds \(bounds)") // This works
let context = NSGraphicsContext.current?.cgContext
// draw stuff
}
Я мог бы жить с этим если бы был какой-то способ форсировать перерисовку. Но я подозреваю, что все это должно обрабатываться автоматически.
Чего мне не хватает?