Accessibility Label for Image

Images that provide context should have an accessibility label or should be explicitly hidden from accessibility

  • Identifier: accessibility_label_for_image
  • Enabled by default: No
  • Supports autocorrection: No
  • Kind: lint
  • Analyzer rule: No
  • Minimum Swift compiler version: 5.1.0
  • Default configuration:
    KeyValue
    severity warning

Rationale

In UIKit, a UIImageView was by default not an accessibility element, and would only be visible to VoiceOver and other assistive technologies if the developer explicitly made them an accessibility element. In SwiftUI, however, an Image is an accessibility element by default. If the developer does not explicitly hide them from accessibility or give them an accessibility label, they will inherit the name of the image file, which often creates a poor experience when VoiceOver reads things like “close icon white”.

Known false negatives for Images declared as instance variables and containers that provide a label but are not accessibility elements. Known false positives for Images created in a separate function from where they have accessibility properties applied.

Non Triggering Examples

struct MyView: View {
    var body: some View {
        Image(decorative: "my-image")
    }
}
struct MyView: View {
    var body: some View {
        Image("my-image", label: Text("Alt text for my image"))
    }
}
struct MyView: View {
    var body: some View {
        Image("my-image")
            .accessibility(hidden: true)
    }
}
struct MyView: View {
    var body: some View {
        Image("my-image")
            .accessibilityHidden(true)
    }
}
struct MyView: View {
    var body: some View {
        Image("my-image")
            .accessibility(label: Text("Alt text for my image"))
    }
}
struct MyView: View {
    var body: some View {
        Image("my-image")
            .accessibilityLabel(Text("Alt text for my image"))
    }
}
struct MyView: View {
    var body: some View {
        Image(uiImage: myUiImage)
            .renderingMode(.template)
            .foregroundColor(.blue)
            .accessibilityHidden(true)
    }
}
struct MyView: View {
    var body: some View {
        Image(uiImage: myUiImage)
            .accessibilityLabel(Text("Alt text for my image"))
    }
}
struct MyView: View {
    var body: some View {
        SwiftUI.Image(uiImage: "my-image").resizable().accessibilityHidden(true)
    }
}
struct MyView: View {
    var body: some View {
        VStack {
            Image(decorative: "my-image")
                .renderingMode(.template)
                .foregroundColor(.blue)
            Image("my-image")
                .accessibility(label: Text("Alt text for my image"))
        }
    }
}
struct MyView: View {
    var body: some View {
        VStack {
            Image("my-image")
                .renderingMode(.template)
                .foregroundColor(.blue)
            Image("my-image")
                .accessibility(label: Text("Alt text for my image"))
        }.accessibilityElement()
    }
}
struct MyView: View {
    var body: some View {
        VStack {
            Image("my-image")
                .renderingMode(.template)
                .foregroundColor(.blue)
            Image("my-image")
                .accessibility(label: Text("Alt text for my image"))
        }.accessibilityHidden(true)
    }
}
struct MyView: View {
    var body: some View {
        HStack(spacing: 8) {
            Image(decorative: "my-image")
                .renderingMode(.template)
                .foregroundColor(.blue)
            Text("Text to accompany my image")
        }.accessibilityElement(children: .combine)
        .padding(16)
    }
}
struct MyView: View {
    var body: some View {
        HStack(spacing: 8) {
            Image("my-image")
                .renderingMode(.template)
                .foregroundColor(.blue)
            Text("Text to accompany my image")
        }.accessibilityElement(children: .ignore)
        .padding(16)
        .accessibilityLabel(Text("Label for my image and text"))
    }
}
struct MyView: View {
    var body: some View {
        Button(action: { doAction() }) {
            Image("my-image")
                .renderingMode(.template)
                .foregroundColor(.blue)
        }
        .accessibilityLabel(Text("Label for my image"))
    }
}

Triggering Examples

struct MyView: View {
    var body: some View {
        Image("my-image")
            .resizable(true)
            .frame(width: 48, height: 48)
    }
}
struct MyView: View {
    var body: some View {
        Image(uiImage: myUiImage)
    }
}
struct MyView: View {
    var body: some View {
        SwiftUI.Image(uiImage: "my-image").resizable().accessibilityHidden(false)
    }
}
struct MyView: View {
    var body: some View {
        Image(uiImage: myUiImage)
            .resizable()
            .frame(width: 48, height: 48)
            .accessibilityLabel(Text("Alt text for my image"))
        Image("other image")
    }
}
struct MyView: View {
    var body: some View {
        Image(decorative: "image1")
        Image("image2")
        Image(uiImage: "image3")
            .accessibility(label: Text("a pretty picture"))
    }
}
struct MyView: View {
    var body: some View {
        VStack {
            Image(decorative: "my-image")
                .renderingMode(.template)
                .foregroundColor(.blue)
            Image("my-image")
        }
    }
}
struct MyView: View {
    var body: some View {
        VStack {
            Image("my-image")
                .renderingMode(.template)
                .foregroundColor(.blue)
            Image("my-image")
                .accessibility(label: Text("Alt text for my image"))
        }.accessibilityElement(children: .contain)
    }
}
struct MyView: View {
    var body: some View {
        VStack {
            Image("my-image")
                .renderingMode(.template)
                .foregroundColor(.blue)
            Image("my-image")
                .accessibility(label: Text("Alt text for my image"))
        }.accessibilityHidden(false)
    }
}
struct MyView: View {
    var body: some View {
        HStack(spacing: 8) {
            Image("my-image")
                .renderingMode(.template)
                .foregroundColor(.blue)
            Text("Text to accompany my image")
        }.accessibilityElement(children: .combine)
        .padding(16)
    }
}
struct MyView: View {
    var body: some View {
        Button(action: { doAction() }) {
            Image("my-image")
                .renderingMode(.template)
                .foregroundColor(.blue)
        }
    }
}
struct MyView: View {
    var body: some View {
        Image(systemName: "circle.plus")
    }
}