import { Que } from "../js/Que.js";
import { graftSolitude } from "..//js/solitude.js";
import { SyslogStmt } from "../js/SyslogStmt.js";
import { LogReceiverReadyMessage } from "./shared/LogReceiverReadyMessage.js";
import { webconfig } from "./WebConfig.js";
window.addEventListener('load', main(document));
function main(document) {
const kernelLogger = window.kernelLogger
kernelLogger.info("main started");
graftSolitude(window);
webconfig(window);
const mysolitude = window.solitude;
mysolitude.apps = {};
Object.assign(mysolitude.apps, window.tmp.solitudeapps);
//アプリケーション毎に初期化操作
initializeSolitudeApps(mysolitude.apps)
Que("li.tab").list().forEach(function (val, index, _list) {
val.addEventListener("click", function () {
selectTab(index);
});
})
const leftMenu = Que("#left-menu").get();
const menuToggle = Que("#menu-toggle").get();
menuToggle.addEventListener("click", function () {
leftMenu.classList.remove("initial")
toggleMenuItem(leftMenu);
Que("#left-menu li span").list().forEach(function (val) {
toggleMenuItem(val);
})
toggleMenuItem(Que("#main").get());
});
// app.js の main 関数内など
mysolitude.message.addListener(LogReceiverReadyMessage.filter((message) => {
// kernelLoggerにログを引き渡すレシーバーを設定
kernelLogger.takeover({
receive: receive,
});
// 溜まっていたログをフラッシュする
kernelLogger.debug("flush !");
kernelLogger.flush();
function receive(msg) {
mysolitude.message.fire({
type: "log",
message: msg
})
}
}));
const b = new SyslogStmt();
kernelLogger.log(b.fac(20).gen("SyslogStmt test2").str);
// 以下、宣言
function toggleMenuItem(element) {
if (element.classList.contains("expanded")) {
element.classList.add("shrinked");
element.classList.remove("expanded");
} else {
element.classList.add("expanded");
element.classList.remove("shrinked");
}
}
function selectTab(index) {
let tab, content;
Que("#main-pane li.tab").list().forEach(function (val) {
val.classList.remove("selected");
if (val.dataset.soloAppId == index) {
tab = val;
}
});
Que("#main-pane div.main-article").list().forEach(function (val) {
val.classList.remove("selected");
if (val.dataset.soloAppId == index) {
content = val;
}
});
tab.classList.add("selected");
content.classList.add("selected");
}
function initializeSolitudeApps(apps) {
const appsProto = {
useMenu: true,
useTab: true,
autorun: false,
};
const appFuncs = [IframeApp, StaticPageApp, BatchApp];
appFuncs.forEach(appFunc => {
appFunc.prototype = appsProto;
});
let app;
let appInstanceID = 0;
for (const [name, conf] of Object.entries(apps)) {
const appType = conf.type || "undef";
switch (appType) {
case "main":
case "undef":
app = null;
//do nothing
break;
case "staticpage":
app = new StaticPageApp(name, conf);
break;
case "iframe":
app = new IframeApp(name, conf);
break;
case "batch":
app = new BatchApp(name, conf);
break;
default:
//something wrong;
break;
}
if (app) {
app.instanceID = ++appInstanceID;
app.load();
kernelLogger.info("loaded ".concat(name, ", instanceID ", app.instanceID));
}
}
//巻き上げを期待しているためclass構文ではない。
function IframeApp(name, conf) {
this.name = name;
this.conf = conf;
this.load = loadApp;
this.template = "#app-type-iframe";
this.callback = iframeCallback;
}
function StaticPageApp(name, conf) {
this.name = name;
this.conf = conf;
this.load = loadApp;
this.template = "#app-type-staticpage";
this.callback = staticpageCallback;
}
function BatchApp(name, conf) {
this.name = name;
this.conf = conf;
this.load = loadBatchApp;
this.template = "#app-type-batch";
this.callback = batchCallback;
}
function loadApp() {
addNewMenu(this.name);
const mount = Que("#left-menu ol");
const app = this;
mount.que("li.init").get().addEventListener("click", function () {
if (isInitialized(app.instanceID)) {
return;
}
addNewTab(app);
addNewContent(app);
kernelLogger.info(app.name + " is initialized");
});
mount.que("li.init").get().classList.remove("init");
}
function isInitialized(appInstanceID) {
//アプリのタブが出ているかでロード済みかを判断
let result = false;
Que("#main-tabs li").list().forEach(elem => {
if (appInstanceID == elem.dataset.soloAppId) {
result = true;
}
});
return result;
}
function loadBatchApp() {
addNewContent(this);
}
function addNewMenu(name) {
const mount = Que("#left-menu ol").get();
let menu = Que("#app-menu").get();
menu = menu.content.cloneNode(true);
const span = Que("span", menu).get();
// template では初期状態はexpanded
if (Que("#left-menu.shrinked").list().length > 0) {
const cls = span.classList;
cls.remove("expanded");
cls.add("shrinked");
}
span.textContent = name;
mount.appendChild(menu);
}
function addNewTab(app) {
const mount = Que("#main-tabs").get();
let tab = Que("#app-tab").get()
tab = tab.content.cloneNode(true);
const li = Que("li", tab).get();
li.textContent = app.name;
li.dataset.soloAppId = app.instanceID;
const index = app.instanceID;
mount.appendChild(tab);
li.addEventListener("click", () => {
selectTab(index);
});
}
function addNewContent(app) {
const appNode = (Que(app.template).get()).content.cloneNode(true);
const base = Que("div.main-article", appNode);
base.get().classList.remove("undefined");
base.get().dataset.soloAppId = app.instanceID;
base.que("div.app-container").get().classList.add(app.name);
app.callback(app, base);
const mount = Que("#app-pane").get();
mount.appendChild(base.get());
}
function iframeCallback(app, base) {
const iframe = Que("div.app-container > iframe", base).get();
iframe.setAttribute("id", app.name);
iframe.setAttribute("title", app.name);
iframe.setAttribute("src", app.conf.src);
}
async function staticpageCallback(app, base) {
const text = await mysolitude.io.fs.read(app.conf.src);
const parser = new DOMParser();
const doc = parser.parseFromString(text, "text/html");
const content = Que("div.app-body", doc).get().cloneNode(true);
Que("div.app-container", base).get().appendChild(content);
//文書内のJavascriptコードを実行する。簡単な実装。
//これだとon.loadイベントとかがキックされなくなってしまう気がする。
const removes = [];
Que("script", content).list().forEach(element => {
const script = document.createElement("script")
script.innerHTML = element.innerHTML;
for (const attr of element.attributes) {
script.setAttribute(attr.name, attr.value);
}
element.before(script)
removes.push(element);
});
for (const script of removes) {
script.remove();
}
}
function batchCallback(app, base) {
const content = document.createElement("script")
content.setAttribute("src", app.conf.src);
Que("div.app-container", base).get().appendChild(content);
}
}
}