搜索结果列表页面开发

This commit is contained in:
付民康
2025-03-12 18:41:20 +08:00
commit 7cebe8fc00
739 changed files with 88149 additions and 0 deletions

View File

@@ -0,0 +1,90 @@
# MilestoneItem组件
### 说明
1. MilestoneItem组件使用场景为里程碑列表
- 时间、进度条、编辑行、描述都可插槽使用,具体见下表
2. MilestoneItem使用demo
``` js
<milestone-item
:data="milestoneItemData"
@handle-edit="handleEdit"
@handle-close="handleClose"
@handle-deleted="handleDeleted"
>
</milestone-item>
const milestoneItemData = [{
title: '1.x',
desc: '完成第一个版本发布的相关功能,包括环境搭建、功能测试及 bug 修复等',
endTime: '2023-07-10',
updateTime: '2023-07-10',
finishPercent: 40,
openNum: 132,
closeNum: 88,
canEdit: true
},
{
title: '1.x',
desc: '完成第一个版本发布的相关功能,包括环境搭建、功能测试及 bug 修复等',
endTime: '2023-07-10',
updateTime: '2023-07-10',
finishPercent: 40,
openNum: 132,
closeNum: 88,
canEdit: false
}
];
const handleEdit = (item:object, index:number) => {
};
const handleClose = (item:object, index:number) => {
};
const handleDeleted = (item:object, index:number) => {
};
```
### Props
| 参数 | 说明 | 类型 | 可选值 | 默认值 |
|----------|---------------------|----------|------------|------------|
| data | 里程碑列表见下表Props(data) | array | | |
| processColor | 进度条颜色 | string | | |
### Props(data)
| 参数 | 说明 | 类型 | 可选值 | 默认值 |
| ------------- | ---------------- | ------- | ------ | ------------ |
| title | 里程碑列表 | string | | |
| desc | 进度条颜色 | string | | |
| endTime | 截止时间 | string | | 暂无截止时间 |
| updateTime | 更新时间 | string | | 暂无更新时间 |
| finishPercent | 完成百分比 | number | | 0 |
| openNum | 开启数 | number | | 0 |
| closeNum | 关闭数 | number | | 0 |
| issuesText | issues自定义文案 | string | | issues |
| canEdit | 是否编辑模式 | boolean | | false |
| typeIcon? | 标题前icon | boolean | | false |
| hideTypeIcon? | 是否隐藏标题前icon | boolean | | false |
### Slots
| 名称 | 说明 |
|---------------|---------------------------------------------------------|
| body | body内容插槽可覆盖盒子中所有内容 |
| handle | 编辑区域插槽 |
| desc | 描述区域插槽 |
| time | 时间区域插槽 |
| right | 右侧进度条区域插槽 |
### Event
| 名称 | 说明 |
| ------------- | ------------------------------------------- |
| handleEdit | 点击编辑按钮触发返回item对象和index |
| handleClose | 点击关闭里程碑按钮触发返回item对象和index |
| handleDeleted | 点击删除按钮触发返回item对象和index |

View File

