Docfile commited on
Commit
1d14a8b
·
verified ·
1 Parent(s): 85cf07e

Create templates/index.html

Browse files
Files changed (1) hide show
  1. templates/index.html +251 -0
templates/index.html ADDED
@@ -0,0 +1,251 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ <!DOCTYPE html>
2
+ <html lang="fr">
3
+ <head>
4
+ <meta charset="UTF-8">
5
+ <meta name="viewport" content="width=device-width, initial-scale=1.0">
6
+ <title>AI Flashcards Generator</title>
7
+ <script src="https://cdn.tailwindcss.com"></script>
8
+ <script src="https://unpkg.com/vue@3/dist/vue.global.js"></script>
9
+ <script src="https://cdnjs.cloudflare.com/ajax/libs/axios/1.6.2/axios.min.js"></script>
10
+ <link href="https://cdnjs.cloudflare.com/ajax/libs/animate.css/4.1.1/animate.min.css" rel="stylesheet">
11
+ <script src="https://cdnjs.cloudflare.com/ajax/libs/gsap/3.12.2/gsap.min.js"></script>
12
+
13
+ <style>
14
+ @import url('https://fonts.googleapis.com/css2?family=Space+Grotesk:wght@300;400;500;600;700&display=swap');
15
+
16
+ body {
17
+ font-family: 'Space Grotesk', sans-serif;
18
+ background: linear-gradient(135deg, #0f172a 0%, #1e293b 100%);
19
+ }
20
+
21
+ .glass-morph {
22
+ background: rgba(255, 255, 255, 0.05);
23
+ backdrop-filter: blur(10px);
24
+ border: 1px solid rgba(255, 255, 255, 0.1);
25
+ }
26
+
27
+ .card-hover {
28
+ transition: all 0.3s ease;
29
+ }
30
+
31
+ .card-hover:hover {
32
+ transform: translateY(-5px);
33
+ box-shadow: 0 20px 40px rgba(0, 0, 0, 0.2);
34
+ }
35
+
36
+ .gradient-text {
37
+ background: linear-gradient(45deg, #60a5fa, #a855f7);
38
+ -webkit-background-clip: text;
39
+ background-clip: text;
40
+ color: transparent;
41
+ }
42
+
43
+ .custom-loader {
44
+ width: 50px;
45
+ height: 50px;
46
+ border: 3px solid #fff;
47
+ border-radius: 50%;
48
+ display: inline-block;
49
+ position: relative;
50
+ box-sizing: border-box;
51
+ animation: rotation 1s linear infinite;
52
+ }
53
+
54
+ .custom-loader::after {
55
+ content: '';
56
+ box-sizing: border-box;
57
+ position: absolute;
58
+ left: 50%;
59
+ top: 50%;
60
+ transform: translate(-50%, -50%);
61
+ width: 40px;
62
+ height: 40px;
63
+ border-radius: 50%;
64
+ border: 3px solid transparent;
65
+ border-bottom-color: #60a5fa;
66
+ }
67
+
68
+ @keyframes rotation {
69
+ 0% { transform: rotate(0deg) }
70
+ 100% { transform: rotate(360deg) }
71
+ }
72
+
73
+ .fade-enter-active, .fade-leave-active {
74
+ transition: opacity 0.5s ease;
75
+ }
76
+ .fade-enter-from, .fade-leave-to {
77
+ opacity: 0;
78
+ }
79
+ </style>
80
+ </head>
81
+ <body class="min-h-screen text-gray-100">
82
+ <div id="app" class="container mx-auto px-4 py-12">
83
+ <!-- Hero Section -->
84
+ <div class="text-center mb-16 animate__animated animate__fadeIn">
85
+ <h1 class="text-5xl font-bold mb-4 gradient-text">AI Flashcards Generator</h1>
86
+ <p class="text-xl text-gray-400 mb-8">Transformez vos sujets en cartes d'apprentissage intelligentes</p>
87
+ </div>
88
+
89
+ <!-- Main Content -->
90
+ <div class="max-w-4xl mx-auto">
91
+ <!-- Input Section -->
92
+ <div class="glass-morph rounded-2xl p-8 mb-12 card-hover">
93
+ <div class="mb-6">
94
+ <label for="topic" class="block text-lg font-medium mb-3 text-gray-300">Quel sujet souhaitez-vous explorer ?</label>
95
+ <div class="relative">
96
+ <input
97
+ type="text"
98
+ id="topic"
99
+ v-model="topic"
100
+ class="w-full px-6 py-4 bg-gray-800/50 rounded-xl border border-gray-700 focus:ring-2 focus:ring-blue-500 focus:border-transparent text-lg transition-all duration-300"
101
+ placeholder="Ex: Intelligence Artificielle, Quantum Computing..."
102
+ :disabled="isLoading"
103
+ >
104
+ </div>
105
+ </div>
106
+ <button
107
+ @click="generateFlashcards"
108
+ :disabled="isLoading"
109
+ class="w-full bg-gradient-to-r from-blue-500 to-purple-600 text-white py-4 px-8 rounded-xl font-medium text-lg hover:opacity-90 transition-all duration-300 flex items-center justify-center space-x-3"
110
+ >
111
+ <span v-if="!isLoading">Générer les Flashcards</span>
112
+ <span v-else class="custom-loader"></span>
113
+ </button>
114
+ </div>
115
+
116
+ <!-- Error Message -->
117
+ <transition name="fade">
118
+ <div v-if="error" class="mb-8 animate__animated animate__shakeX">
119
+ <div class="bg-red-500/20 border border-red-500/50 text-red-300 px-6 py-4 rounded-xl">
120
+ [[error]]
121
+ </div>
122
+ </div>
123
+ </transition>
124
+
125
+ <!-- Results Section -->
126
+ <transition name="fade">
127
+ <div v-if="flashcards.length > 0" class="glass-morph rounded-2xl overflow-hidden">
128
+ <!-- Tabs -->
129
+ <div class="border-b border-gray-700/50">
130
+ <div class="flex">
131
+ <button
132
+ v-for="tab in ['study', 'json']"
133
+ :key="tab"
134
+ @click="activeTab = tab"
135
+ :class="[
136
+ 'px-8 py-4 font-medium text-lg transition-all duration-300',
137
+ activeTab === tab
138
+ ? 'gradient-text border-b-2 border-blue-500'
139
+ : 'text-gray-400 hover:text-gray-300'
140
+ ]"
141
+ >
142
+ [[tab === 'study' ? 'Mode Étude' : 'Mode JSON']]
143
+ </button>
144
+ </div>
145
+ </div>
146
+
147
+ <!-- Tab Content -->
148
+ <div class="p-6">
149
+ <!-- Study Mode -->
150
+ <div v-if="activeTab === 'study'" class="space-y-6">
151
+ <div
152
+ v-for="(card, index) in flashcards"
153
+ :key="index"
154
+ class="glass-morph rounded-xl p-6 card-hover cursor-pointer transition-all duration-300"
155
+ @click="card.showAnswer = !card.showAnswer"
156
+ >
157
+ <div class="flex items-start space-x-4">
158
+ <div class="w-12 h-12 flex items-center justify-center rounded-full bg-blue-500/20 text-blue-400 font-bold">
159
+ [[index + 1]]
160
+ </div>
161
+ <div class="flex-1">
162
+ <h3 class="text-xl font-medium mb-4">[[card.question]]</h3>
163
+ <transition name="fade">
164
+ <div v-if="card.showAnswer" class="mt-4 pt-4 border-t border-gray-700/50">
165
+ <p class="text-gray-300">[[card.answer]]</p>
166
+ </div>
167
+ </transition>
168
+ </div>
169
+ </div>
170
+ </div>
171
+ </div>
172
+
173
+ <!-- JSON Mode -->
174
+ <div v-if="activeTab === 'json'" class="bg-gray-800/50 rounded-xl p-6 overflow-x-auto">
175
+ <pre class="text-gray-300">[[JSON.stringify(flashcards, null, 2)]]</pre>
176
+ </div>
177
+ </div>
178
+ </div>
179
+ </transition>
180
+ </div>
181
+ </div>
182
+
183
+ <script>
184
+ const { createApp } = Vue
185
+
186
+ createApp({
187
+ delimiters: ['[[', ']]'],
188
+ data() {
189
+ return {
190
+ topic: '',
191
+ flashcards: [],
192
+ activeTab: 'study',
193
+ isLoading: false,
194
+ error: null
195
+ }
196
+ },
197
+ methods: {
198
+ async generateFlashcards() {
199
+ if (!this.topic) {
200
+ this.error = 'Veuillez entrer un sujet.'
201
+ return
202
+ }
203
+
204
+ this.isLoading = true
205
+ this.error = null
206
+ this.flashcards = []
207
+
208
+ try {
209
+ const response = await axios.post('/generate', {
210
+ topic: this.topic
211
+ })
212
+
213
+ if (response.data.success) {
214
+ const cards = response.data.flashcards.map(card => ({
215
+ ...card,
216
+ showAnswer: false
217
+ }))
218
+
219
+ // Animation des cartes à leur apparition
220
+ setTimeout(() => {
221
+ this.flashcards = cards
222
+ this.$nextTick(() => {
223
+ gsap.from('.card-hover', {
224
+ y: 30,
225
+ opacity: 0,
226
+ duration: 0.5,
227
+ stagger: 0.1
228
+ })
229
+ })
230
+ }, 300)
231
+ }
232
+ } catch (error) {
233
+ this.error = error.response?.data?.error || 'Une erreur est survenue lors de la génération.'
234
+ } finally {
235
+ this.isLoading = false
236
+ }
237
+ }
238
+ },
239
+ mounted() {
240
+ // Animation du titre à l'entrée
241
+ gsap.from('.gradient-text', {
242
+ y: -50,
243
+ opacity: 0,
244
+ duration: 1,
245
+ ease: 'power3.out'
246
+ })
247
+ }
248
+ }).mount('#app')
249
+ </script>
250
+ </body>
251
+ </html>