Using CSS and JS function defined in Julia module for Pluto

I am creating a Julia package PlutoXXX.jl with some CSS and JS code.

I want when checking a checkbox inside the Pluto notebook to activate the CSS and calling the JS function defined inside my module to activate a mode similar to the Pluto presentation mode.

Before using the module form, I was calling all that directly with something like

using HypertextLiteral
# ╔═╡ 67847c64-df3e-40b2-b9d0-10d1d14ebe71
css_code = read("pathtomyfile/always.css", String)
# ╔═╡ 38535edf-6cb2-478d-823d-6754fa8c89f3
# somehow LocalRessource do no work but this does
@htl("""
<style>
$(css_code)
</style>
""")

and for the JS

# ╔═╡ 1363008d-1a2a-479b-a3cf-1b2fdfab86e6
# # this does work but not @htl ...
PlutoUI.LocalResource("pathtomyfile/functions.js")
@bind mode html"""
<input id="activate_mode" type="checkbox" style="display:none;">
<button onclick="activate_mode.click()">Activate mode Mode</button>
"""

Now I want to put that inside a module PlutoXXX.jl to just have to call

# something like that
using PlutoXXX
@bind activate_mode CheckBox()
PlutoXXX.mode(activate_mode)
  1. Right now the copying what I was doing with the CSS seems to work.
  2. But for the JS just copying PlutoUI.LocalResource("pathtomyfile/functions.js") does not work and does not seem to be link to that activate_mode checkbox.
  3. Any idea how to do that properly?

I must admit I don’t know much about JS and HTML and used some LLM to help me with that.

function mode()
    css_code = read("../css/always.css", String)

    return @htl("""
     <style>
     $(css_code)
     </style>
	 $(PlutoUI.LocalResource("../js/functions.js"))
     """)
end

function button_mode()
    return html"""
    <input id="toggle_input" type="checkbox">
    <button onclick="toggle_input.click()">⧉ Mode</button>
    """
end

with in the notebook

using PlutoXXX
button_mode()

does what I want. The new CSS is displayed only in “mode” with in the JS something

document.body.classList.add("mode");

For now, it seems enough but I am sure there are so many ways to improve…

Hey!

It’s a bit hard to say without seeing what the JS and CSS code is. CSS code you can always “turn on and off” by adding/removing a stylesheet, but JS is not so obvious.

I would use JavaScript to add and remove the style element to the page. Like so:

<div>
<label>
	<input type=checkbox>
	<strong>Enable style</strong>
</label>

<script>
// Create <style> element with my CSS
const style_contents = $(style_contents)
const style = document.createElement("style")
style.textContent = style_contents

// The checkbox
const input = currentScript.parentElement.querySelector("input")
const update = () => {
	if(input.checked) {
		document.head.appendChild(style)
	} else {
		style.remove()
	}
}
input.addEventListener("change", update)
</script>

</div>

I’m not sure about adding/removing the JS. I think I would always add it, and use a simple if to control functionality with the checkbox.

These techniques are described in the “Advanced” section of the Pluto docs, e.g. JavaScript API — Pluto.jl


PS:

This UI element is better served with the <label> element.