mirror of
https://github.com/ant-design/ant-design.git
synced 2025-01-18 14:13:37 +08:00
feat: New Tabs (#24552)
* init style * support size * editable * add shadow * update demo * fix nest style * update rtl * update snapshot * bump * fix hover * fix test case * fix style lint * clean up * updat docs * add onTabScroll * upgrade rc-dropdown * update snapshot * clean snapshot * clean up Co-authored-by: afc163 <afc163@gmail.com>
This commit is contained in:
parent
75d84b2041
commit
77c5adbe4d
@ -839,133 +839,99 @@ exports[`renders ./components/card/demo/tabs.md correctly 1`] = `
|
||||
</div>
|
||||
</div>
|
||||
<div
|
||||
class="ant-tabs ant-tabs-top ant-card-head-tabs ant-tabs-large ant-tabs-line"
|
||||
class="ant-tabs ant-tabs-top ant-card-head-tabs ant-tabs-large"
|
||||
>
|
||||
<div
|
||||
class="ant-tabs-bar ant-tabs-top-bar ant-tabs-large-bar"
|
||||
class="ant-tabs-nav"
|
||||
role="tablist"
|
||||
tabindex="-1"
|
||||
>
|
||||
<div
|
||||
class="ant-tabs-nav-container"
|
||||
class="ant-tabs-nav-wrap"
|
||||
>
|
||||
<span
|
||||
class="ant-tabs-tab-prev ant-tabs-tab-btn-disabled"
|
||||
unselectable="unselectable"
|
||||
>
|
||||
<span
|
||||
class="ant-tabs-tab-prev-icon"
|
||||
>
|
||||
<span
|
||||
aria-label="left"
|
||||
class="anticon anticon-left ant-tabs-tab-prev-icon-target"
|
||||
role="img"
|
||||
>
|
||||
<svg
|
||||
aria-hidden="true"
|
||||
class=""
|
||||
data-icon="left"
|
||||
fill="currentColor"
|
||||
focusable="false"
|
||||
height="1em"
|
||||
viewBox="64 64 896 896"
|
||||
width="1em"
|
||||
>
|
||||
<path
|
||||
d="M724 218.3V141c0-6.7-7.7-10.4-12.9-6.3L260.3 486.8a31.86 31.86 0 000 50.3l450.8 352.1c5.3 4.1 12.9.4 12.9-6.3v-77.3c0-4.9-2.3-9.6-6.1-12.6l-360-281 360-281.1c3.8-3 6.1-7.7 6.1-12.6z"
|
||||
/>
|
||||
</svg>
|
||||
</span>
|
||||
</span>
|
||||
</span>
|
||||
<span
|
||||
class="ant-tabs-tab-next ant-tabs-tab-btn-disabled"
|
||||
unselectable="unselectable"
|
||||
>
|
||||
<span
|
||||
class="ant-tabs-tab-next-icon"
|
||||
>
|
||||
<span
|
||||
aria-label="right"
|
||||
class="anticon anticon-right ant-tabs-tab-next-icon-target"
|
||||
role="img"
|
||||
>
|
||||
<svg
|
||||
aria-hidden="true"
|
||||
class=""
|
||||
data-icon="right"
|
||||
fill="currentColor"
|
||||
focusable="false"
|
||||
height="1em"
|
||||
viewBox="64 64 896 896"
|
||||
width="1em"
|
||||
>
|
||||
<path
|
||||
d="M765.7 486.8L314.9 134.7A7.97 7.97 0 00302 141v77.3c0 4.9 2.3 9.6 6.1 12.6l360 281.1-360 281.1c-3.9 3-6.1 7.7-6.1 12.6V883c0 6.7 7.7 10.4 12.9 6.3l450.8-352.1a31.96 31.96 0 000-50.4z"
|
||||
/>
|
||||
</svg>
|
||||
</span>
|
||||
</span>
|
||||
</span>
|
||||
<div
|
||||
class="ant-tabs-nav-wrap"
|
||||
class="ant-tabs-nav-list"
|
||||
style="transform:translate(0px, 0px)"
|
||||
>
|
||||
<div
|
||||
class="ant-tabs-nav-scroll"
|
||||
<button
|
||||
aria-selected="true"
|
||||
class="ant-tabs-tab ant-tabs-tab-active"
|
||||
role="tab"
|
||||
tabindex="0"
|
||||
type="button"
|
||||
>
|
||||
<div
|
||||
class="ant-tabs-nav ant-tabs-nav-animated"
|
||||
>
|
||||
<div>
|
||||
<div
|
||||
aria-controls="tabpane-tab1"
|
||||
aria-disabled="false"
|
||||
aria-selected="true"
|
||||
class="ant-tabs-tab-active ant-tabs-tab"
|
||||
id="tab-tab1"
|
||||
role="tab"
|
||||
tabindex="0"
|
||||
>
|
||||
tab1
|
||||
</div>
|
||||
<div
|
||||
aria-controls="tabpane-tab2"
|
||||
aria-disabled="false"
|
||||
aria-selected="false"
|
||||
class=" ant-tabs-tab"
|
||||
id="tab-tab2"
|
||||
role="tab"
|
||||
tabindex="-1"
|
||||
>
|
||||
tab2
|
||||
</div>
|
||||
</div>
|
||||
<div
|
||||
class="ant-tabs-ink-bar ant-tabs-ink-bar-animated"
|
||||
/>
|
||||
</div>
|
||||
</div>
|
||||
tab1
|
||||
</button>
|
||||
<button
|
||||
aria-selected="false"
|
||||
class="ant-tabs-tab"
|
||||
role="tab"
|
||||
tabindex="0"
|
||||
type="button"
|
||||
>
|
||||
tab2
|
||||
</button>
|
||||
<div
|
||||
class="ant-tabs-ink-bar ant-tabs-ink-bar-animated"
|
||||
/>
|
||||
</div>
|
||||
</div>
|
||||
<div
|
||||
class="ant-tabs-nav-operations ant-tabs-nav-operations-hidden"
|
||||
>
|
||||
<button
|
||||
aria-controls="null-more-popup"
|
||||
aria-expanded="false"
|
||||
aria-haspopup="listbox"
|
||||
aria-hidden="true"
|
||||
class="ant-tabs-nav-more"
|
||||
id="null-more"
|
||||
style="visibility:hidden;order:1"
|
||||
tabindex="-1"
|
||||
type="button"
|
||||
>
|
||||
<span
|
||||
aria-label="ellipsis"
|
||||
class="anticon anticon-ellipsis"
|
||||
role="img"
|
||||
>
|
||||
<svg
|
||||
aria-hidden="true"
|
||||
class=""
|
||||
data-icon="ellipsis"
|
||||
fill="currentColor"
|
||||
focusable="false"
|
||||
height="1em"
|
||||
viewBox="64 64 896 896"
|
||||
width="1em"
|
||||
>
|
||||
<path
|
||||
d="M176 511a56 56 0 10112 0 56 56 0 10-112 0zm280 0a56 56 0 10112 0 56 56 0 10-112 0zm280 0a56 56 0 10112 0 56 56 0 10-112 0z"
|
||||
/>
|
||||
</svg>
|
||||
</span>
|
||||
</button>
|
||||
</div>
|
||||
</div>
|
||||
<div
|
||||
class="ant-tabs-content ant-tabs-content-animated ant-tabs-top-content"
|
||||
style="margin-left:0%"
|
||||
class="ant-tabs-content-holder"
|
||||
>
|
||||
<div
|
||||
aria-hidden="false"
|
||||
class="ant-tabs-tabpane ant-tabs-tabpane-active"
|
||||
role="tabpanel"
|
||||
style="visibility:visible"
|
||||
tabindex="0"
|
||||
/>
|
||||
<div
|
||||
aria-hidden="true"
|
||||
class="ant-tabs-tabpane ant-tabs-tabpane-inactive"
|
||||
role="tabpanel"
|
||||
style="visibility:hidden"
|
||||
tabindex="-1"
|
||||
/>
|
||||
class="ant-tabs-content ant-tabs-content-top"
|
||||
>
|
||||
<div
|
||||
aria-hidden="false"
|
||||
class="ant-tabs-tabpane ant-tabs-tabpane-active"
|
||||
role="tabpanel"
|
||||
tabindex="0"
|
||||
/>
|
||||
<div
|
||||
aria-hidden="true"
|
||||
class="ant-tabs-tabpane"
|
||||
role="tabpanel"
|
||||
style="display:none"
|
||||
tabindex="-1"
|
||||
/>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
@ -990,16 +956,89 @@ exports[`renders ./components/card/demo/tabs.md correctly 1`] = `
|
||||
class="ant-card-head-wrapper"
|
||||
/>
|
||||
<div
|
||||
class="ant-tabs ant-tabs-top ant-card-head-tabs ant-tabs-large ant-tabs-line"
|
||||
class="ant-tabs ant-tabs-top ant-card-head-tabs ant-tabs-large"
|
||||
>
|
||||
<div
|
||||
class="ant-tabs-bar ant-tabs-top-bar ant-tabs-large-bar"
|
||||
class="ant-tabs-nav"
|
||||
role="tablist"
|
||||
tabindex="-1"
|
||||
>
|
||||
<div
|
||||
class="ant-tabs-nav-wrap"
|
||||
>
|
||||
<div
|
||||
class="ant-tabs-nav-list"
|
||||
style="transform:translate(0px, 0px)"
|
||||
>
|
||||
<button
|
||||
aria-selected="false"
|
||||
class="ant-tabs-tab"
|
||||
role="tab"
|
||||
tabindex="0"
|
||||
type="button"
|
||||
>
|
||||
article
|
||||
</button>
|
||||
<button
|
||||
aria-selected="true"
|
||||
class="ant-tabs-tab ant-tabs-tab-active"
|
||||
role="tab"
|
||||
tabindex="0"
|
||||
type="button"
|
||||
>
|
||||
app
|
||||
</button>
|
||||
<button
|
||||
aria-selected="false"
|
||||
class="ant-tabs-tab"
|
||||
role="tab"
|
||||
tabindex="0"
|
||||
type="button"
|
||||
>
|
||||
project
|
||||
</button>
|
||||
<div
|
||||
class="ant-tabs-ink-bar ant-tabs-ink-bar-animated"
|
||||
/>
|
||||
</div>
|
||||
</div>
|
||||
<div
|
||||
class="ant-tabs-nav-operations ant-tabs-nav-operations-hidden"
|
||||
>
|
||||
<button
|
||||
aria-controls="null-more-popup"
|
||||
aria-expanded="false"
|
||||
aria-haspopup="listbox"
|
||||
aria-hidden="true"
|
||||
class="ant-tabs-nav-more"
|
||||
id="null-more"
|
||||
style="visibility:hidden;order:1"
|
||||
tabindex="-1"
|
||||
type="button"
|
||||
>
|
||||
<span
|
||||
aria-label="ellipsis"
|
||||
class="anticon anticon-ellipsis"
|
||||
role="img"
|
||||
>
|
||||
<svg
|
||||
aria-hidden="true"
|
||||
class=""
|
||||
data-icon="ellipsis"
|
||||
fill="currentColor"
|
||||
focusable="false"
|
||||
height="1em"
|
||||
viewBox="64 64 896 896"
|
||||
width="1em"
|
||||
>
|
||||
<path
|
||||
d="M176 511a56 56 0 10112 0 56 56 0 10-112 0zm280 0a56 56 0 10112 0 56 56 0 10-112 0zm280 0a56 56 0 10112 0 56 56 0 10-112 0z"
|
||||
/>
|
||||
</svg>
|
||||
</span>
|
||||
</button>
|
||||
</div>
|
||||
<div
|
||||
class="ant-tabs-extra-content"
|
||||
style="float:right"
|
||||
>
|
||||
<a
|
||||
href="#"
|
||||
@ -1007,144 +1046,34 @@ exports[`renders ./components/card/demo/tabs.md correctly 1`] = `
|
||||
More
|
||||
</a>
|
||||
</div>
|
||||
<div
|
||||
class="ant-tabs-nav-container"
|
||||
>
|
||||
<span
|
||||
class="ant-tabs-tab-prev ant-tabs-tab-btn-disabled"
|
||||
unselectable="unselectable"
|
||||
>
|
||||
<span
|
||||
class="ant-tabs-tab-prev-icon"
|
||||
>
|
||||
<span
|
||||
aria-label="left"
|
||||
class="anticon anticon-left ant-tabs-tab-prev-icon-target"
|
||||
role="img"
|
||||
>
|
||||
<svg
|
||||
aria-hidden="true"
|
||||
class=""
|
||||
data-icon="left"
|
||||
fill="currentColor"
|
||||
focusable="false"
|
||||
height="1em"
|
||||
viewBox="64 64 896 896"
|
||||
width="1em"
|
||||
>
|
||||
<path
|
||||
d="M724 218.3V141c0-6.7-7.7-10.4-12.9-6.3L260.3 486.8a31.86 31.86 0 000 50.3l450.8 352.1c5.3 4.1 12.9.4 12.9-6.3v-77.3c0-4.9-2.3-9.6-6.1-12.6l-360-281 360-281.1c3.8-3 6.1-7.7 6.1-12.6z"
|
||||
/>
|
||||
</svg>
|
||||
</span>
|
||||
</span>
|
||||
</span>
|
||||
<span
|
||||
class="ant-tabs-tab-next ant-tabs-tab-btn-disabled"
|
||||
unselectable="unselectable"
|
||||
>
|
||||
<span
|
||||
class="ant-tabs-tab-next-icon"
|
||||
>
|
||||
<span
|
||||
aria-label="right"
|
||||
class="anticon anticon-right ant-tabs-tab-next-icon-target"
|
||||
role="img"
|
||||
>
|
||||
<svg
|
||||
aria-hidden="true"
|
||||
class=""
|
||||
data-icon="right"
|
||||
fill="currentColor"
|
||||
focusable="false"
|
||||
height="1em"
|
||||
viewBox="64 64 896 896"
|
||||
width="1em"
|
||||
>
|
||||
<path
|
||||
d="M765.7 486.8L314.9 134.7A7.97 7.97 0 00302 141v77.3c0 4.9 2.3 9.6 6.1 12.6l360 281.1-360 281.1c-3.9 3-6.1 7.7-6.1 12.6V883c0 6.7 7.7 10.4 12.9 6.3l450.8-352.1a31.96 31.96 0 000-50.4z"
|
||||
/>
|
||||
</svg>
|
||||
</span>
|
||||
</span>
|
||||
</span>
|
||||
<div
|
||||
class="ant-tabs-nav-wrap"
|
||||
>
|
||||
<div
|
||||
class="ant-tabs-nav-scroll"
|
||||
>
|
||||
<div
|
||||
class="ant-tabs-nav ant-tabs-nav-animated"
|
||||
>
|
||||
<div>
|
||||
<div
|
||||
aria-controls="tabpane-article"
|
||||
aria-disabled="false"
|
||||
aria-selected="false"
|
||||
class=" ant-tabs-tab"
|
||||
id="tab-article"
|
||||
role="tab"
|
||||
tabindex="-1"
|
||||
>
|
||||
article
|
||||
</div>
|
||||
<div
|
||||
aria-controls="tabpane-app"
|
||||
aria-disabled="false"
|
||||
aria-selected="true"
|
||||
class="ant-tabs-tab-active ant-tabs-tab"
|
||||
id="tab-app"
|
||||
role="tab"
|
||||
tabindex="0"
|
||||
>
|
||||
app
|
||||
</div>
|
||||
<div
|
||||
aria-controls="tabpane-project"
|
||||
aria-disabled="false"
|
||||
aria-selected="false"
|
||||
class=" ant-tabs-tab"
|
||||
id="tab-project"
|
||||
role="tab"
|
||||
tabindex="-1"
|
||||
>
|
||||
project
|
||||
</div>
|
||||
</div>
|
||||
<div
|
||||
class="ant-tabs-ink-bar ant-tabs-ink-bar-animated"
|
||||
/>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
<div
|
||||
class="ant-tabs-content ant-tabs-content-animated ant-tabs-top-content"
|
||||
style="margin-left:-100%"
|
||||
class="ant-tabs-content-holder"
|
||||
>
|
||||
<div
|
||||
aria-hidden="true"
|
||||
class="ant-tabs-tabpane ant-tabs-tabpane-inactive"
|
||||
role="tabpanel"
|
||||
style="visibility:hidden"
|
||||
tabindex="-1"
|
||||
/>
|
||||
<div
|
||||
aria-hidden="false"
|
||||
class="ant-tabs-tabpane ant-tabs-tabpane-active"
|
||||
role="tabpanel"
|
||||
style="visibility:visible"
|
||||
tabindex="0"
|
||||
/>
|
||||
<div
|
||||
aria-hidden="true"
|
||||
class="ant-tabs-tabpane ant-tabs-tabpane-inactive"
|
||||
role="tabpanel"
|
||||
style="visibility:hidden"
|
||||
tabindex="-1"
|
||||
/>
|
||||
class="ant-tabs-content ant-tabs-content-top"
|
||||
>
|
||||
<div
|
||||
aria-hidden="true"
|
||||
class="ant-tabs-tabpane"
|
||||
role="tabpanel"
|
||||
style="display:none"
|
||||
tabindex="-1"
|
||||
/>
|
||||
<div
|
||||
aria-hidden="false"
|
||||
class="ant-tabs-tabpane ant-tabs-tabpane-active"
|
||||
role="tabpanel"
|
||||
tabindex="0"
|
||||
/>
|
||||
<div
|
||||
aria-hidden="true"
|
||||
class="ant-tabs-tabpane"
|
||||
role="tabpanel"
|
||||
style="display:none"
|
||||
tabindex="-1"
|
||||
/>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
File diff suppressed because it is too large
Load Diff
@ -1175,133 +1175,99 @@ exports[`renders ./components/page-header/demo/responsive.md correctly 1`] = `
|
||||
class="ant-page-header-footer"
|
||||
>
|
||||
<div
|
||||
class="ant-tabs ant-tabs-top ant-tabs-line"
|
||||
class="ant-tabs ant-tabs-top"
|
||||
>
|
||||
<div
|
||||
class="ant-tabs-bar ant-tabs-top-bar"
|
||||
class="ant-tabs-nav"
|
||||
role="tablist"
|
||||
tabindex="-1"
|
||||
>
|
||||
<div
|
||||
class="ant-tabs-nav-container"
|
||||
class="ant-tabs-nav-wrap"
|
||||
>
|
||||
<span
|
||||
class="ant-tabs-tab-prev ant-tabs-tab-btn-disabled"
|
||||
unselectable="unselectable"
|
||||
>
|
||||
<span
|
||||
class="ant-tabs-tab-prev-icon"
|
||||
>
|
||||
<span
|
||||
aria-label="left"
|
||||
class="anticon anticon-left ant-tabs-tab-prev-icon-target"
|
||||
role="img"
|
||||
>
|
||||
<svg
|
||||
aria-hidden="true"
|
||||
class=""
|
||||
data-icon="left"
|
||||
fill="currentColor"
|
||||
focusable="false"
|
||||
height="1em"
|
||||
viewBox="64 64 896 896"
|
||||
width="1em"
|
||||
>
|
||||
<path
|
||||
d="M724 218.3V141c0-6.7-7.7-10.4-12.9-6.3L260.3 486.8a31.86 31.86 0 000 50.3l450.8 352.1c5.3 4.1 12.9.4 12.9-6.3v-77.3c0-4.9-2.3-9.6-6.1-12.6l-360-281 360-281.1c3.8-3 6.1-7.7 6.1-12.6z"
|
||||
/>
|
||||
</svg>
|
||||
</span>
|
||||
</span>
|
||||
</span>
|
||||
<span
|
||||
class="ant-tabs-tab-next ant-tabs-tab-btn-disabled"
|
||||
unselectable="unselectable"
|
||||
>
|
||||
<span
|
||||
class="ant-tabs-tab-next-icon"
|
||||
>
|
||||
<span
|
||||
aria-label="right"
|
||||
class="anticon anticon-right ant-tabs-tab-next-icon-target"
|
||||
role="img"
|
||||
>
|
||||
<svg
|
||||
aria-hidden="true"
|
||||
class=""
|
||||
data-icon="right"
|
||||
fill="currentColor"
|
||||
focusable="false"
|
||||
height="1em"
|
||||
viewBox="64 64 896 896"
|
||||
width="1em"
|
||||
>
|
||||
<path
|
||||
d="M765.7 486.8L314.9 134.7A7.97 7.97 0 00302 141v77.3c0 4.9 2.3 9.6 6.1 12.6l360 281.1-360 281.1c-3.9 3-6.1 7.7-6.1 12.6V883c0 6.7 7.7 10.4 12.9 6.3l450.8-352.1a31.96 31.96 0 000-50.4z"
|
||||
/>
|
||||
</svg>
|
||||
</span>
|
||||
</span>
|
||||
</span>
|
||||
<div
|
||||
class="ant-tabs-nav-wrap"
|
||||
class="ant-tabs-nav-list"
|
||||
style="transform:translate(0px, 0px)"
|
||||
>
|
||||
<div
|
||||
class="ant-tabs-nav-scroll"
|
||||
<button
|
||||
aria-selected="true"
|
||||
class="ant-tabs-tab ant-tabs-tab-active"
|
||||
role="tab"
|
||||
tabindex="0"
|
||||
type="button"
|
||||
>
|
||||
<div
|
||||
class="ant-tabs-nav ant-tabs-nav-animated"
|
||||
>
|
||||
<div>
|
||||
<div
|
||||
aria-controls="tabpane-1"
|
||||
aria-disabled="false"
|
||||
aria-selected="true"
|
||||
class="ant-tabs-tab-active ant-tabs-tab"
|
||||
id="tab-1"
|
||||
role="tab"
|
||||
tabindex="0"
|
||||
>
|
||||
Details
|
||||
</div>
|
||||
<div
|
||||
aria-controls="tabpane-2"
|
||||
aria-disabled="false"
|
||||
aria-selected="false"
|
||||
class=" ant-tabs-tab"
|
||||
id="tab-2"
|
||||
role="tab"
|
||||
tabindex="-1"
|
||||
>
|
||||
Rule
|
||||
</div>
|
||||
</div>
|
||||
<div
|
||||
class="ant-tabs-ink-bar ant-tabs-ink-bar-animated"
|
||||
/>
|
||||
</div>
|
||||
</div>
|
||||
Details
|
||||
</button>
|
||||
<button
|
||||
aria-selected="false"
|
||||
class="ant-tabs-tab"
|
||||
role="tab"
|
||||
tabindex="0"
|
||||
type="button"
|
||||
>
|
||||
Rule
|
||||
</button>
|
||||
<div
|
||||
class="ant-tabs-ink-bar ant-tabs-ink-bar-animated"
|
||||
/>
|
||||
</div>
|
||||
</div>
|
||||
<div
|
||||
class="ant-tabs-nav-operations ant-tabs-nav-operations-hidden"
|
||||
>
|
||||
<button
|
||||
aria-controls="null-more-popup"
|
||||
aria-expanded="false"
|
||||
aria-haspopup="listbox"
|
||||
aria-hidden="true"
|
||||
class="ant-tabs-nav-more"
|
||||
id="null-more"
|
||||
style="visibility:hidden;order:1"
|
||||
tabindex="-1"
|
||||
type="button"
|
||||
>
|
||||
<span
|
||||
aria-label="ellipsis"
|
||||
class="anticon anticon-ellipsis"
|
||||
role="img"
|
||||
>
|
||||
<svg
|
||||
aria-hidden="true"
|
||||
class=""
|
||||
data-icon="ellipsis"
|
||||
fill="currentColor"
|
||||
focusable="false"
|
||||
height="1em"
|
||||
viewBox="64 64 896 896"
|
||||
width="1em"
|
||||
>
|
||||
<path
|
||||
d="M176 511a56 56 0 10112 0 56 56 0 10-112 0zm280 0a56 56 0 10112 0 56 56 0 10-112 0zm280 0a56 56 0 10112 0 56 56 0 10-112 0z"
|
||||
/>
|
||||
</svg>
|
||||
</span>
|
||||
</button>
|
||||
</div>
|
||||
</div>
|
||||
<div
|
||||
class="ant-tabs-content ant-tabs-content-animated ant-tabs-top-content"
|
||||
style="margin-left:0%"
|
||||
class="ant-tabs-content-holder"
|
||||
>
|
||||
<div
|
||||
aria-hidden="false"
|
||||
class="ant-tabs-tabpane ant-tabs-tabpane-active"
|
||||
role="tabpanel"
|
||||
style="visibility:visible"
|
||||
tabindex="0"
|
||||
/>
|
||||
<div
|
||||
aria-hidden="true"
|
||||
class="ant-tabs-tabpane ant-tabs-tabpane-inactive"
|
||||
role="tabpanel"
|
||||
style="visibility:hidden"
|
||||
tabindex="-1"
|
||||
/>
|
||||
class="ant-tabs-content ant-tabs-content-top"
|
||||
>
|
||||
<div
|
||||
aria-hidden="false"
|
||||
class="ant-tabs-tabpane ant-tabs-tabpane-active"
|
||||
role="tabpanel"
|
||||
tabindex="0"
|
||||
/>
|
||||
<div
|
||||
aria-hidden="true"
|
||||
class="ant-tabs-tabpane"
|
||||
role="tabpanel"
|
||||
style="display:none"
|
||||
tabindex="-1"
|
||||
/>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
@ -684,6 +684,7 @@
|
||||
@tabs-card-horizontal-padding: (@tabs-card-height - floor(@font-size-base * @line-height-base)) / 2 -
|
||||
@border-width-base @padding-md;
|
||||
@tabs-card-horizontal-padding-sm: 6px @padding-md;
|
||||
@tabs-card-horizontal-padding-lg: 7px @padding-md 6px;
|
||||
@tabs-title-font-size: @font-size-base;
|
||||
@tabs-title-font-size-lg: @font-size-lg;
|
||||
@tabs-title-font-size-sm: @font-size-base;
|
||||
|
@ -1,91 +0,0 @@
|
||||
import * as React from 'react';
|
||||
import ScrollableInkTabBar from 'rc-tabs/lib/ScrollableInkTabBar';
|
||||
import classNames from 'classnames';
|
||||
import UpOutlined from '@ant-design/icons/UpOutlined';
|
||||
import LeftOutlined from '@ant-design/icons/LeftOutlined';
|
||||
import DownOutlined from '@ant-design/icons/DownOutlined';
|
||||
import RightOutlined from '@ant-design/icons/RightOutlined';
|
||||
|
||||
import { TabsProps } from './index';
|
||||
import { ConfigConsumerProps, ConfigConsumer } from '../config-provider';
|
||||
import { cloneElement } from '../_util/reactNode';
|
||||
|
||||
export default class TabBar extends React.Component<TabsProps> {
|
||||
static defaultProps = {
|
||||
animated: true,
|
||||
type: 'line' as TabsProps['type'],
|
||||
};
|
||||
|
||||
renderTabBar = ({ direction }: ConfigConsumerProps) => {
|
||||
const {
|
||||
tabBarStyle,
|
||||
animated,
|
||||
renderTabBar,
|
||||
tabBarExtraContent,
|
||||
tabPosition,
|
||||
prefixCls,
|
||||
className,
|
||||
size,
|
||||
type,
|
||||
} = this.props;
|
||||
const inkBarAnimated = typeof animated === 'object' ? animated.inkBar : animated;
|
||||
|
||||
const isVertical = tabPosition === 'left' || tabPosition === 'right';
|
||||
let prevIconComponent = isVertical ? UpOutlined : LeftOutlined;
|
||||
let nextIconComponent = isVertical ? DownOutlined : RightOutlined;
|
||||
|
||||
if (direction === 'rtl' && !isVertical) {
|
||||
prevIconComponent = RightOutlined;
|
||||
nextIconComponent = LeftOutlined;
|
||||
}
|
||||
const prevIcon = (
|
||||
<span className={`${prefixCls}-tab-prev-icon`}>
|
||||
{React.createElement(prevIconComponent, {
|
||||
className: `${prefixCls}-tab-prev-icon-target`,
|
||||
})}
|
||||
</span>
|
||||
);
|
||||
const nextIcon = (
|
||||
<span className={`${prefixCls}-tab-next-icon`}>
|
||||
{React.createElement(nextIconComponent, {
|
||||
className: `${prefixCls}-tab-next-icon-target`,
|
||||
})}
|
||||
</span>
|
||||
);
|
||||
|
||||
// Additional className for style usage
|
||||
const cls: string = classNames(
|
||||
`${prefixCls}-${tabPosition}-bar`,
|
||||
{
|
||||
[`${prefixCls}-${size}-bar`]: !!size,
|
||||
[`${prefixCls}-card-bar`]: type && type.indexOf('card') >= 0,
|
||||
},
|
||||
className,
|
||||
);
|
||||
|
||||
const renderProps = {
|
||||
...this.props,
|
||||
children: null,
|
||||
inkBarAnimated,
|
||||
extraContent: tabBarExtraContent,
|
||||
style: tabBarStyle,
|
||||
prevIcon,
|
||||
nextIcon,
|
||||
className: cls,
|
||||
};
|
||||
|
||||
let RenderTabBar: React.ReactElement<any>;
|
||||
|
||||
if (renderTabBar) {
|
||||
RenderTabBar = renderTabBar(renderProps, ScrollableInkTabBar);
|
||||
} else {
|
||||
RenderTabBar = <ScrollableInkTabBar {...renderProps} />;
|
||||
}
|
||||
|
||||
return cloneElement(RenderTabBar);
|
||||
};
|
||||
|
||||
render() {
|
||||
return <ConfigConsumer>{this.renderTabBar}</ConfigConsumer>;
|
||||
}
|
||||
}
|
File diff suppressed because it is too large
Load Diff
@ -2,23 +2,24 @@
|
||||
|
||||
exports[`Tabs renderTabBar custom-tab-bar 1`] = `
|
||||
<div
|
||||
class="ant-tabs ant-tabs-top ant-tabs-line"
|
||||
class="ant-tabs ant-tabs-top"
|
||||
>
|
||||
<div>
|
||||
custom-tab-bar
|
||||
</div>
|
||||
<div
|
||||
class="ant-tabs-content ant-tabs-content-animated ant-tabs-top-content"
|
||||
style="margin-left:0%"
|
||||
class="ant-tabs-content-holder"
|
||||
>
|
||||
<div
|
||||
aria-hidden="false"
|
||||
class="ant-tabs-tabpane ant-tabs-tabpane-active"
|
||||
role="tabpanel"
|
||||
style="visibility:visible"
|
||||
tabindex="0"
|
||||
class="ant-tabs-content ant-tabs-content-top"
|
||||
>
|
||||
foo
|
||||
<div
|
||||
aria-hidden="true"
|
||||
class="ant-tabs-tabpane"
|
||||
role="tabpanel"
|
||||
style="display:none"
|
||||
tabindex="-1"
|
||||
/>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
@ -26,218 +27,153 @@ exports[`Tabs renderTabBar custom-tab-bar 1`] = `
|
||||
|
||||
exports[`Tabs rtl render component should be rendered correctly in RTL direction 1`] = `
|
||||
<div
|
||||
class="ant-tabs ant-tabs-top ant-tabs-line ant-tabs-rtl"
|
||||
class="ant-tabs ant-tabs-top ant-tabs-rtl"
|
||||
>
|
||||
<div
|
||||
class="ant-tabs-bar ant-tabs-top-bar"
|
||||
class="ant-tabs-nav"
|
||||
role="tablist"
|
||||
tabindex="-1"
|
||||
>
|
||||
<div
|
||||
class="ant-tabs-nav-container"
|
||||
class="ant-tabs-nav-wrap"
|
||||
>
|
||||
<span
|
||||
class="ant-tabs-tab-prev ant-tabs-tab-btn-disabled"
|
||||
unselectable="unselectable"
|
||||
>
|
||||
<span
|
||||
class="ant-tabs-tab-prev-icon"
|
||||
>
|
||||
<span
|
||||
aria-label="right"
|
||||
class="anticon anticon-right ant-tabs-tab-prev-icon-target"
|
||||
role="img"
|
||||
>
|
||||
<svg
|
||||
aria-hidden="true"
|
||||
class=""
|
||||
data-icon="right"
|
||||
fill="currentColor"
|
||||
focusable="false"
|
||||
height="1em"
|
||||
viewBox="64 64 896 896"
|
||||
width="1em"
|
||||
>
|
||||
<path
|
||||
d="M765.7 486.8L314.9 134.7A7.97 7.97 0 00302 141v77.3c0 4.9 2.3 9.6 6.1 12.6l360 281.1-360 281.1c-3.9 3-6.1 7.7-6.1 12.6V883c0 6.7 7.7 10.4 12.9 6.3l450.8-352.1a31.96 31.96 0 000-50.4z"
|
||||
/>
|
||||
</svg>
|
||||
</span>
|
||||
</span>
|
||||
</span>
|
||||
<span
|
||||
class="ant-tabs-tab-next ant-tabs-tab-btn-disabled"
|
||||
unselectable="unselectable"
|
||||
>
|
||||
<span
|
||||
class="ant-tabs-tab-next-icon"
|
||||
>
|
||||
<span
|
||||
aria-label="left"
|
||||
class="anticon anticon-left ant-tabs-tab-next-icon-target"
|
||||
role="img"
|
||||
>
|
||||
<svg
|
||||
aria-hidden="true"
|
||||
class=""
|
||||
data-icon="left"
|
||||
fill="currentColor"
|
||||
focusable="false"
|
||||
height="1em"
|
||||
viewBox="64 64 896 896"
|
||||
width="1em"
|
||||
>
|
||||
<path
|
||||
d="M724 218.3V141c0-6.7-7.7-10.4-12.9-6.3L260.3 486.8a31.86 31.86 0 000 50.3l450.8 352.1c5.3 4.1 12.9.4 12.9-6.3v-77.3c0-4.9-2.3-9.6-6.1-12.6l-360-281 360-281.1c3.8-3 6.1-7.7 6.1-12.6z"
|
||||
/>
|
||||
</svg>
|
||||
</span>
|
||||
</span>
|
||||
</span>
|
||||
<div
|
||||
class="ant-tabs-nav-wrap"
|
||||
class="ant-tabs-nav-list"
|
||||
style="transform:translate(0px, 0px)"
|
||||
>
|
||||
<div
|
||||
class="ant-tabs-nav-scroll"
|
||||
<button
|
||||
aria-selected="false"
|
||||
class="ant-tabs-tab"
|
||||
role="tab"
|
||||
tabindex="0"
|
||||
type="button"
|
||||
>
|
||||
<div
|
||||
class="ant-tabs-nav ant-tabs-nav-animated"
|
||||
>
|
||||
<div>
|
||||
<div
|
||||
aria-controls="tabpane-xx"
|
||||
aria-disabled="false"
|
||||
aria-selected="true"
|
||||
class="ant-tabs-tab-active ant-tabs-tab"
|
||||
id="tab-xx"
|
||||
role="tab"
|
||||
tabindex="0"
|
||||
>
|
||||
xx
|
||||
</div>
|
||||
</div>
|
||||
<div
|
||||
class="ant-tabs-ink-bar ant-tabs-ink-bar-animated"
|
||||
/>
|
||||
</div>
|
||||
</div>
|
||||
xx
|
||||
</button>
|
||||
<div
|
||||
class="ant-tabs-ink-bar ant-tabs-ink-bar-animated"
|
||||
/>
|
||||
</div>
|
||||
</div>
|
||||
<div
|
||||
class="ant-tabs-nav-operations ant-tabs-nav-operations-hidden"
|
||||
>
|
||||
<button
|
||||
aria-controls="null-more-popup"
|
||||
aria-expanded="false"
|
||||
aria-haspopup="listbox"
|
||||
aria-hidden="true"
|
||||
class="ant-tabs-nav-more"
|
||||
id="null-more"
|
||||
style="visibility:hidden;order:1"
|
||||
tabindex="-1"
|
||||
type="button"
|
||||
>
|
||||
<span
|
||||
aria-label="ellipsis"
|
||||
class="anticon anticon-ellipsis"
|
||||
role="img"
|
||||
>
|
||||
<svg
|
||||
aria-hidden="true"
|
||||
class=""
|
||||
data-icon="ellipsis"
|
||||
fill="currentColor"
|
||||
focusable="false"
|
||||
height="1em"
|
||||
viewBox="64 64 896 896"
|
||||
width="1em"
|
||||
>
|
||||
<path
|
||||
d="M176 511a56 56 0 10112 0 56 56 0 10-112 0zm280 0a56 56 0 10112 0 56 56 0 10-112 0zm280 0a56 56 0 10112 0 56 56 0 10-112 0z"
|
||||
/>
|
||||
</svg>
|
||||
</span>
|
||||
</button>
|
||||
</div>
|
||||
</div>
|
||||
<div
|
||||
class="ant-tabs-content ant-tabs-content-animated ant-tabs-top-content"
|
||||
style="margin-left:100%"
|
||||
class="ant-tabs-content-holder"
|
||||
>
|
||||
<div
|
||||
aria-hidden="false"
|
||||
class="ant-tabs-tabpane ant-tabs-tabpane-active"
|
||||
role="tabpanel"
|
||||
style="visibility:visible"
|
||||
tabindex="0"
|
||||
/>
|
||||
class="ant-tabs-content ant-tabs-content-top"
|
||||
>
|
||||
<div
|
||||
aria-hidden="true"
|
||||
class="ant-tabs-tabpane"
|
||||
role="tabpanel"
|
||||
style="display:none"
|
||||
tabindex="-1"
|
||||
/>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
`;
|
||||
|
||||
exports[`Tabs tabPosition remove card 1`] = `
|
||||
<div
|
||||
class="ant-tabs ant-tabs-left ant-tabs-vertical ant-tabs-line"
|
||||
class="ant-tabs ant-tabs-left"
|
||||
>
|
||||
<div
|
||||
class="ant-tabs-bar ant-tabs-left-bar"
|
||||
class="ant-tabs-nav"
|
||||
role="tablist"
|
||||
tabindex="-1"
|
||||
>
|
||||
<div
|
||||
class="ant-tabs-nav-container"
|
||||
class="ant-tabs-nav-wrap"
|
||||
>
|
||||
<span
|
||||
class="ant-tabs-tab-prev ant-tabs-tab-btn-disabled"
|
||||
unselectable="unselectable"
|
||||
>
|
||||
<span
|
||||
class="ant-tabs-tab-prev-icon"
|
||||
>
|
||||
<span
|
||||
aria-label="up"
|
||||
class="anticon anticon-up ant-tabs-tab-prev-icon-target"
|
||||
role="img"
|
||||
>
|
||||
<svg
|
||||
aria-hidden="true"
|
||||
class=""
|
||||
data-icon="up"
|
||||
fill="currentColor"
|
||||
focusable="false"
|
||||
height="1em"
|
||||
viewBox="64 64 896 896"
|
||||
width="1em"
|
||||
>
|
||||
<path
|
||||
d="M890.5 755.3L537.9 269.2c-12.8-17.6-39-17.6-51.7 0L133.5 755.3A8 8 0 00140 768h75c5.1 0 9.9-2.5 12.9-6.6L512 369.8l284.1 391.6c3 4.1 7.8 6.6 12.9 6.6h75c6.5 0 10.3-7.4 6.5-12.7z"
|
||||
/>
|
||||
</svg>
|
||||
</span>
|
||||
</span>
|
||||
</span>
|
||||
<span
|
||||
class="ant-tabs-tab-next ant-tabs-tab-btn-disabled"
|
||||
unselectable="unselectable"
|
||||
>
|
||||
<span
|
||||
class="ant-tabs-tab-next-icon"
|
||||
>
|
||||
<span
|
||||
aria-label="down"
|
||||
class="anticon anticon-down ant-tabs-tab-next-icon-target"
|
||||
role="img"
|
||||
>
|
||||
<svg
|
||||
aria-hidden="true"
|
||||
class=""
|
||||
data-icon="down"
|
||||
fill="currentColor"
|
||||
focusable="false"
|
||||
height="1em"
|
||||
viewBox="64 64 896 896"
|
||||
width="1em"
|
||||
>
|
||||
<path
|
||||
d="M884 256h-75c-5.1 0-9.9 2.5-12.9 6.6L512 654.2 227.9 262.6c-3-4.1-7.8-6.6-12.9-6.6h-75c-6.5 0-10.3 7.4-6.5 12.7l352.6 486.1c12.8 17.6 39 17.6 51.7 0l352.6-486.1c3.9-5.3.1-12.7-6.4-12.7z"
|
||||
/>
|
||||
</svg>
|
||||
</span>
|
||||
</span>
|
||||
</span>
|
||||
<div
|
||||
class="ant-tabs-nav-wrap"
|
||||
class="ant-tabs-nav-list"
|
||||
style="transform:translate(0px, 0px)"
|
||||
>
|
||||
<div
|
||||
class="ant-tabs-nav-scroll"
|
||||
<button
|
||||
aria-selected="false"
|
||||
class="ant-tabs-tab"
|
||||
role="tab"
|
||||
tabindex="0"
|
||||
type="button"
|
||||
>
|
||||
<div
|
||||
class="ant-tabs-nav ant-tabs-nav-animated"
|
||||
>
|
||||
<div>
|
||||
<div
|
||||
aria-controls="tabpane-1"
|
||||
aria-disabled="false"
|
||||
aria-selected="true"
|
||||
class="ant-tabs-tab-active ant-tabs-tab"
|
||||
id="tab-1"
|
||||
role="tab"
|
||||
tabindex="0"
|
||||
>
|
||||
foo
|
||||
</div>
|
||||
</div>
|
||||
<div
|
||||
class="ant-tabs-ink-bar ant-tabs-ink-bar-animated"
|
||||
/>
|
||||
</div>
|
||||
</div>
|
||||
foo
|
||||
</button>
|
||||
<div
|
||||
class="ant-tabs-ink-bar ant-tabs-ink-bar-animated"
|
||||
/>
|
||||
</div>
|
||||
</div>
|
||||
<div
|
||||
class="ant-tabs-nav-operations ant-tabs-nav-operations-hidden"
|
||||
>
|
||||
<button
|
||||
aria-controls="null-more-popup"
|
||||
aria-expanded="false"
|
||||
aria-haspopup="listbox"
|
||||
aria-hidden="true"
|
||||
class="ant-tabs-nav-more"
|
||||
id="null-more"
|
||||
style="visibility:hidden;order:1"
|
||||
tabindex="-1"
|
||||
type="button"
|
||||
>
|
||||
<span
|
||||
aria-label="ellipsis"
|
||||
class="anticon anticon-ellipsis"
|
||||
role="img"
|
||||
>
|
||||
<svg
|
||||
aria-hidden="true"
|
||||
class=""
|
||||
data-icon="ellipsis"
|
||||
fill="currentColor"
|
||||
focusable="false"
|
||||
height="1em"
|
||||
viewBox="64 64 896 896"
|
||||
width="1em"
|
||||
>
|
||||
<path
|
||||
d="M176 511a56 56 0 10112 0 56 56 0 10-112 0zm280 0a56 56 0 10112 0 56 56 0 10-112 0zm280 0a56 56 0 10112 0 56 56 0 10-112 0z"
|
||||
/>
|
||||
</svg>
|
||||
</span>
|
||||
</button>
|
||||
</div>
|
||||
<div
|
||||
class="ant-tabs-extra-content"
|
||||
>
|
||||
@ -245,17 +181,18 @@ exports[`Tabs tabPosition remove card 1`] = `
|
||||
</div>
|
||||
</div>
|
||||
<div
|
||||
class="ant-tabs-content ant-tabs-content-animated ant-tabs-left-content"
|
||||
style="margin-top:0%"
|
||||
class="ant-tabs-content-holder"
|
||||
>
|
||||
<div
|
||||
aria-hidden="false"
|
||||
class="ant-tabs-tabpane ant-tabs-tabpane-active"
|
||||
role="tabpanel"
|
||||
style="visibility:visible"
|
||||
tabindex="0"
|
||||
class="ant-tabs-content ant-tabs-content-left"
|
||||
>
|
||||
foo
|
||||
<div
|
||||
aria-hidden="true"
|
||||
class="ant-tabs-tabpane"
|
||||
role="tabpanel"
|
||||
style="display:none"
|
||||
tabindex="-1"
|
||||
/>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
@ -37,10 +37,7 @@ describe('Tabs', () => {
|
||||
});
|
||||
|
||||
it('add card', () => {
|
||||
wrapper
|
||||
.find('.ant-tabs-new-tab')
|
||||
.hostNodes()
|
||||
.simulate('click');
|
||||
wrapper.find('.ant-tabs-nav-add').first().simulate('click');
|
||||
expect(handleEdit.mock.calls[0][1]).toBe('add');
|
||||
});
|
||||
|
||||
@ -79,4 +76,13 @@ describe('Tabs', () => {
|
||||
expect(wrapper).toMatchSnapshot();
|
||||
});
|
||||
});
|
||||
|
||||
it('warning for onNextClick', () => {
|
||||
const errorSpy = jest.spyOn(console, 'error').mockImplementation(() => {});
|
||||
mount(<Tabs onNextClick={() => {}} />);
|
||||
expect(errorSpy).toHaveBeenCalledWith(
|
||||
'Warning: [antd: Tabs] `onPrevClick` and `onNextClick` has been removed. Please use `onTabScroll` instead.',
|
||||
);
|
||||
errorSpy.mockRestore();
|
||||
});
|
||||
});
|
||||
|
@ -22,7 +22,7 @@ function callback(key) {
|
||||
console.log(key);
|
||||
}
|
||||
|
||||
ReactDOM.render(
|
||||
const Demo = () => (
|
||||
<Tabs defaultActiveKey="1" onChange={callback}>
|
||||
<TabPane tab="Tab 1" key="1">
|
||||
Content of Tab Pane 1
|
||||
@ -33,7 +33,8 @@ ReactDOM.render(
|
||||
<TabPane tab="Tab 3" key="3">
|
||||
Content of Tab Pane 3
|
||||
</TabPane>
|
||||
</Tabs>,
|
||||
mountNode,
|
||||
</Tabs>
|
||||
);
|
||||
|
||||
ReactDOM.render(<Demo />, mountNode);
|
||||
```
|
||||
|
@ -46,34 +46,22 @@ ReactDOM.render(
|
||||
.card-container p {
|
||||
margin: 0;
|
||||
}
|
||||
.card-container > .ant-tabs-card > .ant-tabs-content {
|
||||
.card-container > .ant-tabs-card .ant-tabs-content {
|
||||
height: 120px;
|
||||
margin-top: -16px;
|
||||
}
|
||||
[data-theme='compact'] .card-container > .ant-tabs-card > .ant-tabs-content {
|
||||
height: 120px;
|
||||
margin-top: -8px;
|
||||
}
|
||||
|
||||
[data-theme='compact'] .card-container > .ant-tabs-card > .ant-tabs-content > .ant-tabs-tabpane,
|
||||
.card-container > .ant-tabs-card > .ant-tabs-content > .ant-tabs-tabpane {
|
||||
.card-container > .ant-tabs-card .ant-tabs-content > .ant-tabs-tabpane {
|
||||
background: #fff;
|
||||
padding: 16px;
|
||||
}
|
||||
|
||||
[data-theme='compact'] .card-container > .ant-tabs-card > .ant-tabs-bar,
|
||||
.card-container > .ant-tabs-card > .ant-tabs-bar {
|
||||
border-color: #fff;
|
||||
.card-container > .ant-tabs-card > .ant-tabs-nav::before {
|
||||
display: none;
|
||||
}
|
||||
|
||||
[data-theme='compact'] .card-container > .ant-tabs-card > .ant-tabs-bar .ant-tabs-tab,
|
||||
.card-container > .ant-tabs-card > .ant-tabs-bar .ant-tabs-tab {
|
||||
.card-container > .ant-tabs-card .ant-tabs-tab {
|
||||
border-color: transparent;
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
[data-theme='compact'] .card-container > .ant-tabs-card > .ant-tabs-bar .ant-tabs-tab-active,
|
||||
.card-container > .ant-tabs-card > .ant-tabs-bar .ant-tabs-tab-active {
|
||||
.card-container > .ant-tabs-card .ant-tabs-tab-active {
|
||||
border-color: #fff;
|
||||
background: #fff;
|
||||
}
|
||||
@ -85,21 +73,21 @@ ReactDOM.render(
|
||||
overflow: hidden;
|
||||
padding: 24px;
|
||||
}
|
||||
|
||||
[data-theme="dark"] .card-container > .ant-tabs-card > .ant-tabs-bar .ant-tabs-tab {
|
||||
[data-theme='compact'] .card-container > .ant-tabs-card .ant-tabs-content {
|
||||
height: 120px;
|
||||
margin-top: -8px;
|
||||
}
|
||||
[data-theme="dark"] .card-container > .ant-tabs-card .ant-tabs-tab {
|
||||
border-color: transparent;
|
||||
background: transparent;
|
||||
}
|
||||
[data-theme="dark"] #components-tabs-demo-card-top .code-box-demo {
|
||||
background: #000;
|
||||
}
|
||||
[data-theme="dark"] .card-container > .ant-tabs-card > .ant-tabs-content > .ant-tabs-tabpane {
|
||||
[data-theme="dark"] .card-container > .ant-tabs-card .ant-tabs-content > .ant-tabs-tabpane {
|
||||
background: #141414;
|
||||
}
|
||||
[data-theme="dark"] .card-container > .ant-tabs-card > .ant-tabs-bar {
|
||||
border-color: #141414;
|
||||
}
|
||||
[data-theme="dark"] .card-container > .ant-tabs-card > .ant-tabs-bar .ant-tabs-tab-active {
|
||||
[data-theme="dark"] .card-container > .ant-tabs-card .ant-tabs-tab-active {
|
||||
border-color: #141414;
|
||||
background: #141414;
|
||||
}
|
||||
|
@ -41,7 +41,7 @@ class SlidingTabsDemo extends React.Component {
|
||||
</Radio.Group>
|
||||
<Tabs defaultActiveKey="1" tabPosition={mode} style={{ height: 220 }}>
|
||||
{[...Array(30).keys()].map(i => (
|
||||
<TabPane tab={`Tab-${i}`} key={i}>
|
||||
<TabPane tab={`Tab-${i}`} key={i} disabled={i === 28}>
|
||||
Content of tab {i}
|
||||
</TabPane>
|
||||
))}
|
||||
|
@ -19,25 +19,24 @@ Ant Design has 3 types of Tabs for different situations.
|
||||
|
||||
### Tabs
|
||||
|
||||
| Property | Description | Type | Default |
|
||||
| --- | --- | --- | --- |
|
||||
| activeKey | Current TabPane's key | string | - |
|
||||
| animated | Whether to change tabs with animation. Only works while `tabPosition="top"\|"bottom"` | boolean \| {inkBar:boolean, tabPane:boolean} | `true`, `false` when `type="card"` |
|
||||
| renderTabBar | replace the TabBar | (props: DefaultTabBarProps, DefaultTabBar: React.ComponentClass) => React.ReactElement | - |
|
||||
| defaultActiveKey | Initial active TabPane's key, if `activeKey` is not set. | string | - |
|
||||
| hideAdd | Hide plus icon or not. Only works while `type="editable-card"` | boolean | `false` |
|
||||
| size | preset tab bar size | `large` \| `default` \| `small` | `default` |
|
||||
| tabBarExtraContent | Extra content in tab bar | React.ReactNode | - |
|
||||
| tabBarGutter | The gap between tabs | number | - |
|
||||
| tabBarStyle | Tab bar style object | object | - |
|
||||
| tabPosition | Position of tabs | `top` \| `right` \| `bottom` \| `left` | `top` |
|
||||
| type | Basic style of tabs | `line` \| `card` \| `editable-card` | `line` |
|
||||
| onChange | Callback executed when active tab is changed | Function(activeKey) {} | - |
|
||||
| onEdit | Callback executed when tab is added or removed. Only works while `type="editable-card"` | (targetKey, action): void | - |
|
||||
| onNextClick | Callback executed when next button is clicked | Function | - |
|
||||
| onPrevClick | Callback executed when prev button is clicked | Function | - |
|
||||
| onTabClick | Callback executed when tab is clicked | Function(key: string, event: MouseEvent) | - |
|
||||
| keyboard | whether to turn on keyboard navigation | boolean | true |
|
||||
| Property | Description | Type | Default | Version |
|
||||
| --- | --- | --- | --- | --- |
|
||||
| activeKey | Current TabPane's key | string | - | |
|
||||
| animated | Whether to change tabs with animation. Only works while `tabPosition="top"\|"bottom"` | boolean \| {inkBar:boolean, tabPane:boolean} | `true`, `false` when `type="card"` | |
|
||||
| renderTabBar | replace the TabBar | (props: DefaultTabBarProps, DefaultTabBar: React.ComponentClass) => React.ReactElement | - | |
|
||||
| defaultActiveKey | Initial active TabPane's key, if `activeKey` is not set. | string | - | |
|
||||
| hideAdd | Hide plus icon or not. Only works while `type="editable-card"` | boolean | `false` | |
|
||||
| size | preset tab bar size | `large` \| `default` \| `small` | `default` | |
|
||||
| tabBarExtraContent | Extra content in tab bar | React.ReactNode | - | |
|
||||
| tabBarGutter | The gap between tabs | number | - | |
|
||||
| tabBarStyle | Tab bar style object | object | - | |
|
||||
| tabPosition | Position of tabs | `top` \| `right` \| `bottom` \| `left` | `top` | |
|
||||
| type | Basic style of tabs | `line` \| `card` \| `editable-card` | `line` | |
|
||||
| onChange | Callback executed when active tab is changed | Function(activeKey) {} | - | |
|
||||
| onEdit | Callback executed when tab is added or removed. Only works while `type="editable-card"` | (targetKey, action): void | - | |
|
||||
| onTabClick | Callback executed when tab is clicked | Function(key: string, event: MouseEvent) | - | |
|
||||
| onTabScroll | Trigger when tab scroll | Function({ direction: 'left' \| 'right' \| 'top' \| 'bottom' }) | - | 4.3.0 |
|
||||
| keyboard | whether to turn on keyboard navigation | boolean | true | |
|
||||
|
||||
More option at [rc-tabs option](https://github.com/react-component/tabs#tabs)
|
||||
|
||||
|
@ -1,205 +1,65 @@
|
||||
import * as React from 'react';
|
||||
import * as ReactDOM from 'react-dom';
|
||||
import RcTabs, { TabPane } from 'rc-tabs';
|
||||
import TabContent from 'rc-tabs/lib/TabContent';
|
||||
import RcTabs, { TabPane, TabsProps as RcTabsProps } from 'rc-tabs';
|
||||
import { EditableConfig } from 'rc-tabs/lib/interface';
|
||||
import classNames from 'classnames';
|
||||
import omit from 'omit.js';
|
||||
import CloseOutlined from '@ant-design/icons/CloseOutlined';
|
||||
import EllipsisOutlined from '@ant-design/icons/EllipsisOutlined';
|
||||
import PlusOutlined from '@ant-design/icons/PlusOutlined';
|
||||
import TabBar from './TabBar';
|
||||
import CloseOutlined from '@ant-design/icons/CloseOutlined';
|
||||
|
||||
import { ConfigConsumer, ConfigConsumerProps } from '../config-provider';
|
||||
import { isFlexSupported } from '../_util/styleChecker';
|
||||
import { cloneElement, isValidElement } from '../_util/reactNode';
|
||||
import devWarning from '../_util/devWarning';
|
||||
import { ConfigContext } from '../config-provider';
|
||||
import { SizeType } from '../config-provider/SizeContext';
|
||||
|
||||
export type TabsType = 'line' | 'card' | 'editable-card';
|
||||
export type TabsPosition = 'top' | 'right' | 'bottom' | 'left';
|
||||
|
||||
export interface TabsProps {
|
||||
activeKey?: string;
|
||||
defaultActiveKey?: string;
|
||||
hideAdd?: boolean;
|
||||
onChange?: (activeKey: string) => void;
|
||||
onTabClick?: Function;
|
||||
onPrevClick?: React.MouseEventHandler<HTMLElement>;
|
||||
onNextClick?: React.MouseEventHandler<HTMLElement>;
|
||||
tabBarExtraContent?: React.ReactNode | null;
|
||||
tabBarStyle?: React.CSSProperties;
|
||||
export interface TabsProps extends Omit<RcTabsProps, 'editable'> {
|
||||
type?: TabsType;
|
||||
tabPosition?: TabsPosition;
|
||||
onEdit?: (targetKey: string | React.MouseEvent<HTMLElement>, action: 'add' | 'remove') => void;
|
||||
size?: 'large' | 'default' | 'small';
|
||||
style?: React.CSSProperties;
|
||||
prefixCls?: string;
|
||||
className?: string;
|
||||
animated?: boolean | { inkBar: boolean; tabPane: boolean };
|
||||
tabBarGutter?: number;
|
||||
renderTabBar?: (
|
||||
props: TabsProps,
|
||||
DefaultTabBar: React.ComponentClass<any>,
|
||||
) => React.ReactElement<any>;
|
||||
destroyInactiveTabPane?: boolean;
|
||||
keyboard?: boolean;
|
||||
size?: SizeType;
|
||||
hideAdd?: boolean;
|
||||
onEdit?: (e: React.MouseEvent | React.KeyboardEvent | string, action: 'add' | 'remove') => void;
|
||||
}
|
||||
|
||||
// Tabs
|
||||
export interface TabPaneProps {
|
||||
/** 选项卡头显示文字 */
|
||||
tab?: React.ReactNode | string;
|
||||
style?: React.CSSProperties;
|
||||
closable?: boolean;
|
||||
className?: string;
|
||||
disabled?: boolean;
|
||||
forceRender?: boolean;
|
||||
key?: string;
|
||||
closeIcon?: React.ReactNode;
|
||||
}
|
||||
function Tabs({ type, className, size, onEdit, hideAdd, ...props }: TabsProps) {
|
||||
const { prefixCls: customizePrefixCls } = props;
|
||||
const { getPrefixCls, direction } = React.useContext(ConfigContext);
|
||||
const prefixCls = getPrefixCls('tabs', customizePrefixCls);
|
||||
|
||||
export default class Tabs extends React.Component<TabsProps, any> {
|
||||
static TabPane = TabPane as React.ClassicComponentClass<TabPaneProps>;
|
||||
|
||||
static defaultProps = {
|
||||
hideAdd: false,
|
||||
tabPosition: 'top' as TabsPosition,
|
||||
};
|
||||
|
||||
componentDidMount() {
|
||||
const NO_FLEX = ' no-flex';
|
||||
const tabNode = ReactDOM.findDOMNode(this) as Element;
|
||||
if (tabNode && !isFlexSupported && tabNode.className.indexOf(NO_FLEX) === -1) {
|
||||
tabNode.className += NO_FLEX;
|
||||
}
|
||||
let editable: EditableConfig | undefined;
|
||||
if (type === 'editable-card') {
|
||||
editable = {
|
||||
onEdit: (editType, { key, event }) => {
|
||||
onEdit?.(editType === 'add' ? event : key!, editType);
|
||||
},
|
||||
removeIcon: <CloseOutlined />,
|
||||
addIcon: <PlusOutlined />,
|
||||
showAdd: hideAdd !== false,
|
||||
};
|
||||
}
|
||||
|
||||
removeTab = (targetKey: string, e: React.MouseEvent<HTMLElement>) => {
|
||||
e.stopPropagation();
|
||||
if (!targetKey) {
|
||||
return;
|
||||
}
|
||||
devWarning(
|
||||
!('onPrevClick' in props) && !('onNextClick' in props),
|
||||
'Tabs',
|
||||
'`onPrevClick` and `onNextClick` has been removed. Please use `onTabScroll` instead.',
|
||||
);
|
||||
|
||||
const { onEdit } = this.props;
|
||||
if (onEdit) {
|
||||
onEdit(targetKey, 'remove');
|
||||
}
|
||||
};
|
||||
|
||||
handleChange = (activeKey: string) => {
|
||||
const { onChange } = this.props;
|
||||
if (onChange) {
|
||||
onChange(activeKey);
|
||||
}
|
||||
};
|
||||
|
||||
createNewTab = (targetKey: React.MouseEvent<HTMLElement>) => {
|
||||
const { onEdit } = this.props;
|
||||
if (onEdit) {
|
||||
onEdit(targetKey, 'add');
|
||||
}
|
||||
};
|
||||
|
||||
renderTabs = ({ getPrefixCls, direction }: ConfigConsumerProps) => {
|
||||
const {
|
||||
prefixCls: customizePrefixCls,
|
||||
className = '',
|
||||
size,
|
||||
type = 'line',
|
||||
tabPosition,
|
||||
children,
|
||||
animated = true,
|
||||
hideAdd,
|
||||
} = this.props;
|
||||
let { tabBarExtraContent } = this.props;
|
||||
|
||||
let tabPaneAnimated = typeof animated === 'object' ? animated.tabPane : animated;
|
||||
|
||||
// card tabs should not have animation
|
||||
if (type !== 'line') {
|
||||
tabPaneAnimated = 'animated' in this.props ? tabPaneAnimated : false;
|
||||
}
|
||||
|
||||
const prefixCls = getPrefixCls('tabs', customizePrefixCls);
|
||||
const cls = classNames(className, {
|
||||
[`${prefixCls}-vertical`]: tabPosition === 'left' || tabPosition === 'right',
|
||||
[`${prefixCls}-${size}`]: !!size,
|
||||
[`${prefixCls}-card`]: type.indexOf('card') >= 0,
|
||||
[`${prefixCls}-${type}`]: true,
|
||||
[`${prefixCls}-no-animation`]: !tabPaneAnimated,
|
||||
});
|
||||
// only card type tabs can be added and closed
|
||||
let childrenWithClose: React.ReactElement<any>[] = [];
|
||||
if (type === 'editable-card') {
|
||||
childrenWithClose = [];
|
||||
React.Children.forEach(children as React.ReactNode, (child, index) => {
|
||||
if (!isValidElement(child)) return child;
|
||||
let { closable } = child.props;
|
||||
const { closeIcon: customCloseIcon } = child.props;
|
||||
closable = typeof closable === 'undefined' ? true : closable;
|
||||
const customIcon = customCloseIcon ? (
|
||||
React.cloneElement(customCloseIcon, {
|
||||
className: `${prefixCls}-close-x`,
|
||||
onClick: e => this.removeTab(child.key as string, e),
|
||||
})
|
||||
) : (
|
||||
<CloseOutlined
|
||||
className={`${prefixCls}-close-x`}
|
||||
onClick={e => this.removeTab(child.key as string, e)}
|
||||
/>
|
||||
);
|
||||
const closeIcon = closable ? customIcon : null;
|
||||
childrenWithClose.push(
|
||||
cloneElement(child, {
|
||||
tab: (
|
||||
<div className={closable ? undefined : `${prefixCls}-tab-unclosable`}>
|
||||
{child.props.tab}
|
||||
{closeIcon}
|
||||
</div>
|
||||
),
|
||||
key: child.key || index,
|
||||
}),
|
||||
);
|
||||
});
|
||||
// Add new tab handler
|
||||
if (!hideAdd) {
|
||||
tabBarExtraContent = (
|
||||
<span>
|
||||
<PlusOutlined className={`${prefixCls}-new-tab`} onClick={this.createNewTab} />
|
||||
{tabBarExtraContent}
|
||||
</span>
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
tabBarExtraContent = tabBarExtraContent ? (
|
||||
<div className={`${prefixCls}-extra-content`}>{tabBarExtraContent}</div>
|
||||
) : null;
|
||||
|
||||
const { ...tabBarProps } = this.props;
|
||||
const contentCls: string = classNames(
|
||||
`${prefixCls}-${tabPosition}-content`,
|
||||
type.indexOf('card') >= 0 && `${prefixCls}-card-content`,
|
||||
);
|
||||
|
||||
return (
|
||||
<RcTabs
|
||||
{...this.props}
|
||||
prefixCls={prefixCls}
|
||||
className={cls}
|
||||
tabBarPosition={tabPosition}
|
||||
direction={direction}
|
||||
renderTabBar={() => (
|
||||
<TabBar {...omit(tabBarProps, ['className'])} tabBarExtraContent={tabBarExtraContent} />
|
||||
)}
|
||||
renderTabContent={() => (
|
||||
<TabContent className={contentCls} animated={tabPaneAnimated} animatedWithMargin />
|
||||
)}
|
||||
onChange={this.handleChange}
|
||||
>
|
||||
{childrenWithClose.length > 0 ? childrenWithClose : children}
|
||||
</RcTabs>
|
||||
);
|
||||
};
|
||||
|
||||
render() {
|
||||
return <ConfigConsumer>{this.renderTabs}</ConfigConsumer>;
|
||||
}
|
||||
return (
|
||||
<RcTabs
|
||||
direction={direction}
|
||||
{...props}
|
||||
moreTransitionName="slide-up"
|
||||
className={classNames(className, {
|
||||
[`${prefixCls}-${size}`]: size,
|
||||
[`${prefixCls}-card`]: ['card', 'editable-card'].includes(type as string),
|
||||
[`${prefixCls}-editable-card`]: type === 'editable-card',
|
||||
})}
|
||||
editable={editable}
|
||||
moreIcon={<EllipsisOutlined />}
|
||||
prefixCls={prefixCls}
|
||||
/>
|
||||
);
|
||||
}
|
||||
|
||||
Tabs.TabPane = TabPane;
|
||||
|
||||
export default Tabs;
|
||||
|
@ -22,25 +22,24 @@ Ant Design 依次提供了三级选项卡,分别用于不同的场景。
|
||||
|
||||
### Tabs
|
||||
|
||||
| 参数 | 说明 | 类型 | 默认值 |
|
||||
| --- | --- | --- | --- |
|
||||
| activeKey | 当前激活 tab 面板的 key | string | 无 |
|
||||
| animated | 是否使用动画切换 Tabs,在 `tabPosition=top|bottom` 时有效 | boolean \| {inkBar:boolean, tabPane:boolean} | true, 当 type="card" 时为 false |
|
||||
| renderTabBar | 替换 TabBar,用于二次封装标签头 | (props: DefaultTabBarProps, DefaultTabBar: React.ComponentClass) => React.ReactElement | 无 |
|
||||
| defaultActiveKey | 初始化选中面板的 key,如果没有设置 activeKey | string | 第一个面板 |
|
||||
| hideAdd | 是否隐藏加号图标,在 `type="editable-card"` 时有效 | boolean | false |
|
||||
| size | 大小,提供 `large` `default` 和 `small` 三种大小 | string | 'default' |
|
||||
| tabBarExtraContent | tab bar 上额外的元素 | React.ReactNode | 无 |
|
||||
| tabBarGutter | tabs 之间的间隙 | number | 无 |
|
||||
| tabBarStyle | tab bar 的样式对象 | object | - |
|
||||
| tabPosition | 页签位置,可选值有 `top` `right` `bottom` `left` | string | 'top' |
|
||||
| type | 页签的基本样式,可选 `line`、`card` `editable-card` 类型 | string | 'line' |
|
||||
| onChange | 切换面板的回调 | Function(activeKey) {} | 无 |
|
||||
| onEdit | 新增和删除页签的回调,在 `type="editable-card"` 时有效 | (targetKey, action): void | 无 |
|
||||
| onNextClick | next 按钮被点击的回调 | Function | 无 |
|
||||
| onPrevClick | prev 按钮被点击的回调 | Function | 无 |
|
||||
| onTabClick | tab 被点击的回调 | Function(key: string, event: MouseEvent) | 无 |
|
||||
| keyboard | 开启键盘切换功能 | boolean | true |
|
||||
| 参数 | 说明 | 类型 | 默认值 | 版本 |
|
||||
| --- | --- | --- | --- | --- |
|
||||
| activeKey | 当前激活 tab 面板的 key | string | - | |
|
||||
| animated | 是否使用动画切换 Tabs,在 `tabPosition=top|bottom` 时有效 | boolean \| {inkBar:boolean, tabPane:boolean} | true, 当 type="card" 时为 false | |
|
||||
| renderTabBar | 替换 TabBar,用于二次封装标签头 | (props: DefaultTabBarProps, DefaultTabBar: React.ComponentClass) => React.ReactElement | - | |
|
||||
| defaultActiveKey | 初始化选中面板的 key,如果没有设置 activeKey | string | 第一个面板 | |
|
||||
| hideAdd | 是否隐藏加号图标,在 `type="editable-card"` 时有效 | boolean | false | |
|
||||
| size | 大小,提供 `large` `default` 和 `small` 三种大小 | string | 'default' | |
|
||||
| tabBarExtraContent | tab bar 上额外的元素 | React.ReactNode | - | |
|
||||
| tabBarGutter | tabs 之间的间隙 | number | - | |
|
||||
| tabBarStyle | tab bar 的样式对象 | object | - | |
|
||||
| tabPosition | 页签位置,可选值有 `top` `right` `bottom` `left` | string | 'top' | |
|
||||
| type | 页签的基本样式,可选 `line`、`card` `editable-card` 类型 | string | 'line' | |
|
||||
| onChange | 切换面板的回调 | Function(activeKey) {} | - | |
|
||||
| onEdit | 新增和删除页签的回调,在 `type="editable-card"` 时有效 | (targetKey, action): void | - | |
|
||||
| onTabClick | tab 被点击的回调 | Function(key: string, event: MouseEvent) | - | |
|
||||
| onTabScroll | tab 滚动时触发 | Function({ direction: 'left' \| 'right' \| 'top' \| 'bottom' }) | - | 4.3.0 |
|
||||
| keyboard | 开启键盘切换功能 | boolean | true | |
|
||||
|
||||
### Tabs.TabPane
|
||||
|
||||
|
@ -1,181 +0,0 @@
|
||||
@import '../../style/themes/index';
|
||||
@import '../../style/mixins/index';
|
||||
|
||||
@tab-prefix-cls: ~'@{ant-prefix}-tabs';
|
||||
|
||||
// card style
|
||||
.@{tab-prefix-cls} {
|
||||
&&-card &-card-bar &-ink-bar {
|
||||
visibility: hidden;
|
||||
}
|
||||
&&-card &-card-bar &-tab {
|
||||
margin: 0;
|
||||
margin-right: @tabs-card-gutter;
|
||||
padding: @tabs-card-horizontal-padding;
|
||||
line-height: 22px;
|
||||
background: @tabs-card-head-background;
|
||||
border: @border-width-base @border-style-base @border-color-split;
|
||||
border-radius: @border-radius-base @border-radius-base 0 0;
|
||||
transition: all 0.3s @ease-in-out;
|
||||
}
|
||||
&&-card &-card-bar &-tab-active {
|
||||
color: @tabs-card-active-color;
|
||||
background: @component-background;
|
||||
border-color: @border-color-split;
|
||||
border-bottom: @border-width-base solid @component-background;
|
||||
|
||||
&::before {
|
||||
border-top: @tabs-card-tab-active-border-top;
|
||||
}
|
||||
}
|
||||
&&-small &-card-bar &-tab {
|
||||
padding: @tabs-card-horizontal-padding-sm;
|
||||
}
|
||||
&&-card &-card-bar &-tab-disabled {
|
||||
color: @disabled-color;
|
||||
}
|
||||
&&-card &-card-bar &-tab-inactive {
|
||||
padding: 0;
|
||||
}
|
||||
&&-card &-card-bar &-nav-wrap {
|
||||
margin-bottom: 0;
|
||||
}
|
||||
&&-card &-card-bar &-tab &-close-x {
|
||||
width: 16px;
|
||||
height: @font-size-base;
|
||||
margin-right: -5px;
|
||||
margin-left: 3px;
|
||||
overflow: hidden;
|
||||
color: @text-color-secondary;
|
||||
font-size: @font-size-sm;
|
||||
vertical-align: middle;
|
||||
transition: all 0.3s;
|
||||
&:hover {
|
||||
color: @heading-color;
|
||||
}
|
||||
}
|
||||
|
||||
&&-card &-card-content > &-tabpane,
|
||||
&&-editable-card &-card-content > &-tabpane {
|
||||
transition: none !important;
|
||||
&-inactive {
|
||||
overflow: hidden;
|
||||
}
|
||||
}
|
||||
|
||||
&&-card &-card-bar &-tab:hover .@{iconfont-css-prefix}-close {
|
||||
opacity: 1;
|
||||
}
|
||||
|
||||
&-extra-content {
|
||||
line-height: @tabs-title-font-size * @line-height-base + extract(@tabs-horizontal-padding, 1) *
|
||||
2;
|
||||
|
||||
.@{tab-prefix-cls}-new-tab {
|
||||
position: relative;
|
||||
width: 20px;
|
||||
height: 20px;
|
||||
color: @text-color;
|
||||
font-size: 12px;
|
||||
line-height: 20px;
|
||||
text-align: center;
|
||||
border: @border-width-base @border-style-base @border-color-split;
|
||||
border-radius: @border-radius-base;
|
||||
cursor: pointer;
|
||||
transition: all 0.3s;
|
||||
&:hover {
|
||||
color: @tabs-card-active-color;
|
||||
border-color: @tabs-card-active-color;
|
||||
}
|
||||
svg {
|
||||
position: absolute;
|
||||
top: 0;
|
||||
right: 0;
|
||||
bottom: 0;
|
||||
left: 0;
|
||||
margin: auto;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// https://github.com/ant-design/ant-design/issues/17865
|
||||
&&-large &-extra-content {
|
||||
line-height: @tabs-title-font-size-lg * @line-height-base +
|
||||
extract(@tabs-horizontal-padding-lg, 1) * 2;
|
||||
}
|
||||
|
||||
// https://github.com/ant-design/ant-design/issues/17865
|
||||
&&-small &-extra-content {
|
||||
line-height: @tabs-title-font-size-sm * @line-height-base +
|
||||
extract(@tabs-horizontal-padding-sm, 1) * 2;
|
||||
}
|
||||
|
||||
// https://github.com/ant-design/ant-design/issues/17865
|
||||
&&-card &-extra-content {
|
||||
line-height: @tabs-card-height;
|
||||
}
|
||||
|
||||
// https://github.com/ant-design/ant-design/issues/4669
|
||||
&-vertical&-card &-card-bar&-left-bar,
|
||||
&-vertical&-card &-card-bar&-right-bar {
|
||||
.@{tab-prefix-cls}-nav-container {
|
||||
height: 100%;
|
||||
}
|
||||
.@{tab-prefix-cls}-tab {
|
||||
margin-bottom: @margin-sm;
|
||||
border-bottom: @border-width-base @border-style-base @border-color-split;
|
||||
&-active {
|
||||
padding-bottom: 4px;
|
||||
}
|
||||
&:last-child {
|
||||
margin-bottom: @margin-sm;
|
||||
}
|
||||
}
|
||||
.@{tab-prefix-cls}-new-tab {
|
||||
width: 90%;
|
||||
}
|
||||
}
|
||||
|
||||
&-vertical&-card&-left &-card-bar&-left-bar {
|
||||
.@{tab-prefix-cls}-nav-wrap {
|
||||
margin-right: 0;
|
||||
}
|
||||
.@{tab-prefix-cls}-tab {
|
||||
margin-right: 1px;
|
||||
border-right: 0;
|
||||
border-radius: @border-radius-base 0 0 @border-radius-base;
|
||||
&-active {
|
||||
margin-right: -1px;
|
||||
padding-right: @padding-md + 2px;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
&-vertical&-card&-right &-card-bar&-right-bar {
|
||||
.@{tab-prefix-cls}-nav-wrap {
|
||||
margin-left: 0;
|
||||
}
|
||||
.@{tab-prefix-cls}-tab {
|
||||
margin-left: 1px;
|
||||
border-left: 0;
|
||||
border-radius: 0 @border-radius-base @border-radius-base 0;
|
||||
&-active {
|
||||
margin-left: -1px;
|
||||
padding-left: @padding-md + 2px;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// https://github.com/ant-design/ant-design/issues/9104
|
||||
& &-card-bar&-bottom-bar &-tab {
|
||||
height: auto;
|
||||
border-top-color: @border-color-split;
|
||||
border-bottom: @border-width-base @border-style-base @border-color-split;
|
||||
border-radius: 0 0 @border-radius-base @border-radius-base;
|
||||
}
|
||||
|
||||
& &-card-bar&-bottom-bar &-tab-active {
|
||||
color: @primary-color;
|
||||
border-top-color: @component-background;
|
||||
}
|
||||
}
|
90
components/tabs/style/card.less
Normal file
90
components/tabs/style/card.less
Normal file
@ -0,0 +1,90 @@
|
||||
@import '../../style/themes/index';
|
||||
@import '../../style/mixins/index';
|
||||
@import './index';
|
||||
|
||||
.@{tab-prefix-cls}-card {
|
||||
> .@{tab-prefix-cls}-nav {
|
||||
.@{tab-prefix-cls}-tab {
|
||||
margin: 0;
|
||||
padding: @tabs-card-horizontal-padding;
|
||||
background: @tabs-card-head-background;
|
||||
border: @border-width-base @border-style-base @border-color-split;
|
||||
transition: all @animation-duration-slow @ease-in-out;
|
||||
|
||||
&-active {
|
||||
color: @tabs-card-active-color;
|
||||
background: @component-background;
|
||||
}
|
||||
}
|
||||
|
||||
.@{tab-prefix-cls}-ink-bar {
|
||||
visibility: hidden;
|
||||
}
|
||||
}
|
||||
|
||||
// ========================== Top & Bottom ==========================
|
||||
&.@{tab-prefix-cls}-top,
|
||||
&.@{tab-prefix-cls}-bottom {
|
||||
> .@{tab-prefix-cls}-nav {
|
||||
.@{tab-prefix-cls}-tab:not(:last-of-type) {
|
||||
margin-right: @tabs-card-gutter;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
&.@{tab-prefix-cls}-top {
|
||||
> .@{tab-prefix-cls}-nav {
|
||||
.@{tab-prefix-cls}-tab {
|
||||
border-radius: @border-radius-base @border-radius-base 0 0;
|
||||
|
||||
&-active {
|
||||
border-bottom-color: @component-background;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
&.@{tab-prefix-cls}-bottom {
|
||||
> .@{tab-prefix-cls}-nav {
|
||||
.@{tab-prefix-cls}-tab {
|
||||
border-radius: 0 0 @border-radius-base @border-radius-base;
|
||||
|
||||
&-active {
|
||||
border-top-color: @component-background;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// ========================== Left & Right ==========================
|
||||
&.@{tab-prefix-cls}-left,
|
||||
&.@{tab-prefix-cls}-right {
|
||||
> .@{tab-prefix-cls}-nav {
|
||||
.@{tab-prefix-cls}-tab:not(:last-of-type) {
|
||||
margin-bottom: @tabs-card-gutter;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
&.@{tab-prefix-cls}-left {
|
||||
> .@{tab-prefix-cls}-nav {
|
||||
.@{tab-prefix-cls}-tab {
|
||||
border-radius: @border-radius-base 0 0 @border-radius-base;
|
||||
|
||||
&-active {
|
||||
border-right-color: @component-background;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
&.@{tab-prefix-cls}-right {
|
||||
> .@{tab-prefix-cls}-nav {
|
||||
.@{tab-prefix-cls}-tab {
|
||||
border-radius: 0 @border-radius-base @border-radius-base 0;
|
||||
|
||||
&-active {
|
||||
border-left-color: @component-background;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
59
components/tabs/style/dropdown.less
Normal file
59
components/tabs/style/dropdown.less
Normal file
@ -0,0 +1,59 @@
|
||||
@import '../../style/themes/index';
|
||||
@import '../../style/mixins/index';
|
||||
@import './index';
|
||||
|
||||
.@{tab-prefix-cls}-dropdown {
|
||||
.reset-component;
|
||||
|
||||
position: absolute;
|
||||
top: -9999px;
|
||||
left: -9999px;
|
||||
z-index: @zindex-dropdown;
|
||||
display: block;
|
||||
|
||||
&-hidden {
|
||||
display: none;
|
||||
}
|
||||
|
||||
&-menu {
|
||||
max-height: 200px;
|
||||
margin: 0;
|
||||
padding: @dropdown-edge-child-vertical-padding 0;
|
||||
overflow-y: auto;
|
||||
text-align: left;
|
||||
list-style-type: none;
|
||||
background-color: @dropdown-menu-bg;
|
||||
background-clip: padding-box;
|
||||
border-radius: @border-radius-base;
|
||||
outline: none;
|
||||
box-shadow: @box-shadow-base;
|
||||
|
||||
&-item {
|
||||
width: 120px;
|
||||
margin: 0;
|
||||
padding: @dropdown-vertical-padding @control-padding-horizontal;
|
||||
overflow: hidden;
|
||||
color: @text-color;
|
||||
font-weight: normal;
|
||||
font-size: @dropdown-font-size;
|
||||
line-height: @dropdown-line-height;
|
||||
white-space: nowrap;
|
||||
text-overflow: ellipsis;
|
||||
cursor: pointer;
|
||||
transition: all 0.3s;
|
||||
|
||||
&:hover {
|
||||
background: @item-hover-bg;
|
||||
}
|
||||
|
||||
&-disabled {
|
||||
&,
|
||||
&:hover {
|
||||
color: @disabled-color;
|
||||
background: transparent;
|
||||
cursor: not-allowed;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
@ -1,442 +1,195 @@
|
||||
@import '../../style/themes/index';
|
||||
@import '../../style/mixins/index';
|
||||
@import './card-style';
|
||||
@import './size';
|
||||
@import './rtl';
|
||||
@import './position';
|
||||
@import './dropdown';
|
||||
@import './card';
|
||||
|
||||
@tab-prefix-cls: ~'@{ant-prefix}-tabs';
|
||||
|
||||
// Hidden content
|
||||
.tabs-hidden-content() {
|
||||
height: 0;
|
||||
padding: 0 !important;
|
||||
overflow: hidden;
|
||||
opacity: 0;
|
||||
pointer-events: none;
|
||||
input {
|
||||
visibility: hidden;
|
||||
}
|
||||
}
|
||||
|
||||
.@{tab-prefix-cls} {
|
||||
.reset-component;
|
||||
|
||||
position: relative;
|
||||
display: flex;
|
||||
overflow: hidden;
|
||||
.clearfix;
|
||||
|
||||
&-ink-bar {
|
||||
position: absolute;
|
||||
bottom: 1px;
|
||||
left: 0;
|
||||
z-index: 1;
|
||||
box-sizing: border-box;
|
||||
width: 0;
|
||||
height: 2px;
|
||||
background-color: @tabs-ink-bar-color;
|
||||
transform-origin: 0 0;
|
||||
}
|
||||
|
||||
&-bar {
|
||||
margin: @tabs-bar-margin;
|
||||
border-bottom: @border-width-base @border-style-base @border-color-split;
|
||||
outline: none;
|
||||
transition: padding 0.3s @ease-in-out;
|
||||
}
|
||||
|
||||
&-nav-container {
|
||||
// ========================== Navigation ==========================
|
||||
> .@{tab-prefix-cls}-nav {
|
||||
position: relative;
|
||||
box-sizing: border-box;
|
||||
margin-bottom: -1px;
|
||||
overflow: hidden;
|
||||
font-size: @tabs-title-font-size;
|
||||
line-height: @line-height-base;
|
||||
white-space: nowrap;
|
||||
transition: padding 0.3s @ease-in-out;
|
||||
.clearfix;
|
||||
display: flex;
|
||||
flex: none;
|
||||
align-items: center;
|
||||
|
||||
&-scrolling {
|
||||
padding-right: @tabs-scrolling-size;
|
||||
padding-left: @tabs-scrolling-size;
|
||||
}
|
||||
}
|
||||
|
||||
// https://github.com/ant-design/ant-design/issues/9104
|
||||
&-bottom &-bottom-bar {
|
||||
margin-top: @margin-md;
|
||||
margin-bottom: 0;
|
||||
border-top: @border-width-base @border-style-base @border-color-split;
|
||||
border-bottom: none;
|
||||
}
|
||||
|
||||
&-bottom &-bottom-bar &-ink-bar {
|
||||
top: 1px;
|
||||
bottom: auto;
|
||||
}
|
||||
|
||||
&-bottom &-bottom-bar &-nav-container {
|
||||
margin-top: -1px;
|
||||
margin-bottom: 0;
|
||||
}
|
||||
|
||||
&-tab-prev,
|
||||
&-tab-next {
|
||||
position: absolute;
|
||||
z-index: 2;
|
||||
width: 0;
|
||||
height: 100%;
|
||||
color: @text-color-secondary;
|
||||
text-align: center;
|
||||
background-color: transparent;
|
||||
border: 0;
|
||||
cursor: pointer;
|
||||
opacity: 0;
|
||||
transition: width 0.3s @ease-in-out, opacity 0.3s @ease-in-out, color 0.3s @ease-in-out;
|
||||
user-select: none;
|
||||
pointer-events: none;
|
||||
|
||||
&.@{tab-prefix-cls}-tab-arrow-show {
|
||||
width: @tabs-scrolling-size;
|
||||
height: 100%;
|
||||
opacity: 1;
|
||||
pointer-events: auto;
|
||||
}
|
||||
|
||||
&:hover {
|
||||
color: @text-color;
|
||||
}
|
||||
|
||||
&-icon {
|
||||
position: absolute;
|
||||
top: 50%;
|
||||
left: 50%;
|
||||
font-weight: bold;
|
||||
font-style: normal;
|
||||
font-variant: normal;
|
||||
line-height: inherit;
|
||||
text-align: center;
|
||||
text-transform: none;
|
||||
transform: translate(-50%, -50%);
|
||||
|
||||
&-target {
|
||||
display: block;
|
||||
.iconfont-size-under-12px(10px);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
&-tab-btn-disabled {
|
||||
cursor: not-allowed;
|
||||
&,
|
||||
&:hover {
|
||||
color: @disabled-color;
|
||||
}
|
||||
}
|
||||
|
||||
&-tab-next {
|
||||
right: 2px;
|
||||
}
|
||||
|
||||
&-tab-prev {
|
||||
left: 0;
|
||||
|
||||
:root & {
|
||||
filter: none;
|
||||
}
|
||||
}
|
||||
|
||||
&-nav-wrap {
|
||||
margin-bottom: -1px;
|
||||
overflow: hidden;
|
||||
}
|
||||
|
||||
&-nav-scroll {
|
||||
overflow: hidden;
|
||||
white-space: nowrap;
|
||||
}
|
||||
|
||||
&-nav {
|
||||
position: relative;
|
||||
display: inline-block;
|
||||
box-sizing: border-box;
|
||||
margin: 0;
|
||||
padding-left: 0;
|
||||
list-style: none;
|
||||
transition: transform 0.3s @ease-in-out;
|
||||
|
||||
&::before,
|
||||
&::after {
|
||||
display: table;
|
||||
content: ' ';
|
||||
}
|
||||
|
||||
&::after {
|
||||
clear: both;
|
||||
}
|
||||
|
||||
.@{tab-prefix-cls}-tab {
|
||||
.@{tab-prefix-cls}-nav-wrap {
|
||||
position: relative;
|
||||
display: inline-block;
|
||||
box-sizing: border-box;
|
||||
height: 100%;
|
||||
margin: @tabs-horizontal-margin;
|
||||
padding: @tabs-horizontal-padding;
|
||||
text-decoration: none;
|
||||
cursor: pointer;
|
||||
transition: color 0.3s @ease-in-out;
|
||||
display: flex;
|
||||
flex: auto;
|
||||
overflow: hidden;
|
||||
white-space: nowrap;
|
||||
transform: translate(0); // Fix chrome render bug
|
||||
|
||||
&::before {
|
||||
// >>>>> Ping shadow
|
||||
&::before,
|
||||
&::after {
|
||||
position: absolute;
|
||||
top: -1px;
|
||||
left: 0;
|
||||
width: 100%;
|
||||
border-top: 2px solid transparent;
|
||||
border-radius: @border-radius-base @border-radius-base 0 0;
|
||||
transition: all 0.3s;
|
||||
z-index: 1;
|
||||
opacity: 0;
|
||||
transition: opacity @animation-duration-slow;
|
||||
content: '';
|
||||
pointer-events: none;
|
||||
}
|
||||
}
|
||||
|
||||
&:last-child {
|
||||
margin-right: 0;
|
||||
.@{tab-prefix-cls}-nav-list {
|
||||
position: relative;
|
||||
display: flex;
|
||||
transition: transform @animation-duration-slow;
|
||||
}
|
||||
|
||||
// >>>>>>>> Operations
|
||||
.@{tab-prefix-cls}-nav-operations {
|
||||
display: flex;
|
||||
align-self: stretch;
|
||||
|
||||
&-hidden {
|
||||
position: absolute;
|
||||
visibility: hidden;
|
||||
pointer-events: none;
|
||||
}
|
||||
}
|
||||
|
||||
.@{tab-prefix-cls}-nav-more {
|
||||
position: relative;
|
||||
padding: @tabs-card-horizontal-padding;
|
||||
background: transparent;
|
||||
border: 0;
|
||||
|
||||
&::after {
|
||||
position: absolute;
|
||||
right: 0;
|
||||
bottom: 0;
|
||||
left: 0;
|
||||
height: 5px;
|
||||
transform: translateY(100%);
|
||||
content: '';
|
||||
}
|
||||
}
|
||||
|
||||
.@{tab-prefix-cls}-nav-add {
|
||||
padding: 0 @padding-xs;
|
||||
background: @tabs-card-head-background;
|
||||
border: @border-width-base @border-style-base @border-color-split;
|
||||
border-radius: @border-radius-base @border-radius-base 0 0;
|
||||
outline: none;
|
||||
cursor: pointer;
|
||||
transition: all @animation-duration-slow @ease-in-out;
|
||||
|
||||
&:hover {
|
||||
color: @tabs-hover-color;
|
||||
}
|
||||
|
||||
&:active,
|
||||
&:focus {
|
||||
color: @tabs-active-color;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
&-extra-content {
|
||||
flex: none;
|
||||
}
|
||||
|
||||
// ============================ InkBar ============================
|
||||
&-ink-bar {
|
||||
position: absolute;
|
||||
background: @tabs-ink-bar-color;
|
||||
pointer-events: none;
|
||||
}
|
||||
|
||||
// ============================= Tabs =============================
|
||||
&-tab {
|
||||
position: relative;
|
||||
display: inline-flex;
|
||||
align-items: center;
|
||||
margin: @tabs-horizontal-margin;
|
||||
padding: @tabs-horizontal-padding;
|
||||
font-size: @tabs-title-font-size;
|
||||
background: transparent;
|
||||
border: 0;
|
||||
outline: none;
|
||||
cursor: pointer;
|
||||
|
||||
&:last-of-type {
|
||||
margin-right: 0;
|
||||
margin-left: 0;
|
||||
}
|
||||
|
||||
& &-remove {
|
||||
flex: none;
|
||||
margin-right: -@margin-xss;
|
||||
margin-left: @margin-xs;
|
||||
color: @text-color-secondary;
|
||||
font-size: @font-size-sm;
|
||||
outline: none;
|
||||
transition: all @animation-duration-slow;
|
||||
|
||||
.@{iconfont-css-prefix} {
|
||||
margin: 0;
|
||||
}
|
||||
|
||||
&:hover {
|
||||
color: @heading-color;
|
||||
}
|
||||
|
||||
&:focus,
|
||||
&:active {
|
||||
color: @tabs-active-color;
|
||||
}
|
||||
}
|
||||
|
||||
.@{iconfont-css-prefix} {
|
||||
margin-right: @margin-sm;
|
||||
}
|
||||
&:focus,
|
||||
&:active {
|
||||
color: @tabs-active-color;
|
||||
}
|
||||
|
||||
&-active {
|
||||
color: @tabs-highlight-color;
|
||||
font-weight: 500;
|
||||
outline: none;
|
||||
}
|
||||
&:hover {
|
||||
color: @tabs-hover-color;
|
||||
}
|
||||
|
||||
&-disabled {
|
||||
&,
|
||||
&:hover {
|
||||
color: @disabled-color;
|
||||
cursor: not-allowed;
|
||||
}
|
||||
}
|
||||
&&-active {
|
||||
color: @tabs-highlight-color;
|
||||
font-weight: 500;
|
||||
}
|
||||
|
||||
&&-disabled {
|
||||
color: @disabled-color;
|
||||
cursor: not-allowed;
|
||||
}
|
||||
|
||||
.@{iconfont-css-prefix} {
|
||||
margin-right: @margin-sm;
|
||||
}
|
||||
}
|
||||
|
||||
.@{tab-prefix-cls}-large-bar {
|
||||
.@{tab-prefix-cls}-nav-container {
|
||||
font-size: @tabs-title-font-size-lg;
|
||||
// =========================== TabPanes ===========================
|
||||
&-content {
|
||||
&-holder {
|
||||
flex: auto;
|
||||
}
|
||||
.@{tab-prefix-cls}-tab {
|
||||
padding: @tabs-horizontal-padding-lg;
|
||||
|
||||
display: flex;
|
||||
width: 100%;
|
||||
|
||||
&-animated {
|
||||
transition: margin @animation-duration-slow;
|
||||
}
|
||||
}
|
||||
|
||||
.@{tab-prefix-cls}-small-bar {
|
||||
.@{tab-prefix-cls}-nav-container {
|
||||
font-size: @tabs-title-font-size-sm;
|
||||
}
|
||||
.@{tab-prefix-cls}-tab {
|
||||
padding: @tabs-horizontal-padding-sm;
|
||||
}
|
||||
}
|
||||
|
||||
// Create an empty element to avoid margin collapsing
|
||||
// https://github.com/ant-design/ant-design/issues/18103
|
||||
&-content::before {
|
||||
display: block;
|
||||
overflow: hidden;
|
||||
content: '';
|
||||
}
|
||||
|
||||
.@{tab-prefix-cls}-tabpane {
|
||||
&-tabpane {
|
||||
flex: none;
|
||||
width: 100%;
|
||||
outline: none;
|
||||
}
|
||||
|
||||
// Horizontal Content
|
||||
.@{tab-prefix-cls}-top-content,
|
||||
.@{tab-prefix-cls}-bottom-content {
|
||||
width: 100%;
|
||||
> .@{tab-prefix-cls}-tabpane {
|
||||
flex-shrink: 0;
|
||||
width: 100%;
|
||||
-webkit-backface-visibility: hidden;
|
||||
opacity: 1;
|
||||
transition: opacity 0.45s;
|
||||
}
|
||||
|
||||
> .@{tab-prefix-cls}-tabpane-inactive {
|
||||
.tabs-hidden-content();
|
||||
}
|
||||
|
||||
&.@{tab-prefix-cls}-content-animated {
|
||||
display: flex;
|
||||
flex-direction: row;
|
||||
transition: margin-left 0.3s @ease-in-out;
|
||||
will-change: margin-left;
|
||||
}
|
||||
}
|
||||
|
||||
// Vertical Bar
|
||||
.@{tab-prefix-cls}-left-bar,
|
||||
.@{tab-prefix-cls}-right-bar {
|
||||
height: 100%;
|
||||
border-bottom: 0;
|
||||
|
||||
.@{tab-prefix-cls}-tab-arrow-show {
|
||||
width: 100%;
|
||||
height: @tabs-scrolling-size;
|
||||
}
|
||||
|
||||
.@{tab-prefix-cls}-tab {
|
||||
display: block;
|
||||
float: none;
|
||||
margin: @tabs-vertical-margin;
|
||||
padding: @tabs-vertical-padding;
|
||||
text-align: center;
|
||||
|
||||
&:last-child {
|
||||
margin-bottom: 0;
|
||||
}
|
||||
}
|
||||
|
||||
.@{tab-prefix-cls}-extra-content {
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
.@{tab-prefix-cls}-nav-scroll {
|
||||
width: auto;
|
||||
}
|
||||
|
||||
.@{tab-prefix-cls}-nav-container,
|
||||
.@{tab-prefix-cls}-nav-wrap {
|
||||
height: 100%;
|
||||
}
|
||||
|
||||
.@{tab-prefix-cls}-nav-container {
|
||||
margin-bottom: 0;
|
||||
|
||||
&.@{tab-prefix-cls}-nav-container-scrolling {
|
||||
padding: @tabs-scrolling-size 0;
|
||||
}
|
||||
}
|
||||
|
||||
.@{tab-prefix-cls}-nav-wrap {
|
||||
margin-bottom: 0;
|
||||
}
|
||||
|
||||
.@{tab-prefix-cls}-nav {
|
||||
width: 100%;
|
||||
}
|
||||
|
||||
.@{tab-prefix-cls}-ink-bar {
|
||||
top: 0;
|
||||
bottom: auto;
|
||||
left: auto;
|
||||
width: 2px;
|
||||
height: 0;
|
||||
}
|
||||
|
||||
.@{tab-prefix-cls}-tab-next {
|
||||
right: 0;
|
||||
bottom: 0;
|
||||
width: 100%;
|
||||
height: @tabs-scrolling-size;
|
||||
}
|
||||
|
||||
.@{tab-prefix-cls}-tab-prev {
|
||||
top: 0;
|
||||
width: 100%;
|
||||
height: @tabs-scrolling-size;
|
||||
}
|
||||
}
|
||||
|
||||
// Vertical Content
|
||||
.@{tab-prefix-cls}-left-content,
|
||||
.@{tab-prefix-cls}-right-content {
|
||||
width: auto;
|
||||
margin-top: 0 !important;
|
||||
overflow: hidden;
|
||||
}
|
||||
|
||||
// Vertical - Left
|
||||
.@{tab-prefix-cls}-left-bar {
|
||||
float: left;
|
||||
margin-right: -1px;
|
||||
margin-bottom: 0;
|
||||
border-right: @border-width-base @border-style-base @border-color-split;
|
||||
.@{tab-prefix-cls}-nav-container {
|
||||
margin-right: -1px;
|
||||
}
|
||||
.@{tab-prefix-cls}-nav-wrap {
|
||||
margin-right: -1px;
|
||||
}
|
||||
.@{tab-prefix-cls}-ink-bar {
|
||||
right: 1px;
|
||||
}
|
||||
}
|
||||
.@{tab-prefix-cls}-left-content {
|
||||
padding-left: @padding-lg;
|
||||
border-left: @border-width-base @border-style-base @border-color-split;
|
||||
}
|
||||
|
||||
// Vertical - Right
|
||||
.@{tab-prefix-cls}-right-bar {
|
||||
float: right;
|
||||
margin-bottom: 0;
|
||||
margin-left: -1px;
|
||||
border-left: @border-width-base @border-style-base @border-color-split;
|
||||
.@{tab-prefix-cls}-nav-container {
|
||||
margin-left: -1px;
|
||||
}
|
||||
.@{tab-prefix-cls}-nav-wrap {
|
||||
margin-left: -1px;
|
||||
}
|
||||
.@{tab-prefix-cls}-ink-bar {
|
||||
left: 1px;
|
||||
}
|
||||
}
|
||||
.@{tab-prefix-cls}-right-content {
|
||||
padding-right: @padding-lg;
|
||||
border-right: @border-width-base @border-style-base @border-color-split;
|
||||
}
|
||||
}
|
||||
|
||||
.@{tab-prefix-cls}-top .@{tab-prefix-cls}-ink-bar-animated,
|
||||
.@{tab-prefix-cls}-bottom .@{tab-prefix-cls}-ink-bar-animated {
|
||||
transition: transform 0.3s @ease-in-out, width 0.2s @ease-in-out, left 0.3s @ease-in-out;
|
||||
}
|
||||
|
||||
.@{tab-prefix-cls}-left .@{tab-prefix-cls}-ink-bar-animated,
|
||||
.@{tab-prefix-cls}-right .@{tab-prefix-cls}-ink-bar-animated {
|
||||
transition: transform 0.3s @ease-in-out, height 0.2s @ease-in-out, top 0.3s @ease-in-out;
|
||||
}
|
||||
|
||||
// No animation
|
||||
.tabs-no-animation() {
|
||||
> .@{tab-prefix-cls}-content-animated {
|
||||
margin-left: 0 !important;
|
||||
transform: none !important;
|
||||
}
|
||||
> .@{tab-prefix-cls}-tabpane-inactive {
|
||||
.tabs-hidden-content();
|
||||
}
|
||||
}
|
||||
|
||||
.no-flex,
|
||||
.@{tab-prefix-cls}-no-animation {
|
||||
> .@{tab-prefix-cls}-content {
|
||||
.tabs-no-animation();
|
||||
}
|
||||
}
|
||||
|
||||
.@{tab-prefix-cls}-left-content,
|
||||
.@{tab-prefix-cls}-right-content {
|
||||
.tabs-no-animation();
|
||||
}
|
||||
|
||||
@import './rtl.less';
|
||||
|
186
components/tabs/style/position.less
Normal file
186
components/tabs/style/position.less
Normal file
@ -0,0 +1,186 @@
|
||||
@import './index';
|
||||
|
||||
.@{tab-prefix-cls} {
|
||||
// ========================== Top & Bottom ==========================
|
||||
&-top,
|
||||
&-bottom {
|
||||
flex-direction: column;
|
||||
|
||||
> .@{tab-prefix-cls}-nav {
|
||||
margin: @tabs-bar-margin;
|
||||
|
||||
&::before {
|
||||
position: absolute;
|
||||
right: 0;
|
||||
left: 0;
|
||||
border-bottom: @border-width-base @border-style-base @border-color-split;
|
||||
content: '';
|
||||
}
|
||||
|
||||
.@{tab-prefix-cls}-ink-bar {
|
||||
height: 2px;
|
||||
|
||||
&-animated {
|
||||
transition: width @animation-duration-slow, left @animation-duration-slow,
|
||||
right @animation-duration-slow;
|
||||
}
|
||||
}
|
||||
|
||||
.@{tab-prefix-cls}-nav-wrap {
|
||||
&::before,
|
||||
&::after {
|
||||
top: 0;
|
||||
bottom: 0;
|
||||
width: 30px;
|
||||
}
|
||||
|
||||
&::before {
|
||||
left: 0;
|
||||
box-shadow: inset 10px 0 8px -8px fade(@shadow-color, 8%);
|
||||
}
|
||||
&::after {
|
||||
right: 0;
|
||||
box-shadow: inset -10px 0 8px -8px fade(@shadow-color, 8%);
|
||||
}
|
||||
|
||||
&.@{tab-prefix-cls}-nav-wrap-ping-left::before {
|
||||
opacity: 1;
|
||||
}
|
||||
&.@{tab-prefix-cls}-nav-wrap-ping-right::after {
|
||||
opacity: 1;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
&-top {
|
||||
> .@{tab-prefix-cls}-nav {
|
||||
&::before {
|
||||
bottom: 0;
|
||||
}
|
||||
|
||||
.@{tab-prefix-cls}-ink-bar {
|
||||
bottom: 0;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
&-bottom {
|
||||
> .@{tab-prefix-cls}-nav {
|
||||
order: 1;
|
||||
margin-top: @margin-md;
|
||||
margin-bottom: 0;
|
||||
|
||||
&::before {
|
||||
top: 0;
|
||||
}
|
||||
|
||||
.@{tab-prefix-cls}-ink-bar {
|
||||
top: 0;
|
||||
}
|
||||
}
|
||||
|
||||
> .@{tab-prefix-cls}-content-holder {
|
||||
order: 0;
|
||||
}
|
||||
}
|
||||
|
||||
// ========================== Left & Right ==========================
|
||||
&-left,
|
||||
&-right {
|
||||
> .@{tab-prefix-cls}-nav {
|
||||
flex-direction: column;
|
||||
min-width: 50px;
|
||||
|
||||
// >>>>>>>>>>> Tab
|
||||
.@{tab-prefix-cls}-tab {
|
||||
margin: @tabs-vertical-margin;
|
||||
padding: @tabs-vertical-padding;
|
||||
text-align: center;
|
||||
|
||||
&:last-of-type {
|
||||
margin-bottom: 0;
|
||||
}
|
||||
}
|
||||
|
||||
// >>>>>>>>>>> Nav
|
||||
.@{tab-prefix-cls}-nav-wrap {
|
||||
flex-direction: column;
|
||||
|
||||
&::before,
|
||||
&::after {
|
||||
right: 0;
|
||||
left: 0;
|
||||
height: 30px;
|
||||
}
|
||||
|
||||
&::before {
|
||||
top: 0;
|
||||
box-shadow: inset 0 10px 8px -8px fade(@shadow-color, 8%);
|
||||
}
|
||||
&::after {
|
||||
bottom: 0;
|
||||
box-shadow: inset 0 -10px 8px -8px fade(@shadow-color, 8%);
|
||||
}
|
||||
|
||||
&.@{tab-prefix-cls}-nav-wrap-ping-top::before {
|
||||
opacity: 1;
|
||||
}
|
||||
&.@{tab-prefix-cls}-nav-wrap-ping-bottom::after {
|
||||
opacity: 1;
|
||||
}
|
||||
}
|
||||
|
||||
// >>>>>>>>>>> Ink Bar
|
||||
.@{tab-prefix-cls}-ink-bar {
|
||||
width: 2px;
|
||||
|
||||
&-animated {
|
||||
transition: height @animation-duration-slow, top @animation-duration-slow;
|
||||
}
|
||||
}
|
||||
|
||||
.@{tab-prefix-cls}-nav-list,
|
||||
.@{tab-prefix-cls}-nav-operations {
|
||||
flex-direction: column;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
&-left {
|
||||
> .@{tab-prefix-cls}-nav {
|
||||
.@{tab-prefix-cls}-ink-bar {
|
||||
right: 0;
|
||||
}
|
||||
}
|
||||
|
||||
> .@{tab-prefix-cls}-content-holder {
|
||||
margin-left: -@border-width-base;
|
||||
border-left: @border-width-base @border-style-base @border-color-split;
|
||||
|
||||
> .@{tab-prefix-cls}-content > .@{tab-prefix-cls}-tabpane {
|
||||
padding-left: @padding-lg;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
&-right {
|
||||
> .@{tab-prefix-cls}-nav {
|
||||
order: 1;
|
||||
|
||||
.@{tab-prefix-cls}-ink-bar {
|
||||
left: 0;
|
||||
}
|
||||
}
|
||||
|
||||
> .@{tab-prefix-cls}-content-holder {
|
||||
order: 0;
|
||||
margin-right: -@border-width-base;
|
||||
border-right: @border-width-base @border-style-base @border-color-split;
|
||||
|
||||
> .@{tab-prefix-cls}-content > .@{tab-prefix-cls}-tabpane {
|
||||
padding-right: @padding-lg;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
@ -1,83 +1,61 @@
|
||||
@import '../../style/themes/index';
|
||||
@import '../../style/mixins/index';
|
||||
@import './card-style';
|
||||
@import './index';
|
||||
|
||||
@tab-prefix-cls: ~'@{ant-prefix}-tabs';
|
||||
.@{tab-prefix-cls}-rtl {
|
||||
direction: rtl;
|
||||
|
||||
.@{tab-prefix-cls} {
|
||||
&-rtl {
|
||||
direction: rtl;
|
||||
}
|
||||
|
||||
&-ink-bar {
|
||||
.@{tab-prefix-cls}-rtl & {
|
||||
right: 0;
|
||||
left: auto;
|
||||
}
|
||||
}
|
||||
|
||||
&-tab-next {
|
||||
.@{tab-prefix-cls}-rtl & {
|
||||
right: auto;
|
||||
left: 2px;
|
||||
}
|
||||
}
|
||||
|
||||
&-tab-prev {
|
||||
.@{tab-prefix-cls}-rtl & {
|
||||
right: 2px;
|
||||
left: auto;
|
||||
}
|
||||
}
|
||||
|
||||
&-nav {
|
||||
> .@{tab-prefix-cls}-nav {
|
||||
.@{tab-prefix-cls}-tab {
|
||||
.@{tab-prefix-cls}-rtl & {
|
||||
margin: @tabs-horizontal-margin-rtl;
|
||||
margin: @tabs-horizontal-margin-rtl;
|
||||
|
||||
&:last-of-type {
|
||||
margin-left: 0;
|
||||
}
|
||||
|
||||
.@{iconfont-css-prefix} {
|
||||
.@{tab-prefix-cls}-rtl & {
|
||||
margin-right: 0;
|
||||
margin-left: @margin-xs;
|
||||
margin-right: 0;
|
||||
margin-left: @margin-sm;
|
||||
}
|
||||
|
||||
.@{tab-prefix-cls}-tab-remove {
|
||||
margin-right: @margin-xs;
|
||||
margin-left: -@margin-xss;
|
||||
|
||||
.@{iconfont-css-prefix} {
|
||||
margin: 0;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
.@{tab-prefix-cls}-left-bar,
|
||||
.@{tab-prefix-cls}-right-bar {
|
||||
.@{tab-prefix-cls}-tab {
|
||||
.@{tab-prefix-cls}-rtl& {
|
||||
margin: @tabs-vertical-margin;
|
||||
}
|
||||
|
||||
&:last-child {
|
||||
margin-bottom: 0;
|
||||
}
|
||||
&.@{tab-prefix-cls}-left {
|
||||
> .@{tab-prefix-cls}-nav {
|
||||
order: 1;
|
||||
}
|
||||
> .@{tab-prefix-cls}-content-holder {
|
||||
order: 0;
|
||||
}
|
||||
}
|
||||
|
||||
.@{tab-prefix-cls}-right-bar {
|
||||
.@{tab-prefix-cls}-ink-bar {
|
||||
.@{tab-prefix-cls}-rtl& {
|
||||
right: auto;
|
||||
left: 1px;
|
||||
&.@{tab-prefix-cls}-right {
|
||||
> .@{tab-prefix-cls}-nav {
|
||||
order: 0;
|
||||
}
|
||||
> .@{tab-prefix-cls}-content-holder {
|
||||
order: 1;
|
||||
}
|
||||
}
|
||||
|
||||
// ====================== Card ======================
|
||||
&.@{tab-prefix-cls}-card {
|
||||
&.@{tab-prefix-cls}-top,
|
||||
&.@{tab-prefix-cls}-bottom {
|
||||
> .@{tab-prefix-cls}-nav {
|
||||
button.@{tab-prefix-cls}-tab:not(:last-of-type) {
|
||||
margin: 0 0 0 @tabs-card-gutter;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// card
|
||||
&&-card &-card-bar &-tab &-close-x {
|
||||
.@{tab-prefix-cls}-rtl& {
|
||||
margin-right: 3px;
|
||||
margin-left: -5px;
|
||||
}
|
||||
}
|
||||
|
||||
&-extra-content {
|
||||
.@{tab-prefix-cls}-rtl & {
|
||||
float: left !important;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
41
components/tabs/style/size.less
Normal file
41
components/tabs/style/size.less
Normal file
@ -0,0 +1,41 @@
|
||||
@import '../../style/themes/index';
|
||||
@import '../../style/mixins/index';
|
||||
@import './index';
|
||||
|
||||
.@{tab-prefix-cls} {
|
||||
&-small {
|
||||
> .@{tab-prefix-cls}-nav {
|
||||
.@{tab-prefix-cls}-tab {
|
||||
padding: @tabs-horizontal-padding-sm;
|
||||
font-size: @tabs-title-font-size-sm;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
&-large {
|
||||
> .@{tab-prefix-cls}-nav {
|
||||
.@{tab-prefix-cls}-tab {
|
||||
padding: @tabs-horizontal-padding-lg;
|
||||
font-size: @tabs-title-font-size-lg;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
&-card {
|
||||
&.@{tab-prefix-cls}-small {
|
||||
> .@{tab-prefix-cls}-nav {
|
||||
.@{tab-prefix-cls}-tab {
|
||||
padding: @tabs-card-horizontal-padding-sm;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
&.@{tab-prefix-cls}-large {
|
||||
> .@{tab-prefix-cls}-nav {
|
||||
.@{tab-prefix-cls}-tab {
|
||||
padding: @tabs-card-horizontal-padding-lg;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
@ -416,15 +416,7 @@ class Base extends React.Component<InternalBlockProps, BaseState> {
|
||||
|
||||
renderContent() {
|
||||
const { ellipsisContent, isEllipsis, expanded } = this.state;
|
||||
const {
|
||||
component,
|
||||
children,
|
||||
className,
|
||||
type,
|
||||
disabled,
|
||||
style,
|
||||
...restProps
|
||||
} = this.props;
|
||||
const { component, children, className, type, disabled, style, ...restProps } = this.props;
|
||||
const { direction } = this.context;
|
||||
const { rows, suffix } = this.getEllipsis();
|
||||
|
||||
|
@ -120,7 +120,7 @@
|
||||
"rc-collapse": "~2.0.0",
|
||||
"rc-dialog": "~8.0.0",
|
||||
"rc-drawer": "~4.0.0",
|
||||
"rc-dropdown": "~3.0.0",
|
||||
"rc-dropdown": "~3.1.2",
|
||||
"rc-field-form": "~1.4.1",
|
||||
"rc-input-number": "~5.0.0",
|
||||
"rc-mentions": "~1.2.0",
|
||||
@ -136,7 +136,7 @@
|
||||
"rc-steps": "~3.6.0",
|
||||
"rc-switch": "~3.2.0",
|
||||
"rc-table": "~7.7.2",
|
||||
"rc-tabs": "~10.1.1",
|
||||
"rc-tabs": "~11.2.0",
|
||||
"rc-tooltip": "~4.2.0",
|
||||
"rc-tree": "~3.3.0",
|
||||
"rc-tree-select": "~3.2.0",
|
||||
|
@ -22,7 +22,7 @@
|
||||
<link rel="stylesheet/less" type="text/css" href="{{ root }}color.less" />
|
||||
<script src="https://polyfill.alicdn.com/polyfill.min.js?features=default,es2015,Intl"></script>
|
||||
<script>
|
||||
(function() {
|
||||
(function () {
|
||||
function isLocalStorageNameSupported() {
|
||||
var testKey = 'test';
|
||||
var storage = window.localStorage;
|
||||
@ -100,10 +100,14 @@
|
||||
</script>
|
||||
<!-- Hotjar Tracking Code for ant.design -->
|
||||
<script>
|
||||
(function(h, o, t, j, a, r) {
|
||||
(function (h, o, t, j, a, r) {
|
||||
if (location.hostname === 'localhost') {
|
||||
return;
|
||||
}
|
||||
|
||||
h.hj =
|
||||
h.hj ||
|
||||
function() {
|
||||
function () {
|
||||
(h.hj.q = h.hj.q || []).push(arguments);
|
||||
};
|
||||
h._hjSettings = { hjid: 473408, hjsv: 5 };
|
||||
|
@ -37,7 +37,8 @@ const MORE_LIST: MoreProps[] = [
|
||||
},
|
||||
{
|
||||
title: 'JCD 驱动 - 复杂系统设计应对之道',
|
||||
description: '基于蚂蚁金服CTO线的业务土壤,我们探索出以JCD为核心的企业级产品设计思维,助力设计师在深耕业务上有章可循。',
|
||||
description:
|
||||
'基于蚂蚁金服CTO线的业务土壤,我们探索出以JCD为核心的企业级产品设计思维,助力设计师在深耕业务上有章可循。',
|
||||
img: 'https://gw.alipayobjects.com/mdn/rms_08e378/afts/img/A*y-xiQoZzBCEAAAAAAAAAAABkARQnAQ',
|
||||
date: '2020-01-17',
|
||||
source: 'zhihu',
|
||||
@ -45,8 +46,7 @@ const MORE_LIST: MoreProps[] = [
|
||||
},
|
||||
{
|
||||
title: '折柱饼 +3 个套路,简单图表你真的会用吗?',
|
||||
description:
|
||||
'本文一句话概括:数据可视化中,如何用最简单的图表高效地传递信息。',
|
||||
description: '本文一句话概括:数据可视化中,如何用最简单的图表高效地传递信息。',
|
||||
img: 'https://gw.alipayobjects.com/mdn/rms_08e378/afts/img/A*Q1DMQpLCDQgAAAAAAAAAAABkARQnAQ',
|
||||
date: '2020-11-28',
|
||||
source: 'zhihu',
|
||||
|
Loading…
Reference in New Issue
Block a user