chuijs 4.0.2 → 4.0.4
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +597 -0
- package/README.md +43 -644
- package/framework/appLayout/default/chui_app_layout.js +602 -496
- package/framework/appLayout/default/global_style.css +288 -97
- package/framework/appLayout/default/main_theme_style.css +188 -101
- package/framework/components/chui_accordion/accordion.js +38 -35
- package/framework/components/chui_accordion/styles.css +13 -12
- package/framework/components/chui_action_sheet/action_sheet.js +93 -64
- package/framework/components/chui_action_sheet/styles.css +12 -5
- package/framework/components/chui_actions_bar/actions_bar.js +338 -0
- package/framework/components/chui_actions_bar/styles.css +139 -0
- package/framework/components/chui_affix/affix.js +16 -11
- package/framework/components/chui_affix/styles.css +5 -0
- package/framework/components/chui_alert/alert.js +34 -19
- package/framework/components/chui_alert/styles.css +7 -0
- package/framework/components/chui_avatar/avatar.js +36 -35
- package/framework/components/chui_avatar/styles.css +1 -1
- package/framework/components/chui_avatar_group/avatar_group.js +25 -23
- package/framework/components/chui_avatar_group/styles.css +1 -1
- package/framework/components/chui_backtop/backtop.js +60 -21
- package/framework/components/chui_backtop/styles.css +21 -0
- package/framework/components/chui_badge/badge.js +30 -28
- package/framework/components/chui_badge/styles.css +6 -6
- package/framework/components/chui_banner/banner.js +222 -0
- package/framework/components/chui_banner/styles.css +170 -0
- package/framework/components/chui_breadcrumb/breadcrumb.js +15 -13
- package/framework/components/chui_breadcrumb/styles.css +1 -1
- package/framework/components/chui_button/button.js +52 -36
- package/framework/components/chui_button/styles.css +7 -7
- package/framework/components/chui_calendar/calendar.js +18 -16
- package/framework/components/chui_card/card.js +52 -32
- package/framework/components/chui_card_scroll/card_scroll.js +169 -0
- package/framework/components/chui_card_scroll/styles.css +86 -0
- package/framework/components/chui_chat/chat.js +140 -79
- package/framework/components/chui_chat/styles.css +18 -7
- package/framework/components/chui_clipboard_history/clipboard_history.js +53 -39
- package/framework/components/chui_clipboard_history/styles.css +13 -9
- package/framework/components/chui_code/code.js +10 -10
- package/framework/components/chui_code/styles.css +4 -4
- package/framework/components/chui_code_editor/code_editor.js +73 -57
- package/framework/components/chui_code_editor/styles.css +6 -5
- package/framework/components/chui_command_palette/command_palette.js +87 -64
- package/framework/components/chui_command_palette/styles.css +5 -5
- package/framework/components/chui_console/console.js +13 -13
- package/framework/components/chui_console/styles.css +6 -3
- package/framework/components/chui_content_block/content_block.js +35 -21
- package/framework/components/chui_content_block/styles.css +2 -2
- package/framework/components/chui_context_menu/context_menu.js +171 -58
- package/framework/components/chui_context_menu/styles.css +82 -8
- package/framework/components/chui_custom_element/custom_element.js +25 -18
- package/framework/components/chui_data_grid/data_grid.js +633 -471
- package/framework/components/chui_data_grid/styles.css +24 -22
- package/framework/components/chui_descriptions/descriptions.js +34 -17
- package/framework/components/chui_descriptions/styles.css +1 -1
- package/framework/components/chui_details/details.js +42 -36
- package/framework/components/chui_details/styles.css +12 -11
- package/framework/components/chui_diff_viewer/diff_viewer.js +172 -147
- package/framework/components/chui_diff_viewer/styles.css +10 -10
- package/framework/components/chui_divider/divider.js +19 -17
- package/framework/components/chui_divider/styles.css +2 -2
- package/framework/components/chui_drawer/drawer.js +63 -38
- package/framework/components/chui_drawer/styles.css +18 -4
- package/framework/components/chui_drop_zone/drop_zone.js +37 -27
- package/framework/components/chui_drop_zone/styles.css +10 -6
- package/framework/components/chui_empty_state/empty_state.js +20 -15
- package/framework/components/chui_fieldset/fieldset.js +40 -23
- package/framework/components/chui_fieldset/styles.css +6 -6
- package/framework/components/chui_file_explorer/file_explorer.js +260 -189
- package/framework/components/chui_file_explorer/styles.css +8 -7
- package/framework/components/chui_form/form.js +40 -28
- package/framework/components/chui_form/styles.css +1 -1
- package/framework/components/chui_gantt/gantt.js +102 -78
- package/framework/components/chui_gantt/styles.css +5 -5
- package/framework/components/chui_graphs/graphs.js +376 -239
- package/framework/components/chui_graphs/styles.css +27 -6
- package/framework/components/chui_hero/hero.js +98 -37
- package/framework/components/chui_hero/styles.css +176 -7
- package/framework/components/chui_html_block/html_block.js +8 -8
- package/framework/components/chui_html_block/styles.css +3 -3
- package/framework/components/chui_hx/hx.js +3 -3
- package/framework/components/chui_hx/styles.css +13 -6
- package/framework/components/chui_icons/icons.js +2115 -2115
- package/framework/components/chui_icons/styles.css +4 -3
- package/framework/components/chui_inputs/chui_check_box/check_box.js +31 -19
- package/framework/components/chui_inputs/chui_check_box/styles.css +30 -21
- package/framework/components/chui_inputs/chui_chips/chips.js +141 -70
- package/framework/components/chui_inputs/chui_chips/styles.css +32 -7
- package/framework/components/chui_inputs/chui_color_picker/color_picker.js +55 -38
- package/framework/components/chui_inputs/chui_color_picker/styles.css +7 -7
- package/framework/components/chui_inputs/chui_combo_box/combo_box.js +127 -109
- package/framework/components/chui_inputs/chui_combo_box/styles.css +23 -21
- package/framework/components/chui_inputs/chui_date/date.js +161 -127
- package/framework/components/chui_inputs/chui_date/styles.css +20 -19
- package/framework/components/chui_inputs/chui_date_range/date_range.js +61 -50
- package/framework/components/chui_inputs/chui_date_range/styles.css +3 -3
- package/framework/components/chui_inputs/chui_datetime/datetime.js +47 -39
- package/framework/components/chui_inputs/chui_datetime/styles.css +3 -3
- package/framework/components/chui_inputs/chui_email/email.js +48 -36
- package/framework/components/chui_inputs/chui_email/styles.css +11 -11
- package/framework/components/chui_inputs/chui_file/file.js +71 -44
- package/framework/components/chui_inputs/chui_file/styles.css +23 -19
- package/framework/components/chui_inputs/chui_hotkey/hotkey.js +101 -76
- package/framework/components/chui_inputs/chui_hotkey/styles.css +6 -6
- package/framework/components/chui_inputs/chui_masked/masked.js +83 -72
- package/framework/components/chui_inputs/chui_masked/styles.css +5 -5
- package/framework/components/chui_inputs/chui_mention/mention.js +87 -40
- package/framework/components/chui_inputs/chui_mention/styles.css +14 -8
- package/framework/components/chui_inputs/chui_multi_combo_box/multi_combo_box.js +242 -212
- package/framework/components/chui_inputs/chui_multi_combo_box/styles.css +23 -15
- package/framework/components/chui_inputs/chui_number/number.js +84 -70
- package/framework/components/chui_inputs/chui_number/styles.css +13 -13
- package/framework/components/chui_inputs/chui_otp/otp.js +71 -62
- package/framework/components/chui_inputs/chui_otp/styles.css +5 -5
- package/framework/components/chui_inputs/chui_password/password.js +72 -56
- package/framework/components/chui_inputs/chui_password/styles.css +15 -15
- package/framework/components/chui_inputs/chui_radio_button/radio_button.js +37 -25
- package/framework/components/chui_inputs/chui_radio_button/styles.css +22 -22
- package/framework/components/chui_inputs/chui_rating/rating.js +54 -50
- package/framework/components/chui_inputs/chui_rating/styles.css +3 -3
- package/framework/components/chui_inputs/chui_select_box/select_box.js +132 -108
- package/framework/components/chui_inputs/chui_select_box/styles.css +21 -21
- package/framework/components/chui_inputs/chui_slider/slider.js +41 -38
- package/framework/components/chui_inputs/chui_slider/styles.css +7 -5
- package/framework/components/chui_inputs/chui_text/styles.css +14 -14
- package/framework/components/chui_inputs/chui_text/text.js +69 -52
- package/framework/components/chui_inputs/chui_text_area/styles.css +14 -14
- package/framework/components/chui_inputs/chui_text_area/text_area.js +59 -36
- package/framework/components/chui_inputs/chui_time/styles.css +18 -20
- package/framework/components/chui_inputs/chui_time/time.js +71 -49
- package/framework/components/chui_inputs/chui_toggle/styles.css +13 -6
- package/framework/components/chui_inputs/chui_toggle/toggle.js +27 -27
- package/framework/components/chui_json_editor/json_editor.js +137 -127
- package/framework/components/chui_json_editor/styles.css +5 -5
- package/framework/components/chui_json_viewer/json_viewer.js +133 -114
- package/framework/components/chui_json_viewer/styles.css +9 -8
- package/framework/components/chui_kanban/kanban.js +78 -60
- package/framework/components/chui_kanban/styles.css +8 -4
- package/framework/components/chui_kbd/kbd.js +12 -10
- package/framework/components/chui_kbd/styles.css +1 -1
- package/framework/components/chui_label/label.js +31 -29
- package/framework/components/chui_label/styles.css +3 -3
- package/framework/components/chui_link/link.js +36 -29
- package/framework/components/chui_link/styles.css +11 -4
- package/framework/components/chui_list/list.js +42 -38
- package/framework/components/chui_list/styles.css +4 -3
- package/framework/components/chui_markdown_editor/markdown_editor.js +125 -109
- package/framework/components/chui_markdown_editor/styles.css +5 -5
- package/framework/components/chui_media/audio.js +457 -364
- package/framework/components/chui_media/audio_styles.css +74 -37
- package/framework/components/chui_media/image.js +99 -64
- package/framework/components/chui_media/image_compare.js +86 -55
- package/framework/components/chui_media/image_compare_styles.css +5 -5
- package/framework/components/chui_media/image_styles.css +4 -4
- package/framework/components/chui_media/video.js +264 -171
- package/framework/components/chui_media/video_styles.css +57 -24
- package/framework/components/chui_menu_bar/menu_bar.js +67 -65
- package/framework/components/chui_menu_bar/styles.css +14 -12
- package/framework/components/chui_message_bar/message_bar.js +551 -0
- package/framework/components/chui_message_bar/styles.css +248 -0
- package/framework/components/chui_modal/modal.js +81 -56
- package/framework/components/chui_modal/styles.css +3 -2
- package/framework/components/chui_notification/notification.js +107 -69
- package/framework/components/chui_notification/notification_download.js +28 -77
- package/framework/components/chui_notification/notification_download_card.js +115 -0
- package/framework/components/chui_notification/notification_download_progress.css +5 -4
- package/framework/components/chui_notification/notification_download_progress.js +73 -105
- package/framework/components/chui_notification/notification_update.js +44 -37
- package/framework/components/chui_notification/status_plate.css +3 -3
- package/framework/components/chui_notification/status_plate.js +2 -2
- package/framework/components/chui_notification/styles.css +6 -1
- package/framework/components/chui_notification/styles_download.css +2 -2
- package/framework/components/chui_notification/styles_update.css +3 -3
- package/framework/components/chui_org_chart/org_chart.js +101 -62
- package/framework/components/chui_org_chart/styles.css +2 -2
- package/framework/components/chui_pagination/pagination.js +65 -30
- package/framework/components/chui_pagination/styles.css +1 -1
- package/framework/components/chui_paragraph/paragraph.js +2 -2
- package/framework/components/chui_paragraph/styles.css +3 -3
- package/framework/components/chui_popover/popover.js +77 -50
- package/framework/components/chui_popover/styles.css +1 -1
- package/framework/components/chui_popups/popups.js +210 -181
- package/framework/components/chui_popups/styles.css +7 -7
- package/framework/components/chui_print_button/print_button.js +48 -33
- package/framework/components/chui_progress_bar/progress_bar.js +49 -19
- package/framework/components/chui_progress_bar/styles.css +6 -6
- package/framework/components/chui_progress_ring/progress_ring.js +32 -30
- package/framework/components/chui_progress_ring/styles.css +1 -1
- package/framework/components/chui_qrcode/qrcode.js +85 -41
- package/framework/components/chui_query_builder/query_builder.js +263 -170
- package/framework/components/chui_query_builder/styles.css +4 -4
- package/framework/components/chui_radio_group/radio_group.js +36 -26
- package/framework/components/chui_radio_group/styles.css +2 -2
- package/framework/components/chui_result/result.js +41 -31
- package/framework/components/chui_result/styles.css +3 -3
- package/framework/components/chui_scheduler/scheduler.js +126 -104
- package/framework/components/chui_scheduler/styles.css +11 -7
- package/framework/components/chui_screen_spinner/screen_spinner.js +167 -0
- package/framework/components/chui_screen_spinner/styles.css +49 -0
- package/framework/components/chui_segmented_control/segmented_control.js +90 -27
- package/framework/components/chui_segmented_control/styles.css +32 -6
- package/framework/components/chui_settings/settings.js +160 -87
- package/framework/components/chui_settings/styles.css +4 -4
- package/framework/components/chui_shortcut_help/shortcut_help.js +82 -61
- package/framework/components/chui_sidebar_nav/sidebar_nav.js +132 -53
- package/framework/components/chui_sidebar_nav/styles.css +9 -3
- package/framework/components/chui_skeleton/skeleton.js +29 -24
- package/framework/components/chui_slideshow/slideshow.js +122 -103
- package/framework/components/chui_slideshow/styles.css +22 -16
- package/framework/components/chui_spinner/spinner.js +17 -17
- package/framework/components/chui_spinner/styles.css +0 -1
- package/framework/components/chui_split_button/split_button.js +53 -30
- package/framework/components/chui_split_button/styles.css +22 -6
- package/framework/components/chui_splitter/splitter.js +46 -39
- package/framework/components/chui_splitter/styles.css +2 -2
- package/framework/components/chui_statistic/statistic.js +111 -84
- package/framework/components/chui_status_bar/status_bar.js +11 -9
- package/framework/components/chui_status_bar/styles.css +2 -2
- package/framework/components/chui_stepper/stepper.js +230 -54
- package/framework/components/chui_stepper/styles.css +79 -14
- package/framework/components/chui_sticky_bar/sticky_bar.js +53 -17
- package/framework/components/chui_sticky_bar/styles.css +11 -7
- package/framework/components/chui_tabs/chui_tabs.js +100 -46
- package/framework/components/chui_tabs/styles.css +43 -15
- package/framework/components/chui_text_editor/styles.css +24 -23
- package/framework/components/chui_text_editor/text_editor.js +103 -79
- package/framework/components/chui_text_editor/text_editor_panel.js +428 -367
- package/framework/components/chui_theme_toggle/theme_toggle.js +46 -25
- package/framework/components/chui_timeline/styles.css +3 -1
- package/framework/components/chui_timeline/timeline.js +14 -12
- package/framework/components/chui_toast_queue/styles.css +11 -11
- package/framework/components/chui_toast_queue/toast_queue.js +82 -73
- package/framework/components/chui_toolbar/styles.css +2 -2
- package/framework/components/chui_toolbar/toolbar.js +20 -13
- package/framework/components/chui_tooltip/styles.css +2 -2
- package/framework/components/chui_tooltip/tooltip.js +40 -27
- package/framework/components/chui_tour/styles.css +12 -7
- package/framework/components/chui_tour/tour.js +132 -98
- package/framework/components/chui_transfer/styles.css +8 -7
- package/framework/components/chui_transfer/transfer.js +143 -123
- package/framework/components/chui_tree_table/styles.css +4 -4
- package/framework/components/chui_tree_table/tree_table.js +88 -74
- package/framework/components/chui_tree_view/styles.css +14 -10
- package/framework/components/chui_tree_view/tree_view.js +298 -253
- package/framework/components/chui_user_bar/styles.css +145 -0
- package/framework/components/chui_user_bar/user_bar.js +402 -0
- package/framework/components/chui_user_list_bar/styles.css +173 -0
- package/framework/components/chui_user_list_bar/user_list_bar.js +485 -0
- package/framework/components/chui_watermark/watermark.js +41 -33
- package/framework/components/chui_webview/styles.css +2 -2
- package/framework/components/chui_webview/webview.js +64 -52
- package/framework/components/chui_write_bar/styles.css +172 -0
- package/framework/components/chui_write_bar/write_bar.js +320 -0
- package/framework/main_window.js +1234 -0
- package/framework/modules/chui_a11y/chui_a11y.js +153 -123
- package/framework/modules/chui_animations/animations.js +105 -43
- package/framework/modules/chui_animations/motion.js +120 -0
- package/framework/modules/chui_animations/styles.css +37 -4
- package/framework/modules/chui_bridge/preload.js +36 -25
- package/framework/modules/chui_functions.js +69 -63
- package/framework/modules/chui_highlight/chui_highlight.js +25 -22
- package/framework/modules/chui_highlight/styles.css +13 -10
- package/framework/modules/chui_i18n/chui_i18n.js +12 -10
- package/framework/modules/chui_i18n/locales/a11y.js +5 -5
- package/framework/modules/chui_i18n/locales/app_layout.js +5 -5
- package/framework/modules/chui_i18n/locales/calendar.js +3 -3
- package/framework/modules/chui_i18n/locales/common.js +3 -3
- package/framework/modules/chui_i18n/locales/data.js +36 -26
- package/framework/modules/chui_i18n/locales/editors.js +40 -13
- package/framework/modules/chui_i18n/locales/feedback.js +65 -3
- package/framework/modules/chui_i18n/locales/forms.js +8 -8
- package/framework/modules/chui_i18n/locales/graphics.js +8 -8
- package/framework/modules/chui_i18n/locales/media.js +4 -4
- package/framework/modules/chui_i18n/locales/navigation.js +12 -8
- package/framework/modules/chui_i18n/locales/validate.js +3 -3
- package/framework/modules/chui_json/chui_json.js +11 -11
- package/framework/modules/chui_layout/chui_layout.js +12 -10
- package/framework/modules/chui_logger/chui_logger.js +47 -28
- package/framework/modules/chui_page/page.js +39 -33
- package/framework/modules/chui_palette/palette.js +61 -0
- package/framework/modules/chui_qr/chui_qr.js +179 -88
- package/framework/modules/chui_scrollbar/chui_scrollbar.js +79 -68
- package/framework/modules/chui_scrollbar/styles.css +4 -2
- package/framework/modules/chui_services/chui_channels.js +27 -13
- package/framework/modules/chui_services/chui_services.js +47 -39
- package/framework/modules/chui_services/desktop.js +108 -101
- package/framework/modules/chui_sortable/chui_sortable.js +33 -28
- package/framework/modules/chui_validate/chui_validate.js +10 -7
- package/framework/tray_bar/chui_menu_items.js +136 -46
- package/index.d.ts +5046 -0
- package/index.js +199 -1254
- package/package.json +81 -68
- package/framework/components/telegram_bot/chui_telegram_bot.js +0 -184
|
@@ -14,44 +14,50 @@
|
|
|
14
14
|
* (popup_button_ok и подобным) tabindex выставляет вызывающий компонент.
|
|
15
15
|
*/
|
|
16
16
|
const FOCUSABLE_SELECTOR = [
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
17
|
+
"a[href]",
|
|
18
|
+
"button:not([disabled])",
|
|
19
|
+
"input:not([disabled])",
|
|
20
|
+
"select:not([disabled])",
|
|
21
|
+
"textarea:not([disabled])",
|
|
22
22
|
'[contenteditable="true"]',
|
|
23
23
|
'[tabindex]:not([tabindex="-1"])',
|
|
24
|
-
].join(
|
|
24
|
+
].join(", ");
|
|
25
25
|
|
|
26
26
|
class OverlayA11y {
|
|
27
27
|
// Стек открытых слоёв: нужен, чтобы вложенный слой не снимал фон-инерт у родителя
|
|
28
28
|
static #stack = [];
|
|
29
|
-
static #
|
|
29
|
+
static #labelledCounter = 0;
|
|
30
30
|
|
|
31
31
|
#element = undefined;
|
|
32
32
|
#role = "dialog";
|
|
33
33
|
#label = undefined;
|
|
34
|
-
#
|
|
35
|
-
#
|
|
36
|
-
#
|
|
37
|
-
#
|
|
38
|
-
#
|
|
39
|
-
|
|
40
|
-
constructor(
|
|
41
|
-
|
|
42
|
-
|
|
43
|
-
|
|
34
|
+
#labelNode = undefined;
|
|
35
|
+
#describedBy = undefined;
|
|
36
|
+
#onEscape = undefined;
|
|
37
|
+
#previousFocus = undefined;
|
|
38
|
+
#isOpen = false;
|
|
39
|
+
|
|
40
|
+
constructor(
|
|
41
|
+
element,
|
|
42
|
+
options = {
|
|
43
|
+
role: String(),
|
|
44
|
+
label: String(),
|
|
45
|
+
labelNode: undefined,
|
|
46
|
+
describedBy: undefined,
|
|
47
|
+
onEscape: undefined,
|
|
48
|
+
}
|
|
49
|
+
) {
|
|
44
50
|
this.#element = element;
|
|
45
51
|
if (options.role !== undefined) this.#role = options.role;
|
|
46
52
|
this.#label = options.label;
|
|
47
|
-
this.#
|
|
48
|
-
this.#
|
|
49
|
-
this.#
|
|
53
|
+
this.#labelNode = options.labelNode;
|
|
54
|
+
this.#describedBy = options.describedBy;
|
|
55
|
+
this.#onEscape = options.onEscape;
|
|
50
56
|
this.#applyAria();
|
|
51
57
|
}
|
|
52
58
|
|
|
53
59
|
get isOpen() {
|
|
54
|
-
return this.#
|
|
60
|
+
return this.#isOpen;
|
|
55
61
|
}
|
|
56
62
|
|
|
57
63
|
setLabel(text = String()) {
|
|
@@ -60,18 +66,18 @@ class OverlayA11y {
|
|
|
60
66
|
}
|
|
61
67
|
|
|
62
68
|
open() {
|
|
63
|
-
if (this.#
|
|
64
|
-
this.#
|
|
69
|
+
if (this.#isOpen) return;
|
|
70
|
+
this.#isOpen = true;
|
|
65
71
|
OverlayA11y.#stack.push(this);
|
|
66
|
-
this.#
|
|
72
|
+
this.#previousFocus = document.activeElement;
|
|
67
73
|
OverlayA11y.#applyInert();
|
|
68
74
|
document.addEventListener("keydown", this.#keydownEvent, true);
|
|
69
75
|
this.#focusFirst();
|
|
70
76
|
}
|
|
71
77
|
|
|
72
78
|
close() {
|
|
73
|
-
if (!this.#
|
|
74
|
-
this.#
|
|
79
|
+
if (!this.#isOpen) return;
|
|
80
|
+
this.#isOpen = false;
|
|
75
81
|
const index = OverlayA11y.#stack.indexOf(this);
|
|
76
82
|
if (index !== -1) OverlayA11y.#stack.splice(index, 1);
|
|
77
83
|
document.removeEventListener("keydown", this.#keydownEvent, true);
|
|
@@ -83,21 +89,21 @@ class OverlayA11y {
|
|
|
83
89
|
const element = this.#element;
|
|
84
90
|
element.setAttribute("role", this.#role);
|
|
85
91
|
element.setAttribute("aria-modal", "true");
|
|
86
|
-
if (this.#
|
|
87
|
-
element.setAttribute("aria-labelledby", OverlayA11y.#ensureId(this.#
|
|
92
|
+
if (this.#labelNode !== undefined) {
|
|
93
|
+
element.setAttribute("aria-labelledby", OverlayA11y.#ensureId(this.#labelNode));
|
|
88
94
|
element.removeAttribute("aria-label");
|
|
89
95
|
} else if (this.#label !== undefined) {
|
|
90
96
|
element.setAttribute("aria-label", this.#label);
|
|
91
97
|
}
|
|
92
|
-
if (this.#
|
|
93
|
-
element.setAttribute("aria-describedby", OverlayA11y.#ensureId(this.#
|
|
98
|
+
if (this.#describedBy !== undefined) {
|
|
99
|
+
element.setAttribute("aria-describedby", OverlayA11y.#ensureId(this.#describedBy));
|
|
94
100
|
}
|
|
95
101
|
}
|
|
96
102
|
|
|
97
103
|
static #ensureId(element) {
|
|
98
104
|
if (element.id === undefined || element.id === "") {
|
|
99
|
-
OverlayA11y.#
|
|
100
|
-
element.id = "chui_a11y_node_" + OverlayA11y.#
|
|
105
|
+
OverlayA11y.#labelledCounter += 1;
|
|
106
|
+
element.id = "chui_a11y_node_" + OverlayA11y.#labelledCounter;
|
|
101
107
|
}
|
|
102
108
|
return element.id;
|
|
103
109
|
}
|
|
@@ -125,8 +131,9 @@ class OverlayA11y {
|
|
|
125
131
|
}
|
|
126
132
|
|
|
127
133
|
#focusables() {
|
|
128
|
-
return [...this.#element.querySelectorAll(FOCUSABLE_SELECTOR)]
|
|
129
|
-
|
|
134
|
+
return [...this.#element.querySelectorAll(FOCUSABLE_SELECTOR)].filter(
|
|
135
|
+
(element) => element.offsetWidth > 0 || element.offsetHeight > 0 || element === document.activeElement
|
|
136
|
+
);
|
|
130
137
|
}
|
|
131
138
|
|
|
132
139
|
#focusFirst() {
|
|
@@ -139,8 +146,8 @@ class OverlayA11y {
|
|
|
139
146
|
}
|
|
140
147
|
|
|
141
148
|
#restoreFocus() {
|
|
142
|
-
const previous = this.#
|
|
143
|
-
this.#
|
|
149
|
+
const previous = this.#previousFocus;
|
|
150
|
+
this.#previousFocus = undefined;
|
|
144
151
|
if (previous !== undefined && previous !== null && document.body.contains(previous)) previous.focus();
|
|
145
152
|
}
|
|
146
153
|
|
|
@@ -170,12 +177,12 @@ class OverlayA11y {
|
|
|
170
177
|
if (event.key === "Escape") {
|
|
171
178
|
event.preventDefault();
|
|
172
179
|
event.stopPropagation();
|
|
173
|
-
if (this.#
|
|
180
|
+
if (this.#onEscape !== undefined) this.#onEscape();
|
|
174
181
|
else this.close();
|
|
175
182
|
return;
|
|
176
183
|
}
|
|
177
184
|
if (event.key === "Tab") this.#trapFocus(event);
|
|
178
|
-
}
|
|
185
|
+
};
|
|
179
186
|
}
|
|
180
187
|
|
|
181
188
|
/**
|
|
@@ -194,16 +201,22 @@ function makeKeyboardButton(element, role = "button") {
|
|
|
194
201
|
return element;
|
|
195
202
|
}
|
|
196
203
|
|
|
197
|
-
exports.OverlayA11y = OverlayA11y
|
|
198
|
-
exports.makeKeyboardButton = makeKeyboardButton
|
|
199
|
-
exports.A11Y_FOCUSABLE_SELECTOR = FOCUSABLE_SELECTOR
|
|
204
|
+
exports.OverlayA11y = OverlayA11y;
|
|
205
|
+
exports.makeKeyboardButton = makeKeyboardButton;
|
|
206
|
+
exports.A11Y_FOCUSABLE_SELECTOR = FOCUSABLE_SELECTOR;
|
|
200
207
|
|
|
201
208
|
// Подсветка активного пункта меню/опции, когда фокус остаётся на поле ввода
|
|
202
209
|
const ACTIVE_CLASS = "chui_a11y_active";
|
|
203
210
|
|
|
204
|
-
const isVisible = (element) =>
|
|
205
|
-
|
|
206
|
-
|
|
211
|
+
const isVisible = (element) =>
|
|
212
|
+
element.offsetWidth > 0 || element.offsetHeight > 0 || element === document.activeElement;
|
|
213
|
+
const isDisabled = (element) =>
|
|
214
|
+
element.disabled === true ||
|
|
215
|
+
element.getAttribute("aria-disabled") === "true" ||
|
|
216
|
+
(element.className !== undefined &&
|
|
217
|
+
String(element.className)
|
|
218
|
+
.split(" ")
|
|
219
|
+
.some((name) => name.endsWith("_disabled")));
|
|
207
220
|
|
|
208
221
|
/**
|
|
209
222
|
* Клавиатура для всплывающих меню (ContextMenu, MenuBar, меню шапки).
|
|
@@ -213,30 +226,37 @@ const isDisabled = (element) => element.disabled === true || element.getAttribut
|
|
|
213
226
|
*/
|
|
214
227
|
class MenuKeyboard {
|
|
215
228
|
#container = undefined;
|
|
216
|
-
#
|
|
229
|
+
#itemSelector = undefined;
|
|
217
230
|
#role = "menu";
|
|
218
|
-
#
|
|
219
|
-
#
|
|
220
|
-
#
|
|
221
|
-
#
|
|
222
|
-
#
|
|
223
|
-
#
|
|
224
|
-
#
|
|
231
|
+
#itemRole = "menuitem";
|
|
232
|
+
#submenuSelector = undefined;
|
|
233
|
+
#onSubmenuOpen = undefined;
|
|
234
|
+
#isSubmenu = false;
|
|
235
|
+
#typeBuffer = "";
|
|
236
|
+
#typeAt = 0;
|
|
237
|
+
#onEscape = undefined;
|
|
225
238
|
#trigger = undefined;
|
|
226
|
-
#
|
|
227
|
-
|
|
228
|
-
constructor(
|
|
229
|
-
|
|
230
|
-
|
|
231
|
-
|
|
239
|
+
#triggerBound = false;
|
|
240
|
+
|
|
241
|
+
constructor(
|
|
242
|
+
container,
|
|
243
|
+
options = {
|
|
244
|
+
role: String(),
|
|
245
|
+
itemRole: String(),
|
|
246
|
+
itemSelector: String(),
|
|
247
|
+
submenuSelector: String(),
|
|
248
|
+
onEscape: undefined,
|
|
249
|
+
trigger: undefined,
|
|
250
|
+
}
|
|
251
|
+
) {
|
|
232
252
|
this.#container = container;
|
|
233
253
|
if (options.role !== undefined) this.#role = options.role;
|
|
234
|
-
if (options.itemRole !== undefined) this.#
|
|
235
|
-
this.#
|
|
236
|
-
this.#
|
|
237
|
-
this.#
|
|
238
|
-
this.#
|
|
239
|
-
this.#
|
|
254
|
+
if (options.itemRole !== undefined) this.#itemRole = options.itemRole;
|
|
255
|
+
this.#itemSelector = options.itemSelector;
|
|
256
|
+
this.#submenuSelector = options.submenuSelector;
|
|
257
|
+
this.#onEscape = options.onEscape;
|
|
258
|
+
this.#onSubmenuOpen = options.onSubmenuOpen;
|
|
259
|
+
this.#isSubmenu = options.submenu === true;
|
|
240
260
|
this.#trigger = options.trigger;
|
|
241
261
|
container.setAttribute("role", this.#role);
|
|
242
262
|
this.refresh();
|
|
@@ -245,17 +265,17 @@ class MenuKeyboard {
|
|
|
245
265
|
// содержит контейнер (строка подменю — предок своей панели), то это тот же путь события:
|
|
246
266
|
// второй обработчик на предке обработал бы одну клавишу дважды — пункт подменю срабатывал бы
|
|
247
267
|
// от одного Enter дважды, а одна стрелка перескакивала бы через пункт.
|
|
248
|
-
this.#
|
|
249
|
-
if (this.#
|
|
268
|
+
this.#triggerBound = options.trigger !== undefined && options.trigger.contains(container) === false;
|
|
269
|
+
if (this.#triggerBound) options.trigger.addEventListener("keydown", this.#keydownEvent);
|
|
250
270
|
}
|
|
251
271
|
|
|
252
272
|
/** Перечитать пункты: роли, tabindex, состояние триггера (в том числе в закрытом меню) */
|
|
253
273
|
refresh() {
|
|
254
274
|
for (const item of this.#allItems()) {
|
|
255
|
-
if (item.getAttribute("role") === null) item.setAttribute("role", this.#
|
|
275
|
+
if (item.getAttribute("role") === null) item.setAttribute("role", this.#itemRole);
|
|
256
276
|
if (item.getAttribute("tabindex") === null) item.setAttribute("tabindex", "-1");
|
|
257
277
|
if (isDisabled(item)) item.setAttribute("aria-disabled", "true");
|
|
258
|
-
if (this.#
|
|
278
|
+
if (this.#submenuSelector !== undefined && item.querySelector(this.#submenuSelector) !== null) {
|
|
259
279
|
item.setAttribute("aria-haspopup", "true");
|
|
260
280
|
}
|
|
261
281
|
}
|
|
@@ -276,8 +296,9 @@ class MenuKeyboard {
|
|
|
276
296
|
|
|
277
297
|
// Все пункты своего уровня (и скрытые — им тоже нужны роли и tabindex)
|
|
278
298
|
#allItems() {
|
|
279
|
-
return [...this.#container.querySelectorAll(this.#
|
|
280
|
-
|
|
299
|
+
return [...this.#container.querySelectorAll(this.#itemSelector)].filter(
|
|
300
|
+
(item) => item.closest('[role="menu"]') === this.#container
|
|
301
|
+
);
|
|
281
302
|
}
|
|
282
303
|
|
|
283
304
|
#focusItem(index) {
|
|
@@ -290,7 +311,7 @@ class MenuKeyboard {
|
|
|
290
311
|
}
|
|
291
312
|
|
|
292
313
|
#activeIndex(items) {
|
|
293
|
-
return items.findIndex(item => item === document.activeElement || item.classList.contains(ACTIVE_CLASS));
|
|
314
|
+
return items.findIndex((item) => item === document.activeElement || item.classList.contains(ACTIVE_CLASS));
|
|
294
315
|
}
|
|
295
316
|
|
|
296
317
|
// Для навигации — только видимые пункты своего уровня
|
|
@@ -309,7 +330,7 @@ class MenuKeyboard {
|
|
|
309
330
|
}
|
|
310
331
|
|
|
311
332
|
#openOrClick(item) {
|
|
312
|
-
if (this.#
|
|
333
|
+
if (this.#submenuSelector !== undefined && item.querySelector(this.#submenuSelector) !== null) {
|
|
313
334
|
this.#openSubmenu(item);
|
|
314
335
|
return;
|
|
315
336
|
}
|
|
@@ -317,11 +338,11 @@ class MenuKeyboard {
|
|
|
317
338
|
}
|
|
318
339
|
|
|
319
340
|
#openSubmenu(row) {
|
|
320
|
-
if (this.#
|
|
321
|
-
const submenu = row.querySelector(this.#
|
|
341
|
+
if (this.#submenuSelector === undefined) return;
|
|
342
|
+
const submenu = row.querySelector(this.#submenuSelector);
|
|
322
343
|
if (submenu === null) return;
|
|
323
|
-
if (this.#
|
|
324
|
-
const first = [...submenu.querySelectorAll(this.#
|
|
344
|
+
if (this.#onSubmenuOpen !== undefined) this.#onSubmenuOpen(row);
|
|
345
|
+
const first = [...submenu.querySelectorAll(this.#itemSelector)].filter(isVisible)[0];
|
|
325
346
|
if (first !== undefined) first.focus();
|
|
326
347
|
}
|
|
327
348
|
|
|
@@ -360,20 +381,20 @@ class MenuKeyboard {
|
|
|
360
381
|
break;
|
|
361
382
|
}
|
|
362
383
|
case "ArrowLeft": {
|
|
363
|
-
if (!this.#
|
|
384
|
+
if (!this.#isSubmenu) break;
|
|
364
385
|
event.preventDefault();
|
|
365
|
-
if (this.#
|
|
386
|
+
if (this.#onEscape !== undefined) this.#onEscape();
|
|
366
387
|
if (this.#trigger !== undefined && document.body.contains(this.#trigger)) this.#trigger.focus();
|
|
367
388
|
break;
|
|
368
389
|
}
|
|
369
390
|
case "Escape":
|
|
370
391
|
event.preventDefault();
|
|
371
392
|
event.stopPropagation();
|
|
372
|
-
if (this.#
|
|
393
|
+
if (this.#onEscape !== undefined) this.#onEscape();
|
|
373
394
|
if (this.#trigger !== undefined && document.body.contains(this.#trigger)) this.#trigger.focus();
|
|
374
395
|
break;
|
|
375
396
|
case "Tab":
|
|
376
|
-
if (this.#
|
|
397
|
+
if (this.#onEscape !== undefined) this.#onEscape();
|
|
377
398
|
break;
|
|
378
399
|
default:
|
|
379
400
|
// Type-ahead: набор букв переводит фокус на пункт с таким началом
|
|
@@ -382,19 +403,19 @@ class MenuKeyboard {
|
|
|
382
403
|
}
|
|
383
404
|
break;
|
|
384
405
|
}
|
|
385
|
-
}
|
|
406
|
+
};
|
|
386
407
|
|
|
387
408
|
#typeahead(char) {
|
|
388
409
|
const now = Date.now();
|
|
389
410
|
// Буфер сбрасывается, если с прошлой буквы прошло больше 700 мс
|
|
390
|
-
this.#
|
|
391
|
-
this.#
|
|
411
|
+
this.#typeBuffer = (now - this.#typeAt > 700 ? "" : this.#typeBuffer) + char.toLowerCase();
|
|
412
|
+
this.#typeAt = now;
|
|
392
413
|
const items = this.#items();
|
|
393
414
|
if (items.length === 0) return;
|
|
394
415
|
const current = this.#activeIndex(items);
|
|
395
416
|
// Ищем по кругу, начиная со следующего пункта
|
|
396
417
|
const ordered = current === -1 ? items : [...items.slice(current + 1), ...items.slice(0, current + 1)];
|
|
397
|
-
const match = ordered.find(item => this.#label(item).startsWith(this.#
|
|
418
|
+
const match = ordered.find((item) => this.#label(item).startsWith(this.#typeBuffer));
|
|
398
419
|
if (match !== undefined) this.#focusItem(items.indexOf(match));
|
|
399
420
|
}
|
|
400
421
|
|
|
@@ -412,7 +433,8 @@ class MenuKeyboard {
|
|
|
412
433
|
|
|
413
434
|
destroy() {
|
|
414
435
|
this.#container.removeEventListener("keydown", this.#keydownEvent);
|
|
415
|
-
if (this.#trigger !== undefined && this.#
|
|
436
|
+
if (this.#trigger !== undefined && this.#triggerBound)
|
|
437
|
+
this.#trigger.removeEventListener("keydown", this.#keydownEvent);
|
|
416
438
|
}
|
|
417
439
|
}
|
|
418
440
|
|
|
@@ -424,21 +446,28 @@ class MenuKeyboard {
|
|
|
424
446
|
class ComboboxKeyboard {
|
|
425
447
|
#input = undefined;
|
|
426
448
|
#dropdown = undefined;
|
|
427
|
-
#
|
|
428
|
-
#
|
|
429
|
-
#
|
|
449
|
+
#optionSelector = undefined;
|
|
450
|
+
#onEscape = undefined;
|
|
451
|
+
#onOpen = undefined;
|
|
430
452
|
#active = undefined;
|
|
431
|
-
#
|
|
432
|
-
|
|
433
|
-
constructor(
|
|
434
|
-
|
|
435
|
-
|
|
453
|
+
#selectionState = undefined;
|
|
454
|
+
|
|
455
|
+
constructor(
|
|
456
|
+
input,
|
|
457
|
+
options = {
|
|
458
|
+
dropdown: undefined,
|
|
459
|
+
optionSelector: String(),
|
|
460
|
+
onEscape: undefined,
|
|
461
|
+
onOpen: undefined,
|
|
462
|
+
selectionState: undefined,
|
|
463
|
+
}
|
|
464
|
+
) {
|
|
436
465
|
this.#input = input;
|
|
437
466
|
this.#dropdown = options.dropdown;
|
|
438
|
-
this.#
|
|
439
|
-
this.#
|
|
440
|
-
this.#
|
|
441
|
-
this.#
|
|
467
|
+
this.#optionSelector = options.optionSelector;
|
|
468
|
+
this.#onEscape = options.onEscape;
|
|
469
|
+
this.#onOpen = options.onOpen;
|
|
470
|
+
this.#selectionState = options.selectionState;
|
|
442
471
|
input.setAttribute("role", "combobox");
|
|
443
472
|
input.setAttribute("aria-haspopup", "listbox");
|
|
444
473
|
input.setAttribute("aria-expanded", "false");
|
|
@@ -455,7 +484,8 @@ class ComboboxKeyboard {
|
|
|
455
484
|
// Роли и id нужны всем опциям, даже когда дропдаун ещё закрыт
|
|
456
485
|
for (const option of this.#allOptions()) {
|
|
457
486
|
if (option.getAttribute("role") === null) option.setAttribute("role", "option");
|
|
458
|
-
if (option.id === undefined || option.id === "")
|
|
487
|
+
if (option.id === undefined || option.id === "")
|
|
488
|
+
option.id = "chui_a11y_option_" + Math.random().toString(36).slice(2, 9);
|
|
459
489
|
}
|
|
460
490
|
this.#applyActive();
|
|
461
491
|
}
|
|
@@ -473,21 +503,21 @@ class ComboboxKeyboard {
|
|
|
473
503
|
|
|
474
504
|
#allOptions() {
|
|
475
505
|
if (this.#dropdown === undefined) return [];
|
|
476
|
-
return [...this.#dropdown.querySelectorAll(this.#
|
|
506
|
+
return [...this.#dropdown.querySelectorAll(this.#optionSelector)];
|
|
477
507
|
}
|
|
478
508
|
|
|
479
509
|
#options() {
|
|
480
|
-
return this.#allOptions().filter(option => isVisible(option) && !isDisabled(option));
|
|
510
|
+
return this.#allOptions().filter((option) => isVisible(option) && !isDisabled(option));
|
|
481
511
|
}
|
|
482
512
|
|
|
483
513
|
#applyActive() {
|
|
484
514
|
// Множественный выбор: `aria-selected` показывает выбор, а не наведение (его несёт
|
|
485
515
|
// `aria-activedescendant`) — иначе пометка «под курсором» выглядела бы как отметка.
|
|
486
|
-
const
|
|
516
|
+
const hasSelection = typeof this.#selectionState === "function";
|
|
487
517
|
for (const option of this.#allOptions()) {
|
|
488
518
|
const active = option === this.#active;
|
|
489
519
|
option.classList.toggle(ACTIVE_CLASS, active);
|
|
490
|
-
const selected =
|
|
520
|
+
const selected = hasSelection ? this.#selectionState(option) === true : active;
|
|
491
521
|
option.setAttribute("aria-selected", selected ? "true" : "false");
|
|
492
522
|
}
|
|
493
523
|
if (this.#active === undefined) this.#input.removeAttribute("aria-activedescendant");
|
|
@@ -511,7 +541,7 @@ class ComboboxKeyboard {
|
|
|
511
541
|
case "ArrowDown":
|
|
512
542
|
case "ArrowUp": {
|
|
513
543
|
event.preventDefault();
|
|
514
|
-
if (this.#input.getAttribute("aria-expanded") !== "true" && this.#
|
|
544
|
+
if (this.#input.getAttribute("aria-expanded") !== "true" && this.#onOpen !== undefined) this.#onOpen();
|
|
515
545
|
this.#move(event.key === "ArrowDown" ? 1 : -1);
|
|
516
546
|
break;
|
|
517
547
|
}
|
|
@@ -541,13 +571,13 @@ class ComboboxKeyboard {
|
|
|
541
571
|
this.#applyActive();
|
|
542
572
|
break;
|
|
543
573
|
}
|
|
544
|
-
if (this.#
|
|
574
|
+
if (this.#onEscape !== undefined) this.#onEscape();
|
|
545
575
|
break;
|
|
546
576
|
}
|
|
547
577
|
default:
|
|
548
578
|
break;
|
|
549
579
|
}
|
|
550
|
-
}
|
|
580
|
+
};
|
|
551
581
|
|
|
552
582
|
destroy() {
|
|
553
583
|
this.#input.removeEventListener("keydown", this.#keydownEvent);
|
|
@@ -563,26 +593,26 @@ class ComboboxKeyboard {
|
|
|
563
593
|
*/
|
|
564
594
|
class RovingKeyboard {
|
|
565
595
|
#container = undefined;
|
|
566
|
-
#
|
|
567
|
-
#
|
|
596
|
+
#itemSelector = undefined;
|
|
597
|
+
#onClick = undefined;
|
|
568
598
|
|
|
569
599
|
constructor(container, options = { itemSelector: String() }) {
|
|
570
600
|
this.#container = container;
|
|
571
|
-
this.#
|
|
601
|
+
this.#itemSelector = options.itemSelector;
|
|
572
602
|
this.refresh();
|
|
573
|
-
this.#
|
|
574
|
-
const item = event.target instanceof Element ? event.target.closest(this.#
|
|
603
|
+
this.#onClick = (event) => {
|
|
604
|
+
const item = event.target instanceof Element ? event.target.closest(this.#itemSelector) : null;
|
|
575
605
|
if (item === null || !this.#container.contains(item)) return;
|
|
576
606
|
this.#applyStop(item);
|
|
577
607
|
};
|
|
578
608
|
container.addEventListener("keydown", this.#keydownEvent);
|
|
579
|
-
container.addEventListener("click", this.#
|
|
609
|
+
container.addEventListener("click", this.#onClick);
|
|
580
610
|
}
|
|
581
611
|
|
|
582
612
|
/** Перечитать пункты: остановка остаётся на прежнем, если он ещё доступен */
|
|
583
613
|
refresh() {
|
|
584
614
|
const visible = this.#items();
|
|
585
|
-
const current = visible.find(item => item.getAttribute("tabindex") === "0");
|
|
615
|
+
const current = visible.find((item) => item.getAttribute("tabindex") === "0");
|
|
586
616
|
// Панель может быть ещё не в документе (размеры нулевые) — тогда остановку получает
|
|
587
617
|
// первый пункт: без неё группа целиком выпала бы из обхода Tab
|
|
588
618
|
const fallback = visible[0] === undefined ? this.#allItems()[0] : visible[0];
|
|
@@ -593,18 +623,18 @@ class RovingKeyboard {
|
|
|
593
623
|
|
|
594
624
|
// Все пункты группы, включая скрытые: tabindex проставляется и до появления панели на экране
|
|
595
625
|
#allItems() {
|
|
596
|
-
return [...this.#container.querySelectorAll(this.#
|
|
626
|
+
return [...this.#container.querySelectorAll(this.#itemSelector)];
|
|
597
627
|
}
|
|
598
628
|
|
|
599
629
|
// Пункты, по которым ходит клавиатура: видимые и не запрещённые
|
|
600
630
|
#items() {
|
|
601
|
-
return this.#allItems().filter(item => !isDisabled(item) && isVisible(item));
|
|
631
|
+
return this.#allItems().filter((item) => !isDisabled(item) && isVisible(item));
|
|
602
632
|
}
|
|
603
633
|
|
|
604
634
|
#activeIndex(items) {
|
|
605
|
-
const focused = items.findIndex(item => item === document.activeElement);
|
|
635
|
+
const focused = items.findIndex((item) => item === document.activeElement);
|
|
606
636
|
if (focused !== -1) return focused;
|
|
607
|
-
return items.findIndex(item => item.getAttribute("tabindex") === "0");
|
|
637
|
+
return items.findIndex((item) => item.getAttribute("tabindex") === "0");
|
|
608
638
|
}
|
|
609
639
|
|
|
610
640
|
#applyStop(item) {
|
|
@@ -655,14 +685,14 @@ class RovingKeyboard {
|
|
|
655
685
|
|
|
656
686
|
destroy() {
|
|
657
687
|
this.#container.removeEventListener("keydown", this.#keydownEvent);
|
|
658
|
-
this.#container.removeEventListener("click", this.#
|
|
688
|
+
this.#container.removeEventListener("click", this.#onClick);
|
|
659
689
|
}
|
|
660
690
|
}
|
|
661
691
|
|
|
662
|
-
exports.MenuKeyboard = MenuKeyboard
|
|
663
|
-
exports.ComboboxKeyboard = ComboboxKeyboard
|
|
664
|
-
exports.RovingKeyboard = RovingKeyboard
|
|
665
|
-
exports.A11Y_ACTIVE_CLASS = ACTIVE_CLASS
|
|
692
|
+
exports.MenuKeyboard = MenuKeyboard;
|
|
693
|
+
exports.ComboboxKeyboard = ComboboxKeyboard;
|
|
694
|
+
exports.RovingKeyboard = RovingKeyboard;
|
|
695
|
+
exports.A11Y_ACTIVE_CLASS = ACTIVE_CLASS;
|
|
666
696
|
|
|
667
697
|
/**
|
|
668
698
|
* Перенести фокус на следующий (или предыдущий) видимый фокусируемый элемент страницы.
|
|
@@ -670,7 +700,7 @@ exports.A11Y_ACTIVE_CLASS = ACTIVE_CLASS
|
|
|
670
700
|
* браузер уведёт фокус в `body`, а не к следующему полю. `skip` — узел или поддерево,
|
|
671
701
|
* которое в обходе не участвует (например, сам список).
|
|
672
702
|
*/
|
|
673
|
-
function moveFocusAway(from, options = {backwards: false, skip: undefined}) {
|
|
703
|
+
function moveFocusAway(from, options = { backwards: false, skip: undefined }) {
|
|
674
704
|
const nodes = [...document.querySelectorAll(FOCUSABLE_SELECTOR)]
|
|
675
705
|
.filter((node) => node.disabled !== true)
|
|
676
706
|
.filter((node) => isVisible(node))
|
|
@@ -684,4 +714,4 @@ function moveFocusAway(from, options = {backwards: false, skip: undefined}) {
|
|
|
684
714
|
return true;
|
|
685
715
|
}
|
|
686
716
|
|
|
687
|
-
exports.moveFocusAway = moveFocusAway
|
|
717
|
+
exports.moveFocusAway = moveFocusAway;
|