Post

Replies

Boosts

Views

Activity

How do you restore a Sheet's window frame in SwiftUI for macOS
On macOS, it's not uncommon to present windows as sheets that can be resized. By setting the NSWindow's various frame auto save properties, you can restore the size of the sheet the next time it is presented. When presenting a Sheet from within SwiftUI using the .sheet view modifier, how can I preserve and restore the sheet's frame size? The closest I've been able to come is to put the SwiftUI view into a custom NSHostingController and then into an NSViewControllerRepresentable and then override viewWillAppear and look for self.view.window, which is all little awkward. Is there a more idiomatic way to achieve this in "pure" SwiftUI?
2
0
139
May ’25
How to effectively use task(id:) when multiple properties are involved?
While adopting SwiftUI (and Swift Concurrency) into a macOS/AppKit application, I'm making extensive use of the .task(id:) view modifier. In general, this is working better than expected however I'm curious if there are design patterns I can better leverage when the number of properties that need to be "monitored" grows. Consider the following pseudo-view whereby I want to call updateFilters whenever one of three separate strings is changed. struct FiltersView: View { @State var argument1: String @State var argument2: String @State var argument3: String var body: some View { TextField($argument1) TextField($argument2) TextField($argument3) }.task(id: argument1) { await updateFilters() }.task(id: argument2) { await updateFilters() }.task(id: argument3) { await updateFilters() } } Is there a better way to handle this? The best I've come up with is to nest the properties inside struct. While that works, I now find myself creating these "dummy types" in a bunch of views whenever two or more properties need to trigger an update. ex: struct FiltersView: View { struct Components: Equatable { var argument1: String var argument2: String var argument3: String } @State var components: Components var body: some View { // TextField's with bindings to $components... }.task(id: components) { await updateFilters() } } Curious if there are any cleaner ways to accomplish this because this gets a bit annoying over a lot of views and gets cumbersome when some values are passed down to child views. It also adds an entire layer of indirection who's only purpose is to trigger task(id:).
2
0
186
May ’25
On macOS, how do you place a toolbar item on the trailing edge of the window's toolbar when an Inspector view is open?
Using SwiftUI on macOS, how can I add a toolbar item on the right-most (trailing) edge of the window's toolbar when an Inspector is used? At the moment, the toolbar items are all left-of (leading) the split view tracking separator. I want the inspector toolbar item to be placed similar to where Xcode's Inspector toolbar item is placed: always as far right (trailing) as possible. NavigationSplitView { // ... snip } detail: { // ... snip } .inspector(isPresented: $isInspectorPresented) { InspectorContentView() } .toolbar { // What is the correct placement value here? ToolbarItem(placement: .primaryAction) { Button { isInspectorPresented.toggle() } label: { Label("Toggle Inspector", systemImage: "sidebar.trailing") } } } See the attached screenshot. When the InspectorView is toggled open, the toolbar item tracks leading the split view tracking separator, which is not consistent with how Xcode works.
Topic: UI Frameworks SubTopic: SwiftUI Tags:
5
0
272
Dec ’25
NSOutlineView incorrectly draws disclosure indicator when item views are SwiftUI views.
I am using an NSOutlineView via NSViewRepresentable in a SwiftUI application running on macOS. Everything has been working fine. Up until lately, I've been returning a custom NSView for each item using the standard: func outlineView(_ outlineView: NSOutlineView, viewFor tableColumn: NSTableColumn?, item: Any) -> NSView? { // View recycling omitted. return MyItemView(item) } Now I want to explore using a little bit more SwiftUI and returning an NSHostingView from this delegate method. func outlineView(_ outlineView: NSOutlineView, viewFor tableColumn: NSTableColumn?, item: Any) -> NSView? { // View recycling omitted. let rootView = MySwiftUIView(item) let hostingView = NSHostingView(rootView: rootView) return hostingView } For the most part, this appears to be working fine. NSOutlineView is even correctly applying highlight styling, so that's great. But there's one small glitch. The outline view's disclosure triangles do not align with the hosting view's content. The disclosure triangles appear to just be pinned to the top. Perhaps they can't find a baseline constraint or something? Is there any SwiftUI modifier or AppKit/SwiftUI technique I can apply here to get the disclosure button to appear in the right place? Here is what the SwiftUI + NSHostingView version looks like: Note the offset disclosure indicators. (Image spacing is a bit off as well using Label, but fixable. Here is what an NSView with NSTextFields looks like: Disclosure indicators are correctly aligned, as you would expect.
1
0
153
Nov ’25
Clarification on SwiftUI Environment Write Performance
I'm looking for clarification on a SwiftUI performance point mentioned in the recent Optimize your app's speed and efficiency | Meet with Apple video. (YouTube link not allowed, but the video is available on the Apple Developer channel.) At the 1:48:50 mark, the presenter says: Writing a value to the Environment doesn't only affect the views that read the key you're updating. It updates any view that reads from any Environment key. [abbreviated quote] That statement seems like a big deal if your app relies heavily on Environment values. Context I'm building a macOS application with a traditional three-panel layout. At any given time, there are many views on screen, plus others that exist in the hierarchy but are currently hidden (for example, views inside tab views or collapsed splitters). Nearly every major view reads something from the environment—often an @Observable object that acts as a service or provider. However, there are a few relatively small values that are written to the environment frequently, such as: The selected tab index The currently selected object on a canvas The Question Based on the presenter's statement, I’m wondering: Does writing any value to the environment really cause all views in the entire SwiftUI view hierarchy that read any environment key to have their body re-evaluated? Do environment writes only affect child views, or do they propagate through the entire SwiftUI hierarchy? Example: View A └─ View B ├─ View C └─ View D If View B updates an environment value, does that affect only C and D, or does it also trigger updates in A and B (assuming each view has at least one @Environment property)? Possible Alternative If all views are indeed invalidated by environment writes, would it be more efficient to “wrap” frequently-changing values inside an @Observable object instead of updating the environment directly? // Pseudocode @Observable final class SelectedTab { var index: Int } ContentView() .environment(\.selectedTab, selectedTab) struct TabView: View { @Environment(\.selectedTab) private var selectedTab var body: some View { Button("Action") { // Would this avoid invalidating all views using the environment? selectedTab.index = 1 } } } Summary From what I understand, it sounds like the environment should primarily be used for stable, long-lived objects—not for rapidly changing values—since writes might cause far more view invalidations than most developers realize. Is that an accurate interpretation? Follow-Up In Xcode 26 / Instruments, is there a way to monitor writes to @Environment?
4
0
1.3k
Nov ’25
Do SwiftUI Segmented Controls on macOS 26 support the icon and title label style?
On macOS 26.3, Xcode 26.3, why does a labelStyle of titleAndIcon not show both the title and the icon of a label? The label styles iconOnly and titleOnly behave as expected. Picker("Label Demo", selection: $selectedItem) { Label { Text("File") } icon: { Image(systemName: "doc") } Label { Text("Folder") } icon: { Image(systemName: "folder") } } .labelStyle(.titleAndIcon) .pickerStyle(.segmented) Note that there is no icon shown. Placing the .labelStyle modifier in different places has no effect. The icon is correctly shown when the labelStyle is set to .iconOnly. An NSSegmentedControl created with AppKit and presented in an NSViewRepresentable does correctly show titles and icons if configured appropriately. Tested on: macOS 26.3 (25D125) Xcode 26.3 (17C519) A brand new SwiftUI "macOS App" project.
2
0
124
Feb ’26
In SwiftUI for macOS, is there an equivalent to NSControl.BorderShape?
In macOS 26, there is a new property on NSControl called .borderShape. The WWDC 2025-310 video says it can be used to "Override preferred shape of control to suit your design." and that it's available on NSButton, NSPopUpButton and NSSegmentedControl. Is there an equivalent to that property for SwiftUI? For example, given the following SwiftUI code: Button("Eject") { } .borderShape(...) <-- ? How can I apply a .borderShape that would match those on controls created in AppKit? I'm aware that SwiftUI offers a plethora of ways to custom design a button such that it can have rounded corners, but I'm interested in this particular property so that SwiftUI buttons and AppKit buttons in the same app have the same look-and-feel.
1
0
117
Feb ’26
How do you set the color of an NSImage symbol when used as the contents of a CALayer?
I'm trying to use an NSImage that represents an SF Symbol as the contents of a CALayer. NSImage has an API for this in the form of [NSImage layerContentsForContentsScale:]. On the NSImage documentation page, there's even a few paragraph at the top dedicated to using this very method. But how do you set the color you want the image to render as if the image is an SF Symbol? NSImageView has .contentTintColor which works great, but CALayer has no such property. final class SymbolLayer: CALayer { func display() { // Just an example... let image = NSImage(systemSymbolName: "paperclip", accessibilityDescription: nil)! let actualScaleFactor = image.recommendedLayerContentsScale(contentsScale) // This obviously produces a black image because there's no color or tint information anywhere.     contents = image.layerContents(forContentsScale: actualScaleFactor) } } Is there a way you can configure the CALayer or the NSImage itself to have some sort of color information when it generates the layer contents? I've attempted to play around with the SymbolConfiguration coolers but without any success. (Even when wrapped inside NSAppearance.performAsCurrentDrawingAppearance.) The best I can come up with is to use CALayer.draw(in:) and then use the old NSImage.cgImage(forProposedRect:...) API. I can then set the fill color on the CGContext and go from there. Is there a more efficient way? override func draw(in context: CGContext) { let image = NSImage(systemSymbolName: "paperclip", accessibilityDescription: nil)!   var rect = bounds image.size = bounds.size let cgImage = image.cgImage( forProposedRect: &rect, context: nil, hints: [.ctm: AffineTransform(scale: contentsScale)] )! NSApp.effectiveAppearance.performAsCurrentDrawingAppearance { // Draw using an Appearance-sensitive color.     context.clip(to: bounds, mask: cgImage)     context.setFillColor(NSColor.labelColor.cgColor)     context.fill(bounds)   } } This is for macOS 12+.
Topic: UI Frameworks SubTopic: AppKit Tags:
0
0
1.8k
Sep ’21
How do you encrypt an AppleArchive with a "human" password?
In WWDC21 session 10233: Bring Encrypted Archives and Performance Improvements to Your App with Accelerate, there is an example of encrypting a directory using the AppleArchive framework. There is also accompanying sample code. However, that sample code uses a SymmetricKey and the hkdf_sha256_aesctr_hmac__symmetric__none profile. The key is set by calling context.setSymmetricKey(encryptionKey). How can you perform the same operation of encrypting a directory using AppleArchive but with a "human" password? (i.e.: A password provided by the user from a prompt?) Simply changing the profile to hkdf_sha256_aesctr_hmac__scrypt__none and then calling `context.setPassword("MyPassword") producing the following output "Error setting password (invalidValue)." I also tried using the command line aea application, but received the output Password is too short. Prompt: > aea encrypt -v -password-value "password" -profile 5 -i MyDirectory -o MyDirectory.aea Operation: encrypt input: FOO output: FOO.aea profile: hkdf_sha256_aesctr_hmac__scrypt__none worker threads: 10 auth data (raw): 0 B compression: lzfse 1 MB Error 0xb9075800 Password is too short Main key derivation failed (-2) Main key derivation Invalid encryption parameters Finally, in the file AEAContext.h, there is a comment associated with the method AEAContextSetPassword() that states: Set context password Stores a copy of password in context. Required to encrypt / decrypt a stream when encryption mode is SCRYPT. An internal size range is enforced for the password. The caller is expected to enforce password strength policies. @param context target object @param password password (raw data) @param password_size password size (bytes) @return 0 on success, a negative error code on failure I cannot find any other documentation that states what the password policy. And if there is a password policy for AppleEncryptedArchives, does that mean AEA is not a good fit for encrypting personal directories where the user just wants to use "any old password", regardless of the password's strength?
0
0
1.2k
Apr ’23
The @Environment(\.dismiss) value in SwiftUI for macOS does not dismiss a sheet presented by an NSWindowController.
I'm wondering what the correct, or recommended, way is to dismiss a SwiftUI that is being presented as a sheet hosted by an NSHostingController. The usual technique of invoking @Environment(\.dismiss) does not appear to work. Consider the code below. An NSWindowController is attempting to display a SwiftUI SettingsView as a sheet. The sheet is correctly presented, but the SettingsView is unable to dismiss itself. I am able to make it work by passing a closure into SettingsView that calls back to the NSWindowController but it's rather convoluted because SettingsView doesn't know the view controller that's hosting it until after SettingsView has been created, which means "finding" that view controller in the window controller to dismiss is more involved than it should be. Is there a better strategy to leverage here? final class MyViewController: NSViewController { @IBAction func buttonClicked(_ sender: NSButton) { if let presenter = window?.contentViewController { presenter.presentAsSheet(NSHostingController(rootView: SettingsView())) } } } struct SettingsView: View { @Environment(\.dismiss) private var dismiss var body: some View { VStack { Button("Cancel", role: .cancel) { dismiss() // This call does not dismiss the sheet. } .keyboardShortcut(.cancelAction) } } } Thank you. macOS 15.4.1 (24E263), Xcode 16.3 (16E140)
0
0
105
Apr ’25
Is it reasonable to vend an NSView from a "ViewModel" when using NSViewRepresentable instead of implementing the Coordinator pattern?
I'm currently integrating SwiftUI into an AppKit based application and was curious if the design pattern below was viable or not. In order to "bridge" between AppKit and SwiftUI, most of my SwiftUI "root" views have aViewModel that is accessible to the SwiftUI view via @ObservedObject. When a SwiftUI views need to use NSViewRepresentable I'm finding the use of a ViewModel and a Coordinator to be an unnecessary layer of indirection. In cases where it makes sense, I've just used the ViewModel as the Coordinator and it all appears to be working ok, but I'm curious if this is reasonable design pattern or if I'm overlooking something. Consider the following pseudo code: // 1. A normal @ObservedObject acting as the ViewModel that also owns and manages an NSTableView. @MainActor final class ViewModel: ObservedObject, NSTableView... { let scrollView: NSScrollView let tableView: NSTableView @Published var selectedTitle: String init() { // ViewModel manages tableView as its dataSource and delegate. tableView.dataSource = self tableView.delegate = self } func reload() { tableView.reloadData() } // Update view model properties. // Simpler than passing back up through a Coordinator. func tableViewSelectionDidChange(_ notification: Notification) { selectedTitle = tableView.selectedItem.title } } // 2. A normal SwiftUI view, mostly driven by the ViewModel. struct ContentView: View { @ObservedObject model: ViewModel var body: some View { Text(model.selectedTitle) // No need to pass anything down other than the view model. MyTableView(model: model) Button("Reload") { model.reload() } Button("Delete") { model.deleteRow(...) } } } // 3. A barebones NSViewRepresentable that just vends the required NSView. No other state is required as the ViewModel handles all interactions with the view. struct MyTableView: NSViewRepresentable { // Can this even be an NSView? let model: ViewModel func makeNSView(context: Context) -> some NSView { return model.scrollView } func updateNSView(_ nsView: NSViewType, context: Context) { // Not needed, all updates are driven through the ViewModel. } } From what I can tell, the above is working as expected, but I'm curious if there are some situations where this could "break", particularly around the lifecycle of NSViewRepresentable Would love to know if overall pattern is "ok" from a SwiftUI perspective.
0
0
85
Apr ’25
Can SwiftUI TextFields in a List on macOS be marked as always editable?
In SwiftUI's List, on macOS, if I embed a TextField then the text field is presented as non-editable. If the user clicks on the text and waits a short period of time, the text field will become editable. I'm aware this is generally the correct behaviour for macOS. However, is there a way in SwiftUI to supress this behaviour such that the TextField is always presented as being editable? I want a scrollable, List of editable text fields, much like how a Form is presented. The reason I'm not using a Form is because I want List's support for reordering by drag-and-drop (.onMove). Use Case A view that allows a user to compose a questionnaire. They are able to add and remove questions (rows) and each question is editable. They require drag-and-drop support so that they can reorder the questions.
0
0
152
May ’25
How to hide the tab bar in SwiftUI's TabView for macOS?
In SwiftUI for macOS, how can I hide the tab bar when using TabView? I would like to provide my own tab bar implementation. In AppKit's NSTabViewController, we can do the following: let tabViewController = NSTabViewController() tabViewController.tabStyle = .unspecified I've come across various posts that suggest using the .toolbar modifier, but none appear to work on macOS (or at least I haven't found the right implementation). struct ContentView: View { var body: some View { TabView { // ... content } <- which view modifier hides the tab bar? } } Latest macOS, Latest Xcode
3
0
258
May ’25
How can I connect NSTableCellView.textField to a SwiftUI view?
When using NSTableView or NSOutlineView, if you use an NSTableCellView and wire up the .imageView and .textField properties then you get some "free" behaviour with respect to styling and sizing of those fields. (ex: They reflect the user's preferred "Sidebar Icon Size" as selected in Settings. ) If I'm using a SwiftUI View inside an NSTableCellView, is there any way to connect a Text or Image to those properties? Consider the following pseudo code: struct MyCellView: View { let text: String let url: URL? var body: some View { HStack { Image(...) // How to indicate this is .imageView? Text(...) // How to indicate this is .textField? } } } final class MyTableCellView: NSTableCellView { private var hostingView: NSHostingView<MyCellView>! init() { self.hostingView = NSHostingView(rootView: MyCellView(text: "", url: nil)) self.addSubview(self.hostingView) } func configureWith(text: String, url: URL) { let rootView = MyCellView(text: text, url: url) hostingView.rootView = rootView // How can I make this connection? self.textField = rootView.??? self.imageView = rootView.??? } } I'm ideally looking for a solution that works on macOS 15+.
2
0
139
Aug ’25
How do you restore a Sheet's window frame in SwiftUI for macOS
On macOS, it's not uncommon to present windows as sheets that can be resized. By setting the NSWindow's various frame auto save properties, you can restore the size of the sheet the next time it is presented. When presenting a Sheet from within SwiftUI using the .sheet view modifier, how can I preserve and restore the sheet's frame size? The closest I've been able to come is to put the SwiftUI view into a custom NSHostingController and then into an NSViewControllerRepresentable and then override viewWillAppear and look for self.view.window, which is all little awkward. Is there a more idiomatic way to achieve this in "pure" SwiftUI?
Replies
2
Boosts
0
Views
139
Activity
May ’25
How to effectively use task(id:) when multiple properties are involved?
While adopting SwiftUI (and Swift Concurrency) into a macOS/AppKit application, I'm making extensive use of the .task(id:) view modifier. In general, this is working better than expected however I'm curious if there are design patterns I can better leverage when the number of properties that need to be "monitored" grows. Consider the following pseudo-view whereby I want to call updateFilters whenever one of three separate strings is changed. struct FiltersView: View { @State var argument1: String @State var argument2: String @State var argument3: String var body: some View { TextField($argument1) TextField($argument2) TextField($argument3) }.task(id: argument1) { await updateFilters() }.task(id: argument2) { await updateFilters() }.task(id: argument3) { await updateFilters() } } Is there a better way to handle this? The best I've come up with is to nest the properties inside struct. While that works, I now find myself creating these "dummy types" in a bunch of views whenever two or more properties need to trigger an update. ex: struct FiltersView: View { struct Components: Equatable { var argument1: String var argument2: String var argument3: String } @State var components: Components var body: some View { // TextField's with bindings to $components... }.task(id: components) { await updateFilters() } } Curious if there are any cleaner ways to accomplish this because this gets a bit annoying over a lot of views and gets cumbersome when some values are passed down to child views. It also adds an entire layer of indirection who's only purpose is to trigger task(id:).
Replies
2
Boosts
0
Views
186
Activity
May ’25
On macOS, how do you place a toolbar item on the trailing edge of the window's toolbar when an Inspector view is open?
Using SwiftUI on macOS, how can I add a toolbar item on the right-most (trailing) edge of the window's toolbar when an Inspector is used? At the moment, the toolbar items are all left-of (leading) the split view tracking separator. I want the inspector toolbar item to be placed similar to where Xcode's Inspector toolbar item is placed: always as far right (trailing) as possible. NavigationSplitView { // ... snip } detail: { // ... snip } .inspector(isPresented: $isInspectorPresented) { InspectorContentView() } .toolbar { // What is the correct placement value here? ToolbarItem(placement: .primaryAction) { Button { isInspectorPresented.toggle() } label: { Label("Toggle Inspector", systemImage: "sidebar.trailing") } } } See the attached screenshot. When the InspectorView is toggled open, the toolbar item tracks leading the split view tracking separator, which is not consistent with how Xcode works.
Topic: UI Frameworks SubTopic: SwiftUI Tags:
Replies
5
Boosts
0
Views
272
Activity
Dec ’25
NSOutlineView incorrectly draws disclosure indicator when item views are SwiftUI views.
I am using an NSOutlineView via NSViewRepresentable in a SwiftUI application running on macOS. Everything has been working fine. Up until lately, I've been returning a custom NSView for each item using the standard: func outlineView(_ outlineView: NSOutlineView, viewFor tableColumn: NSTableColumn?, item: Any) -> NSView? { // View recycling omitted. return MyItemView(item) } Now I want to explore using a little bit more SwiftUI and returning an NSHostingView from this delegate method. func outlineView(_ outlineView: NSOutlineView, viewFor tableColumn: NSTableColumn?, item: Any) -> NSView? { // View recycling omitted. let rootView = MySwiftUIView(item) let hostingView = NSHostingView(rootView: rootView) return hostingView } For the most part, this appears to be working fine. NSOutlineView is even correctly applying highlight styling, so that's great. But there's one small glitch. The outline view's disclosure triangles do not align with the hosting view's content. The disclosure triangles appear to just be pinned to the top. Perhaps they can't find a baseline constraint or something? Is there any SwiftUI modifier or AppKit/SwiftUI technique I can apply here to get the disclosure button to appear in the right place? Here is what the SwiftUI + NSHostingView version looks like: Note the offset disclosure indicators. (Image spacing is a bit off as well using Label, but fixable. Here is what an NSView with NSTextFields looks like: Disclosure indicators are correctly aligned, as you would expect.
Replies
1
Boosts
0
Views
153
Activity
Nov ’25
Clarification on SwiftUI Environment Write Performance
I'm looking for clarification on a SwiftUI performance point mentioned in the recent Optimize your app's speed and efficiency | Meet with Apple video. (YouTube link not allowed, but the video is available on the Apple Developer channel.) At the 1:48:50 mark, the presenter says: Writing a value to the Environment doesn't only affect the views that read the key you're updating. It updates any view that reads from any Environment key. [abbreviated quote] That statement seems like a big deal if your app relies heavily on Environment values. Context I'm building a macOS application with a traditional three-panel layout. At any given time, there are many views on screen, plus others that exist in the hierarchy but are currently hidden (for example, views inside tab views or collapsed splitters). Nearly every major view reads something from the environment—often an @Observable object that acts as a service or provider. However, there are a few relatively small values that are written to the environment frequently, such as: The selected tab index The currently selected object on a canvas The Question Based on the presenter's statement, I’m wondering: Does writing any value to the environment really cause all views in the entire SwiftUI view hierarchy that read any environment key to have their body re-evaluated? Do environment writes only affect child views, or do they propagate through the entire SwiftUI hierarchy? Example: View A └─ View B ├─ View C └─ View D If View B updates an environment value, does that affect only C and D, or does it also trigger updates in A and B (assuming each view has at least one @Environment property)? Possible Alternative If all views are indeed invalidated by environment writes, would it be more efficient to “wrap” frequently-changing values inside an @Observable object instead of updating the environment directly? // Pseudocode @Observable final class SelectedTab { var index: Int } ContentView() .environment(\.selectedTab, selectedTab) struct TabView: View { @Environment(\.selectedTab) private var selectedTab var body: some View { Button("Action") { // Would this avoid invalidating all views using the environment? selectedTab.index = 1 } } } Summary From what I understand, it sounds like the environment should primarily be used for stable, long-lived objects—not for rapidly changing values—since writes might cause far more view invalidations than most developers realize. Is that an accurate interpretation? Follow-Up In Xcode 26 / Instruments, is there a way to monitor writes to @Environment?
Replies
4
Boosts
0
Views
1.3k
Activity
Nov ’25
Do SwiftUI Segmented Controls on macOS 26 support the icon and title label style?
On macOS 26.3, Xcode 26.3, why does a labelStyle of titleAndIcon not show both the title and the icon of a label? The label styles iconOnly and titleOnly behave as expected. Picker("Label Demo", selection: $selectedItem) { Label { Text("File") } icon: { Image(systemName: "doc") } Label { Text("Folder") } icon: { Image(systemName: "folder") } } .labelStyle(.titleAndIcon) .pickerStyle(.segmented) Note that there is no icon shown. Placing the .labelStyle modifier in different places has no effect. The icon is correctly shown when the labelStyle is set to .iconOnly. An NSSegmentedControl created with AppKit and presented in an NSViewRepresentable does correctly show titles and icons if configured appropriately. Tested on: macOS 26.3 (25D125) Xcode 26.3 (17C519) A brand new SwiftUI "macOS App" project.
Replies
2
Boosts
0
Views
124
Activity
Feb ’26
In SwiftUI for macOS, is there an equivalent to NSControl.BorderShape?
In macOS 26, there is a new property on NSControl called .borderShape. The WWDC 2025-310 video says it can be used to "Override preferred shape of control to suit your design." and that it's available on NSButton, NSPopUpButton and NSSegmentedControl. Is there an equivalent to that property for SwiftUI? For example, given the following SwiftUI code: Button("Eject") { } .borderShape(...) <-- ? How can I apply a .borderShape that would match those on controls created in AppKit? I'm aware that SwiftUI offers a plethora of ways to custom design a button such that it can have rounded corners, but I'm interested in this particular property so that SwiftUI buttons and AppKit buttons in the same app have the same look-and-feel.
Replies
1
Boosts
0
Views
117
Activity
Feb ’26
How do you set the color of an NSImage symbol when used as the contents of a CALayer?
I'm trying to use an NSImage that represents an SF Symbol as the contents of a CALayer. NSImage has an API for this in the form of [NSImage layerContentsForContentsScale:]. On the NSImage documentation page, there's even a few paragraph at the top dedicated to using this very method. But how do you set the color you want the image to render as if the image is an SF Symbol? NSImageView has .contentTintColor which works great, but CALayer has no such property. final class SymbolLayer: CALayer { func display() { // Just an example... let image = NSImage(systemSymbolName: "paperclip", accessibilityDescription: nil)! let actualScaleFactor = image.recommendedLayerContentsScale(contentsScale) // This obviously produces a black image because there's no color or tint information anywhere.     contents = image.layerContents(forContentsScale: actualScaleFactor) } } Is there a way you can configure the CALayer or the NSImage itself to have some sort of color information when it generates the layer contents? I've attempted to play around with the SymbolConfiguration coolers but without any success. (Even when wrapped inside NSAppearance.performAsCurrentDrawingAppearance.) The best I can come up with is to use CALayer.draw(in:) and then use the old NSImage.cgImage(forProposedRect:...) API. I can then set the fill color on the CGContext and go from there. Is there a more efficient way? override func draw(in context: CGContext) { let image = NSImage(systemSymbolName: "paperclip", accessibilityDescription: nil)!   var rect = bounds image.size = bounds.size let cgImage = image.cgImage( forProposedRect: &rect, context: nil, hints: [.ctm: AffineTransform(scale: contentsScale)] )! NSApp.effectiveAppearance.performAsCurrentDrawingAppearance { // Draw using an Appearance-sensitive color.     context.clip(to: bounds, mask: cgImage)     context.setFillColor(NSColor.labelColor.cgColor)     context.fill(bounds)   } } This is for macOS 12+.
Topic: UI Frameworks SubTopic: AppKit Tags:
Replies
0
Boosts
0
Views
1.8k
Activity
Sep ’21
How do you encrypt an AppleArchive with a "human" password?
In WWDC21 session 10233: Bring Encrypted Archives and Performance Improvements to Your App with Accelerate, there is an example of encrypting a directory using the AppleArchive framework. There is also accompanying sample code. However, that sample code uses a SymmetricKey and the hkdf_sha256_aesctr_hmac__symmetric__none profile. The key is set by calling context.setSymmetricKey(encryptionKey). How can you perform the same operation of encrypting a directory using AppleArchive but with a "human" password? (i.e.: A password provided by the user from a prompt?) Simply changing the profile to hkdf_sha256_aesctr_hmac__scrypt__none and then calling `context.setPassword("MyPassword") producing the following output "Error setting password (invalidValue)." I also tried using the command line aea application, but received the output Password is too short. Prompt: > aea encrypt -v -password-value "password" -profile 5 -i MyDirectory -o MyDirectory.aea Operation: encrypt input: FOO output: FOO.aea profile: hkdf_sha256_aesctr_hmac__scrypt__none worker threads: 10 auth data (raw): 0 B compression: lzfse 1 MB Error 0xb9075800 Password is too short Main key derivation failed (-2) Main key derivation Invalid encryption parameters Finally, in the file AEAContext.h, there is a comment associated with the method AEAContextSetPassword() that states: Set context password Stores a copy of password in context. Required to encrypt / decrypt a stream when encryption mode is SCRYPT. An internal size range is enforced for the password. The caller is expected to enforce password strength policies. @param context target object @param password password (raw data) @param password_size password size (bytes) @return 0 on success, a negative error code on failure I cannot find any other documentation that states what the password policy. And if there is a password policy for AppleEncryptedArchives, does that mean AEA is not a good fit for encrypting personal directories where the user just wants to use "any old password", regardless of the password's strength?
Replies
0
Boosts
0
Views
1.2k
Activity
Apr ’23
The @Environment(\.dismiss) value in SwiftUI for macOS does not dismiss a sheet presented by an NSWindowController.
I'm wondering what the correct, or recommended, way is to dismiss a SwiftUI that is being presented as a sheet hosted by an NSHostingController. The usual technique of invoking @Environment(\.dismiss) does not appear to work. Consider the code below. An NSWindowController is attempting to display a SwiftUI SettingsView as a sheet. The sheet is correctly presented, but the SettingsView is unable to dismiss itself. I am able to make it work by passing a closure into SettingsView that calls back to the NSWindowController but it's rather convoluted because SettingsView doesn't know the view controller that's hosting it until after SettingsView has been created, which means "finding" that view controller in the window controller to dismiss is more involved than it should be. Is there a better strategy to leverage here? final class MyViewController: NSViewController { @IBAction func buttonClicked(_ sender: NSButton) { if let presenter = window?.contentViewController { presenter.presentAsSheet(NSHostingController(rootView: SettingsView())) } } } struct SettingsView: View { @Environment(\.dismiss) private var dismiss var body: some View { VStack { Button("Cancel", role: .cancel) { dismiss() // This call does not dismiss the sheet. } .keyboardShortcut(.cancelAction) } } } Thank you. macOS 15.4.1 (24E263), Xcode 16.3 (16E140)
Replies
0
Boosts
0
Views
105
Activity
Apr ’25
Is it reasonable to vend an NSView from a "ViewModel" when using NSViewRepresentable instead of implementing the Coordinator pattern?
I'm currently integrating SwiftUI into an AppKit based application and was curious if the design pattern below was viable or not. In order to "bridge" between AppKit and SwiftUI, most of my SwiftUI "root" views have aViewModel that is accessible to the SwiftUI view via @ObservedObject. When a SwiftUI views need to use NSViewRepresentable I'm finding the use of a ViewModel and a Coordinator to be an unnecessary layer of indirection. In cases where it makes sense, I've just used the ViewModel as the Coordinator and it all appears to be working ok, but I'm curious if this is reasonable design pattern or if I'm overlooking something. Consider the following pseudo code: // 1. A normal @ObservedObject acting as the ViewModel that also owns and manages an NSTableView. @MainActor final class ViewModel: ObservedObject, NSTableView... { let scrollView: NSScrollView let tableView: NSTableView @Published var selectedTitle: String init() { // ViewModel manages tableView as its dataSource and delegate. tableView.dataSource = self tableView.delegate = self } func reload() { tableView.reloadData() } // Update view model properties. // Simpler than passing back up through a Coordinator. func tableViewSelectionDidChange(_ notification: Notification) { selectedTitle = tableView.selectedItem.title } } // 2. A normal SwiftUI view, mostly driven by the ViewModel. struct ContentView: View { @ObservedObject model: ViewModel var body: some View { Text(model.selectedTitle) // No need to pass anything down other than the view model. MyTableView(model: model) Button("Reload") { model.reload() } Button("Delete") { model.deleteRow(...) } } } // 3. A barebones NSViewRepresentable that just vends the required NSView. No other state is required as the ViewModel handles all interactions with the view. struct MyTableView: NSViewRepresentable { // Can this even be an NSView? let model: ViewModel func makeNSView(context: Context) -> some NSView { return model.scrollView } func updateNSView(_ nsView: NSViewType, context: Context) { // Not needed, all updates are driven through the ViewModel. } } From what I can tell, the above is working as expected, but I'm curious if there are some situations where this could "break", particularly around the lifecycle of NSViewRepresentable Would love to know if overall pattern is "ok" from a SwiftUI perspective.
Replies
0
Boosts
0
Views
85
Activity
Apr ’25
Can SwiftUI TextFields in a List on macOS be marked as always editable?
In SwiftUI's List, on macOS, if I embed a TextField then the text field is presented as non-editable. If the user clicks on the text and waits a short period of time, the text field will become editable. I'm aware this is generally the correct behaviour for macOS. However, is there a way in SwiftUI to supress this behaviour such that the TextField is always presented as being editable? I want a scrollable, List of editable text fields, much like how a Form is presented. The reason I'm not using a Form is because I want List's support for reordering by drag-and-drop (.onMove). Use Case A view that allows a user to compose a questionnaire. They are able to add and remove questions (rows) and each question is editable. They require drag-and-drop support so that they can reorder the questions.
Replies
0
Boosts
0
Views
152
Activity
May ’25
How to hide the tab bar in SwiftUI's TabView for macOS?
In SwiftUI for macOS, how can I hide the tab bar when using TabView? I would like to provide my own tab bar implementation. In AppKit's NSTabViewController, we can do the following: let tabViewController = NSTabViewController() tabViewController.tabStyle = .unspecified I've come across various posts that suggest using the .toolbar modifier, but none appear to work on macOS (or at least I haven't found the right implementation). struct ContentView: View { var body: some View { TabView { // ... content } <- which view modifier hides the tab bar? } } Latest macOS, Latest Xcode
Replies
3
Boosts
0
Views
258
Activity
May ’25
How to animate tab transitions in SwiftUI's TabView for macOS?
In SwiftUI for macOS, how can I animate the transition from one Tab to another Tab within TabView when the selection changes? In AppKit, we can do the following: let tabViewController = NSTabViewController() tabViewController.transitionOptions = [.crossfade, .allowUserInteraction] How can I achieve the same crossfade effect when using TabView?
Replies
0
Boosts
0
Views
113
Activity
May ’25
How can I connect NSTableCellView.textField to a SwiftUI view?
When using NSTableView or NSOutlineView, if you use an NSTableCellView and wire up the .imageView and .textField properties then you get some "free" behaviour with respect to styling and sizing of those fields. (ex: They reflect the user's preferred "Sidebar Icon Size" as selected in Settings. ) If I'm using a SwiftUI View inside an NSTableCellView, is there any way to connect a Text or Image to those properties? Consider the following pseudo code: struct MyCellView: View { let text: String let url: URL? var body: some View { HStack { Image(...) // How to indicate this is .imageView? Text(...) // How to indicate this is .textField? } } } final class MyTableCellView: NSTableCellView { private var hostingView: NSHostingView<MyCellView>! init() { self.hostingView = NSHostingView(rootView: MyCellView(text: "", url: nil)) self.addSubview(self.hostingView) } func configureWith(text: String, url: URL) { let rootView = MyCellView(text: text, url: url) hostingView.rootView = rootView // How can I make this connection? self.textField = rootView.??? self.imageView = rootView.??? } } I'm ideally looking for a solution that works on macOS 15+.
Replies
2
Boosts
0
Views
139
Activity
Aug ’25