lilact 0.28.5 → 0.29.0

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 (45) hide show
  1. package/dist/lilact.development.js +215 -172
  2. package/dist/lilact.development.js.map +3 -3
  3. package/dist/lilact.development.min.js +33 -33
  4. package/dist/lilact.development.min.js.map +3 -3
  5. package/dist/lilact.production.min.js +33 -33
  6. package/docs/assets/navigation.js +1 -1
  7. package/docs/assets/search.js +1 -1
  8. package/docs/classes/accessories.ErrorBoundary.html +8 -8
  9. package/docs/classes/accessories.Suspense.html +7 -7
  10. package/docs/classes/components.Component.html +11 -11
  11. package/docs/classes/components.HTMLComponent.html +11 -11
  12. package/docs/classes/components.RootComponent.html +11 -11
  13. package/docs/functions/components.cloneComponent.html +1 -1
  14. package/docs/functions/components.createComponent.html +1 -1
  15. package/docs/functions/components.createPortal.html +1 -1
  16. package/docs/functions/components.createRoot.html +1 -1
  17. package/docs/functions/components.memo.html +1 -1
  18. package/docs/functions/components.render.html +1 -1
  19. package/docs/functions/errors.asError.html +1 -0
  20. package/docs/functions/run.lazy.html +1 -1
  21. package/docs/functions/run.require.html +1 -1
  22. package/docs/functions/run.run.html +1 -1
  23. package/docs/functions/run.runScripts.html +1 -1
  24. package/docs/modules/errors.html +1 -1
  25. package/docs/static/index.html +3 -4
  26. package/docs/static/lilact.development.js +215 -172
  27. package/docs/static/lilact.development.js.map +3 -3
  28. package/docs/static/lilact.development.min.js +33 -33
  29. package/docs/static/lilact.development.min.js.map +3 -3
  30. package/docs/static/lilact.production.min.js +33 -33
  31. package/docs/variables/components.cloneElement.html +1 -1
  32. package/docs/variables/errors.blocksInfo.html +1 -0
  33. package/examples/index.html +3 -4
  34. package/examples/lilact.development.js +215 -172
  35. package/examples/lilact.development.js.map +3 -3
  36. package/examples/lilact.development.min.js +33 -33
  37. package/examples/lilact.development.min.js.map +3 -3
  38. package/examples/lilact.production.min.js +33 -33
  39. package/package.json +1 -1
  40. package/src/components.jsx +104 -115
  41. package/src/errors.jsx +4 -4
  42. package/src/expscan.js +40 -15
  43. package/src/jsx.js +67 -38
  44. package/src/run.jsx +51 -40
  45. package/docs/variables/errors.blocks_info.html +0 -1
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "lilact",
3
- "version": "0.28.5",
3
+ "version": "0.29.0",
4
4
  "description": "A Little React/JSX Runtime Implementation for Browser",
5
5
  "repository": "github:arashkazemi/lilact",
6
6
  "homepage": "https://arashkazemi.github.io/lilact/",
@@ -169,148 +169,139 @@ class ComponentCore
169
169
  // TODO: should componentDidUpdate be called after arranging/appending the outlet or before?
170
170
  apply(next_props = this.props, next_state = this.next_state || this.state)
