efront 4.34.1 → 4.35.1

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.
Files changed (48) hide show
  1. package/coms/basic/Matrix.js +3 -1
  2. package/coms/basic/color.js +258 -78
  3. package/coms/basic/color_test.js +23 -2
  4. package/coms/basic/crc.js +6 -2
  5. package/coms/basic/data.js +3 -3
  6. package/coms/basic/decodeASN1.js +2 -2
  7. package/coms/basic/math.js +321 -0
  8. package/coms/basic/math.md +265 -0
  9. package/coms/basic/math_test.xht +56 -0
  10. package/coms/basic/pinyin.js +40 -0
  11. package/coms/basic/pinyin_test.js +40 -0
  12. package/coms/basic/wait.js +1 -1
  13. package/coms/basic_/JSON.js +24 -4
  14. package/coms/compile/Html.js +1 -0
  15. package/coms/compile/Javascript.js +14 -0
  16. package/coms/compile/Javascript_test.js +4 -3
  17. package/coms/compile/Program.js +82 -45
  18. package/coms/compile/autoenum.js +498 -138
  19. package/coms/compile/autoenum_test.js +70 -4
  20. package/coms/compile/autoeval.js +616 -18
  21. package/coms/compile/autoeval_test.js +55 -2
  22. package/coms/compile/common.js +27 -15
  23. package/coms/compile/common_test.js +12 -2
  24. package/coms/compile/downLevel.js +60 -7
  25. package/coms/compile/downLevel_test.js +22 -8
  26. package/coms/compile/powermap.js +2 -2
  27. package/coms/compile/rescan.js +2 -2
  28. package/coms/compile/scanner2.js +25 -1
  29. package/coms/compile/translate.js +18 -7
  30. package/coms/compile/unstruct.js +44 -2
  31. package/coms/compile/unstruct_test.js +14 -9
  32. package/coms/compile//347/256/227/345/274/217.js +276 -0
  33. package/coms/compile//347/256/227/345/274/217_test.js +26 -0
  34. package/coms/compile//347/264/240/351/246/250.js +60 -23
  35. package/coms/compile//347/264/240/351/246/250_test.js +8 -3
  36. package/coms/docs/markdown.js +4 -0
  37. package/coms/frame/ChatRTC.js +60 -18
  38. package/coms/frame/chat-rtc.xht +20 -18
  39. package/coms/frame/chat.js +38 -21
  40. package/coms/frame/chat.less +8 -3
  41. package/coms/reptile/colors.js +1 -0
  42. package/coms/zimoli/prompt.js +12 -2
  43. package/coms/zimoli/render.js +0 -1
  44. package/coms//350/214/250/350/217/260//344/270/212/350/211/262.xht +4 -0
  45. package/coms//350/214/250/350/217/260//346/240/207/347/255/276/345/214/226.js +14 -4
  46. package/package.json +1 -1
  47. package/public/efront.js +1 -1
  48. package/public//346/226/207/344/273/266/347/263/273/347/273/237//344/270/273/351/241/265.jsp +2 -2
@@ -1,11 +1,12 @@
1
1
  var unstruct = require('./unstruct');
2
2
  var scanner2 = require("./scanner2");
3
3
  var { createString, STRAP } = require("./common");
4
- var r = 12;
4
+ var r = 13;
5
5
  var innerjs = new Javascript;
6
6
  innerjs.defaultType = STRAP;
7
7
  function test(codetext, expect, ret = false) {
8
8
  var code = scanner2(codetext, innerjs), i = -2;
9
+ code.scoped;
9
10
  try { code = unstruct(code, () => ++i >= 0 ? "_" + i : '_', ret && "@"); } catch (e) { console.log(r); throw e }
10
11
  assert(code.map(createString).join(";\r\n "), expect, r++);
11
12
  }
@@ -16,6 +17,8 @@ test('if(this){}', `if (!this) return [1, 0]; return [1, 0]`);
16
17
  test('if(!this){}', `if (this) return [1, 0]; return [1, 0]`);
17
18
  test('if(arguments){}', `if (!arguments) return [1, 0]; return [1, 0]`);
18
19
  test('a | c & b', "_ = c & b, a | _");
20
+ test('a || c && b', "_ = a @re _ = c @rz b");
21
+ test('a && c || b', "_ = a @rz _ = c;\r\n @re b");
19
22
  test('a + !c', "_ = !c, a + _");
20
23
  test('a + b * c', "_ = b * c, a + _");
21
24
  test('a + b * !c', "_ = !c, _ = b * _, a + _");
@@ -71,15 +74,16 @@ test("for(var a in b) a.push()", "for (var a in b) a.push()", true);
71
74
  test("for(;;)", "return [0, 0]", true);
72
75
  test("for(a in b)", "for (a in b)", true);
73
76
  test("for(a of b)", "for (a of b)", true);
