@atlaskit/navigation-system 11.3.0 → 11.3.2

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 (50) hide show
  1. package/CHANGELOG.md +14 -0
  2. package/dist/cjs/ui/page-layout/calculate-layout-area-states.js +76 -37
  3. package/dist/cjs/ui/page-layout/chat-panel.js +6 -3
  4. package/dist/cjs/ui/page-layout/layout-area-sizing-context.js +2 -2
  5. package/dist/cjs/ui/page-layout/layout-area-sizing-provider.js +243 -247
  6. package/dist/cjs/ui/page-layout/layout-area-sizing-runtime.js +468 -0
  7. package/dist/cjs/ui/page-layout/main/main.js +1 -1
  8. package/dist/cjs/ui/page-layout/panel-splitter/panel-splitter.js +239 -99
  9. package/dist/cjs/ui/page-layout/panel-splitter/provider.js +3 -1
  10. package/dist/cjs/ui/page-layout/root.compiled.css +14 -3
  11. package/dist/cjs/ui/page-layout/root.js +43 -17
  12. package/dist/cjs/ui/page-layout/side-nav/side-nav.js +14 -3
  13. package/dist/cjs/ui/page-layout/use-css-layout-area-states.js +117 -0
  14. package/dist/cjs/ui/page-layout/use-layout-area-sizing.js +3 -1
  15. package/dist/es2019/ui/page-layout/calculate-layout-area-states.js +51 -17
  16. package/dist/es2019/ui/page-layout/chat-panel.js +29 -5
  17. package/dist/es2019/ui/page-layout/layout-area-sizing-context.js +2 -2
  18. package/dist/es2019/ui/page-layout/layout-area-sizing-provider.js +171 -241
  19. package/dist/es2019/ui/page-layout/layout-area-sizing-runtime.js +419 -0
  20. package/dist/es2019/ui/page-layout/main/main.js +2 -2
  21. package/dist/es2019/ui/page-layout/panel-splitter/panel-splitter.js +60 -10
  22. package/dist/es2019/ui/page-layout/panel-splitter/provider.js +3 -1
  23. package/dist/es2019/ui/page-layout/root.compiled.css +14 -3
  24. package/dist/es2019/ui/page-layout/root.js +30 -3
  25. package/dist/es2019/ui/page-layout/side-nav/side-nav.js +23 -3
  26. package/dist/es2019/ui/page-layout/use-css-layout-area-states.js +73 -0
  27. package/dist/es2019/ui/page-layout/use-layout-area-sizing.js +3 -1
  28. package/dist/esm/ui/page-layout/calculate-layout-area-states.js +75 -37
  29. package/dist/esm/ui/page-layout/chat-panel.js +7 -4
  30. package/dist/esm/ui/page-layout/layout-area-sizing-context.js +2 -2
  31. package/dist/esm/ui/page-layout/layout-area-sizing-provider.js +243 -248
  32. package/dist/esm/ui/page-layout/layout-area-sizing-runtime.js +459 -0
  33. package/dist/esm/ui/page-layout/main/main.js +2 -2
  34. package/dist/esm/ui/page-layout/panel-splitter/panel-splitter.js +238 -98
  35. package/dist/esm/ui/page-layout/panel-splitter/provider.js +3 -1
  36. package/dist/esm/ui/page-layout/root.compiled.css +14 -3
  37. package/dist/esm/ui/page-layout/root.js +42 -16
  38. package/dist/esm/ui/page-layout/side-nav/side-nav.js +14 -3
  39. package/dist/esm/ui/page-layout/use-css-layout-area-states.js +110 -0
  40. package/dist/esm/ui/page-layout/use-layout-area-sizing.js +3 -1
  41. package/dist/types/ui/page-layout/calculate-layout-area-states.d.ts +7 -2
  42. package/dist/types/ui/page-layout/layout-area-sizing-context.d.ts +10 -3
  43. package/dist/types/ui/page-layout/layout-area-sizing-provider.d.ts +6 -0
  44. package/dist/types/ui/page-layout/layout-area-sizing-runtime.d.ts +8 -0
  45. package/dist/types/ui/page-layout/panel-splitter/panel-splitter-context.d.ts +4 -0
  46. package/dist/types/ui/page-layout/panel-splitter/provider.d.ts +1 -1
  47. package/dist/types/ui/page-layout/root.d.ts +2 -0
  48. package/dist/types/ui/page-layout/use-css-layout-area-states.d.ts +8 -0
  49. package/dist/types/ui/page-layout/use-layout-area-sizing.d.ts +2 -0
  50. package/package.json +12 -6
