This commit is contained in:
Abin Toppo
2025-10-01 15:43:42 +05:30
27 changed files with 526 additions and 2300 deletions
+13 -20
View File
@@ -1,5 +1,4 @@
// src/screens/ManagementScreen.tsx
import React, { useState, useCallback, FC, useEffect } from "react";
import {
View,
@@ -16,13 +15,13 @@ import { APPROVE_REQUEST_URL, DECLINE_REQUEST_URL, GET_JOINED_GROUP_URL, MY_GROU
import colors from "../../components/colors";
import AppView from "../../components/AppView";
import { apiCall } from "../../utils/ApiHelper";
import { MyGroup, JoinedGroup, JoinRequest, ApiResponse, UserJoinRequest } from '../../types'; // Adjust import path
import { MyGroup, JoinedGroup, JoinRequest, ApiResponse, UserJoinRequest } from '../../types';
import { MyGroupCard } from "../../components/MyGroupCard";
import { JoinedGroupCard } from "../../components/JoinedGroupCard";
import { RequestCard } from "../../components/RequestCard";
import { useSelector } from "react-redux";
import { UserRequested } from "../../components/UserRequested";
import { RootTabParamList } from "../../navigation/BottomTabs"; // Adjust import path
import { RootTabParamList } from "../../navigation/BottomTabs";
import { RootStackParamList } from "../../navigation/AppNavigator";
// --- TYPE DEFINITIONS ---
@@ -34,7 +33,6 @@ const ManagementScreen: FC = () => {
const user = useSelector((state: any) => state.user);
const navigation = useNavigation<GroupManagementNavProp>();
const route = useRoute<ManagementRouteProp>();
const [activeTab, setActiveTab] = useState<ActiveTab>(user.role === "USER" ? "Joined Groups" : "My Groups");
const [myGroups, setMyGroups] = useState<MyGroup[]>([]);
const [joinedGroups, setJoinedGroups] = useState<JoinedGroup[]>([]);
@@ -43,9 +41,7 @@ const ManagementScreen: FC = () => {
const [loading, setLoading] = useState<boolean>(false);
const [error, setError] = useState<string | null>(null);
// --- HOOKS ---
// Effect to set the initial tab from route params
useEffect(() => {
const passedTab = route.params?.actionTab;
if (passedTab) {
@@ -56,9 +52,9 @@ const ManagementScreen: FC = () => {
}
}, [route.params?.actionTab, user.role]);
// --- FIXED: fetchData dependency array is corrected ---
const fetchData = useCallback(async () => {
// Check for loading state at the start to prevent multiple simultaneous fetches
if (loading) return;
setLoading(true);
@@ -87,20 +83,18 @@ const ManagementScreen: FC = () => {
} finally {
setLoading(false);
}
// The only external dependency that should trigger a re-fetch is the user's role.
}, [user.role]); // **FIXED**: Removed `loading` from the dependency array
// --- FIXED: useFocusEffect now has a stable dependency ---
}, [user.role]);
useFocusEffect(
useCallback(() => {
fetchData();
}, [fetchData]) // This will now only re-run if fetchData (and thus user.role) changes.
}, [fetchData])
);
// --- HANDLERS (No changes needed here) ---
const handleViewGroup = (item: JoinedGroup) => {
// Assuming you have an 'Invite' screen in your RootTabParamList or another navigator
// navigation.navigate('Invite' as any, { groupId: item.id });
};
const handleAction = async (url: string, successMessage: string, failureMessage: string) => {
@@ -122,10 +116,9 @@ const ManagementScreen: FC = () => {
const handleDecline = (req: JoinRequest) => handleAction(DECLINE_REQUEST_URL + req.requestId + "/reject?reason=/", `Request from ${req.userName} has been declined.`, "Failed to decline request.");
const handleManageGroup = (group: MyGroup) => navigation.navigate('ManagementTabs', { groupId: group.id });
// --- RENDER LOGIC ---
const renderContent = () => {
if (error) return <Text style={styles.emptyText}>{error}</Text>;
// Improved loading logic to avoid hiding existing data during a refresh
if (loading && myGroups.length === 0 && joinedGroups.length === 0 && requests.length === 0) {
return <ActivityIndicator size="large" color={colors.primary} style={styles.loader} />;
}
@@ -168,12 +161,12 @@ const styles = StyleSheet.create({
container: { flex: 1, backgroundColor: '#f5f6fa' },
header: { paddingHorizontal: 20, paddingBottom: 15, paddingTop: 10 },
title: { fontSize: 22, fontWeight: "600", color: colors.Settings },
segmentedControl: { flexDirection: 'row', backgroundColor: '#e9ecef', borderRadius: 10, marginHorizontal: 20, marginBottom: 20, padding: 3 },
segmentedControl: { flexDirection: 'row',borderRadius: 10, marginHorizontal: 20, marginBottom: 20, padding: 3 },
segmentButton: { flex: 1, paddingVertical: 12, alignItems: 'center', borderRadius: 8 },
segmentActive: { backgroundColor: colors.pastelOrange, elevation: 3, shadowColor: '#000', shadowOpacity: 0.1, shadowRadius: 5 },
segmentActive: { backgroundColor: colors.pastelOrange, elevation: 5,borderRadius:15, shadowColor: '#000', shadowOpacity: 0.1, shadowRadius: 5 },
segmentText: { fontSize: 14, fontWeight: '600', color: '#6c757d' },
segmentTextActive: { color: colors.textDark },
contentArea: { flex: 1, paddingHorizontal: 20 },
contentArea: { flex: 1},
loader: { marginTop: 50 },
emptyText: { textAlign: 'center', marginTop: 60, fontSize: 16, color: '#6c757d' },
});