Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

feat(tabs): calculate scroll left position #3624

Merged
merged 2 commits into from
Nov 22, 2023
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
7 changes: 7 additions & 0 deletions src/tabs/__tests__/__snapshots__/index.test.jsx.snap
Original file line number Diff line number Diff line change
Expand Up @@ -54,6 +54,7 @@ exports[`Tabs > :props > :addable 1`] = `
/>
</svg>
</div>
<!---->
</div>

<div
Expand Down Expand Up @@ -119,6 +120,7 @@ exports[`Tabs > :props > :defaultValue 1`] = `
<!---->
</transition-stub>
<!---->
<!---->
</div>

<div
Expand Down Expand Up @@ -184,6 +186,7 @@ exports[`Tabs > :props > :disabled 1`] = `
<!---->
</transition-stub>
<!---->
<!---->
</div>

<div
Expand Down Expand Up @@ -249,6 +252,7 @@ exports[`Tabs > :props > :placement 1`] = `
<!---->
</transition-stub>
<!---->
<!---->
</div>

<div
Expand Down Expand Up @@ -313,6 +317,7 @@ exports[`Tabs > :props > :size 1`] = `
<!---->
</transition-stub>
<!---->
<!---->
</div>

<div
Expand Down Expand Up @@ -378,6 +383,7 @@ exports[`Tabs > :props > :theme 1`] = `
<!---->
</transition-stub>
<!---->
<!---->
</div>

