feat: refactorer le système de palette de couleurs avec popup unifié, simplification du CSS pour les notes colorées et backgrounds, et amélioration du positionnement responsive de la palette

This commit is contained in:
2026-02-16 15:50:43 -05:00
parent 8f937c016d
commit 9ca8d345f6
56 changed files with 921 additions and 731 deletions
+158 -629
View File
@@ -542,6 +542,100 @@ body.view-notes .content-container {
color: #e8eaed;
}
.bookmark-palette {
display: inline-flex;
align-items: center;
position: relative;
}
.bookmark-palette > button {
background: none;
border: none;
width: 34px;
height: 34px;
border-radius: 50%;
display: flex;
align-items: center;
justify-content: center;
color: var(--text-light, #5f6368);
cursor: pointer;
font-size: 1.1rem;
transition: background-color 0.2s, color 0.2s;
}
[data-theme="dark"] .bookmark-palette > button {
color: #9aa0a6;
}
.palette-popup {
display: none;
position: absolute;
left: 0;
bottom: calc(100% + 8px);
background: var(--background-secondary, #ffffff);
border: 1px solid rgba(0, 0, 0, 0.12);
border-radius: 12px;
padding: 10px;
box-shadow: 0 10px 24px rgba(0, 0, 0, 0.18);
z-index: 50;
width: max-content;
max-width: min(340px, calc(100vw - 32px));
}
[data-theme="dark"] .palette-popup {
background: #202124;
border-color: rgba(255, 255, 255, 0.16);
}
.palette-popup.open {
display: block;
}
.palette-row {
display: flex;
flex-wrap: wrap;
gap: 8px;
}
.palette-row + .palette-row {
margin-top: 10px;
}
.palette-btn {
width: 24px;
height: 24px;
border-radius: 50%;
border: 1px solid rgba(0, 0, 0, 0.18);
cursor: pointer;
padding: 0;
background-position: center bottom;
background-size: cover;
}
[data-theme="dark"] .palette-btn {
border-color: rgba(255, 255, 255, 0.22);
}
.palette-btn.is-active {
outline: 2px solid var(--primary-color, #2563eb);
outline-offset: 2px;
}
.palette-btn-bg-none {
display: flex;
align-items: center;
justify-content: center;
}
.note-modal-color-picker {
position: relative;
}
.palette-popup.note-modal-palette {
bottom: auto;
top: calc(100% + 8px);
}
.spacer {
flex: 1;
}
@@ -708,18 +802,12 @@ body.view-notes .content-container {
--note-card-fg: #2a2d31;
}
[data-theme="dark"] .note-card.note-color-grey {
background-color: #e8eaed;
border-color: transparent;
--note-card-fg: #2a2d31;
}
.note-card.note-has-bg,
.note-modal.note-has-bg,
.link-outer.note-has-bg {
background-image: linear-gradient(rgba(0, 0, 0, 0.16), rgba(0, 0, 0, 0.16)), var(--note-bg-image);
background-size: cover;
background-position: center;
background-position: center bottom;
}
.note-card .note-title,
@@ -734,642 +822,83 @@ body.view-notes .content-container {
color: var(--note-card-fg, #202124);
}
.link-outer[class*="note-color-"] {
color: var(--note-card-fg, #202124);
}
.link-outer.note-color-default {
background-color: #20293a;
border-color: transparent;
--note-card-fg: #dbe7ff;
}
[data-theme="dark"] .link-outer.note-color-default {
background-color: #20293a;
border-color: transparent;
--note-card-fg: #dbe7ff;
}
.link-outer.note-color-red {
background-color: #f28b82;
border-color: transparent;
--note-card-fg: #2f1714;
}
[data-theme="dark"] .link-outer.note-color-red {
background-color: #f28b82;
border-color: transparent;
--note-card-fg: #2f1714;
}
.link-outer.note-color-orange {
background-color: #fbbc04;
border-color: transparent;
--note-card-fg: #3d2a00;
}
[data-theme="dark"] .link-outer.note-color-orange {
background-color: #fbbc04;
border-color: transparent;
--note-card-fg: #3d2a00;
}
.link-outer.note-color-yellow {
background-color: #fff475;
border-color: transparent;
--note-card-fg: #383100;
}
[data-theme="dark"] .link-outer.note-color-yellow {
background-color: #fff475;
border-color: transparent;
--note-card-fg: #383100;
}
.link-outer.note-color-green {
background-color: #ccff90;
border-color: transparent;
--note-card-fg: #203400;
}
[data-theme="dark"] .link-outer.note-color-green {
background-color: #ccff90;
border-color: transparent;
--note-card-fg: #203400;
}
.link-outer.note-color-teal {
background-color: #a7ffeb;
border-color: transparent;
--note-card-fg: #08342d;
}
[data-theme="dark"] .link-outer.note-color-teal {
background-color: #a7ffeb;
border-color: transparent;
--note-card-fg: #08342d;
}
.link-outer.note-color-blue {
background-color: #cbf0f8;
border-color: transparent;
--note-card-fg: #113541;
}
[data-theme="dark"] .link-outer.note-color-blue {
background-color: #cbf0f8;
border-color: transparent;
--note-card-fg: #113541;
}
.link-outer.note-color-darkblue {
background-color: #aecbfa;
border-color: transparent;
--note-card-fg: #102645;
}
[data-theme="dark"] .link-outer.note-color-darkblue {
background-color: #aecbfa;
border-color: transparent;
--note-card-fg: #102645;
}
.link-outer.note-color-purple {
background-color: #d7aefb;
border-color: transparent;
--note-card-fg: #2f1845;
}
[data-theme="dark"] .link-outer.note-color-purple {
background-color: #d7aefb;
border-color: transparent;
--note-card-fg: #2f1845;
}
.link-outer.note-color-pink {
background-color: #fdcfe8;
border-color: transparent;
--note-card-fg: #4a1d34;
}
[data-theme="dark"] .link-outer.note-color-pink {
background-color: #fdcfe8;
border-color: transparent;
--note-card-fg: #4a1d34;
}
.link-outer.note-color-brown {
background-color: #e6c9a8;
border-color: transparent;
--note-card-fg: #3c2714;
}
[data-theme="dark"] .link-outer.note-color-brown {
background-color: #e6c9a8;
border-color: transparent;
--note-card-fg: #3c2714;
}
.link-outer.note-color-grey {
background-color: #e8eaed;
border-color: transparent;
--note-card-fg: #2a2d31;
}
[data-theme="dark"] .link-outer.note-color-grey {
background-color: #e8eaed;
border-color: transparent;
--note-card-fg: #2a2d31;
}
.link-outer[class*="note-color-"] .link-title,
.link-outer[class*="note-color-"] .link-url,
.link-outer[class*="note-color-"] .link-meta,
.link-outer[class*="note-color-"] .link-description,
.link-outer[class*="note-color-"] .link-tag a,
.link-outer[class*="note-color-"] .link-actions a,
.link-outer[class*="note-color-"] .link-actions button,
.link-outer[class*="note-color-"] .bookmark-palette > button {
color: inherit;
}
.link-actions .bookmark-palette {
display: flex;
align-items: center;
}
.link-actions .bookmark-palette > button {
background: none;
border: none;
width: 36px;
height: 36px;
border-radius: 0.5rem;
display: flex;
align-items: center;
justify-content: center;
padding: 0;
cursor: pointer;
}
.link-actions .bookmark-palette > button i {
font-size: 1.15rem;
}
.link-actions .bookmark-palette > button:hover {
background: rgba(255, 255, 255, 0.08);
}
.link-actions .bookmark-palette .palette-popup {
left: 0;
right: auto;
}
/* --- PALETTE POPUP --- */
.palette-popup {
position: absolute;
bottom: 100%;
left: 0;
width: min(500px, 92vw);
background: #1f232b;
box-shadow: 0 1px 4px rgba(0, 0, 0, 0.2);
border-radius: 12px;
padding: 0;
z-index: 5000;
display: none;
/* JS toggles this */
}
[data-theme="dark"] .palette-popup {
background: #1f232b;
box-shadow: 0 1px 4px rgba(0, 0, 0, 0.5);
border: 1px solid #5f6368;
}
.palette-popup.open {
display: block;
}
.palette-popup.open-down {
top: calc(100% + 8px);
bottom: auto;
}
.palette-btn {
width: 32px;
height: 32px;
min-width: 32px;
min-height: 32px;
padding: 0;
border-radius: 50%;
border: 1px solid rgba(255, 255, 255, 0.18);
cursor: pointer;
display: inline-flex;
align-items: center;
justify-content: center;
position: relative;
flex: 0 0 auto;
background-position: center;
/* --- NOTES: Vue Masonry/Grid (multi-colonnes, largeur variable) --- */
.notes-masonry .note-card.note-has-bg {
/* Les cartes masonry ont des largeurs variables selon les breakpoints:
- >1200px: ~25% (4 colonnes)
- 800-1200px: ~33% (3 colonnes)
- 500-800px: ~50% (2 colonnes)
- <500px: 100% (1 colonne)
On utilise 'cover' avec un focus sur le centre pour garder l'essentiel visible */
background-size: cover;
background-position: center bottom;
/* Pour les petites cartes en masonry, on s'assure que l'image couvre bien */
min-height: 120px;
}
.palette-btn:hover {
border-color: rgba(255, 255, 255, 0.8);
}
[data-theme="dark"] .palette-btn {
border-color: rgba(255, 255, 255, 0.2);
}
.palette-btn.is-active {
outline: 2px solid #a855f7;
outline-offset: 1px;
}
.palette-row {
display: flex;
align-items: center;
gap: 8px;
padding: 10px 12px;
overflow-x: auto;
flex-wrap: nowrap;
scrollbar-width: thin;
}
.palette-row::-webkit-scrollbar {
height: 6px;
}
.palette-row::-webkit-scrollbar-thumb {
background: rgba(255, 255, 255, 0.24);
border-radius: 999px;
}
.palette-row+.palette-row {
border-top: 1px solid rgba(255, 255, 255, 0.14);
}
.palette-btn-default,
.palette-btn-bg-none {
background: #2b313c;
color: #d7dce5;
display: inline-flex;
align-items: center;
justify-content: center;
}
.palette-btn-default i,
.palette-btn-bg-none i {
font-size: 1rem;
}
/* Prevent link action generic button rules from deforming swatches in bookmark palette */
.link-actions .palette-popup .palette-btn {
width: 32px;
height: 32px;
min-width: 32px;
min-height: 32px;
border-radius: 50%;
padding: 0;
background: transparent;
border: 1px solid rgba(255, 255, 255, 0.18);
background-position: center;
/* --- NOTES: Vue Liste (600px max, centré) --- */
.notes-list-view .note-card.note-has-bg {
/* Vue liste: largeur fixe de 600px, cards plus larges qu'en masonry
On peut utiliser cover mais avec une position légèrement ajustée */
background-size: cover;
background-position: center bottom;
/* Les cards en liste sont souvent plus hautes, on adapte */
min-height: 100px;
}
.link-actions .palette-popup .palette-btn:hover {
background: transparent;
border-color: rgba(255, 255, 255, 0.8);
/* --- NOTES: Modal (min(720px, 92vw)) --- */
.note-modal.note-has-bg {
/* Modal plus large (jusqu'à 720px), on privilégie une couverture complète
avec une légère obscurcissement pour la lisibilité du texte */
background-size: cover;
background-position: center bottom;
/* L'overlay gradient est déjà présent dans la règle de base */
}
.link-outer.palette-open,
.view-list .link-outer.palette-open,
.view-compact .link-outer.palette-open {
overflow: visible;
z-index: 4000;
content-visibility: visible;
contain: none;
contain-intrinsic-size: auto;
/* --- BOOKMARKS: Vue Grid (minmax(320px, 1fr)) --- */
.view-grid .link-outer.note-has-bg {
/* Grid bookmarks: cards de minimum 320px, layout en grille
Les cards sont généralement carrées ou rectangulaires selon le contenu */
background-size: cover;
background-position: center bottom;
/* S'assurer que le background couvre bien la card avec le padding existant */
background-origin: padding-box;
}
/* --- MODAL FOR NOTE VIEW --- */
.note-modal-overlay {
position: fixed;
top: 0;
left: 0;
right: 0;
bottom: 0;
background: rgba(0, 0, 0, 0.6);
z-index: 1000;
display: flex;
align-items: center;
justify-content: center;
backdrop-filter: blur(2px);
opacity: 0;
pointer-events: none;
transition: opacity 0.2s;
/* --- BOOKMARKS: Vue Liste (1 colonne, thumbnail latéral) --- */
.view-list .link-outer.note-has-bg {
/* List view: cards en pleine largeur avec layout flex et thumbnail de 300px
On ajuste pour que le background couvre toute la hauteur malgré le thumbnail */
background-size: cover;
background-position: center bottom;
/* Le thumbnail a son propre mask gradient, on s'assure que le background
couvre bien toute la card derrière le contenu */
background-origin: padding-box;
}
.note-modal-overlay.open {
opacity: 1;
pointer-events: auto;
/* --- BOOKMARKS: Vue Compact (liste dense, pas de thumbnail) --- */
.view-compact .link-outer.note-has-bg {
/* Compact view: cards très compactes sans thumbnail, hauteur réduite (~60px)
On utilise contain ou une taille spécifique pour éviter que l'image
soit trop étirée sur une si petite hauteur */
background-size: 200% auto;
background-position: center bottom;
/* Réduire l'opacité du gradient pour plus de visibilité sur petites cards */
background-image: linear-gradient(rgba(0, 0, 0, 0.08), rgba(0, 0, 0, 0.08)), var(--note-bg-image);
}
.note-modal {
background: var(--modal-note-bg, #7a4b00);
color: var(--modal-note-fg, #fff2d9);
width: min(720px, 92vw);
max-height: 88vh;
border-radius: 10px;
overflow: hidden;
box-shadow: 0 12px 32px rgba(0, 0, 0, 0.42);
position: relative;
display: flex;
flex-direction: column;
--note-scrollbar-thumb: rgba(255, 229, 170, 0.75);
--note-separator: rgba(255, 230, 182, 0.22);
--note-footer-bg: rgba(0, 0, 0, 0.14);
}
.note-modal.note-color-default {
--modal-note-bg: #20293a;
--modal-note-fg: #dbe7ff;
--note-scrollbar-thumb: rgba(219, 231, 255, 0.45);
--note-separator: rgba(219, 231, 255, 0.2);
--note-footer-bg: rgba(255, 255, 255, 0.08);
}
.note-modal.note-color-red {
--modal-note-bg: #f28b82;
--modal-note-fg: #2f1714;
--note-scrollbar-thumb: rgba(47, 23, 20, 0.45);
--note-separator: rgba(47, 23, 20, 0.2);
--note-footer-bg: rgba(255, 255, 255, 0.18);
}
.note-modal.note-color-orange {
--modal-note-bg: #fbbc04;
--modal-note-fg: #3d2a00;
--note-scrollbar-thumb: rgba(61, 42, 0, 0.45);
--note-separator: rgba(61, 42, 0, 0.2);
--note-footer-bg: rgba(255, 255, 255, 0.2);
}
.note-modal.note-color-yellow {
--modal-note-bg: #fff475;
--modal-note-fg: #383100;
--note-scrollbar-thumb: rgba(56, 49, 0, 0.45);
--note-separator: rgba(56, 49, 0, 0.2);
--note-footer-bg: rgba(255, 255, 255, 0.24);
}
.note-modal.note-color-green {
--modal-note-bg: #ccff90;
--modal-note-fg: #203400;
--note-scrollbar-thumb: rgba(32, 52, 0, 0.45);
--note-separator: rgba(32, 52, 0, 0.2);
--note-footer-bg: rgba(255, 255, 255, 0.22);
}
.note-modal.note-color-teal {
--modal-note-bg: #a7ffeb;
--modal-note-fg: #08342d;
--note-scrollbar-thumb: rgba(8, 52, 45, 0.45);
--note-separator: rgba(8, 52, 45, 0.2);
--note-footer-bg: rgba(255, 255, 255, 0.22);
}
.note-modal.note-color-blue {
--modal-note-bg: #cbf0f8;
--modal-note-fg: #113541;
--note-scrollbar-thumb: rgba(17, 53, 65, 0.45);
--note-separator: rgba(17, 53, 65, 0.2);
--note-footer-bg: rgba(255, 255, 255, 0.22);
}
.note-modal.note-color-darkblue {
--modal-note-bg: #aecbfa;
--modal-note-fg: #102645;
--note-scrollbar-thumb: rgba(16, 38, 69, 0.45);
--note-separator: rgba(16, 38, 69, 0.2);
--note-footer-bg: rgba(255, 255, 255, 0.2);
}
.note-modal.note-color-purple {
--modal-note-bg: #d7aefb;
--modal-note-fg: #2f1845;
--note-scrollbar-thumb: rgba(47, 24, 69, 0.45);
--note-separator: rgba(47, 24, 69, 0.2);
--note-footer-bg: rgba(255, 255, 255, 0.2);
}
.note-modal.note-color-pink {
--modal-note-bg: #fdcfe8;
--modal-note-fg: #4a1d34;
--note-scrollbar-thumb: rgba(74, 29, 52, 0.45);
--note-separator: rgba(74, 29, 52, 0.2);
--note-footer-bg: rgba(255, 255, 255, 0.2);
}
.note-modal.note-color-brown {
--modal-note-bg: #e6c9a8;
--modal-note-fg: #3c2714;
--note-scrollbar-thumb: rgba(60, 39, 20, 0.45);
--note-separator: rgba(60, 39, 20, 0.2);
--note-footer-bg: rgba(255, 255, 255, 0.2);
}
.note-modal.note-color-grey {
--modal-note-bg: #e8eaed;
--modal-note-fg: #2a2d31;
--note-scrollbar-thumb: rgba(42, 45, 49, 0.45);
--note-separator: rgba(42, 45, 49, 0.2);
--note-footer-bg: rgba(255, 255, 255, 0.2);
}
[data-theme="dark"] .note-modal {
border: 1px solid rgba(255, 255, 255, 0.12);
}
.note-modal-header {
display: flex;
align-items: flex-start;
justify-content: space-between;
gap: 12px;
padding: 18px 20px 10px;
flex-shrink: 0;
}
.note-modal .note-title {
font-size: 1.6rem;
line-height: 1.35;
margin: 0;
color: inherit;
font-weight: 500;
}
.note-modal-pin-toggle {
background: transparent;
border: none;
color: inherit;
opacity: 0.85;
width: 34px;
height: 34px;
border-radius: 50%;
display: inline-flex;
align-items: center;
justify-content: center;
cursor: pointer;
flex-shrink: 0;
transition: background-color 0.2s, opacity 0.2s;
}
.note-modal-pin-toggle i {
font-size: 1.2rem;
}
.note-modal-pin-toggle:hover,
.note-modal-pin-toggle.active {
opacity: 1;
background-color: rgba(255, 255, 255, 0.14);
}
.note-modal-content {
flex: 1;
overflow-y: auto;
padding: 0 20px 18px;
scrollbar-width: thin;
scrollbar-color: var(--note-scrollbar-thumb) transparent;
}
.note-modal-content::-webkit-scrollbar {
width: 10px;
}
.note-modal-content::-webkit-scrollbar-track {
background: transparent;
}
.note-modal-content::-webkit-scrollbar-thumb {
background: var(--note-scrollbar-thumb);
border-radius: 10px;
border: 2px solid transparent;
background-clip: content-box;
}
.note-modal .note-body {
font-size: 1rem;
line-height: 1.75;
display: block;
-webkit-line-clamp: initial;
line-clamp: initial;
-webkit-box-orient: initial;
max-height: none;
overflow: visible;
color: inherit;
}
.note-modal .note-body * {
color: inherit;
}
.note-modal-tags {
display: flex;
flex-wrap: wrap;
gap: 8px;
padding: 10px 20px 12px;
border-top: 1px solid var(--note-separator);
flex-shrink: 0;
}
.note-modal-tags.is-empty {
display: none;
}
.note-modal-tags .note-tag {
background: rgba(255, 255, 255, 0.12);
border: 1px solid rgba(255, 255, 255, 0.22);
color: inherit;
border-radius: 999px;
padding: 4px 10px;
font-size: 0.72rem;
letter-spacing: 0.02em;
}
.note-modal-actions {
display: flex;
align-items: center;
justify-content: space-between;
gap: 10px;
padding: 8px 12px;
border-top: 1px solid var(--note-separator);
background: var(--note-footer-bg);
flex-shrink: 0;
}
.note-modal-actions-left {
display: flex;
align-items: center;
gap: 2px;
flex-wrap: wrap;
}
.note-modal-actions-left > button,
.note-modal-actions-left > a,
.note-modal-actions-left > .note-modal-color-picker > button {
background: transparent;
border: none;
color: inherit;
opacity: 0.9;
width: 32px;
height: 32px;
border-radius: 50%;
display: inline-flex;
align-items: center;
justify-content: center;
cursor: pointer;
text-decoration: none;
transition: background-color 0.2s, opacity 0.2s;
}
.note-modal-actions-left > button:hover,
.note-modal-actions-left > a:hover,
.note-modal-actions-left > .note-modal-color-picker > button:hover {
opacity: 1;
background: rgba(255, 255, 255, 0.14);
}
.note-modal-color-picker {
position: relative;
display: inline-flex;
}
.note-modal-palette {
left: -8px;
bottom: calc(100% + 8px);
width: min(500px, 92vw);
}
.note-modal-close-btn {
background: transparent;
border: none;
color: inherit;
font-weight: 600;
border-radius: 8px;
padding: 6px 10px;
cursor: pointer;
}
.note-modal-close-btn:hover {
background: rgba(255, 255, 255, 0.14);
}
@media (max-width: 640px) {
.note-modal {
width: 96vw;
max-height: 92vh;
/* Responsive: sur petits écrans, ajuster les backgrounds */
@media (max-width: 768px) {
/* En mobile, les cards sont plus étroites, on ajuste */
.notes-masonry .note-card.note-has-bg,
.view-grid .link-outer.note-has-bg {
background-size: cover;
background-position: center bottom;
}
.note-modal .note-title {
font-size: 1.25rem;
/* Vue liste en mobile: thumbnail passe en haut */
.view-list .link-outer.note-has-bg {
background-size: cover;
background-position: center bottom;
}
}