2016-09-21 3 views
0

Как гласит название, когда мое меню состояния открыто и NSAlert запускается из другого потока, пользовательский интерфейс замерзает.NSAlert, появляющийся при открытии NSMenu, вызывает зависание пользовательского интерфейса

Предположительно, это связано с тем, что обе вещи работают на основном потоке. Но поскольку я имею дело с NSAlert и NSMenu, разве у меня нет , чтобы запустить их в основной теме?

NSAlert Код

func showWallpaperUpdateErrorAlert(messageText: String, informativeText: String) { 
    DispatchQueue.main.async { 
     NSApp.activate(ignoringOtherApps: true) 

     let updateErrorAlert = NSAlert() 
     updateErrorAlert.messageText = messageText 
     updateErrorAlert.informativeText = informativeText 
     updateErrorAlert.addButton(withTitle: "OK") 
     updateErrorAlert.runModal() 
    } 
} 

NSMenu Код

func createStatusBarMenu() { 
    // Status bar icon 
    guard let icon = NSImage(named: "iconFrame44") 
     else { NSLog("Error setting status bar icon image."); return } 
    icon.isTemplate = true 
    statusBarItem.image = icon 

    // Create Submenu items 
    let viewOnRedditMenuItem = NSMenuItem(title: "View on Reddit...", action: #selector(viewOnRedditAction), keyEquivalent: "") 
    viewOnRedditMenuItem.target = self 

    let saveThisImageMenuItem = NSMenuItem(title: "Save This Image...", action: #selector(saveThisImageAction), keyEquivalent: "") 
    saveThisImageMenuItem.target = self 

    // Add to title submenu 
    let titleSubmenu = NSMenu(title: "") 
    titleSubmenu.addItem(descriptionMenuItem) 
    titleSubmenu.addItem(NSMenuItem.separator()) 
    titleSubmenu.addItem(viewOnRedditMenuItem) 
    titleSubmenu.addItem(saveThisImageMenuItem) 

    // Create main menu items 
    titleMenuItem = NSMenuItem(title: "No Wallpaperer Image", action: nil, keyEquivalent: "") 
    titleMenuItem.submenu = titleSubmenu 
    titleMenuItem.isEnabled = false 
    getNewWallpaperMenuItem = NSMenuItem(title: "Update Now", action: #selector(getNewWallpaperAction), keyEquivalent: "") 
    getNewWallpaperMenuItem.target = self 

    let preferencesMenuItem = NSMenuItem(title: "Preferences...", action: #selector(preferencesAction), keyEquivalent: "") 
    preferencesMenuItem.target = self 

    let quitMenuItem = NSMenuItem(title: "Quit Wallpaperer", action: #selector(quitAction), keyEquivalent: "") 
    quitMenuItem.target = self 

    // Add to main menu 
    let statusBarMenu = NSMenu(title: "") 
    statusBarMenu.addItem(titleMenuItem) 
    statusBarMenu.addItem(NSMenuItem.separator()) 
    statusBarMenu.addItem(getNewWallpaperMenuItem) 
    statusBarMenu.addItem(NSMenuItem.separator()) 
    statusBarMenu.addItem(preferencesMenuItem) 
    statusBarMenu.addItem(quitMenuItem) 

    statusBarItem.menu = statusBarMenu 

    statusBarMenu.delegate = self 
} 
+0

Привет, какая у вас версия X X? Это os x 10.12 (Sierra)? – DoN1cK

+0

Да, я нахожусь в Сьерра. – yesthisisjoe

ответ

1

В моем случае решение было распускать меню перед показом предупреждения.

я должен был получить доступ к меню из NSStatusItem «s menu собственности и вызвать cancelTrackingWithoutAnimation() (регулярный cancelTracking() не так гладко). По какой-то причине я также должен был делать это за пределами основного потока.

func showWallpaperUpdateErrorAlert(messageText: String, informativeText: String) { 
    statusBarItem.menu?.cancelTrackingWithoutAnimation() // This is new 

    DispatchQueue.main.async { 
     NSApp.activate(ignoringOtherApps: true) 

     let updateErrorAlert = NSAlert() 
     updateErrorAlert.messageText = messageText 
     updateErrorAlert.informativeText = informativeText 
     updateErrorAlert.addButton(withTitle: "OK") 
     updateErrorAlert.runModal() 
    } 
} 
+0

он выполняет свою работу. – DoN1cK

 Смежные вопросы

  • Нет связанных вопросов^_^