Leon 2 rokov pred
rodič
commit
f2b240aefe

+ 8 - 0
src/features/trackTimeDuration/components/IndexItem.tsx

@@ -35,6 +35,14 @@ export default function Component(props: { type: string, data: any, time: any })
 
         if (props.type == 'SLEEP') {
             var realRing = getReal(record, false, true)
+            var currentDot1 = getDot(record, true)
+            var targetBigRing1 = getTarget(record, true)
+            if (record.status == 'ONGOING') {
+                var realRing1 = getReal(record, true, false)
+
+                return <Rings common={common} bgRing={bgRing} currentDot={currentDot1} realRing={realRing1} targetRing={targetBigRing1} canvasId={props.type + props.time + 'big'} />
+            }
+            
             if (record.status == 'WAIT_FOR_START' || record.status == 'ONGOING1') {
                 var realRing1 = getSchedule(record, props.type != 'SLEEP', true)
                 return <Rings common={common} bgRing={bgRing} realRing={realRing1} canvasId={props.type + props.time + 'big'} />

+ 56 - 0
src/features/trackTimeDuration/components/Rings.rn.tsx

@@ -17,6 +17,7 @@ export type CurrentDot = {
     color: string;
     lineWidth: number;
     borderColor: string;
+    timestamp?: number;
 }
 
 export type RealRing = {
@@ -42,6 +43,8 @@ export default function Component(props: {
     bgRing: BgRing; canvasId?: string;
     ctx?: any; setCtx?: any;
     canvas?: any; setCanvas?: any;
+    dotList?: Array<CurrentDot>;
+    stageList?: Array<RealRing>;
 }) {
     const r = props.common.radius
     const strokeWidth = props.common.lineWidth;
@@ -127,6 +130,22 @@ export default function Component(props: {
                     strokeLinecap="round"
                 />
             }
+            {
+                props.stageList && props.stageList.map((item) => {
+                    return <Circle
+                        cx={center}
+                        cy={center}
+                        r={radius}
+                        fillOpacity={0}
+                        stroke={item.color}
+                        transform={`rotate(${item.startArc / (2 * Math.PI) * 360} ${center} ${center})`}
+                        strokeDasharray={`${item.durationArc * radius},1000`}
+                        strokeWidth={lineWidth}
+                        strokeLinecap="round"
+                    />
+
+                })
+            }
             {
                 props.currentDot && <Circle
                     cx={center}
@@ -140,6 +159,7 @@ export default function Component(props: {
                     strokeLinecap="round"
                 />
             }
+            
             {
                 props.currentDot && <Circle
                     cx={center}
@@ -153,6 +173,42 @@ export default function Component(props: {
                     strokeLinecap="round"
                 />
             }
+            {
+                props.dotList && props.dotList.map(item => {
+                    var time1 = item.timestamp ? new Date(item.timestamp) : new Date();
+                    var seconds1 = time1.getHours() * 3600 + time1.getMinutes() * 60 + time1.getSeconds();
+                    var arc1 = seconds1 / 86400 * 2 * Math.PI - Math.PI / 2.0;
+                    return <Circle
+                        cx={center}
+                        cy={center}
+                        r={radius}
+                        fillOpacity={0}
+                        stroke={item.borderColor}
+                        transform={`rotate(${arc1 / (2 * Math.PI) * 360} ${center} ${center})`}
+                        strokeDasharray={`0,1000`}
+                        strokeWidth={lineWidth + 6}
+                        strokeLinecap="round"
+                    />
+                })
+            }
+            {
+                props.dotList && props.dotList.map(item => {
+                    var time1 = item.timestamp ? new Date(item.timestamp) : new Date();
+                    var seconds1 = time1.getHours() * 3600 + time1.getMinutes() * 60 + time1.getSeconds();
+                    var arc1 = seconds1 / 86400 * 2 * Math.PI - Math.PI / 2.0;
+                    return <Circle
+                        cx={center}
+                        cy={center}
+                        r={radius}
+                        fillOpacity={0}
+                        stroke={item.color}
+                        transform={`rotate(${arc1 / (2 * Math.PI) * 360} ${center} ${center})`}
+                        strokeDasharray={`0,1000`}
+                        strokeWidth={lineWidth}
+                        strokeLinecap="round"
+                    />
+                })
+            }
         </Svg>
     }
 

+ 53 - 5
src/features/trackTimeDuration/components/Rings.weapp.tsx

@@ -16,6 +16,7 @@ export type CurrentDot = {
     color: string;
     lineWidth: number;
     borderColor: string;
+    timestamp?:number;
 }
 
 export type RealRing = {
@@ -35,12 +36,19 @@ export type BgRing = {
 }
 
 export default function Rings(props: {
-    common: RingCommon; currentDot?: CurrentDot;
-    realRing?: RealRing; targetRing?: TargetRing; 
+    common: RingCommon; 
+    currentDot?: CurrentDot;
+    realRing?: RealRing; 
+    targetRing?: TargetRing; 
     breathAnimation?:boolean;
-    bgRing: BgRing; canvasId?: string;
-    ctx?:any;setCtx?:any;
-    canvas?:any;setCanvas?:any;
+    bgRing: BgRing; 
+    canvasId?: string;
+    ctx?:any;
+    setCtx?:any;
+    canvas?:any;
+    setCanvas?:any;
+    dotList?:Array<CurrentDot>;
+    stageList?:Array<RealRing>;
 }) {
     const r = props.common.radius
     const strokeWidth = props.common.lineWidth;
@@ -179,6 +187,19 @@ export default function Rings(props: {
             ctx.lineCap = 'round'; // 设置为圆角
             ctx.stroke();
         }
+
+        if (props.stageList){
+            props.stageList.map(item=>{
+                if (item.durationArc <0.01) item.durationArc=0.01;
+            ctx.beginPath();
+            ctx.arc(center, center, radius, item.startArc,
+                item.startArc + item.durationArc);
+            ctx.lineWidth = lineWidth;
+            ctx.strokeStyle = item.color;
+            ctx.lineCap = 'round'; // 设置为圆角
+            ctx.stroke();
+            })
+        }
         //绘制current_dot点
         if (props.currentDot) {
             var time = new Date();
@@ -203,6 +224,33 @@ export default function Rings(props: {
             ctx.stroke();
             ctx.restore()
         }
+
+
+        if (props.dotList){
+            props.dotList.map(item=>{
+                var time = item.timestamp?new Date(item.timestamp):new Date();
+                var seconds = time.getHours() * 3600 + time.getMinutes() * 60 + time.getSeconds();
+                var arc = seconds / 86400 * 2 * Math.PI - Math.PI / 2.0;
+                ctx.beginPath();
+                ctx.arc(center, center, radius, arc,
+                    arc + 0.001);
+                ctx.lineWidth = lineWidth+6;
+                ctx.strokeStyle = item.borderColor;
+                ctx.lineCap = 'round'; // 设置为圆角
+                ctx.stroke();
+                
+                ctx.save()
+                ctx.beginPath();
+                ctx.arc(center, center, radius, arc,
+                    arc + 0.001);
+                ctx.lineWidth = lineWidth;
+                ctx.strokeStyle = item.color;
+                ctx.lineCap = 'round'; // 设置为圆角
+                // ctx.globalAlpha = global.breathAlpha
+                ctx.stroke();
+                ctx.restore()
+            })
+        }
     }
 
     return <Canvas canvasId={canvasId}  id={canvasId} className={canvasId} type="2d" style={{ width: (radius * 2 + lineWidth)+6, height: (radius * 2 + lineWidth)+6, zIndex: 0 }} ref={canvasRef} />

+ 168 - 58
src/pages/clock/Index.tsx

@@ -1,7 +1,7 @@
-import { View, Text, Image } from "@tarojs/components";
+import { View, Text, Image, ScrollView } from "@tarojs/components";
 import Tabbar from "@/components/navigation/TabBar";
 import IndexItem from '@/features/trackTimeDuration/components/IndexItem';
-
+import Rings from "@/features/trackTimeDuration/components/Rings";
 import './Index.scss'
 import { useDispatch, useSelector } from "react-redux";
 import { useReady } from "@tarojs/taro";
@@ -14,6 +14,8 @@ import { setScenario } from "@/store/scenario";
 import { useEffect, useState } from "react";
 import { IconPlus, IconRadioCheck, IconRadioCross } from "@/components/basic/Icons";
 import { ColorType } from "@/context/themes/color";
+import { getBgRing, getCommon, getDot, getSchedule } from "@/features/trackTimeDuration/hooks/RingData";
+import { RealRing, CurrentDot } from "@/features/trackTimeDuration/components/Rings";
 
 export default function Page() {
     const dispatch = useDispatch();
@@ -50,7 +52,7 @@ export default function Page() {
 
     useEffect(() => {
         // if (user.isLogin) {
-            getCheckData()
+        getCheckData()
         // }
     }, [user.isLogin, time.status])
 
@@ -69,24 +71,118 @@ export default function Page() {
     })
 
     function getCheckData() {
-        getClocks().then(res => {
-            // setErrorPage(false)
-            // setData(res as any)
-            // dispatch(updateScenario((res as any).current_record))
-            // dispatch(setConfigs((res as any).time_input_schema));
-            // dispatch(setScenario((res as any).scenario));
-
-            if ((res as any).theme_color) {
-                global.fastColor = (res as any).theme_color.fast
-                global.sleepColor = (res as any).theme_color.sleep
-            }
-        })
+        // getClocks().then(res => {
+        //     // setErrorPage(false)
+        //     // setData(res as any)
+        //     // dispatch(updateScenario((res as any).current_record))
+        //     // dispatch(setConfigs((res as any).time_input_schema));
+        //     // dispatch(setScenario((res as any).scenario));
+
+        //     if ((res as any).theme_color) {
+        //         global.fastColor = (res as any).theme_color.fast
+        //         global.sleepColor = (res as any).theme_color.sleep
+        //     }
+        // })
 
         clockHome().then(res => {
             setHomeData(res as any)
         })
     }
 
+    const startArc = (time: number) => {
+        var date = new Date(time);
+        var hour = date.getHours();
+        var minute = date.getMinutes();
+        var second = date.getSeconds();
+        return (hour * 3600 + minute * 60 + second) / (24 * 3600) * 2 * Math.PI - Math.PI / 2.0;
+    }
+
+    const durationArc = (start_time: number, end_time: number) => {
+        var duration = (end_time - start_time) / 1000;
+        return duration / (24 * 3600) * 2 * Math.PI;
+    }
+
+    function bigRing() {
+        var currentRecord = (homeData as any).fast_sleep.current_record
+
+        var common = getCommon(null, true)
+        common.radius = 42;
+        common.lineWidth = 9;
+        var bgRing = getBgRing()
+        var realRing1 = getSchedule(currentRecord, true, true)
+        realRing1.color = ColorType.fast + '66'
+
+        var list: any = []
+        if (multiData[0].checked) {
+
+            const realRingBig: RealRing = {
+                color: global.fastColor ? global.fastColor : ColorType.fast,
+                startArc: startArc(currentRecord.fast.target_start_time),
+                durationArc: durationArc(currentRecord.fast.target_start_time, currentRecord.sleep.target_start_time)
+            }
+
+            list.push(realRingBig)
+        }
+        if (multiData[1].checked) {
+            const realRingBig: RealRing = {
+                color: global.fastColor ? global.fastColor : ColorType.fast,
+                startArc: startArc(currentRecord.sleep.target_start_time),
+                durationArc: durationArc(currentRecord.sleep.target_start_time, currentRecord.sleep.target_end_time)
+            }
+
+            list.push(realRingBig)
+        }
+        if (multiData[2].checked) {
+            const realRingBig: RealRing = {
+                color: global.fastColor ? global.fastColor : ColorType.fast,
+                startArc: startArc(currentRecord.sleep.target_end_time),
+                durationArc: durationArc(currentRecord.sleep.target_end_time, currentRecord.fast.target_end_time)
+            }
+
+            list.push(realRingBig)
+        }
+
+        var points: any = []
+        for (var i = 0; i < 12; i++) {
+            var dot: CurrentDot = {
+                color: 'red',
+                lineWidth: 8,
+                borderColor: 'black',
+                timestamp: new Date().getTime() + i * 3600 * 1000 * 2
+            }
+            points.push(dot)
+        }
+        return <Rings common={common} bgRing={bgRing} realRing={realRing1} stageList={list} dotList={points} canvasId={'testA'} />
+
+    }
+
+    function smallRing() {
+        var common = getCommon(null, true)
+        common.radius = 28;
+        common.lineWidth = 9;
+        var bgRing = getBgRing()
+        var realRing1 = getSchedule((homeData as any).fast_sleep.current_record, false, false)
+        return <Rings common={common} bgRing={bgRing} realRing={realRing1} canvasId={'testB'} />
+    }
+
+    function rings() {
+        return <View style={{ display: 'flex', flexDirection: 'row', marginLeft: 100, marginBottom: 30 }}>
+            <View style={{ position: 'relative', zIndex: 1 }}>
+                {
+                    bigRing()
+                }
+                {
+                    <View style={{ display: 'flex', position: 'absolute', left: 0, right: 0, top: 0, bottom: 0, alignItems: 'center', justifyContent: 'center' }}>
+                        {
+                            smallRing()
+                        }
+                    </View>
+                }
+
+            </View>
+        </View>
+    }
+
     async function getStorage(key: string) {
         try {
             const res = await Taro.getStorage({ key });
@@ -102,57 +198,71 @@ export default function Page() {
     }
 
     var timestamp = new Date().getTime()
-    return <View className="index_container">
-        <Text className="count">{count}</Text>
-        <IndexItem type="FAST" data={(homeData as any).fast} time={timestamp} />
-        <IndexItem type='SLEEP' data={(homeData as any).sleep} time={timestamp} />
-        <Text className="discovery">探索</Text>
-        <IndexItem type="FAST_SLEEP" data={(homeData as any).fast_sleep} time={timestamp} />
-        <Tabbar index={0} />
-
-        <View>
-            <Text>Single Sel</Text>
-            <View className={selIndex == 0 ? "single_check_sel" : "single_check_nor"} onClick={() => setSelIndex(0)}>
-                <Text className={selIndex == 0 ? "single_check_text_sel" : "single_check_text_nor"}>睡前断食</Text>
-                {
-                    selIndex == 0 ? <Image src={require('@assets/images/check_black.png')} className="single_checked" /> :
-                        <IconPlus color={ColorType.fast} />
-                }
+
+    function render() {
+        return <View className="index_container">
+            <Text className="count">{count}</Text>
+            <IndexItem type="FAST" data={(homeData as any).fast} time={timestamp} />
+            <IndexItem type='SLEEP' data={(homeData as any).sleep} time={timestamp} />
+            <Text className="discovery">探索</Text>
+            <IndexItem type="FAST_SLEEP" data={(homeData as any).fast_sleep} time={timestamp} />
+
+
+            <View>
+                <Text>Single Sel</Text>
+
+                <View className={selIndex == 0 ? "single_check_sel" : "single_check_nor"} onClick={() => setSelIndex(0)}>
+                    <Text className={selIndex == 0 ? "single_check_text_sel" : "single_check_text_nor"}>睡前断食</Text>
+                    {
+                        selIndex == 0 && <Image src={require('@assets/images/check_black.png')} className="single_checked" />
+                    }
+                </View>
+                <View className={selIndex == 1 ? "single_check_sel" : "single_check_nor"} onClick={() => setSelIndex(1)}>
+                    <Text className={selIndex == 1 ? "single_check_text_sel" : "single_check_text_nor"}>睡眠中断食</Text>
+                    {
+                        selIndex == 1 && <Image src={require('@assets/images/check_black.png')} className="single_checked" />
+                    }
+                </View>
+                <View className={selIndex == 2 ? "single_check_sel" : "single_check_nor"} onClick={() => setSelIndex(2)}>
+                    <Text className={selIndex == 2 ? "single_check_text_sel" : "single_check_text_nor"}>起床后断食</Text>
+                    {
+                        selIndex == 2 && <Image src={require('@assets/images/check_black.png')} className="single_checked" />
+                    }
+                </View>
             </View>
-            <View className={selIndex == 1 ? "single_check_sel" : "single_check_nor"} onClick={() => setSelIndex(1)}>
-                <Text className={selIndex == 1 ? "single_check_text_sel" : "single_check_text_nor"}>睡眠中断食</Text>
+
+            <View style={{ marginTop: 50 }}>
+                <Text>Multi Sel</Text>
                 {
-                    selIndex == 1 ? <Image src={require('@assets/images/check_black.png')} className="single_checked" /> :
-                        <IconPlus color={ColorType.fast} />
+                    rings()
                 }
-            </View>
-            <View className={selIndex == 2 ? "single_check_sel" : "single_check_nor"} onClick={() => setSelIndex(2)}>
-                <Text className={selIndex == 2 ? "single_check_text_sel" : "single_check_text_nor"}>起床后断食</Text>
                 {
-                    selIndex == 2 ? <Image src={require('@assets/images/check_black.png')} className="single_checked" /> :
-                        <IconPlus color={ColorType.fast} />
+                    multiData.map((item) => {
+                        return <View className={item.checked ? "single_check_sel" : "single_check_nor"} onClick={() => {
+                            item.checked = !item.checked
+                            setMultiData(JSON.parse(JSON.stringify(multiData)))
+                        }}>
+                            <Text className={item.checked ? "single_check_text_sel" : "single_check_text_nor"}>{item.title}</Text>
+                            {
+                                item.checked ? <Image src={require('@assets/images/check_black.png')} className="single_checked" /> :
+                                    <IconPlus color={ColorType.fast} />
+                            }
+                        </View>
+                    })
                 }
             </View>
+
+            <View style={{ height: 100 }} />
+            <Tabbar index={0} />
         </View>
+    }
 
-        <View style={{ marginTop: 50 }}>
-            <Text>Multi Sel</Text>
+    if (process.env.TARO_ENV=='rn'){
+        return <ScrollView>
             {
-                multiData.map((item) => {
-                    return <View className={item.checked ? "single_check_sel" : "single_check_nor"} onClick={() => {
-                        item.checked = !item.checked
-                        setMultiData(JSON.parse(JSON.stringify(multiData)))
-                    }}>
-                        <Text className={item.checked ? "single_check_text_sel" : "single_check_text_nor"}>{item.title}</Text>
-                        {
-                            item.checked ? <Image src={require('@assets/images/check_black.png')} className="single_checked" /> :
-                                <IconPlus color={ColorType.fast} />
-                        }
-                    </View>
-                })
+                render()
             }
-        </View>
-
-        <View style={{ height: 100 }} />
-    </View>
+        </ScrollView>
+    }
+    return render()
 }

+ 3 - 1
src/pages/rn/RNMain.tsx

@@ -4,6 +4,7 @@ import { createBottomTabNavigator } from '@react-navigation/bottom-tabs';
 import { createStackNavigator } from '@react-navigation/stack';
 
 import Clock from '../clock/Clock'
+import Index from '../clock/Index'
 import Metric from '../metric/Metric'
 import Workout from '../workout/Workout'
 import Profile from '../account/Profile'
@@ -62,7 +63,7 @@ const App: React.FC = () => {
 */
 
 export default function RNMain() {
-  const ClockPage = () => <Clock />
+  const ClockPage = () => <Index />
   const MetricPage = () => <Metric />
   const WorkoutPage = () => <Workout />
   const ProfilePage = () => <Profile />
@@ -167,6 +168,7 @@ export default function RNMain() {
         <Stack.Screen name='Main' component={tabNavigator} options={{ headerShown: false }} />
         <Stack.Screen name='ChooseAuth' component={ChooseAuth} />
         <Stack.Screen name='Auth' component={Auth} />
+        <Stack.Screen name='Clock' component={Clock} />
         <Stack.Screen name='Setting' component={Setting} />
         <Stack.Screen name='ChooseScenario' component={ChooseScenario} />
         <Stack.Screen name='RecordsHistory' component={RecordsHistory} options={{