@lightningjs/blits 1.29.3 → 1.29.4

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/CHANGELOG.md CHANGED
@@ -2,6 +2,14 @@
2
2
 
3
3
  _03 jun 2025_
4
4
 
5
+ ## v1.29.4
6
+
7
+ - Removed excessive shader creation for effects
8
+ - Added explicit cleanup of effects in for loop
9
+ - Improved element destruction
10
+
11
+ _03 jun 2025_
12
+
5
13
  ## v1.29.3
6
14
 
7
15
  - Added first batch internal JS doc types
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@lightningjs/blits",
3
- "version": "1.29.3",
3
+ "version": "1.29.4",
4
4
  "description": "Blits: The Lightning 3 App Development Framework",
5
5
  "bin": "bin/index.js",
6
6
  "exports": {
@@ -47,7 +47,7 @@
47
47
  },
48
48
  "dependencies": {
49
49
  "@lightningjs/msdf-generator": "^1.1.1",
50
- "@lightningjs/renderer": "^2.13.2"
50
+ "@lightningjs/renderer": "^2.13.4"
51
51
  },
52
52
  "repository": {
53
53
  "type": "git",
package/src/component.js CHANGED
@@ -195,6 +195,8 @@ const Component = (name = required('name'), config = required('config')) => {
195
195
  // generate a human readable ID for the component instance (i.e. Blits::ComponentName1)
196
196
  this.componentId = createHumanReadableId(name)
197
197
 
198
+ this[symbols.effects] = []
199
+
198
200
  // instantiate a lifecycle object for this instance
199
201
  this.lifecycle = Object.assign(Object.create(Lifecycle), {
200
202
  component: this,
@@ -305,7 +307,6 @@ const Component = (name = required('name'), config = required('config')) => {
305
307
  // setup (and execute) all the generated side effects based on the
306
308
  // reactive bindings define in the template
307
309
  const effects = config.code.effects
308
- this[symbols.effects] = []
309
310
  for (let i = 0; i < effects.length; i++) {
310
311
  const eff = () => {
311
312
  effects[i](this, this[symbols.children], config, globalComponents, rootComponent, effect)
@@ -381,34 +381,12 @@ const propsTransformer = {
381
381
  v[i].props.color = colors.normalize(v[i].props.color)
382
382
  }
383
383
  }
384
- const effectNames = {}
385
384
  if (this.element.node === undefined) {
386
- this.element.effectNames = []
387
385
  this.props['shader'] = renderer.createShader('DynamicShader', {
388
386
  effects: v.map((effect) => {
389
- let name = effect.type
390
- if (effectNames[name] !== undefined) {
391
- name += ++effectNames[name]
392
- } else {
393
- effectNames[name] = 1
394
- }
395
- name += this.element.counter
396
- this.element.effectNames.push(name)
397
- // temporary add counter to work around shader caching issues
398
- return renderer.createEffect(effect.type, effect.props, name)
387
+ return renderer.createEffect(effect.type, effect.props)
399
388
  }),
400
389
  })
401
- } else {
402
- for (let i = 0; i < v.length; i++) {
403
- const name = this.element.effectNames[i]
404
- // temporary add counter to work around shader caching issues
405
- const target = this.element.node.shader.props[name]
406
- const props = Object.keys(v[i].props)
407
- if (target == undefined) continue
408
- for (let j = 0; j < props.length; j++) {
409
- target[props[j]] = v[i].props[props[j]]
410
- }
411
- }
412
390
  }
413
391
  },
414
392
  set clipping(v) {
@@ -674,7 +652,7 @@ const Element = {
674
652
  return
675
653
  }
676
654
  // fire transition end callback when animation ends (if specified)
677
- if (transition.end && typeof transition.end === 'function') {
655
+ if (this.node !== undefined && transition.end && typeof transition.end === 'function') {
678
656
  transition.end.call(this.component, this, prop, this.node[prop])
679
657
  }
680
658
  // remove the prop from scheduled transitions
@@ -687,9 +665,7 @@ const Element = {
687
665
  destroy() {
688
666
  if (this.node === null) return
689
667
 
690
- Log.debug('Deleting Node', this.nodeId)
691
- this.node.destroy()
692
-
668
+ Log.debug('Deleting Node', this.nodeId)
693
669
  // Clearing transition end callback functions
694
670
  const transitionProps = Object.keys(this.scheduledTransitions)
695
671
  for (let i = 0; i < transitionProps.length; i++) {
@@ -700,7 +676,32 @@ const Element = {
700
676
  }
701
677
  }
702
678
 
703
- // remove node reference
679
+ // not setting to null and deleting,
680
+ // because transition stopped might still be fired (maybe a renderer fix resolves that)
681
+ this.scheduledTransitions = {}
682
+
683
+ this.component = null
684
+ delete this.component
685
+
686
+ this.config = null
687
+ delete this.config
688
+
689
+ this.counter = null
690
+ delete this.counter
691
+
692
+ this.props.raw = {}
693
+ this.props.element = null
694
+ this.props.props = null
695
+ this.props = {}
696
+ delete this.props
697
+
698
+ this.triggerLayout = null
699
+ delete this.triggerLayout
700
+
701
+ this.forComponent = null
702
+ delete this.forComponent
703
+
704
+ this.node.destroy()
704
705
  this.node = null
705
706
  },
706
707
  get nodeId() {
@@ -738,7 +739,6 @@ export default (config, component) => {
738
739
  scheduledTransitions: {},
739
740
  config,
740
741
  component,
741
- effectNames: [],
742
742
  counter: counter++,
743
743
  })
744
744
  }
@@ -511,6 +511,7 @@ const generateForLoopCode = function (templateObject, parent) {
511
511
  }
512
512
  effect(eff${index}, ${key})
513
513
  effects.push(eff${index})
514
+ component[Symbol.for('effects')].push(eff${index})
514
515
  `)
515
516
  } else {
516
517
  // props shouldn't be wrapped in an effect, but simply passed on
@@ -562,17 +563,21 @@ const generateForLoopCode = function (templateObject, parent) {
562
563
 
563
564
  ctx.renderCode.push(`
564
565
  let forEffects${forStartCounter}
565
- effect(() => {
566
+ const eff${forStartCounter} = () => {
566
567
  component[Symbol.for('removeGlobalEffects')](forEffects${forStartCounter})
567
568
  forEffects${forStartCounter} = null
568
569
  forEffects${forStartCounter} = forloop${forStartCounter}(${cast(
569
570
  result[2],
570
571
  ':for'
571
572
  )}, elms, created${forStartCounter})
572
- }, ['${effectKey}', ${effectKeys.join(',')}] )
573
+ }
574
+
575
+ component[Symbol.for('effects')].push(eff${forStartCounter})
576
+
577
+ effect(eff${forStartCounter}, ['${effectKey}', ${effectKeys.join(',')}] )
573
578
  `)
574
579
 
575
- outerScopeEffects.forEach((effect) => {
580
+ outerScopeEffects.forEach((effect, outerScopeEffectsIndex) => {
576
581
  const matches = [...effect.matchAll(scopeRegex)]
577
582
 
578
583
  let l = matches.length
@@ -589,7 +594,7 @@ const generateForLoopCode = function (templateObject, parent) {
589
594
  }
590
595
 
591
596
  ctx.renderCode.push(`
592
- effect(() => {
597
+ const eff${forStartCounter}_${outerScopeEffectsIndex} = () => {
593
598
  void ${refs.join(', ')}
594
599
  for(let __index = 0; __index < ${interpolate(result[2])}.length; __index++) {
595
600
  if(__index < from${forStartCounter} || __index >= to${forStartCounter}) continue
@@ -602,7 +607,9 @@ const generateForLoopCode = function (templateObject, parent) {
602
607
  ctx.renderCode.push(`
603
608
  ${effect}
604
609
  }
605
- })
610
+ }
611
+ component[Symbol.for('effects')].push(eff${forStartCounter}_${outerScopeEffectsIndex})
612
+ effect(eff${forStartCounter}_${outerScopeEffectsIndex})
606
613
  `)
607
614
  })
608
615