<div
Expand Down Expand Up @@ -441,6 +447,7 @@ exports[`Tabs > :props > :value 1`] = `
<!---->
</transition-stub>
<!---->
<!---->
</div>

<div
Expand Down
2 changes: 1 addition & 1 deletion src/tabs/_example/combination.vue
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,6 @@
<script setup>
import { ref } from 'vue';

const value = ref('1');
const value = ref('20');
const theme = ref('normal');
</script>
30 changes: 27 additions & 3 deletions src/tabs/tab-nav.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -33,6 +33,7 @@ export default defineComponent({
type: Array as { new (): Array<InstanceType<typeof TTabPanel>> },
default: (): Array<InstanceType<typeof TTabPanel>> => [] as Array<InstanceType<typeof TTabPanel>>,
},
action: tabProps.action,
value: tabProps.value,
placement: tabProps.placement,
size: tabProps.size,
Expand All @@ -52,6 +53,7 @@ export default defineComponent({
AddIcon: TdAddIcon,
});
const classPrefix = usePrefixClass();

const { SIZE } = useCommonClassName();

const scrollLeft = ref(0);
Expand All @@ -76,9 +78,12 @@ export default defineComponent({
toRightBtn: toRightBtnRef.value,
});

// left right位置 选项卡的位置是在左右侧垂直方向铺开的
const isVerticalPlacement = computed(() => ['left', 'right'].includes(props.placement.toLowerCase()));

// style
const wrapTransformStyle = computed(() => {
if (['left', 'right'].includes(props.placement.toLowerCase())) return {};
if (isVerticalPlacement.value) return {};
return {
transform: `translate3d(${-scrollLeft.value}px, 0, 0)`,
};
Expand Down Expand Up @@ -132,7 +137,7 @@ export default defineComponent({
return [
`${COMPONENT_NAME.value}__nav-wrap`,
`${classPrefix.value}-is-smooth`,
{ [`${classPrefix.value}-is-vertical`]: props.placement === 'left' || props.placement === 'right' },
{ [`${classPrefix.value}-is-vertical`]: isVerticalPlacement.value },
];
});

Expand All @@ -147,26 +152,43 @@ export default defineComponent({

// life times
useResize(debounce(totalAdjust), navsContainerRef.value);
onMounted(totalAdjust);
onMounted(() => {
totalAdjust();
calculateMountedScrollLeft();
});

// calculate scroll left after mounted
const calculateMountedScrollLeft = () => {
if (isVerticalPlacement.value) return;

const container = navsContainerRef.value;
const activeTabEl = activeTabRef.value;
const totalWidthBeforeActiveTab = activeTabEl?.offsetLeft;
const containerWidth = container.offsetWidth || 0;
if (totalWidthBeforeActiveTab > containerWidth) scrollLeft.value = totalWidthBeforeActiveTab;
};
// methods
const adjustScrollLeft = () => {
scrollLeft.value = calcScrollLeft(getRefs(), scrollLeft.value);
};

const adjustArrowDisplay = () => {
canToLeft.value = calculateCanToLeft(getRefs(), scrollLeft.value, props.placement);
canToRight.value = calculateCanToRight(getRefs(), scrollLeft.value, props.placement);
};

const handleScroll = (direction: 'left' | 'right') => {
if (direction === 'left') {
scrollLeft.value = scrollToLeft(getRefs(), scrollLeft.value);
} else {
scrollLeft.value = scrollToRight(getRefs(), scrollLeft.value);
}
};

const handleAddTab = (e: MouseEvent) => {
props.onAdd?.({ e });
};

const tabClick = (event: MouseEvent, nav: Partial<InstanceType<typeof TTabPanel>>) => {
const { value, disabled } = nav;
if (disabled || props.value === value) {
Expand All @@ -191,6 +213,7 @@ export default defineComponent({
};

const { setNavsWrap } = useDragSort(props);

onMounted(() => {
setNavsWrap(navsWrapRef.value);
});
Expand Down Expand Up @@ -259,6 +282,7 @@ export default defineComponent({
<AddIcon></AddIcon>
</div>
) : null}
{props.action}
</div>,
];
};
Expand Down
2 changes: 1 addition & 1 deletion src/tabs/tabs.md
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@

名称 | 类型 | 默认值 | 说明 | 必传
-- | -- | -- | -- | --
action | String / Slot / Function | - | 【开发中】选项卡右侧的操作区域。TS 类型:`string \| TNode`。[通用类型定义](https://github.com/Tencent/tdesign-vue-next/blob/develop/src/common.ts) | N
action | String / Slot / Function | - | 选项卡右侧的操作区域。TS 类型:`string \| TNode`。[通用类型定义](https://github.com/Tencent/tdesign-vue-next/blob/develop/src/common.ts) | N
addable | Boolean | false | 选项卡是否可增加 | N
disabled | Boolean | false | 是否禁用选项卡 | N
dragSort | Boolean | false | 是否开启拖拽调整顺序 | N
Expand Down
2 changes: 2 additions & 0 deletions src/tabs/tabs.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -60,6 +60,7 @@ export default defineComponent({
};
const renderHeader = () => {
const panels = (props.list?.length ? props.list : getSlotPanels()) || [];
const actionContent = renderTNodeJSX('action');
const panelsData = panels.map((item: ComponentPublicInstance) => {
const selfItem = item;

Expand All @@ -80,6 +81,7 @@ export default defineComponent({
addable: props.addable,
panels: panelsData,
dragSort: props.dragSort,
action: actionContent,
};
return (
<div
Expand Down
45 changes: 30 additions & 15 deletions test/unit/snap/__snapshots__/csr.test.js.snap
Original file line number Diff line number Diff line change
Expand Up @@ -64758,6 +64758,7 @@ exports[`csr snapshot test > csr test ./src/form/_example/validate-complicated-d
/>
</svg>
</div>
<!---->
</div>

<div
Expand Down Expand Up @@ -161148,6 +161149,7 @@ exports[`csr snapshot test > csr test ./src/tabs/_example/ban.vue 1`] = `
<!---->
</transition-stub>
<!---->
<!---->
</div>

<div
Expand Down Expand Up @@ -161290,6 +161292,7 @@ exports[`csr snapshot test > csr test ./src/tabs/_example/base.vue 1`] = `
<!---->
</transition-stub>
<!---->
<!---->
</div>

