How to Optimize VoiceOver? Swift, Java, Safari extensions, macOS Sequoia Security
- #Swift
- #Java
- #Safari
• 4 min read
Win a free trip to Apple Park. Improve VoiceControl in your app. Get tips for Safari extensions and other updates from macOS and iOS. I'm Oleksandr Bilous, an engineer with the Setapp team, and let's get started.
Swift Student Challenge
Apple has announced the Swift Student Challenge 2025, a competition for creating apps in Playgrounds. 350 winners will receive a one-year access to the Apple Developer Program and special gifts, while the top 50 will enjoy three unforgettable days with Apple in Cupertino.
The application opens in February next year, so you still have plenty of time to prepare and learn Swift. Thankfully Apple offers excellent guides to get you started.
ServerSide.swift
The ServerSide.swift conference took place in September, giving developers hours of bingeworthy material. I particularly enjoyed the talk on Swift & Interoperability, covering everything on the Foundation framework, including CoreFoundation, Objective-C, and the performance in Swift 6.
swift-java, a toolkit for Swift 6 compatibility with Java, was also announced. There are now two options for working with the Java Development Kit. The first solution, JavaKit, for JDK 17 and above, uses Swift macros to generate code for dynamically calling Java object methods. It leverages Java's reflection capabilities to extract type and method information and generate bindings. The second solution, jextract-swift, offers backward compatibility, allowing you to use Swift in Java. It can convert Swift classes, global functions, and variables.
Learn more about Swift/Java interoperability
Safari Extension SwiftUI
If you've ever wanted to create a Safari extension, this news is for you. Developer Pol Piella has created a step-by-step documentation on setting up a Safari Extension with SwiftUI. The task seems simple, but if you've tried building one on your own, you’ll run into a problem that Xcode generates a project with xib files and JS scripts.
Here’s a quick fix. First, delete script.js from resources and the SafariExtensionViewController files, both .swift
and .xib
. Then, modify Info.plist by adding the SFSafariToolbarItem
key, specifying default settings: Popover Action
, Image
, Label
, and a unique extension identifier. Other parameters depend on your needs.
The final step is to make changes in SafariExtensionHandler
, the main class of the bundle. You just need to override the popoverViewController
method and return your custom ViewController
, which uses NSHostingView
with SwiftUI elements. And to wrap up, a small tip: you can control the extension's availability based on the browser page context using the validateToolbarItem
method.
Optimizing for VoiceOver
Apple always emphasizes interface accessibility and has a dedicated section in the Human Interface Guidelines. Let's look at a practical example of optimizing voice control. In our app, we have a simple SwiftUI element consisting of a title, description, and two buttons—close or take a survey.
The button is implemented via an overlay on our VStack. In this case, the Accessibility Tree starts with the Dismiss Button, followed by the text content. This feels very inconvenient—users know nothing about the element, yet voice control immediately suggests closing it!
To fix this, simply assign an accessibilitySortPriority
to the button, which will move it down the hierarchy. For better user experience, it's recommended to group logical blocks, so we'll use the combine option to merge the title and description. Much better—now VoiceOver provides information about the content inside the element, and only then asks to either confirm or cancel the action.
Optimize your app for VoiceOver and VoiceControl
macOS Sequoia and Screen Recording Permissions
If you've already upgraded to macOS Sequoia, you've likely noticed Apple's security improvements. Аor example, Screen Recording now asks for permissions every month, also requiring users to confirm access each time an app requests to record the screen. While this enhances security, the frequent alerts are a bit annoying, especially if they pop up at the worst times.
It seems these constant requests bothered the developer community, and a solution to this "problem" quickly emerged. Although all access data is stored in the TCC (Transparency, Consent, and Control) database, safeguarded by System Integrity Protection, the information about the next reminder is stored in a plist file.
To modify it, simply grant Terminal Full Disk Access, then set the next request date for the specific executable. In our example, ScreenFloat will show a system alert only in the year 4321.
But don't worry, our next article will come sooner. Until then, subscribe and take care!