@oxyhq/services 5.11.11 → 5.12.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (327) hide show
  1. package/README.md +48 -7
  2. package/lib/commonjs/core/OxyServices.js +162 -12
  3. package/lib/commonjs/core/OxyServices.js.map +1 -1
  4. package/lib/commonjs/i18n/index.js +40 -0
  5. package/lib/commonjs/i18n/index.js.map +1 -0
  6. package/lib/commonjs/i18n/locales/en-US.json +681 -0
  7. package/lib/commonjs/i18n/locales/es-ES.json +689 -0
  8. package/lib/commonjs/ui/components/FollowButton.js +1 -1
  9. package/lib/commonjs/ui/components/FollowButton.js.map +1 -1
  10. package/lib/commonjs/ui/components/GroupedItem.js +2 -1
  11. package/lib/commonjs/ui/components/GroupedItem.js.map +1 -1
  12. package/lib/commonjs/ui/components/Header.js +4 -3
  13. package/lib/commonjs/ui/components/Header.js.map +1 -1
  14. package/lib/commonjs/ui/components/OxyProvider.js +112 -105
  15. package/lib/commonjs/ui/components/OxyProvider.js.map +1 -1
  16. package/lib/commonjs/ui/components/ProfileCard.js +5 -1
  17. package/lib/commonjs/ui/components/ProfileCard.js.map +1 -1
  18. package/lib/commonjs/ui/components/Section.js +1 -1
  19. package/lib/commonjs/ui/components/StepBasedScreen.js +17 -17
  20. package/lib/commonjs/ui/components/StepBasedScreen.js.map +1 -1
  21. package/lib/commonjs/ui/components/internal/GroupedPillButtons.js +15 -3
  22. package/lib/commonjs/ui/components/internal/GroupedPillButtons.js.map +1 -1
  23. package/lib/commonjs/ui/components/internal/PinInput.js +10 -4
  24. package/lib/commonjs/ui/components/internal/PinInput.js.map +1 -1
  25. package/lib/commonjs/ui/context/OxyContext.js +128 -12
  26. package/lib/commonjs/ui/context/OxyContext.js.map +1 -1
  27. package/lib/commonjs/ui/hooks/useI18n.js +22 -0
  28. package/lib/commonjs/ui/hooks/useI18n.js.map +1 -0
  29. package/lib/commonjs/ui/navigation/OxyRouter.js +11 -131
  30. package/lib/commonjs/ui/navigation/OxyRouter.js.map +1 -1
  31. package/lib/commonjs/ui/navigation/routes.js +127 -0
  32. package/lib/commonjs/ui/navigation/routes.js.map +1 -0
  33. package/lib/commonjs/ui/navigation/types.js +7 -0
  34. package/lib/commonjs/ui/navigation/types.js.map +1 -1
  35. package/lib/commonjs/ui/screens/AccountCenterScreen.js +55 -47
  36. package/lib/commonjs/ui/screens/AccountCenterScreen.js.map +1 -1
  37. package/lib/commonjs/ui/screens/AccountOverviewScreen.js +69 -61
  38. package/lib/commonjs/ui/screens/AccountOverviewScreen.js.map +1 -1
  39. package/lib/commonjs/ui/screens/AccountSettingsScreen.js +378 -37
  40. package/lib/commonjs/ui/screens/AccountSettingsScreen.js.map +1 -1
  41. package/lib/commonjs/ui/screens/AccountSwitcherScreen.js +52 -34
  42. package/lib/commonjs/ui/screens/AccountSwitcherScreen.js.map +1 -1
  43. package/lib/commonjs/ui/screens/FeedbackScreen.js +40 -36
  44. package/lib/commonjs/ui/screens/FeedbackScreen.js.map +1 -1
  45. package/lib/commonjs/ui/screens/LanguageSelectorScreen.js +105 -78
  46. package/lib/commonjs/ui/screens/LanguageSelectorScreen.js.map +1 -1
  47. package/lib/commonjs/ui/screens/PaymentGatewayScreen.js +2 -2
  48. package/lib/commonjs/ui/screens/PaymentGatewayScreen.js.map +1 -1
  49. package/lib/commonjs/ui/screens/PremiumSubscriptionScreen.js +92 -60
  50. package/lib/commonjs/ui/screens/PremiumSubscriptionScreen.js.map +1 -1
  51. package/lib/commonjs/ui/screens/ProfileScreen.js +21 -11
  52. package/lib/commonjs/ui/screens/ProfileScreen.js.map +1 -1
  53. package/lib/commonjs/ui/screens/RecoverAccountScreen.js +30 -8
  54. package/lib/commonjs/ui/screens/RecoverAccountScreen.js.map +1 -1
  55. package/lib/commonjs/ui/screens/SignInScreen.js +47 -26
  56. package/lib/commonjs/ui/screens/SignInScreen.js.map +1 -1
  57. package/lib/commonjs/ui/screens/WelcomeNewUserScreen.js +31 -24
  58. package/lib/commonjs/ui/screens/WelcomeNewUserScreen.js.map +1 -1
  59. package/lib/commonjs/ui/screens/internal/SignInPasswordStep.js +11 -7
  60. package/lib/commonjs/ui/screens/internal/SignInPasswordStep.js.map +1 -1
  61. package/lib/commonjs/ui/screens/internal/SignInUsernameStep.js +12 -6
  62. package/lib/commonjs/ui/screens/internal/SignInUsernameStep.js.map +1 -1
  63. package/lib/commonjs/ui/screens/karma/KarmaAboutScreen.js +11 -7
  64. package/lib/commonjs/ui/screens/karma/KarmaAboutScreen.js.map +1 -1
  65. package/lib/commonjs/ui/screens/karma/KarmaCenterScreen.js +15 -11
  66. package/lib/commonjs/ui/screens/karma/KarmaCenterScreen.js.map +1 -1
  67. package/lib/commonjs/ui/screens/karma/KarmaFAQScreen.js +19 -27
  68. package/lib/commonjs/ui/screens/karma/KarmaFAQScreen.js.map +1 -1
  69. package/lib/commonjs/ui/screens/karma/KarmaLeaderboardScreen.js +8 -4
  70. package/lib/commonjs/ui/screens/karma/KarmaLeaderboardScreen.js.map +1 -1
  71. package/lib/commonjs/ui/screens/karma/KarmaRewardsScreen.js +14 -10
  72. package/lib/commonjs/ui/screens/karma/KarmaRewardsScreen.js.map +1 -1
  73. package/lib/commonjs/ui/screens/karma/KarmaRulesScreen.js +7 -3
  74. package/lib/commonjs/ui/screens/karma/KarmaRulesScreen.js.map +1 -1
  75. package/lib/commonjs/ui/screens/steps/RecoverRequestStep.js +19 -14
  76. package/lib/commonjs/ui/screens/steps/RecoverRequestStep.js.map +1 -1
  77. package/lib/commonjs/ui/screens/steps/RecoverResetPasswordStep.js +130 -0
  78. package/lib/commonjs/ui/screens/steps/RecoverResetPasswordStep.js.map +1 -0
  79. package/lib/commonjs/ui/screens/steps/RecoverSuccessStep.js +13 -13
  80. package/lib/commonjs/ui/screens/steps/RecoverSuccessStep.js.map +1 -1
  81. package/lib/commonjs/ui/screens/steps/RecoverVerifyStep.js +14 -20
  82. package/lib/commonjs/ui/screens/steps/RecoverVerifyStep.js.map +1 -1
  83. package/lib/commonjs/ui/screens/steps/SignInPasswordStep.js +22 -8
  84. package/lib/commonjs/ui/screens/steps/SignInPasswordStep.js.map +1 -1
  85. package/lib/commonjs/ui/screens/steps/SignInTotpStep.js +161 -0
  86. package/lib/commonjs/ui/screens/steps/SignInTotpStep.js.map +1 -0
  87. package/lib/commonjs/ui/screens/steps/SignInUsernameStep.js +12 -6
  88. package/lib/commonjs/ui/screens/steps/SignInUsernameStep.js.map +1 -1
  89. package/lib/commonjs/ui/screens/steps/SignUpIdentityStep.js +10 -6
  90. package/lib/commonjs/ui/screens/steps/SignUpIdentityStep.js.map +1 -1
  91. package/lib/commonjs/ui/screens/steps/SignUpSecurityStep.js +10 -6
  92. package/lib/commonjs/ui/screens/steps/SignUpSecurityStep.js.map +1 -1
  93. package/lib/commonjs/ui/screens/steps/SignUpSummaryStep.js +34 -4
  94. package/lib/commonjs/ui/screens/steps/SignUpSummaryStep.js.map +1 -1
  95. package/lib/commonjs/ui/screens/steps/SignUpWelcomeStep.js +9 -10
  96. package/lib/commonjs/ui/screens/steps/SignUpWelcomeStep.js.map +1 -1
  97. package/lib/commonjs/ui/styles/authStyles.js +1 -2
  98. package/lib/commonjs/ui/styles/authStyles.js.map +1 -1
  99. package/lib/commonjs/utils/deviceManager.js +1 -1
  100. package/lib/commonjs/utils/deviceManager.js.map +1 -1
  101. package/lib/commonjs/utils/validationUtils.js +4 -2
  102. package/lib/commonjs/utils/validationUtils.js.map +1 -1
  103. package/lib/module/core/OxyServices.js +162 -12
  104. package/lib/module/core/OxyServices.js.map +1 -1
  105. package/lib/module/i18n/index.js +35 -0
  106. package/lib/module/i18n/index.js.map +1 -0
  107. package/lib/module/i18n/locales/en-US.json +681 -0
  108. package/lib/module/i18n/locales/es-ES.json +689 -0
  109. package/lib/module/ui/components/FollowButton.js +1 -1
  110. package/lib/module/ui/components/FollowButton.js.map +1 -1
  111. package/lib/module/ui/components/GroupedItem.js +2 -1
  112. package/lib/module/ui/components/GroupedItem.js.map +1 -1
  113. package/lib/module/ui/components/Header.js +4 -3
  114. package/lib/module/ui/components/Header.js.map +1 -1
  115. package/lib/module/ui/components/OxyProvider.js +111 -105
  116. package/lib/module/ui/components/OxyProvider.js.map +1 -1
  117. package/lib/module/ui/components/ProfileCard.js +5 -1
  118. package/lib/module/ui/components/ProfileCard.js.map +1 -1
  119. package/lib/module/ui/components/Section.js +1 -1
  120. package/lib/module/ui/components/StepBasedScreen.js +17 -17
  121. package/lib/module/ui/components/StepBasedScreen.js.map +1 -1
  122. package/lib/module/ui/components/internal/GroupedPillButtons.js +15 -3
  123. package/lib/module/ui/components/internal/GroupedPillButtons.js.map +1 -1
  124. package/lib/module/ui/components/internal/PinInput.js +9 -4
  125. package/lib/module/ui/components/internal/PinInput.js.map +1 -1
  126. package/lib/module/ui/context/OxyContext.js +128 -12
  127. package/lib/module/ui/context/OxyContext.js.map +1 -1
  128. package/lib/module/ui/hooks/useI18n.js +18 -0
  129. package/lib/module/ui/hooks/useI18n.js.map +1 -0
  130. package/lib/module/ui/navigation/OxyRouter.js +7 -124
  131. package/lib/module/ui/navigation/OxyRouter.js.map +1 -1
  132. package/lib/module/ui/navigation/routes.js +122 -0
  133. package/lib/module/ui/navigation/routes.js.map +1 -0
  134. package/lib/module/ui/navigation/types.js +19 -1
  135. package/lib/module/ui/navigation/types.js.map +1 -1
  136. package/lib/module/ui/screens/AccountCenterScreen.js +55 -47
  137. package/lib/module/ui/screens/AccountCenterScreen.js.map +1 -1
  138. package/lib/module/ui/screens/AccountOverviewScreen.js +69 -61
  139. package/lib/module/ui/screens/AccountOverviewScreen.js.map +1 -1
  140. package/lib/module/ui/screens/AccountSettingsScreen.js +378 -37
  141. package/lib/module/ui/screens/AccountSettingsScreen.js.map +1 -1
  142. package/lib/module/ui/screens/AccountSwitcherScreen.js +52 -34
  143. package/lib/module/ui/screens/AccountSwitcherScreen.js.map +1 -1
  144. package/lib/module/ui/screens/FeedbackScreen.js +40 -36
  145. package/lib/module/ui/screens/FeedbackScreen.js.map +1 -1
  146. package/lib/module/ui/screens/LanguageSelectorScreen.js +107 -80
  147. package/lib/module/ui/screens/LanguageSelectorScreen.js.map +1 -1
  148. package/lib/module/ui/screens/PaymentGatewayScreen.js +2 -2
  149. package/lib/module/ui/screens/PaymentGatewayScreen.js.map +1 -1
  150. package/lib/module/ui/screens/PremiumSubscriptionScreen.js +92 -60
  151. package/lib/module/ui/screens/PremiumSubscriptionScreen.js.map +1 -1
  152. package/lib/module/ui/screens/ProfileScreen.js +21 -11
  153. package/lib/module/ui/screens/ProfileScreen.js.map +1 -1
  154. package/lib/module/ui/screens/RecoverAccountScreen.js +30 -8
  155. package/lib/module/ui/screens/RecoverAccountScreen.js.map +1 -1
  156. package/lib/module/ui/screens/SignInScreen.js +47 -26
  157. package/lib/module/ui/screens/SignInScreen.js.map +1 -1
  158. package/lib/module/ui/screens/WelcomeNewUserScreen.js +31 -24
  159. package/lib/module/ui/screens/WelcomeNewUserScreen.js.map +1 -1
  160. package/lib/module/ui/screens/internal/SignInPasswordStep.js +11 -7
  161. package/lib/module/ui/screens/internal/SignInPasswordStep.js.map +1 -1
  162. package/lib/module/ui/screens/internal/SignInUsernameStep.js +12 -6
  163. package/lib/module/ui/screens/internal/SignInUsernameStep.js.map +1 -1
  164. package/lib/module/ui/screens/karma/KarmaAboutScreen.js +11 -7
  165. package/lib/module/ui/screens/karma/KarmaAboutScreen.js.map +1 -1
  166. package/lib/module/ui/screens/karma/KarmaCenterScreen.js +15 -11
  167. package/lib/module/ui/screens/karma/KarmaCenterScreen.js.map +1 -1
  168. package/lib/module/ui/screens/karma/KarmaFAQScreen.js +19 -27
  169. package/lib/module/ui/screens/karma/KarmaFAQScreen.js.map +1 -1
  170. package/lib/module/ui/screens/karma/KarmaLeaderboardScreen.js +8 -4
  171. package/lib/module/ui/screens/karma/KarmaLeaderboardScreen.js.map +1 -1
  172. package/lib/module/ui/screens/karma/KarmaRewardsScreen.js +14 -10
  173. package/lib/module/ui/screens/karma/KarmaRewardsScreen.js.map +1 -1
  174. package/lib/module/ui/screens/karma/KarmaRulesScreen.js +7 -3
  175. package/lib/module/ui/screens/karma/KarmaRulesScreen.js.map +1 -1
  176. package/lib/module/ui/screens/steps/RecoverRequestStep.js +19 -14
  177. package/lib/module/ui/screens/steps/RecoverRequestStep.js.map +1 -1
  178. package/lib/module/ui/screens/steps/RecoverResetPasswordStep.js +125 -0
  179. package/lib/module/ui/screens/steps/RecoverResetPasswordStep.js.map +1 -0
  180. package/lib/module/ui/screens/steps/RecoverSuccessStep.js +13 -13
  181. package/lib/module/ui/screens/steps/RecoverSuccessStep.js.map +1 -1
  182. package/lib/module/ui/screens/steps/RecoverVerifyStep.js +14 -20
  183. package/lib/module/ui/screens/steps/RecoverVerifyStep.js.map +1 -1
  184. package/lib/module/ui/screens/steps/SignInPasswordStep.js +22 -8
  185. package/lib/module/ui/screens/steps/SignInPasswordStep.js.map +1 -1
  186. package/lib/module/ui/screens/steps/SignInTotpStep.js +156 -0
  187. package/lib/module/ui/screens/steps/SignInTotpStep.js.map +1 -0
  188. package/lib/module/ui/screens/steps/SignInUsernameStep.js +12 -6
  189. package/lib/module/ui/screens/steps/SignInUsernameStep.js.map +1 -1
  190. package/lib/module/ui/screens/steps/SignUpIdentityStep.js +10 -6
  191. package/lib/module/ui/screens/steps/SignUpIdentityStep.js.map +1 -1
  192. package/lib/module/ui/screens/steps/SignUpSecurityStep.js +10 -6
  193. package/lib/module/ui/screens/steps/SignUpSecurityStep.js.map +1 -1
  194. package/lib/module/ui/screens/steps/SignUpSummaryStep.js +34 -4
  195. package/lib/module/ui/screens/steps/SignUpSummaryStep.js.map +1 -1
  196. package/lib/module/ui/screens/steps/SignUpWelcomeStep.js +9 -10
  197. package/lib/module/ui/screens/steps/SignUpWelcomeStep.js.map +1 -1
  198. package/lib/module/ui/styles/authStyles.js +1 -2
  199. package/lib/module/ui/styles/authStyles.js.map +1 -1
  200. package/lib/module/utils/deviceManager.js +1 -1
  201. package/lib/module/utils/deviceManager.js.map +1 -1
  202. package/lib/module/utils/validationUtils.js +4 -2
  203. package/lib/module/utils/validationUtils.js.map +1 -1
  204. package/lib/typescript/core/OxyServices.d.ts +57 -3
  205. package/lib/typescript/core/OxyServices.d.ts.map +1 -1
  206. package/lib/typescript/i18n/index.d.ts +4 -0
  207. package/lib/typescript/i18n/index.d.ts.map +1 -0
  208. package/lib/typescript/models/interfaces.d.ts +4 -0
  209. package/lib/typescript/models/interfaces.d.ts.map +1 -1
  210. package/lib/typescript/ui/components/GroupedItem.d.ts.map +1 -1
  211. package/lib/typescript/ui/components/Header.d.ts.map +1 -1
  212. package/lib/typescript/ui/components/OxyProvider.d.ts +1 -1
  213. package/lib/typescript/ui/components/OxyProvider.d.ts.map +1 -1
  214. package/lib/typescript/ui/components/ProfileCard.d.ts.map +1 -1
  215. package/lib/typescript/ui/components/StepBasedScreen.d.ts +2 -1
  216. package/lib/typescript/ui/components/StepBasedScreen.d.ts.map +1 -1
  217. package/lib/typescript/ui/components/internal/GroupedPillButtons.d.ts.map +1 -1
  218. package/lib/typescript/ui/components/internal/PinInput.d.ts +6 -3
  219. package/lib/typescript/ui/components/internal/PinInput.d.ts.map +1 -1
  220. package/lib/typescript/ui/context/OxyContext.d.ts +7 -4
  221. package/lib/typescript/ui/context/OxyContext.d.ts.map +1 -1
  222. package/lib/typescript/ui/hooks/useI18n.d.ts +5 -0
  223. package/lib/typescript/ui/hooks/useI18n.d.ts.map +1 -0
  224. package/lib/typescript/ui/navigation/OxyRouter.d.ts.map +1 -1
  225. package/lib/typescript/ui/navigation/routes.d.ts +9 -0
  226. package/lib/typescript/ui/navigation/routes.d.ts.map +1 -0
  227. package/lib/typescript/ui/navigation/types.d.ts +24 -10
  228. package/lib/typescript/ui/navigation/types.d.ts.map +1 -1
  229. package/lib/typescript/ui/screens/AccountCenterScreen.d.ts.map +1 -1
  230. package/lib/typescript/ui/screens/AccountOverviewScreen.d.ts.map +1 -1
  231. package/lib/typescript/ui/screens/AccountSettingsScreen.d.ts.map +1 -1
  232. package/lib/typescript/ui/screens/AccountSwitcherScreen.d.ts.map +1 -1
  233. package/lib/typescript/ui/screens/FeedbackScreen.d.ts.map +1 -1
  234. package/lib/typescript/ui/screens/LanguageSelectorScreen.d.ts.map +1 -1
  235. package/lib/typescript/ui/screens/PremiumSubscriptionScreen.d.ts.map +1 -1
  236. package/lib/typescript/ui/screens/ProfileScreen.d.ts.map +1 -1
  237. package/lib/typescript/ui/screens/RecoverAccountScreen.d.ts.map +1 -1
  238. package/lib/typescript/ui/screens/SignInScreen.d.ts.map +1 -1
  239. package/lib/typescript/ui/screens/WelcomeNewUserScreen.d.ts.map +1 -1
  240. package/lib/typescript/ui/screens/internal/SignInPasswordStep.d.ts +2 -1
  241. package/lib/typescript/ui/screens/internal/SignInPasswordStep.d.ts.map +1 -1
  242. package/lib/typescript/ui/screens/internal/SignInUsernameStep.d.ts.map +1 -1
  243. package/lib/typescript/ui/screens/karma/KarmaAboutScreen.d.ts.map +1 -1
  244. package/lib/typescript/ui/screens/karma/KarmaCenterScreen.d.ts.map +1 -1
  245. package/lib/typescript/ui/screens/karma/KarmaFAQScreen.d.ts.map +1 -1
  246. package/lib/typescript/ui/screens/karma/KarmaLeaderboardScreen.d.ts.map +1 -1
  247. package/lib/typescript/ui/screens/karma/KarmaRewardsScreen.d.ts.map +1 -1
  248. package/lib/typescript/ui/screens/karma/KarmaRulesScreen.d.ts.map +1 -1
  249. package/lib/typescript/ui/screens/steps/RecoverRequestStep.d.ts +4 -1
  250. package/lib/typescript/ui/screens/steps/RecoverRequestStep.d.ts.map +1 -1
  251. package/lib/typescript/ui/screens/steps/RecoverResetPasswordStep.d.ts +24 -0
  252. package/lib/typescript/ui/screens/steps/RecoverResetPasswordStep.d.ts.map +1 -0
  253. package/lib/typescript/ui/screens/steps/RecoverSuccessStep.d.ts +2 -1
  254. package/lib/typescript/ui/screens/steps/RecoverSuccessStep.d.ts.map +1 -1
  255. package/lib/typescript/ui/screens/steps/RecoverVerifyStep.d.ts +3 -1
  256. package/lib/typescript/ui/screens/steps/RecoverVerifyStep.d.ts.map +1 -1
  257. package/lib/typescript/ui/screens/steps/SignInPasswordStep.d.ts +1 -0
  258. package/lib/typescript/ui/screens/steps/SignInPasswordStep.d.ts.map +1 -1
  259. package/lib/typescript/ui/screens/steps/SignInTotpStep.d.ts +19 -0
  260. package/lib/typescript/ui/screens/steps/SignInTotpStep.d.ts.map +1 -0
  261. package/lib/typescript/ui/screens/steps/SignInUsernameStep.d.ts +2 -1
  262. package/lib/typescript/ui/screens/steps/SignInUsernameStep.d.ts.map +1 -1
  263. package/lib/typescript/ui/screens/steps/SignUpIdentityStep.d.ts +2 -1
  264. package/lib/typescript/ui/screens/steps/SignUpIdentityStep.d.ts.map +1 -1
  265. package/lib/typescript/ui/screens/steps/SignUpSecurityStep.d.ts +2 -1
  266. package/lib/typescript/ui/screens/steps/SignUpSecurityStep.d.ts.map +1 -1
  267. package/lib/typescript/ui/screens/steps/SignUpSummaryStep.d.ts +2 -1
  268. package/lib/typescript/ui/screens/steps/SignUpSummaryStep.d.ts.map +1 -1
  269. package/lib/typescript/ui/screens/steps/SignUpWelcomeStep.d.ts +2 -1
  270. package/lib/typescript/ui/screens/steps/SignUpWelcomeStep.d.ts.map +1 -1
  271. package/lib/typescript/ui/styles/authStyles.d.ts +0 -1
  272. package/lib/typescript/ui/styles/authStyles.d.ts.map +1 -1
  273. package/lib/typescript/utils/validationUtils.d.ts.map +1 -1
  274. package/package.json +49 -15
  275. package/src/core/OxyServices.ts +138 -19
  276. package/src/i18n/index.ts +39 -0
  277. package/src/i18n/locales/en-US.json +681 -0
  278. package/src/i18n/locales/es-ES.json +689 -0
  279. package/src/models/interfaces.ts +6 -1
  280. package/src/ui/components/FollowButton.tsx +2 -2
  281. package/src/ui/components/GroupedItem.tsx +2 -1
  282. package/src/ui/components/Header.tsx +4 -3
  283. package/src/ui/components/OxyProvider.tsx +107 -114
  284. package/src/ui/components/ProfileCard.tsx +5 -1
  285. package/src/ui/components/Section.tsx +1 -1
  286. package/src/ui/components/StepBasedScreen.tsx +17 -14
  287. package/src/ui/components/internal/GroupedPillButtons.tsx +10 -6
  288. package/src/ui/components/internal/PinInput.tsx +15 -6
  289. package/src/ui/context/OxyContext.tsx +123 -20
  290. package/src/ui/hooks/useI18n.ts +12 -0
  291. package/src/ui/navigation/OxyRouter.tsx +15 -134
  292. package/src/ui/navigation/routes.ts +153 -0
  293. package/src/ui/navigation/types.ts +28 -10
  294. package/src/ui/screens/AccountCenterScreen.tsx +47 -45
  295. package/src/ui/screens/AccountOverviewScreen.tsx +68 -70
  296. package/src/ui/screens/AccountSettingsScreen.tsx +265 -41
  297. package/src/ui/screens/AccountSwitcherScreen.tsx +35 -33
  298. package/src/ui/screens/FeedbackScreen.tsx +39 -37
  299. package/src/ui/screens/LanguageSelectorScreen.tsx +99 -70
  300. package/src/ui/screens/PaymentGatewayScreen.tsx +6 -6
  301. package/src/ui/screens/PremiumSubscriptionScreen.tsx +56 -54
  302. package/src/ui/screens/ProfileScreen.tsx +14 -8
  303. package/src/ui/screens/RecoverAccountScreen.tsx +29 -8
  304. package/src/ui/screens/SignInScreen.tsx +39 -30
  305. package/src/ui/screens/WelcomeNewUserScreen.tsx +31 -17
  306. package/src/ui/screens/internal/SignInPasswordStep.tsx +11 -8
  307. package/src/ui/screens/internal/SignInUsernameStep.tsx +10 -8
  308. package/src/ui/screens/karma/KarmaAboutScreen.tsx +23 -11
  309. package/src/ui/screens/karma/KarmaCenterScreen.tsx +21 -11
  310. package/src/ui/screens/karma/KarmaFAQScreen.tsx +15 -33
  311. package/src/ui/screens/karma/KarmaLeaderboardScreen.tsx +6 -4
  312. package/src/ui/screens/karma/KarmaRewardsScreen.tsx +28 -10
  313. package/src/ui/screens/karma/KarmaRulesScreen.tsx +5 -3
  314. package/src/ui/screens/steps/RecoverRequestStep.tsx +20 -17
  315. package/src/ui/screens/steps/RecoverResetPasswordStep.tsx +133 -0
  316. package/src/ui/screens/steps/RecoverSuccessStep.tsx +12 -19
  317. package/src/ui/screens/steps/RecoverVerifyStep.tsx +15 -24
  318. package/src/ui/screens/steps/SignInPasswordStep.tsx +19 -6
  319. package/src/ui/screens/steps/SignInTotpStep.tsx +129 -0
  320. package/src/ui/screens/steps/SignInUsernameStep.tsx +11 -10
  321. package/src/ui/screens/steps/SignUpIdentityStep.tsx +10 -11
  322. package/src/ui/screens/steps/SignUpSecurityStep.tsx +10 -11
  323. package/src/ui/screens/steps/SignUpSummaryStep.tsx +24 -9
  324. package/src/ui/screens/steps/SignUpWelcomeStep.tsx +8 -14
  325. package/src/ui/styles/authStyles.ts +0 -1
  326. package/src/utils/deviceManager.ts +1 -1
  327. package/src/utils/validationUtils.ts +5 -3
