From bec7c312eede5e30d0c4099aabe3529a23f98047 Mon Sep 17 00:00:00 2001 From: Thomas von Deyen Date: Thu, 19 Sep 2024 16:43:33 +0200 Subject: [PATCH] Precompile alchem/preview.js Precompile the preview mode code with Rollup and serve this to the preview window. (cherry picked from commit 4b2ebdfafe19422fb073e34688ae78e7d474d3f5) --- app/assets/builds/alchemy/preview.min.js | 1 + app/assets/config/alchemy_manifest.js | 1 - .../alchemy/alchemy.preview.js.coffee | 97 --------------- app/assets/javascripts/alchemy/preview.js | 1 - app/javascript/preview.js | 117 ++++++++++++++++++ app/views/alchemy/_preview_mode_code.html.erb | 2 +- rollup.config.mjs | 8 ++ 7 files changed, 127 insertions(+), 100 deletions(-) create mode 100644 app/assets/builds/alchemy/preview.min.js delete mode 100644 app/assets/javascripts/alchemy/alchemy.preview.js.coffee delete mode 100644 app/assets/javascripts/alchemy/preview.js create mode 100644 app/javascript/preview.js diff --git a/app/assets/builds/alchemy/preview.min.js b/app/assets/builds/alchemy/preview.min.js new file mode 100644 index 0000000000..78928350a6 --- /dev/null +++ b/app/assets/builds/alchemy/preview.min.js @@ -0,0 +1 @@ +window.Alchemy=Alchemy||{},Object.assign(Alchemy,{ElementSelector:{styles:{reset:{outline:"","outline-offset":"",cursor:""},hover:{outline:"2px dashed #f0b437","outline-offset":"4px",cursor:"pointer"},selected:{outline:"2px dashed #90b9d0","outline-offset":"4px"}},init(){window.addEventListener("message",(e=>{switch(e.data.message){case"Alchemy.blurElements":this.blurElements();break;case"Alchemy.focusElement":this.focusElement(e.data);break;default:console.info("Received unknown message!",e.data)}})),this.elements=Array.from(document.querySelectorAll("[data-alchemy-element]")),this.elements.forEach((e=>{e.addEventListener("mouseover",(()=>{e.classList.contains("selected")||Object.assign(e.style,this.getStyle("hover"))})),e.addEventListener("mouseout",(()=>{e.classList.contains("selected")||Object.assign(e.style,this.getStyle("reset"))})),e.addEventListener("click",(t=>{t.stopPropagation(),t.preventDefault(),this.selectElement(e),this.focusElementEditor(e)}))}))},selectElement(e){this.blurElements(e),e.classList.add("selected"),Object.assign(e.style,this.getStyle("selected")),e.scrollIntoView({behavior:"smooth",block:"start"})},blurElements(e){this.elements.forEach((t=>{t!==e&&(t.classList.remove("selected"),Object.assign(t.style,this.getStyle("reset")))}))},focusElement(e){const t=this.getElement(e.element_id);return t?this.selectElement(t):console.warn("Could not focus element with id",e.element_id)},getElement(e){return this.elements.find((t=>t.dataset.alchemyElement===e.toString()))},focusElementEditor(e){const t=e.dataset.alchemyElement;window.parent.postMessage({message:"Alchemy.focusElementEditor",element_id:t},window.location.origin)},getStyle(e){return"reset"===e?this.styles.reset:this.styles[e]}}}),Alchemy.ElementSelector.init(); diff --git a/app/assets/config/alchemy_manifest.js b/app/assets/config/alchemy_manifest.js index 5e86324b67..53a69424c4 100644 --- a/app/assets/config/alchemy_manifest.js +++ b/app/assets/config/alchemy_manifest.js @@ -1,5 +1,4 @@ //= link alchemy/admin/all.js -//= link alchemy/preview.js //= link_tree ../builds/alchemy/ //= link_tree ../builds/tinymce/ //= link_tree ../images/alchemy/ diff --git a/app/assets/javascripts/alchemy/alchemy.preview.js.coffee b/app/assets/javascripts/alchemy/alchemy.preview.js.coffee deleted file mode 100644 index 07b055a0f3..0000000000 --- a/app/assets/javascripts/alchemy/alchemy.preview.js.coffee +++ /dev/null @@ -1,97 +0,0 @@ -window.Alchemy = Alchemy || {} - -Alchemy.initAlchemyPreviewMode = -> - - # The Alchemy JavaScript Object contains all Functions - Object.assign Alchemy, - - ElementSelector: - - styles: - reset: - outline: "" - "outline-offset": "" - cursor: "" - hover: - outline: "2px dashed #f0b437" - "outline-offset": "4px" - cursor: "pointer" - selected: - outline: "2px dashed #90b9d0" - "outline-offset": "4px" - - init: -> - window.addEventListener "message", (event) => - switch event.data.message - when "Alchemy.blurElements" then @blurElements() - when "Alchemy.focusElement" then @focusElement(event.data) - else console.info("Received unknown message!", event.data) - return - @elements = Array.from document.querySelectorAll("[data-alchemy-element]") - @elements.forEach (element) => - element.addEventListener 'mouseover', => - unless element.classList.contains('selected') - Object.assign element.style, @getStyle('hover') - return - element.addEventListener 'mouseout', => - unless element.classList.contains('selected') - Object.assign element.style, @getStyle('reset') - return - element.addEventListener 'click', (e) => - e.stopPropagation() - e.preventDefault() - @selectElement(element) - @focusElementEditor(element) - return - return - return - - # Mark element in preview frame as selected and scrolls to it. - selectElement: (element) -> - @blurElements(element) - element.classList.add('selected') - Object.assign element.style, @getStyle('selected') - element.scrollIntoView - behavior: 'smooth' - block: 'start' - return - - # Blur all elements in preview frame. - blurElements: (selectedElement) -> - @elements.forEach (element) => - if element != selectedElement - element.classList.remove('selected') - Object.assign element.style, @getStyle('reset') - return - return - - # Focus the element in the Alchemy preview window. - focusElement: (data) -> - element = @getElement(data.element_id) - if element - @selectElement(element) - else - console.warn('Could not focus element with id', data.element_id) - - getElement: (element_id) -> - @elements.find (element) -> - element.dataset.alchemyElement == element_id.toString() - - # Focus the element editor in the Alchemy element window. - focusElementEditor: (element) -> - element_id = element.getAttribute('data-alchemy-element') - window.parent.postMessage - message: 'Alchemy.focusElementEditor' - element_id: element_id - , window.location.origin - return - - getStyle: (state) -> - if state == "reset" - @styles["reset"] - else - @styles[state] - - Alchemy.ElementSelector.init() - -Alchemy.initAlchemyPreviewMode() diff --git a/app/assets/javascripts/alchemy/preview.js b/app/assets/javascripts/alchemy/preview.js deleted file mode 100644 index ea7fb1ab11..0000000000 --- a/app/assets/javascripts/alchemy/preview.js +++ /dev/null @@ -1 +0,0 @@ -//= require alchemy/alchemy.preview diff --git a/app/javascript/preview.js b/app/javascript/preview.js new file mode 100644 index 0000000000..c4277c2b14 --- /dev/null +++ b/app/javascript/preview.js @@ -0,0 +1,117 @@ +window.Alchemy = Alchemy || {} + +Object.assign(Alchemy, { + ElementSelector: { + styles: { + reset: { + outline: "", + "outline-offset": "", + cursor: "" + }, + hover: { + outline: "2px dashed #f0b437", + "outline-offset": "4px", + cursor: "pointer" + }, + selected: { + outline: "2px dashed #90b9d0", + "outline-offset": "4px" + } + }, + + init() { + window.addEventListener("message", (event) => { + switch (event.data.message) { + case "Alchemy.blurElements": + this.blurElements() + break + case "Alchemy.focusElement": + this.focusElement(event.data) + break + default: + console.info("Received unknown message!", event.data) + } + }) + this.elements = Array.from( + document.querySelectorAll("[data-alchemy-element]") + ) + this.elements.forEach((element) => { + element.addEventListener("mouseover", () => { + if (!element.classList.contains("selected")) { + Object.assign(element.style, this.getStyle("hover")) + } + }) + element.addEventListener("mouseout", () => { + if (!element.classList.contains("selected")) { + Object.assign(element.style, this.getStyle("reset")) + } + }) + element.addEventListener("click", (e) => { + e.stopPropagation() + e.preventDefault() + this.selectElement(element) + this.focusElementEditor(element) + }) + }) + }, + + // Mark element in preview frame as selected and scrolls to it. + selectElement(element) { + this.blurElements(element) + element.classList.add("selected") + Object.assign(element.style, this.getStyle("selected")) + element.scrollIntoView({ + behavior: "smooth", + block: "start" + }) + }, + + // Blur all elements in preview frame. + blurElements(selectedElement) { + this.elements.forEach((element) => { + if (element !== selectedElement) { + element.classList.remove("selected") + Object.assign(element.style, this.getStyle("reset")) + } + }) + }, + + // Focus the element in the Alchemy preview window. + focusElement(data) { + const element = this.getElement(data.element_id) + if (element) { + return this.selectElement(element) + } else { + return console.warn("Could not focus element with id", data.element_id) + } + }, + + getElement(element_id) { + return this.elements.find( + (element) => element.dataset.alchemyElement === element_id.toString() + ) + }, + + // Focus the element editor in the Alchemy element window. + focusElementEditor(element) { + const element_id = element.dataset.alchemyElement + window.parent.postMessage( + { + message: "Alchemy.focusElementEditor", + element_id + }, + window.location.origin + ) + }, + + getStyle(state) { + if (state === "reset") { + return this.styles["reset"] + } else { + return this.styles[state] + } + } + } +}) + +Alchemy.ElementSelector.init() diff --git a/app/views/alchemy/_preview_mode_code.html.erb b/app/views/alchemy/_preview_mode_code.html.erb index f61b17cfb5..f8bbf65988 100644 --- a/app/views/alchemy/_preview_mode_code.html.erb +++ b/app/views/alchemy/_preview_mode_code.html.erb @@ -2,5 +2,5 @@ - <%= javascript_include_tag("alchemy/preview") %> + <%= javascript_include_tag("alchemy/preview.min") %> <% end %> diff --git a/rollup.config.mjs b/rollup.config.mjs index d5fe1a4f1a..5e8361d924 100644 --- a/rollup.config.mjs +++ b/rollup.config.mjs @@ -67,5 +67,13 @@ export default [ commonjs(), terser() ] + }, + { + input: "app/javascript/preview.js", + output: { + file: "app/assets/builds/alchemy/preview.min.js" + }, + context: "window", + plugins: [terser()] } ]