refactor(TabsLayout, ImageGallery, ChatScreen, GroupInfoScreen, PrivateChatInfoScreen): enhance UI components and improve layout structure
All checks were successful
Frontend CI / build-and-push-web (push) Successful in 3m4s
Frontend CI / ota-android (push) Successful in 12m24s
Frontend CI / build-android-apk (push) Successful in 1h17m36s

- Adjusted tab bar dimensions and margins in TabsLayout for better visual consistency.
- Streamlined ImageGallery by removing loading states and optimizing image transition handling.
- Updated ChatScreen to utilize SafeAreaView for improved layout on different devices.
- Enhanced GroupInfoScreen and PrivateChatInfoScreen with a consistent page header layout, including back navigation.
- Refactored ChatHeader to simplify structure and improve maintainability.
This commit is contained in:
lafay
2026-03-24 15:39:28 +08:00
parent 2ddb9cadd8
commit b49cc0f3bd
6 changed files with 126 additions and 110 deletions

View File

@@ -29,7 +29,7 @@ import {
} from 'react-native';
import { useNavigation, useRouter } from 'expo-router';
import { StatusBar } from 'expo-status-bar';
import { useSafeAreaInsets } from 'react-native-safe-area-context';
import { SafeAreaView, useSafeAreaInsets } from 'react-native-safe-area-context';
import { Text, ImageGallery, ImageGridItem } from '../../components/common';
import { colors } from '../../theme';
import * as hrefs from '../../navigation/hrefs';
@@ -364,12 +364,13 @@ export const ChatScreen: React.FC = () => {
}, [handleMessageListContentSizeChange]);
return (
<KeyboardAvoidingView
style={containerStyle}
behavior={Platform.OS === 'ios' ? 'padding' : undefined}
keyboardVerticalOffset={Platform.OS === 'ios' ? 0 : 0}
>
<StatusBar style="dark" backgroundColor="#FFFFFF" />
<SafeAreaView style={containerStyle} edges={['top']}>
<KeyboardAvoidingView
style={styles.container}
behavior={Platform.OS === 'ios' ? 'padding' : undefined}
keyboardVerticalOffset={Platform.OS === 'ios' ? 0 : 0}
>
<StatusBar style="dark" backgroundColor="#FFFFFF" />
{/* 顶部栏 */}
<ChatHeader
@@ -587,32 +588,33 @@ export const ChatScreen: React.FC = () => {
/>
{/* 群信息侧边栏面板 - 仅大屏幕显示 */}
<GroupInfoPanel
visible={showGroupInfoPanel}
groupId={routeGroupId ? String(routeGroupId) : undefined}
groupInfo={groupInfo as any}
conversationId={conversationId || undefined}
currentUserId={currentUserId}
isPinned={false}
onClose={handleCloseGroupInfoPanel}
onTogglePin={(pinned) => {
// TODO: 实现置顶功能
console.log('Toggle pin:', pinned);
}}
onLeaveGroup={() => {
// TODO: 实现退出群聊功能
console.log('Leave group');
}}
onInviteMembers={() => {
// TODO: 实现邀请新成员功能
console.log('Invite members');
}}
onViewAllMembers={() => {
// TODO: 实现查看全部成员功能
console.log('View all members');
}}
/>
</KeyboardAvoidingView>
<GroupInfoPanel
visible={showGroupInfoPanel}
groupId={routeGroupId ? String(routeGroupId) : undefined}
groupInfo={groupInfo as any}
conversationId={conversationId || undefined}
currentUserId={currentUserId}
isPinned={false}
onClose={handleCloseGroupInfoPanel}
onTogglePin={(pinned) => {
// TODO: 实现置顶功能
console.log('Toggle pin:', pinned);
}}
onLeaveGroup={() => {
// TODO: 实现退出群聊功能
console.log('Leave group');
}}
onInviteMembers={() => {
// TODO: 实现邀请新成员功能
console.log('Invite members');
}}
onViewAllMembers={() => {
// TODO: 实现查看全部成员功能
console.log('View all members');
}}
/>
</KeyboardAvoidingView>
</SafeAreaView>
);
};

View File