@@ -4,11 +4,14 @@ import React, { useState, useEffect, useRef, useMemo, useCallback } from 'react'
4
4
  import { View, Text, TouchableOpacity, StyleSheet, ActivityIndicator, ScrollView, TextInput, Animated, Platform, Image } from 'react-native';
5
5
  import { useOxy } from '../context/OxyContext';
6
6
  import OxyIcon from '../components/icon/OxyIcon';
7
+ import { Ionicons } from '@expo/vector-icons';
7
8
  import { toast } from '../../lib/sonner';
8
9
  import { fontFamilies } from '../styles/fonts';
9
10
  import { confirmAction } from '../utils/confirmAction';
10
11
  import { useAuthStore } from '../stores/authStore';
11
12
  import { Header, GroupedSection } from '../components';
13
+ import { useI18n } from '../hooks/useI18n';
14
+ import QRCode from 'react-native-qrcode-svg';
12
15
  import { jsx as _jsx, jsxs as _jsxs, Fragment as _Fragment } from "react/jsx-runtime";
13
16
  const AccountSettingsScreen = ({
14
17
  onClose,
@@ -21,12 +24,24 @@ const AccountSettingsScreen = ({
21
24
  oxyServices,
22
25
  isLoading: authLoading,
23
26
  isAuthenticated,
24
- showBottomSheet
27
+ showBottomSheet,
28
+ activeSessionId
25
29
  } = useOxy();
30
+ const {
31
+ t
32
+ } = useI18n();
26
33
  const updateUser = useAuthStore(state => state.updateUser);
27
34
  const [isLoading, setIsLoading] = useState(false);
28
35
  const [isSaving, setIsSaving] = useState(false);
29
36
 
37
+ // Two-Factor (TOTP) state
38
+ const [totpSetupUrl, setTotpSetupUrl] = useState(null);
39
+ const [totpCode, setTotpCode] = useState('');
40
+ const [isTotpBusy, setIsTotpBusy] = useState(false);
41
+ const [showRecoveryModal, setShowRecoveryModal] = useState(false);
42
+ const [generatedBackupCodes, setGeneratedBackupCodes] = useState(null);
43
+ const [generatedRecoveryKey, setGeneratedRecoveryKey] = useState(null);
44
+
30
45
  // Animation refs
31
46
  const saveButtonScale = useRef(new Animated.Value(1)).current;
32
47
 
@@ -182,7 +197,7 @@ const AccountSettingsScreen = ({
182
197
  updates.avatar = avatarFileId;
183
198
  }
184
199
  await updateUser(updates, oxyServices);
185
- toast.success('Profile updated successfully');
200
+ toast.success(t('editProfile.toasts.profileUpdated') || 'Profile updated successfully');
186
201
  animateSaveButton(1); // Scale back to normal
187
202
 
188
203
  if (onClose) {
@@ -191,16 +206,16 @@ const AccountSettingsScreen = ({
191
206
  goBack();
192
207
  }
193
208
  } catch (error) {
194
- toast.error(error.message || 'Failed to update profile');
209
+ toast.error(error.message || t('editProfile.toasts.updateFailed') || 'Failed to update profile');
195
210
  animateSaveButton(1); // Scale back to normal on error
196
211
  } finally {
197
212
  setIsSaving(false);
198
213
  }
199
214
  };
200
215
  const handleAvatarRemove = () => {
201
- confirmAction('Remove your profile picture?', () => {
216
+ confirmAction(t('editProfile.confirms.removeAvatar') || 'Remove your profile picture?', () => {
202
217
  setAvatarFileId('');
203
- toast.success('Avatar removed');
218
+ toast.success(t('editProfile.toasts.avatarRemoved') || 'Avatar removed');
204
219
  });
205
220
  };
206
221
  const openAvatarPicker = useCallback(() => {
@@ -212,16 +227,16 @@ const AccountSettingsScreen = ({
212
227
  afterSelect: 'back',
213
228
  onSelect: file => {
214
229
  if (!file.contentType.startsWith('image/')) {
215
- toast.error('Please select an image file');
230
+ toast.error(t('editProfile.toasts.selectImage') || 'Please select an image file');
216
231
  return;
217
232
  }
218
233
  // If already selected, do nothing
219
234
  if (file.id === avatarFileId) {
220
- toast.info?.('Avatar unchanged');
235
+ toast.info?.(t('editProfile.toasts.avatarUnchanged') || 'Avatar unchanged');
221
236
  return;
222
237
  }
223
238
  setAvatarFileId(file.id);
224
- toast.success('Avatar selected');
239
+ toast.success(t('editProfile.toasts.avatarSelected') || 'Avatar selected');
225
240
  // Auto-save avatar immediately (does not close edit profile screen)
226
241
  (async () => {
227
242
  try {
@@ -232,10 +247,10 @@ const AccountSettingsScreen = ({
232
247
  }, oxyServices);
233
248
  // Force refresh current user cache (updateUser already does a fetch with force=true internally)
234
249
  // Extra safeguard: ensure avatarFileId reflects saved id (already set) and trigger any dependent UI.
235
- toast.success('Avatar updated');
250
+ toast.success(t('editProfile.toasts.avatarUpdated') || 'Avatar updated');
236
251
  } catch (e) {
237
252
  console.error('[AccountSettings] Failed to auto-save avatar', e);
238
- toast.error(e.message || 'Failed to update avatar');
253
+ toast.error(e.message || t('editProfile.toasts.updateAvatarFailed') || 'Failed to update avatar');
239
254
  } finally {
240
255
  setIsSaving(false);
241
256
  }
@@ -268,6 +283,11 @@ const AccountSettingsScreen = ({
268
283
  // Don't reset the metadata - keep the existing rich metadata
269
284
  // The tempLinksWithMetadata should already contain the rich data from the database
270
285
  break;
286
+ case 'twoFactor':
287
+ // Reset TOTP temp state
288
+ setTotpSetupUrl(null);
289
+ setTotpCode('');
290
+ break;
271
291
  }
272
292
  setEditingField(type);
273
293
  };
@@ -399,6 +419,179 @@ const AccountSettingsScreen = ({
399
419
  });
400
420
  };
401
421
  const renderEditingField = type => {
422
+ if (type === 'twoFactor') {
423
+ const enabled = !!user?.privacySettings?.twoFactorEnabled;
424
+ return /*#__PURE__*/_jsx(View, {
425
+ style: [styles.editingFieldContainer, {
426
+ backgroundColor: themeStyles.backgroundColor
427
+ }],
428
+ children: /*#__PURE__*/_jsx(View, {
429
+ style: styles.editingFieldContent,
430
+ children: /*#__PURE__*/_jsxs(View, {
431
+ style: styles.newValueSection,
432
+ children: [/*#__PURE__*/_jsx(View, {
433
+ style: styles.editingFieldHeader,
434
+ children: /*#__PURE__*/_jsx(Text, {
435
+ style: [styles.editingFieldLabel, {
436
+ color: themeStyles.isDarkTheme ? '#FFFFFF' : '#1A1A1A'
437
+ }],
438
+ children: "Two\u2011Factor Authentication (TOTP)"
439
+ })
440
+ }), !enabled ? /*#__PURE__*/_jsxs(_Fragment, {
441
+ children: [/*#__PURE__*/_jsx(Text, {
442
+ style: styles.editingFieldDescription,
443
+ children: "Protect your account with a 6\u2011digit code from an authenticator app. Scan the QR code then enter the code to enable."
444
+ }), !totpSetupUrl ? /*#__PURE__*/_jsxs(TouchableOpacity, {
445
+ style: styles.primaryButton,
446
+ disabled: isTotpBusy,
447
+ onPress: async () => {
448
+ if (!activeSessionId) {
449
+ toast.error(t('editProfile.toasts.noActiveSession') || 'No active session');
450
+ return;
451
+ }
452
+ setIsTotpBusy(true);
453
+ try {
454
+ const {
455
+ otpauthUrl
456
+ } = await oxyServices.startTotpEnrollment(activeSessionId);
457
+ setTotpSetupUrl(otpauthUrl);
458
+ } catch (e) {
459
+ toast.error(e?.message || t('editProfile.toasts.totpStartFailed') || 'Failed to start TOTP enrollment');
460
+ } finally {
461
+ setIsTotpBusy(false);
462
+ }
463
+ },
464
+ children: [/*#__PURE__*/_jsx(Ionicons, {
465
+ name: "shield-checkmark",
466
+ size: 18,
467
+ color: "#fff"
468
+ }), /*#__PURE__*/_jsx(Text, {
469
+ style: styles.primaryButtonText,
470
+ children: "Generate QR Code"
471
+ })]
472
+ }) : /*#__PURE__*/_jsxs(View, {
473
+ style: {
474
+ alignItems: 'center',
475
+ gap: 16
476
+ },
477
+ children: [/*#__PURE__*/_jsx(View, {
478
+ style: {
479
+ padding: 16,
480
+ backgroundColor: '#fff',
481
+ borderRadius: 12
482
+ },
483
+ children: /*#__PURE__*/_jsx(QRCode, {
484
+ value: totpSetupUrl,
485
+ size: 180
486
+ })
487
+ }), /*#__PURE__*/_jsxs(View, {
488
+ children: [/*#__PURE__*/_jsx(Text, {
489
+ style: styles.editingFieldLabel,
490
+ children: "Enter 6\u2011digit code"
491
+ }), /*#__PURE__*/_jsx(TextInput, {
492
+ style: styles.editingFieldInput,
493
+ keyboardType: "number-pad",
494
+ placeholder: "123456",
495
+ value: totpCode,
496
+ onChangeText: setTotpCode,
497
+ maxLength: 6
498
+ })]
499
+ }), /*#__PURE__*/_jsxs(TouchableOpacity, {
500
+ style: styles.primaryButton,
501
+ disabled: isTotpBusy || totpCode.length !== 6,
502
+ onPress: async () => {
503
+ if (!activeSessionId) {
504
+ toast.error(t('editProfile.toasts.noActiveSession') || 'No active session');
505
+ return;
506
+ }
507
+ setIsTotpBusy(true);
508
+ try {
509
+ const result = await oxyServices.verifyTotpEnrollment(activeSessionId, totpCode);
510
+ await updateUser({
511
+ privacySettings: {
512
+ twoFactorEnabled: true
513
+ }
514
+ }, oxyServices);
515
+ if (result?.backupCodes || result?.recoveryKey) {
516
+ setGeneratedBackupCodes(result.backupCodes || null);
517
+ setGeneratedRecoveryKey(result.recoveryKey || null);
518
+ setShowRecoveryModal(true);
519
+ } else {
520
+ toast.success(t('editProfile.toasts.twoFactorEnabled') || 'Two‑Factor Authentication enabled');
521
+ setEditingField(null);
522
+ }
523
+ } catch (e) {
524
+ toast.error(e?.message || t('editProfile.toasts.invalidCode') || 'Invalid code');
525
+ } finally {
526
+ setIsTotpBusy(false);
527
+ }
528
+ },
529
+ children: [/*#__PURE__*/_jsx(Ionicons, {
530
+ name: "checkmark-circle",
531
+ size: 18,
532
+ color: "#fff"
533
+ }), /*#__PURE__*/_jsx(Text, {
534
+ style: styles.primaryButtonText,
535
+ children: "Verify & Enable"
536
+ })]
537
+ })]
538
+ })]
539
+ }) : /*#__PURE__*/_jsxs(_Fragment, {
540
+ children: [/*#__PURE__*/_jsx(Text, {
541
+ style: styles.editingFieldDescription,
542
+ children: "Two\u2011Factor Authentication is currently enabled. To disable, enter a code from your authenticator app."
543
+ }), /*#__PURE__*/_jsxs(View, {
544
+ children: [/*#__PURE__*/_jsx(Text, {
545
+ style: styles.editingFieldLabel,
546
+ children: "Enter 6\u2011digit code"
547
+ }), /*#__PURE__*/_jsx(TextInput, {
548
+ style: styles.editingFieldInput,
549
+ keyboardType: "number-pad",
550
+ placeholder: "123456",
551
+ value: totpCode,
552
+ onChangeText: setTotpCode,
553
+ maxLength: 6
554
+ })]
555
+ }), /*#__PURE__*/_jsxs(TouchableOpacity, {
556
+ style: [styles.primaryButton, {
557
+ backgroundColor: '#d9534f'
558
+ }],
559
+ disabled: isTotpBusy || totpCode.length !== 6,
560
+ onPress: async () => {
561
+ if (!activeSessionId) {
562
+ toast.error(t('editProfile.toasts.noActiveSession') || 'No active session');
563
+ return;
564
+ }
565
+ setIsTotpBusy(true);
566
+ try {
567
+ await oxyServices.disableTotp(activeSessionId, totpCode);
568
+ await updateUser({
569
+ privacySettings: {
570
+ twoFactorEnabled: false
571
+ }
572
+ }, oxyServices);
573
+ toast.success(t('editProfile.toasts.twoFactorDisabled') || 'Two‑Factor Authentication disabled');
574
+ setEditingField(null);
575
+ } catch (e) {
576
+ toast.error(e?.message || t('editProfile.toasts.disableFailed') || 'Failed to disable');
577
+ } finally {
578
+ setIsTotpBusy(false);
579
+ }
580
+ },
581
+ children: [/*#__PURE__*/_jsx(Ionicons, {
582
+ name: "close-circle",
583
+ size: 18,
584
+ color: "#fff"
585
+ }), /*#__PURE__*/_jsx(Text, {
586
+ style: styles.primaryButtonText,
587
+ children: "Disable 2FA"
588
+ })]
589
+ })]
590
+ })]
591
+ })
592
+ })
593
+ });
594
+ }
402
595
  if (type === 'displayName') {
403
596
  return /*#__PURE__*/_jsx(View, {
404
597
  style: [styles.editingFieldContainer, {
@@ -940,11 +1133,11 @@ const AccountSettingsScreen = ({
940
1133
  style: [styles.editingBottomTitle, {
941
1134
  color: themeStyles.isDarkTheme ? '#FFFFFF' : '#1A1A1A'
942
1135
  }],
943
- children: editingField === 'displayName' ? 'Display Name' : editingField === 'username' ? 'Username' : editingField === 'email' ? 'Email' : editingField === 'bio' ? 'Bio' : editingField === 'location' ? 'Location' : editingField === 'links' ? 'Links' : 'Field'
1136
+ children: editingField === 'displayName' ? t('editProfile.items.displayName.title') || 'Display Name' : editingField === 'username' ? t('editProfile.items.username.title') || 'Username' : editingField === 'email' ? t('editProfile.items.email.title') || 'Email' : editingField === 'bio' ? t('editProfile.items.bio.title') || 'Bio' : editingField === 'location' ? t('editProfile.items.locations.title') || 'Location' : editingField === 'links' ? t('editProfile.items.links.title') || 'Links' : 'Field'
944
1137
  })]
945
1138
  })]
946
1139
  }) : /*#__PURE__*/_jsx(Header, {
947
- title: "Edit Profile",
1140
+ title: t('editProfile.title') || 'Edit Profile',
948
1141
  theme: theme,
949
1142
  onBack: goBack || onClose,
950
1143
  rightAction: {
@@ -966,11 +1159,115 @@ const AccountSettingsScreen = ({
966
1159
  /*#__PURE__*/
967
1160
  // Show all settings when not editing
968
1161
  _jsxs(_Fragment, {
969
- children: [/*#__PURE__*/_jsxs(View, {
1162
+ children: [showRecoveryModal && /*#__PURE__*/_jsx(View, {
1163
+ style: {
1164
+ position: 'absolute',
1165
+ top: 0,
1166
+ left: 0,
1167
+ right: 0,
1168
+ bottom: 0,
1169
+ backgroundColor: 'rgba(0,0,0,0.6)',
1170
+ zIndex: 50,
1171
+ padding: 16,
1172
+ justifyContent: 'center'
1173
+ },
1174
+ children: /*#__PURE__*/_jsxs(View, {
1175
+ style: {
1176
+ backgroundColor: '#fff',
1177
+ borderRadius: 16,
1178
+ padding: 20,
1179
+ maxHeight: '80%'
1180
+ },
1181
+ children: [/*#__PURE__*/_jsx(Text, {
1182
+ style: {
1183
+ fontSize: 18,
1184
+ fontWeight: '700',
1185
+ marginBottom: 12
1186
+ },
1187
+ children: "Save These Codes Now"
1188
+ }), /*#__PURE__*/_jsx(Text, {
1189
+ style: {
1190
+ fontSize: 14,
1191
+ color: '#444',
1192
+ marginBottom: 12
1193
+ },
1194
+ children: "Backup codes and your Recovery Key are shown only once. Store them securely (paper or password manager)."
1195
+ }), generatedBackupCodes && generatedBackupCodes.length > 0 && /*#__PURE__*/_jsxs(View, {
1196
+ style: {
1197
+ marginBottom: 12
1198
+ },
1199
+ children: [/*#__PURE__*/_jsx(Text, {
1200
+ style: {
1201
+ fontSize: 16,
1202
+ fontWeight: '600',
1203
+ marginBottom: 8
1204
+ },
1205
+ children: "Backup Codes"
1206
+ }), /*#__PURE__*/_jsx(View, {
1207
+ style: {
1208
+ backgroundColor: '#F8F9FA',
1209
+ borderRadius: 8,
1210
+ padding: 12
1211
+ },
1212
+ children: generatedBackupCodes.map((c, idx) => /*#__PURE__*/_jsx(Text, {
1213
+ style: {
1214
+ fontFamily: Platform.OS === 'web' ? 'monospace' : 'monospace',
1215
+ fontSize: 14,
1216
+ marginBottom: 4
1217
+ },
1218
+ children: c
1219
+ }, idx))
1220
+ })]
1221
+ }), generatedRecoveryKey && /*#__PURE__*/_jsxs(View, {
1222
+ style: {
1223
+ marginBottom: 12
1224
+ },
1225
+ children: [/*#__PURE__*/_jsx(Text, {
1226
+ style: {
1227
+ fontSize: 16,
1228
+ fontWeight: '600',
1229
+ marginBottom: 8
1230
+ },
1231
+ children: "Recovery Key"
1232
+ }), /*#__PURE__*/_jsx(View, {
1233
+ style: {
1234
+ backgroundColor: '#F8F9FA',
1235
+ borderRadius: 8,
1236
+ padding: 12
1237
+ },
1238
+ children: /*#__PURE__*/_jsx(Text, {
1239
+ style: {
1240
+ fontFamily: Platform.OS === 'web' ? 'monospace' : 'monospace',
1241
+ fontSize: 14
1242
+ },
1243
+ children: generatedRecoveryKey
1244
+ })
1245
+ })]
1246
+ }), /*#__PURE__*/_jsxs(TouchableOpacity, {
1247
+ style: [styles.primaryButton, {
1248
+ alignSelf: 'flex-end',
1249
+ marginTop: 8
1250
+ }],
1251
+ onPress: () => {
1252
+ setShowRecoveryModal(false);
1253
+ setEditingField(null);
1254
+ toast.success(t('editProfile.toasts.twoFactorEnabled') || 'Two‑Factor Authentication enabled');
1255
+ },
1256
+ children: [/*#__PURE__*/_jsx(Ionicons, {
1257
+ name: "checkmark",
1258
+ size: 18,
1259
+ color: "#fff"
1260
+ }), /*#__PURE__*/_jsx(Text, {
1261
+ style: styles.primaryButtonText,
1262
+ children: "I saved them"
1263
+ })]
1264
+ })]
1265
+ })
1266
+ }), /*#__PURE__*/_jsxs(View, {
970
1267
  style: styles.section,
971
1268
  children: [/*#__PURE__*/_jsx(Text, {
972
1269
  style: styles.sectionTitle,
973
- children: "Profile Picture"
1270
+ children: t('editProfile.sections.profilePicture') || 'Profile Picture'
974
1271
  }), /*#__PURE__*/_jsx(GroupedSection, {
975
1272
  items: [{
976
1273
  id: 'profile-photo',
@@ -996,28 +1293,28 @@ const AccountSettingsScreen = ({
996
1293
  style: styles.section,
997
1294
  children: [/*#__PURE__*/_jsx(Text, {
998
1295
  style: styles.sectionTitle,
999
- children: "Basic Information"
1296
+ children: t('editProfile.sections.basicInfo') || 'Basic Information'
1000
1297
  }), /*#__PURE__*/_jsx(GroupedSection, {
1001
1298
  items: [{
1002
1299
  id: 'display-name',
1003
1300
  icon: 'person',
1004
1301
  iconColor: '#007AFF',
1005
- title: 'Display Name',
1006
- subtitle: [displayName, lastName].filter(Boolean).join(' ') || 'Add your display name',
1302
+ title: t('editProfile.items.displayName.title') || 'Display Name',
1303
+ subtitle: [displayName, lastName].filter(Boolean).join(' ') || t('editProfile.items.displayName.add') || 'Add your display name',
1007
1304
  onPress: () => startEditing('displayName', '')
1008
1305
  }, {
1009
1306
  id: 'username',
1010
1307
  icon: 'at',
1011
1308
  iconColor: '#5856D6',
1012
- title: 'Username',
1013
- subtitle: username || 'Choose a username',
1309
+ title: t('editProfile.items.username.title') || 'Username',
1310
+ subtitle: username || t('editProfile.items.username.choose') || 'Choose a username',
1014
1311
  onPress: () => startEditing('username', username)
1015
1312
  }, {
1016
1313
  id: 'email',
1017
1314
  icon: 'mail',
1018
1315
  iconColor: '#FF9500',
1019
- title: 'Email',
1020
- subtitle: email || 'Add your email address',
1316
+ title: t('editProfile.items.email.title') || 'Email',
1317
+ subtitle: email || t('editProfile.items.email.add') || 'Add your email address',
1021
1318
  onPress: () => startEditing('email', email)
1022
1319
  }],
1023
1320
  theme: theme
@@ -1026,21 +1323,25 @@ const AccountSettingsScreen = ({
1026
1323
  style: styles.section,
1027
1324
  children: [/*#__PURE__*/_jsx(Text, {
1028
1325
  style: styles.sectionTitle,
1029
- children: "About You"
1326
+ children: t('editProfile.sections.about') || 'About You'
1030
1327
  }), /*#__PURE__*/_jsx(GroupedSection, {
1031
1328
  items: [{
1032
1329
  id: 'bio',
1033
1330
  icon: 'document-text',
1034
1331
  iconColor: '#34C759',
1035
- title: 'Bio',
1036
- subtitle: bio || 'Tell people about yourself',
1332
+ title: t('editProfile.items.bio.title') || 'Bio',
1333
+ subtitle: bio || t('editProfile.items.bio.placeholder') || 'Tell people about yourself',
1037
1334
  onPress: () => startEditing('bio', bio)
1038
1335
  }, {
1039
1336
  id: 'locations',
1040
1337
  icon: 'location',
1041
1338
  iconColor: '#FF3B30',
1042
- title: 'Locations',
1043
- subtitle: tempLocations.length > 0 ? `${tempLocations.length} location${tempLocations.length !== 1 ? 's' : ''} added` : 'Add your locations',
1339
+ title: t('editProfile.items.locations.title') || 'Locations',
1340
+ subtitle: tempLocations.length > 0 ? tempLocations.length === 1 ? t('editProfile.items.locations.count', {
1341
+ count: tempLocations.length
1342
+ }) || `${tempLocations.length} location added` : t('editProfile.items.locations.count_plural', {
1343
+ count: tempLocations.length
1344
+ }) || `${tempLocations.length} locations added` : t('editProfile.items.locations.add') || 'Add your locations',
1044
1345
  onPress: () => startEditing('location', ''),
1045
1346
  customContentBelow: tempLocations.length > 0 && /*#__PURE__*/_jsxs(View, {
1046
1347
  style: styles.linksPreviewContainer,
@@ -1072,8 +1373,12 @@ const AccountSettingsScreen = ({
1072
1373
  id: 'links',
1073
1374
  icon: 'link',
1074
1375
  iconColor: '#32D74B',
1075
- title: 'Links',
1076
- subtitle: tempLinksWithMetadata.length > 0 ? `${tempLinksWithMetadata.length} link${tempLinksWithMetadata.length !== 1 ? 's' : ''} added` : 'Add your links',
1376
+ title: t('editProfile.items.links.title') || 'Links',
1377
+ subtitle: tempLinksWithMetadata.length > 0 ? tempLinksWithMetadata.length === 1 ? t('editProfile.items.links.count', {
1378
+ count: tempLinksWithMetadata.length
1379
+ }) || `${tempLinksWithMetadata.length} link added` : t('editProfile.items.links.count_plural', {
1380
+ count: tempLinksWithMetadata.length
1381
+ }) || `${tempLinksWithMetadata.length} links added` : t('editProfile.items.links.add') || 'Add your links',
1077
1382
  onPress: () => startEditing('links', ''),
1078
1383
  multiRow: true,
1079
1384
  customContentBelow: tempLinksWithMetadata.length > 0 && /*#__PURE__*/_jsxs(View, {
@@ -1108,14 +1413,14 @@ const AccountSettingsScreen = ({
1108
1413
  style: styles.section,
1109
1414
  children: [/*#__PURE__*/_jsx(Text, {
1110
1415
  style: styles.sectionTitle,
1111
- children: "Quick Actions"
1416
+ children: t('editProfile.sections.quickActions') || 'Quick Actions'
1112
1417
  }), /*#__PURE__*/_jsx(GroupedSection, {
1113
1418
  items: [{
1114
1419
  id: 'preview-profile',
1115
1420
  icon: 'eye',
1116
1421
  iconColor: '#007AFF',
1117
- title: 'Preview Profile',
1118
- subtitle: 'See how your profile looks to others',
1422
+ title: t('editProfile.items.previewProfile.title') || 'Preview Profile',
1423
+ subtitle: t('editProfile.items.previewProfile.subtitle') || 'See how your profile looks to others',
1119
1424
  onPress: () => navigate?.('Profile', {
1120
1425
  userId: user?.id
1121
1426
  })
@@ -1123,16 +1428,32 @@ const AccountSettingsScreen = ({
1123
1428
  id: 'privacy-settings',
1124
1429
  icon: 'shield-checkmark',
1125
1430
  iconColor: '#8E8E93',
1126
- title: 'Privacy Settings',
1127
- subtitle: 'Control who can see your profile',
1128
- onPress: () => toast.info('Privacy settings coming soon!')
1431
+ title: t('editProfile.items.privacySettings.title') || 'Privacy Settings',
1432
+ subtitle: t('editProfile.items.privacySettings.subtitle') || 'Control who can see your profile',
1433
+ onPress: () => toast.info(t('editProfile.items.privacySettings.coming') || 'Privacy settings coming soon!')
1129
1434
  }, {
1130
1435
  id: 'verify-account',
1131
1436
  icon: 'checkmark-circle',
1132
1437
  iconColor: '#30D158',
1133
- title: 'Verify Account',
1134
- subtitle: 'Get a verified badge',
1135
- onPress: () => toast.info('Account verification coming soon!')
1438
+ title: t('editProfile.items.verifyAccount.title') || 'Verify Account',
1439
+ subtitle: t('editProfile.items.verifyAccount.subtitle') || 'Get a verified badge',
1440
+ onPress: () => toast.info(t('editProfile.items.verifyAccount.coming') || 'Account verification coming soon!')
1441
+ }],
1442
+ theme: theme
1443
+ })]
1444
+ }), /*#__PURE__*/_jsxs(View, {
1445
+ style: styles.section,
1446
+ children: [/*#__PURE__*/_jsx(Text, {
1447
+ style: styles.sectionTitle,
1448
+ children: t('editProfile.sections.security') || 'Security'
1449
+ }), /*#__PURE__*/_jsx(GroupedSection, {
1450
+ items: [{
1451
+ id: 'two-factor',
1452
+ icon: 'shield-checkmark',
1453
+ iconColor: '#007AFF',
1454
+ title: t('editProfile.items.twoFactor.title') || 'Two‑Factor Authentication',
1455
+ subtitle: user?.privacySettings?.twoFactorEnabled ? t('editProfile.items.twoFactor.enabled') || 'Enabled' : t('editProfile.items.twoFactor.disabled') || 'Disabled (recommended)',
1456
+ onPress: () => startEditing('twoFactor', '')
1136
1457
  }],
1137
1458
  theme: theme
1138
1459
  })]
@@ -1216,6 +1537,26 @@ const styles = StyleSheet.create({
1216
1537
  minHeight: 52,
1217
1538
  fontWeight: '400'
1218
1539
  },
1540
+ editingFieldDescription: {
1541
+ fontSize: 14,
1542
+ color: '#666',
1543
+ marginBottom: 16
1544
+ },
1545
+ primaryButton: {
1546
+ flexDirection: 'row',
1547
+ alignItems: 'center',
1548
+ justifyContent: 'center',
1549
+ gap: 8,
1550
+ backgroundColor: '#007AFF',
1551
+ paddingVertical: 12,
1552
+ paddingHorizontal: 16,
1553
+ borderRadius: 10
1554
+ },
1555
+ primaryButtonText: {
1556
+ color: '#fff',
1557
+ fontSize: 16,
1558
+ fontWeight: '600'
1559
+ },
1219
1560
  editingFieldTextArea: {
1220
1561
  backgroundColor: '#fff',
1221
1562
  borderWidth: 2,