From 955211fe146233302424d2b0b188f7a8e2407749 Mon Sep 17 00:00:00 2001 From: shaoying Date: Tue, 10 Dec 2019 01:47:51 +0800 Subject: [PATCH] add pane --- chart.js | 21 ---------- core.js | 8 ++++ frame.js | 79 +++++++++++++++++++++++++++++++------ page.js | 15 +++++++ page/chat.js | 63 +++++++++++++++++++++++++++++ pane/action.js | 57 ++++++++++++++++++++++++++ pane/carte.js | 54 +++++++++++++++++++++++++ pane/toast.js | 55 ++++++++++++++++++++++++++ inner.js => plugin/inner.js | 0 input.js => plugin/input.js | 0 state.js => plugin/state.js | 0 table.js => plugin/table.js | 0 proto.js | 46 +++++++++++++++++---- 13 files changed, 357 insertions(+), 41 deletions(-) delete mode 100644 chart.js create mode 100644 page/chat.js create mode 100644 pane/action.js create mode 100644 pane/carte.js create mode 100644 pane/toast.js rename inner.js => plugin/inner.js (100%) rename input.js => plugin/input.js (100%) rename state.js => plugin/state.js (100%) rename table.js => plugin/table.js (100%) diff --git a/chart.js b/chart.js deleted file mode 100644 index b7834147..00000000 --- a/chart.js +++ /dev/null @@ -1,21 +0,0 @@ -Volcanos("onimport", { - init: function(can, msg, cb, target, option) { - target.innerHTML = msg.result.join("") - }, -}) -Volcanos("onaction", { - copy: function(event, can, msg, cb, target, option) { - can.user.alert("hello world") - }, -}) -Volcanos("onchoice", { - list: ["copy", "复制", "下载"], - copy: function(event, can, msg, cb, target, option) { - can.user.alert("hello world") - }, -}) -Volcanos("ondetail", { - list: ["复制", "下载"], - copy: function(event, can, msg, cb, target, option) { - }, -}) diff --git a/core.js b/core.js index 689ac706..97f2f2c6 100644 --- a/core.js +++ b/core.js @@ -20,4 +20,12 @@ Volcanos("core", {help: "核心模块", } return list; }), + Next: shy("迭代器", function(obj, cb, cbs) {obj = typeof obj == "string"? [obj]: (obj || []) + function next(list, cb) { + list && list.length > 0? typeof cb == "function" && cb(list[0], function() { + list.length > 0 && next(list.slice(1), cb) + }): typeof cbs == "function" && cbs() + } + next(obj, cb) + }), }) diff --git a/frame.js b/frame.js index bc91d50b..ce65aabb 100644 --- a/frame.js +++ b/frame.js @@ -1,5 +1,56 @@ var can = Volcanos("chat", { - Plugin: shy("构造插件", function(can, meta, run, field) { + Page: shy("构造网页", function(can, name, list, cb, target) { + var page = Volcanos(name, {type: "local", + Plugin: can.Plugin, + Inputs: can.Inputs, + Output: can.Output, + run: function(event, option, cmds, cb) { + ctx.Run(event, option, cmds, cb) + }, + }, ["core", "page", "user", "page/"+name], function(page) { + can.core.Next(list, function(item, cb) { + page[item] = can.Pane(page, item, cb, can.page.Select(can, target, "fieldset."+item)[0] || + can.page.AppendField(can, target, item+" dialog")) + }, function() {typeof cb == "function" && cb(page)}) + }) + return page + }), + Pane: shy("构造面板", function(can, name, cb, field) { + var option = field.querySelector("form.option"); + var action = field.querySelector("div.action"); + var output = field.querySelector("div.output"); + + var river = "", storm = ""; + var pane = Volcanos(name, {type: "local", + Save: function(name, output) {pane.Cache(name, output, "hi")}, + Load: function(name, output) {pane.Cache(name, output)}, + + Inputs: can.Inputs, + Output: can.Output, + Plugin: function(item, type, index) {var name = item.name; + pane[item.name] = can.Plugin(pane, item, type, function(event, cmds, cbs) { + pane.run(event, [item.river, item.storm, item.action].concat(cmds), cbs) + }, can.page.AppendField(can, output, "item "+item.group+" "+item.name, item)) + }, + Show: function(river, storm) { + if (river && storm && field.Pane.Load(river+"."+storm, output)) {return} + + pane.run(event, [river, storm], function(msg) { + pane.onimport.init(pane, msg, output) + }) + }, + run: function(event, cmds, cb) {var msg = pane.Event(event) + can.page.Select(can, action, "input", function(item, index) { + msg.Option(item.name, item.value) + }) + can.run(event, option.dataset, cmds, cb) + }, + }, ["core", "page", "user", "pane/"+name], function(pane) { + typeof cb == "function" && cb(pane) + }) + return pane.target = field, field.Pane = pane + }), + Plugin: shy("构造插件", function(can, meta, type, run, field) { var option = field.querySelector("form.option"); var action = field.querySelector("div.action"); var output = field.querySelector("div.output"); @@ -9,11 +60,13 @@ var can = Volcanos("chat", { var name = meta.name, args = meta.args || []; var feature = JSON.parse(meta.feature||'{}'); var plugin = Volcanos(name, {type: "local", + Inputs: can.Inputs, + Output: can.Output, Append: function(item, cb) {item = item || {type: "text", name: "", className: "args temp"}; var name = item.name || item.value || "args"+plugin.page.Select(can, option, "input.args.temp").length; var count = plugin.page.Select(can, option, ".args").length, value = ""; args && count < args.length && (value = args[count] || item.value || ""); - plugin[name] = can.Inputs(plugin, item, name, value, cb, option); + plugin[name] = can.Inputs(plugin, item, "input", name, value, cb, option); }, Select: function(event, target, focus) { can.plugin = field, can.input = target || option.querySelectorAll("input")[1]; @@ -53,17 +106,12 @@ var can = Volcanos("chat", { Show: function(type, msg, cb) {msg._plugin_name = name; return plugin[type] = can.Output(plugin, type, msg, cb, output, option) }, - }, ["core", "page", "user", "state"], function(plugin) { - function next(list, cb) { - list && list.length > 0 && cb(list[0], function() { - list.length > 0 && next(list.slice(1), cb) - }) - } - next(JSON.parse(meta.inputs||"[]"), plugin.Append) + }, ["core", "page", "user", "plugin/"+type], function(plugin) { + can.core.Next(JSON.parse(meta.inputs||"[]"), plugin.Append) }) return plugin.target = field, field.Plugin = plugin }), - Inputs: shy("构造控件", function(can, item, name, value, cb, option) { + Inputs: shy("构造控件", function(can, item, type, name, value, cb, option) { var input = Volcanos(name, {type: "local", item: item, Select: function(event) {can.Select(event, input.target, true)}, Import: function(event, value, key, index) {input.target.value = value; @@ -73,7 +121,7 @@ var can = Volcanos("chat", { (input[item.cb] || can[item.cb] || can.Check)(event, event.target, cb); }, - }, ["core", "page", "user", "input"], function(input) {typeof cb == "function" && cb(); + }, ["core", "page", "user", "plugin/"+type], function(input) {typeof cb == "function" && cb(); var target = input.onimport.init(input, item, name, value, option); input.target = target, target.Input = input; }) @@ -85,10 +133,15 @@ var can = Volcanos("chat", { run: function(event, cmd, cb, silent) { (output[cmd[1]] || can[cmd[1]] || can.Run)(event, cmd, cb, silent); }, - }, ["core", "page", "user", type], function(output) { + }, ["core", "page", "user", "plugin/"+type], function(output) { output.onimport.init(output, msg, cb, target, option); }, msg) return output.target = target, target.Output = output }), -}, ["base", "core", "misc", "page", "user", "state", "input", "table"], function(can) {}) +}, ["base", "core", "misc", "page", "user", + "plugin/state", "plugin/input", "plugin/table"], function(can) { + // can.Page(can, Config.main, Config.list, document.body) + can.user.carte = page.carte.Pane.Show; + can.user.toast = page.toast.Pane.Show; +}) diff --git a/page.js b/page.js index 81e7dc19..baa2684e 100644 --- a/page.js +++ b/page.js @@ -67,8 +67,14 @@ Volcanos("page", {help: "网页模块", type = list[1] || "div" data.innerHTML = list[2] || data.innerHTML || "" name = name || list[3] || "" + + } else if (item.text) {var list = can.core.List(item.text); + data.innerHTML = list[0] || data.innerHTML || "" + type = list[1] || "span" + list.length > 2 && (data.className = list[2]) } + // 创建节点 name = name || data.className || type; var node = can.page.Create(can, type, data); @@ -82,6 +88,15 @@ Volcanos("page", {help: "网页模块", return target.innerHTML = "", can.page.Append(can, target, key, value) }), + AppendField: shy("添加插件", function(can, target, type, item) { + var field = can.page.Append(can, target, [{view: [type, "fieldset"], list: [ + {text: [item.name+item.help, "legend"]}, + {view: ["option", "form"], list: [{type: "input", style: {display: "none"}}]}, + {view: ["action"]}, + {view: ["output"]}, + ]}]).first; + return field; + }), AppendTable: shy("添加表格", function(can, target, msg, list) { var table = can.page.Append(can, target, "table"); var tr = can.page.Append(can, table, "tr"); diff --git a/page/chat.js b/page/chat.js new file mode 100644 index 00000000..2ace0898 --- /dev/null +++ b/page/chat.js @@ -0,0 +1,63 @@ +Volcanos("onimport", {help: "导入数据", list: [], + init: function(can, msg, cb, output, option) {output.innerHTML = ""; + output.innerHTML = msg.Result() + output.onclick = function(event) { + switch (event.target.tagName) { + case "text": + alert(event.target.innerHTML) + break + case "rect": + break + } + } + }, +}) +Volcanos("onaction", {help: "组件交互", list: [], +}) +Volcanos("onchoice", {help: "组件菜单", list: ["返回", "清空", "复制", "下载", "表格", "绘图", "媒体"], + "返回": function(event, can, msg, value, target) { + can.run(event, ["", "Last"]) + }, + "清空": function(event, can, msg, value, target) { + can.target.innerHTML = ""; + }, + "复制": function(event, can, msg, value, target) { + var list = can.onexport.Format(can, msg, "data"); + can.user.toast(can.page.CopyText(can, list[2]), "复制成功") + }, + "下载": function(event, can, msg, value, target) { + var list = can.onexport.Format(can, msg, msg._plugin_name||"data"); + can.page.Download(can, list[0]+list[1], list[2]); + }, +}) +Volcanos("ondetail", {help: "组件详情", list: ["选择", "修改", "删除", "复制", "下载"], + "选择": "select", + "删除": "delete", + "修改": function(event, can, msg, value, index, key, td) { + var text = td.innerHTML; + can.page.Appends(can, td, [{type: "input", style: {width: td.clientWidth+"px"}, data: {onkeydown: function(event) { + if (event.key != "Enter") {return} + can.run(event, [index, "modify", key == "value" && msg.key? msg[key][index]: key, event.target.value,], function(msg) { + td.innerHTML = event.target.value; + can.user.toast("修改成功") + }, true) + }}}]) + }, + "复制": function(event, can, msg, value, index, key, target) { + can.user.toast(can.page.CopyText(can, target.innerHTML), "复制成功") + }, + "下载": function(event, can, msg, value, index, key, target) { + can.page.Download(can, key, target.innerHTML); + }, +}) +Volcanos("onexport", {help: "导出数据", list: [], + Format: function(can, msg, name) { + var ext = ".csv", txt = can.page.Select(can, can.target, "tr", function(tr) { + return can.page.Select(can, tr, "td,th", function(td) {return td.innerText}).join(",") + }).join("\n"); + + !txt && (ext = ".txt", txt = msg.result && msg.result.join("") || ""); + return [name, ext, txt] + }, +}) + diff --git a/pane/action.js b/pane/action.js new file mode 100644 index 00000000..bea1b5bf --- /dev/null +++ b/pane/action.js @@ -0,0 +1,57 @@ +Volcanos("onimport", {help: "导入数据", list: [], + init: function(can, msg, output) {output.innerHTML = ""; + msg.Table(function(item, index) { + can.Plugin(item, "state", index) + }) + }, +}) +Volcanos("onaction", {help: "组件交互", list: [], +}) +Volcanos("onchoice", {help: "组件菜单", list: ["返回", "清空", "复制", "下载", "表格", "绘图", "媒体"], + "返回": function(event, can, msg, value, target) { + can.run(event, ["", "Last"]) + }, + "清空": function(event, can, msg, value, target) { + can.target.innerHTML = ""; + }, + "复制": function(event, can, msg, value, target) { + var list = can.onexport.Format(can, msg, "data"); + can.user.toast(can.page.CopyText(can, list[2]), "复制成功") + }, + "下载": function(event, can, msg, value, target) { + var list = can.onexport.Format(can, msg, msg._plugin_name||"data"); + can.page.Download(can, list[0]+list[1], list[2]); + }, +}) +Volcanos("ondetail", {help: "组件详情", list: ["选择", "修改", "删除", "复制", "下载"], + "选择": "select", + "删除": "delete", + "修改": function(event, can, msg, value, index, key, td) { + var text = td.innerHTML; + can.page.Appends(can, td, [{type: "input", style: {width: td.clientWidth+"px"}, data: {onkeydown: function(event) { + if (event.key != "Enter") {return} + can.run(event, [index, "modify", key == "value" && msg.key? msg[key][index]: key, event.target.value,], function(msg) { + td.innerHTML = event.target.value; + can.user.toast("修改成功") + }, true) + }}}]) + }, + "复制": function(event, can, msg, value, index, key, target) { + can.user.toast(can.page.CopyText(can, target.innerHTML), "复制成功") + }, + "下载": function(event, can, msg, value, index, key, target) { + can.page.Download(can, key, target.innerHTML); + }, +}) +Volcanos("onexport", {help: "导出数据", list: [], + Format: function(can, msg, name) { + var ext = ".csv", txt = can.page.Select(can, can.target, "tr", function(tr) { + return can.page.Select(can, tr, "td,th", function(td) {return td.innerText}).join(",") + }).join("\n"); + + !txt && (ext = ".txt", txt = msg.result && msg.result.join("") || ""); + return [name, ext, txt] + }, +}) + + diff --git a/pane/carte.js b/pane/carte.js new file mode 100644 index 00000000..39963642 --- /dev/null +++ b/pane/carte.js @@ -0,0 +1,54 @@ +Volcanos("onimport", {help: "导入数据", list: [], + init: function(can, field, option, action, output) {output.innerHTML = ""; + }, +}) +Volcanos("onaction", {help: "组件交互", list: [], +}) +Volcanos("onchoice", {help: "组件菜单", list: ["返回", "清空", "复制", "下载", "表格", "绘图", "媒体"], + "返回": function(event, can, msg, value, target) { + can.run(event, ["", "Last"]) + }, + "清空": function(event, can, msg, value, target) { + can.target.innerHTML = ""; + }, + "复制": function(event, can, msg, value, target) { + var list = can.onexport.Format(can, msg, "data"); + can.user.toast(can.page.CopyText(can, list[2]), "复制成功") + }, + "下载": function(event, can, msg, value, target) { + var list = can.onexport.Format(can, msg, msg._plugin_name||"data"); + can.page.Download(can, list[0]+list[1], list[2]); + }, +}) +Volcanos("ondetail", {help: "组件详情", list: ["选择", "修改", "删除", "复制", "下载"], + "选择": "select", + "删除": "delete", + "修改": function(event, can, msg, value, index, key, td) { + var text = td.innerHTML; + can.page.Appends(can, td, [{type: "input", style: {width: td.clientWidth+"px"}, data: {onkeydown: function(event) { + if (event.key != "Enter") {return} + can.run(event, [index, "modify", key == "value" && msg.key? msg[key][index]: key, event.target.value,], function(msg) { + td.innerHTML = event.target.value; + can.user.toast("修改成功") + }, true) + }}}]) + }, + "复制": function(event, can, msg, value, index, key, target) { + can.user.toast(can.page.CopyText(can, target.innerHTML), "复制成功") + }, + "下载": function(event, can, msg, value, index, key, target) { + can.page.Download(can, key, target.innerHTML); + }, +}) +Volcanos("onexport", {help: "导出数据", list: [], + Format: function(can, msg, name) { + var ext = ".csv", txt = can.page.Select(can, can.target, "tr", function(tr) { + return can.page.Select(can, tr, "td,th", function(td) {return td.innerText}).join(",") + }).join("\n"); + + !txt && (ext = ".txt", txt = msg.result && msg.result.join("") || ""); + return [name, ext, txt] + }, +}) + + diff --git a/pane/toast.js b/pane/toast.js new file mode 100644 index 00000000..082ae1ad --- /dev/null +++ b/pane/toast.js @@ -0,0 +1,55 @@ +Volcanos("onimport", {help: "导入数据", list: [], + init: function(can, field, option, action, output) {output.innerHTML = ""; + }, + show: function(can, field, option, action, output) {output.innerHTML = ""; + }, +}) +Volcanos("onaction", {help: "组件交互", list: [], +}) +Volcanos("onchoice", {help: "组件菜单", list: ["返回", "清空", "复制", "下载", "表格", "绘图", "媒体"], + "返回": function(event, can, msg, value, target) { + can.run(event, ["", "Last"]) + }, + "清空": function(event, can, msg, value, target) { + can.target.innerHTML = ""; + }, + "复制": function(event, can, msg, value, target) { + var list = can.onexport.Format(can, msg, "data"); + can.user.toast(can.page.CopyText(can, list[2]), "复制成功") + }, + "下载": function(event, can, msg, value, target) { + var list = can.onexport.Format(can, msg, msg._plugin_name||"data"); + can.page.Download(can, list[0]+list[1], list[2]); + }, +}) +Volcanos("ondetail", {help: "组件详情", list: ["选择", "修改", "删除", "复制", "下载"], + "选择": "select", + "删除": "delete", + "修改": function(event, can, msg, value, index, key, td) { + var text = td.innerHTML; + can.page.Appends(can, td, [{type: "input", style: {width: td.clientWidth+"px"}, data: {onkeydown: function(event) { + if (event.key != "Enter") {return} + can.run(event, [index, "modify", key == "value" && msg.key? msg[key][index]: key, event.target.value,], function(msg) { + td.innerHTML = event.target.value; + can.user.toast("修改成功") + }, true) + }}}]) + }, + "复制": function(event, can, msg, value, index, key, target) { + can.user.toast(can.page.CopyText(can, target.innerHTML), "复制成功") + }, + "下载": function(event, can, msg, value, index, key, target) { + can.page.Download(can, key, target.innerHTML); + }, +}) +Volcanos("onexport", {help: "导出数据", list: [], + Format: function(can, msg, name) { + var ext = ".csv", txt = can.page.Select(can, can.target, "tr", function(tr) { + return can.page.Select(can, tr, "td,th", function(td) {return td.innerText}).join(",") + }).join("\n"); + + !txt && (ext = ".txt", txt = msg.result && msg.result.join("") || ""); + return [name, ext, txt] + }, +}) + diff --git a/inner.js b/plugin/inner.js similarity index 100% rename from inner.js rename to plugin/inner.js diff --git a/input.js b/plugin/input.js similarity index 100% rename from input.js rename to plugin/input.js diff --git a/state.js b/plugin/state.js similarity index 100% rename from state.js rename to plugin/state.js diff --git a/table.js b/plugin/table.js similarity index 100% rename from table.js rename to plugin/table.js diff --git a/proto.js b/proto.js index 70f42d5e..c422efd8 100644 --- a/proto.js +++ b/proto.js @@ -20,7 +20,7 @@ function Volcanos(name, can, libs, cb, msg) { // 封装模块 }; // 定义原型 - var id = 1, conf = {}, conf_cb = {}, sync = {}; + var id = 1, conf = {}, conf_cb = {}, sync = {}, cache = {}; can[name] || list.push({name: name, can: can, create_time: new Date()}) && (can.__proto__ = { create_time: new Date(), name: name, path: "", help: "插件模块", load: function(name) { if (meta.cache[name]) {var cache = meta.cache[name]; @@ -69,12 +69,27 @@ function Volcanos(name, can, libs, cb, msg) { // 封装模块 return loop(0) }), Event: shy("触发器", function(event, msg, proto) { - msg = event.msg = msg || event.msg || {}, msg.__proto__ = proto || msg.__proto__ || { + msg = event.msg = msg || event.msg || {}, msg.__proto__ = proto || { Log: shy("输出日志", function() {console.log(arguments)}), + Option: function(key, val) { + if (val == undefined) {return msg[key]} + msg.option = msg.option || [] + can.core.List(msg.option, function(k) { + if (k == key) {return k} + }).length > 0 || msg.option.push(key) + msg[key] = can.core.List(arguments).slice(1) + }, Echo: shy("输出响应", function(res) {msg.result = msg.result || [] for (var i = 0; i < arguments.length; i++) {msg.result.push(arguments[i])} return msg; }), + Copy: function(res) { + res.result && (msg.result = res.result) + res.append && (msg.append = res.append) && res.append.forEach(function(item) { + res[item] && (msg[item] = res[item]) + }) + return msg + }, Table: shy("遍历数据", function(cb) {if (!msg.append || !msg.append.length || !msg[msg.append[0]]) {return} var max = "", len = 0; can.core.List(msg.append, function(key, index) { @@ -104,10 +119,27 @@ function Volcanos(name, can, libs, cb, msg) { // 封装模块 var ui = can.page.Append(can, target, item? list: [{view: ["item"+style], data: {id: "item"+can.ID(), draggable: false}, list:list}]) return ui["item"+style].Meta = text, ui }), - Cache: shy("缓存器", function(name, data) { - if (data == undefined) { - return + Cache: shy("缓存器", function(name, output, data) { + if (data) { + var temp = document.createDocumentFragment() + while (output.childNodes.length>0) { + var item = output.childNodes[0] + item.parentNode.removeChild(item) + temp.appendChild(item) + } + cache[name] = {node: temp, data: data} + return name } + + var list = cache[name]; + if (!list) {return} + while (list.node.childNodes.length>0) { + var item = list.node.childNodes[0] + item.parentNode.removeChild(item) + output.appendChild(item) + } + delete(cache[name]) + return list.data }), Story: shy("存储器", function(type, meta, list) { }), @@ -118,9 +150,9 @@ function Volcanos(name, can, libs, cb, msg) { // 封装模块 libs && libs.length > 1? Volcanos(name, can, libs.slice(1), cb): typeof cb == "function" && setTimeout(function() {cb(can); if (!can.target) {return} - can.core.Item(can.onaction, function(key, cb) {can.target[key] = function(event) { + can.core.Item(can.onaction, function(key, cb) {key.indexOf("on") == 0 && (can.target[key] = function(event) { cb(event, can); - }}); + })}); can.target.oncontextmenu = function(event) { can.user.carte(event, shy("", can.onchoice, can.onchoice.list, function(event, value, meta) {var cb = meta[value];