Aides embauche : Implémente la logique d'affichage des cartes

pull/1368/head
Maxime Quandalle 2021-02-10 16:48:48 +01:00
parent 38e2f73a2e
commit 7ad3d5d885
7 changed files with 151 additions and 61 deletions

View File

@ -4,13 +4,16 @@ import { TrackerContext } from 'Components/utils/withTracker'
import Animate from 'Components/ui/animate'
import Banner from './Banner'
import { LinkButton } from 'Components/ui/Button'
import { useGetSearchParams } from './utils/useSearchParamsSimulationSharing'
import { useParamsFromSituation } from './utils/useSearchParamsSimulationSharing'
import { useSelector } from 'react-redux'
import { situationSelector } from 'Selectors/simulationSelectors'
export default function ShareSimulationBanner() {
const [opened, setOpened] = useState(false)
const { t } = useTranslation()
const tracker = useContext(TrackerContext)
const getSearchParams = useGetSearchParams()
const situation = useSelector(situationSelector)
const searchParams = useParamsFromSituation(situation)
const shareAPIAvailable = !!window?.navigator?.share
@ -19,7 +22,7 @@ export default function ShareSimulationBanner() {
window.location.origin,
window.location.pathname,
'?',
getSearchParams().toString(),
searchParams.toString(),
].join('')
const startSharing = () => {

View File

@ -13,7 +13,6 @@ import React from 'react'
import { Trans } from 'react-i18next'
import { useSelector } from 'react-redux'
import { firstStepCompletedSelector } from 'Selectors/simulationSelectors'
import useSearchParamsSimulationSharing from 'Components/utils/useSearchParamsSimulationSharing'
import ShareSimulationBanner from 'Components/ShareSimulationBanner'
type SimulationProps = {
@ -30,7 +29,6 @@ export default function Simulation({
showPeriodSwitch,
}: SimulationProps) {
const firstStepCompleted = useSelector(firstStepCompletedSelector)
const getShareSearchParams = useSearchParamsSimulationSharing()
return (
<>
@ -39,7 +37,7 @@ export default function Simulation({
{firstStepCompleted && (
<Animate.fromTop>
{results}
<ShareSimulationBanner getShareSearchParams={getShareSearchParams} />
<ShareSimulationBanner />
<Questions customEndMessages={customEndMessages} />
<br />
<PageFeedback

View File

@ -153,6 +153,9 @@
}
@media (min-width: 700px) {
.ui__.large.box-container {
grid-template-columns: repeat(2, 1fr);
}
.ui__.small.box-container {
grid-template-columns: repeat(4, 1fr);
}
@ -162,6 +165,9 @@
}
@media (min-width: 1000px) {
.ui__.large.box-container {
grid-template-columns: repeat(2, 1fr);
}
.ui__.full-width.small.box-container {
grid-template-columns: repeat(5, auto);
}

View File

@ -1,6 +1,6 @@
import { useEffect, useMemo, useState } from 'react'
import { useSelector, useDispatch } from 'react-redux'
import { RootState, SimulationConfig, Situation } from 'Reducers/rootReducer'
import { SimulationConfig, Situation } from 'Reducers/rootReducer'
import { useSearchParams } from 'Components/utils/useSearchParams'
import { useEngine } from 'Components/utils/EngineContext'
import {
@ -71,15 +71,13 @@ export default function useSearchParamsSimulationSharing() {
])
}
export const useGetSearchParams = () => {
export const useParamsFromSituation = (situation: Situation) => {
const engine = useEngine()
const situation = useSelector(situationSelector)
const dottedNameParamName = useMemo(
() => getRulesParamNames(engine.getParsedRules()),
[engine]
)
return () =>
getSearchParamsFromSituation(engine, situation, dottedNameParamName)
return getSearchParamsFromSituation(engine, situation, dottedNameParamName)
}
const objectifsOfConfig = (config: Partial<SimulationConfig>) =>

View File

@ -1,24 +1,19 @@
import { formatValue } from 'publicodes'
import useSimulationConfig from 'Components/utils/useSimulationConfig'
import Animate from 'Components/ui/animate'
import Conversation from 'Components/conversation/Conversation'
import { Questions } from 'Components/Simulation'
import { useEngine } from 'Components/utils/EngineContext'
import RuleLink from 'Components/RuleLink'
import { DottedName } from 'modele-social'
import { ThemeColorsContext } from 'Components/utils/colors'
import { useContext, useMemo } from 'react'
import { SimulationConfig, Situation } from 'Reducers/rootReducer'
import { situationSelector } from 'Selectors/simulationSelectors'
import { partition } from 'ramda'
import { useSimulationProgress } from 'Components/utils/useNextQuestion'
import { HiddenOptionContext } from 'Components/conversation/Question'
import useSearchParamsSimulationSharing, {
getRulesParamNames,
getSearchParamsFromSituation,
} from 'Components/utils/useSearchParamsSimulationSharing'
import Animate from 'Components/ui/animate'
import { ThemeColorsContext } from 'Components/utils/colors'
import { useEngine } from 'Components/utils/EngineContext'
import { SitePathsContext } from 'Components/utils/SitePathsContext'
import { useSimulationProgress } from 'Components/utils/useNextQuestion'
import { useParamsFromSituation } from 'Components/utils/useSearchParamsSimulationSharing'
import useSimulationConfig from 'Components/utils/useSimulationConfig'
import { DottedName } from 'modele-social'
import Engine, { formatValue } from 'publicodes'
import { partition } from 'ramda'
import { useContext, useMemo } from 'react'
import { Link } from 'react-router-dom'
import { SimulationConfig, Situation } from 'Reducers/rootReducer'
import styled from 'styled-components'
type AideDescriptor = {
title: string
@ -30,36 +25,42 @@ type AideDescriptor = {
// This could be moved into publicodes
const aides = [
{
title: 'Apprenti',
title: 'Apprenti ou contrat Pro jeune',
dottedName:
"contrat salarié . aides employeur . aide exceptionnelle à l'embauche d'apprentis",
situation: {
'contrat salarié . rémunération . brut de base': '1700 €/mois',
// 'contrat salarié': "'apprentissage'",
},
description:
"Pour l'embauche d'un apprenti ou d'un jeune en contrat de professionnalisation",
},
{
title: 'Jeune en CDI',
title: 'Jeune de -26 ans',
dottedName:
"contrat salarié . aides employeur . aide exceptionnelle à l'embauche des jeunes",
situation: {
'contrat salarié . rémunération . brut de base': '2300 €/mois',
// 'contrat salarié': "'CDI'",
'contrat salarié . rémunération . brut de base': '1700 €/mois',
"contrat salarié . aides employeur . aide exceptionnelle à l'embauche des jeunes . jeune de moins de 26 ans":
'oui',
},
},
{
title: 'Jeune en CDD',
dottedName:
"contrat salarié . aides employeur . aide exceptionnelle à l'embauche des jeunes",
title: 'Emploi franc',
dottedName: 'contrat salarié . aides employeur . emploi franc',
situation: {
'contrat salarié . rémunération . brut de base': '2300 €/mois',
// 'contrat salarié': "'CDD'",
'contrat salarié . CDD . durée contrat': '12 mois',
"contrat salarié . aides employeur . aide exceptionnelle à l'embauche des jeunes . jeune de moins de 26 ans":
'contrat salarié . rémunération . brut de base': '1700 €/mois',
'contrat salarié . aides employeur . emploi franc . éligible': 'oui',
},
},
{
title: "Demandeur d'emploi de 45 ans ou plus",
dottedName:
"contrat salarié . aides employeur . aide à l'embauche senior professionnalisation",
situation: {
// 'contrat salarié . rémunération . brut de base': '1700 €/mois',
'contrat salarié . professionnalisation . jeune de moins de 30 ans':
'non',
'contrat salarié . professionnalisation . salarié de 45 ans et plus':
'oui',
},
},
@ -79,7 +80,9 @@ const config = {
'liste noire': [
'contrat salarié . activité partielle',
'contrat salarié . prix du travail',
"contrat salarié . ancienneté . date d'embauche",
'contrat salarié . temps de travail . heures supplémentaires',
'contrat salarié . temps de travail . heures complémentaires',
'contrat salarié . rémunération',
'contrat salarié . aides employeur . emploi franc . éligible',
],
@ -97,7 +100,14 @@ export default function AidesEmbauche() {
<section className="ui__ full-width lighter-bg">
<div className="ui__ container">
<HiddenOptionContext.Provider value={['contrat salarié . stage']}>
<Conversation />
<Conversation
customEndMessages={
<>
Vous pouvez maintenant simuler le coût d'embauche précis en en
sélectionnant une aide éligible.
</>
}
/>
</HiddenOptionContext.Provider>
</div>
</section>
@ -106,26 +116,37 @@ export default function AidesEmbauche() {
<Results />
</Animate.fromTop>
)}
<section>
<h2>En savoir plus sur les aides</h2>
<p>Bla bla 1jeune1solution</p>
</section>
</>
)
}
function Results() {
const engine = useEngine()
const baseEngine = useEngine()
const aidesEngines = aides.map((aide) => {
const engine = new Engine(baseEngine.parsedRules)
const situation = { ...aide.situation, ...baseEngine.parsedSituation }
engine.setSituation({ ...aide.situation, ...baseEngine.parsedSituation })
return { ...aide, situation, engine }
})
const [aidesActives, aidesInactives] = partition(
(aide) => typeof engine.evaluate(aide.dottedName).nodeValue === 'number',
aides
({ dottedName, engine }) =>
typeof engine.evaluate(dottedName).nodeValue === 'number',
aidesEngines
)
return (
<>
<h3>Aides disponibles</h3>
<div className="ui__ box-container">
<div className="ui__ box-container large">
{aidesActives.map((aide, i) => (
<ResultCard {...aide} key={i} />
))}
</div>
<h3>Les autres aides</h3>
<div className="ui__ box-container">
<div className="ui__ box-container large">
{aidesInactives.map((aide, i) => (
<ResultCard {...aide} key={i} />
))}
@ -142,22 +163,13 @@ function ResultCard({
}: AideDescriptor) {
const engine = useEngine()
const rule = engine.getParsedRules()[dottedName]
const valueNode = rule.explanation.valeur.explanation.valeur
const valueNode = (rule.explanation.valeur as any)?.explanation.valeur
const evaluation = engine.evaluate(valueNode)
const dottedNameParamName = useMemo(
() => getRulesParamNames(engine.getParsedRules()),
[engine]
)
const search = getSearchParamsFromSituation(
engine,
situation,
dottedNameParamName
).toString()
const search = useParamsFromSituation(situation).toString()
const sitePaths = useContext(SitePathsContext)
// TODO
return (
<div className="ui__ card box">
<AideCard className="ui__ card box">
<h4>{title}</h4>
<p className="ui__ notice">{description}</p>
<p className="ui__ lead">
@ -170,6 +182,15 @@ function ResultCard({
{formatValue(evaluation, { displayedUnit: '€' })}
</Link>
</p>
</div>
</AideCard>
)
}
const AideCard = styled.div`
max-width: none !important;
align-items: flex-start;
p {
text-align: left;
}
`

View File

@ -0,0 +1,55 @@
<?xml version="1.0" encoding="UTF-8"?>
<!-- Created with Inkscape (http://www.inkscape.org/) -->
<svg width="63.791mm" height="63.791mm" version="1.1" viewBox="0 0 63.791 63.791" xmlns="http://www.w3.org/2000/svg" xmlns:cc="http://creativecommons.org/ns#" xmlns:dc="http://purl.org/dc/elements/1.1/" xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#">
<metadata>
<rdf:RDF>
<cc:Work rdf:about="">
<dc:format>image/svg+xml</dc:format>
<dc:type rdf:resource="http://purl.org/dc/dcmitype/StillImage"/>
<dc:title/>
</cc:Work>
</rdf:RDF>
</metadata>
<g transform="translate(98.646 -205.04)">
<path d="m-66.751 206.79c-16.62 0-30.142 13.522-30.142 30.142 0 16.621 13.522 30.142 30.142 30.142 16.621 0 30.142-13.522 30.142-30.142 0-16.62-13.522-30.142-30.142-30.142m0 62.038c-17.587 0-31.896-14.308-31.896-31.896 0-17.587 14.308-31.896 31.896-31.896 17.587 0 31.896 14.308 31.896 31.896 0 17.587-14.308 31.896-31.896 31.896" fill="#2fac66"/>
<path d="m-66.751 221.35c-8.5908 0-15.58 6.9892-15.58 15.58 0 8.5908 6.9892 15.58 15.58 15.58 8.5908 0 15.58-6.9892 15.58-15.58 0-8.5908-6.9892-15.58-15.58-15.58m0 31.817c-8.9535 0-16.237-7.2838-16.237-16.237s7.2838-16.237 16.237-16.237c8.9535 0 16.237 7.2838 16.237 16.237s-7.2838 16.237-16.237 16.237" fill="#2fac66"/>
<path d="m-45.824 236.17-5.3382 9.2463-5.0105-2.8924 5.3382-9.2467z" fill="#e20d18"/>
<path d="m-50.835 233.28-5.3382 9.2467-5.0105-2.8928 5.3382-9.2467z" fill="#fff"/>
<g fill="#253574">
<path d="m-55.845 230.39-5.3382 9.2463-5.0105-2.8924 5.3382-9.2467z"/>
<path d="m-60.855 227.49-5.3382 9.2463 15.031 8.6783 5.3382-9.2467zm0.21661 0.80822 14.006 8.0864-4.7466 8.2218-14.006-8.0864z"/>
<path d="m-70.707 245.54-0.56938-0.32879 10.614-18.383 0.56938 0.32844z"/>
<path d="m-67.307 236.7-15.031 8.6783-5.3386-9.2467 15.032-8.678z"/>
</g>
<g fill="#ffe910">
<path d="m-75.892 240.04 0.18838-0.4057 0.42862 0.0497-0.32526-0.28645 0.19509-0.39264-0.37641 0.21801-0.32244-0.28187 0.08255 0.41981-0.381 0.21978 0.4251 0.0346z"/>
<path d="m-79.267 234 0.18627-0.39899 0.43039 0.043-0.32103-0.28857 0.1912-0.39052-0.37677 0.21766-0.32385-0.27481 0.08431 0.41345-0.37677 0.21731 0.42192 0.03z"/>
<path d="m-80.719 238.8 0.18662-0.39899 0.4385 0.0378-0.32068-0.28822 0.20108-0.38453-0.38171 0.22013-0.3309-0.27693 0.08255 0.42087-0.381 0.21978 0.41769 0.0215z"/>
<path d="m-74.463 235.17 0.18662-0.39899 0.43427 0.0402-0.31891-0.29528 0.19438-0.375-0.37712 0.21801-0.32632-0.2794 0.07867 0.42263-0.37712 0.21766 0.41769 0.0215z"/>
<path d="m-77.441 233.5 0.19121-0.40111 0.43392 0.0406-0.32103-0.28857 0.19403-0.38665-0.37712 0.21802-0.32879-0.28399 0.08079 0.42722-0.38135 0.22013 0.42298 0.0296z"/>
<path d="m-75.692 233.97 0.19121-0.40181 0.43392 0.0406-0.32314-0.29281 0.19403-0.38594-0.37747 0.21731-0.32632-0.27904 0.07408 0.42545-0.37677 0.21696 0.42686 0.0279z"/>
<path d="m-74.108 236.91 0.18909-0.3944 0.4385 0.0378-0.32138-0.28858 0.1965-0.39264-0.38135 0.22014-0.32702-0.28011 0.07832 0.42333-0.38065 0.22014 0.4251 0.0339z"/>
<path d="m-74.6 238.68 0.18838-0.40534 0.43674 0.0448-0.32314-0.29351 0.19791-0.38806-0.37677 0.21731-0.33091-0.27693 0.07832 0.42298-0.37677 0.21731 0.42263 0.03z"/>
<path d="m-77.632 240.44 0.18838-0.4057 0.44062 0.0423-0.32702-0.29069 0.19791-0.3884-0.38135 0.21977-0.32632-0.2794 0.07832 0.42263-0.3817 0.22014 0.42333 0.0303z"/>
<path d="m-79.341 239.94 0.18909-0.39511 0.4318 0.0363-0.31856-0.28434 0.19579-0.39299-0.381 0.22013-0.3242-0.27482 0.07585 0.4184-0.37712 0.21802 0.42474 0.0339z"/>
<path d="m-81.177 237.13 0.18627-0.39899 0.43921 0.0381-0.3235-0.29316 0.19791-0.3884-0.381 0.22013-0.3309-0.27693 0.07832 0.42298-0.37641 0.21731 0.42263 0.03z"/>
<path d="m-80.738 235.41 0.18662-0.399 0.43427 0.0402-0.32068-0.28857 0.19332-0.38558-0.37606 0.21695-0.33408-0.28116 0.08537 0.42474-0.381 0.22014 0.42298 0.0303z"/>
</g>
<path d="m-62.787 245.54-10.614-18.384 0.56938-0.32844 10.614 18.383z" fill="#253574"/>
<g fill="#2fac66">
<path d="m-90.779 225.36 2.2789-3.9868 1.1529 0.65899-1.4855 2.5996 1.6217 0.9271 1.2622-2.2084 1.1532 0.65899-1.2622 2.2084 2.9118 1.6644-0.7934 1.3878z"/>
<path d="m-83.714 218.17 1.3035 1.5646 0.69144-0.57644c0.51858-0.43215 0.56938-0.98637 0.15875-1.4792-0.3817-0.45826-0.94333-0.51752-1.4623-0.0854zm-2.0775 2e-3 1.85-1.5409c1.3314-1.1091 2.7217-1.1102 3.658 0.0134 0.61207 0.73483 0.7112 1.5752 0.32667 2.3788l4.1257 1.1024-1.4439 1.203-3.6544-1.0996-0.63112 0.52529 2.038 2.4469-1.2277 1.0227z"/>
<path d="m-71.273 215.24-1.7921-2.5929-0.29916 3.1376zm-3.1849-3.7881 2.0256-0.52775 4.8722 6.8725-1.6446 0.42827-1.246-1.7918-3.0498 0.7941-0.21343 2.1724-1.6446 0.42828z"/>
<path d="m-64.849 210.16 2.0055 0.41698 2.2895 6.2936 1.1596-5.5764 1.5649 0.32597-1.6041 7.7135-2.0059-0.41733-2.2892-6.2928-1.1599 5.576-1.5649-0.32561z"/>
<path d="m-51.694 221.96 0.39194 1.5399c-1.1712 0.32349-2.4804 0.0949-3.6033-0.78882-1.9537-1.5378-2.1054-4.0912-0.71367-5.8593 1.3917-1.7681 3.9095-2.22 5.8632-0.68227 1.1225 0.8837 1.6454 2.111 1.6196 3.308l-1.5956-0.0102c0.04339-0.7821-0.24236-1.5653-0.94968-2.1223-1.1666-0.91828-2.7143-0.66216-3.647 0.52247-0.93239 1.185-0.81809 2.7496 0.3489 3.6678 0.70697 0.55703 1.5353 0.65052 2.2856 0.42474"/>
<path d="m-44.614 222 2.2218 4.0174-1.1617 0.64241-1.4489-2.6187-1.6344 0.90346 1.2308 2.2253-1.162 0.64276-1.2305-2.2253-1.7724 0.98002 1.4485 2.6194-1.162 0.64241-2.2218-4.0171z"/>
<path d="m-85.471 244.92-1.8232 0.90699 0.40076 0.80574c0.30057 0.60466 0.82868 0.7814 1.403 0.49601 0.53375-0.26529 0.72108-0.79904 0.42016-1.4034zm0.47731-2.0221 1.0724 2.1558c0.77152 1.5512 0.45226 2.9044-0.8576 3.556-0.85654 0.4258-1.6965 0.32879-2.3897-0.23143l-2.0256 3.7599-0.83679-1.6828 1.9138-3.302-0.36583-0.73519-2.8512 1.4185-0.71155-1.4309z"/>
<path d="m-81.471 249.13 3.3031 3.1881-0.92181 0.95567-2.1537-2.0786-1.2972 1.3437 1.8295 1.7664-0.92181 0.95497-1.8299-1.7656-1.4065 1.4573 2.1537 2.0786-0.92251 0.95532-3.3031-3.1884z"/>
<path d="m-76.785 253.17 1.4365 0.69885-2.8113 5.7767 2.6906 1.3095-0.63465 1.3049-4.1279-2.0087z"/>
<path d="m-67.583 260.41-0.83255-3.0385-1.3208 2.8603zm-1.7512-4.6274 2.0856 0.17216 2.323 8.0962-1.6937-0.13935-0.58244-2.1036-3.1401-0.25965-0.9204 1.9787-1.6933-0.14005z"/>
<path d="m-63.611 256.01 1.923-0.70485 5.2659 4.1328-1.9597-5.3453 1.5-0.54998 2.7114 7.3946-1.9226 0.7052-5.2666-4.1332 1.96 5.3453-1.5 0.54999z"/>
<path d="m-47.628 252.5 1.5755-0.20356c0.18062 1.2016-0.20391 2.474-1.2164 3.4823-1.7621 1.7547-4.3155 1.5981-5.9034 4e-3 -1.5879-1.5946-1.7339-4.149 0.02822-5.9037 1.0125-1.0079 2.2941-1.3797 3.4791-1.2097l-0.20214 1.5829c-0.77117-0.13687-1.5833 0.0522-2.2211 0.68722-1.0523 1.0484-0.98425 2.6155 0.07973 3.684 1.064 1.0682 2.6314 1.1434 3.6837 0.0952 0.63782-0.63535 0.83008-1.4464 0.69674-2.2183"/>
<path d="m-50.314 246.68 1.8863-4.1857 1.2104 0.54504-1.2298 2.7291 1.7032 0.76764 1.0449-2.3184 1.2104 0.54469-1.0446 2.3192 1.8464 0.83185 1.2294-2.7287 1.2107 0.54575-1.8863 4.1854z"/>
</g>
</g>
</svg>

After

Width:  |  Height:  |  Size: 6.9 KiB

View File

@ -27,6 +27,7 @@ import urlIllustrationNetBrut from './images/illustration-net-brut.png'
import RémunérationSASUPreview from './images/RémunérationSASUPreview.png'
import salaireBrutNetPreviewEN from './images/SalaireBrutNetPreviewEN.png'
import salaireBrutNetPreviewFR from './images/SalaireBrutNetPreviewFR.png'
import logoFranceRelance from './images/logo-france-relance.svg'
import PAMCHome from './PAMCHome'
import IndépendantSimulation, {
IndépendantPLSimulation,
@ -768,11 +769,19 @@ export function getSimulatorsData({
title: "Aides à l'embauche",
description: (
<p>
<img
src={logoFranceRelance}
alt="Logo France Relance"
style={{
width: '120px',
marginBottom: '1rem',
marginLeft: '1rem',
float: 'right',
}}
/>
Les employeurs peuvent bénéficier d'une aide financière pour
l'embauche de certains publics prioritaires. Découvrez les dispositifs
existants et estimez le montant de l'aide en répondant aux questions.
<br />
<br />
</p>
),
component: AidesEmbauche,