diff --git a/packages/app-mobile/components/Dropdown.tsx b/packages/app-mobile/components/Dropdown.tsx index a9ede12e5..0a2c48b79 100644 --- a/packages/app-mobile/components/Dropdown.tsx +++ b/packages/app-mobile/components/Dropdown.tsx @@ -1,6 +1,7 @@ const React = require('react'); import { TouchableOpacity, TouchableWithoutFeedback, Dimensions, Text, Modal, View, LayoutRectangle, ViewStyle, TextStyle } from 'react-native'; import { Component } from 'react'; +import { _ } from '@joplin/lib/locale'; const { ItemList } = require('./ItemList.js'); type ValueType = string; @@ -58,6 +59,7 @@ class Dropdown extends Component { const items = this.props.items; const itemHeight = 60; const windowHeight = Dimensions.get('window').height - 50; + const windowWidth = Dimensions.get('window').width; // Dimensions doesn't return quite the right dimensions so leave an extra gap to make // sure nothing is off screen. @@ -66,11 +68,20 @@ class Dropdown extends Component { const maxListTop = windowHeight - listHeight; const listTop = Math.min(maxListTop, this.state.headerSize.y + this.state.headerSize.height); - const wrapperStyle = { + const wrapperStyle: ViewStyle = { width: this.state.headerSize.width, height: listHeight + 2, // +2 for the border (otherwise it makes the scrollbar appear) - marginTop: listTop, - marginLeft: this.state.headerSize.x, + top: listTop, + left: this.state.headerSize.x, + position: 'absolute', + }; + + const backgroundCloseButtonStyle: ViewStyle = { + position: 'absolute', + top: 0, + left: 0, + height: windowHeight, + width: windowWidth, }; const itemListStyle = Object.assign({}, this.props.itemListStyle ? this.props.itemListStyle : {}, { @@ -126,6 +137,7 @@ class Dropdown extends Component { return ( { closeList(); @@ -139,6 +151,22 @@ class Dropdown extends Component { ); }; + // Use a separate screen-reader-only button for closing the menu. If we + // allow the background to be focusable, instead, the focus order might be + // incorrect on some devices. For example, the background button might be focused + // when navigating near the middle of the dropdown's list. + const screenReaderCloseMenuButton = ( + closeList()} + > + {_('Close dropdown')} + + ); + return ( { }} > { + accessibilityElementsHidden={true} + importantForAccessibility='no-hide-descendants' + onPress={() => { closeList(); }} + style={backgroundCloseButtonStyle} > - - - - - + + + + + + + {screenReaderCloseMenuButton} );