diff options
| author | erdgeist <erdgeist@erdgeist.org> | 2026-07-14 04:10:01 +0200 |
|---|---|---|
| committer | erdgeist <erdgeist@erdgeist.org> | 2026-07-14 04:10:01 +0200 |
| commit | e0f2394fd0816ef03bf4b928ab9fa5a18c32ffda (patch) | |
| tree | 0c346c5167c06f1bd4be03c8fd4e358215ed2fbe /public/javascripts/admin_interface.js | |
| parent | 88ebeaac7fcf140cbab489e841bf9c197f84c4ea (diff) | |
Add a toggleable live preview panel to both editors
Hidden by default, shares horizontal space with the body editor once
opened rather than a separate section, and only requests the iframe's
src on first toggle -- no preview traffic at all until someone
actually wants to see it. Refreshes automatically on every successful
autosave; a separate force-render button re-attempts a save-and-
refresh cycle immediately, for when the normal 7-second cycle has
been interrupted (a lock-lost error, a transient failure) and waiting
for the next tick isn't good enough.
Diffstat (limited to 'public/javascripts/admin_interface.js')
| -rw-r--r-- | public/javascripts/admin_interface.js | 43 |
1 files changed, 42 insertions, 1 deletions
diff --git a/public/javascripts/admin_interface.js b/public/javascripts/admin_interface.js index e3d4ff1..9da5d28 100644 --- a/public/javascripts/admin_interface.js +++ b/public/javascripts/admin_interface.js | |||
| @@ -67,6 +67,10 @@ $(document).ready(function () { | |||
| 67 | rrule_builder.initialize(); | 67 | rrule_builder.initialize(); |
| 68 | } | 68 | } |
| 69 | 69 | ||
| 70 | if ($("#preview_panel").length != 0) { | ||
| 71 | cccms.preview.initialize(); | ||
| 72 | } | ||
| 73 | |||
| 70 | if ($('#recent_changes_toggle').length != 0) { | 74 | if ($('#recent_changes_toggle').length != 0) { |
| 71 | hide_all(); | 75 | hide_all(); |
| 72 | $('#recent_changes_toggle').attr("class", "selected"); | 76 | $('#recent_changes_toggle').attr("class", "selected"); |
| @@ -165,7 +169,8 @@ cccms = { | |||
| 165 | } | 169 | } |
| 166 | 170 | ||
| 167 | jQuery.fn.submitWithAjax = function(options) { | 171 | jQuery.fn.submitWithAjax = function(options) { |
| 168 | if (page.title_has_changed() || page.abstract_has_changed() || page.body_has_changed()) { | 172 | options = options || {}; |
| 173 | if (options.force || page.title_has_changed() || page.abstract_has_changed() || page.body_has_changed()) { | ||
| 169 | 174 | ||
| 170 | tinymce.triggerSave(); | 175 | tinymce.triggerSave(); |
| 171 | page.cached_title = elements.title.val(); | 176 | page.cached_title = elements.title.val(); |
| @@ -181,6 +186,9 @@ cccms = { | |||
| 181 | type: "POST", | 186 | type: "POST", |
| 182 | url: this.attr("data-autosave-url"), | 187 | url: this.attr("data-autosave-url"), |
| 183 | data: data, | 188 | data: data, |
| 189 | success: function() { | ||
| 190 | cccms.preview.refresh_if_open(); | ||
| 191 | }, | ||
| 184 | error: function(xhr) { | 192 | error: function(xhr) { |
| 185 | if (xhr.status === 423) { | 193 | if (xhr.status === 423) { |
| 186 | clearInterval(cccms.autosave_timer); | 194 | clearInterval(cccms.autosave_timer); |
| @@ -211,6 +219,39 @@ cccms = { | |||
| 211 | $banner.append("."); | 219 | $banner.append("."); |
| 212 | 220 | ||
| 213 | $flash.html($banner); | 221 | $flash.html($banner); |
| 222 | }, | ||
| 223 | |||
| 224 | preview : { | ||
| 225 | is_open : false, | ||
| 226 | |||
| 227 | initialize : function() { | ||
| 228 | var $panel = $('#preview_panel'); | ||
| 229 | var $toggle = $('#preview_toggle'); | ||
| 230 | var $force = $('#preview_force_render'); | ||
| 231 | |||
| 232 | $toggle.on('click', function() { | ||
| 233 | cccms.preview.is_open = !cccms.preview.is_open; | ||
| 234 | $panel.toggle(cccms.preview.is_open); | ||
| 235 | $force.toggle(cccms.preview.is_open); | ||
| 236 | $toggle.attr('aria-pressed', cccms.preview.is_open); | ||
| 237 | if (cccms.preview.is_open) cccms.preview.refresh(); | ||
| 238 | }); | ||
| 239 | |||
| 240 | $force.on('click', function() { | ||
| 241 | $("#page_editor > form").submitWithAjax({ force: true }); | ||
| 242 | }); | ||
| 243 | }, | ||
| 244 | |||
| 245 | refresh : function() { | ||
| 246 | var $iframe = $('#live_preview_iframe'); | ||
| 247 | if ($iframe.length === 0) return; | ||
| 248 | var base = $iframe.data('src'); | ||
| 249 | $iframe.attr('src', base + (base.indexOf('?') === -1 ? '?' : '&') + '_t=' + Date.now()); | ||
| 250 | }, | ||
| 251 | |||
| 252 | refresh_if_open : function() { | ||
| 253 | if (cccms.preview.is_open) cccms.preview.refresh(); | ||
| 254 | } | ||
| 214 | } | 255 | } |
| 215 | } | 256 | } |
| 216 | 257 | ||
