Commit a0e5e515 authored by Florent Chehab's avatar Florent Chehab

Displaying univ scholarships ok

parent 7e101126
......@@ -26,7 +26,7 @@ import MoreTab from './tabs/MoreTab';
function TabContainer(props) {
let style = { padding: 8 * 3 };
if (!props.display) {
if (props.visible === false) {
style = { display: 'none' }
}
return (
......@@ -91,10 +91,10 @@ class UniversityTemplate extends React.Component {
<Tab label="Autres" icon={<MoreHorizIcon />} />
</Tabs>
</AppBar>
<TabContainer display={value === 0}> <GeneralInfoTab univId={univId} visible={value === 0}/> </TabContainer>
{/* {value === 1 && <TabContainer> <UniversityMoreTab univId={univId} /> </TabContainer>} */}
<TabContainer visible={value === 0}> <GeneralInfoTab univId={univId} visible={value === 0} /> </TabContainer>
{/* {<TabContainer visible={value === 1}> <UniversityMoreTab univId={univId} visible={value === 1} /> </TabContainer>} */}
{/* {value === 2 && <TabContainer> <PreviousDeparturesTab univId={univId} /> </TabContainer>} */}
{/* {value === 3 && <TabContainer> <ScholarshipsTab univId={univId} /> </TabContainer>} */}
{<TabContainer visible={value === 3}> <ScholarshipsTab univId={univId} visible={value === 3} /> </TabContainer>}
{/* {value === 4 && <TabContainer> <CampusesCitiesTab univId={univId} /> </TabContainer>} */}
{/* {value === 5 && <TabContainer> <MoreTab univId={univId} /> </TabContainer>} */}
</div>
......
import React from 'react';
import PropTypes from 'prop-types';
import withStyles from '@material-ui/core/styles/withStyles';
import compose from 'recompose/compose';
import { connect } from "react-redux";
import Editor from '../shared/Editor';
import editorStyle from '../shared/editorStyle';
import getMapStateToPropsForEditor from '../shared/editorFunctions/getMapStateToPropsForEditor';
import getMapDispatchToPropsForEditor from '../shared/editorFunctions/getMapDispatchToPropsForEditor';
import {
universityScholarshipsElSaveData,
universityScholarshipsElSavingHasError
} from '../../../generated/actions';
const styles = theme => ({
...editorStyle(theme)
});
class UniversityScholarshipsEditor extends Editor {
renderEditor() {
const { modelData } = this.props;
return (
<div>
{this.renderObjModerationLevelField()}
{this.renderTitleField()}
{this.renderUniversitiesField()}
{this.renderCommentField()}
{this.renderUsefulLinksField()}
</div>
)
}
}
UniversityScholarshipsEditor.propTypes = {
modelData: PropTypes.object.isRequired,
};
export default compose(
withStyles(styles, { withTheme: true }),
connect(
getMapStateToPropsForEditor('universityScholarshipsEl'),
getMapDispatchToPropsForEditor(universityScholarshipsElSaveData, universityScholarshipsElSavingHasError)
)
)(UniversityScholarshipsEditor);
\ No newline at end of file
import React from 'react';
import PropTypes from 'prop-types';
import withStyles from '@material-ui/core/styles/withStyles';
import compose from 'recompose/compose';
import { connect } from "react-redux";
import __pick from 'lodash/pick';
import MyComponent from '../../MyComponent';
import GenericModule from '../shared/GenericModule';
import GenericGroupModule from '../shared/GenericGroupModule';
import Scholarship from '../shared/Scholarship';
import UniversityScholarshipsEditor from '../editors/UniversityScholarshipsEditor';
import {
universityScholarshipsFetchData,
universityScholarshipsInvalidated,
} from '../../../generated/actions';
const styles = theme => ({
});
function renderCore(rawModelData, classes, outsideData) {
const { comment, frequency, currency, type } = rawModelData;
const amountMin = rawModelData.amount_min,
amountMax = rawModelData.amount_max,
otherAdvantages = rawModelData.other_advantages;
return (
<Scholarship
currency={currency}
currencies={outsideData.currencies}
frequency={frequency}
type={type}
amountMin={amountMin}
amountMax={amountMax}
otherAdvantages={otherAdvantages}
comment={comment}
/>
)
}
function parseRawModelData(rawModelData) {
// reverse serialization
const modelData = __pick(rawModelData,
[
"id",
"title",
"type",
"currency",
"frequency",
"amount_min",
"amount_max",
// "importance_level",
"universities",
"comment",
"other_advantages",
"useful_links",
"obj_moderation_level",
]);
return modelData;
}
class UniversityScholarships extends MyComponent {
ignoreInvalidation = true;
componentWillUnmount() {
this.props.invalidateData(true);
}
myComponentDidUpdate() {
if (this.props.universityScholarships.invalidated && !this.props.universityScholarships.isLoading) {
this.props.fetchData.universityScholarships(this.props.univId);
}
}
myRender() {
const univScholarshipsItems = this.getFetchedData('universityScholarships');
const { universities, currencies, classes } = this.props;
const outsideData = {
universities,
currencies
}
return (
<GenericGroupModule
groupTitle={"Bourses liées à l'université"}
endPoint={"universityScholarship"}
editor={UniversityScholarshipsEditor}
invalidateGroup={this.props.invalidateData}
propsForEditor={{
modelData: { universities: [this.props.univId], importance_level: '-' },
parseRawModelData: parseRawModelData,
outsideData: outsideData,
__apiAttr: this.props.univId,
}}
>
{
univScholarshipsItems.map((rawModelData) => (
<GenericModule
visible={this.props.visible}
buildTitle={(modelData) => modelData.title}
rawModelData={rawModelData}
parseRawModelData={parseRawModelData}
editor={UniversityScholarshipsEditor}
renderCore={renderCore}
coreClasses={classes}
outsideData={outsideData}
moduleInGroupInfos={{ isInGroup: true, invalidateGroup: () => this.props.invalidateData() }}
__apiAttr={this.props.univId}
/>
))
}
</GenericGroupModule >
)
}
__apiAttr = { universityScholarships: "univId" };
}
UniversityScholarships.propTypes = {
classes: PropTypes.object.isRequired,
theme: PropTypes.object.isRequired,
univId: PropTypes.string.isRequired,
universities: PropTypes.object.isRequired,
};
const mapStateToProps = (state) => {
return {
universityScholarships: state.universityScholarships,
};
};
const mapDispatchToProps = (dispatch) => {
return {
fetchData: {
universityScholarships: (univId) => dispatch(universityScholarshipsFetchData(univId)),
},
invalidateData: (resetObj = false) => dispatch(universityScholarshipsInvalidated(true, resetObj))
};
};
export default compose(
withStyles(styles, { withTheme: true }),
connect(mapStateToProps, mapDispatchToProps)
)(UniversityScholarships);
\ No newline at end of file
......@@ -11,6 +11,7 @@ import {
universitiesFetchData,
citiesFetchData,
countriesFetchData,
currenciesFetchData,
mainCampusesFetchData,
} from '../../../generated/actions';
......@@ -20,6 +21,7 @@ class InfoProvider extends MyComponent {
const { city, country } = this.getUnivCityAndCountry(this.props.univId);
const universities = this.getFetchedData('universities');
const countries = this.getFetchedData('countries');
const currencies = this.getFetchedData('currencies');
let propsToAdd = { univId: this.props.univId, visible: this.props.visible };
......@@ -33,6 +35,9 @@ class InfoProvider extends MyComponent {
case 'countries':
propsToAdd[key] = countries;
break;
case 'currencies':
propsToAdd[key] = currencies;
break;
case 'city':
propsToAdd[key] = city;
break;
......@@ -67,6 +72,7 @@ const mapStateToProps = (state) => {
return {
countries: state.countries,
cities: state.cities,
currencies: state.currencies,
mainCampuses: state.mainCampuses,
universities: state.universities,
};
......@@ -77,6 +83,7 @@ const mapDispatchToProps = (dispatch) => {
fetchData: {
countries: () => dispatch(countriesFetchData()),
cities: () => dispatch(citiesFetchData()),
currencies: () => dispatch(currenciesFetchData()),
mainCampuses: () => dispatch(mainCampusesFetchData()),
universities: () => dispatch(universitiesFetchData()),
},
......
......@@ -2,26 +2,8 @@ import React from 'react';
import PropTypes from 'prop-types';
import withStyles from '@material-ui/core/styles/withStyles';
import Table from '@material-ui/core/Table';
import TableBody from '@material-ui/core/TableBody';
import TableCell from '@material-ui/core/TableCell';
import TableHead from '@material-ui/core/TableHead';
import TableRow from '@material-ui/core/TableRow';
import Markdown from '../../shared/Markdown';
import Typography from '@material-ui/core/Typography';
import ArrowForwardIosIcon from '@material-ui/icons/ArrowForwardIos';
import ArrowBackwardIosIcon from '@material-ui/icons/ArrowBackIos';
import PersonIcon from '@material-ui/icons/Person';
import MyComponent from '../../MyComponent';
import TextLink from '../../other/TextLink';
import GenericModule from '../shared/GenericModule';
import Grid from '@material-ui/core/Grid';
import Divider from '@material-ui/core/Divider';
const styles = theme => {
const textAmountsVariant = 'title';
......@@ -54,79 +36,123 @@ const styles = theme => {
}
};
// function renderTypography(str) {
// return (
// <Typography variant='title' color="textSecondary">str</Typography>
// );
// }
// function renderAmount(amount, currency) {
// if (currency == 'EUR') {
// return String(amount) + '€';
// } else {
// return String(amount) + ' ' + currency;
// }
// }
// function renderAmounts() {
// const { amountMin, amountMax, currency, frequency, theme } = this.props;
// let output = renderAmount(amountMin, currency) + ' – ' + renderAmount(amountMax, currency);
// if (amountMin == amountMax) {
// return (
// renderTypography(renderAmount(amountMin, currency))
// renderTypography('/semestre')
// )
// } else {
// return (
// <div>
// </div>
// )
// }
// if (currency != 'EUR') {
// output += ' (~ ' + renderAmount(amountMin, 'EUR') + ' – ' + renderAmount(amountMax, 'EUR') + ')';
// }
// output += ' /'+frequency.toLowerCase();
// return output;
// if (amountMin == amountMax) {
// return (
// <Typography variant='title' color="textSecondary">{renderAmount(amountMin, amountCurrency)}</Typography>
// )
// } else {
// return (
// <Typography variant='caption'>Mis à jour par <em>chehabfl</em> le 08/09/2018 à 15h20</Typography>
// )
// }
// }
class Scholarship extends React.Component {
getFrequency() {
const table = {
w: '/semaine',
m: '/mois',
s: '/semestre',
y: '/année',
o: '(une seule fois)'
}
const { frequency } = this.props;
return table[frequency];
}
getSymbol() {
const { currencies, currency } = this.props;
const currencyInfo = currencies[currency];
const { symbol } = currencyInfo;
if (symbol) {
return symbol;
} else {
return ' '+currency;
}
}
convertAmountToEur(amount) {
const { currencies, currency } = this.props;
const rate = currencies[currency].one_EUR_in_this_currency;
return Math.trunc(amount / rate);
}
getAmounts() {
const { amountMin, amountMax } = this.props;
if (amountMax != null && amountMax != amountMin) {
return `${amountMin}${this.getSymbol()}${amountMax}${this.getSymbol()}`;
} else {
return `${amountMin}${this.getSymbol()}`;
}
}
getConvertedAmounts() {
const { amountMin, amountMax } = this.props;
if (amountMax != null && amountMax != amountMin) {
return `${this.convertAmountToEur(amountMin)}€ – ${this.convertAmountToEur(amountMax)}€`;
} else {
return `${this.convertAmountToEur(amountMin)}€`;
}
}
renderFinancialAdvantage() {
const { amountMin, currency, classes } = this.props;
return (
<div>
<Typography className={classes.item} variant='headline'> Avantage financier : </Typography>
{
amountMin !== null ? (
<div>
<Typography className={classes.textAmount}> {this.getAmounts()}{' '}{this.getFrequency()}</Typography>
{
currency != 'EUR' ?
<Typography variant='caption' ><em>( {this.getConvertedAmounts()}{' '}{this.getFrequency()})</em></Typography>
:
<div></div>
}
</div>
) : (
<Typography variant='caption'><em>Aucun avantage financier est notifié.</em></Typography>
)
}
</div>
)
}
renderOtherAdvantages() {
const { classes, otherAdvantages } = this.props;
return (
<div>
<Typography className={classes.item} variant='headline' > Autre(s) avantage(s) : </Typography>
{
otherAdvantages != '' ?
<Markdown source={otherAdvantages} />
:
<Typography variant='caption'><em>Aucun autre avantage a été notifié.</em></Typography>
}
</div>
)
}
render() {
const { classes, theme } = this.props;
const comment = 'Mon commentaire des familles';
const { comment } = this.props
return (
<GenericModule title={"Bourse Mermoz"} usefulLinks={[{ description: "ENT", url: "https://epfl.ch" }]}>
<Typography className={classes.item} variant='headline'> Avantage financier : </Typography>
<Typography className={classes.textAmount} >300 CHF 400 CHF /mois</Typography>
<Typography variant='caption' ><em>( 300 400 /mois)</em></Typography>
<div>
{this.renderFinancialAdvantage()}
<div style={{ height: 2 * theme.spacing.unit }} />
<Typography className={classes.item} variant='headline' > Autres avantages : </Typography>
<Markdown source={comment} />
{this.renderOtherAdvantages()}
<Typography className={classes.item} variant='headline'> Informations complémentaires : </Typography>
<Markdown source={comment} />
</GenericModule >
</div>
)
}
}
Scholarship.defaultProps = {
amountMin: 0,
amountMax: 200,
frequency: 'Semestre',
currency: 'CHF',
Scholarship.propTypes = {
classes: PropTypes.object.isRequired,
theme: PropTypes.object.isRequired,
currency: PropTypes.string.isRequired,
frequency: PropTypes.string.isRequired,
type: PropTypes.string.isRequired,
comment: PropTypes.string.isRequired,
otherAdvantages: PropTypes.string.isRequired,
amountMin: PropTypes.string,
amountMax: PropTypes.string,
};
export default withStyles(styles, { withTheme: true })(Scholarship);
......@@ -41,12 +41,14 @@ class GeneralInfoTab extends MyComponent {
<Grid container direction='column' >
<Grid item xs style={{ paddingBottom: 2 * theme.spacing.unit }} >
<InfoProvider
add={['city', 'country']}
univId={this.props.univId}
renderAndAddPropsTo={UniversityGeneral}
/>
</Grid>
<Grid item xs>
<InfoProvider
add={['universities']}
univId={this.props.univId}
renderAndAddPropsTo={UniversityDri}
/>
......@@ -54,6 +56,7 @@ class GeneralInfoTab extends MyComponent {
<Grid item xs>
<InfoProvider
univId={this.props.univId}
add={['countries', 'countryId']}
renderAndAddPropsTo={CountryDri}
/>
</Grid>
......@@ -80,6 +83,7 @@ class GeneralInfoTab extends MyComponent {
<Grid item xs={12}>
<InfoProvider
add={['city', 'country']}
univId={this.props.univId}
renderAndAddPropsTo={UniversityGeneral}
/>
......@@ -87,11 +91,13 @@ class GeneralInfoTab extends MyComponent {
<Grid item xs={12}>
<InfoProvider
univId={this.props.univId}
add={['universities']}
renderAndAddPropsTo={UniversityDri}
/>
</Grid>
<Grid item xs={12}>
<InfoProvider
add={['countries', 'countryId']}
univId={this.props.univId}
renderAndAddPropsTo={CountryDri}
/>
......
......@@ -2,33 +2,56 @@ import React from 'react';
import PropTypes from 'prop-types';
import withStyles from '@material-ui/core/styles/withStyles';
import MyComponent from '../../MyComponent';
import compose from 'recompose/compose';
import GenericGroupModules from '../shared/GenericGroupModule';
import Scholarship from '../modules/Scholarship';
import Grid from '@material-ui/core/Grid';
import UniversityScholarships from '../modules/UniversityScholarships';
import UniversityDri from '../modules/UniversityDri';
import InfoProvider from '../shared/InfoProvider';
const styles = theme => ({
root: {},
root: {
display: 'flex',
width: "90%",
marginLeft: "auto",
marginRight: "auto"
},
});
class ScholarshipsTab extends MyComponent {
myRender() {
const { classes, theme } = this.props;
return (
<div>
<GenericGroupModules groupTitle={"Bourse(s) qui concerne 'le pays'"}>
<Scholarship/>
<Scholarship/>
</GenericGroupModules>
<GenericGroupModules groupTitle={"Bourse(s) qui concerne l'université"} />
<div className={classes.root}>
<Grid container spacing={16} >
<Grid item xs={12}>
<InfoProvider
univId={this.props.univId}
add={['universities', 'currencies']}
renderAndAddPropsTo={UniversityScholarships}
/>
</Grid>
</Grid>
</div>
);
}
}
// ScholarshipsTab.propTypes = {
// classes: PropTypes.object.isRequired,
// univId: PropTypes.string.isRequired,
// };
ScholarshipsTab.propTypes = {
classes: PropTypes.object.isRequired,
theme: PropTypes.object.isRequired,
univId: PropTypes.string.isRequired
};
export default withStyles(styles)(ScholarshipsTab);
\ No newline at end of file
export default compose(
withStyles(styles, { withTheme: true }),
)(ScholarshipsTab);
\ No newline at end of file
......@@ -11,9 +11,13 @@ import {
userDataElReducers,
universitiesInfoElReducers,
universityDriReducers,
universityDriElReducers,
universityDriElReducers,
universityScholarshipsReducers,
universityScholarshipsElReducers,
countryDriReducers,
countryDriElReducers,
countryScholarshipsReducers,
countryScholarshipsElReducers,
universitiesSemestersDatesElReducers,
serverModerationStatusReducers,
versionsReducers,
......@@ -45,8 +49,12 @@ const rootReducer = combineReducers({
universitiesSemestersDatesEl: universitiesSemestersDatesElReducers,
universityDri: universityDriReducers,
universityDriEl: universityDriElReducers,
universityScholarships: universityScholarshipsReducers,
universityScholarshipsEl: universityScholarshipsElReducers,
countryDri: countryDriReducers,
countryDriEl: countryDriElReducers,
countryScholarships: countryScholarshipsReducers,
countryScholarshipsEl: countryScholarshipsElReducers,
currencies: currenciesReducers,
mainCampuses: mainCampusesReducers,
userDataEl: userDataElReducers,
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment