@uzum-tech/ui 1.10.0 → 1.11.0

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 (91) hide show
  1. package/dist/index.js +1269 -207
  2. package/dist/index.prod.js +3 -3
  3. package/es/_internal/index.d.ts +2 -0
  4. package/es/_internal/index.js +1 -0
  5. package/es/_internal/safe-top-scrollbar/index.d.ts +2 -0
  6. package/es/_internal/safe-top-scrollbar/index.js +1 -0
  7. package/es/_internal/safe-top-scrollbar/src/SafeTopScrollbar.d.ts +356 -0
  8. package/es/_internal/safe-top-scrollbar/src/SafeTopScrollbar.js +708 -0
  9. package/es/_internal/safe-top-scrollbar/src/styles/index.cssr.d.ts +2 -0
  10. package/es/_internal/safe-top-scrollbar/src/styles/index.cssr.js +80 -0
  11. package/es/_internal/safe-top-scrollbar/src/styles/rtl.cssr.d.ts +2 -0
  12. package/es/_internal/safe-top-scrollbar/src/styles/rtl.cssr.js +10 -0
  13. package/es/_internal/safe-top-scrollbar/styles/common.d.ts +7 -0
  14. package/es/_internal/safe-top-scrollbar/styles/common.js +7 -0
  15. package/es/_internal/safe-top-scrollbar/styles/dark.d.ts +3 -0
  16. package/es/_internal/safe-top-scrollbar/styles/dark.js +8 -0
  17. package/es/_internal/safe-top-scrollbar/styles/index.d.ts +4 -0
  18. package/es/_internal/safe-top-scrollbar/styles/index.js +3 -0
  19. package/es/_internal/safe-top-scrollbar/styles/light.d.ts +18 -0
  20. package/es/_internal/safe-top-scrollbar/styles/light.js +12 -0
  21. package/es/_internal/safe-top-scrollbar/styles/rtl.d.ts +3 -0
  22. package/es/_internal/safe-top-scrollbar/styles/rtl.js +6 -0
  23. package/es/chat/src/Chat.d.ts +14 -1
  24. package/es/chat/src/Chat.js +5 -0
  25. package/es/chat/src/ChatListItems.js +16 -1
  26. package/es/chat/src/ChatParts/ChatAttachment.js +31 -3
  27. package/es/chat/src/ChatParts/MainArea.js +68 -62
  28. package/es/chat/src/interface.d.ts +6 -2
  29. package/es/components.d.ts +1 -0
  30. package/es/components.js +1 -0
  31. package/es/config-provider/src/internal-interface.d.ts +2 -0
  32. package/es/drawer/src/Drawer.d.ts +18 -0
  33. package/es/drawer/src/Drawer.js +28 -26
  34. package/es/drawer/src/DrawerBodyWrapper.d.ts +8 -0
  35. package/es/drawer/src/DrawerBodyWrapper.js +36 -8
  36. package/es/infinite-scroll/src/InfiniteScroll.d.ts +16 -0
  37. package/es/infinite-scroll/src/InfiniteScroll.js +48 -12
  38. package/es/safe-top-scrollbar/index.d.ts +2 -0
  39. package/es/safe-top-scrollbar/index.js +1 -0
  40. package/es/safe-top-scrollbar/src/SafeTopScrollbar.d.ts +177 -0
  41. package/es/safe-top-scrollbar/src/SafeTopScrollbar.js +38 -0
  42. package/es/themes/dark.js +2 -0
  43. package/es/themes/light.js +2 -0
  44. package/es/version.d.ts +1 -1
  45. package/es/version.js +1 -1
  46. package/lib/_internal/index.d.ts +2 -0
  47. package/lib/_internal/index.js +4 -1
  48. package/lib/_internal/safe-top-scrollbar/index.d.ts +2 -0
  49. package/lib/_internal/safe-top-scrollbar/index.js +9 -0
  50. package/lib/_internal/safe-top-scrollbar/src/SafeTopScrollbar.d.ts +356 -0
  51. package/lib/_internal/safe-top-scrollbar/src/SafeTopScrollbar.js +714 -0
  52. package/lib/_internal/safe-top-scrollbar/src/styles/index.cssr.d.ts +2 -0
  53. package/lib/_internal/safe-top-scrollbar/src/styles/index.cssr.js +85 -0
  54. package/lib/_internal/safe-top-scrollbar/src/styles/rtl.cssr.d.ts +2 -0
  55. package/lib/_internal/safe-top-scrollbar/src/styles/rtl.cssr.js +15 -0
  56. package/lib/_internal/safe-top-scrollbar/styles/common.d.ts +7 -0
  57. package/lib/_internal/safe-top-scrollbar/styles/common.js +10 -0
  58. package/lib/_internal/safe-top-scrollbar/styles/dark.d.ts +3 -0
  59. package/lib/_internal/safe-top-scrollbar/styles/dark.js +10 -0
  60. package/lib/_internal/safe-top-scrollbar/styles/index.d.ts +4 -0
  61. package/lib/_internal/safe-top-scrollbar/styles/index.js +12 -0
  62. package/lib/_internal/safe-top-scrollbar/styles/light.d.ts +18 -0
  63. package/lib/_internal/safe-top-scrollbar/styles/light.js +16 -0
  64. package/lib/_internal/safe-top-scrollbar/styles/rtl.d.ts +3 -0
  65. package/lib/_internal/safe-top-scrollbar/styles/rtl.js +12 -0
  66. package/lib/chat/src/Chat.d.ts +14 -1
  67. package/lib/chat/src/Chat.js +5 -0
  68. package/lib/chat/src/ChatListItems.js +16 -1
  69. package/lib/chat/src/ChatParts/ChatAttachment.js +30 -2
  70. package/lib/chat/src/ChatParts/MainArea.js +68 -62
  71. package/lib/chat/src/interface.d.ts +6 -2
  72. package/lib/components.d.ts +1 -0
  73. package/lib/components.js +1 -0
  74. package/lib/config-provider/src/internal-interface.d.ts +2 -0
  75. package/lib/drawer/src/Drawer.d.ts +18 -0
  76. package/lib/drawer/src/Drawer.js +28 -26
  77. package/lib/drawer/src/DrawerBodyWrapper.d.ts +8 -0
  78. package/lib/drawer/src/DrawerBodyWrapper.js +36 -8
  79. package/lib/infinite-scroll/src/InfiniteScroll.d.ts +16 -0
  80. package/lib/infinite-scroll/src/InfiniteScroll.js +47 -11
  81. package/lib/safe-top-scrollbar/index.d.ts +2 -0
  82. package/lib/safe-top-scrollbar/index.js +9 -0
  83. package/lib/safe-top-scrollbar/src/SafeTopScrollbar.d.ts +177 -0
  84. package/lib/safe-top-scrollbar/src/SafeTopScrollbar.js +41 -0
  85. package/lib/themes/dark.js +5 -0
  86. package/lib/themes/light.js +5 -0
  87. package/lib/version.d.ts +1 -1
  88. package/lib/version.js +1 -1
  89. package/package.json +6 -6
  90. package/volar.d.ts +1 -0
  91. package/web-types.json +67 -2
