chuijs 4.0.3 → 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.
Files changed (258) hide show
  1. package/CHANGELOG.md +536 -0
  2. package/framework/appLayout/default/chui_app_layout.js +361 -303
  3. package/framework/appLayout/default/global_style.css +243 -89
  4. package/framework/appLayout/default/main_theme_style.css +188 -101
  5. package/framework/components/chui_accordion/accordion.js +17 -17
  6. package/framework/components/chui_accordion/styles.css +7 -7
  7. package/framework/components/chui_action_sheet/action_sheet.js +35 -32
  8. package/framework/components/chui_action_sheet/styles.css +10 -4
  9. package/framework/components/chui_actions_bar/actions_bar.js +338 -0
  10. package/framework/components/chui_actions_bar/styles.css +139 -0
  11. package/framework/components/chui_affix/affix.js +4 -4
  12. package/framework/components/chui_affix/styles.css +5 -0
  13. package/framework/components/chui_alert/alert.js +11 -5
  14. package/framework/components/chui_alert/styles.css +7 -0
  15. package/framework/components/chui_avatar/avatar.js +13 -13
  16. package/framework/components/chui_avatar/styles.css +1 -1
  17. package/framework/components/chui_avatar_group/avatar_group.js +4 -4
  18. package/framework/components/chui_avatar_group/styles.css +1 -1
  19. package/framework/components/chui_backtop/backtop.js +25 -2
  20. package/framework/components/chui_backtop/styles.css +21 -0
  21. package/framework/components/chui_badge/badge.js +15 -15
  22. package/framework/components/chui_badge/styles.css +6 -6
  23. package/framework/components/chui_banner/banner.js +222 -0
  24. package/framework/components/chui_banner/styles.css +170 -0
  25. package/framework/components/chui_breadcrumb/styles.css +1 -1
  26. package/framework/components/chui_button/button.js +24 -28
  27. package/framework/components/chui_button/styles.css +5 -5
  28. package/framework/components/chui_calendar/calendar.js +6 -6
  29. package/framework/components/chui_card/card.js +14 -14
  30. package/framework/components/chui_card_scroll/card_scroll.js +169 -0
  31. package/framework/components/chui_card_scroll/styles.css +86 -0
  32. package/framework/components/chui_chat/chat.js +73 -51
  33. package/framework/components/chui_chat/styles.css +18 -7
  34. package/framework/components/chui_clipboard_history/clipboard_history.js +25 -20
  35. package/framework/components/chui_clipboard_history/styles.css +10 -8
  36. package/framework/components/chui_code/code.js +8 -8
  37. package/framework/components/chui_code/styles.css +2 -2
  38. package/framework/components/chui_code_editor/code_editor.js +26 -26
  39. package/framework/components/chui_code_editor/styles.css +3 -3
  40. package/framework/components/chui_command_palette/command_palette.js +29 -29
  41. package/framework/components/chui_command_palette/styles.css +5 -5
  42. package/framework/components/chui_console/console.js +9 -9
  43. package/framework/components/chui_console/styles.css +5 -2
  44. package/framework/components/chui_content_block/content_block.js +2 -2
  45. package/framework/components/chui_context_menu/context_menu.js +162 -54
  46. package/framework/components/chui_context_menu/styles.css +82 -8
  47. package/framework/components/chui_custom_element/custom_element.js +11 -11
  48. package/framework/components/chui_data_grid/data_grid.js +268 -268
  49. package/framework/components/chui_data_grid/styles.css +14 -14
  50. package/framework/components/chui_descriptions/styles.css +1 -1
  51. package/framework/components/chui_details/details.js +12 -12
  52. package/framework/components/chui_details/styles.css +7 -7
  53. package/framework/components/chui_diff_viewer/diff_viewer.js +88 -88
  54. package/framework/components/chui_diff_viewer/styles.css +9 -9
  55. package/framework/components/chui_divider/divider.js +6 -6
  56. package/framework/components/chui_divider/styles.css +2 -2
  57. package/framework/components/chui_drawer/drawer.js +37 -14
  58. package/framework/components/chui_drawer/styles.css +18 -4
  59. package/framework/components/chui_drop_zone/drop_zone.js +6 -6
  60. package/framework/components/chui_drop_zone/styles.css +10 -6
  61. package/framework/components/chui_fieldset/fieldset.js +6 -6
  62. package/framework/components/chui_fieldset/styles.css +5 -5
  63. package/framework/components/chui_file_explorer/file_explorer.js +115 -115
  64. package/framework/components/chui_file_explorer/styles.css +6 -6
  65. package/framework/components/chui_form/form.js +11 -11
  66. package/framework/components/chui_gantt/gantt.js +41 -41
  67. package/framework/components/chui_gantt/styles.css +5 -5
  68. package/framework/components/chui_graphs/graphs.js +82 -46
  69. package/framework/components/chui_graphs/styles.css +26 -5
  70. package/framework/components/chui_hero/hero.js +63 -20
  71. package/framework/components/chui_hero/styles.css +176 -7
  72. package/framework/components/chui_html_block/html_block.js +5 -5
  73. package/framework/components/chui_html_block/styles.css +1 -1
  74. package/framework/components/chui_hx/styles.css +2 -2
  75. package/framework/components/chui_icons/icons.js +7 -7
  76. package/framework/components/chui_icons/styles.css +2 -1
  77. package/framework/components/chui_inputs/chui_check_box/styles.css +12 -3
  78. package/framework/components/chui_inputs/chui_chips/chips.js +92 -31
  79. package/framework/components/chui_inputs/chui_chips/styles.css +28 -5
  80. package/framework/components/chui_inputs/chui_color_picker/color_picker.js +20 -15
  81. package/framework/components/chui_inputs/chui_color_picker/styles.css +7 -7
  82. package/framework/components/chui_inputs/chui_combo_box/combo_box.js +58 -58
  83. package/framework/components/chui_inputs/chui_combo_box/styles.css +9 -9
  84. package/framework/components/chui_inputs/chui_date/date.js +93 -95
  85. package/framework/components/chui_inputs/chui_date/styles.css +8 -8
  86. package/framework/components/chui_inputs/chui_date_range/date_range.js +22 -22
  87. package/framework/components/chui_inputs/chui_date_range/styles.css +3 -3
  88. package/framework/components/chui_inputs/chui_datetime/datetime.js +12 -12
  89. package/framework/components/chui_inputs/chui_datetime/styles.css +3 -3
  90. package/framework/components/chui_inputs/chui_email/email.js +10 -10
  91. package/framework/components/chui_inputs/chui_email/styles.css +6 -6
  92. package/framework/components/chui_inputs/chui_file/file.js +8 -8
  93. package/framework/components/chui_inputs/chui_file/styles.css +12 -9
  94. package/framework/components/chui_inputs/chui_hotkey/hotkey.js +39 -39
  95. package/framework/components/chui_inputs/chui_hotkey/styles.css +6 -6
  96. package/framework/components/chui_inputs/chui_masked/masked.js +44 -44
  97. package/framework/components/chui_inputs/chui_masked/styles.css +5 -5
  98. package/framework/components/chui_inputs/chui_mention/mention.js +13 -13
  99. package/framework/components/chui_inputs/chui_mention/styles.css +14 -8
  100. package/framework/components/chui_inputs/chui_multi_combo_box/multi_combo_box.js +147 -137
  101. package/framework/components/chui_inputs/chui_multi_combo_box/styles.css +14 -8
  102. package/framework/components/chui_inputs/chui_number/number.js +42 -45
  103. package/framework/components/chui_inputs/chui_number/styles.css +6 -6
  104. package/framework/components/chui_inputs/chui_otp/otp.js +32 -32
  105. package/framework/components/chui_inputs/chui_otp/styles.css +5 -5
  106. package/framework/components/chui_inputs/chui_password/password.js +30 -36
  107. package/framework/components/chui_inputs/chui_password/styles.css +7 -7
  108. package/framework/components/chui_inputs/chui_radio_button/styles.css +2 -2
  109. package/framework/components/chui_inputs/chui_rating/rating.js +28 -28
  110. package/framework/components/chui_inputs/chui_rating/styles.css +3 -3
  111. package/framework/components/chui_inputs/chui_select_box/select_box.js +54 -54
  112. package/framework/components/chui_inputs/chui_select_box/styles.css +10 -10
  113. package/framework/components/chui_inputs/chui_slider/slider.js +14 -14
  114. package/framework/components/chui_inputs/chui_slider/styles.css +5 -4
  115. package/framework/components/chui_inputs/chui_text/styles.css +7 -7
  116. package/framework/components/chui_inputs/chui_text/text.js +13 -17
  117. package/framework/components/chui_inputs/chui_text_area/styles.css +8 -8
  118. package/framework/components/chui_inputs/chui_text_area/text_area.js +23 -23
  119. package/framework/components/chui_inputs/chui_time/styles.css +13 -17
  120. package/framework/components/chui_inputs/chui_time/time.js +35 -24
  121. package/framework/components/chui_inputs/chui_toggle/styles.css +10 -3
  122. package/framework/components/chui_inputs/chui_toggle/toggle.js +16 -16
  123. package/framework/components/chui_json_editor/json_editor.js +87 -87
  124. package/framework/components/chui_json_editor/styles.css +5 -5
  125. package/framework/components/chui_json_viewer/json_viewer.js +80 -80
  126. package/framework/components/chui_json_viewer/styles.css +6 -6
  127. package/framework/components/chui_kanban/kanban.js +27 -27
  128. package/framework/components/chui_kanban/styles.css +8 -4
  129. package/framework/components/chui_kbd/styles.css +1 -1
  130. package/framework/components/chui_label/label.js +17 -17
  131. package/framework/components/chui_label/styles.css +1 -1
  132. package/framework/components/chui_link/link.js +9 -9
  133. package/framework/components/chui_link/styles.css +11 -4
  134. package/framework/components/chui_list/list.js +11 -11
  135. package/framework/components/chui_list/styles.css +2 -2
  136. package/framework/components/chui_markdown_editor/markdown_editor.js +66 -66
  137. package/framework/components/chui_markdown_editor/styles.css +5 -5
  138. package/framework/components/chui_media/audio.js +240 -246
  139. package/framework/components/chui_media/audio_styles.css +41 -23
  140. package/framework/components/chui_media/image.js +49 -46
  141. package/framework/components/chui_media/image_compare.js +35 -35
  142. package/framework/components/chui_media/image_compare_styles.css +5 -5
  143. package/framework/components/chui_media/image_styles.css +1 -1
  144. package/framework/components/chui_media/video.js +148 -148
  145. package/framework/components/chui_media/video_styles.css +27 -11
  146. package/framework/components/chui_menu_bar/menu_bar.js +54 -54
  147. package/framework/components/chui_menu_bar/styles.css +10 -10
  148. package/framework/components/chui_message_bar/message_bar.js +551 -0
  149. package/framework/components/chui_message_bar/styles.css +248 -0
  150. package/framework/components/chui_modal/modal.js +37 -13
  151. package/framework/components/chui_notification/notification.js +76 -54
  152. package/framework/components/chui_notification/notification_download.js +26 -81
  153. package/framework/components/chui_notification/notification_download_card.js +115 -0
  154. package/framework/components/chui_notification/notification_download_progress.css +2 -2
  155. package/framework/components/chui_notification/notification_download_progress.js +70 -108
  156. package/framework/components/chui_notification/notification_update.js +31 -31
  157. package/framework/components/chui_notification/status_plate.css +3 -3
  158. package/framework/components/chui_notification/styles.css +6 -1
  159. package/framework/components/chui_notification/styles_download.css +1 -1
  160. package/framework/components/chui_notification/styles_update.css +2 -2
  161. package/framework/components/chui_org_chart/org_chart.js +29 -29
  162. package/framework/components/chui_org_chart/styles.css +2 -2
  163. package/framework/components/chui_pagination/pagination.js +3 -3
  164. package/framework/components/chui_pagination/styles.css +1 -1
  165. package/framework/components/chui_paragraph/styles.css +2 -2
  166. package/framework/components/chui_popover/popover.js +29 -23
  167. package/framework/components/chui_popover/styles.css +1 -1
  168. package/framework/components/chui_popups/popups.js +124 -124
  169. package/framework/components/chui_popups/styles.css +5 -5
  170. package/framework/components/chui_print_button/print_button.js +15 -10
  171. package/framework/components/chui_progress_bar/progress_bar.js +34 -12
  172. package/framework/components/chui_progress_bar/styles.css +4 -4
  173. package/framework/components/chui_progress_ring/progress_ring.js +15 -15
  174. package/framework/components/chui_progress_ring/styles.css +1 -1
  175. package/framework/components/chui_qrcode/qrcode.js +12 -12
  176. package/framework/components/chui_query_builder/query_builder.js +46 -46
  177. package/framework/components/chui_query_builder/styles.css +4 -4
  178. package/framework/components/chui_radio_group/styles.css +1 -1
  179. package/framework/components/chui_result/result.js +15 -15
  180. package/framework/components/chui_result/styles.css +3 -3
  181. package/framework/components/chui_scheduler/scheduler.js +74 -74
  182. package/framework/components/chui_scheduler/styles.css +5 -5
  183. package/framework/components/chui_screen_spinner/screen_spinner.js +167 -0
  184. package/framework/components/chui_screen_spinner/styles.css +49 -0
  185. package/framework/components/chui_segmented_control/segmented_control.js +63 -6
  186. package/framework/components/chui_segmented_control/styles.css +32 -6
  187. package/framework/components/chui_settings/settings.js +45 -46
  188. package/framework/components/chui_settings/styles.css +4 -4
  189. package/framework/components/chui_shortcut_help/shortcut_help.js +32 -34
  190. package/framework/components/chui_sidebar_nav/sidebar_nav.js +98 -29
  191. package/framework/components/chui_sidebar_nav/styles.css +9 -3
  192. package/framework/components/chui_slideshow/slideshow.js +85 -85
  193. package/framework/components/chui_slideshow/styles.css +6 -6
  194. package/framework/components/chui_spinner/spinner.js +10 -10
  195. package/framework/components/chui_split_button/split_button.js +30 -12
  196. package/framework/components/chui_split_button/styles.css +21 -5
  197. package/framework/components/chui_splitter/splitter.js +11 -11
  198. package/framework/components/chui_splitter/styles.css +2 -2
  199. package/framework/components/chui_statistic/statistic.js +47 -47
  200. package/framework/components/chui_status_bar/styles.css +2 -2
  201. package/framework/components/chui_stepper/stepper.js +202 -31
  202. package/framework/components/chui_stepper/styles.css +79 -14
  203. package/framework/components/chui_sticky_bar/sticky_bar.js +44 -13
  204. package/framework/components/chui_sticky_bar/styles.css +10 -8
  205. package/framework/components/chui_tabs/chui_tabs.js +74 -26
  206. package/framework/components/chui_tabs/styles.css +40 -12
  207. package/framework/components/chui_text_editor/styles.css +7 -7
  208. package/framework/components/chui_text_editor/text_editor.js +56 -56
  209. package/framework/components/chui_text_editor/text_editor_panel.js +173 -174
  210. package/framework/components/chui_theme_toggle/theme_toggle.js +21 -5
  211. package/framework/components/chui_timeline/styles.css +3 -1
  212. package/framework/components/chui_toast_queue/styles.css +11 -11
  213. package/framework/components/chui_toast_queue/toast_queue.js +30 -27
  214. package/framework/components/chui_toolbar/styles.css +2 -2
  215. package/framework/components/chui_tooltip/styles.css +2 -2
  216. package/framework/components/chui_tooltip/tooltip.js +3 -3
  217. package/framework/components/chui_tour/styles.css +8 -8
  218. package/framework/components/chui_tour/tour.js +72 -72
  219. package/framework/components/chui_transfer/styles.css +6 -6
  220. package/framework/components/chui_transfer/transfer.js +93 -106
  221. package/framework/components/chui_tree_table/styles.css +4 -4
  222. package/framework/components/chui_tree_table/tree_table.js +45 -45
  223. package/framework/components/chui_tree_view/styles.css +10 -8
  224. package/framework/components/chui_tree_view/tree_view.js +185 -183
  225. package/framework/components/chui_user_bar/styles.css +145 -0
  226. package/framework/components/chui_user_bar/user_bar.js +402 -0
  227. package/framework/components/chui_user_list_bar/styles.css +173 -0
  228. package/framework/components/chui_user_list_bar/user_list_bar.js +485 -0
  229. package/framework/components/chui_watermark/watermark.js +17 -17
  230. package/framework/components/chui_webview/webview.js +9 -9
  231. package/framework/components/chui_write_bar/styles.css +172 -0
  232. package/framework/components/chui_write_bar/write_bar.js +320 -0
  233. package/framework/main_window.js +1234 -0
  234. package/framework/modules/chui_a11y/chui_a11y.js +78 -79
  235. package/framework/modules/chui_animations/animations.js +77 -15
  236. package/framework/modules/chui_animations/motion.js +120 -0
  237. package/framework/modules/chui_animations/styles.css +36 -3
  238. package/framework/modules/chui_functions.js +31 -27
  239. package/framework/modules/chui_highlight/styles.css +13 -10
  240. package/framework/modules/chui_i18n/chui_i18n.js +3 -3
  241. package/framework/modules/chui_i18n/locales/feedback.js +62 -0
  242. package/framework/modules/chui_i18n/locales/navigation.js +4 -0
  243. package/framework/modules/chui_json/chui_json.js +2 -2
  244. package/framework/modules/chui_logger/chui_logger.js +23 -8
  245. package/framework/modules/chui_page/page.js +10 -10
  246. package/framework/modules/chui_palette/palette.js +61 -0
  247. package/framework/modules/chui_qr/chui_qr.js +23 -23
  248. package/framework/modules/chui_scrollbar/chui_scrollbar.js +45 -45
  249. package/framework/modules/chui_scrollbar/styles.css +3 -3
  250. package/framework/modules/chui_services/chui_services.js +8 -8
  251. package/framework/modules/chui_services/desktop.js +77 -71
  252. package/framework/modules/chui_sortable/chui_sortable.js +17 -17
  253. package/framework/modules/chui_validate/chui_validate.js +3 -3
  254. package/framework/tray_bar/chui_menu_items.js +2 -2
  255. package/index.d.ts +266 -34
  256. package/index.js +20 -1168
  257. package/package.json +6 -4
  258. package/framework/components/telegram_bot/chui_telegram_bot.js +0 -191
