diff --git a/DDHotKey b/DDHotKey index c7735ee6..a996a0a3 160000 --- a/DDHotKey +++ b/DDHotKey @@ -1 +1 @@ -Subproject commit c7735ee66a0e73f1810d2d41f0b02004a4f5a330 +Subproject commit a996a0a3980de926168df7c2f8b02a1231760561 diff --git a/MacPass.xcodeproj/project.pbxproj b/MacPass.xcodeproj/project.pbxproj index 148ac60a..7645077d 100644 --- a/MacPass.xcodeproj/project.pbxproj +++ b/MacPass.xcodeproj/project.pbxproj @@ -43,6 +43,8 @@ 4C2057EE23CDF6F900C731EC /* MPPathCell.m in Sources */ = {isa = PBXBuildFile; fileRef = 4C2057ED23CDF6F900C731EC /* MPPathCell.m */; }; 4C2057F423CF3BA600C731EC /* MPAutotypeEnvironment.m in Sources */ = {isa = PBXBuildFile; fileRef = 4C2057F323CF3BA600C731EC /* MPAutotypeEnvironment.m */; }; 4C2057F723CF3E9A00C731EC /* NSRunningApplication+MPAdditions.m in Sources */ = {isa = PBXBuildFile; fileRef = 4C2057F623CF3E9A00C731EC /* NSRunningApplication+MPAdditions.m */; }; + 4C20E4C123E4753A00807FAE /* MPDocumentSplitViewController.m in Sources */ = {isa = PBXBuildFile; fileRef = 4C20E4BF23E4753A00807FAE /* MPDocumentSplitViewController.m */; }; + 4C20E4C223E4753A00807FAE /* DocumentSplitView.xib in Resources */ = {isa = PBXBuildFile; fileRef = 4C20E4C023E4753A00807FAE /* DocumentSplitView.xib */; }; 4C224B4217DFCB2400FF6AEE /* MPNumericalInputFormatter.m in Sources */ = {isa = PBXBuildFile; fileRef = 4C224B4117DFCB2400FF6AEE /* MPNumericalInputFormatter.m */; }; 4C25703F1BF11C2300D39416 /* MPPluginPreferencesController.m in Sources */ = {isa = PBXBuildFile; fileRef = 4C25703D1BF11C2300D39416 /* MPPluginPreferencesController.m */; }; 4C25D58716CF0FAA00F6806C /* EntryView.xib in Resources */ = {isa = PBXBuildFile; fileRef = 4C25D58616CF0FAA00F6806C /* EntryView.xib */; }; @@ -412,6 +414,9 @@ 4C2057F323CF3BA600C731EC /* MPAutotypeEnvironment.m */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.objc; path = MPAutotypeEnvironment.m; sourceTree = ""; }; 4C2057F523CF3E9A00C731EC /* NSRunningApplication+MPAdditions.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = "NSRunningApplication+MPAdditions.h"; sourceTree = ""; }; 4C2057F623CF3E9A00C731EC /* NSRunningApplication+MPAdditions.m */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.objc; path = "NSRunningApplication+MPAdditions.m"; sourceTree = ""; }; + 4C20E4BE23E4753A00807FAE /* MPDocumentSplitViewController.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = MPDocumentSplitViewController.h; sourceTree = ""; }; + 4C20E4BF23E4753A00807FAE /* MPDocumentSplitViewController.m */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.objc; path = MPDocumentSplitViewController.m; sourceTree = ""; }; + 4C20E4C023E4753A00807FAE /* DocumentSplitView.xib */ = {isa = PBXFileReference; lastKnownFileType = file.xib; path = DocumentSplitView.xib; sourceTree = ""; }; 4C21F29F195B3A48002D610D /* de */ = {isa = PBXFileReference; lastKnownFileType = text.plist.strings; name = de; path = de.lproj/MainMenu.strings; sourceTree = ""; }; 4C224B4017DFCB2300FF6AEE /* MPNumericalInputFormatter.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = MPNumericalInputFormatter.h; sourceTree = ""; }; 4C224B4117DFCB2400FF6AEE /* MPNumericalInputFormatter.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = MPNumericalInputFormatter.m; sourceTree = ""; }; @@ -1626,6 +1631,9 @@ 4CAD8AA322CF397B0090B2DD /* MPAutotypeDoctorReportViewController.h */, 4CAD8AA422CF397B0090B2DD /* MPAutotypeDoctorReportViewController.m */, 78E1F8B222E3A5D600E738AE /* AutotypeDoctorReportViewController.xib */, + 4C20E4BE23E4753A00807FAE /* MPDocumentSplitViewController.h */, + 4C20E4BF23E4753A00807FAE /* MPDocumentSplitViewController.m */, + 4C20E4C023E4753A00807FAE /* DocumentSplitView.xib */, ); name = "View Controller"; sourceTree = ""; @@ -1920,6 +1928,7 @@ 4C3826AF1AD04D8E007D7D67 /* 34_ConfigureTemplate.pdf in Resources */, 4C3826BB1AD04D8E007D7D67 /* 47_PackageTemplate.pdf in Resources */, 6021FE8D18E1617300C3BC51 /* PasswordCreatorView.xib in Resources */, + 4C20E4C223E4753A00807FAE /* DocumentSplitView.xib in Resources */, 4C3826AC1AD04D8E007D7D67 /* 29_SecureTerminalTemplate.pdf in Resources */, 4C3826741AD04BA5007D7D67 /* infoTemplate.pdf in Resources */, 4C3826B11AD04D8E007D7D67 /* 36_ArchiveTemplate.pdf in Resources */, @@ -2057,6 +2066,7 @@ 4C81867D216664C70068DAFB /* MPPluginRepositoryItemVersionInfo.m in Sources */, 4CDA35751EBA0CF2003CD59F /* NSString+MPComposedCharacterAdditions.m in Sources */, 4CE39ABF16ECE34A000FE29D /* MPIconSelectViewController.m in Sources */, + 4C20E4C123E4753A00807FAE /* MPDocumentSplitViewController.m in Sources */, 4CE39AC416ECE4F7000FE29D /* MPIconImageView.m in Sources */, 4C46B88517063A070046109A /* NSString+MPPasswordCreation.m in Sources */, 4C5A11FE1708DE8700223D8A /* MPPasswordCreatorViewController.m in Sources */, @@ -2778,7 +2788,7 @@ CLANG_WARN__DUPLICATE_METHOD_MATCH = YES; CODE_SIGN_IDENTITY = ""; COPY_PHASE_STRIP = NO; - CURRENT_PROJECT_VERSION = 0.7.11; + CURRENT_PROJECT_VERSION = "0.8-beta"; ENABLE_STRICT_OBJC_MSGSEND = YES; ENABLE_TESTABILITY = YES; GCC_C_LANGUAGE_STANDARD = gnu99; @@ -2800,7 +2810,7 @@ GCC_WARN_UNUSED_FUNCTION = YES; GCC_WARN_UNUSED_VARIABLE = YES; HEADER_SEARCH_PATHS = "$(SDKROOT)/usr/include/libxml2/**"; - MACOSX_DEPLOYMENT_TARGET = 10.10; + MACOSX_DEPLOYMENT_TARGET = 10.13; ONLY_ACTIVE_ARCH = YES; OTHER_LDFLAGS = "-lxml2"; SDKROOT = macosx; @@ -2833,7 +2843,7 @@ CLANG_WARN__DUPLICATE_METHOD_MATCH = YES; CODE_SIGN_IDENTITY = ""; COPY_PHASE_STRIP = YES; - CURRENT_PROJECT_VERSION = 0.7.11; + CURRENT_PROJECT_VERSION = "0.8-beta"; DEBUG_INFORMATION_FORMAT = "dwarf-with-dsym"; ENABLE_STRICT_OBJC_MSGSEND = YES; GCC_C_LANGUAGE_STANDARD = gnu99; @@ -2848,7 +2858,7 @@ GCC_WARN_UNUSED_FUNCTION = YES; GCC_WARN_UNUSED_VARIABLE = YES; HEADER_SEARCH_PATHS = "$(SDKROOT)/usr/include/libxml2/**"; - MACOSX_DEPLOYMENT_TARGET = 10.10; + MACOSX_DEPLOYMENT_TARGET = 10.13; OTHER_LDFLAGS = "-lxml2"; SDKROOT = macosx; WARNING_CFLAGS = "-Wpartial-availability"; diff --git a/MacPass/DDHotKey+MacPassAdditions.m b/MacPass/DDHotKey+MacPassAdditions.m index 7a656aee..1806df97 100644 --- a/MacPass/DDHotKey+MacPassAdditions.m +++ b/MacPass/DDHotKey+MacPassAdditions.m @@ -86,19 +86,19 @@ NSEventModifierFlags flags = 0; switch(self.keyCode) { case kVK_Command: - flags = NSCommandKeyMask; + flags = NSEventModifierFlagCommand; break; case kVK_Shift: case kVK_RightShift: - flags = NSShiftKeyMask; + flags = NSEventModifierFlagShift; break; case kVK_Option: case kVK_RightOption: - flags = NSAlternateKeyMask; + flags = NSEventModifierFlagOption; break; case kVK_Control: case kVK_RightControl: - flags = NSControlKeyMask; + flags = NSEventModifierFlagControl; break; } BOOL missingModifier = self.modifierFlags == 0; diff --git a/MacPass/DocumentSplitView.xib b/MacPass/DocumentSplitView.xib new file mode 100644 index 00000000..d61c3950 --- /dev/null +++ b/MacPass/DocumentSplitView.xib @@ -0,0 +1,22 @@ + + + + + + + + + + + + + + + + + + + + + + diff --git a/MacPass/DocumentWindow.xib b/MacPass/DocumentWindow.xib index 41fe2285..909233db 100644 --- a/MacPass/DocumentWindow.xib +++ b/MacPass/DocumentWindow.xib @@ -1,32 +1,28 @@ - + - + - - + - + - + - - - diff --git a/MacPass/MPAppDelegate.m b/MacPass/MPAppDelegate.m index 7ccae156..942ca07b 100644 --- a/MacPass/MPAppDelegate.m +++ b/MacPass/MPAppDelegate.m @@ -241,7 +241,7 @@ typedef NS_OPTIONS(NSInteger, MPAppStartupState) { self.saveMenuItem.title = saveTitle; } else if(menu == self.fixAutotypeMenuItem.menu) { - self.fixAutotypeMenuItem.hidden = !(NSEvent.modifierFlags & NSAlternateKeyMask); + self.fixAutotypeMenuItem.hidden = !(NSEvent.modifierFlags & NSEventModifierFlagOption); } else if(menu == self.importMenu) { NSMenuItem *exportXML = menu.itemArray.firstObject; diff --git a/MacPass/MPAutotypeDaemon.m b/MacPass/MPAutotypeDaemon.m index 33ccade9..eb44d267 100644 --- a/MacPass/MPAutotypeDaemon.m +++ b/MacPass/MPAutotypeDaemon.m @@ -364,7 +364,7 @@ static MPAutotypeDaemon *_sharedInstance; if(!self.matchSelectionWindow) { self.matchSelectionWindow = [[NSPanel alloc] initWithContentRect:NSMakeRect(0, 0, 100, 100) styleMask:NSWindowStyleMaskNonactivatingPanel|NSWindowStyleMaskTitled - backing:NSBackingStoreRetained + backing:NSBackingStoreBuffered defer:YES]; self.matchSelectionWindow.level = kCGAssistiveTechHighWindowLevel; MPAutotypeCandidateSelectionViewController *vc = [[MPAutotypeCandidateSelectionViewController alloc] init]; diff --git a/MacPass/MPContextButton.m b/MacPass/MPContextButton.m index c09e989f..6c95fa77 100644 --- a/MacPass/MPContextButton.m +++ b/MacPass/MPContextButton.m @@ -102,15 +102,15 @@ NSImageRep *rep = [[self imageForSegment:MPContextButtonSegmentButton] bestRepresentationForRect:NSMakeRect(0, 0, 100, 100) context:nil hints:nil]; CGFloat scale = rep.size.width / rep.size.height; switch (controlSize) { - case NSRegularControlSize: + case NSControlSizeRegular: [self imageForSegment:MPContextButtonSegmentButton].size = NSMakeSize(16 * scale, 16); break; - case NSSmallControlSize: + case NSControlSizeSmall: [self imageForSegment:MPContextButtonSegmentButton].size = NSMakeSize(14 * scale, 14); break; - case NSMiniControlSize: + case NSControlSizeMini: [self imageForSegment:MPContextButtonSegmentButton].size = NSMakeSize(8 * scale, 8); default: diff --git a/MacPass/MPContextMenuHelper.m b/MacPass/MPContextMenuHelper.m index 7304dc91..8fce1f2f 100644 --- a/MacPass/MPContextMenuHelper.m +++ b/MacPass/MPContextMenuHelper.m @@ -84,7 +84,7 @@ static void MPContextmenuHelperBeginSection(NSMutableArray *items) { NSMenuItem *emptyTrash = [[NSMenuItem alloc] initWithTitle:NSLocalizedString(@"EMPTY_TRASH", @"Menu item to empty the trash") action:[MPActionHelper actionOfType:MPActionEmptyTrash] keyEquivalent:@""]; - emptyTrash.keyEquivalentModifierMask = (NSShiftKeyMask | NSCommandKeyMask); + emptyTrash.keyEquivalentModifierMask = (NSEventModifierFlagShift | NSEventModifierFlagCommand); unichar backSpace = NSBackspaceCharacter; emptyTrash.keyEquivalent = [NSString stringWithCharacters:&backSpace length:1]; [items addObject:emptyTrash]; @@ -99,7 +99,7 @@ static void MPContextmenuHelperBeginSection(NSMutableArray *items) { NSMenuItem *copyPassword = [[NSMenuItem alloc] initWithTitle:NSLocalizedString(@"COPY_PASSWORD", @"Menu item to copy the password of an entry") action:[MPActionHelper actionOfType:MPActionCopyPassword] keyEquivalent:@"c"]; - copyPassword.keyEquivalentModifierMask = (copyPassword.keyEquivalentModifierMask | NSAlternateKeyMask); + copyPassword.keyEquivalentModifierMask = (copyPassword.keyEquivalentModifierMask | NSEventModifierFlagOption); NSMenu *urlMenu = [[NSMenu alloc] init]; NSMenuItem *urlItem = [[NSMenuItem alloc] initWithTitle:NSLocalizedString(@"URL", @"Submenu with options what to do with the URL of an entry") action:0 @@ -129,7 +129,7 @@ static void MPContextmenuHelperBeginSection(NSMutableArray *items) { NSMenuItem *showHistory = [[NSMenuItem alloc] initWithTitle:NSLocalizedString(@"SHOW_HISTORY", @"Menu item to show the history of the selected entry") action:[MPActionHelper actionOfType:MPActionShowEntryHistory] keyEquivalent:@"h"]; - showHistory.keyEquivalentModifierMask = (showHistory.keyEquivalentModifierMask | NSCommandKeyMask | NSControlKeyMask); + showHistory.keyEquivalentModifierMask = (showHistory.keyEquivalentModifierMask | NSEventModifierFlagCommand | NSEventModifierFlagControl); [items addObject:showHistory]; } if(insertShowGroupInOutline) { diff --git a/MacPass/MPDocument.m b/MacPass/MPDocument.m index 69ed34e2..523c2736 100644 --- a/MacPass/MPDocument.m +++ b/MacPass/MPDocument.m @@ -295,7 +295,7 @@ NSString *const MPDocumentGroupKey = @"MPDocumentGrou return; } NSAlert *alert = [[NSAlert alloc] init]; - alert.alertStyle = NSWarningAlertStyle; + alert.alertStyle = NSAlertStyleWarning; alert.messageText = NSLocalizedString(@"FILE_CHANGED_BY_OTHERS_MESSAGE_TEXT", @"Message displayed when an open file was changed from another application"); alert.informativeText = NSLocalizedString(@"FILE_CHANGED_BY_OTHERS_INFO_TEXT", @"Informative text displayed when the file was change from another application"); alert.showsSuppressionButton = YES; @@ -369,7 +369,7 @@ NSString *const MPDocumentGroupKey = @"MPDocumentGrou if(mergeKDB) { NSAlert *alert = [[NSAlert alloc] init]; - alert.alertStyle = NSWarningAlertStyle; + alert.alertStyle = NSAlertStyleWarning; alert.messageText = NSLocalizedString(@"ALERT_MERGE_KDB_FILE_MESSAGE", @"Alert message warning user about KDB file merge"); alert.informativeText = NSLocalizedString(@"ALERT_MERGE_KDB_FILE_INFO_TEXT", @"Informative text displayed when merging KDB files"); [alert addButtonWithTitle:NSLocalizedString(@"ALERT_MERGE_CONTINUE", @"Button in dialog to merge KDB changes into file!")]; @@ -751,7 +751,7 @@ NSString *const MPDocumentGroupKey = @"MPDocumentGrou #pragma mark Actions - (void)emptyTrash:(id)sender { NSAlert *alert = [[NSAlert alloc] init]; - alert.alertStyle = NSWarningAlertStyle; + alert.alertStyle = NSAlertStyleWarning; alert.messageText = NSLocalizedString(@"WARNING_ON_EMPTY_TRASH_TITLE", "Message text for the alert displayed when clearing the Trash"); alert.informativeText = NSLocalizedString(@"WARNING_ON_EMPTY_TRASH_DESCRIPTION", "Informative Text displayed when clearing the Trash"); @@ -770,7 +770,7 @@ NSString *const MPDocumentGroupKey = @"MPDocumentGrou KPKEntry *entry = node.asEntry; NSAlert *alert = [[NSAlert alloc] init]; - alert.alertStyle = NSWarningAlertStyle; + alert.alertStyle = NSAlertStyleWarning; alert.messageText = NSLocalizedString(@"WARNING_ON_DELETE_TRASHED_NODE_TITLE", "Message text for the alert displayed when deleting a node"); alert.informativeText = NSLocalizedString(@"WARNING_ON_DELETE_TRASHED_NODE_DESCRIPTION", "Informative Text displayed when clearing the Trash"); diff --git a/MacPass/MPDocumentController.m b/MacPass/MPDocumentController.m index 59731ee8..bccf5692 100644 --- a/MacPass/MPDocumentController.m +++ b/MacPass/MPDocumentController.m @@ -105,7 +105,7 @@ NSAlert *alert = [[NSAlert alloc] init]; alert.messageText = NSLocalizedString(@"FILE_OPEN_ERROR", "Error while reopening last known documents"); alert.informativeText = error.localizedDescription; - alert.alertStyle = NSCriticalAlertStyle; + alert.alertStyle = NSAlertStyleCritical; [alert runModal]; } diff --git a/MacPass/MPDocumentSplitViewController.h b/MacPass/MPDocumentSplitViewController.h new file mode 100644 index 00000000..99cecce8 --- /dev/null +++ b/MacPass/MPDocumentSplitViewController.h @@ -0,0 +1,30 @@ +// +// MPDocumentSplitViewController.h +// MacPass +// +// Created by Michael Starke on 31.01.20. +// Copyright © 2020 HicknHack Software GmbH. All rights reserved. +// + +#import + +NS_ASSUME_NONNULL_BEGIN + +@class MPEntryViewController; +@class MPInspectorViewController; +@class MPOutlineViewController; +@class MPDocument; + +@interface MPDocumentSplitViewController : NSSplitViewController + +@property (readonly, strong) MPEntryViewController *entryViewController; +@property (readonly, strong) MPOutlineViewController *outlineViewController; +@property (readonly, strong) MPInspectorViewController *inspectorViewController; + +- (void)registerNotificationsForDocument:(MPDocument *)document; +- (IBAction)toggleInspector:(id)sender; +- (void)showOutline; + +@end + +NS_ASSUME_NONNULL_END diff --git a/MacPass/MPDocumentSplitViewController.m b/MacPass/MPDocumentSplitViewController.m new file mode 100644 index 00000000..4374aaa4 --- /dev/null +++ b/MacPass/MPDocumentSplitViewController.m @@ -0,0 +1,87 @@ +// +// MPDocumentSplitViewController.m +// MacPass +// +// Created by Michael Starke on 31.01.20. +// Copyright © 2020 HicknHack Software GmbH. All rights reserved. +// + +#import "MPDocumentSplitViewController.h" +#import "MPOutlineViewController.h" +#import "MPEntryViewController.h" +#import "MPInspectorViewController.h" +#import "MPSettingsHelper.h" + +@interface MPDocumentSplitViewController () + +@property (strong) MPEntryViewController *entryViewController; +@property (strong) MPOutlineViewController *outlineViewController; +@property (strong) MPInspectorViewController *inspectorViewController; + +@end + +@implementation MPDocumentSplitViewController + +- (NSNibName)nibName { + return @"DocumentSplitView"; + +} + +- (instancetype)initWithNibName:(NSNibName)nibNameOrNil bundle:(NSBundle *)nibBundleOrNil { + self = [super initWithNibName:nibNameOrNil bundle:nibBundleOrNil]; + if(self) { + _outlineViewController = [[MPOutlineViewController alloc] init]; + _entryViewController = [[MPEntryViewController alloc] init]; + _inspectorViewController = [[MPInspectorViewController alloc] init]; + } + return self; +} + +- (void)viewWillLayout { + self.splitView.autosaveName = @"SplitView"; +} + +- (void)viewDidLoad { + [super viewDidLoad]; + + self.splitView.translatesAutoresizingMaskIntoConstraints = NO; + + NSSplitViewItem *outlineItem = [NSSplitViewItem sidebarWithViewController:self.outlineViewController]; + outlineItem.holdingPriority = NSLayoutPriorityDefaultLow + 2; + outlineItem.canCollapse = NO; + outlineItem.minimumThickness = 150; + NSSplitViewItem *entries = [NSSplitViewItem splitViewItemWithViewController:self.entryViewController]; + entries.canCollapse = NO; + entries.minimumThickness = 150; + NSSplitViewItem *inspector = [NSSplitViewItem splitViewItemWithViewController:self.inspectorViewController]; + inspector.canCollapse = YES; + inspector.minimumThickness = 200; + inspector.holdingPriority = NSLayoutPriorityDefaultLow + 1; + + [self addSplitViewItem:outlineItem]; + [self addSplitViewItem:entries]; + [self addSplitViewItem:inspector]; + + BOOL showInspector = [NSUserDefaults.standardUserDefaults boolForKey:kMPSettingsKeyShowInspector]; + inspector.collapsed = !showInspector; +} + +- (void)registerNotificationsForDocument:(MPDocument *)document { + + [self.entryViewController registerNotificationsForDocument:document]; + [self.outlineViewController registerNotificationsForDocument:document]; + [self.inspectorViewController registerNotificationsForDocument:document]; +} + +- (void)showOutline { + // FIXME: do not require this to be called directly + [self.outlineViewController showOutline]; +} + +- (void)toggleInspector:(id)sender { + NSSplitViewItem *inspector = [self splitViewItemForViewController:self.inspectorViewController]; + inspector.collapsed = !inspector.collapsed; + [NSUserDefaults.standardUserDefaults setBool:!inspector.collapsed forKey:kMPSettingsKeyShowInspector]; +} + +@end diff --git a/MacPass/MPDocumentWindowController.h b/MacPass/MPDocumentWindowController.h index 0927427e..ff0a6f1f 100644 --- a/MacPass/MPDocumentWindowController.h +++ b/MacPass/MPDocumentWindowController.h @@ -34,9 +34,6 @@ @interface MPDocumentWindowController : NSWindowController @property (readonly, strong) MPPasswordInputController *passwordInputController; -@property (readonly, strong) MPEntryViewController *entryViewController; -@property (readonly, strong) MPOutlineViewController *outlineViewController; -@property (readonly, strong) MPInspectorViewController *inspectorViewController; @property (readonly, strong) MPToolbarDelegate *toolbarDelegate; @property (readonly, nonatomic, strong) NSSearchField *searchField; diff --git a/MacPass/MPDocumentWindowController.m b/MacPass/MPDocumentWindowController.m index b09e5858..0eea00bd 100644 --- a/MacPass/MPDocumentWindowController.m +++ b/MacPass/MPDocumentWindowController.m @@ -29,6 +29,7 @@ #import "MPDatabaseSettingsWindowController.h" #import "MPDocument.h" #import "MPDocumentWindowDelegate.h" +#import "MPDocumentSplitViewController.h" #import "MPDuplicateEntryOptionsWindowController.h" #import "MPEntryViewController.h" #import "MPFixAutotypeWindowController.h" @@ -58,14 +59,11 @@ typedef void (^MPPasswordChangedBlock)(BOOL didChangePassword); id _firstResponder; } -@property (strong) IBOutlet NSSplitView *splitView; - @property (strong) NSToolbar *toolbar; @property (strong) MPPasswordInputController *passwordInputController; -@property (strong) MPEntryViewController *entryViewController; -@property (strong) MPOutlineViewController *outlineViewController; -@property (strong) MPInspectorViewController *inspectorViewController; +@property (strong) MPDocumentSplitViewController *splitViewController; + @property (strong) MPDatabaseSettingsWindowController *documentSettingsWindowController; @property (strong) MPDocumentWindowDelegate *documentWindowDelegate; @property (strong) MPPasswordEditWindowController *passwordEditWindowController; @@ -87,9 +85,7 @@ typedef void (^MPPasswordChangedBlock)(BOOL didChangePassword); if( self ) { _firstResponder = nil; _toolbarDelegate = [[MPToolbarDelegate alloc] init]; - _outlineViewController = [[MPOutlineViewController alloc] init]; - _entryViewController = [[MPEntryViewController alloc] init]; - _inspectorViewController = [[MPInspectorViewController alloc] init]; + _splitViewController = [[MPDocumentSplitViewController alloc] init]; _documentWindowDelegate = [[MPDocumentWindowDelegate alloc] init]; } return self; @@ -108,15 +104,12 @@ typedef void (^MPPasswordChangedBlock)(BOOL didChangePassword); MPDocument *document = self.document; - [NSNotificationCenter.defaultCenter addObserver:self selector:@selector(_didRevertDocument:) name:MPDocumentDidRevertNotifiation object:document]; [NSNotificationCenter.defaultCenter addObserver:self selector:@selector(_didUnlockDatabase:) name:MPDocumentDidUnlockDatabaseNotification object:document]; [NSNotificationCenter.defaultCenter addObserver:self selector:@selector(_didAddEntry:) name:MPDocumentDidAddEntryNotification object:document]; [NSNotificationCenter.defaultCenter addObserver:self selector:@selector(_didAddGroup:) name:MPDocumentDidAddGroupNotification object:document]; [NSNotificationCenter.defaultCenter addObserver:self selector:@selector(_didLockDatabase:) name:MPDocumentDidLockDatabaseNotification object:document]; - [self.entryViewController registerNotificationsForDocument:document]; - [self.inspectorViewController registerNotificationsForDocument:document]; - [self.outlineViewController registerNotificationsForDocument:document]; + [self.splitViewController registerNotificationsForDocument:document]; [self.toolbarDelegate registerNotificationsForDocument:document]; self.toolbar = [[NSToolbar alloc] initWithIdentifier:@"MainWindowToolbar"]; @@ -131,23 +124,6 @@ typedef void (^MPPasswordChangedBlock)(BOOL didChangePassword); self.window.toolbar = self.toolbar; self.toolbarDelegate.toolbar = self.toolbar; - self.splitView.translatesAutoresizingMaskIntoConstraints = NO; - - NSView *outlineView = self.outlineViewController.view; - NSView *inspectorView = self.inspectorViewController.view; - NSView *entryView = self.entryViewController.view; - [self.splitView addSubview:outlineView]; - [self.splitView addSubview:entryView]; - [self.splitView addSubview:inspectorView]; - - [self.splitView setHoldingPriority:NSLayoutPriorityDefaultLow+2 forSubviewAtIndex:0]; - [self.splitView setHoldingPriority:NSLayoutPriorityDefaultLow+1 forSubviewAtIndex:2]; - - BOOL showInspector = [NSUserDefaults.standardUserDefaults boolForKey:kMPSettingsKeyShowInspector]; - if(!showInspector) { - [inspectorView removeFromSuperview]; - } - if(document.encrypted) { [self showPasswordInput]; } @@ -155,8 +131,6 @@ typedef void (^MPPasswordChangedBlock)(BOOL didChangePassword); [self showEntries]; } - self.splitView.autosaveName = @"SplitView"; - /* TODO: Add display for database color? NSTitlebarAccessoryViewController *tbc = [[MPTitlebarColorAccessoryViewController alloc] init]; @@ -169,40 +143,13 @@ typedef void (^MPPasswordChangedBlock)(BOOL didChangePassword); return self.toolbarDelegate.searchField; } -- (void)_setContentViewController:(MPViewController *)viewController { - - NSView *newContentView = nil; - if(viewController && viewController.view) { - newContentView = viewController.view; - } - NSView *contentView = self.window.contentView; - NSView *oldSubView = nil; - if(contentView.subviews.count == 1) { - oldSubView = contentView.subviews.firstObject; - } - if(oldSubView == newContentView) { - return; // View is already present - } - [oldSubView removeFromSuperviewWithoutNeedingDisplay]; - [contentView addSubview:newContentView]; - [contentView addConstraints:[NSLayoutConstraint constraintsWithVisualFormat:@"H:|[newContentView]|" - options:0 - metrics:nil - views:NSDictionaryOfVariableBindings(newContentView)]]; - - NSNumber *border = @([[self window] contentBorderThicknessForEdge:NSMinYEdge]); - [contentView addConstraints:[NSLayoutConstraint constraintsWithVisualFormat:@"V:|[newContentView]-border-|" - options:0 - metrics:NSDictionaryOfVariableBindings(border) - views:NSDictionaryOfVariableBindings(newContentView)]]; - - [contentView layout]; - [self.window makeFirstResponder:viewController.reconmendedFirstResponder]; +- (void)setContentViewController:(NSViewController *)contentViewController { + contentViewController.view.frame = self.window.contentView.frame; + [super setContentViewController:contentViewController]; } #pragma mark MPDocument notifications - (void)_didRevertDocument:(NSNotification *)notification { - [self.outlineViewController clearSelection]; [self showPasswordInput]; } @@ -261,7 +208,7 @@ typedef void (^MPPasswordChangedBlock)(BOOL didChangePassword); savePanel.allowedFileTypes = @[(id)kUTTypeXML]; savePanel.canSelectHiddenExtension = YES; [savePanel beginSheetModalForWindow:self.window completionHandler:^(NSInteger result) { - if(result == NSFileHandlingPanelOKButton) { + if(result == NSModalResponseOK) { [document writeXMLToURL:savePanel.URL]; } }]; @@ -277,9 +224,9 @@ typedef void (^MPPasswordChangedBlock)(BOOL didChangePassword); openPanel.prompt = NSLocalizedString(@"OPEN_BUTTON_IMPORT_XML_OPEN_PANEL", "Open button in the open panel to import an XML file"); openPanel.message = NSLocalizedString(@"MESSAGE_XML_OPEN_PANEL", "Message in the open panel to import an XML file"); [openPanel beginSheetModalForWindow:self.window completionHandler:^(NSInteger result) { - if(result == NSFileHandlingPanelOKButton) { + if(result == NSModalResponseOK) { [document readXMLfromURL:openPanel.URL]; - [self.outlineViewController showOutline]; + [self.splitViewController showOutline]; } }]; } @@ -342,7 +289,7 @@ typedef void (^MPPasswordChangedBlock)(BOOL didChangePassword); openPanel.message = NSLocalizedString(@"SELECT_FILE_TO_MERGE", @"Message for the dialog to open a file for merge"); //openPanel.allowedFileTypes = @[(id)kUTTypeXML]; [openPanel beginSheetModalForWindow:self.window completionHandler:^(NSInteger result) { - if(result == NSFileHandlingPanelOKButton) { + if(result == NSModalResponseOK) { [document mergeWithContentsFromURL:openPanel.URL key:document.compositeKey]; } }]; @@ -363,7 +310,7 @@ typedef void (^MPPasswordChangedBlock)(BOOL didChangePassword); if(!self.passwordInputController) { self.passwordInputController = [[MPPasswordInputController alloc] init]; } - [self _setContentViewController:self.passwordInputController]; + self.contentViewController = self.passwordInputController; [self.passwordInputController requestPasswordWithMessage:message cancelLabel:nil completionHandler:^BOOL(NSString *password, NSURL *keyURL, BOOL didCancel, NSError *__autoreleasing *error) { if(didCancel) { return NO; @@ -469,27 +416,17 @@ typedef void (^MPPasswordChangedBlock)(BOOL didChangePassword); } - (void)pickExpiryDate:(id)sender { - [self.inspectorViewController pickExpiryDate:sender]; + // FIXME: use propert responder chain + [self.splitViewController.inspectorViewController pickExpiryDate:sender]; } - (void)showPluginData:(id)sender { - [self.inspectorViewController showPluginData:sender]; + // FIXME: use propert responder chain + [self.splitViewController.inspectorViewController showPluginData:sender]; } - (void)toggleInspector:(id)sender { - NSView *inspectorView = self.inspectorViewController.view; - BOOL inspectorWasVisible = [self _isInspectorVisible]; - if(inspectorWasVisible) { - [inspectorView removeFromSuperview]; - } - else { - [self.splitView addSubview:inspectorView]; - [self.splitView addConstraints:[NSLayoutConstraint constraintsWithVisualFormat:@"[inspectorView(>=200)]" - options:0 - metrics:nil - views:NSDictionaryOfVariableBindings(inspectorView)]]; - } - [[NSUserDefaults standardUserDefaults] setBool:!inspectorWasVisible forKey:kMPSettingsKeyShowInspector]; + [self.splitViewController toggleInspector:sender]; } - (void)performAutotypeForEntry:(id)sender { @@ -507,108 +444,58 @@ typedef void (^MPPasswordChangedBlock)(BOOL didChangePassword); } - (void)focusEntries:(id)sender { - [self.window makeFirstResponder:[self.entryViewController reconmendedFirstResponder]]; + // FIXME: use propert responder chain + [self.window makeFirstResponder:[self.splitViewController.entryViewController reconmendedFirstResponder]]; } - (void)focusGroups:(id)sender { - [self.window makeFirstResponder:[self.outlineViewController reconmendedFirstResponder]]; + // FIXME: use propert responder chain + [self.window makeFirstResponder:[self.splitViewController.outlineViewController reconmendedFirstResponder]]; } - (void)focusInspector:(id)sender { - [self.window makeFirstResponder:[self.inspectorViewController reconmendedFirstResponder]]; + // FIXME: use propert responder chain + [self.window makeFirstResponder:[self.splitViewController.inspectorViewController reconmendedFirstResponder]]; } - (void)showEntries { - NSView *contentView = self.window.contentView; - if(self.splitView == contentView) { - return; // We are displaying the entries already - } - if(contentView.subviews.count == 1) { - [contentView.subviews.firstObject removeFromSuperviewWithoutNeedingDisplay]; - } - [contentView addSubview:self.splitView]; - NSView *outlineView = self.outlineViewController.view; - NSView *inspectorView = self.inspectorViewController.view; - NSView *entryView = self.entryViewController.view; - - /* - The current easy way to prevent layout hiccups is to add the inspector - Add all needed constraints an then remove it again, if it was hidden - */ - BOOL removeInspector = NO; - if(!inspectorView.superview) { - [self.splitView addSubview:inspectorView]; - removeInspector = YES; - } - /* Maybe we should consider not double adding constraints */ - NSDictionary *views = NSDictionaryOfVariableBindings(outlineView, inspectorView, entryView, _splitView); - [self.splitView addConstraints:[NSLayoutConstraint constraintsWithVisualFormat:@"H:|[outlineView(>=150)]-1-[entryView(>=150)]-1-[inspectorView(>=200)]|" - options:0 - metrics:nil - views:views]]; - [self.splitView addConstraints:[NSLayoutConstraint constraintsWithVisualFormat:@"V:|[outlineView]|" - options:0 - metrics:nil - views:views]]; - [self.splitView addConstraints:[NSLayoutConstraint constraintsWithVisualFormat:@"V:|[entryView(>=200)]|" - options:0 - metrics:nil - views:views]]; - [self.splitView addConstraints:[NSLayoutConstraint constraintsWithVisualFormat:@"V:|[inspectorView]|" - options:0 - metrics:nil - views:views]]; - - NSNumber *border = @([[self window] contentBorderThicknessForEdge:NSMinYEdge]); - [contentView addConstraints:[NSLayoutConstraint constraintsWithVisualFormat:@"V:|[_splitView]-border-|" - options:0 - metrics:NSDictionaryOfVariableBindings(border) - views:views]]; - [contentView addConstraints:[NSLayoutConstraint constraintsWithVisualFormat:@"H:|[_splitView]|" - options:0 - metrics:nil - views:views]]; - [self.outlineViewController showOutline]; - - /* Restore the State the inspector view was in before the view change */ - if(removeInspector) { - [inspectorView removeFromSuperview]; - } - [contentView layoutSubtreeIfNeeded]; + self.contentViewController = self.splitViewController; + [self.splitViewController showOutline]; + } - (void)showGroupInOutline:(id)sender { - NSArray *targetEntries = self.entryViewController.currentTargetEntries; + NSArray *targetEntries = self.splitViewController.entryViewController.currentTargetEntries; if(targetEntries.count != 1) { return; } - [self.outlineViewController selectGroup:targetEntries.lastObject.parent]; + [self.splitViewController.outlineViewController selectGroup:targetEntries.lastObject.parent]; } #pragma mark - #pragma mark Actions forwarded to MPEntryViewController - (void)copyUsername:(id)sender { - [self.entryViewController copyUsername:sender]; + [self.splitViewController.entryViewController copyUsername:sender]; } - (void)copyPassword:(id)sender { - [self.entryViewController copyPassword:sender]; + [self.splitViewController.entryViewController copyPassword:sender]; } - (void)copyCustomAttribute:(id)sender { - [self.entryViewController copyCustomAttribute:sender]; + [self.splitViewController.entryViewController copyCustomAttribute:sender]; } - (void)copyAsReference:(id)sender { - [self.entryViewController copyAsReference:sender]; + [self.splitViewController.entryViewController copyAsReference:sender]; } - (void)copyURL:(id)sender { - [self.entryViewController copyURL:sender]; + [self.splitViewController.entryViewController copyURL:sender]; } - (void)openURL:(id)sender { - [self.entryViewController openURL:sender]; + [self.splitViewController.entryViewController openURL:sender]; } #pragma mark Validation @@ -622,7 +509,7 @@ typedef void (^MPPasswordChangedBlock)(BOOL didChangePassword); if(document.shouldEnforcePasswordChange) { NSAlert *alert = [[NSAlert alloc] init]; - alert.alertStyle = NSCriticalAlertStyle; + alert.alertStyle = NSAlertStyleCritical; alert.messageText = NSLocalizedString(@"ENFORCE_PASSWORD_CHANGE_ALERT_TITLE", "Message text for the enforce password change alert"); alert.informativeText = NSLocalizedString(@"ENFORCE_PASSWORD_CHANGE_ALERT_DESCRIPTION", "Informative text for the enforce password change alert"); @@ -653,7 +540,7 @@ typedef void (^MPPasswordChangedBlock)(BOOL didChangePassword); else if(document.shouldRecommendPasswordChange) { NSAlert *alert = [[NSAlert alloc] init]; - alert.alertStyle = NSInformationalAlertStyle; + alert.alertStyle = NSAlertStyleInformational; alert.messageText = NSLocalizedString(@"RECOMMEND_PASSWORD_CHANGE_ALERT_TITLE", "Message text for the recommend password change alert"); alert.informativeText = NSLocalizedString(@"RECOMMEND_PASSWORD_CHANGE_ALERT_DESCRIPTION", "Informative text for the recommend password change alert"); @@ -690,8 +577,8 @@ typedef void (^MPPasswordChangedBlock)(BOOL didChangePassword); #pragma mark UI Helper - (BOOL)_isInspectorVisible { - NSView *inspectorView = self.inspectorViewController.view; - return (nil != inspectorView.superview); + NSSplitViewItem *item = [self.splitViewController splitViewItemForViewController:self.splitViewController.inspectorViewController]; + return !item.isCollapsed; } - (NSTouchBar *)makeTouchBar { diff --git a/MacPass/MPEntryInspectorViewController.m b/MacPass/MPEntryInspectorViewController.m index 7de036f1..0ea63f1c 100644 --- a/MacPass/MPEntryInspectorViewController.m +++ b/MacPass/MPEntryInspectorViewController.m @@ -219,7 +219,7 @@ typedef NS_ENUM(NSUInteger, MPEntryTab) { savePanel.nameFieldStringValue = binary.name; [savePanel beginSheetModalForWindow:self.windowController.window completionHandler:^(NSInteger result) { - if(result == NSFileHandlingPanelOKButton) { + if(result == NSModalResponseOK) { NSError *error; BOOL sucess = [binary saveToLocation:savePanel.URL error:&error]; if(!sucess && error) { @@ -237,7 +237,7 @@ typedef NS_ENUM(NSUInteger, MPEntryTab) { openPanel.prompt = NSLocalizedString(@"OPEN_BUTTON_ADD_ATTACHMENT_OPEN_PANEL", "Open button in the open panel to add attachments to an entry"); openPanel.message = NSLocalizedString(@"MESSAGE_ADD_ATTACHMENT_OPEN_PANEL", "Message in the open panel to add attachments to an entry"); [openPanel beginSheetModalForWindow:self.windowController.window completionHandler:^(NSInteger result) { - if(result == NSFileHandlingPanelOKButton) { + if(result == NSModalResponseOK) { for (NSURL *attachmentURL in openPanel.URLs) { KPKBinary *binary = [[KPKBinary alloc] initWithContentsOfURL:attachmentURL]; [self.observer willChangeModelProperty]; diff --git a/MacPass/MPLockDaemon.m b/MacPass/MPLockDaemon.m index 8851198c..29f9d613 100644 --- a/MacPass/MPLockDaemon.m +++ b/MacPass/MPLockDaemon.m @@ -165,7 +165,7 @@ static MPLockDaemon *_sharedInstance; } /* Create event handler if necessary */ if(!self.localEventHandler) { - self.localEventHandler = [NSEvent addLocalMonitorForEventsMatchingMask:NSAnyEventMask handler:^NSEvent *(NSEvent *theEvent) { + self.localEventHandler = [NSEvent addLocalMonitorForEventsMatchingMask:NSEventMaskAny handler:^NSEvent *(NSEvent *theEvent) { self.lastLocalEventTime = NSDate.timeIntervalSinceReferenceDate; return theEvent; }]; diff --git a/MacPass/MPOutlineViewController.m b/MacPass/MPOutlineViewController.m index 6ca32135..3904bab5 100644 --- a/MacPass/MPOutlineViewController.m +++ b/MacPass/MPOutlineViewController.m @@ -225,6 +225,7 @@ NSString *const _MPOutlinveViewHeaderViewIdentifier = @"HeaderCell"; #pragma mark Notifications - (void)registerNotificationsForDocument:(MPDocument *)document { [NSNotificationCenter.defaultCenter addObserver:self selector:@selector(_didAddGroup:) name:MPDocumentDidAddGroupNotification object:document]; + [NSNotificationCenter.defaultCenter addObserver:self selector:@selector(_didRevertDocument:) name:MPDocumentDidRevertNotifiation object:document]; } - (void)clearSelection { @@ -268,6 +269,9 @@ NSString *const _MPOutlinveViewHeaderViewIdentifier = @"HeaderCell"; [self.outlineView selectRowIndexes:[NSIndexSet indexSetWithIndex:groupRow] byExtendingSelection:NO]; [self.outlineView scrollRowToVisible:groupRow]; } +- (void)_didRevertDocument:(NSNotification *)notification { + [self clearSelection]; +} - (id)itemUnderMouse { NSPoint mouseLocation = [self.outlineView.window mouseLocationOutsideOfEventStream]; diff --git a/MacPass/MPOverlayWindowController.m b/MacPass/MPOverlayWindowController.m index 87397121..cc84925f 100644 --- a/MacPass/MPOverlayWindowController.m +++ b/MacPass/MPOverlayWindowController.m @@ -56,7 +56,7 @@ - (void)windowDidLoad { [super windowDidLoad]; - self.window.styleMask = NSBorderlessWindowMask; + self.window.styleMask = NSWindowStyleMaskBorderless; self.window.alphaValue = 0; self.window.opaque = NO; self.window.hasShadow = YES; diff --git a/MacPass/MPPasswordCreatorViewController.m b/MacPass/MPPasswordCreatorViewController.m index 8c73ea27..cc844cca 100644 --- a/MacPass/MPPasswordCreatorViewController.m +++ b/MacPass/MPPasswordCreatorViewController.m @@ -161,7 +161,7 @@ typedef NS_ENUM(NSUInteger, MPPasswordRating) { if(!self.allowsEntryDefaults || (nil == [self _currentEntryDefaults])) { return; // We aren't using entry so just leave; } - BOOL deleteEntryDefaults = MPIsFlagSetInOptions(NSAlternateKeyMask, [NSEvent modifierFlags]); + BOOL deleteEntryDefaults = MPIsFlagSetInOptions(NSEventModifierFlagOption, NSEvent.modifierFlags); [self _updateSetDefaultsButton:deleteEntryDefaults]; } diff --git a/MacPass/MPPasswordEditWindowController.m b/MacPass/MPPasswordEditWindowController.m index 56cfb2bd..b3ea1926 100644 --- a/MacPass/MPPasswordEditWindowController.m +++ b/MacPass/MPPasswordEditWindowController.m @@ -138,7 +138,7 @@ savePanel.canCreateDirectories = YES; savePanel.title = NSLocalizedString(@"SAVE_KEYFILE", "Button title to save the generated key file"); [savePanel beginWithCompletionHandler:^(NSInteger result) { - if(result == NSFileHandlingPanelOKButton) { + if(result == NSModalResponseOK) { NSURL *keyURL = [savePanel URL]; NSError *error; BOOL saveOk = [data writeToURL:keyURL options:NSDataWritingAtomic error:&error]; diff --git a/MacPass/MPSettingsHelper.m b/MacPass/MPSettingsHelper.m index 7ec3d674..766f51e8 100644 --- a/MacPass/MPSettingsHelper.m +++ b/MacPass/MPSettingsHelper.m @@ -212,7 +212,7 @@ NSString *const kMPDepricatedSettingsKeyAutotypeHideAccessibiltyWarning = @"Au if(!descriptorData) { return; // No user defaults } - NSArray *sortDescriptors = [NSUnarchiver unarchiveObjectWithData:descriptorData]; + NSArray *sortDescriptors = [NSKeyedUnarchiver unarchiveObjectWithData:descriptorData]; for(NSSortDescriptor *descriptor in sortDescriptors) { /* Brute force, just kill the settings if they might cause trouble */ diff --git a/MacPass/MPToolbarButton.m b/MacPass/MPToolbarButton.m index ae9d5514..678ab2b4 100644 --- a/MacPass/MPToolbarButton.m +++ b/MacPass/MPToolbarButton.m @@ -41,15 +41,15 @@ NSImageRep *rep = [self.image bestRepresentationForRect:NSMakeRect(0, 0, 100, 100) context:nil hints:nil]; CGFloat scale = rep.size.width / rep.size.height; switch (controlSize) { - case NSRegularControlSize: + case NSControlSizeRegular: self.image.size = NSMakeSize(16 * scale, 16); break; - case NSSmallControlSize: + case NSControlSizeSmall: self.image.size = NSMakeSize(14 * scale, 14); break; - case NSMiniControlSize: + case NSControlSizeMini: self.image.size = NSMakeSize(8 * scale, 8); default: diff --git a/MacPass/MPTreeDelegate.m b/MacPass/MPTreeDelegate.m index d35b640d..e7fbac9c 100644 --- a/MacPass/MPTreeDelegate.m +++ b/MacPass/MPTreeDelegate.m @@ -88,7 +88,7 @@ NSPanel *panel = [[NSPanel alloc] initWithContentRect:NSMakeRect(0, 0, 100, 100) styleMask:NSWindowStyleMaskNonactivatingPanel|NSWindowStyleMaskTitled|NSWindowStyleMaskResizable - backing:NSBackingStoreRetained + backing:NSBackingStoreBuffered defer:YES]; panel.level = NSScreenSaverWindowLevel; panel.contentViewController = pickFieldViewController; @@ -112,7 +112,7 @@ NSPanel *panel = [[NSPanel alloc] initWithContentRect:NSMakeRect(0, 0, 100, 100) styleMask:NSWindowStyleMaskNonactivatingPanel|NSWindowStyleMaskTitled|NSWindowStyleMaskResizable - backing:NSBackingStoreRetained + backing:NSBackingStoreBuffered defer:YES]; panel.level = NSScreenSaverWindowLevel; panel.contentViewController = pickCharViewController; diff --git a/MacPass/MPWorkflowPreferencesController.m b/MacPass/MPWorkflowPreferencesController.m index 09d13302..a63478b2 100644 --- a/MacPass/MPWorkflowPreferencesController.m +++ b/MacPass/MPWorkflowPreferencesController.m @@ -86,7 +86,7 @@ openPanel.allowedFileTypes = @[@"app"]; [openPanel beginSheetModalForWindow:self.view.window completionHandler:^(NSInteger result) { - if(result == NSFileHandlingPanelOKButton) { + if(result == NSModalResponseOK) { // TODO: Autorelease pool? NSMenuItem *customBrowser = [[NSMenuItem alloc] init]; customBrowser.representedObject = [NSBundle bundleWithPath:openPanel.URL.path].bundleIdentifier;