Skip to content

Commit

Permalink
v1.2 with mod preferences
Browse files Browse the repository at this point in the history
  • Loading branch information
pixelomer committed Feb 22, 2020
1 parent 2992a13 commit ba39cc1
Show file tree
Hide file tree
Showing 16 changed files with 314 additions and 11 deletions.
1 change: 1 addition & 0 deletions ExampleMods/colorfulgoose/PXColorfulGoose.h
Original file line number Diff line number Diff line change
Expand Up @@ -5,4 +5,5 @@
CGFloat hue;
}
- (void)handleFrameInState:(MGGooseFrameState)state;
@property (nonatomic, assign) BOOL enabled;
@end
14 changes: 13 additions & 1 deletion ExampleMods/joethegoose/PXJoeTheGooseMod.h
Original file line number Diff line number Diff line change
@@ -1,5 +1,17 @@
#import <UIKit/UIKit.h>
#import <MobileGoose.h>

@interface PXJoeTheGooseMod : NSObject<MGMod>
#define PrefValue(key) ([NSUserDefaults.standardUserDefaults \
objectForKey:key \
inDomain:@"com.pixelomer.joethegoose" \
])

@interface NSUserDefaults(Private)
- (id)objectForKey:(NSString *)key inDomain:(NSString *)domain;
@end

@interface PXJoeTheGooseMod : NSObject<MGMod> {
UILabel *nameLabel;
}
@property (nonatomic, assign) BOOL enabled;
@end
15 changes: 13 additions & 2 deletions ExampleMods/joethegoose/PXJoeTheGooseMod.m
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@ @implementation PXJoeTheGooseMod

