Browse Source

Passage à Eleventy et édition des tarifs et contacts via Pages CMS

- Déplacement du site de public/ vers src/ ; la page devient un gabarit
  Nunjucks (src/index.njk) généré par Eleventy dans _site/.
- Saison, licence et cotisations extraites dans src/_data/saison.yml ;
  bureau, adresse postale et email dans src/_data/contacts.yml.
- Ajout de .pages.yml : formulaires Pages CMS en français, avec
  validation des saisies (saison, prix, téléphone, code postal, email).
- netlify.toml : build « npm run build » (Node 22), publication de _site.
- README : notice d'utilisation de Pages CMS, nouvelle structure du
  dépôt et suppression des données dupliquées devenues obsolètes.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
main
Nicolas Massé 1 month ago
parent
commit
36c4ce7ffc
  1. 2
      .gitignore
  2. 126
      .pages.yml
  3. 98
      README.md
  4. 35
      eleventy.config.js
  5. 6
      netlify.toml
  6. 1709
      package-lock.json
  7. 14
      package.json
  8. 19
      src/_data/contacts.yml
  9. 26
      src/_data/saison.yml
  10. 114
      src/index.njk
  11. 0
      src/infos-utiles4.png
  12. 0
      src/logo-cc-conches.png
  13. 0
      src/logo-ffsv.jpeg
  14. 0
      src/logo.png
  15. 0
      src/photo-gym1.png
  16. 0
      src/photo-gym2.jpeg
  17. 0
      src/visuel-club.png

2
.gitignore

@ -0,0 +1,2 @@
node_modules/
_site/

126
.pages.yml

@ -0,0 +1,126 @@
# Configuration de Pages CMS (https://app.pagescms.org)
# Définit les formulaires permettant de modifier le site sans toucher au code.
content:
- name: saison
label: Saison et tarifs
type: file
path: src/_data/saison.yml
format: yaml
fields:
- name: annee
label: Saison en cours
type: string
required: true
description: "Format : 2026-2027"
pattern:
regex: "^\\d{4}-\\d{4}$"
message: "Indiquez la saison au format 2026-2027"
- name: licence
label: Licence FFEPGV (obligatoire)
type: object
fields:
- name: prix
label: Prix de la licence (€)
type: string
required: true
description: "Exemple : 29,80"
pattern:
regex: "^\\d+([,.]\\d{1,2})?$"
message: "Indiquez un montant comme 29,80 ou 100 (sans le symbole €)"
- name: avantages
label: Ce qui est inclus
type: string
list: true
- name: cotisations
label: Cotisations
type: object
description: "Une carte par formule, affichée dans l'ordre de la liste. L'icône (1, 2, 3…) suit cet ordre."
list:
collapsible:
collapsed: true
summary: "{fields.titre} : {fields.prix} €"
fields:
- name: titre
label: Intitulé
type: string
required: true
description: "Exemple : 1 cours / semaine"
- name: prix
label: Cotisation annuelle (€)
type: string
required: true
description: "Exemple : 100,00 (la licence est ajoutée automatiquement sous le prix)"
pattern:
regex: "^\\d+([,.]\\d{1,2})?$"
message: "Indiquez un montant comme 100,00 ou 100 (sans le symbole €)"
- name: populaire
label: Mettre en avant (badge « Le plus populaire »)
type: boolean
description: "À cocher sur une seule formule"
- name: avantages
label: Points forts
type: string
list: true
- name: contacts
label: Contacts
type: file
path: src/_data/contacts.yml
format: yaml
fields:
- name: bureau
label: Membres du bureau
type: object
list:
collapsible:
collapsed: true
summary: "{fields.role} : {fields.prenom} {fields.nom}"
fields:
- name: role
label: Fonction
type: string
required: true
description: "Exemple : Présidente, Trésorier, Secrétaire…"
- name: prenom
label: Prénom
type: string
required: true
- name: nom
label: Nom
type: string
required: true
description: "Affiché automatiquement en majuscules"
- name: telephone
label: Téléphone
type: string
description: "Format : 06 12 34 56 78 (laisser vide pour ne pas afficher de numéro)"
pattern:
regex: "^(0\\d( \\d{2}){4})?$"
message: "Indiquez le numéro au format 06 12 34 56 78"
- name: adresse
label: Adresse postale
type: object
fields:
- name: rue
label: Numéro et rue
type: string
required: true
- name: code_postal
label: Code postal
type: string
required: true
pattern:
regex: "^\\d{5}$"
message: "Le code postal comporte 5 chiffres"
- name: ville
label: Ville
type: string
required: true
- name: email
label: Adresse email
type: string
required: true
pattern:
regex: "^[^@\\s]+@[^@\\s]+\\.[^@\\s]+$"
message: "Adresse email invalide"

