Update app.py
Browse files
app.py
CHANGED
@@ -16,56 +16,131 @@ import plotly.graph_objects as go
|
|
16 |
import plotly.io as pio
|
17 |
|
18 |
# ---------------- Branding Verbatify (CSS + Plotly) ----------------
|
19 |
-
VB_CSS = r"""
|
20 |
@import url('https://fonts.googleapis.com/css2?family=Manrope:wght@400;600;700;800&display=swap');
|
|
|
|
|
21 |
:root{
|
22 |
-
--vb-bg:#F8FAFC;
|
23 |
-
--vb-
|
24 |
-
--vb-
|
25 |
-
--vb-
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
26 |
}
|
27 |
-
html,body,.gradio-container{background:var(--vb-bg)!important;color:var(--vb-text);
|
28 |
-
font-family:Manrope,system-ui,-apple-system,Segoe UI,Roboto,Arial,sans-serif;}
|
29 |
-
.gradio-container{max-width:1120px!important;margin:0 auto!important;}
|
30 |
-
.vb-hero{display:flex;align-items:center;gap:14px;padding:18px 20px;margin:8px 0 18px;
|
31 |
-
background:linear-gradient(90deg,rgba(124,58,237,.10),rgba(6,182,212,.10));
|
32 |
-
border:1px solid var(--vb-border);border-radius:var(--vb-radius);}
|
33 |
-
.vb-hero .vb-title{font-size:20px;font-weight:800;letter-spacing:.2px;}
|
34 |
-
.vb-hero .vb-sub{color:var(--vb-muted);font-size:13px;margin-top:-4px;}
|
35 |
-
.gr-markdown,.gr-box,.gr-panel,.gr-article{background:var(--vb-card)!important;border:1px solid var(--vb-border)!important;border-radius:var(--vb-radius)!important;box-shadow:var(--vb-shadow);}
|
36 |
-
.gr-markdown h2{font-size:18px;margin-top:10px;}
|
37 |
-
button,.gr-button{border-radius:var(--vb-radius)!important;border:0!important;box-shadow:var(--vb-shadow);font-weight:700!important;}
|
38 |
-
.gr-button-primary{background:linear-gradient(90deg,var(--vb-primary),var(--vb-primary-2))!important;color:#fff!important;}
|
39 |
-
.gr-button-primary:hover{filter:brightness(1.06);transform:translateY(-1px);}
|
40 |
-
.gr-button-secondary{background:#fff!important;border:1px solid var(--vb-border)!important;color:var(--vb-text)!important;}
|
41 |
-
input,textarea,select,.gr-textbox,.gr-textbox textarea{border-radius:calc(var(--vb-radius) - 4px)!important;border:1px solid var(--vb-border)!important;background:#fff!important;}
|
42 |
-
input[type="checkbox"]:checked{accent-color:var(--vb-primary)!important;}
|
43 |
-
.js-plotly-plot .plotly .bg{fill:#fff!important;}
|
44 |
-
.js-plotly-plot .plotly .xgrid,.js-plotly-plot .plotly .ygrid{stroke:#E2E8F0!important;opacity:1;}
|
45 |
-
.vb-footer{color:var(--vb-muted);font-size:12px;text-align:center;margin:12px 0;}
|
46 |
-
"""
|
47 |
|
48 |
-
|
49 |
-
|
50 |
-
|
51 |
-
|
52 |
-
|
53 |
-
|
54 |
-
|
55 |
-
|
56 |
-
|
57 |
-
|
58 |
-
|
59 |
-
|
60 |
-
|
61 |
-
|
62 |
-
|
63 |
-
|
64 |
-
|
65 |
-
|
66 |
-
|
67 |
-
|
68 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
69 |
|
70 |
# ---------------- unidecode (fallback si paquet absent) ----------------
|
71 |
try:
|
|
|
16 |
import plotly.io as pio
|
17 |
|
18 |
# ---------------- Branding Verbatify (CSS + Plotly) ----------------
|
|
|
19 |
@import url('https://fonts.googleapis.com/css2?family=Manrope:wght@400;600;700;800&display=swap');
|
20 |
+
|
21 |
+
/* ---------- Palette Verbatify ---------- */
|
22 |
:root{
|
23 |
+
--vb-bg:#F8FAFC; /* fond */
|
24 |
+
--vb-card:#FFFFFF; /* cartes */
|
25 |
+
--vb-text:#0F172A; /* texte */
|
26 |
+
--vb-muted:#475569; /* texte secondaire */
|
27 |
+
--vb-primary:#7C3AED; /* violet */
|
28 |
+
--vb-primary-2:#06B6D4; /* cyan */
|
29 |
+
--vb-accent:#2563EB; /* bleu */
|
30 |
+
--vb-positive:#10B981; /* vert succ猫s */
|
31 |
+
--vb-negative:#EF4444; /* rouge */
|
32 |
+
--vb-neutral:#94A3B8; /* neutre */
|
33 |
+
--vb-border:#E2E8F0; /* bordures */
|
34 |
+
--vb-radius:14px;
|
35 |
+
--vb-shadow:0 10px 26px rgba(2,6,23,.08);
|
36 |
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
37 |
|
38 |
+
/* Forcer un look clair, m锚me si l鈥檋么te est en dark */
|
39 |
+
* { color-scheme: light !important; }
|
40 |
+
|
41 |
+
html,body,.gradio-container{
|
42 |
+
background:var(--vb-bg) !important;
|
43 |
+
color:var(--vb-text);
|
44 |
+
font-family:Manrope,system-ui,-apple-system,'Segoe UI',Roboto,Arial,sans-serif;
|
45 |
+
}
|
46 |
+
|
47 |
+
/* largeur contenante */
|
48 |
+
.gradio-container{max-width:1120px !important;margin:0 auto !important}
|
49 |
+
|
50 |
+
/* ---------- Hero / Header ---------- */
|
51 |
+
.vb-hero{
|
52 |
+
display:flex;align-items:center;gap:16px;padding:20px 22px;margin:10px 0 20px;
|
53 |
+
background:linear-gradient(90deg, rgba(124,58,237,.12), rgba(6,182,212,.12));
|
54 |
+
border:1px solid var(--vb-border);border-radius:var(--vb-radius);
|
55 |
+
box-shadow:var(--vb-shadow);
|
56 |
+
}
|
57 |
+
.vb-hero .vb-title{font-size:22px;font-weight:800;letter-spacing:.2px}
|
58 |
+
.vb-hero .vb-sub{color:var(--vb-muted);font-size:13px;margin-top:-2px}
|
59 |
+
|
60 |
+
/* ---------- Cartes / panneaux ---------- */
|
61 |
+
.gradio-container .gr-box,
|
62 |
+
.gradio-container .gr-panel,
|
63 |
+
.gradio-container .gr-accordion,
|
64 |
+
.gradio-container .gr-group,
|
65 |
+
.gradio-container .gr-form,
|
66 |
+
.gradio-container .gr-article{
|
67 |
+
background:var(--vb-card) !important;
|
68 |
+
border:1px solid var(--vb-border) !important;
|
69 |
+
border-radius:var(--vb-radius) !important;
|
70 |
+
box-shadow:var(--vb-shadow);
|
71 |
+
}
|
72 |
+
|
73 |
+
/* labels et titres internes */
|
74 |
+
.gr-markdown h1,.gr-markdown h2,.gr-markdown h3{color:var(--vb-text)}
|
75 |
+
.gr-markdown h2{font-size:18px;margin-top:10px}
|
76 |
+
|
77 |
+
/* ---------- Inputs ---------- */
|
78 |
+
.gradio-container input[type="text"],
|
79 |
+
.gradio-container input[type="number"],
|
80 |
+
.gradio-container textarea,
|
81 |
+
.gradio-container select,
|
82 |
+
.gradio-container .gr-textbox,
|
83 |
+
.gradio-container .gr-textbox textarea{
|
84 |
+
background:#fff !important;
|
85 |
+
border:1px solid var(--vb-border) !important;
|
86 |
+
border-radius:calc(var(--vb-radius) - 4px) !important;
|
87 |
+
box-shadow:none !important;
|
88 |
+
}
|
89 |
+
.gradio-container input::placeholder,
|
90 |
+
.gradio-container textarea::placeholder{color:#9AA4B2}
|
91 |
+
|
92 |
+
/* Checkboxes / radios */
|
93 |
+
.gradio-container input[type="checkbox"],
|
94 |
+
.gradio-container input[type="radio"]{accent-color:var(--vb-primary) !important}
|
95 |
+
|
96 |
+
/* Sliders */
|
97 |
+
.gradio-container input[type="range"]{
|
98 |
+
-webkit-appearance:none;height:6px;background:#EDF2F7;border-radius:999px;outline:none
|
99 |
+
}
|
100 |
+
.gradio-container input[type="range"]::-webkit-slider-thumb{
|
101 |
+
-webkit-appearance:none;width:18px;height:18px;border-radius:50%;
|
102 |
+
background:linear-gradient(135deg, var(--vb-primary), var(--vb-primary-2));
|
103 |
+
border:0;box-shadow:0 2px 8px rgba(124,58,237,.35)
|
104 |
+
}
|
105 |
+
|
106 |
+
/* ---------- Boutons ---------- */
|
107 |
+
button,.gr-button{
|
108 |
+
border-radius:var(--vb-radius) !important;border:0 !important;font-weight:700 !important;
|
109 |
+
box-shadow:var(--vb-shadow);
|
110 |
+
}
|
111 |
+
.gr-button-primary{
|
112 |
+
background:linear-gradient(90deg, var(--vb-primary), var(--vb-primary-2)) !important;
|
113 |
+
color:#fff !important;
|
114 |
+
}
|
115 |
+
.gr-button-primary:hover{filter:brightness(1.06);transform:translateY(-1px)}
|
116 |
+
.gr-button-secondary{
|
117 |
+
background:#fff !important;border:1px solid var(--vb-border) !important;color:var(--vb-text) !important
|
118 |
+
}
|
119 |
+
|
120 |
+
/* ---------- DataFrames / Tables ---------- */
|
121 |
+
.gradio-container table{border-collapse:separate;border-spacing:0;width:100%}
|
122 |
+
.gradio-container thead th{
|
123 |
+
background:linear-gradient(90deg,rgba(124,58,237,.06),rgba(6,182,212,.06));
|
124 |
+
color:#111827;font-weight:800;border-bottom:1px solid var(--vb-border)
|
125 |
+
}
|
126 |
+
.gradio-container td, .gradio-container th{
|
127 |
+
padding:10px;border-bottom:1px solid #F1F5F9
|
128 |
+
}
|
129 |
+
|
130 |
+
/* ---------- Graphiques (Plotly) ---------- */
|
131 |
+
.js-plotly-plot .plotly .bg{fill:#fff !important}
|
132 |
+
.js-plotly-plot .plotly .xgrid,.js-plotly-plot .plotly .ygrid{stroke:#E2E8F0 !important;opacity:1}
|
133 |
+
.js-plotly-plot .plotly .legend text{font-weight:600}
|
134 |
+
|
135 |
+
/* ---------- Chips sentiment (si besoin) ---------- */
|
136 |
+
.vb-chip{display:inline-flex;align-items:center;gap:6px;padding:2px 8px;border-radius:999px;font-size:12px;font-weight:700}
|
137 |
+
.vb-chip.pos{background:rgba(16,185,129,.12);color:#065F46}
|
138 |
+
.vb-chip.neu{background:rgba(148,163,184,.16);color:#334155}
|
139 |
+
.vb-chip.neg{background:rgba(239,68,68,.12);color:#7F1D1D}
|
140 |
+
|
141 |
+
/* ---------- Footer ---------- */
|
142 |
+
.vb-footer{color:var(--vb-muted);font-size:12px;text-align:center;margin:16px 0}
|
143 |
+
|
144 |
|
145 |
# ---------------- unidecode (fallback si paquet absent) ----------------
|
146 |
try:
|