@@ -0,0 +1,2 @@
1
+ declare const _default: import("css-render").CNode;
2
+ export default _default;
@@ -0,0 +1,85 @@
1
+ "use strict";
2
+
3
+ Object.defineProperty(exports, "__esModule", {
4
+ value: true
5
+ });
6
+ const fade_in_cssr_1 = require("../../../../_styles/transitions/fade-in.cssr");
7
+ const cssr_1 = require("../../../../_utils/cssr");
8
+ // vars:
9
+ // --u-scrollbar-bezier
10
+ // --u-scrollbar-color
11
+ // --u-scrollbar-color-hover
12
+ // --u-scrollbar-width
13
+ // --u-scrollbar-height
14
+ // --u-scrollbar-border-radius
15
+ // --u-scrollbar-rail-inset-horizontal
16
+ // --u-scrollbar-rail-inset-vertical
17
+ // --u-scrollbar-rail-color
18
+ exports.default = (0, cssr_1.cB)('safe-top-scrollbar', `
19
+ overflow: hidden;
20
+ position: relative;
21
+ z-index: auto;
22
+ height: 100%;
23
+ width: 100%;
24
+ `, [(0, cssr_1.c)('>', [(0, cssr_1.cB)('scrollbar-container', `
25
+ width: 100%;
26
+ overflow: scroll;
27
+ height: 100%;
28
+ min-height: inherit;
29
+ max-height: inherit;
30
+ scrollbar-width: none;
31
+ `, [(0, cssr_1.c)('&::-webkit-scrollbar, &::-webkit-scrollbar-track-piece, &::-webkit-scrollbar-thumb', `
32
+ width: 0;
33
+ height: 0;
34
+ display: none;
35
+ `), (0, cssr_1.c)('>', [
36
+ // We can't set overflow hidden since it affects positioning.
37
+ (0, cssr_1.cB)('scrollbar-content', `
38
+ box-sizing: border-box;
39
+ min-width: 100%;
40
+ `)])])]), (0, cssr_1.c)('>, +', [(0, cssr_1.cB)('scrollbar-rail', `
41
+ position: absolute;
42
+ pointer-events: none;
43
+ user-select: none;
44
+ background: var(--u-scrollbar-rail-color);
45
+ -webkit-user-select: none;
46
+ `, [(0, cssr_1.cM)('horizontal', `
47
+ height: var(--u-scrollbar-height);
48
+ `, [(0, cssr_1.c)('>', [(0, cssr_1.cE)('scrollbar', `
49
+ height: var(--u-scrollbar-height);
50
+ border-radius: var(--u-scrollbar-border-radius);
51
+ right: 0;
52
+ `)])]), (0, cssr_1.cM)('horizontal--top', `
53
+ top: var(--u-scrollbar-rail-top-horizontal-top);
54
+ right: var(--u-scrollbar-rail-right-horizontal-top);
55
+ bottom: var(--u-scrollbar-rail-bottom-horizontal-top);
56
+ left: var(--u-scrollbar-rail-left-horizontal-top);
57
+ `), (0, cssr_1.cM)('horizontal--bottom', `
58
+ top: var(--u-scrollbar-rail-top-horizontal-bottom);
59
+ right: var(--u-scrollbar-rail-right-horizontal-bottom);
60
+ bottom: var(--u-scrollbar-rail-bottom-horizontal-bottom);
61
+ left: var(--u-scrollbar-rail-left-horizontal-bottom);
62
+ `), (0, cssr_1.cM)('vertical', `
63
+ width: var(--u-scrollbar-width);
64
+ `, [(0, cssr_1.c)('>', [(0, cssr_1.cE)('scrollbar', `
65
+ width: var(--u-scrollbar-width);
66
+ border-radius: var(--u-scrollbar-border-radius);
67
+ bottom: 0;
68
+ `)])]), (0, cssr_1.cM)('vertical--left', `
69
+ top: var(--u-scrollbar-rail-top-vertical-left);
70
+ right: var(--u-scrollbar-rail-right-vertical-left);
71
+ bottom: var(--u-scrollbar-rail-bottom-vertical-left);
72
+ left: var(--u-scrollbar-rail-left-vertical-left);
73
+ `), (0, cssr_1.cM)('vertical--right', `
74
+ top: var(--u-scrollbar-rail-top-vertical-right);
75
+ right: var(--u-scrollbar-rail-right-vertical-right);
76
+ bottom: var(--u-scrollbar-rail-bottom-vertical-right);
77
+ left: var(--u-scrollbar-rail-left-vertical-right);
78
+ `), (0, cssr_1.cM)('disabled', [(0, cssr_1.c)('>', [(0, cssr_1.cE)('scrollbar', 'pointer-events: none;')])]), (0, cssr_1.c)('>', [(0, cssr_1.cE)('scrollbar', `
79
+ z-index: 1;
80
+ position: absolute;
81
+ cursor: pointer;
82
+ pointer-events: all;
83
+ background-color: var(--u-scrollbar-color);
84
+ transition: background-color .2s var(--u-scrollbar-bezier);
85
+ `, [(0, fade_in_cssr_1.fadeInTransition)(), (0, cssr_1.c)('&:hover', 'background-color: var(--u-scrollbar-color-hover);')])])])])]);
@@ -0,0 +1,2 @@
1
+ declare const _default: import("css-render").CNode;
2
+ export default _default;
@@ -0,0 +1,15 @@
1
+ "use strict";
2
+
3
+ Object.defineProperty(exports, "__esModule", {
4
+ value: true
5
+ });
6
+ const cssr_1 = require("../../../../_utils/cssr");
7
+ exports.default = (0, cssr_1.cB)('scrollbar', [(0, cssr_1.cM)('rtl', `
8
+ direction: rtl;
9
+ `, [(0, cssr_1.c)('>', [(0, cssr_1.cB)('scrollbar-rail', [(0, cssr_1.cM)('horizontal', [(0, cssr_1.c)('>', [(0, cssr_1.cE)('scrollbar', `
10
+ left: 0;
11
+ right: unset;
12
+ `)])]), (0, cssr_1.cM)('vertical', `
13
+ left: 4px;
14
+ right: unset;
15
+ `)])])])]);
@@ -0,0 +1,7 @@
1
+ export declare const commonVars: {
2
+ railInsetHorizontalBottom: string;
3
+ railInsetHorizontalTop: string;
4
+ railInsetVerticalRight: string;
5
+ railInsetVerticalLeft: string;
6
+ railColor: string;
7
+ };
@@ -0,0 +1,10 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.commonVars = void 0;
4
+ exports.commonVars = {
5
+ railInsetHorizontalBottom: 'auto 2px 4px 2px',
6
+ railInsetHorizontalTop: '4px 2px auto 2px',
7
+ railInsetVerticalRight: '2px 4px 2px auto',
8
+ railInsetVerticalLeft: '2px auto 2px 4px',
9
+ railColor: 'transparent'
10
+ };
@@ -0,0 +1,3 @@
1
+ import type { SafeTopScrollbarTheme } from './light';
2
+ declare const safeTopScrollbarDark: SafeTopScrollbarTheme;
3
+ export default safeTopScrollbarDark;
@@ -0,0 +1,10 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ const common_1 = require("../../../_styles/common");
4
+ const light_1 = require("./light");
5
+ const safeTopScrollbarDark = {
6
+ name: 'SafeTopScrollbar',
7
+ common: common_1.commonDark,
8
+ self: light_1.self
9
+ };
10
+ exports.default = safeTopScrollbarDark;
@@ -0,0 +1,4 @@
1
+ export { default as scrollbarDark } from './dark';
2
+ export { default as scrollbarLight } from './light';
3
+ export { default as scrollbarRtl } from './rtl';
4
+ export type { SafeTopScrollbarTheme, SafeTopScrollbarThemeVars } from './light';
@@ -0,0 +1,12 @@
1
+ "use strict";
2
+ var __importDefault = (this && this.__importDefault) || function (mod) {
3
+ return (mod && mod.__esModule) ? mod : { "default": mod };
4
+ };
5
+ Object.defineProperty(exports, "__esModule", { value: true });
6
+ exports.scrollbarRtl = exports.scrollbarLight = exports.scrollbarDark = void 0;
7
+ var dark_1 = require("./dark");
8
+ Object.defineProperty(exports, "scrollbarDark", { enumerable: true, get: function () { return __importDefault(dark_1).default; } });
9
+ var light_1 = require("./light");
10
+ Object.defineProperty(exports, "scrollbarLight", { enumerable: true, get: function () { return __importDefault(light_1).default; } });
11
+ var rtl_1 = require("./rtl");
12
+ Object.defineProperty(exports, "scrollbarRtl", { enumerable: true, get: function () { return __importDefault(rtl_1).default; } });
@@ -0,0 +1,18 @@
1
+ import type { ThemeCommonVars } from '../../../_styles/common';
2
+ import type { Theme } from '../../../_mixins';
3
+ export declare const self: (vars: ThemeCommonVars) => {
4
+ height: string;
5
+ width: string;
6
+ borderRadius: string;
7
+ color: string;
8
+ colorHover: string;
9
+ railInsetHorizontalBottom: string;
10
+ railInsetHorizontalTop: string;
11
+ railInsetVerticalRight: string;
12
+ railInsetVerticalLeft: string;
13
+ railColor: string;
14
+ };
15
+ export type SafeTopScrollbarThemeVars = ReturnType<typeof self>;
16
+ declare const safeTopScrollbarLight: Theme<'SafeTopScrollbar', SafeTopScrollbarThemeVars>;
17
+ export default safeTopScrollbarLight;
18
+ export type SafeTopScrollbarTheme = typeof safeTopScrollbarLight;
@@ -0,0 +1,16 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.self = void 0;
4
+ const common_1 = require("../../../_styles/common");
5
+ const common_2 = require("./common");
6
+ const self = (vars) => {
7
+ const { scrollbarColor, scrollbarColorHover, scrollbarHeight, scrollbarWidth, scrollbarBorderRadius } = vars;
8
+ return Object.assign(Object.assign({}, common_2.commonVars), { height: scrollbarHeight, width: scrollbarWidth, borderRadius: scrollbarBorderRadius, color: scrollbarColor, colorHover: scrollbarColorHover });
9
+ };
10
+ exports.self = self;
11
+ const safeTopScrollbarLight = {
12
+ name: 'SafeTopScrollbar',
13
+ common: common_1.commonLight,
14
+ self: exports.self
15
+ };
16
+ exports.default = safeTopScrollbarLight;
@@ -0,0 +1,3 @@
1
+ import type { RtlItem } from '../../../config-provider/src/internal-interface';
2
+ export declare const scrollbarRtl: RtlItem;
3
+ export default scrollbarRtl;
@@ -0,0 +1,12 @@
1
+ "use strict";
2
+ var __importDefault = (this && this.__importDefault) || function (mod) {
3
+ return (mod && mod.__esModule) ? mod : { "default": mod };
4
+ };
5
+ Object.defineProperty(exports, "__esModule", { value: true });
6
+ exports.scrollbarRtl = void 0;
7
+ const rtl_cssr_1 = __importDefault(require("../src/styles/rtl.cssr"));
8
+ exports.scrollbarRtl = {
9
+ name: 'SafeTopScrollbar',
10
+ style: rtl_cssr_1.default
11
+ };
12
+ exports.default = exports.scrollbarRtl;
@@ -191,6 +191,10 @@ export declare const chatProps: {
191
191
  type: PropType<ChatPropsType["onAttachmentUpload"]>;
192
192
  default: undefined;
193
193
  };