@@ -1,4 +1,5 @@
1
1
  const { SERVICES_CHANNELS, SERVICES_CALLS, SERVICES_SYNC_CALLS, APP_PATH_NAMES } = require("./chui_channels");
2
+ const { crossFade } = require("../chui_animations/motion");
2
3
 
3
4
  /**
4
5
  * Десктоп-сервисы со стороны страницы: буфер обмена, последние документы, прогресс на иконке
@@ -86,12 +87,16 @@ class Desktop {
86
87
  off: (accelerator = String(), handler = () => {}) => Desktop.#unsubscribe(accelerator, handler),
87
88
  offAll: () => Desktop.#unsubscribeAll(),
88
89
  /** Комбинации, на которые подписано это окно */
89
- get: () => [...Desktop.#shortcut_handlers.keys()],
90
+ get: () => [...Desktop.#shortcutHandlers.keys()],
90
91
  };
91
92
 
92
93
  /**
93
94
  * Тема приложения. Палитры в стилях разложены по `prefers-color-scheme`, поэтому смена
94
- * источника меняет цвета без правок в DOM.
95
+ * источника меняет цвета без правок в DOM: Chromium сам сообщает странице новое значение
96
+ * запроса. Смена идёт кроссфейдом (`crossFade` в `chui_animations/motion`) — обычный
97
+ * CSS-переход на изменение из запроса браузер не запускает, и без него тема переключалась бы
98
+ * кадром. Смену системной схемы при источнике «system» так показать нельзя: её присылает
99
+ * сама система, и снимка «до» в этот момент уже нет.
95
100
  *
96
101
  * ```javascript
97
102
  * await Desktop.theme.set(Desktop.theme.SOURCE.DARK); // 'dark' | 'light' | 'system'
@@ -102,9 +107,10 @@ class Desktop {
102
107
  SOURCE: { SYSTEM: "system", LIGHT: "light", DARK: "dark" },
103
108
  /** @returns {Promise<{theme: string, source: string}>} фактическая тема и выбранный источник */
104
109
  get: () => Desktop.#call("themeGet"),
105
- set: (source = String()) => Desktop.#call("themeSet", String(source)),
110
+ set: (source = String()) =>
111
+ crossFade(() => Desktop.#call("themeSet", String(source)), { waitFor: "(prefers-color-scheme: dark)" }),
106
112
  /** Переключить светлую и тёмную */
107
- toggle: () => Desktop.#call("themeToggle"),
113
+ toggle: () => crossFade(() => Desktop.#call("themeToggle"), { waitFor: "(prefers-color-scheme: dark)" }),
108
114
  /** Подписка на смену темы; возвращает функцию отписки */
109
115
  onChange: (listener = () => {}) => Desktop.#subscribeTheme(listener),
110
116
  };
@@ -227,21 +233,21 @@ class Desktop {
227
233
  };
228
234
 
229
235
  // accelerator → набор обработчиков этого окна
230
- static #shortcut_handlers = new Map();
231
- static #shortcut_event_bound = false;
232
- static #shortcut_bridge_unsubscribe = undefined;
233
- static #theme_handlers = new Set();
234
- static #theme_event_bound = false;
235
- static #theme_bridge_unsubscribe = undefined;
236
- static #locale_handlers = new Set();
237
- static #locale_event_bound = false;
238
- static #locale_bridge_unsubscribe = undefined;
239
- static #history_handlers = new Set();
240
- static #history_event_bound = false;
241
- static #history_bridge_unsubscribe = undefined;
236
+ static #shortcutHandlers = new Map();
237
+ static #shortcutEventBound = false;
238
+ static #shortcutBridgeUnsubscribe = undefined;
239
+ static #themeHandlers = new Set();
240
+ static #themeEventBound = false;
241
+ static #themeBridgeUnsubscribe = undefined;
242
+ static #localeHandlers = new Set();
243
+ static #localeEventBound = false;
244
+ static #localeBridgeUnsubscribe = undefined;
245
+ static #historyHandlers = new Set();
246
+ static #historyEventBound = false;
247
+ static #historyBridgeUnsubscribe = undefined;
242
248
  // Пути приложения, уже полученные значением: `sendSync` останавливает страницу на время
243
249
  // ответа, поэтому за одним и тем же именем в main ходят один раз
244
- static #app_paths = new Map();
250
+ static #appPaths = new Map();
245
251
 
246
252
  static #bridge() {
247
253
  if (typeof window === "undefined" || window.chui === undefined) return undefined;
@@ -281,9 +287,9 @@ class Desktop {
281
287
  * страницы одним и тем же вызовом.
282
288
  */
283
289
  static #appPath(name = String()) {
284
- if (Desktop.#app_paths.has(name)) return Desktop.#app_paths.get(name);
290
+ if (Desktop.#appPaths.has(name)) return Desktop.#appPaths.get(name);
285
291
  const value = Desktop.#inMainProcess() ? Desktop.#appPathInMain(name) : Desktop.#callSync("appPathSync", name);
286
- Desktop.#app_paths.set(name, value);
292
+ Desktop.#appPaths.set(name, value);
287
293
  return value;
288
294
  }
289
295
 
@@ -317,31 +323,31 @@ class Desktop {
317
323
  }
318
324
 
319
325
  static #subscribe(accelerator = String(), handler = () => {}) {
320
- const handlers = Desktop.#shortcut_handlers.get(accelerator) ?? new Set();
326
+ const handlers = Desktop.#shortcutHandlers.get(accelerator) ?? new Set();
321
327
  const first = handlers.size === 0;
322
328
  handlers.add(handler);
323
- Desktop.#shortcut_handlers.set(accelerator, handlers);
324
- if (!Desktop.#shortcut_event_bound) Desktop.#bindShortcutEvent();
329
+ Desktop.#shortcutHandlers.set(accelerator, handlers);
330
+ if (!Desktop.#shortcutEventBound) Desktop.#bindShortcutEvent();
325
331
  // В main клавиша регистрируется один раз на все окна, поэтому подписка — на первую
326
332
  if (first) Desktop.#call("shortcutSubscribe", accelerator);
327
333
  return () => Desktop.#unsubscribe(accelerator, handler);
328
334
  }
329
335
 
330
336
  static #unsubscribe(accelerator = String(), handler = () => {}) {
331
- const handlers = Desktop.#shortcut_handlers.get(accelerator);
337
+ const handlers = Desktop.#shortcutHandlers.get(accelerator);
332
338
  if (handlers === undefined) return Desktop;
333
339
  handlers.delete(handler);
334
340
  if (handlers.size === 0) {
335
- Desktop.#shortcut_handlers.delete(accelerator);
341
+ Desktop.#shortcutHandlers.delete(accelerator);
336
342
  Desktop.#call("shortcutUnsubscribe", accelerator);
337
343
  }
338
- if (Desktop.#shortcut_handlers.size === 0) Desktop.#unbindShortcutEvent();
344
+ if (Desktop.#shortcutHandlers.size === 0) Desktop.#unbindShortcutEvent();
339
345
  return Desktop;
340
346
  }
341
347
 
342
348
  static #unsubscribeAll() {
343
- for (const accelerator of [...Desktop.#shortcut_handlers.keys()]) {
344
- Desktop.#shortcut_handlers.delete(accelerator);
349
+ for (const accelerator of [...Desktop.#shortcutHandlers.keys()]) {
350
+ Desktop.#shortcutHandlers.delete(accelerator);
345
351
  Desktop.#call("shortcutUnsubscribe", accelerator);
346
352
  }
347
353
  Desktop.#unbindShortcutEvent();
@@ -350,16 +356,16 @@ class Desktop {
350
356
 
351
357
  /** Событие приходит из main: сработала глобальная клавиша */
352
358
  static #onShortcutEvent = (accelerator = String()) => {
353
- const handlers = Desktop.#shortcut_handlers.get(accelerator);
359
+ const handlers = Desktop.#shortcutHandlers.get(accelerator);
354
360
  if (handlers === undefined) return;
355
361
  for (const handler of [...handlers]) handler(accelerator);
356
362
  };
357
363
 
358
364
  static #bindShortcutEvent() {
359
- Desktop.#shortcut_event_bound = true;
365
+ Desktop.#shortcutEventBound = true;
360
366
  const services = Desktop.#bridge();
361
367
  if (services !== undefined && typeof services.onShortcut === "function") {
362
- Desktop.#shortcut_bridge_unsubscribe = services.onShortcut(Desktop.#onShortcutEvent);
368
+ Desktop.#shortcutBridgeUnsubscribe = services.onShortcut(Desktop.#onShortcutEvent);
363
369
  return;
364
370
  }
365
371
  const { ipcRenderer } = require("electron");
@@ -367,11 +373,11 @@ class Desktop {
367
373
  }
368
374
 
369
375
  static #unbindShortcutEvent() {
370
- if (!Desktop.#shortcut_event_bound) return;
371
- Desktop.#shortcut_event_bound = false;
372
- if (Desktop.#shortcut_bridge_unsubscribe !== undefined) {
373
- Desktop.#shortcut_bridge_unsubscribe();
374
- Desktop.#shortcut_bridge_unsubscribe = undefined;
376
+ if (!Desktop.#shortcutEventBound) return;
377
+ Desktop.#shortcutEventBound = false;
378
+ if (Desktop.#shortcutBridgeUnsubscribe !== undefined) {
379
+ Desktop.#shortcutBridgeUnsubscribe();
380
+ Desktop.#shortcutBridgeUnsubscribe = undefined;
375
381
  return;
376
382
  }
377
383
  const { ipcRenderer } = require("electron");
@@ -383,28 +389,28 @@ class Desktop {
383
389
  };
384
390
 
385
391
  static #subscribeTheme(listener = () => {}) {
386
- Desktop.#theme_handlers.add(listener);
387
- if (!Desktop.#theme_event_bound) Desktop.#bindThemeEvent();
392
+ Desktop.#themeHandlers.add(listener);
393
+ if (!Desktop.#themeEventBound) Desktop.#bindThemeEvent();
388
394
  return () => Desktop.#unsubscribeTheme(listener);
389
395
  }
390
396
 
391
397
  static #unsubscribeTheme(listener = () => {}) {
392
- Desktop.#theme_handlers.delete(listener);
393
- if (Desktop.#theme_handlers.size === 0) Desktop.#unbindThemeEvent();
398
+ Desktop.#themeHandlers.delete(listener);
399
+ if (Desktop.#themeHandlers.size === 0) Desktop.#unbindThemeEvent();
394
400
  return Desktop;
395
401
  }
396
402
 
397
403
  /** Событие приходит из main: тема изменилась (системой или по выбору пользователя) */
398
404
  static #onThemeEvent = (theme = String()) => {
399
- for (const listener of [...Desktop.#theme_handlers]) listener(theme);
405
+ for (const listener of [...Desktop.#themeHandlers]) listener(theme);
400
406
  };
401
407
 
402
408
  static #bindThemeEvent() {
403
- Desktop.#theme_event_bound = true;
409
+ Desktop.#themeEventBound = true;
404
410
  const bridge = typeof window === "undefined" ? undefined : window.chui;
405
411
  const theme = bridge === undefined ? undefined : bridge.theme;
406
412
  if (theme !== undefined && typeof theme.onChange === "function") {
407
- Desktop.#theme_bridge_unsubscribe = theme.onChange(Desktop.#onThemeEvent);
413
+ Desktop.#themeBridgeUnsubscribe = theme.onChange(Desktop.#onThemeEvent);
408
414
  return;
409
415
  }
410
416
  const { ipcRenderer } = require("electron");
@@ -412,11 +418,11 @@ class Desktop {
412
418
  }
413
419
 
414
420
  static #unbindThemeEvent() {
415
- if (!Desktop.#theme_event_bound) return;
416
- Desktop.#theme_event_bound = false;
417
- if (Desktop.#theme_bridge_unsubscribe !== undefined) {
418
- Desktop.#theme_bridge_unsubscribe();
419
- Desktop.#theme_bridge_unsubscribe = undefined;
421
+ if (!Desktop.#themeEventBound) return;
422
+ Desktop.#themeEventBound = false;
423
+ if (Desktop.#themeBridgeUnsubscribe !== undefined) {
424
+ Desktop.#themeBridgeUnsubscribe();
425
+ Desktop.#themeBridgeUnsubscribe = undefined;
420
426
  return;
421
427
  }
422
428
  const { ipcRenderer } = require("electron");
@@ -428,28 +434,28 @@ class Desktop {
428
434
  };
429
435
 
430
436
  static #subscribeLocale(listener = () => {}) {
431
- Desktop.#locale_handlers.add(listener);
432
- if (!Desktop.#locale_event_bound) Desktop.#bindLocaleEvent();
437
+ Desktop.#localeHandlers.add(listener);
438
+ if (!Desktop.#localeEventBound) Desktop.#bindLocaleEvent();
433
439
  return () => Desktop.#unsubscribeLocale(listener);
434
440
  }
435
441
 
436
442
  static #unsubscribeLocale(listener = () => {}) {
437
- Desktop.#locale_handlers.delete(listener);
438
- if (Desktop.#locale_handlers.size === 0) Desktop.#unbindLocaleEvent();
443
+ Desktop.#localeHandlers.delete(listener);
444
+ if (Desktop.#localeHandlers.size === 0) Desktop.#unbindLocaleEvent();
439
445
  return Desktop;
440
446
  }
441
447
 
442
448
  /** Событие приходит из main: приложение сменило язык */
443
449
  static #onLocaleEvent = (locale = String()) => {
444
- for (const listener of [...Desktop.#locale_handlers]) listener(locale);
450
+ for (const listener of [...Desktop.#localeHandlers]) listener(locale);
445
451
  };
446
452
 
447
453
  static #bindLocaleEvent() {
448
- Desktop.#locale_event_bound = true;
454
+ Desktop.#localeEventBound = true;
449
455
  const bridge = typeof window === "undefined" ? undefined : window.chui;
450
456
  const locale = bridge === undefined ? undefined : bridge.locale;
451
457
  if (locale !== undefined && typeof locale.onChange === "function") {
452
- Desktop.#locale_bridge_unsubscribe = locale.onChange(Desktop.#onLocaleEvent);
458
+ Desktop.#localeBridgeUnsubscribe = locale.onChange(Desktop.#onLocaleEvent);
453
459
  return;
454
460
  }
455
461
  const { ipcRenderer } = require("electron");
@@ -457,11 +463,11 @@ class Desktop {
457
463
  }
458
464
 
459
465
  static #unbindLocaleEvent() {
460
- if (!Desktop.#locale_event_bound) return;
461
- Desktop.#locale_event_bound = false;
462
- if (Desktop.#locale_bridge_unsubscribe !== undefined) {
463
- Desktop.#locale_bridge_unsubscribe();
464
- Desktop.#locale_bridge_unsubscribe = undefined;
466
+ if (!Desktop.#localeEventBound) return;
467
+ Desktop.#localeEventBound = false;
468
+ if (Desktop.#localeBridgeUnsubscribe !== undefined) {
469
+ Desktop.#localeBridgeUnsubscribe();
470
+ Desktop.#localeBridgeUnsubscribe = undefined;
465
471
  return;
466
472
  }
467
473
  const { ipcRenderer } = require("electron");
@@ -473,26 +479,26 @@ class Desktop {
473
479
  };
474
480
 
475
481
  static #subscribeHistory(listener = () => {}) {
476
- Desktop.#history_handlers.add(listener);
477
- if (!Desktop.#history_event_bound) Desktop.#bindHistoryEvent();
482
+ Desktop.#historyHandlers.add(listener);
483
+ if (!Desktop.#historyEventBound) Desktop.#bindHistoryEvent();
478
484
  return () => Desktop.#unsubscribeHistory(listener);
479
485
  }
480
486
 
481
487
  static #unsubscribeHistory(listener = () => {}) {
482
- Desktop.#history_handlers.delete(listener);
483
- if (Desktop.#history_handlers.size === 0) Desktop.#unbindHistoryEvent();
488
+ Desktop.#historyHandlers.delete(listener);
489
+ if (Desktop.#historyHandlers.size === 0) Desktop.#unbindHistoryEvent();
484
490
  return Desktop;
485
491
  }
486
492
 
487
493
  static #onHistoryEvent = (items = []) => {
488
- for (const listener of [...Desktop.#history_handlers]) listener(items);
494
+ for (const listener of [...Desktop.#historyHandlers]) listener(items);
489
495
  };
490
496
 
491
497
  static #bindHistoryEvent() {
492
- Desktop.#history_event_bound = true;
498
+ Desktop.#historyEventBound = true;
493
499
  const services = Desktop.#bridge();
494
500
  if (services !== undefined && typeof services.onClipboardHistory === "function") {
495
- Desktop.#history_bridge_unsubscribe = services.onClipboardHistory(Desktop.#onHistoryEvent);
501
+ Desktop.#historyBridgeUnsubscribe = services.onClipboardHistory(Desktop.#onHistoryEvent);
496
502
  return;
497
503
  }
498
504
  const { ipcRenderer } = require("electron");
@@ -500,11 +506,11 @@ class Desktop {
500
506
  }
501
507
 
502
508
  static #unbindHistoryEvent() {
503
- if (!Desktop.#history_event_bound) return;
504
- Desktop.#history_event_bound = false;
505
- if (Desktop.#history_bridge_unsubscribe !== undefined) {
506
- Desktop.#history_bridge_unsubscribe();
507
- Desktop.#history_bridge_unsubscribe = undefined;
509
+ if (!Desktop.#historyEventBound) return;
510
+ Desktop.#historyEventBound = false;
511
+ if (Desktop.#historyBridgeUnsubscribe !== undefined) {
512
+ Desktop.#historyBridgeUnsubscribe();
513
+ Desktop.#historyBridgeUnsubscribe = undefined;
508
514
  return;
509
515
  }
510
516
  const { ipcRenderer } = require("electron");
@@ -31,14 +31,14 @@ class Sortable {
31
31
  };
32
32
 
33
33
  #container = undefined;
34
- #item_selector = undefined;
35
- #handle_selector = undefined;
34
+ #itemSelector = undefined;
35
+ #handleSelector = undefined;
36
36
  #axis = Sortable.AXIS.Y;
37
- #on_reorder = undefined;
37
+ #onReorder = undefined;
38
38
  #enabled = true;
39
39
  #source = undefined;
40
40
  #before = undefined;
41
- #order_before = [];
41
+ #orderBefore = [];
42
42
  // Точка отсчёта отмены: сюда возвращает cancel(), и только здесь, а не в каждой перестановке
43
43
  #baseline = [];
44
44
  #bound = false;
@@ -55,10 +55,10 @@ class Sortable {
55
55
  ) {
56
56
  setStyles(__dirname + "/styles.css", "chUiJS_Sortable");
57
57
  this.#container = container;
58
- this.#item_selector = options.itemSelector === undefined ? "*" : options.itemSelector;
59
- this.#handle_selector = options.handleSelector;
58
+ this.#itemSelector = options.itemSelector === undefined ? "*" : options.itemSelector;
59
+ this.#handleSelector = options.handleSelector;
60
60
  this.#axis = options.axis === undefined ? Sortable.AXIS.Y : options.axis;
61
- this.#on_reorder = options.onReorder;
61
+ this.#onReorder = options.onReorder;
62
62
  this.#enabled = options.enabled !== false;
63
63
  this.#container.addEventListener("dragstart", this.#onDragStart);
64
64
  this.#container.addEventListener("dragover", this.#onDragOver);
@@ -89,7 +89,7 @@ class Sortable {
89
89
 
90
90
  /** Порядок изменился после последней перестановки (или с момента refresh) */
91
91
  isChanged() {
92
- return !Sortable.#sameOrder(this.#order_before, this.#items());
92
+ return !Sortable.#sameOrder(this.#orderBefore, this.#items());
93
93
  }
94
94
 
95
95
  // SET
@@ -108,8 +108,8 @@ class Sortable {
108
108
  if (item.getAttribute("tabindex") === null) item.setAttribute("tabindex", "0");
109
109
  item.classList.add("sortable_item");
110
110
  }
111
- this.#order_before = this.#items();
112
- this.#baseline = [...this.#order_before];
111
+ this.#orderBefore = this.#items();
112
+ this.#baseline = [...this.#orderBefore];
113
113
  return this;
114
114
  }
115
115
 
@@ -118,7 +118,7 @@ class Sortable {
118
118
  // Возврат идёт к точке отсчёта refresh(), а не к порядку последней перестановки: иначе
119
119
  // отмена после перетаскивания ничего бы не делала (порядок сверялся бы сам с собой)
120
120
  for (const item of this.#baseline) this.#container.appendChild(item);
121
- this.#order_before = this.#items();
121
+ this.#orderBefore = this.#items();
122
122
  return this;
123
123
  }
124
124
 
@@ -140,15 +140,15 @@ class Sortable {
140
140
  // === ВНУТРЕННЕЕ ===
141
141
  // Только прямые дети контейнера: вложенные списки сортируются своим Sortable
142
142
  #items() {
143
- return [...this.#container.children].filter((child) => child.matches(this.#item_selector));
143
+ return [...this.#container.children].filter((child) => child.matches(this.#itemSelector));
144
144
  }
145
145
 
146
146
  #itemFromEvent(event) {
147
147
  const target = event.target instanceof Element ? event.target : null;
148
148
  if (target === null) return null;
149
- const item = target.closest(this.#item_selector);
149
+ const item = target.closest(this.#itemSelector);
150
150
  if (item === null || item.parentElement !== this.#container) return null;
151
- if (this.#handle_selector !== undefined && target.closest(this.#handle_selector) === null) return null;
151
+ if (this.#handleSelector !== undefined && target.closest(this.#handleSelector) === null) return null;
152
152
  return item;
153
153
  }
154
154
 
@@ -173,9 +173,9 @@ class Sortable {
173
173
  const before = this.#before;
174
174
  this.#source = undefined;
175
175
  this.#before = undefined;
176
- if (Sortable.#sameOrder(this.#order_before, this.#items())) return;
177
- this.#order_before = this.#items();
178
- if (this.#on_reorder !== undefined) this.#on_reorder(this.getOrder(), { source: source, before: before });
176
+ if (Sortable.#sameOrder(this.#orderBefore, this.#items())) return;
177
+ this.#orderBefore = this.#items();
178
+ if (this.#onReorder !== undefined) this.#onReorder(this.getOrder(), { source: source, before: before });
179
179
  }
180
180
 
181
181
  static #sameOrder(left = [], right = []) {
@@ -76,9 +76,9 @@ function check(value, rules = {}) {
76
76
  if (rules.max !== undefined && (Number.isNaN(number) || number > rules.max)) return fail("max", rules);
77
77
  if (rules.minLength !== undefined && text.length < rules.minLength) return fail("minLength", rules);
78
78
  if (rules.maxLength !== undefined && text.length > rules.maxLength) return fail("maxLength", rules);
79
- const is_email = rules.type === "email";
80
- const pattern = is_email ? EMAIL_PATTERN : rules.pattern;
81
- if (pattern !== undefined && !new RegExp(pattern).test(text)) return fail(is_email ? "email" : "pattern", rules);
79
+ const isEmail = rules.type === "email";
80
+ const pattern = isEmail ? EMAIL_PATTERN : rules.pattern;
81
+ if (pattern !== undefined && !new RegExp(pattern).test(text)) return fail(isEmail ? "email" : "pattern", rules);
82
82
  if (typeof rules.validate === "function") {
83
83
  const custom = rules.validate(value);
84
84
  if (custom !== undefined && custom !== null && custom !== true) {
@@ -5,8 +5,8 @@ class MenuItem {
5
5
  separator() {
6
6
  return { type: "separator" };
7
7
  }
8
- submenu(title = String(), submenu_list = Array()) {
9
- return { label: title, submenu: submenu_list };
8
+ submenu(title = String(), submenuList = Array()) {
9
+ return { label: title, submenu: submenuList };
10
10
  }
11
11
  radio(title = String(), checked = Boolean(), action = () => {}) {
12
12
  return { label: title, type: "radio", checked: checked, click: action };