leon 1 rok pred
rodič
commit
50028bf079

+ 20 - 2
src/features/trackTimeDuration/actions/TrackTimeActions.tsx

@@ -1,4 +1,4 @@
-import { API_LOCAL_PUSHES } from "@/services/http/api";
+import { API_LOCAL_PUSHES, API_MIX_CLOCKS } from "@/services/http/api";
 import { request } from "@/services/http/request";
 import { recordCheck } from "@/services/trackTimeDuration";
 import trackTimeService from "@/store/trackTimeMachine"
@@ -100,6 +100,24 @@ export const endSleep = (start_time: number) => {
     });
 }
 
+export const batchClocks = (params: any) => {
+    const extra = {
+        set_time: global.set_time,
+        confirm_time: new Date().getTime(),
+    }
+    return new Promise((resolve, reject) => {
+        request({
+            url: API_MIX_CLOCKS, method: 'POST', data: { extra: extra, ...params }
+        }).then(res => {
+            resolve(res);
+        }).catch(e => {
+            if (global.postBtnUpdateStatus)
+                global.postBtnUpdateStatus('idle')
+            reject(e)
+        })
+    })
+}
+
 export const uploadLocalPushInfo = (params) => {
     request({
         url: API_LOCAL_PUSHES, method: 'POST', data: {
@@ -113,7 +131,7 @@ export const getLocalPush = () => {
     if (process.env.TARO_ENV == 'rn') {
         PushNotification.checkPermissions((res) => {
             console.log('notification status begin')
-            console.log('notification status',res)
+            console.log('notification status', res)
             //允许授权
             if ((kIsIOS && res.authorizationStatus == 2) || (!kIsIOS && res.alert)) {
                 request({

+ 52 - 45
src/features/trackTimeDuration/components/IndexConsole.tsx

@@ -19,11 +19,12 @@ import CircadianDetailPopup from './CircadianDetailPopup';
 import showAlert from '@/components/basic/Alert';
 import CheckAccess from './CheckAccess';
 import { ColorType } from '@/context/themes/color';
+import IndexConsoleMuti from './IndexConsoleMuti';
 
 let useNavigation;
 
-let Linking,PushNotification;
-let  checkNotification;
+let Linking, PushNotification;
+let checkNotification;
 if (process.env.TARO_ENV == 'rn') {
     useNavigation = require("@react-navigation/native").useNavigation
     Linking = require('react-native').Linking;
@@ -50,12 +51,13 @@ export default function IndexConsole(props: { record: any, count: number }) {
     const permission = useSelector((state: any) => state.permission);
     const common = useSelector((state: any) => state.common);
     const [firstEnter, setFirstEnter] = useState(true);
-    
+
     const dayMilliSeconds = 24 * 3600 * 1000;
     const [btnDisable, setBtnDisable] = useState(false)
     const [showStageModal, setShowStageModal] = useState(false)
     const [showTimePicker, setShowTimePicker] = useState(false);
     const [showMutiPicker, setShowMutiPicker] = useState(false);
+    const [mutiEvent, setMutiEvent] = useState('start_fast');
     const dispatch = useDispatch();
 
 
@@ -79,7 +81,7 @@ export default function IndexConsole(props: { record: any, count: number }) {
         if (process.env.TARO_ENV == 'rn') {
             // console.error('current status',status)
             var NativeAppEventEmitter = require('react-native').NativeAppEventEmitter;
-            if (nativePushListener){
+            if (nativePushListener) {
                 (nativePushListener as any).remove()
             }
             if (kIsIOS) {
@@ -88,14 +90,14 @@ export default function IndexConsole(props: { record: any, count: number }) {
             }
             nativePushListener = NativeAppEventEmitter.addListener('notificationReceive', (data) => {
                 console.log('notification receive action', data)
-                const { category_id, action_id,id } = data
+                const { category_id, action_id, id } = data
                 uploadLocalPushInfo({
-                    messageId:id
+                    messageId: id
                 })
                 switch (action_id) {
                     case 'START_TIMER_NOW':
                         {
-                            if (category_id == 'REMINDER_FS_START_FAST'){
+                            if (category_id == 'REMINDER_FS_START_FAST') {
                                 operateType = 'startFast'
                             }
                             else {
@@ -107,7 +109,7 @@ export default function IndexConsole(props: { record: any, count: number }) {
                         break;
                     case 'PICK_EARLIER_START':
                         {
-                            if (category_id == 'REMINDER_FS_START_FAST'){
+                            if (category_id == 'REMINDER_FS_START_FAST') {
                                 tapStartFast(null)
                             }
                             else {
@@ -117,7 +119,7 @@ export default function IndexConsole(props: { record: any, count: number }) {
                         break;
                     case 'END_TIMER_NOW':
                         {
-                            if (category_id == 'REMINDER_FS_END_FAST'){
+                            if (category_id == 'REMINDER_FS_END_FAST') {
                                 operateType = 'endFast'
                             }
                             else {
@@ -129,7 +131,7 @@ export default function IndexConsole(props: { record: any, count: number }) {
                         break;
                     case 'PICK_EARLIER_END':
                         {
-                            if (category_id == 'REMINDER_FS_END_FAST'){
+                            if (category_id == 'REMINDER_FS_END_FAST') {
                                 tapEndFast(null)
                             }
                             else {
@@ -199,6 +201,7 @@ export default function IndexConsole(props: { record: any, count: number }) {
             }
 
             vibrate()
+            setMutiEvent('start_sleep')
             setShowMutiPicker(true);
             return;
         }
@@ -256,6 +259,7 @@ export default function IndexConsole(props: { record: any, count: number }) {
             })
 
             vibrate()
+            setMutiEvent('end_sleep')
             setShowMutiPicker(true);
             return;
         }
@@ -307,11 +311,12 @@ export default function IndexConsole(props: { record: any, count: number }) {
                 icon: 'none'
             })
             vibrate()
+            setMutiEvent('end_fast')
             setShowMutiPicker(true);
             return;
         }
 
-        if (status == 'ONGOING1'){
+        if (status == 'ONGOING1') {
             // showAlert({
             //     title:t('feature.heads_up.alert_title'),
             //     content:t('feature.heads_up.ongoing1_content'),
@@ -319,36 +324,39 @@ export default function IndexConsole(props: { record: any, count: number }) {
             //     confirmText:t('feature.heads_up.ongoing1_confirm'),
             //     showCancel:true,
             //     cancel:()=>{
-                    
+
             //     },
             //     confirm:()=>{
             //         tapEndFastOperate()
             //     }
             // })
+            setMutiEvent('end_fast')
             setShowMutiPicker(true);
             return
         }
-        else if (status == 'ONGOING2'){
-            showAlert({
-                title:t('feature.heads_up.alert_title'),
-                content:t('feature.heads_up.ongoing2_content'),
-                cancelText:t('feature.heads_up.ongoing2_cancel'),
-                confirmText:t('feature.heads_up.ongoing2_confirm'),
-                showCancel:true,
-                cancel:()=>{
-                    
-                },
-                confirm:()=>{
-                    tapEndFastOperate()
-                }
-            })
+        else if (status == 'ONGOING2') {
+            setMutiEvent('end_fast')
+            setShowMutiPicker(true);
+            // showAlert({
+            //     title: t('feature.heads_up.alert_title'),
+            //     content: t('feature.heads_up.ongoing2_content'),
+            //     cancelText: t('feature.heads_up.ongoing2_cancel'),
+            //     confirmText: t('feature.heads_up.ongoing2_confirm'),
+            //     showCancel: true,
+            //     cancel: () => {
+
+            //     },
+            //     confirm: () => {
+            //         tapEndFastOperate()
+            //     }
+            // })
             return
         }
-        
+
         tapEndFastOperate()
     }
 
-    function tapEndFastOperate(){
+    function tapEndFastOperate() {
         operateType = 'endFast'
         global.pauseIndexTimer = true
         global.set_time = new Date().getTime()
@@ -583,9 +591,9 @@ export default function IndexConsole(props: { record: any, count: number }) {
                         }
                     }
                     else {
-                        PushNotification.checkPermissions((res)=>{
+                        PushNotification.checkPermissions((res) => {
                             //允许授权
-                            if ((kIsIOS && res.authorizationStatus == 2) || (!kIsIOS && res.alert)){
+                            if ((kIsIOS && res.authorizationStatus == 2) || (!kIsIOS && res.alert)) {
                                 getLocalPush()
                                 // showAlert({
                                 //     title: t('feature.track_time_duration.reminders.fast_end_title'),
@@ -655,9 +663,9 @@ export default function IndexConsole(props: { record: any, count: number }) {
                         }
                     }
                     else {
-                        PushNotification.checkPermissions((res)=>{
+                        PushNotification.checkPermissions((res) => {
                             //允许授权
-                            if ((kIsIOS && res.authorizationStatus == 2) || (!kIsIOS && res.alert)){
+                            if ((kIsIOS && res.authorizationStatus == 2) || (!kIsIOS && res.alert)) {
                                 getLocalPush()
                                 // showAlert({
                                 //     title: t('feature.track_time_duration.reminders.wake_title'),
@@ -712,7 +720,7 @@ export default function IndexConsole(props: { record: any, count: number }) {
 
                     }
                 }).catch((e) => {
-                    
+
                     setBtnDisable(false)
                     var picker = limitPickerRef.current;
                     (picker as any).resetPickerData()
@@ -741,7 +749,7 @@ export default function IndexConsole(props: { record: any, count: number }) {
                     global.checkAccess((res as any).access)
                     // checkAccessProvisional((res as any).access,showFastAlert)
                 }).catch((e) => {
-                    
+
                     setBtnDisable(false)
                     var picker = limitPickerRef.current;
                     (picker as any).resetPickerData()
@@ -786,7 +794,7 @@ export default function IndexConsole(props: { record: any, count: number }) {
         </Modal>
     }
 
-    function mutiContent(){
+    function mutiContent() {
         return <Modal
             testInfo={null}
             dismiss={() => {
@@ -799,10 +807,9 @@ export default function IndexConsole(props: { record: any, count: number }) {
         </Modal>
     }
 
-    function mutiPickerContent(){
-        return <View>
-            <Text style={{color:'#fff'}}>hell world</Text>
-        </View>
+    function mutiPickerContent() {
+        global.set_time = new Date().getTime()
+        return <IndexConsoleMuti status={status} event={mutiEvent} close={() => setShowMutiPicker(false)} />
     }
 
     function single() {
@@ -811,7 +818,7 @@ export default function IndexConsole(props: { record: any, count: number }) {
                 {
                     status == 'WAIT_FOR_START' &&
                     <View onClick={tapStartFast} className='console_btn'>
-                        <Text style={{ fontWeight: 'bold',color:ColorType.black }}>{t('feature.track_time_duration.common.start_fast')}</Text>
+                        <Text style={{ fontWeight: 'bold', color: ColorType.black }}>{t('feature.track_time_duration.common.start_fast')}</Text>
                     </View>
                 }
                 {/* {
@@ -819,7 +826,7 @@ export default function IndexConsole(props: { record: any, count: number }) {
                 } */}
                 {
                     status == 'ONGOING' && <View onClick={tapEndFast} className={status == 'ONGOING' ? 'console_btn' : 'console_btn btn_disable'}>
-                        <Text style={{ fontWeight: 'bold',color:ColorType.black }}>{t('feature.track_time_duration.common.end_fast')}</Text>
+                        <Text style={{ fontWeight: 'bold', color: ColorType.black }}>{t('feature.track_time_duration.common.end_fast')}</Text>
                     </View>
                 }
                 {
@@ -858,7 +865,7 @@ export default function IndexConsole(props: { record: any, count: number }) {
             {
                 status == 'WAIT_FOR_START' ?
                     <View onClick={tapStartFast} className='console_btn'>
-                        <Text style={{ fontWeight: 'bold', fontSize: rpxToPx(32),color:ColorType.black }}>{t('feature.track_time_duration.common.start_fast')}</Text>
+                        <Text style={{ fontWeight: 'bold', fontSize: rpxToPx(32), color: ColorType.black }}>{t('feature.track_time_duration.common.start_fast')}</Text>
                     </View> :
                     <View onClick={() => { tapStage(0) }} className='stage_btn'>
                         <Text style={{ flex: 1, color: '#fff' }}>{t('feature.track_time_duration.stage.a')}</Text>
@@ -877,7 +884,7 @@ export default function IndexConsole(props: { record: any, count: number }) {
                     {
                         status != 'ONGOING1' && <Image className='lock' src={require('@assets/images/lock.png')} />
                     }
-                    <Text style={{ fontWeight: 'bold', fontSize: rpxToPx(32),color:ColorType.black }}>{t('feature.track_time_duration.common.start_sleep')}</Text>
+                    <Text style={{ fontWeight: 'bold', fontSize: rpxToPx(32), color: ColorType.black }}>{t('feature.track_time_duration.common.start_sleep')}</Text>
                 </View>
             }
             {
@@ -899,7 +906,7 @@ export default function IndexConsole(props: { record: any, count: number }) {
                     {
                         status != 'ONGOING2' && <Image className='lock' src={require('@assets/images/lock.png')} />
                     }
-                    <Text style={{ fontWeight: 'bold', fontSize: rpxToPx(32),color:ColorType.black }}>{t('feature.track_time_duration.common.end_sleep')}</Text>
+                    <Text style={{ fontWeight: 'bold', fontSize: rpxToPx(32), color: ColorType.black }}>{t('feature.track_time_duration.common.end_sleep')}</Text>
                 </View>
             }
             {
@@ -916,7 +923,7 @@ export default function IndexConsole(props: { record: any, count: number }) {
                     {
                         status == 'WAIT_FOR_START' && <Image className='lock' src={require('@assets/images/lock.png')} />
                     }
-                    <Text style={{ fontWeight: 'bold', fontSize: rpxToPx(32),color:ColorType.black  }}>{t('feature.track_time_duration.common.end_fast')}</Text>
+                    <Text style={{ fontWeight: 'bold', fontSize: rpxToPx(32), color: ColorType.black }}>{t('feature.track_time_duration.common.end_fast')}</Text>
                 </View>
             }
             {

+ 19 - 0
src/features/trackTimeDuration/components/IndexConsoleMuti.scss

@@ -0,0 +1,19 @@
+.new_item_cell{
+    height: 96px;
+    display: flex;
+    flex-direction: row;
+    align-items: center;
+    margin-left: 40px;
+    margin-right: 40px;
+}
+
+.new_item_cell_title{
+    font-size: 28px;
+    color: #fff;
+}
+
+.new_item_cell_desc{
+    font-size: 28px;
+    color: #fff;
+    opacity: 0.4;
+}

+ 186 - 0
src/features/trackTimeDuration/components/IndexConsoleMuti.tsx

@@ -0,0 +1,186 @@
+import { View, Text, Image } from "@tarojs/components";
+import { useTranslation } from "react-i18next";
+import { AtActivityIndicator } from "taro-ui";
+import { alphaToHex, rpxToPx } from "@/utils/tools";
+import { ColorType } from "@/context/themes/color";
+import "@/components/layout/Modal.scss";
+import './IndexConsoleMuti.scss';
+import { useState } from "react";
+import { batchClocks, getLocalPush } from "../actions/TrackTimeActions";
+import dayjs from "dayjs";
+
+export default function IndexConsoleMuti(props: { status: string, event: string, close: Function }) {
+    const { t } = useTranslation();
+    const isLoading = false;
+    var color = ColorType.fast;
+    var alpha = alphaToHex(0.4)
+    const [fastStart, setFastStart] = useState<any>(0)
+    const [fastEnd, setFastEnd] = useState<any>(0)
+    const [sleepStart, setSleepStart] = useState<any>(0)
+    const [sleepEnd, setSleepEnd] = useState<any>(0)
+
+
+    function cancel() {
+        props.close()
+    }
+
+    function confirm() {
+        var fast: any = {}
+        var sleep: any = {}
+        switch (props.event) {
+            case 'start_sleep':
+                fast.real_start_time = new Date().getTime() - 100*1000
+                fast.real_start_date = dayjs().format('YYYYMMDD')
+                sleep.real_start_time = new Date().getTime() - 50
+                sleep.real_start_date = dayjs().format('YYYYMMDD')
+                break;
+            case 'end_sleep':
+                if (props.status == 'WAIT_FOR_START') {
+                    fast.real_start_time = new Date().getTime() - 100*1000
+                    fast.real_start_date = dayjs().format('YYYYMMDD')
+                }
+                sleep.real_start_time = new Date().getTime() - 50*1000
+                sleep.real_start_date = dayjs().format('YYYYMMDD')
+                sleep.real_end_time = new Date().getTime()
+                sleep.real_end_date = dayjs().format('YYYYMMDD')
+                break;
+            case 'end_fast':
+                if (props.status == 'WAIT_FOR_START') {
+                    fast.real_start_time = new Date().getTime() - 100*1000
+                    fast.real_start_date = dayjs().format('YYYYMMDD')
+
+                    sleep.real_start_time = new Date().getTime() - 50*1000
+                    sleep.real_start_date = dayjs().format('YYYYMMDD')
+
+                }
+                else if (props.status == 'ONGOING1') {
+                    sleep.real_start_time = new Date().getTime() - 50*1000
+                    sleep.real_start_date = dayjs().format('YYYYMMDD')
+                }
+                sleep.real_end_time = new Date().getTime() - 20*1000
+                sleep.real_end_date = dayjs().format('YYYYMMDD')
+                fast.real_end_time = new Date().getTime()
+                fast.real_end_date = dayjs().format('YYYYMMDD')
+                break;
+        }
+        batchClocks({
+            fast,
+            sleep
+        }).then(res => {
+            getLocalPush()
+            global.indexPageRefresh()
+            global.scrollToLatest()
+            global.refrehWeekly()
+            global.refreshStreaks()
+            global.checkAccess((res as any).access)
+
+            cancel()
+        }).catch(e => {
+
+        })
+    }
+
+    function startFastCell() {
+        return <View className="new_item_cell">
+            <Text className="new_item_cell_title">Start Fast</Text>
+            <View style={{ flex: 1 }} />
+            <Text className="new_item_cell_desc">Pick Time</Text>
+            <Image className="cell_arrow" src={require('@/assets/images/arrow3.png')} />
+        </View>
+    }
+
+    function startSleepCell() {
+        return <View className="new_item_cell">
+            <Text className="new_item_cell_title">Start Sleep</Text>
+            <View style={{ flex: 1 }} />
+            <Text className="new_item_cell_desc">Pick Time</Text>
+            <Image className="cell_arrow" src={require('@/assets/images/arrow3.png')} />
+        </View>
+    }
+
+    function endSleepCell() {
+        return <View className="new_item_cell">
+            <Text className="new_item_cell_title">End Sleep</Text>
+            <View style={{ flex: 1 }} />
+            <Text className="new_item_cell_desc">Pick Time</Text>
+            <Image className="cell_arrow" src={require('@/assets/images/arrow3.png')} />
+        </View>
+    }
+
+    function endFastCell() {
+        return <View className="new_item_cell">
+            <Text className="new_item_cell_title">End Fast</Text>
+            <View style={{ flex: 1 }} />
+            <Text className="new_item_cell_desc">Pick Time</Text>
+            <Image className="cell_arrow" src={require('@/assets/images/arrow3.png')} />
+        </View>
+    }
+
+    return <View className="modal_content">
+        <View style={{
+            marginLeft: rpxToPx(46),
+            height: rpxToPx(120), display: 'flex',
+            flexDirection: 'row', alignItems: 'center',
+            marginTop: rpxToPx(36),
+            marginBottom: rpxToPx(48)
+        }}>
+            <Text style={{ color: '#fff', fontWeight: 'bold', fontSize: rpxToPx(48) }}>Log your timings</Text>
+        </View>
+
+        <View style={{
+            display: 'flex',
+            flexDirection: 'column',
+            backgroundColor: '#262626',
+            borderRadius: rpxToPx(24),
+            marginLeft: rpxToPx(46),
+            marginRight: rpxToPx(46),
+            marginBottom: rpxToPx(60)
+
+        }}>
+            {
+                props.event == 'start_sleep' && startFastCell()
+            }
+            {
+                props.event == 'start_sleep' && startSleepCell()
+            }
+            {
+                props.event == 'end_sleep' && props.status == 'WAIT_FOR_START' && startFastCell()
+            }
+            {
+                props.event == 'end_sleep' && startSleepCell()
+            }
+            {
+                props.event == 'end_sleep' && endSleepCell()
+            }
+            {
+                props.event == 'end_fast' && props.status == 'WAIT_FOR_START' && startFastCell()
+            }
+            {
+                props.event == 'end_fast' && (props.status == 'ONGOING1' || props.status == 'WAIT_FOR_START') && startSleepCell()
+            }
+            {
+                props.event == 'end_fast' && (props.status == 'ONGOING1' || props.status == 'ONGOING2' || props.status == 'WAIT_FOR_START') && endSleepCell()
+            }
+            {
+                props.event == 'end_fast' && endFastCell()
+            }
+        </View>
+
+        <View className='modal_operate'>
+
+            <View className='modal_btn' style={{ backgroundColor: color + alpha }} onClick={cancel}>
+                <Text className='modal_cancel_text' style={{ color: color, fontWeight: 'bold' }}>{t('feature.common.picker_cancel_btn')}</Text>
+            </View>
+            <View className='btn_space' />
+            <View className='modal_btn' style={{ backgroundColor: color, flexDirection: 'row', alignItems: 'center', justifyContent: 'center', opacity: isLoading ? 0.6 : 1 }} onClick={confirm}>
+                {
+                    isLoading && process.env.TARO_ENV == 'rn' && <View style={{ display: 'flex', overflow: 'hidden', height: 20, marginRight: 5 }}><AtActivityIndicator mode="center" color="#000" /></View>
+                }
+
+                <Text className='modal_confirm_text' style={{ color: '#000', fontWeight: 'bold' }}>{t('feature.common.picker_confirm_btn')}</Text>
+            </View>
+
+
+        </View>
+    </View>
+}

+ 1 - 0
src/services/http/api.js

@@ -40,6 +40,7 @@ export const API_SYSTEM_VERSION = `${baseUrl}/api/system/version/fast/`
 export const API_FAST_PLANS = `${baseUrl}/api/fast/plans`
 export const API_FAST_CHECKS = `${baseUrl}/api/fast/checks`
 export const API_FAST_CLOCKS = `${baseUrl}/api/fast/clocks`
+export const API_MIX_CLOCKS = `${baseUrl}/api/fast/batch-clocks`
 export const API_CLOCK_HOME = `${baseUrl}/api/clock/home`
 export const API_CLOCK_STATS = `${baseUrl}/api/clock/summary/stats`
 export const API_FAST_CHECK_ABANDONED = `${baseUrl}/api/fast/check-abandoned`