diff --git a/web-dashboard/index.html b/web-dashboard/index.html
index 6ea4725..c943625 100644
--- a/web-dashboard/index.html
+++ b/web-dashboard/index.html
@@ -2854,6 +2854,33 @@
return `Dokument ${index + 1}.${ext}`;
}
+ // Klick auf den Namen öffnet eine Vorschau im neuen Tab (Browser können
+ // PDFs/Bilder nativ anzeigen); der Pfeil daneben lädt bei Bedarf separat
+ // herunter. Für alle hochgeladenen Dokumente (Verträge, Ausweis, Schufa) einheitlich.
+ function buildDocumentChip(label, url) {
+ const chip = el('span', 'invite-status-chip');
+ chip.style.cssText = 'background:var(--bg); color:var(--text); text-transform:none; display:inline-flex; align-items:center; gap:7px;';
+
+ const previewLink = document.createElement('a');
+ previewLink.href = url;
+ previewLink.target = '_blank';
+ previewLink.rel = 'noopener';
+ previewLink.textContent = label;
+ previewLink.style.color = 'var(--text)';
+ chip.appendChild(previewLink);
+
+ const ext = url.includes('application/pdf') ? 'pdf' : (/^data:image\/(\w+)/.exec(url)?.[1] || 'jpg');
+ const downloadLink = document.createElement('a');
+ downloadLink.href = url;
+ downloadLink.download = `${label.replace(/[^\w.-]+/g, '_')}.${ext}`;
+ downloadLink.title = 'Herunterladen';
+ downloadLink.textContent = '⬇';
+ downloadLink.style.cssText = 'color:var(--text-muted); text-decoration:none; font-size:12px;';
+ chip.appendChild(downloadLink);
+
+ return chip;
+ }
+
function buildProfileCompletenessBadge(user) {
const missing = [];
if (!user.phoneNumber) missing.push('Telefonnummer');
@@ -2894,13 +2921,7 @@
['Schufa-Auskunft', user.schufaDocumentUrl],
].forEach(([label, url]) => {
if (!url) return;
- const link = document.createElement('a');
- link.href = url;
- link.download = label + '.' + (url.includes('application/pdf') ? 'pdf' : 'jpg');
- link.textContent = label;
- link.className = 'invite-status-chip';
- link.style.cssText = 'background:var(--bg); color:var(--text); text-transform:none;';
- linkWrap.appendChild(link);
+ linkWrap.appendChild(buildDocumentChip(label, url));
});
if (linkWrap.children.length) wrap.appendChild(linkWrap);
@@ -2951,14 +2972,7 @@
docWrap.appendChild(el('span', 'meta-text', 'Noch keine Dateien hochgeladen.'));
} else {
c.contractDocumentUrls.forEach((url, idx) => {
- const chip = el('span', 'invite-status-chip');
- chip.style.cssText = 'background:var(--bg); color:var(--text); display:inline-flex; align-items:center; gap:6px; text-transform:none;';
- const link = document.createElement('a');
- link.href = url;
- link.download = documentFileName(url, idx);
- link.textContent = documentFileName(url, idx);
- link.style.color = 'var(--text)';
- chip.appendChild(link);
+ const chip = buildDocumentChip(documentFileName(url, idx), url);
if (isLandlord) {
const removeBtn = document.createElement('button');
removeBtn.type = 'button';
@@ -3068,13 +3082,7 @@
const docWrap = el('div');
docWrap.style.cssText = 'display:flex; flex-wrap:wrap; gap:6px;';
c.contractDocumentUrls.forEach((url, idx) => {
- const link = document.createElement('a');
- link.href = url;
- link.download = documentFileName(url, idx);
- link.textContent = documentFileName(url, idx);
- link.className = 'invite-status-chip';
- link.style.cssText = 'background:var(--bg); color:var(--text); text-transform:none;';
- docWrap.appendChild(link);
+ docWrap.appendChild(buildDocumentChip(documentFileName(url, idx), url));
});
row.appendChild(docWrap);
}