Ajoute un mécanisme de feedback plus discret, moins invasif que le précédent

pull/304/head
Johan Girod 2018-08-23 18:25:18 +02:00
parent 73f23f4abf
commit 59895a3246
7 changed files with 93 additions and 162 deletions

View File

@ -60,11 +60,6 @@
.payslip__salaireNetàPayer {
font-weight: bold;
}
.payslip__notice {
color: rgba(0, 0, 0, 0.7);
font-size: 90%;
margin-top: 2em;
}
/* IE */
@media screen and (-ms-high-contrast: active), (-ms-high-contrast: none) {

View File

@ -132,7 +132,7 @@ const PaySlip = ({
<Montant>{salaireNetImposable.montant}</Montant>
</div>
<br />
<p className="payslip__notice">
<p className="ui__ notice">
<Trans i18nKey="payslip.notice">
Le simulateur vous aide à comprendre votre bulletin de paie, sans lui
être opposable. Pour plus d&apos;informations, rendez vous sur&nbsp;
@ -140,15 +140,15 @@ const PaySlip = ({
alt="service-public.fr"
href="https://www.service-public.fr/particuliers/vosdroits/F559">
service-public.fr
</a>.
</a>
.
</Trans>
</p>
<p className="payslip__notice">
<p className="ui__ notice">
<Trans i18nKey="payslip.disclaimer">
Il ne prend pour l&apos;instant pas en compte les conventions et accords
collectifs, ni la myriade d&apos;aides à explorer sur&nbsp;<a href="https://www.aides-entreprises.fr">
aides-entreprises.fr
</a>.
collectifs, ni la myriade d&apos;aides à explorer sur&nbsp;
<a href="https://www.aides-entreprises.fr">aides-entreprises.fr</a>.
</Trans>
</p>
</div>

View File

@ -20,6 +20,7 @@ import PaySlip from './PaySlip'
import QuickLink from './QuickLink'
import ResultView from './ResultView'
import './Simu.css'
import Sondage from './Sondage'
import TargetSelection from './TargetSelection'
@withColours
@ -126,6 +127,9 @@ export default class Simu extends Component {
{conversationStarted && (
<Animate.fromBottom>
<ResultView />
<div style={{ textAlign: 'center' }}>
<Sondage />
</div>
</Animate.fromBottom>
)}
{displayPreviousAnswers && (
@ -165,6 +169,7 @@ export default class Simu extends Component {
<Trans>Fiche de paie</Trans>
</h2>
<PaySlip />
<Sondage />
</Animate.fromBottom>
)}
</>

View File

@ -1,56 +0,0 @@
.sondage {
background: white;
display: inline-block;
padding: 1em;
border: 2px solid;
box-shadow: 0px 1px 9px 0px rgba(0, 0, 0, 0.45);
border-bottom: none;
border-radius: 0.3em;
border-bottom-left-radius: 0;
border-bottom-right-radius: 0;
}
.sondage__container {
position: fixed;
left: 0;
right: 0;
text-align: center;
bottom: 0;
}
.sondage__closeButton {
margin-left: 0.5em;
}
.sondage__text {
margin-right: 1em;
}
.slide-blurred-bottom-enter {
animation: slide-in-blurred-bottom 0.8s cubic-bezier(0.23, 1, 0.32, 1) both;
animation-delay: 6s;
transform: translateY(1000px) scaleY(2.5) scaleX(0.2);
transform-origin: 50% 100%;
filter: blur(40px);
opacity: 0;
}
.slide-blurred-bottom-leave {
animation: slide-in-blurred-bottom 0.3s cubic-bezier(0.32, 1, 0.23, 1) both
reverse;
}
/**
* ----------------------------------------
* animation slide-in-blurred-bottom
* ----------------------------------------
*/
@keyframes slide-in-blurred-bottom {
0% {
transform: translateY(1000px) scaleY(2.5) scaleX(0.2);
transform-origin: 50% 100%;
filter: blur(40px);
opacity: 0;
}
100% {
transform: translateY(0) scaleY(1) scaleX(1);
transform-origin: 50% 50%;
filter: blur(0);
opacity: 1;
}
}

View File

@ -1,5 +1,6 @@
import withLanguage from 'Components/utils/withLanguage'
import withTracker from 'Components/utils/withTracker'
import React, { Component } from 'react'
import ReactCSSTransitionGroup from 'react-addons-css-transition-group'
import { Trans, translate } from 'react-i18next'
import { connect } from 'react-redux'
import {
@ -7,12 +8,6 @@ import {
noUserInputSelector
} from 'Selectors/analyseSelectors'
import Smiley from './SatisfactionSmiley'
import './Sondage.css'
import ReactPiwik from './Tracker'
import TypeFormEmbed from './TypeFormEmbed'
import { LinkButton } from 'Ui/Button'
import withColours from 'Components/utils/withColours'
import withLanguage from 'Components/utils/withLanguage'
@connect(state => ({
conversationStarted: state.conversationStarted,
@ -21,97 +16,78 @@ import withLanguage from 'Components/utils/withLanguage'
}))
@translate()
@withLanguage
@withColours
@withTracker
export default class Sondage extends Component {
state = {
visible: false,
visible: true,
showForm: false,
askFeedbackTime: 'AFTER_FIRST_ESTIMATE'
}
static getDerivedStateFromProps(nextProps, currentState) {
let feedbackAlreadyAsked = !!document.cookie.includes('feedback_asked=true')
let conditions = {
AFTER_FIRST_ESTIMATE: !nextProps.noUserInput,
AFTER_SIMULATION_COMPLETED:
!nextProps.nextSteps.length && nextProps.conversationStarted
}
return {
visible: conditions[currentState.askFeedbackTime] && !feedbackAlreadyAsked
}
}
componentDidMount() {
this.setState({
askFeedbackTime:
Math.random() > 0.5
? 'AFTER_SIMULATION_COMPLETED'
: 'AFTER_FIRST_ESTIMATE'
})
}
handleClose = () => {
this.setState({ visible: false })
this.setCookie()
}
setCookie = () => {
document.cookie = 'feedback_asked=true;'
}
onSmileyClick = satisfaction => {
ReactPiwik.push(['trackEvent', 'feedback', 'smiley', satisfaction])
this.props.tracker.push(['trackEvent', 'feedback', 'smiley', satisfaction])
this.setState({ showForm: true, satisfaction, visible: false })
this.setCookie()
}
render() {
let { satisfaction, showForm, visible, askFeedbackTime } = this.state,
{
language,
colours: { colour }
} = this.props
let { satisfaction, showForm, visible } = this.state
return (
<>
{showForm && (
<TypeFormEmbed
hiddenVariables={{
exterieur: false,
satisfaction,
answertiming: askFeedbackTime,
language
}}
/>
<div className="sondage__container">
{showForm &&
(satisfaction === ':|' ? (
<p className="ui__ notice">
<strong>
<Trans i18nKey="feedback.bad.headline">
Nous sommes désolé de ne pas vous avoir apporté entière
satisfaction.
</Trans>
</strong>{' '}
<Trans i18nKey="feedback.bad.support">
Si vous le souhaitez, vous pouvez nous envoyer un mail à{' '}
<a href="mailto:contact@embauche.beta.gouv.fr">
contact@embauche.beta.gouv.fr
</a>
Nous vous garantissons de vous répondre au plus vite, et de
faire tout notre possible pour vous venir en aide
</Trans>
</p>
) : (
<p className="ui__ notice">
<strong>
<Trans i18nKey="feedback.good.headline">
Merci pour votre retour !
</Trans>
</strong>{' '}
<Trans i18nKey="feedback.good.support">
Si vous avez une remarque, ou une idée d'amélioration, n'hésitez
pas à nous contacter directement par mail à
<a href="mailto:contact@embauche.beta.gouv.fr">
contact@embauche.beta.gouv.fr
</a>
</Trans>
</p>
))}
{visible && (
<p className="ui__ notice">
<span className="sondage__text">
<Trans>Votre avis nous intéresse !</Trans>
</span>
<br />
<Smiley
text=":)"
hoverColor="#16a085"
onClick={this.onSmileyClick}
/>
<Smiley
text=":|"
hoverColor="#f39c12"
onClick={this.onSmileyClick}
/>
</p>
)}
<ReactCSSTransitionGroup
transitionName="slide-blurred-bottom"
transitionEnterTimeout={6800}
transitionLeaveTimeout={300}>
{visible && (
<div className="sondage__container">
<div
className="sondage"
style={{ color: colour, borderColor: colour }}>
<span className="sondage__text">
<Trans>Votre avis nous intéresse !</Trans>
</span>
<Smiley
text=":)"
hoverColor="#16a085"
onClick={this.onSmileyClick}
/>
<Smiley
text=":|"
hoverColor="#f39c12"
onClick={this.onSmileyClick}
/>
<LinkButton
className="sondage__closeButton"
onClick={this.handleClose}
aria-label="close">
X
</LinkButton>
</div>
</div>
)}
</ReactCSSTransitionGroup>
</>
</div>
)
}
}

View File

@ -38,7 +38,11 @@ button {
margin-left: auto;
padding: 0 0.6em;
}
p.ui__.notice {
font-size: 90%;
color: rgba(0, 0, 0, 0.7);
margin-top: 2em;
}
ul.ui__.no-bullet {
list-style: none;
}

View File

@ -1,7 +1,7 @@
enterSalary: Enter a monthly salary
previousSimulationBanner:
previousSimulationBanner:
info: Your previous simulation data have been saved.
retrieveButton: Retrieve my last simulation
retrieveButton: Retrieve my last simulation
Première estimation: First estimate
Commencer la simulation: Start simulation
selectMany: You may pick more than one
@ -32,31 +32,31 @@ inlineExpressionNegation: Not
déplier: show more
replier: show less
branches:
assurance chômage:
assurance chômage:
name: unemployment
counterpart: Gives income to former employees while they're looking for a new job.
retraite:
name: pensions
counterpart: Guarantees on average 60%-70% of your last income.
formation:
formation:
name: training
counterpart: Gives access to professional training for employees.
logement:
logement:
name: housing
counterpart: Helps build new and affordable housing.
transport:
name: transportation
counterpart: Helps keep the price of a public transportation ticket low.
accidents du travail / maladies professionnelles:
accidents du travail / maladies professionnelles:
name: work accidents / occupational diseases
counterpart: Offers full coverage of occupational illnesses or accidents.
santé:
santé:
name: healthcare
counterpart: Covers most of everyday-life health care needs and 100% for serious illnesses, e.g. hospital stays.
famille:
famille:
name: family allowances
counterpart: Offers a balanced work and family life. Finances day nurseries and various child care.
autres:
counterpart: Offers a balanced work and family life. Finances day nurseries and various child care.
autres:
name: other
counterpart: Other contributions to the social system.
Salaire brut: Gross salary
@ -132,7 +132,7 @@ Total des retenues: Total withheld
Fiche de paie: Payslip
Voir la répartition des cotisations: View contribution breakdown
Cotisations: Contributions
payslip:
payslip:
notice: This simulation helps you understand your French payslip, but it should not be used as one. For further details, check <1>service-public.fr (French)</1>.
heures: 'Number of hours worked: '
disclaimer: It takes into account national law but not union negotiated rules. Lots of financial aids for your enterprise exist, explore them on <1>aides-entreprises.fr (French)</1>.
@ -153,3 +153,10 @@ simulation-end:
title: No more questions left!
text: You have reached the most accurate estimate. You can now turn your hiring project into reality.
cta: Know the procedures
feedback:
bad:
headline: We're sorry we didn't give you complete satisfaction
support: If you wish, you can send us an email at <1>contact@embauche.beta.gouv.fr</1>. We guarantee to answer you as quickly as possible, and to do everything we can to help you.
good:
headline: Thanks for your feedback!
support: If you have a remark, or an idea of improvement, do not hesitate to contact us directly by mail at <1>contact@embauche.beta.gouv.fr</1>