How to hide the Dock icon

老子叫甜甜 提交于 2019-12-17 04:12:08

问题


I want to make a preference for hiding the Dock icon and showing an NSStatusItem. I can create the StatusItem but I don't know how to remove the icon from Dock. :-/

Any ideas?


回答1:


I think you are looking for the LSUIElement in the Info.plist

LSUIElement (String). If this key is set to “1”, Launch Services runs the application as an agent application. Agent applications do not appear in the Dock or in the Force Quit window. Although they typically run as background applications, they can come to the foreground to present a user interface if desired.

See a short discussion here about turning it on/off




回答2:


You can use what is called Activation Policy:

Objective-C

// The application is an ordinary app that appears in the Dock and may
// have a user interface.
[NSApp setActivationPolicy: NSApplicationActivationPolicyRegular];

// The application does not appear in the Dock and does not have a menu
// bar, but it may be activated programmatically or by clicking on one
// of its windows.
[NSApp setActivationPolicy: NSApplicationActivationPolicyAccessory];

// The application does not appear in the Dock and may not create
// windows or be activated.
[NSApp setActivationPolicy: NSApplicationActivationPolicyProhibited];

Swift 4

// The application is an ordinary app that appears in the Dock and may
// have a user interface.
NSApp.setActivationPolicy(.regular)

// The application does not appear in the Dock and does not have a menu
// bar, but it may be activated programmatically or by clicking on one
// of its windows.
NSApp.setActivationPolicy(.accessory)

// The application does not appear in the Dock and may not create
// windows or be activated.
NSApp.setActivationPolicy(.prohibited)

This should hide the dock icon.

See also

  • Answer that inspired this one: How to create a helper application (LSUIElement) that also has a (removable) dock icon
  • Documentation for NSRunningApplicationActivationPolicy.
  • A related question: "Start a GUI process in Mac OS X without dock icon".



回答3:


To do it while abiding to the Apple guidelines of not modifying application bundles and to guarantee that Mac App Store apps/(Lion apps ?) will not have their signature broken by info.plist modification you can set LSUIElement to 1 by default then when the application launches do :

ProcessSerialNumber psn = { 0, kCurrentProcess };
TransformProcessType(&psn, kProcessTransformToForegroundApplication);

to show it's dock icon, or bypass this if the user chose not to want the icon.

There is but one side effect, the application's menu is not shown until it losses and regains focus.

Source: Making a Checkbox Toggle The Dock Icon On and Off

Personally i prefer not setting any Info.plist option and use TransformProcessType(&psn, kProcessTransformToForegroundApplication) or TransformProcessType(&psn, kProcessTransformToUIElementApplication) based on what is the user setting.




回答4:


In Xcode 4 it is shown as "Application is agent (UIElement)" and it is Boolean.

In your Info.plist control-click to an empty space and select "Add Row" from the menu Type "Application is agent (UIElement)" Set it YES.

TO make it optional I added the following line to my code (thanks Valexa!)

 // hide/display dock icon
if (![[NSUserDefaults  standardUserDefaults] boolForKey:@"hideDockIcon"]) {
    //hide icon on Dock
    ProcessSerialNumber psn = { 0, kCurrentProcess };
    TransformProcessType(&psn, kProcessTransformToForegroundApplication);
} 



回答5:


Update for Swift: (Use both ways has been presented above, they have the same result)

public class func toggleDockIcon_Way1(showIcon state: Bool) -> Bool {
    // Get transform state.
    var transformState: ProcessApplicationTransformState
    if state {
        transformState = ProcessApplicationTransformState(kProcessTransformToForegroundApplication)
    }
    else {
        transformState = ProcessApplicationTransformState(kProcessTransformToUIElementApplication)
    }

    // Show / hide dock icon.
    var psn = ProcessSerialNumber(highLongOfPSN: 0, lowLongOfPSN: UInt32(kCurrentProcess))
    let transformStatus: OSStatus = TransformProcessType(&psn, transformState)
    return transformStatus == 0
}

public class func toggleDockIcon_Way2(showIcon state: Bool) -> Bool {
    var result: Bool
    if state {
        result = NSApp.setActivationPolicy(NSApplicationActivationPolicy.Regular)
    }
    else {
        result = NSApp.setActivationPolicy(NSApplicationActivationPolicy.Accessory)
    }
    return result
}



回答6:


If you want to make it a user preference then you can't use UIElement. UIElement resides in the application bundle you shouldn't edit any of the files in the app bundle as this will invalidate the bundles signature.

The best solution I've found is based on this excellent article . My solution is based on the comment by Dan. In short, There's no way to do this with Cocoa, but it is possible with a tiny bit of Carbon code.

The article also suggests making a helper app that handles the dock icon exclusively. The main app then starts and kills this app depending on the users preferences. This approach strikes me as being more robust than using the Carbon code, but I haven't tried it yet.



来源:https://stackoverflow.com/questions/620841/how-to-hide-the-dock-icon

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!