Browse Source

Merge branch 'main' into fix/slider

代强 1 year ago
parent
commit
000672206a
61 changed files with 591 additions and 663 deletions
  1. 61 27
      content/basic/button/index-en-US.md
  2. 41 19
      content/basic/button/index.md
  3. 50 2
      content/navigation/tabs/index-en-US.md
  4. 70 23
      content/navigation/tabs/index.md
  5. 2 2
      content/other/locale/index-en-US.md
  6. 4 4
      content/show/overflowlist/index-en-US.md
  7. 4 4
      content/show/overflowlist/index.md
  8. 1 1
      lerna.json
  9. 3 3
      packages/semi-animation-react/package.json
  10. 1 1
      packages/semi-animation-styled/package.json
  11. 1 1
      packages/semi-animation/package.json
  12. 1 1
      packages/semi-eslint-plugin/package.json
  13. 68 5
      packages/semi-foundation/button/button.scss
  14. 15 6
      packages/semi-foundation/button/variables.scss
  15. 2 2
      packages/semi-foundation/package.json
  16. 34 0
      packages/semi-foundation/tabs/tabs.scss
  17. 5 0
      packages/semi-foundation/tabs/variables.scss
  18. 1 1
      packages/semi-icons-lab/package.json
  19. 1 1
      packages/semi-icons/package.json
  20. 1 1
      packages/semi-illustrations/package.json
  21. 2 2
      packages/semi-next/package.json
  22. 1 1
      packages/semi-rspack/package.json
  23. 1 1
      packages/semi-scss-compile/package.json
  24. 1 1
      packages/semi-theme-default/package.json
  25. 1 1
      packages/semi-theme-default/scss/_palette.scss
  26. 1 1
      packages/semi-theme-default/scss/global.scss
  27. 2 1
      packages/semi-ui/button/Button.tsx
  28. 1 1
      packages/semi-ui/datePicker/_story/v2/FeatInsetInputProps.tsx
  29. 3 0
      packages/semi-ui/locale/interface.ts
  30. 3 0
      packages/semi-ui/locale/source/ar.ts
  31. 3 0
      packages/semi-ui/locale/source/de.ts
  32. 3 0
      packages/semi-ui/locale/source/en_GB.ts
  33. 3 0
      packages/semi-ui/locale/source/en_US.ts
  34. 3 0
      packages/semi-ui/locale/source/es.ts
  35. 3 0
      packages/semi-ui/locale/source/fr.ts
  36. 3 0
      packages/semi-ui/locale/source/id_ID.ts
  37. 3 0
      packages/semi-ui/locale/source/it.ts
  38. 3 0
      packages/semi-ui/locale/source/ja_JP.ts
  39. 3 0
      packages/semi-ui/locale/source/ko_KR.ts
  40. 3 0
      packages/semi-ui/locale/source/ms_MY.ts
  41. 3 0
      packages/semi-ui/locale/source/nl_NL.ts
  42. 3 0
      packages/semi-ui/locale/source/pl_PL.ts
  43. 3 0
      packages/semi-ui/locale/source/pt_BR.ts
  44. 3 0
      packages/semi-ui/locale/source/ro.ts
  45. 3 0
      packages/semi-ui/locale/source/ru_RU.ts
  46. 3 0
      packages/semi-ui/locale/source/sv_SE.ts
  47. 3 0
      packages/semi-ui/locale/source/th_TH.ts
  48. 3 0
      packages/semi-ui/locale/source/tr_TR.ts
  49. 3 0
      packages/semi-ui/locale/source/vi_VN.ts
  50. 3 0
      packages/semi-ui/locale/source/zh_CN.ts
  51. 3 0
      packages/semi-ui/locale/source/zh_TW.ts
  52. 7 7
      packages/semi-ui/package.json
  53. 4 2
      packages/semi-ui/slider/index.tsx
  54. 6 0
      packages/semi-ui/table/_story/RTL/ColumnAlignWithSorter.tsx
  55. 6 0
      packages/semi-ui/table/_story/v2/FixedOnGroupedRowClassName/index.tsx
  56. 67 8
      packages/semi-ui/tabs/TabBar.tsx
  57. 1 1
      packages/semi-ui/tabs/TabItem.tsx
  58. 4 1
      packages/semi-ui/tabs/index.tsx
  59. 6 3
      packages/semi-ui/tabs/interface.ts
  60. 1 1
      packages/semi-webpack/package.json
  61. 44 527
      yarn.lock

+ 61 - 27
content/basic/button/index-en-US.md

@@ -81,6 +81,7 @@ The themes currently available are:
 -   `light`: light background
 -   `solid`: dark background
 -   `borderless`: no background
+-   `outline`: border mode
 
 The default theme is `light`
 
@@ -183,6 +184,39 @@ function ButtonDemo() {
 }
 ```
 
+#### Border Mode
+
+```jsx live=true dir="column"
+import React from 'react';
+import { Button } from '@douyinfe/semi-ui';
+
+function ButtonDemo() {
+    const themes = [['outline', 'outline']];
+    const types = [['primary', 'primary'], ['secondary', 'secondary'], ['tertiary', 'tertiary'], ['warning', 'warning'], ['danger', 'danger']];
+
+    return (
+        <div>{
+            themes.map((theme, idxTheme) => (
+                <div key={idxTheme}>
+                    <ul style={{ listStyle: 'none', display: 'flex', margin: 0, padding: 0 }}>
+                        {types.map((type, idxType) => (
+                            <li key={'' + idxTheme + idxType} style={{ margin: 10 }}>
+                                <Button
+                                    theme={theme[0]}
+                                    type={type[0]}
+                                >
+                                    {theme[1]} {type[1]}
+                                </Button>
+                            </li>)
+                        )}
+                    </ul>
+                </div>))
+        }
+        </div>
+    );
+}
+```
+
 ### Size
 
 Three sizes are defined by default:
@@ -488,37 +522,37 @@ function SplitButtonDemo(){
 
 ### Button
 
-| Properties          | Instructions                                                                                                                                      | Type                             | Default   |
-| ------------------- | ------------------------------------------------------------------------------------------------------------------------------------------------- | -------------------------------- | --------- |
-| aria-label          | Label of the button                                                                                       | string                            | -    |
-| block               | Set the button to the block level button                                                                                                          | boolean                          | false     |
-| className           | Class name                                                                                                                                        | string                           |           |
-| disabled            | Prohibited status                                                                                                                                 | boolean                          | false     |
-| htmlType           | Set the `button` native `type` value, optional values: `"button"`, `"reset"`, `"submit"`                                                          | string                           | "button"  |
-| icon                | Icon                                                                                                                                              | ReactNode              |           |
-| iconPosition        | Icon location, optional value: `"left"`\|`"right"`                                                                                                | string                           | `"left"`  |
-| loading             | Loading state                                                                                                                                     | boolean                          | false     |
+| Properties          | Instructions                                                                                                                                                                              | Type                             | Default   |
+| ------------------- |-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------| -------------------------------- | --------- |
+| aria-label          | Label of the button                                                                                                                                                                       | string                            | -    |
+| block               | Set the button to the block level button                                                                                                                                                  | boolean                          | false     |
+| className           | Class name                                                                                                                                                                                | string                           |           |
+| disabled            | Prohibited status                                                                                                                                                                         | boolean                          | false     |
+| htmlType           | Set the `button` native `type` value, optional values: `"button"`, `"reset"`, `"submit"`                                                                                                  | string                           | "button"  |
+| icon                | Icon                                                                                                                                                                                      | ReactNode              |           |
+| iconPosition        | Icon location, optional value: `"left"`\|`"right"`                                                                                                                                        | string                           | `"left"`  |
+| loading             | Loading state                                                                                                                                                                             | boolean                          | false     |
 | noHorizontalPadding | Set whether to remove the inner margin in the horizontal direction, only valid for iconButton, optional: `true` (equivalent to \["left", "right"\]), "left", "right", \["left", "right"\] | boolean\|string\| Array<string\> | false     |
-| size                | Button size, optional value: `"large"`,`"default"`,`"small"`                                                                                      | string                           | "default" |
-| style               | Custom style                                                                                                                                      | CSSProperties                           |           |
-| theme               | Button theme, optional value: `"solid"` (with background color), `"borderless"` (no background color), `"light"` (light background color)         | string                           | "light"   |
-| type                | Type, optional values: `"primary"`,`"secondary"`, `"tertiary"`, `"warning"`, `"danger"`                                                               | string                           | "primary" |
-| onClick             | Click event                                                                                                                                       | Function(MouseEvent)                         |           |
-| onMouseDown             | Mouse down                                                                                                   | Function(MouseEvent)                        |           |
-| onMouseEnter             | Mouse Enter                                                                                                   | Function(MouseEvent)                        |           |
-| onMouseLeave             | Mouse Leave                                                                                                   | Function(MouseEvent)                        |           |
+| size                | Button size, optional value: `"large"`,`"default"`,`"small"`                                                                                                                              | string                           | "default" |
+| style               | Custom style                                                                                                                                                                              | CSSProperties                           |           |
+| theme               | Button theme, optional value: `"solid"` (with background color), `"borderless"` (no background color), `"light"` (light background color), `"outline"`(Border Mode)                    | string                           | "light"   |
+| type                | Type, optional values: `"primary"`,`"secondary"`, `"tertiary"`, `"warning"`, `"danger"`                                                                                                   | string                           | "primary" |
+| onClick             | Click event                                                                                                                                                                               | Function(MouseEvent)                         |           |
+| onMouseDown             | Mouse down                                                                                                                                                                                | Function(MouseEvent)                        |           |
+| onMouseEnter             | Mouse Enter                                                                                                                                                                               | Function(MouseEvent)                        |           |
+| onMouseLeave             | Mouse Leave                                                                                                                                                                               | Function(MouseEvent)                        |           |
 
 ### ButtonGroup
 
-| Properties | Instructions                | Type    | Default   | Version |
-| ---------- | ----------------------------| ------- | --------- |---------|
-| aria-label | Label of the button group   | string  | - | |
-| className  | Custom class name           | string   | - | |
-| disabled   | Disabled status             | boolean | false | |
-| size       | Button size, optional value: `"large"`,`"default"`,`"small"` | string  | "default" |
-| style      | Custom style                | CSSProperties   | - | 2.20.0 |
-| theme      | Button theme, optional values: `"solid"` (with background color), `"borderless"` (without background color), `"light"` (light background color) | string | "light"  | |
-| type       | Type, optional values: `"primary"`,`"secondary"`, `"tertiary"`, `"warning"`, `"danger"` | string  | "primary" |
+| Properties | Instructions                                                                                                                                     | Type    | Default   | Version |
+| ---------- |--------------------------------------------------------------------------------------------------------------------------------------------------| ------- | --------- |---------|
+| aria-label | Label of the button group                                                                                                                        | string  | - | |
+| className  | Custom class name                                                                                                                                | string   | - | |
+| disabled   | Disabled status                                                                                                                                  | boolean | false | |
+| size       | Button size, optional value: `"large"`,`"default"`,`"small"`                                                                                     | string  | "default" |
+| style      | Custom style                                                                                                                                     | CSSProperties   | - | 2.20.0 |
+| theme      | Button theme, optional values: `"solid"` (with background color), `"borderless"` (without background color), `"light"` (light background color),`"outline"`(Border Mode)   | string | "light"  | |
+| type       | Type, optional values: `"primary"`,`"secondary"`, `"tertiary"`, `"warning"`, `"danger"`                                                          | string  | "primary" |
 
 ### SplitButtonGroup **V1.12.0**
 | Properties   | Instructions                     | Type     | Default   |

+ 41 - 19
content/basic/button/index.md

@@ -80,6 +80,7 @@ function ButtonDemo() {
 -   `light`:浅色背景
 -   `solid`:深色背景
 -   `borderless`:无背景
+-   `outline`: 边框模式
 
 默认的主题为 `light`
 
@@ -143,6 +144,27 @@ function ButtonDemo() {
 
 ```
 
