@hi-ui/menu 4.0.0-beta.7 → 4.0.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.
@@ -2,7 +2,7 @@
2
2
  * @hi-ui/menu
3
3
  * https://github.com/XiaoMi/hiui/tree/master/packages/ui/menu#readme
4
4
  *
5
- * Copyright (c) HIUI <mi-hiui@xiaomi.com>.
5
+ * Copyright (c) HiUI <mi-hiui@xiaomi.com>.
6
6
  *
7
7
  * This source code is licensed under the MIT license found in the
8
8
  * LICENSE file in the root directory of this source tree.
@@ -36,7 +36,7 @@ var Expander = function Expander(_ref) {
36
36
  height = _useState[0],
37
37
  setHeight = _useState[1];
38
38
 
39
- return /*#__PURE__*/React__default['default'].createElement(reactTransitionGroup.CSSTransition, {
39
+ return /*#__PURE__*/React__default["default"].createElement(reactTransitionGroup.CSSTransition, {
40
40
  "in": visible,
41
41
  timeout: 200,
42
42
  classNames: className,
@@ -56,7 +56,7 @@ var Expander = function Expander(_ref) {
56
56
  setHeight(0);
57
57
  });
58
58
  }
59
- }, /*#__PURE__*/React__default['default'].createElement("div", {
59
+ }, /*#__PURE__*/React__default["default"].createElement("div", {
60
60
  style: {
61
61
  height: height,
62
62
  overflow: 'hidden',
@@ -66,4 +66,3 @@ var Expander = function Expander(_ref) {
66
66
  };
67
67
 
68
68
  exports.Expander = Expander;
69
- //# sourceMappingURL=Expander.js.map
package/lib/cjs/Menu.js CHANGED
@@ -2,7 +2,7 @@
2
2
  * @hi-ui/menu
3
3
  * https://github.com/XiaoMi/hiui/tree/master/packages/ui/menu#readme
4
4
  *
5
- * Copyright (c) HIUI <mi-hiui@xiaomi.com>.
5
+ * Copyright (c) HiUI <mi-hiui@xiaomi.com>.
6
6
  *
7
7
  * This source code is licensed under the MIT license found in the
8
8
  * LICENSE file in the root directory of this source tree.
@@ -35,6 +35,18 @@ var useUncontrolledState = require('@hi-ui/use-uncontrolled-state');
35
35
 
36
36
  var Tooltip = require('@hi-ui/tooltip');
37
37
 
38
+ var useToggle = require('@hi-ui/use-toggle');
39
+
40
+ var treeUtils = require('@hi-ui/tree-utils');
41
+
42
+ var typeAssertion = require('@hi-ui/type-assertion');
43
+
44
+ var useResizeObserver = require('@hi-ui/use-resize-observer');
45
+
46
+ var useMergeRefs = require('@hi-ui/use-merge-refs');
47
+
48
+ var useId = require('@hi-ui/use-id');
49
+
38
50
  function _interopDefaultLegacy(e) {
39
51
  return e && _typeof(e) === 'object' && 'default' in e ? e : {
40
52
  'default': e
@@ -46,86 +58,196 @@ var React__default = /*#__PURE__*/_interopDefaultLegacy(React);
46
58
  var Tooltip__default = /*#__PURE__*/_interopDefaultLegacy(Tooltip);
47
59
 
48
60
  var MENU_PREFIX = classname.getPrefixCls('menu');
61
+ var DEFAULT_EXPANDED_IDS = [];
62
+ var NOOP_ARRAY = [];
63
+ var MIN_WIDTH = 56;
64
+ var MENU_MORE_ID = "MENU_MORE_" + useId.uuid();
49
65
  /**
50
66
  * TODO: What is Menu
51
67
  */
52
68
 
53
69
  var Menu = /*#__PURE__*/React.forwardRef(function (_a, ref) {
54
- var _cx;
55
-
56
70
  var _a$prefixCls = _a.prefixCls,
57
71
  prefixCls = _a$prefixCls === void 0 ? MENU_PREFIX : _a$prefixCls,
58
72
  _a$role = _a.role,
59
73
  role = _a$role === void 0 ? 'menu' : _a$role,
60
74
  className = _a.className,
61
- data = _a.data,
75
+ _a$data = _a.data,
76
+ data = _a$data === void 0 ? NOOP_ARRAY : _a$data,
62
77
  _a$placement = _a.placement,
63
78
  placement = _a$placement === void 0 ? 'vertical' : _a$placement,
64
- showCollapse = _a.showCollapse,
79
+ _a$showCollapse = _a.showCollapse,
80
+ showCollapse = _a$showCollapse === void 0 ? false : _a$showCollapse,
65
81
  _a$expandedType = _a.expandedType,
66
82
  expandedType = _a$expandedType === void 0 ? 'collapse' : _a$expandedType,
67
83
  _a$showAllSubMenus = _a.showAllSubMenus,
68
84
  showAllSubMenus = _a$showAllSubMenus === void 0 ? false : _a$showAllSubMenus,
69
- defaultExpandedIds = _a.defaultExpandedIds,
70
- defaultActiveId = _a.defaultActiveId,
71
- activeId = _a.activeId,
85
+ _a$defaultExpandAll = _a.defaultExpandAll,
86
+ defaultExpandAll = _a$defaultExpandAll === void 0 ? false : _a$defaultExpandAll,
87
+ _a$defaultExpandedIds = _a.defaultExpandedIds,
88
+ defaultExpandedIds = _a$defaultExpandedIds === void 0 ? DEFAULT_EXPANDED_IDS : _a$defaultExpandedIds,
89
+ expandedIdsProp = _a.expandedIds,
90
+ onExpand = _a.onExpand,
91
+ _a$defaultActiveId = _a.defaultActiveId,
92
+ defaultActiveId = _a$defaultActiveId === void 0 ? '' : _a$defaultActiveId,
93
+ activeIdProp = _a.activeId,
72
94
  onClickSubMenu = _a.onClickSubMenu,
95
+ collapsed = _a.collapsed,
96
+ _a$defaultCollapsed = _a.defaultCollapsed,
97
+ defaultCollapsed = _a$defaultCollapsed === void 0 ? false : _a$defaultCollapsed,
98
+ onCollapse = _a.onCollapse,
99
+ footerRender = _a.footerRender,
73
100
  onClick = _a.onClick,
74
- rest = tslib.__rest(_a, ["prefixCls", "role", "className", "data", "placement", "showCollapse", "expandedType", "showAllSubMenus", "defaultExpandedIds", "defaultActiveId", "activeId", "onClickSubMenu", "onClick"]);
101
+ rest = tslib.__rest(_a, ["prefixCls", "role", "className", "data", "placement", "showCollapse", "expandedType", "showAllSubMenus", "defaultExpandAll", "defaultExpandedIds", "expandedIds", "onExpand", "defaultActiveId", "activeId", "onClickSubMenu", "collapsed", "defaultCollapsed", "onCollapse", "footerRender", "onClick"]);
75
102
 
76
- var _useUncontrolledState = useUncontrolledState.useUncontrolledState(defaultActiveId || '', activeId, onClick),
77
- _activeId = _useUncontrolledState[0],
103
+ var _useUncontrolledState = useUncontrolledState.useUncontrolledState(defaultActiveId, activeIdProp, onClick),
104
+ activeId = _useUncontrolledState[0],
78
105
  updateActiveId = _useUncontrolledState[1];
79
106
 
80
- var _useState = React.useState(util.getAncestorIds(_activeId, data)),
107
+ var _useState = React.useState(function () {
108
+ return util.getAncestorIds(activeId, data);
109
+ }),
81
110
  activeParents = _useState[0],
82
111
  updateActiveParents = _useState[1];
83
112
 
84
113
  React.useEffect(function () {
85
- updateActiveParents(util.getAncestorIds(_activeId, data));
86
- }, [_activeId, data]);
114
+ updateActiveParents(util.getAncestorIds(activeId, data));
115
+ }, [activeId, data]);
87
116
 
88
- var _useState2 = React.useState(defaultExpandedIds || []),
89
- _expandedIds = _useState2[0],
90
- updateExpanedIds = _useState2[1];
117
+ var _useUncontrolledState2 = useUncontrolledState.useUncontrolledState(function () {
118
+ return defaultExpandAll ? treeUtils.getTreeNodesWithChildren(data).map(function (node) {
119
+ return node.id;
120
+ }) : defaultExpandedIds;
121
+ }, expandedIdsProp, onExpand),
122
+ expandedIds = _useUncontrolledState2[0],
123
+ updateExpandedIds = _useUncontrolledState2[1];
91
124
 
92
- var clickMenu = React.useCallback(function (id) {
93
- updateActiveId(id);
125
+ var clickMenu = React.useCallback(function (id, raw) {
126
+ updateActiveId(id, raw);
94
127
  }, [updateActiveId]);
95
128
  var clickSubMenu = React.useCallback(function (id) {
96
- var expandedIds = _expandedIds.includes(id) ? _expandedIds.filter(function (expandedId) {
129
+ var nextExpandedIds = expandedIds.includes(id) ? expandedIds.filter(function (expandedId) {
97
130
  return expandedId !== id;
98
- }) : _expandedIds.concat(id);
99
- updateExpanedIds(expandedIds);
131
+ }) : expandedIds.concat(id);
132
+ updateExpandedIds(nextExpandedIds);
100
133
 
101
134
  if (onClickSubMenu) {
102
- onClickSubMenu(id, expandedIds);
135
+ onClickSubMenu(id, nextExpandedIds);
103
136
  }
104
- }, [onClickSubMenu, _expandedIds]);
137
+ }, [onClickSubMenu, expandedIds, updateExpandedIds]);
105
138
  var closePopper = React.useCallback(function (id) {
106
- updateExpanedIds(_expandedIds.filter(function (expandedId) {
139
+ updateExpandedIds(expandedIds.filter(function (expandedId) {
107
140
  return expandedId !== id;
108
141
  }));
109
- }, [_expandedIds]);
142
+ }, [expandedIds, updateExpandedIds]);
110
143
  var closeAllPopper = React.useCallback(function () {
111
- updateExpanedIds([]);
112
- }, []);
113
-
114
- var _useState3 = React.useState(false),
115
- mini = _useState3[0],
116
- setMini = _useState3[1];
117
-
118
- var cls = classname.cx(prefixCls, className, prefixCls + "--" + placement, (_cx = {}, _cx[prefixCls + "--mini"] = mini, _cx[prefixCls + "--popup"] = expandedType === 'pop' || showAllSubMenus || mini, _cx));
119
- var onToggle = React.useCallback(function () {
120
- setMini(!mini);
121
- closeAllPopper();
122
- }, [mini, closeAllPopper]);
123
- var canToggle = placement === 'vertical' && showCollapse;
124
- return /*#__PURE__*/React__default['default'].createElement("div", Object.assign({
125
- ref: ref,
144
+ updateExpandedIds([]);
145
+ }, [updateExpandedIds]);
146
+
147
+ var _useUncontrolledToggl = useToggle.useUncontrolledToggle({
148
+ defaultVisible: defaultCollapsed,
149
+ visible: collapsed,
150
+ onToggle: onCollapse
151
+ }),
152
+ mini = _useUncontrolledToggl[0],
153
+ miniToggleAction = _useUncontrolledToggl[1];
154
+
155
+ var showVertical = placement === 'vertical';
156
+ var canToggle = showVertical && showCollapse;
157
+ var showMini = showVertical && mini;
158
+
159
+ var _useState2 = React.useState(null),
160
+ containerElement = _useState2[0],
161
+ setContainerElement = _useState2[1];
162
+
163
+ var _useState3 = React.useState(),
164
+ _useState3$ = _useState3[0],
165
+ containerWidth = _useState3$ === void 0 ? 0 : _useState3$,
166
+ setContainerWidth = _useState3[1];
167
+
168
+ useResizeObserver.useResizeObserver({
169
+ element: containerElement,
170
+ disabled: showVertical,
171
+ getSize: function getSize(element) {
172
+ var itemRect = element.getBoundingClientRect();
173
+ return itemRect.width;
174
+ },
175
+ onResize: function onResize(el, width) {
176
+ setContainerWidth(width);
177
+ }
178
+ });
179
+
180
+ var _useState4 = React.useState(0),
181
+ tagMaxCount = _useState4[0],
182
+ setTagMaxCount = _useState4[1];
183
+
184
+ var mergedTagList = React.useMemo(function () {
185
+ if (showVertical) return data;
186
+ if (containerWidth < MIN_WIDTH) return data;
187
+ return data.slice(0, Math.min(data.length, containerWidth / MIN_WIDTH));
188
+ }, [showVertical, data, containerWidth]);
189
+ var restTagList = React.useMemo(function () {
190
+ if (tagMaxCount > 0) return data.slice(tagMaxCount);
191
+ return [];
192
+ }, [data, tagMaxCount]);
193
+ var getTagWidth = React.useCallback(function (index) {
194
+ if (!containerElement) return MIN_WIDTH;
195
+ var elements = containerElement.getElementsByClassName('hi-v4-menu-item');
196
+ var element = elements && elements[index];
197
+ if (!element) return MIN_WIDTH;
198
+ return element.getBoundingClientRect().width;
199
+ }, [containerElement]);
200
+ React.useLayoutEffect(function () {
201
+ if (showVertical) return;
202
+ var tagMaxCount = 0;
203
+
204
+ if (typeAssertion.isArrayNonEmpty(mergedTagList)) {
205
+ var len = mergedTagList.length;
206
+ var lastIndex = len - 1;
207
+ var totalWidth = 72; // 更多
208
+
209
+ for (var i = 0; i < len; ++i) {
210
+ var currentTagWidth = getTagWidth(i);
211
+
212
+ if (currentTagWidth === undefined) {
213
+ break;
214
+ }
215
+
216
+ totalWidth += currentTagWidth;
217
+
218
+ if (lastIndex === 0 && totalWidth <= containerWidth || i === lastIndex - 1 && totalWidth + getTagWidth(lastIndex) <= containerWidth) {
219
+ tagMaxCount = lastIndex;
220
+ break;
221
+ } else if (totalWidth > containerWidth) {
222
+ tagMaxCount = i - 1;
223
+ break;
224
+ }
225
+ }
226
+ } else {
227
+ tagMaxCount = 0;
228
+ } // 保底要展示 1 个
229
+
230
+
231
+ setTagMaxCount(typeAssertion.isArrayNonEmpty(mergedTagList) && tagMaxCount < 1 ? 1 : tagMaxCount + 1);
232
+ }, [showVertical, getTagWidth, containerWidth, mergedTagList]);
233
+
234
+ var renderFooter = function renderFooter() {
235
+ var collapseNode = canToggle ? /*#__PURE__*/React__default["default"].createElement("div", {
236
+ className: classname.cx(prefixCls + "__toggle"),
237
+ onClick: miniToggleAction.not
238
+ }, mini ? /*#__PURE__*/React__default["default"].createElement(icons.MenuUnfoldOutlined, null) : /*#__PURE__*/React__default["default"].createElement(icons.MenuFoldOutlined, null)) : null;
239
+ return /*#__PURE__*/React__default["default"].createElement(React__default["default"].Fragment, null, typeAssertion.isFunction(footerRender) ? footerRender({
240
+ collapsed: showMini,
241
+ collapseNode: collapseNode
242
+ }) : collapseNode);
243
+ };
244
+
245
+ var cls = classname.cx(prefixCls, className, prefixCls + "--" + placement, mini && prefixCls + "--mini", (expandedType === 'pop' || showAllSubMenus || mini) && prefixCls + "--popup");
246
+ return /*#__PURE__*/React__default["default"].createElement("div", Object.assign({
247
+ ref: useMergeRefs.useMergeRefs(ref, setContainerElement),
126
248
  role: role,
127
249
  className: cls
128
- }, rest), /*#__PURE__*/React__default['default'].createElement(context['default'].Provider, {
250
+ }, rest), /*#__PURE__*/React__default["default"].createElement(context["default"].Provider, {
129
251
  value: {
130
252
  placement: placement,
131
253
  expandedType: expandedType,
@@ -136,31 +258,55 @@ var Menu = /*#__PURE__*/React.forwardRef(function (_a, ref) {
136
258
  closePopper: closePopper,
137
259
  closeAllPopper: closeAllPopper,
138
260
  activeParents: activeParents,
139
- activeId: _activeId,
140
- expandedIds: _expandedIds
261
+ activeId: activeId,
262
+ expandedIds: expandedIds
141
263
  }
142
- }, /*#__PURE__*/React__default['default'].createElement("ul", {
264
+ }, /*#__PURE__*/React__default["default"].createElement("ul", {
143
265
  className: classname.cx(prefixCls + "__wrapper")
144
- }, data.map(function (item) {
145
- return canToggle && mini ? /*#__PURE__*/React__default['default'].createElement(Tooltip__default['default'], {
266
+ }, mergedTagList.map(function (item, index) {
267
+ return showMini ? /*#__PURE__*/React__default["default"].createElement(Tooltip__default["default"], {
146
268
  title: item.title,
147
269
  key: item.id,
148
270
  placement: "right"
149
- }, /*#__PURE__*/React__default['default'].createElement(MenuItem.MenuItem, Object.assign({}, item, {
150
- level: 1
151
- }))) : /*#__PURE__*/React__default['default'].createElement(MenuItem.MenuItem, Object.assign({}, item, {
271
+ }, /*#__PURE__*/React__default["default"].createElement(MenuItem.MenuItem, Object.assign({}, item, {
272
+ level: 1,
273
+ render: renderMenuItemMini,
274
+ raw: item
275
+ }))) : /*#__PURE__*/React__default["default"].createElement(MenuItem.MenuItem, Object.assign({
276
+ hidden: !showVertical && index >= tagMaxCount
277
+ }, item, {
152
278
  key: item.id,
153
- level: 1
279
+ level: 1,
280
+ raw: item
154
281
  }));
155
- })), canToggle ? /*#__PURE__*/React__default['default'].createElement("div", {
156
- className: classname.cx(prefixCls + "__toggle"),
157
- onClick: onToggle
158
- }, mini ? /*#__PURE__*/React__default['default'].createElement(icons.MenuUnfoldOutlined, null) : /*#__PURE__*/React__default['default'].createElement(icons.MenuFoldOutlined, null)) : null));
282
+ }), showVertical || restTagList.length === 0 ? null : /*#__PURE__*/React__default["default"].createElement(MenuItem.MenuItem, {
283
+ key: MENU_MORE_ID,
284
+ id: MENU_MORE_ID,
285
+ title: "\u66F4\u591A",
286
+ children: restTagList
287
+ })), /*#__PURE__*/React__default["default"].createElement("div", {
288
+ className: prefixCls + "__footer"
289
+ }, renderFooter())));
159
290
  });
160
291
 
161
292
  if (env.__DEV__) {
162
293
  Menu.displayName = 'Menu';
163
294
  }
295
+ /**
296
+ * Mini 模式下渲染 item
297
+ */
298
+
299
+
300
+ var renderMenuItemMini = function renderMenuItemMini(menu) {
301
+ if (typeof menu.icon !== 'undefined') {
302
+ return menu.icon;
303
+ }
304
+
305
+ if (typeof menu.title === 'string') {
306
+ return menu.title.substring(0, 1);
307
+ }
308
+
309
+ return menu.title;
310
+ };
164
311
 
165
312
  exports.Menu = Menu;
166
- //# sourceMappingURL=Menu.js.map