From be1ea0e94a2dde9505a6ff4a7d3f7fdf72fd4951 Mon Sep 17 00:00:00 2001 From: Matthew Date: Sat, 5 Nov 2022 21:37:50 +0000 Subject: [PATCH] 2.1 --- .../obj/debug/arm64/trolltoolsroothelper | Bin 67416 -> 100520 bytes .../Resources/DWARF/trolltoolsroothelper | Bin 10405 -> 58917 bytes .../.theos/obj/debug/trolltoolsroothelper | Bin 86608 -> 120864 bytes RootHelper/CoreServices.h | 58 +++ RootHelper/RemoteLog.h | 57 +++ RootHelper/TSUtil.h | 61 +++ RootHelper/TSUtil.m | 450 ++++++++++++++++++ RootHelper/main.m | 189 ++------ RootHelper/uicache.h | 1 + RootHelper/uicache.m | 263 ++++++++++ TrollTools.xcodeproj/project.pbxproj | 8 + .../UserInterfaceState.xcuserstate | Bin 148711 -> 167679 bytes .../Assets.xcassets/64.imageset/Contents.json | 21 + .../64.imageset/TrollUtils.png | Bin 0 -> 3504 bytes .../NotFound.imageset/Contents.json | 21 + .../NotFound.imageset/NotFound.png | Bin 0 -> 2141 bytes TrollTools/Other/Extensions.swift | 13 + TrollTools/Other/ProblemReporter.swift | 12 +- TrollTools/Other/RemoteLog.h | 2 +- TrollTools/Other/TrollToolsApp.swift | 1 + TrollTools/Private APIs/BadgeChanger.swift | 30 ++ .../Private APIs/PasscodeKeyFaceManager.swift | 6 +- TrollTools/Private APIs/RootHelper.swift | 6 +- .../Themes/CatalogThemeManager.swift | 116 ++--- .../Private APIs/Themes/ThemeManager.swift | 193 ++++++-- .../Themes/WebclipsThemeManager.swift | 108 +++-- TrollTools/RootView.swift | 3 + TrollTools/Views/BadgeChangerView.swift | 55 ++- TrollTools/Views/PasscodeEditorView.swift | 7 +- .../Views/Themes/AltIconSelectionView.swift | 56 +++ .../Views/Themes/IconOverridesView.swift | 126 +++++ .../Themes/IndividualIconsEditorView.swift | 113 +++++ TrollTools/Views/Themes/ThemeView.swift | 29 +- .../Views/Themes/ThemesSettingsView.swift | 72 +-- TrollTools/Views/Themes/ThemesView.swift | 217 ++++++--- build.command | 4 +- entitlements.plist | 2 +- 37 files changed, 1851 insertions(+), 449 deletions(-) create mode 100644 RootHelper/CoreServices.h create mode 100644 RootHelper/RemoteLog.h create mode 100644 RootHelper/TSUtil.h create mode 100644 RootHelper/TSUtil.m create mode 100644 RootHelper/uicache.h create mode 100644 RootHelper/uicache.m create mode 100644 TrollTools/Assets.xcassets/64.imageset/Contents.json create mode 100644 TrollTools/Assets.xcassets/64.imageset/TrollUtils.png create mode 100644 TrollTools/Assets.xcassets/NotFound.imageset/Contents.json create mode 100644 TrollTools/Assets.xcassets/NotFound.imageset/NotFound.png create mode 100644 TrollTools/Views/Themes/AltIconSelectionView.swift create mode 100644 TrollTools/Views/Themes/IconOverridesView.swift create mode 100644 TrollTools/Views/Themes/IndividualIconsEditorView.swift diff --git a/RootHelper/.theos/obj/debug/arm64/trolltoolsroothelper b/RootHelper/.theos/obj/debug/arm64/trolltoolsroothelper index 92a568de6911cdc533de9050e514adb6d7ae58c9..7fde8fa6d153d76165d7a0fe8a41cbc40f03aa1d 100755 GIT binary patch literal 100520 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 Ce>l(p literal 10405 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 diff --git a/RootHelper/.theos/obj/debug/trolltoolsroothelper b/RootHelper/.theos/obj/debug/trolltoolsroothelper index a5f7f26def9be2908e7026c3048c3738ea7be24b..31f03d86506590c2213472d4c26b26bb64809ed2 100755 GIT binary patch literal 120864 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 literal 86608 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 CD*Ai? diff --git a/RootHelper/CoreServices.h b/RootHelper/CoreServices.h new file mode 100644 index 0000000..e80af10 --- /dev/null +++ b/RootHelper/CoreServices.h @@ -0,0 +1,58 @@ +@interface LSBundleProxy +@property (nonatomic,readonly) NSString * bundleIdentifier; +@property (nonatomic) NSURL* dataContainerURL; +-(NSString*)localizedName; +@end + +@interface LSApplicationProxy : LSBundleProxy ++ (instancetype)applicationProxyForIdentifier:(NSString*)identifier; +@property NSURL* bundleURL; +@property NSString* bundleType; +@property NSString* canonicalExecutablePath; +@property (nonatomic,readonly) NSDictionary* groupContainerURLs; +@property (nonatomic,readonly) NSArray* plugInKitPlugins; +@property (getter=isInstalled,nonatomic,readonly) BOOL installed; +@property (getter=isPlaceholder,nonatomic,readonly) BOOL placeholder; +@property (getter=isRestricted,nonatomic,readonly) BOOL restricted; +@property (nonatomic,readonly) NSSet * claimedURLSchemes; +@end + +@interface LSApplicationWorkspace : NSObject ++ (instancetype)defaultWorkspace; +- (BOOL)registerApplicationDictionary:(NSDictionary*)dict; +- (BOOL)unregisterApplication:(id)arg1; +- (BOOL)_LSPrivateRebuildApplicationDatabasesForSystemApps:(BOOL)arg1 internal:(BOOL)arg2 user:(BOOL)arg3; +- (BOOL)uninstallApplication:(NSString*)arg1 withOptions:(id)arg2; +- (BOOL)openApplicationWithBundleID:(NSString *)arg1 ; +- (void)enumerateApplicationsOfType:(NSUInteger)type block:(void (^)(LSApplicationProxy*))block; +@end + +@interface LSEnumerator : NSEnumerator +@property (nonatomic,copy) NSPredicate * predicate; ++ (instancetype)enumeratorForApplicationProxiesWithOptions:(NSUInteger)options; +@end + +@interface LSPlugInKitProxy : LSBundleProxy +@property (nonatomic,readonly) NSString* pluginIdentifier; +@property (nonatomic,readonly) NSDictionary * pluginKitDictionary; ++ (instancetype)pluginKitProxyForIdentifier:(NSString*)arg1; +@end + +@interface MCMContainer : NSObject ++ (id)containerWithIdentifier:(id)arg1 createIfNecessary:(BOOL)arg2 existed:(BOOL*)arg3 error:(id*)arg4; +@property (nonatomic,readonly) NSURL * url; +@end + +@interface MCMDataContainer : MCMContainer + +@end + +@interface MCMAppDataContainer : MCMDataContainer + +@end + +@interface MCMAppContainer : MCMContainer +@end + +@interface MCMPluginKitPluginDataContainer : MCMDataContainer +@end \ No newline at end of file diff --git a/RootHelper/RemoteLog.h b/RootHelper/RemoteLog.h new file mode 100644 index 0000000..70835d6 --- /dev/null +++ b/RootHelper/RemoteLog.h @@ -0,0 +1,57 @@ +#ifndef _REMOTE_LOG_H_ +#define _REMOTE_LOG_H_ + +#import +#import +#import +#import + +// change this to match your destination (server) IP address +#define RLOG_IP_ADDRESS "192.168.0.24" +#define RLOG_PORT 11909 + +__attribute__((unused)) static void RLogv(NSString* format, va_list args) +{ + NSString* str = [[NSString alloc] initWithFormat:format arguments:args]; + + int sd = socket(PF_INET, SOCK_DGRAM, IPPROTO_UDP); + if (sd <= 0) + { + NSLog(@"[RemoteLog] Error: Could not open socket"); + return; + } + + int broadcastEnable = 1; + int ret = setsockopt(sd, SOL_SOCKET, SO_BROADCAST, &broadcastEnable, sizeof(broadcastEnable)); + if (ret) + { + NSLog(@"[RemoteLog] Error: Could not open set socket to broadcast mode"); + close(sd); + return; + } + + struct sockaddr_in broadcastAddr; + memset(&broadcastAddr, 0, sizeof broadcastAddr); + broadcastAddr.sin_family = AF_INET; + inet_pton(AF_INET, RLOG_IP_ADDRESS, &broadcastAddr.sin_addr); + broadcastAddr.sin_port = htons(RLOG_PORT); + + char* request = (char*)[str UTF8String]; + ret = sendto(sd, request, strlen(request), 0, (struct sockaddr*)&broadcastAddr, sizeof broadcastAddr); + if (ret < 0) + { + NSLog(@"[RemoteLog] Error: Could not send broadcast"); + close(sd); + return; + } + close(sd); +} + +__attribute__((unused)) static void RLog(NSString* format, ...) +{ + va_list args; + va_start(args, format); + RLogv(format, args); + va_end(args); +} +#endif diff --git a/RootHelper/TSUtil.h b/RootHelper/TSUtil.h new file mode 100644 index 0000000..1fc0bcc --- /dev/null +++ b/RootHelper/TSUtil.h @@ -0,0 +1,61 @@ +@import Foundation; +#import "CoreServices.h" + +#define TrollStoreErrorDomain @"TrollStoreErrorDomain" + +extern void chineseWifiFixup(void); +extern void loadMCMFramework(void); +extern NSString* safe_getExecutablePath(); +extern NSString* rootHelperPath(void); +extern NSString* getNSStringFromFile(int fd); +extern void printMultilineNSString(NSString* stringToPrint); +extern int spawnRoot(NSString* path, NSArray* args, NSString** stdOut, NSString** stdErr); +extern void killall(NSString* processName); +extern void respring(void); +extern void fetchLatestTrollStoreVersion(void (^completionHandler)(NSString* latestVersion)); + +extern NSArray* trollStoreInstalledAppBundlePaths(); +extern NSArray* trollStoreInstalledAppContainerPaths(); +extern NSString* trollStorePath(); +extern NSString* trollStoreAppPath(); + +#import + +@interface UIAlertController (Private) +@property (setter=_setAttributedTitle:,getter=_attributedTitle,nonatomic,copy) NSAttributedString* attributedTitle; +@property (setter=_setAttributedMessage:,getter=_attributedMessage,nonatomic,copy) NSAttributedString* attributedMessage; +@property (nonatomic,retain) UIImage* image; +@end + +typedef enum +{ + PERSISTENCE_HELPER_TYPE_USER = 1 << 0, + PERSISTENCE_HELPER_TYPE_SYSTEM = 1 << 1, + PERSISTENCE_HELPER_TYPE_ALL = PERSISTENCE_HELPER_TYPE_USER | PERSISTENCE_HELPER_TYPE_SYSTEM +} PERSISTENCE_HELPER_TYPE; + +extern LSApplicationProxy* findPersistenceHelperApp(PERSISTENCE_HELPER_TYPE allowedTypes); + +typedef struct __SecCode const *SecStaticCodeRef; + +typedef CF_OPTIONS(uint32_t, SecCSFlags) { + kSecCSDefaultFlags = 0 +}; +#define kSecCSRequirementInformation 1 << 2 +#define kSecCSSigningInformation 1 << 1 + +OSStatus SecStaticCodeCreateWithPathAndAttributes(CFURLRef path, SecCSFlags flags, CFDictionaryRef attributes, SecStaticCodeRef *staticCode); +OSStatus SecCodeCopySigningInformation(SecStaticCodeRef code, SecCSFlags flags, CFDictionaryRef *information); +CFDataRef SecCertificateCopyExtensionValue(SecCertificateRef certificate, CFTypeRef extensionOID, bool *isCritical); +void SecPolicySetOptionsValue(SecPolicyRef policy, CFStringRef key, CFTypeRef value); + +extern CFStringRef kSecCodeInfoEntitlementsDict; +extern CFStringRef kSecCodeInfoCertificates; +extern CFStringRef kSecPolicyAppleiPhoneApplicationSigning; +extern CFStringRef kSecPolicyAppleiPhoneProfileApplicationSigning; +extern CFStringRef kSecPolicyLeafMarkerOid; + +extern SecStaticCodeRef getStaticCodeRef(NSString *binaryPath); +extern NSDictionary* dumpEntitlements(SecStaticCodeRef codeRef); +extern NSDictionary* dumpEntitlementsFromBinaryAtPath(NSString *binaryPath); +extern NSDictionary* dumpEntitlementsFromBinaryData(NSData* binaryData); \ No newline at end of file diff --git a/RootHelper/TSUtil.m b/RootHelper/TSUtil.m new file mode 100644 index 0000000..a6617e4 --- /dev/null +++ b/RootHelper/TSUtil.m @@ -0,0 +1,450 @@ +#import "TSUtil.h" + +#import +#import +#import + +@interface PSAppDataUsagePolicyCache : NSObject ++ (instancetype)sharedInstance; +- (void)setUsagePoliciesForBundle:(NSString*)bundleId cellular:(BOOL)cellular wifi:(BOOL)wifi; +@end + +#define POSIX_SPAWN_PERSONA_FLAGS_OVERRIDE 1 +extern int posix_spawnattr_set_persona_np(const posix_spawnattr_t* __restrict, uid_t, uint32_t); +extern int posix_spawnattr_set_persona_uid_np(const posix_spawnattr_t* __restrict, uid_t); +extern int posix_spawnattr_set_persona_gid_np(const posix_spawnattr_t* __restrict, uid_t); + +void chineseWifiFixup(void) +{ + NSBundle *bundle = [NSBundle bundleWithPath:@"/System/Library/PrivateFrameworks/SettingsCellular.framework"]; + [bundle load]; + [[NSClassFromString(@"PSAppDataUsagePolicyCache") sharedInstance] setUsagePoliciesForBundle:NSBundle.mainBundle.bundleIdentifier cellular:true wifi:true]; +} + +void loadMCMFramework(void) +{ + static dispatch_once_t onceToken; + dispatch_once (&onceToken, ^{ + NSBundle* mcmBundle = [NSBundle bundleWithPath:@"/System/Library/PrivateFrameworks/MobileContainerManager.framework"]; + [mcmBundle load]; + }); +} + +extern char*** _NSGetArgv(); +NSString* safe_getExecutablePath() +{ + char* executablePathC = **_NSGetArgv(); + return [NSString stringWithUTF8String:executablePathC]; +} + +#ifdef EMBEDDED_ROOT_HELPER +NSString* rootHelperPath(void) +{ + return safe_getExecutablePath(); +} +#else +NSString* rootHelperPath(void) +{ + return [[NSBundle mainBundle].bundlePath stringByAppendingPathComponent:@"trollstorehelper"]; +} +#endif + +NSString* getNSStringFromFile(int fd) +{ + NSMutableString* ms = [NSMutableString new]; + ssize_t num_read; + char c; + while((num_read = read(fd, &c, sizeof(c)))) + { + [ms appendString:[NSString stringWithFormat:@"%c", c]]; + } + return ms.copy; +} + +void printMultilineNSString(NSString* stringToPrint) +{ + NSCharacterSet *separator = [NSCharacterSet newlineCharacterSet]; + NSArray* lines = [stringToPrint componentsSeparatedByCharactersInSet:separator]; + for(NSString* line in lines) + { + NSLog(@"%@", line); + } +} + +int spawnRoot(NSString* path, NSArray* args, NSString** stdOut, NSString** stdErr) +{ + NSMutableArray* argsM = args.mutableCopy ?: [NSMutableArray new]; + [argsM insertObject:path.lastPathComponent atIndex:0]; + + NSUInteger argCount = [argsM count]; + char **argsC = (char **)malloc((argCount + 1) * sizeof(char*)); + + for (NSUInteger i = 0; i < argCount; i++) + { + argsC[i] = strdup([[argsM objectAtIndex:i] UTF8String]); + } + argsC[argCount] = NULL; + + posix_spawnattr_t attr; + posix_spawnattr_init(&attr); + + posix_spawnattr_set_persona_np(&attr, 99, POSIX_SPAWN_PERSONA_FLAGS_OVERRIDE); + posix_spawnattr_set_persona_uid_np(&attr, 0); + posix_spawnattr_set_persona_gid_np(&attr, 0); + + posix_spawn_file_actions_t action; + posix_spawn_file_actions_init(&action); + + int outErr[2]; + if(stdErr) + { + pipe(outErr); + posix_spawn_file_actions_adddup2(&action, outErr[1], STDERR_FILENO); + posix_spawn_file_actions_addclose(&action, outErr[0]); + } + + int out[2]; + if(stdOut) + { + pipe(out); + posix_spawn_file_actions_adddup2(&action, out[1], STDOUT_FILENO); + posix_spawn_file_actions_addclose(&action, out[0]); + } + + pid_t task_pid; + int status = -200; + int spawnError = posix_spawn(&task_pid, [path UTF8String], &action, &attr, (char* const*)argsC, NULL); + posix_spawnattr_destroy(&attr); + for (NSUInteger i = 0; i < argCount; i++) + { + free(argsC[i]); + } + free(argsC); + + if(spawnError != 0) + { + NSLog(@"posix_spawn error %d\n", spawnError); + return spawnError; + } + + do + { + if (waitpid(task_pid, &status, 0) != -1) { + NSLog(@"Child status %d", WEXITSTATUS(status)); + } else + { + perror("waitpid"); + return -222; + } + } while (!WIFEXITED(status) && !WIFSIGNALED(status)); + + if(stdOut) + { + close(out[1]); + NSString* output = getNSStringFromFile(out[0]); + *stdOut = output; + } + + if(stdErr) + { + close(outErr[1]); + NSString* errorOutput = getNSStringFromFile(outErr[0]); + *stdErr = errorOutput; + } + + return WEXITSTATUS(status); +} + +void enumerateProcessesUsingBlock(void (^enumerator)(pid_t pid, NSString* executablePath, BOOL* stop)) +{ + static int maxArgumentSize = 0; + if (maxArgumentSize == 0) { + size_t size = sizeof(maxArgumentSize); + if (sysctl((int[]){ CTL_KERN, KERN_ARGMAX }, 2, &maxArgumentSize, &size, NULL, 0) == -1) { + perror("sysctl argument size"); + maxArgumentSize = 4096; // Default + } + } + int mib[3] = { CTL_KERN, KERN_PROC, KERN_PROC_ALL}; + struct kinfo_proc *info; + size_t length; + int count; + + if (sysctl(mib, 3, NULL, &length, NULL, 0) < 0) + return; + if (!(info = malloc(length))) + return; + if (sysctl(mib, 3, info, &length, NULL, 0) < 0) { + free(info); + return; + } + count = length / sizeof(struct kinfo_proc); + for (int i = 0; i < count; i++) { + @autoreleasepool { + pid_t pid = info[i].kp_proc.p_pid; + if (pid == 0) { + continue; + } + size_t size = maxArgumentSize; + char* buffer = (char *)malloc(length); + if (sysctl((int[]){ CTL_KERN, KERN_PROCARGS2, pid }, 3, buffer, &size, NULL, 0) == 0) { + NSString* executablePath = [NSString stringWithCString:(buffer+sizeof(int)) encoding:NSUTF8StringEncoding]; + + BOOL stop = NO; + enumerator(pid, executablePath, &stop); + if(stop) + { + free(buffer); + break; + } + } + free(buffer); + } + } + free(info); +} + +void killall(NSString* processName) +{ + enumerateProcessesUsingBlock(^(pid_t pid, NSString* executablePath, BOOL* stop) + { + if([executablePath.lastPathComponent isEqualToString:processName]) + { + kill(pid, SIGTERM); + } + }); +} + +void respring(void) +{ + killall(@"SpringBoard"); + exit(0); +} + +void fetchLatestTrollStoreVersion(void (^completionHandler)(NSString* latestVersion)) +{ + NSURL* githubLatestAPIURL = [NSURL URLWithString:@"https://api.github.com/repos/opa334/TrollStore/releases/latest"]; + + NSURLSessionDataTask* task = [NSURLSession.sharedSession dataTaskWithURL:githubLatestAPIURL completionHandler:^(NSData *data, NSURLResponse *response, NSError *error) + { + if(!error) + { + if ([response isKindOfClass:[NSHTTPURLResponse class]]) + { + NSError *jsonError; + NSDictionary *jsonResponse = [NSJSONSerialization JSONObjectWithData:data options:0 error:&jsonError]; + + if (!jsonError) + { + completionHandler(jsonResponse[@"tag_name"]); + } + } + } + }]; + + [task resume]; +} + +NSArray* trollStoreInstalledAppContainerPaths() +{ + NSMutableArray* appContainerPaths = [NSMutableArray new]; + + NSString* appContainersPath = @"/var/containers/Bundle/Application"; + + NSError* error; + NSArray* containers = [[NSFileManager defaultManager] contentsOfDirectoryAtPath:appContainersPath error:&error]; + if(error) + { + NSLog(@"error getting app bundles paths %@", error); + } + if(!containers) return nil; + + for(NSString* container in containers) + { + NSString* containerPath = [appContainersPath stringByAppendingPathComponent:container]; + BOOL isDirectory = NO; + BOOL exists = [[NSFileManager defaultManager] fileExistsAtPath:containerPath isDirectory:&isDirectory]; + if(exists && isDirectory) + { + NSString* trollStoreMark = [containerPath stringByAppendingPathComponent:@"_TrollStore"]; + if([[NSFileManager defaultManager] fileExistsAtPath:trollStoreMark]) + { + NSString* trollStoreApp = [containerPath stringByAppendingPathComponent:@"TrollStore.app"]; + if(![[NSFileManager defaultManager] fileExistsAtPath:trollStoreApp]) + { + [appContainerPaths addObject:containerPath]; + } + } + } + } + + return appContainerPaths.copy; +} + +NSArray* trollStoreInstalledAppBundlePaths() +{ + NSMutableArray* appPaths = [NSMutableArray new]; + for(NSString* containerPath in trollStoreInstalledAppContainerPaths()) + { + NSArray* items = [[NSFileManager defaultManager] contentsOfDirectoryAtPath:containerPath error:nil]; + if(!items) return nil; + + for(NSString* item in items) + { + if([item.pathExtension isEqualToString:@"app"]) + { + [appPaths addObject:[containerPath stringByAppendingPathComponent:item]]; + } + } + } + return appPaths.copy; +} + +NSString* trollStorePath() +{ + loadMCMFramework(); + NSError* mcmError; + MCMAppContainer* appContainer = [NSClassFromString(@"MCMAppContainer") containerWithIdentifier:@"com.opa334.TrollStore" createIfNecessary:NO existed:NULL error:&mcmError]; + if(!appContainer) return nil; + return appContainer.url.path; +} + +NSString* trollStoreAppPath() +{ + return [trollStorePath() stringByAppendingPathComponent:@"TrollStore.app"]; +} + +LSApplicationProxy* findPersistenceHelperApp(PERSISTENCE_HELPER_TYPE allowedTypes) +{ + __block LSApplicationProxy* outProxy; + + void (^searchBlock)(LSApplicationProxy* appProxy) = ^(LSApplicationProxy* appProxy) + { + if(appProxy.installed && !appProxy.restricted) + { + if([appProxy.bundleURL.path hasPrefix:@"/private/var/containers"]) + { + NSURL* trollStorePersistenceMarkURL = [appProxy.bundleURL URLByAppendingPathComponent:@".TrollStorePersistenceHelper"]; + if([trollStorePersistenceMarkURL checkResourceIsReachableAndReturnError:nil]) + { + outProxy = appProxy; + } + } + } + }; + + if(allowedTypes & PERSISTENCE_HELPER_TYPE_USER) + { + [[LSApplicationWorkspace defaultWorkspace] enumerateApplicationsOfType:0 block:searchBlock]; + } + if(allowedTypes & PERSISTENCE_HELPER_TYPE_SYSTEM) + { + [[LSApplicationWorkspace defaultWorkspace] enumerateApplicationsOfType:1 block:searchBlock]; + } + + return outProxy; +} + +SecStaticCodeRef getStaticCodeRef(NSString *binaryPath) +{ + if(binaryPath == nil) + { + return NULL; + } + + CFURLRef binaryURL = CFURLCreateWithFileSystemPath(kCFAllocatorDefault, (__bridge CFStringRef)binaryPath, kCFURLPOSIXPathStyle, false); + if(binaryURL == NULL) + { + NSLog(@"[getStaticCodeRef] failed to get URL to binary %@", binaryPath); + return NULL; + } + + SecStaticCodeRef codeRef = NULL; + OSStatus result; + + result = SecStaticCodeCreateWithPathAndAttributes(binaryURL, kSecCSDefaultFlags, NULL, &codeRef); + + CFRelease(binaryURL); + + if(result != errSecSuccess) + { + NSLog(@"[getStaticCodeRef] failed to create static code for binary %@", binaryPath); + return NULL; + } + + return codeRef; +} + +NSDictionary* dumpEntitlements(SecStaticCodeRef codeRef) +{ + if(codeRef == NULL) + { + NSLog(@"[dumpEntitlements] attempting to dump entitlements without a StaticCodeRef"); + return nil; + } + + CFDictionaryRef signingInfo = NULL; + OSStatus result; + + result = SecCodeCopySigningInformation(codeRef, kSecCSRequirementInformation, &signingInfo); + + if(result != errSecSuccess) + { + NSLog(@"[dumpEntitlements] failed to copy signing info from static code"); + return nil; + } + + NSDictionary *entitlementsNSDict = nil; + + CFDictionaryRef entitlements = CFDictionaryGetValue(signingInfo, kSecCodeInfoEntitlementsDict); + if(entitlements == NULL) + { + NSLog(@"[dumpEntitlements] no entitlements specified"); + } + else if(CFGetTypeID(entitlements) != CFDictionaryGetTypeID()) + { + NSLog(@"[dumpEntitlements] invalid entitlements"); + } + else + { + entitlementsNSDict = (__bridge NSDictionary *)(entitlements); + NSLog(@"[dumpEntitlements] dumped %@", entitlementsNSDict); + } + + CFRelease(signingInfo); + return entitlementsNSDict; +} + +NSDictionary* dumpEntitlementsFromBinaryAtPath(NSString *binaryPath) +{ + // This function is intended for one-shot checks. Main-event functions should retain/release their own SecStaticCodeRefs + + if(binaryPath == nil) + { + return nil; + } + + SecStaticCodeRef codeRef = getStaticCodeRef(binaryPath); + if(codeRef == NULL) + { + return nil; + } + + NSDictionary *entitlements = dumpEntitlements(codeRef); + CFRelease(codeRef); + + return entitlements; +} + +NSDictionary* dumpEntitlementsFromBinaryData(NSData* binaryData) +{ + NSDictionary* entitlements; + NSString* tmpPath = [NSTemporaryDirectory() stringByAppendingPathComponent:[NSUUID UUID].UUIDString]; + NSURL* tmpURL = [NSURL fileURLWithPath:tmpPath]; + if([binaryData writeToURL:tmpURL options:NSDataWritingAtomic error:nil]) + { + entitlements = dumpEntitlementsFromBinaryAtPath(tmpPath); + [[NSFileManager defaultManager] removeItemAtURL:tmpURL error:nil]; + } + return entitlements; +} \ No newline at end of file diff --git a/RootHelper/main.m b/RootHelper/main.m index 2bd0320..ed184cf 100644 --- a/RootHelper/main.m +++ b/RootHelper/main.m @@ -11,84 +11,6 @@ #import #import -typedef CF_OPTIONS(uint32_t, SecCSFlags) { - kSecCSDefaultFlags = 0 -}; -#define kSecCSRequirementInformation 1 << 2 -extern CFStringRef kSecCodeInfoEntitlementsDict; - -typedef struct __SecCode const *SecStaticCodeRef; -OSStatus SecStaticCodeCreateWithPathAndAttributes(CFURLRef path, SecCSFlags flags, CFDictionaryRef attributes, SecStaticCodeRef *staticCode); -OSStatus SecCodeCopySigningInformation(SecStaticCodeRef code, SecCSFlags flags, CFDictionaryRef *information); - -NSDictionary* dumpEntitlements(SecStaticCodeRef codeRef) -{ - if(codeRef == NULL) - { - NSLog(@"[dumpEntitlements] attempting to dump entitlements without a StaticCodeRef"); - return nil; - } - - CFDictionaryRef signingInfo = NULL; - OSStatus result; - - result = SecCodeCopySigningInformation(codeRef, kSecCSRequirementInformation, &signingInfo); - - if(result != errSecSuccess) - { - NSLog(@"[dumpEntitlements] failed to copy signing info from static code"); - return nil; - } - - NSDictionary *entitlementsNSDict = nil; - - CFDictionaryRef entitlements = CFDictionaryGetValue(signingInfo, kSecCodeInfoEntitlementsDict); - if(entitlements == NULL) - { - NSLog(@"[dumpEntitlements] no entitlements specified"); - } - else if(CFGetTypeID(entitlements) != CFDictionaryGetTypeID()) - { - NSLog(@"[dumpEntitlements] invalid entitlements"); - } - else - { - entitlementsNSDict = (__bridge NSDictionary *)(entitlements); - NSLog(@"[dumpEntitlements] dumped %@", entitlementsNSDict); - } - - CFRelease(signingInfo); - return entitlementsNSDict; -} -SecStaticCodeRef getStaticCodeRef(NSString *binaryPath) -{ - if(binaryPath == nil) - { - return NULL; - } - - CFURLRef binaryURL = CFURLCreateWithFileSystemPath(kCFAllocatorDefault, (__bridge CFStringRef)binaryPath, kCFURLPOSIXPathStyle, false); - if(binaryURL == NULL) - { - NSLog(@"[getStaticCodeRef] failed to get URL to binary %@", binaryPath); - return NULL; - } - - SecStaticCodeRef codeRef = NULL; - OSStatus result; - - result = SecStaticCodeCreateWithPathAndAttributes(binaryURL, kSecCSDefaultFlags, NULL, &codeRef); - - CFRelease(binaryURL); - - if(result != errSecSuccess) - { - NSLog(@"[getStaticCodeRef] failed to create static code for binary %@", binaryPath); - return NULL; - } - - return codeRef; -} NSSet* immutableAppBundleIdentifiers(void) { NSMutableSet* systemAppIdentifiers = [NSMutableSet new]; @@ -108,91 +30,68 @@ SecStaticCodeRef getStaticCodeRef(NSString *binaryPath) return systemAppIdentifiers.copy; } -NSDictionary* dumpEntitlementsFromBinaryAtPath(NSString *binaryPath) -{ - // This function is intended for one-shot checks. Main-event functions should retain/release their own SecStaticCodeRefs - - if(binaryPath == nil) - { - return nil; - } - - SecStaticCodeRef codeRef = getStaticCodeRef(binaryPath); - if(codeRef == NULL) - { - return nil; - } - - NSDictionary *entitlements = dumpEntitlements(codeRef); - CFRelease(codeRef); - - return entitlements; -} void refreshAppRegistrations() { - //registerPath((char*)trollStoreAppPath().UTF8String, 1); - registerPath((char*)trollStoreAppPath().UTF8String, 0); + registerPath((char*)trollStoreAppPath().UTF8String, 0, YES); for(NSString* appPath in trollStoreInstalledAppBundlePaths()) { - //registerPath((char*)appPath.UTF8String, 1); - registerPath((char*)appPath.UTF8String, 0); + registerPath((char*)appPath.UTF8String, 0, YES); } } -BOOL _installPersistenceHelper(LSApplicationProxy* appProxy, NSString* sourcePersistenceHelper, NSString* sourceRootHelper) +// Apparently there is some odd behaviour where TrollStore installed apps sometimes get restricted +// This works around that issue at least and is triggered when rebuilding icon cache +void cleanRestrictions(void) { - NSLog(@"_installPersistenceHelper(%@, %@, %@)", appProxy, sourcePersistenceHelper, sourceRootHelper); - - NSString* executablePath = appProxy.canonicalExecutablePath; - NSString* bundlePath = appProxy.bundleURL.path; - if(!executablePath) - { - NSBundle* appBundle = [NSBundle bundleWithPath:bundlePath]; - executablePath = [bundlePath stringByAppendingPathComponent:[appBundle objectForInfoDictionaryKey:@"CFBundleExecutable"]]; - } + NSString* clientTruthPath = @"/private/var/containers/Shared/SystemGroup/systemgroup.com.apple.configurationprofiles/Library/ConfigurationProfiles/ClientTruth.plist"; + NSURL* clientTruthURL = [NSURL fileURLWithPath:clientTruthPath]; + NSDictionary* clientTruthDictionary = [NSDictionary dictionaryWithContentsOfURL:clientTruthURL]; - NSString* markPath = [bundlePath stringByAppendingPathComponent:@".TrollStorePersistenceHelper"]; - NSString* rootHelperPath = [bundlePath stringByAppendingPathComponent:@"trollstorehelper"]; + if(!clientTruthDictionary) return; - // remove existing persistence helper binary if exists - if([[NSFileManager defaultManager] fileExistsAtPath:markPath] && [[NSFileManager defaultManager] fileExistsAtPath:executablePath]) - { - [[NSFileManager defaultManager] removeItemAtPath:executablePath error:nil]; - } + NSArray* valuesArr; - // remove existing root helper binary if exists - if([[NSFileManager defaultManager] fileExistsAtPath:rootHelperPath]) + NSDictionary* lsdAppRemoval = clientTruthDictionary[@"com.apple.lsd.appremoval"]; + if(lsdAppRemoval && [lsdAppRemoval isKindOfClass:NSDictionary.class]) { - [[NSFileManager defaultManager] removeItemAtPath:rootHelperPath error:nil]; + NSDictionary* clientRestrictions = lsdAppRemoval[@"clientRestrictions"]; + if(clientRestrictions && [clientRestrictions isKindOfClass:NSDictionary.class]) + { + NSDictionary* unionDict = clientRestrictions[@"union"]; + if(unionDict && [unionDict isKindOfClass:NSDictionary.class]) + { + NSDictionary* removedSystemAppBundleIDs = unionDict[@"removedSystemAppBundleIDs"]; + if(removedSystemAppBundleIDs && [removedSystemAppBundleIDs isKindOfClass:NSDictionary.class]) + { + valuesArr = removedSystemAppBundleIDs[@"values"]; + } + } + } } - // install new persistence helper binary - if(![[NSFileManager defaultManager] copyItemAtPath:sourcePersistenceHelper toPath:executablePath error:nil]) - { - return NO; - } + if(!valuesArr || !valuesArr.count) return; - chmod(executablePath.UTF8String, 0755); - chown(executablePath.UTF8String, 33, 33); + NSMutableArray* valuesArrM = valuesArr.mutableCopy; + __block BOOL changed = NO; - NSError* error; - if(![[NSFileManager defaultManager] copyItemAtPath:sourceRootHelper toPath:rootHelperPath error:&error]) + [valuesArrM enumerateObjectsWithOptions:NSEnumerationReverse usingBlock:^(NSString* value, NSUInteger idx, BOOL *stop) { - NSLog(@"error copying root helper: %@", error); - } + if(![value hasPrefix:@"com.apple."]) + { + [valuesArrM removeObjectAtIndex:idx]; + changed = YES; + } + }]; - chmod(rootHelperPath.UTF8String, 0755); - chown(rootHelperPath.UTF8String, 0, 0); + if(!changed) return; - // mark system app as persistence helper - if(![[NSFileManager defaultManager] fileExistsAtPath:markPath]) - { - [[NSFileManager defaultManager] createFileAtPath:markPath contents:[NSData data] attributes:nil]; - } + NSMutableDictionary* clientTruthDictionaryM = (__bridge_transfer NSMutableDictionary*)CFPropertyListCreateDeepCopy(kCFAllocatorDefault, (__bridge CFDictionaryRef)clientTruthDictionary, kCFPropertyListMutableContainersAndLeaves); + + clientTruthDictionaryM[@"com.apple.lsd.appremoval"][@"clientRestrictions"][@"union"][@"removedSystemAppBundleIDs"][@"values"] = valuesArrM; - return YES; + [clientTruthDictionaryM writeToURL:clientTruthURL error:nil]; } @@ -219,12 +118,12 @@ int main(int argc, char *argv[], char *envp[]) { [dict setObject:[NSNumber numberWithInt:511] forKey:NSFilePosixPermissions]; [[NSFileManager defaultManager] setAttributes:dict ofItemAtPath:source error:nil]; } else if ([action isEqual: @"rebuildiconcache"]) { - [[LSApplicationWorkspace defaultWorkspace] _LSPrivateRebuildApplicationDatabasesForSystemApps:YES internal:YES user:YES]; - refreshAppRegistrations(); // needed for trollstore apps still working after rebuilding, otherwise they won't launch - respring(); + cleanRestrictions(); + [[LSApplicationWorkspace defaultWorkspace] _LSPrivateRebuildApplicationDatabasesForSystemApps:YES internal:YES user:YES]; + refreshAppRegistrations(); + killall(@"backboardd"); } - // NSLog(@"%s", getuid() == 0 ? "root" : "user"); return 0; } } \ No newline at end of file diff --git a/RootHelper/uicache.h b/RootHelper/uicache.h new file mode 100644 index 0000000..128391e --- /dev/null +++ b/RootHelper/uicache.h @@ -0,0 +1 @@ +extern void registerPath(char *path, int unregister, BOOL system); \ No newline at end of file diff --git a/RootHelper/uicache.m b/RootHelper/uicache.m new file mode 100644 index 0000000..cc4e469 --- /dev/null +++ b/RootHelper/uicache.m @@ -0,0 +1,263 @@ +@import Foundation; +@import CoreServices; +#import "CoreServices.h" +#import +#import "dlfcn.h" + +// uicache on steroids + +extern NSSet* immutableAppBundleIdentifiers(void); +extern NSDictionary* dumpEntitlementsFromBinaryAtPath(NSString* binaryPath); + +NSDictionary* constructGroupsContainersForEntitlements(NSDictionary* entitlements, BOOL systemGroups) +{ + if(!entitlements) return nil; + + NSString* entitlementForGroups; + NSString* mcmClass; + if(systemGroups) + { + entitlementForGroups = @"com.apple.security.system-groups"; + mcmClass = @"MCMSystemDataContainer"; + } + else + { + entitlementForGroups = @"com.apple.security.application-groups"; + mcmClass = @"MCMSharedDataContainer"; + } + + NSArray* groupIDs = entitlements[entitlementForGroups]; + if(groupIDs && [groupIDs isKindOfClass:[NSArray class]]) + { + NSMutableDictionary* groupContainers = [NSMutableDictionary new]; + + for(NSString* groupID in groupIDs) + { + MCMContainer* container = [NSClassFromString(mcmClass) containerWithIdentifier:groupID createIfNecessary:YES existed:nil error:nil]; + if(container.url) + { + groupContainers[groupID] = container.url.path; + } + } + + return groupContainers.copy; + } + + return nil; +} + +BOOL constructContainerizationForEntitlements(NSDictionary* entitlements) +{ + NSNumber* noContainer = entitlements[@"com.apple.private.security.no-container"]; + if(noContainer && [noContainer isKindOfClass:[NSNumber class]]) + { + if(noContainer.boolValue) + { + return NO; + } + } + + NSNumber* containerRequired = entitlements[@"com.apple.private.security.container-required"]; + if(containerRequired && [containerRequired isKindOfClass:[NSNumber class]]) + { + if(!containerRequired.boolValue) + { + return NO; + } + } + + return YES; +} + +NSString* constructTeamIdentifierForEntitlements(NSDictionary* entitlements) +{ + NSString* teamIdentifier = entitlements[@"com.apple.developer.team-identifier"]; + if(teamIdentifier && [teamIdentifier isKindOfClass:[NSString class]]) + { + return teamIdentifier; + } + return nil; +} + +NSDictionary* constructEnvironmentVariablesForContainerPath(NSString* containerPath) +{ + NSString* tmpDir = [containerPath stringByAppendingPathComponent:@"tmp"]; + return @{ + @"CFFIXED_USER_HOME" : containerPath, + @"HOME" : containerPath, + @"TMPDIR" : tmpDir + }; +} + +void registerPath(char* cPath, int unregister, BOOL system) +{ + if(!cPath) return; + NSString* path = [NSString stringWithUTF8String:cPath]; + + LSApplicationWorkspace* workspace = [LSApplicationWorkspace defaultWorkspace]; + if(unregister && ![[NSFileManager defaultManager] fileExistsAtPath:path]) + { + LSApplicationProxy* app = [LSApplicationProxy applicationProxyForIdentifier:path]; + if(app.bundleURL) + { + path = [app bundleURL].path; + } + } + + path = [path stringByResolvingSymlinksInPath]; + + NSDictionary* appInfoPlist = [NSDictionary dictionaryWithContentsOfFile:[path stringByAppendingPathComponent:@"Info.plist"]]; + NSString* appBundleID = [appInfoPlist objectForKey:@"CFBundleIdentifier"]; + + if([immutableAppBundleIdentifiers() containsObject:appBundleID.lowercaseString]) return; + + if(appBundleID && !unregister) + { + MCMContainer* appContainer = [NSClassFromString(@"MCMAppDataContainer") containerWithIdentifier:appBundleID createIfNecessary:YES existed:nil error:nil]; + NSString* containerPath = [appContainer url].path; + + NSMutableDictionary* dictToRegister = [NSMutableDictionary dictionary]; + + // Add entitlements + + NSString* appExecutablePath = [path stringByAppendingPathComponent:appInfoPlist[@"CFBundleExecutable"]]; + NSDictionary* entitlements = dumpEntitlementsFromBinaryAtPath(appExecutablePath); + if(entitlements) + { + dictToRegister[@"Entitlements"] = entitlements; + } + + // Misc + + dictToRegister[@"ApplicationType"] = system ? @"System" : @"User"; + dictToRegister[@"CFBundleIdentifier"] = appBundleID; + dictToRegister[@"CodeInfoIdentifier"] = appBundleID; + dictToRegister[@"CompatibilityState"] = @0; + if(containerPath) + { + dictToRegister[@"Container"] = containerPath; + dictToRegister[@"EnvironmentVariables"] = constructEnvironmentVariablesForContainerPath(containerPath); + } + dictToRegister[@"IsDeletable"] = @0; + dictToRegister[@"Path"] = path; + dictToRegister[@"IsContainerized"] = @(constructContainerizationForEntitlements(entitlements)); + dictToRegister[@"SignerOrganization"] = @"Apple Inc."; + dictToRegister[@"SignatureVersion"] = @132352; + dictToRegister[@"SignerIdentity"] = @"Apple iPhone OS Application Signing"; + dictToRegister[@"IsAdHocSigned"] = @YES; + dictToRegister[@"LSInstallType"] = @1; + dictToRegister[@"HasMIDBasedSINF"] = @0; + dictToRegister[@"MissingSINF"] = @0; + dictToRegister[@"FamilyID"] = @0; + dictToRegister[@"IsOnDemandInstallCapable"] = @0; + + NSString* teamIdentifier = constructTeamIdentifierForEntitlements(entitlements); + if(teamIdentifier) dictToRegister[@"TeamIdentifier"] = teamIdentifier; + + // Add group containers + + NSDictionary* appGroupContainers = constructGroupsContainersForEntitlements(entitlements, NO); + NSDictionary* systemGroupContainers = constructGroupsContainersForEntitlements(entitlements, NO); + NSMutableDictionary* groupContainers = [NSMutableDictionary new]; + [groupContainers addEntriesFromDictionary:appGroupContainers]; + [groupContainers addEntriesFromDictionary:systemGroupContainers]; + if(groupContainers.count) + { + if(appGroupContainers.count) + { + dictToRegister[@"HasAppGroupContainers"] = @YES; + } + if(systemGroupContainers.count) + { + dictToRegister[@"HasSystemGroupContainers"] = @YES; + } + dictToRegister[@"GroupContainers"] = groupContainers.copy; + } + + // Add plugins + + NSString* pluginsPath = [path stringByAppendingPathComponent:@"PlugIns"]; + NSArray* plugins = [[NSFileManager defaultManager] contentsOfDirectoryAtPath:pluginsPath error:nil]; + + NSMutableDictionary* bundlePlugins = [NSMutableDictionary dictionary]; + for (NSString* pluginName in plugins) + { + NSString* pluginPath = [pluginsPath stringByAppendingPathComponent:pluginName]; + + NSDictionary* pluginInfoPlist = [NSDictionary dictionaryWithContentsOfFile:[pluginPath stringByAppendingPathComponent:@"Info.plist"]]; + NSString* pluginBundleID = [pluginInfoPlist objectForKey:@"CFBundleIdentifier"]; + + if(!pluginBundleID) continue; + MCMContainer* pluginContainer = [NSClassFromString(@"MCMPluginKitPluginDataContainer") containerWithIdentifier:pluginBundleID createIfNecessary:YES existed:nil error:nil]; + NSString* pluginContainerPath = [pluginContainer url].path; + + NSMutableDictionary* pluginDict = [NSMutableDictionary dictionary]; + + // Add entitlements + + NSString* pluginExecutablePath = [pluginPath stringByAppendingPathComponent:pluginInfoPlist[@"CFBundleExecutable"]]; + NSDictionary* pluginEntitlements = dumpEntitlementsFromBinaryAtPath(pluginExecutablePath); + if(pluginEntitlements) + { + pluginDict[@"Entitlements"] = pluginEntitlements; + } + + // Misc + + pluginDict[@"ApplicationType"] = @"PluginKitPlugin"; + pluginDict[@"CFBundleIdentifier"] = pluginBundleID; + pluginDict[@"CodeInfoIdentifier"] = pluginBundleID; + pluginDict[@"CompatibilityState"] = @0; + if(pluginContainerPath) + { + pluginDict[@"Container"] = pluginContainerPath; + pluginDict[@"EnvironmentVariables"] = constructEnvironmentVariablesForContainerPath(pluginContainerPath); + } + pluginDict[@"Path"] = pluginPath; + pluginDict[@"PluginOwnerBundleID"] = appBundleID; + pluginDict[@"IsContainerized"] = @(constructContainerizationForEntitlements(pluginEntitlements)); + pluginDict[@"SignerOrganization"] = @"Apple Inc."; + pluginDict[@"SignatureVersion"] = @132352; + pluginDict[@"SignerIdentity"] = @"Apple iPhone OS Application Signing"; + + NSString* pluginTeamIdentifier = constructTeamIdentifierForEntitlements(pluginEntitlements); + if(pluginTeamIdentifier) pluginDict[@"TeamIdentifier"] = pluginTeamIdentifier; + + // Add plugin group containers + + NSDictionary* pluginAppGroupContainers = constructGroupsContainersForEntitlements(pluginEntitlements, NO); + NSDictionary* pluginSystemGroupContainers = constructGroupsContainersForEntitlements(pluginEntitlements, NO); + NSMutableDictionary* pluginGroupContainers = [NSMutableDictionary new]; + [pluginGroupContainers addEntriesFromDictionary:pluginAppGroupContainers]; + [pluginGroupContainers addEntriesFromDictionary:pluginSystemGroupContainers]; + if(pluginGroupContainers.count) + { + if(pluginAppGroupContainers.count) + { + pluginDict[@"HasAppGroupContainers"] = @YES; + } + if(pluginSystemGroupContainers.count) + { + pluginDict[@"HasSystemGroupContainers"] = @YES; + } + pluginDict[@"GroupContainers"] = pluginGroupContainers.copy; + } + + [bundlePlugins setObject:pluginDict forKey:pluginBundleID]; + } + [dictToRegister setObject:bundlePlugins forKey:@"_LSBundlePlugins"]; + + if(![workspace registerApplicationDictionary:dictToRegister]) + { + NSLog(@"Error: Unable to register %@", path); + } + } + else + { + NSURL* url = [NSURL fileURLWithPath:path]; + if(![workspace unregisterApplication:url]) + { + NSLog(@"Error: Unable to unregister %@", path); + } + } +} diff --git a/TrollTools.xcodeproj/project.pbxproj b/TrollTools.xcodeproj/project.pbxproj index 2e7a4b5..111aa74 100644 --- a/TrollTools.xcodeproj/project.pbxproj +++ b/TrollTools.xcodeproj/project.pbxproj @@ -32,6 +32,8 @@ CE7D5CFD2906C2BD00EA26D2 /* FSOperations in Frameworks */ = {isa = PBXBuildFile; productRef = CE7D5CFC2906C2BD00EA26D2 /* FSOperations */; }; CE7D5D1D290706C600EA26D2 /* NSTask in Frameworks */ = {isa = PBXBuildFile; productRef = CE7D5D1C290706C600EA26D2 /* NSTask */; }; CE8DC8D52904C22500A1CBB0 /* RootHelper.swift in Sources */ = {isa = PBXBuildFile; fileRef = CE8DC8D42904C22500A1CBB0 /* RootHelper.swift */; }; + CEECE830290C496D007E9496 /* IconOverridesView.swift in Sources */ = {isa = PBXBuildFile; fileRef = CEECE82F290C496D007E9496 /* IconOverridesView.swift */; }; + CEECE832290C5405007E9496 /* AltIconSelectionView.swift in Sources */ = {isa = PBXBuildFile; fileRef = CEECE831290C5405007E9496 /* AltIconSelectionView.swift */; }; CEFE362E2904AC6400938D98 /* TSUtil.m in Sources */ = {isa = PBXBuildFile; fileRef = CEFE36292904AC6400938D98 /* TSUtil.m */; }; CEFE36632904AF8C00938D98 /* Dynamic in Frameworks */ = {isa = PBXBuildFile; productRef = CEFE36622904AF8C00938D98 /* Dynamic */; }; CEFE36642904B27B00938D98 /* CoreServices.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = CE2BF83E2902E18900AD10BE /* CoreServices.framework */; }; @@ -65,6 +67,8 @@ CE76386C290AED160099C6F0 /* ProblemReporter.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = ProblemReporter.swift; sourceTree = ""; }; CE7D5D2229070FA600EA26D2 /* entitlements.plist */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = text.plist.xml; path = entitlements.plist; sourceTree = ""; }; CE8DC8D42904C22500A1CBB0 /* RootHelper.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = RootHelper.swift; sourceTree = ""; }; + CEECE82F290C496D007E9496 /* IconOverridesView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = IconOverridesView.swift; sourceTree = ""; }; + CEECE831290C5405007E9496 /* AltIconSelectionView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = AltIconSelectionView.swift; sourceTree = ""; }; CEFE36262904A8B600938D98 /* Info.plist */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = text.plist.xml; path = Info.plist; sourceTree = ""; }; CEFE36292904AC6400938D98 /* TSUtil.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = TSUtil.m; sourceTree = ""; }; CEFE362C2904AC6400938D98 /* TSUtil.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = TSUtil.h; sourceTree = ""; }; @@ -97,6 +101,8 @@ CE2BF8152902E07F00AD10BE /* ThemesView.swift */, CE141B392903F20800AB48A7 /* ThemesSettingsView.swift */, CE141B3B2903F22F00AB48A7 /* ThemeView.swift */, + CEECE82F290C496D007E9496 /* IconOverridesView.swift */, + CEECE831290C5405007E9496 /* AltIconSelectionView.swift */, ); path = Themes; sourceTree = ""; @@ -294,6 +300,7 @@ files = ( CEFE362E2904AC6400938D98 /* TSUtil.m in Sources */, CE2BF8302902E07F00AD10BE /* PasscodeKeyFaceManager.swift in Sources */, + CEECE830290C496D007E9496 /* IconOverridesView.swift in Sources */, CE2BF82B2902E07F00AD10BE /* RootView.swift in Sources */, CE2BF8372902E10900AD10BE /* TrollToolsApp.swift in Sources */, CE2BF8262902E07F00AD10BE /* ImagePickerView.swift in Sources */, @@ -309,6 +316,7 @@ CE2BF8242902E07F00AD10BE /* Extensions.swift in Sources */, CE141B5A290460AE00AB48A7 /* WebclipsThemeManager.swift in Sources */, CE76386D290AED160099C6F0 /* ProblemReporter.swift in Sources */, + CEECE832290C5405007E9496 /* AltIconSelectionView.swift in Sources */, CE2BF82E2902E07F00AD10BE /* WallpaperGetter.swift in Sources */, CE141B3A2903F20800AB48A7 /* ThemesSettingsView.swift in Sources */, CE2BF82F2902E07F00AD10BE /* ThemeManager.swift in Sources */, diff --git a/TrollTools.xcodeproj/project.xcworkspace/xcuserdata/exerhythm.xcuserdatad/UserInterfaceState.xcuserstate b/TrollTools.xcodeproj/project.xcworkspace/xcuserdata/exerhythm.xcuserdatad/UserInterfaceState.xcuserstate index c1d5c0cd468873eccef722a665736b003c8818e9..7e3961c55a600c9c8ee99ff657f7c63b2d7dacd9 100644 GIT binary patch literal 167679 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�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 literal 148711 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%0DqP)3C-GtNA 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 Hf6BiBeoE(l literal 0 HcmV?d00001 diff --git a/TrollTools/Assets.xcassets/NotFound.imageset/Contents.json b/TrollTools/Assets.xcassets/NotFound.imageset/Contents.json new file mode 100644 index 0000000..f17e092 --- /dev/null +++ b/TrollTools/Assets.xcassets/NotFound.imageset/Contents.json @@ -0,0 +1,21 @@ +{ + "images" : [ + { + "filename" : "NotFound.png", + "idiom" : "universal", + "scale" : "1x" + }, + { + "idiom" : "universal", + "scale" : "2x" + }, + { + "idiom" : "universal", + "scale" : "3x" + } + ], + "info" : { + "author" : "xcode", + "version" : 1 + } +} diff --git a/TrollTools/Assets.xcassets/NotFound.imageset/NotFound.png b/TrollTools/Assets.xcassets/NotFound.imageset/NotFound.png new file mode 100644 index 0000000000000000000000000000000000000000..5fcd1a4ae1efa27b7e4b5c21f9003048fd439da1 GIT binary patch literal 2141 zcmc&#`#;nBAAis0Hb)Gh(%h$!TjZV%)3Q}Z?v=~tGLu**9n;O`vJgdKXbUG@zD_Qo zh!{x`nmHWS1%0VdE-8r^=hH9W??3Q;Jib4?-mmBL{d~S2@9X37%J4i$R77q?0ss^} z_7S|G%>Eg2QqZ_RaET8kSezHp6;uherXfOz2=JgCH~@?xEC*m|Q2_DN0>xG+0Dzam z036D&pL3;B|54ec@c-hU#(kF&OaNp%JqRv739#9q=zYFqHGy;O6zBKdwHkYe6cumm zzk$D@?V^`QQOj7bOHNO(*x{-Ci&}r88bL?WNKeh#@`sEUX;J5ZMZd~`6!xrm_IgCb z=)5sgpE&OvEi8%~%3{uH*Y=H$RTQlVT9%4;o4cu~s|GxW(IbUC2KYk_$IT>Q3 zi!m30`A@^uW3>@Iw-4}WLcT}!G-Qb#ZGH)@FgUm)aueKnM~&G zj^^TSo?H3yer@HehFRe9%GW!%c&P%L>@s3@>_}67aBRsHGI!_U`}9L$VP$>lix_KH_H{?*+{hz;#?!zG(-6TL zbOSLlF=mCOBjZZ?s26Cb1Pl6R^ot!PCOsP%E_c^gV*B*;G<{8EVr5~${)|L1Sgei3 z=>e3=hUH0-DX?eGy_tR8;P2;Wd<%&vY}}k0pi$|Tv#)&H)-REL#Vx;0JZoT#IepI5 zFduC>`~C8E$EhGU^WbKDsjap3JF0OPuBa7;#bV3L%kvykn9b!54i1>CC|u%N!s=2? zf{cS{`g*G7>hms_=X*|QeqexN7t+Wz9`9Ga-NN*M5!2$@N}7`PZRUDKKu!AyMR{(Q z0$%=+@*^}Zk-uDpe=V~IM;I5O4fWu%6KWvDl@xN+*Y|IzWJ)ctIpNB`hBkuOVsQYn z(!VP3k2bAdo-Lyo$C_I^Wsib|28p+{aMH^g8iq}J;h$$-T4kH4uBUFGTE(iE;geUa zHnnMH4ig{Txzm}JxNUq&aj(L&2KoaL$+jKaR-!N4Qb90is>P1Q2YfZgSrS;{dprq6%6k;%R2Ez#2HSai@J$LaI zxxj1Ll{pIiX>1oe6q64$V|%;0biQ!dMVi$p#UC;g$E8>N#^t@KPWCvQcAYk+*>PR3 z$<{1H;Iw|`bM<~1*ihxs0v_+K+7LHCpBkvUd@8%IKNhCkjdnOie_bC#8VC?I`W!lB zS**Y{QCGMJy~ zfN?KzKJVb{9Gov97no6L{6lrMp3*&tLR$v<0w+TvzU-=bZ|9C3ZQ)Uq7wwH~qK z9zG1nmvFi2=Zu3}6Js__hmk{bL3*8E<&oX>i*u6+pDlZunwnmvZHi&`Y@I)%4{rBI z(rAB0U)DHCrRw?#MY;EMDp6oSBO@-+f*~Ce^+V*OFn{oNyd2w3p`YtbFHpV5de?R3 zXhUoxC95fd7^#I3P?1=U-J;y#4(DUxX`pb;gQ`6k@+kgNvbAhj8nCpqRO{~U>A_l* zS;WgJtE=y&R^GjvDP@I(#JnXXS5xb?OL_%fnvRIl!FLN2ooah#M$sF$HS%L05V-B1=Qi$Lg7I@l$ezvIIP@HE2XN-v4{55B!zf; ztI`GcUpL^vPK-O4`PMIBZ3s-ix^(_YchO>xhdQ2_sYzq$vJIue$n*R%?wuo^6H>MtdA*katD;fMYY1#eqnm%b^B%G-ysf3|iH_k)BgS4#3fVKTgI literal 0 HcmV?d00001 diff --git a/TrollTools/Other/Extensions.swift b/TrollTools/Other/Extensions.swift index 089d676..a584a36 100644 --- a/TrollTools/Other/Extensions.swift +++ b/TrollTools/Other/Extensions.swift @@ -7,6 +7,19 @@ import Foundation import SwiftUI +import Combine + +fileprivate var cancellables = [String : AnyCancellable] () + +public extension Published { + init(wrappedValue defaultValue: Value, key: String) { + let value = UserDefaults.standard.object(forKey: key) as? Value ?? defaultValue + self.init(initialValue: value) + cancellables[key] = projectedValue.sink { val in + UserDefaults.standard.set(val, forKey: key) + } + } +} extension StringProtocol { subscript(offset: Int) -> Character { self[index(startIndex, offsetBy: offset)] } diff --git a/TrollTools/Other/ProblemReporter.swift b/TrollTools/Other/ProblemReporter.swift index b87ae8b..dd20940 100644 --- a/TrollTools/Other/ProblemReporter.swift +++ b/TrollTools/Other/ProblemReporter.swift @@ -7,12 +7,12 @@ import Foundation -//func remLog(_ objs: Any...) { -// for obj in objs { -// let args: [CVarArg] = [ String(describing: obj) ] -// withVaList(args) { RLogv("%@", $0) } -// } -//} +func remLog(_ objs: Any...) { + for obj in objs { + let args: [CVarArg] = [ String(describing: obj) ] + withVaList(args) { RLogv("%@", $0) } + } +} //class ProblemReporter { // func report(_ str: String) { diff --git a/TrollTools/Other/RemoteLog.h b/TrollTools/Other/RemoteLog.h index d33bd1a..4be65bd 100644 --- a/TrollTools/Other/RemoteLog.h +++ b/TrollTools/Other/RemoteLog.h @@ -7,7 +7,7 @@ #import // change this to match your destination (server) IP address -#define RLOG_IP_ADDRESS "home.sourceloc.net" +#define RLOG_IP_ADDRESS "192.168.0.24" #define RLOG_PORT 11909 __attribute__((unused)) static void RLogv(NSString* format, va_list args) diff --git a/TrollTools/Other/TrollToolsApp.swift b/TrollTools/Other/TrollToolsApp.swift index 24d0228..bd9a38c 100644 --- a/TrollTools/Other/TrollToolsApp.swift +++ b/TrollTools/Other/TrollToolsApp.swift @@ -27,6 +27,7 @@ struct TrollToolsApp: App { } task.resume() } + try? RootHelper.loadMCM() } } } diff --git a/TrollTools/Private APIs/BadgeChanger.swift b/TrollTools/Private APIs/BadgeChanger.swift index 70ef7eb..bcde450 100644 --- a/TrollTools/Private APIs/BadgeChanger.swift +++ b/TrollTools/Private APIs/BadgeChanger.swift @@ -17,6 +17,20 @@ class BadgeChanger { badge.writeToCPBitmapFile(to: badgeBitmapPath as NSString) } + + static func change(to image: UIImage) throws { + let size = CGSize(width: 26, height: 26) + + UIGraphicsBeginImageContextWithOptions(size, false, 0.0) + image.draw(in: CGRect(origin: CGPoint.zero, size: size)) + let resizedImage = UIGraphicsGetImageFromCurrentImageContext()! + UIGraphicsEndImageContext() + + let badgeBitmapPath = "/var/mobile/Library/Caches/MappedImageCache/Persistent/SBIconBadgeView.BadgeBackground:26:26.cpbitmap" + try? FileManager.default.removeItem(atPath: badgeBitmapPath) + + resizedImage.writeToCPBitmapFile(to: badgeBitmapPath as NSString) + } } extension UIImage { @@ -39,6 +53,22 @@ extension UIImage { return img } + public func withRoundedCorners(radius: CGFloat? = nil) -> UIImage? { + let maxRadius = min(size.width, size.height) / 2 + let cornerRadius: CGFloat + if let radius = radius, radius > 0 && radius <= maxRadius { + cornerRadius = radius + } else { + cornerRadius = maxRadius + } + UIGraphicsBeginImageContextWithOptions(size, false, scale) + let rect = CGRect(origin: .zero, size: size) + UIBezierPath(roundedRect: rect, cornerRadius: cornerRadius).addClip() + draw(in: rect) + let image = UIGraphicsGetImageFromCurrentImageContext() + UIGraphicsEndImageContext() + return image + } } extension String: LocalizedError { diff --git a/TrollTools/Private APIs/PasscodeKeyFaceManager.swift b/TrollTools/Private APIs/PasscodeKeyFaceManager.swift index 637885b..8fc8e19 100644 --- a/TrollTools/Private APIs/PasscodeKeyFaceManager.swift +++ b/TrollTools/Private APIs/PasscodeKeyFaceManager.swift @@ -10,8 +10,8 @@ import UIKit class PasscodeKeyFaceManager { static let telephonyUIURL = URL(fileURLWithPath: "/var/mobile/Library/Caches/TelephonyUI-8") - static func setFace(_ image: UIImage, for n: Int) throws { - let size = CGSize(width: 150, height: 150) + static func setFace(_ image: UIImage, for n: Int, isBig: Bool) throws { + let size = isBig ? CGSize(width: 225, height: 225) : CGSize(width: 152, height: 152) UIGraphicsBeginImageContextWithOptions(size, false, 1.0) image.draw(in: CGRect(origin: .zero, size: size)) let newImage = UIGraphicsGetImageFromCurrentImageContext() @@ -26,7 +26,7 @@ class PasscodeKeyFaceManager { let fm = FileManager.default for imageURL in try fm.contentsOfDirectory(at: telephonyUIURL, includingPropertiesForKeys: nil) { - let size = CGSize(width: 150, height: 150) + let size = CGSize(width: 152, height: 152) UIGraphicsBeginImageContextWithOptions(size, false, 1.0) UIImage().draw(in: CGRect(origin: .zero, size: size)) let newImage = UIGraphicsGetImageFromCurrentImageContext() diff --git a/TrollTools/Private APIs/RootHelper.swift b/TrollTools/Private APIs/RootHelper.swift index 7dc196c..08b55ef 100644 --- a/TrollTools/Private APIs/RootHelper.swift +++ b/TrollTools/Private APIs/RootHelper.swift @@ -9,7 +9,7 @@ import UIKit import NSTaskBridge class RootHelper { - static let rootHelperPath = Bundle.main.url(forAuxiliaryExecutable: "trolltoolsroothelper")!.path + static let rootHelperPath = Bundle.main.url(forAuxiliaryExecutable: "trolltoolsroothelper")?.path ?? "/" static func move(from sourceURL: URL, to destURL: URL) throws { let code = spawnRoot(rootHelperPath, ["filemove", sourceURL.path, destURL.path], nil, nil) @@ -35,4 +35,8 @@ class RootHelper { let code = spawnRoot(rootHelperPath, ["rebuildiconcache", "", ""], nil, nil) guard code == 0 else { throw "Helper.rebuildIconCache: returned non-zero code \(code)" } } + static func loadMCM() throws { + let code = spawnRoot(rootHelperPath, ["", "", ""], nil, nil) + guard code == 0 else { throw "Helper.rebuildIconCache: returned non-zero code \(code)" } + } } diff --git a/TrollTools/Private APIs/Themes/CatalogThemeManager.swift b/TrollTools/Private APIs/Themes/CatalogThemeManager.swift index bac4018..7ad4487 100644 --- a/TrollTools/Private APIs/Themes/CatalogThemeManager.swift +++ b/TrollTools/Private APIs/Themes/CatalogThemeManager.swift @@ -11,71 +11,56 @@ import AssetCatalogWrapper class CatalogThemeManager { - static var fm = FileManager.default + var fm = FileManager.default - static func setTheme(theme: Theme, filenameEnding: String, apps: [LSApplicationProxy], progress: (String) -> ()) throws { - // Itterate over all icons - var systemApps: [LSApplicationProxy] = [] - - let appCount = apps.count - for (i,app) in apps.enumerated() { - guard let bundleID = app.bundleIdentifier else { throw "Bundle not found" } - func sendProgress(_ str: String) { - progress("App #\(i)/\(appCount)\n\(bundleID)\n\n\(str)") - } - - sendProgress("Starting") - guard let appURL = app.bundleURL else { continue } - - // check if it's in /var - sendProgress("Checking if app is in /var") - guard appURL.pathComponents.count >= 1 && (appURL.pathComponents[1] == "var" || appURL.pathComponents[1] == "private") else { - systemApps.append(app) - continue - } - - // Icon url - sendProgress("Getting url of icon in theme") - let themeIconURL = theme.url.appendingPathComponent("IconBundles").appendingPathComponent(bundleID + filenameEnding + ".png") - guard fm.fileExists(atPath: themeIconURL.path) else { continue } - - // Backup assets - let catalogURL = appURL.appendingPathComponent("Assets.car") - let backupURL = try backupAssetsURL(appURL: appURL) - - // Restore broken apps from backup - sendProgress("Checking if assets.car exists") - if !fm.fileExists(atPath: catalogURL.path) { - sendProgress("Catalog not found - \(catalogURL.path).\nChecking if backup exists") - if fm.fileExists(atPath: backupURL.path) { - sendProgress("Restoring from backup") - try RootHelper.copy(from: backupURL, to: catalogURL) - } else { continue } - } - - // Create backup if not made - sendProgress("Checking if backup exists") - if !fm.fileExists(atPath: backupURL.path) { - try RootHelper.copy(from: catalogURL, to: backupURL) - } - - // Get CGImage from icon - sendProgress("Creating icon CGImage from theme") - let imgData = try Data(contentsOf: themeIconURL) - guard let image = UIImage(data: imgData) else { continue } - guard let cgImage = image.cgImage else { continue } - - // Apply new icon - sendProgress("Start modifying") - try modifyIconInCatalog(url: catalogURL, to: cgImage, sendProgress: sendProgress(_:)) - sendProgress("Completed") + func applyChanges(_ changes: [ThemeManager.UserAppIconChange], progress: (Double) -> ()) throws { + let changesCount = Double(changes.count) + for (i,change) in changes.enumerated() { + try? applyChange(change) + progress(Double(i) / changesCount) + } + } + + private func applyChange(_ change: ThemeManager.UserAppIconChange) throws { + let appURL = change.bundleURL + let catalogURL = appURL.appendingPathComponent("Assets.car") + + if let iconURL = change.themeIconURL { + // MARK: Apply custom icon + + // Backup ass :troll: + let backupURL = try backupAssetsURL(appURL: appURL) + + // Restore broken apps from backup + if !fm.fileExists(atPath: catalogURL.path) { + if fm.fileExists(atPath: backupURL.path) { + try RootHelper.copy(from: backupURL, to: catalogURL) + } else { return } + } + + // Create backup if not made + if !fm.fileExists(atPath: backupURL.path) { + try RootHelper.copy(from: catalogURL, to: backupURL) + } + + // Get CGImage from icon + let imgData = try Data(contentsOf: iconURL) + guard let image = UIImage(data: imgData) else { return } + guard let cgImage = image.cgImage else { return } + + // Apply new icon + try modifyIconInCatalog(url: catalogURL, to: cgImage) + } else { + // MARK: Revert icon + guard fm.fileExists(atPath: catalogURL.path) else { return } + let backupURL = try backupAssetsURL(appURL: appURL) + guard fm.fileExists(atPath: backupURL.path) else { return } + try RootHelper.removeItem(at: catalogURL) + try RootHelper.move(from: backupURL, to: catalogURL) } - try WebclipsThemeManager.setTheme(theme: theme, filenameEnding: filenameEnding, apps: systemApps, progress: progress) - - progress("Completed.") } - static func restoreCatalogs(progress: (String) -> ()) throws { + func restoreCatalogs(progress: (String) -> ()) throws { guard let apps = LSApplicationWorkspace.default().allApplications() else { throw "Couldn't get apps" } let appCount = apps.count for (i, app) in apps.enumerated() { @@ -94,18 +79,15 @@ class CatalogThemeManager { } } - static func modifyIconInCatalog(url: URL, to icon: CGImage, sendProgress: (String) -> ()) throws { // icon: CGImage + func modifyIconInCatalog(url: URL, to icon: CGImage) throws { // icon: CGImage let tempAssetDir = URL(fileURLWithPath: "/var/mobile/.DO-NOT-DELETE-TrollTools/temp-assets-\(UUID()).car") - sendProgress("Moving assets to temp dir") try RootHelper.move(from: url, to: tempAssetDir) defer { try? RootHelper.move(from: tempAssetDir, to: url) } - sendProgress("Setting permission") try RootHelper.setPermission(url: tempAssetDir) - sendProgress("Getting renditions") let (catalog, renditionsRoot) = try AssetCatalogWrapper.shared.renditions(forCarArchive: tempAssetDir) for rendition in renditionsRoot { let type = rendition.type @@ -116,14 +98,12 @@ class CatalogThemeManager { try catalog.editItem(rend, fileURL: tempAssetDir, to: .image(icon)) } catch { // remLog("failed to edit rendition: \(error) \(rend.type) \(rend.name) \(rend.namedLookup)") - sendProgress("Editing icon asset failed \(rend.type) \(rend.name) \(rend.namedLookup)") } } } - sendProgress("Moving assets.car back into app's bundle") } - static private func backupAssetsURL(appURL: URL) throws -> URL { + private func backupAssetsURL(appURL: URL) throws -> URL { // Get version of app, so when app updates and user restores assets.car, old guard let infoPlistData = try? Data(contentsOf: appURL.appendingPathComponent("Info.plist")), let plist = try? PropertyListSerialization.propertyList(from: infoPlistData, format: nil) as? [String:Any] else { throw "Couldn't read template webclip plist" } guard let appShortVersion = (plist["CFBundleShortVersionString"] as? String) ?? plist["CFBundleVersion"] as? String else { throw "CFBundleShortVersionString missing for \(appURL.path)" } diff --git a/TrollTools/Private APIs/Themes/ThemeManager.swift b/TrollTools/Private APIs/Themes/ThemeManager.swift index 848dcee..c407c65 100644 --- a/TrollTools/Private APIs/Themes/ThemeManager.swift +++ b/TrollTools/Private APIs/Themes/ThemeManager.swift @@ -23,68 +23,155 @@ var webclipsActiveIconsDir: URL = { #endif }() -class ThemeManager { - static var fm = FileManager.default +class ThemeManager: ObservableObject { + let fm = FileManager.default + var catalogThemeManager = CatalogThemeManager() + var webclipsThemeManager = WebclipsThemeManager() - static func set(theme: Theme, progress: (String) -> ()) throws { - let iconBundlesURL = theme.url.appendingPathComponent("IconBundles") - try? fm.createDirectory(at: webclipsActiveIconsDir, withIntermediateDirectories: true) + @Published var preferedThemes: [Theme] = [] + + var preferedIcons: [String : ThemedIcon] { + get { + var res: [String : ThemedIcon] = [:] + for theme in preferedThemes { + if let icons = try? fm.contentsOfDirectory(at: theme.url, includingPropertiesForKeys: nil) { + for icon in icons { + let appID = appIDFromIcon(url: icon) + res[appID] = .init(appID: appID, themeName: theme.name) + } + } + } + for (overridenAppID, themeName) in iconOverrides { + res[overridenAppID] = .init(appID: overridenAppID, themeName: themeName) + } + return res + } + } + + var themes: [Theme] { + get { guard let data = UserDefaults.standard.data(forKey: "themes") else { return [] }; return (try? JSONDecoder().decode([Theme].self, from: data)) ?? [] } + set { guard let data = try? JSONEncoder().encode(newValue) else { return }; UserDefaults.standard.set(data, forKey: "themes") } + } + var iconOverrides: [String : String] { + get { return UserDefaults.standard.dictionary(forKey: "iconOverrides") as? [String : String] ?? [:] } + set { UserDefaults.standard.set(newValue, forKey: "iconOverrides") } + } + var currentThemedIcons: [ThemedIcon] { + get { guard let data = UserDefaults.standard.data(forKey: "currentThemedIcons") else { return [] }; return (try? JSONDecoder().decode([ThemedIcon].self, from: data)) ?? [] } + set { guard let data = try? JSONEncoder().encode(newValue) else { return }; UserDefaults.standard.set(data, forKey: "currentThemedIcons") } + } + + // MARK: - Set theme + func applyChanges(progress: (String) -> ()) throws { + let (userAppChanges, systemAppChanges) = neededChanges() - // Get theme icon ending like -large or @2x - let iconBundleContents = try fm.contentsOfDirectory(at: iconBundlesURL, includingPropertiesForKeys: nil) - guard let filenameEnding = (iconBundleContents - .first(where: { url1 in url1.lastPathComponent.contains("com.apple.AppStore") }) ?? iconBundleContents.last)? - .deletingPathExtension() - .lastPathComponent - .replacingOccurrences(of: "com.apple.AppStore", with: "") - else { throw "Invalid theme, no icons found" } - // Setting theme - guard let apps = LSApplicationWorkspace.default().allApplications() else { throw "Couldn't get apps" } - try CatalogThemeManager.setTheme(theme: theme, filenameEnding: filenameEnding, apps: apps, progress: progress) + try catalogThemeManager.applyChanges(userAppChanges, progress: { percentage in +// remLog(str) + progress("\(Int(percentage * 100))% done") + }) + try webclipsThemeManager.applyChanges(systemAppChanges, progress: { percentage in +// remLog(str) + progress("\(Int(percentage * 100))% done") + }) } - static func getIconFileEnding(iconFilename: String) throws -> String { - if iconFilename.contains("-large.png") { - return "-large" - } else if iconFilename.contains("@2x.png") { - return"@2x" - } else if iconFilename.contains("@23.png") { - return "@3x" - } else { - throw "Unknown icon filename ending. Couldn't get bundle ids. Please create an issue on github with the name of the theme you used. Thanks" + struct UserAppIconChange { + var bundleURL: URL + var themeIconURL: URL? + } + struct SystemAppIconChange { + var appID: String + var themeIconURL: URL? + var localizedName: String + } + func neededChanges() -> (user: [UserAppIconChange], system: [SystemAppIconChange]) { + let apps = LSApplicationWorkspace.default().allApplications() ?? [] + var userChanges: [UserAppIconChange] = [] + var systemChanges: [SystemAppIconChange] = [] + let preferedIcons = preferedIcons + + for app in apps { + let system = app.bundleURL.pathComponents[1] == "Applications" + if let themedIcon = preferedIcons[app.applicationIdentifier] { + // Icon needs to be themed + if system { + systemChanges.append(.init(appID: app.applicationIdentifier, themeIconURL: themedIcon.themeIconURL, localizedName: app.localizedName())) + } else { + userChanges.append(.init(bundleURL: app.bundleURL, themeIconURL: themedIcon.themeIconURL)) + } + + } else { + // Icon needs to be restored + if system { + systemChanges.append(.init(appID: app.applicationIdentifier, themeIconURL: nil, localizedName: app.localizedName())) + } else { + userChanges.append(.init(bundleURL: app.bundleURL, themeIconURL: nil)) + } + } } + return (userChanges, systemChanges) } - static func getIcons(forBundleIDs bundleIDs: [String], from theme: Theme) throws -> [UIImage?] { - bundleIDs.map { try? getIcon(forBundleID: $0, from: theme) } + // MARK: - Getting icons + func icons(forAppIDs appIDs: [String], from theme: Theme) throws -> [UIImage?] { + appIDs.map { try? icon(forAppID: $0, from: theme) } } - - static private func getIcon(forBundleID bundleID: String, from theme: Theme) throws -> UIImage { - let iconBundlesURL = theme.url.appendingPathComponent("IconBundles") - let filesInIconBundles = try fm.contentsOfDirectory(at: iconBundlesURL, includingPropertiesForKeys: nil) - guard let firstIconFilename = filesInIconBundles.last?.lastPathComponent else { throw "No icons" } - let iconFilenameEnding = try getIconFileEnding(iconFilename: firstIconFilename) - guard let image = UIImage(contentsOfFile: iconBundlesURL.appendingPathComponent(bundleID + iconFilenameEnding).path) else { throw "Couldn't open image" } + func icon(forAppID appID: String, from theme: Theme) throws -> UIImage { + remLog(theme.url.appendingPathComponent(appID).path + ".png") + guard let image = UIImage(contentsOfFile: theme.url.appendingPathComponent(appID).path + ".png") else { throw "Couldn't open image" } return image } + func icon(forAppID appID: String, fromThemeWithName name: String) throws -> UIImage { + return try icon(forAppID: appID, from: Theme(name: name, iconCount: 1)) + } - static func importTheme(from importURL: URL) throws -> Theme { - let name = importURL.deletingPathExtension().lastPathComponent + func importTheme(from importURL: URL) throws -> Theme { + var name = importURL.deletingPathExtension().lastPathComponent try? fm.createDirectory(at: themesDir, withIntermediateDirectories: true) - let themeURL = themesDir.appendingPathComponent(name) + var themeURL = themesDir.appendingPathComponent(name) + + if importURL.lastPathComponent.contains(".theme") { + for folder in (try? fm.contentsOfDirectory(at: importURL, includingPropertiesForKeys: nil)) ?? [] { + if folder.deletingPathExtension().lastPathComponent == "IconBundles" { + themeURL = folder + name = importURL.lastPathComponent.replacingOccurrences(of: ".theme", with: "") + } + } + } try? fm.removeItem(at: themeURL) try fm.createDirectory(at: themeURL, withIntermediateDirectories: true) - try fm.copyItem(at: importURL, to: themeURL.appendingPathComponent("IconBundles")) - return Theme(name: themeURL.deletingPathExtension().lastPathComponent, iconCount: try fm.contentsOfDirectory(at: themeURL.appendingPathComponent("IconBundles"), includingPropertiesForKeys: nil).count) + for icon in (try? fm.contentsOfDirectory(at: importURL, includingPropertiesForKeys: nil)) ?? [] { + try fm.copyItem(at: icon, to: themeURL.appendingPathComponent(appIDFromIcon(url: icon) + ".png")) + } + return Theme(name: themeURL.deletingPathExtension().lastPathComponent, iconCount: try fm.contentsOfDirectory(at: themeURL, includingPropertiesForKeys: nil).count) } - - static func removeImportedTheme(theme: Theme) throws { + func removeImportedTheme(theme: Theme) throws { try fm.removeItem(at: theme.url) } - static func getInstalledApplicationsNames() throws -> [String: String] { + func removeCurrentThemes(removeWebClips: Bool, progress: (String) -> ()) throws { + try catalogThemeManager.restoreCatalogs(progress: progress) + try webclipsThemeManager.removeCurrentThemes() + if removeWebClips { + try webclipsThemeManager.removeWebclips() + } + } + + // MARK: - Utils + func iconFileEnding(iconFilename: String) -> String { + if iconFilename.contains("-large.png") { + return "-large" + } else if iconFilename.contains("@2x.png") { + return"@2x" + } else if iconFilename.contains("@23.png") { + return "@3x" + } else { + return "" + } + } + func installedApplicationsNames() throws -> [String: String] { guard let apps = LSApplicationWorkspace.default().allApplications() else { throw "Couldn't get apps" } return apps.reduce(into: [String: String]()) { let applicationIdentifier = $1.applicationIdentifier @@ -92,14 +179,16 @@ class ThemeManager { $0[applicationIdentifier ?? ""] = displayName } } - static func removeCurrentThemes(progress: (String) -> ()) throws { - try CatalogThemeManager.restoreCatalogs(progress: progress) - try WebclipsThemeManager.removeCurrentThemes() + func appIDFromIcon(url: URL) -> String { + return url.deletingPathExtension().lastPathComponent.replacingOccurrences(of: iconFileEnding(iconFilename: url.lastPathComponent), with: "") + } + func iconURL(appID: String, in theme: Theme) -> URL { + return theme.url.appendingPathComponent(appID + ".png") } } -struct Theme: Codable, Identifiable { +struct Theme: Codable, Identifiable, Equatable { var id = UUID() var name: String @@ -107,8 +196,20 @@ struct Theme: Codable, Identifiable { var url: URL { // Documents/ImportedThemes/Theme.theme return themesDir.appendingPathComponent(name /*+ ".theme"*/) } + + static func == (lhs: Theme, rhs: Theme) -> Bool { + return lhs.name == rhs.name + } } enum IconThemingMethod: String { case webclips, appIcons } + +struct ThemedIcon: Codable { + var appID: String + var themeName: String + var themeIconURL: URL { + themesDir.appendingPathComponent(themeName).appendingPathComponent(appID + ".png") + } +} diff --git a/TrollTools/Private APIs/Themes/WebclipsThemeManager.swift b/TrollTools/Private APIs/Themes/WebclipsThemeManager.swift index f9629a6..07b3c64 100644 --- a/TrollTools/Private APIs/Themes/WebclipsThemeManager.swift +++ b/TrollTools/Private APIs/Themes/WebclipsThemeManager.swift @@ -8,43 +8,55 @@ import UIKit class WebclipsThemeManager { - static var templatePlistURL = Bundle.main.url(forResource: "WebClipTemplate", withExtension: "plist") - static var fm = FileManager.default + var templatePlistURL = Bundle.main.url(forResource: "WebClipTemplate", withExtension: "plist") + var fm = FileManager.default - static func setTheme(theme: Theme, filenameEnding: String, apps: [LSApplicationProxy], progress: (String) -> ()) throws { - // Itterate over all icons - let appCount = apps.count - for (i,app) in apps.enumerated() { - guard let bundleID = app.bundleIdentifier else { throw "Bundle not found" } - func sendProgress(_ str: String) { - progress("System App #\(i)/\(appCount)\n\(bundleID)\n\n\(str)") - } - sendProgress("Getting icon") - let themeIconURL = theme.url.appendingPathComponent("IconBundles").appendingPathComponent(bundleID + filenameEnding + ".png") - guard fm.fileExists(atPath: themeIconURL.path) else { continue } + func applyChanges(_ changes: [ThemeManager.SystemAppIconChange], progress: (Double) -> ()) throws { + let changesCount = Double(changes.count) + guard changesCount > 0 else { throw "No changes" } + for (i,change) in changes.enumerated() { + try? applyChange(change) + progress(Double(i) / changesCount) + } + } + + private func applyChange(_ change: ThemeManager.SystemAppIconChange) throws { + try? fm.createDirectory(at: webclipsActiveIconsDir, withIntermediateDirectories: true) + + let appID = change.appID + + if let iconURL = change.themeIconURL { + guard fm.fileExists(atPath: iconURL.path) else { return } + + let webClipURL = webClipURL(appID: appID) - let webClipURL = webClipURL(bundleID: bundleID) - sendProgress("adding webclip \(webClipURL.path)") // Add webclip if not added if !fm.fileExists(atPath: webClipURL.path) { - guard let displayName = app.localizedName() else { continue } - try addWebClip(bundleID: bundleID, displayName: displayName) + try addWebClip(bundleID: appID, displayName: change.localizedName) } // Copy icon to activeIconsDir - sendProgress("Setting icon") - let activeIconDir = webclipsActiveIconsDir.appendingPathComponent(bundleID + ".png") + let activeIconDir = webclipsActiveIconsDir.appendingPathComponent(appID + ".png") try? fm.removeItem(at: activeIconDir) - sendProgress("changine active icon symlink") - try fm.createSymbolicLink(at: activeIconDir, withDestinationURL: themeIconURL) + try fm.createSymbolicLink(at: activeIconDir, withDestinationURL: iconURL) + } else { + try? fm.removeItem(at: webclipsActiveIconsDir.appendingPathComponent(appID + ".png")) } } - static func removeCurrentThemes() throws { +// func setTheme(theme: Theme, apps: [LSApplicationProxy], progress: (String) -> ()) throws { +// // Itterate over all icons +// let appCount = apps.count +// for (i,app) in apps.enumerated() { +// +// } +// } + + func removeCurrentThemes() throws { try fm.removeItem(at: webclipsActiveIconsDir) } - static func removeWebclips() throws { + func removeWebclips() throws { for url in try fm.contentsOfDirectory(at: URL(fileURLWithPath: "/var/mobile/Library/WebClips/"), includingPropertiesForKeys: nil) { guard url.lastPathComponent.contains(".DO-NOT-DELETE-TrollTools-") else { continue } try fm.removeItem(at: url) @@ -52,16 +64,16 @@ class WebclipsThemeManager { } - static private func webClipURL(bundleID: String) -> URL { + private func webClipURL(appID: String) -> URL { #if targetEnvironment(simulator) - FileManager.default.urls(for: .documentDirectory, in: .userDomainMask)[0].appendingPathComponent("WebClips/.DO-NOT-DELETE-TrollTools-\(bundleID).webclip") + FileManager.default.urls(for: .documentDirectory, in: .userDomainMask)[0].appendingPathComponent("WebClips/.DO-NOT-DELETE-TrollTools-\(appID).webclip") #else - URL(fileURLWithPath: "/var/mobile/Library/WebClips/.DO-NOT-DELETE-TrollTools-\(bundleID).webclip") + URL(fileURLWithPath: "/var/mobile/Library/WebClips/.DO-NOT-DELETE-TrollTools-\(appID).webclip") #endif // return } - static func addWebClip(bundleID: String, displayName: String) throws { - let webClipURL = webClipURL(bundleID: bundleID) + func addWebClip(bundleID: String, displayName: String) throws { + let webClipURL = webClipURL(appID: bundleID) try fm.createDirectory(at: webClipURL, withIntermediateDirectories: true) // Load plist @@ -80,24 +92,24 @@ class WebclipsThemeManager { try plistData.write(to: webClipURL.appendingPathComponent("Info.plist")) } - static func changeLabelVisibility(visible: Bool) throws { - let installedAppNames = try ThemeManager.getInstalledApplicationsNames() - - for url in try fm.contentsOfDirectory(at: URL(fileURLWithPath: "/var/mobile/Library/WebClips/"), includingPropertiesForKeys: nil) { - guard url.lastPathComponent.contains(".DO-NOT-DELETE-TrollTools-") else { continue } - - let plistURL = url.appendingPathComponent("Info.plist") - - let data = try Data(contentsOf: plistURL) - guard var plist = try PropertyListSerialization.propertyList(from: data, format: nil) as? [String:Any] else { throw "Couldn't read template webclip plist" } - - // Modify values - guard let bundleID = plist["ApplicationBundleIdentifier"] as? String else { throw "Couldn't get bundle id of exisitng webclip. Webclip url \(url)" } - plist["Title"] = visible ? installedAppNames[bundleID] : " " - - // Save plist - let plistData = try PropertyListSerialization.data(fromPropertyList: plist, format: .xml, options: 0) - try plistData.write(to: plistURL) - } - } +// func changeLabelVisibility(visible: Bool) throws { +// let installedAppNames = try ThemeManager.getInstalledApplicationsNames() +// +// for url in try fm.contentsOfDirectory(at: URL(fileURLWithPath: "/var/mobile/Library/WebClips/"), includingPropertiesForKeys: nil) { +// guard url.lastPathComponent.contains(".DO-NOT-DELETE-TrollTools-") else { continue } +// +// let plistURL = url.appendingPathComponent("Info.plist") +// +// let data = try Data(contentsOf: plistURL) +// guard var plist = try PropertyListSerialization.propertyList(from: data, format: nil) as? [String:Any] else { throw "Couldn't read template webclip plist" } +// +// // Modify values +// guard let bundleID = plist["ApplicationBundleIdentifier"] as? String else { throw "Couldn't get bundle id of exisitng webclip. Webclip url \(url)" } +// plist["Title"] = visible ? installedAppNames[bundleID] : " " +// +// // Save plist +// let plistData = try PropertyListSerialization.data(fromPropertyList: plist, format: .xml, options: 0) +// try plistData.write(to: plistURL) +// } +// } } diff --git a/TrollTools/RootView.swift b/TrollTools/RootView.swift index f1617b5..7fa7fc1 100644 --- a/TrollTools/RootView.swift +++ b/TrollTools/RootView.swift @@ -8,6 +8,8 @@ import SwiftUI struct RootView: View { + @StateObject var themeManager = ThemeManager() + var body: some View { TabView { ThemesView() @@ -27,6 +29,7 @@ struct RootView: View { // Label("Apple card", systemImage: "creditcard") // } } + .environmentObject(themeManager) } } diff --git a/TrollTools/Views/BadgeChangerView.swift b/TrollTools/Views/BadgeChangerView.swift index 57d0240..c17c825 100644 --- a/TrollTools/Views/BadgeChangerView.swift +++ b/TrollTools/Views/BadgeChangerView.swift @@ -6,10 +6,13 @@ // import SwiftUI +import Photos struct BadgeChangerView: View { @State private var color = Color.red @State private var radius: CGFloat = 24 + @State private var showingImagePicker = false + @State private var image: UIImage? var body: some View { GeometryReader { proxy in @@ -28,41 +31,64 @@ struct BadgeChangerView: View { .frame(width: minSize / 2, height: minSize / 2) .cornerRadius(minSize / 8) ZStack { - Rectangle() - .fill(color) - .frame(width: minSize / 5, height: minSize / 5) - .cornerRadius(minSize * radius / 240) + if image == nil { + Rectangle() + .fill(color) + .frame(width: minSize / 5, height: minSize / 5) + .cornerRadius(minSize * radius / 240) + } else { + Image(uiImage: image!) + .resizable() + .frame(width: minSize / 5, height: minSize / 5) + } Text("1") .foregroundColor(.white) .font(.system(size: 45)) } - .offset(x: minSize / 12, y: -minSize / 22) + .offset(x: minSize / 12, y: -minSize / 12) } Text("TrollTools") .font(.title) .foregroundColor(.white) .fontWeight(.medium) HStack { - ColorPicker("Set the background color", selection: $color) + ColorPicker("Set badge color", selection: $color) .labelsHidden() .scaleEffect(1.5) .padding() Slider(value: $radius, in: 0...24) .frame(width: minSize / 2) } + Button(action: { + if image == nil { + showPicker() + } else { + image = nil + } + }) { + Text(image == nil ? "Custom image" : "Clear image") + .padding(10) + .background(Color.secondary) + .cornerRadius(8) + .foregroundColor(.init(uiColor14: .systemBackground)) + .padding(.top, 24) + } Button("Apply and respring", action: { do { - try BadgeChanger.change(to: UIColor(color), with: radius) + if image == nil { + try BadgeChanger.change(to: UIColor(color), with: radius) + } else { + try BadgeChanger.change(to: image!) + } respring() } catch { UIApplication.shared.alert(body:"An error occured. " + error.localizedDescription) } }) .padding(10) - .background(Color.blue) + .background(Color.accentColor) .cornerRadius(8) .foregroundColor(.white) - .padding(.top, 24) } } .navigationTitle("Badge Color") @@ -70,6 +96,17 @@ struct BadgeChangerView: View { } .navigationViewStyle(StackNavigationViewStyle()) } + .sheet(isPresented: $showingImagePicker) { + ImagePickerView(image: $image) + } + } + + func showPicker() { + PHPhotoLibrary.requestAuthorization(for: .readWrite) { status in + DispatchQueue.main.async { + showingImagePicker = status == .authorized + } + } } } diff --git a/TrollTools/Views/PasscodeEditorView.swift b/TrollTools/Views/PasscodeEditorView.swift index ea14dd1..68c1e1d 100644 --- a/TrollTools/Views/PasscodeEditorView.swift +++ b/TrollTools/Views/PasscodeEditorView.swift @@ -14,6 +14,7 @@ struct PasscodeEditorView: View { @State private var faces: [UIImage?] = [UIImage?](repeating: nil, count: 10) @State private var changedFaces: [Bool] = [Bool](repeating: false, count: 10) @State private var changingFaceN = 0 + @State private var isBig = false var body: some View { GeometryReader { proxy in @@ -68,6 +69,10 @@ struct PasscodeEditorView: View { } } Spacer() + Button(isBig ? "Big" : "Small") { + isBig.toggle() + } + Spacer() Button("Remove all") { do { try PasscodeKeyFaceManager.removeAllFaces() @@ -99,7 +104,7 @@ struct PasscodeEditorView: View { .onChange(of: faces[changingFaceN] ?? UIImage()) { newValue in print(newValue) do { - try PasscodeKeyFaceManager.setFace(newValue, for: changingFaceN) + try PasscodeKeyFaceManager.setFace(newValue, for: changingFaceN, isBig: isBig) } catch { UIApplication.shared.alert(body: "An error occured while changing key face. \(error)") } diff --git a/TrollTools/Views/Themes/AltIconSelectionView.swift b/TrollTools/Views/Themes/AltIconSelectionView.swift new file mode 100644 index 0000000..4c4d950 --- /dev/null +++ b/TrollTools/Views/Themes/AltIconSelectionView.swift @@ -0,0 +1,56 @@ +// +// AltIconSelectionView.swift +// TrollTools +// +// Created by exerhythm on 28.10.2022. +// + +import SwiftUI + +struct AltIconSelectionView: View { + @EnvironmentObject var themeManager: ThemeManager + @State var bundleID: String + @State var displayName: String + @Environment(\.presentationMode) var presentation + var gridItemLayout = [GridItem(.adaptive(minimum: 100, maximum: 100))] + + var onChoose: (String) -> () + @State var icons: [(UIImage, String)] = [] + + var body: some View { + Group { + if icons.count == 0 { + Text("No themes containing icons for \(displayName) (\(bundleID)) have been found.") + .padding() + .background(Color(uiColor14: .secondarySystemBackground)) + .multilineTextAlignment(.center) + .cornerRadius(16) + .font(.footnote) + .foregroundColor(Color(uiColor14: .secondaryLabel)) + } else { + LazyVGrid(columns: gridItemLayout, spacing: 14) { + ForEach(icons, id: \.1) { (icon, themeName) in + Button(action: { + onChoose(themeName) + presentation.wrappedValue.dismiss() + }) { + Image(uiImage: icon) + .resizable() + .aspectRatio(contentMode: .fit) + .frame(width: 100, height: 100) + .cornerRadius(25) + } + } + } + } + } + .navigationTitle(displayName) + .onAppear { + for t in themeManager.themes { + if let icon = try? themeManager.icon(forAppID: bundleID, from: t) { + icons.append((icon, t.name)) + } + } + } + } +} diff --git a/TrollTools/Views/Themes/IconOverridesView.swift b/TrollTools/Views/Themes/IconOverridesView.swift new file mode 100644 index 0000000..b4494dd --- /dev/null +++ b/TrollTools/Views/Themes/IconOverridesView.swift @@ -0,0 +1,126 @@ +// +// IndividualIconsEditorView.swift +// TrollTools +// +// Created by exerhythm on 28.10.2022. +// + +import SwiftUI +//import LaunchServicesBridge +import Dynamic + +struct IconOverridesView: View { + @EnvironmentObject var themeManager: ThemeManager + var gridItemLayout = [GridItem(.adaptive(minimum: 64, maximum: 64))] + + @State var allApps: [IconOverrideViewApp] = [] + + var body: some View { + ScrollView { + LazyVGrid(columns: gridItemLayout, spacing: 14) { + ForEach(allApps, id: \.self) { app in + IconEditorAppView(app: app, edited: themeManager.iconOverrides[app.appID] != nil, updateApps: updateApps) + .padding(.horizontal, 3) + .onAppear { + remLog(app.appID, themeManager.iconOverrides[app.appID]) + } + } + } + } + .navigationTitle("Icons override") + .onAppear { + updateApps() + } + } + + func updateApps() { + let preferedIcons = themeManager.preferedIcons + allApps = LSApplicationWorkspace.default().allApplications().compactMap { + if Dynamic($0).appTags.asArray?.contains("hidden") ?? true + || $0.isRestricted + || Dynamic($0).isLaunchProhibited.asBool ?? false + || (Bundle(url: $0.bundleURL)?.object(forInfoDictionaryKey: "SBAppTags") as? NSArray)?.contains("hidden") ?? false + { return nil } + if let themedIcon = preferedIcons[$0.applicationIdentifier] { + return IconOverrideViewApp(appID: $0.bundleIdentifier, + icon: UIImage(contentsOfFile: themedIcon.themeIconURL.path), displayName: $0.localizedName()) + } else { + return IconOverrideViewApp(appID: $0.bundleIdentifier, + icon: Dynamic(UIImage.self)._applicationIconImage(forBundleIdentifier: $0.bundleIdentifier, + format: 1, + scale: 4.0).asAnyObject as? UIImage, displayName: $0.localizedName()) + } + } + remLog("update") + } + + struct IconEditorAppView: View { + @EnvironmentObject var themeManager: ThemeManager + @State var app: IconOverrideViewApp + @State var edited: Bool + // @State var actionSheetPresented = false + @State var showsAltSelectionSheet = false + + var updateApps: () -> () + + var body: some View { + if !edited { + NavigationLink(destination: AltIconSelectionView(bundleID: app.appID, displayName: app.displayName, onChoose: { name in + themeManager.iconOverrides[app.appID] = name + edited = true + updateApps() + })) { + iconContent + } + } else { + Button(action: { + themeManager.iconOverrides[app.appID] = nil + edited = false + updateApps() + }) { + iconContent + } + } +// .actionSheet(isPresented: $actionSheetPresented) { +// ActionSheet(title: Text("Custom icon"), buttons: [ +// .cancel(), +// .default(Text("Alternative icons"), action: { +// }), +// .default(Text("Choose from photos")) +// ]) +// } + } + + @ViewBuilder + var iconContent: some View { + ZStack(alignment: .topTrailing) { + Image(uiImage: app.icon ?? UIImage(named: "NotFound")!) + .resizable() + .aspectRatio(contentMode: .fit) + .cornerRadius(12) + if edited { + Image(systemName: "lock.fill") + .foregroundColor(.init(uiColor14: .systemBackground)) + .padding(5) + .background(Color.accentColor) + .cornerRadius(.infinity) + .font(.system(size: 13)) + .offset(x: 7, y: -7) + } + } + } + } + + struct IconOverrideViewApp: Hashable { + var appID: String + var icon: UIImage? + var displayName: String + } + +} + +//struct IndividualIconsEditorView_Previews: PreviewProvider { +// static var previews: some View { +// IconOverridesView(editedApps: []) +// } +//} diff --git a/TrollTools/Views/Themes/IndividualIconsEditorView.swift b/TrollTools/Views/Themes/IndividualIconsEditorView.swift new file mode 100644 index 0000000..f1f7551 --- /dev/null +++ b/TrollTools/Views/Themes/IndividualIconsEditorView.swift @@ -0,0 +1,113 @@ +// +// IndividualIconsEditorView.swift +// TrollTools +// +// Created by exerhythm on 28.10.2022. +// + +import SwiftUI +//import LaunchServicesBridge +import Dynamic + +struct ThemeEditorView: View { + @EnvironmentObject var themeManager: ThemeManager + var gridItemLayout = [GridItem(.adaptive(minimum: 64, maximum: 64))] + var editedApps: [IconEditorApp] = { + (LSApplicationWorkspace.default().allApplications() ?? []).map { IconEditorApp(bundleID: $0.bundleIdentifier, icon: Dynamic(UIImage.self)._applicationIconImage(forBundleIdentifier: $0.bundleIdentifier, format: 1, scale: 4.0).asAnyObject as? UIImage ?? UIImage(named: "NotFound")!)} + + }() + + var body: some View { + ScrollView { + LazyVGrid(columns: gridItemLayout, spacing: 14) { + ForEach(editedApps, id: \.bundleID) { app in + IconEditorAppView(app: app) + .padding(.horizontal, 3) + } + } + } + .navigationTitle("Custom icons") + } + + struct IconEditorAppView: View { + @State var app: IconEditorApp + @State var edited = false + @State var actionSheetPresented = false + @State var showsAltSelectionSheet = false + + var body: some View { + Button(action: { + actionSheetPresented = true + }) { + ZStack(alignment: .topTrailing) { + Image(uiImage: app.icon ?? UIImage(named: "NotFound")!) + .resizable() + .aspectRatio(contentMode: .fit) + .cornerRadius(12) + if edited { + Image(systemName: "pencil") + .foregroundColor(.init(uiColor14: .systemBackground)) + .padding(5) + .background(Color.accentColor) + .cornerRadius(.infinity) + .font(.system(size: 13)) + .offset(x: 7, y: -7) + } + } + } + .actionSheet(isPresented: $actionSheetPresented) { + ActionSheet(title: Text("Custom icon"), buttons: [ + .cancel(), + .default(Text("Alternative icons"), action: { + showsAltSelectionSheet = true + }), + .default(Text("Choose from photos")) + ]) + } + .sheet(isPresented: $showsAltSelectionSheet) { + AltIconSelectionView(bundleID: app.bundleID, onChoose: { id in + + + }) + } + } + } +} + +struct IndividualIconsEditorView_Previews: PreviewProvider { + static var previews: some View { + ThemeEditorView(editedApps: [ + .init(bundleID: "com.apple.smth", icon: UIImage(named: "wallpaper")!), + .init(bundleID: "com.apple.smth1", icon: UIImage(named: "64")!), + .init(bundleID: "com.apple.smth2", icon: UIImage(named: "64")!), + .init(bundleID: "com.apple.smth3", icon: UIImage(named: "64")!), + .init(bundleID: "com.apple.smth4", icon: UIImage(named: "wallpaper")!), + .init(bundleID: "com.apple.smth5", icon: UIImage(named: "wallpaper")!), + .init(bundleID: "com.apple.smth6", icon: UIImage(named: "64")!), + .init(bundleID: "com.apple.smth7", icon: UIImage(named: "wallpaper")!), + .init(bundleID: "com.apple.smth8", icon: UIImage(named: "64")!), + .init(bundleID: "com.apple.smth9", icon: UIImage(named: "wallpaper")!), + .init(bundleID: "com.apple.smtha", icon: UIImage(named: "wallpaper")!), + .init(bundleID: "com.apple.smthb", icon: UIImage(named: "64")!), + .init(bundleID: "com.apple.smthc", icon: UIImage(named: "64")!), + .init(bundleID: "com.apple.smthd", icon: UIImage(named: "64")!), + .init(bundleID: "com.apple.smthe", icon: UIImage(named: "64")!), + .init(bundleID: "com.apple.smthf", icon: UIImage(named: "wallpaper")!), + .init(bundleID: "com.apple.smthg", icon: UIImage(named: "64")!), + .init(bundleID: "com.apple.smthh", icon: UIImage(named: "wallpaper")!), + .init(bundleID: "com.apple.smthi", icon: UIImage(named: "64")!), + .init(bundleID: "com.apple.smthj", icon: UIImage(named: "64")!), + .init(bundleID: "com.apple.smthk", icon: UIImage(named: "wallpaper")!), + .init(bundleID: "com.apple.smthl", icon: UIImage(named: "64")!), + .init(bundleID: "com.apple.smthm", icon: UIImage(named: "wallpaper")!), + .init(bundleID: "com.apple.smthn", icon: UIImage(named: "64")!), + .init(bundleID: "com.apple.smtho", icon: UIImage(named: "wallpaper")!), + + ]) + } +} + +struct IconEditorApp { + var bundleID: String + var icon: UIImage? +} diff --git a/TrollTools/Views/Themes/ThemeView.swift b/TrollTools/Views/Themes/ThemeView.swift index 9bd4f8d..9d69c2c 100644 --- a/TrollTools/Views/Themes/ThemeView.swift +++ b/TrollTools/Views/Themes/ThemeView.swift @@ -9,11 +9,12 @@ import SwiftUI struct ThemeView: View { + @EnvironmentObject var themeManager: ThemeManager @State var theme: Theme - @State var isInUse: Bool var wallpaper: UIImage var defaultWallpaper: Bool = false - var applyTheme: (Theme) -> () + @State var icons: [UIImage?] = [] + @State var selected: Bool = false var body: some View { VStack { @@ -26,7 +27,7 @@ struct ThemeView: View { .clipped() .cornerRadius(8) .allowsHitTesting(false) - if let icons = try? ThemeManager.getIcons(forBundleIDs: ["com.apple.mobilephone", "com.apple.mobilesafari", "com.apple.mobileslideshow", "com.apple.camera", "com.apple.AppStore", "com.apple.Preferences", "com.apple.Music", "com.apple.calculator"], from: theme) { + if icons.count >= 8 { VStack { HStack { ForEach(icons[0...3], id: \.self) { @@ -65,29 +66,37 @@ struct ThemeView: View { Spacer() } Button(action: { - if !isInUse { - applyTheme(theme) + UIImpactFeedbackGenerator(style: .light).impactOccurred() + if selected { + themeManager.preferedThemes.removeAll { t in t.name == theme.name } } else { - UIApplication.shared.alert(title: "Use \"Clear current themes\"", body: "You can only turn off *all* themes.") + themeManager.preferedThemes.append(theme) } + selected.toggle() + remLog(themeManager.preferedIcons.keys.count, themeManager.preferedThemes.count) }) { - Text(isInUse ? "In use" : "Activate") + Text(selected ? "Selected" : "Select") .frame(maxWidth: .infinity) + } .padding(10) - .background(isInUse ? Color(red: 48 / 256, green: 209 / 256, blue: 88 / 256, opacity: 0.5) : Color(uiColor14: UIColor.tertiarySystemBackground)) + .background(selected ? Color.blue : Color(uiColor14: UIColor.tertiarySystemBackground)) .cornerRadius(8) - .foregroundColor(.init(uiColor14: .label)) + .foregroundColor(selected ? .white : .init(uiColor14: .label) ) } .padding(10) .background(Color(uiColor14: .secondarySystemBackground)) .cornerRadius(16) + .onAppear { + icons = (try? themeManager.icons(forAppIDs: ["com.apple.mobilephone", "com.apple.mobilesafari", "com.apple.mobileslideshow", "com.apple.camera", "com.apple.AppStore", "com.apple.Preferences", "com.apple.Music", "com.apple.calculator"], from: theme)) ?? [] + selected = themeManager.preferedThemes.contains(where: { t in t.name == theme.name }) + } } } struct ThemeView_Previews: PreviewProvider { static var previews: some View { - ThemeView(theme: Theme(name: "Theme", iconCount: 23), isInUse: true, wallpaper: UIImage(named: "wallpaper")!, applyTheme: { _ in}) + ThemeView(theme: Theme(name: "Theme", iconCount: 23), wallpaper: UIImage(named: "wallpaper")!) .frame(width: 190) } } diff --git a/TrollTools/Views/Themes/ThemesSettingsView.swift b/TrollTools/Views/Themes/ThemesSettingsView.swift index a417260..b3c9e7e 100644 --- a/TrollTools/Views/Themes/ThemesSettingsView.swift +++ b/TrollTools/Views/Themes/ThemesSettingsView.swift @@ -7,40 +7,40 @@ import SwiftUI -struct ThemesSettingsView: View { - @State var hidesLabels = UserDefaults.standard.bool(forKey: "hidesLabels") - - @Environment(\.horizontalSizeClass) var sizeClass - - - var body: some View { - List { - Toggle(isOn: $hidesLabels) { - Text("Hide WebClip Labels") - } - .onChange(of: hidesLabels, perform: { new in - UserDefaults.standard.set(new, forKey: "hidesLabels") - do { - try WebclipsThemeManager.changeLabelVisibility(visible: !hidesLabels) - respring() - } catch { - UIApplication.shared.alert(body: error.localizedDescription) - } - }) -// Button("Change theming method") { -// showsMethodChoosingPopover = true -// } -// .fullScreenCover(isPresented: $showsMethodChoosingPopover) { -// ThemesMethodChoosingView() +//struct ThemesSettingsView: View { +// @State var hidesLabels = UserDefaults.standard.bool(forKey: "hidesLabels") +// +// @Environment(\.horizontalSizeClass) var sizeClass +// +// +// var body: some View { +// List { +// Toggle(isOn: $hidesLabels) { +// Text("Hide WebClip Labels") // } - } - .listStyle(PlainListStyle()) - .frame(minWidth: 300, minHeight: 200) - } -} - -struct ThemesSettings_Previews: PreviewProvider { - static var previews: some View { - ThemesSettingsView() - } -} +// .onChange(of: hidesLabels, perform: { new in +// UserDefaults.standard.set(new, forKey: "hidesLabels") +// do { +// try WebclipsThemeManager.changeLabelVisibility(visible: !hidesLabels) +// respring() +// } catch { +// UIApplication.shared.alert(body: error.localizedDescription) +// } +// }) +//// Button("Change theming method") { +//// showsMethodChoosingPopover = true +//// } +//// .fullScreenCover(isPresented: $showsMethodChoosingPopover) { +//// ThemesMethodChoosingView() +//// } +// } +// .listStyle(PlainListStyle()) +// .frame(minWidth: 300, minHeight: 200) +// } +//} +// +//struct ThemesSettings_Previews: PreviewProvider { +// static var previews: some View { +// ThemesSettingsView() +// } +//} diff --git a/TrollTools/Views/Themes/ThemesView.swift b/TrollTools/Views/Themes/ThemesView.swift index 2139376..c9c7d3e 100644 --- a/TrollTools/Views/Themes/ThemesView.swift +++ b/TrollTools/Views/Themes/ThemesView.swift @@ -8,59 +8,117 @@ import SwiftUI struct ThemesView: View { + @EnvironmentObject var themeManager: ThemeManager @State private var isImporting = false + @State var isSelectingCustomIcons = false + @State var showsSettings = false + @State var wallpaper: UIImage? @State var defaultWallpaper = false private var gridItemLayout = [GridItem(.adaptive(minimum: 160))] + @State var themes: [Theme] = [] - @State var currentThemeIDs: [String] = [] - @State var showsSettings = false var body: some View { - NavigationView { - Group { - if themes.count == 0 { - Text("No themes imported. \nImport them using the button in the top right corner (Themes have to contain icons in the format of .png).") - .padding() - .background(Color(uiColor14: .secondarySystemBackground)) - .multilineTextAlignment(.center) - .cornerRadius(16) - .font(.footnote) - .foregroundColor(Color(uiColor14: .secondaryLabel)) - } else { - ScrollView { - LazyVGrid(columns: gridItemLayout, spacing: 8) { - ForEach(themes, id: \.url) { theme in - ThemeView(theme: theme, isInUse: currentThemeIDs.contains(theme.id.uuidString), wallpaper: wallpaper!, defaultWallpaper: defaultWallpaper, applyTheme: applyTheme) - .contextMenu { - Button { - themes.removeAll { theme1 in theme1.id == theme.id } - saveThemes() - do { - try ThemeManager.removeImportedTheme(theme: theme) - } catch { - UIApplication.shared.alert(body: error.localizedDescription) + ZStack { + NavigationView { + Group { + if themes.count == 0 { + Text("No themes imported. \nImport them using the button in the top right corner (Themes have to contain icons in the format of .png).") + .padding() + .background(Color(uiColor14: .secondarySystemBackground)) + .multilineTextAlignment(.center) + .cornerRadius(16) + .font(.footnote) + .foregroundColor(Color(uiColor14: .secondaryLabel)) + } else { + ScrollView { + LazyVGrid(columns: gridItemLayout, spacing: 8) { + ForEach(themes, id: \.name) { theme in + ThemeView(theme: theme, wallpaper: wallpaper!, defaultWallpaper: defaultWallpaper) + .contextMenu { + Button { + themes.removeAll { theme1 in theme1.id == theme.id } + themeManager.themes = themes + do { + try themeManager.removeImportedTheme(theme: theme) + } catch { + UIApplication.shared.alert(body: error.localizedDescription) + } + } label: { + Label("Remove theme", systemImage: "trash") } - } label: { - Label("Remove theme", systemImage: "trash") } + } + } + .padding(4) + + HStack { + VStack { + Text("TrollTools \(Bundle.main.infoDictionary?["CFBundleShortVersionString"] as? String ?? "Unknown")") + Text("Made by @sourcelocation.") + .font(.caption) + .foregroundColor(.secondary) + } + .frame(maxWidth: .infinity, maxHeight: .infinity) + .padding(10) + .background(Color(uiColor14: .secondarySystemBackground)) + .cornerRadius(16) + VStack { + HStack { + Text("Alternatives") + .font(.headline) + .lineLimit(1) + .minimumScaleFactor(0.7) + .padding(4) + + Text("ยท \(themeManager.iconOverrides.count)") + .font(.headline) + .foregroundColor(Color.secondary) + Spacer() } + NavigationLink(destination: IconOverridesView()) { + Text("Change") + .frame(maxWidth: .infinity) + .padding(10) + .background(Color(uiColor14: UIColor.tertiarySystemBackground)) + .cornerRadius(8) + .foregroundColor(.init(uiColor14: .label)) + } + } + .frame(maxWidth: .infinity) + .padding(10) + .background(Color(uiColor14: .secondarySystemBackground)) + .cornerRadius(16) } + .padding(.bottom, 80) } - .padding(4) - - Text("TrollTools \(Bundle.main.infoDictionary?["CFBundleShortVersionString"] as? String ?? "Unknown") by @sourcelocation.") - .font(.caption) - .foregroundColor(.secondary) - - .padding() + .padding(.horizontal, 6) } - .padding(.horizontal, 6) } + .toolbar { + ToolbarItem(placement: .navigationBarTrailing) { + Button(action: { + isImporting = true + }) { + Image(systemName: "square.and.arrow.down") + } + } + ToolbarItem(placement: .navigationBarLeading) { + Button(action: { + UIApplication.shared.confirmAlert(title: "Full reset", body: "All app icons will be reverted to their original appearance and WebClips will be deleted. Are you sure you want to continue?", onOK: { + removeThemes(removeWebClips: true) + }, noCancel: false) + }) { + Image(systemName: "arrow.uturn.backward") + } + } + } + .navigationTitle("Themes") + .navigationBarTitleTextColor(Color(uiColor14: .label)) } - .navigationTitle("Themes") - .navigationBarTitleTextColor(Color(uiColor14: .label)) + .frame(maxWidth: .infinity, maxHeight: .infinity) .onAppear { wallpaper = WallpaperGetter.homescreen() if wallpaper == nil { @@ -68,27 +126,44 @@ struct ThemesView: View { defaultWallpaper = true } - if let data = UserDefaults.standard.data(forKey: "themes") { - themes = (try? JSONDecoder().decode([Theme].self, from: data)) ?? [] + // Old version check + var shouldReset = false + remLog(themesDir) + for themeURL in (try? FileManager.default.contentsOfDirectory(at: themesDir, includingPropertiesForKeys: nil)) ?? [] { + remLog(themeURL) + for icons in (try? FileManager.default.contentsOfDirectory(at: themeURL, includingPropertiesForKeys: nil)) ?? [] { + remLog(icons) + if icons.lastPathComponent == "IconBundles" { + shouldReset = true + break + } + } + } + if shouldReset { + UIApplication.shared.confirmAlert(title: "Theme reset required", body: "Due to major changes to the engine, a reset of themes is required.", onOK: { + try? FileManager.default.removeItem(at: themesDir) + UserDefaults.standard.set(nil, forKey: "themes") + UserDefaults.standard.set(nil, forKey: "currentThemeIDs") + removeThemes(removeWebClips: false) + }, noCancel: true) } - currentThemeIDs = UserDefaults.standard.array(forKey: "currentThemeIDs") as? [String] ?? [] + themes = themeManager.themes } - .toolbar { - ToolbarItem(placement: .navigationBarTrailing) { - Button(action: { - isImporting = true - }) { - Image(systemName: "square.and.arrow.down") - } - } - ToolbarItem(placement: .navigationBarLeading) { - Button(action: { - UIApplication.shared.confirmAlert(title: "Remove custom icons", body: "All app icons will be reverted to their original appearance, but system app WebClips will remain. If you don't want them, you can safely delete them as any other normal app. Are you sure you want to continue?", onOK: { - removeThemes() - }, noCancel: false) - }) { - Image(systemName: "trash") + + VStack { + Spacer() + Button(action: { + applyChanges() + }) { + if themes.count > 0 { + Text("Apply changes") + .padding() + .frame(maxWidth: .infinity) + .background(Color.blue) + .cornerRadius(8) + .padding() + .foregroundColor(.white) } } } @@ -96,7 +171,7 @@ struct ThemesView: View { .navigationViewStyle(StackNavigationViewStyle()) .fileImporter( isPresented: $isImporting, - allowedContentTypes: [.folder], + allowedContentTypes: [.folder, .init(filenameExtension: "theme")!], allowsMultipleSelection: false ) { result in guard let url = try? result.get().first else { UIApplication.shared.alert(body: "Couldn't get url of file. Did you select it?"); return } @@ -107,27 +182,25 @@ struct ThemesView: View { return } do { - let theme = try ThemeManager.importTheme(from: url) + let theme = try themeManager.importTheme(from: url) themes.append(theme) - saveThemes() + themeManager.themes = themes } catch { UIApplication.shared.alert(body: error.localizedDescription) } } } - - func applyTheme(_ theme: Theme) { + func applyChanges() { func apply() { let timeStart = Date() DispatchQueue.global(qos: .userInitiated).async { UIApplication.shared.alert(title: "Starting", body: "Please wait", animated: false, withButton: false) do { - try ThemeManager.set(theme: theme, progress: { str in + try themeManager.applyChanges(progress: { str in UIApplication.shared.change(title: "In progress", body: str) }) + UINotificationFeedbackGenerator().notificationOccurred(.success) UIApplication.shared.change(title: "Rebuilding Icon Cache...", body: "Device will respring after rebuild\n\nElapsed time: \(Double(Int(-timeStart.timeIntervalSinceNow * 100.0)) / 100.0)s") DispatchQueue.main.asyncAfter(deadline: .now() + 0.1, execute: { try! RootHelper.rebuildIconCache() - currentThemeIDs.append(theme.id.uuidString) - UserDefaults.standard.set(currentThemeIDs, forKey: "currentThemeIDs") exit(0) // because it resprings }) } catch { UIApplication.shared.change(body: error.localizedDescription) } @@ -138,30 +211,28 @@ struct ThemesView: View { if FileManager.default.fileExists(atPath: app.bundleURL.appendingPathComponent("bak.car").path) { if !UserDefaults.standard.bool(forKey: "readAltAppsWarning") { found = true + UINotificationFeedbackGenerator().notificationOccurred(.warning) UIApplication.shared.confirmAlert(title: "Mugunghwa installed - PLEASE READ.", body: "It seems you've used other theming engines on this device. It is highly recommended resetting all their options to default values and removing the app.", onOK: { UserDefaults.standard.set(true, forKey: "readAltAppsWarning"); apply() }, noCancel: false) break } } } - if !found { apply() } - } - func saveThemes() { - guard let data = try? JSONEncoder().encode(themes) else { UIApplication.shared.alert(body: "Couldn't save themes"); return } - UserDefaults.standard.set(data, forKey: "themes") + if !found { + UIImpactFeedbackGenerator(style: .light).impactOccurred(); apply() + } } - func removeThemes() { + func removeThemes(removeWebClips: Bool) { DispatchQueue.global(qos: .userInitiated).async { UIApplication.shared.alert(title: "Starting", body: "Please wait", animated: false, withButton: false) - try? ThemeManager.removeCurrentThemes(progress: { str in + try? themeManager.removeCurrentThemes(removeWebClips: removeWebClips, progress: { str in UIApplication.shared.change(title: "In progress", body: str) }) DispatchQueue.main.async { - currentThemeIDs = [] - UserDefaults.standard.set([], forKey: "currentThemeIDs") + UINotificationFeedbackGenerator().notificationOccurred(.success) UIApplication.shared.change(title: "Rebuilding Icon Cache...", body: "Device will respring after rebuild") DispatchQueue.main.asyncAfter(deadline: .now() + 0.1, execute: { try! RootHelper.rebuildIconCache() - exit(0) // because it resprings + // exit(0) // because it resprings }) } } diff --git a/build.command b/build.command index 15f704a..a1b41aa 100755 --- a/build.command +++ b/build.command @@ -9,6 +9,9 @@ APPLICATION_NAME=TrollTools CONFIGURATION=Debug cd build +if [ -e "$APPLICATION_NAME.tipa" ]; then +rm $APPLICATION_NAME.tipa +fi # Build .app xcodebuild -project "$WORKING_LOCATION/$APPLICATION_NAME.xcodeproj" \ @@ -61,4 +64,3 @@ cp -r $APPLICATION_NAME.app Payload/$APPLICATION_NAME.app zip -vr $APPLICATION_NAME.tipa Payload rm -rf $APPLICATION_NAME.app rm -rf Payload -zip -vr share.zip $APPLICATION_NAME.tipa diff --git a/entitlements.plist b/entitlements.plist index 108995a..35d3f3e 100644 --- a/entitlements.plist +++ b/entitlements.plist @@ -38,4 +38,4 @@ com.apple.private.WebClips.read-write - \ No newline at end of file +