Post

Replies

Boosts

Views

Activity

Reply to Mac Catalyst Menu Bar/Toolbar Actions Not Validating Properly After Changing Active Windows
All they would need to do to fix this is to use a subclass on UIWindow for the scene that is created by NSUIViewToolbarItem (_UIViewHostingScene which is a subclass of UIWindowScene) and return NO from -canBecomeKeyWindow and -canBecomeFocused. Can confirm this by using Objective-C superpowers. Just swizzle -canBecomeKeyWindow and -canBecomeFocused and return NO for both these methods. -(BOOL)jjj_canBecomeKeyWindow { BOOL originalImp = [self jjj_canBecomeKeyWindow]; if ([self.windowScene isKindOfClass:NSClassFromString(@"_UIViewHostingScene")]) { //NEVER, EVER. return NO; } return originalImp; } -(BOOL)jjj_canBecomeFocused { BOOL originalImp = [self jjj_canBecomeFocused]; if ([self.windowScene isKindOfClass:NSClassFromString(@"_UIViewHostingScene")]) { //don't EVER! return NO; } return originalImp; } And then the responder chain/focus system doesn't break when you switch back to your app window.
Topic: UI Frameworks SubTopic: UIKit Tags:
Oct ’23
Reply to Mac Catalyst Menu Bar/Toolbar Actions Not Validating Properly After Changing Active Windows
After returning to this Catalyst project after some time away from it this issue is still occurring in Xcode 15 Sonoma. Basically the responder chain and the focus system breaks after making another app the frontmost app (menu bar owning) and then navigating back my app (making my app frontmost, menubar owning, etc). When I make my app frontmost again on Mac the focus system stops working. Tab key does nothing (it is expected to change focus) and many menu bar actions are not validating. @rttCanada Yes. It does seem like this could be related to NSUIViewToolbarItem. I have a NSUIViewToolbarItem subclass which wraps a UIButton subclass (in the system style). My subclass of UIButton just overrides canBecomeFocused and returns NO (because otherwise tabbing unexpectedly moved focus to this button in the toolbar which seemed wrong). //Wrapped in a NSUIViewToolbarItem subclass @implementation SystemStyledButtonInToolbarDontFocusOnMePleaseItMakesNoSenseUseTheMenuBarOrKeyboardShortcutToInvokeThisActionIfYouWantToGoMouseFree -(BOOL)canBecomeFocused { return NO; } @end My toolbar is customizable and if I remove this button from the toolbar it seems to fix the problem (though more testing is needed to say for sure).
Topic: UI Frameworks SubTopic: UIKit Tags:
Oct ’23
Reply to Enable WKWebView Web Inspector Under Mac Catalyst?
It's better than nothing but still not as good as being able to open the web inspector from the WKWebView itself because: We have to switch to Safari to get the Web Inspector. and 2) You don't get an "Inspect Element..." menu item when you right click to launch the web inspector in the WKWebView itself.
Topic: Safari & Web SubTopic: General Tags:
Oct ’23
Reply to Jump to Definition on Symbols in a Swift Framework's Gigantic Generated "Header"?
FWIW command+clicking on a symbol works sometimes even though there is no "Jump to Definition" context menu item. I think "Jump to Definition" would be useful since so much is scattered about. IMHO it would be better if these generated framework interfaces would instead create separate files grouped logically (in the way you would organize them if you were creating the header files yourself) instead of just dumping everything in gigantic generated interface file with protocols and extensions galore and you gotta hop all over the place to get a sense of an API.
Topic: Programming Languages SubTopic: Swift Tags:
Oct ’23
Reply to Customize NSToolbar context menu on Sonoma
It is important. I'm fully aware the way we do it is a hack and it was not that unexpected to see it stop working at some point... Then instead of doing this: NSView * theContentView = myWindow.contentView; NSMenu * theCustomizeMenu = theContentView.superview.menu; You can try can try enumerating subviews from the content view superview until you find it. Ideally you should isolate this hack in a category because the code is really nasty. Something like this: //Public @interface NSWindow (FindCustomizeToolbarMenu) -(nullable NSMenu*)findToolbarContextMenu; @end **//Put all the in the .m** #import "NSWindow+FindCustomizeToolbarMenu.h" #import <objc/runtime.h> @interface NSMenu (NSToolbarMenuMarkerHack) @property (nonatomic) BOOL isCustomizeToolbarMenu; @end @implementation NSMenu (NSToolbarMenuMarkerHack) static char const * const ToolbarMenuHackKey = "ToolbarMenuHackKey"; -(BOOL)isCustomizeToolbarMenu { NSNumber *result = objc_getAssociatedObject(self, ToolbarMenuHackKey); return (result != nil) ? result.boolValue : NO; } -(void)setIsCustomizeToolbarMenu:(BOOL)isCustomizeToolbarMenu { objc_setAssociatedObject(self, ToolbarMenuHackKey, @(isCustomizeToolbarMenu), OBJC_ASSOCIATION_RETAIN_NONATOMIC); } @end @implementation NSWindow (FindCustomizeToolbarMenu) -(NSMenu*)searchForCustomizeToolbarMenuInSubviews:(NSArray<NSView*>*)subviews { if (subviews.count == 0) { return nil; } NSMenu *foundMenu = nil; for (NSView *aSubview in subviews) { NSMenu *theMenu = aSubview.menu; if (theMenu.isCustomizeToolbarMenu || [theMenu.itemArray.lastObject.title isEqualToString:@"Customize Toolbar…"]) // <--Should compare a localized string! If you append on the found menu later this check will fail because "Customize Toolbar…" will no longer be the last object! { foundMenu.isCustomizeToolbarMenu = YES; //Mark it in case you mutate the menu later and "Customize Toolbar…" is not the last menu item. foundMenu = theMenu; break; } } //Found it? if (foundMenu != nil) { return foundMenu; } else { //Didn't find it. Dig through descendant views. for (NSView *aSubviewToDigIn in subviews) { NSMenu *nested = [self searchForCustomizeToolbarMenuInSubviews:aSubviewToDigIn.subviews]; if (nested != nil) { foundMenu = nested; break; } } return foundMenu; } } -(NSMenu*)findToolbarContextMenu { NSView *theContentView = self.contentView; NSView *contentViewSuperview = theContentView.superview; NSMutableArray *theSuperViewSubviews = [contentViewSuperview.subviews mutableCopy]; [theSuperViewSubviews removeObject:theContentView]; //Don't need to search the content view since we know it doesn't have it. NSMenu *foundMenu = [self searchForCustomizeToolbarMenuInSubviews:theSuperViewSubviews]; return foundMenu; } This is very ugly and fragile and untested so inspect the code and use at your own risk. But in theory you should be able to do something like this using the category: NSMenu *toolbarMenu = [self.window findToolbarContextMenu]; [toolbarMenu addItemWithTitle:@"CUSTOM" action:nil keyEquivalent:@""]; You could try filing a Feedback and ask Apple to improve the API but I have my doubts about that. You'd at least have to wait a year for them to add it and there's a good chance they never will.
Topic: UI Frameworks SubTopic: AppKit Tags:
Oct ’23
Reply to Jump to Definition on Symbols in a Swift Framework's Gigantic Generated "Header"?
Oh my, the SwitfUI generated "Interface" is a single 85833 lines and there's no "Jump to Definition" menu item when you right click on any symbols. And because almost everything is Protocols in Swift you can't reason about the API using this generated interface because when you right click on a protocol you can't jump the definition of the protocol. You got 85 thousand lines to scroll through to find it. Does everyone really like working like this? Is it really that hard to write a header file? Just asking.
Topic: Programming Languages SubTopic: Swift Tags:
Oct ’23
Reply to Find all Finder tags
This limitation never made any sense especially given the fact that NSURL has NSURLTagNamesKey which may be set and get. Way back in the day I was looking to do this. I naturally thought NSWorkspace API related to "file labels" (which I think tags replaced) would maybe just map to tag names but it didn't work. NSWorkspaceDidChangeFileLabelsNotification never got posted so I gave up.
Topic: Programming Languages SubTopic: Swift Tags:
Oct ’23
Reply to WKWebView UIDelegate Methods Not Being Called on Mac Catalyst (WKUIDelegate)
I am actually seeing -webView:contextMenuConfigurationForElement:completionHandler: being called sometimes and only when a link is right clicked but I'd like to be able to add context menu items when the background of the page is right clicked.
Topic: Safari & Web SubTopic: General Tags:
Replies
Boosts
Views
Activity
Oct ’23
Reply to Mac Catalyst Menu Bar/Toolbar Actions Not Validating Properly After Changing Active Windows
All they would need to do to fix this is to use a subclass on UIWindow for the scene that is created by NSUIViewToolbarItem (_UIViewHostingScene which is a subclass of UIWindowScene) and return NO from -canBecomeKeyWindow and -canBecomeFocused. Can confirm this by using Objective-C superpowers. Just swizzle -canBecomeKeyWindow and -canBecomeFocused and return NO for both these methods. -(BOOL)jjj_canBecomeKeyWindow { BOOL originalImp = [self jjj_canBecomeKeyWindow]; if ([self.windowScene isKindOfClass:NSClassFromString(@"_UIViewHostingScene")]) { //NEVER, EVER. return NO; } return originalImp; } -(BOOL)jjj_canBecomeFocused { BOOL originalImp = [self jjj_canBecomeFocused]; if ([self.windowScene isKindOfClass:NSClassFromString(@"_UIViewHostingScene")]) { //don't EVER! return NO; } return originalImp; } And then the responder chain/focus system doesn't break when you switch back to your app window.
Topic: UI Frameworks SubTopic: UIKit Tags:
Replies
Boosts
Views
Activity
Oct ’23
Reply to Mac Catalyst Menu Bar/Toolbar Actions Not Validating Properly After Changing Active Windows
After returning to this Catalyst project after some time away from it this issue is still occurring in Xcode 15 Sonoma. Basically the responder chain and the focus system breaks after making another app the frontmost app (menu bar owning) and then navigating back my app (making my app frontmost, menubar owning, etc). When I make my app frontmost again on Mac the focus system stops working. Tab key does nothing (it is expected to change focus) and many menu bar actions are not validating. @rttCanada Yes. It does seem like this could be related to NSUIViewToolbarItem. I have a NSUIViewToolbarItem subclass which wraps a UIButton subclass (in the system style). My subclass of UIButton just overrides canBecomeFocused and returns NO (because otherwise tabbing unexpectedly moved focus to this button in the toolbar which seemed wrong). //Wrapped in a NSUIViewToolbarItem subclass @implementation SystemStyledButtonInToolbarDontFocusOnMePleaseItMakesNoSenseUseTheMenuBarOrKeyboardShortcutToInvokeThisActionIfYouWantToGoMouseFree -(BOOL)canBecomeFocused { return NO; } @end My toolbar is customizable and if I remove this button from the toolbar it seems to fix the problem (though more testing is needed to say for sure).
Topic: UI Frameworks SubTopic: UIKit Tags:
Replies
Boosts
Views
Activity
Oct ’23
Reply to WKWebView UIDelegate Methods Not Being Called on Mac Catalyst (WKUIDelegate)
Just looked in the header file I see these are stubbed out on Mac Catalyst: Seems weird that you can't add actions to the context on Mac Catalyst.
Topic: Safari & Web SubTopic: General Tags:
Replies
Boosts
Views
Activity
Oct ’23
Reply to Enable WKWebView Web Inspector Under Mac Catalyst?
It's better than nothing but still not as good as being able to open the web inspector from the WKWebView itself because: We have to switch to Safari to get the Web Inspector. and 2) You don't get an "Inspect Element..." menu item when you right click to launch the web inspector in the WKWebView itself.
Topic: Safari & Web SubTopic: General Tags:
Replies
Boosts
Views
Activity
Oct ’23
Reply to AVSpeechSynthesizer is broken on iOS 17 in Xcode 15
Certain voices just stop at random points on speech strings in my app testing. Also the -willSpeakRange: delegate callback sometimes jumps all over the place. Doesn't seem to be any rhyme or reason to it.
Topic: Media Technologies SubTopic: Audio Tags:
Replies
Boosts
Views
Activity
Oct ’23
Reply to "Customize Toolbar" on NSToolbar Causes Autolayout Constraints Violation on macOS Sonoma
FB13257579
Topic: UI Frameworks SubTopic: AppKit Tags:
Replies
Boosts
Views
Activity
Oct ’23
Reply to AVSpeechSynthesizer is broken on iOS 17 in Xcode 15
Nothing in the iOS 17.1 Beta 2 Release Notes regarding AVFoundation. Anyone try the Beta?
Topic: Media Technologies SubTopic: Audio Tags:
Replies
Boosts
Views
Activity
Oct ’23
Reply to Jump to Definition on Symbols in a Swift Framework's Gigantic Generated "Header"?
FWIW command+clicking on a symbol works sometimes even though there is no "Jump to Definition" context menu item. I think "Jump to Definition" would be useful since so much is scattered about. IMHO it would be better if these generated framework interfaces would instead create separate files grouped logically (in the way you would organize them if you were creating the header files yourself) instead of just dumping everything in gigantic generated interface file with protocols and extensions galore and you gotta hop all over the place to get a sense of an API.
Topic: Programming Languages SubTopic: Swift Tags:
Replies
Boosts
Views
Activity
Oct ’23
Reply to Customize NSToolbar context menu on Sonoma
It is important. I'm fully aware the way we do it is a hack and it was not that unexpected to see it stop working at some point... Then instead of doing this: NSView * theContentView = myWindow.contentView; NSMenu * theCustomizeMenu = theContentView.superview.menu; You can try can try enumerating subviews from the content view superview until you find it. Ideally you should isolate this hack in a category because the code is really nasty. Something like this: //Public @interface NSWindow (FindCustomizeToolbarMenu) -(nullable NSMenu*)findToolbarContextMenu; @end **//Put all the in the .m** #import "NSWindow+FindCustomizeToolbarMenu.h" #import <objc/runtime.h> @interface NSMenu (NSToolbarMenuMarkerHack) @property (nonatomic) BOOL isCustomizeToolbarMenu; @end @implementation NSMenu (NSToolbarMenuMarkerHack) static char const * const ToolbarMenuHackKey = "ToolbarMenuHackKey"; -(BOOL)isCustomizeToolbarMenu { NSNumber *result = objc_getAssociatedObject(self, ToolbarMenuHackKey); return (result != nil) ? result.boolValue : NO; } -(void)setIsCustomizeToolbarMenu:(BOOL)isCustomizeToolbarMenu { objc_setAssociatedObject(self, ToolbarMenuHackKey, @(isCustomizeToolbarMenu), OBJC_ASSOCIATION_RETAIN_NONATOMIC); } @end @implementation NSWindow (FindCustomizeToolbarMenu) -(NSMenu*)searchForCustomizeToolbarMenuInSubviews:(NSArray<NSView*>*)subviews { if (subviews.count == 0) { return nil; } NSMenu *foundMenu = nil; for (NSView *aSubview in subviews) { NSMenu *theMenu = aSubview.menu; if (theMenu.isCustomizeToolbarMenu || [theMenu.itemArray.lastObject.title isEqualToString:@"Customize Toolbar…"]) // <--Should compare a localized string! If you append on the found menu later this check will fail because "Customize Toolbar…" will no longer be the last object! { foundMenu.isCustomizeToolbarMenu = YES; //Mark it in case you mutate the menu later and "Customize Toolbar…" is not the last menu item. foundMenu = theMenu; break; } } //Found it? if (foundMenu != nil) { return foundMenu; } else { //Didn't find it. Dig through descendant views. for (NSView *aSubviewToDigIn in subviews) { NSMenu *nested = [self searchForCustomizeToolbarMenuInSubviews:aSubviewToDigIn.subviews]; if (nested != nil) { foundMenu = nested; break; } } return foundMenu; } } -(NSMenu*)findToolbarContextMenu { NSView *theContentView = self.contentView; NSView *contentViewSuperview = theContentView.superview; NSMutableArray *theSuperViewSubviews = [contentViewSuperview.subviews mutableCopy]; [theSuperViewSubviews removeObject:theContentView]; //Don't need to search the content view since we know it doesn't have it. NSMenu *foundMenu = [self searchForCustomizeToolbarMenuInSubviews:theSuperViewSubviews]; return foundMenu; } This is very ugly and fragile and untested so inspect the code and use at your own risk. But in theory you should be able to do something like this using the category: NSMenu *toolbarMenu = [self.window findToolbarContextMenu]; [toolbarMenu addItemWithTitle:@"CUSTOM" action:nil keyEquivalent:@""]; You could try filing a Feedback and ask Apple to improve the API but I have my doubts about that. You'd at least have to wait a year for them to add it and there's a good chance they never will.
Topic: UI Frameworks SubTopic: AppKit Tags:
Replies
Boosts
Views
Activity
Oct ’23
Reply to Jump to Definition on Symbols in a Swift Framework's Gigantic Generated "Header"?
Oh my, the SwitfUI generated "Interface" is a single 85833 lines and there's no "Jump to Definition" menu item when you right click on any symbols. And because almost everything is Protocols in Swift you can't reason about the API using this generated interface because when you right click on a protocol you can't jump the definition of the protocol. You got 85 thousand lines to scroll through to find it. Does everyone really like working like this? Is it really that hard to write a header file? Just asking.
Topic: Programming Languages SubTopic: Swift Tags:
Replies
Boosts
Views
Activity
Oct ’23
Reply to NSOpenPanel returning immediately in MacCatalyst
Still doesn't seem possible to provide some explanation text to users for open/save panel from Mac Catalyst via UIDocumentInteractionController/UIDocumentPickerViewController unless you call into AppKit which is kind of a shame.
Topic: UI Frameworks SubTopic: AppKit Tags:
Replies
Boosts
Views
Activity
Oct ’23
Reply to UISplitViewController on Mac Catalyst Collapse the Primary (Sidebar) View Controller by Dragging the Split macOS Style?
Still doesn't appear to be supported on Sonoma. Oh well.
Topic: UI Frameworks SubTopic: UIKit Tags:
Replies
Boosts
Views
Activity
Oct ’23
Reply to Enable WKWebView Web Inspector Under Mac Catalyst?
You can now open the web inspector from Safari's "Develop" menu in the menu bar for a WKWebView in a Mac Catalyst app if you set the isInspectable property to YES. They added this in iOS 16.4.
Topic: Safari & Web SubTopic: General Tags:
Replies
Boosts
Views
Activity
Oct ’23
Reply to Find all Finder tags
This limitation never made any sense especially given the fact that NSURL has NSURLTagNamesKey which may be set and get. Way back in the day I was looking to do this. I naturally thought NSWorkspace API related to "file labels" (which I think tags replaced) would maybe just map to tag names but it didn't work. NSWorkspaceDidChangeFileLabelsNotification never got posted so I gave up.
Topic: Programming Languages SubTopic: Swift Tags:
Replies
Boosts
Views
Activity
Oct ’23