@@ -0,0 +1,110 @@
1
+ import _toConsumableArray from "@babel/runtime/helpers/toConsumableArray";
2
+ import _slicedToArray from "@babel/runtime/helpers/slicedToArray";
3
+ function _createForOfIteratorHelper(r, e) { var t = "undefined" != typeof Symbol && r[Symbol.iterator] || r["@@iterator"]; if (!t) { if (Array.isArray(r) || (t = _unsupportedIterableToArray(r)) || e && r && "number" == typeof r.length) { t && (r = t); var _n = 0, F = function F() {}; return { s: F, n: function n() { return _n >= r.length ? { done: !0 } : { done: !1, value: r[_n++] }; }, e: function e(r) { throw r; }, f: F }; } throw new TypeError("Invalid attempt to iterate non-iterable instance.\nIn order to be iterable, non-array objects must have a [Symbol.iterator]() method."); } var o, a = !0, u = !1; return { s: function s() { t = t.call(r); }, n: function n() { var r = t.next(); return a = r.done, r; }, e: function e(r) { u = !0, o = r; }, f: function f() { try { a || null == t.return || t.return(); } finally { if (u) throw o; } } }; }
4
+ function _unsupportedIterableToArray(r, a) { if (r) { if ("string" == typeof r) return _arrayLikeToArray(r, a); var t = {}.toString.call(r).slice(8, -1); return "Object" === t && r.constructor && (t = r.constructor.name), "Map" === t || "Set" === t ? Array.from(r) : "Arguments" === t || /^(?:Ui|I)nt(?:8|16|32)(?:Clamped)?Array$/.test(t) ? _arrayLikeToArray(r, a) : void 0; } }
5
+ function _arrayLikeToArray(r, a) { (null == a || a > r.length) && (a = r.length); for (var e = 0, n = Array(a); e < a; e++) n[e] = r[e]; return n; }
6
+ import { useEffect, useState } from 'react';
7
+ import { bindAll } from 'bind-event-listener';
8
+ /**
9
+ * Observe CSS's responsive modes without loading the drag allocator or publishing
10
+ * measured widths back into CSS. Observe the host and independent occupied tracks;
11
+ * managed panels, TopNav and Banner are deliberately not observed during dragging.
12
+ */
13
+ export function useCssLayoutAreaStates(layoutRef, revision, isEnabled) {
14
+ var _useState = useState({}),
15
+ _useState2 = _slicedToArray(_useState, 2),
16
+ modes = _useState2[0],
17
+ setModes = _useState2[1];
18
+ useEffect(function () {
19
+ var root = layoutRef === null || layoutRef === void 0 ? void 0 : layoutRef.current;
20
+ if (!root || !isEnabled) {
21
+ return;
22
+ }
23
+ var measure = function measure() {
24
+ var selectors = {
25
+ 'side-nav': ':scope > nav[data-layout-slot]',
26
+ panel: '[data-layout-with-panel-slot]',
27
+ 'chat-panel': ':scope > [data-layout-chat-panel]'
28
+ };
29
+ var next = {};
30
+ var _iterator = _createForOfIteratorHelper(['side-nav', 'panel', 'chat-panel']),
31
+ _step;
32
+ try {
33
+ for (_iterator.s(); !(_step = _iterator.n()).done;) {
34
+ var area = _step.value;
35
+ var element = root.querySelector(selectors[area]);
36
+ if (element) {
37
+ next[area] = getComputedStyle(element).gridArea.split('/')[0].trim() === area ? 'inline' : 'overlay';
38
+ }
39
+ }
40
+ } catch (err) {
41
+ _iterator.e(err);
42
+ } finally {
43
+ _iterator.f();
44
+ }
45
+ setModes(function (previous) {
46
+ return ['side-nav', 'panel', 'chat-panel'].every(function (area) {
47
+ return previous[area] === next[area];
48
+ }) ? previous : next;
49
+ });
50
+ };
51
+ var widths = new Map();
52
+ var observer = new ResizeObserver(function (entries) {
53
+ var changed = false;
54
+ var _iterator2 = _createForOfIteratorHelper(entries),
55
+ _step2;
56
+ try {
57
+ for (_iterator2.s(); !(_step2 = _iterator2.n()).done;) {
58
+ var entry = _step2.value;
59
+ if (widths.get(entry.target) !== entry.contentRect.width) {
60
+ widths.set(entry.target, entry.contentRect.width);
61
+ changed = true;
62
+ }
63
+ }
64
+ } catch (err) {
65
+ _iterator2.e(err);
66
+ } finally {
67
+ _iterator2.f();
68
+ }
69
+ if (changed) {
70
+ measure();
71
+ }
72
+ });
73
+ var observeSlots = function observeSlots() {
74
+ observer.disconnect();
75
+ widths.clear();
76
+ var occupied = Array.from(root.children).filter(function (element) {
77
+ return element.matches('[data-layout-slot]:not(nav):not(header):not([role="main"]):not([data-layout-chat-panel])') && ['aside', 'ribbon', 'panel'].includes(getComputedStyle(element).gridArea.split('/')[0].trim());
78
+ });
79
+ for (var _i = 0, _arr = [root].concat(_toConsumableArray(occupied)); _i < _arr.length; _i++) {
80
+ var element = _arr[_i];
81
+ widths.set(element, element.getBoundingClientRect().width);
82
+ observer.observe(element);
83
+ }
84
+ measure();
85
+ };
86
+ observeSlots();
87
+ var mutations = new MutationObserver(observeSlots);
88
+ mutations.observe(root, {
89
+ childList: true
90
+ });
91
+ var queries = [window.matchMedia('(min-width: 40rem)'), window.matchMedia('(min-width: 64rem)')];
92
+ var unbind = [bindAll(window, [{
93
+ type: 'resize',
94
+ listener: measure
95
+ }])].concat(_toConsumableArray(queries.map(function (query) {
96
+ return bindAll(query, [{
97
+ type: 'change',
98
+ listener: measure
99
+ }]);
100
+ })));
101
+ return function () {
102
+ observer.disconnect();
103
+ mutations.disconnect();
104
+ unbind.forEach(function (cleanup) {
105
+ return cleanup();
106
+ });
107
+ };
108
+ }, [isEnabled, layoutRef, revision]);
109
+ return modes;
110
+ }
@@ -62,6 +62,8 @@ export function useLayoutAreaSizing(_ref) {
62
62
  startResize: startResize,
63
63
  resize: resize,
64
64
  completeResize: completeResize,
65
- getResizeBounds: getResizeBounds
65
+ getResizeBounds: getResizeBounds,
66
+ isManaged: context !== null,
67
+ prepareResize: context === null || context === void 0 ? void 0 : context.prepareResize
66
68
  };
