Interaction and Media Accessibility in iOS

Accessibility in iOS apps goes beyond just visual elements—it also includes interaction and media. In this post, we'll focus on interaction and media-related accessibility topics, completing our coverage of accessibility in iOS 17.

As we go through the post, I'll share a sample project and source code to illustrate the key concepts.

This post is a continuation of our previous article on visual accessibility in iOS.

Voice Control

Voice Control accessibility belongs to Ineraction group and is a feature that allows users to navigate and interact with their device entirely through spoken commands, without needing to touch the screen. It enables control over system-wide functions and app interfaces, such as tapping buttons, swiping, typing, dictating text, and navigating menus using voice instructions. Designed for users with limited mobility, Voice Control works by recognizing labels, accessibility identifiers, and numbered overlays on screen elements, making it essential for developers to provide clear and descriptive accessibility metadata in their apps to ensure seamless and inclusive user experiences.

We will start by conding following chunk:

struct VoiceControlView: View {
    @State private var name: String = ""
    @State private var message: String = ""

    var body: some View {
        VStack(spacing: 20) {
            Text("Voice Control Example")
                .font(.title)
                .accessibilityAddTraits(.isHeader)
            
            TextField("Enter your name", text: $name)
                .textFieldStyle(RoundedBorderTextFieldStyle())
                .padding()
                .accessibilityLabel("Name Field")
                .accessibilityIdentifier("nameField")

            Button(action: {
                message = "Hello, \(name)!"
            }) {
                Text("Submit")
                    .padding()
                    .frame(maxWidth: .infinity)
                    .background(Color.blue)
                    .foregroundColor(.white)
                    .cornerRadius(10)
            }
            .accessibilityLabel("Submit Button")
            .accessibilityIdentifier("submitButton")

            if !message.isEmpty {
                Text(message)
                    .font(.headline)
                    .accessibilityLabel(message)
            }

            Spacer()
        }
        .padding()
    }
}

This SwiftUI code defines a simple view called VoiceControlView that demonstrates how to make an interface accessible using iOS Voice Control. It includes a title, a text field for entering a name, and a submit button that, when tapped (or activated by voice), displays a personalized greeting message. Accessibility labels and identifiers are provided for the text field and button, allowing users to interact with them using voice commands like «Tap Name Field» or «Tap Submit Button.» The view is designed to be fully accessible, enhancing usability for users who rely on voice input for navigation and interaction.

For a more realistic experience, I recommend running the demo on a real device. Note that Voice Control is not enabled by default—you’ll need to turn it on by going to Settings > Accessibility > Voice Control.

Screenshot
Screenshot 2025-07-26 at 20.43.11

Deploy the app in a real device, and if Voice Control was setup properly, you should have to see following:

Screenshot 2025-07-26 at 20.57.13
Screenshot 2025-07-26 at 20.56.05

Instead of tapping controls on the device screen, simply say «Tap» followed by the label shown on the control you want to interact with. For example, say «Tap More» to access the view dedicated to Voice Control, «Tap Name» to start entering text into the input field, and «Tap Submit» to submit the form.

Voice Over

VoiceOver belongs to Ineraction group and is an iOS accessibility feature that provides spoken feedback to help users with visual impairments navigate and interact with their devices. It reads aloud on-screen elements such as buttons, labels, text, and images, and allows users to control their device using gestures tailored for non-visual interaction. When VoiceOver is enabled, users can explore the interface by dragging a finger across the screen or using swipe gestures to move between elements, with each item being read aloud. Developers can enhance VoiceOver support by providing descriptive accessibility labels, traits, and hints to ensure that all content is understandable and usable without relying on sight.

Lets take a look at the code  prepared for voice over:

struct VoiceOverView: View {
    @State private var isToggled = false
       
       var body: some View {
           VStack(spacing: 40) {
               Text("VoiceOver Interaction Example")
                   .font(.title)
                   .accessibilityAddTraits(.isHeader)
               
               Button(action: {
                   isToggled.toggle()
               }) {
                   Image(systemName: isToggled ? "checkmark.circle.fill" : "circle")
                       .resizable()
                       .frame(width: 60, height: 60)
                       .foregroundColor(isToggled ? .green : .gray)
               }
               .accessibilityLabel("Toggle button")
               .accessibilityValue(isToggled ? "On" : "Off")
               .accessibilityHint("Double tap to change the toggle state")

               Text("Toggle is currently \(isToggled ? "On" : "Off")")
           }
           .padding()
       }
}

The VoiceOverView SwiftUI struct defines a user interface that includes a header, a toggle button represented by an icon, and a status text label, with full VoiceOver accessibility support. The toggle button switches between a green checkmark and a gray circle when tapped, reflecting its «On» or «Off» state. For VoiceOver users, the button is described as «Toggle button» with a dynamic accessibility value («On» or «Off») and a hint explaining that a double-tap changes its state. The header is marked with .isHeader to assist navigation, and the toggle state is also shown in plain text. This setup ensures visually impaired users can fully interact with and understand the UI using VoiceOver.

Deploy in the simulator and present the screen to audit and open Accesibility Inspector, select simulator and Run Audit:

Captions

Captions belong to the Media Accessibility group and consist of providing text descriptions of dialogue and other audible content during media playback. They help people who are deaf or hard of hearing access important information such as speech, nonverbal communication, music, and sound effects. Ensure that users can enable captions for all video or audio content. In this case, there is nothing to code—just make sure that if your app plays video, the content includes the option to enable captions (speech, non-verbal communication, music or sound effects).

Audio descriptions

Audio Descriptions belong to the Media Accessibility group and provide spoken narration during natural pauses in the main audio to describe important visual elements of the content. This helps people who are blind or have low vision understand what is happening on screen. Make sure users can easily find content that includes audio descriptions. For example, most video streaming apps display an «AD» icon to indicate availability. As with captions, this accessibility requirement applies to the content being played—not the app itself.

Conclusions

With this post, we wrap up the remaining accessibility groups—Interaction and Media—that we set aside in a previous post. The Interaction group includes coding tasks that require implementation, while the Media group mainly concerns the accessibility of streamed content within the app, so there’s typically nothing to code.

You can find source code that we have used for conducting this post in following GitHub repository.

References

Copyright © 2024-2025 JaviOS. All rights reserved