From ccf0c8a3634af666aef74eb52db5929d23dd5afa Mon Sep 17 00:00:00 2001 From: Guus der Kinderen Date: Thu, 7 Jun 2018 22:32:18 +0200 Subject: [PATCH] fix(i18n) Accessiblity labels translations (#3071) * fix(toolbar): accessibilityLabel should be translatable. This commit adds a helper property to get the accessibilityLabel of an item, providing a translation if one is available. This mimics the behavior of label and tooltip. * fix(toolbar) 'hangup' button accessibilityLabel i18n * fix(toolbar) 'mute' button accessibilityLabel i18n * fix(toolbar) 'videomute' button accessibilityLabel i18n * fix(toolbar) 'moreActions' button accessibilityLabel i18n * fix(toolbar) 'shareRoom' button accessibilityLabel i18n * fix(toolbar) 'audioRoute' button accessibilityLabel i18n * fix(toolbar) 'toggleCamera' button accessibilityLabel i18n * fix(toolbar) 'audioOnly' button accessibilityLabel i18n * fix(toolbar) 'roomLock' button accessibilityLabel i18n * fix(toolbar) 'pip' button accessibilityLabel i18n * fix(toolbar) 'invite' button accessibilityLabel i18n * fix(toolbar) 'raiseHand' button accessibilityLabel i18n * fix(toolbar) 'chat' button accessibilityLabel i18n * fix(toolbar) 'shareYourScreen' button accessibilityLabel i18n * fix(toolbar) 'fullScreen' button accessibilityLabel i18n * fix(toolbar) 'sharedvideo' button accessibilityLabel i18n * fix(toolbar) 'document' button accessibilityLabel i18n * fix(toolbar) 'speakerStats' button accessibilityLabel i18n * fix(toolbar) 'feedback' button accessibilityLabel i18n * fix(toolbar) 'shortcuts' button accessibilityLabel i18n * fix(toolbar) 'recording' button accessibilityLabel i18n * fix(toolbar) 'settings' button accessibilityLabel i18n * fix(welcomepage) accessibilityLabels i18n * fix(toolbar) 'info' button accessibilityLabel i18n * fix(i18n): Add translation to various aria-label property values. * fix(i18n): Differentiate between overflow menu and button. --- lang/main.json | 35 ++++++++++++++++++ .../features/always-on-top/AudioMuteButton.js | 2 ++ react/features/always-on-top/HangupButton.js | 3 ++ .../features/always-on-top/VideoMuteButton.js | 2 ++ .../components/AbstractAudioMuteButton.js | 1 - .../components/AbstractHangupButton.js | 1 - .../toolbox/components/AbstractToolboxItem.js | 11 ++++++ .../components/AbstractVideoMuteButton.js | 1 - .../toolbox/components/ToolboxItem.native.js | 3 +- .../toolbox/components/ToolboxItem.web.js | 3 +- .../invite/components/InfoDialogButton.web.js | 2 +- .../invite/components/InviteButton.native.js | 2 +- .../audio-mode/components/AudioRouteButton.js | 2 +- .../components/PictureInPictureButton.js | 2 +- .../room-lock/components/RoomLockButton.js | 2 +- .../settings/components/web/SettingsButton.js | 2 +- .../toolbox/components/AudioMuteButton.js | 1 + .../toolbox/components/HangupButton.js | 1 + .../toolbox/components/VideoMuteButton.js | 1 + .../components/native/AudioOnlyButton.js | 2 +- .../components/native/OverflowMenuButton.js | 2 +- .../components/native/ToggleCameraButton.js | 2 +- .../components/web/OverflowMenuButton.js | 3 +- .../web/OverflowMenuLiveStreamingItem.js | 2 +- .../components/web/OverflowMenuProfileItem.js | 2 +- .../toolbox/components/web/Toolbox.js | 36 ++++++++++++------- .../OverflowMenuVideoQualityItem.web.js | 3 +- .../welcome/components/WelcomePage.native.js | 7 ++-- 28 files changed, 102 insertions(+), 34 deletions(-) diff --git a/lang/main.json b/lang/main.json index 6dc869ac2..c7fd10292 100644 --- a/lang/main.json +++ b/lang/main.json @@ -46,6 +46,10 @@ "showSpeakerStats": "Show speaker stats" }, "welcomepage":{ + "accessibilityLabel": { + "join": "Tap to join", + "roomname": "Enter room name" + }, "appDescription": "Go ahead, video chat with the whole team. In fact, invite everyone you know. __app__ is a fully encrypted, 100% open source video conferencing solution that you can use all day, every day, for free — with no account needed.", "audioVideoSwitch": { "audio": "Voice", @@ -72,6 +76,33 @@ "rejoinKeyTitle": "Rejoin" }, "toolbar": { + "accessibilityLabel": { + "audioOnly": "Toggle audio only", + "audioRoute": "Select the audio route", + "callQuality": "Manage call quality", + "chat": "Toggle chat window", + "document": "Toggle shared document", + "feedback": "Leave feedback", + "fullScreen": "Toggle full screen", + "hangup": "Leave the call", + "invite": "Invite people", + "lockRoom": "Toggle room lock", + "moreActions": "Toggle more actions menu", + "moreActionsMenu": "More actions menu", + "mute": "Toggle mute audio", + "pip": "Toggle Picture-in-Picture mode", + "profile": "Edit your profile", + "raiseHand": "Toggle raise hand", + "recording": "Toggle recording", + "Settings": "Toggle settings", + "sharedvideo": "Toggle Youtube video sharing", + "shareRoom": "Invite someone", + "shareYourScreen": "Toggle screenshare", + "shortcuts": "Toggle shortcuts", + "speakerStats": "Toggle speaker statistics", + "toggleCamera": "Toggle camera", + "videomute": "Toggle mute video" + }, "addPeople": "Add people to your call", "audioonly": "Enable / Disable audio only mode (saves bandwidth)", "audioOnlyOn": "Enable audio only mode (saves bandwidth)", @@ -207,6 +238,9 @@ "suboptimalExperienceDescription": "Eer... we are afraid your experience with __appName__ isn't going to be that great here. We are looking for ways to improve this but, until then, please try using one of the fully supported browsers." }, "dialog": { + "accessibilityLabel": { + "liveStreaming": "Live Stream" + }, "allow": "Allow", "confirm": "Confirm", "kickMessage": "Ouch! You have been kicked out of the meet!", @@ -523,6 +557,7 @@ "veryGood": "Very Good" }, "info": { + "accessibilityLabel": "Show info", "addPassword": "Add password", "cancelPassword": "Cancel password", "conferenceURL": "Link:", diff --git a/react/features/always-on-top/AudioMuteButton.js b/react/features/always-on-top/AudioMuteButton.js index 35d89bb48..910aba311 100644 --- a/react/features/always-on-top/AudioMuteButton.js +++ b/react/features/always-on-top/AudioMuteButton.js @@ -27,6 +27,8 @@ type State = { export default class AudioMuteButton extends AbstractAudioMuteButton { + accessibilityLabel = 'Audio mute'; + /** * Initializes a new {@code AudioMuteButton} instance. * diff --git a/react/features/always-on-top/HangupButton.js b/react/features/always-on-top/HangupButton.js index c9e88b020..e9490fc93 100644 --- a/react/features/always-on-top/HangupButton.js +++ b/react/features/always-on-top/HangupButton.js @@ -9,6 +9,9 @@ const { api } = window.alwaysOnTop; * Stateless hangup button for the Always-on-Top windows. */ export default class HangupButton extends AbstractHangupButton { + + accessibilityLabel = 'Hangup'; + /** * Helper function to perform the actual hangup action. * diff --git a/react/features/always-on-top/VideoMuteButton.js b/react/features/always-on-top/VideoMuteButton.js index bd55779cc..15d511518 100644 --- a/react/features/always-on-top/VideoMuteButton.js +++ b/react/features/always-on-top/VideoMuteButton.js @@ -27,6 +27,8 @@ type State = { export default class VideoMuteButton extends AbstractVideoMuteButton { + accessibilityLabel = 'Video mute'; + /** * Initializes a new {@code VideoMuteButton} instance. * diff --git a/react/features/base/toolbox/components/AbstractAudioMuteButton.js b/react/features/base/toolbox/components/AbstractAudioMuteButton.js index 1a354603c..2c202c64d 100644 --- a/react/features/base/toolbox/components/AbstractAudioMuteButton.js +++ b/react/features/base/toolbox/components/AbstractAudioMuteButton.js @@ -9,7 +9,6 @@ import type { Props } from './AbstractButton'; export default class AbstractAudioMuteButton extends AbstractButton { - accessibilityLabel = 'Audio mute'; iconName = 'icon-microphone'; toggledIconName = 'icon-mic-disabled toggled'; diff --git a/react/features/base/toolbox/components/AbstractHangupButton.js b/react/features/base/toolbox/components/AbstractHangupButton.js index 8523496af..9b82e46ff 100644 --- a/react/features/base/toolbox/components/AbstractHangupButton.js +++ b/react/features/base/toolbox/components/AbstractHangupButton.js @@ -9,7 +9,6 @@ import type { Props } from './AbstractButton'; export default class AbstractHangupButton

extends AbstractButton { - accessibilityLabel = 'Hangup'; iconName = 'icon-hangup'; /** diff --git a/react/features/base/toolbox/components/AbstractToolboxItem.js b/react/features/base/toolbox/components/AbstractToolboxItem.js index f45cf68d7..bc801d7fe 100644 --- a/react/features/base/toolbox/components/AbstractToolboxItem.js +++ b/react/features/base/toolbox/components/AbstractToolboxItem.js @@ -146,6 +146,17 @@ export default class AbstractToolboxItem

extends Component

{ return this._maybeTranslateAttribute(this.props.tooltip); } + /** + * Helper property to get the item accessibilityLabel. If a translation + * function was provided then it will be translated using it. + * + * @protected + * @returns {?string} + */ + get accessibilityLabel(): ?string { + return this._maybeTranslateAttribute(this.props.accessibilityLabel); + } + /** * Utility function to translate the given string, if a translation * function is available. diff --git a/react/features/base/toolbox/components/AbstractVideoMuteButton.js b/react/features/base/toolbox/components/AbstractVideoMuteButton.js index a31f0b24e..9cf7e0aee 100644 --- a/react/features/base/toolbox/components/AbstractVideoMuteButton.js +++ b/react/features/base/toolbox/components/AbstractVideoMuteButton.js @@ -9,7 +9,6 @@ import type { Props } from './AbstractButton'; export default class AbstractVideoMuteButton

extends AbstractButton { - accessibilityLabel = 'Video mute'; iconName = 'icon-camera'; toggledIconName = 'icon-camera-disabled toggled'; diff --git a/react/features/base/toolbox/components/ToolboxItem.native.js b/react/features/base/toolbox/components/ToolboxItem.native.js index ef3e67651..90bb4213d 100644 --- a/react/features/base/toolbox/components/ToolboxItem.native.js +++ b/react/features/base/toolbox/components/ToolboxItem.native.js @@ -50,7 +50,6 @@ export default class ToolboxItem extends AbstractToolboxItem { */ _renderItem() { const { - accessibilityLabel, disabled, onClick, showLabel, @@ -83,7 +82,7 @@ export default class ToolboxItem extends AbstractToolboxItem { return ( { */ _renderItem() { const { - accessibilityLabel, onClick, showLabel } = this.props; const props = { - 'aria-label': accessibilityLabel, + 'aria-label': this.accessibilityLabel, className: showLabel ? 'overflow-menu-item' : 'toolbox-button', onClick }; diff --git a/react/features/invite/components/InfoDialogButton.web.js b/react/features/invite/components/InfoDialogButton.web.js index 0df0acb4b..9a6e32ddd 100644 --- a/react/features/invite/components/InfoDialogButton.web.js +++ b/react/features/invite/components/InfoDialogButton.web.js @@ -170,7 +170,7 @@ class InfoDialogButton extends Component { onClose = { this._onDialogClose } position = { 'top right' }> diff --git a/react/features/invite/components/InviteButton.native.js b/react/features/invite/components/InviteButton.native.js index c3c78eb18..b329b2a5f 100644 --- a/react/features/invite/components/InviteButton.native.js +++ b/react/features/invite/components/InviteButton.native.js @@ -52,7 +52,7 @@ const _SHARE_ROOM_TOOLBAR_BUTTON = true; * current call/conference/meeting. */ class InviteButton extends AbstractButton { - accessibilityLabel = 'Share room'; + accessibilityLabel = 'toolbar.accessibilityLabel.shareRoom'; iconName = 'icon-link'; label = 'toolbar.shareRoom'; diff --git a/react/features/mobile/audio-mode/components/AudioRouteButton.js b/react/features/mobile/audio-mode/components/AudioRouteButton.js index cfa5aab4d..44768454e 100644 --- a/react/features/mobile/audio-mode/components/AudioRouteButton.js +++ b/react/features/mobile/audio-mode/components/AudioRouteButton.js @@ -43,7 +43,7 @@ type Props = AbstractButtonProps & { * A toolbar button which triggers an audio route picker when pressed. */ class AudioRouteButton extends AbstractButton { - accessibilityLabel = 'Audio route'; + accessibilityLabel = 'toolbar.accessibilityLabel.audioRoute'; iconName = 'icon-volume'; label = 'toolbar.audioRoute'; diff --git a/react/features/mobile/picture-in-picture/components/PictureInPictureButton.js b/react/features/mobile/picture-in-picture/components/PictureInPictureButton.js index 537074c16..065d6d356 100644 --- a/react/features/mobile/picture-in-picture/components/PictureInPictureButton.js +++ b/react/features/mobile/picture-in-picture/components/PictureInPictureButton.js @@ -26,7 +26,7 @@ type Props = AbstractButtonProps & { * An implementation of a button for entering Picture-in-Picture mode. */ class PictureInPictureButton extends AbstractButton { - accessibilityLabel = 'Picture in picture'; + accessibilityLabel = 'toolbar.accessibilityLabel.pip'; iconName = 'icon-menu-down'; label = 'toolbar.pip'; diff --git a/react/features/room-lock/components/RoomLockButton.js b/react/features/room-lock/components/RoomLockButton.js index acce4a6e5..1c2c2d8ee 100644 --- a/react/features/room-lock/components/RoomLockButton.js +++ b/react/features/room-lock/components/RoomLockButton.js @@ -32,7 +32,7 @@ type Props = AbstractButtonProps & { * An implementation of a button for locking / unlocking a room. */ class RoomLockButton extends AbstractButton { - accessibilityLabel = 'Room lock'; + accessibilityLabel = 'toolbar.accessibilityLabel.lockRoom'; iconName = 'security'; label = 'dialog.lockRoom'; toggledIconName = 'security-locked'; diff --git a/react/features/settings/components/web/SettingsButton.js b/react/features/settings/components/web/SettingsButton.js index d4c7e98cc..c8119b82e 100644 --- a/react/features/settings/components/web/SettingsButton.js +++ b/react/features/settings/components/web/SettingsButton.js @@ -36,7 +36,7 @@ type Props = AbstractButtonProps & { * An abstract implementation of a button for accessing settings. */ class SettingsButton extends AbstractButton { - accessibilityLabel = 'Settings'; + accessibilityLabel = 'toolbar.accessibilityLabel.Settings'; iconName = 'icon-settings'; label = 'toolbar.Settings'; tooltip = 'toolbar.Settings'; diff --git a/react/features/toolbox/components/AudioMuteButton.js b/react/features/toolbox/components/AudioMuteButton.js index 1e6bf56cd..58fa45af9 100644 --- a/react/features/toolbox/components/AudioMuteButton.js +++ b/react/features/toolbox/components/AudioMuteButton.js @@ -40,6 +40,7 @@ type Props = AbstractButtonProps & { * @extends AbstractAudioMuteButton */ class AudioMuteButton extends AbstractAudioMuteButton { + accessibilityLabel = 'toolbar.accessibilityLabel.mute'; label = 'toolbar.mute'; tooltip = 'toolbar.mute'; diff --git a/react/features/toolbox/components/HangupButton.js b/react/features/toolbox/components/HangupButton.js index e1986d640..dfc5f3f52 100644 --- a/react/features/toolbox/components/HangupButton.js +++ b/react/features/toolbox/components/HangupButton.js @@ -26,6 +26,7 @@ type Props = AbstractButtonProps & { * @extends AbstractHangupButton */ class HangupButton extends AbstractHangupButton { + accessibilityLabel = 'toolbar.accessibilityLabel.hangup'; label = 'toolbar.hangup'; tooltip = 'toolbar.hangup'; diff --git a/react/features/toolbox/components/VideoMuteButton.js b/react/features/toolbox/components/VideoMuteButton.js index e15370253..99856f611 100644 --- a/react/features/toolbox/components/VideoMuteButton.js +++ b/react/features/toolbox/components/VideoMuteButton.js @@ -49,6 +49,7 @@ type Props = AbstractButtonProps & { * @extends AbstractVideoMuteButton */ class VideoMuteButton extends AbstractVideoMuteButton { + accessibilityLabel = 'toolbar.accessibilityLabel.videomute'; label = 'toolbar.videomute'; tooltip = 'toolbar.videomute'; diff --git a/react/features/toolbox/components/native/AudioOnlyButton.js b/react/features/toolbox/components/native/AudioOnlyButton.js index 9295a6f39..dc9d9a1c7 100644 --- a/react/features/toolbox/components/native/AudioOnlyButton.js +++ b/react/features/toolbox/components/native/AudioOnlyButton.js @@ -27,7 +27,7 @@ type Props = AbstractButtonProps & { * An implementation of a button for toggling the audio-only mode. */ class AudioOnlyButton extends AbstractButton { - accessibilityLabel = 'Audio only mode'; + accessibilityLabel = 'toolbar.accessibilityLabel.audioOnly'; iconName = 'visibility'; label = 'toolbar.audioOnlyOn'; toggledIconName = 'visibility-off'; diff --git a/react/features/toolbox/components/native/OverflowMenuButton.js b/react/features/toolbox/components/native/OverflowMenuButton.js index e398fc3a4..f1784fad9 100644 --- a/react/features/toolbox/components/native/OverflowMenuButton.js +++ b/react/features/toolbox/components/native/OverflowMenuButton.js @@ -24,7 +24,7 @@ type Props = AbstractButtonProps & { * An implementation of a button for showing the {@code OverflowMenu}. */ class OverflowMenuButton extends AbstractButton { - accessibilityLabel = 'Overflow menu'; + accessibilityLabel = 'toolbar.accessibilityLabel.moreActions'; iconName = 'icon-thumb-menu'; label = 'toolbar.moreActions'; diff --git a/react/features/toolbox/components/native/ToggleCameraButton.js b/react/features/toolbox/components/native/ToggleCameraButton.js index 2242f3bab..f3fd3777f 100644 --- a/react/features/toolbox/components/native/ToggleCameraButton.js +++ b/react/features/toolbox/components/native/ToggleCameraButton.js @@ -33,7 +33,7 @@ type Props = AbstractButtonProps & { * An implementation of a button for toggling the camera facing mode. */ class ToggleCameraButton extends AbstractButton { - accessibilityLabel = 'Toggle camera'; + accessibilityLabel = 'toolbar.accessibilityLabel.toggleCamera'; iconName = 'icon-switch-camera'; label = 'toolbar.toggleCamera'; diff --git a/react/features/toolbox/components/web/OverflowMenuButton.js b/react/features/toolbox/components/web/OverflowMenuButton.js index 35da66a5a..37759be0b 100644 --- a/react/features/toolbox/components/web/OverflowMenuButton.js +++ b/react/features/toolbox/components/web/OverflowMenuButton.js @@ -73,7 +73,8 @@ class OverflowMenuButton extends Component { onClose = { this._onCloseDialog } position = { 'top right' }> diff --git a/react/features/toolbox/components/web/OverflowMenuLiveStreamingItem.js b/react/features/toolbox/components/web/OverflowMenuLiveStreamingItem.js index f6da37d29..78b018de8 100644 --- a/react/features/toolbox/components/web/OverflowMenuLiveStreamingItem.js +++ b/react/features/toolbox/components/web/OverflowMenuLiveStreamingItem.js @@ -49,7 +49,7 @@ class OverflowMenuLiveStreamingItem extends Component { return (

  • diff --git a/react/features/toolbox/components/web/OverflowMenuProfileItem.js b/react/features/toolbox/components/web/OverflowMenuProfileItem.js index 16c3a73f9..44394688a 100644 --- a/react/features/toolbox/components/web/OverflowMenuProfileItem.js +++ b/react/features/toolbox/components/web/OverflowMenuProfileItem.js @@ -74,7 +74,7 @@ class OverflowMenuProfileItem extends Component { return (
  • diff --git a/react/features/toolbox/components/web/Toolbox.js b/react/features/toolbox/components/web/Toolbox.js index b97823c7f..3b6b09722 100644 --- a/react/features/toolbox/components/web/Toolbox.js +++ b/react/features/toolbox/components/web/Toolbox.js @@ -336,6 +336,7 @@ class Toolbox extends Component { const overflowMenuContent = this._renderOverflowMenuContent(); const overflowHasItems = Boolean(overflowMenuContent.filter( child => child).length); + const toolbarAccLabel = 'toolbar.accessibilityLabel.moreActionsMenu'; return (
    { && this._renderDesktopSharingButton() } { this._shouldShowButton('raisehand') && { { this._shouldShowButton('chat') &&
    { { this._shouldShowButton('invite') && !_hideInviteButton && } @@ -388,7 +392,7 @@ class Toolbox extends Component { isOpen = { _overflowMenuVisible } onVisibilityChange = { this._onSetOverflowVisible }>
      { overflowMenuContent }
    @@ -946,7 +950,8 @@ class Toolbox extends Component { return ( @@ -985,7 +990,8 @@ class Toolbox extends Component { onClick = { this._onToolbarOpenVideoQuality } />, this._shouldShowButton('fullscreen') && { && this._renderRecordingButton(), this._shouldShowButton('sharedvideo') && { this._shouldShowButton('etherpad') && _etherpadInitialized && { visible = { this._shouldShowButton('settings') } />, this._shouldShowButton('stats') && { this._shouldShowButton('feedback') && _feedbackConfigured && , this._shouldShowButton('shortcuts') && { return ( { return (
  • diff --git a/react/features/welcome/components/WelcomePage.native.js b/react/features/welcome/components/WelcomePage.native.js index e5feab817..d53a6dc35 100644 --- a/react/features/welcome/components/WelcomePage.native.js +++ b/react/features/welcome/components/WelcomePage.native.js @@ -85,6 +85,7 @@ class WelcomePage extends AbstractWelcomePage { */ render() { const { buttonStyle, pageStyle } = Header; + const roomnameAccLabel = 'welcomepage.accessibilityLabel.roomname'; const { t } = this.props; return ( @@ -101,7 +102,7 @@ class WelcomePage extends AbstractWelcomePage {