@nebula.js/stardust 2.1.0 → 2.2.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.
package/CHANGELOG.md CHANGED
@@ -3,6 +3,10 @@
3
3
  All notable changes to this project will be documented in this file.
4
4
  See [Conventional Commits](https://conventionalcommits.org) for commit guidelines.
5
5
 
6
+ # [2.2.0](https://github.com/qlik-oss/nebula.js/compare/v2.1.0...v2.2.0) (2021-11-17)
7
+
8
+ **Note:** Version bump only for package @nebula.js/stardust
9
+
6
10
  # [2.1.0](https://github.com/qlik-oss/nebula.js/compare/v2.0.0...v2.1.0) (2021-10-20)
7
11
 
8
12
  ### Features
package/core/esm/dev.js CHANGED
@@ -1,5 +1,5 @@
1
1
  /*
2
- * @nebula.js/stardust v2.1.0
2
+ * @nebula.js/stardust v2.2.0
3
3
  * Copyright (c) 2021 QlikTech International AB
4
4
  * Released under the MIT license.
5
5
  */
@@ -5690,7 +5690,7 @@ function useAppSelections(app) {
5690
5690
  return [appSelections, navState];
5691
5691
  }
5692
5692
 
5693
- var NEBULA_VERSION_HASH = "5337" ;
5693
+ var NEBULA_VERSION_HASH = "34e9" ;
5694
5694
  var counter = 0;
5695
5695
  var NebulaApp = forwardRef(function (_ref, ref) {
5696
5696
  var initialContext = _ref.initialContext,
@@ -5766,7 +5766,7 @@ function boot(_ref2) {
5766
5766
  var appRef = React.createRef();
5767
5767
  var element = document.createElement('div');
5768
5768
  element.style.display = 'none';
5769
- element.setAttribute('data-nebulajs-version', "2.1.0" );
5769
+ element.setAttribute('data-nebulajs-version', "2.2.0" );
5770
5770
  element.setAttribute('data-app-id', app.id);
5771
5771
  document.body.appendChild(element);
5772
5772
  ReactDOM.render( /*#__PURE__*/React.createElement(NebulaApp, {
@@ -7634,6 +7634,9 @@ var Item = React.forwardRef(function (_ref, ref) {
7634
7634
  ref: !addAnchor ? ref : null,
7635
7635
  title: item.label,
7636
7636
  onClick: item.action,
7637
+ onKeyDown: function onKeyDown(e) {
7638
+ return ['Enter', ' ', 'Spacebar'].includes(e.key) && item.keyboardAction();
7639
+ },
7637
7640
  disabled: disabled,
7638
7641
  style: style,
7639
7642
  className: ActionElement.className
@@ -7680,7 +7683,9 @@ function useDefaultSelectionActions(_ref) {
7680
7683
  _ref$onConfirm = _ref.onConfirm,
7681
7684
  onConfirm = _ref$onConfirm === void 0 ? function () {} : _ref$onConfirm,
7682
7685
  _ref$onCancel = _ref.onCancel,
7683
- onCancel = _ref$onCancel === void 0 ? function () {} : _ref$onCancel;
7686
+ onCancel = _ref$onCancel === void 0 ? function () {} : _ref$onCancel,
7687
+ _ref$onKeyDeactivate = _ref.onKeyDeactivate,
7688
+ onKeyDeactivate = _ref$onKeyDeactivate === void 0 ? function () {} : _ref$onKeyDeactivate;
7684
7689
 
7685
7690
  var _useContext = useContext(InstanceContext),
7686
7691
  translator = _useContext.translator;
@@ -7704,8 +7709,13 @@ function useDefaultSelectionActions(_ref) {
7704
7709
  return api.canCancel();
7705
7710
  },
7706
7711
  action: function action() {
7712
+ onCancel();
7707
7713
  api.cancel();
7714
+ },
7715
+ keyboardAction: function keyboardAction(e) {
7716
+ onKeyDeactivate(e);
7708
7717
  onCancel();
7718
+ api.cancel();
7709
7719
  },
7710
7720
  getSvgIconShape: close
7711
7721
  }, {
@@ -7716,8 +7726,13 @@ function useDefaultSelectionActions(_ref) {
7716
7726
  return api.canConfirm();
7717
7727
  },
7718
7728
  action: function action() {
7729
+ onConfirm();
7719
7730
  api.confirm();
7731
+ },
7732
+ keyboardAction: function keyboardAction(e) {
7733
+ onKeyDeactivate(e);
7720
7734
  onConfirm();
7735
+ api.confirm();
7721
7736
  },
7722
7737
  getSvgIconShape: tick
7723
7738
  }];
@@ -7924,14 +7939,19 @@ var ActionsToolbar = function ActionsToolbar(_ref2) {
7924
7939
  popover = _ref2$popover === void 0 ? {
7925
7940
  show: false,
7926
7941
  anchorEl: null
7927
- } : _ref2$popover;
7942
+ } : _ref2$popover,
7943
+ _ref2$focusHandler = _ref2.focusHandler,
7944
+ focusHandler = _ref2$focusHandler === void 0 ? null : _ref2$focusHandler,
7945
+ _ref2$actionsRefMock = _ref2.actionsRefMock,
7946
+ actionsRefMock = _ref2$actionsRefMock === void 0 ? null : _ref2$actionsRefMock;
7928
7947
  var defaultSelectionActions = useDefaultSelectionActions(selections);
7929
7948
 
7930
7949
  var _useStyles2 = useStyles$8(),
7931
7950
  itemSpacing = _useStyles2.itemSpacing;
7932
7951
 
7933
7952
  var _useContext = useContext(InstanceContext),
7934
- translator = _useContext.translator;
7953
+ translator = _useContext.translator,
7954
+ keyboardNavigation = _useContext.keyboardNavigation;
7935
7955
 
7936
7956
  var _useState = useState$1(false),
7937
7957
  _useState2 = _slicedToArray(_useState, 2),
@@ -7954,12 +7974,21 @@ var ActionsToolbar = function ActionsToolbar(_ref2) {
7954
7974
  setMoreAlignTo = _useState8[1];
7955
7975
 
7956
7976
  var moreRef = useRef();
7977
+ var actionsRef = useRef();
7957
7978
  var theme = useTheme$1();
7958
7979
  var dividerStyle = useMemo$1(function () {
7959
7980
  return {
7960
7981
  margin: theme.spacing(0.5, 0)
7961
7982
  };
7962
7983
  });
7984
+
7985
+ var getEnabledButton = function getEnabledButton(last) {
7986
+ var actionsElement = actionsRef.current || actionsRefMock;
7987
+ if (!actionsElement) return null;
7988
+ var buttons = actionsElement.querySelectorAll('button:not(.Mui-disabled)');
7989
+ return buttons[last ? buttons.length - 1 : 0];
7990
+ };
7991
+
7963
7992
  useEffect$1(function () {
7964
7993
  return function () {
7965
7994
  return setShowMoreItems(false);
@@ -7968,6 +7997,22 @@ var ActionsToolbar = function ActionsToolbar(_ref2) {
7968
7997
  useEffect$1(function () {
7969
7998
  setMoreEnabled(more$1.enabled);
7970
7999
  }, [more$1.enabled]);
8000
+ useEffect$1(function () {
8001
+ if (!focusHandler) return;
8002
+
8003
+ var focusFirst = function focusFirst() {
8004
+ var enabledButton = getEnabledButton(false);
8005
+ enabledButton && enabledButton.focus();
8006
+ };
8007
+
8008
+ var focusLast = function focusLast() {
8009
+ var enabledButton = getEnabledButton(true);
8010
+ enabledButton && enabledButton.focus();
8011
+ };
8012
+
8013
+ focusHandler.on('focus_toolbar_first', focusFirst);
8014
+ focusHandler.on('focus_toolbar_last', focusLast);
8015
+ }, []);
7971
8016
  var newActions = useMemo$1(function () {
7972
8017
  return actions.filter(function (a) {
7973
8018
  return !a.hidden;
@@ -8000,10 +8045,23 @@ var ActionsToolbar = function ActionsToolbar(_ref2) {
8000
8045
  setMoreAlignTo(moreRef);
8001
8046
  }
8002
8047
 
8048
+ var tabCallback = // if keyboardNavigation is true, create a callback to handle tabbing from the first/last button in the toolbar that resets focus on the content
8049
+ keyboardNavigation && focusHandler && focusHandler.refocusContent ? function (evt) {
8050
+ if (evt.key !== 'Tab') return;
8051
+ var isTabbingOut = evt.shiftKey && getEnabledButton(false) === evt.target || !evt.shiftKey && getEnabledButton(true) === evt.target;
8052
+
8053
+ if (isTabbingOut) {
8054
+ evt.preventDefault();
8055
+ evt.stopPropagation();
8056
+ focusHandler.refocusContent();
8057
+ }
8058
+ } : null;
8003
8059
  var showActions = newActions.length > 0;
8004
8060
  var showMore = moreActions.length > 0;
8005
8061
  var showDivider = showActions && selections.show || showMore && selections.show;
8006
8062
  var Actions = /*#__PURE__*/React.createElement(Grid, {
8063
+ ref: actionsRef,
8064
+ onKeyDown: tabCallback,
8007
8065
  container: true,
8008
8066
  spacing: 0,
8009
8067
  wrap: "nowrap"
@@ -10222,7 +10280,9 @@ function hcHandler(_ref) {
10222
10280
 
10223
10281
  function fieldType(f) {
10224
10282
  if ( // a string starting with '=' is just a convention we use
10225
- typeof f === 'string' && f[0] === '=' || _typeof$1(f) === 'object' && f.qDef && f.qDef.qDef || _typeof$1(f) === 'object' && f.qLibraryId && f.type === 'measure') {
10283
+ typeof f === 'string' && f[0] === '=' || // based on NxMeasure and NxInlineMeasureDef
10284
+ _typeof$1(f) === 'object' && f.qDef && f.qDef.qDef || // use 'type' instead of 'qType' since this is not a real property
10285
+ _typeof$1(f) === 'object' && f.qLibraryId && f.type === 'measure') {
10226
10286
  return 'measure';
10227
10287
  }
10228
10288
 
@@ -11611,7 +11671,8 @@ var Header = function Header(_ref) {
11611
11671
  var layout = _ref.layout,
11612
11672
  sn = _ref.sn,
11613
11673
  anchorEl = _ref.anchorEl,
11614
- hovering = _ref.hovering;
11674
+ hovering = _ref.hovering,
11675
+ focusHandler = _ref.focusHandler;
11615
11676
  var showTitle = layout.showTitles && !!layout.title;
11616
11677
  var showSubtitle = layout.showTitles && !!layout.subtitle;
11617
11678
  var showInSelectionActions = layout.qSelectionInfo && layout.qSelectionInfo.qInSelections;
@@ -11657,13 +11718,15 @@ var Header = function Header(_ref) {
11657
11718
  show: showToolbar,
11658
11719
  selections: {
11659
11720
  show: showInSelectionActions,
11660
- api: sn.component.selections
11721
+ api: sn.component.selections,
11722
+ onKeyDeactivate: focusHandler.refocusContent
11661
11723
  },
11662
11724
  actions: actions,
11663
11725
  popover: {
11664
11726
  show: showPopoverToolbar,
11665
11727
  anchorEl: anchorEl
11666
- }
11728
+ },
11729
+ focusHandler: focusHandler
11667
11730
  });
11668
11731
  return /*#__PURE__*/React.createElement(Grid, {
11669
11732
  ref: containerRef,
@@ -12068,7 +12131,7 @@ var LoadingSn = function LoadingSn(_ref) {
12068
12131
  return clearTimeout(handle);
12069
12132
  };
12070
12133
  }, []);
12071
- return showLoading && /*#__PURE__*/React.createElement(Loading, null);
12134
+ return showLoading ? /*#__PURE__*/React.createElement(Loading, null) : null;
12072
12135
  };
12073
12136
 
12074
12137
  var handleModal = function handleModal(_ref2) {
@@ -12309,12 +12372,12 @@ var getType = /*#__PURE__*/function () {
12309
12372
 
12310
12373
  var loadType = /*#__PURE__*/function () {
12311
12374
  var _ref8 = _asyncToGenerator( /*#__PURE__*/regeneratorRuntime.mark(function _callee3(_ref7) {
12312
- var dispatch, types, visualization, version, model, app, selections, blurCallback, nebbie, snType, sn;
12375
+ var dispatch, types, visualization, version, model, app, selections, nebbie, focusHandler, snType, sn;
12313
12376
  return regeneratorRuntime.wrap(function _callee3$(_context3) {
12314
12377
  while (1) {
12315
12378
  switch (_context3.prev = _context3.next) {
12316
12379
  case 0:
12317
- dispatch = _ref7.dispatch, types = _ref7.types, visualization = _ref7.visualization, version = _ref7.version, model = _ref7.model, app = _ref7.app, selections = _ref7.selections, blurCallback = _ref7.blurCallback, nebbie = _ref7.nebbie;
12380
+ dispatch = _ref7.dispatch, types = _ref7.types, visualization = _ref7.visualization, version = _ref7.version, model = _ref7.model, app = _ref7.app, selections = _ref7.selections, nebbie = _ref7.nebbie, focusHandler = _ref7.focusHandler;
12318
12381
  _context3.prev = 1;
12319
12382
  _context3.next = 4;
12320
12383
  return getType({
@@ -12330,7 +12393,7 @@ var loadType = /*#__PURE__*/function () {
12330
12393
  app: app,
12331
12394
  selections: selections,
12332
12395
  nebbie: nebbie,
12333
- blurCallback: blurCallback
12396
+ focusHandler: focusHandler
12334
12397
  });
12335
12398
  return _context3.abrupt("return", sn);
12336
12399
 
@@ -12404,9 +12467,10 @@ var Cell = forwardRef(function (_ref9, ref) {
12404
12467
  appLayout = _useAppLayout2[0];
12405
12468
 
12406
12469
  var _useRect3 = useRect$1(),
12407
- _useRect4 = _slicedToArray(_useRect3, 2),
12470
+ _useRect4 = _slicedToArray(_useRect3, 3),
12408
12471
  contentRef = _useRect4[0],
12409
- contentRect = _useRect4[1];
12472
+ contentRect = _useRect4[1],
12473
+ contentNode = _useRect4[2];
12410
12474
 
12411
12475
  var _useState3 = useState$1(initialSnOptions),
12412
12476
  _useState4 = _slicedToArray(_useState3, 2),
@@ -12431,6 +12495,27 @@ var Cell = forwardRef(function (_ref9, ref) {
12431
12495
  enter: null,
12432
12496
  leave: null
12433
12497
  });
12498
+ var focusHandler = useRef({
12499
+ focusToolbarButton: function focusToolbarButton(last) {
12500
+ // eslint-disable-next-line react/no-this-in-sfc
12501
+ this.emit(last ? 'focus_toolbar_last' : 'focus_toolbar_first');
12502
+ }
12503
+ });
12504
+ useEffect$1(function () {
12505
+ eventmixin(focusHandler.current);
12506
+ }, []);
12507
+
12508
+ focusHandler.current.blurCallback = function (resetFocus) {
12509
+ halo.root.toggleFocusOfCells();
12510
+
12511
+ if (resetFocus && contentNode) {
12512
+ contentNode.focus();
12513
+ }
12514
+ };
12515
+
12516
+ focusHandler.current.refocusContent = function () {
12517
+ state.sn.component && typeof state.sn.component.focus === 'function' && state.sn.component.focus();
12518
+ };
12434
12519
 
12435
12520
  var handleOnMouseEnter = function handleOnMouseEnter() {
12436
12521
  if (hoveringDebouncer.current.leave) {
@@ -12463,14 +12548,6 @@ var Cell = forwardRef(function (_ref9, ref) {
12463
12548
  }
12464
12549
  };
12465
12550
 
12466
- var relinquishFocus = function relinquishFocus(resetFocus) {
12467
- halo.root.toggleFocusOfCells();
12468
-
12469
- if (resetFocus && cellNode) {
12470
- cellNode.focus();
12471
- }
12472
- };
12473
-
12474
12551
  useEffect$1(function () {
12475
12552
  if (initialError || !appLayout || !layout) {
12476
12553
  return undefined;
@@ -12543,7 +12620,7 @@ var Cell = forwardRef(function (_ref9, ref) {
12543
12620
  app: app,
12544
12621
  selections: selections,
12545
12622
  nebbie: nebbie,
12546
- blurCallback: relinquishFocus
12623
+ focusHandler: focusHandler.current
12547
12624
  });
12548
12625
 
12549
12626
  case 3:
@@ -12744,14 +12821,12 @@ var Cell = forwardRef(function (_ref9, ref) {
12744
12821
  height: '100%',
12745
12822
  overflow: 'hidden'
12746
12823
  },
12747
- tabIndex: keyboardNavigation ? 0 : -1,
12748
12824
  elevation: 0,
12749
12825
  square: true,
12750
12826
  className: CellElement.className,
12751
12827
  ref: cellRef,
12752
12828
  onMouseEnter: handleOnMouseEnter,
12753
- onMouseLeave: handleOnMouseLeave,
12754
- onKeyDown: keyboardNavigation ? handleKeyDown : null
12829
+ onMouseLeave: handleOnMouseLeave
12755
12830
  }, /*#__PURE__*/React.createElement(Grid, {
12756
12831
  container: true,
12757
12832
  direction: "column",
@@ -12768,8 +12843,11 @@ var Cell = forwardRef(function (_ref9, ref) {
12768
12843
  layout: layout,
12769
12844
  sn: state.sn,
12770
12845
  anchorEl: cellNode,
12771
- hovering: hovering
12846
+ hovering: hovering,
12847
+ focusHandler: focusHandler.current
12772
12848
  }, "\xA0"), /*#__PURE__*/React.createElement(Grid, {
12849
+ tabIndex: keyboardNavigation ? 0 : -1,
12850
+ onKeyDown: keyboardNavigation ? handleKeyDown : null,
12773
12851
  item: true,
12774
12852
  xs: true,
12775
12853
  style: {
@@ -15054,6 +15132,7 @@ function useRenderState() {
15054
15132
  * @property {boolean} active Set to true when the chart is activated, ie a user tabs to the chart and presses Enter or Space.
15055
15133
  * @property {function=} blur Function used by the visualization to tell Nebula to it wants to relinquish focus
15056
15134
  * @property {function=} focus Function used by the visualization to tell Nebula to it wants focus
15135
+ * @property {function=} focusSelection Function used by the visualization to tell Nebula to focus the selection toolbar
15057
15136
  */
15058
15137
 
15059
15138
  /**
@@ -15087,7 +15166,7 @@ function useRenderState() {
15087
15166
 
15088
15167
  function useKeyboard() {
15089
15168
  var keyboardNavigation = useInternalContext('keyboardNavigation');
15090
- var blurCallback = useInternalContext('blurCallback');
15169
+ var focusHandler = useInternalContext('focusHandler');
15091
15170
 
15092
15171
  if (!currentComponent.__hooks.accessibility.exitFunction) {
15093
15172
  var exitFunction = function (resetFocus) {
@@ -15095,7 +15174,7 @@ function useKeyboard() {
15095
15174
 
15096
15175
  if (acc.enabled && acc.active) {
15097
15176
  blur(this);
15098
- blurCallback && blurCallback(resetFocus);
15177
+ focusHandler && focusHandler.blurCallback && focusHandler.blurCallback(resetFocus);
15099
15178
  }
15100
15179
  }.bind(currentComponent);
15101
15180
 
@@ -15105,22 +15184,34 @@ function useKeyboard() {
15105
15184
  var acc = this.__hooks.accessibility;
15106
15185
 
15107
15186
  if (acc.enabled && !acc.active) {
15108
- blurCallback && blurCallback(false);
15187
+ focusHandler && focusHandler.blurCallback && focusHandler.blurCallback(false);
15109
15188
  focus(this);
15110
15189
  }
15111
15190
  }.bind(currentComponent);
15112
15191
 
15113
15192
  currentComponent.__hooks.accessibility.focusFunction = focusFunction;
15193
+
15194
+ var focusSelectionFunction = function (focusLast) {
15195
+ var acc = this.__hooks.accessibility;
15196
+
15197
+ if (acc.enabled) {
15198
+ focusHandler && focusHandler.focusToolbarButton && focusHandler.focusToolbarButton(focusLast);
15199
+ }
15200
+ }.bind(currentComponent);
15201
+
15202
+ currentComponent.__hooks.accessibility.focusSelectionFunction = focusSelectionFunction;
15114
15203
  }
15115
15204
 
15116
15205
  var focusFunc = currentComponent.__hooks.accessibility.focusFunction;
15117
15206
  var exitFunc = currentComponent.__hooks.accessibility.exitFunction;
15207
+ var focusSelectionFunc = currentComponent.__hooks.accessibility.focusSelectionFunction;
15118
15208
 
15119
15209
  var _useState9 = useState({
15120
15210
  active: false,
15121
15211
  enabled: keyboardNavigation,
15122
15212
  blur: exitFunc,
15123
- focus: focusFunc
15213
+ focus: focusFunc,
15214
+ focusSelection: focusSelectionFunc
15124
15215
  }),
15125
15216
  _useState10 = _slicedToArray(_useState9, 2),
15126
15217
  acc = _useState10[0],
@@ -15133,7 +15224,8 @@ function useKeyboard() {
15133
15224
  active: false,
15134
15225
  enabled: keyboardNavigation,
15135
15226
  blur: exitFunc,
15136
- focus: focusFunc
15227
+ focus: focusFunc,
15228
+ focusSelection: focusSelectionFunc
15137
15229
  });
15138
15230
  }, [keyboardNavigation]);
15139
15231
  return acc;
@@ -15152,7 +15244,8 @@ function focus(component) {
15152
15244
  active: true,
15153
15245
  enabled: acc.enabled,
15154
15246
  blur: acc.exitFunction,
15155
- focus: acc.focusFunction
15247
+ focus: acc.focusFunction,
15248
+ focusSelection: acc.focusSelectionFunction
15156
15249
  });
15157
15250
  }
15158
15251
  }
@@ -15170,7 +15263,8 @@ function blur(component) {
15170
15263
  active: false,
15171
15264
  enabled: acc.enabled,
15172
15265
  blur: acc.exitFunction,
15173
- focus: acc.focusFunction
15266
+ focus: acc.focusFunction,
15267
+ focusSelection: acc.focusSelectionFunction
15174
15268
  });
15175
15269
  }
15176
15270
  }
@@ -15246,7 +15340,7 @@ function createWithHooks(generator, opts, galaxy) {
15246
15340
  layout: {},
15247
15341
  appLayout: {},
15248
15342
  keyboardNavigation: opts.keyboardNavigation,
15249
- blurCallback: opts.blurCallback,
15343
+ focusHandler: opts.focusHandler,
15250
15344
  constraints: forcedConstraints,
15251
15345
  options: {},
15252
15346
  plugins: []
@@ -15281,9 +15375,9 @@ function createWithHooks(generator, opts, galaxy) {
15281
15375
  changed = true;
15282
15376
  }
15283
15377
 
15284
- if (r.context && r.context.blurCallback) {
15378
+ if (r.context && r.context.focusHandler) {
15285
15379
  // Needs to be added here due to how the client renders
15286
- this.context.blurCallback = r.context.blurCallback;
15380
+ this.context.focusHandler = r.context.focusHandler;
15287
15381
  }
15288
15382
 
15289
15383
  if (r.options) {