簡體   English   中英

如何通過Qt應用在OS X上使用Login Items API?

[英]How to use the Login Items API on OS X from a Qt app?

我希望我的應用程序在此列表中注冊自己:

System Preferences -> Accounts -> (your name) -> Login Items

我了解到,執行此操作的方法是使用LSSharedFileList.h進行一些函數調用來執行此操作。 當我嘗試這樣做時:

#include <LSSharedFileList.h>

我懂了

fatal error: 'LSSharedFileList.h' file not found

搜索我的硬盤驅動器,我看到此文件在這里:

/System/Library/Frameworks/CoreServices.framework/Versions/A/Frameworks/LaunchServices.framework/Versions/A/Headers/LSSharedFileList.h

是否需要在.pro文件中添加一些內容才能檢測到此框架? 我注意到,如果對已構建的可執行文件執行otool -L ,則會鏈接以下框架:

/System/Library/Frameworks/ApplicationServices.framework/Versions/A/ApplicationServices (compatibility version 1.0.0, current version 48.0.0)
/System/Library/Frameworks/CoreServices.framework/Versions/A/CoreServices (compatibility version 1.0.0, current version 62.0.0)

所以我有一個不知道如何獲取構建系統來查找頭文件的問題。

最重要的是,C ++ / Qt代碼演示了如何將應用程序添加到“登錄項”列表中,以及如何將其從列表中刪除。

這是到目前為止我得到的。 我對硬編碼的包含路徑不滿意。 .pro文件中:

INCLUDEPATH +=\
    /System/Library/Frameworks/CoreServices.framework/Versions/A/Frameworks/LaunchServices.framework/Versions/A/Headers

然后是安裝“登錄項”條目的代碼:

void installRunOnLoginHook(QString app_path) {
    QString app_name = QApplication::instance()->applicationName();
    QByteArray app_path_byte_array = app_path.toLocal8Bit();
    CFURLRef url = CFURLCreateFromFileSystemRepresentation(
        NULL, (const UInt8 *)app_path_byte_array.constData(), app_path_byte_array.size(), false);
    if (!url) {
        qWarning("unable to create CFURLRef");
        return;
    }
    LSSharedFileListRef login_items = LSSharedFileListCreate(NULL, kLSSharedFileListSessionLoginItems, NULL);
    if (!login_items) {
        qWarning("unable to get login items");
        return;
    }

    CFArrayRef login_items_array = LSSharedFileListCopySnapshot(login_items, NULL);
    if (!login_items_array) {
        qWarning("unable to get login items array");
        CFRelease(login_items);
        return;
    }
    CFIndex count = CFArrayGetCount(login_items_array);
    CFStringRef url_string = CFURLGetString(url);
    CFURLRef item_url = NULL;
    for (CFIndex i = 0; i < count; i += 1) {
        LSSharedFileListItemRef item = (LSSharedFileListItemRef) CFArrayGetValueAtIndex(login_items_array, i);
        if (LSSharedFileListItemResolve(item, 0, &item_url, NULL) != 0) {
            qWarning("unable to resolve login item");
            CFRelease(login_items_array);
            CFRelease(login_items);
            return;
        }
        CFStringRef item_url_string = CFURLGetString(item_url);
        CFComparisonResult result = CFStringCompare(url_string, item_url_string, 0);
        CFRelease(item_url);
        if (result == kCFCompareEqualTo) {
            qWarning("found in login items already");
            CFRelease(login_items_array);
            CFRelease(login_items);
            return;
        }
    }

    LSSharedFileListItemRef item = LSSharedFileListInsertItemURL(
        login_items, kLSSharedFileListItemLast, app_name.toCFString(), NULL, url, NULL, NULL);
    if (!item) {
        qWarning("Unable to add to login items");
        CFRelease(login_items_array);
        CFRelease(login_items);
        return;
    }
    CFRelease(item);
    CFRelease(login_items_array);
    CFRelease(login_items);
}

嘗試將以下內容放入您的.pro文件:

macx {
    LIBS += -framework CoreServices
}

並添加到包括:

#include <CoreServices/CoreServices.h>

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM