jsuites 6.2.0 → 6.3.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 (2) hide show
  1. package/dist/jsuites.js +328 -27
  2. package/package.json +2 -2
package/dist/jsuites.js CHANGED
@@ -4618,7 +4618,7 @@ const Mask = utils.Mask;
4618
4618
  } else {
4619
4619
  setCursor(s);
4620
4620
 
4621
- update();
4621
+ update(e);
4622
4622
  }
4623
4623
  }
4624
4624
  }
@@ -4626,7 +4626,10 @@ const Mask = utils.Mask;
4626
4626
  // Update Calendar
4627
4627
  const update = function(e) {
4628
4628
  self.setValue(getValue());
4629
- self.close({ origin: 'button' });
4629
+
4630
+ if (! (e && e.type === 'click' && e.target.tagName === 'DIV' && self.time === true)) {
4631
+ self.close({ origin: 'button' });
4632
+ }
4630
4633
  }
4631
4634
 
4632
4635
  const reset = function() {
@@ -4906,7 +4909,7 @@ const Mask = utils.Mask;
4906
4909
  }
4907
4910
  } else if (e.code === 'Enter') {
4908
4911
  if (! self.isClosed()) {
4909
- update();
4912
+ update(e);
4910
4913
  } else {
4911
4914
  self.open();
4912
4915
  }
@@ -14503,11 +14506,22 @@ function Tabs(el, options) {
14503
14506
  var prev = null;
14504
14507
  var next = null;
14505
14508
  var border = null;
14509
+ var header = null;
14510
+ var controls = null;
14511
+ var add = null;
14512
+
14513
+ // Event handler references for cleanup
14514
+ var headersClickHandler = null;
14515
+ var headersContextMenuHandler = null;
14506
14516
 
14507
14517
  // Helpers
14508
14518
  const setBorder = function(index) {
14509
14519
  if (obj.options.animation) {
14510
14520
  setTimeout(function() {
14521
+ // Guard against destroyed state
14522
+ if (!obj.headers || !obj.headers.children[index]) {
14523
+ return;
14524
+ }
14511
14525
  let rect = obj.headers.children[index].getBoundingClientRect();
14512
14526
 
14513
14527
  if (obj.options.palette === 'modern') {
@@ -14528,6 +14542,10 @@ function Tabs(el, options) {
14528
14542
  }
14529
14543
 
14530
14544
  var updateControls = function(x) {
14545
+ // Guard against destroyed state
14546
+ if (!obj.headers) {
14547
+ return;
14548
+ }
14531
14549
  if (typeof(obj.headers.scrollTo) == 'function') {
14532
14550
  obj.headers.scrollTo({
14533
14551
  left: x,
@@ -14842,7 +14860,7 @@ function Tabs(el, options) {
14842
14860
  }
14843
14861
 
14844
14862
  // Header
14845
- var header = document.createElement('div');
14863
+ header = document.createElement('div');
14846
14864
  header.className = 'jtabs-headers-container';
14847
14865
  header.appendChild(obj.headers);
14848
14866
  if (obj.options.maxWidth) {
@@ -14850,7 +14868,7 @@ function Tabs(el, options) {
14850
14868
  }
14851
14869
 
14852
14870
  // Controls
14853
- var controls = document.createElement('div');
14871
+ controls = document.createElement('div');
14854
14872
  controls.className = 'jtabs-controls';
14855
14873
  controls.setAttribute('draggable', 'false');
14856
14874
  header.appendChild(controls);
@@ -14866,7 +14884,7 @@ function Tabs(el, options) {
14866
14884
 
14867
14885
  // New button
14868
14886
  if (obj.options.allowCreate == true) {
14869
- var add = document.createElement('div');
14887
+ add = document.createElement('div');
14870
14888
  add.className = 'jtabs-add';
14871
14889
  add.onclick = function() {
14872
14890
  obj.create();
@@ -14935,7 +14953,7 @@ function Tabs(el, options) {
14935
14953
  }
14936
14954
 
14937
14955
  // Events
14938
- obj.headers.addEventListener("click", function(e) {
14956
+ headersClickHandler = function(e) {
14939
14957
  if (e.target.parentNode.classList.contains('jtabs-headers')) {
14940
14958
  var target = e.target;
14941
14959
  } else {
@@ -14951,11 +14969,13 @@ function Tabs(el, options) {
14951
14969
  if (typeof(obj.options.onclick) == 'function') {
14952
14970
  obj.options.onclick(el, obj, index, obj.headers.children[index], obj.content.children[index]);
14953
14971
  }
14954
- });
14972
+ };
14973
+ obj.headers.addEventListener("click", headersClickHandler);
14955
14974
 
14956
- obj.headers.addEventListener("contextmenu", function(e) {
14975
+ headersContextMenuHandler = function(e) {
14957
14976
  obj.selectIndex(e.target);
14958
- });
14977
+ };
14978
+ obj.headers.addEventListener("contextmenu", headersContextMenuHandler);
14959
14979
 
14960
14980
  if (obj.headers.children.length) {
14961
14981
  // Open first tab
@@ -15029,6 +15049,71 @@ function Tabs(el, options) {
15029
15049
  obj.init();
15030
15050
  }
15031
15051
 
15052
+ /**
15053
+ * Destroy the tabs instance and release all resources
15054
+ */
15055
+ obj.destroy = function() {
15056
+ // Remove event listeners from headers
15057
+ if (obj.headers) {
15058
+ if (headersClickHandler) {
15059
+ obj.headers.removeEventListener('click', headersClickHandler);
15060
+ }
15061
+ if (headersContextMenuHandler) {
15062
+ obj.headers.removeEventListener('contextmenu', headersContextMenuHandler);
15063
+ }
15064
+ }
15065
+
15066
+ // Clear onclick handlers
15067
+ if (prev) {
15068
+ prev.onclick = null;
15069
+ }
15070
+ if (next) {
15071
+ next.onclick = null;
15072
+ }
15073
+ if (add) {
15074
+ add.onclick = null;
15075
+ }
15076
+
15077
+ // Remove DOM elements
15078
+ if (header && header.parentNode) {
15079
+ header.parentNode.removeChild(header);
15080
+ }
15081
+ if (obj.content && obj.content.parentNode) {
15082
+ obj.content.parentNode.removeChild(obj.content);
15083
+ }
15084
+
15085
+ // Remove class from element
15086
+ el.classList.remove('jtabs');
15087
+ el.classList.remove('jtabs-animation');
15088
+ el.classList.remove('jtabs-modern');
15089
+
15090
+ // Remove instance reference
15091
+ delete el.tabs;
15092
+
15093
+ // Clear options callbacks to release closures
15094
+ if (obj.options) {
15095
+ obj.options.onclick = null;
15096
+ obj.options.onload = null;
15097
+ obj.options.onchange = null;
15098
+ obj.options.oncreate = null;
15099
+ obj.options.ondelete = null;
15100
+ obj.options.onbeforecreate = null;
15101
+ obj.options.onchangeposition = null;
15102
+ }
15103
+
15104
+ // Clear references
15105
+ obj.headers = null;
15106
+ obj.content = null;
15107
+ header = null;
15108
+ controls = null;
15109
+ prev = null;
15110
+ next = null;
15111
+ border = null;
15112
+ add = null;
15113
+ headersClickHandler = null;
15114
+ headersContextMenuHandler = null;
15115
+ }
15116
+
15032
15117
  el.tabs = obj;
15033
15118
 
15034
15119
  return obj;
@@ -15228,11 +15313,13 @@ function Color(el, options) {
15228
15313
  * Close color pallete
15229
15314
  */
15230
15315
  obj.close = function(ignoreEvents) {
15231
- if (container.classList.contains('jcolor-focus')) {
15316
+ if (container && container.classList.contains('jcolor-focus')) {
15232
15317
  // Remove focus
15233
15318
  container.classList.remove('jcolor-focus');
15234
15319
  // Make sure backdrop is hidden
15235
- backdrop.style.display = '';
15320
+ if (backdrop) {
15321
+ backdrop.style.display = '';
15322
+ }
15236
15323
  // Call related events
15237
15324
  if (! ignoreEvents && typeof(obj.options.onclose) == 'function') {
15238
15325
  obj.options.onclose(el, obj);
@@ -15241,7 +15328,7 @@ function Color(el, options) {
15241
15328
  tracking(obj, false);
15242
15329
  }
15243
15330
 
15244
- return obj.options.value;
15331
+ return obj.options.value ? obj.options.value : null;
15245
15332
  }
15246
15333
 
15247
15334
  /**
@@ -15652,7 +15739,7 @@ function Color(el, options) {
15652
15739
  el.appendChild(container);
15653
15740
  }
15654
15741
 
15655
- container.addEventListener("click", function(e) {
15742
+ containerClickHandler = function(e) {
15656
15743
  if (e.target.tagName == 'TD') {
15657
15744
  var value = e.target.getAttribute('data-value');
15658
15745
  if (value) {
@@ -15671,21 +15758,24 @@ function Color(el, options) {
15671
15758
  } else {
15672
15759
  obj.open();
15673
15760
  }
15674
- });
15761
+ };
15762
+ container.addEventListener("click", containerClickHandler);
15675
15763
 
15676
15764
  /**
15677
15765
  * If element is focus open the picker
15678
15766
  */
15679
- el.addEventListener("mouseup", function(e) {
15767
+ elMouseupHandler = function(e) {
15680
15768
  obj.open();
15681
- });
15769
+ };
15770
+ el.addEventListener("mouseup", elMouseupHandler);
15682
15771
 
15683
15772
  // If the picker is open on the spectrum tab, it changes the canvas size when the window size is changed
15684
- window.addEventListener('resize', function() {
15773
+ windowResizeHandler = function() {
15685
15774
  if (container.classList.contains('jcolor-focus') && jsuitesTabs.getActive() == 1) {
15686
15775
  resizeCanvas();
15687
15776
  }
15688
- });
15777
+ };
15778
+ window.addEventListener('resize', windowResizeHandler);
15689
15779
 
15690
15780
  // Default opened
15691
15781
  if (obj.options.opened == true) {
@@ -15729,6 +15819,73 @@ function Color(el, options) {
15729
15819
  }
15730
15820
  }
15731
15821
 
15822
+ // Store event handler references for cleanup
15823
+ var containerClickHandler = null;
15824
+ var elMouseupHandler = null;
15825
+ var windowResizeHandler = null;
15826
+
15827
+ /**
15828
+ * Destroy the color picker instance and release all resources
15829
+ */
15830
+ obj.destroy = function() {
15831
+ // Close if open (removes from tracking)
15832
+ obj.close(true);
15833
+
15834
+ // Remove event listeners
15835
+ if (container && containerClickHandler) {
15836
+ container.removeEventListener('click', containerClickHandler);
15837
+ }
15838
+ if (el && elMouseupHandler) {
15839
+ el.removeEventListener('mouseup', elMouseupHandler);
15840
+ }
15841
+ if (windowResizeHandler) {
15842
+ window.removeEventListener('resize', windowResizeHandler);
15843
+ }
15844
+
15845
+ // Destroy the tabs component if it has destroy method
15846
+ if (jsuitesTabs && typeof jsuitesTabs.destroy === 'function') {
15847
+ jsuitesTabs.destroy();
15848
+ }
15849
+
15850
+ // Clear rgbInputs references
15851
+ rgbInputs = [];
15852
+
15853
+ // Remove container from DOM
15854
+ if (container && container.parentNode) {
15855
+ container.parentNode.removeChild(container);
15856
+ }
15857
+
15858
+ // Clean up element
15859
+ if (el.tagName === 'INPUT') {
15860
+ el.classList.remove('jcolor-input');
15861
+ el.readOnly = false;
15862
+ el.style.color = '';
15863
+ el.style.backgroundColor = '';
15864
+ }
15865
+
15866
+ // Remove instance properties from el
15867
+ delete el.color;
15868
+ delete el.change;
15869
+ delete el.val;
15870
+
15871
+ // Clear options callbacks to release closures
15872
+ if (obj.options) {
15873
+ obj.options.onchange = null;
15874
+ obj.options.onclose = null;
15875
+ obj.options.onopen = null;
15876
+ obj.options.onload = null;
15877
+ }
15878
+
15879
+ // Clear references
15880
+ container = null;
15881
+ backdrop = null;
15882
+ content = null;
15883
+ resetButton = null;
15884
+ closeButton = null;
15885
+ tabs = null;
15886
+ jsuitesTabs = null;
15887
+ }
15888
+
15732
15889
  init();
15733
15890
 
15734
15891
  return obj;
@@ -18105,6 +18262,58 @@ function Picker(el, options) {
18105
18262
  }
18106
18263
  }
18107
18264
 
18265
+ /**
18266
+ * Destroy the picker instance and release all resources
18267
+ */
18268
+ obj.destroy = function() {
18269
+ // Close if open (removes from tracking)
18270
+ obj.close();
18271
+
18272
+ // Remove event listeners
18273
+ el.onmousedown = null;
18274
+ if (dropdownContent) {
18275
+ dropdownContent.onclick = null;
18276
+ }
18277
+
18278
+ // Remove created DOM elements
18279
+ if (dropdownHeader && dropdownHeader.parentNode) {
18280
+ dropdownHeader.parentNode.removeChild(dropdownHeader);
18281
+ }
18282
+ if (dropdownContent && dropdownContent.parentNode) {
18283
+ dropdownContent.parentNode.removeChild(dropdownContent);
18284
+ }
18285
+
18286
+ // Remove classes and attributes from el
18287
+ el.classList.remove('jpicker');
18288
+ el.classList.remove('jpicker-focus');
18289
+ el.removeAttribute('role');
18290
+ el.removeAttribute('aria-haspopup');
18291
+ el.removeAttribute('aria-expanded');
18292
+ el.removeAttribute('aria-controls');
18293
+ el.removeAttribute('tabindex');
18294
+
18295
+ // Remove instance properties from el
18296
+ delete el.picker;
18297
+ delete el.value;
18298
+ delete el.change;
18299
+ delete el.val;
18300
+
18301
+ // Clear options callbacks to release closures
18302
+ if (obj.options) {
18303
+ obj.options.onchange = null;
18304
+ obj.options.onclose = null;
18305
+ obj.options.onopen = null;
18306
+ obj.options.onload = null;
18307
+ obj.options.onselect = null;
18308
+ obj.options.onmouseover = null;
18309
+ obj.options.render = null;
18310
+ }
18311
+
18312
+ // Clear references
18313
+ dropdownHeader = null;
18314
+ dropdownContent = null;
18315
+ }
18316
+
18108
18317
  /**
18109
18318
  * Create floating picker
18110
18319
  */
@@ -18187,6 +18396,13 @@ function Toolbar(el, options) {
18187
18396
  var obj = { type:'toolbar' };
18188
18397
  obj.options = {};
18189
18398
 
18399
+ // Track internal components for cleanup
18400
+ var internalComponents = [];
18401
+
18402
+ // Event handler references for cleanup
18403
+ var elClickHandler = null;
18404
+ var windowResizeHandler = null;
18405
+
18190
18406
  // Default configuration
18191
18407
  var defaults = {
18192
18408
  app: null,
@@ -18257,8 +18473,88 @@ function Toolbar(el, options) {
18257
18473
  }
18258
18474
 
18259
18475
  obj.destroy = function() {
18260
- toolbar.remove();
18476
+ // Close if open (removes from tracking)
18477
+ obj.close();
18478
+
18479
+ // Destroy all internal components (pickers, etc.)
18480
+ for (var i = 0; i < internalComponents.length; i++) {
18481
+ var comp = internalComponents[i];
18482
+ if (comp) {
18483
+ // First destroy any nested components created in onload (stored on the picker instance)
18484
+ if (comp.components && comp.components.length) {
18485
+ for (var j = 0; j < comp.components.length; j++) {
18486
+ if (comp.components[j] && typeof comp.components[j].destroy === 'function') {
18487
+ comp.components[j].destroy();
18488
+ }
18489
+ }
18490
+ comp.components = null;
18491
+ }
18492
+ // Then destroy the picker/component itself
18493
+ if (typeof comp.destroy === 'function') {
18494
+ comp.destroy();
18495
+ }
18496
+ }
18497
+ }
18498
+ internalComponents = [];
18499
+
18500
+ // Clear onclick handlers from DOM elements (releases bound function references)
18501
+ if (toolbarContent) {
18502
+ var items = toolbarContent.querySelectorAll('.jtoolbar-item');
18503
+ for (var i = 0; i < items.length; i++) {
18504
+ items[i].onclick = null;
18505
+ items[i].updateState = null;
18506
+ }
18507
+ }
18508
+ if (toolbarFloating) {
18509
+ var items = toolbarFloating.querySelectorAll('.jtoolbar-item');
18510
+ for (var i = 0; i < items.length; i++) {
18511
+ items[i].onclick = null;
18512
+ items[i].updateState = null;
18513
+ }
18514
+ }
18515
+
18516
+ // Clear options items callbacks to release closures
18517
+ if (obj.options && obj.options.items) {
18518
+ for (var i = 0; i < obj.options.items.length; i++) {
18519
+ var item = obj.options.items[i];
18520
+ // Clear all callback references
18521
+ item.onclick = null;
18522
+ item.onchange = null;
18523
+ item.onload = null;
18524
+ item.render = null;
18525
+ item.updateState = null;
18526
+ item.onopen = null;
18527
+ item.onclose = null;
18528
+ }
18529
+ obj.options.items = null;
18530
+ }
18531
+
18532
+ // Remove event listeners
18533
+ if (elClickHandler) {
18534
+ el.removeEventListener('click', elClickHandler);
18535
+ elClickHandler = null;
18536
+ }
18537
+ if (windowResizeHandler) {
18538
+ window.removeEventListener('resize', windowResizeHandler);
18539
+ windowResizeHandler = null;
18540
+ }
18541
+
18542
+ // Clear DOM
18261
18543
  el.innerHTML = '';
18544
+
18545
+ // Clear references
18546
+ toolbarContent = null;
18547
+ toolbarFloating = null;
18548
+ toolbarArrow = null;
18549
+
18550
+ // Remove classes
18551
+ el.classList.remove('jtoolbar');
18552
+ el.classList.remove('jtoolbar-container');
18553
+ el.classList.remove('jtoolbar-mobile');
18554
+ el.classList.remove('jtoolbar-disabled');
18555
+
18556
+ // Remove instance reference
18557
+ delete el.toolbar;
18262
18558
  }
18263
18559
 
18264
18560
  obj.update = function(a, b) {
@@ -18320,7 +18616,8 @@ function Toolbar(el, options) {
18320
18616
  }
18321
18617
 
18322
18618
  if (items[i].type == 'select' || items[i].type == 'dropdown') {
18323
- Picker(toolbarItem, items[i]);
18619
+ var picker = Picker(toolbarItem, items[i]);
18620
+ internalComponents.push(picker);
18324
18621
  } else if (items[i].type == 'divisor') {
18325
18622
  toolbarItem.classList.add('jtoolbar-divisor');
18326
18623
  } else if (items[i].type == 'label') {
@@ -18414,7 +18711,9 @@ function Toolbar(el, options) {
18414
18711
  }
18415
18712
 
18416
18713
  obj.close = function() {
18417
- toolbarArrow.classList.remove('jtoolbar-arrow-selected')
18714
+ if (toolbarArrow) {
18715
+ toolbarArrow.classList.remove('jtoolbar-arrow-selected')
18716
+ }
18418
18717
  // End tracking
18419
18718
  tracking(obj, false);
18420
18719
  }
@@ -18457,7 +18756,7 @@ function Toolbar(el, options) {
18457
18756
  el.classList[state]('jtoolbar-disabled');
18458
18757
  }
18459
18758
 
18460
- el.onclick = function(e) {
18759
+ elClickHandler = function(e) {
18461
18760
  var element = helpers.findElement(e.target, 'jtoolbar-item');
18462
18761
  if (element) {
18463
18762
  obj.selectItem(element);
@@ -18466,11 +18765,13 @@ function Toolbar(el, options) {
18466
18765
  if (e.target.classList.contains('jtoolbar-arrow') || e.target.parentNode.classList.contains('jtoolbar-arrow')) {
18467
18766
  obj.open();
18468
18767
  }
18469
- }
18768
+ };
18769
+ el.addEventListener('click', elClickHandler);
18470
18770
 
18471
- window.addEventListener('resize', function() {
18771
+ windowResizeHandler = function() {
18472
18772
  obj.refresh();
18473
- });
18773
+ };
18774
+ window.addEventListener('resize', windowResizeHandler);
18474
18775
 
18475
18776
  // Toolbar
18476
18777
  el.classList.add('jtoolbar');
@@ -23146,7 +23447,7 @@ var jSuites = {
23146
23447
  ...dictionary,
23147
23448
  ...helpers,
23148
23449
  /** Current version */
23149
- version: '6.2.0',
23450
+ version: '6.3.0',
23150
23451
  /** Bind new extensions to Jsuites */
23151
23452
  setExtensions: function(o) {
23152
23453
  if (typeof(o) == 'object') {
package/package.json CHANGED
@@ -26,14 +26,14 @@
26
26
  },
27
27
  "main": "dist/jsuites.js",
28
28
  "types": "dist/jsuites.d.ts",
29
- "version": "6.2.0",
29
+ "version": "6.3.0",
30
30
  "bugs": "https://github.com/jsuites/jsuites/issues",
31
31
  "homepage": "https://github.com/jsuites/jsuites",
32
32
  "docs": "https://jsuites.net",
33
33
  "download": "https://github.com/jsuites/jsuites/archive/master.zip",
34
34
  "dependencies": {
35
35
  "@jsuites/utils": "^6.0.4",
36
- "@lemonadejs/calendar": "^5.8.3",
36
+ "@lemonadejs/calendar": "^5.8.4",
37
37
  "@lemonadejs/color": "^5.8.0",
38
38
  "@lemonadejs/contextmenu": "^5.8.3",
39
39
  "@lemonadejs/dropdown": "^5.8.2",