New vertical layout

This commit is contained in:
2022-09-07 01:30:54 +02:00
parent 19bea2f48f
commit 45cd07fa85
5 changed files with 347 additions and 65 deletions
+127 -43
View File
@@ -6,7 +6,7 @@ import { differenceInMinutes, format, getWeek, startOfDay } from 'date-fns'
import { it } from 'date-fns/locale'
import _ from 'lodash'
import { useEffect, useRef } from 'preact/hooks'
import { useEffect, useRef, useState } from 'preact/hooks'
import { layoutIntervals } from '../interval-layout.js'
function hashString(str, seed = 0) {
@@ -36,12 +36,10 @@ const WorkWeekView = ({ events }) => {
)
)
console.log(rowLayouts)
const weekDays = ['Lunedì', 'Martedì', 'Mercoledì', 'Giovedì', 'Venerdì']
return (
<div class="workweek-view">
<div class="work-week-h-view">
<div class="week">
{weekDays.map((label, index) => (
<div class="day" style={{ '--size': rowLayouts[index + 1]?.length ?? 0 }}>
@@ -126,52 +124,136 @@ const WorkWeekView = ({ events }) => {
)
}
/*
{sortedKeys.map(blockStart => (
<div
class="stacked"
style={{
'--start':
differenceInMinutes(
stacked[blockStart][0].start,
startOfDay(stacked[blockStart][0].start)
) -
60 * 8,
}}
>
{stacked[blockStart].map(event => (
<Event {...event} />
))}
</div>
))}
const WorkWeekVerticalView = ({ events }) => {
const eventsByWeekday = _.groupBy(events, event => event.start.getDay())
const dayIntervalLayout = _.mapValues(eventsByWeekday, events =>
layoutIntervals(
events.map(e => ({
start: differenceInMinutes(e.start, startOfDay(e.start)),
end: differenceInMinutes(e.end, startOfDay(e.start)),
data: e,
}))
)
)
const weekDays = ['Lunedì', 'Martedì', 'Mercoledì', 'Giovedì', 'Venerdì']
const [currentlyHovered, setCurrentlyHovered] = useState(null)
const element = useRef()
useEffect(() => {
if (element.current) {
const l = e => {
const $event = e.target.closest('.event')
if ($event) {
setCurrentlyHovered($event.dataset.eventId)
} else {
setCurrentlyHovered(null)
}
}
element.current.addEventListener('mousemove', l)
return () => {
element.current.removeEventListener('mousemove', l)
}
}
}, [element.current])
{Object.values(eventsByWeekday).map(dayEvents => {
return (
<div class="day">
{dayEvents.map(({ name, start, end }) => {
return (
<div class="work-week-v-view" ref={element}>
<div class="pivot"></div>
<div class="left-header">
<div class="blocks">
<div
class="event"
class="block skip-border"
style={{
'--hue':
(Math.abs(hashString('seed3' + name)) % 360) +
'deg',
'--start':
differenceInMinutes(start, startOfDay(start)) -
60 * 8,
'--size': differenceInMinutes(end, start),
'--start': 9 - 7,
'--size': 2,
}}
>
{_.startCase(_.lowerCase(name))
.replaceAll('Ii', 'II')
.replaceAll('Iii', 'III')}
9:00 &ndash; 11:00
</div>
)
})}
<div
class="block"
style={{
'--start': 11 - 7,
'--size': 2,
}}
>
11:00 &ndash; 13:00
</div>
<div
class="block skip-border"
style={{
'--start': 14 - 7,
'--size': 2,
}}
>
14:00 &ndash; 16:00
</div>
<div
class="block"
style={{
'--start': 16 - 7,
'--size': 2,
}}
>
16:00 &ndash; 18:00
</div>
</div>
</div>
{Object.values(dayIntervalLayout).map((layout, index) => (
<div class="day" style={{ '--size': layout.length }}>
<div class="top-header">{weekDays[index]}</div>
<div class="events">
{layout.map((events, stackIndex) => (
<>
{events.map(event => (
<div
class={
'event' +
(currentlyHovered === event.data.name
? ' highlight'
: '')
}
data-event-id={event.data.name}
style={{
'--start': event.start / 60 - 7,
'--stack': stackIndex + 1,
'--size': (event.end - event.start) / 60,
'--hue':
(Math.abs(hashString('seed3' + event.data.name)) %
360) +
'deg',
}}
>
<div class="title">
{_.startCase(_.lowerCase(event.data.name))
.replaceAll('Ii', 'II')
.replaceAll('Iii', 'III')
.replaceAll(/\bE\b/g, 'e')}
</div>
<div class="aula">{event.data.aula}</div>
</div>
))}
</>
))}
{/* Grid Tracks */}
{[1, 3, 5].map(i => (
<div class="grid-line-h" style={{ '--track': i }}></div>
))}
{[6, 8, 10].map(i => (
<div class="grid-line-h" style={{ '--track': i }}></div>
))}
</div>
</div>
))}
</div>
)
})}
*/
}
const CourseView = ({ events }) => {
const eventsByCourse = _.groupBy(events, 'name')
@@ -183,7 +265,8 @@ const CourseView = ({ events }) => {
<div class="title">
{_.startCase(_.lowerCase(name))
.replaceAll('Ii', 'II')
.replaceAll('Iii', 'III')}
.replaceAll('Iii', 'III')
.replaceAll(/\bE\b/g, 'e')}
</div>
<div class="docenti">{courseEvents[0].docenti.join(', ')}</div>
<div class="events">
@@ -207,7 +290,8 @@ const CourseView = ({ events }) => {
//
const viewModeMap = {
'work-week': WorkWeekView,
'work-week-h': WorkWeekView,
'work-week-v': WorkWeekVerticalView,
'course': CourseView,
}
+20 -5
View File
@@ -1,3 +1,5 @@
import { Icon } from './Icon.jsx'
export const Toolbar = ({ mode, setMode }) => {
return (
<div class="toolbar">
@@ -12,16 +14,29 @@ export const Toolbar = ({ mode, setMode }) => {
Corso
</button>
<button
class={'radio' + (mode === 'work-week' ? ' selected' : '')}
onClick={() => setMode('work-week')}
class={'radio' + (mode === 'work-week-v' ? ' selected' : '')}
onClick={() => setMode('work-week-v')}
>
Settimana
</button>
<button
class={'radio' + (mode === 'work-week-h' ? ' selected' : '')}
onClick={() => setMode('work-week-h')}
>
Settimana<sup>T</sup>
</button>
</div>
</div>
<div class="item option">Opzione 2</div>
<div class="item option">Opzione 3</div>
<div class="item option">Opzione 4</div>
<div class="item option">
<button class="icon">
<Icon name="filter_list" />
</button>
</div>
<div class="item option">
<button class="icon">
<Icon name="print" />
</button>
</div>
</div>
</div>
)