Редактируемый NSTextField внутри не .titled NSPanel

Я делаю мост для react-native-macos. Мне нужен NSPanel с тем же поведением, что и Spotlight.

Я программно создал внутри NSPanel и NSTextField. Все работает как положено, но если я меняю NSPanel на не .titled - текстовое поле отключается.

Работает:

panel = NSPanel(contentRect: NSRect(x: 0, y: 0, width: 400, height: 40), styleMask: [
    .borderless,
    .nonactivatingPanel,
    .titled,  < ------- HERE
    .resizable,
  ], backing: .buffered, defer: true)

searchField = NSTextField()
searchField.delegate = self
searchField.isBezeled = false
searchField.font = NSFont.systemFont(ofSize: 20, weight: .light
searchField.drawsBackground = false
searchField.placeholderString = "Query here..."
searchField.setFrameSize(NSMakeSize(400, 40)

Не работает:

panel = NSPanel(contentRect: NSRect(x: 0, y: 0, width: 400, height: 40), styleMask: [
    .borderless,
    .nonactivatingPanel,
    .resizable,
  ], backing: .buffered, defer: true)

searchField = NSTextField()
searchField.delegate = self
searchField.isBezeled = false
searchField.font = NSFont.systemFont(ofSize: 20, weight: .light
searchField.drawsBackground = false
searchField.placeholderString = "Query here..."
searchField.setFrameSize(NSMakeSize(400, 40)

Как я могу сделать NSPanel со скрытой панелью заголовка и редактируемым NSTextField внутри?


person Denis    schedule 25.07.2020    source источник


Ответы (1)


Я считаю, что .borderless и .titled взаимоисключающие. Другими словами, когда вы указываете .borderless в верхнем коде, .titled переопределяет его, и в итоге вы получаете обычное окно, которое нормально обрабатывает события. Во втором коде .borderless фактически регистрируется, и в итоге вы получаете подкласс окон без полей, который обрабатывает события совсем по-другому. Но все это не по делу.

Предполагая, что вам может потребоваться больше, чем macOS 10.10, вы можете использовать следующий код:

panel = NSPanel(contentRect: NSRect(x: 0, y: 0, width: 400, height: 40), styleMask: [
    .titled,
    .fullSizeContentView,
    ], backing: .buffered, defer: true)
panel.titleVisibility = .hidden
panel.titlebarAppearsTransparent = true
panel.makeFirstResponder(searchField)
panel.makeKeyAndOrderFront(nil)

Получается полноразмерная озаглавленная панель, которая нормально обрабатывает события (позволяет своим представлениям стать ключевыми). Затем, прежде чем показывать панель, скройте заголовок, а также сделайте его прозрачным. Обратите внимание: чтобы заголовок полностью исчез, вам не нужно использовать какие-либо параметры .resizable, .closable или .miniaturizable.

person NSGod    schedule 26.07.2020