feat: add QR code login and enhance chat experience

- Add QR code login flow with scanner and confirmation screens
- Implement swipe-to-reply in chat with SwipeableMessageBubble
- Replace FlatList with FlashList for chat performance optimization
- Add Schedule stack navigator with CourseDetail screen support
- Configure deep linking for QR code login (carrotbbs://qrcode/login/:sessionId)
- Update branding from 胡萝卜 to 萝卜社区
- Display dynamic app version in settings
This commit is contained in:
lafay
2026-03-20 19:28:42 +08:00
parent 59877e6ae3
commit a005fb0a15
24 changed files with 2878 additions and 1859 deletions

View File

@@ -42,6 +42,8 @@ import { getUserCache } from '../../services/database';
import { EmbeddedChat } from './components/EmbeddedChat';
// 导入 NotificationsScreen 用于在内部显示
import { NotificationsScreen } from './NotificationsScreen';
// 导入扫码组件
import { QRCodeScanner } from '../../components/business/QRCodeScanner';
type NavigationProp = NativeStackNavigationProp<RootStackParamList>;
type MessageNavProp = NativeStackNavigationProp<MessageStackParamList>;
@@ -182,6 +184,7 @@ export const MessageListScreen: React.FC = () => {
const [isSearching, setIsSearching] = useState(false);
const [activeSearchTab, setActiveSearchTab] = useState<'chat' | 'user'>('chat');
const [actionMenuVisible, setActionMenuVisible] = useState(false);
const [scannerVisible, setScannerVisible] = useState(false);
// 系统通知显示状态 - 用于在移动端显示通知页面
const [showNotifications, setShowNotifications] = useState(false);
@@ -356,7 +359,7 @@ export const MessageListScreen: React.FC = () => {
setActionMenuVisible(true);
};
const runMenuAction = (action: 'join' | 'create' | 'readAll') => {
const runMenuAction = (action: 'join' | 'create' | 'readAll' | 'scanQRCode') => {
setActionMenuVisible(false);
if (action === 'join') {
handleJoinGroup();
@@ -366,6 +369,10 @@ export const MessageListScreen: React.FC = () => {
handleCreateGroup();
return;
}
if (action === 'scanQRCode') {
setScannerVisible(true);
return;
}
handleMarkAllRead();
};
@@ -911,6 +918,10 @@ export const MessageListScreen: React.FC = () => {
<Modal visible={actionMenuVisible} transparent animationType="fade" onRequestClose={() => setActionMenuVisible(false)}>
<Pressable style={styles.actionMenuBackdrop} onPress={() => setActionMenuVisible(false)}>
<View style={styles.actionMenu}>
<TouchableOpacity style={styles.actionMenuItem} onPress={() => runMenuAction('scanQRCode')}>
<MaterialCommunityIcons name="qrcode-scan" size={21} color="#444" />
<Text style={styles.actionMenuText}></Text>
</TouchableOpacity>
<TouchableOpacity style={styles.actionMenuItem} onPress={() => runMenuAction('join')}>
<MaterialCommunityIcons name="account-plus-outline" size={21} color="#444" />
<Text style={styles.actionMenuText}></Text>
@@ -980,6 +991,7 @@ export const MessageListScreen: React.FC = () => {
renderConversationList()
)}
{renderActionMenu()}
<QRCodeScanner visible={scannerVisible} onClose={() => setScannerVisible(false)} />
</SafeAreaView>
);
};