74
- test(`var [size, names] = memery.SIGNITEMS? await enpack(readfrom, hd, 7, key, cert) : await enpack(readfrom, hd, 7);`, 'if (!memery.SIGNITEMS) return [2, 0]; _ = enpack(readfrom, hd, 7, key, cert); return [_, 1];\r\n _ = @; [size, names] = _; return [3, 0];\r\n _ = enpack(readfrom, hd, 7); return [_, 1];\r\n _ = @; [size, names] = _; return [1, 0] ', true)
77
+ test(`var [size, names] = memery.SIGNITEMS? await enpack(readfrom, hd, 7, key, cert) : await enpack(readfrom, hd, 7);`, 'if (!memery.SIGNITEMS) return [2, 0]; _ = enpack(readfrom, hd, 7, key, cert); return [_, 1];\r\n _ = @; [size, names] = _; return [3, 0];\r\n _ = enpack(readfrom, hd, 7); return [_, 1];\r\n _ = @; [size, names] = _; return [1, 0]', true)
75
78
  test("for await(a of b)", "for await (a of b)", true);
76
79
  test("for(a = os[Symbol.iterator] || os[Symbol.asyncIterator] || Array.prototype[Symbol.iterator], a = a.call(os), b = a.next(); !b.done && (o = b.value, true); b = a.next())", "_ = Symbol.iterator; _ = os[_]; if (_) return [1, 0]; _ = Symbol.asyncIterator; _ = os[_]; if (_) return [1, 0]; _ = Symbol.iterator; _ = Array.prototype[_];\r\n a = _; a = a.call(os); b = a.next(); return [1, 0];\r\n _ = !b.done; if (!_) return [1, 0]; o = b.value; _ = true;\r\n if (!_) return [1, 0]; b = a.next(); return [-1, 0]", true);
77
- test("for(a=0;a<1;a++)if(a==0)continue\r\n else a=1", `a = 0; return [1, 0];\r\n _ = a < 1; if (!_) return [2, 0]; _ = a == 0; if (_) return [1, 0]; a = 1; return [1, 0];\r\n _ = a++; return [-1, 0]`, true);
78
- test("for(a=0;a<1;a++)if(a==0){continue} else {a=1}", `a = 0; return [1, 0];\r\n _ = a < 1; if (!_) return [3, 0]; _ = a == 0; if (!_) return [1, 0]; return [2, 0];\r\n a = 1; return [1, 0];\r\n _ = a++; return [-2, 0]`, true);
79
- test("for(a=0;a<1;a++){if(a==0){a=2;continue} else if(b) {a=1;continue} c=3}", `a = 0; return [1, 0];\r\n _ = a < 1; if (!_) return [4, 0]; _ = a == 0; if (!_) return [1, 0]; a = 2; return [3, 0];\r\n if (!b) return [1, 0]; a = 1; return [2, 0];\r\n c = 3; return [1, 0];\r\n _ = a++; return [-3, 0]`, true);
80
- test("for(a=0;a<10;a++) await a", "a = 0; return [1, 0];\r\n _ = a < 10; if (!_) return [2, 0]; _ = a; return [_, 1];\r\n _ = @; _ = a++; return [-1, 0]", true);
81
- test("for(a=0;a<10;a++) await a, await b", "a = 0; return [1, 0];\r\n _ = a < 10; if (!_) return [3, 0]; _ = a; return [_, 1];\r\n _ = @; _ = b; return [_, 1];\r\n _ = @; _ = a++; return [-2, 0]", true);
82
- test("for(a=0;b=2,a<10;a++) await a, await b", "a = 0; return [1, 0];\r\n b = 2; _ = a < 10; if (!_) return [3, 0]; _ = a; return [_, 1];\r\n _ = @; _ = b; return [_, 1];\r\n _ = @; _ = a++; return [-2, 0]", true);
80
+ test("for(a=0;a<1;a++)", `a = 0; return [1, 0];\r\n _ = a < 1; if (!_) return [1, 0]; a++; return [0, 0]`, true);
81
+ test("for(a=0;a<1;a++)if(a==0)continue\r\n else a=1", `a = 0; return [1, 0];\r\n _ = a < 1; if (!_) return [2, 0]; _ = a == 0; if (_) return [1, 0]; a = 1; return [1, 0];\r\n a++; return [-1, 0]`, true);
82
+ test("for(a=0;a<1;a++)if(a==0){continue} else {a=1}", `a = 0; return [1, 0];\r\n _ = a < 1; if (!_) return [3, 0]; _ = a == 0; if (!_) return [1, 0]; return [2, 0];\r\n a = 1; return [1, 0];\r\n a++; return [-2, 0]`, true);
83
+ test("for(a=0;a<1;a++){if(a==0){a=2;continue} else if(b) {a=1;continue} c=3}", `a = 0; return [1, 0];\r\n _ = a < 1; if (!_) return [4, 0]; _ = a == 0; if (!_) return [1, 0]; a = 2; return [3, 0];\r\n if (!b) return [1, 0]; a = 1; return [2, 0];\r\n c = 3; return [1, 0];\r\n a++; return [-3, 0]`, true);
84
+ test("for(a=0;a<10;a++) await a", "a = 0; return [1, 0];\r\n _ = a < 10; if (!_) return [2, 0]; _ = a; return [_, 1];\r\n _ = @; a++; return [-1, 0]", true);
85
+ test("for(a=0;a<10;a++) await a, await b", "a = 0; return [1, 0];\r\n _ = a < 10; if (!_) return [3, 0]; _ = a; return [_, 1];\r\n _ = @; _ = b; return [_, 1];\r\n _ = @; a++; return [-2, 0]", true);
86
+ test("for(a=0;b=2,a<10;a++) await a, await b", "a = 0; return [1, 0];\r\n b = 2; _ = a < 10; if (!_) return [3, 0]; _ = a; return [_, 1];\r\n _ = @; _ = b; return [_, 1];\r\n _ = @; a++; return [-2, 0]", true);
83
87
  test("while(a) await b", "if (!a) return [2, 0]; _ = b; return [_, 1];\r\n _ = @; return [-1, 0]", true);
