mirror of
https://github.com/balzack/databag.git
synced 2025-04-23 01:55:17 +00:00
implementing call gui
This commit is contained in:
parent
a60c104f3c
commit
8ff0443aea
@ -1,5 +1,7 @@
|
||||
PODS:
|
||||
- boost (1.84.0)
|
||||
- BVLinearGradient (2.8.3):
|
||||
- React-Core
|
||||
- DoubleConversion (1.1.6)
|
||||
- FBLazyVector (0.75.4)
|
||||
- Firebase/CoreOnly (11.5.0):
|
||||
@ -1862,6 +1864,7 @@ PODS:
|
||||
|
||||
DEPENDENCIES:
|
||||
- boost (from `../node_modules/react-native/third-party-podspecs/boost.podspec`)
|
||||
- BVLinearGradient (from `../node_modules/react-native-linear-gradient`)
|
||||
- DoubleConversion (from `../node_modules/react-native/third-party-podspecs/DoubleConversion.podspec`)
|
||||
- FBLazyVector (from `../node_modules/react-native/Libraries/FBLazyVector`)
|
||||
- fmt (from `../node_modules/react-native/third-party-podspecs/fmt.podspec`)
|
||||
@ -1970,6 +1973,8 @@ SPEC REPOS:
|
||||
EXTERNAL SOURCES:
|
||||
boost:
|
||||
:podspec: "../node_modules/react-native/third-party-podspecs/boost.podspec"
|
||||
BVLinearGradient:
|
||||
:path: "../node_modules/react-native-linear-gradient"
|
||||
DoubleConversion:
|
||||
:podspec: "../node_modules/react-native/third-party-podspecs/DoubleConversion.podspec"
|
||||
FBLazyVector:
|
||||
@ -2140,6 +2145,7 @@ EXTERNAL SOURCES:
|
||||
|
||||
SPEC CHECKSUMS:
|
||||
boost: 4cb898d0bf20404aab1850c656dcea009429d6c1
|
||||
BVLinearGradient: 880f91a7854faff2df62518f0281afb1c60d49a3
|
||||
DoubleConversion: 76ab83afb40bddeeee456813d9c04f67f78771b5
|
||||
FBLazyVector: 430e10366de01d1e3d57374500b1b150fe482e6d
|
||||
Firebase: 7a56fe4f56b5ab81b86a6822f5b8f909ae6fc7e2
|
||||
|
@ -39,6 +39,7 @@
|
||||
"react-native-gesture-handler": "^2.19.0",
|
||||
"react-native-image-crop-picker": "^0.41.2",
|
||||
"react-native-keyboard-aware-scroll-view": "^0.9.5",
|
||||
"react-native-linear-gradient": "^2.8.3",
|
||||
"react-native-paper": "^5.12.5",
|
||||
"react-native-reanimated": "^3.15.2",
|
||||
"react-native-rsa-native": "^2.0.5",
|
||||
|
@ -25,6 +25,11 @@ export const styles = StyleSheet.create({
|
||||
alignItems: 'center',
|
||||
justifyContent: 'center',
|
||||
},
|
||||
call: {
|
||||
width: '100%',
|
||||
height: '100%',
|
||||
display: 'flex',
|
||||
},
|
||||
image: {
|
||||
width: '100%',
|
||||
height: '100%',
|
||||
@ -32,8 +37,32 @@ export const styles = StyleSheet.create({
|
||||
},
|
||||
frame: {
|
||||
display: 'flex',
|
||||
alignItems: 'center',
|
||||
justifyContent: 'center',
|
||||
borderRadius: 8,
|
||||
overflow: 'hidden',
|
||||
padding: 2,
|
||||
position: 'relative',
|
||||
},
|
||||
closeIcon: {
|
||||
borderRadius: 8,
|
||||
},
|
||||
name: {
|
||||
fontSize: 28,
|
||||
minWidth: '50%',
|
||||
color: '#aaaaaa',
|
||||
paddingLeft: 16,
|
||||
width: '100%',
|
||||
height: '100%',
|
||||
padding: 16,
|
||||
},
|
||||
overlap: {
|
||||
display: 'flex',
|
||||
flexDirection: 'row',
|
||||
position: 'absolute',
|
||||
alignItems: 'center',
|
||||
width: '100%',
|
||||
justifyContent: 'center',
|
||||
paddingBottom: 8,
|
||||
paddingTop: 8,
|
||||
gap: 32,
|
||||
},
|
||||
});
|
||||
|
@ -1,5 +1,5 @@
|
||||
import React, { useEffect, useState } from 'react';
|
||||
import { Image, SafeAreaView, Modal, ScrollView, View } from 'react-native';
|
||||
import { useWindowDimensions, Image, SafeAreaView, Modal, ScrollView, View } from 'react-native';
|
||||
import { Surface, Icon, Divider, Button, IconButton, Text, TextInput} from 'react-native-paper';
|
||||
import {styles} from './Calling.styled';
|
||||
import {useCalling} from './useCalling.hook';
|
||||
@ -7,11 +7,28 @@ import {BlurView} from '@react-native-community/blur';
|
||||
import { Confirm } from '../confirm/Confirm';
|
||||
import { ActivityIndicator } from 'react-native-paper';
|
||||
import FastImage from 'react-native-fast-image'
|
||||
import LinearGradient from 'react-native-linear-gradient';
|
||||
import { Colors } from '../constants/Colors';
|
||||
|
||||
export function Calling({ callCard }: { callCard: string }) {
|
||||
const { state, actions } = useCalling();
|
||||
const [alert, setAlert] = useState(false);
|
||||
const [connecting, setConnecting] = useState(false);
|
||||
const [ending, setEnding] = useState(false);
|
||||
const {height, width} = useWindowDimensions();
|
||||
|
||||
const end = async () => {
|
||||
if (!ending) {
|
||||
setEnding(true);
|
||||
try {
|
||||
await actions.end();
|
||||
} catch (err) {
|
||||
console.log(err);
|
||||
setAlert(true);
|
||||
}
|
||||
setEnding(false);
|
||||
}
|
||||
}
|
||||
|
||||
const call = async (cardId: string) => {
|
||||
if (!connecting) {
|
||||
@ -44,6 +61,10 @@ export function Calling({ callCard }: { callCard: string }) {
|
||||
}
|
||||
}, [callCard]);
|
||||
|
||||
const overlap = (width + 128) > height;
|
||||
const frameWidth = width > height ? height : width - 16;
|
||||
const frameHeight = frameWidth;
|
||||
//const frameHeight = overlap ? frameWidth : frameWidth + 128;
|
||||
return (
|
||||
<View style={(connecting || state.calling || state.ringing.length > 0 || alert) ? styles.active : styles.inactive}>
|
||||
<BlurView style={styles.blur} blurType="dark" blurAmount={9} reducedTransparencyFallbackColor="dark" />
|
||||
@ -51,13 +72,43 @@ export function Calling({ callCard }: { callCard: string }) {
|
||||
<ActivityIndicator size={72} />
|
||||
)}
|
||||
{ state.calling && (
|
||||
<View style={styles.frame}>
|
||||
<Surface style={{ ...styles.frame, width: frameWidth, height: frameHeight }}>
|
||||
<Image
|
||||
style={styles.image}
|
||||
resizeMode="contain"
|
||||
source={{ uri: state.calling.imageUrl }}
|
||||
onLayout={actions.loaded}
|
||||
/>
|
||||
</View>
|
||||
{ state.loaded && (
|
||||
<LinearGradient style={{...styles.overlap, height: frameHeight / 2, top: 2, borderRadius: 8}} start={{x: 0, y: 0}} end={{x: 0, y: 0.5}} colors={['rgba(64,64,64,1)', 'rgba(64,64,64, 0)']}>
|
||||
<LinearGradient style={{...styles.overlap, height: frameHeight / 2, top: 2, borderRadius: 8}} start={{x: 0, y: 0}} end={{x: 0, y: 0.5}} colors={['rgba(64,64,64,1)', 'rgba(64,64,64, 0)']}>
|
||||
</LinearGradient>
|
||||
</LinearGradient>
|
||||
)}
|
||||
{ state.loaded && (
|
||||
<LinearGradient style={{...styles.overlap, height: frameHeight / 2, bottom: 2, borderRadius: 8}} start={{x: 0, y: 0.5}} end={{x: 0, y: 1}} colors={['rgba(64,64,64,0)', 'rgba(64,64,64, 1)']}>
|
||||
<LinearGradient style={{...styles.overlap, height: frameHeight / 2, bottom: 2, borderRadius: 8}} start={{x: 0, y: 0.5}} end={{x: 0, y: 1}} colors={['rgba(64,64,64,0)', 'rgba(64,64,64, 1)']}>
|
||||
</LinearGradient>
|
||||
</LinearGradient>
|
||||
)}
|
||||
{ state.loaded && (
|
||||
<View style={{ ...styles.overlap, top: 0 }}>
|
||||
{ state.calling.name && (
|
||||
<Text style={styles.name} adjustsFontSizeToFit={true} numberOfLines={1}>{ state.calling.name }</Text>
|
||||
)}
|
||||
{ !state.calling.name && (
|
||||
<Text style={styles.name} adjustsFontSizeToFit={true} numberOfLines={1}>{ `${state.calling.handle}/${state.calling.node}` }</Text>
|
||||
)}
|
||||
</View>
|
||||
)}
|
||||
{ state.loaded && (
|
||||
<View style={{ ...styles.overlap, bottom: 0 }}>
|
||||
<IconButton style={styles.closeIcon} iconColor="white" containerColor={Colors.primary} icon="microphone" compact="true" mode="contained" size={32} onPress={end} />
|
||||
<IconButton style={styles.closeIcon} iconColor="white" containerColor={Colors.primary} icon="video-outline" compact="true" mode="contained" size={32} onPress={end} />
|
||||
<IconButton style={styles.closeIcon} iconColor="white" containerColor={Colors.danger} icon="phone-hangup-outline" compact="true" mode="contained" size={32} onPress={end} />
|
||||
</View>
|
||||
)}
|
||||
</Surface>
|
||||
)}
|
||||
<Confirm show={alert} params={alertParams} />
|
||||
</View>
|
||||
|
@ -27,6 +27,8 @@ export function useCalling() {
|
||||
cards: [],
|
||||
calling: null as null | Card,
|
||||
failed: false,
|
||||
loaded: false,
|
||||
panelOffset: 0,
|
||||
})
|
||||
|
||||
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
||||
@ -55,8 +57,6 @@ export function useCalling() {
|
||||
};
|
||||
|
||||
const linkStatus = async (status: string) => {
|
||||
console.log("LINK STATUS: ", status);
|
||||
|
||||
if (call.current) {
|
||||
const { policy, peer, link } = call.current;
|
||||
if (status === 'connected') {
|
||||
@ -84,8 +84,6 @@ console.log("LINK STATUS: ", status);
|
||||
try {
|
||||
peer.close();
|
||||
link.close();
|
||||
link.clearStatusListener();
|
||||
link.clearMessageListener();
|
||||
} catch (err) {
|
||||
console.log(err);
|
||||
}
|
||||
@ -96,8 +94,6 @@ console.log("LINK STATUS: ", status);
|
||||
}
|
||||
|
||||
const linkMessage = async (message: any) => {
|
||||
console.log("LINK MSG: ", message);
|
||||
|
||||
if (call.current) {
|
||||
const { peer, link, candidates, policy } = call.current;
|
||||
try {
|
||||
@ -135,13 +131,9 @@ console.log("LINK MSG: ", message);
|
||||
updateState({ failed: true });
|
||||
}
|
||||
}
|
||||
|
||||
console.log("LINK MSG: done");
|
||||
|
||||
}
|
||||
|
||||
const peerCandidate = async (candidate) => {
|
||||
console.log("PEER CANDIDATE");
|
||||
if (call.current && candidate) {
|
||||
const { link } = call.current;
|
||||
await link.sendMessage({ candidate });
|
||||
@ -149,7 +141,6 @@ console.log("PEER CANDIDATE");
|
||||
}
|
||||
|
||||
const peerNegotiate = async () => {
|
||||
console.log("PEER NEGOTIATE");
|
||||
if (call.current) {
|
||||
const { peer, link } = call.current;
|
||||
const description = await peer.createOffer(constraints);
|
||||
@ -204,6 +195,20 @@ console.log("PEER NEGOTIATE");
|
||||
}, [app.state.session]);
|
||||
|
||||
const actions = {
|
||||
end: async () => {
|
||||
if (!call.current) {
|
||||
throw new Error('no active call');
|
||||
}
|
||||
const { link, peer } = call.current;
|
||||
try {
|
||||
peer.close();
|
||||
link.close();
|
||||
} catch (err) {
|
||||
console.log(err);
|
||||
}
|
||||
call.current = null;
|
||||
updateState({ calling: null });
|
||||
},
|
||||
accept: async (callId: string, call: Call) => {
|
||||
if (call.current) {
|
||||
throw new Error('active call in progress');
|
||||
@ -239,6 +244,14 @@ console.log("PEER NEGOTIATE");
|
||||
link.setMessageListener(linkMessage);
|
||||
updateState({ calling: card });
|
||||
},
|
||||
loaded: (e) => {
|
||||
const { width, height } = e.nativeEvent.layout;
|
||||
if (width > (height + 80)) {
|
||||
updateState({ panelOffset: 0, loaded: true });
|
||||
} else {
|
||||
updateState({ panelOffset: ((height - width) - 80) / 2, loaded: true });
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return { state, actions }
|
||||
|
@ -1,6 +1,6 @@
|
||||
export const Colors = {
|
||||
primary: '#408060',
|
||||
danger: '#ff8888',
|
||||
danger: '#ff6666',
|
||||
placeholder: '#888888',
|
||||
unsaved: '#555555',
|
||||
confirmed: '#aaaaaa',
|
||||
|
@ -4461,6 +4461,7 @@ __metadata:
|
||||
react-native-gesture-handler: ^2.19.0
|
||||
react-native-image-crop-picker: ^0.41.2
|
||||
react-native-keyboard-aware-scroll-view: ^0.9.5
|
||||
react-native-linear-gradient: ^2.8.3
|
||||
react-native-paper: ^5.12.5
|
||||
react-native-reanimated: ^3.15.2
|
||||
react-native-rsa-native: ^2.0.5
|
||||
@ -10705,6 +10706,16 @@ __metadata:
|
||||
languageName: node
|
||||
linkType: hard
|
||||
|
||||
"react-native-linear-gradient@npm:^2.8.3":
|
||||
version: 2.8.3
|
||||
resolution: "react-native-linear-gradient@npm:2.8.3"
|
||||
peerDependencies:
|
||||
react: "*"
|
||||
react-native: "*"
|
||||
checksum: f980d324e551bbc475c6406bdc5250a08242020cbe653412fa169bbdf51e28a502e225de105b4d696d6a1a1b733d44782469020f4936d8b3ce0e2c78e51cf58f
|
||||
languageName: node
|
||||
linkType: hard
|
||||
|
||||
"react-native-paper@npm:^5.12.5":
|
||||
version: 5.13.1
|
||||
resolution: "react-native-paper@npm:5.13.1"
|
||||
|
Loading…
x
Reference in New Issue
Block a user