aboutsummaryrefslogtreecommitdiff
path: root/AppKit
diff options
context:
space:
mode:
authorGravatar gtm.daemon <gtm.daemon@7dc7ac4e-7543-0410-b95c-c1676fc8e2a3>2010-04-02 19:30:55 +0000
committerGravatar gtm.daemon <gtm.daemon@7dc7ac4e-7543-0410-b95c-c1676fc8e2a3>2010-04-02 19:30:55 +0000
commit749900bde6560d275418871bff922df9cf1e9643 (patch)
treeac72670816b130fb8d5381ed05ae2813c4ce1695 /AppKit
parent1c82518f5bd4a505516cb3a22df61b3fd279df14 (diff)
[Author: csilv]
use LaunchServices APIs when running on 10.5 and above. R=dmaclach,thomasvl APPROVED=dmaclach DELTA=150 (150 added, 0 deleted, 0 changed)
Diffstat (limited to 'AppKit')
-rw-r--r--AppKit/GTMLoginItems.m156
1 files changed, 153 insertions, 3 deletions
diff --git a/AppKit/GTMLoginItems.m b/AppKit/GTMLoginItems.m
index f124ef5..9da1ff9 100644
--- a/AppKit/GTMLoginItems.m
+++ b/AppKit/GTMLoginItems.m
@@ -7,9 +7,9 @@
// Licensed under the Apache License, Version 2.0 (the "License"); you may not
// use this file except in compliance with the License. You may obtain a copy
// of the License at
-//
+//
// http://www.apache.org/licenses/LICENSE-2.0
-//
+//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
// WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
@@ -19,6 +19,7 @@
#import "GTMLoginItems.h"
#import "GTMDefines.h"
+#import "GTMGarbageCollection.h"
#include <Carbon/Carbon.h>
@@ -27,12 +28,25 @@ NSString * const kGTMLoginItemsNameKey = @"Name";
NSString * const kGTMLoginItemsPathKey = @"Path";
NSString * const kGTMLoginItemsHiddenKey = @"Hide";
+// kLSSharedFileListLoginItemHidden is supported on
+// 10.5, but missing from the 10.5 headers.
+// http://openradar.appspot.com/6482251
+#if MAC_OS_X_VERSION_MAX_ALLOWED < MAC_OS_X_VERSION_10_6
+static NSString * const kLSSharedFileListLoginItemHidden =
+ @"com.apple.loginitem.HideOnLaunch";
+#endif // MAC_OS_X_VERSION_MAX_ALLOWED < MAC_OS_X_VERSION_10_6
+
@interface GTMLoginItems (PrivateMethods)
+ (NSInteger)indexOfLoginItemWithValue:(id)value
forKey:(NSString *)key
loginItems:(NSArray *)items;
+#if MAC_OS_X_VERSION_MIN_REQUIRED >= MAC_OS_X_VERSION_10_5
++ (LSSharedFileListRef)loginItemsFileListRef;
++ (NSArray *)loginItemsArrayForFileListRef:(LSSharedFileListRef)fileListRef;
+#else // MAC_OS_X_VERSION_MIN_REQUIRED >= MAC_OS_X_VERSION_10_5
+ (BOOL)compileAndRunScript:(NSString *)script
withError:(NSError **)errorInfo;
+#endif // MAC_OS_X_VERSION_MIN_REQUIRED >= MAC_OS_X_VERSION_10_5
@end
@implementation GTMLoginItems (PrivateMethods)
@@ -53,6 +67,23 @@ NSString * const kGTMLoginItemsHiddenKey = @"Hide";
return NSNotFound;
}
+#if MAC_OS_X_VERSION_MIN_REQUIRED >= MAC_OS_X_VERSION_10_5
+
++ (LSSharedFileListRef)loginItemsFileListRef {
+ LSSharedFileListRef loginItemsRef =
+ LSSharedFileListCreate(NULL, kLSSharedFileListSessionLoginItems, NULL);
+ return (LSSharedFileListRef)GTMCFAutorelease(loginItemsRef);
+}
+
++ (NSArray *)loginItemsArrayForFileListRef:(LSSharedFileListRef)fileListRef {
+ UInt32 seedValue;
+ CFArrayRef filelistArrayRef = LSSharedFileListCopySnapshot(fileListRef,
+ &seedValue);
+ return GTMCFAutorelease(filelistArrayRef);
+}
+
+#else // MAC_OS_X_VERSION_MIN_REQUIRED >= MAC_OS_X_VERSION_10_5
+
+ (BOOL)compileAndRunScript:(NSString *)script
withError:(NSError **)errorInfo {
if ([script length] == 0) {
@@ -83,10 +114,70 @@ NSString * const kGTMLoginItemsHiddenKey = @"Hide";
return YES;
}
+#endif // MAC_OS_X_VERSION_MIN_REQUIRED >= MAC_OS_X_VERSION_10_5
+
@end
@implementation GTMLoginItems
+#if MAC_OS_X_VERSION_MIN_REQUIRED >= MAC_OS_X_VERSION_10_5
+
++ (NSArray*)loginItems:(NSError **)errorInfo {
+ // get the login items from LaunchServices
+ LSSharedFileListRef loginItemsRef = [self loginItemsFileListRef];
+ if (!loginItemsRef) {
+ // COV_NF_START - no real way to test this
+ if (errorInfo) {
+ *errorInfo = [NSError errorWithDomain:@"GTMLoginItems"
+ code:-1
+ userInfo:nil];
+ }
+ return nil;
+ // COV_NF_END
+ }
+ NSArray *fileList = [self loginItemsArrayForFileListRef:loginItemsRef];
+
+ // build our results
+ NSMutableArray *result = [NSMutableArray array];
+ for (id item in fileList) {
+ LSSharedFileListItemRef itemRef = (LSSharedFileListItemRef)item;
+ // name
+ NSMutableDictionary *item = [NSMutableDictionary dictionary];
+ CFStringRef nameRef = LSSharedFileListItemCopyDisplayName(itemRef);
+ if (nameRef) {
+ [item setObject:[(NSString *)nameRef stringByDeletingPathExtension]
+ forKey:kGTMLoginItemsNameKey];
+ CFRelease(nameRef);
+ }
+ // path
+ CFURLRef urlRef = NULL;
+ if (LSSharedFileListItemResolve(itemRef, 0, &urlRef, NULL) == noErr) {
+ if (urlRef) {
+ NSString *path = [(NSURL *)urlRef path];
+ if (path) {
+ [item setObject:path forKey:kGTMLoginItemsPathKey];
+ }
+ CFRelease(urlRef);
+ }
+ }
+ // hidden
+ CFBooleanRef hiddenRef = LSSharedFileListItemCopyProperty(itemRef,
+ (CFStringRef)kLSSharedFileListLoginItemHidden);
+ if (hiddenRef) {
+ if (hiddenRef == kCFBooleanTrue) {
+ [item setObject:[NSNumber numberWithBool:YES]
+ forKey:kGTMLoginItemsHiddenKey];
+ }
+ CFRelease(hiddenRef);
+ }
+ [result addObject:item];
+ }
+
+ return result;
+}
+
+#else // MAC_OS_X_VERSION_MIN_REQUIRED >= MAC_OS_X_VERSION_10_5
+
+ (NSArray*)loginItems:(NSError **)errorInfo {
NSDictionary *errDict = nil;
// get the script compiled and saved off
@@ -139,10 +230,12 @@ NSString * const kGTMLoginItemsHiddenKey = @"Hide";
}
[result addObject:item];
}
-
+
return result;
}
+#endif // MAC_OS_X_VERSION_MIN_REQUIRED >= MAC_OS_X_VERSION_10_5
+
+ (BOOL)pathInLoginItems:(NSString *)path {
NSArray *loginItems = [self loginItems:nil];
NSInteger itemIndex = [self indexOfLoginItemWithValue:path
@@ -164,30 +257,87 @@ NSString * const kGTMLoginItemsHiddenKey = @"Hide";
// make sure it isn't already there
if ([self pathInLoginItems:path]) return;
// now append it
+#if MAC_OS_X_VERSION_MIN_REQUIRED >= MAC_OS_X_VERSION_10_5
+ NSURL *url = [NSURL fileURLWithPath:path];
+ if (url) {
+ LSSharedFileListRef loginItemsRef = [self loginItemsFileListRef];
+ if (loginItemsRef) {
+ NSDictionary *setProperties =
+ [NSDictionary dictionaryWithObject:[NSNumber numberWithBool:hide]
+ forKey:kLSSharedFileListLoginItemHidden];
+ LSSharedFileListItemRef itemRef =
+ LSSharedFileListInsertItemURL(loginItemsRef,
+ kLSSharedFileListItemLast, NULL, NULL,
+ (CFURLRef)url,
+ (CFDictionaryRef)setProperties, NULL);
+ if (itemRef) CFRelease(itemRef);
+ }
+ }
+#else // MAC_OS_X_VERSION_MIN_REQUIRED >= MAC_OS_X_VERSION_10_5
NSString *scriptSource =
[NSString stringWithFormat:
@"tell application \"System Events\" to make new login item with properties { path:\"%s\", hidden:%s } at end",
[path UTF8String],
(hide ? "yes" : "no")];
[self compileAndRunScript:scriptSource withError:nil];
+#endif // MAC_OS_X_VERSION_MIN_REQUIRED >= MAC_OS_X_VERSION_10_5
}
+ (void)removePathFromLoginItems:(NSString*)path {
if ([path length] == 0) return;
+#if MAC_OS_X_VERSION_MIN_REQUIRED >= MAC_OS_X_VERSION_10_5
+ NSURL *url = [NSURL fileURLWithPath:path];
+ LSSharedFileListRef loginItemsRef = [self loginItemsFileListRef];
+ if (loginItemsRef) {
+ NSArray *fileList = [self loginItemsArrayForFileListRef:loginItemsRef];
+ for (id item in fileList) {
+ LSSharedFileListItemRef itemRef = (LSSharedFileListItemRef)item;
+ CFURLRef urlRef = NULL;
+ if (LSSharedFileListItemResolve(itemRef, 0, &urlRef, NULL) == noErr) {
+ if (urlRef) {
+ if (CFEqual(urlRef, (CFURLRef)url)) {
+ LSSharedFileListItemRemove(loginItemsRef, itemRef);
+ }
+ CFRelease(urlRef);
+ }
+ }
+ }
+ }
+#else // MAC_OS_X_VERSION_MIN_REQUIRED >= MAC_OS_X_VERSION_10_5
NSString *scriptSource =
[NSString stringWithFormat:
@"tell application \"System Events\" to delete (login items whose path is \"%s\")",
[path UTF8String]];
[self compileAndRunScript:scriptSource withError:nil];
+#endif // MAC_OS_X_VERSION_MIN_REQUIRED >= MAC_OS_X_VERSION_10_5
}
+ (void)removeItemWithNameFromLoginItems:(NSString *)name {
if ([name length] == 0) return;
+#if MAC_OS_X_VERSION_MIN_REQUIRED >= MAC_OS_X_VERSION_10_5
+ LSSharedFileListRef loginItemsRef = [self loginItemsFileListRef];
+ if (loginItemsRef) {
+ NSArray *fileList = [self loginItemsArrayForFileListRef:loginItemsRef];
+ for (id item in fileList) {
+ LSSharedFileListItemRef itemRef = (LSSharedFileListItemRef)item;
+ CFStringRef itemNameRef = LSSharedFileListItemCopyDisplayName(itemRef);
+ if (itemNameRef) {
+ NSString *itemName =
+ [(NSString *)itemNameRef stringByDeletingPathExtension];
+ if ([itemName isEqual:name]) {
+ LSSharedFileListItemRemove(loginItemsRef, itemRef);
+ }
+ CFRelease(itemNameRef);
+ }
+ }
+ }
+#else // MAC_OS_X_VERSION_MIN_REQUIRED >= MAC_OS_X_VERSION_10_5
NSString *scriptSource =
[NSString stringWithFormat:
@"tell application \"System Events\" to delete (login items whose name is \"%s\")",
[name UTF8String]];
[self compileAndRunScript:scriptSource withError:nil];
+#endif // MAC_OS_X_VERSION_MIN_REQUIRED >= MAC_OS_X_VERSION_10_5
}
@end