<div
Expand Down Expand Up @@ -161432,6 +161435,7 @@ exports[`csr snapshot test > csr test ./src/tabs/_example/base.vue 1`] = `
<!---->
</transition-stub>
<!---->
<!---->
</div>

<div
Expand Down Expand Up @@ -161649,6 +161653,7 @@ exports[`csr snapshot test > csr test ./src/tabs/_example/combination.vue 1`] =
<!---->
</transition-stub>
<!---->
<!---->
</div>

<div
Expand All @@ -161666,11 +161671,11 @@ exports[`csr snapshot test > csr test ./src/tabs/_example/combination.vue 1`] =
/>

<div
class="t-tabs__nav-item t-is-active t-size-m"
class="t-tabs__nav-item t-size-m"
draggable="false"
>
<div
class="t-tabs__nav-item-wrapper t-is-active"
class="t-tabs__nav-item-wrapper"
>
<span
class="t-tabs__nav-item-text-wrapper"
Expand Down Expand Up @@ -161951,11 +161956,11 @@ exports[`csr snapshot test > csr test ./src/tabs/_example/combination.vue 1`] =
<!---->
</div>
<div
class="t-tabs__nav-item t-size-m"
class="t-tabs__nav-item t-is-active t-size-m"
draggable="false"
>
<div
class="t-tabs__nav-item-wrapper"
class="t-tabs__nav-item-wrapper t-is-active"
>
<span
class="t-tabs__nav-item-text-wrapper"
Expand All @@ -161975,17 +161980,6 @@ exports[`csr snapshot test > csr test ./src/tabs/_example/combination.vue 1`] =
class="t-tabs__content"
>

<div
class="t-tab-panel"
>

<p
style="padding: 25px;"
>
选项卡2
</p>

</div>
<!---->
<!---->
<!---->
Expand All @@ -162005,6 +161999,17 @@ exports[`csr snapshot test > csr test ./src/tabs/_example/combination.vue 1`] =
<!---->
<!---->
<!---->
<div
class="t-tab-panel"
>

<p
style="padding: 25px;"
>
选项卡21
</p>

</div>

</div>

Expand Down Expand Up @@ -162079,6 +162084,7 @@ exports[`csr snapshot test > csr test ./src/tabs/_example/custom.vue 1`] = `
/>
</svg>
</div>
<!---->
</div>

<div
Expand Down Expand Up @@ -162298,6 +162304,7 @@ exports[`csr snapshot test > csr test ./src/tabs/_example/drag-sort.vue 1`] = `
<!---->
</transition-stub>
<!---->
<!---->
</div>

<div
Expand Down Expand Up @@ -162521,6 +162528,7 @@ exports[`csr snapshot test > csr test ./src/tabs/_example/icon.vue 1`] = `
<!---->
</transition-stub>
<!---->
<!---->
</div>

<div
Expand Down Expand Up @@ -162690,6 +162698,7 @@ exports[`csr snapshot test > csr test ./src/tabs/_example/lazy-load.vue 1`] = `
<!---->
</transition-stub>
<!---->
<!---->
</div>

<div
Expand Down Expand Up @@ -162872,6 +162881,7 @@ exports[`csr snapshot test > csr test ./src/tabs/_example/operation.vue 1`] = `
/>
</svg>
</div>
<!---->
</div>

<div
Expand Down Expand Up @@ -163130,6 +163140,7 @@ exports[`csr snapshot test > csr test ./src/tabs/_example/position.vue 1`] = `
<!---->
</transition-stub>
<!---->
<!---->
</div>

<div
Expand Down Expand Up @@ -163281,6 +163292,7 @@ exports[`csr snapshot test > csr test ./src/tabs/_example/size.vue 1`] = `
<!---->
</transition-stub>
<!---->
<!---->
</div>

<div
Expand Down Expand Up @@ -163413,6 +163425,7 @@ exports[`csr snapshot test > csr test ./src/tabs/_example/size.vue 1`] = `
<!---->
</transition-stub>
<!---->
<!---->
</div>

<div
Expand Down Expand Up @@ -163569,6 +163582,7 @@ exports[`csr snapshot test > csr test ./src/tabs/_example/theme.vue 1`] = `
<!---->
</transition-stub>
<!---->
<!---->
</div>

<div
Expand Down Expand Up @@ -163701,6 +163715,7 @@ exports[`csr snapshot test > csr test ./src/tabs/_example/theme.vue 1`] = `
<!---->
</transition-stub>
<!---->
<!---->
</div>

<div
Expand Down
24 changes: 12 additions & 12 deletions test/unit/snap/__snapshots__/ssr.test.js.snap

Large diffs are not rendered by default.

Loading