From 2f25c5cffed61458e3a16aba54e5baa40b5a2864 Mon Sep 17 00:00:00 2001 From: Sofiya Tepikin Date: Thu, 22 Aug 2019 23:01:54 +0200 Subject: [PATCH] Splits the temperature view to simplify it --- .../cycle-day/symptoms/temperature-input.js | 103 +++++++++++++ components/cycle-day/symptoms/temperature.js | 135 +++++------------- components/cycle-day/symptoms/time-input.js | 62 ++++++++ 3 files changed, 198 insertions(+), 102 deletions(-) create mode 100644 components/cycle-day/symptoms/temperature-input.js create mode 100644 components/cycle-day/symptoms/time-input.js diff --git a/components/cycle-day/symptoms/temperature-input.js b/components/cycle-day/symptoms/temperature-input.js new file mode 100644 index 0000000..d6de38f --- /dev/null +++ b/components/cycle-day/symptoms/temperature-input.js @@ -0,0 +1,103 @@ +import React, { Component } from 'react' +import PropTypes from 'prop-types' + +import { View } from 'react-native' +import AppText from '../../app-text' +import AppTextInput from '../../app-text-input' + +import { temperature as labels } from '../../../i18n/en/cycle-day' + +import styles from '../../../styles' + +import { getPreviousTemperature } from '../../../db' +import { scaleObservable } from '../../../local-storage' +import config from '../../../config' + +export default class TemperatureInput extends Component { + + static propTypes = { + temperature: PropTypes.string, + handleTemperatureChange: PropTypes.func, + date: PropTypes.string, + } + + constructor(props) { + super(props) + + let shouldShowSuggestion = false + let suggestedTemperature = null + + if (!props.temperature) { + const prevTemp = getPreviousTemperature(props.date) + if (prevTemp) { + shouldShowSuggestion = true + suggestedTemperature = prevTemp.toString() + } + } + + this.state = { + temperature: props.temperature, + shouldShowSuggestion, + suggestedTemperature + } + } + + setTemperature = (temperature) => { + this.setState({ + shouldShowSuggestion: false, + temperature + }) + this.props.handleTemperatureChange(Number(temperature)) + } + + render () { + const { + shouldShowSuggestion, + suggestedTemperature, + temperature + } = this.state + const inputStyle = [ + styles.temperatureTextInput, + shouldShowSuggestion ? styles.temperatureTextInputSuggestion : null + ] + return ( + + + + °C + + + + ) + } +} + +const OutOfRangeWarning = ({ temperature }) => { + if (temperature === '') { + return false + } + + const value = Number(temperature) + const { min, max } = config.temperatureScale + const range = { min, max } + const scale = scaleObservable.value + + let warningMsg + + if (value < range.min || value > range.max) { + warningMsg = labels.outOfAbsoluteRangeWarning + } else if (value < scale.min || value > scale.max) { + warningMsg = labels.outOfRangeWarning + } else { + warningMsg = null + } + + return {warningMsg} +} diff --git a/components/cycle-day/symptoms/temperature.js b/components/cycle-day/symptoms/temperature.js index f0db45a..dd90580 100644 --- a/components/cycle-day/symptoms/temperature.js +++ b/components/cycle-day/symptoms/temperature.js @@ -1,32 +1,31 @@ import React from 'react' -import { - View, - Switch, - Keyboard, - ScrollView -} from 'react-native' +import { Switch, ScrollView } from 'react-native' +import PropTypes from 'prop-types' import { connect } from 'react-redux' import { getDate } from '../../../slices/date' -import DateTimePicker from 'react-native-modal-datetime-picker-nevo' -import padWithZeros from '../../helpers/pad-time-with-zeros' - -import { getPreviousTemperature } from '../../../db' import styles from '../../../styles' import { LocalTime, ChronoUnit } from 'js-joda' import { temperature as labels } from '../../../i18n/en/cycle-day' -import { scaleObservable } from '../../../local-storage' import { shared as sharedLabels } from '../../../i18n/en/labels' -import config from '../../../config' + import AppTextInput from '../../app-text-input' -import AppText from '../../app-text' import SymptomSection from './symptom-section' import SymptomView from './symptom-view' +import TimeInput from './time-input' +import TemperatureInput from './temperature-input' const minutes = ChronoUnit.MINUTES -class Temp extends SymptomView { +class Temperature extends SymptomView { + + static propTypes = { + cycleDay: PropTypes.object, + handleBackButtonPress: PropTypes.func, + date: PropTypes.string, + } + constructor(props) { super(props) const cycleDay = props.cycleDay @@ -37,23 +36,9 @@ class Temp extends SymptomView { this.state = { exclude: temp ? temp.exclude : false, time: temp ? temp.time : LocalTime.now().truncatedTo(minutes).toString(), - isTimePickerVisible: false, + temperature: temp ? temp.value : null, note: temp ? temp.note : null } - - if (temp) { - this.state.temperature = temp.value.toString() - if (temp.value === Math.floor(temp.value)) { - this.state.temperature = `${this.state.temperature}.0` - } - this.state.outOfRangeWarning = makeOutOfRangeWarningMessage(this.state.temperature) - } else { - const prevTemp = getPreviousTemperature(props.date) - if (prevTemp) { - this.state.suggestedTemperature = prevTemp.toString() - this.state.isSuggestion = true - } - } } symptomName = 'temperature' @@ -67,13 +52,13 @@ class Temp extends SymptomView { } autoSave = () => { - if (typeof this.state.temperature != 'string' || this.state.temperature === '') { + if (!this.state.temperature) { this.deleteSymptomEntry() return } const dataToSave = { - value: Number(this.state.temperature), + value: this.state.temperature, exclude: this.state.exclude, time: this.state.time, note: this.state.note @@ -82,73 +67,38 @@ class Temp extends SymptomView { this.saveSymptomEntry(dataToSave) } + setTime = (time) => { + this.setState({ time }) + } setTemperature = (temperature) => { - if (isNaN(Number(temperature))) return - this.setState({ - temperature, isSuggestion: false, - outOfRangeWarning: makeOutOfRangeWarningMessage(temperature) - }) + this.setState({ temperature }) } setNote = (note) => { this.setState({ note }) } - showTimePicker = () => { - Keyboard.dismiss() - this.setState({ isTimePickerVisible: true }) - } - renderContent() { - const inputStyle = [styles.temperatureTextInput] - if (this.state.isSuggestion) { - inputStyle.push(styles.temperatureTextInputSuggestion) - } + const { temperature } = this.state + return ( - - - °C - - {this.state.outOfRangeWarning && - - {this.state.outOfRangeWarning} - - } + - - - - { - this.setState({ - time: padWithZeros(jsDate), - isTimePickerVisible: false - }) - }} - onCancel={() => this.setState({ isTimePickerVisible: false })} - /> - + + { export default connect( mapStateToProps, null -)(Temp) - -function makeOutOfRangeWarningMessage(temperature) { - if (temperature === '') return - const value = Number(temperature) - const { min, max } = config.temperatureScale - const range = { min, max } - const scale = scaleObservable.value - let warningMsg - - if (value < range.min || value > range.max) { - warningMsg = labels.outOfAbsoluteRangeWarning - } else if (value < scale.min || value > scale.max) { - warningMsg = labels.outOfRangeWarning - } else { - warningMsg = null - } - - return warningMsg -} \ No newline at end of file +)(Temperature) diff --git a/components/cycle-day/symptoms/time-input.js b/components/cycle-day/symptoms/time-input.js new file mode 100644 index 0000000..2848eb4 --- /dev/null +++ b/components/cycle-day/symptoms/time-input.js @@ -0,0 +1,62 @@ +import React, { Component } from 'react' +import PropTypes from 'prop-types' +import { Keyboard } from 'react-native' + +import AppTextInput from '../../app-text-input' +import styles from '../../../styles' + +import DateTimePicker from 'react-native-modal-datetime-picker-nevo' +import moment from 'moment' + +export default class TimeInput extends Component { + + static propTypes = { + time: PropTypes.string, + handleTimeChange: PropTypes.func, + } + + constructor(props) { + super(props) + + this.state = { + isTimePickerVisible: false, + } + + } + + showTimePicker = () => { + Keyboard.dismiss() + this.setState({ isTimePickerVisible: true }) + } + + hideTimePicker = () => { + this.setState({ isTimePickerVisible: false }) + } + + handleConfirm = (jsDate) => { + // DateTimePicker also when in mode="time" returns full date (with time) + const time = moment(jsDate).format('HH:mm') + this.props.handleTimeChange(time) + this.setState({ + isTimePickerVisible: false + }) + } + + render () { + return ( + + + + + ) + } +}