67
69
  }
@@ -1,5 +1,5 @@
1
- import type { LayoutArea, LayoutAreaAllocation, LayoutWidthBound, ResizeSession, StoredLayoutArea } from './layout-area-sizing-context';
2
- export declare function calculateLayoutAreaStates({ viewportWidth, layoutWidth, isChatPanelOverlay, isSideNavOverlay, occupiedWidth, mainMinWidth: mainMinWidthBound, areas, resizeSession, }: {
1
+ import type { LayoutArea, LayoutAreaAllocation, LayoutAreaMode, LayoutWidthBound, ResizeSession, StoredLayoutArea } from './layout-area-sizing-context';
2
+ export declare function calculateLayoutAreaStates({ viewportWidth, layoutWidth, isChatPanelOverlay, isSideNavOverlay, occupiedWidth, mainMinWidth: mainMinWidthBound, areas, resizeSession, initialModes, }: {
3
3
  viewportWidth: number;
4
4
  /**
5
5
  * Root's content width, excluding scrollbars, borders and padding.
@@ -17,4 +17,9 @@ export declare function calculateLayoutAreaStates({ viewportWidth, layoutWidth,
17
17
  mainMinWidth: LayoutWidthBound;
18
18
  areas: Partial<Record<LayoutArea, StoredLayoutArea>>;
19
19
  resizeSession?: ResizeSession | null;
20
+ /**
21
+ * The CSS-rendered modes during deferred activation. Bounds must describe the
22
+ * existing layout until the user actually resizes it.
23
+ */
24
+ initialModes?: Partial<Record<LayoutArea, LayoutAreaMode>>;
20
25
  }): Partial<Record<LayoutArea, LayoutAreaAllocation>>;
@@ -22,15 +22,21 @@ export type StoredLayoutArea = LayoutAreaConfig & {
22
22
  mode: LayoutAreaMode;
23
23
  width: number;
24
24
  };
25
- openedAt?: number;
26
25
  };
27
26
  /**
28
- * Effective sibling widths held fixed during and after a user resize, until the
29
- * layout dimensions or configuration change. This is not a resize history.
27
+ * One resize transaction. Keep its starting widths for controlled rejection,
28
+ * and its resulting widths for synchronous or delayed acknowledgement.
30
29
  */
31
30
  export type ResizeSession = {
32
31
  area: LayoutArea;
33
32
  baselineWidths: Partial<Record<LayoutArea, number>>;
33
+ /**
34
+ * Overlay resizing changes only its surface width, not the inline layout modes.
35
+ * Retain these modes until a layout/configuration change ends the transaction.
36
+ */
37
+ overlayModes?: Partial<Record<LayoutArea, LayoutAreaMode>>;
38
+ completedWidth?: number;
39
+ completedWidths?: Partial<Record<LayoutArea, number>>;
34
40
  };
35
41
  export type LayoutAreaState = {
36
42
  mode: LayoutAreaMode;
@@ -44,6 +50,7 @@ export type LayoutAreaAllocation = LayoutAreaState & {
44
50
  };
45
51
  };
46
52
  export type LayoutAreaSizingContextValue = {
53
+ prepareResize?: () => Promise<boolean>;
47
54
  getResizeBounds: (area: LayoutArea) => ResizeBounds | undefined;
48
55
  registerArea: (area: LayoutArea, config: LayoutAreaConfig) => void;
49
56
  unregisterArea: (area: LayoutArea) => void;
@@ -1,4 +1,10 @@
1
1
  import React, { type ReactNode } from 'react';
2
+ /**
3
+ * Stable, synchronous boundary for SSR content. The drag/cascade implementation
4
+ * is a sibling, not a replacement wrapper, so loading it cannot remount the app.
5
+ * CSS handles initial and responsive geometry; only splitter interaction requests
6
+ * the asynchronous chunk. The eager observer reads modes without changing widths.
7
+ */
2
8
  export declare function LayoutAreaSizingProvider({ children, layoutRef, }: {
3
9
  children: ReactNode;
4
10
  layoutRef?: React.RefObject<HTMLDivElement | null>;
@@ -0,0 +1,8 @@
1
+ import React, { type ReactNode } from 'react';
2
+ import { type LayoutArea, type LayoutAreaState, type LayoutAreaSizingContextValue } from './layout-area-sizing-context';
3
+ export declare function LayoutAreaSizingRuntime({ children, layoutRef, onReady, onUpdate, }: {
4
+ children?: ReactNode;
5
+ layoutRef?: React.RefObject<HTMLDivElement | null>;
6
+ onReady?: (actions: LayoutAreaSizingContextValue | null) => void;
7
+ onUpdate?: (states: Partial<Record<LayoutArea, LayoutAreaState>>) => void;
8
+ }): JSX.Element;
@@ -32,6 +32,10 @@ export type PanelSplitterContextType = {
32
32
  * Called with the unconstrained live pointer width while dragging.
33
33
  */
34
34
  onResizeInternal?: (newWidth: number) => void;
35
+ /**
36
+ * Loads the optional sizing engine before committing an interaction.
37
+ */
38
+ prepareResize?: () => Promise<boolean>;
35
39
  /**
36
40
  * The minimum and maximum bounds for resizing the panel.
37
41
  * The bounds can be provided as `px` or `vw` values.
@@ -25,4 +25,4 @@ export type PanelSplitterProviderProps = Omit<PanelSplitterContextType, 'portalR
25
25
  *
26
26
  * Should be used in the layout area components, e.g. SideNav, Aside etc, as opposed to products.
27
27
  */
28
- export declare const PanelSplitterProvider: ({ panelId, panelWidth, onCompleteResize, onResizeStartInternal, onResizeInternal, getResizeBounds, resizingCssVar, panelRef, resizingElementRef, portalRef: providedPortalRef, position, isEnabled, shortcut, children, }: PanelSplitterProviderProps) => React.JSX.Element;
28
+ export declare const PanelSplitterProvider: ({ panelId, panelWidth, onCompleteResize, onResizeStartInternal, onResizeInternal, prepareResize, getResizeBounds, resizingCssVar, panelRef, resizingElementRef, portalRef: providedPortalRef, position, isEnabled, shortcut, children, }: PanelSplitterProviderProps) => React.JSX.Element;
@@ -5,6 +5,8 @@
5
5
  import React from 'react';
6
6
  import type { StrictXCSSProp } from '@atlaskit/css';
7
7
  export declare const gridRootId = "unsafe-design-system-page-layout-root";
8
+ export declare const gridRootFitId: string;
9
+ export declare const gridRootChatFitId: string;
8
10
  /**
9
11
  * The root component of the navigation system. It wraps the underlying components with the necessary contexts allowing to use certain data and hooks
10
12
  * @param skipLinksLabel - The very first element of the layout is a skip links container that can be accessed by pressing Tab button and holds the links to the other sections of the layout thus improving accessibility. This parameter defines the header text for this container
@@ -0,0 +1,8 @@
1
+ import { type RefObject } from 'react';
2
+ import type { LayoutArea, LayoutAreaMode } from './layout-area-sizing-context';
3
+ /**
4
+ * Observe CSS's responsive modes without loading the drag allocator or publishing
5
+ * measured widths back into CSS. Observe the host and independent occupied tracks;
6
+ * managed panels, TopNav and Banner are deliberately not observed during dragging.
7
+ */
8
+ export declare function useCssLayoutAreaStates(layoutRef: RefObject<HTMLDivElement | null> | undefined, revision: number, isEnabled: boolean): Partial<Record<LayoutArea, LayoutAreaMode>>;
@@ -4,6 +4,8 @@ export declare function useLayoutAreaSizing({ area, config, }: {
4
4
  area: LayoutArea;
5
5
  config: LayoutAreaConfig;
6
6
  }): {
7
+ isManaged: boolean;
8
+ prepareResize: (() => Promise<boolean>) | undefined;
7
9
  state: LayoutAreaState | undefined;
8
10
  getResizeBounds: () => ResizeBounds | undefined;
9
11
  startResize: (mode: LayoutAreaMode) => void;
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@atlaskit/navigation-system",
3
- "version": "11.3.0",
3
+ "version": "11.3.2",
4
4
  "description": "The latest navigation system for Atlassian apps.",
5
5
  "repository": "https://bitbucket.org/atlassian/atlassian-frontend-mirror",
6
6
  "license": "Apache-2.0",
@@ -60,7 +60,7 @@
60
60
  "@atlaskit/analytics-next": "^12.6.0",
61
61
  "@atlaskit/app-provider": "^8.1.0",
62
62
  "@atlaskit/avatar": "^30.0.0",
63
- "@atlaskit/button": "^25.4.0",
63
+ "@atlaskit/button": "^25.5.0",
64
64
  "@atlaskit/css": "^1.1.0",
65
65
  "@atlaskit/ds-lib": "^8.0.0",
66
66
  "@atlaskit/icon": "^38.0.0",
@@ -69,7 +69,7 @@
69
69
  "@atlaskit/motion": "^9.4.0",
70
70
  "@atlaskit/platform-feature-flags": "^2.2.0",
71
71
  "@atlaskit/platform-feature-flags-react": "^1.2.0",
72
- "@atlaskit/popup": "^9.0.0",
72
+ "@atlaskit/popup": "^10.0.0",
73
73
  "@atlaskit/pragmatic-drag-and-drop": "^4.0.0",
74
74
  "@atlaskit/primitives": "^22.6.0",
75
75
  "@atlaskit/react-compiler-gating": "^0.2.0",
@@ -90,10 +90,12 @@
90
90
  "devDependencies": {
91
91
  "@af/accessibility-testing": "workspace:^",
92
92
  "@af/integration-testing": "workspace:^",
93
+ "@af/react-unit-testing": "workspace:^",
93
94
  "@af/visual-regression": "workspace:^",
94
95
  "@atlaskit/badge": "^22.0.0",
95
96
  "@atlaskit/banner": "^15.3.0",
96
97
  "@atlaskit/breadcrumbs": "^17.8.0",
98
+ "@atlaskit/docs": "^12.3.0",
97
99
  "@atlaskit/dropdown-menu": "^21.0.0",
98
100
  "@atlaskit/flag": "^19.0.0",
99
101
  "@atlaskit/form": "^18.2.0",
@@ -104,26 +106,30 @@
104
106
  "@atlaskit/link": "^5.1.0",
105
107
  "@atlaskit/lozenge": "^17.0.0",
106
108
  "@atlaskit/menu": "^11.0.0",
107
- "@atlaskit/modal-dialog": "^17.0.0",
109
+ "@atlaskit/modal-dialog": "^17.1.0",
108
110
  "@atlaskit/onboarding": "^15.4.0",
109
111
  "@atlaskit/page-header": "^13.3.0",
110
112
  "@atlaskit/page-layout": "^5.5.0",
111
113
  "@atlaskit/popper": "^9.4.0",
112
114
  "@atlaskit/pragmatic-drag-and-drop-auto-scroll": "^3.2.0",
115
+ "@atlaskit/pragmatic-drag-and-drop-flourish": "^3.2.0",
116
+ "@atlaskit/pragmatic-drag-and-drop-live-region": "^2.1.0",
117
+ "@atlaskit/radio": "^10.2.0",
113
118
  "@atlaskit/section-message": "^10.2.0",
114
119
  "@atlaskit/select": "^23.1.0",
115
120
  "@atlaskit/skeleton": "^4.4.0",
116
121
  "@atlaskit/spotlight": "^4.2.0",
117
122
  "@atlaskit/tabs": "^21.3.0",
118
123
  "@atlaskit/tag": "^17.0.0",
124
+ "@atlaskit/textarea": "^10.2.0",
119
125
  "@atlaskit/textfield": "^10.2.0",
120
- "@atlaskit/top-layer": "^6.2.0",
126
+ "@atlaskit/top-layer": "^6.3.0",
121
127
  "@atlassian/feature-flags-test-utils": "^1.3.0",
122
128
  "@atlassian/gemini": "^1.54.0",
123
129
  "@atlassian/panel-system": "^1.14.0",
124
130
  "@atlassian/react-async": "^0.23.0",
125
131
  "@atlassian/react-entrypoint": "^1.1.0",
126
- "@atlassian/search-dialog": "^10.21.0",
132
+ "@atlassian/search-dialog": "^10.22.0",
127
133
  "@atlassian/ssr-tests": "workspace:^",
128
134
  "@atlassian/test-utils": "^1.1.0",
129
135
  "@atlassian/testing-library": "^0.12.0",