Skip to content

Commit

Permalink
fix: added close drawer accessibility tap area (#11184)
Browse files Browse the repository at this point in the history
**Motivation**

Currently, a user can tap the `Overlay` next to an open drawer to close
the drawer. This is useful in an Accessibility setting when swipe
actions are not obvious to the user. Unfortunately, it is not obvious to
someone with a visual deficit that this area can be tapped to close the
drawer, as this overlay does not have an accessibilityLabel prop
exposed.

This PR exposes an `accessibilityLabel` prop on this overlay component
and modifies existing accessibility props to allow for accessibility tap
permissions on the overlay component. It then surfaces this prop at the
`Drawer` level as `closeAccessibilityLabel`.

**Test plan**

Open up the example app with TalkBack (Android) or VoiceOver (iOS)
enabled. Tap on the overlay next to the drawer and observe that it will
now read out as "Close drawer".
  • Loading branch information
mikegarfinkle authored and satya164 committed Feb 12, 2023
1 parent c9abfa5 commit 500f0de
Show file tree
Hide file tree
Showing 7 changed files with 47 additions and 6 deletions.
7 changes: 7 additions & 0 deletions packages/drawer/src/types.tsx
Expand Up @@ -171,6 +171,12 @@ export type DrawerNavigationOptions = HeaderOptions & {
*/
overlayColor?: string;

/**
* Accessibility label for the overlay. This is read by the screen reader when the user taps the overlay.
* Defaults to "Close drawer".
*/
overlayAccessibilityLabel?: string;

/**
* Style object for the component wrapping the screen content.
*/
Expand Down Expand Up @@ -310,4 +316,5 @@ export type DrawerProps = {
swipeEdgeWidth: number;
swipeEnabled: boolean;
swipeVelocityThreshold: number;
overlayAccessibilityLabel?: string;
};
2 changes: 2 additions & 0 deletions packages/drawer/src/views/DrawerView.tsx
Expand Up @@ -65,6 +65,7 @@ function DrawerViewBase({
Platform.OS !== 'windows' &&
Platform.OS !== 'macos',
swipeMinDistance,
overlayAccessibilityLabel,
} = descriptors[focusedRouteKey].options;

const [loaded, setLoaded] = React.useState([focusedRouteKey]);
Expand Down Expand Up @@ -248,6 +249,7 @@ function DrawerViewBase({
statusBarAnimation={drawerStatusBarAnimation}
keyboardDismissMode={keyboardDismissMode}
drawerType={drawerType}
overlayAccessibilityLabel={overlayAccessibilityLabel}
drawerPosition={drawerPosition}
drawerStyle={[
{ backgroundColor: colors.card },
Expand Down
6 changes: 6 additions & 0 deletions packages/react-native-drawer-layout/src/types.tsx
Expand Up @@ -58,6 +58,12 @@ export type DrawerProps = {
*/
overlayStyle?: StyleProp<ViewStyle>;

/**
* Accessibility label for the overlay. This is read by the screen reader when the user taps the overlay.
* Defaults to "Close drawer".
*/
overlayAccessibilityLabel?: string;

/**
* Whether the keyboard should be dismissed when the swipe gesture begins.
* Defaults to `'on-drag'`. Set to `'none'` to disable keyboard handling.
Expand Down
Expand Up @@ -502,6 +502,7 @@ export default class Drawer extends React.Component<Props> {
renderDrawerContent,
children,
gestureHandlerProps,
overlayAccessibilityLabel,
} = this.props;

const isOpen = drawerType === 'permanent' ? true : open;
Expand Down Expand Up @@ -592,6 +593,7 @@ export default class Drawer extends React.Component<Props> {
<Overlay
progress={progress}
onPress={() => this.toggleDrawer(false)}
accessibilityLabel={overlayAccessibilityLabel}
style={overlayStyle as any}
accessibilityElementsHidden={!isOpen}
importantForAccessibility={
Expand Down Expand Up @@ -619,7 +621,6 @@ export default class Drawer extends React.Component<Props> {
/>
)}
<Animated.View
accessibilityViewIsModal={isOpen && drawerType !== 'permanent'}
removeClippedSubviews={Platform.OS !== 'ios'}
onLayout={this.handleDrawerLayout}
style={[
Expand Down
16 changes: 14 additions & 2 deletions packages/react-native-drawer-layout/src/views/legacy/Overlay.tsx
Expand Up @@ -18,10 +18,17 @@ const PROGRESS_EPSILON = 0.05;
type Props = React.ComponentProps<typeof Animated.View> & {
progress: Animated.Node<number>;
onPress: () => void;
accessibilityLabel?: string;
};

const Overlay = React.forwardRef(function Overlay(
{ progress, onPress, style, ...props }: Props,
{
progress,
onPress,
style,
accessibilityLabel = 'Close drawer',
...props
}: Props,
ref: React.Ref<Animated.View>
) {
const animatedStyle = {
Expand All @@ -48,7 +55,12 @@ const Overlay = React.forwardRef(function Overlay(
ref={ref}
style={[styles.overlay, overlayStyle, animatedStyle, style]}
>
<Pressable onPress={onPress} style={styles.pressable} />
<Pressable
onPress={onPress}
style={styles.pressable}
accessibilityRole="button"
accessibilityLabel={accessibilityLabel}
/>
</Animated.View>
);
});
Expand Down
Expand Up @@ -55,6 +55,7 @@ export default function Drawer({
onOpen,
open,
overlayStyle,
overlayAccessibilityLabel,
statusBarAnimation,
swipeEnabled,
swipeEdgeWidth,
Expand Down Expand Up @@ -366,11 +367,11 @@ export default function Drawer({
progress={progress}
onPress={() => toggleDrawer(false)}
style={overlayStyle}
accessibilityLabel={overlayAccessibilityLabel}
/>
) : null}
</Animated.View>
<Animated.View
accessibilityViewIsModal={isOpen && drawerType !== 'permanent'}
removeClippedSubviews={Platform.OS !== 'ios'}
style={[
styles.container,
Expand Down
16 changes: 14 additions & 2 deletions packages/react-native-drawer-layout/src/views/modern/Overlay.tsx
Expand Up @@ -10,10 +10,17 @@ const PROGRESS_EPSILON = 0.05;
type Props = React.ComponentProps<typeof Animated.View> & {
progress: Animated.SharedValue<number>;
onPress: () => void;
accessibilityLabel?: string;
};

const Overlay = React.forwardRef(function Overlay(
{ progress, onPress, style, ...props }: Props,
{
progress,
onPress,
style,
accessibilityLabel = 'Close drawer',
...props
}: Props,
ref: React.Ref<Animated.View>
) {
const animatedStyle = useAnimatedStyle(() => {
Expand Down Expand Up @@ -42,7 +49,12 @@ const Overlay = React.forwardRef(function Overlay(
style={[styles.overlay, overlayStyle, animatedStyle, style]}
animatedProps={animatedProps}
>
<Pressable onPress={onPress} style={styles.pressable} />
<Pressable
onPress={onPress}
style={styles.pressable}
accessibilityRole="button"
accessibilityLabel={accessibilityLabel}
/>
</Animated.View>
);
});
Expand Down

0 comments on commit 500f0de

Please sign in to comment.