171
171
  {
172
+ try {
172
173
 
173
- let do_rerender = true;
174
+ let do_rerender = true;
174
175
 
175
- if(this.outlet && this?.[MEMOIZED]) {
176
+ if(this.outlet && this?.[MEMOIZED]) {
176
177
 
177
- if( shallowEqual(this.props, next_props, "children") &&
178
- shallowEqual(this.props?.children, next_props?.children) ) {
179
- do_rerender=false;
178
+ if( shallowEqual(this.props, next_props, "children") &&
179
+ shallowEqual(this.props?.children, next_props?.children) ) {
180
+ do_rerender=false;
181
+ }
180
182
  }
181
- }
182
183
 
183
- if(do_rerender) {
184
+ if(do_rerender) {
184
185
 
185
- if(DEBUG) {
186
+ if(DEBUG) {
186
187
 
187
- if(this.entity?.propTypes) {
188
- PropTypes.checkPropTypes(this.entity.propTypes, this.props, 'prop', this.entity.name);
189
- }
190
- else if(this.component?.propTypes) {
191
- PropTypes.checkPropTypes(this.component.propTypes, this.props, 'prop', this.component.name);
192
- }
188
+ if(this.entity?.propTypes) {
189
+ PropTypes.checkPropTypes(this.entity.propTypes, this.props, 'prop', this.entity.name);
190
+ }
191
+ else if(this.component?.propTypes) {
192
+ PropTypes.checkPropTypes(this.component.propTypes, this.props, 'prop', this.component.name);
193
+ }
193
194
 
194
- }
195
- if(typeof(next_state)==='function') next_state = next_state(this.state);
195
+ }
196
+ if(typeof(next_state)==='function') next_state = next_state(this.state);
196
197
 
197
- if(this.component.constructor.defaultProps) {
198
- next_props = {...this.component.constructor.defaultProps, ...next_props};
199
- }
198
+ if(this.component.constructor.defaultProps) {
199
+ next_props = {...this.component.constructor.defaultProps, ...next_props};
200
+ }
200
201
 
201
- if(this?.parent?.component?.context || this?.parent?.component?.getChildContext ) {
202
- this.context = { ...this.parent.component.context, ...this.parent.component.getChildContext?.() };
202
+ if(this?.parent?.component?.context || this?.parent?.component?.getChildContext ) {
203
+ this.context = { ...this.parent.component.context, ...this.parent.component.getChildContext?.() };
203
204
 
204
- if(DEBUG && this.component.constructor.contextTypes) {
205
- PropTypes.checkPropTypes(this.component.constructor.contextTypes, this.context, 'context', this.entity.name);
205
+ if(DEBUG && this.component.constructor.contextTypes) {
206
+ PropTypes.checkPropTypes(this.component.constructor.contextTypes, this.context, 'context', this.entity.name);
207
+ }
206
208
  }
207
- }
208
209
 
209
- if( this.component.shouldComponentUpdate &&
210
- !this.component.shouldComponentUpdate
211
- (next_state, next_props, this.context) ) return;
210
+ if( this.component.shouldComponentUpdate &&
211
+ !this.component.shouldComponentUpdate
212
+ (next_state, next_props, this.context) ) return;
212
213
 
213
214
 
214
- if( typeof(this.entity)==='string' ) {
215
- if(!(this.element instanceof Element)) {
215
+ if( typeof(this.entity)==='string' ) {
216
+ if(!(this.element instanceof Element)) {
216
217
 
217
- if(this.is_svg || this.container.is_svg) {
218
- this.is_svg = true;
219
- this.element = document.createElementNS(SVG_NS, this.entity);
218
+ if(this.is_svg || this.container.is_svg) {
219
+ this.is_svg = true;
220
+ this.element = document.createElementNS(SVG_NS, this.entity);
221
+ }
222
+ else {
223
+ this.element = document.createElement(this.entity);
224
+ }
225
+ if(next_props?.defaultValue) this.element.value = String(next_props.defaultValue).slice(0, next_props?.maxLength);
226
+ if(next_props?.defaultChecked) this.element.checked = next_props.defaultChecked;
227
+ }
228
+ this.element[COMPONENT] = this.component;
229
+ }
230
+
231
+ if(next_props.ref) {
232
+ if(typeof(next_props.ref)==='function') {
233
+ next_props.ref(this.element || this.component);
220
234
  }
221
235
  else {
222
- this.element = document.createElement(this.entity);
236
+ next_props.ref.current = this.element || this.component;
223
237
  }
224
- if(next_props?.defaultValue) this.element.value = String(next_props.defaultValue).slice(0, next_props?.maxLength);
225
- if(next_props?.defaultChecked) this.element.checked = next_props.defaultChecked;
226
238
  }
227
- this.element[COMPONENT] = this.component;
228
- }
229
239
 
230
- if(next_props.ref) {
231
- if(typeof(next_props.ref)==='function') {
232
- next_props.ref(this.element || this.component);
240
+ if(next_props!==undefined && this.component.componentWillReceiveProps) {
241
+ this.component.componentWillReceiveProps(next_props);
233
242
  }
234
- else {
235
- next_props.ref.current = this.element || this.component;
236
- }
237
- }
238
-
239
- if(next_props!==undefined && this.component.componentWillReceiveProps) {
240
- this.component.componentWillReceiveProps(next_props);
241
- }
242
243
 
243
- if(this.component.componentWillUpdate) {
244
- this.component.componentWillUpdate(next_props, next_state);
245
- }
244
+ if(this.component.componentWillUpdate) {
245
+ this.component.componentWillUpdate(next_props, next_state);
246
+ }
246
247
 
247
- const prev_state = this.state, prev_props=this.props;
248
+ const prev_state = this.state, prev_props=this.props;
248
249
 
249
- if(this.element) {
250
- this.updateElementProps(next_props);
251
- }
252
- this.props = next_props;
250
+ if(this.element) {
251
+ this.updateElementProps(next_props);
252
+ }
253
+ this.props = next_props;
253
254
 
254
- if(typeof this.next_state==='object') {
255
- if(!this.state) this.state = {...next_state};
256
- else Object.assign( this.state, next_state );
257
- }
258
- else if(this.next_state!==undefined) throw new Error('Component.setState only accepts objects or functions is new state.');
255
+ if(typeof this.next_state==='object') {
256
+ if(!this.state) this.state = {...next_state};
257
+ else Object.assign( this.state, next_state );
258
+ }
259
+ else if(this.next_state!==undefined) throw new Error('Component.setState only accepts objects or functions is new state.');
259
260
 
260
261
 
261
- if(this.next_state) delete this.next_state;
262
+ if(this.next_state) delete this.next_state;
262
263
 
263
264
 
264
- if(this.hooks!==undefined) {
265
- this.hook_index = 0;
266
- Lilact.current_component = [this, Lilact.current_component];
265
+ if(this.hooks!==undefined) {
266
+ this.hook_index = 0;
267
+ Lilact.current_component = [this, Lilact.current_component];
267
268
 
268
- try {
269
269
  this.outlet = this.component.render(next_props, {current: this.element || this.component} );
270
- }
271
- catch(e) {
272
- renderErrorHandler(this, e);
273
- }
274
270
 
275
- Lilact.current_component = Lilact.current_component[1];
276
- }
277
- else {
278
- try {
279
- this.outlet = this.component.render({current: this.element || this.component});
271
+ Lilact.current_component = Lilact.current_component[1];
280
272
  }
281
- catch(e) {
282
- renderErrorHandler(this, e);
273
+ else {
274
+ this.outlet = this.component.render({current: this.element || this.component});
283
275
  }
284
- }
285
-
286
- if( this?.portal ) {
287
- this.element = this.portal;
288
- }
289
-
290
- if(this.outlet?.constructor?.name!=='Array') {
291
- this.outlet = [this.outlet];
292
- }
293
-
294
- this.outlet = [...this.outlet];
295
-
296
- for (let i=0;i<this.outlet.length;i++) {
297
- let item = this.outlet[i];
298
276
 
299
- if(item===undefined || item===null || typeof(item)==='boolean') {
300
- this.outlet.splice(i, 1);
301
- i--;
277
+ if( this?.portal ) {
278
+ this.element = this.portal;
302
279
  }
303
- else if(typeof item==='function') {
304
- const res = this.childFunctionHandler(item);
305
- this.outlet.splice(i, 1, res);
306
- i--;
307
- }
308
- else if(item.constructor.name === 'Array') {
309
- this.outlet.splice(i, 1, ...item);
310
- i--;
280
+
281
+ if(this.outlet?.constructor?.name!=='Array') {
282
+ this.outlet = [this.outlet];
311
283
  }
312
284
  else {
313
- try {
285
+ this.outlet = [...this.outlet];
286
+ }
287
+
288
+ for (let i=0;i<this.outlet.length;i++) {
289
+ let item = this.outlet[i];
290
+
291
+ if(item===undefined || item===null || typeof(item)==='boolean') {
292
+ this.outlet.splice(i, 1);
293
+ i--;
294
+ }
295
+ else if(typeof item==='function') {
296
+ const res = this.childFunctionHandler(item);
297
+ this.outlet.splice(i, 1, res);
298
+ i--;
299
+ }
300
+ else if(item.constructor.name === 'Array') {
301
+ this.outlet.splice(i, 1, ...item);
302
+ i--;
303
+ }
304
+ else {
314
305
  const core = prepareCore(this, item);
315
306
  this.outlet[i] = core;
316
307
 
@@ -329,23 +320,22 @@ if(DEBUG) {
329
320
  }
330
321
  }
331
322
  }
332
- catch(e) {
333
- renderErrorHandler(this, e);
334
- }
335
-
336
323
  }
337
- }
338
324
 
339
- if(this.cache) this.cache.commit();
325
+ if(this.cache) this.cache.commit();
340
326
 
327
+ if(this.element) this.arrangeOutlet();
341
328
 
342
- if(this.element) this.arrangeOutlet();
329
+ if(this.component.componentDidUpdate) {
330
+ this.component.componentDidUpdate(prev_props, prev_state, this.last_snapshot);
331
+ }
343
332
 
344
- if(this.component.componentDidUpdate) {
345
- this.component.componentDidUpdate(prev_props, prev_state, this.last_snapshot);
333
+ if(this.last_snapshot) delete this.last_snapshot;
346
334
  }
347
335
 
348
- if(this.last_snapshot) delete this.last_snapshot;
336
+ }
337
+ catch(e) {
338
+ renderErrorHandler(this, e);
349
339
  }
350
340
 
351
341
  }
@@ -610,7 +600,7 @@ if(DEBUG) {
610
600
  core.container.appendElement(core);
611
601
  }
612
602
  else {
613
- if(core.arrangeOutlet) core.arrangeOutlet();
603
+ if(core.arrangeOutlet && core.outlet) core.arrangeOutlet();
614
604
 
615
605
  // todo: is there a way to remove this useless flag?
616
606
  if(!core?.mounted) {
@@ -624,7 +614,6 @@ if(DEBUG) {
624
614
  }
625
615
  }
626
616
  }
627
-
628
617
  }
629
618
 
630
619
  // note: override this to tailor function children like <Transition>{(state)=>{...}}</Transition>
package/src/errors.jsx CHANGED
@@ -51,7 +51,7 @@ function number(value) {
51
51
  return Number.isFinite(result) ? result : null;
52
52
  }
53
53
 
54
- function asError(value) {
54
+ export function asError(value) {
55
55
  if (value instanceof Error) return value;
56
56
  if (value?.error instanceof Error) return value.error;
57
57
 
@@ -130,7 +130,7 @@ function blockInfo(error) {
130
130
  const trace = traceBlock(error);
131
131
  return trace == null
132
132
  ? null
133
- : Lilact.blocks_info?.labels?.[trace];
133
+ : Lilact.blocksInfo?.labels?.[trace];
134
134
  }
135
135
 
136
136
  function mapLocation(mappings, line, column) {
@@ -408,7 +408,7 @@ export function scanBlockLabels(code, path) {
408
408
  for (const match of String(code).matchAll(
409
409
  /LILACTBLOCK(\d+):(\d+),(\d+):([^*]+)\*\//gm
410
410
  )) {
411
- Lilact.blocks_info.labels[match[1]] = {
411
+ Lilact.blocksInfo.labels[match[1]] = {
412
412
  path,
413
413
  line: Number(match[2]),
414
414
  column: Number(match[3]),
@@ -417,7 +417,7 @@ export function scanBlockLabels(code, path) {
417
417
  }
418
418
  }
419
419
 
420
- export const blocks_info = {
420
+ export const blocksInfo = {
421
421
  counter: 0,
422
422
  labels: {},
423
423
  };
package/src/expscan.js CHANGED
@@ -106,7 +106,7 @@ export function generateSequence(arr, labeler = labeler.bind(null, null))
106
106
  const import_export_regexp = /(?:i[C \n]*(?:(?:I|J|(?:\*[C \n]*a[C \n]*I))[C \n]*,[C \n]*)*(?:(?:(?:I(?:[C \n]*a[C \n]*I)?)|J|(?:\*[C \n]*a[C \n]*I))[C \n]*f[C \n]*)?S)|(?:e[C \n]*(?:(?:[*J][C \n]*f[C \n]*S)|(?:d[C \n]*[IFJ])|J|(?:[VF][c \n]*I)|I))|(?:r[c \n]*P)/mg;
107
107
  const props_regexp = /O[C \n]*(?:[Id](?:[C \n]*a[C \n]*I)?[C \n]*,[C \n]*)*(?:I(?:[C \n]*a[C \n]*I)?)[C \n]*O/mg;
108
108
 
109
- export function processImportExports(node, jsx)
109
+ export function processImportExports(node, jsx, meta)
110
110
  {
111
111
  const s = generateSequence(node.out,
112
112
  labeler.bind(null,
@@ -150,6 +150,10 @@ export function processImportExports(node, jsx)
150
150
 
151
151
  begins.push(node.end);
152
152
 
153
+ meta.imports ??= {};
154
+
155
+ const imported_names = new Set;
156
+
153
157
  for (const m of s.matchAll(import_export_regexp)) {
154
158
 
155
159
  // Require (to inject requirer argument)
@@ -173,9 +177,10 @@ export function processImportExports(node, jsx)
173
177
  if(s[i]==='.') continue;
174
178
 
175
179
  const src = jsx.substring(node.out[m.index+imp.length-1].begin, node.out[m.index+imp.length-1].end);
176
- const imports = {};
177
- let star_imports = [];
178
- let import_alls = [];
180
+ const named_imports = {};
181
+ let import_stars = [];
182
+ let import_defaults = [];
183
+
179
184
 
180
185
  for(i = m.index+1;i<m.index+imp.length-1;i++) {
181
186
 
@@ -192,7 +197,7 @@ export function processImportExports(node, jsx)
192
197
  case ',':
193
198
  break;
194
199
  case 'I': {
195
- import_alls.push(node.out[i]);
200
+ import_defaults.push(node.out[i]);
196
201
  continue;
197
202
  }
198
203
  case 'J': {
@@ -214,11 +219,11 @@ export function processImportExports(node, jsx)
214
219
  if(sj[j]==='a') {
215
220
  j++;
216
221
  while(sj[j]===' ' || sj[j]==='\n' || sj[j]==='C') j++;
217
- imports[ps[j]] = prop;
222
+ named_imports[ps[j]] = prop;
218
223
  j++;
219
224
  }
220
225
  else {
221
- imports[prop] = prop;
226
+ named_imports[prop] = prop;
222
227
  }
223
228
  }
224
229
  continue;
@@ -230,7 +235,7 @@ export function processImportExports(node, jsx)
230
235
  i++;
231
236
  skip_spaces();
232
237
 
233
- star_imports.push(node.out[i]);
238
+ import_stars.push(node.out[i]);
234
239
  continue;
235
240
  }
236
241
  case 'S':
@@ -240,28 +245,31 @@ export function processImportExports(node, jsx)
240
245
  }
241
246
 
242
247
  let cjs = '';
243
- for(const s of star_imports) {
248
+ for(const s of import_stars) {
244
249
  cjs+=`const ${s} = require(${src},{requirer:module});\n`;
250
+ imported_names.add(s);
245
251
  }
246
- for(const s of import_alls) {
252
+ for(const s of import_defaults) {
247
253
  cjs+=`const ${s} = require(${src},{requirer:module, checkExport: ['default']}).default;\n`;
254
+ imported_names.add(s);
248
255
  }
249
- if(Object.keys(imports).length) {
256
+ if(Object.keys(named_imports).length) {
250
257
  let o = '{';
251
258
  let ls = '[';
252
259
 
253
- for(const p in imports) {
260
+ for(const p in named_imports) {
261
+ imported_names.add(p);
254
262
  if(o.length>1) {
255
263
  o+=',';
256
264
  ls+=',';
257
265
  }
258
- if(p===imports[p]) {
266
+ if(p===named_imports[p]) {
259
267
  o+=p;
260
268
  ls+=`'${p}'`;
261
269
  }
262
270
  else {
263
- o+=p+":"+imports[p];
264
- ls+=`'${imports[p]}'`;
271
+ o+=p+":"+named_imports[p];
272
+ ls+=`'${named_imports[p]}'`;
265
273
  }
266
274
 
267
275
  }
@@ -272,6 +280,7 @@ export function processImportExports(node, jsx)
272
280
  }
273
281
  else if(cjs.length===0) {
274
282
  cjs+=`require(${src},{requirer:module})`;
283
+ named_imports[''] = src;
275
284
  }
276
285
 
277
286
  // 2. add nodes
@@ -279,6 +288,15 @@ export function processImportExports(node, jsx)
279
288
  continue;
280
289
  }
281
290
  }
291
+
292
+ const ss = src.slice(1,src.length-1);
293
+ if(meta.imports[ss]) {
294
+ meta.imports[ss] = { import_stars: [ ...meta.imports[ss].import_stars, ...import_stars],
295
+ import_defaults: [ ...meta.imports[ss].import_defaults, ...import_defaults],
296
+ named_imports: { ...meta.imports[ss].named_imports, ...named_imports } }
297
+ }
298
+ else meta.imports[ss] = {import_stars, import_defaults, named_imports };
299
+
282
300
  }
283
301
  // Export
284
302
  else {
@@ -418,4 +436,11 @@ export function processImportExports(node, jsx)
418
436
  }
419
437
  }
420
438
  }
439
+
440
+ if(meta.imported_names) {
441
+ meta.imported_names = new Set([...meta.imported_names,...imported_names]);
442
+ }
443
+ else {
444
+ meta.imported_names = imported_names;
445
+ }
421
446
  }