初版卡片列表模板.

This commit is contained in:
lijiahang
2023-09-29 17:24:25 +08:00
parent 93edcd216a
commit 05af36a578
4 changed files with 175 additions and 38 deletions

View File

@@ -2,9 +2,9 @@
-- 父菜单 -- 父菜单
INSERT INTO system_menu INSERT INTO system_menu
(parent_id, name, type, sort, visible, status, cache) (parent_id, name, type, sort, visible, status, cache, component)
VALUES VALUES
(0, '${table.comment}管理', 1, 10, 1, 1, 1); (0, '${table.comment}管理', 1, 10, 1, 1, 1, '$vue.moduleEntityFirstLower');
-- 设置临时父菜单id -- 设置临时父菜单id
SELECT @TMP_PARENT_ID:=LAST_INSERT_ID(); SELECT @TMP_PARENT_ID:=LAST_INSERT_ID();

View File

@@ -1,6 +1,7 @@
.layout-container { .layout-container {
background-color: var(--color-fill-2); background-color: var(--color-fill-2);
padding: 16px 16px 0 16px; // fixme
// padding: 16px 16px 0 16px;
display: flex; display: flex;
flex-direction: column; flex-direction: column;
} }

View File

@@ -4,19 +4,22 @@
<icon-apps /> <icon-apps />
</a-breadcrumb-item> </a-breadcrumb-item>
<a-breadcrumb-item v-for="item in items" :key="item"> <a-breadcrumb-item v-for="item in items" :key="item">
{{ $t(item) }} {{ item }}
</a-breadcrumb-item> </a-breadcrumb-item>
</a-breadcrumb> </a-breadcrumb>
</template> </template>
<script lang="ts" setup> <script lang="ts" setup>
import { PropType } from 'vue'; import { PropType } from 'vue';
import { useRoute } from 'vue-router';
defineProps({ defineProps({
items: { items: {
type: Array as PropType<string[]>, type: Array as PropType<string[]>,
default() { default() {
return []; return useRoute().matched
.map(s => s.meta?.locale)
.filter(Boolean) || [];
}, },
}, },
}); });
@@ -24,7 +27,6 @@
<style scoped lang="less"> <style scoped lang="less">
.container-breadcrumb { .container-breadcrumb {
margin: 16px 0;
:deep(.arco-breadcrumb-item) { :deep(.arco-breadcrumb-item) {
color: rgb(var(--gray-6)); color: rgb(var(--gray-6));

View File

@@ -1,33 +1,55 @@
<template> <template>
<div class="card-list-layout"> <div class="card-list-layout">
<!-- 头部固定 -->
<div class="card-list-layout-top" :style="{width: `calc(100% - ${menuWidth}px)`}">
<!-- 路由面包屑 -->
<Breadcrumb />
<!-- header -->
<div class="card-list-header"> <div class="card-list-header">
<!-- title slot --> <!-- 左侧固定 -->
<!-- plusIcon | field field field searchFieldInput searchIcon resetIcon -->
<!-- margin -->
<!-- cardList / empty -->
<!-- margin -->
<!-- page -->
<div>
title
</div>
<div class="card-list-header-left"> <div class="card-list-header-left">
<a-space>
<!-- 创建 -->
<div class="header-icon-wrapper">
<icon-plus />
</div> </div>
<!-- 条件显示 -->
</a-space>
</div>
<!-- 右侧固定 -->
<div class="card-list-header-right"> <div class="card-list-header-right">
right search/add <a-space>
<!-- 搜索框 -->
<a-input size="small" placeholder="输入名称/地址">
<template #suffix>
<icon-search />
</template>
</a-input>
<!-- 条件 -->
<div class="header-icon-wrapper">
<icon-filter />
</div>
<!-- 刷新 -->
<div class="header-icon-wrapper">
<icon-refresh />
</div>
</a-space>
</div> </div>
</div> </div>
<div> </div>
card 区域 <!-- 固定身体 -->
<a-row :gutter="cardLayoutGutter"> <div class="card-list-layout-body">
<!-- 卡片列表 -->
<a-row v-if="list.length === 0"
:gutter="cardLayoutGutter">
<!-- 数据卡片 -->
<a-col v-for="item in list" <a-col v-for="item in list"
:key="item.id" :key="item.id"
class="wrapper"
v-bind="cardLayoutCols"> v-bind="cardLayoutCols">
<a-card class="general-card" <a-card class="general-card card-list-item"
:bordered="false" :bordered="false"
:hoverable="true" :hoverable="true">
style="width: 98%; height: 120px;">
<template #title> <template #title>
{{ item.name }} {{ item.name }}
</template> </template>
@@ -36,12 +58,32 @@
</template> </template>
</a-card> </a-card>
</a-col> </a-col>
</a-row> <!-- 添加卡片 -->
<a-col v-bind="cardLayoutCols">
<a-card class="general-card card-list-item"
:body-style="{ height: '100%' }"
:bordered="false"
:hoverable="true">
<div class="create-card-body">
<icon-plus class="create-card-body-icon" />
<span class="create-card-body-text">点击进行创建</span>
</div> </div>
</a-card>
</a-col>
</a-row>
<!-- 空列表 -->
<template v-else>
<a-card class="general-card empty-list-card"
:body-style="{ height: '100%' }">
<a-empty description="暂无数据 点击进行创建" />
</a-card>
</template>
<!-- 翻页区域 -->
<div> <div>
page 区域 page 区域
</div> </div>
</div> </div>
</div>
</template> </template>
<script lang="ts"> <script lang="ts">
@@ -51,7 +93,15 @@
</script> </script>
<script setup lang="ts"> <script setup lang="ts">
import { ref } from 'vue'; import { computed, ref } from 'vue';
import { useAppStore } from '@/store';
const appStore = useAppStore();
const menuWidth = computed(() => {
return appStore.menu && !appStore.topMenu && !appStore.hideMenu
? appStore.menuCollapse ? 48 : appStore.menuWidth
: 0;
});
const cardLayoutGutter = [ const cardLayoutGutter = [
{ xs: 16, sm: 16, md: 16 }, { xs: 16, sm: 16, md: 16 },
@@ -62,14 +112,14 @@
xs: 24, xs: 24,
sm: 12, sm: 12,
md: 8, md: 8,
lg: 6, lg: 8,
xl: 4, xl: 6,
xxl: 4, xxl: 4,
}; };
const list = ref<Array<any>>([]); const list = ref<Array<any>>([]);
for (let i = 0; i < 20; i++) { for (let i = 0; i < 18; i++) {
list.value.push({ list.value.push({
id: i + 1, id: i + 1,
name: `名称 ${i + 1}`, name: `名称 ${i + 1}`,
@@ -80,29 +130,113 @@
</script> </script>
<style scoped lang="less"> <style scoped lang="less">
@header-height: 48;
@top-width: 16 + 24 + 16 + 48 + 16;
@header-height-px: @{header-height}px;
@top-width-px: @{top-width}px;
@card-height: 120;
@card-height-px: @{card-height}px;
@empty-list-card-height: 120 * 2 + 16;
@empty-list-card-height-px: @{empty-list-card-height}px;
.card-list-layout-body {
margin-top: @top-width-px;
}
.card-list-layout { .card-list-layout {
&-top {
padding: 16px;
position: fixed;
background: var(--color-fill-2);
z-index: 999;
height: @top-width-px;
transition: none;
}
&-body {
padding: 0 16px 16px 16px;
}
.card-list-header { .card-list-header {
display: flex; display: flex;
justify-content: space-between; justify-content: space-between;
align-items: center; align-items: center;
background: var(--color-bg-4); background: var(--color-bg-4);
height: @header-height-px;
padding: 12px;
margin-top: 16px;
&-left { &-left {
color: red; display: flex;
align-items: center;
} }
&-right { &-right {
color: blue; display: flex;
align-items: center;
} }
} }
} }
.general-card { .header-icon-wrapper {
display: flex;
justify-content: center;
align-items: center;
width: 27px;
height: 27px;
color: var(--color-text-2);
background: var(--color-fill-2);
border-radius: 2px;
cursor: pointer;
border: 1px solid transparent;
transition: background-color 0.1s cubic-bezier(0, 0, 1, 1);
}
.header-icon-wrapper:hover {
background: var(--color-fill-3);
}
.card-list-item {
height: @card-height-px;
transition-property: all; transition-property: all;
} }
.general-card:hover { .card-list-item:hover {
transform: translateY(-4px); transform: translateY(-4px);
box-shadow: 2px 2px 12px rgba(0, 0, 0, .15);
} }
.create-card-body {
width: 100%;
height: 100%;
display: flex;
align-items: center;
flex-direction: column;
justify-content: center;
cursor: pointer;
&-icon {
font-size: 18px;
margin-bottom: 4px;
}
&-text {
color: rgb(var(--arcoblue-6)) !important;
}
}
.empty-list-card {
height: @empty-list-card-height-px;
}
.empty-list {
height: 100%;
display: flex;
align-items: center;
flex-direction: column;
justify-content: center;
}
</style> </style>