84
88
  test("do{await b}while(a)", "_ = b; return [_, 1];\r\n _ = @; if (a) return [-1, 0]", true);
85
89
  test("switch(a){case 1:}", "if (a === 1) return [1, 0]; return [1, 0]", true);
@@ -175,5 +179,6 @@ test(`a.b.c += menus[0][str_name] += [str__v_, version[0], str__v_1][str_join]("
175
179
  test(`menus[0].c += menus[0][str_name] += [str__v_, version[0], str__v_1][str_join]("")`, `_ = menus[0]; _0 = menus[0]; _1 = version[0]; _1 = [str__v_, _1, str__v_1]; _1 = _1[str_join](""); _2 = _0[str_name], _2 = _2 + _1; _0[str_name] = _2; _3 = _.c, _3 = _3 + _2; _.c = _3`);
176
180
  test(`new Array(2).join("") + 1`, `_0 = new Array(2); _ = _0.join(""), _ + 1`);
177
181
  test(`new window.Array(2).join("") + 1`, `_0 = new window.Array(2); _ = _0.join(""), _ + 1`);
182
+ test(`readbuff(h, offset += 2, length)`, `_ = offset + 2; offset = _; readbuff(h, _, length)`);
178
183
  unstruct.debug = true; r++;
179
- test(`readbuff(h, offset += 2, length)`, `_ = offset + 2; offset = _; readbuff(h, _, length)`);
184
+ test('a[i] = a[--i]', `_ = i; _0 = --i; _0 = a[_0]; a[_] = _0`, true);
@@ -0,0 +1,276 @@
1
+ const {
2
+ STAMP, EXPRESS, SCOPED,
3
+ createExpressList,
4
+ skipAssignment,
5
+ } = require("./common");
6
+ var powermap = require("./powermap");
7
+
8
+ class Math extends Program {
9
+ number_reg = /^(\d+(\.\d+)?|\.\d+)$/;
10
+ }
11
+ var math = new Math;
12
+ math.stamps.push('\\', '_');
13
+ var pmap = math.powermap = Object.assign({}, powermap);
14
+ pmap["×"] = pmap[".*"] = powermap["*"];
15
+ pmap["≈"] = pmap["~="] = pmap["=="];
16
+ pmap["≉"] = pmap["!≈"] = pmap["!~="] = pmap["~!="] = pmap["=="];
17
+ pmap["≠"] = powermap["!="];
18
+ pmap["≢"] = powermap["!=="];
19
+ pmap["^"] = powermap["**"];
20
+ pmap["_"] = powermap["?."];
21
+ pmap["'"] = powermap["?."];
22
+ var puncmap = {
23
+ "*": "×", // 叉乘
24
+ '.*': '·',
25
+ "!=": "≉",
26
+ "!==": "≢",
27
+ "~=": "≈",
28
+ "-+": "±",
29
+ "!<": "≮",
30
+ "!>": "≯",
31
+ ">=": "≥",
32
+ "<=": '≤',
33
+ "/": "÷",
34
+ };
35
+ var isNull = a => a == null || a === '';
36
+ var make = function (pt, left, right) {
37
+ if (left) left = uncup(left);
38
+ if (right) right = uncup(right);
39
+ if (isNull(left)) {
40
+ return { [pt]: right instanceof Array ? ["", right] : right };
41
+ }
42
+ if (isNull(right)) {
43
+ return { [pt]: [left] };
44
+ }
45
+ if (left[pt]) {
46
+ left[pt].push(right);
47
+ return left
48
+ }
49
+ return { [pt]: [left, right] };
50
+ };
51
+
52
+ var split = function (code, comma) {
53
+ var rows = [];
54
+ var broken = false, bx = 0;
55
+ for (var cx = 0, dx = code.length; cx < dx; cx++) {
56
+ var o = code[cx];
57
+ if (o.type & COMMENT) continue;
58
+ if (broken && o.type & SPACE) {
59
+ bx = cx;
60
+ continue;
61
+ }
62
+ if (o.type === STAMP && o.text === comma) {
63
+ if (broken || !rows.length || bx < cx) {
64
+ rows.push(code.slice(bx, cx));
65
+ }
66
+ broken = true;
67
+ bx = cx + 1;
68
+ continue;
69
+ }
70
+ broken = false;
71
+ }
72
+ if (!broken) rows.push(code.slice(bx, dx));
73
+ return rows;
74
+ }
75
+ var getRows = function (code) {
76
+ var rows = split(code, ';');
77
+ if (rows.length === 1) a: {
78
+ var last = code.last;
79
+ if (last.type & STAMP && last.text === ';') break a;
80
+ return getArgs(rows[0]);
81
+ }
82
+ var trs = [];
83
+ var maxsize = 0;
84
+ for (var r of rows) {
85
+ var row = split(r, ',').map(toFlat);
86
+ maxsize = row.length;
87
+ trs.push(row);
88
+ }
89
+ rows.maxsize = maxsize;
90
+ return trs;
91
+ }
92
+ var getArgs = function (a) {
93
+ return split(a, ',').map(toFlat);
94
+ }
95
+ var uncup = function (cup) {
96
+ if (cup.iscup && cup.length <= 1) cup = cup[0];
97
+ return cup;
98
+ };
99
+ var back = function (cache) {
100
+ if (!cache.length) return;
101
+ var i = cache.length - 3;
102
+ var left = cache[i];
103
+ while (i >= 0 && left && left.iscup && !left.length) {
104
+ left = cache[i];
105
+ i -= 3;
106
+ };
107
+ if (i === cache.length - 3) return;
108
+ i += 3;
109
+ var s = i;
110
+ while (i <= cache.length - 3) {
111
+ left = make(cache[i + 1], left);
112
+ i += 3;
113
+ }
114
+ cache[s] = left;
115
+ s += 3;
116
+ cache.splice(s, cache.length - s);
117
+ }
118
+ var toFlat = function (exp) {
119
+ if (exp.length === 1 && exp[0].type !== SCOPED) return exp[0].text;
120
+ var bx = 0;
121
+ var p0 = 0;
122
+ var left = [];
123
+ left.iscup = true;
124
+ var cache = [];
125
+ for (var cx = 0, dx = exp.length; cx < dx; cx++) {
126
+ var e = exp[cx];
127
+ if (e.type & (SPACE | COMMENT)) continue;
128
+ if (e.type & STAMP) {
129
+ var p = pmap[e.text] || 0;
130
+ if ((!p0 || p > p0 || !left.length) && !e.ion) {
131
+ cache.push(left, e.text, p0);
132
+ left = [];
133
+ left.iscup = true;
134
+ p0 = p;
135
+ continue;
136
+ }
137
+ if (!left.length) {
138
+ back(cache);
139
+ [left, pt, p0] = cache.splice(cache.length - 3, 3);
140
+ }
141
+ if (e.ion) {
142
+ left = [make(e.text, left)];
143
+ left.iscup = true;
144
+ continue;
145
+ }
146
+ while (p <= p0) {
147
+ var right = left;
148
+ p0 = cache.pop();
149
+ var pt = cache.pop();
150
+ left = cache.pop();
151
+ left = make(pt, left, right);
152
+ }
153
+ cache.push(left, e.text, p0);
154
+ p0 = p;
155
+ left = [];
156
+ left.iscup = true;
157
+ }
158
+ else if (e.type === SCOPED) {
159
+ if (e.entry === '(') {
160
+ var args = getArgs(e);
161
+ if (left.length) {
162
+ var f = left.pop();
163
+ if (f instanceof Array) {
164
+ left.push({ "_": [uncup(f), ...args] });
165
+ }
166
+ else if (f instanceof Object) {
167
+ left.push(make("", f, args));
168
+ }
169
+ else {
170
+ left.push({ [f]: args });
171
+ }
172
+ }
173
+ else {
174
+ if (args.length === 1) args = args[0];
175
+ left.push(args);
176
+ }
177
+ }
178
+ else if (e.entry === '[') {
179
+ if (left.length) {
180
+ var last = e.last;
181
+ if (last?.ion) {
182
+ // 离子
183
+ var ions = [];
184
+ while (last && last.ion) {
185
+ ions.push(last.text);
186
+ last = last.prev;
187
+ }
188
+ e = e.slice();
189
+ ions = ions.reverse().join('');
190
+ if (last) {
191
+ e = e.slice(0, e.indexOf(last) + 1);
192
+ var args = getArgs(e);
193
+ if (typeof args[args.length - 1] !== 'object') {
194
+ args[args.length - 1] += ions;
195
+ }
196
+ else {
197
+ args.push(ions);
198
+ }
199
+ left = [make("**", left, ...args)];
200
+ }
201
+ else {
202
+ left = [make("**", left, ions)];
203
+ }
204
+ }
205
+ else {
206
+ var args = getArgs(e);
207
+ console.log(args)
208
+ // 下标
209
+ left = [make("_", left, ...args)];
210
+ }
211
+ left.iscup = true;
212
+ }
213
+ else {
214
+ // 矩阵
215
+ left.push(getRows(e));
216
+ }
217
+ }
218
+ else if (e.entry === "{") {
219
+ }
220
+ }
221
+ else {
222
+ if (e.text === "Infinity") {
223
+ left.push(Infinity);
224
+ continue;
225
+ }
226
+ if (e.isdigit) a: {
227
+ var et = e.text;
228
+ var v = +et;
229
+ if (/^\+/.test(et)) {
230
+ if (String(v) !== et.slice(1)) break a;
231
+ v = make("+", '', v);
232
+ }
233
+ if (String(v) !== et) break a;
234
+ left.push(v);
235
+ continue;
236
+ }
237
+ left.push(e.text);
238
+ }
239
+ }
240
+ if (!left.length) {
241
+ back(cache);
242
+ }
243
+ while (cache.length) {
244
+ var right = left;
245
+ var p0 = cache.pop();
246
+ var pt = cache.pop();
247
+ left = cache.pop();
248
+ left = make(pt, left, right);
249
+ }
250
+ return uncup(left);
251
+ }
252
+
253
+ function main(text) {
254
+ var code = scanner2(text, math);
255
+ var rows = split(code, ';');
256
+ var res = [];
257
+ res.iscup = true;
258
+ for (var r of rows) {
259
+ var cells = split(r, ',');
260
+ for (var c of cells) {
261
+ var exps = createExpressList(c);
262
+ for (var e of exps) {
263
+ var a = toFlat(e);
264
+ if (!a) continue;
265
+ if (a.iscup) {
266
+ for (var b of a) res.push(b, ' ');
267
+ }
268
+ else res.push(a, ' ');
269
+ }
270
+ if (res.length) res[res.length - 1] = ', ';
271
+ }
272
+ if (res.length) res[res.length - 1] = '\r\n';
273
+ }
274
+ res.pop();
275
+ return uncup(res);
276
+ }
@@ -0,0 +1,26 @@
1
+ var JSON = require('../basic_/JSON')
2
+ var t = function (text, want) {
3
+ var obj = 算式(text);
4
+ if (t.debug) console.log(JSON.toJS(obj, null, 4))
5
+ };
6
+ t(`a**2+b**2=c**2`);
7
+ t(`(a/b)*(b/d)=a/d`);
8
+ t(`S=sqrt(p*(p-a)*(p-b)*(p-c))`);
9
+ t(`root(x,3)`);
10
+ t(`+2`);
11
+ t(`+Infinity`);
12
+ t(`-Infinity`);
13
+ t(`a[n]`);
14
+ t(`2a`);
15
+ t(`[1 2;3 4]`);
16
+ t(`[1 2,3 4]`);
17
+ t(`[1,2;3,4]`);
18
+ t(`a!!`);
19
+ t(`!a`);
20
+ t(`a(b,c)`)
21
+ t(`[b,c]'`)
22
+ t(`H[+]`)
23
+ t(`H[2-]`)
24
+ t.debug = true;
25
+ t(`H'*1`)
26
+ t(`cos(theta,2)*E +(1 - cos(theta))*K'*K+sin(theta)*[0,-K_2,K_1;K_2,0,-K_0;-K_1,K_0,0]`)
@@ -1,4 +1,5 @@
1
1
  var { STAMP, PROPERTY, SCOPED, VALUE, STRAP, EXPRESS, QUOTED, SPACE, COMMENT, createString: _createString, splice } = require("./common");
2
+ var numberReg = /((?:[\+\-]+)?(?:\d+(?:\.\d*)?|\.\d+))([a-zH]+|%)?/;
2
3
  var createString = function (a) {
3
4
  a.autospace = false;
4
5
  return _createString(a);
@@ -9,12 +10,12 @@ class 素玉 extends Program {
9
10
  quotes = this.quotes.slice(0, 2).concat();
10
11
  keepspace = true;
11
12
  scopes = [["(", ")"], ["{", "}"]];
13
+ number_reg = numberReg;
12
14
  setType() { }
13
15
  }
14
16
 
15
17
  var rarg = new 素玉;
16
18
  rarg.quotes.push(["url(", ")"]);
17
- var numberReg = /((?:[\+\-]+)?(?:\d+(?:\.\d*)?|\.\d+))(?:\s*(px|%|pt|pc|in|cm|mm|r?em|deg|rad|vw|vh|%))?/;
18
19
  var replaceHReg = new RegExp(numberReg.source + /\s*([\/\*])\s*/.source + numberReg.source, 'gi');
19
20
  var replaceLReg = new RegExp(numberReg.source + /(\s*[\+\-]\s+|[\+\-])/.source + numberReg.source, 'gi');
20
21
  var replaceTReg = new RegExp(numberReg.source + /\s*[\/\*\+\-]\s*/.source + numberReg.source, 'i');
@@ -306,6 +307,7 @@ class 素心 extends Program {
306
307
  quotes = rarg.quotes;
307
308
  keepspace = true;
308
309
  control_reg = presets;
310
+ number_reg = numberReg;
309
311
  scopes = [["{", "}"], ["(", ")"]]
310
312
  }
311
313
 
@@ -438,9 +440,21 @@ var getFromScopeList = function (name, varsList, value = name) {
438
440
  return value;
439
441
  };
440
442
  var removeSelectorSpace = a => a.trim().replace(/\s*([\+~\>])\s*/g, "$1");
441
- var fixBase = function (b, a) {
443
+ var addCap = function (c, a) {
444
+ if (!c) return a;
445
+ if (/^[\>~\+]/.test(a) || /[\>~\+]$/.test(c)) {
446
+ a = c + a;
447
+ }
448
+ else a = c + " " + a;
449
+ return a;
450
+ }
451
+ var fixBase = function (b, a, seekroot) {
452
+ seekroot = seekroot !== false;
442
453
  if (/@keyframes\s/i.test(a)) {
443
454
  var bs = [];
455
+ if (seekroot && !baserooted) {
456
+ bs.push(basepath[basepath.length - 1]);
457
+ }
444
458
  splitParams(b).forEach(b => {
445
459
  b.replace(/@{@[^\}]+}/g, a => {
446
460
  if (bs.indexOf(a) < 0) bs.push(a)
@@ -459,22 +473,18 @@ var fixBase = function (b, a) {
459
473
  })
460
474
  if (rootindex > 0) a = a.slice(rootindex);
461
475
  return splitParams(b).map(b => {
462
- var b1 = b.replace(/^\:root\s*/g, '');
463
- var rindex = rootindex;
464
- if (b1.length !== b.length) rindex = true;;
465
- b = b1;
466
- b = b.replace(/^(&|\:scope)\s*/g, "");
467
476
  var a1 = a.replace(/&|\:scope/g, function () {
468
477
  replaced = true;
469
- if (!rindex) return b;
470
- return '';
478
+ return b;
471
479
  });
472
- if (!b && !replaced) return a1;
473
- if (!replaced) {
474
- if (/^[\>~\+]/.test(a) || /[\>~\+]$/.test(b)) {
475
- a1 = b + a1;
476
- }
477
- else if (!rindex) a1 = b + " " + a;
480
+ if (rootindex) return addCap(basepath[0], a1);
481
+ if (!replaced && b) {
482
+ if (!rootindex) a1 = addCap(b, a1);
483
+ }
484
+ if (seekroot && !baserooted) {
485
+ var bp = basepath[basepath.length - 1];
486
+ if (bp) a1 = splitParams(bp)
487
+ .map(b => addCap(b, a1)).join(',');
478
488
  }
479
489
  return a1;
480
490
  }).join(",");
@@ -482,7 +492,7 @@ var fixBase = function (b, a) {
482
492
  }
483
493
  var Method = function () {
484
494
  var valueMap = Object.create(null);
485
- if (!this.base) this.base = base;
495
+ this.base = halfbase || base;
486
496
  vlist.push(valueMap);
487
497
  var argDefaults = this.args.defaults;
488
498
  var ipd = 0;
@@ -549,11 +559,34 @@ var initvars = function (vars) {
549
559
  vars[k] = replace_punc(calcvars(v));
550
560
  }
551
561
  };
552
- var evalthis = function (p) {
553
- var temp = base;
554
- base = p.base || "&";
562
+ var basepath = [], baserooted = false, halfbase = null;
563
+ var evalthis = function (p, k) {
564
+ var _baserooted = baserooted || basepath.length < 1;
565
+ var _base = base, _halfbase = halfbase;
566
+ var needpop = true;
567
+ if (_baserooted) basepath.push(base);
568
+ else basepath.push(halfbase);
569
+ if (k && !(/^@/.test(k))) {
570
+ var rooted1 = /\:root/.test(k);
571
+ if (rooted1 || /(\:scope|&)/.test(k)) {
572
+ k = fixBase(base, k, false);
573
+ if (!_baserooted) {
574
+ basepath.pop();
575
+ needpop = false;
576
+ }
577
+ }
578
+ else baserooted = false;
579
+ if (rooted1) baserooted = !!k;
580
+ base = k;
581
+ }
582
+ else base = p.base || '', baserooted = !!base;
583
+ if (baserooted) halfbase = base;
584
+ else halfbase = p.base;
555
585
  var res = eval2(p.used);
556
- base = temp;
586
+ if (needpop) basepath.pop();
587
+ halfbase = _halfbase;
588
+ base = _base;
589
+ baserooted = _baserooted;
557
590
  return res;
558
591
  };
559
592
  var evalproc = function (k, retnoparam) {
@@ -639,7 +672,7 @@ var eval2 = function (props) {
639
672
  else p.base = presets.test(k) ? `@{${k}}` : k;
640
673
  if (vars) vlist.push(vars);
641
674
  initvars(vars);
642
- var value = evalthis(p);
675
+ var value = evalthis(p, k);
643
676
  if (vars) vlist.pop();
644
677
  if (value.rest.length) rest = rest.concat(value.rest);
645
678
  if (value.length) rest.push([p.base, '{', value.join(""), "}"]);
@@ -669,6 +702,7 @@ var eval2 = function (props) {
669
702
  function evalscoped(scoped, scopeName = '') {
670
703
  var _base = base;
671
704
  base = removeSelectorSpace(scopeName);
705
+ baserooted = true;
672
706
  var smaps = scoped.maps;
673
707
  var root = smaps[":root"], scope = smaps[":scope"];
674
708
  var and = smaps["&"];
@@ -680,7 +714,8 @@ function evalscoped(scoped, scopeName = '') {
680
714
  clist.push(smaps);
681
715
  kfmap = Object.create(null);
682
716
  initvars(vars);
683
- var result = eval2(scoped, [vars]);
717
+ var result = eval2(scoped);
718
+ baserooted = false;
684
719
  kfmap = null;
685
720
  vlist.pop();
686
721
  clist.pop();
@@ -731,4 +766,6 @@ function 素馨(text, scopeName, compress) {
731
766
  return a;
732
767
  }).filter(a => !!a).join(compress ? "" : "\r\n") + getquried();
733
768
  }
734
- 素馨.素心 = 素心;
769
+ 素馨.素心 = 素心;
770
+ 素馨.number_reg = numberReg;
771
+ 素馨.macros = macros;
@@ -81,11 +81,10 @@ test(`.type(@type,@media) {.@{type} {&:before{content:"@{media}";}}}.type(videoi
81
81
  assert(素馨(`:not(a):not(b){c:d}`, 'abc'), `abc :not(a):not(b){c:d;}`);
82
82
  assert(素馨(`&:not(a):not(b){c:d}`, 'abc'), `abc:not(a):not(b){c:d;}`);
83
83
  assert(素馨(`:scope{&:not(a):not(b){c:d}}`, 'abc'), `abc:not(a):not(b){c:d;}`);
84
- assert(素馨(`:root{&:not(a):not(b){c:d}}`, 'abc1'), `:not(a):not(b){c:d;}`);
84
+ assert(素馨(`:root{&:not(a):not(b){c:d}}`, 'abc1'), `abc1:not(a):not(b){c:d;}`);
85
85
  assert(素馨(`&{&:not(a):not(b){c:d}}`, 'abc'), `abc:not(a):not(b){c:d;}`);
86
86
  assert(素馨(`:root>a{&:not(a):not(b){c:d}}`, '.abc-'), `.abc->a:not(a):not(b){c:d;}`);
87
- assert(素馨(`a>:root{&:not(a):not(b){c:d}}`, '.abc-'), `:not(a):not(b){c:d;}`);
88
-
87
+ assert(素馨(`a>:root{&:not(a):not(b){c:d}}`, '.abc-'), `.abc-:not(a):not(b){c:d;}`);
89
88
  assert(素馨(`.a (){ &:after{abc:1}} .b{.a();}`, '.abc-'), `.abc- .b:after{abc:1;}`);
90
89
  assert(素馨(`@a:1px;@margin-x:@a+10px; a{m:-@margin-x}`), `a{m:-11px;}`);
91
90
  assert(素馨(`a{@a:1px;@margin-x:@a+10px;m:-@margin-x}`), `a{m:-11px;}`);
@@ -114,3 +113,9 @@ assert(scanner2(`-0.2em .3em -0.2em 0`, new 素馨.素心)[0].text, '-0.2em');
114
113
  assert(scanner2(`-0.2em .3em -0.2em 0`, new 素馨.素心)[0].isdigit, true);
115
114
  assert(scanner2(`-0.2em .3em -0.2em 0`, new 素馨.素心)[2].text, ".3em");
116
115
  assert(scanner2(`-0.2em .3em -0.2em 0`, new 素馨.素心)[2].isdigit, true);
116
+ assert(素馨(`a{ .b{b&{a:1}}}`, '', true), `a b.b{a:1;}`);
117
+ assert(素馨(`h1{a:c; span{a:b} i{a:b} }`, '.home-', true), `.home- h1 span{a:b;}.home- h1 i{a:b;}.home- h1{a:c;}`);
118
+ assert(素馨(`h1{ button{&:not(hover){.track{a:b}}} }`, '.home-', true), `.home- h1 button:not(hover) .track{a:b;}`);
119
+ assert(素馨(`@type(@a){&[type=@a]{a:1}} @type(white)`, '.btn-', true), `.btn-[type=white]{a:1;}`);
120
+ assert(素馨(`a,b{c,d{ g&{e:f}}}`, '', true), `a gc,b gc,a gd,b gd{e:f;}`);
121
+ assert(素馨(`a{a:lch(from rgb(20 20 20) l c h)}`, '', true), `a{a:lch(from rgb(20 20 20) l c h);}`);
@@ -120,6 +120,10 @@ function markdown(text) {
120
120
  var t = /^\S+/.exec(c);
121
121
  if (t) t = t[0]; c = c.slice(t.length).replace(/^(\r\n|\r|\n)|\s+$/g, '');
122
122
  try {
123
+ if (t === 'math') {
124
+ var suanshi = compile$算式(c);
125
+ return suanshi.iscup ? math.apply(null, suanshi) : math(suanshi);
126
+ }
123
127
  return s1 + 茨菰$上色(t, c) + s2;
124
128
  } catch (e) {
125
129
  console.error(e);
@@ -26,10 +26,40 @@ class ChatRTC {
26
26
  */
27
27
  peerConnection = null;
28
28
  candidates = [];
29
- constructor() {
30
- this.peerConnection = new RTCPeerConnection(configuration);
29
+ waiters = {};
30
+ channels = {};
31
+ constructor(ondate) {
32
+ var peerConnection = this.peerConnection = new RTCPeerConnection(configuration);
33
+ peerConnection.ondatachannel = (event) => {
34
+ var channel = event.channel;
35
+ var label = channel.label;
36
+ var waiter = this.waiters[label];
37
+ console.log('data-channel', channel, waiter);
38
+ if (waiter) {
39
+ delete this.waiters[label];
40
+ waiter(channel);
41
+ return;
42
+ }
43
+ this.channels[label] = channel;
44
+ };
45
+ this.ready = new Promise((ok, oh) => {
46
+ peerConnection.oniceconnectionstatechange = function () {
47
+ console.log('completed', this.iceConnectionState)
48
+ if (this.iceConnectionState === 'completed') {
49
+ ok();
50
+ }
51
+ else if (this.iceConnectionState === 'failed') {
52
+ oh();
53
+ }
54
+ }
55
+ });
56
+
57
+ peerConnection.onicecandidate = oncandidate;
58
+ peerConnection.emitDidate = ondate;
31
59
  }
32
60
  async setAnswer(answer) {
61
+ if (this.answer) return;
62
+ this.answer = answer;
33
63
  await this.peerConnection.setRemoteDescription(new RTCSessionDescription(answer));
34
64
  flushDidate(this);
35
65
  }
@@ -51,35 +81,45 @@ class ChatRTC {
51
81
  local.play();
52
82
  addTracks(this.peerConnection, localStream);
53
83
  }
54
- async createChannel(id, options) {
55
- return this.peerConnection.createDataChannel(id, options);
84
+ async createChannel(label, options) {
85
+ try {
86
+ // await this.ready;
87
+ return this.peerConnection.createDataChannel(label, options);
88
+ } catch (e) {
89
+ alert('无法建立连接', 'error');
90
+ }
56
91
  }
57
- waitChannel() {
92
+ waitChannel(label) {
58
93
  return new Promise((ok) => {
59
- if (this.channel) return ok(this.channel);
60
- this.peerConnection.ondatachannel = (event) => {
61
- this.channel = event.channel;
62
- ok(this.channel);
63
- };
94
+ if (this.channels[label]) {
95
+ var channel = this.channels[label];
96
+ delete this.channels[label];
97
+ return ok(channel);
98
+ }
99
+ this.waiters[label] = ok;
64
100
  });
65
101
  }
66
- async init(ondate, offer) {
102
+ async initOffer() {
67
103
  var peerConnection = this.peerConnection;
68
- peerConnection.emitDidate = ondate;
69
- peerConnection.onicecandidate = oncandidate;
70
- peerConnection.ondatachannel = event => this.channel = event.channel;
71
- if (offer) return takeOffer(this, offer);
72
- offer = await peerConnection.createOffer();
104
+ var offer = this.offer;
105
+ if (offer) return offer;
106
+ delete this.answer;
107
+ offer = this.offer = await peerConnection.createOffer();
73
108
  await peerConnection.setLocalDescription(offer);
74
109
  return offer;
75
110
  }
76
- async call(ondate, offer) {
111
+ takeOffer(offer) {
112
+ if (this.offer) return this.answer;
113
+ this.offer = offer;
114
+ return this.answer = takeOffer(this, offer);
115
+ }
116
+ async call(offer) {
77
117
  await this.initMedia();
78
118
  var peerConnection = this.peerConnection;
79
119
  // 处理 ICE 候选
80
120
  peerConnection.remote = this.remote;
81
121
  peerConnection.ontrack = ontrack;
82
- return this.init(ondate, offer);
122
+ return this.takeOffer(offer);
83
123
  };
84
124
  async hangup() {
85
125
  var { peerConnection, localStream, local, remote } = this;
@@ -97,6 +137,7 @@ async function takeOffer(rtc, offer) {
97
137
  var answer = await pc.createAnswer();
98
138
  await pc.setLocalDescription(answer);
99
139
  flushDidate(rtc);
140
+ rtc.answer = answer;
100
141
  return answer;
101
142
  }
102
143
 
@@ -129,6 +170,7 @@ var stopTracks = function (localStream) {
129
170
  }
130
171
  }
131
172
  var oncandidate = function (event) {
173
+ console.log(event, 'icedidate');
132
174
  var candidate = event.candidate;
133
175
  if (!candidate) return this.emitDidate(null);
134
176
  var { sdpMid, candidate, sdpMLineIndex, usernameFragment } = candidate;