2021-03-29 09:11:33 +00:00
|
|
|
import { useNavigation } from '@react-navigation/native'
|
|
|
|
import { StackNavigationProp } from '@react-navigation/stack'
|
2021-02-07 16:14:45 +00:00
|
|
|
import {
|
|
|
|
useCalendar,
|
2021-04-03 07:36:26 +00:00
|
|
|
useMenu,
|
2021-02-15 12:33:47 +00:00
|
|
|
useNews,
|
|
|
|
useNotifications,
|
2021-02-07 16:14:45 +00:00
|
|
|
useSchedule,
|
|
|
|
} from '@skolplattformen/api-hooks'
|
2021-03-26 08:38:15 +00:00
|
|
|
import { Child } from '@skolplattformen/embedded-api'
|
2021-02-20 08:38:08 +00:00
|
|
|
import { Avatar, Button, Card, Text } from '@ui-kitten/components'
|
2021-02-15 12:33:47 +00:00
|
|
|
import moment from 'moment'
|
2021-02-20 08:38:08 +00:00
|
|
|
import React from 'react'
|
2021-03-26 09:44:46 +00:00
|
|
|
import { StyleSheet, View } from 'react-native'
|
2021-03-31 08:16:41 +00:00
|
|
|
import { Colors, Layout, Sizing } from '../styles'
|
2021-02-19 14:30:48 +00:00
|
|
|
import { studentName } from '../utils/peopleHelpers'
|
2021-04-13 15:03:14 +00:00
|
|
|
import { translate } from '../utils/translation'
|
2021-02-20 08:38:08 +00:00
|
|
|
import {
|
|
|
|
CalendarOutlineIcon,
|
2021-04-03 07:36:26 +00:00
|
|
|
MenuIcon,
|
2021-02-20 08:38:08 +00:00
|
|
|
NewsIcon,
|
|
|
|
NotificationsIcon,
|
|
|
|
} from './icon.component'
|
2021-03-26 08:38:15 +00:00
|
|
|
import { RootStackParamList } from './navigation.component'
|
2021-01-04 21:40:54 +00:00
|
|
|
|
2021-03-26 08:38:15 +00:00
|
|
|
interface ChildListItemProps {
|
|
|
|
child: Child
|
|
|
|
color: string
|
|
|
|
}
|
|
|
|
|
2021-03-29 09:11:33 +00:00
|
|
|
type ChildListItemNavigationProp = StackNavigationProp<
|
|
|
|
RootStackParamList,
|
|
|
|
'Children'
|
|
|
|
>
|
|
|
|
|
|
|
|
export const ChildListItem = ({ child, color }: ChildListItemProps) => {
|
2021-02-14 20:06:23 +00:00
|
|
|
// Forces rerender when child.id changes
|
2021-02-20 08:38:08 +00:00
|
|
|
React.useEffect(() => {}, [child.id])
|
2021-02-14 20:06:23 +00:00
|
|
|
|
2021-03-29 09:11:33 +00:00
|
|
|
const navigation = useNavigation<ChildListItemNavigationProp>()
|
2021-02-11 08:20:41 +00:00
|
|
|
const { data: notifications, status: notificationsStatus } = useNotifications(
|
2021-02-15 12:33:47 +00:00
|
|
|
child
|
2021-02-07 16:14:45 +00:00
|
|
|
)
|
2021-02-11 08:20:41 +00:00
|
|
|
const { data: news, status: newsStatus } = useNews(child)
|
|
|
|
const { data: calendar, status: calendarStatus } = useCalendar(child)
|
2021-02-15 12:33:47 +00:00
|
|
|
const { data: schedule } = useSchedule(
|
2021-02-07 16:14:45 +00:00
|
|
|
child,
|
2021-03-30 18:54:28 +00:00
|
|
|
moment().toISOString(),
|
|
|
|
moment().add(7, 'days').toISOString()
|
2021-02-07 16:14:45 +00:00
|
|
|
)
|
2021-04-03 07:36:26 +00:00
|
|
|
const { status: menuStatus } = useMenu(child)
|
2021-01-04 21:40:54 +00:00
|
|
|
|
2021-04-02 08:50:03 +00:00
|
|
|
const notificationsThisWeek = notifications.filter(({ dateCreated }) =>
|
2021-04-01 11:41:36 +00:00
|
|
|
dateCreated ? moment(dateCreated).isSame(moment(), 'week') : false
|
2021-04-02 08:50:03 +00:00
|
|
|
)
|
|
|
|
|
|
|
|
const newsThisWeek = news.filter(({ published }) =>
|
|
|
|
published ? moment(published).isSame(moment(), 'week') : false
|
|
|
|
)
|
2021-02-19 14:29:41 +00:00
|
|
|
|
|
|
|
const scheduleAndCalendarThisWeek = [
|
|
|
|
...(calendar ?? []),
|
|
|
|
...(schedule ?? []),
|
2021-04-01 11:41:36 +00:00
|
|
|
].filter(({ startDate }) =>
|
2021-04-02 08:50:03 +00:00
|
|
|
startDate
|
|
|
|
? moment(startDate).isBetween(
|
|
|
|
moment().startOf('day'),
|
|
|
|
moment().add(7, 'days')
|
|
|
|
)
|
|
|
|
: false
|
2021-04-01 11:41:36 +00:00
|
|
|
)
|
2021-02-19 14:29:41 +00:00
|
|
|
|
2021-04-02 08:50:03 +00:00
|
|
|
const displayDate = (date: moment.MomentInput) => {
|
|
|
|
return moment(date).fromNow()
|
|
|
|
}
|
|
|
|
|
2021-04-20 10:51:38 +00:00
|
|
|
const getClassName = () => {
|
|
|
|
// Taken from Skolverket
|
|
|
|
// https://www.skolverket.se/skolutveckling/anordna-och-administrera-utbildning/administrera-utbildning/skoltermer-pa-engelska
|
|
|
|
const abbrevations = {
|
|
|
|
G: translate('abbrevations.upperSecondarySchool'),
|
|
|
|
GR: translate('abbrevations.compulsorySchool'),
|
|
|
|
F: translate('abbrevations.leisureTimeCentre'),
|
|
|
|
FS: translate('abbrevations.preSchool'),
|
|
|
|
}
|
|
|
|
|
|
|
|
return child.status
|
|
|
|
? child.status
|
|
|
|
.split(';')
|
|
|
|
.map((status) => {
|
|
|
|
const statusAsAbbreviation = status as keyof typeof abbrevations
|
|
|
|
|
|
|
|
return abbrevations[statusAsAbbreviation] || status
|
|
|
|
})
|
|
|
|
.join(', ')
|
|
|
|
: null
|
|
|
|
}
|
|
|
|
|
|
|
|
const className = getClassName()
|
|
|
|
|
2021-02-15 12:33:47 +00:00
|
|
|
const Footer = () => (
|
2021-02-21 07:47:01 +00:00
|
|
|
<View style={styles.itemFooter}>
|
|
|
|
<Button
|
|
|
|
style={[styles.item, styles[newsStatus]]}
|
|
|
|
status="control"
|
|
|
|
size="small"
|
|
|
|
onPress={() =>
|
|
|
|
navigation.navigate('Child', {
|
|
|
|
child,
|
|
|
|
color,
|
2021-04-14 08:11:49 +00:00
|
|
|
initialRouteName: translate('navigation.news'),
|
2021-02-21 07:47:01 +00:00
|
|
|
})
|
|
|
|
}
|
|
|
|
accessoryLeft={NewsIcon}
|
|
|
|
>
|
|
|
|
{`${(news || []).length}`}
|
|
|
|
</Button>
|
|
|
|
<Button
|
|
|
|
style={[styles.item, styles[notificationsStatus]]}
|
|
|
|
status="control"
|
|
|
|
size="small"
|
|
|
|
onPress={() =>
|
|
|
|
navigation.navigate('Child', {
|
|
|
|
child,
|
|
|
|
color,
|
2021-04-14 08:11:49 +00:00
|
|
|
initialRouteName: translate('navigation.notifications'),
|
2021-02-21 07:47:01 +00:00
|
|
|
})
|
|
|
|
}
|
|
|
|
accessoryLeft={NotificationsIcon}
|
|
|
|
>
|
|
|
|
{`${(notifications || []).length}`}
|
|
|
|
</Button>
|
|
|
|
<Button
|
|
|
|
style={[styles.item, styles[calendarStatus]]}
|
|
|
|
status="control"
|
|
|
|
size="small"
|
|
|
|
onPress={() =>
|
|
|
|
navigation.navigate('Child', {
|
|
|
|
child,
|
|
|
|
color,
|
2021-04-14 08:11:49 +00:00
|
|
|
initialRouteName: translate('navigation.calender'),
|
2021-02-21 07:47:01 +00:00
|
|
|
})
|
|
|
|
}
|
|
|
|
accessoryLeft={CalendarOutlineIcon}
|
|
|
|
>
|
2021-04-02 22:11:25 +00:00
|
|
|
{`${(calendar || []).length}`}
|
2021-02-21 07:47:01 +00:00
|
|
|
</Button>
|
|
|
|
<Button
|
2021-04-03 07:36:26 +00:00
|
|
|
style={[styles.item, styles[menuStatus]]}
|
2021-02-21 07:47:01 +00:00
|
|
|
status="control"
|
|
|
|
size="small"
|
|
|
|
onPress={() =>
|
|
|
|
navigation.navigate('Child', {
|
|
|
|
child,
|
|
|
|
color,
|
2021-04-14 08:15:59 +00:00
|
|
|
initialRouteName: translate('navigation.menu'),
|
2021-02-21 07:47:01 +00:00
|
|
|
})
|
|
|
|
}
|
2021-04-03 07:36:26 +00:00
|
|
|
accessoryLeft={MenuIcon}
|
|
|
|
/>
|
2021-02-21 07:47:01 +00:00
|
|
|
</View>
|
2021-01-04 21:40:54 +00:00
|
|
|
)
|
|
|
|
|
|
|
|
return (
|
|
|
|
<Card
|
2021-02-16 15:48:40 +00:00
|
|
|
style={styles.card}
|
2021-02-07 16:14:45 +00:00
|
|
|
appearance="filled"
|
2021-01-04 21:40:54 +00:00
|
|
|
status={color}
|
2021-03-26 08:38:15 +00:00
|
|
|
header={(props) => (
|
|
|
|
<View {...props} style={styles.cardHeader}>
|
|
|
|
<View style={styles.cardAvatar}>
|
|
|
|
<Avatar source={require('../assets/avatar.png')} shape="square" />
|
|
|
|
</View>
|
|
|
|
<View style={styles.cardHeaderText}>
|
|
|
|
<Text category="h6">{studentName(child.name)}</Text>
|
2021-04-20 10:51:38 +00:00
|
|
|
{className ? <Text category="s1">{className}</Text> : null}
|
2021-03-26 08:38:15 +00:00
|
|
|
</View>
|
|
|
|
</View>
|
|
|
|
)}
|
2021-01-04 21:40:54 +00:00
|
|
|
footer={Footer}
|
2021-02-15 12:33:47 +00:00
|
|
|
onPress={() => navigation.navigate('Child', { child, color })}
|
|
|
|
>
|
2021-02-19 14:29:41 +00:00
|
|
|
{scheduleAndCalendarThisWeek.slice(0, 3).map((calendarItem, i) => (
|
2021-04-02 08:50:03 +00:00
|
|
|
<Text appearance="hint" category="c1" key={i}>
|
|
|
|
{`${calendarItem.title} (${displayDate(calendarItem.startDate)})`}
|
|
|
|
</Text>
|
|
|
|
))}
|
|
|
|
{notificationsThisWeek.slice(0, 3).map((notification, i) => (
|
|
|
|
<Text appearance="hint" category="c1" key={i}>
|
2021-04-13 19:49:30 +00:00
|
|
|
{translate('notifications.notificationTitle', {
|
|
|
|
message: notification.message,
|
|
|
|
dateCreated: displayDate(notification.dateCreated),
|
|
|
|
})}
|
2021-02-19 14:29:41 +00:00
|
|
|
</Text>
|
|
|
|
))}
|
2021-04-02 08:50:03 +00:00
|
|
|
{newsThisWeek.slice(0, 3).map((newsItem, i) => (
|
2021-02-19 14:29:41 +00:00
|
|
|
<Text appearance="hint" category="c1" key={i}>
|
2021-04-14 11:14:41 +00:00
|
|
|
{translate('news.notificationTitle', {
|
2021-04-13 19:49:30 +00:00
|
|
|
header: newsItem.header,
|
|
|
|
published: displayDate(newsItem.published),
|
|
|
|
})}
|
2021-02-19 14:29:41 +00:00
|
|
|
</Text>
|
|
|
|
))}
|
|
|
|
{scheduleAndCalendarThisWeek.length ||
|
2021-04-02 08:50:03 +00:00
|
|
|
notificationsThisWeek.length ||
|
|
|
|
newsThisWeek.length ? null : (
|
2021-02-19 14:29:41 +00:00
|
|
|
<Text appearance="hint" category="c1">
|
2021-04-13 19:49:30 +00:00
|
|
|
{translate('news.noNewNewsItemsThisWeek')}
|
2021-02-19 14:29:41 +00:00
|
|
|
</Text>
|
|
|
|
)}
|
2021-02-21 07:47:01 +00:00
|
|
|
<View style={styles.itemFooterAbsence}>
|
|
|
|
<Button
|
|
|
|
size="small"
|
|
|
|
onPress={() => navigation.navigate('Absence', { child })}
|
|
|
|
>
|
2021-04-13 15:03:14 +00:00
|
|
|
{translate('abscense.title')}
|
2021-02-21 07:47:01 +00:00
|
|
|
</Button>
|
|
|
|
</View>
|
2021-01-04 21:40:54 +00:00
|
|
|
</Card>
|
|
|
|
)
|
|
|
|
}
|
|
|
|
|
|
|
|
const styles = StyleSheet.create({
|
|
|
|
card: {
|
2021-03-31 08:16:41 +00:00
|
|
|
marginBottom: Sizing.t5,
|
2021-01-04 21:40:54 +00:00
|
|
|
},
|
2021-02-21 15:43:24 +00:00
|
|
|
cardHeader: {
|
2021-03-31 08:16:41 +00:00
|
|
|
...Layout.flex.row,
|
|
|
|
...Layout.mainAxis.center,
|
2021-02-21 15:43:24 +00:00
|
|
|
},
|
2021-03-31 08:16:41 +00:00
|
|
|
cardAvatar: { margin: Sizing.t5, marginRight: 0 },
|
|
|
|
cardHeaderText: { margin: Sizing.t5, flex: 1 },
|
2021-01-04 21:40:54 +00:00
|
|
|
itemFooter: {
|
2021-03-31 08:16:41 +00:00
|
|
|
...Layout.flex.row,
|
|
|
|
...Layout.crossAxis.evenly,
|
|
|
|
paddingVertical: Sizing.t2,
|
2021-01-05 11:27:38 +00:00
|
|
|
borderRadius: 5,
|
2021-02-07 16:14:45 +00:00
|
|
|
margin: 0,
|
2021-01-05 11:27:38 +00:00
|
|
|
},
|
2021-02-19 08:18:22 +00:00
|
|
|
itemFooterAbsence: {
|
2021-03-31 08:16:41 +00:00
|
|
|
...Layout.mainAxis.flexStart,
|
|
|
|
marginTop: Sizing.t4,
|
2021-02-19 08:18:22 +00:00
|
|
|
},
|
2021-01-26 12:39:22 +00:00
|
|
|
item: {
|
2021-01-05 11:27:38 +00:00
|
|
|
paddingHorizontal: 0,
|
2021-01-26 12:39:22 +00:00
|
|
|
},
|
|
|
|
loaded: {
|
2021-03-31 08:16:41 +00:00
|
|
|
color: Colors.neutral.black,
|
2021-01-04 21:40:54 +00:00
|
|
|
},
|
2021-01-05 11:27:38 +00:00
|
|
|
loading: {
|
2021-02-07 16:14:45 +00:00
|
|
|
color: '#555',
|
2021-01-26 12:39:22 +00:00
|
|
|
},
|
|
|
|
error: {
|
2021-02-07 16:14:45 +00:00
|
|
|
color: '#500',
|
|
|
|
},
|
2021-03-26 08:38:15 +00:00
|
|
|
pending: {},
|
2021-01-04 21:40:54 +00:00
|
|
|
})
|