src/components/Gantt.js
c6a95b0d
 import React from 'react';
 import { withContentRect } from 'react-measure'
 import { filter, range, map, pipe } from 'rambda';
 import { ScatterChart, Scatter, XAxis, YAxis, CartesianGrid, Brush, Label } from 'recharts';
 import Job from './Job';
 import { maxTime, minTime } from '../ganttUtils';
 import theme from '../theme';
 
 class Gannt extends React.PureComponent {
   constructor(props) {
     super(props);
 
     this.state = {
       startTime: minTime(props.data),
       endTime: maxTime(props.data)
     };
   }
 
   render() {
     const { data, measureRef, contentRect: { bounds: dimensions } } = this.props;
     const { startTime } = this.state;
     const endTime = this.state.endTime === startTime ? startTime + 1 : this.state.endTime;
 
     const scopeData = map(processorData =>
       pipe(
         filter(datum =>
           (datum.startTime >= startTime
             || (datum.startTime < startTime && datum.endTime >= startTime)
           )
           && datum.startTime <= endTime
         ),
         map(datum => {
           let newDatum = datum;
           if (newDatum.startTime < startTime) {
             newDatum = { ...newDatum, startTime, formerStartTime: newDatum.startTime };
           }
 
           if (newDatum.endTime > endTime) {
             newDatum = { ...newDatum, endTime, formerEndTime: newDatum.endTime };
           }
 
           return newDatum;
         })
       )(processorData),
       data
     );
 
     const processors = range(1, data.length + 1);
 
     const scopeMinTime = minTime(scopeData);
     const scopeMaxTime = maxTime(scopeData);
     const ticksCountX = scopeMinTime + scopeMaxTime;
 
     const width = Math.max(theme.gantt.maxWidth, dimensions.width);
     const height = 100 + 1.75 * theme.gantt.job.height * processors.length;
 
     const horizontalGuideLines = map(
       i => theme.gantt.margin.top + i * 1.75 * theme.gantt.job.height - i * 10,
       range(0, processors.length)
     );
 
     return (
       <div ref={measureRef}>
9d471776
         <h1>Ganttov diagram</h1>
 
c6a95b0d
         <ScatterChart width={width} height={height} data={data[0]} margin={theme.gantt.margin}>
           <CartesianGrid
             stroke={theme.gantt.grid.stroke}
             strokeDasharray="5 5"
             horizontalPoints={horizontalGuideLines}
           />
           <XAxis
             type="number"
             dataKey="startTime"
             interval={0}
             domain={[scopeMinTime, scopeMaxTime]}
             tickCount={ticksCountX}
             allowDecimals={false}
           >
9d471776
             <Label offset={-30} position="insideBottom">Čas</Label>
c6a95b0d
           </XAxis>
           <YAxis
             type="number"
             dataKey="processor"
             interval={0}
             name="processor"
             allowDecimals={false}
             domain={[0.5, processors.length + 0.5]}
             ticks={processors}
           >
9d471776
             <Label position="insideLeft" angle={-90}>Pracovníci</Label>
c6a95b0d
           </YAxis>
           <Brush
             dataKey="startTime"
             y={height - theme.gantt.brush.height - 10}
             height={theme.gantt.brush.height}
             stroke={theme.gantt.brush.stroke}
             onChange={({ startIndex, endIndex }) =>
               this.setState({ startTime: startIndex + 1, endTime: endIndex + 1 })
             }
           />
           {scopeData.map((processorData, i) => (
             <Scatter key={i} data={processorData} shape={<Job />} />
           ))}
         </ScatterChart>
       </div>
     );
   }
 }
 
 export default withContentRect('bounds')(Gannt);