How to implement a NSButton like the Finder button

240 views Asked by At

Please refer to the screenshot, I want to implement a NSButton like the buttons on Finder window. It seems that the button style is similar with a NSButton recessed. I have tried the recessed button but it is a little different from the Finder button, even the one which have a drop down menu. I have no idea how to make a drop down menu with recessed button.

If I choose to make a bevel style borderless NSButton with a special image, I cannot set a highlighted hover background whose size is larger than the image inside. The hover area is always the same with the image.

So any body known how to implement this. Thanks

enter image description here

1

There are 1 answers

0
RTXGamer On

Use NSMenuToolbarItem instead and check the inline comment in the sample source:


Assign this custom class MainWindowController to the initial NSWindowController controller:

class MainWindowController: NSWindowController {
    
    // `NSMenuToolbarItem` Items
    var dropDownMenu: NSMenu = {
        var menu = NSMenu(title: "DropDown")
        let item1 = NSMenuItem(title: "Item 1", action: nil, keyEquivalent: "")
        let item2 = NSMenuItem(title: "Item 1", action: nil, keyEquivalent: "")
        let item3 = NSMenuItem(title: "Item 3", action: nil, keyEquivalent: "")
        menu.items = [item1, item2, item3]
        return menu
    }()
    
    override func windowDidLoad() {
        super.windowDidLoad()
        
        configureToolbar()
    }
    
    private func configureToolbar() {
        if  let safeWindow = self.window {
            let toolbar = NSToolbar(identifier: "mainWindowToolbar")
            toolbar.delegate = self
            toolbar.displayMode = .default
            
            safeWindow.toolbarStyle = .automatic
            
            safeWindow.toolbar = toolbar
            safeWindow.toolbar?.validateVisibleItems()
        }
    }
}

extension MainWindowController: NSToolbarDelegate {
    func toolbar(_ toolbar: NSToolbar, itemForItemIdentifier itemIdentifier: NSToolbarItem.Identifier, willBeInsertedIntoToolbar flag: Bool) -> NSToolbarItem? {
       
        let toolbarItem = NSMenuToolbarItem(itemIdentifier: itemIdentifier)
        toolbarItem.showsIndicator = true // To display DropDown Indicator
        toolbarItem.menu = self.dropDownMenu
        toolbarItem.isBordered = true // Show ToolBar Item Background on Mouse Hover
        toolbarItem.image = NSImage(systemSymbolName: "ellipsis.circle", accessibilityDescription: "")
        return toolbarItem
    }
    
    func toolbarDefaultItemIdentifiers(_ toolbar: NSToolbar) -> [NSToolbarItem.Identifier] {
        return [NSToolbarItem.Identifier("DropDownAction")]
    }
    
    func toolbarAllowedItemIdentifiers(_ toolbar: NSToolbar) -> [NSToolbarItem.Identifier] {
        return [NSToolbarItem.Identifier("DropDownAction")]
    }
}


Output:

enter image description here