Skip to content

Commit

Permalink
Paramètres du calendrier (affichage uniquement) (#302)
Browse files Browse the repository at this point in the history
  • Loading branch information
Donov4n committed Jan 9, 2022
1 parent d944e78 commit 6e05079
Show file tree
Hide file tree
Showing 12 changed files with 262 additions and 25 deletions.
3 changes: 3 additions & 0 deletions client/src/components/Button/_variables.scss
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
/// Marge entre l'icône et le texte des boutons (quand il y en a une, d'icône)
/// @type Number
$icon-margin: 0.3571rem !default;
21 changes: 21 additions & 0 deletions client/src/components/Button/index.scss
Original file line number Diff line number Diff line change
@@ -0,0 +1,21 @@
@use './variables' as *;

.Button {
// - Icône
&::before,
&__icon {
display: inline-flex;
align-items: center;
justify-content: center;
width: 1.1em;
height: 1.1em;
font-size: 1.1em;
line-height: 1.35em;
text-align: center;
vertical-align: -0.05rem;
}

&__icon + &__content {
margin-left: $icon-margin;
}
}
78 changes: 78 additions & 0 deletions client/src/components/Button/index.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,78 @@
import './index.scss';
import { toRefs, computed } from '@vue/composition-api';
import Icon from '@/components/Icon';

import type { Component, SetupContext } from '@vue/composition-api';
import type { Props as IconProps } from '@/components/Icon';

type Props = {
/**
* Le type de bouton pour l'attribut `type` de la balise `<button>`?
*
* Options disponibles: `submit`, `button` ou `reset`.
*/
htmlType?: 'submit' | 'button' | 'reset',

/**
* Le code de l'éventuelle icône qui sera ajoutée au bouton.
*
* Pour utiliser une variante de l'icône, vous pouvez suffixer le nom de l'icône avec `:[variante]`.
* Par exemple: `plus:solid` ou `birthday-cake:regular`.
*
* Voir le component <Icon> concernant la liste des codes et les variantes possibles.
*/
icon?: string | undefined,

/** Le bouton est-il désactivé ? */
disabled?: boolean,

/** Des éventuelles classes supplémentaires qui seront ajoutées au component. */
class?: string,
};

// @vue/component
const Button: Component<Props> = (props: Props, { slots }: SetupContext) => {
const { htmlType, icon, disabled } = toRefs(props as Required<Props>);
const _icon = computed<IconProps | null>(() => {
if (!icon.value) {
return null;
}

if (!icon.value.includes(':')) {
return { name: icon.value };
}

const [iconType, variant] = icon.value.split(':');
return { name: iconType, variant: variant as any };
});

const _className = ['Button', {
'Button--with-icon': !!_icon,
}];

return () => {
const children = slots.default?.();

return (
// eslint-disable-next-line react/button-has-type
<button type={htmlType.value} class={_className} disabled={disabled.value}>
{_icon.value && <Icon {...{ props: _icon.value } as any} class="Button__icon" />}
{children && <span class="Button__content">{children}</span>}
</button>
);
};
};

Button.props = {
htmlType: {
default: 'button',
validator: (value: unknown) => (
typeof value === 'string' &&
['button', 'submit', 'reset'].includes(value)
),
},
icon: { type: String, default: undefined },
disabled: { type: Boolean, default: false },
};

export default Button;
18 changes: 12 additions & 6 deletions client/src/components/FormField/index.scss
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,8 @@
@use 'sass:math';

.FormField {
$block: &;

flex: 1;

&__label {
Expand All @@ -25,6 +27,10 @@
width: 90%;
}

&__switch {
display: flex;
}

&__addon {
display: inline-block;
min-width: 2.7rem;
Expand All @@ -51,7 +57,7 @@
}

&--with-addon {
.FormField__input {
#{$block}__input {
display: inline-block;
padding-right: 0;
border-right: 0;
Expand All @@ -60,11 +66,11 @@
}

&--with-error {
.FormField__input:not(:focus),
.FormField__datepicker .mx-input:not(:focus),
.FormField__select:not(:focus),
.FormField__textarea:not(:focus),
.FormField__addon {
#{$block}__input:not(:focus),
#{$block}__datepicker .mx-input:not(:focus),
#{$block}__select:not(:focus),
#{$block}__textarea:not(:focus),
#{$block}__addon {
border-color: globals.$input-error-border-color;
}
}
Expand Down
44 changes: 44 additions & 0 deletions client/src/components/Icon/index.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,44 @@
import { toRefs, computed } from '@vue/composition-api';

import type { Component } from '@vue/composition-api';

export type Props = {
/**
* Le nom de l'icône à afficher.
*
* Pour une liste exhaustive des codes, voir : https://fontawesome.com/v5.15/icons?m=free
*/
name: string,

/** Quelle variante faut-il utiliser pour l'icône ? */
variant?: 'regular' | 'solid' | 'brands',

/** Des éventuelles classes supplémentaires qui seront ajoutées au component. */
class?: string,
};

const VARIANT_MAP = {
'regular': 'far',
'solid': 'fas',
'brands': 'fab',
} as const;

// @vue/component
const Icon: Component<Props> = (props: Props) => {
const { name, variant } = toRefs(props as Required<Props>);
const baseClass = computed(() => VARIANT_MAP[variant.value]);
return () => <i class={[baseClass.value, `fa-${name.value}`]} aria-hidden="true" />;
};

Icon.props = {
name: { type: String, required: true },
variant: {
default: 'solid',
validator: (value: unknown) => (
typeof value === 'string' &&
['solid', 'regular', 'brands'].includes(value)
),
},
};

export default Icon;
3 changes: 3 additions & 0 deletions client/src/locale/en/pages.js
Original file line number Diff line number Diff line change
Expand Up @@ -390,6 +390,9 @@ export default {
'custom-text-content': "Text content",
'saved': "Event summaries settings were successfully saved.",
},
'calendar': {
'title': "Calendar",
},
},

'page-estimate': {
Expand Down
3 changes: 3 additions & 0 deletions client/src/locale/fr/pages.js
Original file line number Diff line number Diff line change
Expand Up @@ -390,6 +390,9 @@ export default {
'custom-text-content': "Contenu du texte",
'saved': "Les paramètres des fiches de sortie ont bien été sauvegardés.",
},
'calendar': {
'title': "Calendrier",
},
},

'page-estimate': {
Expand Down
25 changes: 25 additions & 0 deletions client/src/pages/Settings/Calendar/index.scss
Original file line number Diff line number Diff line change
@@ -0,0 +1,25 @@
@use '~@/style/globals';

.CalendarSettings {
&__form {
max-width: globals.$form-max-width;
}

&__section {
margin-top: globals.$content-padding-large-vertical;

.FormField {
&__label {
flex-basis: 250px;
}

+ .FormField {
margin-top: globals.$content-padding-small-vertical;
}
}
}

&__actions {
margin-top: globals.$content-padding-large-vertical;
}
}
48 changes: 48 additions & 0 deletions client/src/pages/Settings/Calendar/index.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,48 @@
import { ref } from '@vue/composition-api';
import useI18n from '@/hooks/useI18n';
import FormField from '@/components/FormField';
import Button from '@/components/Button';

import type { Component } from '@vue/composition-api';

// @vue/component
const CalendarSettings: Component = () => {
const __ = useI18n();
const isSaving = ref(false);

const handleSubmit = (e: SubmitEvent): void => {
e.preventDefault();
};

return () => (
<div class="CalendarSettings">
<form class="CalendarSettings__form" onSubmit={handleSubmit}>
<section class="CalendarSettings__section">
<h3>Données affichées dans les événements du calendrier</h3>
<FormField
type="switch"
label="Afficher le lieu de l'événement ?"
name="calendar.event.showLocation"
/>
<FormField
type="switch"
label="Afficher le bénéficiaire / emprunteur ?"
name="calendar.event.showBorrower"
/>
</section>
<section class="CalendarSettings__actions">
<Button
icon="save"
htmlType="submit"
class="success"
disabled={isSaving.value}
>
{isSaving.value ? __('saving') : __('save')}
</Button>
</section>
</form>
</div>
);
};

export default CalendarSettings;
19 changes: 8 additions & 11 deletions client/src/pages/Settings/EventSummary/Form/index.js
Original file line number Diff line number Diff line change
Expand Up @@ -12,14 +12,7 @@ export default {
errors: { type: Object, default: null },
},
data() {
const initialListModeOptions = LIST_MODES.map((mode) => (
{ value: mode, label: `page-settings.event-summary.list-display-mode-${mode}` }
));

return {
initialListModeOptions,
defaultListMode: 'sub-categories',
};
return { defaultListMode: 'sub-categories' };
},
computed: {
values() {
Expand All @@ -29,9 +22,12 @@ export default {
listModeOptions() {
const parks = this.$store.state.parks.list;

return this.initialListModeOptions.filter((mode) => (
mode.value !== 'parks' || parks.length > 1
));
return LIST_MODES
.filter((mode) => mode !== 'parks' || parks.length > 1)
.map((mode) => ({
value: mode,
label: `page-settings.event-summary.list-display-mode-${mode}`,
}));
},
},
mounted() {
Expand All @@ -40,6 +36,7 @@ export default {
methods: {
handleSubmit(e) {
e.preventDefault();

this.$emit('save', getFormDataAsJson(e.target));
},
},
Expand Down
18 changes: 10 additions & 8 deletions client/src/pages/Settings/EventSummary/Form/index.scss
Original file line number Diff line number Diff line change
Expand Up @@ -5,18 +5,20 @@

&__section {
margin-top: globals.$content-padding-large-vertical;

.FormField {
&__textarea {
min-height: 200px;
}

+ .FormField {
margin-top: globals.$content-padding-small-vertical;
}
}
}

&__actions {
margin-top: globals.$content-padding-large-vertical;
text-align: right;
}

.FormField {
margin-bottom: globals.$content-padding-small-vertical;

&__textarea {
min-height: 200px;
}
}
}
7 changes: 7 additions & 0 deletions client/src/pages/Settings/index.js
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
import { Tabs, Tab } from 'vue-slim-tabs';
import EventSummarySettings from './EventSummary';
import CalendarSettings from './Calendar';

// @vue/component
export default {
Expand All @@ -15,9 +16,15 @@ export default {
<template slot="event-summary">
<i class="fas fa-print" /> {__('page-settings.event-summary.title')}
</template>
<template slot="calendar">
<i class="fas fa-calendar-alt" /> {__('page-settings.calendar.title')}
</template>
<Tab title-slot="event-summary">
<EventSummarySettings />
</Tab>
<Tab title-slot="calendar">
<CalendarSettings />
</Tab>
</Tabs>
</div>
</div>
Expand Down

0 comments on commit 6e05079

Please sign in to comment.