mirror of
https://github.com/pure-admin/vue-pure-admin.git
synced 2025-06-07 17:07:19 +08:00
feat: add anchor、tabs、treeSelect Components
This commit is contained in:
parent
8d539d4c21
commit
2e5667f652
@ -48,5 +48,8 @@ export default {
|
|||||||
hsFail: "Fail Page",
|
hsFail: "Fail Page",
|
||||||
hsIconSelect: "Icon Select",
|
hsIconSelect: "Icon Select",
|
||||||
hsTimeline: "Time Line",
|
hsTimeline: "Time Line",
|
||||||
hsLineTree: "LineTree"
|
hsLineTree: "LineTree",
|
||||||
|
hsAntTabs: "Imitate Antdv Tabs",
|
||||||
|
hsAntAnchor: "Imitate Antdv Anchor",
|
||||||
|
hsAntTreeSelect: "Imitate Antdv TreeSelector"
|
||||||
};
|
};
|
||||||
|
@ -48,5 +48,8 @@ export default {
|
|||||||
hsFail: "失败页面",
|
hsFail: "失败页面",
|
||||||
hsIconSelect: "图标选择器",
|
hsIconSelect: "图标选择器",
|
||||||
hsTimeline: "时间线",
|
hsTimeline: "时间线",
|
||||||
hsLineTree: "树形连接线"
|
hsLineTree: "树形连接线",
|
||||||
|
hsAntTabs: "仿antdv标签页",
|
||||||
|
hsAntAnchor: "仿antdv锚点",
|
||||||
|
hsAntTreeSelect: "仿antdv树型选择器"
|
||||||
};
|
};
|
||||||
|
@ -66,6 +66,33 @@ const ableRouter = {
|
|||||||
title: $t("menus.hsLineTree"),
|
title: $t("menus.hsLineTree"),
|
||||||
i18n: true
|
i18n: true
|
||||||
}
|
}
|
||||||
|
},
|
||||||
|
{
|
||||||
|
path: "/able/antTabs",
|
||||||
|
name: "reAntTabs",
|
||||||
|
component: () => import("/@/views/able/ant-tabs.vue"),
|
||||||
|
meta: {
|
||||||
|
title: $t("menus.hsAntTabs"),
|
||||||
|
i18n: true
|
||||||
|
}
|
||||||
|
},
|
||||||
|
{
|
||||||
|
path: "/able/antAnchor",
|
||||||
|
name: "reAntAnchor",
|
||||||
|
component: () => import("/@/views/able/ant-anchor.vue"),
|
||||||
|
meta: {
|
||||||
|
title: $t("menus.hsAntAnchor"),
|
||||||
|
i18n: true
|
||||||
|
}
|
||||||
|
},
|
||||||
|
{
|
||||||
|
path: "/able/antTreeSelect",
|
||||||
|
name: "reAntTreeSelect",
|
||||||
|
component: () => import("/@/views/able/ant-treeSelect.vue"),
|
||||||
|
meta: {
|
||||||
|
title: $t("menus.hsAntTreeSelect"),
|
||||||
|
i18n: true
|
||||||
|
}
|
||||||
}
|
}
|
||||||
]
|
]
|
||||||
};
|
};
|
||||||
|
@ -107,15 +107,3 @@ ul {
|
|||||||
color: var(--el-color-primary) !important;
|
color: var(--el-color-primary) !important;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
// .ant-tabs-tab-btn:focus,
|
|
||||||
// .ant-tabs-tab-remove:focus,
|
|
||||||
// .ant-tabs-tab-btn:active,
|
|
||||||
// .ant-tabs-tab-remove:active {
|
|
||||||
// color: var(--el-color-primary) !important;
|
|
||||||
// }
|
|
||||||
// .ant-tabs-tab.ant-tabs-tab-active .ant-tabs-tab-btn {
|
|
||||||
// color: var(--el-color-primary) !important;
|
|
||||||
// }
|
|
||||||
// .ant-tabs-card > div > .ant-tabs-nav .ant-tabs-tab-active {
|
|
||||||
// color: var(--el-color-primary) !important;
|
|
||||||
// }
|
|
||||||
|
66
src/views/able/ant-anchor.vue
Normal file
66
src/views/able/ant-anchor.vue
Normal file
@ -0,0 +1,66 @@
|
|||||||
|
<script setup lang="ts">
|
||||||
|
import { Anchor, AnchorLink } from "@pureadmin/components";
|
||||||
|
|
||||||
|
// const getCurrentAnchor = () => {
|
||||||
|
// return "one";
|
||||||
|
// };
|
||||||
|
|
||||||
|
function handleAnchorClick(e, link) {
|
||||||
|
e.preventDefault();
|
||||||
|
const srcolls = document.getElementById(link.href);
|
||||||
|
srcolls.scrollIntoView({ block: "start", behavior: "smooth" });
|
||||||
|
}
|
||||||
|
</script>
|
||||||
|
|
||||||
|
<template>
|
||||||
|
<el-card>
|
||||||
|
<template #header>
|
||||||
|
<div class="card-header">
|
||||||
|
<span class="font-medium"
|
||||||
|
>仿antdv锚点,采用<el-link
|
||||||
|
href="https://www.npmjs.com/package/@pureadmin/components"
|
||||||
|
target="_blank"
|
||||||
|
style="font-size: 16px; margin: 0 4px 5px"
|
||||||
|
>@pureadmin/components</el-link
|
||||||
|
>,完全兼容antdv的<el-link
|
||||||
|
href="https://next.antdv.com/components/anchor-cn"
|
||||||
|
target="_blank"
|
||||||
|
style="font-size: 16px; margin: 0 4px 5px"
|
||||||
|
>Anchor</el-link
|
||||||
|
>写法</span
|
||||||
|
>
|
||||||
|
</div>
|
||||||
|
</template>
|
||||||
|
<div class="w-400px">
|
||||||
|
<Anchor class="float-left mt-200px" @click="handleAnchorClick">
|
||||||
|
<AnchorLink href="one" title="测试one" />
|
||||||
|
<AnchorLink href="two" title="测试two" />
|
||||||
|
<AnchorLink href="three" title="测试three" />
|
||||||
|
</Anchor>
|
||||||
|
|
||||||
|
<el-scrollbar class="float-right overflow-auto" height="600px">
|
||||||
|
<header
|
||||||
|
id="one"
|
||||||
|
class="w-200px h-600px text-cyan-50 flex justify-center items-center text-4xl"
|
||||||
|
style="background: #409eff"
|
||||||
|
>
|
||||||
|
测试one
|
||||||
|
</header>
|
||||||
|
<header
|
||||||
|
id="two"
|
||||||
|
class="w-200px h-600px text-cyan-50 flex justify-center items-center text-4xl"
|
||||||
|
style="background: #67c23a"
|
||||||
|
>
|
||||||
|
测试two
|
||||||
|
</header>
|
||||||
|
<header
|
||||||
|
id="three"
|
||||||
|
class="w-200px h-600px text-cyan-50 flex justify-center items-center text-4xl"
|
||||||
|
style="background: #f56c6c"
|
||||||
|
>
|
||||||
|
测试three
|
||||||
|
</header>
|
||||||
|
</el-scrollbar>
|
||||||
|
</div>
|
||||||
|
</el-card>
|
||||||
|
</template>
|
46
src/views/able/ant-tabs.vue
Normal file
46
src/views/able/ant-tabs.vue
Normal file
@ -0,0 +1,46 @@
|
|||||||
|
<script setup lang="ts">
|
||||||
|
import { ref } from "vue";
|
||||||
|
import { Tabs, TabPane } from "@pureadmin/components";
|
||||||
|
|
||||||
|
const mode = ref("top");
|
||||||
|
const activeKey = ref(1);
|
||||||
|
const callback = (val: string) => {
|
||||||
|
console.log(val);
|
||||||
|
};
|
||||||
|
</script>
|
||||||
|
|
||||||
|
<template>
|
||||||
|
<el-card>
|
||||||
|
<template #header>
|
||||||
|
<div class="card-header">
|
||||||
|
<span class="font-medium"
|
||||||
|
>仿antdv标签页,采用<el-link
|
||||||
|
href="https://www.npmjs.com/package/@pureadmin/components"
|
||||||
|
target="_blank"
|
||||||
|
style="font-size: 16px; margin: 0 4px 5px"
|
||||||
|
>@pureadmin/components</el-link
|
||||||
|
>,完全兼容antdv的<el-link
|
||||||
|
href="https://next.antdv.com/components/tabs-cn"
|
||||||
|
target="_blank"
|
||||||
|
style="font-size: 16px; margin: 0 4px 5px"
|
||||||
|
>Tabs</el-link
|
||||||
|
>写法</span
|
||||||
|
>
|
||||||
|
</div>
|
||||||
|
</template>
|
||||||
|
<el-radio-group v-model="mode" size="small" class="mb-2">
|
||||||
|
<el-radio label="top" border>Horizontal</el-radio>
|
||||||
|
<el-radio label="left" border>Vertical</el-radio>
|
||||||
|
</el-radio-group>
|
||||||
|
<Tabs
|
||||||
|
v-model:activeKey="activeKey"
|
||||||
|
:tab-position="mode"
|
||||||
|
:style="{ height: '200px' }"
|
||||||
|
@tabScroll="callback"
|
||||||
|
>
|
||||||
|
<TabPane v-for="i in 30" :key="i" :tab="`Tab-${i}`">
|
||||||
|
Content of tab {{ i }}
|
||||||
|
</TabPane>
|
||||||
|
</Tabs>
|
||||||
|
</el-card>
|
||||||
|
</template>
|
209
src/views/able/ant-treeSelect.vue
Normal file
209
src/views/able/ant-treeSelect.vue
Normal file
@ -0,0 +1,209 @@
|
|||||||
|
<script setup lang="ts">
|
||||||
|
import { ref } from "vue";
|
||||||
|
import { TreeSelect } from "@pureadmin/components";
|
||||||
|
|
||||||
|
const value1 = ref<string>("");
|
||||||
|
const treeData1 = ref([
|
||||||
|
{
|
||||||
|
title: "parent 1",
|
||||||
|
value: "parent 1",
|
||||||
|
children: [
|
||||||
|
{
|
||||||
|
title: "parent 1-0",
|
||||||
|
value: "parent 1-0",
|
||||||
|
children: [
|
||||||
|
{
|
||||||
|
title: "my leaf",
|
||||||
|
value: "leaf1"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
title: "your leaf",
|
||||||
|
value: "leaf2"
|
||||||
|
}
|
||||||
|
]
|
||||||
|
},
|
||||||
|
{
|
||||||
|
title: "parent 1-1",
|
||||||
|
value: "parent 1-1"
|
||||||
|
}
|
||||||
|
]
|
||||||
|
}
|
||||||
|
]);
|
||||||
|
|
||||||
|
const SHOW_PARENT = TreeSelect.SHOW_PARENT;
|
||||||
|
|
||||||
|
function dig(path = "0", level = 3) {
|
||||||
|
const list = [];
|
||||||
|
for (let i = 0; i < 10; i += 1) {
|
||||||
|
const value = `${path}-${i}`;
|
||||||
|
const treeNode = {
|
||||||
|
title: value,
|
||||||
|
value
|
||||||
|
};
|
||||||
|
|
||||||
|
if (level > 0) {
|
||||||
|
// @ts-expect-error
|
||||||
|
treeNode.children = dig(value, level - 1);
|
||||||
|
}
|
||||||
|
|
||||||
|
list.push(treeNode);
|
||||||
|
}
|
||||||
|
return list;
|
||||||
|
}
|
||||||
|
|
||||||
|
const checkedKeys = ref<string[]>(["0-0-0", "0-0-1"]);
|
||||||
|
|
||||||
|
const value2 = ref<string[]>(["0-0-0"]);
|
||||||
|
const treeData2 = [
|
||||||
|
{
|
||||||
|
title: "Node1",
|
||||||
|
value: "0-0",
|
||||||
|
children: [
|
||||||
|
{
|
||||||
|
title: "Child Node1",
|
||||||
|
value: "0-0-0"
|
||||||
|
}
|
||||||
|
]
|
||||||
|
},
|
||||||
|
{
|
||||||
|
title: "Node2",
|
||||||
|
value: "0-1",
|
||||||
|
|
||||||
|
children: [
|
||||||
|
{
|
||||||
|
title: "Child Node3",
|
||||||
|
value: "0-1-0",
|
||||||
|
disabled: true
|
||||||
|
},
|
||||||
|
{
|
||||||
|
title: "Child Node4",
|
||||||
|
value: "0-1-1"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
title: "Child Node5",
|
||||||
|
value: "0-1-2"
|
||||||
|
}
|
||||||
|
]
|
||||||
|
}
|
||||||
|
];
|
||||||
|
|
||||||
|
const value3 = ref<string>();
|
||||||
|
const treeData3 = ref([
|
||||||
|
{ id: 1, pId: 0, value: "1", title: "Expand to load" },
|
||||||
|
{ id: 2, pId: 0, value: "2", title: "Expand to load" },
|
||||||
|
{ id: 3, pId: 0, value: "3", title: "Tree Node", isLeaf: true }
|
||||||
|
]);
|
||||||
|
const genTreeNode = (parentId: number, isLeaf = false) => {
|
||||||
|
const random = Math.random().toString(36).substring(2, 6);
|
||||||
|
return {
|
||||||
|
id: random,
|
||||||
|
pId: parentId,
|
||||||
|
value: random,
|
||||||
|
title: isLeaf ? "Tree Node" : "Expand to load",
|
||||||
|
isLeaf
|
||||||
|
};
|
||||||
|
};
|
||||||
|
const onLoadData = treeNode => {
|
||||||
|
return new Promise(resolve => {
|
||||||
|
const { id } = treeNode.dataRef;
|
||||||
|
setTimeout(() => {
|
||||||
|
// @ts-expect-error
|
||||||
|
treeData3.value = treeData3.value.concat([
|
||||||
|
genTreeNode(id, false),
|
||||||
|
genTreeNode(id, true)
|
||||||
|
]);
|
||||||
|
resolve(true);
|
||||||
|
}, 300);
|
||||||
|
});
|
||||||
|
};
|
||||||
|
</script>
|
||||||
|
|
||||||
|
<template>
|
||||||
|
<el-card>
|
||||||
|
<template #header>
|
||||||
|
<div class="card-header">
|
||||||
|
<span class="font-medium"
|
||||||
|
>仿antdv树选择,采用<el-link
|
||||||
|
href="https://www.npmjs.com/package/@pureadmin/components"
|
||||||
|
target="_blank"
|
||||||
|
style="font-size: 16px; margin: 0 4px 5px"
|
||||||
|
>@pureadmin/components</el-link
|
||||||
|
>,完全兼容antdv的<el-link
|
||||||
|
href="https://next.antdv.com/components/tree-select-cn"
|
||||||
|
target="_blank"
|
||||||
|
style="font-size: 16px; margin: 0 4px 5px"
|
||||||
|
>TreeSelect</el-link
|
||||||
|
>写法</span
|
||||||
|
>
|
||||||
|
</div>
|
||||||
|
</template>
|
||||||
|
<div class="flex justify-around flex-wrap">
|
||||||
|
<div>
|
||||||
|
<span>线性样式:</span>
|
||||||
|
<TreeSelect
|
||||||
|
class="w-200px"
|
||||||
|
v-model:value="value1"
|
||||||
|
show-search
|
||||||
|
:dropdown-style="{ maxHeight: '400px', overflow: 'auto' }"
|
||||||
|
placeholder="Please select"
|
||||||
|
allow-clear
|
||||||
|
:tree-line="true"
|
||||||
|
tree-default-expand-all
|
||||||
|
:tree-data="treeData1"
|
||||||
|
>
|
||||||
|
<template #title="{ value: val, title }">
|
||||||
|
<b v-if="val === 'parent 1-1'" style="color: #08c">sss</b>
|
||||||
|
<template v-else>{{ title }}</template>
|
||||||
|
</template>
|
||||||
|
</TreeSelect>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div>
|
||||||
|
<span>虚拟滚动:</span>
|
||||||
|
<TreeSelect
|
||||||
|
class="w-200px mt-6"
|
||||||
|
v-model:value="checkedKeys"
|
||||||
|
tree-checkable
|
||||||
|
tree-default-expand-all
|
||||||
|
:show-checked-strategy="SHOW_PARENT"
|
||||||
|
:height="233"
|
||||||
|
:tree-data="dig()"
|
||||||
|
:max-tag-count="10"
|
||||||
|
>
|
||||||
|
<template #title="{ title, value }">
|
||||||
|
<span v-if="value === '0-0-1-0'" style="color: #1890ff">{{
|
||||||
|
title
|
||||||
|
}}</span>
|
||||||
|
<template v-else>{{ title }}</template>
|
||||||
|
</template>
|
||||||
|
</TreeSelect>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div>
|
||||||
|
<span>可勾选:</span>
|
||||||
|
<TreeSelect
|
||||||
|
class="w-200px"
|
||||||
|
v-model:value="value2"
|
||||||
|
:tree-data="treeData2"
|
||||||
|
tree-checkable
|
||||||
|
allow-clear
|
||||||
|
:show-checked-strategy="SHOW_PARENT"
|
||||||
|
placeholder="Please select"
|
||||||
|
/>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div>
|
||||||
|
<span>异步加载:</span>
|
||||||
|
<TreeSelect
|
||||||
|
class="w-200px"
|
||||||
|
v-model:value="value3"
|
||||||
|
tree-data-simple-mode
|
||||||
|
:dropdown-style="{ maxHeight: '400px', overflow: 'auto' }"
|
||||||
|
:tree-data="treeData3"
|
||||||
|
placeholder="Please select"
|
||||||
|
:load-data="onLoadData"
|
||||||
|
/>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</el-card>
|
||||||
|
</template>
|
Loading…
x
Reference in New Issue
Block a user