Author SHA1 Message Date
fen 3ac575a2dc Line wrap toggle for editor and paste viewer with remembered preference (#130)
CI / docker (pull_request) Skipped
CI / test (pull_request) Successful in 26s
- wrap toggle button on /new editor and paste view (accent active state)
- flips white-space pre <-> pre-wrap on the code body
- shared localStorage preference palette-wrap, default off
- settings checkbox reads and writes the same preference
2026-09-09 22:31:07 -05:00
4 changed files with 59 additions and 0 deletions
+5
View File
@@ -691,3 +691,8 @@ button[type="submit"]:focus-visible,
.attachment-chip:hover { border-color: var(--accent); }
.attachment-chip .attachment-size { color: var(--muted-fg); font-size: 19px; }
.attachment-preview img { max-width: 480px; max-height: 360px; border-radius: var(--radius); border: 1px solid var(--border); }
/* line wrap toggle (#130): body wrap variants + toggle button */
.editor.wrap, .codebody.wrap { white-space: pre-wrap; word-break: break-word; }
.wrap-toggle[aria-pressed="true"] { background: var(--accent); color: var(--bg); border-color: var(--accent); }
.editor-tools { display: flex; justify-content: flex-end; }
+23
View File
@@ -22,6 +22,9 @@
<div class="gutter" id="gutter">1</div>
<textarea class="editor" id="content" placeholder="Paste your code, text, or notes here…" spellcheck="false"></textarea>
</div>
<div class="editor-tools">
<button class="iconbtn wrap-toggle" id="wrap-toggle" type="button" title="Toggle line wrap" aria-label="Toggle line wrap" aria-pressed="false">wrap</button>
</div>
<div class="created-banner" id="created"></div>
<div class="actionbar">
<span class="hint">Ctrl+Enter to create</span>
@@ -291,5 +294,25 @@ window.addEventListener('pageshow', e => {
document.addEventListener('keydown', e => {
if ((e.ctrlKey || e.metaKey) && e.key === 'Enter') { e.preventDefault(); create(); }
});
// #130: line wrap toggle, shared preference with the viewer (palette-wrap)
(function () {
var el = document.getElementById('content');
var btn = document.getElementById('wrap-toggle');
function apply(on) {
el.classList.toggle('wrap', on);
btn.setAttribute('aria-pressed', on ? 'true' : 'false');
}
var on = false;
try { on = localStorage.getItem('palette-wrap') === 'true'; } catch (e) {}
apply(on);
btn.addEventListener('click', function () {
on = !on;
try { localStorage.setItem('palette-wrap', on ? 'true' : 'false'); } catch (e) {}
apply(on);
});
// follow changes made in settings on other tabs/pages
document.addEventListener('palette-wrapchange', function (e) { apply(e.detail); });
})();
</script>
{{template "foot" .}}
+20
View File
@@ -6,6 +6,7 @@
<h1>{{if .Title}}{{.Title}}{{else}}Untitled paste{{end}}</h1>
{{if .CustomSlug}}<span class="slug">/{{.CustomSlug}}</span>{{end}}
<div class="spacer"></div>
<button class="iconbtn wrap-toggle" id="wrap-toggle" type="button" title="Toggle line wrap" aria-label="Toggle line wrap" aria-pressed="false">wrap</button>
<a class="iconbtn" href="/raw/{{.ID}}">raw</a>
<a class="iconbtn" href="#" id="copy-btn" onclick="copyContent(this); return false;">copy</a>
{{if .DeletionToken}}<a class="iconbtn danger" href="#" onclick="redeem('{{.DeletionToken}}'); return false;">delete</a>{{end}}
@@ -80,5 +81,24 @@ function redeem(token) {
fetch('/api/pastes/{{.ID}}/redeem?token=' + encodeURIComponent(token), {method: 'DELETE'})
.then(r => { if (r.ok) location.href = '/history'; else alert('delete failed'); });
}
// #130: line wrap toggle, shared preference with the editor (palette-wrap)
(function () {
var el = document.getElementById('codebody');
var btn = document.getElementById('wrap-toggle');
function apply(on) {
el.classList.toggle('wrap', on);
btn.setAttribute('aria-pressed', on ? 'true' : 'false');
}
var on = false;
try { on = localStorage.getItem('palette-wrap') === 'true'; } catch (e) {}
apply(on);
btn.addEventListener('click', function () {
on = !on;
try { localStorage.setItem('palette-wrap', on ? 'true' : 'false'); } catch (e) {}
apply(on);
});
document.addEventListener('palette-wrapchange', function (e) { apply(e.detail); });
})();
</script>
{{template "foot" .}}
+11
View File
@@ -13,6 +13,8 @@
<svg class="icon-moon" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round" aria-hidden="true"><path d="M21 12.79A9 9 0 1 1 11.21 3 7 7 0 0 0 21 12.79z"/></svg>
<span>Dark mode</span>
</button>
<h3>Line wrap</h3>
<label class="toggle"><input type="checkbox" id="settings-wrap-toggle"> Wrap lines in the editor and paste view</label>
<p class="admin-link-row"><a class="admin-link" href="/admin">Admin</a></p>
</div>
</div>
@@ -95,6 +97,15 @@
if (btns.length) btns[0].click(); else document.dispatchEvent(new CustomEvent('palette-darkchange'));
});
document.addEventListener('palette-darkchange', sync);
// #130: line wrap setting shares the palette-wrap preference with the
// editor and paste view toggles.
var wt = document.getElementById('settings-wrap-toggle');
try { wt.checked = localStorage.getItem('palette-wrap') === 'true'; } catch (e) {}
wt.addEventListener('change', function () {
var on = wt.checked;
try { localStorage.setItem('palette-wrap', on ? 'true' : 'false'); } catch (e) {}
document.dispatchEvent(new CustomEvent('palette-wrapchange', { detail: on }));
});
})();
</script>
{{template "foot" .}}