#16: trim the schedule form when scheduling from a group
A group's members are automatically the meeting's participants, so the Invite-participants, Invite-by-email and "Guests must be admitted by host" sections are noise there. openScheduleModal now omits them when a group id is present (inviteBlock is empty), and the email/participant/lobby handlers are null-guarded so the save path still works without those fields. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
This commit is contained in:
+16
-10
@@ -4846,6 +4846,18 @@ function openScheduleModal(gid, editMtg){
|
|||||||
const label12=m=>{ let h=Math.floor(m/60),mm=m%60; const ap=h<12?'AM':'PM'; let h12=h%12||12; return h12+':'+pad(mm)+' '+ap; };
|
const label12=m=>{ let h=Math.floor(m/60),mm=m%60; const ap=h<12?'AM':'PM'; let h12=h%12||12; return h12+':'+pad(mm)+' '+ap; };
|
||||||
const dateLabel=d=>d.toLocaleDateString([],{weekday:'short',month:'short',day:'numeric'});
|
const dateLabel=d=>d.toLocaleDateString([],{weekday:'short',month:'short',day:'numeric'});
|
||||||
const invitedIds=new Set(editing&&Array.isArray(editMtg.invitedIds)?editMtg.invitedIds:[]);
|
const invitedIds=new Set(editing&&Array.isArray(editMtg.invitedIds)?editMtg.invitedIds:[]);
|
||||||
|
// #16: scheduling FROM a group doesn't need the invite-participants / invite-by-email / admit-by-host
|
||||||
|
// sections — the group's members are automatically the meeting's participants. Drop them for a group.
|
||||||
|
const fromGroup=!!gid;
|
||||||
|
const inviteBlock = fromGroup ? '' : (
|
||||||
|
'<label class="flbl">Invite participants</label>'
|
||||||
|
+ (CONTACTS.length>6?'<div class="gi-search" style="margin:.15rem 0 .35rem"><input id="schPplSearch" placeholder="Search people…" autocomplete="off"></div>':'')
|
||||||
|
+ '<div class="gi-list" id="schPeople" style="max-height:20vh;overflow:auto">'+(CONTACTS.length?CONTACTS.map(c=>'<label class="chk" data-nm="'+pEsc((c.name||'').toLowerCase())+'"><input type="checkbox" value="'+pEsc(c.id)+'"'+(invitedIds.has(c.id)?' checked':'')+'><span class="mini-av" style="background:'+avColor(c.name)+'">'+pEsc(initials(c.name))+'</span><span class="mn">'+pEsc(c.name)+'</span></label>').join(''):'<div class="gi-noresult">No contacts to invite</div>')+'</div>'
|
||||||
|
+ '<label class="flbl" style="margin-top:.7rem">Invite by email <span class="opt">(guests — no Connect account needed)</span></label>'
|
||||||
|
+ '<div class="email-invite"><input id="schEmail" class="finput" type="email" placeholder="name@example.com" autocomplete="off"><button type="button" class="email-add" id="schEmailAdd">'+ic('userPlus',15)+' Add</button></div>'
|
||||||
|
+ '<div class="email-chips" id="schEmailChips"></div>'
|
||||||
|
+ '<label class="chk2 switch-row" style="margin-top:.6rem"><span>'+ic('users',15)+' Guests must be admitted by the host</span><span class="switch"><input type="checkbox" id="schLobby" checked><span class="slider"></span></span></label>'
|
||||||
|
);
|
||||||
const ov=document.createElement('div'); ov.className='modal-ov'; ov.id='schedModal';
|
const ov=document.createElement('div'); ov.className='modal-ov'; ov.id='schedModal';
|
||||||
ov.innerHTML='<div class="modal sched">'
|
ov.innerHTML='<div class="modal sched">'
|
||||||
+'<div class="gi-head" style="margin-bottom:.6rem"><div class="avatar grp" style="width:40px;height:40px;flex:0 0 40px;background:var(--blue)">'+ic('calendarClock',20)+'</div>'
|
+'<div class="gi-head" style="margin-bottom:.6rem"><div class="avatar grp" style="width:40px;height:40px;flex:0 0 40px;background:var(--blue)">'+ic('calendarClock',20)+'</div>'
|
||||||
@@ -4860,13 +4872,7 @@ function openScheduleModal(gid, editMtg){
|
|||||||
+'<label class="chk2 switch-row"><span>'+ic('calendarClock',15)+' Repeat weekly</span><span class="switch"><input type="checkbox" id="schRepeat"><span class="slider"></span></span></label>'
|
+'<label class="chk2 switch-row"><span>'+ic('calendarClock',15)+' Repeat weekly</span><span class="switch"><input type="checkbox" id="schRepeat"><span class="slider"></span></span></label>'
|
||||||
+'<div class="sch-days hidden" id="schDays">'+DAY1.map((d,i)=>'<button type="button" class="day-chip" data-d="'+i+'" title="'+DAYW[i]+'">'+d+'</button>').join('')+'<button type="button" class="day-all" data-all="1">Everyday</button></div>'
|
+'<div class="sch-days hidden" id="schDays">'+DAY1.map((d,i)=>'<button type="button" class="day-chip" data-d="'+i+'" title="'+DAYW[i]+'">'+d+'</button>').join('')+'<button type="button" class="day-all" data-all="1">Everyday</button></div>'
|
||||||
+'<label class="flbl">Description <span class="opt">(optional)</span></label><textarea id="schDesc" class="finput" rows="2" placeholder="What\'s this call about?"></textarea>'
|
+'<label class="flbl">Description <span class="opt">(optional)</span></label><textarea id="schDesc" class="finput" rows="2" placeholder="What\'s this call about?"></textarea>'
|
||||||
+'<label class="flbl">Invite participants</label>'
|
+inviteBlock // #16: empty when scheduling from a group — the members are the invitees (no invite/email/admit section)
|
||||||
+(CONTACTS.length>6?'<div class="gi-search" style="margin:.15rem 0 .35rem"><input id="schPplSearch" placeholder="Search people…" autocomplete="off"></div>':'')
|
|
||||||
+'<div class="gi-list" id="schPeople" style="max-height:20vh;overflow:auto">'+(CONTACTS.length?CONTACTS.map(c=>'<label class="chk" data-nm="'+pEsc((c.name||'').toLowerCase())+'"><input type="checkbox" value="'+pEsc(c.id)+'"'+(invitedIds.has(c.id)?' checked':'')+'><span class="mini-av" style="background:'+avColor(c.name)+'">'+pEsc(initials(c.name))+'</span><span class="mn">'+pEsc(c.name)+'</span></label>').join(''):'<div class="gi-noresult">No contacts to invite</div>')+'</div>'
|
|
||||||
+'<label class="flbl" style="margin-top:.7rem">Invite by email <span class="opt">(guests — no Connect account needed)</span></label>'
|
|
||||||
+'<div class="email-invite"><input id="schEmail" class="finput" type="email" placeholder="name@example.com" autocomplete="off"><button type="button" class="email-add" id="schEmailAdd">'+ic('userPlus',15)+' Add</button></div>'
|
|
||||||
+'<div class="email-chips" id="schEmailChips"></div>'
|
|
||||||
+'<label class="chk2 switch-row" style="margin-top:.6rem"><span>'+ic('users',15)+' Guests must be admitted by the host</span><span class="switch"><input type="checkbox" id="schLobby" checked><span class="slider"></span></span></label>'
|
|
||||||
+'<button class="gobtn" id="schSave" style="width:100%;margin-top:.9rem;background:var(--blue);color:#fff">'+(editing?'Save changes':'Schedule & invite')+'</button>'
|
+'<button class="gobtn" id="schSave" style="width:100%;margin-top:.9rem;background:var(--blue);color:#fff">'+(editing?'Save changes':'Schedule & invite')+'</button>'
|
||||||
+'<div class="hint" id="schErr"></div></div>';
|
+'<div class="hint" id="schErr"></div></div>';
|
||||||
document.body.appendChild(ov);
|
document.body.appendChild(ov);
|
||||||
@@ -4916,8 +4922,8 @@ function openScheduleModal(gid, editMtg){
|
|||||||
const emailList=(editing&&Array.isArray(editMtg.guestEmails))?editMtg.guestEmails.slice():[];
|
const emailList=(editing&&Array.isArray(editMtg.guestEmails))?editMtg.guestEmails.slice():[];
|
||||||
function renderEmailChips(){ const w=$('schEmailChips'); if(!w) return; w.innerHTML=emailList.map((e,i)=>'<span class="echip">'+pEsc(e)+'<button type="button" data-i="'+i+'" title="Remove">'+ic('x',12)+'</button></span>').join(''); w.querySelectorAll('.echip button').forEach(b=>b.onclick=()=>{ emailList.splice(+b.dataset.i,1); renderEmailChips(); }); }
|
function renderEmailChips(){ const w=$('schEmailChips'); if(!w) return; w.innerHTML=emailList.map((e,i)=>'<span class="echip">'+pEsc(e)+'<button type="button" data-i="'+i+'" title="Remove">'+ic('x',12)+'</button></span>').join(''); w.querySelectorAll('.echip button').forEach(b=>b.onclick=()=>{ emailList.splice(+b.dataset.i,1); renderEmailChips(); }); }
|
||||||
function addEmail(){ const inp=$('schEmail'); const v=(inp.value||'').trim().toLowerCase(); if(!v) return; if(!EMAIL_RE.test(v)){ err.textContent='Enter a valid email address.'; return; } if(!emailList.includes(v)) emailList.push(v); inp.value=''; err.textContent=''; renderEmailChips(); }
|
function addEmail(){ const inp=$('schEmail'); const v=(inp.value||'').trim().toLowerCase(); if(!v) return; if(!EMAIL_RE.test(v)){ err.textContent='Enter a valid email address.'; return; } if(!emailList.includes(v)) emailList.push(v); inp.value=''; err.textContent=''; renderEmailChips(); }
|
||||||
$('schEmailAdd').onclick=addEmail;
|
{ const ea=$('schEmailAdd'); if(ea) ea.onclick=addEmail; } // #16: absent when scheduling from a group
|
||||||
$('schEmail').addEventListener('keydown',e=>{ if(e.key==='Enter'){ e.preventDefault(); addEmail(); } });
|
{ const em=$('schEmail'); if(em) em.addEventListener('keydown',e=>{ if(e.key==='Enter'){ e.preventDefault(); addEmail(); } }); }
|
||||||
renderEmailChips();
|
renderEmailChips();
|
||||||
// #10: filter the participant list as you type.
|
// #10: filter the participant list as you type.
|
||||||
{ const ps=$('schPplSearch'); if(ps) ps.addEventListener('input',()=>{ const q=ps.value.trim().toLowerCase(); ov.querySelectorAll('#schPeople .chk').forEach(l=>{ l.style.display=(!q||(l.dataset.nm||'').includes(q))?'':'none'; }); }); }
|
{ const ps=$('schPplSearch'); if(ps) ps.addEventListener('input',()=>{ const q=ps.value.trim().toLowerCase(); ov.querySelectorAll('#schPeople .chk').forEach(l=>{ l.style.display=(!q||(l.dataset.nm||'').includes(q))?'':'none'; }); }); }
|
||||||
@@ -4926,7 +4932,7 @@ function openScheduleModal(gid, editMtg){
|
|||||||
const desc=$('schDesc').value.trim();
|
const desc=$('schDesc').value.trim();
|
||||||
const durationMins=parseInt($('schDur').value,10)||30;
|
const durationMins=parseInt($('schDur').value,10)||30;
|
||||||
const participants=[...ov.querySelectorAll('#schPeople input:checked')].map(i=>i.value);
|
const participants=[...ov.querySelectorAll('#schPeople input:checked')].map(i=>i.value);
|
||||||
{ const pend=($('schEmail').value||'').trim().toLowerCase(); if(pend && EMAIL_RE.test(pend) && !emailList.includes(pend)) emailList.push(pend); } // include a typed-but-not-added email
|
{ const em=$('schEmail'); const pend=((em&&em.value)||'').trim().toLowerCase(); if(pend && EMAIL_RE.test(pend) && !emailList.includes(pend)) emailList.push(pend); } // include a typed-but-not-added email (#16: absent for group schedules)
|
||||||
clearErrAll();
|
clearErrAll();
|
||||||
if(!title){ err.textContent='Please add a title.'; $('schTitle').classList.add('field-err'); $('schTitle').focus(); return; }
|
if(!title){ err.textContent='Please add a title.'; $('schTitle').classList.add('field-err'); $('schTitle').focus(); return; }
|
||||||
const ts=new Date(selDate.getFullYear(),selDate.getMonth(),selDate.getDate(),Math.floor(selMin/60),selMin%60,0,0).getTime();
|
const ts=new Date(selDate.getFullYear(),selDate.getMonth(),selDate.getDate(),Math.floor(selMin/60),selMin%60,0,0).getTime();
|
||||||
|
|||||||
Reference in New Issue
Block a user