Explore the various UI frameworks available for building app interfaces. Discuss the use cases for different frameworks, share best practices, and get help with specific framework-related questions.

All subtopics
Posts under UI Frameworks topic

Post

Replies

Boosts

Views

Activity

RePlayKit:screen recording method return sampleBuffer is nil
I want record screen in my app,the method startCaptureWithHandler:completionHandler:,the sampleBuffer, It is supposed to exist but it has become nil.Not only that,but there‘s another problem,when I want to stop recording and save the video,I will check [RPScreenRecorder sharedRecorder].recording first, it will be false sometime,that problems are unusual in iOS 18.3.2 iPhoneXs Max,and unexpected,here is my code -(void)startCaptureScreen { NSLog(@"AKA++ startCaptureScreen"); if ([[RPScreenRecorder sharedRecorder] isRecording]) { return; } //屏幕录制 [[RPScreenRecorder sharedRecorder]setMicrophoneEnabled:YES]; NSLog(@"AKA++ MicrophoneEnabled AAAA startCaptureScreen"); [[RPScreenRecorder sharedRecorder]setCameraEnabled:YES]; [[RPScreenRecorder sharedRecorder] startCaptureWithHandler:^(CMSampleBufferRef _Nonnull sampleBuffer, RPSampleBufferType bufferType, NSError * _Nullable error) { if(self.assetWriter == nil){ if (self.AVAssetWriterStatus == 0) { [self setupAssetWriterAndStartWith:sampleBuffer]; } } if (self.AVAssetWriterStatus != 2) { return; } if (error) { // deal with error return; } if (self.assetWriter.status != AVAssetWriterStatusWriting) { [self assetWriterAppendSampleBufferFailWith:bufferType]; return; } if (bufferType == RPSampleBufferTypeVideo) { if(self.assetWriter.status == 0 ||self.assetWriter.status > 2){ } else if(self.videoAssetWriterInput.readyForMoreMediaData == YES){ BOOL success = [self.videoAssetWriterInput appendSampleBuffer:sampleBuffer]; } } if (bufferType == RPSampleBufferTypeAudioMic) { if(self.assetWriter.status == 0 ||self.assetWriter.status > 2){ } else if(self.audioAssetWriterInput.readyForMoreMediaData == YES){ BOOL success = [self.audioAssetWriterInput appendSampleBuffer:sampleBuffer]; } } } completionHandler:^(NSError * _Nullable error) { //deal with error }]; } and than ,when want to save it : -(void)stopRecording { if([[RPScreenRecorder sharedRecorder] isRecording]){ // The problem is sporadic,recording action failed,it makes me confused } [[RPScreenRecorder sharedRecorder] stopCaptureWithHandler:^(NSError * _Nullable error) { if(!error) { //post message } }]; }
0
0
91
Apr ’25
Must a custom UIInputView be assigned directly to the UIInputViewController.inputView or can it be a subview?
I'm making a custom keyboard extension in Objective-C for iOS 15+. Originally I designed myCustomInputView and put all my keyboard stuff into it, using constraints for everything. I then would add it as a subview like this: [myCustomKeyboardVC.inputView addSubview:myCustomInputView] and then contain it to .inputView. That mostly worked fine, except that after making and dismissing several I had a bunch of myCustomInputView objects remaining, being referenced by _inputViewContent which isn't being used by a custom keyboard anymore. I saw a suggestion that I should do this instead: myCustomKeyboardVC.inputView = myCustomInputView so that myCustomInputView is assigned directly to the VC's .inputView rather than being a subview of it. But this has problems because I now don't know what to constrain it to, and it runs wider than the screen. (ie, how do I constrain myCustomInputView to the keyboard width)? So I guess my basic question is: must custom UIInputViews be assigned directly to .inputView or can they be a subview of it?
Topic: UI Frameworks SubTopic: UIKit
1
0
124
Apr ’25
Get MacOS menubar size in Swift
To get menubar size, we can call. let menuBarHeight = NSStatusBar.system.thickness That is returning 24 and it is the same as my external screen. I did command + shift + 5 and use the screen capture tool to rougly measure the size of menubar. It is roughly 24px. However, for my macbook pro 14 inches m2 pro. The menubar seem thicker because of the webcam. Is there a way to find out the size in Swift?
2
1
227
Apr ’25
Implement Continuity Markup in Mac app?
Hello, is there a way to implement Continuity Markup in our own apps? (This is what I'm talking about: https://support.apple.com/en-us/102269 , scroll down to "Use Continuity Markup"). Also, why does a QuickLook panel (QLPreviewPanel.shared()) not display the markup options when triggered from my app for png image files in my app's Group Container? Do I need to implement certain NSServicesMenuRequestor methods for that? Sadly, I could not find any docs on that. Thank you, – Matthias
0
0
134
Apr ’25
popup window don't react to touch on iOS 18, works fine on iOS 17
popup window don't react to touch on iOS 18, works fine on iOS 17, this is the code: import SwiftUI extension View { public func popup<Content, Item>( item: Binding<Item?>, onDismiss: (() -> Void)? = nil, @ViewBuilder content: @escaping (Item) -> Content ) -> some View where Content: View, Item: Equatable { return self.overlay( PopupWrapper(item: item, onDismiss: onDismiss, content: content) ) } } struct PopupWrapper<Content, Item>: View where Content: View, Item: Equatable { @Binding var item: Item? var onDismiss: (() -> Void)? var content: (Item) -> Content @State var isAnimating = false var body: some View { Group { if let item { ZStack { Color.black .opacity(0.3) .ignoresSafeArea() .contentShape(Rectangle()) .gesture( TapGesture().onEnded { withAnimation(.spring(duration: 0.2)) { isAnimating = false DispatchQueue.main.asyncAfter(deadline: .now() + 0.2) { dismiss() } } } ) content(item) .scaleEffect(isAnimating ? 1 : 0.3) .opacity(isAnimating ? 1 : 0) .onAppear { withAnimation(.spring(duration: 0.3)) { isAnimating = true } } .gesture( TapGesture().onEnded { withAnimation(.spring(duration: 0.2)) { isAnimating = false DispatchQueue.main.asyncAfter(deadline: .now() + 0.2) { dismiss() } } } ) .onDisappear { dismiss() } } } else { EmptyView() } } } func dismiss() { item = nil isAnimating = false onDismiss?() } }
Topic: UI Frameworks SubTopic: SwiftUI
2
0
83
Apr ’25
SwiftUI FileImporter errors
When using FileImporter in SwiftUI, the following error is always returned when closed; even if the user taps "Cancel" The view service did terminate with error: Error Domain=_UIViewServiceErrorDomain Code=1 "(null)" UserInfo={Terminated=disconnect method} Recreation rate is 10/10. It feels like a threading issue, but in SwiftUI we are leveraging the .fileImporter modifier, so we cannot hold on to the reference like we would in a class. Is there a different approach we should be using for this? Code for recreation import SwiftUI struct ContentView: View { @State private var fileURL: URL? @State private var showFileImporter: Bool = false var body: some View { VStack { if let fileURL { Text(fileURL.absoluteString) } Button { showFileImporter = true } label: { Text("Select PDF") } .fileImporter( isPresented: $showFileImporter, allowedContentTypes: [.pdf], allowsMultipleSelection: true ) { result in switch result { case .success(let files): files.forEach { file in let gotAccess = file.startAccessingSecurityScopedResource() if !gotAccess { return } fileURL = file file.stopAccessingSecurityScopedResource() } case .failure(let error): print(error) } } } } }
1
0
106
Apr ’25
SwiftUI tvOS NavigationTransition and matchedTransitionSource
According to the docs tvOS 18+ supports the new NavigationTransition and the matchedTransitionSource and navigationTransition(.zoom(sourceID: id, in: namespace)) modifiers, however they don't seems to work. Taking the DestinationVideo project example from the latest WWDC the matchedTransitionSourceis marked with #if os(iOS) Is it supported by tvOS or is it for iOS only? https://developer.apple.com/documentation/swiftui/view/navigationtransition(_:) https://developer.apple.com/documentation/swiftui/view/matchedtransitionsource(id:in:configuration:)
2
0
67
Apr ’25
scenePhase not behaving as expected on screen lock
Seeing weird sequences of changes when locking the screen when view is visable. .onChange(of: scenePhase) { phase in if phase == .active { if UIApplication.shared.applicationState == .active { print("KDEBUG: App genuinely became active") } else { print("KDEBUG: False active signal detected") } } else if phase == .inactive { print("KDEBUG: App became inactive") // Handle inactive state if needed } else if phase == .background { print("KDEBUG: App went to background") // Handle background state if needed } } seen: (locks screen) KDEBUG: App became inactive KDEBUG: App genuinely became active KDEBUG: App went to background expected (locks screen) KDEBUG: App became inactive KDEBUG: App went to background
2
0
116
Apr ’25
iOS 18.4 (?) FamilyActivityPicker regression: presenting SFSafariViewController on top bugs
If I present "SFSafariViewController" when a "FamilyActivityPicker" is visible, it will automatically dismiss the "SFSafariViewController" and crash the "FamilyActivityPicker." I'm assuming the cause of the bug is that each is in a separate process (aside from the app), and there's some hacks to try to stop "FamilyActivityPicker" from crashing, and this is causing the new bug because "SFSafariViewController" is also in a separate process. (I'm not 100% if its just in 18.4 or iOS 18 overall...) (I'll try to file a feedback soon, but its 100% reproducible for me across multiple devices on iOS 18.4)
6
0
297
Apr ’25
Get NSTextView selection frame with NSTextLayoutManager
I'm trying to update my app to use TextKit 2. The one thing that I'm still not sure about is how I can get the selection frame. My app uses it to auto-scroll the text to keep the cursor at the same height when the text wraps onto a new line or a newline is manually inserted. Currently I'm using NSLayoutManager.layoutManager!.boundingRect(forGlyphRange:in:). The code below almost works. When editing the text or changing the selection, the current selection frame is printed out. My expectation is that the selection frame after a text or selection change should be equal to the selection frame before the next text change. I've noticed that this is not always true when the text has a NSParagraphStyle with spacing > 0. As long as I type at the end of the text, everything's fine, but if I insert some lines, then move the selection somewhere into the middle of the text and insert another newline, the frame printed after manually moving the selection is different than the frame before the newline is inserted. It seems that the offset between the two frames is exactly the same as the paragraph style's spacing. Instead when moving the selection with the arrow key the printed frames are correct. I've filed FB17104954. class ViewController: NSViewController, NSTextViewDelegate { private var textView: NSTextView! override func loadView() { let scrollView = NSScrollView(frame: CGRect(x: 0, y: 0, width: 400, height: 400)) textView = NSTextView(frame: scrollView.frame) textView.autoresizingMask = [.width, .height] textView.delegate = self let paragraphStyle = NSMutableParagraphStyle() paragraphStyle.lineSpacing = 40 textView.typingAttributes = [.foregroundColor: NSColor.labelColor, .paragraphStyle: paragraphStyle] scrollView.documentView = textView scrollView.hasVerticalScroller = true view = scrollView } func textView(_ textView: NSTextView, shouldChangeTextIn affectedCharRange: NSRange, replacementString: String?) -> Bool { print("before", selectionFrame.maxY, selectionFrame) return true } func textDidChange(_ notification: Notification) { print("after ", selectionFrame.maxY, selectionFrame) } func textViewDidChangeSelection(_ notification: Notification) { print("select", selectionFrame.maxY, selectionFrame) } var selectionFrame: CGRect { guard let selection = textView.textLayoutManager!.textSelections.first?.textRanges.first else { return .null } var frame = CGRect.null textView.textLayoutManager!.ensureLayout(for: selection) textView.textLayoutManager!.enumerateTextSegments(in: selection, type: .selection, options: [.rangeNotRequired]) { _, rect, _, _ in frame = rect return false } return frame } }
0
1
148
Apr ’25
SwiftUI views lock up after background and sleep for “Designed for iPad” apps
There's an easily reproducible SwiftUI bug on macOS where an app's UI state no longer updates/re-renders for "Designed for iPad" apps (i.e. ProcessInfo.processInfo.isiOSAppOnMac == true). The bug occurs in Xcode and also if the app is running independent of Xcode. The bug occurs when: the user Hides the app (i.e. it goes into the background) the user puts the Mac to sleep (e.g. Apple menu > Sleep) a total of ~60 seconds transpires (i.e. macOS puts the app into the "suspended state") when the app is brought back into the foreground the UI no longer updates properly The only way I have found to fix this is to manually open a new actual full app window via File > New, in which case the app works fine again in the new window. The following extremely simple code in a default Xcode project illustrates the issue: import SwiftUI @main struct staleApp: App { @State private var isBright = true var body: some Scene { WindowGroup() { ZStack { (isBright ? Color.white : Color.black).ignoresSafeArea() Button("TOGGLE") { isBright.toggle(); print("TAPPED") } } .onAppear { print("\(isBright ? "light" : "dark") view appeared") } } } } For the code above, after Hiding the app and putting the computer to sleep for 60 seconds or more, the button no longer swaps views, although the print statements still appear in the console upon tapping the button. Also, while in this buggy state, i can get the view to update to the current state (i.e. the view triggered by the last tap) by manually dragging the corner of the app window to resize the window. But after resizing, the view again does not update upon button tapping until I resize the window again. so it appears the diff engine is mucked or that the Scene or WindowGroup are no longer correctly running on the main thread I have tried rebuilding the entire view hierarchy by updating .id() on views but this approach does NOT work. I have tried many other options/hacks but have not been able to reset the 'view engine' other than opening a new window manually or by using: @Environment(.openWindow) private var openWindow openWindow could be a viable solution except there's no way to programmatically close the old window for isiOSAppOnMac (@Environment(.dismissWindow) private var dismissWindow doesn't work for iOS)
0
0
172
Apr ’25
SwiftUI Buttons and onMoveCommand Missing Presses
In tvOS 18 the onMoveCommand is missing the first press after a view is loaded and every time the direction is changed. It also misses the first press on a button after a focus change. This appears to only impact the newer silver remote and not the older black remote or IR remotes. With the code bellow press any direction 3 times and it will only log twice. struct ButtonTest: View { var body: some View { VStack { Button { debugPrint("button 1") } label: { Text("Button 1") } Button { debugPrint("button 2") } label: { Text("Button 2") } Button { debugPrint("button 3") } label: { Text("Button 3") } } .onMoveCommand(perform: { direction in debugPrint("move \(direction)") }) .padding() } }
Topic: UI Frameworks SubTopic: SwiftUI Tags:
12
8
1.3k
Apr ’25
NSDocumentController not adding "Open Recent" menu
I have a SwiftUI based app. For lots of reasons I was forced to use NSDocument instead of using DocumentGroup. I configure the main menu in my AppDelegate. It has the following code: let fileMenuItem = NSMenuItem() let fileMenu = NSMenu(title: "File") fileMenu.addItem(withTitle: "New", action: #selector(NSDocumentController.newDocument(_:)), keyEquivalent: "n") fileMenu.addItem(withTitle: "Open...", action: #selector(NSDocumentController.openDocument(_:)), keyEquivalent: "o") The New and Open work as expected. It is my understanding that the NSDocumentController should automatically add the "Open Recent" menu when it sees the Open action based on the NSDocumentController. It is not appearing. When I print the state of the recent documents using print("recent documents \(NSDocumentController.shared.recentDocumentURLs), maximum \(NSDocumentController.shared.maximumRecentDocumentCount)") I see the recent document urls and a count of 10. What can I do to make the menu appear? Thanks for the help.
5
0
288
Apr ’25
iOS 18.4 crash in WebCore with NSAttributedString
My app started crashing since iOS 18.4 update. Crashes started happening in 18.4 beta and are still happening in the official 18.4 RTM build (22E240). Crash is happening randomly and I cannot reproduce it, but it affects a few percent of users. As you can see in log, crash happen when NSAttributedString is loading HTML with init(data:options:documentAttributes:) with .html documentType. Crash-2025-04-02-154720.ips
3
0
481
Apr ’25
self.window.isVisible = NO not working in windowDidLoad
The following code won't work: - (void)windowDidLoad { [super windowDidLoad]; self.window.isVisible = NO; } The only main window still shows on application startup (in a minimal newly created app). One of my published apps in App Store relies on this behavior which had been working for many years since I started Xcode development.
Topic: UI Frameworks SubTopic: AppKit
11
0
216
Apr ’25
App Clip is installed but not displayed on the device.
Hello, I am new to App Clip development. I have uploaded a build with app clip to App Store Connect and the build is visible on the TestFlight. I am able to open the App Clip via TestFlight and I do see everything working, but the app clip is not getting added in Recent Apps folder and is no where found on the device. If I want to launch the app clip again, I have to scan the QR code again. When I use other app clips, like Panera Bread, the app clip stays in my Recent App/Recently Added folder. My app clip size is close to 75MB. Is the app clip not in Recently Added folder because the app clip is installed from TestFlight or is it happening because of the app clip size? Thanks!
2
0
153
Apr ’25
On iOS 16, VoiceOver will not speak "¥1,230" in Japanese.
In iOS 16, VoiceOver no longer speaks numbers such as “¥1,230" in Japanese, which worked correctly in iOS 15 and earlier. This is a very important bug in Accessibility support. Steps to reproduce Create iOS App Project on Xcode. (I used Xcode 14) Set the Development Localization to "Japanese" on the project settings. (to make VoiceOver speak Japanese) For example, write the following code. Build and run the App targeting the actual device, not the simulator. Actual devices running iOS 15 or earlier will correctly read out loud with VoiceOver, while iOS 16 will have some reading problems. import SwiftUI @main struct VoiceOverProblemApp: App {   var body: some Scene {     WindowGroup {       // on project settings, set the development localization to Japanese.       VStack {         // ✅ said "Hello, world!"         Text("Hello, world!")                   // ✅ said "残高 (ざんだか, zan-daka)"         Text("残高")                   // ❌ said nothing (until iOS 15 or earlier, said "千二百三十円 (せんにひゃくさんじゅうえん, sen-nihyaku-san-ju-yen)"         Text("¥1,230")                   // ❌ said wrong         //  correct (iOS 15 or earlier):  "残高は千二百三十円です (zan-daka wa sen-nihyaku-san-ju-yen desu)"         //  incorrect (iOS 16)      : "残高はです (zan-daka wa desu)"         Text("残高は ¥1,230 です")       }     }   } } The above sample code uses SwiftUI's Text but the same problem occurs with UIKit's UILabel.
1
0
1.3k
Apr ’25
RePlayKit:screen recording method return sampleBuffer is nil
I want record screen in my app,the method startCaptureWithHandler:completionHandler:,the sampleBuffer, It is supposed to exist but it has become nil.Not only that,but there‘s another problem,when I want to stop recording and save the video,I will check [RPScreenRecorder sharedRecorder].recording first, it will be false sometime,that problems are unusual in iOS 18.3.2 iPhoneXs Max,and unexpected,here is my code -(void)startCaptureScreen { NSLog(@"AKA++ startCaptureScreen"); if ([[RPScreenRecorder sharedRecorder] isRecording]) { return; } //屏幕录制 [[RPScreenRecorder sharedRecorder]setMicrophoneEnabled:YES]; NSLog(@"AKA++ MicrophoneEnabled AAAA startCaptureScreen"); [[RPScreenRecorder sharedRecorder]setCameraEnabled:YES]; [[RPScreenRecorder sharedRecorder] startCaptureWithHandler:^(CMSampleBufferRef _Nonnull sampleBuffer, RPSampleBufferType bufferType, NSError * _Nullable error) { if(self.assetWriter == nil){ if (self.AVAssetWriterStatus == 0) { [self setupAssetWriterAndStartWith:sampleBuffer]; } } if (self.AVAssetWriterStatus != 2) { return; } if (error) { // deal with error return; } if (self.assetWriter.status != AVAssetWriterStatusWriting) { [self assetWriterAppendSampleBufferFailWith:bufferType]; return; } if (bufferType == RPSampleBufferTypeVideo) { if(self.assetWriter.status == 0 ||self.assetWriter.status > 2){ } else if(self.videoAssetWriterInput.readyForMoreMediaData == YES){ BOOL success = [self.videoAssetWriterInput appendSampleBuffer:sampleBuffer]; } } if (bufferType == RPSampleBufferTypeAudioMic) { if(self.assetWriter.status == 0 ||self.assetWriter.status > 2){ } else if(self.audioAssetWriterInput.readyForMoreMediaData == YES){ BOOL success = [self.audioAssetWriterInput appendSampleBuffer:sampleBuffer]; } } } completionHandler:^(NSError * _Nullable error) { //deal with error }]; } and than ,when want to save it : -(void)stopRecording { if([[RPScreenRecorder sharedRecorder] isRecording]){ // The problem is sporadic,recording action failed,it makes me confused } [[RPScreenRecorder sharedRecorder] stopCaptureWithHandler:^(NSError * _Nullable error) { if(!error) { //post message } }]; }
Replies
0
Boosts
0
Views
91
Activity
Apr ’25
Must a custom UIInputView be assigned directly to the UIInputViewController.inputView or can it be a subview?
I'm making a custom keyboard extension in Objective-C for iOS 15+. Originally I designed myCustomInputView and put all my keyboard stuff into it, using constraints for everything. I then would add it as a subview like this: [myCustomKeyboardVC.inputView addSubview:myCustomInputView] and then contain it to .inputView. That mostly worked fine, except that after making and dismissing several I had a bunch of myCustomInputView objects remaining, being referenced by _inputViewContent which isn't being used by a custom keyboard anymore. I saw a suggestion that I should do this instead: myCustomKeyboardVC.inputView = myCustomInputView so that myCustomInputView is assigned directly to the VC's .inputView rather than being a subview of it. But this has problems because I now don't know what to constrain it to, and it runs wider than the screen. (ie, how do I constrain myCustomInputView to the keyboard width)? So I guess my basic question is: must custom UIInputViews be assigned directly to .inputView or can they be a subview of it?
Topic: UI Frameworks SubTopic: UIKit
Replies
1
Boosts
0
Views
124
Activity
Apr ’25
Get MacOS menubar size in Swift
To get menubar size, we can call. let menuBarHeight = NSStatusBar.system.thickness That is returning 24 and it is the same as my external screen. I did command + shift + 5 and use the screen capture tool to rougly measure the size of menubar. It is roughly 24px. However, for my macbook pro 14 inches m2 pro. The menubar seem thicker because of the webcam. Is there a way to find out the size in Swift?
Replies
2
Boosts
1
Views
227
Activity
Apr ’25
Implement Continuity Markup in Mac app?
Hello, is there a way to implement Continuity Markup in our own apps? (This is what I'm talking about: https://support.apple.com/en-us/102269 , scroll down to "Use Continuity Markup"). Also, why does a QuickLook panel (QLPreviewPanel.shared()) not display the markup options when triggered from my app for png image files in my app's Group Container? Do I need to implement certain NSServicesMenuRequestor methods for that? Sadly, I could not find any docs on that. Thank you, – Matthias
Replies
0
Boosts
0
Views
134
Activity
Apr ’25
popup window don't react to touch on iOS 18, works fine on iOS 17
popup window don't react to touch on iOS 18, works fine on iOS 17, this is the code: import SwiftUI extension View { public func popup<Content, Item>( item: Binding<Item?>, onDismiss: (() -> Void)? = nil, @ViewBuilder content: @escaping (Item) -> Content ) -> some View where Content: View, Item: Equatable { return self.overlay( PopupWrapper(item: item, onDismiss: onDismiss, content: content) ) } } struct PopupWrapper<Content, Item>: View where Content: View, Item: Equatable { @Binding var item: Item? var onDismiss: (() -> Void)? var content: (Item) -> Content @State var isAnimating = false var body: some View { Group { if let item { ZStack { Color.black .opacity(0.3) .ignoresSafeArea() .contentShape(Rectangle()) .gesture( TapGesture().onEnded { withAnimation(.spring(duration: 0.2)) { isAnimating = false DispatchQueue.main.asyncAfter(deadline: .now() + 0.2) { dismiss() } } } ) content(item) .scaleEffect(isAnimating ? 1 : 0.3) .opacity(isAnimating ? 1 : 0) .onAppear { withAnimation(.spring(duration: 0.3)) { isAnimating = true } } .gesture( TapGesture().onEnded { withAnimation(.spring(duration: 0.2)) { isAnimating = false DispatchQueue.main.asyncAfter(deadline: .now() + 0.2) { dismiss() } } } ) .onDisappear { dismiss() } } } else { EmptyView() } } } func dismiss() { item = nil isAnimating = false onDismiss?() } }
Topic: UI Frameworks SubTopic: SwiftUI
Replies
2
Boosts
0
Views
83
Activity
Apr ’25
SwiftUI FileImporter errors
When using FileImporter in SwiftUI, the following error is always returned when closed; even if the user taps "Cancel" The view service did terminate with error: Error Domain=_UIViewServiceErrorDomain Code=1 "(null)" UserInfo={Terminated=disconnect method} Recreation rate is 10/10. It feels like a threading issue, but in SwiftUI we are leveraging the .fileImporter modifier, so we cannot hold on to the reference like we would in a class. Is there a different approach we should be using for this? Code for recreation import SwiftUI struct ContentView: View { @State private var fileURL: URL? @State private var showFileImporter: Bool = false var body: some View { VStack { if let fileURL { Text(fileURL.absoluteString) } Button { showFileImporter = true } label: { Text("Select PDF") } .fileImporter( isPresented: $showFileImporter, allowedContentTypes: [.pdf], allowsMultipleSelection: true ) { result in switch result { case .success(let files): files.forEach { file in let gotAccess = file.startAccessingSecurityScopedResource() if !gotAccess { return } fileURL = file file.stopAccessingSecurityScopedResource() } case .failure(let error): print(error) } } } } }
Replies
1
Boosts
0
Views
106
Activity
Apr ’25
Add Caching in AsyncImage
Hi can you add caching to AsyncImage in the next swift revision pls see image below. without caching support it will redownload everything. wasting api calls
Replies
1
Boosts
0
Views
73
Activity
Apr ’25
SwiftUI tvOS NavigationTransition and matchedTransitionSource
According to the docs tvOS 18+ supports the new NavigationTransition and the matchedTransitionSource and navigationTransition(.zoom(sourceID: id, in: namespace)) modifiers, however they don't seems to work. Taking the DestinationVideo project example from the latest WWDC the matchedTransitionSourceis marked with #if os(iOS) Is it supported by tvOS or is it for iOS only? https://developer.apple.com/documentation/swiftui/view/navigationtransition(_:) https://developer.apple.com/documentation/swiftui/view/matchedtransitionsource(id:in:configuration:)
Replies
2
Boosts
0
Views
67
Activity
Apr ’25
scenePhase not behaving as expected on screen lock
Seeing weird sequences of changes when locking the screen when view is visable. .onChange(of: scenePhase) { phase in if phase == .active { if UIApplication.shared.applicationState == .active { print("KDEBUG: App genuinely became active") } else { print("KDEBUG: False active signal detected") } } else if phase == .inactive { print("KDEBUG: App became inactive") // Handle inactive state if needed } else if phase == .background { print("KDEBUG: App went to background") // Handle background state if needed } } seen: (locks screen) KDEBUG: App became inactive KDEBUG: App genuinely became active KDEBUG: App went to background expected (locks screen) KDEBUG: App became inactive KDEBUG: App went to background
Replies
2
Boosts
0
Views
116
Activity
Apr ’25
iOS 18.4 (?) FamilyActivityPicker regression: presenting SFSafariViewController on top bugs
If I present "SFSafariViewController" when a "FamilyActivityPicker" is visible, it will automatically dismiss the "SFSafariViewController" and crash the "FamilyActivityPicker." I'm assuming the cause of the bug is that each is in a separate process (aside from the app), and there's some hacks to try to stop "FamilyActivityPicker" from crashing, and this is causing the new bug because "SFSafariViewController" is also in a separate process. (I'm not 100% if its just in 18.4 or iOS 18 overall...) (I'll try to file a feedback soon, but its 100% reproducible for me across multiple devices on iOS 18.4)
Replies
6
Boosts
0
Views
297
Activity
Apr ’25
Get NSTextView selection frame with NSTextLayoutManager
I'm trying to update my app to use TextKit 2. The one thing that I'm still not sure about is how I can get the selection frame. My app uses it to auto-scroll the text to keep the cursor at the same height when the text wraps onto a new line or a newline is manually inserted. Currently I'm using NSLayoutManager.layoutManager!.boundingRect(forGlyphRange:in:). The code below almost works. When editing the text or changing the selection, the current selection frame is printed out. My expectation is that the selection frame after a text or selection change should be equal to the selection frame before the next text change. I've noticed that this is not always true when the text has a NSParagraphStyle with spacing > 0. As long as I type at the end of the text, everything's fine, but if I insert some lines, then move the selection somewhere into the middle of the text and insert another newline, the frame printed after manually moving the selection is different than the frame before the newline is inserted. It seems that the offset between the two frames is exactly the same as the paragraph style's spacing. Instead when moving the selection with the arrow key the printed frames are correct. I've filed FB17104954. class ViewController: NSViewController, NSTextViewDelegate { private var textView: NSTextView! override func loadView() { let scrollView = NSScrollView(frame: CGRect(x: 0, y: 0, width: 400, height: 400)) textView = NSTextView(frame: scrollView.frame) textView.autoresizingMask = [.width, .height] textView.delegate = self let paragraphStyle = NSMutableParagraphStyle() paragraphStyle.lineSpacing = 40 textView.typingAttributes = [.foregroundColor: NSColor.labelColor, .paragraphStyle: paragraphStyle] scrollView.documentView = textView scrollView.hasVerticalScroller = true view = scrollView } func textView(_ textView: NSTextView, shouldChangeTextIn affectedCharRange: NSRange, replacementString: String?) -> Bool { print("before", selectionFrame.maxY, selectionFrame) return true } func textDidChange(_ notification: Notification) { print("after ", selectionFrame.maxY, selectionFrame) } func textViewDidChangeSelection(_ notification: Notification) { print("select", selectionFrame.maxY, selectionFrame) } var selectionFrame: CGRect { guard let selection = textView.textLayoutManager!.textSelections.first?.textRanges.first else { return .null } var frame = CGRect.null textView.textLayoutManager!.ensureLayout(for: selection) textView.textLayoutManager!.enumerateTextSegments(in: selection, type: .selection, options: [.rangeNotRequired]) { _, rect, _, _ in frame = rect return false } return frame } }
Replies
0
Boosts
1
Views
148
Activity
Apr ’25
SwiftUI views lock up after background and sleep for “Designed for iPad” apps
There's an easily reproducible SwiftUI bug on macOS where an app's UI state no longer updates/re-renders for "Designed for iPad" apps (i.e. ProcessInfo.processInfo.isiOSAppOnMac == true). The bug occurs in Xcode and also if the app is running independent of Xcode. The bug occurs when: the user Hides the app (i.e. it goes into the background) the user puts the Mac to sleep (e.g. Apple menu > Sleep) a total of ~60 seconds transpires (i.e. macOS puts the app into the "suspended state") when the app is brought back into the foreground the UI no longer updates properly The only way I have found to fix this is to manually open a new actual full app window via File > New, in which case the app works fine again in the new window. The following extremely simple code in a default Xcode project illustrates the issue: import SwiftUI @main struct staleApp: App { @State private var isBright = true var body: some Scene { WindowGroup() { ZStack { (isBright ? Color.white : Color.black).ignoresSafeArea() Button("TOGGLE") { isBright.toggle(); print("TAPPED") } } .onAppear { print("\(isBright ? "light" : "dark") view appeared") } } } } For the code above, after Hiding the app and putting the computer to sleep for 60 seconds or more, the button no longer swaps views, although the print statements still appear in the console upon tapping the button. Also, while in this buggy state, i can get the view to update to the current state (i.e. the view triggered by the last tap) by manually dragging the corner of the app window to resize the window. But after resizing, the view again does not update upon button tapping until I resize the window again. so it appears the diff engine is mucked or that the Scene or WindowGroup are no longer correctly running on the main thread I have tried rebuilding the entire view hierarchy by updating .id() on views but this approach does NOT work. I have tried many other options/hacks but have not been able to reset the 'view engine' other than opening a new window manually or by using: @Environment(.openWindow) private var openWindow openWindow could be a viable solution except there's no way to programmatically close the old window for isiOSAppOnMac (@Environment(.dismissWindow) private var dismissWindow doesn't work for iOS)
Replies
0
Boosts
0
Views
172
Activity
Apr ’25
SwiftUI Buttons and onMoveCommand Missing Presses
In tvOS 18 the onMoveCommand is missing the first press after a view is loaded and every time the direction is changed. It also misses the first press on a button after a focus change. This appears to only impact the newer silver remote and not the older black remote or IR remotes. With the code bellow press any direction 3 times and it will only log twice. struct ButtonTest: View { var body: some View { VStack { Button { debugPrint("button 1") } label: { Text("Button 1") } Button { debugPrint("button 2") } label: { Text("Button 2") } Button { debugPrint("button 3") } label: { Text("Button 3") } } .onMoveCommand(perform: { direction in debugPrint("move \(direction)") }) .padding() } }
Topic: UI Frameworks SubTopic: SwiftUI Tags:
Replies
12
Boosts
8
Views
1.3k
Activity
Apr ’25
NSDocumentController not adding "Open Recent" menu
I have a SwiftUI based app. For lots of reasons I was forced to use NSDocument instead of using DocumentGroup. I configure the main menu in my AppDelegate. It has the following code: let fileMenuItem = NSMenuItem() let fileMenu = NSMenu(title: "File") fileMenu.addItem(withTitle: "New", action: #selector(NSDocumentController.newDocument(_:)), keyEquivalent: "n") fileMenu.addItem(withTitle: "Open...", action: #selector(NSDocumentController.openDocument(_:)), keyEquivalent: "o") The New and Open work as expected. It is my understanding that the NSDocumentController should automatically add the "Open Recent" menu when it sees the Open action based on the NSDocumentController. It is not appearing. When I print the state of the recent documents using print("recent documents \(NSDocumentController.shared.recentDocumentURLs), maximum \(NSDocumentController.shared.maximumRecentDocumentCount)") I see the recent document urls and a count of 10. What can I do to make the menu appear? Thanks for the help.
Replies
5
Boosts
0
Views
288
Activity
Apr ’25
iOS 18.4 crash in WebCore with NSAttributedString
My app started crashing since iOS 18.4 update. Crashes started happening in 18.4 beta and are still happening in the official 18.4 RTM build (22E240). Crash is happening randomly and I cannot reproduce it, but it affects a few percent of users. As you can see in log, crash happen when NSAttributedString is loading HTML with init(data:options:documentAttributes:) with .html documentType. Crash-2025-04-02-154720.ips
Replies
3
Boosts
0
Views
481
Activity
Apr ’25
custom keyboard Extension throwing following warning
unifieldFlexKeyboard[53102:24145174] [External] -[UIInputViewController needsInputModeSwitchKey] was called before a connection was established to the host application. This will produce an inaccurate result. Please make sure to call this after your primary view controller has been initialized. hey
Replies
1
Boosts
2
Views
661
Activity
Apr ’25
self.window.isVisible = NO not working in windowDidLoad
The following code won't work: - (void)windowDidLoad { [super windowDidLoad]; self.window.isVisible = NO; } The only main window still shows on application startup (in a minimal newly created app). One of my published apps in App Store relies on this behavior which had been working for many years since I started Xcode development.
Topic: UI Frameworks SubTopic: AppKit
Replies
11
Boosts
0
Views
216
Activity
Apr ’25
screen recording method return sampleBuffer is nil
I want record screen in my app,the method startCaptureWithHandler:completionHandler:,the sampleBuffer, It is supposed to exist but it has become nil, that problem is unusual in iOS 18.3.2 iPhoneXs Max
Replies
4
Boosts
0
Views
208
Activity
Apr ’25
App Clip is installed but not displayed on the device.
Hello, I am new to App Clip development. I have uploaded a build with app clip to App Store Connect and the build is visible on the TestFlight. I am able to open the App Clip via TestFlight and I do see everything working, but the app clip is not getting added in Recent Apps folder and is no where found on the device. If I want to launch the app clip again, I have to scan the QR code again. When I use other app clips, like Panera Bread, the app clip stays in my Recent App/Recently Added folder. My app clip size is close to 75MB. Is the app clip not in Recently Added folder because the app clip is installed from TestFlight or is it happening because of the app clip size? Thanks!
Replies
2
Boosts
0
Views
153
Activity
Apr ’25
On iOS 16, VoiceOver will not speak "¥1,230" in Japanese.
In iOS 16, VoiceOver no longer speaks numbers such as “¥1,230" in Japanese, which worked correctly in iOS 15 and earlier. This is a very important bug in Accessibility support. Steps to reproduce Create iOS App Project on Xcode. (I used Xcode 14) Set the Development Localization to "Japanese" on the project settings. (to make VoiceOver speak Japanese) For example, write the following code. Build and run the App targeting the actual device, not the simulator. Actual devices running iOS 15 or earlier will correctly read out loud with VoiceOver, while iOS 16 will have some reading problems. import SwiftUI @main struct VoiceOverProblemApp: App {   var body: some Scene {     WindowGroup {       // on project settings, set the development localization to Japanese.       VStack {         // ✅ said "Hello, world!"         Text("Hello, world!")                   // ✅ said "残高 (ざんだか, zan-daka)"         Text("残高")                   // ❌ said nothing (until iOS 15 or earlier, said "千二百三十円 (せんにひゃくさんじゅうえん, sen-nihyaku-san-ju-yen)"         Text("¥1,230")                   // ❌ said wrong         //  correct (iOS 15 or earlier):  "残高は千二百三十円です (zan-daka wa sen-nihyaku-san-ju-yen desu)"         //  incorrect (iOS 16)      : "残高はです (zan-daka wa desu)"         Text("残高は ¥1,230 です")       }     }   } } The above sample code uses SwiftUI's Text but the same problem occurs with UIKit's UILabel.
Replies
1
Boosts
0
Views
1.3k
Activity
Apr ’25