efront 4.11.2 → 4.11.5
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/#/345/233/275/351/231/205/345/214/226.yml +1 -1
- package/apps/pivot/cert/list.js +3 -7
- package/coms/basic/#loader.js +13 -14
- package/coms/basic/JSAM.js +2 -1
- package/coms/basic/assert.js +5 -3
- package/coms/basic/cookie.js +9 -9
- package/coms/basic/data.js +1 -1
- package/coms/basic/i18n.js +4 -2
- package/coms/basic_/Array2.js +4 -1
- package/coms/compile/Html_test.js +1 -0
- package/coms/compile/Javascript.js +5 -1
- package/coms/compile/Javascript_test.js +14 -2
- package/coms/compile/Program.js +6 -3
- package/coms/compile/common.js +1 -1
- package/coms/docs/markdown.js +5 -3
- package/coms/frame/route.js +15 -15
- package/coms/pivot/pedit.less +23 -1
- package/coms/zimoli/cless.js +2 -1
- package/coms/zimoli/forceUpdate.js +1 -1
- package/coms/zimoli/render.js +44 -64
- package/coms/zimoli/view.less +0 -1
- package/coms//350/214/250/350/217/260/tab.js +35 -0
- package/coms//350/214/250/350/217/260//344/270/212/350/211/262.xht +99 -0
- package/coms//350/214/250/350/217/260//345/205/211/346/240/207.js +1 -0
- package/coms//350/214/250/350/217/260//346/211/253/346/217/217.js +12 -0
- package/coms/{docs/codecolor.js → /350/214/250/350/217/260//346/240/207/347/255/276/345/214/226.js} +2 -1
- package/coms//350/214/250/350/217/260//346/270/262/346/237/223.js +45 -0
- package/coms//350/214/250/350/217/260//347/274/226/350/276/221/346/241/206.xht +132 -0
- package/coms//350/214/250/350/217/260//350/257/255/350/250/200.js +210 -0
- package/coms//350/214/250/350/217/260//350/277/275/345/212/240/345/205/211/346/240/207.js +62 -0
- package/docs//347/273/204/344/273/266.xht +8 -162
- package/package.json +1 -1
- package/public/efront.js +1 -1
- package/readme-en.md +4 -5
- package/readme.md +2 -5
- package/coms/docs/codetext.xht +0 -386
package/coms/zimoli/render.js
CHANGED
|
@@ -109,13 +109,19 @@ function rebuild(element) {
|
|
|
109
109
|
}
|
|
110
110
|
var variableReg = /([^\:\,\+\=\-\!%\^\|\/\&\*\!\;\?\>\<~\{\}\s\[\]\(\)]|\?\s*\.(?=[^\d])|\s*\.\s*)+/g;
|
|
111
111
|
var variableOnlyReg = new RegExp(`^${variableReg.source}$`);
|
|
112
|
+
var getScopeList = function (element) {
|
|
113
|
+
return element.$parentScopes.concat([element.$scope]);
|
|
114
|
+
};
|
|
112
115
|
var createGetter = function (target, search, isprop = true) {
|
|
113
116
|
if (!search) return function () { };
|
|
114
117
|
if (/^\{/.test(search)) search = `(${search})`;
|
|
115
118
|
search = renderExpress(search);
|
|
116
|
-
|
|
117
|
-
if (
|
|
118
|
-
else
|
|
119
|
+
var scopes = getScopeList(target);
|
|
120
|
+
if (isprop) var getter = $$eval.bind(target, search, scopes);
|
|
121
|
+
else if (variableOnlyReg.test(search)) getter = $$eval.bind(target, search + "(event)", scopes);
|
|
122
|
+
else getter = $$eval.bind(target, search, scopes);
|
|
123
|
+
getter.scopes = scopes;
|
|
124
|
+
return getter;
|
|
119
125
|
};
|
|
120
126
|
var createComment = function (renders, type, expression) {
|
|
121
127
|
var comment = document.createComment(`${type} ${expression}`);
|
|
@@ -389,10 +395,11 @@ var parseIfWithRepeat = function (ifExpression, repeatExpression) {
|
|
|
389
395
|
};
|
|
390
396
|
};
|
|
391
397
|
|
|
392
|
-
var mountElementIds = function (element) {
|
|
398
|
+
var mountElementIds = function (element, ids) {
|
|
393
399
|
var scope = element.$scope;
|
|
394
|
-
|
|
395
|
-
|
|
400
|
+
if (!scope) return;
|
|
401
|
+
for (var id of ids) {
|
|
402
|
+
if (isHandled(scope[id]) && scope[id] !== element) throw new Error(i18n`同一个id不能使用两次:` + id);
|
|
396
403
|
scope[id] = element;
|
|
397
404
|
}
|
|
398
405
|
}
|
|
@@ -447,28 +454,6 @@ var structures = {
|
|
|
447
454
|
};
|
|
448
455
|
structures["else-if"] = structures.elseif = structures.else;
|
|
449
456
|
structures["for-each"] = structures.foreach = structures.for = structures.each = structures.repeat;
|
|
450
|
-
var createBinder = function (binder) {
|
|
451
|
-
return function (search) {
|
|
452
|
-
var getter = createGetter(this, `(${search})`);
|
|
453
|
-
var oldValue;
|
|
454
|
-
this.$renders.push(function () {
|
|
455
|
-
var value = getter(this);
|
|
456
|
-
if (shallowEqual(value, oldValue)) return;
|
|
457
|
-
var oldv = oldValue;
|
|
458
|
-
oldValue = value;
|
|
459
|
-
if (isNode(value) || isArray(value)) {
|
|
460
|
-
if (value !== this.firstChild) {
|
|
461
|
-
remove(this.childNodes);
|
|
462
|
-
appendChild(this, value);
|
|
463
|
-
}
|
|
464
|
-
} else {
|
|
465
|
-
if (isEmpty(value)) value = '';
|
|
466
|
-
if (binder(this) !== value) binder(this, value, oldv);
|
|
467
|
-
}
|
|
468
|
-
});
|
|
469
|
-
|
|
470
|
-
}
|
|
471
|
-
}
|
|
472
457
|
var createMapper = function (write, mapper) {
|
|
473
458
|
return function (search) {
|
|
474
459
|
var getter = isArray(search) ? search.map(s => createGetter(this, s)) : createGetter(this, search);
|
|
@@ -596,7 +581,7 @@ var directives = {
|
|
|
596
581
|
var change = getstr || "'value' in this?this.value:this.innerHTML";
|
|
597
582
|
}
|
|
598
583
|
setter2 = null;
|
|
599
|
-
var changeme = $$eval.bind(this, search + "=" + change,
|
|
584
|
+
var changeme = $$eval.bind(this, search + "=" + change, getScopeList(this));
|
|
600
585
|
var onchange = function () {
|
|
601
586
|
changeme(this);
|
|
602
587
|
var value = getter(this);
|
|
@@ -687,12 +672,9 @@ var createEmiter = function (on) {
|
|
|
687
672
|
}
|
|
688
673
|
var res;
|
|
689
674
|
if (scope) {
|
|
690
|
-
|
|
691
|
-
this.$parentScopes.push(temp);
|
|
692
|
-
this.$scope = scope;
|
|
675
|
+
getter.scopes.push(scope);
|
|
693
676
|
res = getter(this, e);
|
|
694
|
-
|
|
695
|
-
this.$scope = temp;
|
|
677
|
+
getter.scopes.pop();
|
|
696
678
|
}
|
|
697
679
|
else {
|
|
698
680
|
res = getter(this, e);
|
|
@@ -750,6 +732,8 @@ function renderRest(element, struct, replacer = element) {
|
|
|
750
732
|
}
|
|
751
733
|
if (binds.src) directives.src.call(element, binds.src);
|
|
752
734
|
if (renders && renders.length) element.$renders.push.apply(element.$renders, renders);
|
|
735
|
+
if (!isElement(replacer)) replacer = element;
|
|
736
|
+
struct.ons.forEach(([on, key, value]) => on.call(element, replacer, key, value));
|
|
753
737
|
}
|
|
754
738
|
|
|
755
739
|
function renderElement(element, scope = element.$scope, parentScopes = element.$parentScopes, once) {
|
|
@@ -774,10 +758,12 @@ function renderElement(element, scope = element.$scope, parentScopes = element.$
|
|
|
774
758
|
}
|
|
775
759
|
element.$parentScopes = parentScopes || [];
|
|
776
760
|
var s = createStructure(element);
|
|
761
|
+
element.$struct = s;
|
|
762
|
+
mountElementIds(element, s.ids);
|
|
777
763
|
if (isEmpty(s.once)) s.once = once;
|
|
778
764
|
element.$eval = $eval;
|
|
779
765
|
}
|
|
780
|
-
|
|
766
|
+
element.$scope = scope;
|
|
781
767
|
if (element.$renderid <= -1) element = renderStructure(element);
|
|
782
768
|
if (!element) return;
|
|
783
769
|
if (!element || element.$renderid < 0 || element.nodeType !== 1) {
|
|
@@ -791,8 +777,9 @@ function renderElement(element, scope = element.$scope, parentScopes = element.$
|
|
|
791
777
|
if (parentNode) {
|
|
792
778
|
if (parentNode.$renderid > 1 || isMounted(parentNode)) element.$renderid = 2;
|
|
793
779
|
}
|
|
780
|
+
var $struct = element.$struct;
|
|
794
781
|
element.$renders = element.$renders || element.renders ? [].concat(element.$renders || [], element.renders || []) : [];
|
|
795
|
-
var { copys, binds, once } =
|
|
782
|
+
var { copys, binds, once } = $struct;
|
|
796
783
|
if (once) element.$renderid = 9;
|
|
797
784
|
if (binds.src) {
|
|
798
785
|
element.$src = parseRepeat(binds.src);
|
|
@@ -802,15 +789,18 @@ function renderElement(element, scope = element.$scope, parentScopes = element.$
|
|
|
802
789
|
var constructor = getFromScopes(tagName, scope, parentScopes);
|
|
803
790
|
if (isFunction(constructor)) {
|
|
804
791
|
var replacer = constructor.call(scope, element, scope, parentScopes);
|
|
805
|
-
if (
|
|
806
|
-
|
|
807
|
-
|
|
792
|
+
if (element === replacer) {
|
|
793
|
+
var struct1 = createStructure(element, false);
|
|
794
|
+
renderRest(element, struct1);
|
|
795
|
+
element.$scope = scope;
|
|
796
|
+
}
|
|
797
|
+
else if (isNode(replacer)) {
|
|
808
798
|
if (isElement(replacer) && !replacer.$renderid) {
|
|
799
|
+
if (!replacer.$scope) replacer.$scope = scope;
|
|
800
|
+
if (!replacer.$parentScopes) replacer.$parentScopes = parentScopes;
|
|
809
801
|
createStructure(replacer);
|
|
810
|
-
replacer.$struct = mergeStruct(element.$struct, replacer.$struct);
|
|
811
802
|
if (replacer.children && replacer.children.length) renderElement(replacer.children, replacer.$scope, replacer.$parentScopes, once);
|
|
812
803
|
renderRest(replacer, replacer.$struct);
|
|
813
|
-
replacer.$struct.ons.forEach(([on, key, value]) => on.call(replacer, replacer, key, value));
|
|
814
804
|
}
|
|
815
805
|
copyAttribute(replacer, copys);
|
|
816
806
|
if (nextSibling) appendChild.before(nextSibling, replacer);
|
|
@@ -827,18 +817,12 @@ function renderElement(element, scope = element.$scope, parentScopes = element.$
|
|
|
827
817
|
if (element.children && element.children.length) renderElement(element.children, scope, parentScopes, once);
|
|
828
818
|
}
|
|
829
819
|
if (!isFirstRender) return element;
|
|
830
|
-
renderRest(element,
|
|
820
|
+
renderRest(element, $struct, replacer);
|
|
831
821
|
if (isNode(replacer) && replacer !== element) {
|
|
832
822
|
if (!replacer.$renders) replacer.$renders = [];
|
|
833
823
|
replacer.$renders.push.apply(replacer.$renders, element.$renders);
|
|
834
|
-
if (replacer.$struct && replacer.$struct !== element.$struct) {
|
|
835
|
-
element.$struct.ons.forEach(([on, key, value]) => on.call(element, replacer, key, value));
|
|
836
|
-
}
|
|
837
824
|
element = replacer;
|
|
838
825
|
}
|
|
839
|
-
else {
|
|
840
|
-
element.$struct.ons.forEach(([on, key, value]) => on.call(element, element, key, value));
|
|
841
|
-
}
|
|
842
826
|
if (element.$renders.length) {
|
|
843
827
|
if (element.$renderid !== 9) {
|
|
844
828
|
onmounted(element, addRenderElement);
|
|
@@ -857,26 +841,22 @@ var createEval = function (deep) {
|
|
|
857
841
|
while (deep-- > 0) {
|
|
858
842
|
context[deep] = `with($parentScopes[${deep}])`;
|
|
859
843
|
}
|
|
860
|
-
return new Function("$parentScopes", "
|
|
844
|
+
return new Function("$parentScopes", "code", "event", `${context.join('')}return eval(code)`);
|
|
861
845
|
};
|
|
862
846
|
var evalcontexts = [createEval(0)];
|
|
863
847
|
|
|
864
|
-
function $$eval(search,
|
|
865
|
-
var
|
|
866
|
-
if (needpop) {
|
|
867
|
-
this.$parentScopes.push(this.$scope);
|
|
868
|
-
this.$scope = scope;
|
|
869
|
-
}
|
|
870
|
-
var length = this.$parentScopes ? this.$parentScopes.length : 0;
|
|
848
|
+
function $$eval(search, scopes, target = this, event) {
|
|
849
|
+
var length = scopes.length;
|
|
871
850
|
if (!evalcontexts[length]) evalcontexts[length] = createEval(length);
|
|
872
851
|
var eval2 = evalcontexts[length];
|
|
873
|
-
var res = eval2.call(target,
|
|
874
|
-
if (needpop) this.$scope = this.$parentScopes.pop();
|
|
852
|
+
var res = eval2.call(target, scopes, search, event);
|
|
875
853
|
return res;
|
|
876
854
|
}
|
|
877
855
|
|
|
878
856
|
function $eval(search, scope, event) {
|
|
879
|
-
|
|
857
|
+
var scopes = getScopeList(this);
|
|
858
|
+
if (isHandled(scope) && scope !== this.$scope) scopes.push(scope);
|
|
859
|
+
return $$eval.call(this, search, scopes, this, event);
|
|
880
860
|
}
|
|
881
861
|
|
|
882
862
|
var merge = function (dst, src) {
|
|
@@ -938,9 +918,9 @@ var pushid = function (ids, name) {
|
|
|
938
918
|
if (name1 !== name) ids.push(name1);
|
|
939
919
|
};
|
|
940
920
|
|
|
941
|
-
function createStructure(element) {
|
|
921
|
+
function createStructure(element, useExists) {
|
|
942
922
|
if (isArrayLike(element)) return Array.prototype.map.call(element, createStructure);
|
|
943
|
-
if (element.$struct) return element.$struct;
|
|
923
|
+
if (useExists !== false && element.$struct) return element.$struct;
|
|
944
924
|
if (element.nodeType !== 1) return;
|
|
945
925
|
// 处理结构流
|
|
946
926
|
var attributes = element.attributes;
|
|
@@ -1009,7 +989,7 @@ function createStructure(element) {
|
|
|
1009
989
|
// ng-html,ng-src,ng-text,ng-model,ng-style,ng-class,...
|
|
1010
990
|
var key = name.replace(/^(ng|v|[^\_\:\.]*?)\-|^[\:\_\.]|^v\-bind\:/i, "").toLowerCase();
|
|
1011
991
|
if (directives.hasOwnProperty(key) || /^([\_\:\.]|v\-bind\:)/.test(name)) {
|
|
1012
|
-
binds[key] = value;
|
|
992
|
+
if (value) binds[key] = value;
|
|
1013
993
|
element.removeAttribute(name);
|
|
1014
994
|
}
|
|
1015
995
|
// ng-click on-click v-click @click @mousedown ...
|
|
@@ -1017,11 +997,11 @@ function createStructure(element) {
|
|
|
1017
997
|
var match = emiter_reg.exec(name);
|
|
1018
998
|
var ngon = (match[1] || match[0]).toLowerCase() === 'once' ? 'once' : 'on';
|
|
1019
999
|
element.removeAttribute(name);
|
|
1020
|
-
ons.push([emiters[ngon], name.replace(emiter_reg, ''), value]);
|
|
1000
|
+
if (value) ons.push([emiters[ngon], name.replace(emiter_reg, ''), value]);
|
|
1021
1001
|
}
|
|
1022
1002
|
// placeholder_ href_ checked_ ...
|
|
1023
1003
|
else if (/[_@\:\.]$/.test(name)) {
|
|
1024
|
-
attr1[name.replace(/[_@\:\.]$/, "")] = value;
|
|
1004
|
+
if (value) attr1[name.replace(/[_@\:\.]$/, "")] = value;
|
|
1025
1005
|
element.removeAttribute(name);
|
|
1026
1006
|
}
|
|
1027
1007
|
// title alt name type placeholder href checked ...
|
package/coms/zimoli/view.less
CHANGED
|
@@ -0,0 +1,35 @@
|
|
|
1
|
+
var ensp = s => Array(s + 1).join("\u2002"/*&ensp*/);
|
|
2
|
+
var getEnspBefore = function (node) {
|
|
3
|
+
if (!node) return 0;
|
|
4
|
+
while (node && (node.nodeType !== 1 || !/^br$/i.test(node.tagName))) {
|
|
5
|
+
node = node.previousSibling;
|
|
6
|
+
}
|
|
7
|
+
if (node) {
|
|
8
|
+
var next = node.nextSibling;
|
|
9
|
+
if (next) {
|
|
10
|
+
next = /^[\u2002\u0020\u00a0]+/.exec(next.nodeValue);
|
|
11
|
+
if (next) return next[0].length;
|
|
12
|
+
}
|
|
13
|
+
}
|
|
14
|
+
};
|
|
15
|
+
return function (forcetab) {
|
|
16
|
+
var selection = document.getSelection();
|
|
17
|
+
var { anchorNode, anchorOffset } = selection;
|
|
18
|
+
if (anchorNode.nodeType === 1) {
|
|
19
|
+
var child = anchorNode.childNodes[anchorOffset];
|
|
20
|
+
var spaceSize = 4;
|
|
21
|
+
if (child.nodeType === 1) spaceSize = getEnspBefore(child?.previousSibling?.previousSibling || anchorNode);
|
|
22
|
+
if (!spaceSize && forcetab !== false) spaceSize = 4;
|
|
23
|
+
if (!spaceSize) return;
|
|
24
|
+
var space = document.createTextNode(ensp(spaceSize));
|
|
25
|
+
anchorNode.insertBefore(space, child);
|
|
26
|
+
selection.setBaseAndExtent(space, spaceSize, space, spaceSize);
|
|
27
|
+
}
|
|
28
|
+
else if (anchorNode.nodeType === 3) {
|
|
29
|
+
if (forcetab === 0) return;
|
|
30
|
+
var spaceSize = (4 - anchorOffset % 4);
|
|
31
|
+
anchorNode.nodeValue = anchorNode.nodeValue.slice(0, anchorOffset) + ensp(spaceSize) + anchorNode.nodeValue.slice(anchorOffset);
|
|
32
|
+
anchorOffset += spaceSize;
|
|
33
|
+
selection.setBaseAndExtent(anchorNode, anchorOffset, anchorNode, anchorOffset);
|
|
34
|
+
}
|
|
35
|
+
};
|
|
@@ -0,0 +1,99 @@
|
|
|
1
|
+
<style>
|
|
2
|
+
:scope {
|
|
3
|
+
white-space: pre-wrap;
|
|
4
|
+
line-height: 1.36;
|
|
5
|
+
word-break: break-all;
|
|
6
|
+
padding: 10px 20px;
|
|
7
|
+
border-radius: 3px;
|
|
8
|
+
display: inline-block;
|
|
9
|
+
background: #2c2c2c;
|
|
10
|
+
color: #d4d4d4;
|
|
11
|
+
font-family: Consolas, "Courier New", monospace;
|
|
12
|
+
vertical-align: top;
|
|
13
|
+
text-decoration-line: none;
|
|
14
|
+
tab-size: 4;
|
|
15
|
+
}
|
|
16
|
+
|
|
17
|
+
stamp {
|
|
18
|
+
color: #808080;
|
|
19
|
+
}
|
|
20
|
+
|
|
21
|
+
strap,
|
|
22
|
+
value {
|
|
23
|
+
color: #569cd6;
|
|
24
|
+
}
|
|
25
|
+
|
|
26
|
+
regexp {
|
|
27
|
+
color: #d16969;
|
|
28
|
+
}
|
|
29
|
+
|
|
30
|
+
text {
|
|
31
|
+
color: #ce9178;
|
|
32
|
+
}
|
|
33
|
+
|
|
34
|
+
flow {
|
|
35
|
+
color: #c586c0;
|
|
36
|
+
}
|
|
37
|
+
|
|
38
|
+
digit {
|
|
39
|
+
color: #b5cea8;
|
|
40
|
+
}
|
|
41
|
+
|
|
42
|
+
label {
|
|
43
|
+
color: #569cd6;
|
|
44
|
+
}
|
|
45
|
+
|
|
46
|
+
selector {
|
|
47
|
+
color: #d7ba7d;
|
|
48
|
+
}
|
|
49
|
+
|
|
50
|
+
@deep(@num, @color) {
|
|
51
|
+
deep@num {
|
|
52
|
+
color: @color;
|
|
53
|
+
}
|
|
54
|
+
}
|
|
55
|
+
|
|
56
|
+
@deep(0, #ffd700);
|
|
57
|
+
@deep(1, #da70d6);
|
|
58
|
+
@deep(2, #179fff);
|
|
59
|
+
@deep(3, #ffd700);
|
|
60
|
+
@deep(4, #da70d6);
|
|
61
|
+
@deep(5, #179fff);
|
|
62
|
+
@deep(6, #ffd700);
|
|
63
|
+
@deep(7, #da70d6);
|
|
64
|
+
@deep(8, #179fff);
|
|
65
|
+
@deep(9, #ffd700);
|
|
66
|
+
@deep(10, #da70d6);
|
|
67
|
+
@deep(11, #179fff);
|
|
68
|
+
@deep(12, #ffd700);
|
|
69
|
+
@deep(13, #da70d6);
|
|
70
|
+
@deep(14, #179fff);
|
|
71
|
+
@deep(15, #ffd700);
|
|
72
|
+
@deep(16, #da70d6);
|
|
73
|
+
@deep(17, #179fff);
|
|
74
|
+
|
|
75
|
+
express,
|
|
76
|
+
property {
|
|
77
|
+
color: #9cdcfe;
|
|
78
|
+
}
|
|
79
|
+
|
|
80
|
+
invoke,
|
|
81
|
+
method {
|
|
82
|
+
color: #dcdcaa;
|
|
83
|
+
}
|
|
84
|
+
|
|
85
|
+
predef {
|
|
86
|
+
color: #4ec9b0;
|
|
87
|
+
}
|
|
88
|
+
|
|
89
|
+
outside {
|
|
90
|
+
color: #4fc1ff;
|
|
91
|
+
}
|
|
92
|
+
|
|
93
|
+
comment {
|
|
94
|
+
color: #6a9955;
|
|
95
|
+
}
|
|
96
|
+
</style>
|
|
97
|
+
<script>
|
|
98
|
+
茨菰$渲染;
|
|
99
|
+
</script>
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
return "\u0080";
|
|
@@ -0,0 +1,12 @@
|
|
|
1
|
+
var { STAMP, PIECE, SPACE } = compile$common;
|
|
2
|
+
return function (a, type) {
|
|
3
|
+
if (光标) var index = a.indexOf(光标);
|
|
4
|
+
if (index >= 0) a = a.slice(0, index) + a.slice(index + 1);
|
|
5
|
+
var c = compile$scanner2(a, type);
|
|
6
|
+
if (index >= 0) {
|
|
7
|
+
c.scoped;
|
|
8
|
+
var patched = 追加光标(c, index, 光标);
|
|
9
|
+
if (!patched) c.push({ type: SPACE, text: 光标 });
|
|
10
|
+
}
|
|
11
|
+
return c;
|
|
12
|
+
}
|
|
@@ -0,0 +1,45 @@
|
|
|
1
|
+
|
|
2
|
+
var { SCOPED, QUOTED, SPACE, STAMP, STRAP, EXPRESS, PROPERTY } = compile$common;
|
|
3
|
+
var encode = function (text) {
|
|
4
|
+
return text.replace(/[\<\>\|]/g, a => `&#${a.charCodeAt()};`);
|
|
5
|
+
};
|
|
6
|
+
|
|
7
|
+
var rows = function (type, text) {
|
|
8
|
+
if (typeof text !== 'string') {
|
|
9
|
+
console.log(text)
|
|
10
|
+
return [];
|
|
11
|
+
}
|
|
12
|
+
type = type.toLowerCase();
|
|
13
|
+
if (type in 语言) {
|
|
14
|
+
var c = 语言[type](text);
|
|
15
|
+
标签化(c, encode);
|
|
16
|
+
text = c.toString();
|
|
17
|
+
|
|
18
|
+
}
|
|
19
|
+
else text = encode(text);
|
|
20
|
+
|
|
21
|
+
var codes = text.split(/\r\n|\r|\n/);
|
|
22
|
+
var minSpace = Infinity;
|
|
23
|
+
for (var c of codes) {
|
|
24
|
+
var m = /^\s+/.exec(c);
|
|
25
|
+
if (!m) {
|
|
26
|
+
minSpace = 0;
|
|
27
|
+
break;
|
|
28
|
+
}
|
|
29
|
+
if (m[0].length < minSpace) {
|
|
30
|
+
minSpace = m[0].length;
|
|
31
|
+
}
|
|
32
|
+
}
|
|
33
|
+
if (minSpace > 0 && minSpace < Infinity) codes = codes.map(c => /^\s+/.test(c) ? c.slice(minSpace) : c);
|
|
34
|
+
return codes;
|
|
35
|
+
}
|
|
36
|
+
function 茨菰(type, text) {
|
|
37
|
+
return `<code type=${type}>${rows(type, text).join("<br/>")}</code>`;
|
|
38
|
+
}
|
|
39
|
+
茨菰.text = function (type, text) {
|
|
40
|
+
return `${rows(type, text).join("<br/>")}`;
|
|
41
|
+
};
|
|
42
|
+
|
|
43
|
+
茨菰.rows = rows;
|
|
44
|
+
茨菰.encode = encode;
|
|
45
|
+
return 茨菰;
|
|
@@ -0,0 +1,132 @@
|
|
|
1
|
+
<编辑框 e-class="上色.className" e-style="{whiteSpace:'pre'}" onkeyup="!event.isComposing&&updatecode(event)"
|
|
2
|
+
onkeydown.tab="keytab(event)" onkeyup.enter="tab(false)">
|
|
3
|
+
</编辑框>
|
|
4
|
+
<script>
|
|
5
|
+
var coder = this;
|
|
6
|
+
care(coder, function ([text, type]) {
|
|
7
|
+
try {
|
|
8
|
+
var colored = 上色.text(type, text);
|
|
9
|
+
coder.innerHTML = colored;
|
|
10
|
+
coder.type = type;
|
|
11
|
+
} catch {
|
|
12
|
+
if (typeof text === 'string') coder.innerHTML = 渲染.encode(text);
|
|
13
|
+
}
|
|
14
|
+
})
|
|
15
|
+
var markAnchorOffset = function () {
|
|
16
|
+
var { anchorNode, anchorOffset } = document.getSelection();
|
|
17
|
+
if (!anchorNode || !coder) return;
|
|
18
|
+
var [c] = coder.children;
|
|
19
|
+
if (anchorNode.nodeType === 1) {
|
|
20
|
+
var node = document.createTextNode(光标);
|
|
21
|
+
anchorNode.insertBefore(node, anchorNode.childNodes[anchorOffset])
|
|
22
|
+
}
|
|
23
|
+
else if (anchorNode.nodeType === 3) {
|
|
24
|
+
anchorNode.nodeValue = anchorNode.nodeValue.slice(0, anchorOffset) + 光标 + anchorNode.nodeValue.slice(anchorOffset);
|
|
25
|
+
}
|
|
26
|
+
};
|
|
27
|
+
var unmarkAnchorOffset = function () {
|
|
28
|
+
var c = coder;
|
|
29
|
+
var node = c.firstChild;
|
|
30
|
+
while (node) {
|
|
31
|
+
if (node.nodeType === 1) {
|
|
32
|
+
if (node.innerText.indexOf(光标) >= 0) {
|
|
33
|
+
node = node.firstChild;
|
|
34
|
+
continue;
|
|
35
|
+
}
|
|
36
|
+
}
|
|
37
|
+
else if (node.nodeType === 3) {
|
|
38
|
+
if (node.nodeValue.indexOf(光标) >= 0) break;
|
|
39
|
+
}
|
|
40
|
+
node = node.nextSibling;
|
|
41
|
+
}
|
|
42
|
+
if (node) {
|
|
43
|
+
var offset = node.nodeValue.indexOf(光标);
|
|
44
|
+
node.nodeValue = node.nodeValue.slice(0, offset) + node.nodeValue.slice(offset + 1);
|
|
45
|
+
document.getSelection().setBaseAndExtent(node, offset, node, offset);
|
|
46
|
+
if (!node.nodeValue) {
|
|
47
|
+
remove(node);
|
|
48
|
+
}
|
|
49
|
+
}
|
|
50
|
+
}
|
|
51
|
+
var getAnchorOffset = function () {
|
|
52
|
+
var { anchorNode, anchorOffset } = document.getSelection();
|
|
53
|
+
var [c] = coder.children;
|
|
54
|
+
if (anchorNode === c || !anchorNode) return -anchorOffset;
|
|
55
|
+
var sibling = anchorNode.previousSibling ? anchorNode.previousSibling : anchorNode.parentNode.previousSibling;
|
|
56
|
+
while (sibling && sibling !== c) {
|
|
57
|
+
switch (sibling.nodeType) {
|
|
58
|
+
case 1:
|
|
59
|
+
anchorOffset += sibling.innerText.length || 1;
|
|
60
|
+
break;
|
|
61
|
+
case 3:
|
|
62
|
+
anchorOffset += sibling.nodeValue.length;
|
|
63
|
+
break;
|
|
64
|
+
}
|
|
65
|
+
sibling = sibling.previousSibling ? sibling.previousSibling : sibling.parentNode.previousSibling;
|
|
66
|
+
}
|
|
67
|
+
return anchorOffset;
|
|
68
|
+
};
|
|
69
|
+
var setAnchorOffset = function (anchorOffset) {
|
|
70
|
+
var [c] = coder.children;
|
|
71
|
+
if (anchorOffset < 0) {
|
|
72
|
+
anchorOffset = -anchorOffset;
|
|
73
|
+
if (anchorOffset > c.childNodes.length) anchorOffset = c.childNodes.length;
|
|
74
|
+
return document.getSelection().setBaseAndExtent(c, anchorOffset, c, anchorOffset);
|
|
75
|
+
}
|
|
76
|
+
var offset = anchorOffset;
|
|
77
|
+
var child = c.firstChild;
|
|
78
|
+
while (child) {
|
|
79
|
+
var delta = 0;
|
|
80
|
+
switch (child.nodeType) {
|
|
81
|
+
case 1:
|
|
82
|
+
delta = child.innerText.length || 1;
|
|
83
|
+
break;
|
|
84
|
+
case 3:
|
|
85
|
+
delta = child.nodeValue.length;
|
|
86
|
+
break;
|
|
87
|
+
}
|
|
88
|
+
if (delta >= offset) {
|
|
89
|
+
if (child.nodeType === 1) {
|
|
90
|
+
if (child.firstChild) {
|
|
91
|
+
child = child.firstChild;
|
|
92
|
+
continue;
|
|
93
|
+
}
|
|
94
|
+
offset -= 1;
|
|
95
|
+
break;
|
|
96
|
+
}
|
|
97
|
+
break;
|
|
98
|
+
}
|
|
99
|
+
offset -= delta;
|
|
100
|
+
if (offset <= 0) break;
|
|
101
|
+
child = child.nextSibling;
|
|
102
|
+
}
|
|
103
|
+
if (!child) child = c, offset = c.childNodes.length;
|
|
104
|
+
return document.getSelection().setBaseAndExtent(child, offset, child, offset);
|
|
105
|
+
}
|
|
106
|
+
var trimspace = (_, a) => a ? "" : " ";
|
|
107
|
+
var jstext = "";
|
|
108
|
+
var 更新 = function (colored) {
|
|
109
|
+
var { scrollTop, scrollLeft } = coder;
|
|
110
|
+
coder.innerHTML = colored;
|
|
111
|
+
coder.scrollTop = scrollTop;
|
|
112
|
+
coder.scrollLeft = scrollLeft;
|
|
113
|
+
};
|
|
114
|
+
var updatecode = lazy(function (event) {
|
|
115
|
+
var trimreg = /[\s\u00a0\u2002\u0080]+([\}\{\;\[\]\(\)\,\>\<\+\-\*\&\^\/%!~:?])*/g;
|
|
116
|
+
var innerText = coder.innerText;
|
|
117
|
+
if (jstext.replace(trimreg, trimspace).trim() === innerText.replace(trimreg, trimspace).trim()) return;
|
|
118
|
+
jstext = innerText;
|
|
119
|
+
markAnchorOffset();
|
|
120
|
+
var innerText = coder.innerText;
|
|
121
|
+
unmarkAnchorOffset();
|
|
122
|
+
var text = 上色.text(coder.type, innerText);
|
|
123
|
+
更新(text);
|
|
124
|
+
unmarkAnchorOffset();
|
|
125
|
+
return;
|
|
126
|
+
});
|
|
127
|
+
var keytab = function (event) {
|
|
128
|
+
event.preventDefault();
|
|
129
|
+
tab();
|
|
130
|
+
};
|
|
131
|
+
|
|
132
|
+
</script>
|