3434 .safe-header { padding-top : calc (1rem + env (safe-area-inset-top, 0px )); padding-bottom : 1rem ; }
3535 # loading-overlay { background : # 0f172a ; position : fixed; inset : 0 ; z-index : 100 ; display : flex; align-items : center; justify-content : center; transition : opacity 0.5s ; }
3636 .sortable-ghost { opacity : 0.4 ; background : # 334155 ; }
37+ .calendar-grid { display : grid; grid-template-columns : repeat (7 , 1fr ); gap : 0.5rem ; }
3738 </ style >
3839</ head >
3940< body class ="bg-dark-900 text-slate-100 min-h-screen flex flex-col items-center overflow-hidden ">
4041
4142 < div id ="loading-overlay ">
4243 < div class ="flex flex-col items-center ">
4344 < i class ="fa-solid fa-circle-notch fa-spin text-4xl text-emerald-500 mb-4 "> </ i >
44- < p class ="text-gray-400 animate-pulse text-sm "> Data synchroniseren ...</ p >
45+ < p class ="text-gray-400 animate-pulse text-sm "> Lijsten laden ...</ p >
4546 </ div >
4647 </ div >
4748
@@ -155,9 +156,10 @@ <h2 id="stats-month-year" class="text-lg font-bold text-white capitalize"></h2>
155156 < script type ="module ">
156157 import OfflineManager from './offline_manager.js' ;
157158
158- const APP_NAME = 'supermarkey' ;
159- const CLIENT_ID = 'sandman' ;
160- const API_URL = 'http://10.10.2.20:5000' ;
159+ // CONFIGURATIE
160+ const APP_NAME = 'superlijst' ;
161+ const CLIENT_ID = 'jouw-unieke-id' ; // Tip: kan ook uit localStorage komen
162+ const API_URL = 'http://localhost:5000' ;
161163
162164 const manager = new OfflineManager ( API_URL , CLIENT_ID , APP_NAME ) ;
163165
@@ -169,47 +171,27 @@ <h2 id="stats-month-year" class="text-lg font-bold text-white capitalize"></h2>
169171 const DataService = {
170172 getLists : async ( ) => {
171173 const lists = await manager . getSmartCollection ( 'lists' ) ;
172- // Belangrijk: we gebruiken hier unieke mapping om duplicaten te voorkomen
173- const uniqueMap = new Map ( ) ;
174- ( lists || [ ] ) . forEach ( l => {
175- const id = l . _id || l . id ;
176- if ( id ) uniqueMap . set ( id , l ) ;
177- } ) ;
178- return Array . from ( uniqueMap . values ( ) ) . map ( l => ( { id : l . _id || l . id , data : l } ) ) ;
174+ return lists . map ( l => ( { id : l . _id || l . id , data : l } ) ) ;
179175 } ,
180176 saveList : async ( listObj ) => {
181- // DEXIE FIX: Het 'id' veld van Dexie mag NOOIT handmatig overschreven worden.
182- // We sturen alleen de payload en het _id voor de database mee.
183- const payload = {
184- name : listObj . name ,
185- items : listObj . items
186- } ;
187-
188- // Als er al een _id is, voegen we die toe aan de payload voor een UPDATE
189- if ( listObj . _id ) {
190- payload . _id = listObj . _id ;
191- }
192-
193- const result = await manager . saveSmartDocument ( 'lists' , payload ) ;
194- return result ;
177+ // De manager V3 handelt _id en duplicaten nu zelf af!
178+ return await manager . saveSmartDocument ( 'lists' , listObj ) ;
195179 } ,
196180 deleteList : async ( id ) => {
181+ // Gebruik gateway direct voor delete
197182 await manager . gateway . deleteDocument ( 'lists' , id ) ;
198183 await manager . refreshCache ( 'lists' ) ;
199184 } ,
200185 getHistory : async ( ) => {
201186 const history = await manager . getSmartCollection ( 'history' ) ;
202- return ( history || [ ] ) . map ( h => h . data || h ) ;
187+ return history ;
203188 } ,
204189 addHistory : async ( entry ) => {
205190 await manager . saveSmartDocument ( 'history' , entry ) ;
206191 } ,
207192 clearHistory : async ( ) => {
208- const history = await manager . getSmartCollection ( 'history' ) ;
209- for ( const item of history ) {
210- await manager . gateway . deleteDocument ( 'history' , item . _id || item . id ) ;
211- }
212- await manager . refreshCache ( 'history' ) ;
193+ // Gebruik de Smart Clear van de manager V3
194+ await manager . clearSmartCollection ( 'history' ) ;
213195 }
214196 } ;
215197
@@ -224,30 +206,25 @@ <h2 id="stats-month-year" class="text-lg font-bold text-white capitalize"></h2>
224206 statDate : new Date ( ) ,
225207
226208 init : async ( ) => {
227- // 1. Initialiseer Dashboard
228209 await app . renderDashboard ( ) ;
229210
230- // 2. Verberg loading overlay
231211 const overlay = document . getElementById ( 'loading-overlay' ) ;
232212 if ( overlay ) {
233213 overlay . style . opacity = '0' ;
234214 setTimeout ( ( ) => overlay . remove ( ) , 500 ) ;
235215 }
236216
237- // 3. Sync en refresh
238217 if ( navigator . onLine ) {
239218 manager . syncOutbox ( ) . then ( ( ) => app . renderDashboard ( ) ) ;
240219 }
241220
242221 window . addEventListener ( 'online' , ( ) => {
243- app . showToast ( "Verbinding hersteld..." ) ;
222+ app . showToast ( "Verbinding hersteld, sync gestart ..." ) ;
244223 manager . syncOutbox ( ) . then ( ( ) => app . renderDashboard ( ) ) ;
245224 } ) ;
246225
247226 if ( 'serviceWorker' in navigator ) {
248- window . addEventListener ( 'load' , ( ) => {
249- navigator . serviceWorker . register ( './sw.js' ) . catch ( e => console . error ( e ) ) ;
250- } ) ;
227+ navigator . serviceWorker . register ( './sw.js' ) . catch ( e => console . error ( e ) ) ;
251228 }
252229 } ,
253230
@@ -275,8 +252,6 @@ <h2 id="stats-month-year" class="text-lg font-bold text-white capitalize"></h2>
275252 const savedContainer = tpl . getElementById ( 'saved-list-container' ) ;
276253 const emptyState = tpl . getElementById ( 'empty-state' ) ;
277254
278- savedContainer . innerHTML = '' ;
279-
280255 document . getElementById ( 'header-title' ) . innerText = "SuperLijst" ;
281256 document . getElementById ( 'header-actions' ) . innerHTML = `<button onclick="app.renderStats()" class="text-gray-400 hover:text-white transition"><i class="fa-solid fa-calendar-days text-xl"></i></button>` ;
282257
@@ -285,10 +260,9 @@ <h2 id="stats-month-year" class="text-lg font-bold text-white capitalize"></h2>
285260 if ( lists . length === 0 ) {
286261 emptyState . classList . remove ( 'hidden' ) ;
287262 } else {
288- lists . sort ( ( a , b ) => a . data . name . localeCompare ( b . data . name ) ) ;
289- lists . forEach ( item => {
290- savedContainer . appendChild ( app . createListCard ( item , true ) ) ;
291- } ) ;
263+ // Sorteren op naam
264+ lists . sort ( ( a , b ) => ( a . data . name || "" ) . localeCompare ( b . data . name || "" ) ) ;
265+ lists . forEach ( item => savedContainer . appendChild ( app . createListCard ( item ) ) ) ;
292266 }
293267 } catch ( e ) {
294268 console . error ( e ) ;
@@ -297,10 +271,10 @@ <h2 id="stats-month-year" class="text-lg font-bold text-white capitalize"></h2>
297271 main . appendChild ( tpl ) ;
298272 } ,
299273
300- createListCard : ( item , isSaved ) => {
274+ createListCard : ( item ) => {
301275 const div = document . createElement ( 'div' ) ;
302276 div . className = "bg-dark-800 p-4 rounded-xl border border-gray-700 hover:border-emerald-500/50 transition flex justify-between items-center group cursor-pointer" ;
303- div . onclick = ( ) => app . startEdit ( item . data , isSaved ? item . id : null ) ;
277+ div . onclick = ( ) => app . startEdit ( item . data ) ;
304278
305279 div . innerHTML = `
306280 <div class="flex items-center gap-3">
@@ -324,22 +298,17 @@ <h2 id="stats-month-year" class="text-lg font-bold text-white capitalize"></h2>
324298 }
325299 } ;
326300 div . appendChild ( delBtn ) ;
327-
328301 return div ;
329302 } ,
330303
331- startEdit : ( data , id = null ) => {
332- // Zorg voor een schone kopie van de data
333- app . currentList = {
334- name : data . name || '' ,
335- items : Array . isArray ( data . items ) ? [ ...data . items ] : [ ] ,
336- _id : id || data . _id || null
337- } ;
304+ startEdit : ( data ) => {
305+ // Schone kopie maken voor bewerken
306+ app . currentList = JSON . parse ( JSON . stringify ( data ) ) ;
338307 app . renderEditor ( ) ;
339308 } ,
340309
341310 startEmpty : ( ) => {
342- app . currentList = { name : '' , items : [ ] , _id : null } ;
311+ app . currentList = { name : '' , items : [ ] } ;
343312 app . renderEditor ( ) ;
344313 } ,
345314
@@ -349,7 +318,7 @@ <h2 id="stats-month-year" class="text-lg font-bold text-white capitalize"></h2>
349318
350319 const tpl = document . getElementById ( 'tpl-editor' ) . content . cloneNode ( true ) ;
351320 const nameInput = tpl . getElementById ( 'list-name-input' ) ;
352- nameInput . value = app . currentList . name ;
321+ nameInput . value = app . currentList . name || '' ;
353322 nameInput . oninput = ( e ) => app . currentList . name = e . target . value ;
354323
355324 const ul = tpl . getElementById ( 'editor-items' ) ;
@@ -395,13 +364,10 @@ <h2 id="stats-month-year" class="text-lg font-bold text-white capitalize"></h2>
395364 saveOnly : async ( ) => {
396365 if ( ! app . currentList . name ) app . currentList . name = "Naamloze lijst" ;
397366 try {
398- const saved = await DataService . saveList ( app . currentList ) ;
399- // Update het ID voor het geval het een nieuwe lijst was
400- if ( saved && saved . _id ) {
401- app . currentList . _id = saved . _id ;
402- }
367+ await DataService . saveList ( app . currentList ) ;
403368 app . showToast ( "Opgeslagen" ) ;
404- setTimeout ( ( ) => app . renderDashboard ( ) , 150 ) ;
369+ // Geef de manager even tijd om de _id koppeling te doen bij een sync
370+ setTimeout ( ( ) => app . renderDashboard ( ) , 200 ) ;
405371 } catch ( e ) {
406372 app . showToast ( "Opslaan mislukt" , "danger" ) ;
407373 }
@@ -410,14 +376,11 @@ <h2 id="stats-month-year" class="text-lg font-bold text-white capitalize"></h2>
410376 saveAndShop : async ( ) => {
411377 if ( ! app . currentList . name ) app . currentList . name = "Mijn lijst" ;
412378 if ( app . currentList . items . length === 0 ) {
413- app . showToast ( "Lijst is leeg !" , "danger" ) ;
379+ app . showToast ( "Voeg eerst producten toe !" , "danger" ) ;
414380 return ;
415381 }
416382 try {
417- const saved = await DataService . saveList ( app . currentList ) ;
418- if ( saved && saved . _id ) {
419- app . currentList . _id = saved . _id ;
420- }
383+ await DataService . saveList ( app . currentList ) ;
421384 app . shoppingList = app . currentList . items . map ( i => ( { ...i , done : false } ) ) ;
422385 app . renderShopping ( ) ;
423386 } catch ( e ) {
@@ -466,7 +429,11 @@ <h2 id="stats-month-year" class="text-lg font-bold text-white capitalize"></h2>
466429 } ,
467430
468431 finishShopping : async ( ) => {
469- await DataService . addHistory ( { date : new Date ( ) . toISOString ( ) , listName : app . currentList . name } ) ;
432+ await DataService . addHistory ( {
433+ date : new Date ( ) . toISOString ( ) ,
434+ listName : app . currentList . name ,
435+ itemCount : app . shoppingList . length
436+ } ) ;
470437 app . showToast ( "Winkelen voltooid!" ) ;
471438 app . renderDashboard ( ) ;
472439 } ,
@@ -477,7 +444,6 @@ <h2 id="stats-month-year" class="text-lg font-bold text-white capitalize"></h2>
477444 main . innerHTML = '' ;
478445
479446 const tpl = document . getElementById ( 'tpl-stats' ) . content . cloneNode ( true ) ;
480-
481447 const year = app . statDate . getFullYear ( ) ;
482448 const month = app . statDate . getMonth ( ) ;
483449 tpl . getElementById ( 'stats-month-year' ) . innerText = new Intl . DateTimeFormat ( 'nl-NL' , { month : 'long' , year : 'numeric' } ) . format ( app . statDate ) ;
@@ -496,7 +462,7 @@ <h2 id="stats-month-year" class="text-lg font-bold text-white capitalize"></h2>
496462 for ( let day = 1 ; day <= daysInMonth ; day ++ ) {
497463 const count = monthHistory . filter ( h => new Date ( h . date ) . getDate ( ) === day ) . length ;
498464 const div = document . createElement ( 'div' ) ;
499- div . className = `aspect-square rounded-lg flex flex-col items-center justify-center text-sm border ${ count > 0 ? 'bg-emerald-500/20 border-emerald-500 text-white' : 'bg-dark-900 border-gray-800 text-gray-500' } ` ;
465+ div . className = `aspect-square rounded-lg flex flex-col items-center justify-center text-sm border ${ count > 0 ? 'bg-emerald-500/20 border-emerald-500 text-white shadow-[0_0_10px_rgba(16,185,129,0.2)] ' : 'bg-dark-900 border-gray-800 text-gray-500' } ` ;
500466 div . innerHTML = `<span>${ day } </span>${ count > 0 ? `<span class="text-[9px] text-emerald-400 font-bold">+${ count } </span>` : '' } ` ;
501467 daysContainer . appendChild ( div ) ;
502468 }
0 commit comments