diff --git a/public/index.html b/public/index.html
index 4368e77..5bcf1f6 100644
--- a/public/index.html
+++ b/public/index.html
@@ -28,5 +28,6 @@ function timeline(c){let a=mems();c.innerHTML=`
MEMORY ARCHI
function museumApp(c){let a=museum(),ms=mems();c.innerHTML=`
MUSEUM
Preserved moments Worth keeping for the long view.
${a.length?`
${a.map(x=>{let m=ms.find(q=>q.id===x.memoryId);return m?`COLLECTION #${x.id.slice(-4).toUpperCase()} ${esc(m.filmTitle)} ${fmtDate(m.date)} STATUS: PRESERVED `:''}).join('')}
`:'
A museum begins with one preserved moment.
'}`}
function streak(a){let s=0,d=new Date();while(a.some(m=>m.date===d.toISOString().slice(0,10))){s++;d.setDate(d.getDate()-1)}return s}function longest(a){let ds=a.map(x=>x.date).sort(),best=0,run=0,last='';ds.forEach(d=>{run=last&&((new Date(d)-new Date(last))/864e5===1)?run+1:1;best=Math.max(best,run);last=d});return best}function insights(c){let a=mems(),last=a.filter(m=>(Date.now()-new Date(m.date+'T12:00:00'))<2592e6),cnt={clear:0,light:0,cloudy:0,rain:0,storm:0};last.forEach(x=>cnt[x.mood]++);let avg=a.length?(a.reduce((s,x)=>s+x.energy,0)/a.length).toFixed(1):'—',days={};a.forEach(x=>{let d=new Date(x.date+'T12:00:00').toLocaleDateString('en-US',{weekday:'long'});days[d]=(days[d]||0)+1});let active=Object.entries(days).sort((x,y)=>y[1]-x[1])[0]?.[0]||'—';c.innerHTML=`
LAST 30 DAYS
Insights, quietly. WEATHER
${Object.entries(cnt).map(([k,v])=>`${cap(k)} ${v} DAYS
`).join('')}AVERAGE ENERGY
${avg} / 5
${a.slice(0,10).reverse().map(x=>` `).join('')||'No entries yet '}
CURRENT STREAK
${streak(a)} DAYS
Longest streak: ${longest(a)} days
`}
function profileApp(c){let p=profile(),a=mems(),common=Object.entries(a.reduce((o,m)=>(o[m.mood]=(o[m.mood]||0)+1,o),{})).sort((x,y)=>y[1]-x[1])[0]?.[0]||'—',avg=a.length?(a.reduce((x,m)=>x+m.energy,0)/a.length).toFixed(1):'—',started=Math.max(1,Math.floor((Date.now()-new Date(p.startDate))/864e5));c.innerHTML=`
SYSTEM PROFILE
${p.name?esc(p.name)+' · ':''}LIFE OS ONLINE ${started} DAYS ONLINE
${a.length} MEMORIES
${museum().length} MUSEUM ITEMS
${streak(a)} CURRENT STREAK
${longest(a)} LONGEST STREAK
${cap(common)} COMMON WEATHER
PERSONAL SYSTEM
Display Name
Birthday (optional)
Life OS Start Date
Personal Motto
SAVE PROFILE AVERAGE ENERGY ${avg} / 5
`}function saveProfile(){save('lifeos_profile',{name:pname.value,birthday:pbday.value,startDate:pstart.value||day(),motto:pmotto.value});renderAll();toast('PROFILE SAVED')}
+function today(c){let m=mems().find(x=>x.date===day());if(todayDraft===null){selectedMood=m?.mood||'cloudy';selectedEnergy=m?.energy||3}let f=m||filmFor(selectedMood,selectedEnergy),text=todayDraft===null?(m?.text||''):todayDraft,cWeek=new Date().toLocaleDateString(lang()==='zh'?'zh-CN':'en-US',{weekday:'long'}).toUpperCase();c.innerHTML=`
${cWeek}
${fmtDate(day()).replace(/^[^,]+, /,'')} ${i18n('How was your day?')}
${i18n(m?'UPDATE MEMORY':'ARCHIVE TODAY')}
${i18n("TODAY'S WEATHER")}
${['clear','light','cloudy','rain','storm'].map(x=>`${moodName(x)} `).join('')}
${i18n('ENERGY LEVEL')}
${[1,2,3,4,5].map(x=>`${x} `).join('')}
${i18n("TODAY'S FILM")}
${f.filmTitle}
${f.filmSubtitle}
“${f.filmLine}”
`}function rerenderToday(){let old=document.querySelector('#entry');todayDraft=old?old.value:todayDraft||'';today(document.querySelector('#content-today'));let entry=document.querySelector('#entry');entry?.focus();entry?.setSelectionRange(entry.value.length,entry.value.length)}
function systemApp(c){let s=settings(),bytes=new Blob([JSON.stringify({mems:mems(),museum:museum(),profile:profile()})]).size;let rec=s.lastBackup&&(Date.now()-new Date(s.lastBackup)>12096e5);c.innerHTML=`
SYSTEM SETTINGS
System, local and yours. APPEARANCE
${['dark','light','auto'].map(x=>`${x.toUpperCase()} `).join('')}
STORAGE
Local Storage ${mems().length} memories · ${museum().length} museum items · Approx. ${Math.ceil(bytes/1024)} KB
DATA STORAGE
Your data is stored locally in this browser. Create regular backups to prevent data loss.
${s.lastBackup?'LAST BACKUP · '+fmtDate(s.lastBackup.slice(0,10)):'LAST BACKUP · NEVER'} ${rec?'BACKUP RECOMMENDED ':''}
VERSION
Life OS Version 0.1 · Schema v1
`}function theme(x){let s=settings();s.theme=x;save('lifeos_settings',s);init();renderAll()}function exportData(){let data={app:'Life OS',version:'0.1',schemaVersion:1,exportedAt:new Date().toISOString(),profile:profile(),memories:mems(),museum:museum(),settings:settings()};let a=document.createElement('a');a.href=URL.createObjectURL(new Blob([JSON.stringify(data,null,2)],{type:'application/json'}));a.download='life-os-backup-'+day()+'.json';a.click();let s=settings();s.lastBackup=new Date().toISOString();save('lifeos_settings',s);renderAll();toast('BACKUP CREATED')}function readImport(el){let f=el.files[0];if(!f)return;let r=new FileReader;r.onload=()=>{try{let d=JSON.parse(r.result);if(d.app!=='Life OS'||d.schemaVersion!==1||!Array.isArray(d.memories)||!Array.isArray(d.museum))throw 0;importData=d;importPreview()}catch{toast('INVALID BACKUP FILE')}};r.readAsText(f)}function importPreview(){let d=importData;modal.innerHTML=`
LIFE OS BACKUP
Ready to restore Exported: ${fmtDate(d.exportedAt.slice(0,10))} Memories: ${d.memories.length} Museum Items: ${d.museum.length}
MERGE REPLACE ALL DATA CANCEL
`}function replaceConfirm(){modal.innerHTML=`
FINAL CONFIRMATION
Replace all Life OS data? This will replace all current Life OS data.
REPLACE DATA CANCEL
`}function applyImport(mode){let d=importData;if(mode==='replace'){save('lifeos_memories',d.memories);save('lifeos_museum',d.museum);save('lifeos_profile',d.profile||{});save('lifeos_settings',d.settings||{})}else{let a=mems(), ids=new Set(a.map(x=>x.id)),dates=new Set(a.map(x=>x.date));save('lifeos_memories',[...a,...d.memories.filter(x=>!ids.has(x.id)&&!dates.has(x.date))]);let mu=museum(),mi=new Set(mu.map(x=>x.id));save('lifeos_museum',[...mu,...d.museum.filter(x=>!mi.has(x.id))])}modal.innerHTML='';toast('RESTORING SYSTEM...');setTimeout(()=>{renderAll();toast('SYSTEM RESTORED')},500)}function resetConfirm(){modal.innerHTML=`
RESET LIFE OS
Reset all local data? Export a backup first if you want to keep it.
RESET DATA CANCEL
`}function toast(t){let x=document.createElement('div');x.className='toast';x.textContent=t;document.body.append(x);setTimeout(()=>x.remove(),2000)}init();