stream-chat-react-native-core 6.3.1 → 6.4.0-beta.2
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/commonjs/components/Attachment/AudioAttachment.js +255 -216
- package/lib/commonjs/components/Attachment/AudioAttachment.js.map +1 -1
- package/lib/commonjs/components/Attachment/FileAttachmentGroup.js +11 -11
- package/lib/commonjs/components/Attachment/FileAttachmentGroup.js.map +1 -1
- package/lib/commonjs/components/Attachment/Gallery.js +9 -0
- package/lib/commonjs/components/Attachment/Gallery.js.map +1 -1
- package/lib/commonjs/components/ChannelList/ChannelList.js +23 -0
- package/lib/commonjs/components/ChannelList/ChannelList.js.map +1 -1
- package/lib/commonjs/components/ChannelList/hooks/listeners/useAddedToChannelNotification.js +31 -8
- package/lib/commonjs/components/ChannelList/hooks/listeners/useAddedToChannelNotification.js.map +1 -1
- package/lib/commonjs/components/ChannelList/hooks/listeners/useChannelMemberUpdated.js +75 -0
- package/lib/commonjs/components/ChannelList/hooks/listeners/useChannelMemberUpdated.js.map +1 -0
- package/lib/commonjs/components/ChannelList/hooks/listeners/useNewMessage.js +21 -10
- package/lib/commonjs/components/ChannelList/hooks/listeners/useNewMessage.js.map +1 -1
- package/lib/commonjs/components/ChannelList/hooks/listeners/useNewMessageNotification.js +23 -7
- package/lib/commonjs/components/ChannelList/hooks/listeners/useNewMessageNotification.js.map +1 -1
- package/lib/commonjs/components/ChannelList/hooks/useChannelMembershipState.js +17 -0
- package/lib/commonjs/components/ChannelList/hooks/useChannelMembershipState.js.map +1 -0
- package/lib/commonjs/components/ChannelList/hooks/useSelectedChannelState.js +32 -0
- package/lib/commonjs/components/ChannelList/hooks/useSelectedChannelState.js.map +1 -0
- package/lib/commonjs/components/ChannelList/hooks/utils/index.js +102 -0
- package/lib/commonjs/components/ChannelList/hooks/utils/index.js.map +1 -0
- package/lib/commonjs/components/ChannelList/utils.js +23 -11
- package/lib/commonjs/components/ChannelList/utils.js.map +1 -1
- package/lib/commonjs/components/ChannelPreview/ChannelPreviewMessenger.js +1 -2
- package/lib/commonjs/components/ChannelPreview/ChannelPreviewMessenger.js.map +1 -1
- package/lib/commonjs/components/ImageGallery/components/ImageGalleryVideoControl.js +24 -13
- package/lib/commonjs/components/ImageGallery/components/ImageGalleryVideoControl.js.map +1 -1
- package/lib/commonjs/components/Message/Message.js.map +1 -1
- package/lib/commonjs/components/MessageInput/FileUploadPreview.js +35 -23
- package/lib/commonjs/components/MessageInput/FileUploadPreview.js.map +1 -1
- package/lib/commonjs/components/ProgressControl/ProgressControl.js +57 -54
- package/lib/commonjs/components/ProgressControl/ProgressControl.js.map +1 -1
- package/lib/commonjs/components/ProgressControl/WaveProgressBar.js +52 -52
- package/lib/commonjs/components/ProgressControl/WaveProgressBar.js.map +1 -1
- package/lib/commonjs/components/index.js +22 -0
- package/lib/commonjs/components/index.js.map +1 -1
- package/lib/commonjs/contexts/themeContext/utils/theme.js +1 -0
- package/lib/commonjs/contexts/themeContext/utils/theme.js.map +1 -1
- package/lib/commonjs/hooks/useAudioPlayer.js +158 -0
- package/lib/commonjs/hooks/useAudioPlayer.js.map +1 -0
- package/lib/commonjs/icons/Archieve.js +33 -0
- package/lib/commonjs/icons/Archieve.js.map +1 -0
- package/lib/commonjs/icons/Pause.js +2 -2
- package/lib/commonjs/icons/Pause.js.map +1 -1
- package/lib/commonjs/icons/Play.js +2 -2
- package/lib/commonjs/icons/Play.js.map +1 -1
- package/lib/commonjs/icons/index.js +11 -0
- package/lib/commonjs/icons/index.js.map +1 -1
- package/lib/commonjs/native.js.map +1 -1
- package/lib/commonjs/types/types.js.map +1 -1
- package/lib/commonjs/version.json +1 -1
- package/lib/module/components/Attachment/AudioAttachment.js +255 -216
- package/lib/module/components/Attachment/AudioAttachment.js.map +1 -1
- package/lib/module/components/Attachment/FileAttachmentGroup.js +11 -11
- package/lib/module/components/Attachment/FileAttachmentGroup.js.map +1 -1
- package/lib/module/components/Attachment/Gallery.js +9 -0
- package/lib/module/components/Attachment/Gallery.js.map +1 -1
- package/lib/module/components/ChannelList/ChannelList.js +23 -0
- package/lib/module/components/ChannelList/ChannelList.js.map +1 -1
- package/lib/module/components/ChannelList/hooks/listeners/useAddedToChannelNotification.js +31 -8
- package/lib/module/components/ChannelList/hooks/listeners/useAddedToChannelNotification.js.map +1 -1
- package/lib/module/components/ChannelList/hooks/listeners/useChannelMemberUpdated.js +75 -0
- package/lib/module/components/ChannelList/hooks/listeners/useChannelMemberUpdated.js.map +1 -0
- package/lib/module/components/ChannelList/hooks/listeners/useNewMessage.js +21 -10
- package/lib/module/components/ChannelList/hooks/listeners/useNewMessage.js.map +1 -1
- package/lib/module/components/ChannelList/hooks/listeners/useNewMessageNotification.js +23 -7
- package/lib/module/components/ChannelList/hooks/listeners/useNewMessageNotification.js.map +1 -1
- package/lib/module/components/ChannelList/hooks/useChannelMembershipState.js +17 -0
- package/lib/module/components/ChannelList/hooks/useChannelMembershipState.js.map +1 -0
- package/lib/module/components/ChannelList/hooks/useSelectedChannelState.js +32 -0
- package/lib/module/components/ChannelList/hooks/useSelectedChannelState.js.map +1 -0
- package/lib/module/components/ChannelList/hooks/utils/index.js +102 -0
- package/lib/module/components/ChannelList/hooks/utils/index.js.map +1 -0
- package/lib/module/components/ChannelList/utils.js +23 -11
- package/lib/module/components/ChannelList/utils.js.map +1 -1
- package/lib/module/components/ChannelPreview/ChannelPreviewMessenger.js +1 -2
- package/lib/module/components/ChannelPreview/ChannelPreviewMessenger.js.map +1 -1
- package/lib/module/components/ImageGallery/components/ImageGalleryVideoControl.js +24 -13
- package/lib/module/components/ImageGallery/components/ImageGalleryVideoControl.js.map +1 -1
- package/lib/module/components/Message/Message.js.map +1 -1
- package/lib/module/components/MessageInput/FileUploadPreview.js +35 -23
- package/lib/module/components/MessageInput/FileUploadPreview.js.map +1 -1
- package/lib/module/components/ProgressControl/ProgressControl.js +57 -54
- package/lib/module/components/ProgressControl/ProgressControl.js.map +1 -1
- package/lib/module/components/ProgressControl/WaveProgressBar.js +52 -52
- package/lib/module/components/ProgressControl/WaveProgressBar.js.map +1 -1
- package/lib/module/components/index.js +22 -0
- package/lib/module/components/index.js.map +1 -1
- package/lib/module/contexts/themeContext/utils/theme.js +1 -0
- package/lib/module/contexts/themeContext/utils/theme.js.map +1 -1
- package/lib/module/hooks/useAudioPlayer.js +158 -0
- package/lib/module/hooks/useAudioPlayer.js.map +1 -0
- package/lib/module/icons/Archieve.js +33 -0
- package/lib/module/icons/Archieve.js.map +1 -0
- package/lib/module/icons/Pause.js +2 -2
- package/lib/module/icons/Pause.js.map +1 -1
- package/lib/module/icons/Play.js +2 -2
- package/lib/module/icons/Play.js.map +1 -1
- package/lib/module/icons/index.js +11 -0
- package/lib/module/icons/index.js.map +1 -1
- package/lib/module/native.js.map +1 -1
- package/lib/module/types/types.js.map +1 -1
- package/lib/module/version.json +1 -1
- package/lib/typescript/components/Attachment/AudioAttachment.d.ts +2 -2
- package/lib/typescript/components/Attachment/AudioAttachment.d.ts.map +1 -1
- package/lib/typescript/components/Attachment/FileAttachmentGroup.d.ts.map +1 -1
- package/lib/typescript/components/Attachment/Gallery.d.ts.map +1 -1
- package/lib/typescript/components/ChannelList/ChannelList.d.ts +20 -6
- package/lib/typescript/components/ChannelList/ChannelList.d.ts.map +1 -1
- package/lib/typescript/components/ChannelList/hooks/listeners/useAddedToChannelNotification.d.ts +4 -3
- package/lib/typescript/components/ChannelList/hooks/listeners/useAddedToChannelNotification.d.ts.map +1 -1
- package/lib/typescript/components/ChannelList/hooks/listeners/useChannelMemberUpdated.d.ts +12 -0
- package/lib/typescript/components/ChannelList/hooks/listeners/useChannelMemberUpdated.d.ts.map +1 -0
- package/lib/typescript/components/ChannelList/hooks/listeners/useNewMessage.d.ts +4 -3
- package/lib/typescript/components/ChannelList/hooks/listeners/useNewMessage.d.ts.map +1 -1
- package/lib/typescript/components/ChannelList/hooks/listeners/useNewMessageNotification.d.ts +4 -3
- package/lib/typescript/components/ChannelList/hooks/listeners/useNewMessageNotification.d.ts.map +1 -1
- package/lib/typescript/components/ChannelList/hooks/useChannelMembershipState.d.ts +5 -0
- package/lib/typescript/components/ChannelList/hooks/useChannelMembershipState.d.ts.map +1 -0
- package/lib/typescript/components/ChannelList/hooks/useSelectedChannelState.d.ts +13 -0
- package/lib/typescript/components/ChannelList/hooks/useSelectedChannelState.d.ts.map +1 -0
- package/lib/typescript/components/ChannelList/hooks/utils/index.d.ts +22 -0
- package/lib/typescript/components/ChannelList/hooks/utils/index.d.ts.map +1 -0
- package/lib/typescript/components/ChannelList/utils.d.ts +10 -4
- package/lib/typescript/components/ChannelList/utils.d.ts.map +1 -1
- package/lib/typescript/components/ChannelPreview/ChannelPreviewMessenger.d.ts.map +1 -1
- package/lib/typescript/components/ImageGallery/components/ImageGalleryVideoControl.d.ts.map +1 -1
- package/lib/typescript/components/Message/Message.d.ts +22 -11
- package/lib/typescript/components/Message/Message.d.ts.map +1 -1
- package/lib/typescript/components/MessageInput/FileUploadPreview.d.ts.map +1 -1
- package/lib/typescript/components/ProgressControl/ProgressControl.d.ts +35 -2
- package/lib/typescript/components/ProgressControl/ProgressControl.d.ts.map +1 -1
- package/lib/typescript/components/ProgressControl/WaveProgressBar.d.ts +27 -0
- package/lib/typescript/components/ProgressControl/WaveProgressBar.d.ts.map +1 -1
- package/lib/typescript/components/index.d.ts +2 -0
- package/lib/typescript/components/index.d.ts.map +1 -1
- package/lib/typescript/contexts/themeContext/utils/theme.d.ts +1 -0
- package/lib/typescript/contexts/themeContext/utils/theme.d.ts.map +1 -1
- package/lib/typescript/hooks/useAudioPlayer.d.ts +16 -0
- package/lib/typescript/hooks/useAudioPlayer.d.ts.map +1 -0
- package/lib/typescript/icons/Archieve.d.ts +4 -0
- package/lib/typescript/icons/Archieve.d.ts.map +1 -0
- package/lib/typescript/icons/Pause.d.ts.map +1 -1
- package/lib/typescript/icons/index.d.ts +1 -0
- package/lib/typescript/icons/index.d.ts.map +1 -1
- package/lib/typescript/native.d.ts +10 -3
- package/lib/typescript/native.d.ts.map +1 -1
- package/lib/typescript/types/types.d.ts +5 -1
- package/lib/typescript/types/types.d.ts.map +1 -1
- package/package.json +4 -2
- package/src/components/Attachment/AudioAttachment.tsx +173 -137
- package/src/components/Attachment/FileAttachmentGroup.tsx +9 -16
- package/src/components/Attachment/Gallery.tsx +3 -0
- package/src/components/ChannelList/ChannelList.tsx +38 -3
- package/src/components/ChannelList/hooks/listeners/useAddedToChannelNotification.ts +32 -3
- package/src/components/ChannelList/hooks/listeners/useChannelMemberUpdated.ts +116 -0
- package/src/components/ChannelList/hooks/listeners/useNewMessage.ts +46 -17
- package/src/components/ChannelList/hooks/listeners/useNewMessageNotification.ts +18 -3
- package/src/components/ChannelList/hooks/useChannelMembershipState.ts +22 -0
- package/src/components/ChannelList/hooks/useSelectedChannelState.ts +57 -0
- package/src/components/ChannelList/hooks/utils/index.ts +130 -0
- package/src/components/ChannelList/utils.ts +50 -14
- package/src/components/ChannelPreview/ChannelPreviewMessenger.tsx +1 -2
- package/src/components/ImageGallery/components/ImageGalleryVideoControl.tsx +23 -13
- package/src/components/Message/Message.tsx +26 -4
- package/src/components/MessageInput/FileUploadPreview.tsx +29 -28
- package/src/components/ProgressControl/ProgressControl.tsx +115 -92
- package/src/components/ProgressControl/WaveProgressBar.tsx +96 -59
- package/src/components/index.ts +2 -0
- package/src/contexts/themeContext/utils/theme.ts +2 -0
- package/src/hooks/useAudioPlayer.ts +59 -0
- package/src/icons/Archieve.tsx +10 -0
- package/src/icons/Pause.tsx +2 -5
- package/src/icons/Play.tsx +2 -2
- package/src/icons/index.ts +1 -0
- package/src/native.ts +11 -3
- package/src/types/types.ts +14 -1
- package/src/version.json +1 -1
|
@@ -1,31 +1,67 @@
|
|
|
1
|
-
import
|
|
2
|
-
|
|
1
|
+
import type { Channel, ChannelSort, StreamChat } from 'stream-chat';
|
|
2
|
+
|
|
3
|
+
import { findLastPinnedChannelIndex, shouldConsiderPinnedChannels } from './hooks/utils';
|
|
3
4
|
|
|
4
5
|
import type { DefaultStreamChatGenerics } from '../../types/types';
|
|
5
6
|
|
|
6
7
|
type MoveParameters<
|
|
7
8
|
StreamChatGenerics extends DefaultStreamChatGenerics = DefaultStreamChatGenerics,
|
|
8
9
|
> = {
|
|
9
|
-
channels: Channel<StreamChatGenerics
|
|
10
|
-
|
|
10
|
+
channels: Array<Channel<StreamChatGenerics>>;
|
|
11
|
+
channelToMove: Channel<StreamChatGenerics>;
|
|
12
|
+
/**
|
|
13
|
+
* If the index of the channel within `channels` list which is being moved upwards
|
|
14
|
+
* (`channelToMove`) is known, you can supply it to skip extra calculation.
|
|
15
|
+
*/
|
|
16
|
+
channelToMoveIndexWithinChannels?: number;
|
|
17
|
+
sort?: ChannelSort<StreamChatGenerics>;
|
|
11
18
|
};
|
|
12
19
|
|
|
13
20
|
export const moveChannelUp = <
|
|
14
21
|
StreamChatGenerics extends DefaultStreamChatGenerics = DefaultStreamChatGenerics,
|
|
15
22
|
>({
|
|
16
|
-
channels
|
|
17
|
-
|
|
23
|
+
channels,
|
|
24
|
+
channelToMove,
|
|
25
|
+
channelToMoveIndexWithinChannels,
|
|
26
|
+
sort,
|
|
18
27
|
}: MoveParameters<StreamChatGenerics>) => {
|
|
19
|
-
// get channel
|
|
20
|
-
const
|
|
21
|
-
|
|
22
|
-
|
|
28
|
+
// get index of channel to move up
|
|
29
|
+
const targetChannelIndex =
|
|
30
|
+
channelToMoveIndexWithinChannels ??
|
|
31
|
+
channels.findIndex((channel) => channel.cid === channelToMove.cid);
|
|
32
|
+
|
|
33
|
+
const targetChannelExistsWithinList = targetChannelIndex >= 0;
|
|
34
|
+
const targetChannelAlreadyAtTheTop = targetChannelIndex === 0;
|
|
35
|
+
|
|
36
|
+
// pinned channels should not move within the list based on recent activity, channels which
|
|
37
|
+
// receive messages and are not pinned should move upwards but only under the last pinned channel
|
|
38
|
+
// in the list
|
|
39
|
+
const considerPinnedChannels = shouldConsiderPinnedChannels(sort);
|
|
40
|
+
|
|
41
|
+
if (targetChannelAlreadyAtTheTop) return channels;
|
|
42
|
+
|
|
43
|
+
const newChannels = [...channels];
|
|
44
|
+
|
|
45
|
+
// target channel index is known, remove it from the list
|
|
46
|
+
if (targetChannelExistsWithinList) {
|
|
47
|
+
newChannels.splice(targetChannelIndex, 1);
|
|
48
|
+
}
|
|
49
|
+
|
|
50
|
+
// as position of pinned channels has to stay unchanged, we need to
|
|
51
|
+
// find last pinned channel in the list to move the target channel after
|
|
52
|
+
let lastPinnedChannelIndex: number | null = null;
|
|
53
|
+
if (considerPinnedChannels) {
|
|
54
|
+
lastPinnedChannelIndex = findLastPinnedChannelIndex({ channels: newChannels });
|
|
55
|
+
}
|
|
23
56
|
|
|
24
|
-
//
|
|
25
|
-
|
|
26
|
-
|
|
57
|
+
// re-insert it at the new place (to specific index if pinned channels are considered)
|
|
58
|
+
newChannels.splice(
|
|
59
|
+
typeof lastPinnedChannelIndex === 'number' ? lastPinnedChannelIndex + 1 : 0,
|
|
60
|
+
0,
|
|
61
|
+
channelToMove,
|
|
62
|
+
);
|
|
27
63
|
|
|
28
|
-
return
|
|
64
|
+
return newChannels;
|
|
29
65
|
};
|
|
30
66
|
|
|
31
67
|
type GetParameters<
|
|
@@ -1,6 +1,5 @@
|
|
|
1
1
|
import React from 'react';
|
|
2
|
-
import { StyleSheet, View } from 'react-native';
|
|
3
|
-
import { TouchableOpacity } from 'react-native-gesture-handler';
|
|
2
|
+
import { StyleSheet, TouchableOpacity, View } from 'react-native';
|
|
4
3
|
|
|
5
4
|
import { ChannelAvatar } from './ChannelAvatar';
|
|
6
5
|
import type { ChannelPreviewProps } from './ChannelPreview';
|
|
@@ -12,6 +12,14 @@ import { ProgressControl } from '../../ProgressControl/ProgressControl';
|
|
|
12
12
|
const styles = StyleSheet.create({
|
|
13
13
|
durationTextStyle: {
|
|
14
14
|
fontWeight: 'bold',
|
|
15
|
+
marginLeft: 16,
|
|
16
|
+
},
|
|
17
|
+
progressContainer: {
|
|
18
|
+
flex: 1,
|
|
19
|
+
},
|
|
20
|
+
progressDurationText: {
|
|
21
|
+
fontWeight: 'bold',
|
|
22
|
+
marginRight: 16,
|
|
15
23
|
},
|
|
16
24
|
roundedView: {
|
|
17
25
|
alignItems: 'center',
|
|
@@ -20,15 +28,15 @@ const styles = StyleSheet.create({
|
|
|
20
28
|
elevation: 2,
|
|
21
29
|
height: 36,
|
|
22
30
|
justifyContent: 'center',
|
|
31
|
+
marginRight: 16,
|
|
23
32
|
width: 36,
|
|
24
33
|
},
|
|
25
34
|
videoContainer: {
|
|
26
35
|
alignItems: 'center',
|
|
27
36
|
backgroundColor: 'rgba(52, 52, 52, 0.1)',
|
|
28
|
-
display: 'flex',
|
|
29
37
|
flexDirection: 'row',
|
|
30
|
-
justifyContent: 'space-
|
|
31
|
-
padding:
|
|
38
|
+
justifyContent: 'space-evenly',
|
|
39
|
+
padding: 12,
|
|
32
40
|
},
|
|
33
41
|
});
|
|
34
42
|
|
|
@@ -46,7 +54,7 @@ export const ImageGalleryVideoControl = React.memo(
|
|
|
46
54
|
theme: {
|
|
47
55
|
colors: { accent_blue, black, static_black, static_white },
|
|
48
56
|
imageGallery: {
|
|
49
|
-
videoControl: { durationTextStyle, roundedView, videoContainer },
|
|
57
|
+
videoControl: { durationTextStyle, progressDurationText, roundedView, videoContainer },
|
|
50
58
|
},
|
|
51
59
|
},
|
|
52
60
|
} = useTheme();
|
|
@@ -74,18 +82,20 @@ export const ImageGalleryVideoControl = React.memo(
|
|
|
74
82
|
</TouchableOpacity>
|
|
75
83
|
<Text
|
|
76
84
|
accessibilityLabel='Progress Duration'
|
|
77
|
-
style={[styles.
|
|
85
|
+
style={[styles.progressDurationText, { color: black }, progressDurationText]}
|
|
78
86
|
>
|
|
79
87
|
{progressDuration}
|
|
80
88
|
</Text>
|
|
81
|
-
<
|
|
82
|
-
|
|
83
|
-
|
|
84
|
-
|
|
85
|
-
|
|
86
|
-
|
|
87
|
-
|
|
88
|
-
|
|
89
|
+
<View style={styles.progressContainer}>
|
|
90
|
+
<ProgressControl
|
|
91
|
+
duration={duration}
|
|
92
|
+
filledColor={accent_blue}
|
|
93
|
+
progress={progress}
|
|
94
|
+
testID={'progress-control'}
|
|
95
|
+
width={180}
|
|
96
|
+
/>
|
|
97
|
+
</View>
|
|
98
|
+
|
|
89
99
|
<Text
|
|
90
100
|
accessibilityLabel='Video Duration'
|
|
91
101
|
style={[styles.durationTextStyle, { color: black }, durationTextStyle]}
|
|
@@ -40,6 +40,7 @@ import {
|
|
|
40
40
|
isEditedMessage,
|
|
41
41
|
MessageStatusTypes,
|
|
42
42
|
} from '../../utils/utils';
|
|
43
|
+
import type { Thumbnail } from '../Attachment/utils/buildGallery/types';
|
|
43
44
|
|
|
44
45
|
import {
|
|
45
46
|
isMessageWithStylesReadByAndDateSeparator,
|
|
@@ -55,23 +56,40 @@ export type TouchableEmitter =
|
|
|
55
56
|
| 'messageReplies'
|
|
56
57
|
| 'reactionList';
|
|
57
58
|
|
|
59
|
+
export type TextMentionTouchableHandlerAdditionalInfo<
|
|
60
|
+
StreamChatGenerics extends DefaultStreamChatGenerics = DefaultStreamChatGenerics,
|
|
61
|
+
> = { user?: UserResponse<StreamChatGenerics> };
|
|
62
|
+
|
|
58
63
|
export type TextMentionTouchableHandlerPayload<
|
|
59
64
|
StreamChatGenerics extends DefaultStreamChatGenerics = DefaultStreamChatGenerics,
|
|
60
65
|
> = {
|
|
61
66
|
emitter: 'textMention';
|
|
62
|
-
additionalInfo?:
|
|
67
|
+
additionalInfo?: TextMentionTouchableHandlerAdditionalInfo<StreamChatGenerics>;
|
|
63
68
|
};
|
|
64
69
|
|
|
70
|
+
export type UrlTouchableHandlerAdditionalInfo = { url?: string };
|
|
71
|
+
|
|
65
72
|
export type UrlTouchableHandlerPayload = {
|
|
66
73
|
emitter: 'textLink' | 'card';
|
|
67
|
-
additionalInfo?:
|
|
74
|
+
additionalInfo?: UrlTouchableHandlerAdditionalInfo;
|
|
68
75
|
};
|
|
69
76
|
|
|
77
|
+
export type FileAttachmentTouchableHandlerAdditionalInfo<
|
|
78
|
+
StreamChatGenerics extends DefaultStreamChatGenerics = DefaultStreamChatGenerics,
|
|
79
|
+
> = { attachment?: Attachment<StreamChatGenerics> };
|
|
80
|
+
|
|
70
81
|
export type FileAttachmentTouchableHandlerPayload<
|
|
71
82
|
StreamChatGenerics extends DefaultStreamChatGenerics = DefaultStreamChatGenerics,
|
|
72
83
|
> = {
|
|
73
84
|
emitter: 'fileAttachment';
|
|
74
|
-
additionalInfo?:
|
|
85
|
+
additionalInfo?: FileAttachmentTouchableHandlerAdditionalInfo<StreamChatGenerics>;
|
|
86
|
+
};
|
|
87
|
+
|
|
88
|
+
export type GalleryThumbnailTouchableHandlerAdditionalInfo = { thumbnail?: Thumbnail };
|
|
89
|
+
|
|
90
|
+
export type GalleryThumbnailTouchableHandlerPayload = {
|
|
91
|
+
emitter: 'gallery';
|
|
92
|
+
additionalInfo?: GalleryThumbnailTouchableHandlerAdditionalInfo;
|
|
75
93
|
};
|
|
76
94
|
|
|
77
95
|
export type PressableHandlerPayload = {
|
|
@@ -79,11 +97,15 @@ export type PressableHandlerPayload = {
|
|
|
79
97
|
event?: GestureResponderEvent;
|
|
80
98
|
} & (
|
|
81
99
|
| {
|
|
82
|
-
emitter?: Exclude<
|
|
100
|
+
emitter?: Exclude<
|
|
101
|
+
TouchableEmitter,
|
|
102
|
+
'textMention' | 'textLink' | 'card' | 'fileAttachment' | 'gallery'
|
|
103
|
+
>;
|
|
83
104
|
}
|
|
84
105
|
| TextMentionTouchableHandlerPayload
|
|
85
106
|
| UrlTouchableHandlerPayload
|
|
86
107
|
| FileAttachmentTouchableHandlerPayload
|
|
108
|
+
| GalleryThumbnailTouchableHandlerPayload
|
|
87
109
|
);
|
|
88
110
|
|
|
89
111
|
export type MessagePressableHandlerPayload<
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import React, { useEffect, useRef, useState } from 'react';
|
|
1
|
+
import React, { useEffect, useMemo, useRef, useState } from 'react';
|
|
2
2
|
import { FlatList, I18nManager, StyleSheet, Text, TouchableOpacity, View } from 'react-native';
|
|
3
3
|
|
|
4
4
|
import { UploadProgressIndicator } from './UploadProgressIndicator';
|
|
@@ -143,18 +143,19 @@ const FileUploadPreviewWithContext = <
|
|
|
143
143
|
FileAttachmentIcon,
|
|
144
144
|
fileUploads,
|
|
145
145
|
removeFile,
|
|
146
|
-
setFileUploads,
|
|
147
146
|
uploadFile,
|
|
148
147
|
} = props;
|
|
149
148
|
|
|
149
|
+
const [filesToDisplay, setFilesToDisplay] = useState<FileUpload[]>([]);
|
|
150
|
+
|
|
150
151
|
const flatListRef = useRef<FlatList<FileUpload> | null>(null);
|
|
151
152
|
const [flatListWidth, setFlatListWidth] = useState(0);
|
|
152
153
|
|
|
153
154
|
useEffect(() => {
|
|
154
|
-
|
|
155
|
+
setFilesToDisplay(
|
|
155
156
|
fileUploads.map((file) => ({
|
|
156
157
|
...file,
|
|
157
|
-
duration: file.duration || 0,
|
|
158
|
+
duration: file.duration || filesToDisplay.find((f) => f.id === file.id)?.duration || 0,
|
|
158
159
|
paused: true,
|
|
159
160
|
progress: 0,
|
|
160
161
|
})),
|
|
@@ -164,31 +165,20 @@ const FileUploadPreviewWithContext = <
|
|
|
164
165
|
|
|
165
166
|
// Handler triggered when an audio is loaded in the message input. The initial state is defined for the audio here and the duration is set.
|
|
166
167
|
const onLoad = (index: string, duration: number) => {
|
|
167
|
-
|
|
168
|
-
|
|
168
|
+
setFilesToDisplay((prevFilesUploads) =>
|
|
169
|
+
prevFilesUploads.map((fileUpload, id) => ({
|
|
169
170
|
...fileUpload,
|
|
170
|
-
duration:
|
|
171
|
-
file: {
|
|
172
|
-
...fileUpload.file,
|
|
173
|
-
duration: fileUpload.id === index ? duration : fileUpload.duration,
|
|
174
|
-
},
|
|
171
|
+
duration: id.toString() === index ? duration : fileUpload.duration,
|
|
175
172
|
})),
|
|
176
173
|
);
|
|
177
174
|
};
|
|
178
175
|
|
|
179
176
|
// The handler which is triggered when the audio progresses/ the thumb is dragged in the progress control. The progressed duration is set here.
|
|
180
|
-
const onProgress = (index: string,
|
|
181
|
-
|
|
182
|
-
|
|
177
|
+
const onProgress = (index: string, progress: number) => {
|
|
178
|
+
setFilesToDisplay((prevFilesUploads) =>
|
|
179
|
+
prevFilesUploads.map((fileUpload, id) => ({
|
|
183
180
|
...fileUpload,
|
|
184
|
-
progress:
|
|
185
|
-
fileUpload.id === index
|
|
186
|
-
? hasEnd
|
|
187
|
-
? 1
|
|
188
|
-
: currentTime
|
|
189
|
-
? currentTime / (fileUpload.duration as number)
|
|
190
|
-
: 0
|
|
191
|
-
: fileUpload.progress,
|
|
181
|
+
progress: id.toString() === index ? progress : fileUpload.progress,
|
|
192
182
|
})),
|
|
193
183
|
);
|
|
194
184
|
};
|
|
@@ -197,15 +187,15 @@ const FileUploadPreviewWithContext = <
|
|
|
197
187
|
const onPlayPause = (index: string, pausedStatus?: boolean) => {
|
|
198
188
|
if (pausedStatus === false) {
|
|
199
189
|
// If the status is false we set the audio with the index as playing and the others as paused.
|
|
200
|
-
|
|
201
|
-
prevFileUploads.map((fileUpload) => ({
|
|
190
|
+
setFilesToDisplay((prevFileUploads) =>
|
|
191
|
+
prevFileUploads.map((fileUpload, id) => ({
|
|
202
192
|
...fileUpload,
|
|
203
|
-
paused:
|
|
193
|
+
paused: id.toString() !== index,
|
|
204
194
|
})),
|
|
205
195
|
);
|
|
206
196
|
} else {
|
|
207
197
|
// If the status is true we simply set all the audio's paused state as true.
|
|
208
|
-
|
|
198
|
+
setFilesToDisplay((prevFileUploads) =>
|
|
209
199
|
prevFileUploads.map((fileUpload) => ({
|
|
210
200
|
...fileUpload,
|
|
211
201
|
paused: true,
|
|
@@ -225,6 +215,7 @@ const FileUploadPreviewWithContext = <
|
|
|
225
215
|
|
|
226
216
|
const renderItem = ({ item }: { item: FileUpload }) => {
|
|
227
217
|
const indicatorType = getIndicatorTypeForFileState(item.state, enableOfflineSupport);
|
|
218
|
+
const isAudio = item.file.mimeType?.startsWith('audio/');
|
|
228
219
|
|
|
229
220
|
return (
|
|
230
221
|
<>
|
|
@@ -235,13 +226,14 @@ const FileUploadPreviewWithContext = <
|
|
|
235
226
|
style={styles.overlay}
|
|
236
227
|
type={indicatorType}
|
|
237
228
|
>
|
|
238
|
-
{
|
|
229
|
+
{isAudio && isSoundPackageAvailable() ? (
|
|
239
230
|
<AudioAttachmentUploadPreview
|
|
240
231
|
hideProgressBar={true}
|
|
241
232
|
item={item}
|
|
242
233
|
onLoad={onLoad}
|
|
243
234
|
onPlayPause={onPlayPause}
|
|
244
235
|
onProgress={onProgress}
|
|
236
|
+
showSpeedSettings={false}
|
|
245
237
|
testID='audio-attachment-upload-preview'
|
|
246
238
|
/>
|
|
247
239
|
) : (
|
|
@@ -308,9 +300,18 @@ const FileUploadPreviewWithContext = <
|
|
|
308
300
|
}
|
|
309
301
|
}, [fileUploadsLength]);
|
|
310
302
|
|
|
303
|
+
const memoizedFilesToDisplay = useMemo(
|
|
304
|
+
() =>
|
|
305
|
+
filesToDisplay.map((file, index) => ({
|
|
306
|
+
...file,
|
|
307
|
+
id: index.toString(),
|
|
308
|
+
})),
|
|
309
|
+
[filesToDisplay],
|
|
310
|
+
);
|
|
311
|
+
|
|
311
312
|
return fileUploadsLength ? (
|
|
312
313
|
<FlatList
|
|
313
|
-
data={
|
|
314
|
+
data={memoizedFilesToDisplay}
|
|
314
315
|
getItemLayout={(_, index) => ({
|
|
315
316
|
index,
|
|
316
317
|
length: FILE_PREVIEW_HEIGHT + 8,
|
|
@@ -1,26 +1,52 @@
|
|
|
1
|
-
import React, {
|
|
2
|
-
import {
|
|
1
|
+
import React, { useState } from 'react';
|
|
2
|
+
import { StyleSheet, View } from 'react-native';
|
|
3
3
|
import { Gesture, GestureDetector } from 'react-native-gesture-handler';
|
|
4
|
-
import Animated, {
|
|
5
|
-
cancelAnimation,
|
|
6
|
-
runOnJS,
|
|
7
|
-
useAnimatedStyle,
|
|
8
|
-
useSharedValue,
|
|
9
|
-
} from 'react-native-reanimated';
|
|
4
|
+
import Animated, { runOnJS, useAnimatedStyle, useSharedValue } from 'react-native-reanimated';
|
|
10
5
|
|
|
11
6
|
import { useTheme } from '../../contexts/themeContext/ThemeContext';
|
|
12
7
|
|
|
13
8
|
export type ProgressControlProps = {
|
|
9
|
+
/**
|
|
10
|
+
* The duration of the audio in seconds
|
|
11
|
+
*/
|
|
14
12
|
duration: number;
|
|
13
|
+
/**
|
|
14
|
+
* The color of the filled progress bar
|
|
15
|
+
*/
|
|
15
16
|
filledColor: string;
|
|
17
|
+
/**
|
|
18
|
+
* The progress of the progress bar in percentage
|
|
19
|
+
*/
|
|
16
20
|
progress: number;
|
|
21
|
+
/**
|
|
22
|
+
* The test ID of the progress control
|
|
23
|
+
*/
|
|
17
24
|
testID: string;
|
|
18
|
-
|
|
25
|
+
/**
|
|
26
|
+
* The function to be called when the user ends dragging the progress bar
|
|
27
|
+
*/
|
|
28
|
+
onEndDrag?: (progress: number) => void;
|
|
29
|
+
/**
|
|
30
|
+
* The function to be called when the user plays or pauses the audio
|
|
31
|
+
* @deprecated Use onStartDrag and onEndDrag instead
|
|
32
|
+
*/
|
|
19
33
|
onPlayPause?: (status?: boolean) => void;
|
|
34
|
+
/**
|
|
35
|
+
* The function to be called when the user is dragging the progress bar
|
|
36
|
+
*/
|
|
20
37
|
onProgressDrag?: (progress: number) => void;
|
|
38
|
+
/**
|
|
39
|
+
* The function to be called when the user starts dragging the progress bar
|
|
40
|
+
*/
|
|
41
|
+
onStartDrag?: (progress: number) => void;
|
|
42
|
+
/**
|
|
43
|
+
* The width of the progress control
|
|
44
|
+
*/
|
|
45
|
+
width?: number | string;
|
|
21
46
|
};
|
|
22
47
|
|
|
23
|
-
const
|
|
48
|
+
const TRACK_HEIGHT = 3;
|
|
49
|
+
const THUMB_WIDTH = 8;
|
|
24
50
|
|
|
25
51
|
const ProgressControlThumb = () => {
|
|
26
52
|
const {
|
|
@@ -38,100 +64,97 @@ const ProgressControlThumb = () => {
|
|
|
38
64
|
);
|
|
39
65
|
};
|
|
40
66
|
|
|
41
|
-
export const ProgressControl =
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
|
|
45
|
-
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
|
|
50
|
-
|
|
51
|
-
|
|
52
|
-
const state = useSharedValue(0);
|
|
53
|
-
const translateX = useSharedValue(0);
|
|
54
|
-
const { width: windowWidth } = Dimensions.get('screen');
|
|
55
|
-
const widthInNumbers = width
|
|
56
|
-
? typeof width === 'string'
|
|
57
|
-
? (windowWidth * Number(width?.substring(0, width.length - 1))) / 100
|
|
58
|
-
: width
|
|
59
|
-
: 0;
|
|
60
|
-
const {
|
|
61
|
-
theme: {
|
|
62
|
-
colors: { grey_dark },
|
|
63
|
-
progressControl: { container, filledColor: filledColorFromTheme, filledStyles, thumb },
|
|
64
|
-
},
|
|
65
|
-
} = useTheme();
|
|
66
|
-
const pan = Gesture.Pan()
|
|
67
|
-
.maxPointers(1)
|
|
68
|
-
.onStart(() => {
|
|
69
|
-
if (onPlayPause) runOnJS(onPlayPause)(true);
|
|
70
|
-
cancelAnimation(translateX);
|
|
71
|
-
state.value = translateX.value;
|
|
72
|
-
})
|
|
73
|
-
.onChange((event) => {
|
|
74
|
-
state.value = translateX.value + event.translationX;
|
|
75
|
-
if (state.value > widthInNumbers) state.value = widthInNumbers;
|
|
76
|
-
else if (state.value < 0) state.value = 0;
|
|
77
|
-
})
|
|
78
|
-
.onEnd(() => {
|
|
79
|
-
translateX.value = state.value;
|
|
80
|
-
const dragFinishLocationInSeconds = (state.value / widthInNumbers) * duration;
|
|
81
|
-
if (onProgressDrag) runOnJS(onProgressDrag)(dragFinishLocationInSeconds);
|
|
82
|
-
if (onPlayPause) runOnJS(onPlayPause)(false);
|
|
83
|
-
})
|
|
84
|
-
.withTestId(testID);
|
|
67
|
+
export const ProgressControl = (props: ProgressControlProps) => {
|
|
68
|
+
const [widthInNumbers, setWidthInNumbers] = useState(0);
|
|
69
|
+
const {
|
|
70
|
+
filledColor: filledColorFromProp,
|
|
71
|
+
onEndDrag,
|
|
72
|
+
onPlayPause,
|
|
73
|
+
onProgressDrag,
|
|
74
|
+
onStartDrag,
|
|
75
|
+
progress,
|
|
76
|
+
testID,
|
|
77
|
+
} = props;
|
|
85
78
|
|
|
86
|
-
|
|
79
|
+
const progressValue = useSharedValue(progress);
|
|
80
|
+
const {
|
|
81
|
+
theme: {
|
|
82
|
+
colors: { grey_dark },
|
|
83
|
+
progressControl: { container, filledColor: filledColorFromTheme, filledStyles, thumb },
|
|
84
|
+
},
|
|
85
|
+
} = useTheme();
|
|
87
86
|
|
|
88
|
-
|
|
89
|
-
|
|
90
|
-
|
|
91
|
-
|
|
92
|
-
|
|
93
|
-
|
|
94
|
-
|
|
87
|
+
const pan = Gesture.Pan()
|
|
88
|
+
.maxPointers(1)
|
|
89
|
+
.onStart((event) => {
|
|
90
|
+
const currentProgress = (progressValue.value + event.x) / widthInNumbers;
|
|
91
|
+
progressValue.value = Math.max(0, Math.min(currentProgress, 1));
|
|
92
|
+
if (onStartDrag) runOnJS(onStartDrag)(progressValue.value);
|
|
93
|
+
if (onPlayPause) runOnJS(onPlayPause)(true);
|
|
94
|
+
})
|
|
95
|
+
.onUpdate((event) => {
|
|
96
|
+
const currentProgress = (progressValue.value + event.x) / widthInNumbers;
|
|
97
|
+
progressValue.value = Math.max(0, Math.min(currentProgress, 1));
|
|
98
|
+
if (onProgressDrag) runOnJS(onProgressDrag)(progressValue.value);
|
|
99
|
+
})
|
|
100
|
+
.onEnd((event) => {
|
|
101
|
+
const currentProgress = (progressValue.value + event.x) / widthInNumbers;
|
|
102
|
+
progressValue.value = Math.max(0, Math.min(currentProgress, 1));
|
|
103
|
+
if (onEndDrag) runOnJS(onEndDrag)(progressValue.value);
|
|
104
|
+
if (onPlayPause) runOnJS(onPlayPause)(false);
|
|
105
|
+
})
|
|
106
|
+
.withTestId(testID);
|
|
95
107
|
|
|
96
|
-
|
|
97
|
-
backgroundColor: filledColor,
|
|
98
|
-
width: state.value,
|
|
99
|
-
}));
|
|
108
|
+
const filledColor = filledColorFromProp || filledColorFromTheme;
|
|
100
109
|
|
|
101
|
-
|
|
102
|
-
|
|
103
|
-
|
|
110
|
+
const thumbStyles = useAnimatedStyle(
|
|
111
|
+
() => ({
|
|
112
|
+
transform: [{ translateX: progress * widthInNumbers - THUMB_WIDTH / 2 }],
|
|
113
|
+
}),
|
|
114
|
+
[progress],
|
|
115
|
+
);
|
|
104
116
|
|
|
105
|
-
|
|
117
|
+
const animatedFilledStyles = useAnimatedStyle(
|
|
118
|
+
() => ({
|
|
119
|
+
width: progress * widthInNumbers,
|
|
120
|
+
}),
|
|
121
|
+
[progress],
|
|
122
|
+
);
|
|
123
|
+
|
|
124
|
+
return (
|
|
125
|
+
<GestureDetector gesture={pan}>
|
|
106
126
|
<View
|
|
107
|
-
|
|
127
|
+
onLayout={({ nativeEvent }) => {
|
|
128
|
+
setWidthInNumbers(nativeEvent.layout.width);
|
|
129
|
+
}}
|
|
130
|
+
style={[styles.container, { backgroundColor: grey_dark }, container]}
|
|
108
131
|
>
|
|
109
|
-
<Animated.View
|
|
110
|
-
|
|
111
|
-
|
|
112
|
-
|
|
113
|
-
|
|
114
|
-
|
|
132
|
+
<Animated.View
|
|
133
|
+
style={[
|
|
134
|
+
styles.filledStyle,
|
|
135
|
+
animatedFilledStyles,
|
|
136
|
+
{
|
|
137
|
+
backgroundColor: filledColor,
|
|
138
|
+
},
|
|
139
|
+
filledStyles,
|
|
140
|
+
]}
|
|
141
|
+
/>
|
|
142
|
+
<Animated.View style={[thumbStyles, thumb]}>
|
|
143
|
+
{onEndDrag || onProgressDrag ? <ProgressControlThumb /> : null}
|
|
144
|
+
</Animated.View>
|
|
115
145
|
</View>
|
|
116
|
-
|
|
117
|
-
|
|
118
|
-
|
|
119
|
-
if (
|
|
120
|
-
prevProps.duration === nextProps.duration &&
|
|
121
|
-
prevProps.progress === nextProps.progress &&
|
|
122
|
-
prevProps.width === nextProps.width
|
|
123
|
-
)
|
|
124
|
-
return true;
|
|
125
|
-
else return false;
|
|
126
|
-
},
|
|
127
|
-
);
|
|
146
|
+
</GestureDetector>
|
|
147
|
+
);
|
|
148
|
+
};
|
|
128
149
|
|
|
129
150
|
const styles = StyleSheet.create({
|
|
130
151
|
container: {
|
|
131
|
-
|
|
152
|
+
borderRadius: 2,
|
|
153
|
+
height: TRACK_HEIGHT,
|
|
132
154
|
},
|
|
133
155
|
filledStyle: {
|
|
134
|
-
|
|
156
|
+
borderRadius: 2,
|
|
157
|
+
height: TRACK_HEIGHT,
|
|
135
158
|
},
|
|
136
159
|
progressControlThumbStyle: {
|
|
137
160
|
borderRadius: 5,
|
|
@@ -145,7 +168,7 @@ const styles = StyleSheet.create({
|
|
|
145
168
|
shadowOpacity: 0.27,
|
|
146
169
|
shadowRadius: 4.65,
|
|
147
170
|
top: -15,
|
|
148
|
-
width:
|
|
171
|
+
width: THUMB_WIDTH,
|
|
149
172
|
},
|
|
150
173
|
});
|
|
151
174
|
ProgressControl.displayName = 'ProgressControl';
|