From ecf90a81da7beb955de5ee2d6a7818204f62aca9 Mon Sep 17 00:00:00 2001 From: harveyshao Date: Fri, 20 Jan 2023 14:50:58 +0800 Subject: [PATCH] opt log --- frame.js | 21 ++-- index.css | 6 +- lib/misc.js | 81 +++++++++------- lib/user.js | 24 ++--- manifest.json | 17 +--- panel/action.js | 38 +++++++- panel/footer.js | 53 ++++++++-- panel/river.js | 2 +- plugin/input.js | 3 +- plugin/local/chat/iframe.js | 2 +- plugin/local/code/inner.css | 18 ++-- plugin/local/code/inner.js | 64 +++++++------ plugin/local/code/vimer.css | 2 - plugin/local/code/vimer.js | 134 ++++++++++---------------- plugin/local/code/xterm.js | 11 +-- plugin/state.js | 5 +- plugin/table.js | 186 +++++++++++++++++------------------- proto.js | 16 +++- 18 files changed, 360 insertions(+), 323 deletions(-) diff --git a/frame.js b/frame.js index 23b928b2..900ff3db 100644 --- a/frame.js +++ b/frame.js @@ -2,7 +2,7 @@ Volcanos(chat.ONENGINE, {_init: function(can, meta, list, cb, target) { can.user.isMobile && can.require(["https://unpkg.com/vconsole@latest/dist/vconsole.min.js"], function() { return window.VConsole() }) if (!can.user.isMailMaster) { if (can.misc.Search(can, ice.MSG_SESSID)) { can.misc.CookieSessid(can, can.misc.Search(can, ice.MSG_SESSID)); return can.misc.Search(can, ice.MSG_SESSID, "") } - } + } can._path = location.href can.user.title(can.misc.Search(can, chat.TITLE)||can.misc.Search(can, ice.POD)||location.host) can.run = function(event, cmds, cb) { var msg = can.request(event); cmds = cmds||[]; return (can.onengine[cmds[0]]||can.onengine._remote)(event, can, msg, can, cmds, cb) } can.require([can.volcano], null, function(can, key, sub) { can[key] = sub }) @@ -15,7 +15,6 @@ Volcanos(chat.ONENGINE, {_init: function(can, meta, list, cb, target) { }, target) }, function() { can.onlayout._init(can, target), can.onmotion._init(can, target), can.onkeymap._init(can, target) can.onengine.listen(can, chat.ONSEARCH, function(msg, arg) { arg[0] == ctx.COMMAND && can.run(msg, ["can.command"]) }) - can._path = location.href can.onengine.signal(can, chat.ONMAIN, can.request()), can.base.isFunc(cb) && cb(can) }) can.onappend.topic(can, html.DARK), can.onappend.topic(can, html.LIGHT, {panel: "white", plugin: "aliceblue", legend: "lavender", input: "white", output: "white", table: "aliceblue", @@ -126,7 +125,8 @@ Volcanos(chat.ONAPPEND, {_init: function(can, meta, list, cb, target, field) { }, Action: function(key, value) { return can.page.SelectArgs(can, action, key, value)[0] }, Option: function(key, value) { return can.page.SelectArgs(can, option, key, value)[0] }, - Update: function(event, cmds, cb, silent) { sub.onappend._output0(sub, sub.Conf(), event||{}, cmds||sub.Input([], !silent), cb, silent); return true }, + Update: function(event, cmds, cb, silent) { sub.request(event)._caller() + sub.onappend._output0(sub, sub.Conf(), event||{}, cmds||sub.Input([], !silent), cb, silent); return true }, Focus: function() { can.page.SelectOne(can, option, html.INPUT_ARGS, function(target) { target.focus() }) }, Input: function(cmds, save) { cmds = cmds && cmds.length > 0? cmds: can.page.SelectArgs(sub), cmds = can.base.trim(cmds) return !save || cmds[0] == ctx.ACTION || can.base.Eq(sub._history[sub._history.length-1], cmds) || sub._history.push(cmds), cmds @@ -156,7 +156,7 @@ Volcanos(chat.ONAPPEND, {_init: function(can, meta, list, cb, target, field) { CloneField: can.Clone, CloneInput: function() { can.onmotion.focus(can, add(item)._target) }, Option: can.Option, Action: can.Action, Status: can.Status, Input: can.Input, }, [item.display, chat.PLUGIN_INPUT_JS], function(sub) { sub.Conf(item) - sub.run = function(event, cmds, cb, silent) { var msg = can.request(event, kit.Dict(chat._TOAST, ice.PROCESS)) + sub.run = function(event, cmds, cb, silent) { var msg = can.request(event, kit.Dict(chat._TOAST, ice.PROCESS))._caller() msg.RunAction(event, sub, cmds) || msg.RunAction(event, can.core.Value(can, chat._OUTPUTS_CURRENT), cmds) || can.Update(event, can.Input(cmds, !silent), cb, silent) }, can._inputs[item.name] = sub, sub.sup = can can.core.ItemCB(sub.onaction, function(key, cb) { sub._target[key] = function(event) { can.misc.Event(event, can, function(msg) { cb(event, sub) })} }) @@ -204,7 +204,7 @@ Volcanos(chat.ONAPPEND, {_init: function(can, meta, list, cb, target, field) { Update: can.Update, Option: can.Option, Action: can.Action, Status: can.Status, }, [display, chat.PLUGIN_TABLE_JS], function(sub) { sub.Conf(can.Conf()) sub.run = function(event, cmds, cb, silent) { - can.request(event).RunAction(event, sub, cmds) || can.Update(event, can.Input(cmds, !silent), cb, silent) + sub.request(event)._caller().RunAction(event, sub, cmds) || can.Update(event, can.Input(cmds, !silent), cb, silent) }, can._outputs && can._outputs.push(sub), sub.sup = can sub._index = can._index, sub._msg = msg, sub.Conf(sub._args = can.base.ParseURL(display)) sub._trans = can.base.Copy(can.base.Copy(sub._trans||{}, can._trans), can.core.Value(sub, [chat.ONACTION, chat._TRANS])) @@ -215,7 +215,7 @@ Volcanos(chat.ONAPPEND, {_init: function(can, meta, list, cb, target, field) { action === false || can.onmotion.clear(can, can._action), sub.onappend._action(sub, can.Conf(ice.MSG_ACTION)||msg.Option(ice.MSG_ACTION), action||can._action) action === false || sub.onappend._status(sub, sub.onexport&&sub.onexport.list||msg.Option(ice.MSG_STATUS)), can.user.isMobile || sub.onappend.tools(sub, msg) can.core.List([chat.FLOAT, chat.FULL, chat.CMD], function(mode) { can.page.ClassList.has(can, can._target, mode) && sub.onlayout[mode](sub) }) - can.onmotion.story.auto(can, can._output), can.onaction._output(can, msg), can.base.isFunc(cb) && cb(msg) + can.onmotion.story.auto(can, can._output), can.onexport.output(can, msg), can.onaction._output(can, msg), can.base.isFunc(cb) && cb(msg) }, target: output}) }) }, @@ -433,14 +433,16 @@ Volcanos(chat.ONAPPEND, {_init: function(can, meta, list, cb, target, field) { var value = can.onengine.plugin(can, meta.index); if (value) { can.onappend._plugin(can, value, meta, function(sub, meta, skip) { value.meta && value.meta._init && value.meta._init(sub, meta), _cb(sub, meta, skip) }, target, field); return res } - can.runAction({}, ctx.COMMAND, [meta.index], function(msg) { msg.Table(function(value) { can.onappend._plugin(can, value, meta, _cb, target, field) })}); return res + can.runAction(can.request()._caller(), ctx.COMMAND, [meta.index], function(msg) { msg.Table(function(value) { can.onappend._plugin(can, value, meta, _cb, target, field) })}); return res }, _plugin: function(can, value, meta, cb, target, field) { can.base.Copy(meta, value, true) meta.type = meta.type||chat.STORY, meta.name = meta.name||value.meta&&value.meta.name||"", meta.height = meta.height||can.ConfHeight(), meta.width = meta.width||can.ConfWidth() meta.inputs = can.base.getValid(meta.inputs, can.base.Obj(value.list))||[], meta.feature = can.base.getValid(meta.feature, can.base.Obj(value.meta))||{} meta.args = can.base.getValid(can.base.Obj(meta.args), can.base.Obj(meta.arg), can.base.Obj(value.args), can.base.Obj(value.arg))||[] can.onappend._init(can, meta, [chat.PLUGIN_STATE_JS], function(sub, skip) { - sub.run = function(event, cmds, cb) { can.runActionCommand(event, sub._index, cmds, cb) } + sub.run = function(event, cmds, cb) { + can.runActionCommand(sub.request(event), sub._index, cmds, cb) + } sub._index = value.index||meta.index, can.base.isFunc(cb) && cb(sub, meta, skip) }, target||can._output, field) }, @@ -473,7 +475,8 @@ Volcanos(chat.ONAPPEND, {_init: function(can, meta, list, cb, target, field) { Volcanos(chat.ONLAYOUT, {_init: function(can, target) { target = target||can._root._target; var height = can.page.height(), width = can.page.width() can.page.SelectChild(can, target, can.page.Keys(html.FIELDSET_HEAD, html.FIELDSET_FOOT), function(field) { height -= field.offsetHeight }) can.page.SelectChild(can, target, html.FIELDSET_LEFT, function(field) { can.user.isMobile || (width -= field.offsetWidth) - can.page.SelectChild(can, field, html.DIV_OUTPUT, function(output) { can.page.styleHeight(can, output, height-html.ACTION_HEIGHT) }) + var h = height; can.page.SelectChild(can, field, html.DIV_ACTION, function(action) { h -= action.offsetHeight }) + can.page.SelectChild(can, field, html.DIV_OUTPUT, function(output) { can.page.styleHeight(can, output, h) }) }) can.page.SelectChild(can, target, html.FIELDSET_MAIN, function(field) { can.page.SelectChild(can, field, html.DIV_ACTION, function(action) { height -= action.offsetHeight }) diff --git a/index.css b/index.css index 115adc91..8a765ad9 100644 --- a/index.css +++ b/index.css @@ -137,14 +137,16 @@ form.option>div.item>label, div.action>div.item>label, .hidden, .hide { display: form.option>div.textarea { width:100%; } form.option>div.textarea>textarea { width:100%; } form.option>div.cmd { width:100%; } -div.action, div.output, div.status, div.project, div.display, div.profile, div.content, table.content, table.content td, div.code, div.plug, div.story, div.toast { overflow:auto; } legend, form.option, form.option>div.item, div.action, div.action>div.item, div.action>div.tabs, div.status>div.item { float:left; } +div.action, div.output, div.status, div.project, div.display, div.profile, div.content, table.content, table.content td, div.code, div.plug, div.story, div.toast { overflow:auto; } fieldset>div.output, fieldset>div.status, div.item.textarea, div.project div.item, div.content, div.code, div.story[data-type=spark] { clear:both; } div.status>legend { margin-left:2px; margin-right:0; float:right; clear:none; } fieldset.plugin:not(.float):not(.full):not(.cmd) { padding:10px; margin:10px; } fieldset.plugin:not(.float):not(.full):not(.cmd)>legend { float:none; } fieldset.auto, fieldset.full, fieldset.float, div.float { position:fixed; z-index:10; } div.carte { overflow:auto; } +div.zone>div.action input::placeholder { font-style:italic; } +input::placeholder { font-style:italic; } fieldset.input { overflow:auto; } div.code { position:sticky; left:0; } hr { border-bottom:gray dashed 1px; margin:5px; } @@ -324,3 +326,5 @@ fieldset.panel.Action>div.output::-webkit-scrollbar { width:0 !important; height div.story[data-type=spark]::-webkit-scrollbar { width:0 !important; height:0 !important; } div.project::-webkit-scrollbar { width:0 !important; height:0 !important; } div.content::-webkit-scrollbar { width:0 !important; height:0 !important; } + +fieldset.data div.item:not(.string):not(.number):not(.boolean)>span.value { color:silver; } diff --git a/lib/misc.js b/lib/misc.js index b6737c6d..2e69ed79 100644 --- a/lib/misc.js +++ b/lib/misc.js @@ -78,6 +78,14 @@ Volcanos("misc", {Message: function(event, can) { var msg = {} can.onappend.board(can, msg) can.onmotion.story.auto(can) }, + _caller: function(skip) { + msg.Option("log.caller") || msg.Option("log.caller", can.misc.fileLine((skip||2)+1).link) + return msg + }, + _callers: function(skip) { + msg.Option("log.caller") || msg.Option("log.caller", can.misc._fileLine((skip||2)+1).link) + return msg + }, }; return kit.proto(msg, proto) }, concat: function(can, to, from) { to = to||[], from = from||[] @@ -92,6 +100,7 @@ Volcanos("misc", {Message: function(event, can) { var msg = {} if (meta[cmds[0]]) { return meta[cmds[0]](cmds.slice(1)), true } }, Event: function(event, can, cb) { + for (var i = 3; i < arguments.length; i++) { can.request(event, arguments[i]) } cb(can.request(event)) }, Run: function(event, can, dataset, cmds, cb) { var msg = can.request(event) @@ -127,28 +136,29 @@ Volcanos("misc", {Message: function(event, can) { var msg = {} if (xhr.status == 200) { return can.base.isFunc(cb) && cb(xhr.responseText) } can.misc.Warn(xhr.status, res, url, form) }; try { xhr.send() } catch(e) { can.misc.Warn(e) } }, - WSS: function(can, args, cb, onopen, onclose, onerror) { if (can.user.isIE) { return } + WSS: function(can, args, cb, onopen, onclose, onerror, _msg) { if (can.user.isIE) { return } var url = location.protocol.replace(ice.HTTP, "ws")+"//"+location.host+"/space/" if (url.indexOf(html.CHROME) == 0) { url = "ws://localhost:9020/space/" } var socket = new WebSocket(can.base.MergeURL(url, args)) + _msg = _msg || can.request()._caller() socket.onclose = function() { can.misc.Log(html.WSS, cli.CLOSE, args) can.base.isFunc(onclose)? onclose(socket): can.core.Timer(can.base.random(3000, 100), function() { - args.name = args.name||can._wss_name, can.misc.WSS(can, args, cb, onopen, onerror, onclose) + args.name = args.name||can._wss_name, can.misc.WSS(can, args, cb, onopen, onerror, onclose, _msg) }) }, socket.onerror = function() { can.misc.Log(html.WSS, log.ERROR, args) can.base.isFunc(onerror)? onerror(socket): socket.close() - }, socket.onopen = function() { can.misc.Log(html.WSS, cli.OPEN, args) + }, socket.onopen = function() { can.misc.Log(html.WSS, cli.OPEN, args, _msg) can.base.isFunc(onopen) && onopen(socket) }, socket.onmessage = function(event) { can.misc.Event(event, can, function(msg) { try { var data = JSON.parse(event.data) } catch (e) { var data = {detail: [event.data]} } msg.Reply = function() { var res = can.request({}, {_handle: ice.TRUE}) res._target = (msg[ice.MSG_SOURCE]||[]).reverse(), res._source = (msg[ice.MSG_TARGET]||[]).reverse().slice(1)||[] res.append = msg.append, can.core.List(msg.append, function(key) { res[key] = msg[key] }), res.result = (msg.result||[]).concat(can.core.List(arguments)) - res.Option(ice.LOG_DISABLE, msg.Option(ice.LOG_DISABLE)) != ice.TRUE && can.misc.Log(html.WSS, ice.MSG_RESULT, msg.result||[], msg) + res.Option(ice.LOG_DISABLE, msg.Option(ice.LOG_DISABLE)) != ice.TRUE && can.misc.Log(html.WSS, ice.MSG_RESULT, msg.result||[], msg, _msg) socket.send(JSON.stringify(res)) }, msg.detail = data.detail, msg.Copy(data) try { - msg.Option(ice.LOG_DISABLE) != ice.TRUE && can.misc.Log(html.WSS, ice.MSG_DETAIL, msg.detail, msg) + msg.Option(ice.LOG_DISABLE) != ice.TRUE && can.misc.Log(html.WSS, ice.MSG_DETAIL, msg.detail, msg, _msg) can.core.CallFunc(cb, {event: event, msg: msg, cmd: msg.detail[0], arg: msg.detail.slice(1), cb: function() { msg.Reply() }}) } catch (e) { can.misc.Warn(e), msg.Reply() } }) } @@ -201,11 +211,12 @@ Volcanos("misc", {Message: function(event, can) { var msg = {} if (value != undefined) { localStorage.setItem(key, value) } return localStorage.getItem(key) }, - _signal: function(can, args) { this._list.push(args) - if (can && can.onengine) { can.onengine.signal(can, chat.ONDEBUG, can.request({}, {time: this._time(), fileline: this.FileLine(-4), _args: args})) } - }, _list: [], - Log: function() { var args = [this._time(), this.FileLine(2, 3), ""] - for (var i in arguments) { arguments[i] != undefined && args.push(arguments[i]) } + _signal: function(can, args) { this._list.push(args) }, _list: [], + Log: function() { var pos = arguments[0] && arguments[0].indexOf && arguments[0].indexOf("on") == 0? arguments[0] == "onremote"? 5: 3: 2 + var args = [this._time(), this.fileLine(pos).link] + for (var i in arguments) { var arg = arguments[i]; if (!arg) { continue } args.push(arg) + if (arg.Option && arg.Option("log.caller")) { args[1] = arg.Option("log.caller") } + } console.log.apply(console, args), this._signal(arguments[0], args) }, Info: function() { var args = [this._time(), this.FileLine(2, 3), log.INFO] @@ -219,7 +230,7 @@ Volcanos("misc", {Message: function(event, can) { var msg = {} }, Error: function() { var args = [this._time(), this.fileLine(2, 3).link, log.ERROR] for (var i in arguments) { arguments[i] != undefined && args.push(arguments[i]) } - args.push(ice.NL, this._stack().slice(1).join(ice.NL)) + args.push(ice.NL, this._stacks().slice(1).join(ice.NL)) console.error.apply(console, args), this._signal(arguments[0], args) debugger }, @@ -230,43 +241,39 @@ Volcanos("misc", {Message: function(event, can) { var msg = {} }, Trace: function() { var filter = "", output = false var args = [this._time(), this.fileLine(2, 3).link, log.TRACE] - for (var i in arguments) { var item = arguments[i]; if (item == undefined) { continue } - if (item.misc && item.misc.Search) { - filter += item.misc.Search(item, log.TRACE)||"" - item._name && args.push(item._name) - } else if (item.Option) { - filter += item.Option(log.TRACE)||"" - } else if (arguments[i].indexOf && arguments[i].indexOf(filter||log.TRACE) > -1) { - output = true - } args.push(arguments[i]) - } if (output) { return console.trace.apply(console, args), true } + for (var i in arguments) { var arg = arguments[i]; if (!arg) { continue } args.push(arg) + if (arg.Option && arg.Option("log.trace") == ice.TRUE) { output = true } + if (arg.Conf && arg.Conf("log.trace") == ice.TRUE) { output = true } + } if (!output) { return } + args.push(ice.NL, this._stacks().slice(1, 4).join(ice.NL)) + console.debug.apply(console, args), this._signal(arguments[0], args) debugger }, - FileLine: function(depth, length) { var file = this.fileLine(depth+1, length||9); return file.file+ice.DF+file.line }, - fileLine: function(depth, length) { var list = this._stack() + FileLine: function(depth, length) { var file = this.fileLine(depth+1, length||9); return file.link }, + _fileLine: function(depth, length) { + var file = this.fileLine(depth+1, length||9) + for (var i = depth+1; i < 10; i++) { + var _file = this.fileLine(i+1, length||9) + if (_file && _file.link != file.link && !_file.path.indexOf("/lib/") == 0) { return _file } + } + return file + }, + fileLine: function(depth, length) { var list = this._stacks() function split(i) { if (!list[i]) { return {} } - var ls = list[i].trim().split(ice.SP).slice(-2), link = ls.slice(-1)[0]; link.indexOf("(") == 0 && (link = link.slice(1, -1)), link.indexOf("@") > -1 && (ls = link.split("@"), link = ls[1]) - var path = link, file = "", line = "", cols = ""; path = link.indexOf(ice.HTTP) == 0 && (path = link.split(ice.PS).slice(3).join(ice.PS)) - for (var i = path.length; i > 0; i--) { if (path[i] != ice.DF) { continue } - if (cols == "") { cols = path.slice(i+1), path = path.slice(0, i) } else if (line == "") { - line = path.slice(i+1), path = path.slice(0, i) - file = path.split(ice.PS).slice(-length).join(ice.PS), path = path.slice(0, -file.length) - break - } - } return {name: ls[0], link: link, path: path, file: file, line: line, cols: cols} + var ls = /(https*:\/\/[^/]+)*([^:]+):([0-9]+):([0-9]+)/.exec(list[i]) + var name = ""; list[i].lastIndexOf(ice.TB) > 0 && (name = list[i].split(ice.TB).pop()) + return {name: name, link: ls[0], path: ls[2], file: ls[2].split(ice.PS).slice(-length).join(ice.PS), line: ls[3], cols: ls[4]} } if (depth < 0) { var current = split(-depth) - for (var i = -depth+1; i < list.length; i++) { var pos = split(i); if (pos.file != current.file) { return pos } } + for (var i = -depth+1; i < list.length; i++) { var pos = split(i); if (pos.path != current.path) { return pos } } } return split(depth)||{} }, - _stack: function() { return ((new Error()).stack||"").split(ice.NL).slice(2) }, - _stacks: function() { var list = ((new Error()).stack||"").split(ice.NL).slice(2), prefix = location.protocol+"//"+location.host + _stacks: function() { var list = ((new Error()).stack||"").split(ice.NL).slice(2) for (var i = 0; i < list.length; i++) { var ls = list[i].trim().split(ice.SP) list[i] = ls.pop().trim(); if (list[i][0] == "(") { list[i] = list[i].slice(1, -1) } - if (list[i].indexOf(prefix) == 0) { list[i] = list[i].slice(prefix.length).split(ice.PS).slice(-2).join(ice.PS) } list[i] = ice.TB+list[i]; if (ls.length > 1) { list[i] += ice.TB+ls.pop() } } return list - }, + }, _stack: function() { return ((new Error()).stack||"").split(ice.NL).slice(2) }, _time: function() { var now = new Date() var hour = now.getHours(); hour < 10 && (hour = "0"+hour) var minute = now.getMinutes(); minute < 10 && (minute = "0"+minute) diff --git a/lib/user.js b/lib/user.js index ff74c0c5..960f58eb 100644 --- a/lib/user.js +++ b/lib/user.js @@ -74,7 +74,7 @@ Volcanos("user", {info: {}, agent: { html.ACTION, !can.base.isUndefined(meta.progress) && {view: "progress", style: {width: width-10}, list: [ {view: "current", style: {width: (meta.progress||0)*(width-14)/100}}, ]}, - ] }]); can.onengine.signal(can, chat.ONTOAST, can.request({}, {time: can.misc._time(), title: meta.title, content: meta.content, fileline: can.misc.FileLine(-3)})) + ] }]); can.onengine.signal(can, chat.ONTOAST, can.request({}, {time: can.misc._time(), title: meta.title, content: meta.content, fileline: can.misc.FileLine(-3)})._callers(1)) var action = can.onappend._action(can, meta.action && meta.action.list? meta.action.list: meta.action||[""], ui.action, { _engine: function(event, button) { can.core.CallFunc(meta.action[button]||meta.action, [event, button]) }, open: function(event) { meta.content.indexOf(ice.HTTP) == 0 && can.user.open(meta.content), meta.title.indexOf(ice.HTTP) == 0 && can.user.open(meta.title) }, @@ -97,21 +97,17 @@ Volcanos("user", {info: {}, agent: { return can.user.toastSuccess(can, text, "copy success"), can.misc.Log(nfs.COPY, text), text }, carte: function(event, can, meta, list, cb, parent, trans) { - meta = meta||can.ondetail||can.onaction||{}, list = can.base.getValid(list, meta.list, can.core.Item(meta))||[]; if (list.length == 0) { return } - cb = cb||function(event, button, meta) { var cb = meta[button]||meta[chat._ENGINE]; can.base.isFunc(cb) && cb(event, can, button) } - parent || can.page.Select(can, document.body, "div.carte.float", function(target) { can.onmotion.delay(can, function () { can.page.Remove(can, target) }) }) + meta = meta||can.ondetail||can.onaction||{}, list = can.base.getValid(list, meta.list, can.core.Item(meta)); if (!list || list.length == 0) { return } + function click(event, button) { meta[button]? meta[button](event, can, button): can.base.isFunc(cb)? cb(event, button, meta, carte): + can.core.CallFunc([can.onaction, button], [event, can, button]), can.page.Remove(can, ui._target) } function remove_sub(carte) { carte._sub && can.page.Remove(can, carte._sub._target), delete(carte._sub) } - function click(event, item) { can.base.isFunc(cb)? cb(event, item, meta): meta[item] && meta[item](event, can, item), can.onkeymap.prevent(event), can.user.isMobile && can.page.Remove(can, ui._target) } var ui = can.page.Append(can, document.body, [{view: [[chat.CARTE, meta._style||"", chat.FLOAT]], list: can.core.List(list, function(item, index) { - return can.base.isString(item)? item ==""? /* space */ {type: html.HR}: /* string */ {view: [html.ITEM, html.DIV, can.user.trans(can, item, trans)], onclick: function(event) { click(event, item) }, onmouseenter: function(event) { remove_sub(carte) } }: - can.base.isArray(item)? /* array */ {view: html.ITEM, list: [{text: can.user.trans(can, item[0], trans)+" -> "}], onmouseenter: function(event) { - var sub = can.user.carte(event, can, meta, item.slice(1), cb, carte, trans); can.onlayout.figure(event, can, sub._target, true), remove_sub(carte), carte._sub = sub - // } }: #<{(| object |)}># {view: html.ITEM, list: [{text: can.user.trans(can, item.name, trans), onclick: function(event) { click(event, item.name) }, onmouseenter: function(event) { remove_sub(carte) } }] } - } }: /* object */ item - }), onmouseover: function(event) { can.onkeymap.prevent(event) } }]); can.onkeymap.prevent(event) - var carte = {_target: ui._target, _parent: parent, layout: can.onlayout.figure(event, can, ui._target)} - can.page.Select(can, ui._target, "img", function(target) { target.onload = function() { can.onlayout.figure(event, can, ui._target) } }) - return carte + return item ==""? /* 0.space */ {type: html.HR}: can.base.isString(item)? /* 1.string */ {view: [html.ITEM, html.DIV, can.user.trans(can, item, trans)], onclick: function(event) { click(event, item) }, onmouseenter: function(event) { remove_sub(carte) } }: + can.base.isArray(item)? /* 2.array */ {view: html.ITEM, list: [{text: can.user.trans(can, item[0], trans)+" >"}], onmouseenter: function(event) { + var sub = can.user.carte(event, can, meta, item.slice(1), cb, carte, trans); can.onlayout.figure(event, can, sub._target, true), remove_sub(carte), carte._sub = sub + } }: /* 3.object */ item + })}]); can.onkeymap.prevent(event), can.page.Select(can, ui._target, html.IMG, function(target) { target.onload = function() { can.onlayout.figure(event, can, ui._target) } }) + var carte = {_target: ui._target, _parent: parent, layout: can.onlayout.figure(event, can, ui._target), close: function() { can.page.Remove(can, ui._target) }}; return carte }, carteRight: function(event, can, meta, list, cb, parent) { var carte = can.user.carte(event, can, meta, list, cb, parent) return can.page.style(can, carte._target, can.onlayout.figure(event, can, carte._target, true)), carte diff --git a/manifest.json b/manifest.json index bda35a91..68a22c09 100644 --- a/manifest.json +++ b/manifest.json @@ -3,18 +3,9 @@ "background": {"page": "/publish/chrome/daemon.html"}, "browser_action": {"default_popup": "/publish/chrome/popup.html"}, "content_scripts": [ - { - "matches": [""], - "permissions": [ - "tabs", - "history", - "cookies", - "bookmarks", - "contextMenus", - "notifications", - "http://localhost:9020/*" - ], - "css": ["/page/can.css"], "js": ["/page/can.js", "/publish/chrome/contexts.js"] - } + {"matches": [""], "permissions": [ + "tabs", "history", "cookies", "bookmarks", "contextMenus", "notifications", + "http://localhost:9020/*" + ], "css": ["/page/can.css"], "js": ["/page/can.js", "/publish/chrome/contexts.js"]} ] } diff --git a/panel/action.js b/panel/action.js index fed2e8d2..4525e697 100644 --- a/panel/action.js +++ b/panel/action.js @@ -235,7 +235,43 @@ Volcanos(chat.ONPLUGIN, { can.Option(chat.LAYOUT, can.getAction(chat.LAYOUT)||ice.AUTO) }, }, ["layout:select=auto,tabs,tabview,horizon,vertical,free,grid,flow,page", ice.RUN], function(can, msg, arg) { can.onaction.layout(can, arg[0], true) }), - + data: shy("网页标签", function(can, msg, arg) { + can.onmotion.delay(can, function() { var can = msg._can + function show(value) { switch (typeof value) { + case "object": + if (value._path) { + return {type: "plugin", open: "- ", close: "+ ", value: "\""+value._path+"\""} + } + if (value.tagName) { + return {type: "html", open: "- ", close: "+ ", value: value.tagName.toLowerCase()+ice.PT+value.className.replaceAll(ice.SP, ice.PT)} + } + if (value.length != undefined) { + return {type: "array", open: "- ", close: "+ ", value: "["+can.core.List(value, function(value) { return show(value).value }).join(",")+"]"} + } + return {type: typeof value, open: "- ", close: "+ ", value: ""} + case "string": return {type: typeof value, open: "s ", close: "s ", value: "\""+value+"\""} + case "number": return {type: typeof value, open: "n ", close: "n ", value: value} + case "boolean": return {type: typeof value, open: "b ", close: "b ", value: value} + case "function": return {type: typeof value, open: "f ", close: "f ", value: (""+value).split(ice.NL)[0]} + default: return {type: typeof value, open: " ", close: " ", value: value} + } } + function add(target, key, value) { var loaded = false, _show = show(value) + var ui = can.page.Append(can, target, [{view: [[html.ITEM, _show.type]], list: [ + {view: [html.ICON, html.SPAN, _show.close]}, + {view: [mdb.NAME, html.SPAN, key+" "]}, + {view: [mdb.VALUE, html.SPAN, _show.value]}, + ], onclick: function() { if (typeof value != "object") { return } + if (loaded) { return ui.icon.innerText = can.onmotion.toggle(can, ui.list)? _show.open: _show.close } loaded = true, ui.icon.innerText = _show.open + can.core.List(can.core.Item(value, function(key) { if (value.hasOwnProperty(key)) { return key } }).sort(), function(key) { add(ui.list, key, value[key]) }) + }}, {view: html.LIST, style: {"margin-left": "20px"}}]) + } add(can._output, can._root._name, can._root) + }) + }), + view: shy("网页标签", function(can, msg, arg) { + can.onmotion.delay(can, function() { var can = msg._can + can.page.Append(can, can._output, [{view: [html.ITEM, html.DIV, "html"]}]) + }) + }), "parse": shy("生成网页", { "show": function(can, msg, arg) { var name = arg[1]||ice.CAN; can.isCmdMode() && can.user.title(name) arg && arg[0] && Volcanos(name, {_follow: can.core.Keys(can._follow, name)}, [chat.PLUGIN_STORY+"parse.js"], function(sub) { diff --git a/panel/footer.js b/panel/footer.js index 928a766f..f7e349c7 100644 --- a/panel/footer.js +++ b/panel/footer.js @@ -1,4 +1,4 @@ -(function() { var NTIP = "ntip", NCMD = "ncmd", NLOG = "nlog" +(function() { var NTIP = "ntip", NCMD = "ncmd" Volcanos(chat.ONIMPORT, {_init: function(can, msg, target) { can.onimport._title(can, msg, target) can.onimport._state(can, msg, target) @@ -6,7 +6,7 @@ Volcanos(chat.ONIMPORT, {_init: function(can, msg, target) { can.onimport._command(can, msg, target) }, _title: function(can, msg, target) { can.user.isMobile || can.core.List(msg.result, function(item) { can.page.Append(can, target, [{view: [chat.TITLE, html.DIV, item], title: "联系站长"}]) }) }, - _state: function(can, msg, target) { can.core.List(can.base.Obj(can.Conf(chat.STATE)||msg.Option(chat.STATE), [NTIP, NCMD, NLOG]).reverse(), function(item) { + _state: function(can, msg, target) { can.core.List(can.base.Obj(can.Conf(chat.STATE)||msg.Option(chat.STATE), [NTIP, NCMD]).reverse(), function(item) { can.page.Append(can, target, [{view: [[chat.STATE], html.DIV, can.Conf(item)], list: [ {text: [item, html.LABEL]}, {text: [": ", html.LABEL]}, {text: [can.Conf(item)||"", html.SPAN, item]}, ], onclick: function(event) { can.onexport[item](can) }}]) @@ -22,7 +22,6 @@ Volcanos(chat.ONIMPORT, {_init: function(can, msg, target) { } }}, "", target, [chat.TITLE]) }, count: function(can, name) { can.page.Select(can, can._output, can.core.Keys(html.SPAN, name), function(item) { item.innerHTML = can.Conf(name, parseInt(can.Conf(name)||"0")+1+"")+"" }) }, toast: function(can, msg, title, content, fileline, time) { can.onimport._data(can, NTIP, {time: time, fileline: fileline, title: title, content: content}), can.page.Modify(can, can.toast, [time, title, content].join(ice.SP)) }, - debug: function(can, msg, _args, fileline, time) { can.onimport._data(can, NLOG, {time: time, fileline: fileline, type: _args[2], content: _args.slice(4).join(ice.SP)}) }, ncmd: function(can, msg, _follow, _cmds) { can.onimport._data(can, NCMD, {time: can.base.Time(), follow: _follow, cmds: _cmds}) }, _data: function(can, name, item) { can[name] = can[name]||can.request(), can[name].Push(item), can.onimport.count(can, name) }, }) @@ -30,13 +29,13 @@ Volcanos(chat.ONACTION, {_init: function(can) { if (can.user.isExtension || can. onsize: function(can) { can.ConfHeight(can._target.offsetHeight), can.ConfWidth(can._target.offsetWidth) }, onlogin: function(can, msg) { can.run({}, [], function(msg) { can.onmotion.clear(can), can.onimport._init(can, msg, can._output) }) }, ontoast: function(can, msg) { can.core.CallFunc(can.onimport.toast, {can: can, msg: msg}) }, - ondebug: function(can, msg) { can.core.CallFunc(can.onimport.debug, {can: can, msg: msg}) }, onremote: function(can, msg) { can.core.CallFunc(can.onimport.ncmd, {can: can, msg: msg}) }, onaction_cmd: function(can) { can.onappend.style(can, can._target, html.HIDE) }, oncommand_focus: function(can) { can.page.Select(can, can._output, ["div.cmd", html.INPUT], function(target) { can.onmotion.focus(can, target) }) }, }) Volcanos(chat.ONEXPORT, {height: function(can) { return can._target.offsetHeight }, - float: function(can, msg, name, cb) { if (!can[name]) { return } if (can[name]._target) { return can[name]._target.close() } var ui = can.onappend.field(can, chat.STORY, {name: name, pos: chat.FLOAT}, can._root._target); can[name]._target = ui + float: function(can, msg, name, cb) { if (!can[name]) { return } if (can[name]._target) { return can[name]._target.close() } var ui = can.onappend.field(can, chat.STORY, {name: name}, can._root._target); can[name]._target = ui + can.onappend.style(can, html.FLOAT, ui._target) ui.close = function() { can.page.Remove(can, ui._target), delete(can[name]._target) }, ui.refresh = function() { ui.close(), can.toast.click() } can.getActionSize(function(height, width) { can.page.style(can, ui._target, html.RIGHT, 0, html.BOTTOM, can.onexport.height(can)) can.page.style(can, ui.output, html.MAX_HEIGHT, height-html.ACTION_HEIGHT, html.MAX_WIDTH, width) @@ -49,9 +48,6 @@ Volcanos(chat.ONEXPORT, {height: function(can) { return can._target.offsetHeight }, ui.output), msg && can.onappend.board(can, msg.Result(), ui.output); return ui }, ntip: function(can) { can.onexport.float(can, can[NTIP], NTIP, function(value, key, index, line) { can.onappend._float(can, web.CODE_INNER, [ice.USR_VOLCANOS].concat(line.fileline.split(ice.DF))) }) }, - nlog: function(can) { var ui = can.onexport.float(can, can[NLOG], NLOG, function(value, key, index, line) { can.onappend._float(can, web.CODE_INNER, [ice.USR_VOLCANOS].concat(line.fileline.split(ice.DF))) }) - ui && can.page.Select(can, ui.output, [html.TBODY, html.TR], function(tr, i) { can.page.ClassList.add(can, tr, can[NLOG][mdb.TYPE][i]) }) - }, ncmd: function(can) { can.onexport.float(can, can[NCMD], NCMD, function(value, key, index, line) { var cmds = can.base.Obj(line.cmds); switch (line.follow) { case "can.Action": cmds = cmds.slice(2); break @@ -67,7 +63,44 @@ Volcanos(chat.ONEXPORT, {height: function(can) { return can._target.offsetHeight }) Volcanos(chat.ONPLUGIN, { alert: shy("提示", [wiki.CONTENT], function(can, msg, arg) { arg && arg.length > 0 && can.user.alert(arg[0]) }), - toast: shy("提示", [wiki.CONTENT, wiki.TITLE], function(can, msg, arg) { arg && arg.length > 0 && can.user.toast(can, arg[0], arg[1]), msg.Copy(can[NTIP]), msg.StatusTimeCount() }), - debug: shy("日志", ["type:select=Info,Warn,Error,Debug", wiki.CONTENT], function(can, msg, arg) { arg && arg.length > 1 && can.misc[arg[0]](can, arg[1]), msg.Copy(can[NLOG]), msg.StatusTimeCount() }), + toast: shy("提示", [wiki.CONTENT, wiki.TITLE], function(can, msg, arg) { + arg && arg.length > 0 && can.user.toast(can, arg[0], arg[1]), msg.Copy(can[NTIP]), msg.StatusTimeCount() + }), + debug: shy("日志", ["type:select=Info,Warn,Error,Debug", "_text"], function(can, msg, arg) { + arg && arg.length > 1 && can.misc[arg[0]](can, arg[1]) + can.onmotion.delay(can, function() { var sub = msg._can; sub.page.style(can, sub._output, html.MAX_HEIGHT, 200) + can.page.Append(can, sub._output, [{type: html.TABLE, className: html.CONTENT, list: [{type: html.TR, list: [ + {type: html.TH, inner: mdb.TIME}, + {type: html.TH, inner: nfs.FILE}, + {type: html.TH, inner: mdb.TYPE}, + {type: html.TH, inner: mdb.TEXT}, + ]}].concat(can.core.List(can.misc._list, function(list) { return {type: html.TR, list: [ + {type: html.TD, inner: list[0]}, + {type: html.TD, inner: list[1].indexOf(location.origin) == 0? list[1].slice(location.origin.length+1): list[1]}, + {type: html.TD, inner: list[2]}, + {type: html.TD, inner: can.core.List(list.slice(3), function(item) { + if (item.Conf) { + return "can" + } else if (item.Option) { + return "msg" + } else if (can.base.isString(item)) { + return item + } else { + return JSON.stringify(item) + } + }).join(ice.SP)}, + ], onclick: function(event) { + var _ls = /(https*:\/\/[^/]+)*([^:]+):([0-9]+):([0-9]+)/.exec(list[1]) + sub.onexport.record(sub, list[1], mdb.LINK, { + time: list[0], + link: list[1], + type: list[2], + path: "usr/volcanos/", + file: _ls[2], + line: _ls[3], + }) + }} })) }]) + }) + }), }) })() diff --git a/panel/river.js b/panel/river.js index 03e921d6..03ac8a38 100644 --- a/panel/river.js +++ b/panel/river.js @@ -6,7 +6,7 @@ Volcanos(chat.ONIMPORT, {_init: function(can, msg) { var select; can.page.Append can._main_river = can.misc.Search(can, chat.RIVER)||msg.Option(ice.MSG_RIVER)||Volcanos.meta.args.river||can._main_river||ls[0]||"project" can._main_storm = can.misc.Search(can, chat.STORM)||msg.Option(ice.MSG_STORM)||Volcanos.meta.args.storm||can._main_storm||ls[1]||"studio" }, - _menu: function(can, msg) { if (can.user.mod.isPod) { return } + _menu: function(can, msg) { if (can.user.mod.isPod) { return } return can.setHeaderMenu(can.base.Obj(can.Conf(chat.MENUS)||msg.Option(chat.MENUS), can.ondetail._menus), function(event, button) { can.core.CallFunc([can.ondetail, button], [event, can, button, can.Conf(chat.RIVER), can.Conf(chat.STORM)]) }), can.onappend._action(can, can.Conf(ctx.ACTION)||can.onaction.list) diff --git a/plugin/input.js b/plugin/input.js index 9aabf5f9..4cebcfd2 100644 --- a/plugin/input.js +++ b/plugin/input.js @@ -8,8 +8,7 @@ Volcanos(chat.ONACTION, { onkeydown: function(event, can) { can.onkeymap.input(event, can, event.target) if (can.Conf(mdb.TYPE) == html.TEXTAREA) { if (!event.ctrlKey) { return } } if (event.key == lang.ENTER) { return can.run(event), can.onmotion.focus(can, event.target), can.onkeymap.prevent(event) } - if (!event.ctrlKey) { return } - switch (event.key) { + if (!event.ctrlKey) { return } switch (event.key) { case "m": can.CloneField(); break case "b": can.CloneInput(); break default: can.onkeymap.selectOutput(event, can.sup); return diff --git a/plugin/local/chat/iframe.js b/plugin/local/chat/iframe.js index 0194d4f9..efdc56a5 100644 --- a/plugin/local/chat/iframe.js +++ b/plugin/local/chat/iframe.js @@ -1,5 +1,5 @@ Volcanos(chat.ONIMPORT, {_init: function(can, msg) { can.current = msg.TableDetail(), can.onimport.layout(can) }, - layout: function(can) { var item = can.current; can.onimport.title(can, item.name||item.link.split("?")[0]) + layout: function(can) { var item = can.current; can.onexport.title(can, item.name||item.link.split("?")[0]) can.page.Appends(can, can._output, [{type: html.IFRAME, src: item.link, height: can.ConfHeight(), width: can.ConfWidth(), style: {border: 0}}]) }, }) diff --git a/plugin/local/code/inner.css b/plugin/local/code/inner.css index 7fb9321a..4864be01 100644 --- a/plugin/local/code/inner.css +++ b/plugin/local/code/inner.css @@ -1,7 +1,7 @@ fieldset.inner>form.option input[name=path] { width:80px; } fieldset.inner>form.option input[name=file] { width:160px; } -fieldset.inner>div.output { overflow:hidden; } -fieldset.inner>div.output * { font-size:14px; font-family:monospace; outline:none; } +fieldset.inner>div.output>div.project * { font-size:14px; font-family:monospace; outline:none; } +fieldset.inner>div.output>div.layout>div.layout>div.content * { font-size:14px; font-family:monospace; outline:none; } fieldset.inner>div.output legend { font-size:1rem; line-height:2rem; } fieldset.inner>div.output div.content { position:relative; } fieldset.inner>div.output div.content td.text span.comment { color:green; } @@ -13,7 +13,15 @@ fieldset.inner>div.output div.content td.text span.constant { color:magenta; } fieldset.inner>div.output div.content td.text span.string { color:magenta; } fieldset.inner>div.output div.content td.text span.object { color:cyan; } fieldset.inner>div.output>div.project { width:230px; } +fieldset.inner>div.output>div.project>div.zone fieldset.plug { position:static; } +fieldset.inner>div.output>div.project>div.zone fieldset.plug legend { display:none; } +fieldset.inner>div.output>div.project>div.zone fieldset.plug form.option { display:none; } +fieldset.inner>div.output>div.project>div.zone fieldset.plug div.action { display:none; } +fieldset.inner>div.output>div.project>div.zone fieldset.plug div.status { display:none; } +fieldset.inner>div.output>div.project>div.zone fieldset.plug { position:static; } fieldset.inner>div.output>div.project>div.zone>div.item { letter-spacing:10px; } +fieldset.inner>div.output>div.project>div.zone>div.item span.icon { font-size:22px; line-height:18px; width:20px; float:right; display:none; } +fieldset.inner>div.output>div.project>div.zone:hover>div.item span.icon { display:block; } fieldset.inner>div.output>div.project>div.zone div.action>div.item { padding-right:0; width:100%; } fieldset.inner>div.output>div.project>div.zone div.action>div.item>input { width:100%; } fieldset.inner>div.output>div.layout.flow { position:relative; } @@ -36,10 +44,8 @@ fieldset.inner.cmd>div.output>div.layout.flow>div.path span.view { font-size:22p fieldset.inner.cmd>div.output>div.layout.flow>div.plug { height:31px; clear:both; } fieldset.inner.cmd>div.output>div.layout.flow>div.plug>legend { float:right; } fieldset.inner.cmd>div.output fieldset.plug { bottom:31px; position:absolute; } -// fieldset.inner.cmd>div.output>div.layout.flow>fieldset.plug { display:block; } fieldset.inner fieldset.story form.option div.icon { display:block; } - body.black fieldset.inner>div.output div.content td.text span.comment { background-color:blue; color:cyan; } body.white fieldset.inner.cmd>div.output { background-color:aliceblue; } body.white fieldset.inner.cmd>div.output div.content { background-color:white; } @@ -75,10 +81,6 @@ body.dark fieldset.inner>div.output div.content td.text span.object { color:gold body.mobile fieldset.inner>form.option input[name=file] { width:90px; } body.mobile fieldset.word fieldset.inner>form.option input[type=text] { display:none; } -// div.action>div div.icon { margin-left:10px; margin-top:1px; float:right; visibility:hidden; } -// div.action>div:hover div.icon { visibility:visible; } div.action>div.select div.icon { visibility:visible; } -// div.tabs>div div.icon { margin-left:10px; margin-top:1px; float:right; visibility:hidden; } -// div.tabs>div:hover div.icon { visibility:visible; } div.tabs>div.select div.icon { visibility:visible; } div.carte.path.float { font-size:14px; border-radius:0; } div.carte.path.float div.item { padding:5px; } div.path span.item { padding:5px; cursor:pointer; } tr.line>td.line { text-align:right; padding:0 10px; position:sticky; left:0; } diff --git a/plugin/local/code/inner.js b/plugin/local/code/inner.js index 51bd7dd6..29753075 100644 --- a/plugin/local/code/inner.js +++ b/plugin/local/code/inner.js @@ -9,11 +9,12 @@ Volcanos(chat.ONIMPORT, {_init: function(can, msg, cb, target) { can.onmotion.cl can.db = {paths: paths, tabview: {}, history: [], profile_size: {}, display_size: {}, toolkit: {}, extentions: {}}, can.onengine.plugin(can, can.onplugin) can.ui = can.onappend.layout(can, can._output, "", [html.PROJECT, [html.TABS, nfs.PATH, [html.CONTENT, html.PROFILE], html.DISPLAY, html.PLUG]]) can.ui._content = can.ui.content, can.ui._profile = can.ui.profile, can.ui._display = can.ui.display + can.onmotion.hidden(can, can.ui.plug) + can.onengine.plugin(can, can.onplugin) switch (can.Mode()) { case chat.SIMPLE: can.onmotion.hidden(can, can.ui.project); break case chat.FLOAT: can.onmotion.hidden(can, can.ui.project); break - case chat.CMD: can.page.style(can, document.body, html.OVERFLOW, html.HIDDEN) - can.onmotion.hidden(can, can._status), can.onimport._keydown(can) // no break + case chat.CMD: can.onmotion.hidden(can, can._status), can.onimport._keydown(can) // no break case chat.FULL: // no break default: can.onimport.project(can, paths), can.onimport._tabs(can) can.onmotion.delay(can, function() { can.core.Next(files.slice(1), function(file, next) { @@ -54,7 +55,7 @@ Volcanos(chat.ONIMPORT, {_init: function(can, msg, cb, target) { can.onmotion.cl _tabInputs: function(can, ps, key, value, cb, target) { can.core.List(can.core.Split(value, ps), function(value, index, array) { can.page.Append(can, target, [{text: [value+(index 4) { ls = [ls.slice(0, 2).join(ice.PS)+"/.../"+ls.slice(-2).join(ice.PS)] } can.Status(kit.Dict("文件", ls.join(ice.PS), "类型", can.db.parse)), can.onimport.layout(can) - if (!skip) { - can.onaction.selectLine(can, can.Option(nfs.LINE), true) - } + can.onaction.selectLine(can, can.Option(nfs.LINE), true) +// if (!skip) { can.onaction.selectLine(can, can.Option(nfs.LINE), true) } can.base.isFunc(cb) && cb(), cb = null }) } function load(msg) { var skip = false; can.db.tabview[key] = msg - can.onimport.tabs(can, [{name: file.split(isCommand()? ice.PT: ice.PS).pop(), text: file}], function(event, tabs) { + can.onimport.tabs(can, [{name: file.split(isCommand()? ice.PT: ice.PS).pop(), text: file, _menu: shy([nfs.SAVE, "compile"], function(event, button, meta) { + can.onaction[button](event, can, button) + })}], function(event, tabs) { can._tab = msg._tab = tabs._target, show(skip), skip = true }, function(tabs) { can.onengine.signal(can, "tabview.view.delete", msg) msg._content != can.ui._content && can.page.Remove(can, msg._content), msg._profile != can.ui._profile && can.page.Remove(can, msg._profile) delete(can.ui._content._cache[key]), delete(can.ui._profile._cache[key]), delete(can.ui.display._cache[key]) delete(can._cache_data[key]), delete(can.db.tabview[key]) - }, can.ui.tabs).ondblclick = function(event) { can.misc.Event(event, can, function(msg) { - can.onaction.clear(event, can) - }) } + }, can.ui.tabs) } if (can.db.tabview[key]) { return !can._msg._tab && !can.isSimpleMode()? load(can.db.tabview[key]): show() } isCommand()||isDream()? load(can.request({}, {index: file, line: line})): can.run({}, [path, file], load, true) @@ -202,7 +201,7 @@ Volcanos(chat.ONIMPORT, {_init: function(can, msg, cb, target) { can.onmotion.cl return can.onmotion.toggle(can, target, false), can.onimport.layout(can), can.user.toastFailure(can, "nothing to display") } return can.onmotion.toggle(can, target, true), can.onimport.layout(can), can.user.toastSuccess(can) }, - toolkit: function(can, meta, cb) { + toolkit: function(can, meta, cb) { can.page.isDisplay(can.ui.plug) || can.onmotion.toggle(can, can.ui.plug, true) && can.onimport.layout(can) can.onimport.plug(can, meta, function(sub) { can.onappend.style(sub, [html.FLOAT, html.HIDE]) can.ui.plug.appendChild(sub._legend), sub._legend.onclick = function(event) { can.misc.Event(event, can, function(msg) { if (can.page.SelectOne(can, can.ui.plug, ice.PT+html.SELECT, function(target) { @@ -272,10 +271,10 @@ Volcanos(chat.ONSYNTAX, {_init: function(can, msg, cb) { can.db.parse = can.base.Ext(can.db.file), can.Status("模式", mdb.PLUGIN); return can.db.file }, can.ui._content, can.ui._profile, can.ui._display)) { return can.base.isFunc(cb) && cb(msg._content) } if (msg.Option(ctx.INDEX)) { return can.onsyntax._index(can, msg, cb) } - function init(p) { + function init(p) { msg._can = can + var list = ((new Error()).stack||"").split(ice.NL) can.db.max = 0, can.core.List(can.db.ls = msg.Result().split(ice.NL), function(item) { can.onaction.appendLine(can, item) }) - msg._can = can - can.base.isFunc(cb) && cb(msg._content = can.ui._content), can.onengine.signal(can, "tabview.view.init", msg) + can.onengine.signal(can, "tabview.view.init", msg), can.base.isFunc(cb) && cb(msg._content = can.ui._content) } can.require(["inner/syntax.js"], function() { can.Conf(chat.PLUG) && (can.onsyntax[can.db.parse] = can.Conf(chat.PLUG)) var p = can.onsyntax[can.db.parse]; !p? can.runAction({}, mdb.PLUGIN, [can.db.parse, can.Option(nfs.FILE), can.Option(nfs.PATH)], function(msg) { init(p = can.onsyntax[can.db.parse] = can.base.Obj(msg.Result()||"{}")) @@ -283,14 +282,17 @@ Volcanos(chat.ONSYNTAX, {_init: function(can, msg, cb) { }) }, _index: function(can, msg, cb) { - if (can.Option(nfs.LINE) == web.DREAM) { + if (can.Option(nfs.LINE) == web.DREAM) { can.ui.dream && can.onmotion.delay(can, function() { can.ui.dream.refresh() }, 5000) return can.base.isFunc(cb) && cb(msg._content = msg._content||can.page.insertBefore(can, [{view: [html.CONTENT, html.IFRAME], src: can.misc.MergePodCmd(can, {pod: can.Option(nfs.FILE)}), height: can.ui.content.offsetHeight, width: can.ui.content.offsetWidth}], can.ui._content)) } var meta = {type: "story", index: msg.Option(ctx.INDEX), args: can.Option(nfs.PATH) == ctx.COMMAND && can.Option(nfs.LINE) != ctx.INDEX? [can.Option(nfs.LINE)]: []} return can.onimport.plug(can, meta, function(sub) { can.page.ClassList.del(sub, sub._target, html.HIDE) sub.onaction.close = function() { can.onaction.back(can), msg._tab._close() } - sub.onimport.title = function(_, title) { can.page.Modify(can, msg._tab, title) } + sub.onexport.title = function(_, title) { can.page.Modify(can, msg._tab, title) } + sub.onexport.record = function(_, value, key, line) { + line.path && can.onimport.tabview(can, line.path, line.file, line.line) + } sub.onimport._open = function(sub, msg, _arg) { var url = can.base.ParseURL(_arg), ls = url.origin.split("/chat/pod/") if (_arg.indexOf(location.origin) == 0 && ls.length > 1) { return can.onimport.tabview(can, can.Option(nfs.PATH), ls[1].split(ice.PS)[0], web.DREAM), sub.Update() @@ -334,6 +336,15 @@ Volcanos(chat.ONACTION, { can.onaction.find(event, can) }}, {view: [html.TEXT, html.TD, can.onsyntax._parse(can, value)], onclick: function(event) { + if (event.metaKey) { + if (ui.text.innerText.indexOf(ice.HTTP) > -1) { + var ls = (/(http[^ ]+)/).exec(ui.text.innerText) + if (ls && ls[1]) { + can.user.open(ls[1]) + return + } + } + } can.onaction.selectLine(can, ui.tr) }, ondblclick: function(event) { can.onaction.searchLine(event, can, can.onexport.selection(can, ui.text.innerText)) @@ -395,7 +406,7 @@ Volcanos(chat.ONACTION, { if (can.page.Select(can, can.ui.plug, "legend.select", function(item) { return item.click(), item }).length > 0) { return } if (can.page.isDisplay(can.ui.display)) { return can.onmotion.hidden(can, can.ui.display), can.onimport.layout(can) } if (can.page.isDisplay(can.ui.profile)) { return can.onmotion.hidden(can, can.ui.profile), can.onimport.layout(can) } - can.onmotion.toggle(can, can.ui.project), can.onimport.layout(can) + // can.onmotion.toggle(can, can.ui.project), can.onimport.layout(can) }, exec: function(event, can) { if (can.base.Ext(can.Option(nfs.FILE)) == nfs.JS) { delete(Volcanos.meta.cache[can.base.Path(ice.PS, ice.REQUIRE, can.Option(nfs.PATH), can.Option(nfs.FILE))]) } @@ -479,10 +490,7 @@ Volcanos(chat.ONACTION, { }) Volcanos(chat.ONEXPORT, {list: ["目录", "类型", "文件", "行号", "跳转"], hash: function(can) { if (!can.isCmdMode()) { return } - var list = []; if (can.Option(nfs.PATH) != can.misc.Search(can, nfs.PATH)) { list.push(can.Option(nfs.PATH)) } - if (list.length > 0 || can.Option(nfs.FILE) != can.misc.Search(can, nfs.FILE)) { list.push(can.Option(nfs.FILE)) } - if (list.length > 0 || can.Option(nfs.LINE) != can.misc.Search(can, nfs.LINE)) { list.push(can.Option(nfs.LINE)) } - location.hash = list.join(ice.DF) + location.hash = [can.Option(nfs.PATH), can.Option(nfs.FILE), can.Option(nfs.LINE)].join(ice.DF) }, keys: function(can, path, file) { return [path||can.Option(nfs.PATH), file||can.Option(nfs.FILE)].join(ice.DF) }, line: function(can, line) { return parseInt(can.core.Value(can.page.SelectOne(can, line, "td.line"), "innerText")) }, diff --git a/plugin/local/code/vimer.css b/plugin/local/code/vimer.css index 3b876c22..850e455f 100644 --- a/plugin/local/code/vimer.css +++ b/plugin/local/code/vimer.css @@ -1,6 +1,4 @@ fieldset.vimer>div.output div.project div.zone.recent>div.list { max-height:200px; } -fieldset.vimer>div.output div.project div.zone.repos>div.list { max-height:120px; } -fieldset.vimer>div.output div.project div.zone.dream>div.list { max-height:120px; } fieldset.vimer>div.output div.project div.zone.dream div.item.stop { color:gray; } fieldset.vimer>div.output input.current { background-color:transparent; color:transparent; padding-left:10px; height:20px; position:absolute; } fieldset.vimer>div.output input.current.insert { caret-color:black; } diff --git a/plugin/local/code/vimer.js b/plugin/local/code/vimer.js index 901e7dc9..7e0c49d8 100644 --- a/plugin/local/code/vimer.js +++ b/plugin/local/code/vimer.js @@ -1,59 +1,39 @@ -Volcanos(chat.ONIMPORT, {_init: function(can, msg, cb, target) { - can.require(["inner.js"], function(can) { can.onimport._last_init(can, msg, function() { - can.db.undo = [], can.db.redo = [], can.onappend.style(can, code.VIMER) - can.onimport._input(can), can.onkeymap._build(can), can.onkeymap._plugin(can) - can.onengine.listen(can, "tabview.line.select", function(msg) { can.onaction._selectLine(can) }) - can.onengine.plugin(can, can.onplugin), can.base.isFunc(cb) && cb(msg) - can.ui.project.onscroll = function() { can.onmotion.clearFloat(can) } - can.isCmdMode() && can.run({}, [ctx.ACTION, ctx.COMMAND].concat(["can.topic", "nfs.dir", "web.code.xterm", "web.code.git.status"]), function(msg) { - msg.Table(function(value) { can.onimport.toolkit(can, value, function(sub) { can.db.toolkit[value.index] = sub }) }) - }) - }, target) }) - }, +Volcanos(chat.ONIMPORT, {_init: function(can, msg, cb, target) { can.require(["inner.js"], function(can) { can.onimport._last_init(can, msg, function() { + can.db.undo = [], can.db.redo = [], can.onimport._input(can), can.base.isFunc(cb) && cb(msg) + can.onengine.listen(can, "tabview.line.select", function(msg) { can.onaction._selectLine(can) }) + }, target) }) }, _input: function(can) { var ui = can.page.Append(can, can.ui.content.parentNode, [ - {view: [code.CURRENT, html.INPUT], spellcheck: false, onkeydown: function(event) { - if (event.metaKey) { return can.db.mode == mdb.INSERT && can.onmotion.delay(can, function() { can.current.text(can.ui.current.value) }) } - if (event.ctrlKey && can.onaction._complete(event, can)) { return } + {view: [code.CURRENT, html.INPUT], spellcheck: false, onkeydown: function(event) { can.onimport._value(can); if (event.metaKey) { return } can.db._keylist = can.onkeymap._parse(event, can, can.db.mode+(event.ctrlKey? "_ctrl": ""), can.db._keylist, can.ui.current) - if (can.db.mode == mdb.INSERT) { can.db._keylist = [], can.onmotion.delay(can, function() { can.current.text(can.ui.current.value) }) } if (can.db.mode == mdb.NORMAL) { can.onkeymap.prevent(event), can.Status("按键", can.db._keylist.join("")) } - }, onkeyup: function(event) { - if (event.metaKey) { return can.db.mode == mdb.INSERT && can.onmotion.delay(can, function() { can.current.text(can.ui.current.value) }) } + if (can.db.mode == mdb.INSERT) { can.db._keylist = [] } + }, onkeyup: function(event) { can.onimport._value(can); if (event.metaKey) { return } can.onaction._complete(event, can) - }, onfocus: function() { - var target = can.ui.complete; can.current.line.appendChild(target), can.onmotion.toggle(can, target, true) + }, onfocus: function(event) { + can.current.line.appendChild(can.ui.complete) }, onclick: function(event) { can.onkeymap._insert(event, can) }}, {view: [[code.COMPLETE, chat.FLOAT]]}, - ]); can.ui.current = ui.current, can.ui.complete = ui.complete }, + ]); can.ui.current = ui.current, can.ui.complete = ui.complete, can.onkeymap._build(can), can.onkeymap._plugin(can) }, + _value: function(can) { can.db.mode == mdb.INSERT && can.onmotion.delay(can, function() { can.current.text(can.ui.current.value) }) }, }, [""]) Volcanos(chat.ONFIGURE, { - recent: function(can, target, zone, path) { var total = 0 - function show(msg, cb) { var list = {}; msg.Table(function(item) { var path = item.path+item.file - if (!list[path]) { can.page.Append(can, target, cb(item, path)), zone._total(++total) } list[path] = item - }) } - can.runAction({}, code.FAVOR, ["_recent_file"], function(msg) { - can.core.List([ - "index.css", "proto.js", "frame.js", "plugin/table.js", - "plugin/local/code/vimer.js", - "plugin/local/code/inner.js", - "plugin/local/code/inner.css", - "plugin/local/code/vimer.css", - ], function(item) { msg.Push(nfs.PATH, ice.USR_VOLCANOS).Push(nfs.FILE, item) }) + recent: function(can, target, zone) { var total = 0 + function show(msg, cb) { var list = {}; msg.Table(function(item) { var path = item.path+item.file; if (!list[path]) { list[path] = item, can.page.Append(can, target, cb(item, path)), total++ } }) } + can.runAction({}, code.FAVOR, ["_recent_file"], function(msg) { can.core.List(["plugin/local/code/vimer.js"], function(item) { msg.Push(nfs.PATH, ice.USR_VOLCANOS).Push(nfs.FILE, item) }) show(msg, function(item, path) { return [{text: [path.split(ice.PS).slice(-2).join(ice.PS), html.DIV, html.ITEM], onclick: function(event) { can.onimport.tabview(can, item.path, item.file) - }}] }) + }}] }), zone._total(total) }) }, - source: function(can, target, zone, path) { var total = 0 - var args = can.base.getValid(can.misc.SearchHash(can), [can.Option(nfs.PATH), can.Option(nfs.FILE)]) - function show(target, zone, path) { can.run(can.request({}, {dir_root: path, dir_deep: true}), [nfs.PWD], function(msg) { - can.onmotion.clear(can, target) - var node; function add(list) { + source: function(can, target, zone, path) { var args = can.base.getValid(can.misc.SearchHash(can), [can.Option(nfs.PATH), can.Option(nfs.FILE)]) + zone._icon({"+": function(event) { can.user.carteRight(event, can, {}, ["script", "autogen"]) } }) + function show(target, zone, path) { can.run(can.request({}, {dir_root: path, dir_deep: true}), [nfs.PWD], function(msg) { can.onmotion.clear(can, target) + if (path == nfs.SRC) { can.ui.source.refresh = function() { show(target, zone, path) } } + var total, node; function add(list) { can.core.List(list, function(item) { if (path == args[0] && args[1].indexOf(item.path) == 0) { item.expand = true } item._menu = shy({ create: function(event) { can.user.input(event, can, ["filename"], function(list) { - can.base.endWith(item.path, ice.PS)? can.request(event, {path: path+item.path, file: list[0]}): - can.request(event, {path: path+item.path.split(ice.PS).slice(0, -1).join(ice.PS)+ice.PS, file: list[0]}) + can.request(event, {path: can.base.endWith(item.path, ice.PS)? path+item.path: path+item.path.split(ice.PS).slice(0, -1).join(ice.PS)+ice.PS, file: list[0]}) can.runAction(event, nfs.SAVE, [], function(msg) { var file = (msg.Option(nfs.PATH)+msg.Option(nfs.FILE)).slice(path.length) add([{path: file}], node), can.onimport.tabview(can, path, file) }) @@ -62,52 +42,26 @@ Volcanos(chat.ONFIGURE, { }), item._init = function(target) { item._remove = function() { can.page.Remove(can, target.parentNode), delete(node[item.path]) } } }) return can.onimport.tree(can, list, nfs.PATH, ice.PS, function(event, item) { can.onimport.tabview(can, path, item.path) }, target, node) } node = add(msg.Table(), node), can.Status("目录", zone._total(msg.Length())) - - if (zone._icon == true) { return } zone._icon = true - can.page.Append(can, zone._legend, [{view: "icon s16 create", onclick: function(event) { can.user.input(event, can, ["filename"], function(list) { - can.runAction(can.request(event, {path: path, file: list[0]}), nfs.SAVE, [], function(msg) { can.onimport.tabview(can, path, list[0]) - can.onimport.tree(can, [{path: list[0]}], nfs.PATH, ice.PS, function(event, item) { can.onimport.tabview(can, path, item.path) }, target, node) - can.core.List(list[0].split(ice.PS), function(item, index, array) { can.onmotion.toggle(can, node[array.slice(0, index+1).join(ice.PS)], true) }) - }) - }), can.onkeymap.prevent(event) }}]) - can.page.Append(can, zone._legend, [{view: "icon s16 refresh", onclick: function(event) { - show(target, zone, path), can.onkeymap.prevent(event), can.user.toastSuccess(can) - }}]) }, true) } if (path.length == 1) { return show(target, path[0]) } can.onimport.zone(can, can.core.List(path, function(path) { return path.indexOf("-story") == -1 && path.indexOf("-dict") == -1 && {name: path, _init: function(target, zone) { path == args[0] && show(target, zone, path) }, _delay_show: path == args[0]? undefined: function(target, zone) { show(target, zone, path) }} - }), target), can.page.Remove(can, target.previousSibling) + }), target), can.page.Remove(can, zone._action) }, - repos: function(can, target, zone, path) { zone._delay_show = function() { can.runAction({}, nfs.REPOS, [], function(msg) { - msg.Table(function(value) { can.onimport.item(can, {name: can.page.Color(value.type)+ice.TB+value.file}, function() { - can.onimport.tabview(can, value.path, value.file) - }, function() {}, target) }), zone._total(msg.Length()) - }) } }, - dream: function(can, target, zone) { var call = arguments.callee - zone._delay_show = function() { - can.runAction({}, ice.RUN, [web.DREAM], function(msg) { can.onmotion.clear(can, target), msg.Table(function(item) { - can.page.ClassList.add(can, can.onimport.item(can, item, function(event) { can.onimport.tabview(can, can.Option(nfs.PATH), item.name, web.DREAM) }, function(event) { - return shy(kit.Dict(cli.START, [cli.OPEN, cli.STOP], cli.STOP, [cli.START, nfs.TRASH])[item.status], function(event, button) { - can.runAction(can.request({}, item), ice.RUN, [web.DREAM, ctx.ACTION, button], function(msg) { - can.sup.onimport._process(can.sup, msg) || call(can, target, zone) - }) - }) - }, target), item.status) - }), zone._total(msg.Length()), can.user.toastSuccess(can) }) - } - return shy(kit.Dict( - web.REFRESH, function(event, can, button) { call(can, target, zone) }, - mdb.CREATE, function(event, can, button) { can.onaction.dream(event, can, web.DREAM) }, - code.PUBLISH, function(event, can, button) { can.runAction(event, button, [], function(msg) { can.user.toastConfirm(can, msg.Result(), button) }) }, - )) - }, - plugin: function(can, target, zone) { zone._delay_show = function() { var total = 0 - can.onimport.tree(can, can.core.ItemKeys(can.onengine.plugin.meta, function(key) { return total++, {index: key} }), ctx.INDEX, ice.PT, function(event, item) { - can.onimport.tabview(can, can.Option(nfs.PATH), can.core.Keys(ice.CAN, item.index), ctx.INDEX) - }, target), zone._total(total), can.onmotion.hidden(can, target), can.onmotion.hidden(can, target.previousSibling) - } }, + repos: function(can, target, zone) { can.onimport._zone(can, zone, "web.code.git.status", function(sub, msg) { + sub.onexport.record = function(sub, value, key, line) { can.onimport.tabview(can, line.path, line.file) } + zone._icon({ "\u21BA": function() { sub.Update() }, + "\u21C8": function() { sub.run({}, [ctx.ACTION, "push"]) }, + "\u21CA": function() { sub.run({}, [ctx.ACTION, "pull"]) }, + "=": function() { can.onimport.tabview(can, can.Option(nfs.PATH), "web.code.git.status", ctx.INDEX) }, + }) + }) }, + dream: function(can, target, zone) { can.onimport._zone(can, zone, web.DREAM, function(sub, msg) { + sub.onexport.record = function(sub, value, key, line) { can.onimport.tabview(can, can.Option(nfs.PATH), value, web.DREAM) } + can.page.Select(can, sub._output, html.DIV_ITEM, function(target, index) { can.onappend.style(can, msg.status[index], target) }) + zone._icon({ "\u21BA": function() { sub.Update() }, "+": function() { sub.run({}, [ctx.ACTION, mdb.CREATE]) }}) + }) }, module: function(can, target, zone) { zone._delay_show = function() { can.runAction(can.request({}, {fields: ctx.INDEX}), ctx.COMMAND, [mdb.SEARCH, ctx.COMMAND], function(msg) { can.onimport.tree(can, msg.Table(), ctx.INDEX, ice.PT, function(event, item) { @@ -115,9 +69,13 @@ Volcanos(chat.ONFIGURE, { }, target), zone._total(msg.Length()) }) } }, + plugin: function(can, target, zone) { zone._delay_show = function() { var total = 0 + can.onimport.tree(can, can.core.ItemKeys(can.onengine.plugin.meta, function(key) { return total++, {index: key} }), ctx.INDEX, ice.PT, function(event, item) { + can.onimport.tabview(can, can.Option(nfs.PATH), can.core.Keys(ice.CAN, item.index), ctx.INDEX) + }, target), zone._total(total) + } }, }) -Volcanos(chat.ONACTION, { - list: ["autogen", "script", "save", "compile", "dream", "首页", "官网", "文档", "git"], +Volcanos(chat.ONACTION, {list: ["首页", "官网", "文档"], _daemon: function(event, can, arg) { switch (arg[0]) { case web.DREAM: can.runAction({}, arg[0], arg.slice(1), function(msg) { can.onimport.tabview(can, can.Option(nfs.PATH), can.core.Keys(can.misc.Search(can, ice.POD), msg.Option(mdb.NAME)), web.DREAM) }); break case code.XTERM: can.runAction({}, arg[0], arg.slice(1), function(msg) { can.onimport.tabview(can, ctx.COMMAND, code.XTERM, msg.Result()) }); break @@ -129,13 +87,13 @@ Volcanos(chat.ONACTION, { _runs: function(event, can, button, cb) { var meta = can.Conf(); can.request(event, {action: button}) can.user.input(event, can, meta.feature[button], function(args) { can.onaction._run(event, can, button, args, cb) }) }, - autogen: function(event, can, button) { can.onaction._runs(can.request(event, {path: "src/"}), can, button, function(msg) { + autogen: function(event, can, button) { can.onaction._runs(can.request(event, {path: nfs.SRC}), can, button, function(msg) { can.onimport.tabview(can, msg.Option(nfs.PATH), msg.Option(cli.MAIN), "", function() { can.onimport.tabview(can, msg.Option(nfs.PATH), msg.Option(nfs.FILE)), can.ui.source.refresh(), can.user.toastSuccess(can) }, true) }) }, script: function(event, can, button) { - can.onaction._runs(can.request(event, {path: "src/", file: can.base.trimSuffix(can.Option(nfs.FILE), can.base.Ext(can.Option(nfs.FILE)))+nfs.JS}), can, button) + can.onaction._runs(can.request(event, {path: nfs.SRC, file: can.base.trimSuffix(can.Option(nfs.FILE), can.base.Ext(can.Option(nfs.FILE)))+nfs.JS}), can, button) }, dream: function(event, can, button) { can.onaction._runs(can.request(event, {name: can.base.trimSuffix(can.Option(nfs.FILE).split(ice.PS).pop(), ice.PT+can.base.Ext(can.Option(nfs.FILE)))}), can, button, function(msg) { @@ -298,6 +256,9 @@ Volcanos(chat.ONKEYMAP, { n: shy("命令模式", function(event, can) { can.onkeymap._normal(can) }), ":": shy("底行模式", function(event, can) { can.onimport.toolkit(can, {index: "cli.system"}, function(sub) { can.db.toolkit["cli.system"] = sub.select(), can.onmotion.delay(can, function() { sub.Focus() }) }) }), + d: shy("查找替换", function(event, can) { + can.page.Select(can, can.ui.path, "span.func", function(target) { target.click() }) + }), g: shy("查找替换", function(event, can) { can.onaction.find(event, can) }), s: shy("保存文件", function(event, can) { can.onaction.save(event, can, nfs.SAVE) }), c: shy("编译项目", function(event, can) { can.onaction.compile(event, can, code.COMPILE) }), @@ -378,6 +339,7 @@ Volcanos(chat.ONKEYMAP, { zz: shy("将当前行拉到屏幕中间", function(can, count) { return can.current.scroll(can.current.scroll()-(count = count>1? count: can.current.window()/2)), true }), zb: shy("将当前行拉到屏幕最下", function(can, count) { return can.current.scroll(can.current.scroll()-can.current.window()+(count>1? count: 5)), true }), s: shy("保存文件", function(event, can) { can.onaction.save(event, can, nfs.SAVE) }), + c: shy("编译项目", function(event, can) { can.onaction.compile(event, can, code.COMPILE) }), }, normal_ctrl: { f: shy("向下翻页", function(can, count) { @@ -409,6 +371,8 @@ Volcanos(chat.ONKEYMAP, { } else if (deep(text) >= deep(can.onexport.text(can, line+1)) && rest == "") { can.onaction.insertLine(can, left+item[1], can.current.next()) } left += ice.TB + } else if (can.base.beginWith(rest, item[1])) { + left = left.slice(0, -1) }}) var line = can.onaction.insertLine(can, left+rest, can.current.next()) can.current.text(text.trimRight()||text), can.onaction.selectLine(can, line), can.onkeymap._insert(event, can, 0, left.length) diff --git a/plugin/local/code/xterm.js b/plugin/local/code/xterm.js index 00373f63..54434fd7 100644 --- a/plugin/local/code/xterm.js +++ b/plugin/local/code/xterm.js @@ -11,11 +11,11 @@ Volcanos(chat.ONIMPORT, {_init: function(can, msg, cb) { can.onmotion.clear(can) var fitAddon = new FitAddon.FitAddon(); term.loadAddon(fitAddon), term._fit = fitAddon can.onmotion.delay(can, function() { fitAddon.fit() }) term.loadAddon(new WebLinksAddon.WebLinksAddon()) - term.onTitleChange(function(title) { can.sup.onimport.title(can, title) }) + term.onTitleChange(function(title) { can.onexport.title(can, title) }) term.onResize(function(size) { can.onimport._resize(can, size) }) term.onData(function(data) { can.onimport._input(can, data) }) term.onCursorMove(function() { can.onexport.term(can) }) - can.sup.onimport.title(can, item.name) + can.onexport.title(can, item.name) can._current = term, term._item = item term.open(can._output), term.focus() }, @@ -28,14 +28,11 @@ Volcanos(chat.ONIMPORT, {_init: function(can, msg, cb) { can.onmotion.clear(can) }, grow: function(can, msg, _arg) { can._current.write(_arg) }, }) -Volcanos(chat.ONLAYOUT, { - _init: function(can) { +Volcanos(chat.ONLAYOUT, {_init: function(can) { can.page.style(can, can._output, html.HEIGHT, can.ConfHeight()+8, html.WIDTH, can.ConfWidth()+18, html.MAX_WIDTH, "") can._current && can._current._fit.fit(), can.onexport.term(can) }, - cmd: function(can) { can._current && can.onimport._title(can, can._current._item.name), can.ConfWidth(can.ConfWidth()-10) - // can.Option(mdb.HASH) && can.Option(mdb.HASH) == can.misc.Search(can, mdb.HASH)? can.sup.onaction.full({}, can.sup): can.onlayout._init(can) - }, + cmd: function(can) { can._current && can.onexport.title(can, can._current._item.name), can.ConfWidth(can.ConfWidth()-10) }, }) Volcanos(chat.ONACTION, { refresh: function(event, can, button) { can.onlayout._init(can), can._current.focus() }, diff --git a/plugin/state.js b/plugin/state.js index 91a2057f..5268398c 100644 --- a/plugin/state.js +++ b/plugin/state.js @@ -237,7 +237,10 @@ Volcanos(chat.ONACTION, {list: [ }) }, }) -Volcanos(chat.ONEXPORT, {record: function(can, line) {}, +Volcanos(chat.ONEXPORT, { + output: function(can, msg) {}, + action: function(can, button, line) {}, + record: function(can, value, key, line) {}, statusHeight: function(can) { return can._status.style.display == html.NONE || can._status.innerHTML == "" || can._status.offsetHeight == 0? 0: html.ACTION_HEIGHT }, actionHeight: function(can) { return can._action.style.display == html.NONE || can._action.innerHTML == ""? 0: html.ACTION_HEIGHT }, link: function(can) { var meta = can.Conf(), args = can.Option() diff --git a/plugin/table.js b/plugin/table.js index 82df82ef..c67b9615 100644 --- a/plugin/table.js +++ b/plugin/table.js @@ -1,10 +1,21 @@ Volcanos(chat.ONIMPORT, {_init: function(can, msg, target) { can.onmotion.clear(can, target) + if (can.Mode() == html.ZONE) { + msg.Table(function(value) { var action = [] + can.page.Select(can, can.page.Create(can, html.DIV, value.action), html.INPUT, function(target) { + action.push(target.name), target.name != target.value && can.user.trans(can, kit.Dict(target.name, target.value)) + }) + can.onimport.item(can, {name: can.page.Color(value[can.Conf(mdb.FIELD)||mdb.VIEW]||value[mdb.NAME])}, function() { + can.sup.onexport.record(can, value.name, mdb.NAME, value) + }, function() { return shy(action, function(event, button, meta, carte) { can.misc.Event(event, can, function(msg) { + can.sup.onexport.action(can, button, value) || can.run(event, [ctx.ACTION, button], function(msg) { can.Update() }) + carte.close() + }, value) }) }) + }) + return + } var cbs = can.onimport[can.Conf(ctx.STYLE)||msg.Option(ctx.STYLE)]; if (can.base.isFunc(cbs)) { - can.core.CallFunc(cbs, {can: can, msg: msg, target: target}) - can.page.ClassList.add(can, target, can._args[ctx.STYLE]) - } else { - can.onappend.table(can, msg, null, target), can.onappend.board(can, msg, target) - } can.onmotion.story.auto(can, target) + can.onappend.style(can, can._args[ctx.STYLE], target), can.core.CallFunc(cbs, {can: can, msg: msg, target: target}) + } else { can.onappend.table(can, msg, null, target), can.onappend.board(can, msg, target) } can.onmotion.story.auto(can, target) if (can.isCmdMode()) { can.page.style(can, can._output, html.MAX_HEIGHT, can.ConfHeight()) } }, _system_app: function(can, msg, target) { @@ -23,12 +34,19 @@ Volcanos(chat.ONIMPORT, {_init: function(can, msg, target) { can.onmotion.clear( ], onclick: function(event) { can.runAction(can.request(event, item, can.Option()), "click", []) }} })) }, - _title: function(can, title) { can.user.title(title) }, - title: function(can, title) { can._legend.innerHTML = title - can.sup && can.sup._tabs && (can.sup._tabs.innerHTML = title) - can.sup && can.sup._header_tabs && (can.sup._header_tabs.innerHTML = title) - can.isCmdMode() && can.onimport._title(can, title) - }, + _zone: function(can, zone, index, cb, field) { zone._delay_show = function() { can.onimport.plug(can, {index: index, mode: html.ZONE, field: field}, function(sub) { + var action = can.core.List(sub.Conf(ctx.INPUTS), function(item) { if (item.type == html.BUTTON && [ice.LIST, ice.BACK].indexOf(item.name) == -1) { return item.name } }) + sub.onexport.output = function(sub, msg) { zone._total(msg.Length()), cb(sub, msg) + zone._menu = shy({_trans: sub._trans}, action.concat(can.base.Obj(msg.Option(ice.MSG_ACTION), [])), function(event, button, meta, carte) { + sub.Update(event, [ctx.ACTION, button]), carte.close() + }), can.user.toastSuccess(can) + }, zone._target = sub._target, can.ui[zone.name].refresh = function() { sub.Update() } + }, zone._target) } }, + card: function(can, msg, target) { can.page.Appends(can, target||can._output, msg.Table(function(item) { + return {view: [[html.ITEM, item.status]], list: [{view: [wiki.TITLE, html.DIV, item.name]}, {view: [wiki.CONTENT, html.DIV, item.text]}, + {view: html.ACTION, inner: item.action, onclick: function(event) { can.run(can.request(event, item), [ctx.ACTION, event.target.name]) }}, + ]} + })) }, tabs: function(can, list, cb, cbs, action) { action = action||can._action return can.page.Append(can, action, can.core.List(list, function(tabs) { @@ -43,130 +61,97 @@ Volcanos(chat.ONIMPORT, {_init: function(can, msg, target) { can.onmotion.clear( can.page.Modify(can, target, {draggable: true, _close: function() { close(target) }, ondragstart: function(event) { action._drop = function(before) { before.parentNode == action && action.insertBefore(target, before) } }, ondragover: function(event) { event.preventDefault(), action._drop(event.target) }, - ondrop: function(event) { event.preventDefault(), action._drop(event.target) }, oncontextmenu: function(event) { can.user.carte(event, can, kit.Dict("Close", function(event) { close(target) }, "Close Other", function(event) { can.page.Select(can, action, html.DIV_TABS, function(target) { target == tabs._target || close(target) }) }, - ), ["Close", "Close Other", ""].concat(menu.list), function(event, button, meta) { (meta[button]||menu)(event, button, meta) }) }, + menu.meta + ), ["Close", "Close Other", ""].concat(can.base.getValid(menu.list, can.core.Item(menu.meta))), function(event, button, meta) { (meta[button]||menu)(event, button, meta) }) }, }), can.onmotion.delay(can, function() { target.click() }) }} }))._target }, - tool: function(can, list, cb, target) { target = target||can._output - can.core.List(list.reverse(), function(meta) { can.base.isString(meta) && (meta = {index: meta}) - can.onimport.plug(can, meta, function(sub) { sub._delay_init = true - sub.ConfHeight(can.ConfHeight()-4*html.ACTION_HEIGHT), sub.ConfWidth(can.ConfWidth()) - can.page.style(can, sub._output, html.MAX_HEIGHT, sub.ConfHeight(), html.MAX_WIDTH, sub.ConfWidth()) - can._status.appendChild(sub._legend), sub._legend.onclick = function(event) { can.misc.Event(event, can, function(msg) { - if (can.page.Select(can, can._status, ice.PT+html.SELECT)[0] == event.target) { - can.page.ClassList.del(can, event.target, html.SELECT) - can.page.ClassList.del(can, sub._target, html.SELECT) - return - } - can.onmotion.select(can, target, html.FIELDSET, sub._target), sub.Focus() - can.onmotion.select(can, can._status, html.LEGEND, event.target) - if (sub._delay_init || meta.msg == true) { sub._delay_init = false, meta.msg = false, sub.Update() } - }) }, sub.select = function() { return sub._legend.click(), sub }, sub._legend.onmouseenter = null - sub.onaction.close = function() { sub.select() } - can.base.isFunc(cb) && cb(sub) + tool: function(can, list, cb, target, status) { target = target||can._output, status = status||can._status + can.core.List(list.reverse(), function(meta) { can.base.isString(meta) && (meta = {index: meta}), meta.mode = html.FLOAT + can.onimport.plug(can, meta, function(sub) { can.onmotion.hidden(can, sub._target), sub._delay_init = true + sub.ConfHeight(can.ConfHeight()-4*html.ACTION_HEIGHT), sub.ConfWidth(can.ConfWidth()), can.page.style(can, sub._output, html.MAX_HEIGHT, sub.ConfHeight(), html.MAX_WIDTH, sub.ConfWidth()) + status.appendChild(sub._legend), sub._legend._fields = sub._target, sub._legend.onclick = function(event) { can.misc.Event(event, can, function(msg) { + if (can.page.SelectOne(can, status, ice.PT+html.SELECT, function(target) { can.onmotion.hidden(can, target._fields), can.page.ClassList.del(can, target, html.SELECT) }) == sub._legend) { return } + if (sub._delay_init || meta.msg) { sub._delay_init = false, meta.msg = false, sub.Update() } + can.onmotion.select(can, status, html.LEGEND, sub._legend), can.onmotion.toggle(can, sub._target, true), sub.Focus() + }) }, sub.select = function() { return sub._legend.click(), sub }, sub.onaction.close = function() { sub.select() }, can.base.isFunc(cb) && cb(sub) }, target) }) }, plug: function(can, meta, cb, target) { if (!meta || !meta.index) { return } - meta.type = meta.type||"plug", meta.name = meta.index, can.onappend.plugin(can, meta, function(sub) { sub.sup = can - sub.ConfHeight(target.offsetHeight-2*html.ACTION_HEIGHT) - can.page.style(can, sub._output, html.MAX_HEIGHT, sub.ConfHeight(), html.MAX_WIDTH, sub.ConfWidth()) - sub.run = function(event, cmds, cb) { - if (can.page.Select(can, sub._option, "input[name=path]").length > 0 && sub.Option(nfs.PATH) == "") { - sub.request(event, {path: "./"}) - } - can.runActionCommand(can.request(event, can.Option()), meta.index, cmds, cb) } - sub.onaction.close = function() { can.onmotion.hidden(can, target) } - can.base.isFunc(cb) && cb(sub) + meta.type = meta.type||html.PLUG, meta.name = meta.index, can.onappend.plugin(can, meta, function(sub) { sub.sup = can + sub.ConfHeight(can.ConfHeight()-2*html.ACTION_HEIGHT), sub.ConfWidth(can.ConfWidth()), can.page.style(can, sub._output, html.MAX_HEIGHT, sub.ConfHeight(), html.MAX_WIDTH, sub.ConfWidth()) + sub.run = function(event, cmds, cb) { if (can.page.Select(can, sub._option, "input[name=path]").length > 0 && sub.Option(nfs.PATH) == "") { sub.request(event, {path: "./"}) } + can.runActionCommand(can.request(event, can.Option()), meta.index, cmds, cb) + }, sub.onaction.close = function() { can.onmotion.hidden(can, target) }, can.base.isFunc(cb) && cb(sub) }, target) }, + icon: function(can, name, button, target) { + can.page.Append(can, target, [{text: [name, html.SPAN, html.ICON], onclick: function(event) { + can.base.isFunc(button)? button(event, button): can.onaction[button](event, can, button), can.onkeymap.prevent(event) + }}]) + }, zone: function(can, list, target) { return can.page.Append(can, target, can.core.List(list, function(zone) { can.base.isString(zone) && (zone = {name: zone}); return zone && {view: [[html.ZONE, zone.name]], list: [ - {view: html.ITEM, inner: can.user.trans(can, zone.name), _init: function(target) { - zone._legend = target - }, onclick: function() { + {view: html.ITEM, inner: can.user.trans(can, zone.name), _init: function(target) { zone._legend = target }, onclick: function() { if (zone._delay_show) { zone._delay_show(zone._target, zone), delete(zone._delay_show) } can.onmotion.toggle(can, zone._action), can.onmotion.toggle(can, zone._target) - }, oncontextmenu: function(event) { - zone._menu? can.user.carteRight(event, can, zone._menu.meta, zone._menu.list||can.core.Item(zone._menu.meta), function(event, button, meta) { - (meta[button]||can.onaction[button])(event, can, button) + }, oncontextmenu: function(event) { var menu = zone._menu + menu? can.user.carteRight(event, can, menu.meta, menu.list||can.core.Item(menu.meta), can.base.isFunc(menu)? menu: function(event, button, meta, carte) { + can.runAction(event, button), carte.close() }): can.onmotion.clearCarte(can) }}, {view: html.ACTION, _init: function(target) { zone._action = target - can.onappend._action(can, [{input: html.TEXT, placeholder: mdb.SEARCH, onkeyup: function(event) { - can.onkeymap.selectItems(event, can, zone._target) - can.page.Select(can, zone._target, html.DIV_LIST, function(item) { can.onmotion.toggle(can, item, true) }) - if (event.target.value == "") { - can.page.Select(can, zone._target, html.DIV_LIST, function(target) { can.page.ClassList.add(can, target, html.HIDE) }) - can.page.Select(can, zone._target, "div.switch", function(target) { can.page.ClassList.del(can, target, "open") }) + can.onappend._action(can, [{input: html.TEXT, _init: function(target) { zone._search = target }, onkeyup: function(event) { + can.onkeymap.selectItems(event, can, zone._target), can.page.Select(can, zone._target, html.DIV_LIST, function(item) { can.onmotion.toggle(can, item, true) }) + if (event.target.value == "") { can.page.Select(can, zone._target, html.DIV_LIST, function(target) { can.onmotion.hidden(can, target) }) + can.page.Select(can, zone._target, "div.switch", function(target) { can.page.ClassList.del(can, target, cli.OPEN) }) } - }, onfocus: function(event) { var target = event.target - target.setSelectionRange && target.setSelectionRange(0, target.value.length) - }, _init: function(target) { zone._search = target - }}], target, {}) + }, onfocus: function(event) { var target = event.target; target.setSelectionRange && target.setSelectionRange(0, target.value.length) }}], target, {}) }}, - {view: html.LIST, _init: function(target) { can.ui[zone.name] = zone + {view: html.LIST, _init: function(target) { can.ui[zone.name] = zone, zone._target = target, zone.refresh = function() { can.onmotion.clear(can, target), zone._init(target, zone) } zone._total = function(total) { return can.page.Modify(can, zone._search, {placeholder: "search in "+total+" item"}), total } - zone._target = target, zone.refresh = function() { zone._init(target, zone) } - can.base.isFunc(zone._init) && (zone._menu = zone._init(target, zone)||zone._menu) - if (zone._delay_show) { can.onmotion.hidden(can, zone._action), can.onmotion.hidden(can, zone._target) } + zone._icon = function(list) { + can.page.Select(can, zone._legend, "span.icon", function(target) { can.page.Remove(can, target) }) + can.core.Item(list, function(name, button) { can.onimport.icon(can, name, button, zone._legend) }) + } + can.base.isFunc(zone._init) && (zone._menu = zone._init(target, zone)||zone._menu); if (zone._delay_show) { can.onmotion.hidden(can, zone._action), can.onmotion.hidden(can, zone._target) } }} ]} })) }, tree: function(can, list, field, split, cb, target, node) { - node = node||{"": target}; can.core.List(list, function(item) { - item[field] && can.core.List(item[field].split(split), function(value, index, array) { if (!value) { return } - var last = array.slice(0, index).join(split), name = array.slice(0, index+1).join(split); if (node[name]) { return } - var ui = can.page.Append(can, node[last], [{view: html.ITEM, list: [{view: ["switch"+(item.expand? " open": ""), html.DIV, (index==array.length-1?"":"\u25B8")]}, {view: [mdb.NAME, html.DIV, value+(index==array.length-1?"":"")], _init: item._init, oncontextmenu: function(event) { if (!item._menu) { return } - can.user.carteRight(event, can, item._menu.meta, item._menu.list||can.core.Item(item._meta.meta), function(event, button) { - (item._menu.meta[button]||item._menu)(event, can, button) - }) - }}], onclick: function(event) { if (node[name].childElementCount == 2) { node[name].firstChild.click() } - index < array.length - 1? can.page.ClassList.set(can, ui["switch"], "open", !can.page.ClassList.neg(can, node[name], html.HIDE)): can.base.isFunc(cb) && cb(event, item) - }}, {view: [[html.LIST, item.expand? "": html.HIDE]]}]); node[name] = ui.list - }) - }); return node + node = node||{"": target}; can.core.List(list, function(item) { item[field] && can.core.List(item[field].split(split), function(value, index, array) { if (!value) { return } + var last = array.slice(0, index).join(split), name = array.slice(0, index+1).join(split); if (node[name]) { return } + var ui = can.page.Append(can, node[last], [{view: html.ITEM, list: [ + {view: [["switch", item.expand? cli.OPEN: ""], html.DIV, (index==array.length-1? "": "\u25B8")]}, + {view: [mdb.NAME, html.DIV, value], _init: item._init}, + ], onclick: function(event) { if (node[name].childElementCount == 2) { node[name].firstChild.click() } + index < array.length - 1? can.page.ClassList.set(can, ui["switch"], cli.OPEN, !can.page.ClassList.neg(can, node[name], html.HIDE)): can.base.isFunc(cb) && cb(event, item) + }, oncontextmenu: function(event) { if (!item._menu) { return } + var menu = item._menu; can.user.carteRight(event, can, menu.meta, menu.list, menu) + }}, {view: [[html.LIST, item.expand? "": html.HIDE]]}]); node[name] = ui.list + }) }); return node }, item: function(can, item, cb, cbs, target) { target = target||(can.ui && can.ui.project? can.ui.project: can._output) - var ui = can.page.Append(can, target, [{view: [html.ITEM, html.DIV, item.nick||item.name], - onclick: function(event) { can.onmotion.select(can, target, html.DIV_ITEM, event.target) + var ui = can.page.Append(can, target, [{view: [html.ITEM, html.DIV, item.nick||item.name], onclick: function(event) { can.onmotion.select(can, target, html.DIV_ITEM, event.target) cb(event, event.target, event.target._list && can.onmotion.toggle(can, event.target._list)) - }, oncontextmenu: function(event) { - if (can.base.isFunc(cbs)) { var menu = cbs(event, ui._target); if (menu) { - can.user.carteRight(event, can, menu.meta, menu.list, menu) - } } - }, + }, oncontextmenu: function(event) { if (can.base.isFunc(cbs)) { var menu = cbs(event, ui._target); if (menu) { can.user.carteRight(event, can, menu.meta, menu.list, menu) } } }, }]); return ui._target }, itemlist: function(can, list, cb, cbs, target) { return target._list = can.page.insertBefore(can, [{view: html.LIST, list: can.core.List(list, function(item) { return {view: [html.ITEM, html.DIV, item.name], onclick: function(event) { - cb(event, item, event.target._list && can.page.ClassList.neg(can, event.target._list, "hide")) - }, onmouseenter: function(event) { cbs(event, item) }} + cb(event, item, event.target._list && can.page.ClassList.neg(can, event.target._list, html.HIDE)) + }, oncontextmenu: function(event) { if (can.base.isFunc(cbs)) { var menu = cbs(event, ui._target); if (menu) { can.user.carteRight(event, can, menu.meta, menu.list, menu) } } }} }) }], target.nextSibling, target.parentNode) }, list: function(can, root, cb, target) { target = target||can._output - can.core.List(root.list, function(item) { - var ui = can.page.Append(can, target, [{view: [html.ITEM, html.DIV, item.meta.name], onclick: function(event) { - can.base.isFunc(cb) && cb(event, item) || can.page.ClassList.neg(can, ui.list, "hide") - can.onmotion.select(can, target, html.DIV_ITEM, event.target) - }}, {view: html.LIST}]); can.onimport.list(can, item, cb, ui.list) - }) - }, - card: function(can, msg, target) { - can.page.Appends(can, target, msg.Table(function(item) { - return {view: html.ITEM+ice.SP+(item.status||""), list: [ - {view: [wiki.TITLE, html.DIV, item.name]}, - {view: [wiki.CONTENT, html.DIV, item.text]}, - {view: html.ACTION, inner: item.action, onclick: function(event) { - can.run(can.request(event, item), [ctx.ACTION, event.target.name]) - }}, - ]} - })) + can.core.List(root.list, function(item) { var ui = can.page.Append(can, target, [{view: [html.ITEM, html.DIV, item.meta.name], onclick: function(event) { + can.base.isFunc(cb) && cb(event, item) || can.onmotion.toggle(can, ui.list), can.onmotion.select(can, target, html.DIV_ITEM, event.target) + }}, {view: html.LIST}]); can.onimport.list(can, item, cb, ui.list) }) }, }) Volcanos(chat.ONLAYOUT, { @@ -184,4 +169,9 @@ Volcanos(chat.ONEXPORT, { }); return res.join(ice.NL) }, board: function(can) { var msg = can._msg; return msg.Result() }, + title: function(can, title) { can._legend.innerHTML = title + can.sup && can.sup._tabs && (can.sup._tabs.innerHTML = title) + can.sup && can.sup._header_tabs && (can.sup._header_tabs.innerHTML = title) + can.isCmdMode() && can.user.title(title) + }, }) diff --git a/proto.js b/proto.js index 06d888d4..f2464b53 100644 --- a/proto.js +++ b/proto.js @@ -37,6 +37,7 @@ var ice = { MSG_PROCESS: "_process", PROCESS_AGAIN: "_again", + MSG_MODE: "sess.mode", MSG_TITLE: "sess.title", MSG_TOPIC: "sess.topic", MSG_RIVER: "sess.river", MSG_STORM: "sess.storm", MSG_WIDTH: "sess.width", MSG_HEIGHT: "sess.height", MSG_DAEMON: "sess.daemon", MSG_USERNAME: "user.name", MSG_USERNICK: "user.nick", @@ -58,6 +59,7 @@ var ctx = { } var mdb = { DICT: "dict", META: "meta", HASH: "hash", LIST: "list", + DATA: "data", VIEW: "view", ID: "id", KEY: "key", TIME: "time", ZONE: "zone", TYPE: "type", NAME: "name", TEXT: "text", LINK: "link", SCAN: "scan", HELP: "help", SHORT: "short", FIELD: "field", TOTAL: "total", COUNT: "count", LIMIT: "limit", @@ -112,6 +114,7 @@ var nfs = { ZML: "zml", IML: "iml", TXT: "txt", PNG: "png", WEBM: "webm", _CSS: ".css", _JS: ".js", REPOS: "repos", REPLACE: "replace", FROM: "from", TO: "to", + SRC: "src/", } var cli = { PWD: "pwd", SYSTEM: "system", DAEMON: "daemon", ORDER: "order", BUILD: "build", @@ -206,7 +209,7 @@ var html = {PLUGIN_MARGIN: 10, ACTION_HEIGHT: 31, ACTION_MARGIN: 200, FIELDSET: "fieldset", LEGEND: "legend", OPTION: "option", ACTION: "action", OUTPUT: "output", STATUS: "status", FORM_OPTION: "form.option", DIV_ACTION: "div.action", DIV_OUTPUT: "div.output", DIV_STATUS: "div.status", FIELDSET_PANEL: "fieldset.panel", FIELDSET_PLUGIN: "fieldset.plugin", FIELDSET_STORY: "fieldset.story", FIELDSET_INPUT: "fieldset.input", FIELDSET_FLOAT: "fieldset.float", - FIELDSET_HEAD: "fieldset.head", FIELDSET_FOOT: "fieldset.foot", FIELDSET_LEFT: "fieldset.left", FIELDSET_MAIN: "fieldset.main", + FIELDSET_HEAD: "fieldset.head", FIELDSET_FOOT: "fieldset.foot", FIELDSET_LEFT: "fieldset.left", FIELDSET_MAIN: "fieldset.main", FIELDSET_PLUG: "fieldset.plug", OPTION_ARGS: "select.args,input.args,textarea.args", INPUT_ARGS: "input.args,textarea.args", INPUT_BUTTON: "input[type=button]", INPUT_FILE: "input[type=file]", BODY: "body", FORM: "form", SELECT: "select", INPUT: "input", TEXT: "text", FILE: "file", BUTTON: "button", TEXTAREA: "textarea", CLICK: "click", CANCEL: "cancel", SUBMIT: "submit", UPLOAD: "upload", USERNAME: "username", PASSWORD: "password", @@ -214,7 +217,7 @@ var html = {PLUGIN_MARGIN: 10, ACTION_HEIGHT: 31, ACTION_MARGIN: 200, H1: "h1", H2: "h2", H3: "h3", A: "a", LABEL: "label", INNER: "inner", TITLE: "title", SPAN: "span", CODE: "code", DIV: "div", IMG: "img", VIDEO: "video", WSS: "wss", SVG: "svg", CANVAS: "canvas", IFRAME: "iframe", WEBVIEW: "webview", CHROME: "chrome", MOBILE: "mobile", LANDSCAPE: "landscape", - + CLASS: "class", DISPLAY: "display", BLOCK: "block", NONE: "none", OVERFLOW: "overflow", HIDDEN: "hidden", SCROLL: "scroll", FLOAT: "float", CLEAR: "clear", BOTH: "both", PADDING: "padding", BORDER: "border", MARGIN: "margin", MARGIN_TOP: "margin-top", MARGIN_X: "margin-x", MARGIN_Y: "margin-y", HEIGHT: "height", WIDTH: "width", MIN_HEIGHT: "min-height", MAX_HEIGHT: "max-height", MIN_WIDTH: "min-width", MAX_WIDTH: "max-width", LEFT: "left", TOP: "top", RIGHT: "right", BOTTOM: "bottom", @@ -222,6 +225,7 @@ var html = {PLUGIN_MARGIN: 10, ACTION_HEIGHT: 31, ACTION_MARGIN: 200, HOVER: "hover", HOVER_SELECT: "hover,select", LIGHT: "light", DARK: "dark", + PANEL: "panel", VIEW: "view", PLUG: "plug", DIV_PLUG: "div.plug", @@ -295,7 +299,7 @@ var Volcanos = shy({version: window._version||"", iceberg: "/chat/", volcano: "/ key.indexOf("_") == 0 || key.indexOf("user.") == 0 || set(key, item.Option(key)) }): can.core.Item(can.base.isFunc(item)? item(): item, set) }); - set(ice.MSG_HEIGHT, can.ConfHeight()), set(ice.MSG_WIDTH, can.ConfWidth()) + set(ice.MSG_MODE, can.Mode()), set(ice.MSG_HEIGHT, can.ConfHeight()), set(ice.MSG_WIDTH, can.ConfWidth()) return msg }, @@ -306,8 +310,10 @@ var Volcanos = shy({version: window._version||"", iceberg: "/chat/", volcano: "/ } can.runAction(event, cmds[1], cmds.slice(2), cb, true) }, - runActionCommand: function(event, index, args, cb) { can.runAction(event, ice.RUN, can.misc.concat(can, [index], args), cb, true) }, - runAction: function(event, action, args, cb, silent) { can.request(event, {_handle: ice.TRUE}, can.Option()) + runActionCommand: function(event, index, args, cb) { can.request(event)._caller() + can.runAction(event, ice.RUN, can.misc.concat(can, [index], args), cb, true) + }, + runAction: function(event, action, args, cb, silent) { can.request(event, {_handle: ice.TRUE}, can.Option())._caller() can.run(event, can.misc.concat(can, [ctx.ACTION].concat(action), args), cb, silent) },