MainConsole.tsx 31 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874
  1. import { WindowStatusType, WindowType } from "@/utils/types";
  2. import { View, Text, Image } from "@tarojs/components";
  3. import dayjs from "dayjs";
  4. import { useEffect, useRef, useState } from "react";
  5. import { useDispatch, useSelector } from "react-redux";
  6. import './MainConsole.scss'
  7. import { jumpPage } from "../trackTimeDuration/hooks/Common";
  8. import Modal from "@/components/layout/Modal.weapp";
  9. import { MainColorType } from "@/context/themes/color";
  10. import ConsolePicker from "../trackTimeDuration/components/ConsolePicker";
  11. import { clockTimes, makeDone, updateEventDuration, updateSchedule, updateTarget } from "@/services/health";
  12. import TimePicker from "../common/TimePicker";
  13. import showActionSheet from "@/components/basic/ActionSheet";
  14. import { rpxToPx } from "@/utils/tools";
  15. import { setMode, setShowActionTip } from "@/store/health";
  16. import { getCountownTime, getDuration, getScenario, getThemeColor, getWindowStatus } from "./hooks/health_hooks";
  17. import { IconCellArrow, IconMore } from "@/components/basic/Icons";
  18. import DurationPicker from "@/_health/components/duration_picker";
  19. import Taro from "@tarojs/taro";
  20. import { systemLocation } from "@/services/common";
  21. import { TimeFormatter } from "@/utils/time_format";
  22. import { clearLocation } from "@/services/user";
  23. import OnBoard from "@/_health/components/onboard";
  24. import NewButton, { NewButtonType } from "@/_health/base/new_button";
  25. let useNavigation;
  26. let min = 0
  27. let max = 0
  28. let defaultTimestamp = 0
  29. if (process.env.TARO_ENV == 'rn') {
  30. useNavigation = require("@react-navigation/native").useNavigation
  31. }
  32. export default function MainConsole(props: { type: WindowType }) {
  33. const health = useSelector((state: any) => state.health);
  34. const user = useSelector((state: any) => state.user);
  35. const [showPicker, setShowPicker] = useState(false)
  36. const [showTimePicker, setShowTimePicker] = useState(false)
  37. const [durationPicker, setDurationPicker] = useState(false)
  38. const [operateType, setOperateType] = useState('')
  39. const [btnDisable, setBtnDisable] = useState(false)
  40. const [selItem, setSelItem] = useState<any>(null)
  41. const limitPickerRef = useRef(null)
  42. const dispatch = useDispatch()
  43. let navigation, showActionSheetWithOptions;
  44. if (useNavigation) {
  45. navigation = useNavigation()
  46. }
  47. useEffect(() => {
  48. }, [props.type])
  49. function edit(item) {
  50. if (item.scenario != 'FAST' && item.scenario != 'SLEEP') {
  51. return
  52. }
  53. if (item.action == 'NA' || item.action == 'POST_MOMENT' || 'SLEEP_WAKE_UP' == item.action) {
  54. return;
  55. }
  56. if (!user.isLogin) {
  57. jumpPage('/pages/account/ChooseAuth', 'ChooseAuth', navigation)
  58. return
  59. }
  60. console.log(item)
  61. setSelItem(item)
  62. setShowPicker(true)
  63. }
  64. function record(item) {
  65. if (!user.isLogin) {
  66. jumpPage('/pages/account/ChooseAuth', 'ChooseAuth', navigation)
  67. return
  68. }
  69. setSelItem(item)
  70. switch (item.action) {
  71. case 'START':
  72. {
  73. defaultTimestamp = new Date().getTime()
  74. min = defaultTimestamp - 1 * 24 * 3600 * 1000
  75. max = defaultTimestamp
  76. setOperateType('startFast')
  77. setShowTimePicker(true)
  78. }
  79. return;
  80. case 'END':
  81. {
  82. defaultTimestamp = new Date().getTime()
  83. // defaultTimestamp = e ? new Date().getTime() : logEventTimestamp
  84. min = defaultTimestamp - 1 * 24 * 3600 * 1000
  85. max = defaultTimestamp
  86. setOperateType('endFast')
  87. setShowTimePicker(true)
  88. }
  89. return;
  90. case 'MARK_DONE':
  91. {
  92. setBtnDisable(true)
  93. clockTimes({
  94. check_items: [{
  95. schedule_id: item.schedule_id,
  96. date: dayjs().format('YYYYMMDD'),
  97. timestamp: new Date().getTime()
  98. }]
  99. }).then(res => {
  100. // dispatch(setShowActionTip({
  101. // isShow: true,
  102. // isCompleted: (selItem.event == 'FAST_END' || selItem.event == 'SLEEP_WAKE_UP')
  103. // }))
  104. // setBtnDisable(false)
  105. // setShowTimePicker(false)
  106. global.refreshWindow()
  107. global.refreshHistory()
  108. }).catch(e => {
  109. })
  110. }
  111. return;
  112. }
  113. jumpPage(`/_health/pages/add_moment?moment=${JSON.stringify(item)}&title=${item.title}&schedule_id=${item.schedule_id}&event_id=${item.event_id}`)
  114. }
  115. function operateTitle(item) {
  116. switch (item.action) {
  117. case 'START':
  118. case 'END':
  119. return '打卡'
  120. case 'MARK_DONE':
  121. return 'Action'
  122. }
  123. return '记录'
  124. }
  125. function itemTitle(item: any) {
  126. // if (health.mode == 'DAY' || health.mode == 'NIGHT') {
  127. // return item.title
  128. // }
  129. if (item.real) {
  130. return dayjs(item.real.timestamp).format('HH:mm')
  131. }
  132. if (!item.target || !item.target.timestamp) {
  133. return item.time_label
  134. }
  135. return dayjs(item.target.timestamp).format('HH:mm')
  136. }
  137. function itemValue(item: any) {
  138. let themeColor: any = getThemeColor(health.mode)
  139. const scenario = getScenario(health.windows, health.mode)
  140. if (item.action == 'END' && !scenario.real) {
  141. themeColor = '#B2B2B2'
  142. }
  143. if (health.mode == 'DAY' || health.mode == 'NIGHT') {
  144. return null
  145. }
  146. if (item.action && item.action != 'NA') {
  147. if (health.mode == 'FAST' || health.mode == 'SLEEP') {
  148. if (item.action == 'POST_MOMENT') {
  149. return <IconCellArrow color='#B2B2B2' width={rpxToPx(34)} />
  150. }
  151. }
  152. else if (health.mode == 'ACTIVE' && item.action == 'POST_MOMENT') {
  153. return <NewButton
  154. color={themeColor}
  155. type={NewButtonType.border}
  156. title={operateTitle(item)}
  157. width={rpxToPx(128)}
  158. height={rpxToPx(72)}
  159. bold={true}
  160. onClick={() => record(item)} />
  161. // return <View className="timeline_operate" style={{ color: themeColor, backgroundColor: '#fff', borderColor: themeColor, borderWidth: 1, borderStyle: 'solid' }}
  162. // onClick={() => record(item)}>{operateTitle(item)}</View>
  163. }
  164. return <NewButton
  165. color={themeColor}
  166. type={NewButtonType.alpha}
  167. title={operateTitle(item)}
  168. width={rpxToPx(128)}
  169. height={rpxToPx(72)}
  170. bold={true}
  171. onClick={() => record(item)} />
  172. }
  173. return <View />
  174. }
  175. function tapTimeline(item, inex) {
  176. if (health.mode == 'DAY' || health.mode == 'NIGHT') {
  177. return;
  178. }
  179. if (!user.isLogin) {
  180. jumpPage('/pages/account/ChooseAuth', 'ChooseAuth', navigation)
  181. return
  182. }
  183. if (!item.event_id) {
  184. return
  185. }
  186. jumpPage(`/_health/pages/timeline_detail?event_id=${item.event_id}&schedule_id=${item.schedule_id}`)
  187. }
  188. function timelineItem(item: any, index: number, count: number) {
  189. var hasDescription = item.moment && item.moment.description
  190. return <View key={index}
  191. className="timeline_item"
  192. // hoverClass='cell_hover' hoverStayTime={50}
  193. onClick={() => tapTimeline(item, index)}>
  194. <View className="timeline_left">
  195. {/* space */}
  196. <View style={{
  197. height: hasDescription ? rpxToPx(28) : rpxToPx(36), flexShrink: 0
  198. }} />
  199. <View style={{ display: 'flex', flexDirection: 'row', alignItems: 'center' }}>
  200. {/* {
  201. !item.reminder && <Image src={require('@assets/images/notification_off.png')} className='notification_icon' />
  202. } */}
  203. <View style={{
  204. flexShrink: 0,
  205. width: rpxToPx(28),
  206. height: rpxToPx(28),
  207. borderRadius: rpxToPx(14),
  208. marginRight: rpxToPx(8),
  209. backgroundColor: 'gray'
  210. }} />
  211. <Text className="timeline_time">{itemTitle(item)}</Text>
  212. </View>
  213. <Text className="timeline_title"
  214. onClick={() => edit(item)}>{(item.moment && item.moment.title) ? item.moment.title : item.title}</Text>
  215. {
  216. hasDescription && <Text className="timeline_desc">{item.moment.description}</Text>
  217. }
  218. {/* space */}
  219. <View style={{
  220. height: hasDescription ? rpxToPx(28) : rpxToPx(54), flexShrink: 0,
  221. }} />
  222. </View>
  223. <View style={{ flex: 1 }} />
  224. {
  225. item.moment && item.moment.media && item.moment.media.length > 0 && <Image
  226. src={item.moment.media[0].url}
  227. mode="aspectFill"
  228. className="console_item_img" />
  229. }
  230. {
  231. itemValue(item)
  232. }
  233. <View className="seperate_line" style={{ left: count - 1 == index ? -rpxToPx(52) : rpxToPx(52) }} />
  234. </View>
  235. }
  236. function timeContent() {
  237. return <Modal
  238. testInfo={null}
  239. dismiss={() => {
  240. setShowPicker(false)
  241. }}
  242. confirm={() => { }}>
  243. {
  244. pickerContent()
  245. }
  246. </Modal>
  247. }
  248. function pickerContent() {
  249. const timestamp = selItem.target.timestamp
  250. const strTime = dayjs(timestamp).format('HH:mm')
  251. var title, color;
  252. switch (selItem.scenario) {
  253. case 'FAST':
  254. title = selItem.event == 'FAST_END' ? '结束断食' : '开始断食'
  255. color = MainColorType.fast
  256. break;
  257. case 'SLEEP':
  258. title = selItem.event == 'SLEEP_WAKE_UP' ? '结束睡眠' : '开始睡眠'
  259. color = MainColorType.sleep
  260. }
  261. return <TimePicker time={strTime}
  262. color={color}
  263. title={title}
  264. confirm={(e) => {
  265. confirmPickerTime(e)
  266. }}
  267. cancel={() => {
  268. setShowPicker(false)
  269. }} />
  270. }
  271. function confirmPickerTime(strTime) {
  272. if (selItem.event == 'FAST_END') {
  273. const obj = health.windows.fast_eat.fast.timeline[0]
  274. if (obj.action == 'POST_MOMENT' || obj.action == 'NA') {
  275. const format = dayjs(obj.target.timestamp).format(`YYYY-MM-DDT${strTime}:ss`)
  276. var t = new Date(format).getTime()
  277. if (t <= obj.target.timestamp) {
  278. t += 24 * 3600 * 1000
  279. }
  280. updateTarget(t, obj.event_id).then(res => {
  281. global.refreshWindow()
  282. global.refreshHistory()
  283. setShowPicker(false)
  284. })
  285. return;
  286. }
  287. }
  288. else if (selItem.event == 'SLEEP_WAKE_UP') {
  289. const obj = health.windows.sleep_active.sleep.timeline[0]
  290. if (obj.action == 'POST_MOMENT' || obj.action == 'NA') {
  291. const format = dayjs(obj.target.timestamp).format(`YYYY-MM-DDT${strTime}:ss`)
  292. var t = new Date(format).getTime()
  293. if (t <= obj.target.timestamp) {
  294. t += 24 * 3600 * 1000
  295. }
  296. updateTarget(t, obj.event_id).then(res => {
  297. global.refreshWindow()
  298. global.refreshHistory()
  299. setShowPicker(false)
  300. })
  301. return;
  302. }
  303. }
  304. updateSchedule({
  305. time: strTime,
  306. event: selItem.event,
  307. title: selItem.title,
  308. is_all_day: false
  309. }, selItem.schedule_id).then(res => {
  310. global.refreshWindow()
  311. global.refreshHistory()
  312. setShowPicker(false)
  313. })
  314. }
  315. function modalContent() {
  316. global.set_time = new Date().getTime()
  317. return <Modal
  318. testInfo={null}
  319. dismiss={() => {
  320. setShowTimePicker(false)
  321. }}
  322. confirm={() => { }}>
  323. {
  324. timePickerContent()
  325. }
  326. </Modal>
  327. }
  328. function timePickerContent() {
  329. var title, color;
  330. switch (selItem.scenario) {
  331. case 'FAST':
  332. title = selItem.event == 'FAST_END' ? '结束断食' : '开始断食'
  333. color = MainColorType.fast
  334. break;
  335. case 'SLEEP':
  336. title = selItem.event == 'SLEEP_WAKE_UP' ? '结束睡眠' : '开始睡眠'
  337. color = MainColorType.sleep
  338. break
  339. }
  340. var endTimestamp = 0
  341. if (selItem.envent == 'FAST_END') {
  342. endTimestamp = new Date().getTime()//fastData.target.end_time
  343. }
  344. var duration = 24 * 3600 * 1000//fastData.target.duration
  345. global.set_time = new Date().getTime()
  346. return <View className="modal_content">
  347. <ConsolePicker ref={limitPickerRef}
  348. themeColor={color}
  349. title={title}
  350. onCancel={() => {
  351. setShowTimePicker(false)
  352. }}
  353. min={min}
  354. max={max}
  355. current={defaultTimestamp}
  356. duration={duration}
  357. endTimestamp={endTimestamp}
  358. isFast={true}
  359. isEnd={operateType == 'endFast'}
  360. isTimeout={false}
  361. isLoading={btnDisable}
  362. onChange={(e) => {
  363. pickerConfirm(e, null)
  364. global.pauseIndexTimer = false
  365. }}
  366. />
  367. </View>
  368. }
  369. function pickerConfirm(t1: number, event: any) {
  370. if (btnDisable) {
  371. return
  372. }
  373. global.scenario = 'FAST'
  374. setBtnDisable(true)
  375. clockTimes({
  376. check_items: [{
  377. schedule_id: selItem.schedule_id,
  378. date: dayjs(t1).format('YYYYMMDD'),
  379. timestamp: t1,
  380. extra: {
  381. set_time: global.set_time ? global.set_time : new Date().getTime(),
  382. confirm_time: new Date().getTime()
  383. }
  384. }]
  385. }).then(res => {
  386. dispatch(setShowActionTip({
  387. isShow: true,
  388. isCompleted: (selItem.event == 'FAST_END' || selItem.event == 'SLEEP_WAKE_UP')
  389. }))
  390. setBtnDisable(false)
  391. setShowTimePicker(false)
  392. global.refreshWindow()
  393. global.refreshHistory()
  394. }).catch(e => {
  395. setBtnDisable(false)
  396. })
  397. }
  398. function more() {
  399. var list: any = []
  400. switch (health.mode) {
  401. case 'DAY':
  402. case 'NIGHT':
  403. list = ['设置提醒', '设置位置']
  404. break;
  405. case 'FAST':
  406. case 'SLEEP':
  407. {
  408. const obj = getScenario(health.windows, health.mode)
  409. if (obj.window_id) {
  410. list.push('编辑本次时长')
  411. if (obj.timeline && obj.timeline[0].moment) {
  412. list.push('删除本次记录')
  413. }
  414. }
  415. list.push('编辑日程列表')
  416. }
  417. break;
  418. case 'EAT':
  419. {
  420. list = [
  421. 'Add Snack',
  422. '编辑日程列表',
  423. ]
  424. if (getScenario(health.windows, health.mode).window_id) {
  425. list.push('Make done')
  426. }
  427. }
  428. break;
  429. case 'ACTIVE':
  430. {
  431. list = [
  432. '记录一次活动',
  433. '编辑日程列表',
  434. ]
  435. if (getScenario(health.windows, health.mode).window_id) {
  436. list.push('Make done')
  437. }
  438. }
  439. break;
  440. }
  441. showActionSheet({
  442. showActionSheetWithOptions: showActionSheetWithOptions,
  443. title: 'Oprate Title',
  444. itemList: list,
  445. success: (res) => {
  446. tapActionSheet(res)
  447. }
  448. });
  449. }
  450. function tapActionSheet(index) {
  451. switch (index) {
  452. case 0:
  453. {
  454. switch (health.mode) {
  455. case 'DAY':
  456. case 'NIGHT':
  457. jumpPage('/_health/pages/schedules?mode=' + health.mode)
  458. break;
  459. case 'FAST':
  460. case 'SLEEP':
  461. {
  462. const obj = getScenario(health.windows, health.mode)
  463. if (obj.window_id) {
  464. //编辑本次时长
  465. setDurationPicker(true)
  466. }
  467. else {
  468. jumpPage('/_health/pages/schedules?mode=' + health.mode)
  469. }
  470. }
  471. break;
  472. case 'EAT':
  473. //add snack
  474. jumpPage(`/_health/pages/add_moment?title=加餐&is_temp=${true}`)
  475. break;
  476. case 'ACTIVE':
  477. //记录一次活动
  478. jumpPage(`/_health/pages/add_moment?title=&is_temp=${true}`)
  479. break;
  480. }
  481. }
  482. break;
  483. case 1:
  484. {
  485. switch (health.mode) {
  486. case 'EAT':
  487. jumpPage('/_health/pages/schedules?mode=' + health.mode)
  488. break;
  489. case 'FAST':
  490. case 'SLEEP':
  491. const obj = getScenario(health.windows, health.mode)
  492. if (obj.window_id) {
  493. //del record
  494. jumpPage('/_health/pages/schedules?mode=' + health.mode)
  495. console.log('zzzzzzzzz')
  496. }
  497. else {
  498. }
  499. break;
  500. case 'ACTIVE':
  501. jumpPage('/_health/pages/schedules?mode=' + health.mode)
  502. break;
  503. case 'DAY':
  504. case 'NIGHT':
  505. chooseLocation()
  506. break;
  507. }
  508. }
  509. break;
  510. case 2:
  511. {
  512. switch (health.mode) {
  513. case 'EAT':
  514. case 'ACTIVE':
  515. tapMakeDone()
  516. break;
  517. }
  518. }
  519. break;
  520. }
  521. }
  522. function tapMakeDone() {
  523. makeDone(getScenario(health.windows, health.mode).window_id).then(res => {
  524. global.refreshWindow()
  525. global.refreshHistory()
  526. })
  527. }
  528. function detail() {
  529. const { day, night } = health.windows.night_day
  530. const { fast, eat } = health.windows.fast_eat
  531. const { sleep, active } = health.windows.sleep_active
  532. let list: any = []
  533. switch (health.mode) {
  534. case 'DAY':
  535. list = day.timeline
  536. if (day.onboard == false) {
  537. return <OnBoard title='你还没有开启位置授权'
  538. desc="获取准确的日出日落信息需要您开启微信运动授权,点击下方按钮进行授权"
  539. btnTitle="去开启"
  540. onClick={chooseLocation}
  541. />
  542. }
  543. break;
  544. case 'NIGHT':
  545. list = night.timeline
  546. if (night.onboard == false) {
  547. return <OnBoard title='你还没有开启位置授权'
  548. desc='获取准确的日出日落信息需要您开启微信运动授权,点击下方按钮进行授权'
  549. btnTitle="去开启"
  550. onClick={chooseLocation}
  551. />
  552. }
  553. break;
  554. case 'FAST':
  555. list = fast.timeline
  556. break;
  557. case 'EAT':
  558. list = eat.timeline
  559. break;
  560. case 'SLEEP':
  561. list = sleep.timeline
  562. break;
  563. case 'ACTIVE':
  564. list = active.timeline
  565. if (active.onboard == false) {
  566. return <OnBoard title={list[0].title}
  567. desc="Subtitle"
  568. btnTitle="Action"
  569. onClick={() => {
  570. jumpPage('/_health/pages/active_plan?schedule=' + JSON.stringify(list.length > 0 ? list[0] : '{}'))
  571. }}
  572. />
  573. }
  574. break;
  575. }
  576. return <View>
  577. {
  578. list.map((item, index) => {
  579. return timelineItem(item, index, list.length)
  580. })
  581. }
  582. </View>
  583. }
  584. function switchText() {
  585. switch (health.mode) {
  586. case 'FAST':
  587. return 'Switch to Eat'
  588. case 'EAT':
  589. return 'Switch to Fast'
  590. case 'DAY':
  591. return 'Switch to Night'
  592. case 'NIGHT':
  593. return 'Switch to Daylight'
  594. case 'SLEEP':
  595. return 'Switch to Activity'
  596. case 'ACTIVE':
  597. return 'Switch to Sleep'
  598. }
  599. return ''
  600. }
  601. function tapSwitchBtn() {
  602. switch (health.mode) {
  603. case 'FAST':
  604. dispatch(setMode('EAT'));
  605. break
  606. case 'EAT':
  607. dispatch(setMode('FAST'));
  608. break
  609. case 'DAY':
  610. dispatch(setMode('NIGHT'));
  611. break
  612. case 'NIGHT':
  613. dispatch(setMode('DAY'));
  614. break
  615. case 'SLEEP':
  616. dispatch(setMode('ACTIVE'));
  617. break
  618. case 'ACTIVE':
  619. dispatch(setMode('SLEEP'));
  620. break
  621. }
  622. }
  623. function windowStatus() {
  624. var statusType = getWindowStatus(health.windows, health.mode)
  625. switch (statusType) {
  626. case WindowStatusType.open:
  627. return 'New open'
  628. case WindowStatusType.process:
  629. return 'In process'
  630. case WindowStatusType.upcoming:
  631. return 'Upcoming'
  632. }
  633. return ''
  634. }
  635. function tapClearLocation() {
  636. Taro.showModal({
  637. title: '提示',
  638. content: '确认清除位置数据?',
  639. success: function (res) {
  640. if (res.confirm) {
  641. clearLocation().then(res => {
  642. global.refreshWindow()
  643. })
  644. } else if (res.cancel) {
  645. console.log('用户点击取消')
  646. }
  647. }
  648. })
  649. }
  650. function chooseLocation() {
  651. if (!user.isLogin) {
  652. jumpPage('/pages/account/ChooseAuth', 'ChooseAuth', navigation)
  653. return
  654. }
  655. Taro.chooseLocation({
  656. // latitude: authInfo && authInfo.lat ? authInfo.lat : undefined,
  657. // longitude: authInfo && authInfo.lat ? authInfo.lng : undefined,
  658. success: function (res) {
  659. uploadLocation(res)
  660. },
  661. fail(res) {
  662. Taro.showToast({
  663. title: '位置修改失败!\n请重新选择就近位置',
  664. icon: 'none'
  665. })
  666. },
  667. complete(res) {
  668. }
  669. })
  670. }
  671. function uploadLocation(res) {
  672. var today = new Date()
  673. var yesterday = new Date(today.getTime() - 24 * 3600 * 1000)
  674. var tomorrow = new Date(today.getTime() + 24 * 3600 * 1000 * 5)
  675. var strYesterday = `${yesterday.getFullYear()}-${TimeFormatter.padZero(yesterday.getMonth() + 1)}-${TimeFormatter.padZero(yesterday.getDate())}`
  676. var strTomorrow = `${tomorrow.getFullYear()}-${TimeFormatter.padZero(tomorrow.getMonth() + 1)}-${TimeFormatter.padZero(tomorrow.getDate())}`
  677. systemLocation({
  678. lat: res.latitude,
  679. lng: res.longitude,
  680. name: res.name,
  681. address: res.address,
  682. date_start: strYesterday,
  683. date_end: strTomorrow,
  684. coordinate_system_standard: process.env.TARO_ENV == 'weapp' ? 'GCJ-02' : 'WGS-84'
  685. }).then(data => {
  686. global.refreshWindow()
  687. })
  688. }
  689. function updateDuration(duration) {
  690. setDurationPicker(false)
  691. const scenario = getScenario(health.windows, health.mode)
  692. updateEventDuration(scenario.timeline[0].event_id, duration).then(res => {
  693. global.refreshWindow()
  694. })
  695. }
  696. function timePointClass() {
  697. if (getWindowStatus(health.windows, health.mode) == WindowStatusType.process) {
  698. return 'time_point time_point_animation'
  699. }
  700. return 'time_point'
  701. }
  702. return <View className="main-console-bg">
  703. <Image className="main_arrow" src={require('@assets/images/center_arrow.png')} />
  704. <View className="main_summary">
  705. {/* <View className="main_summary_status" style={{ color: getThemeColor(health.mode) }}>{windowStatus()}</View> */}
  706. <View className="main_summary_time" style={{ color: getWindowStatus(health.windows, health.mode) == WindowStatusType.upcoming ? '#B2B2B2' : '#000' }}>{getCountownTime(health.windows, health.mode)}
  707. <View className={timePointClass()}
  708. style={{ backgroundColor: getWindowStatus(health.windows, health.mode) == WindowStatusType.upcoming ? '#B2B2B2' : getThemeColor(health.mode) }} />
  709. </View>
  710. <Text className="main_summary_duration">Total {getDuration(health.windows, health.mode)}</Text>
  711. <View className="border_footer_line" />
  712. </View>
  713. <View style={{ backgroundColor: '#fff', width: rpxToPx(750) }}>
  714. {
  715. detail()
  716. }
  717. {
  718. health.mode == 'ACTIVE' && <View onClick={() => {
  719. var list = getScenario(health.windows, health.mode).timeline
  720. jumpPage('/_health/pages/active_plan?schedule=' + JSON.stringify(list.length > 0 ? list[0] : '{}'))
  721. }}>测试</View>
  722. }
  723. </View>
  724. <View className="main_footer">
  725. <Text className="main_footer_text" onClick={tapSwitchBtn}>{switchText()}</Text>
  726. {/* {
  727. (health.mode == 'EAT' || health.mode == 'ACTIVE') && <Text style={{ display: 'flex', alignItems: 'center', justifyContent: 'center' }} onClick={more}>更多</Text>
  728. } */}
  729. {/* {
  730. (health.mode == 'DAY' || health.mode == 'NIGHT') && <Text onClick={chooseLocation}>选择位置</Text>
  731. } */}
  732. {
  733. (health.mode == 'DAY' || health.mode == 'NIGHT') && <Text onClick={tapClearLocation}>清除位置</Text>
  734. }
  735. <View className="main_footer_more" onClick={more}>
  736. <IconMore color="#b2b2b2" width={17} />
  737. </View>
  738. </View>
  739. {
  740. health.mode == 'ACTIVE' && <View className="console_active_bg" onClick={() => {
  741. if (!user.isLogin) {
  742. jumpPage('/pages/account/ChooseAuth', 'ChooseAuth', navigation)
  743. return
  744. }
  745. jumpPage('/_health/pages/move')
  746. }}>
  747. <View className="console_active">
  748. <Image className="active_icon" src={require('@assets/_health/walk.png')} />
  749. <Text className="active_text">Move More</Text>
  750. <Image className="cell_arrow" src={require('@assets/_health/cell_arrow.png')} />
  751. </View>
  752. </View>
  753. }
  754. {
  755. health.mode == 'FAST' && <View className="console_active_bg" onClick={() => {
  756. if (!user.isLogin) {
  757. jumpPage('/pages/account/ChooseAuth', 'ChooseAuth', navigation)
  758. return
  759. }
  760. jumpPage('/_health/pages/fast_sleep')
  761. }}>
  762. <View className="console_active">
  763. <Image className="active_icon" src={require('@assets/_health/fast.png')} />
  764. <Text className="active_text">Fast with sleep</Text>
  765. <Image className="cell_arrow" src={require('@assets/_health/cell_arrow.png')} />
  766. </View>
  767. </View>
  768. }
  769. {
  770. health.mode == 'FAST' && <View className="console_active_bg" onClick={() => {
  771. if (!user.isLogin) {
  772. jumpPage('/pages/account/ChooseAuth', 'ChooseAuth', navigation)
  773. return
  774. }
  775. jumpPage('/_health/pages/long_fast')
  776. }}>
  777. <View className="console_active">
  778. <Image className="active_icon" src={require('@assets/_health/fast.png')} />
  779. <Text className="active_text">Long fast</Text>
  780. <Image className="cell_arrow" src={require('@assets/_health/cell_arrow.png')} />
  781. </View>
  782. </View>
  783. }
  784. <View className="circle" />
  785. {
  786. showTimePicker && modalContent()
  787. }
  788. {
  789. showPicker && timeContent()
  790. }
  791. {
  792. durationPicker && <DurationPicker
  793. done={(time) => {
  794. updateDuration(time)
  795. }}
  796. dismiss={() => {
  797. setDurationPicker(false)
  798. }} time={getScenario(health.windows, health.mode).target.duration} />
  799. }
  800. </View>
  801. }