Skip to content

Commit

Permalink
Merge branch 'reanimate'
Browse files Browse the repository at this point in the history
  • Loading branch information
obov committed Jan 25, 2023
2 parents edcdae1 + 6ced870 commit 0cb8a2e
Show file tree
Hide file tree
Showing 6 changed files with 488 additions and 180 deletions.
5 changes: 3 additions & 2 deletions babel.config.js
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
module.exports = function(api) {
module.exports = function (api) {
api.cache(true);
return {
presets: ['babel-preset-expo']
presets: ["babel-preset-expo"],
plugins: ["react-native-reanimated/plugin"],
};
};
206 changes: 162 additions & 44 deletions components/Calendar.js
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,7 @@ import {
FlatList,
} from "react-native";
import { Dimensions } from "react-native";
import { useState } from "react";
import { useState, useEffect } from "react";
import { Ionicons } from "@expo/vector-icons";
import {
changeMonth,
Expand All @@ -19,20 +19,118 @@ import {
isSameMonth,
} from "../utils";
import { saturday, sunday, workDays } from "../libs";
const CalendarComponent = ({ chidren }) => {
const [dateViewed, setDateViewed] = useState(new Date());
const [dateSelected, setDateSelected] = useState(null);
import { Gesture, GestureDetector } from "react-native-gesture-handler";
import Animated, {
useSharedValue,
useAnimatedStyle,
withTiming,
runOnJS,
withDelay,
} from "react-native-reanimated";

const CalendarBody = ({ dateSelected, setDateSelected, dateViewed }) => {
const handlePressDate = (date) => () => {
setDateSelected(date);
};
const fistDate = getPrevSun(getFirstDate(dateViewed));
const lastDate = getNextSatur(getLastDate(dateViewed));
return (
<FlatList
keyExtractor={(item) => item.getTime()}
scrollEnabled={false}
data={getDaysRange(fistDate, lastDate)}
style={styles.body}
ItemSeparatorComponent={() => <View style={{ height: 10, width: 10 }} />}
columnWrapperStyle={{
justifyContent: "space-between",
}}
renderItem={({ item }) => (
<TouchableOpacity style={styles.date} onPress={handlePressDate(item)}>
<View
style={
dateSelected
? isSameDate(item, dateSelected)
? styles.selected
: styles.null
: styles.null
}
>
<Text
style={
isSameMonth(item, dateViewed)
? styles.dateInMonth
: styles.dateOutMonth
}
>
{item.getDate()}
</Text>
</View>
</TouchableOpacity>
)}
numColumns={7}
/>
);
};
const CalendarComponent = () => {
const [dateViewed, setDateViewed] = useState(new Date());
const [dateSelected, setDateSelected] = useState(null);
const dateViewedChangeMonth = changeMonth(dateViewed);
const changeMonthOnJS = (val) => {
setDateViewed((cur) => changeMonth(cur)(val));
};
const INIT_HEIGHT = 300;
const END_POSITION_Y = INIT_HEIGHT - 50;
const END_POSITION_X = Dimensions.get("window").width;
const isWeeklyView = useSharedValue(false);
const positionY = useSharedValue(0);
const positionX = useSharedValue(0);
const panGesture = Gesture.Pan()
.onUpdate((e) => {
if (isWeeklyView.value) {
positionY.value =
END_POSITION_Y - e.translationY > INIT_HEIGHT
? INIT_HEIGHT
: END_POSITION_Y - e.translationY;
} else {
positionY.value = -e.translationY;
}

positionX.value = e.translationX;
})
.onTouchesUp((e) => {
if (positionY.value > END_POSITION_Y / 2) {
positionY.value = withTiming(END_POSITION_Y, { duration: 100 });
isWeeklyView.value = true;
} else {
positionY.value = withTiming(0, { duration: 100 });
isWeeklyView.value = false;
}
if (Math.abs(positionX.value) > END_POSITION_X / 2) {
positionX.value = withTiming(
Math.sign(positionX.value) * END_POSITION_X,
{ duration: 500 },
() => {
runOnJS(changeMonthOnJS)(Math.sign(positionX.value) * -1);
}
);
} else {
positionX.value = withTiming(0, { duration: 500 });
}
});
const animatedStyle = useAnimatedStyle(() => ({
height: INIT_HEIGHT - positionY.value,
transform: [{ translateX: positionX.value }],
}));

const handlePressLeft = () => {
setDateViewed((cur) => changeMonth(cur)(-1));
};
const handlePressRight = () => {
setDateViewed((cur) => changeMonth(cur)(+1));
};
const handlePressDate = (date) => () => {
setDateSelected(date);
};
useEffect(() => {
positionX.value = 0;
}, [dateViewed]);
return (
<>
<View style={styles.header}>
Expand All @@ -54,50 +152,69 @@ const CalendarComponent = ({ chidren }) => {
<Text style={styles.sun}>{sunday[0]}</Text>
</View>
{workDays.map((day) => (
<View style={styles.day}>
<View key={day} style={styles.day}>
<Text>{day}</Text>
</View>
))}
<View style={styles.day}>
<Text style={styles.sat}>{saturday[0]}</Text>
</View>
</View>
<View style={{ height: 400 }}>
<FlatList
keyExtractor={(item) => item.getTime()}
data={getDaysRange(fistDate, lastDate)}
style={styles.body}
ItemSeparatorComponent={() => (
<View style={{ height: 10, width: 10 }} />
)}
columnWrapperStyle={{
justifyContent: "space-between",
}}
renderItem={({ item }) => (
<TouchableOpacity
style={styles.date}
onPress={handlePressDate(item)}
<GestureDetector gesture={panGesture}>
<View style={{ flex: 1 }}>
<Animated.View
style={[
{
overflow: "hidden",
display: "flex",
flexDirection: "row",
width: Dimensions.get("window").width * 3,
},
animatedStyle,
]}
>
<View
style={{
width: Dimensions.get("window").width,
height: 300,
backgroundColor: "#555555",
}}
>
<View
style={
dateSelected
? isSameDate(item, dateSelected)
? styles.selected
: styles.null
: styles.null
}
>
{isSameMonth(item, dateViewed) ? (
<Text style={styles.dateInMonth}>{item.getDate()}</Text>
) : (
<Text style={styles.dateOutMonth}>{item.getDate()}</Text>
)}
</View>
</TouchableOpacity>
)}
numColumns={7}
/>
</View>
<CalendarBody
dateSelected={dateSelected}
setDateSelected={setDateSelected}
dateViewed={dateViewedChangeMonth(-1)}
/>
</View>
<View
style={{
width: Dimensions.get("window").width,
height: 300,
backgroundColor: "#777777",
}}
>
<CalendarBody
dateSelected={dateSelected}
setDateSelected={setDateSelected}
dateViewed={dateViewed}
/>
</View>
<View
style={{
width: Dimensions.get("window").width,
height: 300,
backgroundColor: "#111111",
}}
>
<CalendarBody
dateSelected={dateSelected}
setDateSelected={setDateSelected}
dateViewed={dateViewedChangeMonth(1)}
/>
</View>
</Animated.View>
</View>
</GestureDetector>
</>
);
};
Expand Down Expand Up @@ -159,7 +276,8 @@ const styles = StyleSheet.create({
width: Dimensions.get("window").width,
height: 300,
paddingHorizontal: 10,
paddingTop: 20,
paddingTop: 5,
backgroundColor: "#eeeeee",
},
arrow: {
width: 30,
Expand Down

0 comments on commit 0cb8a2e

Please sign in to comment.