194
+ onAttachmentDownload: {
195
+ type: PropType<ChatPropsType["onAttachmentDownload"]>;
196
+ default: undefined;
197
+ };
194
198
  onFilterChange: {
195
199
  type: PropType<ChatPropsType["onFilterChange"]>;
196
200
  default: undefined;
@@ -2413,6 +2417,10 @@ declare const _default: import("vue").DefineComponent<{
2413
2417
  type: PropType<ChatPropsType["onAttachmentUpload"]>;
2414
2418
  default: undefined;
2415
2419
  };
2420
+ onAttachmentDownload: {
2421
+ type: PropType<ChatPropsType["onAttachmentDownload"]>;
2422
+ default: undefined;
2423
+ };
2416
2424
  onFilterChange: {
2417
2425
  type: PropType<ChatPropsType["onFilterChange"]>;
2418
2426
  default: undefined;
@@ -5652,6 +5660,10 @@ declare const _default: import("vue").DefineComponent<{
5652
5660
  type: PropType<ChatPropsType["onAttachmentUpload"]>;
5653
5661
  default: undefined;
5654
5662
  };
5663
+ onAttachmentDownload: {
5664
+ type: PropType<ChatPropsType["onAttachmentDownload"]>;
5665
+ default: undefined;
5666
+ };
5655
5667
  onFilterChange: {
5656
5668
  type: PropType<ChatPropsType["onFilterChange"]>;
5657
5669
  default: undefined;
@@ -7716,6 +7728,7 @@ declare const _default: import("vue").DefineComponent<{
7716
7728
  onChatItemsScrollToBottom: () => void;
7717
7729
  messages: ChatMessageData[] | undefined;
7718
7730
  onMessageRetry: ((message: ChatMessageData) => void) | undefined;
7731
+ onAttachmentUpload: import("./interface").OnAttachmentUpload | undefined;
7719
7732
  onChatClose: () => void;
7720
7733
  onChatShare: () => void;
7721
7734
  onUserProfile: () => void;
@@ -7749,7 +7762,7 @@ declare const _default: import("vue").DefineComponent<{
7749
7762
  chatItemsLoadingCount: number | undefined;
7750
7763
  messagesLoading: boolean | undefined;
7751
7764
  messagesLoadingCount: number | undefined;
7752
- onAttachmentUpload: import("./interface").OnAttachmentUpload | undefined;
7765
+ onAttachmentDownload: import("./interface").OnAttachmentDownload | undefined;
7753
7766
  onFilterChange: import("./interface").OnFilterChange | undefined;
7754
7767
  onNetworkError: import("./interface").OnNetworkError | undefined;
7755
7768
  onUploadError: import("./interface").OnUploadError | undefined;
@@ -154,6 +154,9 @@ exports.chatProps = Object.assign(Object.assign({}, _mixins_1.useTheme.props), {
154
154
  }, onAttachmentUpload: {
155
155
  type: Function,
156
156
  default: undefined
157
+ }, onAttachmentDownload: {
158
+ type: Function,
159
+ default: undefined
157
160
  }, onFilterChange: {
158
161
  type: Function,
159
162
  default: undefined
@@ -400,6 +403,8 @@ exports.default = (0, vue_1.defineComponent)({
400
403
  handleNetworkError,
401
404
  handleUploadError,
402
405
  handleSendError,
406
+ onAttachmentUpload: (0, vue_1.toRef)(props, 'onAttachmentUpload'),
407
+ onAttachmentDownload: (0, vue_1.toRef)(props, 'onAttachmentDownload'),
403
408
  onChatClose: (0, vue_1.toRef)(props, 'onChatClose'),
404
409
  onChatShare: (0, vue_1.toRef)(props, 'onChatShare'),
405
410
  onUserProfile: (0, vue_1.toRef)(props, 'onUserProfile'),
@@ -96,11 +96,26 @@ exports.default = (0, vue_1.defineComponent)({
96
96
  var _a;
97
97
  (_a = props.onChatSelect) === null || _a === void 0 ? void 0 : _a.call(props, chatId);
98
98
  };
99
+ const toKeyString = (value) => {
100
+ if (typeof value === 'symbol')
101
+ return value.toString();
102
+ if (typeof value === 'function') {
103
+ const result = value();
104
+ return typeof result === 'string' || typeof result === 'number'
105
+ ? String(result)
106
+ : '';
107
+ }
108
+ return value != null ? String(value) : '';
109
+ };
99
110
  const renderChatItem = (item) => {
100
111
  var _a, _b;
101
112
  const isSelected = props.selectedChatId === item.id;
102
113
  const isTyping = (_b = (_a = props.typingChatIds) === null || _a === void 0 ? void 0 : _a.includes(item.id)) !== null && _b !== void 0 ? _b : false;
103
- return ((0, vue_1.h)(list_1.UListItem, { key: item.id, showIcon: false, onClick: () => {
114
+ const { id, title, subtitle } = item;
115
+ const keyId = toKeyString(id);
116
+ const keyTitle = toKeyString(title);
117
+ const keySubtitle = toKeyString(subtitle);
118
+ return ((0, vue_1.h)(list_1.UListItem, { key: `${keyId}-${keyTitle}-${keySubtitle}`, showIcon: false, onClick: () => {
104
119
  handleChatSelect(item.id);
105
120
  }, class: [
106
121
  `${mergedClsPrefixRef.value}-chat-sidebar__item`,
@@ -1,7 +1,17 @@
1
1
  "use strict";
2
+ var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) {
3
+ function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
4
+ return new (P || (P = Promise))(function (resolve, reject) {
5
+ function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
6
+ function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
7
+ function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
8
+ step((generator = generator.apply(thisArg, _arguments || [])).next());
9
+ });
10
+ };
2
11
  Object.defineProperty(exports, "__esModule", { value: true });
3
12
  const vue_1 = require("vue");
4
13
  const upload_1 = require("../../../upload");
14
+ const interface_1 = require("../interface");
5
15
  exports.default = (0, vue_1.defineComponent)({
6
16
  name: 'ChatAttachment',
7
17
  props: {
@@ -23,10 +33,28 @@ exports.default = (0, vue_1.defineComponent)({
23
33
  }
24
34
  },
25
35
  setup(props, { slots }) {
36
+ const UChat = (0, vue_1.inject)(interface_1.chatInjectionKey, null);
37
+ const onAttachmentDownload = UChat === null || UChat === void 0 ? void 0 : UChat.onAttachmentDownload;
26
38
  const getThumbnailUrl = (attachment) => {
27
39
  const url = [attachment.preview, attachment.thumbnail].find((value) => typeof value === 'string');
28
40
  return url !== null && url !== void 0 ? url : null;
29
41
  };
42
+ const handleDownload = (file) => __awaiter(this, void 0, void 0, function* () {
43
+ if (onAttachmentDownload === null || onAttachmentDownload === void 0 ? void 0 : onAttachmentDownload.value) {
44
+ const attachment = props.attachments.find((att) => att.name === file.name);
45
+ if (attachment) {
46
+ try {
47
+ yield onAttachmentDownload.value(attachment);
48
+ return false;
49
+ }
50
+ catch (error) {
51
+ console.error('Download failed:', error);
52
+ return false;
53
+ }
54
+ }
55
+ }
56
+ return true;
57
+ });
30
58
  const renderAttachment = () => {
31
59
  const fileList = props.attachments.map((attachment, index) => {
32
60
  var _a, _b, _c;
@@ -42,7 +70,7 @@ exports.default = (0, vue_1.defineComponent)({
42
70
  batchId: null
43
71
  });
44
72
  });
45
- const uploadComponent = ((0, vue_1.h)(upload_1.UUpload, Object.assign({ abstract: true, fileList: fileList, fileListStyle: props.withPadding
73
+ const uploadComponent = ((0, vue_1.h)(upload_1.UUpload, Object.assign({ abstract: true }, props.uploadProps, { fileList: fileList, fileListStyle: props.withPadding
46
74
  ? {
47
75
  display: 'flex',
48
76
  flexDirection: 'column',
@@ -51,7 +79,7 @@ exports.default = (0, vue_1.defineComponent)({
51
79
  }
52
80
  : undefined, showRemoveButton: false, showDownloadButton: props.attachments.some((attachment) => attachment.status === 'finished' &&
53
81
  attachment.url &&
54
- attachment.url !== '#'), showRetryButton: props.attachments.some((attachment) => attachment.status === 'error') }, props.uploadProps), {
82
+ attachment.url !== '#'), showRetryButton: props.attachments.some((attachment) => attachment.status === 'error'), onDownload: handleDownload }), {
55
83
  default: () => ((0, vue_1.h)(upload_1.UUploadFileList, null, {
56
84
  'upload-file-title': slots['upload-file-title']
57
85
  ? ({ file }) => { var _a; return (_a = slots['upload-file-title']) === null || _a === void 0 ? void 0 : _a.call(slots, file); }
@@ -17,7 +17,7 @@ const interface_1 = require("../interface");
17
17
  const input_1 = require("../../../input");
18
18
  const button_1 = require("../../../button");
19
19
  const icon_1 = require("../../../icon");
20
- const scrollbar_1 = require("../../../scrollbar");
20
+ const safe_top_scrollbar_1 = require("../../../safe-top-scrollbar");
21
21
  const tooltip_1 = require("../../../tooltip");
22
22
  const upload_1 = require("../../../upload");
23
23
  const flex_1 = require("../../../flex");
@@ -29,13 +29,14 @@ const SENDING_DELAY = 100;
29
29
  exports.default = (0, vue_1.defineComponent)({
30
30
  name: 'ChatMainArea',
31
31
  setup(_, { slots }) {
32
- const { mergedClsPrefixRef, mergedThemeRef, selectedChatRef, messagesRef, typingChatIdsRef, messagesLoadingRef, messagesLoadingCountRef, headerButtonPropsRef, headerIconPropsRef, headerShareButtonPropsRef, headerProfileButtonPropsRef, headerCloseButtonPropsRef, headerShareIconPropsRef, headerProfileIconPropsRef, messageUploadPropsRef, footerInputPropsRef, footerButtonPropsRef, footerUploadPropsRef, footerIconPropsRef, inputPlaceholderRef, retryTextRef, typingTextRef, closeButtonTextRef, shareButtonTooltipRef, profileButtonTooltipRef, unreadNotificationTextRef, notificationsShownSetRef, unreadCountsBeforeReadRef, markNotificationShown, handleMessageSend, handleMessageRetry, handleFooterInputChange, onChatClose, onChatShare, onUserProfile, onMessagesScrollToTop, onMessagesScrollToBottom
32
+ const { mergedClsPrefixRef, mergedThemeRef, selectedChatRef, messagesRef, typingChatIdsRef, messagesLoadingRef, messagesLoadingCountRef, headerButtonPropsRef, headerIconPropsRef, headerShareButtonPropsRef, headerProfileButtonPropsRef, headerCloseButtonPropsRef, headerShareIconPropsRef, headerProfileIconPropsRef, messageUploadPropsRef, footerInputPropsRef, footerButtonPropsRef, footerUploadPropsRef, footerIconPropsRef, inputPlaceholderRef, retryTextRef, typingTextRef, closeButtonTextRef, shareButtonTooltipRef, profileButtonTooltipRef, unreadNotificationTextRef, notificationsShownSetRef, unreadCountsBeforeReadRef, markNotificationShown, handleMessageSend, handleMessageRetry, handleFooterInputChange, onAttachmentUpload, onChatClose, onChatShare, onUserProfile, onMessagesScrollToTop, onMessagesScrollToBottom
33
33
  // eslint-disable-next-line @typescript-eslint/no-non-null-assertion
34
34
  } = (0, vue_1.inject)(interface_1.chatInjectionKey);
35
35
  const messagesBodyRef = (0, vue_1.ref)();
36
36
  const inputRef = (0, vue_1.ref)();
37
37
  const inputValue = (0, vue_1.ref)('');
38
38
  const attachmentFileList = (0, vue_1.ref)([]);
39
+ const uploadedAttachmentsMap = (0, vue_1.ref)(new Map());
39
40
  const lastScrollTop = (0, vue_1.ref)(0);
40
41
  const scrollTopFired = (0, vue_1.ref)(false);
41
42
  const scrollBottomFired = (0, vue_1.ref)(false);
@@ -60,6 +61,8 @@ exports.default = (0, vue_1.defineComponent)({
60
61
  scrollTopFired.value = false;
61
62
  scrollBottomFired.value = false;
62
63
  shouldScrollOnLoad.value = true;
64
+ attachmentFileList.value = [];
65
+ uploadedAttachmentsMap.value.clear();
63
66
  if (unreadBeforeRead > 0 &&
64
67
  !notificationsShownSetRef.value.has(newChat.id)) {
65
68
  hasUnreadMessages.value = true;
@@ -158,22 +161,36 @@ exports.default = (0, vue_1.defineComponent)({
158
161
  el.scrollTop = el.scrollHeight;
159
162
  }
160
163
  };
164
+ const toKeyString = (value) => {
165
+ if (typeof value === 'symbol')
166
+ return value.toString();
167
+ if (typeof value === 'function') {
168
+ const result = value();
169
+ return typeof result === 'string' || typeof result === 'number'
170
+ ? String(result)
171
+ : '';
172
+ }
173
+ return value != null ? String(value) : '';
174
+ };
161
175
  const renderHeader = () => {
162
176
  return ((0, vue_1.h)("div", { class: `${mergedClsPrefixRef.value}-chat-main__header` },
163
177
  (0, vue_1.h)(flex_1.UFlex, { justify: "space-between", align: "flex-start", wrap: false }, {
164
- default: () => ((0, vue_1.h)(vue_1.Fragment, null,
165
- (0, vue_1.h)(typography_1.UText, { variant: "heading-s-bold", class: `${mergedClsPrefixRef.value}-chat-main__header-title`, theme: mergedThemeRef.value.peers.Typography, themeOverrides: mergedThemeRef.value.peerOverrides.Typography }, {
166
- default: () => { var _a, _b; return (_b = (_a = selectedChatRef.value) === null || _a === void 0 ? void 0 : _a.title) !== null && _b !== void 0 ? _b : ''; }
167
- }),
168
- (0, vue_1.h)(flex_1.UFlex, { align: "center", size: "small", class: `${mergedClsPrefixRef.value}-chat-main__header-actions` }, {
169
- default: () => (0, _utils_1.resolveSlot)(slots.headerActions, () => {
170
- const shareButtonProps = Object.assign(Object.assign({}, headerButtonPropsRef.value), headerShareButtonPropsRef.value);
171
- const profileButtonProps = Object.assign(Object.assign({}, headerButtonPropsRef.value), headerProfileButtonPropsRef.value);
172
- const closeButtonProps = Object.assign(Object.assign({}, headerButtonPropsRef.value), headerCloseButtonPropsRef.value);
173
- const shareIconProps = Object.assign(Object.assign({}, headerIconPropsRef.value), headerShareIconPropsRef.value);
174
- const profileIconProps = Object.assign(Object.assign({}, headerIconPropsRef.value), headerProfileIconPropsRef.value);
175
- const buttons = [];
176
- if (shareButtonProps.disabled !== true) {
178
+ default: () => {
179
+ const chat = selectedChatRef.value;
180
+ const keyId = toKeyString(chat === null || chat === void 0 ? void 0 : chat.id);
181
+ const keyTitle = toKeyString(chat === null || chat === void 0 ? void 0 : chat.title);
182
+ return ((0, vue_1.h)(vue_1.Fragment, null,
183
+ (0, vue_1.h)(typography_1.UText, { key: `${keyId}-${keyTitle}`, variant: "heading-s-bold", class: `${mergedClsPrefixRef.value}-chat-main__header-title`, theme: mergedThemeRef.value.peers.Typography, themeOverrides: mergedThemeRef.value.peerOverrides.Typography }, {
184
+ default: () => { var _a, _b; return (_b = (_a = selectedChatRef.value) === null || _a === void 0 ? void 0 : _a.title) !== null && _b !== void 0 ? _b : ''; }
185
+ }),
186
+ (0, vue_1.h)(flex_1.UFlex, { align: "center", size: "small", class: `${mergedClsPrefixRef.value}-chat-main__header-actions` }, {
187
+ default: () => (0, _utils_1.resolveSlot)(slots.headerActions, () => {
188
+ const shareButtonProps = Object.assign(Object.assign({}, headerButtonPropsRef.value), headerShareButtonPropsRef.value);
189
+ const profileButtonProps = Object.assign(Object.assign({}, headerButtonPropsRef.value), headerProfileButtonPropsRef.value);
190
+ const closeButtonProps = Object.assign(Object.assign({}, headerButtonPropsRef.value), headerCloseButtonPropsRef.value);
191
+ const shareIconProps = Object.assign(Object.assign({}, headerIconPropsRef.value), headerShareIconPropsRef.value);
192
+ const profileIconProps = Object.assign(Object.assign({}, headerIconPropsRef.value), headerProfileIconPropsRef.value);
193
+ const buttons = [];
177
194
  buttons.push((0, vue_1.h)(tooltip_1.UTooltip, null, {
178
195
  trigger: () => ((0, vue_1.h)(button_1.UButton, Object.assign({ secondary: true, circle: true, size: "large" }, shareButtonProps, { theme: mergedThemeRef.value.peers.Button, themeOverrides: mergedThemeRef.value.peerOverrides
179
196
  .Button, onClick: () => { var _a; return (_a = onChatShare === null || onChatShare === void 0 ? void 0 : onChatShare.value) === null || _a === void 0 ? void 0 : _a.call(onChatShare); } }), {
@@ -184,8 +201,6 @@ exports.default = (0, vue_1.defineComponent)({
184
201
  })),
185
202
  default: () => shareButtonTooltipRef.value
186
203
  }));
187
- }
188
- if (profileButtonProps.disabled !== true) {
189
204
  buttons.push((0, vue_1.h)(tooltip_1.UTooltip, null, {
190
205
  trigger: () => ((0, vue_1.h)(button_1.UButton, Object.assign({ secondary: true, circle: true, size: "large" }, profileButtonProps, { theme: mergedThemeRef.value.peers.Button, themeOverrides: mergedThemeRef.value.peerOverrides
191
206
  .Button, onClick: () => { var _a; return (_a = onUserProfile === null || onUserProfile === void 0 ? void 0 : onUserProfile.value) === null || _a === void 0 ? void 0 : _a.call(onUserProfile); } }), {
@@ -196,15 +211,13 @@ exports.default = (0, vue_1.defineComponent)({
196
211
  })),
197
212
  default: () => profileButtonTooltipRef.value
198
213
  }));
199
- }
200
- if (closeButtonProps.disabled !== true) {
201
214
  buttons.push((0, vue_1.h)(button_1.UButton, Object.assign({ type: "primary", size: "large", round: true }, closeButtonProps, { theme: mergedThemeRef.value.peers.Button, themeOverrides: mergedThemeRef.value.peerOverrides.Button, onClick: () => { var _a; return (_a = onChatClose === null || onChatClose === void 0 ? void 0 : onChatClose.value) === null || _a === void 0 ? void 0 : _a.call(onChatClose); } }), {
202
215
  default: () => closeButtonTextRef.value
203
216
  }));
204
- }
205
- return buttons;
206
- })
207
- })))
217
+ return buttons;
218
+ })
219
+ })));
220
+ }
208
221
  })));
209
222
  };
210
223
  const renderMessages = () => {
@@ -231,7 +244,11 @@ exports.default = (0, vue_1.defineComponent)({
231
244
  const attachments = attachmentFileList.value.length > 0
232
245
  ? attachmentFileList.value.map((file) => {
233
246
  var _a, _b, _c;
234
- return ({
247
+ const uploadedAttachment = uploadedAttachmentsMap.value.get(file.id);
248
+ if (uploadedAttachment) {
249
+ return uploadedAttachment;
250
+ }
251
+ return {
235
252
  id: file.id,
236
253
  type: interface_1.ChatMessageType.FILE,
237
254
  name: file.name,
@@ -241,13 +258,14 @@ exports.default = (0, vue_1.defineComponent)({
241
258
  thumbnail: (_b = file.thumbnailUrl) !== null && _b !== void 0 ? _b : undefined,
242
259
  status: file.status,
243
260
  percentage: (_c = file.percentage) !== null && _c !== void 0 ? _c : undefined
244
- });
261
+ };
245
262
  })
246
263
  : undefined;
247
264
  handleMessageSend(inputValue.value.trim(), attachments);
248
265
  inputValue.value = '';
249
266
  attachmentFileList.value = [];
250
267
  chatInputs.value[selectedChatRef.value.id] = '';
268
+ uploadedAttachmentsMap.value.clear();
251
269
  hasUnreadMessages.value = false;
252
270
  showNotificationManually.value = false;
253
271
  }
@@ -258,39 +276,24 @@ exports.default = (0, vue_1.defineComponent)({
258
276
  }
259
277
  }
260
278
  });
261
- let fileUploadTimer = null;
262
- const pendingFiles = (0, vue_1.ref)([]);
263
279
  const handleFileListUpdate = (fileList) => {
264
- const newFiles = fileList.filter((file) => !attachmentFileList.value.some((existing) => existing.id === file.id) &&
265
- !pendingFiles.value.some((existing) => existing.id === file.id));
266
- if (newFiles.length > 0) {
267
- pendingFiles.value = [...pendingFiles.value, ...newFiles];
268
- if (fileUploadTimer) {
269
- clearTimeout(fileUploadTimer);
270
- }
271
- fileUploadTimer = setTimeout(() => {
272
- if (pendingFiles.value.length > 0 && handleMessageSend) {
273
- const hasError = pendingFiles.value.some((file) => file.status === 'error');
274
- const batchStatus = hasError ? 'error' : 'finished';
275
- const attachments = pendingFiles.value.map((file) => {
276
- var _a, _b, _c;
277
- return ({
278
- id: file.id,
279
- type: interface_1.ChatMessageType.FILE,
280
- name: file.name,
281
- url: file.url ||
282
- (file.file ? URL.createObjectURL(file.file) : '#'),
283
- size: (_a = file.file) === null || _a === void 0 ? void 0 : _a.size,
284
- thumbnail: (_b = file.thumbnailUrl) !== null && _b !== void 0 ? _b : undefined,
285
- status: batchStatus,
286
- percentage: (_c = file.percentage) !== null && _c !== void 0 ? _c : undefined
287
- });
288
- });
289
- handleMessageSend('', attachments);
290
- pendingFiles.value = [];
291
- attachmentFileList.value = [];
280
+ attachmentFileList.value = fileList;
281
+ const uploadCallback = onAttachmentUpload === null || onAttachmentUpload === void 0 ? void 0 : onAttachmentUpload.value;
282
+ if (uploadCallback) {
283
+ const newFiles = fileList.filter((file) => file.file && !uploadedAttachmentsMap.value.has(file.id));
284
+ void (() => __awaiter(this, void 0, void 0, function* () {
285
+ for (const uploadFile of newFiles) {
286
+ if (uploadFile.file) {
287
+ try {
288
+ const attachment = yield uploadCallback(uploadFile.file);
289
+ uploadedAttachmentsMap.value.set(uploadFile.id, attachment);
290
+ }
291
+ catch (error) {
292
+ console.error('File upload failed:', error);
293
+ }
294
+ }
292
295
  }
293
- }, SENDING_DELAY);
296
+ }))();
294
297
  }
295
298
  };
296
299
  const renderFooter = () => {
@@ -299,11 +302,14 @@ exports.default = (0, vue_1.defineComponent)({
299
302
  default: () => ((0, vue_1.h)(flex_1.UFlex, { align: "center", size: "small", class: `${mergedClsPrefixRef.value}-chat-main__input-container` }, {
300
303
  default: () => ((0, vue_1.h)(vue_1.Fragment, null,
301
304
  (0, vue_1.h)(upload_1.UUploadTrigger, { abstract: true }, {
302
- default: ({ handleClick }) => ((0, vue_1.h)(button_1.UButton, Object.assign({ secondary: true, size: "large", class: `${mergedClsPrefixRef.value}-chat-main__attach-btn` }, footerButtonPropsRef.value, { theme: mergedThemeRef.value.peers.Button, themeOverrides: mergedThemeRef.value.peerOverrides.Button, onClick: handleClick }), {
303
- default: () => ((0, vue_1.h)(icon_1.UIcon, Object.assign({ size: 24 }, footerIconPropsRef.value, { theme: mergedThemeRef.value.peers.Icon, themeOverrides: mergedThemeRef.value.peerOverrides.Icon }), {
304
- default: () => (0, vue_1.h)(icons_1.AttachIcon, null)
305
- }))
306
- }))
305
+ default: ({ handleClick }) => {
306
+ var _a;
307
+ return ((0, vue_1.h)(button_1.UButton, Object.assign({ secondary: true, size: "large", class: `${mergedClsPrefixRef.value}-chat-main__attach-btn` }, footerButtonPropsRef.value, { disabled: (_a = footerInputPropsRef.value) === null || _a === void 0 ? void 0 : _a.disabled, theme: mergedThemeRef.value.peers.Button, themeOverrides: mergedThemeRef.value.peerOverrides.Button, onClick: handleClick }), {
308
+ default: () => ((0, vue_1.h)(icon_1.UIcon, Object.assign({ size: 24 }, footerIconPropsRef.value, { theme: mergedThemeRef.value.peers.Icon, themeOverrides: mergedThemeRef.value.peerOverrides.Icon }), {
309
+ default: () => (0, vue_1.h)(icons_1.AttachIcon, null)
310
+ }))
311
+ }));
312
+ }
307
313
  }),
308
314
  (0, vue_1.h)(input_1.UInput, Object.assign({ ref: "inputRef", value: inputValue.value, placeholder: inputPlaceholderRef.value, class: `${mergedClsPrefixRef.value}-chat-main__input` }, footerInputPropsRef.value, { theme: mergedThemeRef.value.peers.Input, themeOverrides: mergedThemeRef.value.peerOverrides.Input, onUpdateValue: (value) => {
309
315
  inputValue.value = value;
@@ -337,7 +343,7 @@ exports.default = (0, vue_1.defineComponent)({
337
343
  const { mergedClsPrefixRef } = (0, vue_1.inject)(interface_1.chatInjectionKey);
338
344
  return ((0, vue_1.h)("div", { class: `${mergedClsPrefixRef.value}-chat-main` },
339
345
  this.renderHeader(),
340
- (0, vue_1.h)(scrollbar_1.UScrollbar, { ref: "messagesBodyRef", class: `${mergedClsPrefixRef.value}-chat-main__body`, onScroll: this.handleMessagesScroll }, {
346
+ (0, vue_1.h)(safe_top_scrollbar_1.USafeTopScrollbar, { ref: "messagesBodyRef", class: `${mergedClsPrefixRef.value}-chat-main__body`, onScroll: this.handleMessagesScroll }, {
341
347
  default: () => this.renderMessages()
342
348
  }),
343
349
  this.renderFooter()));