diff --git a/app/app.config.js b/app/app.config.js index 50994d5..bfdca4d 100644 --- a/app/app.config.js +++ b/app/app.config.js @@ -1,5 +1,8 @@ export default defineAppConfig({ title: "Orchestre national d'Île-de-France - ONDIF", + brand: { + logoAlt: "Orchestre National d’Île-de-France", + }, theme: { primaryColor: '#6c63ff', }, diff --git a/app/app.vue b/app/app.vue index 80332fa..6744805 100644 --- a/app/app.vue +++ b/app/app.vue @@ -1,15 +1,17 @@ diff --git a/app/assets/fonts/robotoflex.ttf b/app/assets/fonts/robotoflex.ttf new file mode 100644 index 0000000..2e5c2a2 Binary files /dev/null and b/app/assets/fonts/robotoflex.ttf differ diff --git a/app/assets/img/icones/arrow_right.svg b/app/assets/img/icones/arrow_right.svg new file mode 100644 index 0000000..91d7f88 --- /dev/null +++ b/app/assets/img/icones/arrow_right.svg @@ -0,0 +1 @@ + \ No newline at end of file diff --git a/app/assets/img/icones/hamurger_black.svg b/app/assets/img/icones/hamurger_black.svg new file mode 100644 index 0000000..180e5e8 --- /dev/null +++ b/app/assets/img/icones/hamurger_black.svg @@ -0,0 +1,12 @@ + + + Group + + + + + + + + + \ No newline at end of file diff --git a/app/assets/img/icones/hamurger_white.svg b/app/assets/img/icones/hamurger_white.svg new file mode 100644 index 0000000..abb04d7 --- /dev/null +++ b/app/assets/img/icones/hamurger_white.svg @@ -0,0 +1,11 @@ + + + Group + + + + + + + + \ No newline at end of file diff --git a/app/assets/img/icones/ticket_black.svg b/app/assets/img/icones/ticket_black.svg new file mode 100644 index 0000000..fcd1287 --- /dev/null +++ b/app/assets/img/icones/ticket_black.svg @@ -0,0 +1,25 @@ + + + noun-tickets-956198 + + + + + + + + + + + + + + + + + + + + + + \ No newline at end of file diff --git a/app/assets/img/icones/ticket_white.svg b/app/assets/img/icones/ticket_white.svg new file mode 100644 index 0000000..a555249 --- /dev/null +++ b/app/assets/img/icones/ticket_white.svg @@ -0,0 +1,25 @@ + + + noun-tickets-956198 + + + + + + + + + + + + + + + + + + + + + + \ No newline at end of file diff --git a/app/assets/img/illustrations/map_idf.jpg b/app/assets/img/illustrations/map_idf.jpg new file mode 100644 index 0000000..b19f10a Binary files /dev/null and b/app/assets/img/illustrations/map_idf.jpg differ diff --git a/app/assets/img/logos/logo_pref_idf.webp b/app/assets/img/logos/logo_pref_idf.webp new file mode 100644 index 0000000..a03a289 Binary files /dev/null and b/app/assets/img/logos/logo_pref_idf.webp differ diff --git a/app/assets/img/logos/logo_region_idf.webp b/app/assets/img/logos/logo_region_idf.webp new file mode 100644 index 0000000..eddfe88 Binary files /dev/null and b/app/assets/img/logos/logo_region_idf.webp differ diff --git a/app/assets/img/logos/logo_region_paris.webp b/app/assets/img/logos/logo_region_paris.webp new file mode 100644 index 0000000..e883a90 Binary files /dev/null and b/app/assets/img/logos/logo_region_paris.webp differ diff --git a/app/assets/scss/base/_colors.scss b/app/assets/scss/base/_colors.scss index d47cc87..84612fb 100644 --- a/app/assets/scss/base/_colors.scss +++ b/app/assets/scss/base/_colors.scss @@ -10,4 +10,8 @@ $rouge_transparent: #e3061391; $vert: green; $bleu_fonce: #0056b3; -$bleu_clair: #007bff; \ No newline at end of file +$bleu_clair: #007bff; + + + + diff --git a/app/assets/scss/base/_fonts.scss b/app/assets/scss/base/_fonts.scss index 4892122..7cf1665 100644 --- a/app/assets/scss/base/_fonts.scss +++ b/app/assets/scss/base/_fonts.scss @@ -1,81 +1,76 @@ -@font-face { - font-family: 'brandontext_black_italic'; - src: url('~/assets/fonts/brandontext_black_italic.woff2') format('woff2'); -} -@font-face { - font-family: 'brandontext_black'; - src: url('~/assets/fonts/brandontext_black.woff2') format('woff2'); -} @font-face { font-family: 'brandontext_bold_italic'; - src: url('~/assets/fonts/brandontext_bold_italic.woff2') format('woff2'); + src: url('@/assets/fonts/brandontext_boldItalic.woff2') format('woff2'); } @font-face { font-family: 'brandontext_bold'; - src: url('~/assets/fonts/brandontext_bold.woff2') format('woff2'); -} -@font-face { - font-family: 'brandontext_light_italic'; - src: url('~/assets/fonts/brandontext_light_italic.woff2') format('woff2'); -} -@font-face { - font-family: 'brandontext_light'; - src: url('~/assets/fonts/brandontext_light.woff2') format('woff2'); + src: url('@/assets/fonts/brandontext_bold.woff2') format('woff2'); } @font-face { font-family: 'brandontext_medium_italic'; - src: url('~/assets/fonts/brandontext_medium_italic.woff2') format('woff2'); + src: url('@/assets/fonts/brandontext_mediumItalic.woff2') format('woff2'); } @font-face { font-family: 'brandontext_medium'; - src: url('~/assets/fonts/brandontext_medium.woff2') format('woff2'); + src: url('@/assets/fonts/brandontext_medium.woff2') format('woff2'); } @font-face { font-family: 'brandontext_regular_italic'; - src: url('~/assets/fonts/brandontext_regular_italic.woff2') format('woff2'); + src: url('@/assets/fonts/brandontext_regularItalic.woff2') format('woff2'); } @font-face { font-family: 'brandontext_regular'; - src: url('~/assets/fonts/brandontext_regular.woff2') format('woff2'); + src: url('@/assets/fonts/brandontext_regular.woff2') format('woff2'); } -@font-face { - font-family: 'brandontext_thin_italic'; - src: url('~/assets/fonts/brandontext_thin_italic.woff2') format('woff2'); -} -@font-face { - font-family: 'brandontext_thin'; - src: url('~/assets/fonts/brandontext_thin.woff2') format('woff2'); -} - @font-face { font-family: 'barlow_medium'; - src: url('~/assets/fonts/barlow_medium.ttf') format('truetype'); + src: url('@/assets/fonts/barlow_medium.ttf') format('truetype'); } @font-face { font-family: 'barlow_semibold'; - src: url('~/assets/fonts/barlow_semibold.ttf') format('truetype'); + src: url('@/assets/fonts/barlow_semibold.ttf') format('truetype'); } @font-face { font-family: 'barlow_regular'; - src: url('~/assets/fonts/barlow_regular.ttf') format('truetype'); + src: url('@/assets/fonts/barlow_regular.ttf') format('truetype'); } @font-face { font-family: 'barlow_light'; - src: url('~/assets/fonts/barlow_light.ttf') format('truetype'); + src: url('@/assets/fonts/barlow_light.ttf') format('truetype'); } @font-face { font-family: 'barlow_extrabold'; - src: url('~/assets/fonts/barlow_extrabold.ttf') format('truetype'); + src: url('@/assets/fonts/barlow_extrabold.ttf') format('truetype'); } @font-face { font-family: 'barlow_bold'; - src: url('~/assets/fonts/barlow_bold.ttf') format('truetype'); + src: url('@/assets/fonts/barlow_bold.ttf') format('truetype'); } @font-face { font-family: 'barlow_black'; - src: url('~/assets/fonts/barlow_black.ttf') format('truetype'); + src: url('@/assets/fonts/barlow_black.ttf') format('truetype'); } +@font-face { + font-family: "Roboto Flex"; + src: url("@/assets/fonts/robotoflex.ttf") format("truetype"); + font-weight: 100 1000; + font-stretch: 25% 151%; + font-style: oblique 0deg 10deg; + font-display: swap; +} + + .brandontext_bold { font-family: brandontext_bold !important; -} \ No newline at end of file +} + +.roboto_regular { + font-family: Roboto Flex; + font-weight: 400 +} + +.roboto_semibold { + font-family: Roboto Flex; + font-weight: 600 +} diff --git a/app/assets/scss/base/_reset.scss b/app/assets/scss/base/_reset.scss index a7d16e7..94f0e44 100644 --- a/app/assets/scss/base/_reset.scss +++ b/app/assets/scss/base/_reset.scss @@ -2,6 +2,9 @@ margin: 0; padding: 0; } +*, *::before, *::after { + box-sizing: border-box; +} h1, h2, h3, h4, h5, h6 { font-size: inherit; diff --git a/app/assets/scss/base/_spaces.scss b/app/assets/scss/base/_spaces.scss index 4cfaca6..391f875 100644 --- a/app/assets/scss/base/_spaces.scss +++ b/app/assets/scss/base/_spaces.scss @@ -19,3 +19,10 @@ .height_33 { height: 33px; } + +.margin_left_-20 { + margin-left: -20px; +} +.padding_top_1 { + padding-top: 1px; +} \ No newline at end of file diff --git a/app/assets/scss/base/_text.scss b/app/assets/scss/base/_text.scss deleted file mode 100644 index cec7c52..0000000 --- a/app/assets/scss/base/_text.scss +++ /dev/null @@ -1,9 +0,0 @@ -@use 'colors' as *; - -h1 { - color: red; -} - -p { - color: $vert; -} \ No newline at end of file diff --git a/app/assets/scss/component/_header_full.scss b/app/assets/scss/component/_header_full.scss deleted file mode 100644 index 60f7685..0000000 --- a/app/assets/scss/component/_header_full.scss +++ /dev/null @@ -1,214 +0,0 @@ -@use '../base/colors' as *; -@use '../layout/media_queries'; - -.header_full { - display: grid; - - grid-template-rows: 130px auto auto; - - @include media_queries.media_min(tablet_600) { - grid-template-columns: 1fr 500px 1fr; - } - @include media_queries.media_min(tablet_900) { - grid-template-columns: 1fr 890px 1fr; - } - @include media_queries.media_min(desktop_1000) { - grid-template-columns: auto 980px auto; - } - @include media_queries.media_min(desktop_1100) { - grid-template-columns: auto 1090px auto; - } - @include media_queries.media_min(desktop_1200) { - grid-template-columns: auto 1160px auto; - } - @include media_queries.media_min(desktop_1300) { - grid-template-columns: 1fr 1250px 1fr; - } - @include media_queries.media_min(desktop_1500) { - grid-template-columns: 1fr 1420px 1fr; - } - @include media_queries.media_min(desktop_1800) { - grid-template-columns: 1fr 1700px 1fr; - } - - - nav { - color: $blanc; - a { - color: $blanc; - } - } - - .header_navigation { - grid-column: 2; - grid-row: 1; - z-index: 10; - } - .obscur { - grid-column: 1 / -1; - grid-row: 1; - z-index: 5; - //background-color: #0000007a; - background-color: rgba(0,0,0,.4); - } - .header-img_cont { - grid-column: 1 / -1; - grid-row: 1 / -1; - } - .header-img_text { - grid-column: 2; - grid-row: 3; - color: $blanc; - - width: 650px; - - margin-left: 80px; - margin-bottom: 150px; - - - .header-img_titre { - margin-bottom: 10px; - text-transform: uppercase; - font-family: 'barlow_black'; - font-size: 50px; - } - .header-img_description { - margin-bottom: 20px; - font-family: 'barlow_regular'; - font-size: 20px; - } - - .decouvrir { - display: flex; - .decouvrir_icone { - margin-top: 2px; - margin-right: 5px; - } - .decouvrir_texte { - font-family: 'barlow_regular'; - font-size: 18px; - } - } - } - -} - -.header_full_2 { - display: grid; - - @include media_queries.media_min(tablet_600) { - grid-template-rows: 117px auto auto; - } - @include media_queries.media_min(tablet_900) { - grid-template-rows: 117px auto auto; - } - @include media_queries.media_min(desktop_1800) { - grid-template-rows: 130px auto auto; - } - - @include media_queries.media_min(tablet_600) { - grid-template-columns: 1fr 500px 1fr; - } - @include media_queries.media_min(tablet_900) { - grid-template-columns: 1fr 890px 1fr; - } - @include media_queries.media_min(desktop_1000) { - grid-template-columns: auto 980px auto; - } - @include media_queries.media_min(desktop_1100) { - grid-template-columns: auto 1090px auto; - } - @include media_queries.media_min(desktop_1200) { - grid-template-columns: auto 1160px auto; - } - @include media_queries.media_min(desktop_1300) { - grid-template-columns: 1fr 1250px 1fr; - } - @include media_queries.media_min(desktop_1500) { - grid-template-columns: 1fr 1420px 1fr; - } - @include media_queries.media_min(desktop_1800) { - grid-template-columns: 1fr 1700px 1fr; - } - - - nav { - color: $noir; - a { - color: $noir; - } - } - - .header_navigation { - grid-column: 2; - grid-row: 1; - z-index: 10; - } - .obscur { - grid-column: 1 / -1; - grid-row: 1; - z-index: 5; - background-color: rgb(255 255 255 / 98%); - } - .header-img_cont { - grid-column: 1 / -1; - grid-row: 1 / -1; - } - - .header-img_text { - grid-column: 2; - grid-row: 3; - color: $blanc; - - width: 650px; - - - margin-left: 80px; - margin-bottom: 150px; - - - .header-img_titre { - display: inline-block; - background-color: $rouge_transparent; - - padding-bottom: 5px; - padding-left: 10px; - padding-right: 10px; - text-transform: uppercase; - font-family: 'barlow_black'; - font-size: 50px; - } - .header-img_description { - display: inline-block; - background-color: $rouge_transparent; - padding-bottom: 20px; - padding-top: 5px; - padding-left: 10px; - padding-right: 10px; - font-family: 'barlow_regular'; - font-size: 20px; - } - - .decouvrir { - display: flex; - - .decouvrir_icone { - display: inline-block; - background-color: $rouge_transparent; - padding-top: 2px; - padding-left: 10px; - padding-right: 5px; - padding-bottom: 5px; - } - .decouvrir_texte { - display: inline-block; - background-color: $rouge_transparent; - padding-bottom: 5px; - font-family: 'barlow_regular'; - font-size: 18px; - padding-right: 10px; - } - } - } - -} \ No newline at end of file diff --git a/app/assets/scss/component/_header_layout.scss b/app/assets/scss/component/_header_layout.scss new file mode 100644 index 0000000..9ef1bd8 --- /dev/null +++ b/app/assets/scss/component/_header_layout.scss @@ -0,0 +1,129 @@ +@use '../base/colors' as *; +@use '../layout/media_queries'; + +/* thème clair */ +.header_layout.header--light { + --header-text-color: #{$noir}; +} + +/* thème sombre */ +.header_layout.header--dark { + --header-text-color: #{$blanc}; +} + +.header_layout { + display: grid; + + grid-template-rows: 130px auto auto; + + @include media_queries.media_max(tablet_700) { + grid-template-columns: 10px minmax(0, 1fr) 10px; + } + @include media_queries.media_min(tablet_700) { + grid-template-columns: 10px minmax(0, 1fr) 10px; + } + @include media_queries.media_min(tablet_800) { + grid-template-columns: 10px minmax(0, 1fr) 10px; + } + @include media_queries.media_min(tablet_900) { + grid-template-columns: 15px minmax(0, 1fr) 15px; + } + @include media_queries.media_min(desktop_1000) { + grid-template-columns: auto 980px auto; + } + @include media_queries.media_min(desktop_1100) { + grid-template-columns: auto 1090px auto; + } + @include media_queries.media_min(desktop_1200) { + grid-template-columns: auto 1160px auto; + } + @include media_queries.media_min(desktop_1300) { + grid-template-columns: 1fr 1250px 1fr; + } + @include media_queries.media_min(desktop_1500) { + grid-template-columns: 1fr 1420px 1fr; + } + @include media_queries.media_min(desktop_1800) { + grid-template-columns: 1fr 1700px 1fr; + } + + + nav { + color: var(--header-text-color); + a { + color: var(--header-text-color); + } + } + + .header_navigation { + grid-column: 2; + grid-row: 1; + z-index: 10; + } + .obscur { + grid-column: 1 / -1; + grid-row: 1; + z-index: 5; + //background-color: #0000007a; + background-color: rgba(0,0,0,.4); + } + .header-img_cont { + grid-column: 1 / -1; + grid-row: 1 / -1; + } + .header-img_text { + grid-column: 2; + grid-row: 3; + color: $blanc; + + + + margin-left: 80px; + margin-bottom: 150px; + + @include media_queries.media_max(tablet_800) { + width: 500px; + } + @include media_queries.media_min(tablet_800) { + width: 650px; + } + + .header-img_titre { + margin-bottom: 10px; + text-transform: uppercase; + font-family: 'barlow_black'; + + @include media_queries.media_max(tablet_800) { + font-size: 40px; + } + @include media_queries.media_min(tablet_800) { + font-size: 50px; + } + } + .header-img_description { + margin-bottom: 20px; + font-family: 'barlow_regular'; + + @include media_queries.media_max(tablet_800) { + font-size: 18px; + } + @include media_queries.media_min(tablet_800) { + font-size: 20px; + } + } + + .decouvrir { + display: flex; + .decouvrir_icone { + margin-top: 2px; + margin-right: 5px; + } + .decouvrir_texte { + font-family: 'barlow_regular'; + font-size: 18px; + } + } + } + +} + diff --git a/app/assets/scss/component/_header_nav.scss b/app/assets/scss/component/_header_nav.scss index 0b7efbb..1dd9914 100644 --- a/app/assets/scss/component/_header_nav.scss +++ b/app/assets/scss/component/_header_nav.scss @@ -8,11 +8,53 @@ font-family: 'brandontext_regular'; font-size: 16px; - .header_nav_item { + .header_nav_topbar_item { + list-style: none; + cursor: pointer; + margin-right: 30px; &:last-child { margin-right: 0px; } + position: relative; + cursor: pointer; + + &:hover { + .header_nav_topbar_submenu { + visibility: visible; + /* Pour l'effet de transition */ + opacity: 1; + } + } + } + .header_nav_topbar_submenu { + position: absolute; + left: 0; + z-index: 2; + width: 187px; + visibility:hidden; + /* Pour l'effet de transition */ + opacity: 0; + transition: visibility 0.2s,opacity 0.2s cubic-bezier(0.4, 0, 1, 1); + padding-top: 10px; + padding-left: 9px; + padding-right: 16px; + padding-bottom: 5px; + text-align: left; + background-color: rgba(255, 255, 255, 0.95); + border-radius: 3px; + + .header_nav_topbar_submenu_item { + list-style: none; + font-family: 'brandontext_regular'; + font-size: 15px; + padding-bottom: 2px; + &:hover { + a { + color: var(--c-brand_rouge); + } + } + } } .header_nav_lang { display: flex; @@ -29,12 +71,16 @@ display: grid; grid-template-rows: 1fr; + grid-template-columns: 1fr; - @include media_queries.media_min(tablet_600) { + @include media_queries.media_min(tablet_701) { grid-template-columns: 140px 1fr; - } + } + @include media_queries.media_min(tablet_800) { + grid-template-columns: 140px 1fr; + } @include media_queries.media_min(tablet_900) { - grid-template-columns: 140px 1fr; + grid-template-columns: 171px 1fr; } @include media_queries.media_min(desktop_1000) { grid-template-columns: 200px 1fr; @@ -51,16 +97,65 @@ } .header_nav_logo { - margin-top: -17px; + + @include media_queries.media_min(tablet_700) { + margin-top: -7px; + } + @include media_queries.media_min(tablet_800) { + margin-top: -7px; + } + @include media_queries.media_min(tablet_900) { + margin-top: -17px; + } + + + @include media_queries.media_max(tablet_700) { + width: 166px; + margin-left: 43px; + } + @include media_queries.media_max(phone_500) { + margin-left: 0px; + } + @include media_queries.media_max(phone_300) { + margin-left: 0px; + } + + + } .header_nav_cont { - margin-left: 30px; - margin-right: 30px; + + @include media_queries.media_max(tablet_800) { + margin-left: 40px; + margin-right: 20px; + } + @include media_queries.media_min(tablet_800) { + margin-left: 25px; + margin-right: 25px; + } + @include media_queries.media_min(tablet_900) { + margin-left: 30px; + margin-right: 30px; + } + + @include media_queries.media_max(tablet_700) { + margin-top: -9px; + } .header_nav { display: flex; + row-gap: 13px; justify-content: center; + @include media_queries.media_min(tablet_700) { + justify-content: flex-start; + } + @include media_queries.media_min(tablet_800) { + justify-content: center; + } + flex-wrap: wrap; + + text-wrap-mode: nowrap; font-family: 'brandontext_regular'; @@ -81,8 +176,23 @@ } .header_nav_item { - margin-right: 34px; - @include media_queries.media_min(tablet_600) { + position: relative; + cursor: pointer; + + &:hover { + .header_nav_sub_menu { + visibility: visible; + /* Pour l'effet de transition */ + opacity: 1; + } + } + list-style: none; + + + &:nth-child(5) { + margin-right: 10px; + } + @include media_queries.media_min(tablet_701) { margin-right: 20px; } @include media_queries.media_min(tablet_900) { @@ -100,24 +210,51 @@ &:last-child { margin-right: 0px; } + + } + + .header_nav_sub_menu { + position: absolute; + left: 0; + z-index: 2; + visibility:hidden; + /* Pour l'effet de transition */ + opacity: 0; + transition: visibility 0.2s,opacity 0.2s cubic-bezier(0.4, 0, 1, 1); + padding-top: 10px; + padding-left: 9px; + padding-right: 16px; + padding-bottom: 5px; + text-align: left; + background-color: rgba(255, 255, 255, 0.93); + border-radius: 3px; + + .header_nav_sub_menu_item { + list-style: none; + font-family: 'brandontext_regular'; + font-size: 18px; + padding-bottom: 2px; + &:hover { + a { + color: var(--c-brand_rouge); + } + } + } + } + + .header_nav_icones { + display: flex; } .nav_icone { display: flex; .nav_icone_img { - margin-right: 6px; - - @include media_queries.media_min(tablet_600) { - margin-top: 1px; - } - @include media_queries.media_min(tablet_900) { - margin-top: 1px; - } - @include media_queries.media_min(desktop_1800) { - margin-top: 2px; - } + img { + @include media_queries.media_max(tablet_600) { + width: 83%; + } @include media_queries.media_min(tablet_600) { width: 83%; } @@ -128,9 +265,195 @@ width: 100%; } } - + } + .nav_icone_img--agenda { + margin-right: 13px; + @include media_queries.media_min(tablet_600) { + margin-top: 1px; + } + @include media_queries.media_min(tablet_900) { + margin-top: 2px; + } + @include media_queries.media_min(desktop_1800) { + margin-top: 2px; + } + } + .nav_icone_img--ticket { + width: 46px; + margin-top: -4px; } } } -} \ No newline at end of file + /* accessibilité pour que les écran est le message "ouvrir le menu" mais non visible sur l'écran en mode normal*/ + .sr-only { + position: absolute; + width: 1px; height: 1px; + padding: 0; margin: -1px; + overflow: hidden; + clip: rect(0, 0, 0, 0); + white-space: nowrap; + border: 0; + } + + /* Par défaut : desktop visible, mobile caché */ + .header_nav--desktop { display: flex; } + .header_nav--mobile { display: none; } + .header_nav--mobile-icons { display: none; } + .header_drawer { display: none; } + + /* ✅ Mobile < 700px : on inverse */ + @media (max-width: 700px) { + .header_nav--desktop { display: none; } + + .header_nav--mobile { + display: flex; + justify-content: flex-end; + margin-top: -21px; + } + + .header_nav--mobile-icons { + display: none; + @include media_queries.media_min(phone_400) { + display: flex; + } + justify-content: flex-end; + margin-top: -23px; + margin-right: 60px; + } + + .hamburger_black { + background-color: $noir; + } + .hamburger_white { + background-color: $blanc; + } + .header_burger { + position: relative; + background: transparent; + border: 0; + cursor: pointer; + + width: 27px; + + padding: 8px; + + font-size: 26px; + line-height: 1; + + img { + width: 31px; + } + .burger_line { + position: absolute; + left: 0; + width: 100%; + height: 3px; + transition: + transform 0.25s ease, + opacity 0.2s ease, + top 0.25s ease; + } + + .burger_line:nth-child(1) { top: 0; } + .burger_line:nth-child(2) { top: 8px; } + .burger_line:nth-child(3) { top: 16px; } + + &.is-open { + .burger_line:nth-child(1) { + top: 8px; + transform: rotate(45deg); + } + + .burger_line:nth-child(2) { + opacity: 0; + } + + .burger_line:nth-child(3) { + top: 8px; + transform: rotate(-45deg); + } + } + } + + .header_drawer { + display: block; + width: 100%; + position: absolute; + left: 0; + + border-top: 1px solid rgba(0,0,0,.1); + background-color: rgba(0, 0, 0, 0.9); + margin-top: 47px; + + + + padding-bottom: 10px; + padding-right: 10px; + padding-left: 40px; + } + + .header_drawer[data-open="false"] { + display: none; + } + + .header_drawer_inner { + display: flex; + flex-direction: column; + gap: 12px; + padding: 12px 0; + } + + .header_drawer_link { + text-decoration: none; + color: $blanc; + padding: 6px 0; + font-size: 26px; + position: relative; + cursor: pointer; + + + &.is-open { + .header_drawer_sub_menu { + display: block; + visibility: visible; + opacity: 1; + } + } + list-style: none; + } + .header_drawer_sub_menu { + display: none; + max-width: 300px; + //position: absolute; + left: 0; + z-index: 2; + visibility:hidden; + /* Pour l'effet de transition */ + opacity: 0; + transition: visibility 0.2s,opacity 0.2s cubic-bezier(0.4, 0, 1, 1); + margin-top: 10px; + margin-left: 20px; + padding-top: 10px; + padding-left: 9px; + padding-right: 16px; + padding-bottom: 5px; + text-align: left; + background-color: rgba(255, 255, 255, 0.93); + border-radius: 3px; + } + .header_drawer_sub_menu_item { + list-style: none; + font-family: 'brandontext_regular'; + font-size: 18px; + padding-bottom: 2px; + &:hover { + a { + color: var(--c-brand_rouge); + } + } + } + } + + +} diff --git a/app/assets/scss/component/_orbites.scss b/app/assets/scss/component/_orbites.scss new file mode 100644 index 0000000..de25892 --- /dev/null +++ b/app/assets/scss/component/_orbites.scss @@ -0,0 +1,33 @@ +.bg-orbs { + position: absolute; + inset: 0; + z-index: 0; + transform: translateZ(0); + overflow: hidden; +} + +.orb { + position: absolute; + border-radius: 999px; + filter: blur(3px); + opacity: 0.30; + will-change: transform; + transform: translate3d(0,0,0); + + //background: radial-gradient(circle, rgba(255,255,255,0.20), rgba(255,255,255,0) 60%); + background: red; +} + +.orb--1 { width: 100px; height: 100px; top: 2%; left: 18%; animation: orb1 6s ease-in-out infinite alternate; } +.orb--2 { width: 320px; height: 320px; top: 6%; left: 72%; animation: orb2 6s ease-in-out infinite alternate; } + +@keyframes orb1 { to { transform: translate3d(30px, 18px, 0); } } +@keyframes orb2 { to { transform: translate3d(-26px, 34px, 0); } } +@keyframes orb3 { to { transform: translate3d(22px, -28px, 0); } } +@keyframes orb4 { to { transform: translate3d(34px, -14px, 0); } } +@keyframes orb5 { to { transform: translate3d(-18px, -18px, 0); } } +@keyframes orb6 { to { transform: translate3d(-34px, 12px, 0); } } + +@media (prefers-reduced-motion: reduce) { + .orb { animation: none !important; } +} \ No newline at end of file diff --git a/app/assets/scss/layout/_layout.scss b/app/assets/scss/layout/_layout.scss index 28acc07..9c80eec 100644 --- a/app/assets/scss/layout/_layout.scss +++ b/app/assets/scss/layout/_layout.scss @@ -1,4 +1,13 @@ - .page-enter-active, + .app { + min-height: 100vh; + display: flex; + flex-direction: column; + } + // Pour que main occupe toute la place de la page et que le footer soit en bas (au cas où le main n'occupe pas toute la hauteur de la page + #main-content { + flex: 1; + } + .page-enter-active, .page-leave-active { transition: all 0.4s ease; } diff --git a/app/assets/scss/layout/_media_queries.scss b/app/assets/scss/layout/_media_queries.scss index 7212336..936754d 100644 --- a/app/assets/scss/layout/_media_queries.scss +++ b/app/assets/scss/layout/_media_queries.scss @@ -8,6 +8,7 @@ $breakpoints: ( "tablet_600": 600px, "tablet_640": 640px, "tablet_700": 700px, + "tablet_701": 701px, "tablet_800": 800px, "tablet_900": 900px, "desktop_1000": 1000px, diff --git a/app/assets/scss/main.scss b/app/assets/scss/main.scss index 49084f6..fe420f1 100644 --- a/app/assets/scss/main.scss +++ b/app/assets/scss/main.scss @@ -1,13 +1,19 @@ @use 'base/reset'; + +/* à remplacer par Design system */ @use 'base/colors'; -@use 'base/text'; @use 'base/button'; @use 'base/img'; @use 'base/fonts'; + @use 'base/spaces'; +/* Design system */ +@use "@root/design-system/tokens/index" as *; + @use 'layout/layout'; @use 'layout/media_queries'; -@use 'component/header_full'; -@use 'component/header_nav'; \ No newline at end of file +@use 'component/_header_layout'; +@use 'component/header_nav'; +@use 'component/orbites'; \ No newline at end of file diff --git a/app/components/Footer.vue b/app/components/Footer.vue new file mode 100644 index 0000000..f63c3f3 --- /dev/null +++ b/app/components/Footer.vue @@ -0,0 +1,193 @@ + + + + + + \ No newline at end of file diff --git a/app/components/NewsletterCta.vue b/app/components/NewsletterCta.vue new file mode 100644 index 0000000..69d28e9 --- /dev/null +++ b/app/components/NewsletterCta.vue @@ -0,0 +1,73 @@ + + + + + diff --git a/app/components/button_link.vue b/app/components/button_link.vue deleted file mode 100644 index ca4893a..0000000 --- a/app/components/button_link.vue +++ /dev/null @@ -1,30 +0,0 @@ - - - - - \ No newline at end of file diff --git a/app/components/concert/ConcertCard.vue b/app/components/concert/ConcertCard.vue new file mode 100644 index 0000000..060975c --- /dev/null +++ b/app/components/concert/ConcertCard.vue @@ -0,0 +1,88 @@ + + + + + \ No newline at end of file diff --git a/app/components/concert/ConcertCardList.vue b/app/components/concert/ConcertCardList.vue new file mode 100644 index 0000000..aaf9211 --- /dev/null +++ b/app/components/concert/ConcertCardList.vue @@ -0,0 +1,126 @@ + + + diff --git a/app/components/header/BurgerIcon.vue b/app/components/header/BurgerIcon.vue new file mode 100644 index 0000000..613ba09 --- /dev/null +++ b/app/components/header/BurgerIcon.vue @@ -0,0 +1,13 @@ + + + \ No newline at end of file diff --git a/app/components/header/HeaderDefault.vue b/app/components/header/HeaderDefault.vue new file mode 100644 index 0000000..1bf2b9f --- /dev/null +++ b/app/components/header/HeaderDefault.vue @@ -0,0 +1,34 @@ + + + + + \ No newline at end of file diff --git a/app/components/header/HeaderFull.vue b/app/components/header/HeaderFull.vue new file mode 100644 index 0000000..279f209 --- /dev/null +++ b/app/components/header/HeaderFull.vue @@ -0,0 +1,57 @@ + + + + diff --git a/app/components/header/HeaderNav.vue b/app/components/header/HeaderNav.vue new file mode 100644 index 0000000..458af89 --- /dev/null +++ b/app/components/header/HeaderNav.vue @@ -0,0 +1,278 @@ + + + + + diff --git a/app/components/header/HeaderWrapper.vue b/app/components/header/HeaderWrapper.vue new file mode 100644 index 0000000..2fd7dab --- /dev/null +++ b/app/components/header/HeaderWrapper.vue @@ -0,0 +1,21 @@ + + + \ No newline at end of file diff --git a/app/components/header_content.vue b/app/components/header_content.vue deleted file mode 100644 index ffa38c0..0000000 --- a/app/components/header_content.vue +++ /dev/null @@ -1,77 +0,0 @@ - - - - - \ No newline at end of file diff --git a/app/components/header_full.vue b/app/components/header_full.vue deleted file mode 100644 index 0e48c8c..0000000 --- a/app/components/header_full.vue +++ /dev/null @@ -1,36 +0,0 @@ - - - \ No newline at end of file diff --git a/app/components/section/PageSection.vue b/app/components/section/PageSection.vue new file mode 100644 index 0000000..ecb6491 --- /dev/null +++ b/app/components/section/PageSection.vue @@ -0,0 +1,59 @@ + + + + + + diff --git a/app/components/section/PageSectionInner.vue b/app/components/section/PageSectionInner.vue new file mode 100644 index 0000000..9905bde --- /dev/null +++ b/app/components/section/PageSectionInner.vue @@ -0,0 +1,99 @@ + + + + + + + \ No newline at end of file diff --git a/app/components/section/SectionContent.vue b/app/components/section/SectionContent.vue new file mode 100644 index 0000000..2b41187 --- /dev/null +++ b/app/components/section/SectionContent.vue @@ -0,0 +1,60 @@ + + + + + diff --git a/app/components/section/SectionTitle.vue b/app/components/section/SectionTitle.vue new file mode 100644 index 0000000..69c61f7 --- /dev/null +++ b/app/components/section/SectionTitle.vue @@ -0,0 +1,56 @@ + + + + + diff --git a/app/layouts/default.vue b/app/layouts/default.vue new file mode 100644 index 0000000..eaf251f --- /dev/null +++ b/app/layouts/default.vue @@ -0,0 +1,20 @@ + + + \ No newline at end of file diff --git a/app/layouts/pageheaderfull.vue b/app/layouts/pageheaderfull.vue new file mode 100644 index 0000000..ebc3d15 --- /dev/null +++ b/app/layouts/pageheaderfull.vue @@ -0,0 +1,15 @@ + \ No newline at end of file diff --git a/app/pages/agenda.vue b/app/pages/agenda.vue index 1478aea..7121444 100644 --- a/app/pages/agenda.vue +++ b/app/pages/agenda.vue @@ -1,68 +1,15 @@ - - - - \ No newline at end of file diff --git a/app/pages/agendatest.vue b/app/pages/agendatest.vue new file mode 100644 index 0000000..0b6bf9e --- /dev/null +++ b/app/pages/agendatest.vue @@ -0,0 +1,66 @@ + + + + + diff --git a/app/pages/concerts/concert-[id].vue b/app/pages/concerts/concert-[id].vue index 3038465..ec3a90e 100644 --- a/app/pages/concerts/concert-[id].vue +++ b/app/pages/concerts/concert-[id].vue @@ -19,6 +19,6 @@ }) - \ No newline at end of file diff --git a/app/pages/design-system.vue b/app/pages/design-system.vue new file mode 100644 index 0000000..ab5dbce --- /dev/null +++ b/app/pages/design-system.vue @@ -0,0 +1,138 @@ + + + + + + + \ No newline at end of file diff --git a/app/pages/index copie.vue b/app/pages/index copie.vue new file mode 100644 index 0000000..dcf47db --- /dev/null +++ b/app/pages/index copie.vue @@ -0,0 +1,90 @@ + + + + + diff --git a/app/pages/index.vue b/app/pages/index.vue index 5ca089f..d08c5a4 100644 --- a/app/pages/index.vue +++ b/app/pages/index.vue @@ -1,36 +1,122 @@ - \ No newline at end of file + diff --git a/app/pages/orchestre.vue b/app/pages/orchestre.vue new file mode 100644 index 0000000..d27abb0 --- /dev/null +++ b/app/pages/orchestre.vue @@ -0,0 +1,64 @@ + + + + + \ No newline at end of file diff --git a/app/pages/test_header_2.vue b/app/pages/test_header_2.vue index ef18056..3296012 100644 --- a/app/pages/test_header_2.vue +++ b/app/pages/test_header_2.vue @@ -34,7 +34,7 @@ console.log("test 3 : ",appConfig.title) // "Mon site Nuxt" - \ No newline at end of file diff --git a/app/utils/clientLog.js b/app/utils/clientLog.js new file mode 100644 index 0000000..3a58603 --- /dev/null +++ b/app/utils/clientLog.js @@ -0,0 +1,17 @@ +const ALLOWED_LEVELS = ['info', 'warn', 'error']; + +export async function clientLog(level, message, meta = {}) { + if (!ALLOWED_LEVELS.includes(level)) { + console.warn('clientLog: invalid level, fallback to info', level); + level = 'info'; + } + + try { + await $fetch('/api/log', { + method: 'POST', + body: { level, message, meta } + }); + } catch (e) { + console.error('Failed to send client log', e); + } +} \ No newline at end of file diff --git a/design-system/components/DsCard.vue b/design-system/components/DsCard.vue new file mode 100644 index 0000000..e34ec32 --- /dev/null +++ b/design-system/components/DsCard.vue @@ -0,0 +1,39 @@ + + + + + \ No newline at end of file diff --git a/design-system/primitives/DsButton.vue b/design-system/primitives/DsButton.vue new file mode 100644 index 0000000..6e72a3e --- /dev/null +++ b/design-system/primitives/DsButton.vue @@ -0,0 +1,225 @@ + + + + + diff --git a/design-system/primitives/DsButtonArrow.vue b/design-system/primitives/DsButtonArrow.vue new file mode 100644 index 0000000..e9bed6d --- /dev/null +++ b/design-system/primitives/DsButtonArrow.vue @@ -0,0 +1,161 @@ + + + + + \ No newline at end of file diff --git a/design-system/primitives/DsHeading.vue b/design-system/primitives/DsHeading.vue new file mode 100644 index 0000000..a5c0202 --- /dev/null +++ b/design-system/primitives/DsHeading.vue @@ -0,0 +1,143 @@ + + + + + \ No newline at end of file diff --git a/design-system/primitives/DsMedia.vue b/design-system/primitives/DsMedia.vue new file mode 100644 index 0000000..d87c6f9 --- /dev/null +++ b/design-system/primitives/DsMedia.vue @@ -0,0 +1,37 @@ + + + + + \ No newline at end of file diff --git a/design-system/primitives/DsText.vue b/design-system/primitives/DsText.vue new file mode 100644 index 0000000..7958f7a --- /dev/null +++ b/design-system/primitives/DsText.vue @@ -0,0 +1,127 @@ + + + + + + diff --git a/design-system/tokens/_colors.scss b/design-system/tokens/_colors.scss new file mode 100644 index 0000000..94d8fa1 --- /dev/null +++ b/design-system/tokens/_colors.scss @@ -0,0 +1,31 @@ +:root { + /* Texte */ + --c-text: #111; + --c-surface: #ffffff; + --c-text-muted: #555; + --c-text-invert: #fff; + + /* Marque / accent (ex: rouge ONDIF) */ + //--c-brand_rouge: #E30613; + --c-brand_rouge: #E20018; + --c-brand_rouge45: rgba(226, 0, 24, 0.45); + --c-brand_rouge-weak: #e3061391; + --c-backgroud-black: #111; + --c-backgroud-brandreverse: #ACCFCF; + + /* États */ + --c-success: green; + --c-warning: #E30613; + --c-danger: #E30613; + + /* Liens / info (si tu veux) */ + --c-info: #0056b3; + + --c-bleu_fonce: #0056b3; + --c-bleu_clair: #007bff; + --c-border: rgba(0,0,0,0.10); + --c-border-strong: rgba(0,0,0,0.18); + + --c-hover: rgba(0,0,0,0.04); + --c-focus: rgba(227, 6, 19, 0.25); +} \ No newline at end of file diff --git a/design-system/tokens/_fonts.scss b/design-system/tokens/_fonts.scss new file mode 100644 index 0000000..f4c48c8 --- /dev/null +++ b/design-system/tokens/_fonts.scss @@ -0,0 +1,102 @@ +@font-face { + font-family: "Roboto Flex"; + src: url("@/assets/fonts/robotoflex.ttf") format("truetype"); + font-weight: 100 1000; + font-stretch: 25% 151%; + font-style: oblique 0deg 10deg; + font-display: swap; +} + +@font-face { + font-family: 'Brandon Text'; + src: url('@/assets/fonts/brandontext_bold.woff2') format('woff2'); + font-weight: 700; + font-style: normal; + font-display: swap; +} + +@font-face { + font-family: 'Brandon Text'; + src: url('@/assets/fonts/brandontext_boldItalic.woff2') format('woff2'); + font-weight: 700; + font-style: italic; + font-display: swap; +} +@font-face { + font-family: 'Brandon Text'; + src: url('@/assets/fonts/brandontext_mediumItalic.woff2') format('woff2'); + font-weight: 500; + font-style: italic; + font-display: swap; +} +@font-face { + font-family: 'Brandon Text'; + src: url('@/assets/fonts/brandontext_medium.woff2') format('woff2'); + font-weight: 500; + font-style: normal; + font-display: swap; +} +@font-face { + font-family: 'Brandon Text'; + src: url('@/assets/fonts/brandontext_regularItalic.woff2') format('woff2'); + font-weight: 400; + font-style: italic; + font-display: swap; +} +@font-face { + font-family: 'Brandon Text'; + src: url('@/assets/fonts/brandontext_regular.woff2') format('woff2'); + font-weight: 400; + font-style: normal; + font-display: swap; +} +@font-face { + font-family: 'Barlow'; + src: url('@/assets/fonts/barlow_medium.ttf') format('truetype'); + font-weight: 500; + font-style: normal; + font-display: swap; +} +@font-face { + font-family: 'Barlow'; + src: url('@/assets/fonts/barlow_semibold.ttf') format('truetype'); + font-weight: 600; + font-style: normal; + font-display: swap; +} +@font-face { + font-family: 'Barlow'; + src: url('@/assets/fonts/barlow_regular.ttf') format('truetype'); + font-weight: 400; + font-style: normal; + font-display: swap; +} +@font-face { + font-family: 'Barlow'; + src: url('@/assets/fonts/barlow_light.ttf') format('truetype'); + font-weight: 300; + font-style: normal; + font-display: swap; +} +@font-face { + font-family: 'Barlow'; + src: url('@/assets/fonts/barlow_extrabold.ttf') format('truetype'); + font-weight: 800; + font-style: normal; + font-display: swap; +} +@font-face { + font-family: 'Barlow'; + src: url('@/assets/fonts/barlow_bold.ttf') format('truetype'); + font-weight: 700; + font-style: normal; + font-display: swap; +} +@font-face { + font-family: 'Barlow'; + src: url('@/assets/fonts/barlow_black.ttf') format('truetype'); + font-weight: 900; + font-style: normal; + font-display: swap; +} + diff --git a/design-system/tokens/_layout.scss b/design-system/tokens/_layout.scss new file mode 100644 index 0000000..73eedb2 --- /dev/null +++ b/design-system/tokens/_layout.scss @@ -0,0 +1,28 @@ +:root { + /* Containers – largeur de contenu */ + + /* padding latéral (respiration) */ + --page-padding-mobile: 0.5rem; /* 16px */ + --page-padding-tablet: 1.5rem; /* 24px */ + --page-padding-desktop: 2rem; /* 32px */ + + --container-narrow: 48rem; /* 768px → éditorial, texte long */ + --container-default: 72rem; /* 1152px → pages standard */ + --container-wide: 90rem; /* 1440px → listings, agenda */ + + --gap-cards: var(--sp-22); + + + +} + +@media (min-width: 600px) { + :root { + --gap-cards: var(--sp-16); + } +} +@media (min-width: 1200px) { + :root { + --gap-cards: var(--sp-22); + } +} \ No newline at end of file diff --git a/design-system/tokens/_radius.scss b/design-system/tokens/_radius.scss new file mode 100644 index 0000000..5bab899 --- /dev/null +++ b/design-system/tokens/_radius.scss @@ -0,0 +1,4 @@ +:root { + --r-md: 0.75rem; + --sh-soft: 0 2px 6px rgba(0,0,0,0.06), 0 0 20px rgba(0,0,0,0.08); +} \ No newline at end of file diff --git a/design-system/tokens/_shadow.scss b/design-system/tokens/_shadow.scss new file mode 100644 index 0000000..e6dd759 --- /dev/null +++ b/design-system/tokens/_shadow.scss @@ -0,0 +1,3 @@ +:root { + --sh-md: 0 8px 20px rgba(0, 0, 0, 0.12), 0 2px 6px rgba(0, 0, 0, 0.08); +} diff --git a/design-system/tokens/_spacing.scss b/design-system/tokens/_spacing.scss new file mode 100644 index 0000000..b050fdc --- /dev/null +++ b/design-system/tokens/_spacing.scss @@ -0,0 +1,31 @@ +:root { + /* Base unit */ + --sp-0: 0; + + /* Micro spacing (UI fine) */ + --sp-4: 0.25rem; /* 4px */ + --sp-6: 0.375rem; /* 6px */ + --sp-8: 0.5rem; /* 8px */ + --sp-12: 0.75rem; /* 12px */ + + /* Spacing standard */ + --sp-16: 1rem; /* 16px */ + --sp-20: 1.25rem; /* 20px */ + --sp-22: 1.375rem; /* 22px */ + --sp-24: 1.5rem; /* 24px */ + + /* Spacing fort (sections, titres) */ + --sp-32: 2rem; /* 32px */ + --sp-40: 2.5rem; /* 40px */ + --sp-45: 45px; /* 45px */ + --sp-48: 3rem; /* 48px */ + + /* Spacing très fort (pages, hero) */ + --sp-64: 4rem; /* 64px */ + --sp-80: 5rem; /* 80px */ + --sp-96: 6rem; /* 96px */ + --sp-120: 7.5rem; /* 120px */ + --sp-180: 11.25rem; /* 120px */ + --sp-200: 200px; /* 200px */ + --sp-220: 13.75rem; /* 220px */ +} \ No newline at end of file diff --git a/design-system/tokens/_typography.scss b/design-system/tokens/_typography.scss new file mode 100644 index 0000000..953ce16 --- /dev/null +++ b/design-system/tokens/_typography.scss @@ -0,0 +1,113 @@ +:root { + /* Font stacks (remplace Inter si tu as une font ONDIF) */ + --font-roboto: "Roboto Flex", system-ui, -apple-system, "Segoe UI", Roboto, Arial, sans-serif; + --font-brandon: 'Brandon Text', + system-ui, + -apple-system, + "Segoe UI", + Roboto, + Arial, + sans-serif; + --font-barlow: 'Barlow', + system-ui, + -apple-system, + "Segoe UI", + Roboto, + Arial, + sans-serif; + + /* Font weights */ + --fw-extralight: 200; + --fw-light: 300; + --fw-regular: 400; + --fw-medium: 500; + --fw-semibold: 600; + --fw-bold: 700; + --fw-extrabold: 800; + --fw-black: 900; + + /* Optical size (opsz) : utile avec Roboto Flex */ + --opsz-body: 14; + --opsz-title: 28; + + /* Line heights */ + --lh-tight: 1.15; + --lh-snug: 1.25; + --lh-base: 1.5; + + /* Letter spacing (optionnel mais utile) */ + --ls-tight: -0.01em; + --ls-normal: 0; + --ls-wide: 0.02em; + + /* Scale (mobile-first) */ + --fs-12: 0.75rem; /* 12 */ + --fs-14: 0.875rem; /* 14 */ + --fs-16: 1rem; /* 16 */ + --fs-17: 1.0625rem; /* 17 */ + --fs-18: 1.125rem; /* 18 */ + --fs-20: 1.25rem; /* 20 */ + --fs-23: 1.4375rem; /* 23 */ + --fs-24: 1.5rem; /* 24 */ + --fs-28: 1.75rem; /* 28 */ + --fs-30: 1.875rem; /* 30 */ + --fs-32: 2rem; /* 32 */ + --fs-40: 2.5rem; /* 40 */ + + /* Semantic mapping (ça c’est ton “API” DS) */ + --text-xs: var(--fs-12); + --text-sm: var(--fs-14); + --text-md: var(--fs-16); + --text-lg: var(--fs-18); + + --title-xs: var(--fs-16); + --title-xs2: var(--fs-17); + --title-sm: var(--fs-18); + --title-md: var(--fs-20); + --title-md2: var(--fs-23); + --title-lg: var(--fs-24); + --title-lg2: var(--fs-30); + --title-xl: var(--fs-32); + --title-2xl: var(--fs-40); +} + +/* Option : ajustements desktop */ +@media (max-width: 700px) { + :root { + --title-xs: var(--fs-12); + --title-xs2: var(--fs-14); + --title-sm: var(--fs-14); + --title-md: var(--fs-16); + --title-md2: var(--fs-17); + --title-lg: var(--fs-18); + --title-lg2: var(--fs-20); + --title-xl: var(--fs-20); + --title-2xl: var(--fs-24); + } +} +@media (min-width: 700px) { + :root { + --title-xs: var(--fs-14); + --title-xs2: var(--fs-16); + --title-sm: var(--fs-16); + --title-md: var(--fs-18); + --title-md2: var(--fs-20); + --title-lg: var(--fs-20); + --title-lg2: var(--fs-24); + --title-xl: var(--fs-24); + --title-2xl: var(--fs-32); + } +} +@media (min-width: 1024px) { + :root { + --title-xs: var(--fs-16); + --title-xs2: var(--fs-17); + --title-sm: var(--fs-18); + --title-md: var(--fs-20); + --title-md2: var(--fs-23); + --title-lg: var(--fs-24); + --title-lg2: var(--fs-30); + --title-xl: var(--fs-32); + --title-2xl: var(--fs-40); + } +} diff --git a/design-system/tokens/index.scss b/design-system/tokens/index.scss new file mode 100644 index 0000000..63e0028 --- /dev/null +++ b/design-system/tokens/index.scss @@ -0,0 +1,8 @@ +@use "./fonts"; +@use "./typography"; + +@use "./colors"; +@use "./spacing"; +@use "./radius"; +@use "./shadow"; +@use "./layout"; \ No newline at end of file diff --git a/nuxt.config.js b/nuxt.config.js index 605dded..8500d02 100644 --- a/nuxt.config.js +++ b/nuxt.config.js @@ -1,4 +1,6 @@ // https://nuxt.com/docs/api/configuration/nuxt-config +import { fileURLToPath, URL } from 'node:url' + export default defineNuxtConfig({ compatibilityDate: '2025-07-15', @@ -18,8 +20,41 @@ export default defineNuxtConfig({ }, }, + // Auto-import des composants du dossier app/ sans prefixe de chemin + components: [ + { path: '~/components', pathPrefix: false } + ], + + // un chemin avec root pour aller chercher les fichiers qui ne sont pas dans app mais à la racine avec un @ + vite: { + resolve: { + alias: { + '@root': fileURLToPath(new URL('./', import.meta.url)) + } + } + }, + + //une barre fine en haut de la page lors des chargements + loadingIndicator: { + color: '#dd1e1eff', + background: '#fff', + height: '20px' + }, + css: ['@/assets/scss/main.scss'], + + runtimeConfig: { + // Server-side only (jamais exposé au client) + strapiToken: process.env.STRAPI_API_TOKEN || '', + + // 🌍 Public (accessible dans le navigateur) + public: { + strapiUrl: process.env.NUXT_PUBLIC_STRAPI_URL || 'http://localhost:1337', + }, + }, + + //configuration du module @nuxt/image image: { // Domaine de tes images Strapi / OVH domains: [ @@ -55,4 +90,4 @@ export default defineNuxtConfig({ }, modules: ['@nuxt/image'], -}) \ No newline at end of file +}) diff --git a/package-lock.json b/package-lock.json index 06b7451..9af20e8 100644 --- a/package-lock.json +++ b/package-lock.json @@ -9,8 +9,12 @@ "dependencies": { "@nuxt/image": "^1.11.0", "nuxt": "^4.1.3", + "printf": "^0.6.1", + "radix-vue": "^1.9.17", "vue": "^3.5.22", - "vue-router": "^4.5.1" + "vue-router": "^4.5.1", + "winston": "^3.19.0", + "winston-daily-rotate-file": "^5.0.0" }, "devDependencies": { "sass": "^1.93.2" @@ -437,6 +441,26 @@ "node": ">=10.0.0" } }, + "node_modules/@colors/colors": { + "version": "1.6.0", + "resolved": "https://registry.npmjs.org/@colors/colors/-/colors-1.6.0.tgz", + "integrity": "sha512-Ir+AOibqzrIsL6ajt3Rz3LskB7OiMVHqltZmspbW/TJuTVuyOMirVqAkjfY6JISiLHgyNqicAC8AyHHGzNd/dA==", + "license": "MIT", + "engines": { + "node": ">=0.1.90" + } + }, + "node_modules/@dabh/diagnostics": { + "version": "2.0.8", + "resolved": "https://registry.npmjs.org/@dabh/diagnostics/-/diagnostics-2.0.8.tgz", + "integrity": "sha512-R4MSXTVnuMzGD7bzHdW2ZhhdPC/igELENcq5IjEverBvq5hn1SXCWcsi6eSsdWP0/Ur+SItRRjAktmdoX/8R/Q==", + "license": "MIT", + "dependencies": { + "@so-ric/colorspace": "^1.1.6", + "enabled": "2.0.x", + "kuler": "^2.0.0" + } + }, "node_modules/@emnapi/core": { "version": "1.5.0", "resolved": "https://registry.npmjs.org/@emnapi/core/-/core-1.5.0.tgz", @@ -894,6 +918,86 @@ "node": ">=14" } }, + "node_modules/@floating-ui/core": { + "version": "1.7.3", + "resolved": "https://registry.npmjs.org/@floating-ui/core/-/core-1.7.3.tgz", + "integrity": "sha512-sGnvb5dmrJaKEZ+LDIpguvdX3bDlEllmv4/ClQ9awcmCZrlx5jQyyMWFM5kBI+EyNOCDDiKk8il0zeuX3Zlg/w==", + "license": "MIT", + "dependencies": { + "@floating-ui/utils": "^0.2.10" + } + }, + "node_modules/@floating-ui/dom": { + "version": "1.7.4", + "resolved": "https://registry.npmjs.org/@floating-ui/dom/-/dom-1.7.4.tgz", + "integrity": "sha512-OOchDgh4F2CchOX94cRVqhvy7b3AFb+/rQXyswmzmGakRfkMgoWVjfnLWkRirfLEfuD4ysVW16eXzwt3jHIzKA==", + "license": "MIT", + "dependencies": { + "@floating-ui/core": "^1.7.3", + "@floating-ui/utils": "^0.2.10" + } + }, + "node_modules/@floating-ui/utils": { + "version": "0.2.10", + "resolved": "https://registry.npmjs.org/@floating-ui/utils/-/utils-0.2.10.tgz", + "integrity": "sha512-aGTxbpbg8/b5JfU1HXSrbH3wXZuLPJcNEcZQFMxLs3oSzgtVu6nFPkbbGGUvBcUjKV2YyB9Wxxabo+HEH9tcRQ==", + "license": "MIT" + }, + "node_modules/@floating-ui/vue": { + "version": "1.1.9", + "resolved": "https://registry.npmjs.org/@floating-ui/vue/-/vue-1.1.9.tgz", + "integrity": "sha512-BfNqNW6KA83Nexspgb9DZuz578R7HT8MZw1CfK9I6Ah4QReNWEJsXWHN+SdmOVLNGmTPDi+fDT535Df5PzMLbQ==", + "license": "MIT", + "dependencies": { + "@floating-ui/dom": "^1.7.4", + "@floating-ui/utils": "^0.2.10", + "vue-demi": ">=0.13.0" + } + }, + "node_modules/@floating-ui/vue/node_modules/vue-demi": { + "version": "0.14.10", + "resolved": "https://registry.npmjs.org/vue-demi/-/vue-demi-0.14.10.tgz", + "integrity": "sha512-nMZBOwuzabUO0nLgIcc6rycZEebF6eeUfaiQx9+WSk8e29IbLvPU9feI6tqW4kTo3hvoYAJkMh8n8D0fuISphg==", + "hasInstallScript": true, + "license": "MIT", + "bin": { + "vue-demi-fix": "bin/vue-demi-fix.js", + "vue-demi-switch": "bin/vue-demi-switch.js" + }, + "engines": { + "node": ">=12" + }, + "funding": { + "url": "https://github.com/sponsors/antfu" + }, + "peerDependencies": { + "@vue/composition-api": "^1.0.0-rc.1", + "vue": "^3.0.0-0 || ^2.6.0" + }, + "peerDependenciesMeta": { + "@vue/composition-api": { + "optional": true + } + } + }, + "node_modules/@internationalized/date": { + "version": "3.10.0", + "resolved": "https://registry.npmjs.org/@internationalized/date/-/date-3.10.0.tgz", + "integrity": "sha512-oxDR/NTEJ1k+UFVQElaNIk65E/Z83HK1z1WI3lQyhTtnNg4R5oVXaPzK3jcpKG8UHKDVuDQHzn+wsxSz8RP3aw==", + "license": "Apache-2.0", + "dependencies": { + "@swc/helpers": "^0.5.0" + } + }, + "node_modules/@internationalized/number": { + "version": "3.6.5", + "resolved": "https://registry.npmjs.org/@internationalized/number/-/number-3.6.5.tgz", + "integrity": "sha512-6hY4Kl4HPBvtfS62asS/R22JzNNy8vi/Ssev7x6EobfCp+9QIB2hKvI2EtbdJ0VSQacxVNtqhE/NmF/NZ0gm6g==", + "license": "Apache-2.0", + "dependencies": { + "@swc/helpers": "^0.5.0" + } + }, "node_modules/@ioredis/commands": { "version": "1.4.0", "resolved": "https://registry.npmjs.org/@ioredis/commands/-/commands-1.4.0.tgz", @@ -3111,12 +3215,103 @@ "url": "https://github.com/sponsors/sindresorhus" } }, + "node_modules/@so-ric/colorspace": { + "version": "1.1.6", + "resolved": "https://registry.npmjs.org/@so-ric/colorspace/-/colorspace-1.1.6.tgz", + "integrity": "sha512-/KiKkpHNOBgkFJwu9sh48LkHSMYGyuTcSFK/qMBdnOAlrRJzRSXAOFB5qwzaVQuDl8wAvHVMkaASQDReTahxuw==", + "license": "MIT", + "dependencies": { + "color": "^5.0.2", + "text-hex": "1.0.x" + } + }, + "node_modules/@so-ric/colorspace/node_modules/color": { + "version": "5.0.3", + "resolved": "https://registry.npmjs.org/color/-/color-5.0.3.tgz", + "integrity": "sha512-ezmVcLR3xAVp8kYOm4GS45ZLLgIE6SPAFoduLr6hTDajwb3KZ2F46gulK3XpcwRFb5KKGCSezCBAY4Dw4HsyXA==", + "license": "MIT", + "dependencies": { + "color-convert": "^3.1.3", + "color-string": "^2.1.3" + }, + "engines": { + "node": ">=18" + } + }, + "node_modules/@so-ric/colorspace/node_modules/color-convert": { + "version": "3.1.3", + "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-3.1.3.tgz", + "integrity": "sha512-fasDH2ont2GqF5HpyO4w0+BcewlhHEZOFn9c1ckZdHpJ56Qb7MHhH/IcJZbBGgvdtwdwNbLvxiBEdg336iA9Sg==", + "license": "MIT", + "dependencies": { + "color-name": "^2.0.0" + }, + "engines": { + "node": ">=14.6" + } + }, + "node_modules/@so-ric/colorspace/node_modules/color-name": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/color-name/-/color-name-2.1.0.tgz", + "integrity": "sha512-1bPaDNFm0axzE4MEAzKPuqKWeRaT43U/hyxKPBdqTfmPF+d6n7FSoTFxLVULUJOmiLp01KjhIPPH+HrXZJN4Rg==", + "license": "MIT", + "engines": { + "node": ">=12.20" + } + }, + "node_modules/@so-ric/colorspace/node_modules/color-string": { + "version": "2.1.4", + "resolved": "https://registry.npmjs.org/color-string/-/color-string-2.1.4.tgz", + "integrity": "sha512-Bb6Cq8oq0IjDOe8wJmi4JeNn763Xs9cfrBcaylK1tPypWzyoy2G3l90v9k64kjphl/ZJjPIShFztenRomi8WTg==", + "license": "MIT", + "dependencies": { + "color-name": "^2.0.0" + }, + "engines": { + "node": ">=18" + } + }, "node_modules/@speed-highlight/core": { "version": "1.2.7", "resolved": "https://registry.npmjs.org/@speed-highlight/core/-/core-1.2.7.tgz", "integrity": "sha512-0dxmVj4gxg3Jg879kvFS/msl4s9F3T9UXC1InxgOf7t5NvcPD97u/WTA5vL/IxWHMn7qSxBozqrnnE2wvl1m8g==", "license": "CC0-1.0" }, + "node_modules/@swc/helpers": { + "version": "0.5.17", + "resolved": "https://registry.npmjs.org/@swc/helpers/-/helpers-0.5.17.tgz", + "integrity": "sha512-5IKx/Y13RsYd+sauPb2x+U/xZikHjolzfuDgTAl/Tdf3Q8rslRvC19NKDLgAJQ6wsqADk10ntlv08nPFw/gO/A==", + "license": "Apache-2.0", + "dependencies": { + "tslib": "^2.8.0" + } + }, + "node_modules/@tanstack/virtual-core": { + "version": "3.13.13", + "resolved": "https://registry.npmjs.org/@tanstack/virtual-core/-/virtual-core-3.13.13.tgz", + "integrity": "sha512-uQFoSdKKf5S8k51W5t7b2qpfkyIbdHMzAn+AMQvHPxKUPeo1SsGaA4JRISQT87jm28b7z8OEqPcg1IOZagQHcA==", + "license": "MIT", + "funding": { + "type": "github", + "url": "https://github.com/sponsors/tannerlinsley" + } + }, + "node_modules/@tanstack/vue-virtual": { + "version": "3.13.13", + "resolved": "https://registry.npmjs.org/@tanstack/vue-virtual/-/vue-virtual-3.13.13.tgz", + "integrity": "sha512-Cf2xIEE8nWAfsX0N5nihkPYMeQRT+pHt4NEkuP8rNCn6lVnLDiV8rC8IeIxbKmQC0yPnj4SIBLwXYVf86xxKTQ==", + "license": "MIT", + "dependencies": { + "@tanstack/virtual-core": "3.13.13" + }, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/tannerlinsley" + }, + "peerDependencies": { + "vue": "^2.7.0 || ^3.0.0" + } + }, "node_modules/@trysound/sax": { "version": "0.2.0", "resolved": "https://registry.npmjs.org/@trysound/sax/-/sax-0.2.0.tgz", @@ -3155,6 +3350,18 @@ "integrity": "sha512-60BCwRFOZCQhDncwQdxxeOEEkbc5dIMccYLwbxsS4TUNeVECQ/pBJ0j09mrHOl/JJvpRPGwO9SvE4nR2Nb/a4Q==", "license": "MIT" }, + "node_modules/@types/triple-beam": { + "version": "1.3.5", + "resolved": "https://registry.npmjs.org/@types/triple-beam/-/triple-beam-1.3.5.tgz", + "integrity": "sha512-6WaYesThRMCl19iryMYP7/x2OVgCtbIVflDGFpWnb9irXI3UjYE4AzmYuiUKY1AJstGijoY+MgUszMgRxIYTYw==", + "license": "MIT" + }, + "node_modules/@types/web-bluetooth": { + "version": "0.0.20", + "resolved": "https://registry.npmjs.org/@types/web-bluetooth/-/web-bluetooth-0.0.20.tgz", + "integrity": "sha512-g9gZnnXVq7gM7v3tJCWV/qw7w+KeOlSHAhgF9RytFyifW6AF61hdT2ucrYhPq9hLs5JIryeupHV3qGk95dH9ow==", + "license": "MIT" + }, "node_modules/@unhead/vue": { "version": "2.0.19", "resolved": "https://registry.npmjs.org/@unhead/vue/-/vue-2.0.19.tgz", @@ -3525,6 +3732,94 @@ "integrity": "sha512-F4yc6palwq3TT0u+FYf0Ns4Tfl9GRFURDN2gWG7L1ecIaS/4fCIuFOjMTnCyjsu/OK6vaDKLCrGAa+KvvH+h4w==", "license": "MIT" }, + "node_modules/@vueuse/core": { + "version": "10.11.1", + "resolved": "https://registry.npmjs.org/@vueuse/core/-/core-10.11.1.tgz", + "integrity": "sha512-guoy26JQktXPcz+0n3GukWIy/JDNKti9v6VEMu6kV2sYBsWuGiTU8OWdg+ADfUbHg3/3DlqySDe7JmdHrktiww==", + "license": "MIT", + "dependencies": { + "@types/web-bluetooth": "^0.0.20", + "@vueuse/metadata": "10.11.1", + "@vueuse/shared": "10.11.1", + "vue-demi": ">=0.14.8" + }, + "funding": { + "url": "https://github.com/sponsors/antfu" + } + }, + "node_modules/@vueuse/core/node_modules/vue-demi": { + "version": "0.14.10", + "resolved": "https://registry.npmjs.org/vue-demi/-/vue-demi-0.14.10.tgz", + "integrity": "sha512-nMZBOwuzabUO0nLgIcc6rycZEebF6eeUfaiQx9+WSk8e29IbLvPU9feI6tqW4kTo3hvoYAJkMh8n8D0fuISphg==", + "hasInstallScript": true, + "license": "MIT", + "bin": { + "vue-demi-fix": "bin/vue-demi-fix.js", + "vue-demi-switch": "bin/vue-demi-switch.js" + }, + "engines": { + "node": ">=12" + }, + "funding": { + "url": "https://github.com/sponsors/antfu" + }, + "peerDependencies": { + "@vue/composition-api": "^1.0.0-rc.1", + "vue": "^3.0.0-0 || ^2.6.0" + }, + "peerDependenciesMeta": { + "@vue/composition-api": { + "optional": true + } + } + }, + "node_modules/@vueuse/metadata": { + "version": "10.11.1", + "resolved": "https://registry.npmjs.org/@vueuse/metadata/-/metadata-10.11.1.tgz", + "integrity": "sha512-IGa5FXd003Ug1qAZmyE8wF3sJ81xGLSqTqtQ6jaVfkeZ4i5kS2mwQF61yhVqojRnenVew5PldLyRgvdl4YYuSw==", + "license": "MIT", + "funding": { + "url": "https://github.com/sponsors/antfu" + } + }, + "node_modules/@vueuse/shared": { + "version": "10.11.1", + "resolved": "https://registry.npmjs.org/@vueuse/shared/-/shared-10.11.1.tgz", + "integrity": "sha512-LHpC8711VFZlDaYUXEBbFBCQ7GS3dVU9mjOhhMhXP6txTV4EhYQg/KGnQuvt/sPAtoUKq7VVUnL6mVtFoL42sA==", + "license": "MIT", + "dependencies": { + "vue-demi": ">=0.14.8" + }, + "funding": { + "url": "https://github.com/sponsors/antfu" + } + }, + "node_modules/@vueuse/shared/node_modules/vue-demi": { + "version": "0.14.10", + "resolved": "https://registry.npmjs.org/vue-demi/-/vue-demi-0.14.10.tgz", + "integrity": "sha512-nMZBOwuzabUO0nLgIcc6rycZEebF6eeUfaiQx9+WSk8e29IbLvPU9feI6tqW4kTo3hvoYAJkMh8n8D0fuISphg==", + "hasInstallScript": true, + "license": "MIT", + "bin": { + "vue-demi-fix": "bin/vue-demi-fix.js", + "vue-demi-switch": "bin/vue-demi-switch.js" + }, + "engines": { + "node": ">=12" + }, + "funding": { + "url": "https://github.com/sponsors/antfu" + }, + "peerDependencies": { + "@vue/composition-api": "^1.0.0-rc.1", + "vue": "^3.0.0-0 || ^2.6.0" + }, + "peerDependenciesMeta": { + "@vue/composition-api": { + "optional": true + } + } + }, "node_modules/abbrev": { "version": "3.0.1", "resolved": "https://registry.npmjs.org/abbrev/-/abbrev-3.0.1.tgz", @@ -3688,6 +3983,18 @@ "url": "https://github.com/sponsors/sindresorhus" } }, + "node_modules/aria-hidden": { + "version": "1.2.6", + "resolved": "https://registry.npmjs.org/aria-hidden/-/aria-hidden-1.2.6.tgz", + "integrity": "sha512-ik3ZgC9dY/lYVVM++OISsaYDeg1tb0VtP5uL3ouh1koGOaUMDPpbFIei4JkFimWUFPn90sbMNMXQAIVOlnYKJA==", + "license": "MIT", + "dependencies": { + "tslib": "^2.0.0" + }, + "engines": { + "node": ">=10" + } + }, "node_modules/ast-kit": { "version": "2.1.3", "resolved": "https://registry.npmjs.org/ast-kit/-/ast-kit-2.1.3.tgz", @@ -5136,6 +5443,12 @@ "integrity": "sha512-L18DaJsXSUk2+42pv8mLs5jJT2hqFkFE4j21wOmgbUqsZ2hL72NsUU785g9RXgo3s0ZNgVl42TiHp3ZtOv/Vyg==", "license": "MIT" }, + "node_modules/enabled": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/enabled/-/enabled-2.0.0.tgz", + "integrity": "sha512-AKrN98kuwOzMIdAizXGI86UFBoo26CL21UM763y1h/GMSJ4/OHU9k2YlsmBpyScFo/wbLzWQJBMCW4+IO3/+OQ==", + "license": "MIT" + }, "node_modules/encodeurl": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/encodeurl/-/encodeurl-2.0.0.tgz", @@ -5340,6 +5653,12 @@ "integrity": "sha512-VO5fQUzZtI6C+vx4w/4BWJpg3s/5l+6pRQEHzFRM8WFi4XffSP1Z+4qi7GbjWbvRQEbdIco5mIMq+zX4rPuLrw==", "license": "MIT" }, + "node_modules/fast-deep-equal": { + "version": "3.1.3", + "resolved": "https://registry.npmjs.org/fast-deep-equal/-/fast-deep-equal-3.1.3.tgz", + "integrity": "sha512-f3qQ9oQy9j2AhBe/H9VC91wLmKBCCU/gDOnKNAYG5hswO7BLKj09Hc5HYNz9cGI++xlpDCIgDaitVs03ATR84Q==", + "license": "MIT" + }, "node_modules/fast-fifo": { "version": "1.3.2", "resolved": "https://registry.npmjs.org/fast-fifo/-/fast-fifo-1.3.2.tgz", @@ -5397,6 +5716,12 @@ } } }, + "node_modules/fecha": { + "version": "4.2.3", + "resolved": "https://registry.npmjs.org/fecha/-/fecha-4.2.3.tgz", + "integrity": "sha512-OP2IUU6HeYKJi3i0z4A19kHMQoLVs4Hc+DPqqxI2h/DPZHTm/vjsfC6P0b4jCMy14XizLBqvndQ+UilD7707Jw==", + "license": "MIT" + }, "node_modules/figures": { "version": "6.1.0", "resolved": "https://registry.npmjs.org/figures/-/figures-6.1.0.tgz", @@ -5412,6 +5737,15 @@ "url": "https://github.com/sponsors/sindresorhus" } }, + "node_modules/file-stream-rotator": { + "version": "0.6.1", + "resolved": "https://registry.npmjs.org/file-stream-rotator/-/file-stream-rotator-0.6.1.tgz", + "integrity": "sha512-u+dBid4PvZw17PmDeRcNOtCP9CCK/9lRN2w+r1xIS7yOL9JFrIBKTvrYsxT4P0pGtThYTn++QS5ChHaUov3+zQ==", + "license": "MIT", + "dependencies": { + "moment": "^2.29.1" + } + }, "node_modules/file-uri-to-path": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/file-uri-to-path/-/file-uri-to-path-1.0.0.tgz", @@ -5430,6 +5764,12 @@ "node": ">=8" } }, + "node_modules/fn.name": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/fn.name/-/fn.name-1.1.0.tgz", + "integrity": "sha512-GRnmB5gPyJpAhTQdSZTSp9uaPSvl09KoYcMQtsB9rQoOmzs9dH6ffeccH+Z+cv6P68Hu5bC6JjRh4Ah/mHSNRw==", + "license": "MIT" + }, "node_modules/foreground-child": { "version": "3.3.1", "resolved": "https://registry.npmjs.org/foreground-child/-/foreground-child-3.3.1.tgz", @@ -6302,6 +6642,12 @@ "integrity": "sha512-xYSH7AvuQ6nXkq42x0v5S8/Iry+cfulBz/DJQzhIyESdLD7425jXsPy4vn5cCXU+HhRN2kVw51Vd1K6/By4BQg==", "license": "MIT" }, + "node_modules/kuler": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/kuler/-/kuler-2.0.0.tgz", + "integrity": "sha512-Xq9nH7KlWZmXAtodXDDRE7vs6DU1gTU8zYDHDiWLSip45Egwq3plLHzPn27NgvzL2r1LMPC1vdqh98sQxtqj4A==", + "license": "MIT" + }, "node_modules/launch-editor": { "version": "2.11.1", "resolved": "https://registry.npmjs.org/launch-editor/-/launch-editor-2.11.1.tgz", @@ -6466,6 +6812,23 @@ "integrity": "sha512-xfBaXQd9ryd9dlSDvnvI0lvxfLJlYAZzXomUYzLKtUeOQvOP5piqAWuGtrhWeqaXK9hhoM/iyJc5AV+XfsX3HQ==", "license": "MIT" }, + "node_modules/logform": { + "version": "2.7.0", + "resolved": "https://registry.npmjs.org/logform/-/logform-2.7.0.tgz", + "integrity": "sha512-TFYA4jnP7PVbmlBIfhlSe+WKxs9dklXMTEGcBCIvLhE/Tn3H6Gk1norupVW7m5Cnd4bLcr08AytbyV/xj7f/kQ==", + "license": "MIT", + "dependencies": { + "@colors/colors": "1.6.0", + "@types/triple-beam": "^1.3.2", + "fecha": "^4.2.0", + "ms": "^2.1.1", + "safe-stable-stringify": "^2.3.1", + "triple-beam": "^1.3.0" + }, + "engines": { + "node": ">= 12.0.0" + } + }, "node_modules/lru-cache": { "version": "5.1.1", "resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-5.1.1.tgz", @@ -6726,6 +7089,15 @@ "integrity": "sha512-aF7yRQr/Q0O2/4pIXm6PZ5G+jAd7QS4Yu8m+WEeEHGnbo+7mE36CbLSDQiXYV8bVL3NfmdeqPJct0tUlnjVSnA==", "license": "MIT" }, + "node_modules/moment": { + "version": "2.30.1", + "resolved": "https://registry.npmjs.org/moment/-/moment-2.30.1.tgz", + "integrity": "sha512-uEmtNhbDOrWPFS+hdjFCBfy9f2YoyzRpwcl+DqpC6taX21FzsTLQVbMV/W7PzNSX6x/bhC1zA3c2UQ5NzH6how==", + "license": "MIT", + "engines": { + "node": "*" + } + }, "node_modules/mrmime": { "version": "2.0.1", "resolved": "https://registry.npmjs.org/mrmime/-/mrmime-2.0.1.tgz", @@ -7145,6 +7517,15 @@ "node": "^14.16.0 || >=16.10.0" } }, + "node_modules/object-hash": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/object-hash/-/object-hash-3.0.0.tgz", + "integrity": "sha512-RSn9F68PjH9HqtltsSnqYC1XXoWe9Bju5+213R98cNGttag9q9yAOTzdbsqvIa7aNm5WffBZFpWYr2aWrklWAw==", + "license": "MIT", + "engines": { + "node": ">= 6" + } + }, "node_modules/ofetch": { "version": "1.4.1", "resolved": "https://registry.npmjs.org/ofetch/-/ofetch-1.4.1.tgz", @@ -7196,6 +7577,15 @@ "wrappy": "1" } }, + "node_modules/one-time": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/one-time/-/one-time-1.0.0.tgz", + "integrity": "sha512-5DXOiRKwuSEcQ/l0kGCF6Q3jcADFv5tSmRaJck/OqkVFcOzutB134KRSfF0xDrL39MNnqxbHBbUUcjZIhTgb2g==", + "license": "MIT", + "dependencies": { + "fn.name": "1.x.x" + } + }, "node_modules/onetime": { "version": "6.0.0", "resolved": "https://registry.npmjs.org/onetime/-/onetime-6.0.0.tgz", @@ -8100,6 +8490,15 @@ "url": "https://github.com/sponsors/sindresorhus" } }, + "node_modules/printf": { + "version": "0.6.1", + "resolved": "https://registry.npmjs.org/printf/-/printf-0.6.1.tgz", + "integrity": "sha512-is0ctgGdPJ5951KulgfzvHGwJtZ5ck8l042vRkV6jrkpBzTmb/lueTqguWHy2JfVA+RY6gFVlaZgUS0j7S/dsw==", + "license": "MIT", + "engines": { + "node": ">= 0.9.0" + } + }, "node_modules/process": { "version": "0.11.10", "resolved": "https://registry.npmjs.org/process/-/process-0.11.10.tgz", @@ -8181,6 +8580,28 @@ ], "license": "MIT" }, + "node_modules/radix-vue": { + "version": "1.9.17", + "resolved": "https://registry.npmjs.org/radix-vue/-/radix-vue-1.9.17.tgz", + "integrity": "sha512-mVCu7I2vXt1L2IUYHTt0sZMz7s1K2ZtqKeTIxG3yC5mMFfLBG4FtE1FDeRMpDd+Hhg/ybi9+iXmAP1ISREndoQ==", + "license": "MIT", + "dependencies": { + "@floating-ui/dom": "^1.6.7", + "@floating-ui/vue": "^1.1.0", + "@internationalized/date": "^3.5.4", + "@internationalized/number": "^3.5.3", + "@tanstack/vue-virtual": "^3.8.1", + "@vueuse/core": "^10.11.0", + "@vueuse/shared": "^10.11.0", + "aria-hidden": "^1.2.4", + "defu": "^6.1.4", + "fast-deep-equal": "^3.1.3", + "nanoid": "^5.0.7" + }, + "peerDependencies": { + "vue": ">= 3.2.0" + } + }, "node_modules/radix3": { "version": "1.1.2", "resolved": "https://registry.npmjs.org/radix3/-/radix3-1.1.2.tgz", @@ -8498,6 +8919,15 @@ ], "license": "MIT" }, + "node_modules/safe-stable-stringify": { + "version": "2.5.0", + "resolved": "https://registry.npmjs.org/safe-stable-stringify/-/safe-stable-stringify-2.5.0.tgz", + "integrity": "sha512-b3rppTKm9T+PsVCBEOUR46GWI7fdOs00VKZ1+9c1EWDaDMvjQc6tUwuFyIprgGgTcWoVHSKrU8H31ZHA2e0RHA==", + "license": "MIT", + "engines": { + "node": ">=10" + } + }, "node_modules/sass": { "version": "1.93.2", "resolved": "https://registry.npmjs.org/sass/-/sass-1.93.2.tgz", @@ -8858,6 +9288,15 @@ "node": ">=20.16.0" } }, + "node_modules/stack-trace": { + "version": "0.0.10", + "resolved": "https://registry.npmjs.org/stack-trace/-/stack-trace-0.0.10.tgz", + "integrity": "sha512-KGzahc7puUKkzyMt+IqAep+TVNbKP+k2Lmwhub39m1AsTSkaDutx56aDCo+HLDzf/D26BIHTJWNiTG1KAJiQCg==", + "license": "MIT", + "engines": { + "node": "*" + } + }, "node_modules/standard-as-callback": { "version": "2.1.0", "resolved": "https://registry.npmjs.org/standard-as-callback/-/standard-as-callback-2.1.0.tgz", @@ -9226,6 +9665,12 @@ "b4a": "^1.6.4" } }, + "node_modules/text-hex": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/text-hex/-/text-hex-1.0.0.tgz", + "integrity": "sha512-uuVGNWzgJ4yhRaNSiubPY7OjISw4sw4E5Uv0wbjp+OzcbmVU/rsT8ujgcXJhn9ypzsgr5vlzpPqP+MBBKcGvbg==", + "license": "MIT" + }, "node_modules/tiny-invariant": { "version": "1.3.3", "resolved": "https://registry.npmjs.org/tiny-invariant/-/tiny-invariant-1.3.3.tgz", @@ -9290,12 +9735,20 @@ "integrity": "sha512-N3WMsuqV66lT30CrXNbEjx4GEwlow3v6rr4mCcv6prnfwhS01rkgyFdjPNBYd9br7LpXV1+Emh01fHnq2Gdgrw==", "license": "MIT" }, + "node_modules/triple-beam": { + "version": "1.4.1", + "resolved": "https://registry.npmjs.org/triple-beam/-/triple-beam-1.4.1.tgz", + "integrity": "sha512-aZbgViZrg1QNcG+LULa7nhZpJTZSLm/mXnHXnbAbjmN5aSa0y7V+wvv6+4WaBtpISJzThKy+PIPxc1Nq1EJ9mg==", + "license": "MIT", + "engines": { + "node": ">= 14.0.0" + } + }, "node_modules/tslib": { "version": "2.8.1", "resolved": "https://registry.npmjs.org/tslib/-/tslib-2.8.1.tgz", "integrity": "sha512-oJFu94HQb+KVduSUQL7wnpmqnfmLsOA/nAh6b6EH0wCEoK0/mPeXU6c3wKDV83MkOuHPRHtSXKKU99IBazS/2w==", - "license": "0BSD", - "optional": true + "license": "0BSD" }, "node_modules/tunnel-agent": { "version": "0.6.0", @@ -10113,6 +10566,100 @@ "node": "^18.17.0 || >=20.5.0" } }, + "node_modules/winston": { + "version": "3.19.0", + "resolved": "https://registry.npmjs.org/winston/-/winston-3.19.0.tgz", + "integrity": "sha512-LZNJgPzfKR+/J3cHkxcpHKpKKvGfDZVPS4hfJCc4cCG0CgYzvlD6yE/S3CIL/Yt91ak327YCpiF/0MyeZHEHKA==", + "license": "MIT", + "dependencies": { + "@colors/colors": "^1.6.0", + "@dabh/diagnostics": "^2.0.8", + "async": "^3.2.3", + "is-stream": "^2.0.0", + "logform": "^2.7.0", + "one-time": "^1.0.0", + "readable-stream": "^3.4.0", + "safe-stable-stringify": "^2.3.1", + "stack-trace": "0.0.x", + "triple-beam": "^1.3.0", + "winston-transport": "^4.9.0" + }, + "engines": { + "node": ">= 12.0.0" + } + }, + "node_modules/winston-daily-rotate-file": { + "version": "5.0.0", + "resolved": "https://registry.npmjs.org/winston-daily-rotate-file/-/winston-daily-rotate-file-5.0.0.tgz", + "integrity": "sha512-JDjiXXkM5qvwY06733vf09I2wnMXpZEhxEVOSPenZMii+g7pcDcTBt2MRugnoi8BwVSuCT2jfRXBUy+n1Zz/Yw==", + "license": "MIT", + "dependencies": { + "file-stream-rotator": "^0.6.1", + "object-hash": "^3.0.0", + "triple-beam": "^1.4.1", + "winston-transport": "^4.7.0" + }, + "engines": { + "node": ">=8" + }, + "peerDependencies": { + "winston": "^3" + } + }, + "node_modules/winston-transport": { + "version": "4.9.0", + "resolved": "https://registry.npmjs.org/winston-transport/-/winston-transport-4.9.0.tgz", + "integrity": "sha512-8drMJ4rkgaPo1Me4zD/3WLfI/zPdA9o2IipKODunnGDcuqbHwjsbB79ylv04LCGGzU0xQ6vTznOMpQGaLhhm6A==", + "license": "MIT", + "dependencies": { + "logform": "^2.7.0", + "readable-stream": "^3.6.2", + "triple-beam": "^1.3.0" + }, + "engines": { + "node": ">= 12.0.0" + } + }, + "node_modules/winston-transport/node_modules/readable-stream": { + "version": "3.6.2", + "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-3.6.2.tgz", + "integrity": "sha512-9u/sniCrY3D5WdsERHzHE4G2YCXqoG5FTHUiCC4SIbr6XcLZBY05ya9EKjYek9O5xOAwjGq+1JdGBAS7Q9ScoA==", + "license": "MIT", + "dependencies": { + "inherits": "^2.0.3", + "string_decoder": "^1.1.1", + "util-deprecate": "^1.0.1" + }, + "engines": { + "node": ">= 6" + } + }, + "node_modules/winston/node_modules/is-stream": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/is-stream/-/is-stream-2.0.1.tgz", + "integrity": "sha512-hFoiJiTl63nn+kstHGBtewWSKnQLpyb155KHheA1l39uvtO9nWIop1p3udqPcUd/xbF1VLMO4n7OI6p7RbngDg==", + "license": "MIT", + "engines": { + "node": ">=8" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/winston/node_modules/readable-stream": { + "version": "3.6.2", + "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-3.6.2.tgz", + "integrity": "sha512-9u/sniCrY3D5WdsERHzHE4G2YCXqoG5FTHUiCC4SIbr6XcLZBY05ya9EKjYek9O5xOAwjGq+1JdGBAS7Q9ScoA==", + "license": "MIT", + "dependencies": { + "inherits": "^2.0.3", + "string_decoder": "^1.1.1", + "util-deprecate": "^1.0.1" + }, + "engines": { + "node": ">= 6" + } + }, "node_modules/wrap-ansi": { "version": "8.1.0", "resolved": "https://registry.npmjs.org/wrap-ansi/-/wrap-ansi-8.1.0.tgz", diff --git a/package.json b/package.json index 7096e8d..25279e4 100644 --- a/package.json +++ b/package.json @@ -12,8 +12,12 @@ "dependencies": { "@nuxt/image": "^1.11.0", "nuxt": "^4.1.3", + "printf": "^0.6.1", + "radix-vue": "^1.9.17", "vue": "^3.5.22", - "vue-router": "^4.5.1" + "vue-router": "^4.5.1", + "winston": "^3.19.0", + "winston-daily-rotate-file": "^5.0.0" }, "devDependencies": { "sass": "^1.93.2" diff --git a/public/img/icones/arrow_right.svg b/public/img/icones/arrow_right.svg new file mode 100644 index 0000000..91d7f88 --- /dev/null +++ b/public/img/icones/arrow_right.svg @@ -0,0 +1 @@ + \ No newline at end of file diff --git a/public/img/icones/facebook_rond_bleu.svg b/public/img/icones/facebook_rond_bleu.svg new file mode 100644 index 0000000..ef03167 --- /dev/null +++ b/public/img/icones/facebook_rond_bleu.svg @@ -0,0 +1,14 @@ + + + facebook + + + + + + + + + + + \ No newline at end of file diff --git a/public/img/icones/instagram_gradient.svg b/public/img/icones/instagram_gradient.svg new file mode 100644 index 0000000..835cf34 --- /dev/null +++ b/public/img/icones/instagram_gradient.svg @@ -0,0 +1 @@ + \ No newline at end of file diff --git a/public/img/icones/linkedin_bleu.png b/public/img/icones/linkedin_bleu.png new file mode 100644 index 0000000..f0f2b09 Binary files /dev/null and b/public/img/icones/linkedin_bleu.png differ diff --git a/public/img/icones/youtube_play_rouge.svg b/public/img/icones/youtube_play_rouge.svg new file mode 100644 index 0000000..444044c --- /dev/null +++ b/public/img/icones/youtube_play_rouge.svg @@ -0,0 +1,16 @@ + + + g12 + + + + + + + + + + + + + \ No newline at end of file diff --git a/public/img/logos/logo_orchestre_blanc.png b/public/img/logos/logo_orchestre_blanc.png new file mode 100644 index 0000000..72a3127 Binary files /dev/null and b/public/img/logos/logo_orchestre_blanc.png differ diff --git a/server/api/log.post.js b/server/api/log.post.js new file mode 100644 index 0000000..8fedae9 --- /dev/null +++ b/server/api/log.post.js @@ -0,0 +1,17 @@ +import logger from '~~/server/utils/logger'; + +const ALLOWED_LEVELS = ['info', 'warn', 'error']; + +export default defineEventHandler(async (event) => { + const body = await readBody(event); + const { level, message, meta } = body || {}; + + const logLevel = ALLOWED_LEVELS.includes(level) ? level : 'info'; + + logger[logLevel](message, { + label: 'front-end', + ...meta, + }); + + return { status: 'ok' }; +}); \ No newline at end of file diff --git a/server/plugins/logger_global.js b/server/plugins/logger_global.js new file mode 100644 index 0000000..454d800 --- /dev/null +++ b/server/plugins/logger_global.js @@ -0,0 +1,30 @@ +import { getRequestIP } from 'h3'; +import logger from '~~/server/utils/logger'; + +export default defineNitroPlugin((nitroApp) => { + nitroApp.hooks.hook('request', (event) => { + // 1. On ignore les requêtes internes de Nuxt Image + if (event.path.startsWith('/_ipx')) return; + + // 2. On ignore l’endpoint de log, qui est déjà tracé par logger client_log + if (event.path === '/api/log') return; + // message: 'logger_global', + logger.info('logger_global', { + label: 'back-end', + internal: event._internal, + method: event.method, + url: event.path, + ip: getRequestIP(event) || 'unknown', + }); + }); + + nitroApp.hooks.hook('error', (error, { event }) => { + logger.error('Unhandled error', { + message: error.message, + stack: error.stack, + internal: event._internal, + method: event?.method, + url: event?.path, + }); + }); +}); \ No newline at end of file diff --git a/server/services/test.js b/server/services/test.js new file mode 100644 index 0000000..be16598 --- /dev/null +++ b/server/services/test.js @@ -0,0 +1,6 @@ +import logger from '~~/server/utils/logger'; +import path from 'path'; + +const filename = path.basename(new URL(import.meta.url).pathname); + +logger.info('test de log avec winston', { label: filename }); \ No newline at end of file diff --git a/server/utils/logger.js b/server/utils/logger.js new file mode 100644 index 0000000..ad4317e --- /dev/null +++ b/server/utils/logger.js @@ -0,0 +1,81 @@ +import winston from 'winston'; +import DailyRotateFile from 'winston-daily-rotate-file'; + +const { createLogger, format, transports } = winston; +const { combine, timestamp, label, printf } = format; + + +const myFormatFile = printf((info) => { + const { level, message, timestamp, ...meta } = info; + const label = meta.label || 'toto'; + delete meta.label; // pour ne pas le répéter dans le JSON + const base = `${timestamp} ${level} [${label}] ${message}`; + + const metaString = Object.keys(meta).length ? ` ${JSON.stringify(meta)}` : ''; + return base + metaString; +}); + +const myFormatConsole = printf(({ level, message, label, timestamp }) => { + return `${timestamp} ${level} [${label}] ${message}`; +}); + + + +const logger = winston.createLogger({ + //level: 'info', + format: combine( + timestamp({format: 'YYYY-MM-DD HH:mm:ss'}), + myFormatFile + ), + defaultMeta: { service: 'user-service' }, + transports: [ + new DailyRotateFile({ + dirname: 'logs', + filename: 'log_global-%DATE%.log', + datePattern: 'YYYY-MM-DD', + zippedArchive: true, + maxFiles: '14d', + }), + ], + exceptionHandlers: [ + new DailyRotateFile({ + dirname: 'logs', + filename: 'log_global-%DATE%.log', + datePattern: 'YYYY-MM-DD', + zippedArchive: true, + maxFiles: '14d', + }), + new winston.transports.Console() + ], + rejectionHandlers: [ + new DailyRotateFile({ + dirname: 'logs', + filename: 'log_global-%DATE%.log', + datePattern: 'YYYY-MM-DD', + zippedArchive: true, + maxFiles: '14d', + }), + new winston.transports.Console() + ] +}); + + + + +if (process.env.ENV !== 'production' ) { + logger.add(new winston.transports.Console( + { + format: combine( + label({ label: '' }), + timestamp({format: 'YYYY-MM-DD HH:mm:ss'}), + myFormatConsole + ), + handleExceptions: true //pour afficher également les exceptions dans la console + }) + ); +} + +///////////////////////////////////////////////// +// EXPORT DE MODULE POUR QU'IL SOIT LU DANS LES AUTRES FICHIERS JS +///////////////////////////////////////////////// +export default logger; \ No newline at end of file