refactor(HomeScreen): simplify capsule visibility logic and improve list rendering
- Removed unnecessary state and logic related to capsule visibility based on scroll position, streamlining the component's functionality. - Adjusted FlatList properties to enhance rendering performance and layout consistency. - Updated styles for the list header to ensure full-width display, improving the overall UI experience.
This commit is contained in:
@@ -9,9 +9,7 @@ import {
|
||||
View,
|
||||
FlatList,
|
||||
ScrollView,
|
||||
LayoutAnimation,
|
||||
Platform,
|
||||
UIManager,
|
||||
StyleSheet,
|
||||
RefreshControl,
|
||||
StatusBar,
|
||||
@@ -48,7 +46,6 @@ const SWIPE_COOLDOWN_MS = 300;
|
||||
const MOBILE_TAB_BAR_HEIGHT = 64;
|
||||
const MOBILE_TAB_FLOATING_MARGIN = 12;
|
||||
const MOBILE_FAB_GAP = 12;
|
||||
const CAPSULE_HIDE_THRESHOLD = 24;
|
||||
|
||||
type ViewMode = 'list' | 'grid';
|
||||
type PostType = 'follow' | 'hot' | 'latest';
|
||||
@@ -77,7 +74,6 @@ export const HomeScreen: React.FC = () => {
|
||||
const [viewMode, setViewMode] = useState<ViewMode>('list');
|
||||
const [latestCapsules, setLatestCapsules] = useState<LatestCapsule[]>([{ id: '', name: '全部' }]);
|
||||
const [activeCapsuleId, setActiveCapsuleId] = useState('');
|
||||
const [showLatestCapsules, setShowLatestCapsules] = useState(true);
|
||||
|
||||
// 图片查看器状态
|
||||
const [showImageViewer, setShowImageViewer] = useState(false);
|
||||
@@ -94,15 +90,8 @@ export const HomeScreen: React.FC = () => {
|
||||
const postIdsRef = useRef<Set<string>>(new Set());
|
||||
const lastSwipeAtRef = useRef(0);
|
||||
|
||||
// 网格模式滚动位置检测
|
||||
const gridScrollYRef = useRef(0);
|
||||
const listScrollYRef = useRef(0);
|
||||
const isLoadingMoreRef = useRef(false);
|
||||
|
||||
if (Platform.OS === 'android' && UIManager.setLayoutAnimationEnabledExperimental) {
|
||||
UIManager.setLayoutAnimationEnabledExperimental(true);
|
||||
}
|
||||
|
||||
// 构建一个以 postId 为 key 的 map,用于快速查找
|
||||
const postsMap = useMemo(() => {
|
||||
const map = new Map<string, Post>();
|
||||
@@ -125,21 +114,6 @@ export const HomeScreen: React.FC = () => {
|
||||
const isLatestTab = activeIndex === 1;
|
||||
const currentChannelId = isLatestTab && activeCapsuleId ? activeCapsuleId : undefined;
|
||||
|
||||
const updateCapsuleVisibilityByScroll = useCallback((nextY: number, previousY: number) => {
|
||||
if (!isLatestTab) return;
|
||||
const delta = nextY - previousY;
|
||||
const isScrollingDown = delta > CAPSULE_HIDE_THRESHOLD;
|
||||
const isScrollingUp = delta < -CAPSULE_HIDE_THRESHOLD;
|
||||
|
||||
if (isScrollingDown && showLatestCapsules) {
|
||||
LayoutAnimation.configureNext(LayoutAnimation.Presets.easeInEaseOut);
|
||||
setShowLatestCapsules(false);
|
||||
} else if (isScrollingUp && !showLatestCapsules) {
|
||||
LayoutAnimation.configureNext(LayoutAnimation.Presets.easeInEaseOut);
|
||||
setShowLatestCapsules(true);
|
||||
}
|
||||
}, [isLatestTab, showLatestCapsules]);
|
||||
|
||||
// 使用差异更新 Hook 获取帖子列表
|
||||
const listKey = useMemo(
|
||||
() => `home_${getPostType()}_${currentChannelId || 'all'}`,
|
||||
@@ -196,9 +170,7 @@ export const HomeScreen: React.FC = () => {
|
||||
if (scrollY + visibleHeight >= contentHeight - 200) {
|
||||
loadMore();
|
||||
}
|
||||
updateCapsuleVisibilityByScroll(scrollY, gridScrollYRef.current);
|
||||
gridScrollYRef.current = scrollY;
|
||||
}, [loadMore, updateCapsuleVisibilityByScroll]);
|
||||
}, [loadMore]);
|
||||
|
||||
// 刷新方法 - 先获取正确类型的帖子,再刷新
|
||||
const refresh = useCallback(async () => {
|
||||
@@ -303,12 +275,6 @@ export const HomeScreen: React.FC = () => {
|
||||
setActiveIndex(nextIndex);
|
||||
}, [activeIndex]);
|
||||
|
||||
useEffect(() => {
|
||||
setShowLatestCapsules(true);
|
||||
listScrollYRef.current = 0;
|
||||
gridScrollYRef.current = 0;
|
||||
}, [activeIndex]);
|
||||
|
||||
useEffect(() => {
|
||||
const loadChannels = async () => {
|
||||
const list = await channelService.list();
|
||||
@@ -481,7 +447,7 @@ export const HomeScreen: React.FC = () => {
|
||||
};
|
||||
|
||||
const renderLatestCapsules = () => {
|
||||
if (!isLatestTab || !showLatestCapsules) {
|
||||
if (!isLatestTab) {
|
||||
return null;
|
||||
}
|
||||
|
||||
@@ -716,6 +682,7 @@ export const HomeScreen: React.FC = () => {
|
||||
renderItem={renderPostList}
|
||||
keyExtractor={keyExtractor}
|
||||
ListHeaderComponent={renderLatestCapsules()}
|
||||
ListHeaderComponentStyle={styles.listHeader}
|
||||
contentContainerStyle={[
|
||||
styles.listContent,
|
||||
{
|
||||
@@ -735,11 +702,6 @@ export const HomeScreen: React.FC = () => {
|
||||
}
|
||||
onEndReached={loadMore}
|
||||
onEndReachedThreshold={0.3}
|
||||
onScroll={(event) => {
|
||||
const nextY = event.nativeEvent.contentOffset.y;
|
||||
updateCapsuleVisibilityByScroll(nextY, listScrollYRef.current);
|
||||
listScrollYRef.current = nextY;
|
||||
}}
|
||||
scrollEventThrottle={16}
|
||||
ListEmptyComponent={renderEmpty}
|
||||
ListFooterComponent={isLoadingMore ? <Loading size="sm" /> : null}
|
||||
@@ -747,7 +709,7 @@ export const HomeScreen: React.FC = () => {
|
||||
maxToRenderPerBatch={8}
|
||||
updateCellsBatchingPeriod={60}
|
||||
windowSize={7}
|
||||
removeClippedSubviews
|
||||
removeClippedSubviews={false}
|
||||
/>
|
||||
);
|
||||
};
|
||||
@@ -918,6 +880,9 @@ const styles = StyleSheet.create({
|
||||
listContent: {
|
||||
flexGrow: 1,
|
||||
},
|
||||
listHeader: {
|
||||
width: '100%',
|
||||
},
|
||||
contentContainer: {
|
||||
flex: 1,
|
||||
},
|
||||
|
||||
Reference in New Issue
Block a user