@droppii-org/chat-mobile 0.2.29 → 0.2.30
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/lib/module/components/flows/inputButtons/index.js +6 -3
- package/lib/module/components/flows/inputButtons/index.js.map +1 -1
- package/lib/module/config/api-endpoints.js +2 -1
- package/lib/module/config/api-endpoints.js.map +1 -1
- package/lib/module/context/ChatDetailContext.js +35 -2
- package/lib/module/context/ChatDetailContext.js.map +1 -1
- package/lib/module/context/index.js +1 -0
- package/lib/module/context/index.js.map +1 -1
- package/lib/module/hooks/conversation/useGetConversationDetail.js +58 -0
- package/lib/module/hooks/conversation/useGetConversationDetail.js.map +1 -0
- package/lib/module/hooks/flows/useFlow.js +1 -1
- package/lib/module/hooks/flows/useFlow.js.map +1 -1
- package/lib/module/hooks/flows/useGetConversationFlowMainMenu.js +17 -0
- package/lib/module/hooks/flows/useGetConversationFlowMainMenu.js.map +1 -0
- package/lib/module/hooks/message/useSendMessage.js +32 -7
- package/lib/module/hooks/message/useSendMessage.js.map +1 -1
- package/lib/module/hooks/query-keys.js +4 -1
- package/lib/module/hooks/query-keys.js.map +1 -1
- package/lib/module/hooks/useChatCompose.js +0 -1
- package/lib/module/hooks/useChatCompose.js.map +1 -1
- package/lib/module/index.js +4 -2
- package/lib/module/index.js.map +1 -1
- package/lib/module/screens/chat-detail/ChatAttachmentPanel.js +4 -14
- package/lib/module/screens/chat-detail/ChatAttachmentPanel.js.map +1 -1
- package/lib/module/screens/chat-detail/ChatComposer.js +26 -15
- package/lib/module/screens/chat-detail/ChatComposer.js.map +1 -1
- package/lib/module/screens/chat-detail/ChatDetail.js +58 -71
- package/lib/module/screens/chat-detail/ChatDetail.js.map +1 -1
- package/lib/module/screens/chat-detail/ChatDetailHeader.js +7 -10
- package/lib/module/screens/chat-detail/ChatDetailHeader.js.map +1 -1
- package/lib/module/screens/chat-detail/ChatListLegend.js +1 -1
- package/lib/module/screens/chat-detail/ChatListLegend.js.map +1 -1
- package/lib/module/screens/chat-detail/ChatLoadEarlier.js.map +1 -1
- package/lib/module/screens/chat-detail/ChatQuickActions.js +2 -1
- package/lib/module/screens/chat-detail/ChatQuickActions.js.map +1 -1
- package/lib/module/screens/chat-detail/constants.js +30 -24
- package/lib/module/screens/chat-detail/constants.js.map +1 -1
- package/lib/module/screens/chat-detail/index.js +2 -2
- package/lib/module/screens/chat-detail/index.js.map +1 -1
- package/lib/module/screens/chat-detail/types.js +15 -1
- package/lib/module/screens/chat-detail/types.js.map +1 -1
- package/lib/module/services/attachmentHandlers/imageAttachmentHandler.js +2 -2
- package/lib/module/services/attachmentHandlers/imageAttachmentHandler.js.map +1 -1
- package/lib/module/services/endpoints.js +3 -1
- package/lib/module/services/endpoints.js.map +1 -1
- package/lib/module/translation/resources/i18n.js +7 -1
- package/lib/module/translation/resources/i18n.js.map +1 -1
- package/lib/module/types/chat.js +9 -0
- package/lib/module/types/chat.js.map +1 -1
- package/lib/module/types/flows.js +5 -0
- package/lib/module/types/flows.js.map +1 -1
- package/lib/module/utils/flows.js +5 -0
- package/lib/module/utils/flows.js.map +1 -1
- package/lib/module/utils/imageUtils.js +0 -3
- package/lib/module/utils/imageUtils.js.map +1 -1
- package/lib/module/utils/messageUtils.js +5 -19
- package/lib/module/utils/messageUtils.js.map +1 -1
- package/lib/typescript/src/components/flows/inputButtons/index.d.ts.map +1 -1
- package/lib/typescript/src/config/api-endpoints.d.ts +1 -0
- package/lib/typescript/src/config/api-endpoints.d.ts.map +1 -1
- package/lib/typescript/src/context/ChatDetailContext.d.ts +1 -1
- package/lib/typescript/src/context/ChatDetailContext.d.ts.map +1 -1
- package/lib/typescript/src/context/index.d.ts +1 -0
- package/lib/typescript/src/context/index.d.ts.map +1 -1
- package/lib/typescript/src/hooks/conversation/useGetConversationDetail.d.ts +17 -0
- package/lib/typescript/src/hooks/conversation/useGetConversationDetail.d.ts.map +1 -0
- package/lib/typescript/src/hooks/flows/useGetConversationFlowMainMenu.d.ts +3 -0
- package/lib/typescript/src/hooks/flows/useGetConversationFlowMainMenu.d.ts.map +1 -0
- package/lib/typescript/src/hooks/message/useSendMessage.d.ts +5 -4
- package/lib/typescript/src/hooks/message/useSendMessage.d.ts.map +1 -1
- package/lib/typescript/src/hooks/query-keys.d.ts +3 -0
- package/lib/typescript/src/hooks/query-keys.d.ts.map +1 -1
- package/lib/typescript/src/index.d.ts +6 -4
- package/lib/typescript/src/index.d.ts.map +1 -1
- package/lib/typescript/src/screens/chat-detail/ChatAttachmentPanel.d.ts +2 -2
- package/lib/typescript/src/screens/chat-detail/ChatAttachmentPanel.d.ts.map +1 -1
- package/lib/typescript/src/screens/chat-detail/ChatComposer.d.ts +3 -1
- package/lib/typescript/src/screens/chat-detail/ChatComposer.d.ts.map +1 -1
- package/lib/typescript/src/screens/chat-detail/ChatDetail.d.ts +1 -1
- package/lib/typescript/src/screens/chat-detail/ChatDetail.d.ts.map +1 -1
- package/lib/typescript/src/screens/chat-detail/ChatDetailHeader.d.ts +1 -1
- package/lib/typescript/src/screens/chat-detail/ChatDetailHeader.d.ts.map +1 -1
- package/lib/typescript/src/screens/chat-detail/ChatLoadEarlier.d.ts +3 -2
- package/lib/typescript/src/screens/chat-detail/ChatLoadEarlier.d.ts.map +1 -1
- package/lib/typescript/src/screens/chat-detail/ChatQuickActions.d.ts +1 -1
- package/lib/typescript/src/screens/chat-detail/ChatQuickActions.d.ts.map +1 -1
- package/lib/typescript/src/screens/chat-detail/constants.d.ts +3 -3
- package/lib/typescript/src/screens/chat-detail/constants.d.ts.map +1 -1
- package/lib/typescript/src/screens/chat-detail/index.d.ts +3 -3
- package/lib/typescript/src/screens/chat-detail/index.d.ts.map +1 -1
- package/lib/typescript/src/screens/chat-detail/types.d.ts +28 -19
- package/lib/typescript/src/screens/chat-detail/types.d.ts.map +1 -1
- package/lib/typescript/src/services/endpoints.d.ts +2 -0
- package/lib/typescript/src/services/endpoints.d.ts.map +1 -1
- package/lib/typescript/src/store/conversation.d.ts +1 -1
- package/lib/typescript/src/store/conversation.d.ts.map +1 -1
- package/lib/typescript/src/translation/resources/i18n.d.ts.map +1 -1
- package/lib/typescript/src/types/chat.d.ts +26 -2
- package/lib/typescript/src/types/chat.d.ts.map +1 -1
- package/lib/typescript/src/types/flows.d.ts +3 -0
- package/lib/typescript/src/types/flows.d.ts.map +1 -1
- package/lib/typescript/src/utils/flows.d.ts +2 -0
- package/lib/typescript/src/utils/flows.d.ts.map +1 -1
- package/lib/typescript/src/utils/imageUtils.d.ts +0 -1
- package/lib/typescript/src/utils/imageUtils.d.ts.map +1 -1
- package/lib/typescript/src/utils/messageUtils.d.ts +1 -1
- package/lib/typescript/src/utils/messageUtils.d.ts.map +1 -1
- package/package.json +3 -5
- package/src/components/flows/inputButtons/index.tsx +11 -3
- package/src/config/api-endpoints.ts +2 -0
- package/src/context/ChatDetailContext.tsx +57 -4
- package/src/context/index.ts +1 -0
- package/src/hooks/conversation/useGetConversationDetail.ts +78 -0
- package/src/hooks/flows/useFlow.ts +1 -1
- package/src/hooks/flows/useGetConversationFlowMainMenu.ts +19 -0
- package/src/hooks/message/useSendMessage.ts +43 -14
- package/src/hooks/query-keys.ts +6 -0
- package/src/hooks/useChatCompose.ts +1 -1
- package/src/index.tsx +15 -6
- package/src/screens/chat-detail/ChatAttachmentPanel.tsx +8 -25
- package/src/screens/chat-detail/ChatComposer.tsx +26 -21
- package/src/screens/chat-detail/ChatDetail.tsx +61 -77
- package/src/screens/chat-detail/ChatDetailHeader.tsx +7 -18
- package/src/screens/chat-detail/ChatListLegend.tsx +1 -1
- package/src/screens/chat-detail/ChatLoadEarlier.tsx +1 -2
- package/src/screens/chat-detail/ChatQuickActions.tsx +6 -2
- package/src/screens/chat-detail/constants.ts +33 -27
- package/src/screens/chat-detail/index.ts +5 -8
- package/src/screens/chat-detail/types.ts +30 -28
- package/src/services/attachmentHandlers/imageAttachmentHandler.ts +2 -2
- package/src/services/endpoints.ts +4 -0
- package/src/store/conversation.ts +1 -1
- package/src/translation/resources/i18n.ts +6 -0
- package/src/types/chat.ts +31 -1
- package/src/types/flows.ts +4 -0
- package/src/utils/flows.ts +7 -0
- package/src/utils/imageUtils.ts +0 -4
- package/src/utils/messageUtils.ts +7 -22
- package/lib/module/screens/chat-detail/ChatDay.js +0 -65
- package/lib/module/screens/chat-detail/ChatDay.js.map +0 -1
- package/lib/module/types/message.js +0 -17
- package/lib/module/types/message.js.map +0 -1
- package/lib/module/utils/resolveMessageType.js +0 -47
- package/lib/module/utils/resolveMessageType.js.map +0 -1
- package/lib/typescript/src/screens/chat-detail/ChatDay.d.ts +0 -3
- package/lib/typescript/src/screens/chat-detail/ChatDay.d.ts.map +0 -1
- package/lib/typescript/src/types/message.d.ts +0 -16
- package/lib/typescript/src/types/message.d.ts.map +0 -1
- package/lib/typescript/src/utils/resolveMessageType.d.ts +0 -4
- package/lib/typescript/src/utils/resolveMessageType.d.ts.map +0 -1
- package/src/screens/chat-detail/ChatDay.tsx +0 -73
- package/src/types/message.ts +0 -18
- package/src/utils/resolveMessageType.ts +0 -51
|
@@ -0,0 +1,78 @@
|
|
|
1
|
+
import { useQuery } from '@tanstack/react-query';
|
|
2
|
+
import OpenIMSDK, { SessionType } from '@droppii/openim-rn-client-sdk';
|
|
3
|
+
import { useConversationStore } from '../../store/conversation';
|
|
4
|
+
import { apiInstance } from '../../services/apis';
|
|
5
|
+
import type { BaseResponse } from '../../types/auth';
|
|
6
|
+
import { conversationQueryKeys } from '../query-keys';
|
|
7
|
+
import { ENDPOINTS } from '../../services/endpoints';
|
|
8
|
+
|
|
9
|
+
interface UseGetConversationDetailParams {
|
|
10
|
+
targetConversationId?: string;
|
|
11
|
+
targetUserId?: string;
|
|
12
|
+
targetGroupId?: string;
|
|
13
|
+
targetBotId?: string;
|
|
14
|
+
}
|
|
15
|
+
|
|
16
|
+
interface UseGetConversationDetailResult {
|
|
17
|
+
conversationId: string;
|
|
18
|
+
isLoading: boolean;
|
|
19
|
+
}
|
|
20
|
+
|
|
21
|
+
const useBotConversationData = (botId?: string) =>
|
|
22
|
+
useQuery({
|
|
23
|
+
queryKey: conversationQueryKeys.detailByBotId(botId || ''),
|
|
24
|
+
queryFn: async () => {
|
|
25
|
+
const res = await apiInstance?.get<
|
|
26
|
+
BaseResponse<{ groupId: string; conversationId: string }>
|
|
27
|
+
>(ENDPOINTS.chatService.getConversationByBotId(botId || ''));
|
|
28
|
+
return res?.data?.data || undefined;
|
|
29
|
+
},
|
|
30
|
+
enabled: !!botId,
|
|
31
|
+
});
|
|
32
|
+
|
|
33
|
+
export const useGetOneConversation = ({
|
|
34
|
+
targetUserId,
|
|
35
|
+
targetGroupId,
|
|
36
|
+
}: {
|
|
37
|
+
targetUserId?: string;
|
|
38
|
+
targetGroupId?: string;
|
|
39
|
+
}) => {
|
|
40
|
+
return useQuery({
|
|
41
|
+
queryKey: conversationQueryKeys.detailBySourceId(
|
|
42
|
+
targetUserId || targetGroupId || ''
|
|
43
|
+
),
|
|
44
|
+
queryFn: async () => {
|
|
45
|
+
const res = await OpenIMSDK.getOneConversation({
|
|
46
|
+
sourceID: targetUserId || targetGroupId || '',
|
|
47
|
+
sessionType: targetUserId ? SessionType.Single : SessionType.Group,
|
|
48
|
+
});
|
|
49
|
+
if (res?.conversationID) {
|
|
50
|
+
useConversationStore.getState().updateConversations([res]);
|
|
51
|
+
}
|
|
52
|
+
return res || undefined;
|
|
53
|
+
},
|
|
54
|
+
enabled: !!targetUserId || !!targetGroupId,
|
|
55
|
+
});
|
|
56
|
+
};
|
|
57
|
+
|
|
58
|
+
export const useGetConversationDetail = ({
|
|
59
|
+
targetConversationId,
|
|
60
|
+
targetUserId,
|
|
61
|
+
targetGroupId,
|
|
62
|
+
targetBotId,
|
|
63
|
+
}: UseGetConversationDetailParams): UseGetConversationDetailResult => {
|
|
64
|
+
const { data: botData, isLoading: botIdLoading } =
|
|
65
|
+
useBotConversationData(targetBotId);
|
|
66
|
+
|
|
67
|
+
const { data: conversationData, isLoading: conversationLoading } =
|
|
68
|
+
useGetOneConversation({
|
|
69
|
+
targetUserId,
|
|
70
|
+
targetGroupId: targetGroupId || botData?.groupId,
|
|
71
|
+
});
|
|
72
|
+
|
|
73
|
+
return {
|
|
74
|
+
conversationId:
|
|
75
|
+
targetConversationId || conversationData?.conversationID || '',
|
|
76
|
+
isLoading: botIdLoading || conversationLoading,
|
|
77
|
+
};
|
|
78
|
+
};
|
|
@@ -20,7 +20,7 @@ export const useResetFlow = () => {
|
|
|
20
20
|
const { sendMessage } = useSendMessage();
|
|
21
21
|
const conversationFlow = useChatDetailContext().conversationFlow;
|
|
22
22
|
return useMutation({
|
|
23
|
-
mutationKey: conversationQueryKeys.
|
|
23
|
+
mutationKey: conversationQueryKeys.resetFlow(conversationId),
|
|
24
24
|
mutationFn: async () => {
|
|
25
25
|
await sendMessage({
|
|
26
26
|
plainText: trans('restart'),
|
|
@@ -0,0 +1,19 @@
|
|
|
1
|
+
import { useQuery } from '@tanstack/react-query';
|
|
2
|
+
import { conversationQueryKeys } from '../query-keys';
|
|
3
|
+
import { apiInstance } from '../../services/apis';
|
|
4
|
+
import type { BaseResponse } from '../../types/auth';
|
|
5
|
+
import type { InputButtonItem } from '../../types/flows';
|
|
6
|
+
import { ENDPOINTS } from '../../services/endpoints';
|
|
7
|
+
|
|
8
|
+
export const useGetConversationFlowMainMenu = (conversationId?: string) => {
|
|
9
|
+
return useQuery({
|
|
10
|
+
queryKey: [conversationQueryKeys.flowMainMenu(conversationId || '')],
|
|
11
|
+
queryFn: async () => {
|
|
12
|
+
const res = await apiInstance?.get<BaseResponse<InputButtonItem[]>>(
|
|
13
|
+
ENDPOINTS.chatService.conversationFlowMainMenu(conversationId || '')
|
|
14
|
+
);
|
|
15
|
+
return res?.data?.data || undefined;
|
|
16
|
+
},
|
|
17
|
+
enabled: !!conversationId,
|
|
18
|
+
});
|
|
19
|
+
};
|
|
@@ -1,14 +1,22 @@
|
|
|
1
1
|
import { useCallback } from 'react';
|
|
2
|
-
import type { UploadFileItem } from 'react-native-fs';
|
|
3
2
|
import { useConversationStore } from '../../store/conversation';
|
|
4
|
-
import type {
|
|
3
|
+
import type {
|
|
4
|
+
CustomMsgParams,
|
|
5
|
+
MessageItem,
|
|
6
|
+
OfflinePush,
|
|
7
|
+
} from '@droppii/openim-rn-client-sdk';
|
|
5
8
|
import { MessageStatus, MessageType } from '@droppii/openim-rn-client-sdk';
|
|
6
9
|
import { extractUrls } from '../../utils/url';
|
|
7
10
|
import OpenIMSDK from '@droppii/openim-rn-client-sdk';
|
|
8
|
-
import
|
|
11
|
+
import {
|
|
12
|
+
CustomMessageType,
|
|
13
|
+
type CustomMessagePayload,
|
|
14
|
+
type IMessageItemEx,
|
|
15
|
+
} from '../../types/chat';
|
|
9
16
|
import { useChatContext } from '../../context';
|
|
10
17
|
import { generateContentBasedOnMessageType } from '../../utils/conversation';
|
|
11
18
|
import { markMessageRevoked, useMessageStore } from '../../store/message';
|
|
19
|
+
import uuid from 'react-native-uuid';
|
|
12
20
|
|
|
13
21
|
import type { IUrlMetadata } from '../../types/common';
|
|
14
22
|
import type { IRunConversationFlowPayload } from '../../types/flows';
|
|
@@ -63,14 +71,14 @@ export const useSendMessage = () => {
|
|
|
63
71
|
const sendMessage = useCallback(
|
|
64
72
|
async ({
|
|
65
73
|
plainText,
|
|
66
|
-
files,
|
|
67
74
|
urlMetadata,
|
|
68
75
|
flow,
|
|
76
|
+
customMessage,
|
|
69
77
|
}: {
|
|
70
78
|
plainText?: string;
|
|
71
|
-
files?: UploadFileItem[];
|
|
72
79
|
urlMetadata?: IUrlMetadata;
|
|
73
80
|
flow?: IRunConversationFlowPayload;
|
|
81
|
+
customMessage?: CustomMessagePayload;
|
|
74
82
|
}) => {
|
|
75
83
|
const { userID: recvID, groupID } =
|
|
76
84
|
useConversationStore.getState().getCurrentConversation() || {};
|
|
@@ -78,13 +86,10 @@ export const useSendMessage = () => {
|
|
|
78
86
|
|
|
79
87
|
const messageList: MessageItem[] = [];
|
|
80
88
|
|
|
81
|
-
for (const file of files || []) {
|
|
82
|
-
if (!file) continue;
|
|
83
|
-
}
|
|
84
|
-
|
|
85
89
|
const hasText = !!plainText && plainText.trim() !== '';
|
|
86
90
|
const hasPreview = !!urlMetadata?.url;
|
|
87
91
|
|
|
92
|
+
//text msg
|
|
88
93
|
if (hasText || hasPreview) {
|
|
89
94
|
const urls = hasText ? extractUrls(plainText) : [];
|
|
90
95
|
const isUrlMessage = urls.length > 0 || hasPreview;
|
|
@@ -100,6 +105,21 @@ export const useSendMessage = () => {
|
|
|
100
105
|
messageList.push(message);
|
|
101
106
|
}
|
|
102
107
|
|
|
108
|
+
//custom msg
|
|
109
|
+
if (customMessage) {
|
|
110
|
+
let customElem: CustomMsgParams = {
|
|
111
|
+
data: JSON.stringify(customMessage.data),
|
|
112
|
+
extension: customMessage.type,
|
|
113
|
+
description:
|
|
114
|
+
customMessage?.type === CustomMessageType.Order
|
|
115
|
+
? customMessage?.data?.orderCode
|
|
116
|
+
: '',
|
|
117
|
+
};
|
|
118
|
+
const message = await createCustomMessage(customElem);
|
|
119
|
+
if (!message) return;
|
|
120
|
+
messageList.push(message);
|
|
121
|
+
}
|
|
122
|
+
|
|
103
123
|
for (const message of messageList) {
|
|
104
124
|
const extendMessageInfo: IMessageItemEx = {
|
|
105
125
|
applicationType,
|
|
@@ -212,10 +232,7 @@ const generateOfflinePushInfo = (
|
|
|
212
232
|
};
|
|
213
233
|
|
|
214
234
|
export const createTextMessage = async (text: string) => {
|
|
215
|
-
let textMessage = await OpenIMSDK.createTextMessage(
|
|
216
|
-
text,
|
|
217
|
-
new Date().getTime().toString()
|
|
218
|
-
)
|
|
235
|
+
let textMessage = await OpenIMSDK.createTextMessage(text, uuid.v4())
|
|
219
236
|
.then((data) => {
|
|
220
237
|
return data;
|
|
221
238
|
})
|
|
@@ -230,7 +247,7 @@ export const createUrlTextMessage = async (text: string, urls: string[]) => {
|
|
|
230
247
|
let urlTextMessage = await OpenIMSDK.createUrlTextMessage(
|
|
231
248
|
text,
|
|
232
249
|
urls,
|
|
233
|
-
|
|
250
|
+
uuid.v4()
|
|
234
251
|
)
|
|
235
252
|
.then((data) => {
|
|
236
253
|
return data;
|
|
@@ -241,3 +258,15 @@ export const createUrlTextMessage = async (text: string, urls: string[]) => {
|
|
|
241
258
|
});
|
|
242
259
|
return urlTextMessage;
|
|
243
260
|
};
|
|
261
|
+
|
|
262
|
+
export const createCustomMessage = async (params: CustomMsgParams) => {
|
|
263
|
+
let customMessage = await OpenIMSDK.createCustomMessage(params, uuid.v4())
|
|
264
|
+
.then((data) => {
|
|
265
|
+
return data;
|
|
266
|
+
})
|
|
267
|
+
.catch(({ errCode, errMsg }) => {
|
|
268
|
+
console.error('createUrlTextMessage', errCode, errMsg);
|
|
269
|
+
return null;
|
|
270
|
+
});
|
|
271
|
+
return customMessage;
|
|
272
|
+
};
|
package/src/hooks/query-keys.ts
CHANGED
|
@@ -12,11 +12,17 @@ export const conversationQueryKeys = {
|
|
|
12
12
|
detail: (conversationId: string) =>
|
|
13
13
|
[...conversationQueryKeys.details(), conversationId] as const,
|
|
14
14
|
flow: (conversationId: string) => ['conversationFlow', conversationId],
|
|
15
|
+
flowMainMenu: (conversationId: string) => [
|
|
16
|
+
'conversationFlowMainMenu',
|
|
17
|
+
conversationId,
|
|
18
|
+
],
|
|
15
19
|
resetFlow: (conversationId: string) => [
|
|
16
20
|
'resetConversationFlow',
|
|
17
21
|
conversationId,
|
|
18
22
|
],
|
|
19
23
|
runFlow: (conversationId: string) => ['runConversationFlow', conversationId],
|
|
24
|
+
detailByBotId: (botId: string) => ['conversationByBotId', botId],
|
|
25
|
+
detailBySourceId: (sourceId: string) => ['detailBySourceId', sourceId],
|
|
20
26
|
};
|
|
21
27
|
|
|
22
28
|
export type ConversationQueryKeys = typeof conversationQueryKeys;
|
|
@@ -151,7 +151,7 @@ export function useChatCompose() {
|
|
|
151
151
|
// Clear composer immediately — message is already in chat list with Sending status.
|
|
152
152
|
// User retries from the bubble, not the composer.
|
|
153
153
|
setText('');
|
|
154
|
-
await sendMessage({
|
|
154
|
+
await sendMessage({ plainText, urlMetadata: urlMeta });
|
|
155
155
|
}
|
|
156
156
|
}, [
|
|
157
157
|
imageAttachment,
|
package/src/index.tsx
CHANGED
|
@@ -14,6 +14,7 @@ export * from './store';
|
|
|
14
14
|
export * from './context';
|
|
15
15
|
export * from './hooks/useConversationList';
|
|
16
16
|
export * from './hooks/useChatMessages';
|
|
17
|
+
export * from './hooks/message/useSendMessage';
|
|
17
18
|
export { useImageAttachment } from './hooks/useImageAttachment';
|
|
18
19
|
export { useMediaViewer } from './hooks/useMediaViewer';
|
|
19
20
|
export type { MediaItem } from './hooks/useMediaViewer';
|
|
@@ -34,24 +35,32 @@ export {
|
|
|
34
35
|
ChatComposer,
|
|
35
36
|
ChatQuickActions,
|
|
36
37
|
ChatAttachmentPanel,
|
|
37
|
-
|
|
38
|
-
|
|
38
|
+
DEFAULT_QUICK_ACTIONS,
|
|
39
|
+
DEFAULT_PANNEL_ACTIONS,
|
|
40
|
+
DChatPannelActionItemType,
|
|
41
|
+
DChatQuickActionItemType,
|
|
39
42
|
} from './screens/chat-detail';
|
|
40
43
|
export type {
|
|
41
44
|
DChatActionItem,
|
|
42
45
|
DChatActionIconProvider,
|
|
43
46
|
DChatQuickAction,
|
|
44
|
-
|
|
47
|
+
DChatPannelAction,
|
|
45
48
|
ChatDetailProps,
|
|
46
49
|
ChatDetailHeaderProps,
|
|
47
50
|
ChatListProps,
|
|
48
51
|
ChatComposerProps,
|
|
49
52
|
ChatQuickActionsProps,
|
|
50
53
|
ChatQuickActionsRenderParams,
|
|
51
|
-
|
|
54
|
+
ChatPanelProps,
|
|
52
55
|
} from './screens/chat-detail';
|
|
53
56
|
|
|
54
|
-
export
|
|
55
|
-
export {
|
|
57
|
+
export { LoginStatus, MessageType } from '@droppii/openim-rn-client-sdk';
|
|
58
|
+
export type {
|
|
59
|
+
PeerType,
|
|
60
|
+
ConversationItem,
|
|
61
|
+
MessageItem,
|
|
62
|
+
} from '@droppii/openim-rn-client-sdk';
|
|
56
63
|
|
|
57
64
|
export { registerUIUtils, UIUtils } from './utils/UIUtils';
|
|
65
|
+
|
|
66
|
+
export { DFlowContext } from './types/flows';
|
|
@@ -8,8 +8,7 @@ import {
|
|
|
8
8
|
KSpacingValue,
|
|
9
9
|
} from '@droppii/libs';
|
|
10
10
|
import { ATTACHMENT_PANEL_COLUMNS } from './constants';
|
|
11
|
-
import {
|
|
12
|
-
import type { DChatAttachmentAction, ChatAttachmentPanelProps } from './types';
|
|
11
|
+
import type { DChatPannelAction, ChatPanelProps } from './types';
|
|
13
12
|
|
|
14
13
|
const AttachmentActionItem = memo(
|
|
15
14
|
({
|
|
@@ -17,9 +16,9 @@ const AttachmentActionItem = memo(
|
|
|
17
16
|
itemWidth,
|
|
18
17
|
onPress,
|
|
19
18
|
}: {
|
|
20
|
-
action:
|
|
19
|
+
action: DChatPannelAction;
|
|
21
20
|
itemWidth: `${number}%`;
|
|
22
|
-
onPress: (action:
|
|
21
|
+
onPress: (action: DChatPannelAction) => void;
|
|
23
22
|
}) => {
|
|
24
23
|
const handlePress = useCallback(() => {
|
|
25
24
|
onPress(action);
|
|
@@ -61,42 +60,26 @@ const AttachmentActionItem = memo(
|
|
|
61
60
|
AttachmentActionItem.displayName = 'AttachmentActionItem';
|
|
62
61
|
|
|
63
62
|
export const ChatAttachmentPanel = memo(
|
|
64
|
-
({
|
|
65
|
-
actions,
|
|
66
|
-
columns = ATTACHMENT_PANEL_COLUMNS,
|
|
67
|
-
onActionPress,
|
|
68
|
-
renderAction,
|
|
69
|
-
}: ChatAttachmentPanelProps) => {
|
|
70
|
-
const handleActionPress = useChatActionPress(onActionPress);
|
|
71
|
-
|
|
63
|
+
({ actions, columns = ATTACHMENT_PANEL_COLUMNS }: ChatPanelProps) => {
|
|
72
64
|
const itemWidth = useMemo(
|
|
73
65
|
() => `${100 / columns}%` as `${number}%`,
|
|
74
66
|
[columns]
|
|
75
67
|
);
|
|
76
68
|
|
|
77
|
-
const renderItem = useCallback<ListRenderItem<
|
|
69
|
+
const renderItem = useCallback<ListRenderItem<DChatPannelAction>>(
|
|
78
70
|
({ item }) => {
|
|
79
|
-
const onPress = () => handleActionPress(item);
|
|
80
|
-
|
|
81
|
-
if (renderAction) {
|
|
82
|
-
return <>{renderAction(item, onPress)}</>;
|
|
83
|
-
}
|
|
84
|
-
|
|
85
71
|
return (
|
|
86
72
|
<AttachmentActionItem
|
|
87
73
|
action={item}
|
|
88
74
|
itemWidth={itemWidth}
|
|
89
|
-
onPress={
|
|
75
|
+
onPress={() => item?.onPress?.()}
|
|
90
76
|
/>
|
|
91
77
|
);
|
|
92
78
|
},
|
|
93
|
-
[
|
|
79
|
+
[itemWidth]
|
|
94
80
|
);
|
|
95
81
|
|
|
96
|
-
const keyExtractor = useCallback(
|
|
97
|
-
(item: DChatAttachmentAction) => item.id,
|
|
98
|
-
[]
|
|
99
|
-
);
|
|
82
|
+
const keyExtractor = useCallback((item: DChatPannelAction) => item.id, []);
|
|
100
83
|
|
|
101
84
|
if (!actions?.length) {
|
|
102
85
|
return null;
|
|
@@ -18,11 +18,11 @@ import { ChatMessageInput } from './components/ChatMessageInput';
|
|
|
18
18
|
import { AttachmentPreview } from '../../components/AttachmentPreview';
|
|
19
19
|
|
|
20
20
|
import {
|
|
21
|
-
|
|
22
|
-
DEFAULT_Chat_QUICK_ACTIONS,
|
|
21
|
+
DEFAULT_QUICK_ACTIONS,
|
|
23
22
|
getAttachmentPanelHeight,
|
|
23
|
+
DEFAULT_PANNEL_ACTIONS,
|
|
24
24
|
} from './constants';
|
|
25
|
-
import type
|
|
25
|
+
import { DChatPannelActionItemType, type DChatPannelAction } from './types';
|
|
26
26
|
import { useChatComposerState } from './hooks/useChatComposerState';
|
|
27
27
|
import { useChatComposerAnimation } from './hooks/useChatComposerAnimation';
|
|
28
28
|
import { useChatDetailContext } from '../../context/ChatDetailContext';
|
|
@@ -35,10 +35,11 @@ import { useChatCompose } from '../../hooks/useChatCompose';
|
|
|
35
35
|
|
|
36
36
|
interface ChatComposerInternalProps {
|
|
37
37
|
isEmptyMessage?: boolean;
|
|
38
|
+
pannelActions?: DChatPannelAction[];
|
|
38
39
|
}
|
|
39
40
|
|
|
40
41
|
export const ChatComposer = memo(
|
|
41
|
-
({ isEmptyMessage = false }: ChatComposerInternalProps) => {
|
|
42
|
+
({ isEmptyMessage = false, pannelActions }: ChatComposerInternalProps) => {
|
|
42
43
|
const insets = useSafeAreaInsets();
|
|
43
44
|
|
|
44
45
|
const { isBotConversation, conversationFlow } = useChatDetailContext();
|
|
@@ -57,7 +58,7 @@ export const ChatComposer = memo(
|
|
|
57
58
|
} = useChatComposerState(compose.text);
|
|
58
59
|
|
|
59
60
|
const panelHeight = useMemo(
|
|
60
|
-
() => getAttachmentPanelHeight(
|
|
61
|
+
() => getAttachmentPanelHeight(DEFAULT_PANNEL_ACTIONS.length),
|
|
61
62
|
[]
|
|
62
63
|
);
|
|
63
64
|
|
|
@@ -132,18 +133,25 @@ export const ChatComposer = memo(
|
|
|
132
133
|
})
|
|
133
134
|
);
|
|
134
135
|
|
|
135
|
-
const
|
|
136
|
-
|
|
137
|
-
|
|
138
|
-
|
|
139
|
-
|
|
140
|
-
|
|
141
|
-
|
|
142
|
-
|
|
136
|
+
const resolvedPannelActons = useMemo(() => {
|
|
137
|
+
return (pannelActions || DEFAULT_PANNEL_ACTIONS)?.map((p) => {
|
|
138
|
+
let onPress;
|
|
139
|
+
switch (p.id) {
|
|
140
|
+
case DChatPannelActionItemType.Gallery:
|
|
141
|
+
onPress = debouncedImagePickerRef.current;
|
|
142
|
+
break;
|
|
143
|
+
case DChatPannelActionItemType.Documents:
|
|
144
|
+
onPress = debouncedFilePickerRef.current;
|
|
145
|
+
break;
|
|
146
|
+
default:
|
|
147
|
+
break;
|
|
143
148
|
}
|
|
144
|
-
|
|
145
|
-
|
|
146
|
-
|
|
149
|
+
return {
|
|
150
|
+
...p,
|
|
151
|
+
onPress: p.onPress || onPress,
|
|
152
|
+
};
|
|
153
|
+
});
|
|
154
|
+
}, [pannelActions]);
|
|
147
155
|
|
|
148
156
|
const inputRowStyle = useMemo(
|
|
149
157
|
() => ({ paddingBottom: isAttachmentOpen ? 8 : insets.bottom + 12 }),
|
|
@@ -186,7 +194,7 @@ export const ChatComposer = memo(
|
|
|
186
194
|
<KContainer.View background={'rgba(131, 137, 157, 0.05)'}>
|
|
187
195
|
<ChatQuickActions
|
|
188
196
|
visible
|
|
189
|
-
actions={
|
|
197
|
+
actions={DEFAULT_QUICK_ACTIONS}
|
|
190
198
|
onActionPress={(action) =>
|
|
191
199
|
console.log('[ChatComposer] quick action:', action.id)
|
|
192
200
|
}
|
|
@@ -272,10 +280,7 @@ export const ChatComposer = memo(
|
|
|
272
280
|
style={[styles.accessorySlot, accessorySlotStyle]}
|
|
273
281
|
pointerEvents={isAttachmentOpen ? 'auto' : 'none'}
|
|
274
282
|
>
|
|
275
|
-
<ChatAttachmentPanel
|
|
276
|
-
actions={DEFAULT_ATTACHMENT_ACTIONS}
|
|
277
|
-
onActionPress={handleAttachmentAction}
|
|
278
|
-
/>
|
|
283
|
+
<ChatAttachmentPanel actions={resolvedPannelActons} />
|
|
279
284
|
</Reanimated.View>
|
|
280
285
|
</KContainer.View>
|
|
281
286
|
);
|
|
@@ -14,30 +14,22 @@ import { useConversation, useConversationStore } from '../../store';
|
|
|
14
14
|
import ChatDetailHeader from './ChatDetailHeader';
|
|
15
15
|
import { ChatListLegend } from './ChatListLegend';
|
|
16
16
|
import { ChatComposer } from './ChatComposer';
|
|
17
|
-
import {
|
|
18
|
-
getConversationAvatarUri,
|
|
19
|
-
getConversationSubtitle,
|
|
20
|
-
getConversationTitle,
|
|
21
|
-
shouldShowAddMember,
|
|
22
|
-
} from './conversationHeader.utils';
|
|
17
|
+
import { shouldShowAddMember } from './conversationHeader.utils';
|
|
23
18
|
import type { ChatDetailProps } from './types';
|
|
24
|
-
import { ChatDetailProvider } from '../../context/ChatDetailContext';
|
|
25
19
|
import { normalizeUrl } from '../../utils/url';
|
|
26
|
-
// import { ChatMessageAPI } from '../../services/message';
|
|
27
20
|
import { MessageToolboxOverlay } from './messageToolbox/MessageToolboxOverlay';
|
|
28
21
|
import type { MeasuredRect, MessageToolboxRef } from './messageToolbox/types';
|
|
29
22
|
import type { DMessageItem } from '../../types/chat';
|
|
23
|
+
import { useGetConversationDetail } from '../../hooks/conversation/useGetConversationDetail';
|
|
30
24
|
|
|
31
25
|
const ChatDetail = memo(
|
|
32
26
|
({
|
|
33
|
-
|
|
27
|
+
targetConversationId = '',
|
|
28
|
+
targetUserId = '',
|
|
29
|
+
targetGroupId = '',
|
|
30
|
+
targetBotId = '',
|
|
34
31
|
enabled = true,
|
|
35
|
-
title,
|
|
36
|
-
subtitle,
|
|
37
|
-
avatarUri,
|
|
38
|
-
avatarFullName,
|
|
39
32
|
showAddMember,
|
|
40
|
-
getSubtitle,
|
|
41
33
|
onBack,
|
|
42
34
|
onPressSearch,
|
|
43
35
|
onPressAddMember,
|
|
@@ -45,10 +37,20 @@ const ChatDetail = memo(
|
|
|
45
37
|
onPressAvatar,
|
|
46
38
|
onPressUrl,
|
|
47
39
|
customMessageItemFactory,
|
|
40
|
+
pannelActions,
|
|
48
41
|
}: ChatDetailProps) => {
|
|
49
42
|
const navigation = useNavigation();
|
|
50
43
|
const mediaViewerRef = useRef<MediaViewerModalHandle>(null);
|
|
51
44
|
const messageToolboxRef = useRef<MessageToolboxRef>(null);
|
|
45
|
+
|
|
46
|
+
const { conversationId, isLoading: isLoadingConversation } =
|
|
47
|
+
useGetConversationDetail({
|
|
48
|
+
targetConversationId,
|
|
49
|
+
targetUserId,
|
|
50
|
+
targetGroupId,
|
|
51
|
+
targetBotId,
|
|
52
|
+
});
|
|
53
|
+
|
|
52
54
|
const conversation = useConversation(conversationId);
|
|
53
55
|
|
|
54
56
|
const handleBackDefault = useCallback(() => {
|
|
@@ -75,31 +77,16 @@ const ChatDetail = memo(
|
|
|
75
77
|
} = useChatMessages({ conversationId, enabled });
|
|
76
78
|
|
|
77
79
|
useEffect(() => {
|
|
78
|
-
|
|
80
|
+
if (conversationId) {
|
|
81
|
+
useConversationStore.getState().setCurrentConversation(conversationId);
|
|
82
|
+
}
|
|
83
|
+
return () => {
|
|
84
|
+
useConversationStore.getState().setCurrentConversation(undefined);
|
|
85
|
+
};
|
|
79
86
|
}, [conversationId]);
|
|
80
87
|
|
|
81
|
-
// useEffect(() => {
|
|
82
|
-
// if (!conversationId) return;
|
|
83
|
-
// ChatMessageAPI.searchLocalMessages(conversationId, { count: 20 })
|
|
84
|
-
// .then((result) => {
|
|
85
|
-
// console.log('[TEST searchLocalMessages] success:', result);
|
|
86
|
-
// })
|
|
87
|
-
// .catch((err) => {
|
|
88
|
-
// console.log('[TEST searchLocalMessages] error:', err);
|
|
89
|
-
// });
|
|
90
|
-
// }, [conversationId]);
|
|
91
|
-
|
|
92
|
-
const resolvedTitle = title ?? getConversationTitle(conversation);
|
|
93
|
-
const resolvedAvatarUri =
|
|
94
|
-
avatarUri ?? getConversationAvatarUri(conversation);
|
|
95
|
-
const resolvedAvatarFullName = avatarFullName ?? resolvedTitle;
|
|
96
88
|
const resolvedShowAddMember =
|
|
97
89
|
showAddMember ?? shouldShowAddMember(conversation);
|
|
98
|
-
const resolvedSubtitle = useMemo(() => {
|
|
99
|
-
if (subtitle !== undefined) return subtitle;
|
|
100
|
-
if (getSubtitle && conversation) return getSubtitle(conversation);
|
|
101
|
-
return getConversationSubtitle(conversation);
|
|
102
|
-
}, [conversation, getSubtitle, subtitle]);
|
|
103
90
|
|
|
104
91
|
const insets = useSafeAreaInsets();
|
|
105
92
|
|
|
@@ -123,51 +110,48 @@ const ChatDetail = memo(
|
|
|
123
110
|
);
|
|
124
111
|
|
|
125
112
|
return (
|
|
126
|
-
<
|
|
127
|
-
<
|
|
128
|
-
|
|
129
|
-
|
|
130
|
-
|
|
131
|
-
|
|
132
|
-
|
|
133
|
-
|
|
134
|
-
|
|
135
|
-
|
|
136
|
-
|
|
137
|
-
|
|
138
|
-
|
|
139
|
-
|
|
140
|
-
|
|
141
|
-
|
|
142
|
-
<
|
|
143
|
-
|
|
144
|
-
behavior="padding"
|
|
145
|
-
keyboardVerticalOffset={keyboardVerticalOffset}
|
|
146
|
-
>
|
|
147
|
-
<ChatListLegend
|
|
148
|
-
messages={messages}
|
|
149
|
-
currentUserId={currentUserId}
|
|
150
|
-
customMessageItemFactory={customMessageItemFactory}
|
|
151
|
-
onLoadEarlier={onLoadEarlier}
|
|
152
|
-
isLoading={isLoading}
|
|
153
|
-
isLoadingEarlier={isLoadingEarlier}
|
|
154
|
-
hasMoreEarlier={hasMoreEarlier}
|
|
155
|
-
onMediaPress={handleMediaPress}
|
|
156
|
-
onPressUrl={handlePressUrl}
|
|
157
|
-
onLongPress={handleMessageLongPress}
|
|
158
|
-
/>
|
|
159
|
-
|
|
160
|
-
<ChatComposer isEmptyMessage={messages?.length === 0} />
|
|
161
|
-
</KeyboardAvoidingView>
|
|
162
|
-
|
|
163
|
-
<MediaViewerModal ref={mediaViewerRef} />
|
|
164
|
-
<MessageToolboxOverlay
|
|
165
|
-
ref={messageToolboxRef}
|
|
113
|
+
<KContainer.Page flex edges={['bottom']}>
|
|
114
|
+
<ChatDetailHeader
|
|
115
|
+
conversationId={conversationId}
|
|
116
|
+
showAddMember={resolvedShowAddMember}
|
|
117
|
+
onBack={onBack ?? handleBackDefault}
|
|
118
|
+
onPressSearch={onPressSearch}
|
|
119
|
+
onPressAddMember={onPressAddMember}
|
|
120
|
+
onPressMenu={onPressMenu}
|
|
121
|
+
onPressAvatar={onPressAvatar}
|
|
122
|
+
/>
|
|
123
|
+
|
|
124
|
+
<KeyboardAvoidingView
|
|
125
|
+
style={styles.keyboardAvoiding}
|
|
126
|
+
behavior="padding"
|
|
127
|
+
keyboardVerticalOffset={keyboardVerticalOffset}
|
|
128
|
+
>
|
|
129
|
+
<ChatListLegend
|
|
130
|
+
messages={messages}
|
|
166
131
|
currentUserId={currentUserId}
|
|
167
132
|
customMessageItemFactory={customMessageItemFactory}
|
|
133
|
+
onLoadEarlier={onLoadEarlier}
|
|
134
|
+
isLoading={isLoading || isLoadingConversation}
|
|
135
|
+
isLoadingEarlier={isLoadingEarlier}
|
|
136
|
+
hasMoreEarlier={hasMoreEarlier}
|
|
137
|
+
onMediaPress={handleMediaPress}
|
|
138
|
+
onPressUrl={handlePressUrl}
|
|
139
|
+
onLongPress={handleMessageLongPress}
|
|
140
|
+
/>
|
|
141
|
+
|
|
142
|
+
<ChatComposer
|
|
143
|
+
isEmptyMessage={messages?.length === 0}
|
|
144
|
+
pannelActions={pannelActions}
|
|
168
145
|
/>
|
|
169
|
-
</
|
|
170
|
-
|
|
146
|
+
</KeyboardAvoidingView>
|
|
147
|
+
|
|
148
|
+
<MediaViewerModal ref={mediaViewerRef} />
|
|
149
|
+
<MessageToolboxOverlay
|
|
150
|
+
ref={messageToolboxRef}
|
|
151
|
+
currentUserId={currentUserId}
|
|
152
|
+
customMessageItemFactory={customMessageItemFactory}
|
|
153
|
+
/>
|
|
154
|
+
</KContainer.Page>
|
|
171
155
|
);
|
|
172
156
|
}
|
|
173
157
|
);
|