UNPKG

mediasfu-reactnative-expo

Version:
252 lines (247 loc) 8.59 kB
// WaitingRoomModal.tsx import React, { useEffect, useState } from "react"; import { Modal, View, Text, Pressable, StyleSheet, ScrollView, TextInput, Dimensions, } from "react-native"; import { FontAwesome } from "@expo/vector-icons"; import { getModalPosition } from "../../methods/utils/getModalPosition"; import { respondToWaiting, } from "../../methods/waitingMethods/respondToWaiting"; /** * WaitingRoomModal is a React Native functional component that displays a modal containing a list of participants who are waiting to join a room. Users can filter, accept, or reject participants from the waiting list. * * @component * @param {WaitingRoomModalOptions} props - The properties for the WaitingRoomModal component. * @returns {JSX.Element} The rendered WaitingRoomModal component. * * @example * ```tsx * import React from 'react'; * import { WaitingRoomModal } from 'mediasfu-reactnative-expo'; * * function App() { * const waitingRoomList = [ * { id: 1, name: 'John Doe' }, * { id: 2, name: 'Jane Smith' }, * ]; * * const handleWaitingRoomItemPress = ({ participantId, type }) => { * console.log(`Participant ID ${participantId} was ${type ? 'accepted' : 'rejected'}`); * }; * * return ( * <WaitingRoomModal * isWaitingModalVisible={true} * onWaitingRoomClose={() => console.log('Modal closed')} * waitingRoomCounter={waitingRoomList.length} * onWaitingRoomFilterChange={(filter) => console.log('Filter applied:', filter)} * waitingRoomList={waitingRoomList} * updateWaitingList={(updatedList) => console.log('Updated list:', updatedList)} * roomName="Main Room" * socket={socketInstance} * onWaitingRoomItemPress={handleWaitingRoomItemPress} * backgroundColor="#83c0e9" * position="topRight" * parameters={{ * getUpdatedAllParams: () => ({ filteredWaitingRoomList: waitingRoomList }), * }} * /> * ); * } * export default App; * ``` */ const WaitingRoomModal = ({ isWaitingModalVisible, onWaitingRoomClose, waitingRoomCounter, onWaitingRoomFilterChange, waitingRoomList, updateWaitingList, roomName, socket, onWaitingRoomItemPress = respondToWaiting, position = "topRight", backgroundColor = "#83c0e9", parameters, }) => { const screenWidth = Dimensions.get("window").width; let modalWidth = 0.8 * screenWidth; if (modalWidth > 400) { modalWidth = 400; } const [filteredWaitingRoomList, setFilteredWaitingRoomList] = useState(waitingRoomList); const [waitingRoomCounter_s, setWaitingRoomCounter_s] = useState(waitingRoomCounter); const [filterText, setFilterText] = useState(""); useEffect(() => { const { getUpdatedAllParams } = parameters; const updatedParams = getUpdatedAllParams(); setFilteredWaitingRoomList(updatedParams.filteredWaitingRoomList); setWaitingRoomCounter_s(updatedParams.filteredWaitingRoomList.length); }, [waitingRoomList, parameters]); return (<Modal transparent animationType="fade" visible={isWaitingModalVisible} onRequestClose={onWaitingRoomClose}> <View style={[styles.modalContainer, getModalPosition({ position })]}> <View style={[styles.modalContent, { backgroundColor, width: modalWidth }]}> {/* Header */} <View style={styles.modalHeader}> <Text style={styles.modalTitle}> Waiting <Text style={styles.badge}>{waitingRoomCounter_s}</Text> </Text> <Pressable onPress={onWaitingRoomClose} style={styles.closeButton}> <FontAwesome name="times" size={24} color="black"/> </Pressable> </View> <View style={styles.separator}/> {/* Search Input */} <View style={styles.modalBody}> <View style={styles.formGroup}> <TextInput style={styles.input} placeholder="Search ..." value={filterText} onChangeText={(text) => { setFilterText(text); onWaitingRoomFilterChange(text); }}/> </View> {/* Waiting List */} <ScrollView style={styles.scrollView}> <View> {filteredWaitingRoomList && filteredWaitingRoomList.length > 0 ? (filteredWaitingRoomList.map((participant, index) => (<View key={index} style={styles.waitingItem}> <View style={styles.participantName}> <Text style={styles.participantText}> {participant.name} </Text> </View> <View style={styles.actionButtons}> {/* Accept Button */} <Pressable style={styles.acceptButton} onPress={() => onWaitingRoomItemPress({ participantId: participant.id, participantName: participant.name, updateWaitingList, waitingList: waitingRoomList, roomName, type: true, // accepted socket, })}> <FontAwesome name="check" size={24} color="green"/> </Pressable> {/* Reject Button */} <Pressable style={styles.rejectButton} onPress={() => onWaitingRoomItemPress({ participantId: participant.id, participantName: participant.name, updateWaitingList, waitingList: waitingRoomList, roomName, type: false, // rejected socket, })}> <FontAwesome name="times" size={24} color="red"/> </Pressable> </View> </View>))) : (<Text style={styles.noParticipantsText}> No participants found. </Text>)} </View> </ScrollView> </View> </View> </View> </Modal>); }; export default WaitingRoomModal; /** * Stylesheet for the WaitingRoomModal component. */ const styles = StyleSheet.create({ modalContainer: { flex: 1, justifyContent: "flex-end", alignItems: "flex-end", zIndex: 9, elevation: 9, borderWidth: 2, borderColor: "black", }, modalContent: { height: "65%", backgroundColor: "#83c0e9", borderRadius: 10, padding: 15, maxHeight: "80%", shadowColor: "#000", shadowOffset: { width: 0, height: 2 }, shadowOpacity: 0.25, shadowRadius: 4, zIndex: 9, elevation: 9, borderWidth: 2, borderColor: "black", }, modalHeader: { flexDirection: "row", justifyContent: "space-between", alignItems: "center", marginBottom: 15, }, modalTitle: { fontSize: 18, fontWeight: "bold", color: "black", flexDirection: "row", alignItems: "center", }, badge: { backgroundColor: "#fff", color: "#000", borderRadius: 12, paddingHorizontal: 5, paddingVertical: 2, marginLeft: 5, fontSize: 14, }, modalBody: { flex: 1, }, closeButton: { padding: 5, marginRight: 10, }, separator: { height: 1, backgroundColor: "#000000", marginVertical: 10, }, formGroup: { marginBottom: 15, }, input: { height: 40, borderColor: "gray", borderWidth: 1, borderRadius: 5, paddingLeft: 10, fontSize: 16, color: "black", }, scrollView: { flexGrow: 1, maxHeight: "100%", maxWidth: "100%", }, waitingItem: { flexDirection: "row", alignItems: "center", marginVertical: 5, paddingVertical: 10, borderBottomWidth: 1, borderBottomColor: "#ddd", }, participantName: { flex: 5, }, participantText: { fontSize: 16, color: "black", }, actionButtons: { flex: 2, flexDirection: "row", justifyContent: "space-around", alignItems: "center", }, acceptButton: { padding: 5, }, rejectButton: { padding: 5, }, noParticipantsText: { textAlign: "center", color: "gray", fontSize: 16, marginTop: 20, }, }); //# sourceMappingURL=WaitingModal.js.map