98
README.md

@ -13,6 +13,7 @@ Site statique Bootstrap 5 de l'association **Gymnastique Volontaire de Conches-e
| Dépôt GitHub | https://github.com/nmasse-itix/gvdc-site |
| Espace FFEPGV | https://ffepgv.fr/ |
| Page Intramuros | https://www.conches-en-ouche.fr/associations/175709 |
| Édition des tarifs et contacts (Pages CMS) | https://app.pagescms.org |
---
@ -20,8 +21,11 @@ Site statique Bootstrap 5 de l'association **Gymnastique Volontaire de Conches-e
```
gvdc-site/
├── public/ ← Dossier publié par Netlify
│ ├── index.html ← Page unique du site (Bootstrap 5)
├── src/ ← Sources du site
│ ├── index.njk ← Page unique du site (Bootstrap 5, gabarit Nunjucks)
│ ├── _data/ ← Données modifiables via Pages CMS
│ │ ├── saison.yml ← Saison en cours, licence et cotisations
│ │ └── contacts.yml ← Bureau, adresse postale, email
│ ├── visuel-club.png ← Logo/silhouette du club (navbar)
│ ├── logo.png ← Badge Label Qualité Sport-Santé FFEPGV
│ ├── logo-ffsv.jpeg ← Logo Fédération Française Sport Vitalité
@ -30,29 +34,35 @@ gvdc-site/
│ ├── photo-gym1.png ← Photo galerie (séance détente)
│ └── photo-gym2.jpeg ← Photo galerie (séance renforcement)
│
├── netlify.toml ← Configuration Netlify
├── .pages.yml ← Configuration des formulaires Pages CMS
├── eleventy.config.js ← Configuration Eleventy (générateur du site)
├── package.json ← Dépendances Node.js (Eleventy)
├── netlify.toml ← Configuration Netlify (build + en-têtes)
└── README.md ← Ce fichier
```
> **Règle importante** : seul le dossier `public/` est déployé. Tout fichier ajouté à la racine du dépôt reste privé et n'est pas accessible sur le site.
> **Règle importante** : Netlify génère le site dans `_site/` à partir de `src/`. Seuls la page et les images de `src/` sont publiées ; les fichiers à la racine du dépôt et les données brutes de `src/_data/` ne sont pas accessibles sur le site.
---
## Déploiement
Le site est hébergé sur **Netlify** avec déploiement continu : chaque `git push` sur la branche `main` déclenche automatiquement une mise en ligne.
Le site est hébergé sur **Netlify** avec déploiement continu : chaque `git push` (ou chaque enregistrement dans Pages CMS) sur la branche `main` déclenche automatiquement la génération du site par Eleventy (`npm run build`) puis sa mise en ligne.
### Première installation (à faire une seule fois)
```bash
git clone git@github.com:nmasse-itix/gvdc-site.git
cd gvdc-site
npm install
```
Prérequis : Node.js 18 ou plus récent (Netlify utilise Node.js 22).
### Publier une modification
```bash
git add public/index.html # ou les fichiers modifiés
git add src/index.njk # ou les fichiers modifiés
git commit -m "Description du changement"
git push
```
@ -63,41 +73,61 @@ Netlify déploie en 1 à 2 minutes. Le statut du déploiement est visible sur ht
```bash
cd gvdc-site
python3 -m http.server 8080 --bind 0.0.0.0 --directory public
npm start
```
Puis ouvrir http://localhost:8080 dans un navigateur.
Puis ouvrir http://localhost:8080 dans un navigateur. La page se recharge automatiquement à chaque modification.
---
## Mettre à jour les tarifs, la saison et les contacts (sans compétence technique)
La saison en cours, les tarifs, les membres du bureau, l'adresse postale et l'email se modifient depuis **[Pages CMS](https://app.pagescms.org)**, une interface web gratuite qui enregistre les modifications dans le dépôt GitHub à votre place.
### Accès (à faire une seule fois)
1. La personne chargée des mises à jour crée un compte gratuit sur https://github.com.
2. Un administrateur du dépôt l'invite comme collaboratrice : sur GitHub, *Settings → Collaborators → Add people*. Elle accepte l'invitation reçue par email.
3. Elle se connecte sur https://app.pagescms.org avec *Sign in with GitHub* et choisit le dépôt `gvdc-site` (à la première connexion, Pages CMS demande d'autoriser l'accès au dépôt).
### Faire une modification
1. Ouvrir https://app.pagescms.org et choisir le dépôt `gvdc-site`.
2. Dans le menu de gauche, choisir **Saison et tarifs** ou **Contacts**.
3. Modifier les champs :
- **Saison en cours** : au format `2026-2027`.
- **Prix** : sans le symbole €, par exemple `29,80` ou `100`.
- **Cotisations** et **Membres du bureau** : le bouton *Add* ajoute une entrée, la corbeille la supprime, et les poignées permettent de changer l'ordre d'affichage.
- **Téléphone** : au format `06 12 34 56 78`.
4. Cliquer sur **Save**.
5. Le site en ligne est à jour **1 à 2 minutes plus tard**. Recharger la page pour vérifier.
> En cas d'erreur, rien n'est perdu : chaque enregistrement est conservé dans l'historique GitHub et peut être annulé par un administrateur.
---
## Modifier le contenu du site
## Modifier le reste du contenu (développeurs)
Tout le contenu est dans **`public/index.html`**. Le fichier est organisé en sections clairement délimitées par des commentaires :
La mise en page et les autres textes sont dans **`src/index.njk`** (HTML + balises [Nunjucks](https://mozilla.github.io/nunjucks/) `{{ … }}` / `{% … %}` qui insèrent les données de `src/_data/`). Le fichier est organisé en sections clairement délimitées par des commentaires :
```
<!-- NAVBAR -->
<!-- HERO --> ← Accueil
<!-- À PROPOS -->
<!-- ACTIVITÉS --> ← Horaires
<!-- TARIFS -->
<!-- TARIFS --> ← données : src/_data/saison.yml
<!-- GALERIE -->
<!-- ACTUALITÉS -->
<!-- CONTACT -->
<!-- CONTACT --> ← données : src/_data/contacts.yml
<!-- FOOTER -->
```
Pour rendre un nouvel élément modifiable dans Pages CMS : l'ajouter dans un fichier de `src/_data/`, l'utiliser dans `src/index.njk`, puis déclarer le champ correspondant dans `.pages.yml` ([documentation](https://pagescms.org/docs/configuration/)).
### Mettre à jour les horaires
Chercher la section `id="activites"` et modifier les blocs `.schedule-card` (jour, heure, salle, ville).
### Mettre à jour les tarifs
Chercher la section `id="tarifs"` et modifier les valeurs dans les `.price-amount` et la liste des avantages.
### Mettre à jour les contacts
Chercher la section `id="contact"` et modifier les noms, titres et numéros de téléphone dans les `.contact-card`.
### Ajouter une actualité
Chercher la section `id="actualites"` et remplacer le bloc `.p-5.rounded-4.bg-light` (message "Aucune actualité") par une ou plusieurs cartes Bootstrap :
@ -114,7 +144,7 @@ Chercher la section `id="actualites"` et remplacer le bloc `.p-5.rounded-4.bg-li
### Ajouter une photo à la galerie
1. Copier l'image dans `public/` (formats acceptés : JPG, PNG, WebP).
1. Copier l'image dans `src/` (formats acceptés : JPG, PNG, WebP).
2. Dans la section `id="galerie"`, dupliquer un bloc `.col-md-6` et adapter le `src` et le `alt`.
```html
@ -137,16 +167,8 @@ Chercher la section `id="actualites"` et remplacer le bloc `.p-5.rounded-4.bg-li
| Numéro d'association | 27015 |
| Fédération | FFEPGV (1re fédération non-compétitive, reconnue d'utilité publique) |
| Label | Qualité Club Sport-Santé 2025-2029 |
| Email | gymnastiquevolontaireconches@gmail.com |
| Adresse | 39 bis rue François Décorchemont, 27190 Conches-en-Ouche |
### Bureau
| Rôle | Nom | Téléphone |
|---|---|---|
| Président | Didier MASSÉ | 06 87 75 11 15 |
| Secrétaire | Patricia ODEN | 06 84 44 03 07 |
| Trésorière | Monique LORIEUL | 06 20 17 47 54 |
Saison, tarifs, bureau, adresse postale et email : voir `src/_data/saison.yml` et `src/_data/contacts.yml` (ou Pages CMS).
### Moniteur
@ -162,14 +184,6 @@ Chercher la section `id="actualites"` et remplacer le bloc `.p-5.rounded-4.bg-li
Séances hors congés scolaires.
### Tarifs 2025-2026
| Poste | Montant |
|---|---|
| Licence FFEPGV (obligatoire) | 29,80 € |
| Cotisation 1 cours / semaine | 100,00 € |
| Cotisation 2 cours / semaine | 155,00 € |
---
## Technologies utilisées
@ -178,10 +192,12 @@ Séances hors congés scolaires.
|---|---|---|
| [Bootstrap](https://getbootstrap.com) | 5.3.3 | Framework CSS/JS (chargé via CDN) |
| [Bootstrap Icons](https://icons.getbootstrap.com) | 1.11.3 | Icônes (chargées via CDN) |
| Netlify | — | Hébergement et déploiement continu |
| [Eleventy](https://www.11ty.dev) | 3.x | Générateur de site statique (assemble la page et les données) |
| [Pages CMS](https://pagescms.org) | — | Interface d'édition des données (gratuite, sans hébergement) |
| Netlify | — | Hébergement, génération et déploiement continu |
| GitHub | — | Dépôt de code source |
Le site ne nécessite **aucun serveur**, **aucune base de données** et **aucune dépendance Node.js**. Toute modification se fait directement dans `public/index.html`.
Le site ne nécessite **aucun serveur** ni **aucune base de données** : Eleventy produit une page HTML statique au moment du déploiement, et Pages CMS se contente de modifier les fichiers YAML du dépôt.
---
@ -194,7 +210,7 @@ Le site ne nécessite **aucun serveur**, **aucune base de données** et **aucune
| Fond clair | `#f5f2fb` |
| Police | Système (Bootstrap par défaut) |
Les couleurs sont définies en variables CSS au début du bloc `<style>` de `index.html` :
Les couleurs sont définies en variables CSS au début du bloc `<style>` de `src/index.njk` :
```css
:root {

35
eleventy.config.js

@ -0,0 +1,35 @@
import { load as chargerYaml } from "js-yaml";
export default function (eleventyConfig) {
// Fichiers de données modifiés via Pages CMS (src/_data/*.yml)
eleventyConfig.addDataExtension("yml,yaml", (contenu) => chargerYaml(contenu));
// Images et autres fichiers statiques copiés tels quels
eleventyConfig.addPassthroughCopy("src/*.{png,jpg,jpeg,webp,svg,ico}");
// "29,80" ou "29.8" → { euros: "29", centimes: "80" }
eleventyConfig.addFilter("prix", (valeur) => {
const [euros, centimes = ""] = String(valeur).trim().replace(".", ",").split(",");
// Espace insécable avant « : ; ! ? » (typographie française)
eleventyConfig.addFilter("nbsp", (texte) =>
String(texte).replace(/ ([:;!?»])/g, "\u00a0$1").replace(/« /g, "«\u00a0")
);
return { euros, centimes: centimes.padEnd(2, "0") };
});
// "06 20 17 47 54" → "+33620174754" (pour les liens tel:)
eleventyConfig.addFilter("tel", (numero) => {
const chiffres = String(numero).replace(/[^\d+]/g, "");
return chiffres.startsWith("0") ? "+33" + chiffres.slice(1) : chiffres;
});
// Espace insécable avant « : ; ! ? » (typographie française)
eleventyConfig.addFilter("nbsp", (texte) =>
String(texte).replace(/ ([:;!?»])/g, "\u00a0$1").replace(/« /g, "«\u00a0")
);
return {
dir: { input: "src", output: "_site" },
};
}

6
netlify.toml

@ -1,5 +1,9 @@
[build]
publish = "public"
command = "npm run build"
publish = "_site"
[build.environment]
NODE_VERSION = "22"
[[headers]]
for = "/*"

1709
package-lock.json

File diff suppressed because it is too large

14
package.json

@ -0,0 +1,14 @@
{
"name": "gvdc-site",
"private": true,
"description": "Site de l'association Gymnastique Volontaire de Conches-en-Ouche",
"type": "module",
"scripts": {
"build": "eleventy",
"start": "eleventy --serve"
},
"devDependencies": {
"@11ty/eleventy": "^3.1.6",
"js-yaml": "^5.4.2"
}
}

19
src/_data/contacts.yml

@ -0,0 +1,19 @@
# Bureau et coordonnées — modifiable via Pages CMS (https://app.pagescms.org)
bureau:
- role: Présidente
prenom: Monique
nom: LORIEUL
telephone: 06 20 17 47 54
- role: Trésorière
prenom: Patricia
nom: ODEN
telephone: 06 84 44 03 07
- role: Secrétaire
prenom: Khalissa
nom: SELMANI
telephone: 06 77 43 42 31
adresse:
rue: 2 Place du onze novembre 1918
code_postal: "27190"
ville: Conches-en-Ouche
email: gymnastiquevolontaireconches@gmail.com

26
src/_data/saison.yml

@ -0,0 +1,26 @@
# Saison en cours et tarifs — modifiable via Pages CMS (https://app.pagescms.org)
annee: "2026-2027"
licence:
prix: "29,80"
avantages:
- Affiliation FFEPGV
- Assurance incluse
- Espace personnel FFEPGV
- Reçu fiscal
cotisations:
- titre: 1 cours / semaine
prix: "100,00"
populaire: true
avantages:
- "Au choix : Lundi, Mercredi ou Vendredi"
- 1 heure par séance
- Cours multisports
- Moniteur qualifié
- titre: 2 cours / semaine
prix: "155,00"
populaire: false
avantages:
- Parmi les 3 créneaux
- 1 heure par séance
- Progression optimisée
- Moniteur qualifié

114
public/index.html → src/index.njk

@ -326,8 +326,9 @@
════════════════════════════════════════════════ -->
<section id="tarifs">
<div class="container">
<h2 class="section-title text-center">Tarifs saison 2026-2027</h2>
<h2 class="section-title text-center">Tarifs saison {{ saison.annee }}</h2>
{%- set licence = saison.licence.prix | prix %}
<div class="row g-4 justify-content-center">
<!-- Licence -->
@ -338,63 +339,44 @@
</div>
<h5 class="fw-bold mb-1">Licence</h5>
<p class="text-muted small mb-3">Obligatoire</p>
<div class="price-amount">29<span class="fs-4">,80&nbsp;€</span></div>
<div class="price-amount">{{ licence.euros }}<span class="fs-4">,{{ licence.centimes }}&nbsp;€</span></div>
<p class="text-muted small mb-3">par saison</p>
<hr>
<ul class="list-unstyled text-start small">
<li class="mb-2"><i class="bi bi-check-circle-fill check-teal me-2"></i>Affiliation FFEPGV</li>
<li class="mb-2"><i class="bi bi-check-circle-fill check-teal me-2"></i>Assurance incluse</li>
<li class="mb-2"><i class="bi bi-check-circle-fill check-teal me-2"></i>Espace personnel FFEPGV</li>
<li class="mb-2"><i class="bi bi-check-circle-fill check-teal me-2"></i>Reçu fiscal</li>
{%- for avantage in saison.licence.avantages %}
<li class="mb-2"><i class="bi bi-check-circle-fill check-teal me-2"></i>{{ avantage | nbsp }}</li>
{%- endfor %}
</ul>
</div>
</div>
<!-- 1 cours/semaine -->
{% for cotisation in saison.cotisations %}
{%- set montant = cotisation.prix | prix %}
{%- set couleur = "purple" if cotisation.populaire else "teal" %}
<!-- {{ cotisation.titre }} -->
<div class="col-md-4 col-lg-3">
<div class="card pricing-card featured shadow-lg text-center p-4 h-100">
<div class="card pricing-card {{ "featured shadow-lg" if cotisation.populaire else "shadow" }} text-center p-4 h-100">
{%- if cotisation.populaire %}
<span class="badge rounded-pill mb-3 px-3 py-2" style="background:var(--gvdc-purple);">
Le plus populaire
</span>
{%- endif %}
<div class="mb-3">
<i class="bi bi-1-circle-fill fs-1" style="color:var(--gvdc-purple);"></i>
<i class="bi bi-{{ loop.index }}-circle-fill fs-1" style="color:var(--gvdc-{{ couleur }});"></i>
</div>
<h5 class="fw-bold mb-1">1 cours / semaine</h5>
<h5 class="fw-bold mb-1">{{ cotisation.titre | nbsp }}</h5>
<p class="text-muted small mb-3">Cotisation annuelle</p>
<div class="price-amount">100<span class="fs-4">,00&nbsp;€</span></div>
<div class="price-amount">{{ montant.euros }}<span class="fs-4">,{{ montant.centimes }}&nbsp;€</span></div>
<p class="text-muted small mb-3">par saison</p>
<hr>
<ul class="list-unstyled text-start small">
<li class="mb-2"><i class="bi bi-check-circle-fill check-purple me-2"></i>Au choix&nbsp;: Lundi, Mercredi ou Vendredi</li>
<li class="mb-2"><i class="bi bi-check-circle-fill check-purple me-2"></i>1 heure par séance</li>
<li class="mb-2"><i class="bi bi-check-circle-fill check-purple me-2"></i>Cours multisports</li>
<li class="mb-2"><i class="bi bi-check-circle-fill check-purple me-2"></i>Moniteur qualifié</li>
{%- for avantage in cotisation.avantages %}
<li class="mb-2"><i class="bi bi-check-circle-fill check-{{ couleur }} me-2"></i>{{ avantage | nbsp }}</li>
{%- endfor %}
</ul>
<p class="text-muted small mt-auto">+ 29,80&nbsp;€ de licence</p>
<p class="text-muted small mt-auto">+ {{ licence.euros }},{{ licence.centimes }}&nbsp;€ de licence</p>
</div>
</div>
<!-- 2 cours/semaine -->
<div class="col-md-4 col-lg-3">
<div class="card pricing-card shadow text-center p-4 h-100">
<div class="mb-3">
<i class="bi bi-2-circle-fill fs-1" style="color:var(--gvdc-teal);"></i>
</div>
<h5 class="fw-bold mb-1">2 cours / semaine</h5>
<p class="text-muted small mb-3">Cotisation annuelle</p>
<div class="price-amount">155<span class="fs-4">,00&nbsp;€</span></div>
<p class="text-muted small mb-3">par saison</p>
<hr>
<ul class="list-unstyled text-start small">
<li class="mb-2"><i class="bi bi-check-circle-fill check-teal me-2"></i>Parmi les 3 créneaux</li>
<li class="mb-2"><i class="bi bi-check-circle-fill check-teal me-2"></i>1 heure par séance</li>
<li class="mb-2"><i class="bi bi-check-circle-fill check-teal me-2"></i>Progression optimisée</li>
<li class="mb-2"><i class="bi bi-check-circle-fill check-teal me-2"></i>Moniteur qualifié</li>
</ul>
<p class="text-muted small mt-auto">+ 29,80&nbsp;€ de licence</p>
</div>
</div>
{% endfor %}
</div>
<p class="text-center text-muted mt-4">
@ -456,53 +438,25 @@
<h2 class="section-title text-center">Nous contacter</h2>
<!-- Bureau -->
<div class="row g-4 mb-4">
<div class="col-md-4">
<div class="card contact-card shadow-sm p-4 h-100">
<div class="d-flex align-items-center gap-3 mb-3">
<div class="icon-circle"><i class="bi bi-person-badge-fill"></i></div>
<div>
<div class="text-muted small">Présidente</div>
<div class="fw-bold">Monique LORIEUL</div>
</div>
</div>
<a href="tel:+33620174754" class="btn btn-outline-secondary btn-sm">
<i class="bi bi-telephone me-2"></i>06 20 17 47 54
</a>
</div>
</div>
<div class="row g-4 mb-4 justify-content-center">
{% for membre in contacts.bureau %}
<div class="col-md-4">
<div class="card contact-card shadow-sm p-4 h-100">
<div class="d-flex align-items-center gap-3 mb-3">
<div class="icon-circle"><i class="bi bi-person-badge-fill"></i></div>
<div>
<div class="text-muted small">Trésorière</div>
<div class="fw-bold">Patricia ODEN</div>
<div class="text-muted small">{{ membre.role }}</div>
<div class="fw-bold">{{ membre.prenom }} {{ membre.nom | upper }}</div>
</div>
</div>
<a href="tel:+33684440307" class="btn btn-outline-secondary btn-sm">
<i class="bi bi-telephone me-2"></i>06 84 44 03 07
{%- if membre.telephone %}
<a href="tel:{{ membre.telephone | tel }}" class="btn btn-outline-secondary btn-sm">
<i class="bi bi-telephone me-2"></i>{{ membre.telephone }}
</a>
{%- endif %}
</div>
</div>
<div class="col-md-4">
<div class="card contact-card shadow-sm p-4 h-100">
<div class="d-flex align-items-center gap-3 mb-3">
<div class="icon-circle"><i class="bi bi-person-badge-fill"></i></div>
<div>
<div class="text-muted small">Secrétaire</div>
<div class="fw-bold">Khalissa SELMANI</div>
</div>
</div>
<a href="tel:+33677434231" class="btn btn-outline-secondary btn-sm">
<i class="bi bi-telephone me-2"></i>06 77 43 42 31
</a>
</div>
</div>
{% endfor %}
</div>
<!-- Adresse & Email -->
@ -515,8 +469,8 @@
<div>
<div class="fw-bold mb-1">Adresse postale</div>
<p class="text-muted mb-0">
2 Place du onze novembre 1918<br>
27190 Conches-en-Ouche
{{ contacts.adresse.rue }}<br>
{{ contacts.adresse.code_postal }} {{ contacts.adresse.ville }}
</p>
</div>
</div>
@ -529,9 +483,9 @@
<div class="icon-circle"><i class="bi bi-envelope-fill"></i></div>
<div>
<div class="fw-bold mb-1">Email</div>
<a href="mailto:gymnastiquevolontaireconches@gmail.com"
<a href="mailto:{{ contacts.email }}"
style="color:var(--gvdc-purple); word-break:break-all;">
gymnastiquevolontaireconches@gmail.com
{{ contacts.email }}
</a>
</div>
</div>

0
public/infos-utiles4.png → src/infos-utiles4.png

Before

Width:  |  Height:  |  Size: 176 KiB

After

Width:  |  Height:  |  Size: 176 KiB

0
public/logo-cc-conches.png → src/logo-cc-conches.png

Before

Width:  |  Height:  |  Size: 56 KiB

After

Width:  |  Height:  |  Size: 56 KiB

0
public/logo-ffsv.jpeg → src/logo-ffsv.jpeg

Before

Width:  |  Height:  |  Size: 106 KiB

After

Width:  |  Height:  |  Size: 106 KiB

0
public/logo.png → src/logo.png

Before

Width:  |  Height:  |  Size: 154 KiB

After

Width:  |  Height:  |  Size: 154 KiB

0
public/photo-gym1.png → src/photo-gym1.png

Before

Width:  |  Height:  |  Size: 195 KiB

After

Width:  |  Height:  |  Size: 195 KiB

0
public/photo-gym2.jpeg → src/photo-gym2.jpeg

Before

Width:  |  Height:  |  Size: 157 KiB

After

Width:  |  Height:  |  Size: 157 KiB

0
public/visuel-club.png → src/visuel-club.png

Before

Width:  |  Height:  |  Size: 38 KiB

After

Width:  |  Height:  |  Size: 38 KiB

Loading…
Cancel
Save