diff --git a/src/assets/images/profile/ico-edit.svg b/src/assets/images/profile/ico-edit.svg new file mode 100644 index 0000000000..b3e37a33dc --- /dev/null +++ b/src/assets/images/profile/ico-edit.svg @@ -0,0 +1,6 @@ + + + + + + diff --git a/src/assets/images/tools/device-types/ico-edit.svg b/src/assets/images/tools/device-types/ico-edit.svg new file mode 100644 index 0000000000..b3e37a33dc --- /dev/null +++ b/src/assets/images/tools/device-types/ico-edit.svg @@ -0,0 +1,6 @@ + + + + + + diff --git a/src/assets/images/tools/service-provider-types/ico-edit.svg b/src/assets/images/tools/service-provider-types/ico-edit.svg new file mode 100644 index 0000000000..b3e37a33dc --- /dev/null +++ b/src/assets/images/tools/service-provider-types/ico-edit.svg @@ -0,0 +1,6 @@ + + + + + + diff --git a/src/assets/images/tools/software-types/ico-edit.svg b/src/assets/images/tools/software-types/ico-edit.svg new file mode 100644 index 0000000000..b3e37a33dc --- /dev/null +++ b/src/assets/images/tools/software-types/ico-edit.svg @@ -0,0 +1,6 @@ + + + + + + diff --git a/src/assets/images/tools/subscription-types/ico-edit.svg b/src/assets/images/tools/subscription-types/ico-edit.svg new file mode 100644 index 0000000000..b3e37a33dc --- /dev/null +++ b/src/assets/images/tools/subscription-types/ico-edit.svg @@ -0,0 +1,6 @@ + + + + + + diff --git a/src/shared/components/Settings/CofirmationModal/index.jsx b/src/shared/components/Settings/CofirmationModal/index.jsx index 6bf41b5347..d97fd8164e 100644 --- a/src/shared/components/Settings/CofirmationModal/index.jsx +++ b/src/shared/components/Settings/CofirmationModal/index.jsx @@ -4,15 +4,14 @@ import { Modal, PrimaryButton, GhostButton } from 'topcoder-react-ui-kit'; import modal from './styles.scss'; export default function ConfirmationModal(props) { - const { onConfirm, onCancel } = props; + const { onConfirm, onCancel, name } = props; return (
-
Heads Up!
+
HEADS UP!
- Are you sure you want to delete? This action can't be undone - later. + Are you sure you want to delete `{name}`? This action can't be undone.
@@ -31,4 +30,5 @@ export default function ConfirmationModal(props) { ConfirmationModal.propTypes = { onConfirm: PT.func.isRequired, onCancel: PT.func.isRequired, + name: PT.string.isRequired, }; diff --git a/src/shared/components/Settings/ErrorMessage/index.jsx b/src/shared/components/Settings/ErrorMessage/index.jsx new file mode 100644 index 0000000000..a26d8d81c4 --- /dev/null +++ b/src/shared/components/Settings/ErrorMessage/index.jsx @@ -0,0 +1,30 @@ +import React from 'react'; +import PropTypes from 'prop-types'; + +import './styles.scss'; + +const marginTop = (value) => { + if (value) { + return 'active-margin'; + } + + return 'active'; +}; + +const ErrorMessage = ({ invalid, message, addMargin }) => ( + + {message} + +); + +ErrorMessage.defaultProps = { + addMargin: false, +}; + +ErrorMessage.propTypes = { + invalid: PropTypes.bool.isRequired, + message: PropTypes.string.isRequired, + addMargin: PropTypes.bool, +}; + +export default ErrorMessage; diff --git a/src/shared/components/Settings/ErrorMessage/styles.scss b/src/shared/components/Settings/ErrorMessage/styles.scss new file mode 100644 index 0000000000..1e629638b2 --- /dev/null +++ b/src/shared/components/Settings/ErrorMessage/styles.scss @@ -0,0 +1,27 @@ +@import "../style"; + +.error-message { + display: none; + + &.active { + @include roboto-medium; + + display: inline; + border-radius: 5px; + background-color: $tc-red-10; + color: $tc-red-110; + font-size: 15px; + margin: 0 auto 0 0; + } + + &.active-margin { + @include roboto-medium; + + display: inline; + border-radius: 5px; + background-color: $tc-red-10; + color: $tc-red-110; + font-size: 15px; + margin: 10px auto 0 0; + } +} diff --git a/src/shared/components/Settings/Profile/BasicInfo/index.jsx b/src/shared/components/Settings/Profile/BasicInfo/index.jsx index e9741c941d..c1df0e3398 100644 --- a/src/shared/components/Settings/Profile/BasicInfo/index.jsx +++ b/src/shared/components/Settings/Profile/BasicInfo/index.jsx @@ -15,12 +15,14 @@ import { PrimaryButton } from 'topcoder-react-ui-kit'; import ConsentComponent from 'components/Settings/ConsentComponent'; import Select from 'components/Select'; import DatePicker from 'components/challenge-listing/Filters/DatePicker'; +import ErrorMessage from 'components/Settings/ErrorMessage'; import ImageInput from '../ImageInput'; import Track from './Track'; import DefaultImageInput from './ImageInput'; import dropdowns from './dropdowns.json'; import tracks from './tracks'; + import './styles.scss'; export default class BasicInfo extends ConsentComponent { @@ -41,7 +43,6 @@ export default class BasicInfo extends ConsentComponent { this.state = { inputChanged: false, formInvalid: false, - errorMessage: '', basicInfoTrait: this.loadBasicInfoTraits(userTraits), personalizationTrait: this.loadPersonalizationTrait(userTraits), newBasicInfo: { @@ -98,46 +99,26 @@ export default class BasicInfo extends ConsentComponent { onCheckFormValue(newBasicInfo) { let invalid = false; - let errorMessage = ''; - let dateError = ''; - let birthDateInvalid = false; - const invalidFields = []; if (!_.trim(newBasicInfo.firstName).length) { - invalidFields.push('First Name'); invalid = true; } if (!_.trim(newBasicInfo.lastName).length) { - invalidFields.push('Last Name'); invalid = true; } if (!_.trim(newBasicInfo.country).length) { - invalidFields.push('Country'); invalid = true; } - if (invalidFields.length > 0) { - errorMessage += invalidFields.join(', '); - errorMessage += ' cannot be empty'; - } - if (_.trim(newBasicInfo.birthDate).length > 0) { if (!moment().isAfter(newBasicInfo.birthDate)) { - dateError = 'You must enter a valid date for Birth Date'; - birthDateInvalid = true; + invalid = true; } } - if (errorMessage.length > 0) { - errorMessage = `${errorMessage}. ${dateError}`; - } else if (dateError.length > 0) { - errorMessage = dateError; - invalid = birthDateInvalid; - } - - this.setState({ errorMessage, formInvalid: invalid }); + this.setState({ formInvalid: invalid }); return invalid; } @@ -170,7 +151,7 @@ export default class BasicInfo extends ConsentComponent { */ onHandleSaveBasicInfo(e) { e.preventDefault(); - this.setState({ isSaving: true }); + this.setState({ isSaving: true, inputChange: true }); const { newBasicInfo } = this.state; if (this.onCheckFormValue(newBasicInfo)) { this.setState({ isSaving: false }); @@ -465,8 +446,7 @@ export default class BasicInfo extends ConsentComponent { render() { const { newBasicInfo, - formInvalid, - errorMessage, + inputChanged, } = this.state; const canModifyTrait = !this.props.traitRequestCount; @@ -507,6 +487,7 @@ export default class BasicInfo extends ConsentComponent {
* Required +
@@ -519,6 +500,7 @@ export default class BasicInfo extends ConsentComponent {
* Required +
@@ -619,6 +601,7 @@ export default class BasicInfo extends ConsentComponent { disabled={!canModifyTrait} clearable={false} /> +
@@ -745,6 +728,7 @@ export default class BasicInfo extends ConsentComponent { +
+
@@ -826,6 +811,7 @@ export default class BasicInfo extends ConsentComponent { clearable={false} disabled={!canModifyTrait} /> +
@@ -931,9 +917,6 @@ export default class BasicInfo extends ConsentComponent { }
-
- {errorMessage} -
{ + if (_.isEmpty(education.timePeriodFrom) && _.isEmpty(education.timePeriodTo) + && !education.graduated) { + return false; + } + + return true; + }; + + const getDate = () => { + let start = ''; + if (!_.isEmpty(education.timePeriodFrom)) { + start = moment(education.timePeriodFrom).format('YYYY'); + } + let end = ''; + if (!_.isEmpty(education.timePeriodTo)) { + end = moment(education.timePeriodTo).format('YYYY'); + } + + if (_.isEmpty(start) && _.isEmpty(end)) { + return ''; + } + + if (!_.isEmpty(start) && !_.isEmpty(end)) { + return `${start} - ${end} `; + } + + if (!_.isEmpty(start) && _.isEmpty(end)) { + return `${start} `; + } + + if (_.isEmpty(start) && !_.isEmpty(end)) { + return `${end} `; + } + + return ''; + }; + + const getGraduated = () => { + const date = getDate(); + if (!_.isEmpty(date)) { + if (education.graduated) { + return '| Graduated'; + } + + return ''; + } + + if (education.graduated) { + return 'Graduated'; + } + return ''; + }; + return (
-
-
- { `${education.schoolCollegeName} ${education.type}` } -
-
- { `${moment(education.timePeriodFrom).format('YYYY')} - ${moment(education.timePeriodTo).format('YYYY')}${education.graduated ? ' | Graduated' : ''}` } -
-
-

- {`${moment(education.timePeriodFrom).format('YYYY')} - ${moment(education.timePeriodTo).format('YYYY')}`} -

- { - education.graduated && ( -

- Graduated -

- ) - } +
+
+ { `${education.schoolCollegeName}` }
+ { + hasSecondLine() && ( + +
+ { + `${getDate()}${getGraduated()}` + } +
+
+ { + !_.isEmpty(getDate()) && ( +

+ {`${getDate()}`} +

+ ) + } + { + education.graduated && ( +

+ Graduated +

+ ) + } +
+
+ ) + }
- onDeleteItem(index)} - tabIndex={0} - role="button" - onClick={() => onDeleteItem(index)} - > - delete-icon -

- Delete -

-
+
); } @@ -68,4 +150,5 @@ Item.propTypes = { education: PT.shape().isRequired, index: PT.number.isRequired, onDeleteItem: PT.func.isRequired, + onEditItem: PT.func.isRequired, }; diff --git a/src/shared/components/Settings/Profile/Education/List/Item/styles.scss b/src/shared/components/Settings/Profile/Education/List/Item/styles.scss index 1f9610afa3..2f9a2117a3 100644 --- a/src/shared/components/Settings/Profile/Education/List/Item/styles.scss +++ b/src/shared/components/Settings/Profile/Education/List/Item/styles.scss @@ -36,6 +36,11 @@ line-height: 20px; text-transform: capitalize; padding-right: 20px; + + &.single-line { + flex-direction: row; + align-items: center; + } } .parameter-first-line { @@ -44,6 +49,10 @@ margin-bottom: 10px; word-break: break-all; + &.single-line { + margin-bottom: 0; + } + @include upto-sm { margin-bottom: 0; } @@ -74,32 +83,70 @@ } } -.delete { +.operation-container { display: flex; - flex-direction: column; - justify-items: center; - justify-content: center; - cursor: pointer; - outline-style: none; + flex-direction: row; + justify-content: space-between; - img { - margin-bottom: 10px; + .delete { + display: flex; + flex-direction: column; + justify-items: center; + justify-content: center; + cursor: pointer; + outline-style: none; + margin-left: 10px; + + img { + margin-bottom: 10px; + + @include upto-sm { + margin-bottom: 0; + } + } + + p { + @include roboto-regular; - @include upto-sm { - margin-bottom: 0; + font-size: 11px; + line-height: 15px; + font-weight: 400; + color: $tc-gray-50; + + @include upto-sm { + display: none; + } } } - p { - @include roboto-regular; + .edit { + display: flex; + flex-direction: column; + align-items: center; + justify-content: center; + cursor: pointer; + outline-style: none; + margin-left: 10px; + + img { + margin-bottom: 10px; + + @include upto-sm { + margin-bottom: 0; + } + } - font-size: 11px; - line-height: 15px; - font-weight: 400; - color: $tc-gray-50; + p { + @include roboto-regular; + + font-size: 11px; + line-height: 15px; + font-weight: 400; + color: $tc-gray-50; - @include upto-sm { - display: none; + @include upto-sm { + display: none; + } } } } diff --git a/src/shared/components/Settings/Profile/Education/List/index.jsx b/src/shared/components/Settings/Profile/Education/List/index.jsx index b8eaf68c7c..624afdc5f3 100644 --- a/src/shared/components/Settings/Profile/Education/List/index.jsx +++ b/src/shared/components/Settings/Profile/Education/List/index.jsx @@ -11,6 +11,7 @@ export default function EducationList(props) { const { educationList, onDeleteItem, + onEditItem, } = props; return ( @@ -19,7 +20,12 @@ export default function EducationList(props) { { educationList.items.map((education, index) => (
  • - +
  • )) } @@ -31,4 +37,5 @@ export default function EducationList(props) { EducationList.propTypes = { educationList: PT.shape().isRequired, onDeleteItem: PT.func.isRequired, + onEditItem: PT.func.isRequired, }; diff --git a/src/shared/components/Settings/Profile/Education/dropdowns.json b/src/shared/components/Settings/Profile/Education/dropdowns.json deleted file mode 100644 index 3821590f7a..0000000000 --- a/src/shared/components/Settings/Profile/Education/dropdowns.json +++ /dev/null @@ -1,12 +0,0 @@ -{ - "type": [ - { - "key": "type", - "name": "Secondary School" - }, - { - "key": "type", - "name": "University" - } - ] -} \ No newline at end of file diff --git a/src/shared/components/Settings/Profile/Education/index.jsx b/src/shared/components/Settings/Profile/Education/index.jsx index 326ce05fc5..ffc9d7cecb 100644 --- a/src/shared/components/Settings/Profile/Education/index.jsx +++ b/src/shared/components/Settings/Profile/Education/index.jsx @@ -10,11 +10,12 @@ import React from 'react'; import PT from 'prop-types'; import _ from 'lodash'; import moment from 'moment'; -import Select from 'components/Select'; import ConsentComponent from 'components/Settings/ConsentComponent'; import { PrimaryButton } from 'topcoder-react-ui-kit'; import DatePicker from 'components/challenge-listing/Filters/DatePicker'; -import dropdowns from './dropdowns.json'; +import ErrorMessage from 'components/Settings/ErrorMessage'; +import { validateStartDate, validateEndDate } from 'utils/settings'; +import ConfirmationModal from '../../CofirmationModal'; import EducationList from './List'; import './styles.scss'; @@ -25,6 +26,7 @@ export default class Education extends ConsentComponent { super(props); this.onHandleDeleteEducation = this.onHandleDeleteEducation.bind(this); this.onDeleteEducation = this.onDeleteEducation.bind(this); + this.onEditEducation = this.onEditEducation.bind(this); this.onUpdateSelect = this.onUpdateSelect.bind(this); this.loadEducationTrait = this.loadEducationTrait.bind(this); this.onUpdateInput = this.onUpdateInput.bind(this); @@ -33,23 +35,30 @@ export default class Education extends ConsentComponent { this.loadPersonalizationTrait = this.loadPersonalizationTrait.bind(this); this.updatePredicate = this.updatePredicate.bind(this); this.onUpdateDate = this.onUpdateDate.bind(this); + this.onCancelEditStatus = this.onCancelEditStatus.bind(this); const { userTraits } = props; this.state = { formInvalid: false, - errorMessage: '', + startDateInvalid: false, + startDateInvalidMsg: '', + endDateInvalid: false, + endDateInvalidMsg: '', educationTrait: this.loadEducationTrait(userTraits), personalizationTrait: this.loadPersonalizationTrait(userTraits), newEducation: { - type: '', schoolCollegeName: '', major: '', timePeriodFrom: '', timePeriodTo: '', graduated: false, }, + isSubmit: false, isMobileView: false, screenSM: 767, + isEdit: false, + indexNo: null, + showConfirmation: false, }; } @@ -65,9 +74,12 @@ export default class Education extends ConsentComponent { educationTrait, personalizationTrait, formInvalid: false, - errorMessage: '', + startDateInvalid: false, + startDateInvalidMsg: '', + endDateInvalid: false, + endDateInvalidMsg: '', + isSubmit: false, newEducation: { - type: '', schoolCollegeName: '', major: '', timePeriodFrom: '', @@ -88,71 +100,84 @@ export default class Education extends ConsentComponent { */ onCheckFormValue(newEducation) { let invalid = false; - let dateInvalid = false; - let errorMessage = ''; - let dateCount = 0; - let dateError = ''; - let haveDate = false; - - if (!_.trim(newEducation.type).length) { - errorMessage += 'Type, '; - invalid = true; - } if (!_.trim(newEducation.schoolCollegeName).length) { - errorMessage += 'Name, '; invalid = true; } - if (!_.trim(newEducation.major).length) { - errorMessage += 'Major, '; - invalid = true; - } + const fromDateValidResult = validateStartDate(newEducation.graduated, + newEducation.timePeriodFrom, newEducation.timePeriodTo); + const endDateValidResult = validateEndDate(newEducation.graduated, + newEducation.timePeriodFrom, newEducation.timePeriodTo); + const formInvalid = invalid || fromDateValidResult.invalid || endDateValidResult.invalid; - if (errorMessage.length > 0) { - errorMessage += ' cannot be empty'; - } + this.setState({ + formInvalid, + startDateInvalid: fromDateValidResult.invalid, + startDateInvalidMsg: fromDateValidResult.message, + endDateInvalidMsg: endDateValidResult.message, + endDateInvalid: endDateValidResult.invalid, + }); + return formInvalid; + } - const fromDate = new Date(newEducation.timePeriodFrom).getTime(); - const toDate = new Date(newEducation.timePeriodTo).getTime(); + onCheckStartDate() { + const { newEducation } = this.state; + const currentDate = new Date().setHours(0, 0, 0, 0); + const result = { + invalid: false, + message: '', + }; - if (fromDate > toDate) { - dateError += 'From Date value should be smaller than To Date value. '; - dateInvalid = true; - haveDate = true; - } + if (!_.isEmpty(newEducation.timePeriodFrom) && _.isEmpty(newEducation.timePeriodTo)) { + const fromDate = new Date(newEducation.timePeriodFrom).setHours(0, 0, 0, 0); - if (!haveDate) { - if (!_.trim(newEducation.timePeriodFrom).length) { - dateError += 'From Date, '; - dateInvalid = true; - dateCount += 1; + if (fromDate > currentDate) { + result.invalid = true; + result.message = 'Start Date should be in past or current'; } + } else if (!_.isEmpty(newEducation.timePeriodFrom) && !_.isEmpty(newEducation.timePeriodTo)) { + const fromDate = new Date(newEducation.timePeriodFrom).setHours(0, 0, 0, 0); + const toDate = new Date(newEducation.timePeriodTo).setHours(0, 0, 0, 0); - if (!_.trim(newEducation.timePeriodTo).length) { - dateError += 'To Date, '; - dateInvalid = true; - dateCount += 1; + if (fromDate > currentDate) { + result.invalid = true; + result.message = 'Start Date should be in past or current'; } - if (dateError.length > 0) { - dateError = `The ${dateError} ${dateCount > 1 ? 'are' : 'is'} incomplete or ${dateCount > 1 ? 'have' : 'has'} an invalid date.`; + + if (fromDate >= toDate) { + result.invalid = true; + result.message = 'Start Date should be before End Date'; } } + return result; + } - if (errorMessage.length > 0) { - errorMessage = `${errorMessage}. \n${dateError}`; - } else if (dateError.length > 0) { - errorMessage = dateError; - invalid = dateInvalid; - } + onCheckEndDate() { + const { newEducation } = this.state; + const currentDate = new Date().setHours(0, 0, 0, 0); + const result = { + invalid: false, + message: '', + }; + + if (!_.isEmpty(newEducation.timePeriodFrom) && !_.isEmpty(newEducation.timePeriodTo)) { + const toDate = new Date(newEducation.timePeriodTo).setHours(0, 0, 0, 0); - this.setState({ errorMessage, formInvalid: invalid }); - return invalid; + if (newEducation.graduated && (toDate > currentDate)) { + result.invalid = true; + result.message = 'End Date should be in past or current'; + } + } + return formInvalid; } onHandleDeleteEducation(indexNo) { - this.showConsent(this.onDeleteEducation.bind(this, indexNo)); + this.setState({ + showConfirmation: true, + indexNo, + }); } onUpdateDate(date, timePeriod) { @@ -160,7 +185,7 @@ export default class Education extends ConsentComponent { const { newEducation: oldEducation } = this.state; const newEducation = { ...oldEducation }; newEducation[timePeriod] = date; - this.setState({ newEducation }); + this.setState({ newEducation, isSubmit: false }); } } @@ -188,6 +213,43 @@ export default class Education extends ConsentComponent { } else { deleteUserTrait(handle, 'education', tokenV3); } + + this.setState({ + showConfirmation: false, + indexNo: null, + isSubmit: false, + isEdit: false, + formInvalid: false, + startDateInvalid: false, + startDateInvalidMsg: '', + endDateInvalid: false, + endDateInvalidMsg: '', + }); + } + + /** + * Edit Education by index + * @param indexNo the education index no + */ + onEditEducation(indexNo) { + const { educationTrait } = this.state; + this.setState({ + newEducation: { + schoolCollegeName: educationTrait.traits.data[indexNo].schoolCollegeName, + major: _.isEmpty(educationTrait.traits.data[indexNo].major) ? '' : educationTrait.traits.data[indexNo].major, + timePeriodFrom: _.isEmpty(educationTrait.traits.data[indexNo].timePeriodFrom) ? '' : educationTrait.traits.data[indexNo].timePeriodFrom, + timePeriodTo: _.isEmpty(educationTrait.traits.data[indexNo].timePeriodTo) ? '' : educationTrait.traits.data[indexNo].timePeriodTo, + graduated: educationTrait.traits.data[indexNo].graduated, + }, + isSubmit: false, + isEdit: true, + indexNo, + formInvalid: false, + startDateInvalid: false, + startDateInvalidMsg: '', + endDateInvalid: false, + endDateInvalidMsg: '', + }); } /** @@ -195,7 +257,9 @@ export default class Education extends ConsentComponent { * @param answer user consent answer value */ onAddEducation(answer) { - const { newEducation, personalizationTrait } = this.state; + const { + newEducation, personalizationTrait, isEdit, indexNo, + } = this.state; if (this.onCheckFormValue(newEducation)) { return; @@ -210,32 +274,46 @@ export default class Education extends ConsentComponent { const { educationTrait } = this.state; - newEducation.timePeriodFrom = new Date(newEducation.timePeriodFrom).getTime(); - newEducation.timePeriodTo = new Date(newEducation.timePeriodTo).getTime(); + const education = _.clone(newEducation); + if (_.isEmpty(education.major)) { + delete education.major; + } + if (_.isEmpty(education.timePeriodFrom)) { + delete education.timePeriodFrom; + } else { + education.timePeriodFrom = new Date(newEducation.timePeriodFrom).getTime(); + } + if (_.isEmpty(education.timePeriodTo)) { + delete education.timePeriodTo; + } else { + education.timePeriodTo = new Date(newEducation.timePeriodTo).getTime(); + } if (educationTrait.traits && educationTrait.traits.data.length > 0) { - const newEducationTrait = { ...educationTrait }; - newEducationTrait.traits.data.push(newEducation); - this.setState({ educationTrait: newEducationTrait }); + const newEducationTrait = _.cloneDeep(educationTrait); + if (isEdit) { + newEducationTrait.traits.data.splice(indexNo, 1); + } + newEducationTrait.traits.data.push(education); updateUserTrait(handle, 'education', newEducationTrait.traits.data, tokenV3); } else { const newEducations = []; - newEducations.push(newEducation); - const traits = { - data: newEducations, - }; - this.setState({ educationTrait: { traits } }); + newEducations.push(education); addUserTrait(handle, 'education', newEducations, tokenV3); } const empty = { - type: '', schoolCollegeName: '', major: '', timePeriodFrom: '', timePeriodTo: '', graduated: false, }; - this.setState({ newEducation: empty }); + this.setState({ + newEducation: empty, + isEdit: false, + indexNo: null, + isSubmit: false, + }); // save personalization if (_.isEmpty(personalizationTrait)) { const personalizationData = { userConsent: answer }; @@ -256,8 +334,20 @@ export default class Education extends ConsentComponent { onUpdateInput(e) { const { newEducation: oldEducation } = this.state; const newEducation = { ...oldEducation }; - newEducation[e.target.name] = e.target.type !== 'checkbox' ? e.target.value : e.target.checked; - this.setState({ newEducation }); + if (e.target.type !== 'checkbox') { + newEducation[e.target.name] = e.target.value; + } else { + newEducation[e.target.name] = e.target.checked; + if (e.target.checked) { // if graduated and toDate is in Future, nullify it + const toDate = new Date(newEducation.timePeriodTo).setHours(0, 0, 0, 0); + const currentDate = new Date().setHours(0, 0, 0, 0); + if (toDate > currentDate) { + newEducation.timePeriodTo = ''; + } + } + } + + this.setState({ newEducation, isSubmit: false }); } /** @@ -269,7 +359,7 @@ export default class Education extends ConsentComponent { const { newEducation: oldEducation } = this.state; const newEducation = { ...oldEducation }; newEducation[option.key] = option.name; - this.setState({ newEducation }); + this.setState({ newEducation, isSubmit: false }); } } @@ -280,6 +370,7 @@ export default class Education extends ConsentComponent { onHandleAddEducation(e) { e.preventDefault(); const { newEducation } = this.state; + this.setState({ isSubmit: true }); if (this.onCheckFormValue(newEducation)) { return; } @@ -311,6 +402,29 @@ export default class Education extends ConsentComponent { this.setState({ isMobileView: window.innerWidth <= screenSM }); } + onCancelEditStatus() { + const { isEdit } = this.state; + if (isEdit) { + this.setState({ + isEdit: false, + isSubmit: false, + indexNo: null, + newEducation: { + schoolCollegeName: '', + major: '', + timePeriodFrom: '', + timePeriodTo: '', + graduated: false, + }, + formInvalid: false, + startDateInvalid: false, + startDateInvalidMsg: '', + endDateInvalid: false, + endDateInvalidMsg: '', + }); + } + } + render() { const { settingsUI, @@ -318,13 +432,22 @@ export default class Education extends ConsentComponent { const { educationTrait, isMobileView, + isEdit, + showConfirmation, + indexNo, + formInvalid, + startDateInvalid, + startDateInvalidMsg, + endDateInvalid, + endDateInvalidMsg, + isSubmit, } = this.state; const tabs = settingsUI.TABS.PROFILE; const currentTab = settingsUI.currentProfileTab; const containerStyle = currentTab === tabs.EDUCATION ? '' : 'hide'; const educationItems = educationTrait.traits ? educationTrait.traits.data.slice() : []; - const { newEducation, formInvalid, errorMessage } = this.state; + const { newEducation } = this.state; return ( @@ -332,10 +455,19 @@ export default class Education extends ConsentComponent { { this.shouldRenderConsent() && this.renderConsent() } + { + showConfirmation && ( + this.showConsent(this.onDeleteEducation.bind(this, indexNo))} + onCancel={() => this.setState({ + showConfirmation: false, + indexNo: null, + })} + name={educationTrait.traits.data[indexNo].schoolCollegeName} + /> + ) + }
    -
    - { errorMessage } -

    Education

    @@ -347,98 +479,113 @@ export default class Education extends ConsentComponent { && ( ) }
    0 ? 'second' : 'first'}`}> - Add a new education + { + isEdit ? (Edit education) + : (Add a new education) + }
    -
    -
    - -
    -
    - * Required -
    * Required + { + isSubmit && formInvalid && ( + + ) + }
    -
    +
    - * Required
    -
    +
    - * Required this.onUpdateDate(date, 'timePeriodFrom')} placeholder="dd/mm/yyyy" /> + { + isSubmit && ( + + ) + }
    -
    +
    - * Required - this.onUpdateDate(date, 'timePeriodTo')} - placeholder="dd/mm/yyyy" - /> + { + newEducation.graduated ? ( + this.onUpdateDate(date, 'timePeriodTo')} + placeholder="dd/mm/yyyy" + /> + ) : ( + this.onUpdateDate(date, 'timePeriodTo')} + placeholder="dd/mm/yyyy" + allowFutureYear + /> + ) + } + { + isSubmit && ( + + ) + }
    @@ -467,45 +614,55 @@ export default class Education extends ConsentComponent {
    -
    - - Add education to your list - +
    +
    + + { + isEdit ? (Edit education to your list) + : (Add education to your list) + } + +
    + { + isEdit && ( +
    + + Cancel + +
    + ) + }

    - Add Education + { + isEdit ? (Edit Education) + : (Add Education) + }

    -
    - - + { + isSubmit && formInvalid && ( + + ) + }