Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
8 changes: 8 additions & 0 deletions src/networking/index.js
Original file line number Diff line number Diff line change
Expand Up @@ -91,6 +91,14 @@ class HttpService {
return this._get(`routines/${routine.id}/log_entries`)
}

getRoutineCalculations (routine) {
return this._get(`routines/${routine.id}/readings/calculations`)
}

calculationsToCsv (routine) {
return `${process.env.REACT_APP_BASE_API_URL}/routines/${routine.id}/readings/calculations_to_csv`
}

createRoutine (routine) {
return this._post('routines', { routine })
}
Expand Down
2 changes: 1 addition & 1 deletion src/presentation/common/sensor_chart/index.js
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,7 @@ import LineChart from '../../common/chart/line'
const MAGNITUDE_COLORS = {
temp: '#DB9439',
ph: '#8DB5B2',
observancy: '#C6625B',
product: '#C6625B',
substratum: '#739E53',
biomass: '#A37EA0'
}
Expand Down
2 changes: 1 addition & 1 deletion src/presentation/common/timeline_navigation_chart/index.js
Original file line number Diff line number Diff line change
Expand Up @@ -40,7 +40,7 @@ export default class TimelineNavigationChart extends Component {
datasets={[
{ data: this.props.timeline.temp, stroke: '#DB9439', label: 'Temperatura' },
{ data: this.props.timeline.ph, stroke: '#8DB5B2', label: 'pH' },
{ data: this.props.timeline.observancy, stroke: '#C6625B', label: 'Observancia' },
{ data: this.props.timeline.product, stroke: '#C6625B', label: 'Producto' },
{ data: this.props.timeline.substratum, stroke: '#739E53', label: 'Sustrato' },
{ data: this.props.timeline.biomass, stroke: '#A37EA0', label: 'Biomasa' }
]}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -18,7 +18,7 @@ class AddExternalRoutine extends Component {
super(props)
this.state = {
magnitudes: {
observancy: null,
product: null,
substratum: null,
biomass: null
},
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -18,13 +18,13 @@ const AddExternalRoutinePresenter = ({ magnitudes, error, onUpdateMagnitudes, on
<Modal.Content>
<Form>
<TextInput
name='observancy'
name='product'
error={error}
label='Observancia'
label='Producto'
required
type='number'
min={0}
onChange={observancy => onUpdateMagnitudes({ ...magnitudes, observancy })}
onChange={product => onUpdateMagnitudes({ ...magnitudes, product })}
/>
<TextInput
name='substratum'
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,7 @@ import SensorChart from '../../common/sensor_chart'
import Button from '../../common/button'
import Container from '../../common/container'

const isExternalMagnitude = magnitude => ['observancy', 'biomass', 'substratum'].includes(magnitude)
const isExternalMagnitude = magnitude => ['product', 'biomass', 'substratum'].includes(magnitude)

const ExpandedMagnitudeModal = ({ title, magnitude, timeline, onClose, onAddReadings }) => {
return (
Expand Down
10 changes: 5 additions & 5 deletions src/presentation/dashboard/running_routine/presenter.js
Original file line number Diff line number Diff line change
Expand Up @@ -14,7 +14,7 @@ const magnitudeTitle = magnitude => {
switch (magnitude) {
case 'temp': return 'Temperatura'
case 'ph': return 'pH'
case 'observancy': return 'Observancia'
case 'product': return 'Producto'
case 'substratum': return 'Sustrato'
case 'biomass': return 'Biomasa'
}
Expand Down Expand Up @@ -89,10 +89,10 @@ export default class SensorsDashboardPresenter extends Component {
/>

<MagnitudeCard
title={magnitudeTitle('observancy')}
title={magnitudeTitle('product')}
valueUnit='g/L'
currentValue={this.props.currentValue.observancy}
onClick={() => this.onClickMagnitude('observancy')}
currentValue={this.props.currentValue.product}
onClick={() => this.onClickMagnitude('product')}
/>

<MagnitudeCard
Expand All @@ -112,7 +112,7 @@ export default class SensorsDashboardPresenter extends Component {

{ this.props.timeline &&
<SensorChart
magnitudes={['temp', 'ph', 'observancy', 'substratum', 'biomass']}
magnitudes={['temp', 'ph', 'product', 'substratum', 'biomass']}
timeline={this.props.timeline}
height={140}
/>
Expand Down
25 changes: 13 additions & 12 deletions src/presentation/experiment/details/presenter.js
Original file line number Diff line number Diff line change
Expand Up @@ -2,14 +2,14 @@ import React from 'react'
import './styles.css'
import { Grid } from 'semantic-ui-react'
import moment from 'moment'
import { Link } from 'react-router-dom'

import Screen from '../../common/screen'
import Container from '../../common/container'
import SensorChart from '../../common/sensor_chart'
import Button from '../../common/button'
import ButtonLink from '../../common/button/link'

import Network from '../../../networking'
import ButtonIcon from '../../common/button/icon'

import TagsList from './tags'

Expand All @@ -28,6 +28,9 @@ const ExperimentPresenter = ({ routine, timeline, fetching, error, onAnalyzeData
{ !routine.started &&
<Button primary onClick={onStart}>Comenzar</Button>
}
{ routine.startedDate &&
<ButtonLink primary pathname={`/experiments/${routine.id}/report`}>Reporte</ButtonLink>
}
</Container>
</Container>

Expand Down Expand Up @@ -61,16 +64,8 @@ const ExperimentPresenter = ({ routine, timeline, fetching, error, onAnalyzeData

<Container>

<Container row>
<Container>
<h3>Ejecución</h3>
{ routine.startedDate &&
<Container row>
<ButtonLink primary pathname={`/experiments/${routine.id}/analysis`}>Analizar datos</ButtonLink>
<a href={Network.routineToCsvUrl(routine)}>
<Button primary>Exportar a csv</Button>
</a>
</Container>
}
</Container>

<Grid>
Expand Down Expand Up @@ -124,9 +119,15 @@ const ExperimentPresenter = ({ routine, timeline, fetching, error, onAnalyzeData

</Grid>

<Container row end>
<Link to={{ pathname: `/experiments/${routine.id}/execution` }}>
<ButtonIcon primary icon='expand' />
</Link>
</Container>

{ routine.readings.length > 0 &&
<SensorChart
magnitudes={['temp', 'ph', 'observancy', 'substratum', 'biomass']}
magnitudes={['temp', 'ph', 'product', 'substratum', 'biomass']}
timeline={timeline}
/>
}
Expand Down
28 changes: 27 additions & 1 deletion src/presentation/experiment/details/styles.css
Original file line number Diff line number Diff line change
@@ -1,3 +1,29 @@
.routineDetails .title {
margin-top: 30px;
}
}

/* .routineDetails .chart .overlay {
display: none;
} */

.routineDetails .chart {
position: relative;
}

.routineDetails .chart .overlay {
position: absolute;
background: rgba(65, 132, 202, 0.4);
border-radius: 10px;
top: 0;
left: 0;
right: 0;
bottom: 0;
display: flex;
justify-content: center;
align-items: center;
display: flex;
}

.routineDetails .chart:hover .overlay {
display: flex;
}
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
import React, { Component } from 'react'
import { connect } from 'react-redux'

import ExperimentAnalysisPresenter from './presenter'
import ExperimentExecutionPresenter from './presenter'

import {
selectRoutineFetchingStatus, selectSelectedRoutine
Expand All @@ -17,14 +17,14 @@ import {
fetchRequest
} from '../../../redux/routine/actions'

class ExperimentAnalysis extends Component {
class ExperimentExecution extends Component {
componentWillMount () {
this.props.requestRoutine(this.props.match.params)
}

render () {
return (
<ExperimentAnalysisPresenter
<ExperimentExecutionPresenter
routine={this.props.routine}
fetching={this.props.fetching}
error={this.props.error}
Expand All @@ -50,4 +50,4 @@ const mapDispatchToProps = dispatch => {
}
}

export default connect(mapStateToProps, mapDispatchToProps)(ExperimentAnalysis)
export default connect(mapStateToProps, mapDispatchToProps)(ExperimentExecution)
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
import React from 'react'
import './styles.css'
import Network from '../../../networking'

import Screen from '../../common/screen'
import Container from '../../common/container'
Expand All @@ -9,16 +10,23 @@ import Button from '../../common/button'
import NavigationChart from './navigation_chart'
import LogEntry from './log_entry'

const ExperimentAnalysisPresenter = ({ routine = {}, timeline, logEntries, fetching, error }) => {
const ExperimentExecutionPresenter = ({ routine = {}, timeline, logEntries, fetching, error }) => {
return (
<Screen loading={fetching || timeline.labels.lenght === 0}>

<div className='analysisContent'>
<div className='data'>

<Container row>
<h2>{routine.title}</h2>
<Button primary onClick={() => window.print()}>Imprimir</Button>
<Container row end>
<a href={Network.routineToCsvUrl(routine)}>
<Button primary>Exportar a csv</Button>
</a>
<Button primary onClick={() => window.print()}>Imprimir</Button>
</Container>
</Container>

<Container>
<h3>Temperatura</h3>
<SensorChart
Expand All @@ -36,9 +44,9 @@ const ExperimentAnalysisPresenter = ({ routine = {}, timeline, logEntries, fetch
</Container>

<Container>
<h3>Observancia</h3>
<h3>Producto</h3>
<SensorChart
magnitudes={['observancy']}
magnitudes={['product']}
timeline={timeline}
/>
</Container>
Expand Down Expand Up @@ -76,4 +84,4 @@ const ExperimentAnalysisPresenter = ({ routine = {}, timeline, logEntries, fetch
)
}

export default ExperimentAnalysisPresenter
export default ExperimentExecutionPresenter
14 changes: 10 additions & 4 deletions src/presentation/experiment/index.js
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,8 @@ import Toolbar from '../common/toolbar'

import Experiments from './list'
import Experiment from './details'
import ExperimentAnalysis from './analysis'
import ExperimentExecution from './execution'
import ExperimentReport from './report'
import ExperimentCreation from './upsert'

const ROUTES = match => [{
Expand All @@ -21,10 +22,15 @@ const ROUTES = match => [{
component: Experiment,
title: 'Experimento'
}, {
path: match.url + '/:id/analysis',
component: ExperimentAnalysis,
path: match.url + '/:id/execution',
component: ExperimentExecution,
itemIndex: 2,
title: 'Análisis'
title: 'Ejecución'
}, {
path: match.url + '/:id/report',
component: ExperimentReport,
itemIndex: 2,
title: 'Reporte'
}]

const ExperimentNavigation = ({ match }) => {
Expand Down
19 changes: 19 additions & 0 deletions src/presentation/experiment/report/calculation/chart/index.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,19 @@
import React from 'react'

import LineChart from '../../../../common/chart/line'

const ReportChart = ({ calculation, color }) => {
return (
<LineChart
datasets={[{
data: calculation.map(({ x, y }) => y),
label: calculation.map(({ x, y }) => x),
stroke: color
}]}
height={60}
labels={calculation.map(({ x, y }) => x)}
/>
)
}

export default ReportChart
54 changes: 54 additions & 0 deletions src/presentation/experiment/report/calculation/index.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,54 @@
import React from 'react'
import './styles.css'

import Chart from './chart'
import Container from '../../../common/container'

const MAGNITUDE_COLORS = {
temp: '#DB9439',
ph: '#8DB5B2',
product: '#C6625B',
substratum: '#739E53',
biomass: '#A37EA0'
}

const CALCULATION_NAMES = {
specificProductVelocity: 'Velocidad Específica de Producto',
productVolumetricPerformance: 'Rendimiento volumétrico de Producto',
productPerformance: 'Rendimiento de Producto',
maxProductVolumetricPerformance: 'Máximo rendmiento de Producto volumétrico',
maxProductVelocity: 'Máxima velocidad de producto',

productBiomassPerformance: 'Rendimiento de Producto Biomasa',

specificBiomassVelocity: 'Velocidad Específica de Biomasa',
biomassVolumetricPerformance: 'Rendimiento volumétrico de Biomasa',
biomassPerformance: 'Rendimiento de Biomasa',
maxBiomassVolumetricPerformance: 'Máxima rendimiento de Biomasa volumétrica',
maxBiomassVelocity: 'Máxima velocidad de Biomasa',

specificPhVelocity: 'Velocidad Específica de pH',
maxPhVelocity: 'Máxima velocidad de pH'
}

const getMagnitudeName = calculationName =>
Object.keys(MAGNITUDE_COLORS).find(m => calculationName.toLowerCase().includes(m))

const Calculation = ({ routine, calculation, max }) => {
return (
<Container className='calculation'>
<Container noPadding row>
<h4>{CALCULATION_NAMES[calculation]}</h4>
{ routine.calculations[max] &&
<h4 className='maximum'>Máximo {routine.calculations[max].y}</h4>
}
</Container>
<Chart
calculation={routine.calculations[calculation]}
color={MAGNITUDE_COLORS[getMagnitudeName(calculation)]}
/>
</Container>
)
}

export default Calculation
3 changes: 3 additions & 0 deletions src/presentation/experiment/report/calculation/styles.css
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
.maximum {
margin-top: 0;
}
Loading