function ListEditPage({ listId }) {
  const { AppBootstrap } = window.__CRM__;
  const {
    Container, Stack, Typography, TextField, Button, Breadcrumbs, Link, Paper, useMediaQuery,
    Table, TableHead, TableRow, TableCell, TableBody, TableContainer, Pagination,
    IconButton, Chip, Checkbox, Dialog, DialogTitle, DialogContent, DialogActions, Grid, MenuItem, Card, CardContent, Divider
  } = MaterialUI;

  const isXs = useMediaQuery('(max-width:600px)');
  const isSm = useMediaQuery('(max-width:900px)');

  const [loading, setLoading] = React.useState(true);
  const [err, setErr] = React.useState('');
  const [list, setList] = React.useState(null);

  // table state
  const [q, setQ] = React.useState('');
  const [rows, setRows] = React.useState([]);
  const [total, setTotal] = React.useState(0);
  const [page, setPage] = React.useState(1);
  const limit = 25;
  const [selected, setSelected] = React.useState(new Set());

  // Add/Edit modal
  const emptyForm = { id:0, name:'', phone:'', email:'', status:'Active', address_line:'', apt_suite:'', city:'', state:'', zip_code:'', country:'', notes:'' };
  const [openEdit, setOpenEdit] = React.useState(false);
  const [form, setForm] = React.useState(emptyForm);

  // Add from Contacts modal
  const [openFrom, setOpenFrom] = React.useState(false);
  const [searchC, setSearchC] = React.useState('');
  const [candidates, setCandidates] = React.useState([]);
  const [pick, setPick] = React.useState(new Set());

  React.useEffect(() => {
    let alive = true;
    (async () => {
      try {
        const r = await fetch(`/api/lists_get.php?id=${encodeURIComponent(listId)}`, { credentials:'include' });
        if (!alive) return;
        if (!r.ok) { setErr('List not found'); setLoading(false); return; }
        const j = await r.json();
        setList(j.list); setLoading(false);
      } catch { if (!alive) return; setErr('Failed to load list'); setLoading(false); }
    })();
    return () => { alive = false; };
  }, [listId]);

  async function load(p=1){
    const offset = (p-1)*limit;
    const res = await fetch(`/api/list_contacts_list.php?list_id=${listId}&q=${encodeURIComponent(q)}&limit=${limit}&offset=${offset}`, { credentials:'include' });
    const j = await res.json();
    setRows(j.items||[]); setTotal(j.total||0); setPage(p); setSelected(new Set());
  }
  React.useEffect(()=>{ if(list) load(1); }, [list]);

  // CRUD
  async function upsert(payload){
    await fetch('/api/list_contacts_upsert.php', { method:'POST', headers:{'Content-Type':'application/json'}, body:JSON.stringify({ ...payload, list_id: Number(listId) }), credentials:'include' });
  }
  async function delOne(id){
    await fetch('/api/list_contacts_delete.php', { method:'POST', body:new URLSearchParams({ list_id:String(listId), id:String(id) }), credentials:'include' });
  }
  async function delBulk(){
    if(!selected.size) return;
    if(!confirm(`Delete ${selected.size} selected contact(s) from this list?`)) return;
    await fetch('/api/list_contacts_delete_bulk.php', { method:'POST', headers:{'Content-Type':'application/json'}, body:JSON.stringify({ list_id:Number(listId), ids:Array.from(selected) }), credentials:'include' });
    load(page);
  }

  function exportAll(){ location.href = `/api/lists_export.php?id=${encodeURIComponent(listId)}`; }
  function exportSelected(){
    if(!selected.size) return;
    location.href = `/api/lists_export.php?id=${encodeURIComponent(listId)}&ids=${encodeURIComponent(Array.from(selected).join(','))}`;
  }

  // Edit modal handlers
  function openAdd(){ setForm(emptyForm); setOpenEdit(true); }
  function openEditRow(r){ setForm({ ...r }); setOpenEdit(true); }
  function closeEdit(){ setOpenEdit(false); }
  async function saveEdit(){
    if(!form.name.trim()) { alert('Name is required'); return; }
    await upsert(form); setOpenEdit(false); load(form.id? page : 1);
  }

  // From Contacts modal
  async function searchContacts(){
    const r = await fetch(`/api/contacts_search.php?q=${encodeURIComponent(searchC)}&limit=50`, { credentials:'include' });
    const j = await r.json();
    setCandidates(j.items||[]);
  }
  function togglePick(id){
    setPick(prev=>{ const n=new Set(prev); if(n.has(id)) n.delete(id); else n.add(id); return n; });
  }
  async function addFromContacts(){
    if(!pick.size) { setOpenFrom(false); return; }
    await fetch('/api/list_contacts_add_from_contacts.php', { method:'POST', headers:{'Content-Type':'application/json'}, body:JSON.stringify({ list_id:Number(listId), contact_ids:Array.from(pick) }), credentials:'include' });
    setOpenFrom(false); setPick(new Set()); load(1);
  }

  // selection helpers
  const allIdsOnPage = React.useMemo(()=>rows.map(r=>r.id),[rows]);
  const allSelected = allIdsOnPage.length>0 && allIdsOnPage.every(id=>selected.has(id));
  const someSelected = allIdsOnPage.some(id=>selected.has(id));
  function toggleOne(id){ setSelected(prev=>{ const n=new Set(prev); if(n.has(id)) n.delete(id); else n.add(id); return n; }); }
  function toggleAllPage(){ setSelected(prev=>{ const n=new Set(prev); if(allSelected){ allIdsOnPage.forEach(id=>n.delete(id)); } else { allIdsOnPage.forEach(id=>n.add(id)); } return n; }); }

  const pages = Math.max(1, Math.ceil(total/limit));

  const CardRow = ({ r }) => (
    <Card variant="outlined" sx={{ mb:1, borderRadius:2 }}>
      <CardContent sx={{ p:2 }}>
        <Stack direction="row" justifyContent="space-between" alignItems="center" sx={{ mb:1 }}>
          <Stack direction="row" spacing={1} alignItems="center">
            <Checkbox size="small" checked={selected.has(r.id)} onChange={()=>toggleOne(r.id)} />
            <Typography variant="subtitle1" sx={{ fontWeight:700, overflow:'hidden', textOverflow:'ellipsis', whiteSpace:'nowrap' }}>{r.name}</Typography>
          </Stack>
        </Stack>
        <Stack spacing={0.5} sx={{ color:'text.secondary', fontSize:14 }}>
          {r.phone && <div><b>Phone:</b> {r.phone}</div>}
          {r.email && <div><b>Email:</b> {r.email}</div>}
          {(r.city||r.state) && <div><b>Location:</b> {[r.city,r.state].filter(Boolean).join(' / ')}</div>}
          {r.address_line && <div><b>Address:</b> {r.address_line}</div>}
          {r.notes && <div><b>Notes:</b> {r.notes}</div>}
        </Stack>
        <Divider sx={{ my:1 }} />
        <Stack direction="row" spacing={1} justifyContent="flex-end">
          <IconButton size="small" onClick={()=>openEditRow(r)} title="Edit"><span class="material-icons">edit</span></IconButton>
          <IconButton size="small" onClick={()=>{ if(confirm('Delete this contact from list?')){ delOne(r.id).then(()=>load(page)); }}} title="Delete"><span class="material-icons">delete</span></IconButton>
        </Stack>
      </CardContent>
    </Card>
  );

  return (
    <AppBootstrap>
      <Container maxWidth="xl" sx={{ py: 3 }}>
        <Breadcrumbs sx={{ mb: 1 }}>
          <Link href="#/lists" underline="hover">Lists</Link>
          <Typography color="text.primary">Edit List</Typography>
        </Breadcrumbs>

        <Stack direction={{ xs:'column', md:'row' }} alignItems={{ xs:'flex-start', md:'center' }} justifyContent="space-between" spacing={2} sx={{ mb: 2 }}>
          <Typography variant={isSm?'h6':'h5'} sx={{ fontWeight:700 }}>
            {loading ? 'Loading…' : (list ? list.name : 'List')}
          </Typography>
          <Stack direction="row" spacing={1}>
            <TextField size="small" placeholder="Search in this list" value={q} onChange={e=>setQ(e.target.value)} />
            <Button variant="outlined" onClick={()=>load(1)}>Search</Button>
             </Stack>
          <Stack direction="row" spacing={1} >
            <Button variant="outlined" component="label">Import CSV<input type="file" accept=".csv,text/csv" hidden onChange={(e)=>{ const f=e.target.files?.[0]; if(!f) return; const fd=new FormData(); fd.append('list_id', String(listId)); fd.append('file', f); fetch('/api/list_contacts_import.php',{method:'POST',body:fd,credentials:'include'}).then(()=>{ e.target.value=''; load(1); }); }} /></Button>
            <Button variant="outlined" onClick={exportAll}>Export CSV</Button>
            <Button variant="contained" onClick={openAdd}>Add Contact</Button>
            <Button variant="contained" onClick={()=>{ setOpenFrom(true); setSearchC(''); setCandidates([]); setPick(new Set()); }}>Add from Contacts</Button>
            <Button variant="contained" color="error" disabled={!selected.size} onClick={delBulk}>Delete Selected{selected.size?` (${selected.size})`:''}</Button>
            <Button variant="outlined" disabled={!selected.size} onClick={exportSelected}>Export Selected{selected.size?` (${selected.size})`:''}</Button>
          </Stack>
        </Stack>

        {err && <Paper sx={{ p:2, color:'error.main' }}>{err}</Paper>}

        {!err && (isXs ? (
          <div>
            {rows.length===0 ? <Typography sx={{ p:2 }} color="text.secondary">No records.</Typography>
              : rows.map(r => <CardRow key={r.id} r={r} />)}
          </div>
        ) : (
          <Paper>
            <TableContainer sx={{ maxHeight: isSm ? 520 : 'none' }}>
              <Table size="small" stickyHeader>
                <TableHead>
                  <TableRow>
                    <TableCell padding="checkbox">
                      <Checkbox indeterminate={!allSelected && someSelected} checked={allSelected} onChange={toggleAllPage} />
                    </TableCell>
                    <TableCell>Name</TableCell>
                    <TableCell>Phone</TableCell>
                    <TableCell>Email</TableCell>
                    <TableCell>Status</TableCell>
                    <TableCell sx={{ display:{ xs:'none', md:'table-cell' } }}>Address</TableCell>
                    <TableCell sx={{ display:{ xs:'none', md:'table-cell' } }}>City</TableCell>
                    <TableCell sx={{ display:{ xs:'none', lg:'table-cell' } }}>State</TableCell>
                    <TableCell sx={{ display:{ xs:'none', lg:'table-cell' } }}>Zip</TableCell>
                    <TableCell sx={{ display:{ xs:'none', lg:'table-cell' } }}>Country</TableCell>
                    <TableCell sx={{ display:{ xs:'none', lg:'table-cell' }, maxWidth:260, whiteSpace:'nowrap', overflow:'hidden', textOverflow:'ellipsis' }}>Notes</TableCell>
                    <TableCell align="right">Actions</TableCell>
                  </TableRow>
                </TableHead>
                <TableBody>
                  {rows.map(r=>{
                    const checked = selected.has(r.id);
                    return (
                      <TableRow key={r.id} hover selected={checked}>
                        <TableCell padding="checkbox">
                          <Checkbox checked={checked} onChange={()=>toggleOne(r.id)} />
                        </TableCell>
                        <TableCell sx={{ maxWidth:220, whiteSpace:'nowrap', textOverflow:'ellipsis', overflow:'hidden' }}>{r.name}</TableCell>
                        <TableCell>{r.phone||'-'}</TableCell>
                        <TableCell sx={{ maxWidth:220, whiteSpace:'nowrap', textOverflow:'ellipsis', overflow:'hidden' }}>{r.email||'-'}</TableCell>
                        <TableCell><Chip size="small" label={r.status} color={r.status === 'Blocked' ? 'error' : 'success'} /></TableCell>
                        <TableCell sx={{ display:{ xs:'none', md:'table-cell' } }}>{r.address_line||'-'}</TableCell>
                        <TableCell sx={{ display:{ xs:'none', md:'table-cell' } }}>{r.city||'-'}</TableCell>
                        <TableCell sx={{ display:{ xs:'none', lg:'table-cell' } }}>{r.state||'-'}</TableCell>
                        <TableCell sx={{ display:{ xs:'none', lg:'table-cell' } }}>{r.zip_code||'-'}</TableCell>
                        <TableCell sx={{ display:{ xs:'none', lg:'table-cell' } }}>{r.country||'-'}</TableCell>
                        <TableCell sx={{ display:{ xs:'none', lg:'table-cell' }, maxWidth:260, whiteSpace:'nowrap', textOverflow:'ellipsis', overflow:'hidden' }}>{r.notes||'-'}</TableCell>
                        <TableCell align="right">
                          <Stack direction="row" spacing={1} justifyContent="flex-end">
                            <IconButton size="small" onClick={()=>openEditRow(r)} title="Edit"><span class="material-icons">edit</span></IconButton>
                            <IconButton size="small" onClick={()=>{ if(confirm('Delete this contact from list?')){ delOne(r.id).then(()=>load(page)); }}} title="Delete"><span class="material-icons">delete</span></IconButton>
                          </Stack>
                        </TableCell>
                      </TableRow>
                    );
                  })}
                  {rows.length===0 && (
                    <TableRow><TableCell colSpan={12}><Typography sx={{ p:2 }} color="text.secondary">No records.</Typography></TableCell></TableRow>
                  )}
                </TableBody>
              </Table>
            </TableContainer>
          </Paper>
        ))}

        <Stack alignItems="center" sx={{ mt:2 }}>
          <Pagination count={pages} page={page} onChange={(_,p)=>load(p)} />
        </Stack>
      </Container>

      {/* Add/Edit contact modal */}
      <Dialog open={openEdit} onClose={closeEdit} maxWidth="md" fullWidth>
        <DialogTitle>{form.id ? 'Edit Contact' : 'Add Contact'}</DialogTitle>
        <DialogContent dividers>
          <Grid container spacing={2} sx={{ pt:1 }}>
            <Grid item xs={12} md={6}><TextField label="Name" value={form.name} onChange={e=>setForm({...form,name:e.target.value})} fullWidth required /></Grid>
            <Grid item xs={12} md={6}>
              <TextField label="Status" select value={form.status} onChange={e=>setForm({...form,status:e.target.value})} fullWidth>
                <MenuItem value="Active">Active</MenuItem>
                <MenuItem value="Blocked">Blocked</MenuItem>
              </TextField>
            </Grid>
            <Grid item xs={12} md={6}><TextField label="Phone" value={form.phone} onChange={e=>setForm({...form,phone:e.target.value})} fullWidth /></Grid>
            <Grid item xs={12} md={6}><TextField label="Email" type="email" value={form.email} onChange={e=>setForm({...form,email:e.target.value})} fullWidth /></Grid>
            <Grid item xs={12}><TextField label="Address" value={form.address_line} onChange={e=>setForm({...form,address_line:e.target.value})} fullWidth /></Grid>
            <Grid item xs={12} md={4}><TextField label="Apt/Suite" value={form.apt_suite} onChange={e=>setForm({...form,apt_suite:e.target.value})} fullWidth /></Grid>
            <Grid item xs={12} md={4}><TextField label="City" value={form.city} onChange={e=>setForm({...form,city:e.target.value})} fullWidth /></Grid>
            <Grid item xs={12} md={4}><TextField label="State" value={form.state} onChange={e=>setForm({...form,state:e.target.value})} fullWidth /></Grid>
            <Grid item xs={12} md={4}><TextField label="Zip Code" value={form.zip_code} onChange={e=>setForm({...form,zip_code:e.target.value})} fullWidth /></Grid>
            <Grid item xs={12} md={4}><TextField label="Country" value={form.country} onChange={e=>setForm({...form,country:e.target.value})} fullWidth /></Grid>
            <Grid item xs={12}><TextField label="Notes" value={form.notes} onChange={e=>setForm({...form,notes:e.target.value})} fullWidth multiline minRows={3} /></Grid>
          </Grid>
        </DialogContent>
        <DialogActions>
          <Button onClick={closeEdit}>Cancel</Button>
          <Button variant="contained" onClick={saveEdit}>{form.id?'Save':'Add'}</Button>
        </DialogActions>
      </Dialog>

      {/* Add from Contacts modal */}
      <Dialog open={openFrom} onClose={()=>setOpenFrom(false)} maxWidth="md" fullWidth>
        <DialogTitle>Add from Contacts</DialogTitle>
        <DialogContent dividers sx={{ pt:1 }}>
          <Stack direction={{xs:'column', md:'row'}} spacing={1} alignItems={{xs:'stretch', md:'center'}} sx={{ mb:1 }}>
            <TextField size="small" placeholder="Search contacts (name, email, phone)" value={searchC} onChange={e=>setSearchC(e.target.value)} fullWidth />
            <Button variant="outlined" onClick={searchContacts}>Search</Button>
          </Stack>
          <Paper variant="outlined" sx={{ maxHeight: 360, overflow:'auto' }}>
            <Table size="small" stickyHeader>
              <TableHead>
                <TableRow>
                  <TableCell padding="checkbox"></TableCell>
                  <TableCell>Name</TableCell>
                  <TableCell>Phone</TableCell>
                  <TableCell>Email</TableCell>
                </TableRow>
              </TableHead>
              <TableBody>
                {candidates.map(c => {
                  const checked = pick.has(c.id);
                  return (
                    <TableRow key={c.id} hover selected={checked} onClick={()=>togglePick(c.id)} sx={{ cursor:'pointer' }}>
                      <TableCell padding="checkbox"><Checkbox checked={checked} /></TableCell>
                      <TableCell sx={{ maxWidth:260, whiteSpace:'nowrap', overflow:'hidden', textOverflow:'ellipsis' }}>{c.name}</TableCell>
                      <TableCell>{c.phone||'-'}</TableCell>
                      <TableCell sx={{ maxWidth:260, whiteSpace:'nowrap', overflow:'hidden', textOverflow:'ellipsis' }}>{c.email||'-'}</TableCell>
                    </TableRow>
                  );
                })}
                {candidates.length===0 && (
                  <TableRow><TableCell colSpan={4}><Typography sx={{ p:2 }} color="text.secondary">No results.</Typography></TableCell></TableRow>
                )}
              </TableBody>
            </Table>
          </Paper>
        </DialogContent>
        <DialogActions>
          <Button onClick={()=>setOpenFrom(false)}>Cancel</Button>
          <Button variant="contained" onClick={addFromContacts} disabled={!pick.size}>Add Selected{pick.size?` (${pick.size})`:''}</Button>
        </DialogActions>
      </Dialog>
    </AppBootstrap>
  );
}
window.ListEditPage = ListEditPage;