@@ -44,6 +44,7 @@ import * as hrefs from '../../navigation/hrefs';
import { messageManager } from '../../stores/messageManager';
import { groupManager } from '../../stores/groupManager';
import MutualFollowSelectorModal from './components/MutualFollowSelectorModal';
import { AppBackButton } from '../../components/common';
const { width: SCREEN_WIDTH } = Dimensions.get('window');
@@ -537,7 +538,12 @@ const GroupInfoScreen: React.FC = () => {
if (loading) {
return (
<SafeAreaView style={styles.container} edges={['bottom']}>
<SafeAreaView style={styles.container} edges={['top', 'bottom']}>
<View style={styles.pageHeader}>
<AppBackButton onPress={() => router.back()} />
<Text variant="h3" style={styles.pageTitle}></Text>
<View style={styles.pageHeaderPlaceholder} />
</View>
<Loading />
</SafeAreaView>
);
@@ -545,7 +551,12 @@ const GroupInfoScreen: React.FC = () => {
if (!group) {
return (
<SafeAreaView style={styles.container} edges={['bottom']}>
<SafeAreaView style={styles.container} edges={['top', 'bottom']}>
<View style={styles.pageHeader}>
<AppBackButton onPress={() => router.back()} />
<Text variant="h3" style={styles.pageTitle}></Text>
<View style={styles.pageHeaderPlaceholder} />
</View>
<View style={styles.errorContainer}>
<Text variant="body" color={colors.text.secondary}>
@@ -556,7 +567,12 @@ const GroupInfoScreen: React.FC = () => {
}
return (
<SafeAreaView style={styles.container} edges={['bottom']}>
<SafeAreaView style={styles.container} edges={['top', 'bottom']}>
<View style={styles.pageHeader}>
<AppBackButton onPress={() => router.back()} />
<Text variant="h3" style={styles.pageTitle}></Text>
<View style={styles.pageHeaderPlaceholder} />
</View>
<ScrollView
style={styles.scrollView}
contentContainerStyle={styles.scrollContent}
@@ -1060,6 +1076,23 @@ const styles = StyleSheet.create({
flex: 1,
backgroundColor: colors.background.default,
},
pageHeader: {
flexDirection: 'row',
alignItems: 'center',
justifyContent: 'space-between',
paddingHorizontal: spacing.md,
paddingVertical: spacing.sm,
backgroundColor: colors.background.paper,
borderBottomWidth: 1,
borderBottomColor: colors.divider,
},
pageTitle: {
fontWeight: '600',
},
pageHeaderPlaceholder: {
width: 40,
height: 40,
},
scrollView: {
flex: 1,
},

View File

@@ -30,6 +30,7 @@ import { userManager } from '../../stores/userManager';
import { Avatar, Text, Button, Loading, Divider } from '../../components/common';
import { User } from '../../types';
import * as hrefs from '../../navigation/hrefs';
import { AppBackButton } from '../../components/common';
const PrivateChatInfoScreen: React.FC = () => {
const router = useRouter();
@@ -309,7 +310,12 @@ const PrivateChatInfoScreen: React.FC = () => {
if (loading) {
return (
<SafeAreaView style={styles.container} edges={['bottom']}>
<SafeAreaView style={styles.container} edges={['top', 'bottom']}>
<View style={styles.pageHeader}>
<AppBackButton onPress={() => router.back()} />
<Text variant="h3" style={styles.pageTitle}></Text>
<View style={styles.pageHeaderPlaceholder} />
</View>
<Loading />
</SafeAreaView>
);
@@ -322,7 +328,12 @@ const PrivateChatInfoScreen: React.FC = () => {
};
return (
<SafeAreaView style={styles.container} edges={['bottom']}>
<SafeAreaView style={styles.container} edges={['top', 'bottom']}>
<View style={styles.pageHeader}>
<AppBackButton onPress={() => router.back()} />
<Text variant="h3" style={styles.pageTitle}></Text>
<View style={styles.pageHeaderPlaceholder} />
</View>
<ScrollView
style={styles.scrollView}
contentContainerStyle={styles.scrollContent}
@@ -414,6 +425,23 @@ const styles = StyleSheet.create({
flex: 1,
backgroundColor: colors.background.default,
},
pageHeader: {
flexDirection: 'row',
alignItems: 'center',
justifyContent: 'space-between',
paddingHorizontal: spacing.md,
paddingVertical: spacing.sm,
backgroundColor: colors.background.paper,
borderBottomWidth: 1,
borderBottomColor: colors.divider,
},
pageTitle: {
fontWeight: '600',
},
pageHeaderPlaceholder: {
width: 40,
height: 40,
},
scrollView: {
flex: 1,
},

View File

@@ -5,7 +5,6 @@
import React, { useMemo } from 'react';
import { View, TouchableOpacity, StyleSheet } from 'react-native';
import { SafeAreaView } from 'react-native-safe-area-context';
import { MaterialCommunityIcons } from '@expo/vector-icons';
import { Avatar, Text, AppBackButton } from '../../../../components/common';
import { colors, spacing } from '../../../../theme';
@@ -69,14 +68,9 @@ export const ChatHeader: React.FC<ChatHeaderProps> = ({
};
return (
<SafeAreaView edges={['top']} style={styles.headerContainer}>
<View style={styles.headerContainer}>
<View style={styles.header}>
{/* 大屏幕(>= 768px时隐藏返回按钮 */}
{!isWideScreen ? (
<AppBackButton style={styles.backButton} onPress={onBack} />
) : (
<View style={styles.backButton} />
)}
<AppBackButton style={styles.backButton} onPress={onBack} />
<View style={styles.headerCenter}>
<TouchableOpacity
@@ -136,7 +130,7 @@ export const ChatHeader: React.FC<ChatHeaderProps> = ({
</TouchableOpacity>
)}
</View>
</SafeAreaView>
</View>
);
};