+
+#### 边框模式
+
+```jsx live=true dir="column"
+import React from 'react';
+import { Button } from '@douyinfe/semi-ui';
+
+function ButtonDemo() {
+    return (
+        <>
+            <Button theme='outline' type='primary' style={{ marginRight: 8 }}>主要</Button>
+            <Button theme='outline' type='secondary' style={{ marginRight: 8 }}>次要</Button>
+            <Button theme='outline' type='tertiary' style={{ marginRight: 8 }}>第三</Button>
+            <Button theme='outline' type='warning' style={{ marginRight: 8 }}>警告</Button>
+            <Button theme='outline' type='danger' style={{ marginRight: 8 }}>危险</Button>
+        </>
+    );
+}
+
+```
+
 ### 尺寸
 
 默认定义了三种尺寸:
@@ -448,25 +470,25 @@ function SplitButtonDemo(){
 
 ### Button
 
-| 属性                | 说明                                                                                                       | 类型                            | 默认值    |
-| ------------------- | ---------------------------------------------------------------------------------------------------------- | ------------------------------- | --------- |
-| aria-label          | 按钮的标签                                                                                       | string                            | -    |
-| block               | 将按钮设置为块级按钮                                                                                       | bool                            | false     |
-| className           | 类名                                                                                                       | string                          |           |
-| disabled            | 禁用状态                                                                                                   | boolean                         | false     |
-| htmlType           | 设置 `button` 原生的 `type` 值,可选值:`button`、`reset`、`submit`                                        | string                          | "button"  |
-| icon                | 图标                                                                                                       | ReactNode               |           |
-| iconPosition        | 图标位置,可选值:`left`\|`right`                                                                          | string                          | `left`    |
-| loading             | 加载状态                                                                                                   | boolean                         | false     |
+| 属性                | 说明                                                                                                          | 类型                            | 默认值    |
+| ------------------- |-------------------------------------------------------------------------------------------------------------| ------------------------------- | --------- |
+| aria-label          | 按钮的标签                                                                                                       | string                            | -    |
+| block               | 将按钮设置为块级按钮                                                                                                  | bool                            | false     |
+| className           | 类名                                                                                                          | string                          |           |
+| disabled            | 禁用状态                                                                                                        | boolean                         | false     |
+| htmlType           | 设置 `button` 原生的 `type` 值,可选值:`button`、`reset`、`submit`                                                      | string                          | "button"  |
+| icon                | 图标                                                                                                          | ReactNode               |           |
+| iconPosition        | 图标位置,可选值:`left`\|`right`                                                                                    | string                          | `left`    |
+| loading             | 加载状态                                                                                                        | boolean                         | false     |
 | noHorizontalPadding | 设置水平方向是否去掉内边距,只对设置了 icon 的 Button 有效。可选值:`true`(等效于 \["left", "right"\]),"left","right",\["left", "right"\] | boolean\|string\|Array<string\> | false     |
-| size                | 按钮大小,可选值:`large`、`default`、`small`                                                              | string                          | "default" |
-| style               | 自定义样式                                                                                                 | CSSProperties                          |           |
-| theme               | 按钮主题,可选值:`solid`(有背景色)、 `borderless`(无背景色)、 `light`(浅背景色)                     | string                          | "light"   |
-| type                | 类型,可选值:`primary`、`secondary`、`tertiary`、`warning`、 `danger`                                     | string                          | "primary" |
-| onClick             | 单击事件                                                                                                   | function(MouseEvent)                        |           |
-| onMouseDown             | 鼠标按下事件                                                                                                   | function(MouseEvent)                        |           |
-| onMouseEnter             | 鼠标移入事件                                                                                                   | function(MouseEvent)                        |           |
-| onMouseLeave             | 鼠标移出事件                                                                                                   | function(MouseEvent)                        |           |
+| size                | 按钮大小,可选值:`large`、`default`、`small`                                                                          | string                          | "default" |
+| style               | 自定义样式                                                                                                       | CSSProperties                          |           |
+| theme               | 按钮主题,可选值:`solid`(有背景色)、 `borderless`(无背景色)、 `light`(浅背景色)、`outline`(边框模式)                                | string                          | "light"   |
+| type                | 类型,可选值:`primary`、`secondary`、`tertiary`、`warning`、 `danger`                                                 | string                          | "primary" |
+| onClick             | 单击事件                                                                                                        | function(MouseEvent)                        |           |
+| onMouseDown             | 鼠标按下事件                                                                                                      | function(MouseEvent)                        |           |
+| onMouseEnter             | 鼠标移入事件                                                                                                      | function(MouseEvent)                        |           |
+| onMouseLeave             | 鼠标移出事件                                                                                                      | function(MouseEvent)                        |           |
 
 ### ButtonGroup
 
@@ -477,7 +499,7 @@ function SplitButtonDemo(){
 | disabled   | 禁用状态     | boolean | false | |
 | size       | 按钮大小,可选值:`large`、`default`、`small` | string  | "default" | |
 | style      | 自定义样式   | CSSProperties   | - | 2.20.0 |
-| theme      | 按钮主题,可选值:`solid`(有背景色)、 `borderless`(无背景色)、 `light`(浅背景色) | string | "light"   | |
+| theme      | 按钮主题,可选值:`solid`(有背景色)、 `borderless`(无背景色)、 `light`(浅背景色)、`outline`(边框模式)   | string | "light"   | |
 | type     | 类型,可选值:`primary`、`secondary`、`tertiary`、`warning`、 `danger` | string  | "primary" | |
 
 ### SplitButtonGroup **V1.12.0新增**

+ 50 - 2
content/navigation/tabs/index-en-US.md

@@ -220,6 +220,53 @@ class App extends React.Component {
 }
 ```
 
+
+### More with Dropdown 
+
+
+Supports merging redundant tabs into a `more` drop-down menu. Just pass in a number for `more`. The number represents the number of tabs included in the drop-down menu. 
+
+
+```jsx live=true dir=column
+import React from 'react';
+import { Tabs, TabPane } from '@douyinfe/semi-ui';
+
+function Demo(){
+  return (
+          <Tabs more={4} style={{ width: '60%', margin: '20px' }} type="card">
+            {[0, 1, 2, 3, 4, 5, 6, 7, 8, 9].map(i => (
+                    <TabPane tab={`Tab-${i}`} itemKey={`Tab-${i}`} key={i}>
+                      Content of card tab {i}
+                    </TabPane>
+            ))}
+          </Tabs>
+  );
+}
+```
+
+Advanced configuration is also supported, passing the object to `more`, and it can be passed in
+
+- `count`: Represents the number of Tabs in the income drop-down menu
+- `render`: Customize the rendering function of Trigger. The returned ReactNode will be rendered as the Trigger of the drop-down menu.
+- `dropdownProps`: Incoming DropDown Props will be transparently transmitted to the drop-down menu. If you need to customize the drop-down menu, use the render method in dropdownProps
+
+```jsx live=true dir=column
+import React from 'react';
+import { Tabs, TabPane } from '@douyinfe/semi-ui';
+
+function Demo(){
+  return (
+          <Tabs more={{ count: 4, render: ()=>{return <div style={{ display: 'inline-block' }}>Click to show More</div>;}, dropdownProps: { trigger: "click" } }} style={{ width: '60%', margin: '20px' }} type="card">
+            {[0, 1, 2, 3, 4, 5, 6, 7, 8, 9].map(i => (
+                    <TabPane tab={`Tab-${i}`} itemKey={`Tab-${i}`} key={i}>
+                      Content of card tab {i}
+                    </TabPane>
+            ))}
+          </Tabs>
+  );
+}
+```
+
 ### Vertical mode
 
 Support two positions: `tabPosition='left|top'`
@@ -505,7 +552,7 @@ import React from 'react';
 import { Tabs, TabPane } from '@douyinfe/semi-ui';
 
 class App extends React.Component {
-    constructor(props){
+    constructor(props) {
         super(props);
         this.state = {
             tabList: [
@@ -515,7 +562,7 @@ class App extends React.Component {
             ]
         };
     }
-    close(key){
+    close(key) {
         const newTabList = [...this.state.tabList];
         const closeIndex = newTabList.findIndex(t=>t.itemKey===key);
         newTabList.splice(closeIndex, 1);
@@ -546,6 +593,7 @@ contentStyle | The outer style object of the content area | CSSProperties | None
 defaultActiveKey | Initialize the key value of the selected tab page | string | '1' |
 keepDOM | Whether to render the DOM structure of the hidden panel when using TabPane writing, **>=1.0.0** | boolean | true |
 lazyRender | Lazy rendering, only when the panel is activated will it be rendered in the DOM tree, **>=1.0.0** | boolean | false |
+more | Render a portion of the Tab into a drop-down menu ** >= 2.59.0** | number \| {count:number,render:()=>ReactNode,dropdownProps:DropDownProps} | -       |    
 renderTabBar | Used for secondary packaging tab bar | (tabBarProps: object, defaultTabBar: React.ComponentType) => ReactNode | None |
 preventScroll | Indicates whether the browser should scroll the document to display the newly focused element, acting on the focus method inside the component, excluding the component passed in by the user | boolean |  |  |
 size | Size, providing three types of `large`, `medium`, and `small`, **>=1.11.0, currently only supports linear Tabs** | string | `large` |

+ 70 - 23
content/navigation/tabs/index.md

@@ -205,6 +205,52 @@ import { IconFile, IconGlobe, IconHelpCircle } from '@douyinfe/semi-icons';
 );
 ```
 
+### 更多选项收入 More 展示 
+
+
+支持将多余 Tab 合并为 ”更多“ 下拉菜单,`more` 传入数字即可,数字表示收入下拉菜单的 Tab 数量。
+
+```jsx live=true dir=column
+import React from 'react';
+import { Tabs, TabPane } from '@douyinfe/semi-ui';
+
+function Demo(){
+  return (
+          <Tabs more={4} style={{ width: '60%', margin: '20px' }} type="card">
+            {[0, 1, 2, 3, 4, 5, 6, 7, 8, 9].map(i => (
+                    <TabPane tab={`Tab-${i}`} itemKey={`Tab-${i}`} key={i}>
+                      Content of card tab {i}
+                    </TabPane>
+            ))}
+          </Tabs>
+  );
+}
+```
+
+也支持高级配置,向 `more` 传入对象,内可传入 
+
+- `count`: 表示收入下拉菜单的 Tab 数量
+- `render`: 自定义 Trigger 的渲染函数,返回的 ReactNode 会被渲染为下拉菜单的 Trigger
+- `dropdownProps`: 传入 DropDown Props,会被透传到下拉菜单,如果需要自定义下拉菜单,使用 dropdownProps 中的 render 方法
+
+```jsx live=true dir=column
+import React from 'react';
+import { Tabs, TabPane } from '@douyinfe/semi-ui';
+
+function Demo(){
+  return (
+          <Tabs more={{ count: 4, render: ()=>{return <div style={{ display: 'inline-block' }}>Click to show More</div>;}, dropdownProps: { trigger: "click" } }} style={{ width: '60%', margin: '20px' }} type="card">
+            {[0, 1, 2, 3, 4, 5, 6, 7, 8, 9].map(i => (
+                    <TabPane tab={`Tab-${i}`} itemKey={`Tab-${i}`} key={i}>
+                      Content of card tab {i}
+                    </TabPane>
+            ))}
+          </Tabs>
+  );
+}
+```
+
+
 ### 垂直的标签栏
 
 支持水平和垂直两种模式, `tabPosition='left|top'`
@@ -525,7 +571,7 @@ import React from 'react';
 import { Tabs, TabPane } from '@douyinfe/semi-ui';
 
 class App extends React.Component {
-    constructor(props){
+    constructor(props) {
         super(props);
         this.state = {
             tabList: [
@@ -535,7 +581,7 @@ class App extends React.Component {
             ]
         };
     }
-    close(key){
+    close(key) {
         const newTabList = [...this.state.tabList];
         const closeIndex = newTabList.findIndex(t=>t.itemKey===key);
         newTabList.splice(closeIndex, 1);
@@ -558,27 +604,28 @@ class App extends React.Component {
 
 ### Tab
 
-属性 | 说明 | 类型 | 默认值 |
---- | --- | --- | --- |
-activeKey | 当前激活的 tab 页的 itemKey 值 | string | 无 |
-className | 类名 | string | 无 |
-collapsible | 折叠的 Tabs,**>=1.1.0** | boolean | false |
-contentStyle | 内容区域外层样式对象 | CSSProperties | 无 |
-defaultActiveKey | 初始化选中的 tab 页的 key 值 | string | '1' |
-keepDOM | 使用 TabPane 写法时是否渲染隐藏面板的 DOM 结构,**>=1.0.0** | boolean | true |
-lazyRender | 懒渲染,仅当面板激活过才被渲染在 DOM 树中, **>=1.0.0** | boolean | false |
-renderTabBar | 用于二次封装标签栏 | (tabBarProps: object, defaultTabBar: React.ComponentType) => ReactNode | 无 |
-preventScroll | 指示浏览器是否应滚动文档以显示新聚焦的元素,作用于组件内的 focus 方法 | boolean |  |  |
-size | 大小,提供 `large`、`medium`、`small` 三种类型,**>=1.11.0,目前仅支持线性 Tabs** | string | `large` |
-style | 样式对象 | CSSProperties | 无 |
-tabBarExtraContent | 用于扩展标签栏的内容 | ReactNode | 无 |
-tabList | 标签页对象组成的数组,该对象支持 itemKey(对应 activeKey,tab(标签页文字)及 icon(标签页图标) | TabPane[] | 无 |
-tabPaneMotion | 是否使用动画切换 tabs | boolean | true |
-tabPosition | tab 的位置,支持`top`(水平), `left`(垂直),**>=1.0.0** | string | `top` |
-type | 标签栏的样式,可选`line`、 `card`、 `button` | string | `line` |
-onChange | 切换 tab 页时的回调函数 | function(activeKey: string) | 无 |
-onTabClick | 单击事件 | function(key: string, e: Event) | 无 |
-onTabClose | 关闭 tab 页时的回调函数 **>=2.1.0** |  function(tabKey: string) | 无
+属性 | 说明 | 类型                                                                        | 默认值     |
+--- | --- |---------------------------------------------------------------------------|---------|
+activeKey | 当前激活的 tab 页的 itemKey 值 | string                                                                    | 无       |
+className | 类名 | string                                                                    | 无       |
+collapsible | 折叠的 Tabs,**>=1.1.0** | boolean                                                                   | false   |
+contentStyle | 内容区域外层样式对象 | CSSProperties                                                             | 无       |
+defaultActiveKey | 初始化选中的 tab 页的 key 值 | string                                                                    | '1'     |
+keepDOM | 使用 TabPane 写法时是否渲染隐藏面板的 DOM 结构,**>=1.0.0** | boolean                                                                   | true    |
+lazyRender | 懒渲染,仅当面板激活过才被渲染在 DOM 树中, **>=1.0.0** | boolean                                                                   | false   |
+more | 将一部分 Tab 渲染到下拉菜单中 ** >= 2.59.0** | number \| {count:number,render:()=>ReactNode,dropdownProps:DropDownProps} | -       |                                                              
+renderTabBar | 用于二次封装标签栏 | (tabBarProps: object, defaultTabBar: React.ComponentType) => ReactNode    | 无       |
+preventScroll | 指示浏览器是否应滚动文档以显示新聚焦的元素,作用于组件内的 focus 方法 | boolean                                                                   |         |  |
+size | 大小,提供 `large`、`medium`、`small` 三种类型,**>=1.11.0,目前仅支持线性 Tabs** | string                                                                    | `large` |
+style | 样式对象 | CSSProperties                                                             | 无       |
+tabBarExtraContent | 用于扩展标签栏的内容 | ReactNode                                                                 | 无       |
+tabList | 标签页对象组成的数组,该对象支持 itemKey(对应 activeKey,tab(标签页文字)及 icon(标签页图标) | TabPane[]                                                                 | 无       |
+tabPaneMotion | 是否使用动画切换 tabs | boolean                                                                   | true    |
+tabPosition | tab 的位置,支持`top`(水平), `left`(垂直),**>=1.0.0** | string                                                                    | `top`   |
+type | 标签栏的样式,可选`line`、 `card`、 `button` | string                                                                    | `line`  |
+onChange | 切换 tab 页时的回调函数 | function(activeKey: string)                                               | 无       |
+onTabClick | 单击事件 | function(key: string, e: Event)                                           | 无       |
+onTabClose | 关闭 tab 页时的回调函数 **>=2.1.0** | function(tabKey: string)                                                  | 无       
 
 ### TabPane
 

+ 2 - 2
content/other/locale/index-en-US.md

@@ -303,7 +303,7 @@ class I18nDemo extends React.Component {
                         key: i,
                     };
                 });
-            })
+            });
             const srcList = useMemo(() => ([
                 "https://lf3-static.bytednsdoc.com/obj/eden-cn/ptlz_zlp/ljhwZthlaukjlkulzlp/root-web-sites/abstract.jpg",
                 "https://lf3-static.bytednsdoc.com/obj/eden-cn/ptlz_zlp/ljhwZthlaukjlkulzlp/root-web-sites/sky.jpg",
@@ -371,7 +371,7 @@ class I18nDemo extends React.Component {
                     <h5>Typography - Copyable</h5>
                     <Typography.Paragraph copyable>Click to copy text.</Typography.Paragraph>
                     <h5>Typography - Collapsible</h5>
-                    <Typography.Paragraph ellipsis={{ rows: 3, expandable: true, collapsible: true}} style={{ width: 300 }}>
+                    <Typography.Paragraph ellipsis={{ rows: 3, expandable: true, collapsible: true }} style={{ width: 300 }}>
                         {`Expandable and collapsible: Life's but a walking shadow, a poor player, that struts and frets his hour upon the stage, and then is heard no more; it is a tale told by an idiot, full of sound and fury, signifying nothing.`}
                     </Typography.Paragraph>
                     <h5>Transfer</h5>

+ 4 - 4
content/show/overflowlist/index-en-US.md

@@ -27,7 +27,7 @@ import { IconAlarm, IconBookmark, IconCamera, IconDuration, IconEdit, IconFolder
 () => {
     const [width, setWidth] = useState(100);
     const renderOverflow = items => {
-        return items.length ? <Tag style={{ flex: '0 0 auto' }}>+{items.length}</Tag> : null;
+        return items.length ? <Tag style={{ flex: '0 0 auto', fontVariantNumeric: 'tabular-nums' }}>+{items.length}</Tag> : null;
     };
     const renderItem = (item, ind) => {
         return (
@@ -72,7 +72,7 @@ import { IconAlarm, IconBookmark, IconCamera, IconDuration, IconEdit, IconFolder
 () => {
     const [width, setWidth] = useState(100);
     const renderOverflow = items => {
-        return items.length ? <Tag style={{ marginRight: 8, flex: '0 0 auto' }}>+{items.length}</Tag> : null;
+        return items.length ? <Tag style={{ marginRight: 8, flex: '0 0 auto', fontVariantNumeric: 'tabular-nums' }}>+{items.length}</Tag> : null;
     };
     const renderItem = (item, ind) => {
         return (
@@ -122,7 +122,7 @@ import { IconAlarm, IconBookmark, IconCamera, IconDuration, IconEdit, IconFolder
 () => {
     const [width, setWidth] = useState(100);
     const renderOverflow = items => {
-        return items.length ? <Tag style={{ flex: '0 0 auto' }}>+{items.length}</Tag> : null;
+        return items.length ? <Tag style={{ flex: '0 0 auto', fontVariantNumeric: 'tabular-nums' }}>+{items.length}</Tag> : null;
     };
     const renderItem = (item, ind) => {
         return (
@@ -173,7 +173,7 @@ import { IconAlarm, IconBookmark, IconCamera, IconDuration, IconEdit, IconFolder
 () => {
     const [width, setWidth] = useState(100);
     const renderOverflow = items => {
-        return items.map(item => <Tag style={{ marginRight: 8, marginLeft: 8, flex: '0 0 auto' }} key={item.key}>+{item.length}</Tag>);
+        return items.map(item => <Tag style={{ marginRight: 8, marginLeft: 8, flex: '0 0 auto', fontVariantNumeric: 'tabular-nums' }} key={item.key}>+{item.length}</Tag>);
     };
     const renderItem = (item, ind) => {
         return (

+ 4 - 4
content/show/overflowlist/index.md

@@ -27,7 +27,7 @@ import { IconAlarm, IconBookmark, IconCamera, IconDuration, IconEdit, IconFolder
 () => {
     const [width, setWidth] = useState(100);
     const renderOverflow = items => {
-        return items.length ? <Tag style={{ flex: '0 0 auto' }}>+{items.length}</Tag> : null;
+        return items.length ? <Tag style={{ flex: '0 0 auto', fontVariantNumeric: 'tabular-nums' }}>+{items.length}</Tag> : null;
     };
     const renderItem = (item, ind) => {
         return (
@@ -72,7 +72,7 @@ import { IconAlarm, IconBookmark, IconCamera, IconDuration, IconEdit, IconFolder
 () => {
     const [width, setWidth] = useState(100);
     const renderOverflow = items => {
-        return items.length ? <Tag style={{ marginRight: 8, flex: '0 0 auto' }}>+{items.length}</Tag> : null;
+        return items.length ? <Tag style={{ marginRight: 8, flex: '0 0 auto', fontVariantNumeric: 'tabular-nums' }}>+{items.length}</Tag> : null;
     };
     const renderItem = (item, ind) => {
         return (
@@ -122,7 +122,7 @@ import { IconAlarm, IconBookmark, IconCamera, IconDuration, IconEdit, IconFolder
 () => {
     const [width, setWidth] = useState(100);
     const renderOverflow = items => {
-        return items.length ? <Tag style={{ flex: '0 0 auto' }}>+{items.length}</Tag> : null;
+        return items.length ? <Tag style={{ flex: '0 0 auto', fontVariantNumeric: 'tabular-nums' }}>+{items.length}</Tag> : null;
     };
     const renderItem = (item, ind) => {
         return (
@@ -172,7 +172,7 @@ import { IconAlarm, IconBookmark, IconCamera, IconDuration, IconEdit, IconFolder
 () => {
     const [width, setWidth] = useState(100);
     const renderOverflow = items => {
-        return items.map(item => <Tag style={{ marginRight: 8, marginLeft: 8, flex: '0 0 auto' }} key={item.key}>+{item.length}</Tag>);
+        return items.map(item => <Tag style={{ marginRight: 8, marginLeft: 8, flex: '0 0 auto', fontVariantNumeric: 'tabular-nums' }} key={item.key}>+{item.length}</Tag>);
     };
     const renderItem = (item, ind) => {
         return (

+ 1 - 1
lerna.json

@@ -1,5 +1,5 @@
 {
     "useWorkspaces": true,
     "npmClient": "yarn",
-    "version": "2.57.0"
+    "version": "2.57.1-alpha.0"
 }

+ 3 - 3
packages/semi-animation-react/package.json

@@ -1,6 +1,6 @@
 {
     "name": "@douyinfe/semi-animation-react",
-    "version": "2.57.0",
+    "version": "2.57.1-alpha.0",
     "description": "motion library for semi-ui-react",
     "keywords": [
         "motion",
@@ -25,8 +25,8 @@
         "prepublishOnly": "npm run build:lib"
     },
     "dependencies": {
-        "@douyinfe/semi-animation": "2.57.0",
-        "@douyinfe/semi-animation-styled": "2.57.0",
+        "@douyinfe/semi-animation": "2.57.1-alpha.0",
+        "@douyinfe/semi-animation-styled": "2.57.1-alpha.0",
         "classnames": "^2.2.6"
     },
     "devDependencies": {

+ 1 - 1
packages/semi-animation-styled/package.json

@@ -1,6 +1,6 @@
 {
     "name": "@douyinfe/semi-animation-styled",
-    "version": "2.57.0",
+    "version": "2.57.1-alpha.0",
     "description": "semi styled animation",
     "keywords": [
         "semi",

+ 1 - 1
packages/semi-animation/package.json

@@ -1,6 +1,6 @@
 {
     "name": "@douyinfe/semi-animation",
-    "version": "2.57.0",
+    "version": "2.57.1-alpha.0",
     "description": "animation base library for semi-ui",
     "keywords": [
         "animation",

+ 1 - 1
packages/semi-eslint-plugin/package.json

@@ -1,6 +1,6 @@
 {
     "name": "eslint-plugin-semi-design",
-    "version": "2.57.0",
+    "version": "2.57.1-alpha.0",
     "description": "semi ui eslint plugin",
     "keywords": [
         "semi",

+ 68 - 5
packages/semi-foundation/button/button.scss

@@ -45,7 +45,10 @@ $module: #{$prefix}-button;
 
         &-disabled {
             background-color: $color-button_disabled_danger-bg-default;
-
+            &.#{$module}-outline {
+                background-color: transparent;
+                border: $width-button_outline-border solid $color-button_disabled_outline-border-default;
+            }
             &.#{$module}-light {
                 background-color: $color-button_disabled_light_danger-bg-default;
             }
@@ -59,7 +62,14 @@ $module: #{$prefix}-button;
             background-color: $color-button_danger-bg-active;
         }
 
+        &.#{$module}-outline{
+            background-color: transparent;
+            border: $width-button_outline-border solid $color-button_danger_outline-border-default;
+        }
+
+
         &.#{$module}-light,
+        &.#{$module}-outline,
         &.#{$module}-borderless {
             color: $color-button_danger_borderless-text-default;
         }
@@ -78,7 +88,10 @@ $module: #{$prefix}-button;
 
         &-disabled {
             background-color: $color-button_disabled_warning-bg-default;
-
+            &.#{$module}-outline {
+                background-color: transparent;
+                border: $width-button_outline-border solid $color-button_disabled_outline-border-default;
+            }
             &.#{$module}-light {
                 background-color: $color-button_disabled_light_warning-bg-default;
             }
@@ -92,7 +105,13 @@ $module: #{$prefix}-button;
             background-color: $color-button_warning-bg-active;
         }
 
+        &.#{$module}-outline{
+            background-color: transparent;
+            border: $width-button_outline-border solid $color-button_warning_outline-border-default;
+        }
+
         &.#{$module}-light,
+        &.#{$module}-outline,
         &.#{$module}-borderless {
             color: $color-button_warning_borderless-text-default;
         }
@@ -111,7 +130,10 @@ $module: #{$prefix}-button;
 
         &-disabled {
             background-color: $color-button_disabled_tertiary-bg-default;
-
+            &.#{$module}-outline {
+                background-color: transparent;
+                border: $width-button_outline-border solid $color-button_disabled_outline-border-default;
+            }
             &.#{$module}-light {
                 background-color: $color-button_disabled_light_tertiary-bg-default;
             }
@@ -125,7 +147,13 @@ $module: #{$prefix}-button;
             background-color: $color-button_tertiary-bg-active;
         }
 
+        &.#{$module}-outline{
+            background-color: transparent;
+            border: $width-button_outline-border solid $color-button_tertiary_outline-border-default;
+        }
+
         &.#{$module}-light,
+        &.#{$module}-outline,
         &.#{$module}-borderless {
             color: $color-button_tertiary_solid-text-default;
         }
@@ -144,17 +172,29 @@ $module: #{$prefix}-button;
             &.#{$module}-light {
                 background: $color-button_disabled_light_primary-bg-default;
             }
+
+            &.#{$module}-outline {
+                background-color: transparent;
+                border: $width-button_outline-border solid $color-button_disabled_outline-border-default;
+            }
         }
 
-        &:not(.#{$module}-borderless):not(.#{$module}-light):hover {
+        &:not(.#{$module}-borderless):not(.#{$module}-light):not(.#{$module}-outline):hover {
             background-color: $color-button_primary-bg-hover;
         }
 
-        &:not(.#{$module}-borderless):not(.#{$module}-light):active {
+        &.#{$module}-outline{
+            background-color: transparent;
+            border: $width-button_outline-border solid $color-button_primary_outline-border-default;
+        }
+
+
+        &:not(.#{$module}-borderless):not(.#{$module}-light):not(.#{$module}-outline):active {
             background-color: $color-button_primary-bg-active;
         }
 
         &.#{$module}-light,
+        &.#{$module}-outline,
         &.#{$module}-borderless {
             color: $color-button_primary_borderless-text-default;
         }
@@ -171,11 +211,21 @@ $module: #{$prefix}-button;
         &-disabled {
             background-color: $color-button_disabled_secondary-bg-default;
 
+            &.#{$module}-outline {
+                background-color: transparent;
+                border: $width-button_outline-border solid $color-button_disabled_outline-border-default;
+            }
+
             &.#{$module}-light {
                 background-color: $color-button_disabled_light_secondary-bg-default;
             }
         }
 
+        &.#{$module}-outline{
+            background-color: transparent;
+            border: $width-button_outline-border solid $color-button_secondary_outline-border-default;
+        }
+
         &:hover {
             background-color: $color-button_secondary-bg-hover;
         }
@@ -185,6 +235,7 @@ $module: #{$prefix}-button;
         }
 
         &.#{$module}-light,
+        &.#{$module}-outline,
         &.#{$module}-borderless {
             color: $color-button_secondary_borderless-text-default;
         }
@@ -222,6 +273,18 @@ $module: #{$prefix}-button;
         }
     }
 
+    &-outline {
+        background-color: transparent;
+
+        &:not(.#{$module}-disabled):hover {
+            background-color: $color-button_outline-bg-hover;
+        }
+
+        &:not(.#{$module}-disabled):active {
+            background-color: $color-button_outline-bg-active;
+        }
+    }
+
     &-light {
         background-color: $color-button_light-bg-default;
         border: $width-button_light-border $color-button_light-border-default solid;

+ 15 - 6
packages/semi-foundation/button/variables.scss

@@ -11,6 +11,7 @@ $color-button_primary-bg-active: var(--semi-color-primary-active); // 主要按
 $color-button_primary-border-active: var(--semi-color-primary-active); // 主要按钮描边颜色 - 按下
 $color-button_primary-text-active: rgba(var(--semi-white), 1); // 主要按钮文字颜色 - 按下
 $color-button_primary-outline-focus: var(--semi-color-primary-light-active); // 主要按钮轮廓 - 聚焦
+$color-button_primary_outline-border-default: var(--semi-color-border); // 边框模式下 primary 边框颜色
 
 $color-button_primary_borderless-text-default: var(--semi-color-primary); // 主要按钮无边框文字颜色
 
@@ -26,6 +27,7 @@ $color-button_secondary-text-hover: rgba(var(--semi-white), 1); // 次要按钮
 $color-button_secondary-bg-active: var(--semi-color-secondary-active); // 次要按钮背景颜色 - 按下
 $color-button_secondary-border-active: var(--semi-color-secondary-active); // 次要按钮描边颜色 - 按下
 $color-button_secondary-text-active: rgba(var(--semi-white), 1); // 次要按钮文字颜色 - 按下
+$color-button_secondary_outline-border-default: var(--semi-color-border); // 边框模式下 secondary 边框颜色
 
 $color-button_secondary_borderless-text-default: var(--semi-color-secondary); // 次要按钮无边框文字颜色
 
@@ -42,6 +44,7 @@ $color-button_danger-bg-active: var(--semi-color-danger-active); // 危险按钮
 $color-button_danger-border-active: var(--semi-color-danger-active); // 危险按钮描边颜色 - 按下
 $color-button_danger-text-active: rgba(var(--semi-white), 1); // 危险按钮文字颜色 - 按下
 $color-button_danger-outline-focus: var(--semi-color-danger-light-active); // 危险按钮轮廓 - 聚焦
+$color-button_danger_outline-border-default: var(--semi-color-danger); // 边框模式下 danger 边框颜色
 
 $color-button_danger_borderless-text-default: var(--semi-color-danger); // 危险按钮无边框文字颜色
 
@@ -58,7 +61,7 @@ $color-button_warning-bg-active: var(--semi-color-warning-active); // 警告按
 $color-button_warning-border-active: var(--semi-color-warning-active); // 警告按钮描边颜色 - 按下
 $color-button_warning-text-active: rgba(var(--semi-white), 1); // 警告按钮文字颜色 - 按下
 $color-button_warning-outline-focus: var(--semi-color-warning-light-active); // 警告按钮轮廓 - 聚焦
-
+$color-button_warning_outline-border-default: var(--semi-color-warning); // 边框模式下 warning 边框颜色
 $color-button_warning_borderless-text-default: var(--semi-color-warning); // 警告按钮无边框文字颜色
 
 // tertiary
@@ -73,7 +76,7 @@ $color-button_tertiary-text-hover: rgba(var(--semi-white), 1); // 第三按钮
 $color-button_tertiary-bg-active: var(--semi-color-tertiary-active); // 第三按钮背景颜色 - 按下
 $color-button_tertiary-border-active: var(--semi-color-tertiary-active); // 第三按钮描边颜色 - 按下
 $color-button_tertiary-text-active: rgba(var(--semi-white), 1); // 第三按钮文字颜色 - 按下
-
+$color-button_tertiary_outline-border-default: var(--semi-color-border); // 边框模式下 danger 边框颜色
 $color-button_tertiary_solid-text-default: var(--semi-color-text-1); // 浅色第三按钮文字颜色
 
 // disabled
@@ -87,7 +90,7 @@ $color-button_disabled_secondary-bg-default: $color-button_disabled-bg-default;
 $color-button_disabled_danger-bg-default: $color-button_disabled-bg-default; // 禁用 danger 按钮背景颜色
 $color-button_disabled_warning-bg-default: $color-button_disabled-bg-default; // 禁用 warning 按钮背景颜色
 $color-button_disabled_tertiary-bg-default: $color-button_disabled-bg-default; // 禁用 tertiary 按钮背景颜色
-
+$color-button_disabled_outline-border-default: var(--semi-color-border); // 边框模式下 disable 边框颜色
 
 
 // light
@@ -114,6 +117,12 @@ $color-button_borderless-border-hover: $color-button_borderless-border-default;
 $color-button_borderless-border-active: $color-button_borderless-border-hover; // 无背景按钮描边颜色 - 按下
 $width-button_borderless-border: 0; // 无背景按钮描边宽度
 
+
+// outline
+$width-button_outline-border: 1px; // 边框模式按钮边框宽度
+$color-button_outline-bg-hover: var(--semi-color-fill-0); // 边框模式按钮背景颜色 - 悬浮
+$color-button_outline-bg-active: var(--semi-color-fill-1); // 边框模式按钮背景颜色 - 按下
+
 // buttongroup
 
 $color-button_group-border-default: var(--semi-color-border); // 按钮组分割线颜色
@@ -163,6 +172,6 @@ $width-button-outline: 2px; // 按钮轮廓宽度
 
 
 $radius-button_splitButtonGroup_first_topLeft: var(--semi-border-radius-small); // split button 左上圆角
-$radius-button_splitButtonGroup_first_bottomLeft:var(--semi-border-radius-small); // split button 左下圆角
-$radius-button_splitButtonGroup_last_topRight:var(--semi-border-radius-small); // split button 右上圆角
-$radius-button_splitButtonGroup_last_bottomRight:var(--semi-border-radius-small); // split button 右下圆角
+$radius-button_splitButtonGroup_first_bottomLeft: var(--semi-border-radius-small); // split button 左下圆角
+$radius-button_splitButtonGroup_last_topRight: var(--semi-border-radius-small); // split button 右上圆角
+$radius-button_splitButtonGroup_last_bottomRight: var(--semi-border-radius-small); // split button 右下圆角

+ 2 - 2
packages/semi-foundation/package.json

@@ -1,13 +1,13 @@
 {
     "name": "@douyinfe/semi-foundation",
-    "version": "2.57.0",
+    "version": "2.57.1-alpha.0",
     "description": "",
     "scripts": {
         "build:lib": "node ./scripts/compileLib.js",
         "prepublishOnly": "npm run build:lib"
     },
     "dependencies": {
-        "@douyinfe/semi-animation": "2.57.0",
+        "@douyinfe/semi-animation": "2.57.1-alpha.0",
         "async-validator": "^3.5.0",
         "classnames": "^2.2.6",
         "date-fns": "^2.29.3",

+ 34 - 0
packages/semi-foundation/tabs/tabs.scss

@@ -11,6 +11,7 @@ $ignoreIcon: '.#{$prefix}-icon-checkbox_tick, .#{$prefix}-icon-radio, .#{$prefix
     box-sizing: border-box;
     position: relative;
 
+
     &-left {
         display: flex;
         flex-direction: row;
@@ -30,6 +31,39 @@ $ignoreIcon: '.#{$prefix}-icon-checkbox_tick, .#{$prefix}-icon-radio, .#{$prefix
             padding: $spacing-tabs_bar_extra-paddingY $spacing-tabs_bar_extra-paddingX;
         }
 
+        &-more-trigger{
+            display: inline-block;
+            cursor: pointer;
+            color: var(--semi-color-text-2);
+
+            &-content{
+                display: flex;
+                align-content: center;
+
+                &-icon:not(:not(&-icon)){ // increase priority
+                    margin-top: $spacing-tabs_tab-more_trigger_icon-marginTop;
+                    margin-bottom: $spacing-tabs_tab-more_trigger_icon-marginBottom;
+                    margin-left: $spacing-tabs_tab-more_trigger_icon-marginLeft;
+                    margin-right: $spacing-tabs_tab-more_trigger_icon-marginRight;
+                    flex-shrink: 0;
+                    display: flex;
+                    align-items: center;
+                }
+            }
+
+            &-line{
+                padding: $spacing-tabs_bar_line_tab-paddingTop $spacing-tabs_bar_line_tab-paddingRight $spacing-tabs_bar_line_tab-paddingBottom $spacing-tabs_bar_line_tab-paddingLeft;
+            }
+
+            &-card{
+                padding: $spacing-tabs_bar_card_tab-paddingY $spacing-tabs_bar_card_tab-paddingX;
+            }
+
+            &-button{
+                padding: $spacing-tabs_bar_button_tab-paddingY $spacing-tabs_bar_button_tab-paddingX;
+            }
+        }
+
         .#{$module}-tab {
             @include font-size-regular;
             cursor: pointer;

+ 5 - 0
packages/semi-foundation/tabs/variables.scss

@@ -85,6 +85,11 @@ $font-tabs_bar_extra_large-lineHeight: $height-tabs_bar_extra_large; // 大尺
 $height-tabs_bar_extra_small: 36px; // 小尺寸页签高度
 $font-tabs_bar_extra_small-lineHeight: $height-tabs_bar_extra_small; // 小尺寸页签文字行高
 
+$spacing-tabs_tab-more_trigger_icon-marginLeft: 8px;
+$spacing-tabs_tab-more_trigger_icon-marginRight: 8px;
+$spacing-tabs_tab-more_trigger_icon-marginTop: 0px;
+$spacing-tabs_tab-more_trigger_icon-marginBottom: 0px;
+
 $spacing-tabs_tab-pane_arrow: 8px; //滚动折叠箭头内边距
 $spacing-tabs_bar_extra-paddingY: 0px; // 附加操作垂直内边距
 $spacing-tabs_bar_extra-paddingX: 5px; // 附加操作水平内边距

+ 1 - 1
packages/semi-icons-lab/package.json

@@ -1,6 +1,6 @@
 {
   "name": "@douyinfe/semi-icons-lab",
-  "version": "2.57.0",
+  "version": "2.57.1-alpha.0",
   "description": "semi icons lab",
   "keywords": [
     "semi",

+ 1 - 1
packages/semi-icons/package.json

@@ -1,6 +1,6 @@
 {
     "name": "@douyinfe/semi-icons",
-    "version": "2.57.0",
+    "version": "2.57.1-alpha.0",
     "description": "semi icons",
     "keywords": [
         "semi",

+ 1 - 1
packages/semi-illustrations/package.json

@@ -1,6 +1,6 @@
 {
     "name": "@douyinfe/semi-illustrations",
-    "version": "2.57.0",
+    "version": "2.57.1-alpha.0",
     "description": "semi illustrations",
     "keywords": [
         "semi",

+ 2 - 2
packages/semi-next/package.json

@@ -1,6 +1,6 @@
 {
     "name": "@douyinfe/semi-next",
-    "version": "2.57.0",
+    "version": "2.57.1-alpha.0",
     "description": "Plugin that support Semi Design in Next.js",
     "author": "伍浩威 <[email protected]>",
     "homepage": "",
@@ -23,7 +23,7 @@
         "typescript": "^4"
     },
     "dependencies": {
-        "@douyinfe/semi-webpack-plugin": "2.57.0"
+        "@douyinfe/semi-webpack-plugin": "2.57.1-alpha.0"
     },
     "gitHead": "eb34a4f25f002bb4cbcfa51f3df93bed868c831a"
 }

+ 1 - 1
packages/semi-rspack/package.json

@@ -1,6 +1,6 @@
 {
     "name": "@douyinfe/semi-rspack-plugin",
-    "version": "2.57.0",
+    "version": "2.57.1-alpha.0",
     "description": "",
     "homepage": "",
     "license": "MIT",

+ 1 - 1
packages/semi-scss-compile/package.json

@@ -1,6 +1,6 @@
 {
     "name": "@douyinfe/semi-scss-compile",
-    "version": "2.57.0",
+    "version": "2.57.1-alpha.0",
     "description": "compile semi scss to css",
     "author": "[email protected]",
     "license": "MIT",

+ 1 - 1
packages/semi-theme-default/package.json

@@ -1,6 +1,6 @@
 {
     "name": "@douyinfe/semi-theme-default",
-    "version": "2.57.0",
+    "version": "2.57.1-alpha.0",
     "description": "semi-theme-default",
     "keywords": [
         "semi-theme",

+ 1 - 1
packages/semi-theme-default/scss/_palette.scss

@@ -163,7 +163,7 @@ body, body .semi-always-light, :host, :host .semi-always-light {
     --semi-yellow-9: 83,72,0;
 }
 
-body[theme-mode="dark"], body .semi-always-dark, :host-context(body[theme-mode="dark"]), :host .semi-always-dark {
+body[theme-mode="dark"], body .semi-always-dark, :host([theme-mode="dark"]), :host .semi-always-dark {
     --semi-red-0: 108,9,11;
     --semi-red-1: 144,17,16;
     --semi-red-2: 180,32,25;

+ 1 - 1
packages/semi-theme-default/scss/global.scss

@@ -125,7 +125,7 @@ body, body[theme-mode="dark"] .semi-always-light, :host, :host .semi-always-ligh
     --semi-color-data-19: rgba(188, 198, 255, 1); //vchart 数据色板颜色 - 19
 }
 
-body[theme-mode="dark"], body .semi-always-dark, :host-context(body[theme-mode="dark"]), :host .semi-always-dark {
+body[theme-mode="dark"], body .semi-always-dark, :host([theme-mode="dark"]), :host .semi-always-dark {
     font-family: "Inter", -apple-system, BlinkMacSystemFont, "Segoe UI", "PingFang SC", "Hiragino Sans GB", "Microsoft YaHei", "Helvetica Neue", Helvetica, Arial, sans-serif;
     -webkit-font-smoothing: antialiased;
     --semi-color-white: rgba(228, 231, 245, 1);

+ 2 - 1
packages/semi-ui/button/Button.tsx

@@ -11,7 +11,7 @@ const { htmlTypes, btnTypes } = strings;
 
 export type HtmlType = 'button' | 'reset' | 'submit';
 export type Size = 'default' | 'small' | 'large';
-export type Theme = 'solid' | 'borderless' | 'light';
+export type Theme = 'solid' | 'borderless' | 'light' | 'outline';
 export type Type = 'primary' | 'secondary' | 'tertiary' | 'warning' | 'danger';
 
 export interface ButtonProps extends Omit<React.ButtonHTMLAttributes<HTMLButtonElement>, 'type'>{
@@ -106,6 +106,7 @@ export default class Button extends PureComponent<ButtonProps> {
                     [`${prefixCls}-block`]: block,
                     [`${prefixCls}-circle`]: circle,
                     [`${prefixCls}-borderless`]: theme === 'borderless',
+                    [`${prefixCls}-outline`]: theme === "outline",
                     [`${prefixCls}-${type}-disabled`]: disabled && type,
                 },
                 className

+ 1 - 1
packages/semi-ui/datePicker/_story/v2/FeatInsetInputProps.tsx

@@ -41,7 +41,7 @@ export default function App() {
             </div>
             <Space wrap spacing={spacing}>
                 <DatePicker placeholder='选择单个日期' {...props} />
-                <DatePicker placeholder='选择月' {...props} type='month' />
+                <DatePicker placeholder='选择月' {...props} type='month' dropdownClassName="chromatic-ignore" />
                 <DatePicker placeholder='选择日期时间' {...props} type='dateTime' />
                 <DatePicker placeholder='选择日期范围' {...props} type='dateRange' />
                 <DatePicker placeholder='选择日期时间范围' {...props} type='dateTimeRange' />

+ 3 - 0
packages/semi-ui/locale/interface.ts

@@ -13,6 +13,9 @@ export interface Locale {
         confirm: string;
         cancel: string
     };
+    Tabs: {
+        more: string
+    };
     TimePicker: {
         placeholder: {
             time: string;

+ 3 - 0
packages/semi-ui/locale/source/ar.ts

@@ -14,6 +14,9 @@ const local: Locale = {
         confirm: 'تؤكد',
         cancel: 'إلغاء',
     },
+    Tabs: {
+        more: "أكثر"
+    },
     TimePicker: {
         placeholder: {
             time: 'حدد الوقت',

+ 3 - 0
packages/semi-ui/locale/source/de.ts

@@ -14,6 +14,9 @@ const local: Locale = {
         confirm: 'Bestätigen',
         cancel: 'Abbrechen',
     },
+    Tabs: {
+        more: "Mehr"
+    },
     TimePicker: {
         placeholder: {
             time: 'Zeit auswählen',

+ 3 - 0
packages/semi-ui/locale/source/en_GB.ts

@@ -14,6 +14,9 @@ const local: Locale = {
         confirm: 'Confirm',
         cancel: 'Cancel',
     },
+    Tabs: {
+        more: "More"
+    },
     TimePicker: {
         placeholder: {
             time: 'Select time',

+ 3 - 0
packages/semi-ui/locale/source/en_US.ts

@@ -14,6 +14,9 @@ const local: Locale = {
         confirm: 'Confirm',
         cancel: 'Cancel',
     },
+    Tabs: {
+        more: "More"
+    },
     TimePicker: {
         placeholder: {
             time: 'Select time',

+ 3 - 0
packages/semi-ui/locale/source/es.ts

@@ -19,6 +19,9 @@ const locale: Locale = {
         confirm: 'Aceptar',
         cancel: 'Cancelar',
     },
+    Tabs: {
+        more: "Más"
+    },
     TimePicker: {
         placeholder: {
             time: 'Seleccionar hora',

+ 3 - 0
packages/semi-ui/locale/source/fr.ts

@@ -14,6 +14,9 @@ const local: Locale = {
         confirm: 'Confirmer',
         cancel: 'Annuler',
     },
+    Tabs: {
+        more: "Plus",
+    },
     TimePicker: {
         placeholder: {
             time: 'Sélectionner temps',

+ 3 - 0
packages/semi-ui/locale/source/id_ID.ts

@@ -14,6 +14,9 @@ const local: Locale = {
         confirm: 'Konfirmasi',
         cancel: 'Batalkan',
     },
+    Tabs: {
+        more: "Lagi"
+    },
     TimePicker: {
         placeholder: {
             time: 'Pilih waktu',

+ 3 - 0
packages/semi-ui/locale/source/it.ts

@@ -14,6 +14,9 @@ const local: Locale = {
         confirm: 'Conferma',
         cancel: 'Cancella',
     },
+    Tabs: {
+        more: "Di più"
+    },
     TimePicker: {
         placeholder: {
             time: 'Seleziona ora',

+ 3 - 0
packages/semi-ui/locale/source/ja_JP.ts

@@ -14,6 +14,9 @@ const local: Locale = {
         confirm: '確認する',
         cancel: 'キャンセル',
     },
+    Tabs: {
+        more: "もっと"
+    },
     TimePicker: {
         placeholder: {
             time: '時間を選択してください',

+ 3 - 0
packages/semi-ui/locale/source/ko_KR.ts

@@ -14,6 +14,9 @@ const local: Locale = {
         confirm: '확인',
         cancel: '취소',
     },
+    Tabs: {
+        more: "더"
+    },
     TimePicker: {
         placeholder: {
             time: '시간 선택',

+ 3 - 0
packages/semi-ui/locale/source/ms_MY.ts

@@ -14,6 +14,9 @@ const local: Locale = {
         confirm: 'Sahkan',
         cancel: 'Batal',
     },
+    Tabs: {
+        more: "Lagi"
+    },
     TimePicker: {
         placeholder: {
             time: 'Pilih masa',

+ 3 - 0
packages/semi-ui/locale/source/nl_NL.ts

@@ -21,6 +21,9 @@ const local: Locale = {
         confirm: 'Bevestigen',
         cancel: 'Annuleren',
     },
+    Tabs: {
+        more: "Meer"
+    },
     TimePicker: {
         placeholder: {
             time: 'Tijd selecteren',

+ 3 - 0
packages/semi-ui/locale/source/pl_PL.ts

@@ -22,6 +22,9 @@ const local: Locale = {
         confirm: 'Potwierdź',
         cancel: 'Anuluj',
     },
+    Tabs: {
+        more: "Więcej"
+    },
     TimePicker: {
         placeholder: {
             time: 'Wybierz czas',

+ 3 - 0
packages/semi-ui/locale/source/pt_BR.ts

@@ -14,6 +14,9 @@ const local: Locale = {
         confirm: 'OK',
         cancel: 'Cancelar',
     },
+    Tabs: {
+        more: "Mais"
+    },
     TimePicker: {
         placeholder: {
             time: 'Por favor escolha a hora',

+ 3 - 0
packages/semi-ui/locale/source/ro.ts

@@ -14,6 +14,9 @@ const local: Locale = {
         confirm: 'Confirmă',
         cancel: 'Anulează',
     },
+    Tabs: {
+        more: "Mai mult"
+    },
     TimePicker: {
         placeholder: {
             time: 'Selectează timpul',

+ 3 - 0
packages/semi-ui/locale/source/ru_RU.ts

@@ -14,6 +14,9 @@ const local: Locale = {
         confirm: 'подтвердить',
         cancel: 'отмена',
     },
+    Tabs: {
+        more: "Более"
+    },
     TimePicker: {
         placeholder: {
             time: 'Выбрать время',

+ 3 - 0
packages/semi-ui/locale/source/sv_SE.ts

@@ -19,6 +19,9 @@ const local: Locale = {
         confirm: 'Bekräfta',
         cancel: 'Avbryt',
     },
+    Tabs: {
+        more: "Mer"
+    },
     TimePicker: {
         placeholder: {
             time: 'Välj tid',

+ 3 - 0
packages/semi-ui/locale/source/th_TH.ts

@@ -14,6 +14,9 @@ const local: Locale = {
         confirm: 'ตกลง',
         cancel: 'ยกเลิก',
     },
+    Tabs: {
+        more: "มากกว่า"
+    },
     TimePicker: {
         placeholder: {
             time: 'โปรดเลือกเวลา',

+ 3 - 0
packages/semi-ui/locale/source/tr_TR.ts

@@ -14,6 +14,9 @@ const local: Locale = {
         confirm: 'Tamam',
         cancel: 'İptal'
     },
+    Tabs: {
+        more: "Daha"
+    },
     TimePicker: {
         placeholder: {
             time: 'Lütfen bir zaman seçin',

+ 3 - 0
packages/semi-ui/locale/source/vi_VN.ts

@@ -14,6 +14,9 @@ const local: Locale = {
         confirm: 'Xác nhận',
         cancel: 'Huỷ bỏ',
     },
+    Tabs: {
+        more: "Hơn"
+    },
     TimePicker: {
         placeholder: {
             time: 'Chọn thời gian',

+ 3 - 0
packages/semi-ui/locale/source/zh_CN.ts

@@ -14,6 +14,9 @@ const local: Locale = {
         confirm: '确定',
         cancel: '取消',
     },
+    Tabs: {
+        more: "更多",
+    },
     TimePicker: {
         placeholder: {
             time: '请选择时间',

+ 3 - 0
packages/semi-ui/locale/source/zh_TW.ts

@@ -14,6 +14,9 @@ const local: Locale = {
         confirm: '確定',
         cancel: '取消',
     },
+    Tabs: {
+        more: "更多"
+    },
     TimePicker: {
         placeholder: {
             time: '請選擇時間',

+ 7 - 7
packages/semi-ui/package.json

@@ -1,6 +1,6 @@
 {
     "name": "@douyinfe/semi-ui",
-    "version": "2.57.0",
+    "version": "2.57.1-alpha.0",
     "description": "A modern, comprehensive, flexible design system and UI library. Connect DesignOps & DevOps. Quickly build beautiful React apps. Maintained by Douyin-fe team.",
     "main": "lib/cjs/index.js",
     "module": "lib/es/index.js",
@@ -20,12 +20,12 @@
         "@dnd-kit/core": "^6.0.8",
         "@dnd-kit/sortable": "^7.0.2",
         "@dnd-kit/utilities": "^3.2.1",
-        "@douyinfe/semi-animation": "2.57.0",
-        "@douyinfe/semi-animation-react": "2.57.0",
-        "@douyinfe/semi-foundation": "2.57.0",
-        "@douyinfe/semi-icons": "2.57.0",
-        "@douyinfe/semi-illustrations": "2.57.0",
-        "@douyinfe/semi-theme-default": "2.57.0",
+        "@douyinfe/semi-animation": "2.57.1-alpha.0",
+        "@douyinfe/semi-animation-react": "2.57.1-alpha.0",
+        "@douyinfe/semi-foundation": "2.57.1-alpha.0",
+        "@douyinfe/semi-icons": "2.57.1-alpha.0",
+        "@douyinfe/semi-illustrations": "2.57.1-alpha.0",
+        "@douyinfe/semi-theme-default": "2.57.1-alpha.0",
         "async-validator": "^3.5.0",
         "classnames": "^2.2.6",
         "copy-text-to-clipboard": "^2.1.1",

+ 4 - 2
packages/semi-ui/slider/index.tsx

@@ -132,9 +132,11 @@ export default class Slider extends BaseComponent<SliderProps, SliderState> {
             getSliderLengths: () => {
                 if (this.sliderEl && this.sliderEl.current) {
                     const rect = this.sliderEl.current.getBoundingClientRect();
+                    const offsetParentRect = this.sliderEl.current.offsetParent?.getBoundingClientRect();
+
                     const offset = {
-                        x: this.sliderEl.current.offsetLeft,
-                        y: this.sliderEl.current.offsetTop,
+                        x: offsetParentRect ? (rect.left - offsetParentRect.left): this.sliderEl.current.offsetLeft,
+                        y: offsetParentRect ? (rect.top - offsetParentRect.top) : this.sliderEl.current.offsetTop,
                     };
                     return {
                         sliderX: offset.x,

+ 6 - 0
packages/semi-ui/table/_story/RTL/ColumnAlignWithSorter.tsx

@@ -16,4 +16,10 @@ function App() {
     );
 }
 
+App.parameters = {
+    chromatic: {
+        delay: 3000,
+    },
+};
+
 export default App;

+ 6 - 0
packages/semi-ui/table/_story/v2/FixedOnGroupedRowClassName/index.tsx

@@ -103,3 +103,9 @@ export default function App() {
         </div>
     );
 }
+
+App.parameters = {
+    chromatic: {
+        disableSnapshot: true,
+    },
+};

+ 67 - 8
packages/semi-ui/tabs/TabBar.tsx

@@ -4,13 +4,15 @@ import cls from 'classnames';
 import { cssClasses, strings } from '@douyinfe/semi-foundation/tabs/constants';
 import getDataAttr from '@douyinfe/semi-foundation/utils/getDataAttr';
 import OverflowList from '../overflowList';
-import Dropdown from '../dropdown';
+import Dropdown, { DropdownProps } from '../dropdown';
 import Button from '../button';
 import { TabBarProps, PlainTab } from './interface';
 import { isEmpty, pick } from 'lodash';
-import { IconChevronRight, IconChevronLeft, IconClose } from '@douyinfe/semi-icons';
+import { IconChevronRight, IconChevronLeft, IconChevronDown } from '@douyinfe/semi-icons';
 import { getUuidv4 } from '@douyinfe/semi-foundation/utils/uuid';
 import TabItem from './TabItem';
+import { Locale } from "../locale/interface";
+import LocaleConsumer from "../locale/localeConsumer";
 
 export interface TabBarState {
     endInd: number;
@@ -37,7 +39,8 @@ class TabBar extends React.Component<TabBarProps, TabBarState> {
         tabPosition: PropTypes.oneOf(strings.POSITION_MAP),
         type: PropTypes.oneOf(strings.TYPE_MAP),
         closable: PropTypes.bool,
-        deleteTabItem: PropTypes.func
+        deleteTabItem: PropTypes.func,
+        more: PropTypes.oneOfType([PropTypes.number, PropTypes.object]),
     };
 
     constructor(props: TabBarProps) {
@@ -104,7 +107,7 @@ class TabBar extends React.Component<TabBarProps, TabBarState> {
         return (
             <TabItem
                 {...pick(panel, ['disabled', 'icon', 'itemKey', 'tab', 'closable'])}
-                key={this._getItemKey(panel.itemKey)} 
+                key={this._getItemKey(panel.itemKey)}
                 selected={isSelected}
                 size={size}
                 type={type}
@@ -195,7 +198,7 @@ class TabBar extends React.Component<TabBarProps, TabBarState> {
     };
 
     renderOverflow = (items: any[]): Array<ReactNode> => items.map((item, ind) => {
-        const icon = ind === 0 ? <IconChevronLeft /> : <IconChevronRight />;
+        const icon = ind === 0 ? <IconChevronLeft/> : <IconChevronRight/>;
         const pos = ind === 0 ? 'start' : 'end';
         return this.renderCollapse(item, icon, pos);
     });
@@ -218,8 +221,63 @@ class TabBar extends React.Component<TabBarProps, TabBarState> {
         );
     };
 
+    renderWithMoreTrigger = (): ReactNode => {
+        const { list, more } = this.props;
+        let tabElements: ReactNode[] = [];
+        let moreTrigger: ReactNode = <div className={cls({
+            [`${cssClasses.TABS_BAR}-more-trigger`]: true,
+            [`${cssClasses.TABS_BAR}-more-trigger-${this.props.type}`]: true
+        })}>
+            <LocaleConsumer componentName="Tabs">
+                {(locale: Locale['Tabs'], localeCode: Locale['code']) => (
+                    <div className={`${cssClasses.TABS_BAR}-more-trigger-content`}>
+                        <div>{locale.more}</div>
+                        <IconChevronDown className={`${cssClasses.TABS_BAR}-more-trigger-content-icon`}/>
+                    </div>
+                )}
+            </LocaleConsumer>
+        </div>;
+        let keepCount: number;
+        if (typeof more === "number") {
+            keepCount = list.length - Math.min(more, list.length);
+            tabElements = list.slice(0, keepCount).map(panel => this.renderTabItem(panel));
+        } else if (typeof more === 'object') {
+            keepCount = list.length - Math.min(more.count, list.length);
+            tabElements = list.slice(0, keepCount).map(panel => this.renderTabItem(panel));
+            if (more.render) {
+                moreTrigger = more.render();
+            }
+
+        } else if (more !== undefined) {
+            throw new Error("[Semi Tabs]: invalid tab props format: more");
+        }
+
+        return <>
+            {tabElements}
+            {this.renderMoreDropdown(list.slice(keepCount), more?.['dropdownProps'], moreTrigger)}
+        </>;
+    }
+
+    renderMoreDropdown = (panels: PlainTab[], dropDownProps: DropdownProps, trigger: ReactNode): ReactNode => {
+
+        return <Dropdown trigger={'hover'} showTick position={'bottomLeft'}
+            className={`${cssClasses.TABS_BAR}-more-dropdown-${this.props.type}`}
+            clickToHide={true}
+            menu={panels.map(panel => ({
+                node: 'item',
+                name: panel.tab as string,
+                icon: panel.icon,
+                onClick: (e) => this.props.onTabClick(panel.itemKey, e),
+                active: this.props.activeKey === panel.itemKey
+            }))}
+            {...dropDownProps}
+        >
+            {trigger}
+        </Dropdown>;
+    }
+
     render(): ReactNode {
-        const { type, style, className, list, tabPosition, collapsible, ...restProps } = this.props;
+        const { type, style, className, list, tabPosition, more, collapsible, ...restProps } = this.props;
         const classNames = cls(className, {
             [cssClasses.TABS_BAR]: true,
             [cssClasses.TABS_BAR_LINE]: type === 'line',
@@ -230,10 +288,11 @@ class TabBar extends React.Component<TabBarProps, TabBarState> {
         });
 
         const extra = this.renderExtra();
-        const contents = collapsible ? this.renderCollapsedTab() : this.renderTabComponents(list);
+        const contents = collapsible ? this.renderCollapsedTab() : (more ? this.renderWithMoreTrigger() : this.renderTabComponents(list));
 
         return (
-            <div role="tablist" aria-orientation={tabPosition === "left" ? "vertical" : "horizontal"} className={classNames} style={style} {...getDataAttr(restProps)} data-uuid={this.state.uuid}>
+            <div role="tablist" aria-orientation={tabPosition === "left" ? "vertical" : "horizontal"}
+                className={classNames} style={style} {...getDataAttr(restProps)} data-uuid={this.state.uuid}>
                 {contents}
                 {extra}
             </div>

+ 1 - 1
packages/semi-ui/tabs/TabItem.tsx

@@ -48,7 +48,7 @@ const TabItem = (props: TabItemProps, ref: LegacyRef<HTMLDivElement>) => {
 
     const renderIcon = useCallback(
         (icon: ReactNode) => (
-            <span>
+            <span className={`${cssClasses.TABS_BAR}-icon`}>
                 {icon}
             </span>
         ), []);

+ 4 - 1
packages/semi-ui/tabs/index.tsx

@@ -52,6 +52,7 @@ class Tabs extends BaseComponent<TabsProps, TabsState> {
         type: PropTypes.oneOf(strings.TYPE_MAP),
         onTabClose: PropTypes.func,
         preventScroll: PropTypes.bool,
+        more: PropTypes.oneOfType([PropTypes.number, PropTypes.object]),
     };
     static __SemiComponentName__ = "Tabs";
     static defaultProps: TabsProps = getDefaultPropsFromGlobalConfig(Tabs.__SemiComponentName__, {
@@ -253,6 +254,7 @@ class Tabs extends BaseComponent<TabsProps, TabsState> {
             tabPaneMotion,
             tabPosition,
             type,
+            more,
             ...restProps
         } = this.props;
         const { panes, activeKey } = this.state;
@@ -278,7 +280,8 @@ class Tabs extends BaseComponent<TabsProps, TabsState> {
             tabPosition,
             type,
             deleteTabItem: this.deleteTabItem,
-            handleKeyDown: this.foundation.handleKeyDown
+            handleKeyDown: this.foundation.handleKeyDown,
+            more,
         } as TabBarProps;
 
         const tabBar = renderTabBar ? renderTabBar(tabBarProps, TabBar) : <TabBar {...tabBarProps} />;

+ 6 - 3
packages/semi-ui/tabs/interface.ts

@@ -1,6 +1,7 @@
 import React, { ComponentType, CSSProperties, MouseEvent, ReactNode } from 'react';
 import { Motion } from '../_base/base';
 import TabBar from './TabBar';
+import { DropdownProps } from "../dropdown";
 
 export type TabType = 'line' | 'card' | 'button';
 export type TabSize = 'small' | 'medium' | 'large';
@@ -37,7 +38,8 @@ export interface TabsProps {
     tabPosition?: TabPosition;
     type?: TabType;
     onTabClose?: (tabKey: string) => void;
-    preventScroll?: boolean
+    preventScroll?: boolean;
+    more?: number | { count: number; render?: () => ReactNode; dropdownProps?: DropdownProps }
 }
 
 export interface TabBarProps {
@@ -55,7 +57,8 @@ export interface TabBarProps {
     dropdownStyle?: CSSProperties;
     closable?: boolean;
     deleteTabItem?: (tabKey: string, event: MouseEvent<Element>) => void;
-    handleKeyDown?: (event: React.KeyboardEvent, itemKey: string, closable: boolean) => void
+    handleKeyDown?: (event: React.KeyboardEvent, itemKey: string, closable: boolean) => void;
+    more?: TabsProps['more']
 }
 
 export interface TabPaneProps {
@@ -85,6 +88,6 @@ export interface TabContextValue {
     panes?: Array<PlainTab>;
     tabPaneMotion?: boolean;
     tabPosition?: TabPosition;
-    prevActiveKey?: string|null;
+    prevActiveKey?: string | null;
     forceDisableMotion?: boolean
 }

+ 1 - 1
packages/semi-webpack/package.json

@@ -1,6 +1,6 @@
 {
     "name": "@douyinfe/semi-webpack-plugin",
-    "version": "2.57.0",
+    "version": "2.57.1-alpha.0",
     "description": "",
     "author": "伍浩威 <[email protected]>",
     "homepage": "",

File diff suppressed because it is too large
+ 44 - 527
yarn.lock


Some files were not shown because too many files changed in this diff