380 lines
9.2 KiB
Markdown
380 lines
9.2 KiB
Markdown
# GuideBar 统一控制实现总结
|
||
|
||
## ✅ 已完成的统一改造
|
||
|
||
所有页面和组件现在都使用 **`global store`** 统一管理 `GuideBar` 的显示与隐藏。
|
||
|
||
---
|
||
|
||
## 📦 核心实现
|
||
|
||
### 1. **Global Store** (`src/store/global.ts`)
|
||
|
||
```typescript
|
||
interface GlobalState {
|
||
showGuideBar: boolean;
|
||
guideBarZIndex: 'low' | 'high';
|
||
}
|
||
|
||
interface GlobalActions {
|
||
setShowGuideBar: (show: boolean) => void;
|
||
setGuideBarZIndex: (zIndex: 'low' | 'high') => void;
|
||
toggleGuideBar: () => void;
|
||
}
|
||
|
||
// 使用方法
|
||
import { useGlobalState } from "@/store/global";
|
||
|
||
const { showGuideBar, setShowGuideBar } = useGlobalState();
|
||
```
|
||
|
||
---
|
||
|
||
## 🎯 已改造的组件
|
||
|
||
### 1️⃣ **LocationConfirmDialog** - 定位确认弹窗
|
||
**文件:** `src/components/LocationConfirmDialog/index.tsx`
|
||
|
||
**改造内容:**
|
||
- 使用 `useEffect` 监听 `visible` 状态
|
||
- `visible = true` 时自动隐藏 GuideBar
|
||
- `visible = false` 时自动显示 GuideBar
|
||
|
||
```typescript
|
||
const { setShowGuideBar } = useGlobalState();
|
||
|
||
useEffect(() => {
|
||
if (visible) {
|
||
setShowGuideBar(false); // 弹窗显示时隐藏
|
||
} else {
|
||
setShowGuideBar(true); // 弹窗关闭时显示
|
||
}
|
||
}, [visible, setShowGuideBar]);
|
||
```
|
||
|
||
**使用场景:**
|
||
- 用户首次打开应用时的定位确认
|
||
- 检测到位置变化时的切换提示
|
||
|
||
---
|
||
|
||
### 2️⃣ **HomeNavbar** - 首页导航栏
|
||
**文件:** `src/components/HomeNavbar/index.tsx`
|
||
|
||
**改造内容:**
|
||
- 引入 `setShowGuideBar` 方法
|
||
- 在显示定位弹窗时调用隐藏
|
||
- 在确认/取消时调用显示
|
||
|
||
```typescript
|
||
const { setShowGuideBar } = useGlobalState();
|
||
|
||
const showLocationConfirmDialog = () => {
|
||
setShowGuideBar(false);
|
||
// ...
|
||
};
|
||
|
||
const handleLocationDialogConfirm = () => {
|
||
// ...
|
||
setShowGuideBar(true);
|
||
};
|
||
|
||
const handleLocationDialogCancel = () => {
|
||
// ...
|
||
setShowGuideBar(true);
|
||
};
|
||
```
|
||
|
||
**使用场景:**
|
||
- 城市切换提示
|
||
- 定位权限请求
|
||
|
||
---
|
||
|
||
### 3️⃣ **UserInfo** - 用户信息组件(✨ 重要改造)
|
||
**文件:** `src/components/UserInfo/index.tsx`
|
||
|
||
**改造内容:**
|
||
- ❌ 移除 `FamilyContext` 依赖
|
||
- ✅ 改用 `useGlobalState` 统一管理
|
||
- 优化了所有选择器(性别、地区、NTRP、职业)的 GuideBar 控制逻辑
|
||
|
||
**之前(使用 Context):**
|
||
```typescript
|
||
const { handleGrandchildTrigger } = useContext(FamilyContext);
|
||
handleGrandchildTrigger(true); // 隐藏(逻辑反转)
|
||
handleGrandchildTrigger(false); // 显示
|
||
```
|
||
|
||
**现在(使用 Store):**
|
||
```typescript
|
||
const { setShowGuideBar } = useGlobalState();
|
||
setShowGuideBar(false); // 隐藏(直观明了)
|
||
setShowGuideBar(true); // 显示
|
||
```
|
||
|
||
**具体改动:**
|
||
|
||
1. **打开编辑弹窗时隐藏 GuideBar**
|
||
```typescript
|
||
const handle_open_edit_modal = (field: string) => {
|
||
setShowGuideBar(false); // 之前: handleGrandchildTrigger(true)
|
||
// ...
|
||
};
|
||
```
|
||
|
||
2. **关闭编辑弹窗时显示 GuideBar**
|
||
```typescript
|
||
const handle_edit_modal_cancel = () => {
|
||
setShowGuideBar(true); // 之前: handleGrandchildTrigger(false)
|
||
// ...
|
||
};
|
||
```
|
||
|
||
3. **选择器状态联动**
|
||
```typescript
|
||
useEffect(() => {
|
||
const visibles = [
|
||
gender_picker_visible,
|
||
location_picker_visible,
|
||
ntrp_picker_visible,
|
||
occupation_picker_visible,
|
||
];
|
||
const allPickersClosed = visibles.every((item) => !item);
|
||
// 所有选择器都关闭时显示 GuideBar,否则隐藏
|
||
setShowGuideBar(allPickersClosed);
|
||
}, [
|
||
gender_picker_visible,
|
||
location_picker_visible,
|
||
ntrp_picker_visible,
|
||
occupation_picker_visible,
|
||
]);
|
||
```
|
||
|
||
**使用场景:**
|
||
- "我的"页面编辑个人信息
|
||
- 性别选择器
|
||
- 地区选择器
|
||
- NTRP 等级选择器
|
||
- 职业选择器
|
||
- 昵称/简介编辑
|
||
|
||
---
|
||
|
||
### 4️⃣ **MainPage** - 主页面容器
|
||
**文件:** `src/main_pages/index.tsx`
|
||
|
||
**改造内容:**
|
||
- 从 store 获取 `showGuideBar` 和 `setShowGuideBar`
|
||
- 保留 `handleGrandchildTrigger` 以保持向后兼容(但已无实际使用)
|
||
|
||
```typescript
|
||
const { showGuideBar, guideBarZIndex, setShowGuideBar, setGuideBarZIndex } = useGlobalState();
|
||
|
||
// 根据状态渲染 GuideBar
|
||
{
|
||
showGuideBar ?
|
||
<GuideBar
|
||
currentPage={currentTab}
|
||
guideBarClassName={guideBarZIndex === 'low' ? 'guide-bar-low-z-index' : 'guide-bar-high-z-index'}
|
||
onTabChange={handleTabChange}
|
||
onPublishMenuVisibleChange={handlePublishMenuVisibleChange}
|
||
/> :
|
||
null
|
||
}
|
||
```
|
||
|
||
---
|
||
|
||
## 🔄 工作流程
|
||
|
||
### 示例:用户编辑个人信息
|
||
|
||
1. **用户点击"编辑"按钮**
|
||
```
|
||
handle_open_edit_modal() 调用
|
||
→ setShowGuideBar(false)
|
||
→ GuideBar 隐藏
|
||
```
|
||
|
||
2. **用户打开性别选择器**
|
||
```
|
||
setGenderPickerVisible(true)
|
||
→ useEffect 检测到 visibles 变化
|
||
→ setShowGuideBar(false)
|
||
→ GuideBar 保持隐藏
|
||
```
|
||
|
||
3. **用户关闭选择器**
|
||
```
|
||
setGenderPickerVisible(false)
|
||
→ useEffect 检测到所有选择器都关闭
|
||
→ setShowGuideBar(true)
|
||
→ GuideBar 显示
|
||
```
|
||
|
||
4. **用户点击"取消"**
|
||
```
|
||
handle_edit_modal_cancel() 调用
|
||
→ setShowGuideBar(true)
|
||
→ GuideBar 显示
|
||
```
|
||
|
||
---
|
||
|
||
## 📊 对比表
|
||
|
||
| 项目 | 之前(FamilyContext) | 现在(Global Store) |
|
||
|------|---------------------|---------------------|
|
||
| **状态管理** | Context API(跨层传递) | Zustand Store(全局统一) |
|
||
| **调用方式** | `handleGrandchildTrigger(value)` | `setShowGuideBar(show)` |
|
||
| **逻辑清晰度** | ❌ 反转逻辑(true=隐藏) | ✅ 直观逻辑(false=隐藏) |
|
||
| **依赖关系** | ❌ 需要 Context Provider | ✅ 直接引入 hook |
|
||
| **类型安全** | ⚠️ `any` 类型 | ✅ 完整 TypeScript 类型 |
|
||
| **调试能力** | ❌ 难以追踪状态变化 | ✅ 集中日志,易于调试 |
|
||
| **可维护性** | ⚠️ 分散在多处 | ✅ 统一管理 |
|
||
| **性能** | ⚠️ Context 更新触发重渲染 | ✅ Zustand 精确订阅 |
|
||
|
||
---
|
||
|
||
## 🎨 优势
|
||
|
||
### 1. **代码更简洁**
|
||
```typescript
|
||
// 之前
|
||
const { handleGrandchildTrigger } = useContext(FamilyContext);
|
||
handleGrandchildTrigger(true); // 反直觉
|
||
|
||
// 现在
|
||
const { setShowGuideBar } = useGlobalState();
|
||
setShowGuideBar(false); // 直观明了
|
||
```
|
||
|
||
### 2. **逻辑更清晰**
|
||
- `setShowGuideBar(true)` → 显示 GuideBar
|
||
- `setShowGuideBar(false)` → 隐藏 GuideBar
|
||
- 不需要记忆反转逻辑
|
||
|
||
### 3. **调试更方便**
|
||
所有状态变化都有日志:
|
||
```
|
||
[UserInfo] 打开编辑弹窗,隐藏 GuideBar
|
||
[Store] setShowGuideBar called with: false
|
||
[Store] showGuideBar updated to: false
|
||
```
|
||
|
||
### 4. **类型安全**
|
||
```typescript
|
||
// 完整的 TypeScript 类型定义
|
||
interface GlobalActions {
|
||
setShowGuideBar: (show: boolean) => void; // ✅ 明确的参数类型
|
||
toggleGuideBar: () => void;
|
||
}
|
||
```
|
||
|
||
### 5. **易于扩展**
|
||
需要新功能时,只需在 store 中添加:
|
||
```typescript
|
||
// 未来可以轻松添加更多控制方法
|
||
interface GlobalActions {
|
||
setShowGuideBar: (show: boolean) => void;
|
||
setGuideBarZIndex: (zIndex: 'low' | 'high') => void;
|
||
toggleGuideBar: () => void;
|
||
hideGuideBarTemporarily: (duration: number) => void; // 新功能
|
||
}
|
||
```
|
||
|
||
---
|
||
|
||
## 📝 使用指南
|
||
|
||
### 在任何组件中使用
|
||
|
||
```typescript
|
||
import { useGlobalState } from "@/store/global";
|
||
|
||
function YourComponent() {
|
||
const { showGuideBar, setShowGuideBar, toggleGuideBar } = useGlobalState();
|
||
|
||
// 隐藏 GuideBar
|
||
const hideGuideBar = () => setShowGuideBar(false);
|
||
|
||
// 显示 GuideBar
|
||
const showGuideBar = () => setShowGuideBar(true);
|
||
|
||
// 切换显示/隐藏
|
||
const toggle = () => toggleGuideBar();
|
||
|
||
return <View>...</View>;
|
||
}
|
||
```
|
||
|
||
### 自动控制(推荐)
|
||
|
||
使用 `useEffect` 监听状态变化:
|
||
```typescript
|
||
useEffect(() => {
|
||
if (modalVisible) {
|
||
setShowGuideBar(false);
|
||
} else {
|
||
setShowGuideBar(true);
|
||
}
|
||
}, [modalVisible, setShowGuideBar]);
|
||
```
|
||
|
||
---
|
||
|
||
## ✅ 测试清单
|
||
|
||
### 定位弹窗测试
|
||
- [ ] 首次打开应用时,定位弹窗显示,GuideBar 隐藏
|
||
- [ ] 点击"切换到XX",弹窗关闭,GuideBar 显示
|
||
- [ ] 点击"继续浏览XX",弹窗关闭,GuideBar 显示
|
||
|
||
### 用户信息编辑测试
|
||
- [ ] 点击"编辑"按钮,编辑弹窗显示,GuideBar 隐藏
|
||
- [ ] 打开性别选择器,GuideBar 保持隐藏
|
||
- [ ] 关闭性别选择器,GuideBar 显示
|
||
- [ ] 打开地区选择器,GuideBar 隐藏
|
||
- [ ] 关闭地区选择器,GuideBar 显示
|
||
- [ ] 打开 NTRP 选择器,GuideBar 隐藏
|
||
- [ ] 关闭 NTRP 选择器,GuideBar 显示
|
||
- [ ] 点击"取消",编辑弹窗关闭,GuideBar 显示
|
||
|
||
### 多选择器联动测试
|
||
- [ ] 同时打开多个选择器时,GuideBar 保持隐藏
|
||
- [ ] 只有所有选择器都关闭时,GuideBar 才显示
|
||
|
||
---
|
||
|
||
## 🔍 调试方法
|
||
|
||
### 查看控制台日志
|
||
```
|
||
[UserInfo] 打开编辑弹窗,隐藏 GuideBar
|
||
[Store] setShowGuideBar called with: false
|
||
[Store] showGuideBar updated to: false
|
||
|
||
[UserInfo] 关闭编辑弹窗,显示 GuideBar
|
||
[Store] setShowGuideBar called with: true
|
||
[Store] showGuideBar updated to: true
|
||
```
|
||
|
||
### React DevTools
|
||
1. 打开 React DevTools
|
||
2. 找到 `MainPage` 组件
|
||
3. 查看 `showGuideBar` 的实时值
|
||
4. 观察状态变化是否符合预期
|
||
|
||
---
|
||
|
||
## 🎉 总结
|
||
|
||
✅ **LocationConfirmDialog** - 使用 store 统一控制
|
||
✅ **HomeNavbar** - 使用 store 统一控制
|
||
✅ **UserInfo** - 已从 FamilyContext 迁移到 store
|
||
✅ **MainPage** - 使用 store 统一渲染
|
||
|
||
所有组件现在都通过 **`useGlobalState`** 统一管理 GuideBar,代码更简洁、逻辑更清晰、维护更容易!🚀
|
||
|