profile.tsx 5.5 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138
  1. import { ActivityIndicator, Modal, Toast } from '@ant-design/react-native';
  2. import { Ionicons } from '@expo/vector-icons';
  3. import { Image } from 'expo-image';
  4. import { Pressable, ScrollView, Text, View } from 'react-native';
  5. import { SafeAreaView } from 'react-native-safe-area-context';
  6. import { MenuRow } from '@/components/ui/menu-row';
  7. import api from '@/utils/api';
  8. import { signOut, useAuthContext } from '@/utils/auth';
  9. import { useSWC } from '@/utils/cache';
  10. export default function ProfileScreen() {
  11. const { setToken } = useAuthContext();
  12. const handleLogout = () => {
  13. Modal.alert('退出登录', '确定要退出当前账号吗?', [
  14. { text: '取消', style: 'cancel' },
  15. {
  16. text: '退出',
  17. style: 'destructive',
  18. onPress: async () => {
  19. const l = Toast.loading("请稍候");
  20. try {
  21. await signOut();
  22. } catch(e) {
  23. console.warn(e);
  24. }
  25. setToken(null);
  26. Toast.remove(l);
  27. },
  28. },
  29. ]);
  30. };
  31. const {data: userInfo, loading}: any = useSWC("me", async ()=> {
  32. return await api.post('user/profile')
  33. }, {
  34. cacheOnly: true,
  35. cacheTimeout: 15*60
  36. });
  37. if (loading) {
  38. return <ActivityIndicator />;
  39. }
  40. return (
  41. <SafeAreaView className="flex-1 bg-surface" edges={['top']}>
  42. <View className="h-14 flex-row items-center justify-between border-b border-outline-variant/20 bg-surface-container-lowest px-5">
  43. <View className="flex-row items-center gap-3">
  44. <View className="h-9 w-9 items-center justify-center rounded-full bg-slate-900">
  45. <Ionicons name="person" size={18} color="#ffffff" />
  46. </View>
  47. <Text className="text-xl font-extrabold tracking-tight text-on-surface">
  48. 贷款助手
  49. </Text>
  50. </View>
  51. <Pressable hitSlop={8}>
  52. <Ionicons name="notifications-outline" size={20} color="#94a3b8" />
  53. </Pressable>
  54. </View>
  55. <ScrollView
  56. className="flex-1"
  57. contentContainerClassName="px-5 pt-4 pb-24"
  58. showsVerticalScrollIndicator={false}
  59. >
  60. <View className="mb-8 items-center">
  61. <View className="relative mb-4">
  62. <View className="h-28 w-28 rounded-full bg-primary-container p-1.5">
  63. <View className="h-full w-full items-center justify-center rounded-full border-4 border-surface-container-lowest bg-slate-900">
  64. {userInfo?.avatar&&<Image source={{uri: userInfo.avatar}} />}
  65. </View>
  66. </View>
  67. <View className="absolute bottom-1 right-1 h-8 w-8 items-center justify-center rounded-full border-4 border-surface-container-lowest bg-primary">
  68. <Ionicons name="checkmark" size={15} color="#ffffff" />
  69. </View>
  70. </View>
  71. <Text className="mb-2 text-3xl font-extrabold tracking-tight text-on-surface">
  72. {userInfo?.nickname}
  73. </Text>
  74. <Text className="text-base font-medium text-on-surface-variant">
  75. 高级信贷经理 · 智融金融
  76. </Text>
  77. </View>
  78. <View className="mb-8 flex-row gap-3">
  79. <View className="flex-1 items-center rounded-2xl border border-outline-variant bg-surface-container-lowest px-4 py-5">
  80. <Text className="text-3xl font-extrabold text-primary">128</Text>
  81. <Text className="mt-2 text-sm font-bold text-outline">已完成</Text>
  82. </View>
  83. <View className="flex-1 items-center rounded-2xl border border-outline-variant bg-surface-container-lowest px-4 py-5">
  84. <Text className="text-3xl font-extrabold text-primary">94%</Text>
  85. <Text className="mt-2 text-sm font-bold text-outline">成功率</Text>
  86. </View>
  87. <View className="flex-1 items-center rounded-2xl border border-outline-variant bg-surface-container-lowest px-4 py-5">
  88. <Text className="text-3xl font-extrabold text-primary">¥42k</Text>
  89. <Text className="mt-2 text-sm font-bold text-outline">本月收入</Text>
  90. </View>
  91. </View>
  92. <View className="mb-5 overflow-hidden rounded-2xl border border-outline-variant bg-surface-container-lowest">
  93. <MenuRow icon="people-outline" label="我的客户" iconBgClass="bg-blue-50" />
  94. <MenuRow
  95. icon="business-outline"
  96. label="机构设置"
  97. iconBgClass="bg-indigo-50"
  98. iconColorClass="#4f46e5"
  99. />
  100. </View>
  101. <View className="mb-5 overflow-hidden rounded-2xl border border-outline-variant bg-surface-container-lowest">
  102. <MenuRow
  103. icon="shield-outline"
  104. label="安全设置"
  105. iconBgClass="bg-orange-50"
  106. iconColorClass="#ea580c"
  107. />
  108. <MenuRow
  109. icon="help-circle-outline"
  110. label="帮助与支持"
  111. iconBgClass="bg-green-50"
  112. iconColorClass="#16a34a"
  113. />
  114. <MenuRow
  115. icon="information-circle-outline"
  116. label="关于我们"
  117. iconBgClass="bg-slate-100"
  118. iconColorClass="#475569"
  119. />
  120. </View>
  121. <Pressable
  122. onPress={handleLogout}
  123. className="mt-2 flex-row items-center justify-center gap-2 rounded-2xl bg-surface-container-low py-3.5 active:opacity-88"
  124. >
  125. <Ionicons name="log-out-outline" size={18} color={Colors.error.DEFAULT} />
  126. <Text className="text-base font-bold text-error">退出登录</Text>
  127. </Pressable>
  128. </ScrollView>
  129. </SafeAreaView>
  130. );
  131. }