- (instancetype)initWithGoose:(MGGooseView *)goose bundle:(NSBundle *)bundle {
if ((self = [super init])) {
UILabel *nameLabel = [[UILabel alloc] initWithFrame:CGRectMake(
nameLabel = [[UILabel alloc] initWithFrame:CGRectMake(
14.0,
goose.frame.size.height / 1.5,
goose.frame.size.width - 35.0,
Expand All @@ -15,10 +15,21 @@ - (instancetype)initWithGoose:(MGGooseView *)goose bundle:(NSBundle *)bundle {
nameLabel.textAlignment = NSTextAlignmentCenter;
nameLabel.minimumScaleFactor = 0.1;
nameLabel.backgroundColor = [UIColor colorWithWhite:1.0 alpha:0.75];
nameLabel.text = @"Joe";
[goose addSubview:nameLabel];
[self preferenceWithKey:@"Name" didChangeToValue:nil];
}
return self;
}

- (void)setEnabled:(BOOL)enabled {
nameLabel.hidden = !enabled;
_enabled = enabled;
}

- (void)preferenceWithKey:(NSString *)key didChangeToValue:(id)value {
if (!value) value = PrefValue(key);
if (![key isEqualToString:@"Name"] || ![value isKindOfClass:[NSString class]]) return;
nameLabel.text = ((NSString *)value).length ? value : @"Joe";
}

@end
2 changes: 2 additions & 0 deletions ExampleMods/joethegoose/Resources/Info.plist
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,8 @@
<string>1.0.0</string>
<key>NSPrincipalClass</key>
<string>PXJoeTheGooseMod</string>
<key>CFBundleDisplayName</key>
<string>Goose Name Tag</string>
</dict>
</plist>

27 changes: 27 additions & 0 deletions ExampleMods/joethegoose/Resources/Root.plist
Original file line number Diff line number Diff line change
@@ -0,0 +1,27 @@
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
<plist version="1.0">
<dict>
<key>items</key>
<array>
<dict>
<key>cell</key>
<string>PSGroupCell</string>
<key>label</key>
<string>Options</string>
</dict>
<dict>
<key>cell</key>
<string>PSEditTextCell</string>
<key>default</key>
<string>Joe</string>
<key>placeholder</key>
<string>Joe</string>
<key>key</key>
<string>Name</string>
<key>label</key>
<string>Goose Name:</string>
</dict>
</array>
</dict>
</plist>
2 changes: 1 addition & 1 deletion Goose/MGGooseController.mm
Original file line number Diff line number Diff line change
Expand Up @@ -16,7 +16,7 @@ @implementation MGGooseController
- (void)loadMeme {
BOOL isImage = [imageContainer isKindOfClass:[MGImageContainerView class]];
NSString *path = [NSString
stringWithFormat:@"/Library/Application Support/MobileGoose/%@",
stringWithFormat:@"/Library/MobileGoose/%@",
isImage ? @"Memes" : @"Notes"
];
NSArray *files = [NSFileManager.defaultManager contentsOfDirectoryAtPath:path error:nil];
Expand Down
2 changes: 1 addition & 1 deletion Prefs/Makefile
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@ include $(THEOS)/makefiles/common.mk

BUNDLE_NAME = MobileGoose

MobileGoose_FILES = PXMGPRootListController.m
MobileGoose_FILES = $(wildcard *.m)
MobileGoose_INSTALL_PATH = /Library/PreferenceBundles
MobileGoose_FRAMEWORKS = UIKit
MobileGoose_PRIVATE_FRAMEWORKS = Preferences
Expand Down
6 changes: 6 additions & 0 deletions Prefs/PXMGPModDetailsController.h
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
#import <Preferences/PSListController.h>

@interface PXMGPModDetailsController : PSListController {
NSBundle *_modBundle;
}
@end
95 changes: 95 additions & 0 deletions Prefs/PXMGPModDetailsController.m
Original file line number Diff line number Diff line change
@@ -0,0 +1,95 @@
#include "PXMGPModDetailsController.h"
#import <Preferences/PSSpecifier.h>

@interface PSSpecifier(Private)
- (instancetype)initWithName:(NSString *)identifier target:(id)target set:(SEL)set get:(SEL)get detail:(Class)detail cell:(PSCellType)cellType edit:(Class)edit;
@end

@interface NSUserDefaults(Private)
- (void)setObject:(id)arg1 forKey:(id)arg2 inDomain:(id)arg3;
- (id)objectForKey:(id)arg1 inDomain:(id)arg2;
@end

@interface NSDistributedNotificationCenter : NSNotificationCenter
- (void)postNotificationName:(NSNotificationName)name
object:(NSString *)object
userInfo:(NSDictionary *)userInfo
deliverImmediately:(BOOL)deliverImmediately;
@end

@implementation PXMGPModDetailsController

- (void)viewDidLoad {
[super viewDidLoad];
self.title = self.specifier.name;
}

- (NSArray *)specifiers {
if (!_specifiers) {
NSString *modPath = [self.specifier propertyForKey:@"modPath"];
if (!modPath) return nil;
_modBundle = [NSBundle bundleWithPath:modPath];
if (!_modBundle) return nil;
NSMutableArray *mutableSpecifiers = [NSMutableArray new];
PSSpecifier *enabledSpecifier;
SEL setter = @selector(setModPreferenceValue:specifier:);
SEL getter = @selector(modPreferenceValueForSpecifier:);
enabledSpecifier = [PSSpecifier
preferenceSpecifierNamed:@"Enabled"
target:self
set:setter
get:getter
detail:nil
cell:PSSwitchCell
edit:nil
];
[enabledSpecifier setProperty:@"Enabled" forKey:@"key"];
[enabledSpecifier setProperty:@YES forKey:@"default"];
[mutableSpecifiers addObject:enabledSpecifier];
NSArray *specifiersFromFile = [self
loadSpecifiersFromPlistName:@"Root"
target:self
bundle:_modBundle
];
for (PSSpecifier *specifier in specifiersFromFile) {
NSMutableDictionary *properties = specifier.properties;
PSSpecifier *correctedSpecifier = [specifier
initWithName:specifier.name
target:self
set:setter
get:getter
detail:nil
cell:specifier.cellType
edit:nil
];
specifier.properties = properties;
[mutableSpecifiers addObject:correctedSpecifier];
}
_specifiers = mutableSpecifiers.copy;
}
return _specifiers;
}

- (void)setModPreferenceValue:(id)value specifier:(PSSpecifier *)specifier {
NSLog(@"%@ <= %@", specifier, value);
NSString *key = [specifier propertyForKey:@"key"];
NSString *bundleID = _modBundle.bundleIdentifier;
[NSUserDefaults.standardUserDefaults setObject:value forKey:key inDomain:bundleID];
[NSUserDefaults.standardUserDefaults synchronize];
[(NSDistributedNotificationCenter *)[NSClassFromString(@"NSDistributedNotificationCenter") defaultCenter]
postNotificationName:@"com.pixelomer.mobilegoose/ModPreferencesChanged"
object:_modBundle.bundlePath
userInfo:@{ @"key": key, @"newValue" : value }
deliverImmediately:YES
];
}

- (id)modPreferenceValueForSpecifier:(PSSpecifier *)specifier {
NSString *key = [specifier propertyForKey:@"key"];
NSString *bundleID = _modBundle.bundleIdentifier;
id value = [NSUserDefaults.standardUserDefaults objectForKey:key inDomain:bundleID];
NSLog(@"%@ => %@", specifier, value);
return value ?: [specifier propertyForKey:@"default"];
}

@end
5 changes: 5 additions & 0 deletions Prefs/PXMGPModListController.h
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
#import <Preferences/PSListController.h>

@interface PXMGPModListController : PSListController

@end
69 changes: 69 additions & 0 deletions Prefs/PXMGPModListController.m
Original file line number Diff line number Diff line change
@@ -0,0 +1,69 @@
#import "PXMGPModListController.h"
#import "PXMGPModDetailsController.h"
#import <Preferences/PSSpecifier.h>

@implementation PXMGPModListController

- (NSArray *)specifiers {
if (!_specifiers) {
NSMutableArray *mutableSpecifiers = [NSMutableArray new];
NSString *modRoot = @"/Library/MobileGoose/Mods";
NSError *error = nil;
NSArray *modNames = [NSFileManager.defaultManager
contentsOfDirectoryAtPath:modRoot
error:&error
];
PSSpecifier *specifier;
if (!error && modNames.count) {
specifier = [PSSpecifier
preferenceSpecifierNamed:@"Installed Mods"
target:nil
set:nil
get:nil
detail:nil
cell:PSGroupCell
edit:nil
];
[mutableSpecifiers addObject:specifier];
for (NSString *modName in modNames) {
@autoreleasepool {
NSString *fullModPath = [modRoot stringByAppendingPathComponent:modName];
NSBundle *bundle = [NSBundle bundleWithPath:fullModPath];
specifier = [PSSpecifier
preferenceSpecifierNamed:(
(bundle.localizedInfoDictionary ?: bundle.infoDictionary)[@"CFBundleDisplayName"] ?:
modName.stringByDeletingPathExtension
)
target:self
set:nil
get:nil
detail:(bundle ? [PXMGPModDetailsController class] : nil)
cell:PSLinkCell
edit:nil
];
NSLog(@"%@ %@", specifier.name, bundle.infoDictionary);
[specifier setProperty:fullModPath forKey:@"modPath"];
[mutableSpecifiers addObject:specifier];
}
}
}
else {
specifier = [PSSpecifier
preferenceSpecifierNamed:nil
target:nil
set:nil
get:nil
detail:nil
cell:PSGroupCell
edit:nil
];
[specifier setProperty:@"No MobileGoose mods seem to be installed." forKey:@"footerText"];
[mutableSpecifiers addObject:specifier];
}
_specifiers = mutableSpecifiers.copy;
}

return _specifiers;
}

@end
16 changes: 16 additions & 0 deletions Prefs/Resources/Root.plist
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,12 @@
<dict>
<key>items</key>
<array>
<dict>
<key>cell</key>
<string>PSGroupCell</string>
<key>label</key>
<string>MobileGooses</string>
</dict>
<dict>
<key>cell</key>
<string>PSSwitchCell</string>
Expand All @@ -20,6 +26,16 @@
<key>anyNotification</key>
<string>com.pixelomer.mobilegoose/PreferenceChange</string>
</dict>
<dict>
<key>cell</key>
<string>PSLinkCell</string>
<key>detail</key>
<string>PXMGPModListController</string>
<key>isController</key>
<true/>
<key>label</key>
<string>Mods</string>
</dict>
<dict>
<key>cell</key>
<string>PSGroupCell</string>
Expand Down
6 changes: 6 additions & 0 deletions Template/MobileGoose.h
Original file line number Diff line number Diff line change
Expand Up @@ -19,11 +19,17 @@ typedef void(^MGGooseFrameHandler)(MGGooseView *, MGGooseFrameState);
typedef void(^MGGooseCommonBlock)(MGGooseView *);

@protocol MGMod

@required
@property (nonatomic, assign) BOOL enabled;

@optional
- (void)preferenceWithKey:(NSString *)key didChangeToValue:(id)value;
- (instancetype)initWithGoose:(MGGooseView *)goose;
- (instancetype)initWithGoose:(MGGooseView *)goose bundle:(NSBundle *)bundle;
- (void)handleFrameInState:(MGGooseFrameState)state;
- (void)springboardDidFinishLaunching:(SpringBoard *)application;

@end

// ALL of the methods in this class MUST be called on the main thread.
Expand Down
Loading

0 comments on commit ba39cc1

Please sign in to comment.