@@ -0,0 +1,206 @@
<template>
<div class="g-milestone-item">
<div class="g-milestone-item-card" v-for="(item, index) in data" :key="index + '-' + item.id">
<slot name="body">
<div class="g-milestone-item-index">
<span v-if="!hideTypeIcon"><Icon :name="typeIcon" color="#707A87" size="16px"></Icon></span>
<div class="flex-auto overflow-hidden">
<div class="g-milestone-item-header">
<div class="g-milestone-item-header-title" :class="{'show-all': showAll}" @click="emits('goDetail', { ...item, index })" :title="item.title">
<slot name="title" :row="item">{{ item.title }}</slot>
</div>
<div class="w-[50px] text-right">
<slot name="handle" :row="item">
<d-dropdown align="start">
<d-icon name="icon-more-operate" rotate="90" operable></d-icon>
<template #menu>
<gc-option v-if="item.openNum" @click.stop="emits('handleEdit', { ...item, index })"><d-icon name="icon-edit" class="mr-1 align-middle"></d-icon>编辑</gc-option>
<gc-option v-if="item.openNum" @click.stop="emits('handleClose', { ...item, index })"><d-icon name="icon-remove" class="mr-1 align-middle"></d-icon>关闭</gc-option>
<gc-option @click.stop="emits('handleDeleted', { ...item, index })"><d-icon name="icon-delete" class="mr-1 align-middle" ></d-icon>删除</gc-option>
</template>
</d-dropdown>
</slot>
</div>
</div>
<div class="flex justify-between">
<div class="g-milestone-item-status flex">
<span v-if="item.openNum || item.openNum === 0">
<!-- <Number :number="item.openNum"/> -->
开启</span>
<span>{{ item.openNum }}</span>
<span class="g-milestone-item-dot"></span>
<span v-if="item.closeNum || item.closeNum === 0">
<!-- <Number :number="item.closeNum"/> -->
关闭</span>
<span>{{ item.closeNum }}</span>
<template v-if="item.finishPercent">
<span class="g-milestone-item-dot"></span>
<span>{{ item.finishPercent }}%</span>
</template>
</div>
<div>
<slot name="time">
<div class="g-milestone-item-time">
<span v-if="item.endTime">
<!-- <Time :time="item.endTime" />截止-->
{{ item.endTime }} 截止
</span>
<span v-else>暂无截止日期</span>
<span v-if="item.updateTime">
更新于<Time :time="item.updateTime" />
</span>
<span v-else>暂无更新日期</span>
</div>
</slot>
</div>
</div>
<div class="g-milestone-item-process">
<d-progress :key="item.id" :percentage="item.finishPercent" height="4px" :barBgColor="processColor"></d-progress>
</div>
<slot name="desc">
<!-- show-list样式给了最大高度52产品要求展示所有只不过只能看到一部分 -->
<div class="g-milestone-item-desc" :class="showAll ? 'show-all': 'show-list'">
<MdRender v-model="item.desc"></MdRender>
</div>
</slot>
</div>
</div>
</slot>
</div>
</div>
</template>
<script setup lang="ts">
interface MilestoneItemRow {
id?: String | number
title?: String;
desc?: String;
endTime?: String
updateTime?: String
finishPercent?: Number
openNum?: Number
closeNum?: Number
issuesText?: String
canEdit?: Boolean
}
withDefaults(defineProps<{
data: Array<MilestoneItemRow>
processColor?: string
typeIcon?: string
hideTypeIcon?: boolean
showAll?: boolean
}>(), {
data: () => [],
processColor: '#10B981',
typeIcon: 'gt-milestone',
hideTypeIcon: false
});
import MdRender from '@/components/MdRender/index.vue';
const emits = defineEmits(['handleEdit', 'handleClose', 'handleDeleted', 'goDetail']);
</script>
<style lang="scss" scoped>
$g-milestone-item-border-color: var(--color-G300);
$g-milestone-item-text-color: var(--color-G600);
$g-milestone-item-border-radius: 0px;
$g-milestone-item-font-size: 14px;
.g-milestone-item {
border-radius: $g-milestone-item-border-radius;
border-bottom-width: 0;
&-card {
padding: 16px 20px;
border-bottom: solid 1px $g-milestone-item-border-color;
@apply overflow-hidden;
}
&-index {
width: 100%;
display: flex;
gap: 0 20px;
}
&-card:last-of-type {
border-bottom: none;
}
&-header {
@apply flex gap-4 justify-between;
&-title {
font-size: $devui-font-size-card-title;
font-weight: 500;
color: var(--color-G900);
line-height: 32px;
@apply text-ellipsis whitespace-nowrap overflow-hidden break-all;
&.show-all {
@apply overflow-visible whitespace-normal break-all;
}
}
&-edit {
:deep(.devui-button) {
margin-left: 20px;
font-size: $g-milestone-item-font-size;
i {
font-size: $g-milestone-item-font-size !important;
}
}
}
}
&-desc {
font-size: $g-milestone-item-font-size;
color: $g-milestone-item-text-color;
@apply mt-2 text-ellipsis whitespace-nowrap overflow-hidden;
&.show-all {
@apply overflow-visible whitespace-normal whitespace-pre-wrap break-all;
}
&.show-list{
@apply overflow-visible whitespace-normal whitespace-pre-wrap break-all;
max-height: 52px;
overflow: hidden;
}
}
&-dot {
display: block;
width: 1px;
height: 12px;
background-color: $g-milestone-item-border-color;
margin-top: 5px;
}
&-time {
color: $g-milestone-item-text-color;
font-size: $g-milestone-item-font-size;
display: flex;
span {
margin-left: 16px;
}
}
&-process {
margin-top: 8px;
}
&-status {
color: $g-milestone-item-text-color;
span {
margin-right: 8px;
font-size: $g-milestone-item-font-size;
}
}
}
</style>