diff --git a/package.json b/package.json index 3f4b1d4..085ccb9 100755 --- a/package.json +++ b/package.json @@ -1,6 +1,6 @@ { "name": "wljs-editor", - "version": "1.1.8", + "version": "1.1.9", "description": "WLJS Code editor", "scripts": { "build": "node --max-old-space-size=8192 ./node_modules/.bin/rollup --config rollup.config.mjs", @@ -38,7 +38,8 @@ "src/Notifications.wl", "src/Autocomplete.wl", "src/ContextMenu.wl", - "src/FileUpload.wl" + "src/FileUpload.wl", + "src/FrontendRuntime.wl" ], "kernel": [ "src/FrontendObject.wl", @@ -56,7 +57,8 @@ "src/MetaMarkersKernel.wl", "src/AutocompleteKernel.wl", "src/RasterizeKernel.wl", - "src/System.wl" + "src/System.wl", + "src/FrontendRuntimeKernel.wl" ], "styles": "src/styles.css", "priority": -10, diff --git a/src/EditorKernel.wl b/src/EditorKernel.wl index 5427c0a..95d99de 100644 --- a/src/EditorKernel.wl +++ b/src/EditorKernel.wl @@ -11,7 +11,6 @@ CellView::usage = "A view component for an input or output cell CellView[_String InputEditor::usage = "InputEditor[string_] _EventObject" - Begin["`Private`"] diff --git a/src/FrontendRuntime.wl b/src/FrontendRuntime.wl new file mode 100644 index 0000000..549089c --- /dev/null +++ b/src/FrontendRuntime.wl @@ -0,0 +1,65 @@ + +BeginPackage["Notebook`Editor`FrontEndRuntime`", { + "JerryI`Misc`Events`", + "JerryI`Misc`Events`Promise`", + "JerryI`Misc`WLJS`Transport`", + "JerryI`Notebook`Kernel`", + "JerryI`Notebook`", + "JerryI`Notebook`AppExtensions`", + "Notebook`Editor`", + "JerryI`WLX`WebUI`" +}] + + + +Begin["`Private`"] + +frontEndRuntime = <| + {"Modules", "js"} -> {}, + {"Modules", "css"} -> {} +|> + +rebuild := ( + compiledString = { + StringRiffle[StringJoin[""] &/@ frontEndRuntime[{"Modules", "js"}] ], + StringRiffle[StringJoin[""] &/@ frontEndRuntime[{"Modules", "css"}] ] + } // StringRiffle; +); + +rebuild; + +component[__] := compiledString + +AppExtensions`TemplateInjection["AppHead"] = component + +injectInRuntime[{"Modules", "js"}, data_List] := With[{notebooks = Values[Notebook`HashMap]}, + WebUISubmit[ Global`UIHeadInject["js", data ], #["Socket"] ] &/@ notebooks; +] + +EventHandler[NotebookEditorChannel // EventClone, + { + "RequestRuntimeExtensions" -> Function[assoc, + With[{result = frontEndRuntime, kernel = Kernel`HashMap[assoc["Kernel"] ], promise = assoc["Promise"]}, + Kernel`Async[kernel, EventFire[promise, Resolve, result] ]; + ] + ], + + "UpdateRuntimeExtensions" -> Function[assoc, + With[{promise = assoc["Promise"], data = assoc["Data"], kernel = Kernel`HashMap[assoc["Kernel"] ], key = assoc["Key"]}, + + With[{new = Complement[data, frontEndRuntime[key] // DeleteDuplicates ] // DeleteDuplicates}, + frontEndRuntime[key] = data // DeleteDuplicates; + injectInRuntime[key, new]; + ]; + + rebuild; + Pause[0.3]; + Kernel`Async[kernel, EventFire[promise, Resolve, True] ]; + ] + ] + + } +] + +End[] +EndPackage[] \ No newline at end of file diff --git a/src/FrontendRuntimeKernel.wl b/src/FrontendRuntimeKernel.wl new file mode 100644 index 0000000..7b3359d --- /dev/null +++ b/src/FrontendRuntimeKernel.wl @@ -0,0 +1,37 @@ + + +BeginPackage["Notebook`Editor`Kernel`FrontEndRuntime`", { + "JerryI`Misc`Events`", + "JerryI`Misc`Events`Promise`" +}] + +FrontEndRuntime::usage = "FrontEndRuntime[] gives a list of properties possible to extend during the runtime" + +Begin["`Internal`"] + +FrontEndRuntime[any_List] := With[{r = FrontEndRuntime[]}, + If[FailureQ[r], + $Failed + , + r[any] + ] +] + +FrontEndRuntime[] := With[{promise = Promise[]}, + EventFire[Internal`Kernel`CommunicationChannel, "RequestRuntimeExtensions", <|"Promise" -> (promise), "Kernel"->Internal`Kernel`Hash|>]; + With[{r = (promise // WaitAll)}, + r + ] + ] + +FrontEndRuntime /: Set[FrontEndRuntime[key_], data_List] := With[{promise = Promise[]}, + With[{ + list = Select[data /. {File[path_String] :> Import[path, "Text"]}, StringQ] + }, + EventFire[Internal`Kernel`CommunicationChannel, "UpdateRuntimeExtensions", <|"Promise" -> (promise), "Kernel"->Internal`Kernel`Hash, "Data"->list, "Key"->key|>]; + promise // WaitAll + ] +] + +End[] +EndPackage[] diff --git a/src/misc.js b/src/misc.js index 5f829e7..7a7a8cf 100644 --- a/src/misc.js +++ b/src/misc.js @@ -67,6 +67,32 @@ core['Notebook`Editor`Rasterize`Internal`OverlayView'].Create = async (args, env }, 1000); } +core.UIHeadInject = async (args, env) => { + const type = await interpretate(args[0], env); + await core.UIHeadInject[type](args.slice(1), env); +} + +core.UIHeadInject.js = async (args, env) => { + const data = await interpretate(args[0], env); + + data.forEach((el) => { + const script = document.createElement('script'); + script.type = "module"; + script.textContent = el; + document.head.appendChild(script); + }) +} + +core.UIHeadInject.css = async (args, env) => { + const data = await interpretate(args[0], env); + + data.forEach((el) => { + const style = document.createElement('style'); + style.textContent = el; + document.head.appendChild(style); + }) +} + core.SystemOpen = async (args, env) => { const type = await interpretate(args[1], env); await core.SystemOpen[type](args[0], env);