mirror of
https://github.com/balzack/databag.git
synced 2025-02-11 19:19:16 +00:00
adding audio playback support
This commit is contained in:
parent
bae8ce9405
commit
1b18d5bc8a
@ -359,6 +359,8 @@ PODS:
|
|||||||
- React-RCTText
|
- React-RCTText
|
||||||
- ReactCommon/turbomodule/core
|
- ReactCommon/turbomodule/core
|
||||||
- Yoga
|
- Yoga
|
||||||
|
- RNSoundPlayer (0.13.2):
|
||||||
|
- React-Core
|
||||||
- TOCropViewController (2.6.0)
|
- TOCropViewController (2.6.0)
|
||||||
- Yoga (1.14.0)
|
- Yoga (1.14.0)
|
||||||
|
|
||||||
@ -411,6 +413,7 @@ DEPENDENCIES:
|
|||||||
- RNGestureHandler (from `../node_modules/react-native-gesture-handler`)
|
- RNGestureHandler (from `../node_modules/react-native-gesture-handler`)
|
||||||
- RNImageCropPicker (from `../node_modules/react-native-image-crop-picker`)
|
- RNImageCropPicker (from `../node_modules/react-native-image-crop-picker`)
|
||||||
- RNReanimated (from `../node_modules/react-native-reanimated`)
|
- RNReanimated (from `../node_modules/react-native-reanimated`)
|
||||||
|
- RNSoundPlayer (from `../node_modules/react-native-sound-player`)
|
||||||
- Yoga (from `../node_modules/react-native/ReactCommon/yoga`)
|
- Yoga (from `../node_modules/react-native/ReactCommon/yoga`)
|
||||||
|
|
||||||
SPEC REPOS:
|
SPEC REPOS:
|
||||||
@ -513,6 +516,8 @@ EXTERNAL SOURCES:
|
|||||||
:path: "../node_modules/react-native-image-crop-picker"
|
:path: "../node_modules/react-native-image-crop-picker"
|
||||||
RNReanimated:
|
RNReanimated:
|
||||||
:path: "../node_modules/react-native-reanimated"
|
:path: "../node_modules/react-native-reanimated"
|
||||||
|
RNSoundPlayer:
|
||||||
|
:path: "../node_modules/react-native-sound-player"
|
||||||
Yoga:
|
Yoga:
|
||||||
:path: "../node_modules/react-native/ReactCommon/yoga"
|
:path: "../node_modules/react-native/ReactCommon/yoga"
|
||||||
|
|
||||||
@ -565,6 +570,7 @@ SPEC CHECKSUMS:
|
|||||||
RNGestureHandler: 7673697e7c0e9391adefae4faa087442bc04af33
|
RNGestureHandler: 7673697e7c0e9391adefae4faa087442bc04af33
|
||||||
RNImageCropPicker: ffbba608264885c241cbf3a8f78eb7aeeb978241
|
RNImageCropPicker: ffbba608264885c241cbf3a8f78eb7aeeb978241
|
||||||
RNReanimated: 7faa787e8d4493fbc95fab2ad331fa7625828cfa
|
RNReanimated: 7faa787e8d4493fbc95fab2ad331fa7625828cfa
|
||||||
|
RNSoundPlayer: 369105c565b8fe6ea0a43fc882dc81eba444e842
|
||||||
TOCropViewController: 3105367e808b7d3d886a74ff59bf4804e7d3ab38
|
TOCropViewController: 3105367e808b7d3d886a74ff59bf4804e7d3ab38
|
||||||
Yoga: c2b1f2494060865ac1f27e49639e72371b1205fa
|
Yoga: c2b1f2494060865ac1f27e49639e72371b1205fa
|
||||||
|
|
||||||
|
@ -31,6 +31,7 @@
|
|||||||
"react-native-safe-area-context": "^4.3.3",
|
"react-native-safe-area-context": "^4.3.3",
|
||||||
"react-native-safe-area-view": "^1.1.1",
|
"react-native-safe-area-view": "^1.1.1",
|
||||||
"react-native-snap-carousel": "4.0.0-beta.6",
|
"react-native-snap-carousel": "4.0.0-beta.6",
|
||||||
|
"react-native-sound-player": "^0.13.2",
|
||||||
"react-native-sqlite-storage": "^6.0.1",
|
"react-native-sqlite-storage": "^6.0.1",
|
||||||
"react-native-swipe-gestures": "^1.0.5",
|
"react-native-swipe-gestures": "^1.0.5",
|
||||||
"react-native-video": "^5.2.1",
|
"react-native-video": "^5.2.1",
|
||||||
|
@ -27,7 +27,8 @@ export function TopicItem({ item }) {
|
|||||||
<VideoAsset topicId={item.topicId} asset={asset.item.video} />
|
<VideoAsset topicId={item.topicId} asset={asset.item.video} />
|
||||||
)}
|
)}
|
||||||
{ asset.item.audio && (
|
{ asset.item.audio && (
|
||||||
<AudioAsset topicId={item.topicId} asset={asset.item.audio} />
|
<AudioAsset topicId={item.topicId} asset={asset.item.audio} active={state.activeId == asset.dataIndex}
|
||||||
|
setActive={() => actions.setActive(asset.dataIndex)} />
|
||||||
)}
|
)}
|
||||||
</TouchableOpacity>
|
</TouchableOpacity>
|
||||||
)
|
)
|
||||||
|
@ -1,10 +1,34 @@
|
|||||||
import { Image, View, TouchableOpacity } from 'react-native';
|
import { Text, Image, View, TouchableOpacity } from 'react-native';
|
||||||
import Colors from 'constants/Colors';
|
import Colors from 'constants/Colors';
|
||||||
|
import { useAudioAsset } from './useAudioAsset.hook';
|
||||||
|
import { styles } from './AudioAsset.styled';
|
||||||
|
import audio from 'images/audio.png';
|
||||||
|
import Icons from '@expo/vector-icons/MaterialCommunityIcons';
|
||||||
|
|
||||||
export function AudioAsset({ topicId, asset, onClearCarousel }) {
|
export function AudioAsset({ topicId, asset, active, setActive }) {
|
||||||
|
|
||||||
|
const { state, actions } = useAudioAsset(topicId, asset);
|
||||||
|
|
||||||
|
const play = () => {
|
||||||
|
actions.play();
|
||||||
|
setActive();
|
||||||
|
}
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<TouchableOpacity onPress={onClearCarousel} activeOpacity={1} style={{ width: 100, height: 100, backgroundColor: 'yellow' }} onPress={onClearCarousel} />
|
<View style={styles.background}>
|
||||||
|
<Image source={audio} style={{ width: state.length, height: state.length }} resizeMode={'cover'} />
|
||||||
|
<Text style={styles.label}>{ asset.label }</Text>
|
||||||
|
{ state.playing && active && (
|
||||||
|
<TouchableOpacity style={styles.control} onPress={actions.pause}>
|
||||||
|
<Icons name="stop-circle-outline" size={92} color={Colors.white} />
|
||||||
|
</TouchableOpacity>
|
||||||
|
)}
|
||||||
|
{ (!state.playing || !active) && (
|
||||||
|
<TouchableOpacity style={styles.control} onPress={play}>
|
||||||
|
<Icons name="play-circle-outline" size={92} color={Colors.white} />
|
||||||
|
</TouchableOpacity>
|
||||||
|
)}
|
||||||
|
</View>
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -0,0 +1,23 @@
|
|||||||
|
import { StyleSheet } from 'react-native';
|
||||||
|
import { Colors } from 'constants/Colors';
|
||||||
|
|
||||||
|
export const styles = StyleSheet.create({
|
||||||
|
background: {
|
||||||
|
backgroundColor: Colors.lightgrey,
|
||||||
|
borderRadius: 4,
|
||||||
|
display: 'flex',
|
||||||
|
alignItems: 'center',
|
||||||
|
justifyContent: 'center',
|
||||||
|
},
|
||||||
|
label: {
|
||||||
|
position: 'absolute',
|
||||||
|
textAlign: 'center',
|
||||||
|
fontSize: 20,
|
||||||
|
paddingTop: 8,
|
||||||
|
top: 0,
|
||||||
|
},
|
||||||
|
control: {
|
||||||
|
position: 'absolute',
|
||||||
|
}
|
||||||
|
})
|
||||||
|
|
@ -0,0 +1,49 @@
|
|||||||
|
import { useState, useRef, useEffect, useContext } from 'react';
|
||||||
|
import { ConversationContext } from 'context/ConversationContext';
|
||||||
|
import { Image } from 'react-native';
|
||||||
|
import { useWindowDimensions } from 'react-native';
|
||||||
|
import SoundPlayer from 'react-native-sound-player'
|
||||||
|
|
||||||
|
export function useAudioAsset(topicId, asset) {
|
||||||
|
|
||||||
|
const [state, setState] = useState({
|
||||||
|
length: null,
|
||||||
|
playing: false,
|
||||||
|
});
|
||||||
|
|
||||||
|
const conversation = useContext(ConversationContext);
|
||||||
|
const dimensions = useWindowDimensions();
|
||||||
|
|
||||||
|
const updateState = (value) => {
|
||||||
|
setState((s) => ({ ...s, ...value }));
|
||||||
|
}
|
||||||
|
|
||||||
|
useEffect(() => {
|
||||||
|
if (dimensions.width < dimensions.height) {
|
||||||
|
updateState({ length: 0.8 * dimensions.width });
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
updateState({ length: 0.8 * dimensions.height });
|
||||||
|
}
|
||||||
|
}, [dimensions]);
|
||||||
|
|
||||||
|
useEffect(() => {
|
||||||
|
const url = conversation.actions.getTopicAssetUrl(topicId, asset.full);
|
||||||
|
updateState({ url, playing: false });
|
||||||
|
return () => { SoundPlayer.stop() }
|
||||||
|
}, [topicId, conversation, asset]);
|
||||||
|
|
||||||
|
const actions = {
|
||||||
|
play: () => {
|
||||||
|
SoundPlayer.playUrl(state.url);
|
||||||
|
updateState({ playing: true });
|
||||||
|
},
|
||||||
|
pause: () => {
|
||||||
|
SoundPlayer.stop();
|
||||||
|
updateState({ playing: false });
|
||||||
|
},
|
||||||
|
};
|
||||||
|
|
||||||
|
return { state, actions };
|
||||||
|
}
|
||||||
|
|
@ -16,6 +16,7 @@ export function useTopicItem(item) {
|
|||||||
carouselIndex: 0,
|
carouselIndex: 0,
|
||||||
width: null,
|
width: null,
|
||||||
height: null,
|
height: null,
|
||||||
|
activeId: null,
|
||||||
});
|
});
|
||||||
|
|
||||||
const profile = useContext(ProfileContext);
|
const profile = useContext(ProfileContext);
|
||||||
@ -111,6 +112,9 @@ export function useTopicItem(item) {
|
|||||||
hideCarousel: () => {
|
hideCarousel: () => {
|
||||||
updateState({ carousel: false });
|
updateState({ carousel: false });
|
||||||
},
|
},
|
||||||
|
setActive: (activeId) => {
|
||||||
|
updateState({ activeId });
|
||||||
|
},
|
||||||
};
|
};
|
||||||
|
|
||||||
return { state, actions };
|
return { state, actions };
|
||||||
|
10049
app/mobile/yarn.lock
10049
app/mobile/yarn.lock
File diff suppressed because it is too large
Load Diff
Loading…
Reference in New Issue
Block a user