refactor(robotaxi/home): 优化登录态命名和快捷胶囊逻辑
- 修复原登录态命名逻辑反向的问题,将setIsLogin重命名为setNeedLogin,让状态语义更准确
- 将useLocationFlow中的isLogin参数重命名为isLoggedIn,提升代码可读性
- 在首页新增派生状态isGuest和shouldShowLoginEntry,简化逻辑判断
- 重构useQuickCapsule,将原本的站点数组状态改为单个站点状态(此前仅使用数组第一项)
- 更新所有钩子和首页的相关调用逻辑,适配新的API和状态结构
| | |
| | | setTripStatus: (value: HomeTripStatus) => void; |
| | | /** 认证校验 */ |
| | | checkOtp: (silent?: boolean) => Promise<any>; |
| | | /** 设置登录态 */ |
| | | setIsLogin: (value: boolean) => void; |
| | | /** 设置是否需要登录 */ |
| | | setNeedLogin: (value: boolean) => void; |
| | | /** 协议查询 */ |
| | | getAgreement: () => Promise<any>; |
| | | /** 设置隐私弹窗 */ |
| | |
| | | */ |
| | | const syncAuthAndOrder = async () => { |
| | | const otp = await deps.checkOtp(false); |
| | | deps.setIsLogin(!otp); |
| | | deps.setNeedLogin(!otp); |
| | | if (!otp) return false; |
| | | wsManager.connect(deps.wsHost); |
| | | const agreement = await deps.getAgreement(); |
| | |
| | | mapState: any; |
| | | siteState: any; |
| | | cityState: any; |
| | | isLogin: boolean; |
| | | isLoggedIn: boolean; |
| | | onLocationSettled: (lat: number, lng: number, isInside: boolean) => void; |
| | | }; |
| | | |
| | | /** |
| | | * 定位流程编排:不持有状态,仅组合 map/site/city 状态 hook 完成定位主链路。 |
| | | */ |
| | | export default function useLocationFlow({ mapState, siteState, cityState, isLogin, onLocationSettled }: Deps) { |
| | | export default function useLocationFlow({ mapState, siteState, cityState, isLoggedIn, onLocationSettled }: Deps) { |
| | | const updateByStartSite = async () => { |
| | | const startSite = Taro.getStorageSync('startSite'); |
| | | if (!(startSite && startSite.latitude && startSite.longitude)) return false; |
| | |
| | | } catch (error) { |
| | | } |
| | | const cachedCity = Taro.getStorageSync('selectedCity'); |
| | | if (isLogin && cachedCity?.code && addressData?.regeocodeData?.addressComponent) { |
| | | if (isLoggedIn && cachedCity?.code && addressData?.regeocodeData?.addressComponent) { |
| | | const { city, province, adcode } = addressData.regeocodeData.addressComponent; |
| | | const cityName = city && typeof city === 'string' && city.length > 0 ? city : province; |
| | | const currentCityCode = convertAdcodeToCityCode(adcode, cityName, province); |
| | |
| | | * 首页快捷胶囊编排:负责登录态校验、数据请求、点击跳转。 |
| | | */ |
| | | export default function useQuickCapsule(deps: Deps) { |
| | | const [capsuleSites, setCapsuleSites] = useState<CapsuleSite[]>([]); // 快捷胶囊站点列表 |
| | | const [capsuleSite, setCapsuleSite] = useState<CapsuleSite | null>(null); // 快捷胶囊站点 |
| | | const requestSeqRef = useRef(0); // 快捷胶囊请求序号,避免旧请求覆盖 |
| | | |
| | | /** |
| | |
| | | * 清空快捷胶囊数据。 |
| | | */ |
| | | const clearQuickCapsule = () => { |
| | | setCapsuleSites([]); |
| | | setCapsuleSite(null); |
| | | }; |
| | | |
| | | /** |
| | |
| | | if (nextSeq !== requestSeqRef.current) { |
| | | return; |
| | | } |
| | | const rawList = Array.isArray(res?.points) ? res.points : Array.isArray(res) ? res : []; |
| | | const normalizedList = rawList |
| | | .map(normalizeCapsuleSite) |
| | | .filter((item: CapsuleSite | null): item is CapsuleSite => !!item); |
| | | setCapsuleSites(normalizedList); |
| | | const normalizedSite = normalizeCapsuleSite(res); |
| | | setCapsuleSite(normalizedSite); |
| | | } catch (error) { |
| | | if (nextSeq !== requestSeqRef.current) { |
| | | return; |
| | |
| | | Taro.showToast({ title: '请先选择起点站点', icon: 'none' }); |
| | | return; |
| | | } |
| | | if (capsuleSites.length === 0) { |
| | | if (!capsuleSite) { |
| | | Taro.showToast({ title: '暂无快捷目的地', icon: 'none' }); |
| | | return; |
| | | } |
| | | const targetSite = capsuleSites[0]; |
| | | Taro.setStorageSync('endSite', targetSite); |
| | | Taro.setStorageSync('endSite', capsuleSite); |
| | | Taro.setStorageSync('startSite', targetStartSite); |
| | | await Taro.reLaunch({ url: '/robotaxi/pages/begin-route/index' }); |
| | | }; |
| | |
| | | * 胶囊展示文案。 |
| | | */ |
| | | const quickCapsuleText = useMemo(() => { |
| | | if (capsuleSites.length === 0) return ''; |
| | | return `去:${capsuleSites[0].name}`; |
| | | }, [capsuleSites]); |
| | | if (!capsuleSite?.name) return ''; |
| | | return `去:${capsuleSite.name}`; |
| | | }, [capsuleSite]); |
| | | |
| | | // 游客态清空,非游客态拉取 |
| | | useEffect(() => { |
| | |
| | | }, [deps.isGuest, effectiveStartPointId]); |
| | | |
| | | return { |
| | | capsuleSites, |
| | | capsuleSite, |
| | | quickCapsuleText, |
| | | showQuickCapsule: !!quickCapsuleText, |
| | | showQuickCapsule: !!capsuleSite, |
| | | refreshQuickCapsule, |
| | | handleQuickCapsuleClick |
| | | }; |
| | |
| | | const [bannerList, setBannerList] = useState<any[]>([]); // 轮播图列表 |
| | | const [weatherData, setWeatherData] = useState<any>(null); // 天气数据 |
| | | const [orderData, setOrderData] = useState<any>({}); // 订单数据 |
| | | const [isLogin, setIsLogin] = useState(false); // 是否登录 |
| | | const [needLogin, setNeedLogin] = useState(false); // 是否需要登录 |
| | | const [overlayAnchorBottom, setOverlayAnchorBottom] = useState<number | null>(null); // 浮层初始化锚点(距底部) |
| | | const [temperatureUnit, setTemperatureUnit] = useState(DEFAULT_TEMPERATURE_UNIT); // 后台配置的温度单位 |
| | | const [operatingGeofenceList, setOperatingGeofenceList] = useState<any[]>([]); // 运营区围栏原始数据 |
| | |
| | | |
| | | const displayTemperatureUnit = useMemo(() => normalizeTemperatureUnit(temperatureUnit), [temperatureUnit]); // 页面展示温度单位 |
| | | const displayTemperature = useMemo(() => convertTemperatureByUnit(weatherData?.temperature, displayTemperatureUnit), [weatherData?.temperature, displayTemperatureUnit]); // 页面展示温度值 |
| | | const isLoggedIn = !needLogin; // 当前是否已登录 |
| | | const isGuest = needLogin; // 当前是否游客态 |
| | | const shouldShowLoginEntry = needLogin; // 是否展示登录入口 |
| | | |
| | | /** |
| | | * 按当前命中的场站围栏刷新地图覆盖物,运营区始终常驻展示。 |
| | |
| | | mapState, |
| | | siteState, |
| | | cityState, |
| | | isLogin, |
| | | isLoggedIn, |
| | | onLocationSettled: syncStationFenceVisibility |
| | | }); // 定位流程编排 |
| | | |
| | |
| | | setIsAdsorbed, |
| | | setTripStatus, |
| | | checkOtp, |
| | | setIsLogin, |
| | | setNeedLogin, |
| | | getAgreement, |
| | | setShowPrivacy, |
| | | getOrderActive, |
| | |
| | | refreshQuickCapsule, |
| | | handleQuickCapsuleClick |
| | | } = useQuickCapsule({ |
| | | isGuest: isLogin, |
| | | isGuest, |
| | | checkOtp, |
| | | currentSite |
| | | }); // 快捷胶囊编排 |
| | |
| | | handleBannerClick, |
| | | toPersonalCenter |
| | | } = useNavigation({ |
| | | isGuest: isLogin, |
| | | isGuest, |
| | | showPrivacy, |
| | | setShowPrivacy, |
| | | isLocationAuthDenied, |
| | |
| | | <Image onClick={toOrigin} className="origin-icon" src={originIcon} /> |
| | | </View> |
| | | <MapOverlayTips |
| | | isGuest={Taro.getStorageSync('has_show_privicy_Robotaxi') != 'true' && !isLogin} |
| | | isGuest={Taro.getStorageSync('has_show_privicy_Robotaxi') != 'true' && isGuest} |
| | | isLocationAuthDenied={isLocationAuthDenied} |
| | | isOperatingArea={isOperatingArea} |
| | | isMaintain={isMaintain} |
| | |
| | | } |
| | | {/* 是否展示登录入口 */} |
| | | { |
| | | isLogin && |
| | | <View className={`login-bar ${isLogin ? '' : 'hide'}`}> |
| | | shouldShowLoginEntry && |
| | | <View className='login-bar'> |
| | | <View className='text'>立即登录,即可体验Robotaxi行程服务</View> |
| | | <View className='more' |
| | | onClick={toLogin} |