feat ui设计稿
This commit is contained in:
@@ -309,15 +309,15 @@ function clearChips(): void {
|
||||
<style lang="less" scoped>
|
||||
.case-filter {
|
||||
flex-shrink: 0;
|
||||
width: 300px;
|
||||
padding: @spacing-lg 0 @spacing-base;
|
||||
width: 397px; // 设计04 面板 516 × 0.77
|
||||
padding: 12px 0 40px; // 顶 15 × 0.77 / 底 50 × 0.77
|
||||
border-radius: @radius-base;
|
||||
background: @white;
|
||||
|
||||
&__head,
|
||||
&__group,
|
||||
&__actions {
|
||||
padding: 0 @spacing-base;
|
||||
padding: 0 38px 0 27px; // 内容左 35 × 0.77 / 右 50 × 0.77
|
||||
}
|
||||
|
||||
&__head {
|
||||
@@ -325,13 +325,13 @@ function clearChips(): void {
|
||||
}
|
||||
|
||||
&__title {
|
||||
font-size: @font-size-lg;
|
||||
font-weight: 600;
|
||||
color: @heading-color;
|
||||
font-size: 22px; // 设计 28 × 0.77
|
||||
font-weight: 500;
|
||||
color: @cases-filter-title;
|
||||
}
|
||||
|
||||
&__link {
|
||||
color: @primary-color;
|
||||
color: @primary-strong;
|
||||
font-size: @font-size-base;
|
||||
|
||||
&:hover {
|
||||
@@ -343,25 +343,30 @@ function clearChips(): void {
|
||||
margin-top: @spacing-lg;
|
||||
}
|
||||
|
||||
// 标题 → 第一组(设计 11 × 0.77)
|
||||
&__head + &__group {
|
||||
margin-top: 9px;
|
||||
}
|
||||
|
||||
&__group-title {
|
||||
font-size: @font-size-base;
|
||||
font-weight: 600;
|
||||
color: @heading-color;
|
||||
font-size: 18px; // 设计 24 × 0.77
|
||||
font-weight: 500;
|
||||
color: @cases-text;
|
||||
}
|
||||
|
||||
/* 业务类型:整行可点,选中整行铺满底色 */
|
||||
&__rows {
|
||||
margin-top: @spacing-sm;
|
||||
margin-top: 14px; // 设计 19 × 0.77
|
||||
}
|
||||
|
||||
&__row {
|
||||
.flex(row, flex-start, center);
|
||||
gap: @spacing-sm;
|
||||
gap: 9px; // 设计 12 × 0.77
|
||||
width: 100%;
|
||||
height: 36px;
|
||||
padding: 0 @spacing-base;
|
||||
color: @text-color;
|
||||
font-size: @font-size-base;
|
||||
height: 38px; // 行距 50 × 0.77
|
||||
padding: 0;
|
||||
color: @cases-text;
|
||||
font-size: 15px; // 设计 20 × 0.77
|
||||
text-align: left;
|
||||
transition: background 0.2s;
|
||||
|
||||
@@ -371,7 +376,7 @@ function clearChips(): void {
|
||||
|
||||
&.is-active {
|
||||
background: @filter-selected-bg;
|
||||
color: @primary-color;
|
||||
color: @primary-strong;
|
||||
font-weight: 600;
|
||||
}
|
||||
}
|
||||
@@ -379,22 +384,22 @@ function clearChips(): void {
|
||||
&__box {
|
||||
position: relative;
|
||||
flex-shrink: 0;
|
||||
width: 14px;
|
||||
height: 14px;
|
||||
border: 1px solid @border-color-dark;
|
||||
width: 12px; // 设计 16 × 0.77
|
||||
height: 12px;
|
||||
border: 1px solid @cases-input-border;
|
||||
border-radius: 2px;
|
||||
|
||||
.case-filter__row.is-active & {
|
||||
border-color: @primary-color;
|
||||
background: @primary-color;
|
||||
border-color: @primary-strong;
|
||||
background: @primary-strong;
|
||||
|
||||
&::after {
|
||||
content: '';
|
||||
position: absolute;
|
||||
top: 1px;
|
||||
left: 4px;
|
||||
left: 3px;
|
||||
width: 4px;
|
||||
height: 7px;
|
||||
height: 6px;
|
||||
border: solid @white;
|
||||
border-width: 0 1.5px 1.5px 0;
|
||||
transform: rotate(45deg);
|
||||
@@ -408,51 +413,55 @@ function clearChips(): void {
|
||||
}
|
||||
|
||||
&__row-count {
|
||||
color: @text-color-secondary;
|
||||
color: @cases-muted;
|
||||
font-weight: 400;
|
||||
}
|
||||
|
||||
// 选中行的计数随行文字变蓝、加粗(设计15)
|
||||
.case-filter__row.is-active &__row-count {
|
||||
color: inherit;
|
||||
font-weight: inherit;
|
||||
}
|
||||
|
||||
/* 胶囊选项(两列;minmax(0,1fr) 防止内部长内容(日期区间)把列撑宽) */
|
||||
&__pills {
|
||||
display: grid;
|
||||
grid-template-columns: repeat(2, minmax(0, 1fr));
|
||||
gap: @spacing-sm;
|
||||
margin-top: @spacing-sm;
|
||||
gap: 18px 25px; // 行距 24 × 0.77 / 列距 33 × 0.77
|
||||
margin-top: 15px; // 设计 21 × 0.77
|
||||
}
|
||||
|
||||
&__pill {
|
||||
height: 34px;
|
||||
height: 41px; // 设计 53 × 0.77
|
||||
padding: 0 @spacing-sm;
|
||||
border-radius: @radius-round;
|
||||
border-radius: @radius-base;
|
||||
background: @pill-bg;
|
||||
color: @text-color;
|
||||
font-size: @font-size-base;
|
||||
color: @cases-text;
|
||||
font-size: 15px; // 设计 20 × 0.77
|
||||
.ellipsis();
|
||||
transition: all 0.2s;
|
||||
|
||||
&:hover {
|
||||
color: @primary-color;
|
||||
}
|
||||
|
||||
&.is-active {
|
||||
background: @primary-color;
|
||||
color: @white;
|
||||
color: @primary-strong;
|
||||
}
|
||||
|
||||
&.is-active,
|
||||
&.is-light {
|
||||
background: @pill-selected-bg;
|
||||
color: @primary-color;
|
||||
font-weight: 600;
|
||||
color: @white;
|
||||
font-weight: 500;
|
||||
}
|
||||
}
|
||||
|
||||
&__date {
|
||||
grid-column: 1 / -1;
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
width: 100%;
|
||||
min-width: 0;
|
||||
height: 34px;
|
||||
height: 41px;
|
||||
padding: 0 @spacing-sm;
|
||||
border-radius: @radius-round;
|
||||
border-radius: @radius-base;
|
||||
background: @input-bg;
|
||||
box-shadow: none;
|
||||
|
||||
@@ -471,18 +480,18 @@ function clearChips(): void {
|
||||
flex: 0 1 auto;
|
||||
width: 76px;
|
||||
background: transparent;
|
||||
color: @text-color;
|
||||
font-size: @font-size-sm;
|
||||
color: @cases-text;
|
||||
font-size: 15px;
|
||||
|
||||
&::placeholder {
|
||||
color: @text-color-secondary;
|
||||
color: @cases-text;
|
||||
}
|
||||
}
|
||||
|
||||
:deep(.el-range-separator) {
|
||||
color: @text-color-secondary;
|
||||
font-size: @font-size-sm;
|
||||
line-height: 34px;
|
||||
color: @cases-text;
|
||||
font-size: 15px;
|
||||
line-height: 41px;
|
||||
}
|
||||
|
||||
&.is-focus {
|
||||
@@ -492,8 +501,8 @@ function clearChips(): void {
|
||||
|
||||
/* 已选条件 */
|
||||
&__selected {
|
||||
margin-top: @spacing-lg;
|
||||
padding: @spacing-base;
|
||||
margin: 18px 38px 0 27px; // 上距 23 × 0.77,左右与内容对齐(50/35 × 0.77)
|
||||
padding: 12px 18px 16px; // 设计 16/24/21 × 0.77
|
||||
border-radius: @radius-base;
|
||||
background: @chips-panel-bg;
|
||||
}
|
||||
@@ -503,31 +512,32 @@ function clearChips(): void {
|
||||
}
|
||||
|
||||
&__selected-title {
|
||||
color: @primary-color;
|
||||
font-size: @font-size-base;
|
||||
font-weight: 600;
|
||||
color: @cases-text;
|
||||
font-size: 15px; // 设计 20 × 0.77
|
||||
font-weight: 500;
|
||||
}
|
||||
|
||||
&__selected-empty {
|
||||
margin-top: @spacing-sm;
|
||||
color: @text-color-secondary;
|
||||
color: @cases-muted;
|
||||
font-size: @font-size-sm;
|
||||
}
|
||||
|
||||
&__chips {
|
||||
.flex(row, flex-start, center);
|
||||
flex-wrap: wrap;
|
||||
gap: @spacing-sm;
|
||||
margin-top: @spacing-sm;
|
||||
gap: 11px 10px; // 行距 14 × 0.77 / 列距 13 × 0.77
|
||||
margin-top: 12px; // 设计 16 × 0.77
|
||||
}
|
||||
|
||||
&__chip {
|
||||
height: 26px;
|
||||
height: 25px; // 设计 32 × 0.77
|
||||
padding: 0 @spacing-sm;
|
||||
border-radius: @radius-round;
|
||||
background: @white;
|
||||
color: @primary-color;
|
||||
font-size: @font-size-sm;
|
||||
color: @cases-accent;
|
||||
font-size: 11px; // 设计 14 → 10.8,取可读下限 11
|
||||
font-weight: 500;
|
||||
transition: color 0.2s;
|
||||
|
||||
&:hover {
|
||||
@@ -538,36 +548,37 @@ function clearChips(): void {
|
||||
/* 底部操作 */
|
||||
&__actions {
|
||||
.flex(row, flex-start, center);
|
||||
gap: @spacing-sm;
|
||||
margin-top: @spacing-base;
|
||||
gap: 10px; // 设计 13 × 0.77
|
||||
margin-top: 23px; // 设计 30 × 0.77
|
||||
}
|
||||
|
||||
&__reset {
|
||||
width: 88px;
|
||||
height: 36px;
|
||||
width: 104px; // 设计 135 × 0.77
|
||||
height: 23px; // 设计 30 × 0.77
|
||||
border-radius: @radius-round;
|
||||
background: @pill-bg;
|
||||
color: @text-color;
|
||||
font-size: @font-size-base;
|
||||
transition: color 0.2s;
|
||||
background: @cases-reset-bg;
|
||||
color: @black;
|
||||
font-size: 11px; // 设计 14 → 10.8,取可读下限 11
|
||||
font-weight: 400;
|
||||
transition: filter 0.2s;
|
||||
|
||||
&:hover {
|
||||
color: @primary-color;
|
||||
filter: brightness(0.96);
|
||||
}
|
||||
}
|
||||
|
||||
&__confirm {
|
||||
flex: 1;
|
||||
height: 36px;
|
||||
height: 23px;
|
||||
border-radius: @radius-round;
|
||||
background: @primary-color;
|
||||
background: @cases-confirm;
|
||||
color: @white;
|
||||
font-size: @font-size-base;
|
||||
font-weight: 600;
|
||||
font-size: 11px;
|
||||
font-weight: 400;
|
||||
transition: background 0.2s;
|
||||
|
||||
&:hover {
|
||||
background: @primary-hover;
|
||||
background: @cases-accent;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -41,16 +41,16 @@ const emit = defineEmits<{
|
||||
<style lang="less" scoped>
|
||||
.cases-grid {
|
||||
&__total {
|
||||
font-size: 24px;
|
||||
font-weight: 600;
|
||||
font-size: 15px; // 设计15 计数 20 × 0.77
|
||||
font-weight: 700;
|
||||
color: @heading-color;
|
||||
}
|
||||
|
||||
&__list {
|
||||
display: grid;
|
||||
grid-template-columns: repeat(3, 1fr);
|
||||
gap: @spacing-base;
|
||||
margin-top: @spacing-base;
|
||||
gap: 18px 22px; // 设计04 行距 23 / 列距 28 × 0.77
|
||||
margin-top: 12px; // 设计15 计数 → 卡片 15 × 0.77
|
||||
}
|
||||
|
||||
&__empty {
|
||||
|
||||
@@ -60,65 +60,68 @@ const keyword = computed<string>({
|
||||
<style lang="less" scoped>
|
||||
.case-search {
|
||||
.flex(row, flex-start, center);
|
||||
gap: @spacing-sm;
|
||||
padding: @spacing-base @spacing-lg;
|
||||
gap: 18px; // 按钮间距 24 × 0.77
|
||||
padding: 30px 36px; // 卡片 128 高、输入 49 高:上下 40 × 0.77 / 左右 47 × 0.77
|
||||
border-radius: @radius-base;
|
||||
background: @white;
|
||||
|
||||
&__field {
|
||||
position: relative;
|
||||
flex: 1;
|
||||
max-width: 520px;
|
||||
max-width: 456px; // 设计输入框 592 × 0.77
|
||||
margin-right: 28px; // 与按钮总间距 60 × 0.77(叠加 bar gap 18)
|
||||
}
|
||||
|
||||
&__icon {
|
||||
position: absolute;
|
||||
top: 50%;
|
||||
left: 12px;
|
||||
width: 16px;
|
||||
height: 16px;
|
||||
right: 16px; // 设计放大镜在输入框右侧
|
||||
left: auto;
|
||||
width: 20px; // 设计 27 × 0.77
|
||||
height: 20px;
|
||||
transform: translateY(-50%);
|
||||
fill: none;
|
||||
stroke: @text-color-secondary;
|
||||
stroke: @cases-icon;
|
||||
stroke-width: 1.8;
|
||||
}
|
||||
|
||||
&__input {
|
||||
width: 100%;
|
||||
height: 36px;
|
||||
padding: 0 @spacing-base 0 36px;
|
||||
border: 1px solid transparent;
|
||||
border-radius: @radius-base;
|
||||
background: @input-bg;
|
||||
color: @text-color;
|
||||
font-size: @font-size-base;
|
||||
height: 38px; // 设计 49 × 0.77
|
||||
padding: 0 44px 0 16px;
|
||||
border: 1px solid @cases-input-border;
|
||||
border-radius: @radius-sm;
|
||||
background: @white;
|
||||
color: @cases-text;
|
||||
font-size: 15px; // 设计 20 × 0.77
|
||||
outline: none;
|
||||
transition: border-color 0.2s;
|
||||
|
||||
&::placeholder {
|
||||
color: @text-color-secondary;
|
||||
color: @cases-input-border; // 设计占位 @cases-input-border
|
||||
}
|
||||
|
||||
&:focus {
|
||||
border-color: @primary-color;
|
||||
border-color: @cases-accent;
|
||||
}
|
||||
}
|
||||
|
||||
&__btn {
|
||||
height: 36px;
|
||||
padding: 0 @spacing-lg;
|
||||
border-radius: @radius-base;
|
||||
background: @pill-bg;
|
||||
color: @text-color;
|
||||
font-size: @font-size-base;
|
||||
min-width: 77px; // 设计 100 × 0.77
|
||||
height: 38px; // 设计 49 × 0.77
|
||||
padding: 0 @spacing-base;
|
||||
border-radius: @radius-sm;
|
||||
background: @cases-accent; // 设计 重置/搜索 均为 rgba(7,92,255)
|
||||
color: @white;
|
||||
font-size: 15px; // 设计 20 × 0.77
|
||||
transition: all 0.2s;
|
||||
|
||||
&:hover {
|
||||
color: @primary-color;
|
||||
background: @primary-hover;
|
||||
}
|
||||
|
||||
&--primary {
|
||||
background: @primary-color;
|
||||
background: @cases-accent;
|
||||
color: @white;
|
||||
|
||||
&:hover {
|
||||
|
||||
@@ -111,23 +111,24 @@ onMounted(() => {
|
||||
|
||||
<style lang="less" scoped>
|
||||
.cases {
|
||||
padding-bottom: @spacing-xxl;
|
||||
padding-bottom: 60px; // 设计04 正文 → 页脚 78 × 0.77
|
||||
|
||||
&__hero {
|
||||
padding: @spacing-lg 0;
|
||||
padding: 25px 0 33px; // 标题上 32 / 标语下 43 × 0.77
|
||||
background: @white;
|
||||
}
|
||||
|
||||
&__title {
|
||||
font-size: @font-size-xxl;
|
||||
font-weight: 600;
|
||||
color: @heading-color;
|
||||
font-size: @font-size-xxl; // 设计 36 × 0.77 ≈ 28
|
||||
font-weight: 700;
|
||||
color: @cases-hero-title;
|
||||
}
|
||||
|
||||
&__slogan {
|
||||
margin-top: @spacing-xs;
|
||||
font-size: @font-size-base;
|
||||
color: @text-color-secondary;
|
||||
margin-top: 12px; // 设计 15 × 0.77
|
||||
font-size: 18.5px; // 设计 24 × 0.77
|
||||
font-weight: 500;
|
||||
color: @cases-muted;
|
||||
}
|
||||
|
||||
&__body {
|
||||
@@ -139,7 +140,7 @@ onMounted(() => {
|
||||
&__main {
|
||||
.flex(column, flex-start);
|
||||
flex: 1;
|
||||
gap: @spacing-base;
|
||||
gap: 18px; // 设计04 搜索卡 → 卡片网格 23 × 0.77
|
||||
min-width: 0;
|
||||
}
|
||||
|
||||
|
||||
@@ -63,17 +63,17 @@ const SIGN_VARIANTS: Record<SignStatus, 'primary' | 'success' | 'warning' | 'dan
|
||||
关联项目
|
||||
</h3>
|
||||
<div class="contract-info__related-body">
|
||||
<div class="contract-info__field">
|
||||
<span class="contract-info__label text-secondary">
|
||||
项目名称
|
||||
<button class="contract-info__link" @click="emit('viewProject')">查看详情</button>
|
||||
</span>
|
||||
<span class="contract-info__value">{{ contract.relatedProjectName }}</span>
|
||||
</div>
|
||||
<div class="contract-info__field">
|
||||
<span class="contract-info__label text-secondary">项目编号</span>
|
||||
<span class="contract-info__value">{{ contract.projectNo }}</span>
|
||||
</div>
|
||||
<div class="contract-info__field">
|
||||
<span class="contract-info__label text-secondary">项目名称</span>
|
||||
<span class="contract-info__value">{{ contract.relatedProjectName }}</span>
|
||||
</div>
|
||||
<button class="contract-info__link" @click="emit('viewProject')">
|
||||
查看详情
|
||||
</button>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
@@ -112,60 +112,90 @@ const SIGN_VARIANTS: Record<SignStatus, 'primary' | 'success' | 'warning' | 'dan
|
||||
</template>
|
||||
|
||||
<style lang="less" scoped>
|
||||
// 合同详情信息区(设计 40:灰底页面直排、标签 + 灰底值框、蓝竖条区块标题)
|
||||
.contract-info {
|
||||
.flex(column, flex-start);
|
||||
gap: @spacing-lg;
|
||||
padding: @spacing-lg @spacing-xl;
|
||||
border-radius: @radius-lg;
|
||||
background: @white;
|
||||
box-shadow: @shadow-base;
|
||||
.flex(column, flex-start, stretch);
|
||||
gap: 24px;
|
||||
|
||||
&__grid {
|
||||
&__grid,
|
||||
&__related-body {
|
||||
display: grid;
|
||||
grid-template-columns: repeat(2, 1fr);
|
||||
gap: @spacing-base @spacing-xl;
|
||||
column-gap: 46px; // 列间距 60 设计 × 0.77
|
||||
row-gap: 15px; // 行间距 20 设计 × 0.77
|
||||
}
|
||||
|
||||
&__field {
|
||||
.flex(row, flex-start, center);
|
||||
gap: @spacing-sm;
|
||||
.flex(column, flex-start, stretch);
|
||||
gap: 6px; // 标签 → 值框(设计 8 × 0.77)
|
||||
min-width: 0;
|
||||
}
|
||||
|
||||
&__label {
|
||||
flex-shrink: 0;
|
||||
width: 70px;
|
||||
font-size: @font-size-sm;
|
||||
font-size: 11px; // 设计 13 → 可读下限
|
||||
font-weight: 500;
|
||||
line-height: 1.4;
|
||||
color: @heading-color; // 设计 @heading-color(覆盖 .text-secondary)
|
||||
}
|
||||
|
||||
// 值框:设计 40 实取 #F3F4F6 底 + 浅描边,高 38 设计 × 0.77
|
||||
&__value {
|
||||
font-size: @font-size-base;
|
||||
color: @heading-color;
|
||||
width: 100%;
|
||||
height: 29px;
|
||||
padding: 0 10px;
|
||||
border: 1px solid @border-color;
|
||||
border-radius: @radius-sm;
|
||||
background: @input-bg;
|
||||
font-size: 11px;
|
||||
line-height: 27px;
|
||||
color: @text-color; // 设计 @text-color
|
||||
.ellipsis();
|
||||
}
|
||||
|
||||
// 合同状态(StatusTag)同样入灰底值框,去彩色胶囊
|
||||
&__field :deep(.status-tag) {
|
||||
width: 100%;
|
||||
height: 29px;
|
||||
padding: 0 10px;
|
||||
border: 1px solid @border-color;
|
||||
border-radius: @radius-sm;
|
||||
background: @input-bg;
|
||||
font-size: 11px;
|
||||
line-height: 27px;
|
||||
color: @text-color;
|
||||
}
|
||||
|
||||
// 区块标题:蓝色竖条(设计 40 实取 4×17 设计px #024FFF)+ 15 设计px 半粗
|
||||
&__section-title {
|
||||
margin-bottom: @spacing-base;
|
||||
font-size: @font-size-lg;
|
||||
font-weight: 600;
|
||||
position: relative;
|
||||
padding-left: 10px;
|
||||
margin-bottom: 14px; // 设计 18 × 0.77
|
||||
font-size: @font-size-sm; // 12px = 设计 15 × 0.77
|
||||
font-weight: 700;
|
||||
line-height: 16px;
|
||||
color: @heading-color;
|
||||
|
||||
&::before {
|
||||
content: '';
|
||||
position: absolute;
|
||||
left: 0;
|
||||
top: 50%;
|
||||
width: 4px;
|
||||
height: 15px;
|
||||
border-radius: @radius-round;
|
||||
background: @primary-strong;
|
||||
transform: translateY(-50%);
|
||||
}
|
||||
}
|
||||
|
||||
&__related,
|
||||
&__files-section {
|
||||
padding-top: @spacing-base;
|
||||
border-top: 1px solid @border-color;
|
||||
}
|
||||
|
||||
&__related-body {
|
||||
.flex(row, flex-start, center);
|
||||
flex-wrap: wrap;
|
||||
gap: @spacing-base;
|
||||
margin-top: 6px; // 区块间距合计 30(设计 40 × 0.77)
|
||||
}
|
||||
|
||||
&__link {
|
||||
font-size: @font-size-base;
|
||||
color: @primary-color;
|
||||
font-size: 11px; // 设计 10 → 可读下限
|
||||
font-weight: 500;
|
||||
color: @primary-strong;
|
||||
transition: opacity 0.2s;
|
||||
|
||||
&:hover {
|
||||
@@ -173,34 +203,44 @@ const SIGN_VARIANTS: Record<SignStatus, 'primary' | 'success' | 'warning' | 'dan
|
||||
}
|
||||
}
|
||||
|
||||
// 设计 40:「项目名称 查看详情」同一行内联
|
||||
&__label &__link {
|
||||
margin-left: 3px;
|
||||
}
|
||||
|
||||
&__files {
|
||||
.flex(column, flex-start);
|
||||
.flex(column, flex-start, stretch);
|
||||
gap: @spacing-sm;
|
||||
}
|
||||
|
||||
// 文件行:设计 40 浅灰通栏底(#F7F8FA),无描边
|
||||
&__file {
|
||||
.flex(row, space-between);
|
||||
gap: @spacing-base;
|
||||
padding: @spacing-sm @spacing-base;
|
||||
border: 1px solid @border-color;
|
||||
min-height: 42px; // 通栏高 54 设计 × 0.77
|
||||
padding: 7px 16px;
|
||||
border: none;
|
||||
border-radius: @radius-base;
|
||||
background: @bg-color-light;
|
||||
background: @finance-row-bg;
|
||||
}
|
||||
|
||||
&__file-info {
|
||||
.flex(column, flex-start);
|
||||
.flex(column, flex-start, stretch);
|
||||
gap: 2px;
|
||||
min-width: 0;
|
||||
}
|
||||
|
||||
&__file-name {
|
||||
font-size: @font-size-base;
|
||||
color: @heading-color;
|
||||
font-size: 11px;
|
||||
line-height: 1.3;
|
||||
color: @heading-color; // 设计 @heading-color
|
||||
.ellipsis();
|
||||
}
|
||||
|
||||
&__file-meta {
|
||||
font-size: @font-size-sm;
|
||||
font-size: 11px; // 设计 11 → 可读下限
|
||||
line-height: 1.3;
|
||||
color: @text-color-disabled; // 设计 @text-color-disabled
|
||||
}
|
||||
|
||||
&__file-actions {
|
||||
|
||||
@@ -23,20 +23,20 @@ const emit = defineEmits<{ refresh: [] }>()
|
||||
</template>
|
||||
|
||||
<style lang="less" scoped>
|
||||
// 签署卡(设计 39:白底圆角卡、二维码直接置于卡面、右侧四步指引)
|
||||
.sign-panel {
|
||||
.flex(row, flex-start, stretch);
|
||||
gap: @spacing-lg;
|
||||
padding: @spacing-xl;
|
||||
.flex(row, flex-start, flex-start);
|
||||
gap: 48px; // 二维码区 → 步骤区(设计 63 × 0.77)
|
||||
padding: 28px 32px; // 卡内边距(设计 37/40 × 0.77)
|
||||
border-radius: @radius-lg;
|
||||
background: @white;
|
||||
box-shadow: @shadow-base;
|
||||
|
||||
&__left {
|
||||
.flex(row, center);
|
||||
flex-shrink: 0;
|
||||
padding: @spacing-lg;
|
||||
border-radius: @radius-base;
|
||||
background: @bg-color-light;
|
||||
padding: 0;
|
||||
background: transparent;
|
||||
border-radius: 0;
|
||||
}
|
||||
|
||||
&__right {
|
||||
|
||||
@@ -81,32 +81,44 @@ const SIGN_VARIANTS: Record<SignStatus, 'primary' | 'success' | 'warning' | 'dan
|
||||
<style lang="less" scoped>
|
||||
.contract-table {
|
||||
overflow-x: auto;
|
||||
border-radius: @radius-lg;
|
||||
background: @white;
|
||||
box-shadow: @shadow-base;
|
||||
.scrollbar();
|
||||
|
||||
// 表格本体(设计 46:外框 1px #999、灰表头、横分隔线、无竖线、无卡面——卡面在页面层)
|
||||
&__grid {
|
||||
width: 100%;
|
||||
border: 1px solid @contract-line;
|
||||
border-collapse: collapse;
|
||||
font-size: @font-size-base;
|
||||
table-layout: fixed;
|
||||
font-size: 15px; // 设计 20 × 0.77
|
||||
|
||||
th,
|
||||
td {
|
||||
padding: @spacing-base;
|
||||
text-align: left;
|
||||
border-bottom: 1px solid @border-color;
|
||||
padding: 8px 10px;
|
||||
border-bottom: 1px solid @contract-line;
|
||||
vertical-align: middle;
|
||||
white-space: nowrap;
|
||||
font-size: 15px; // 设计 20 × 0.77
|
||||
}
|
||||
|
||||
// 长名称列按设计稿换行显示(设计首行双行文本)
|
||||
td.contract-table__name {
|
||||
white-space: normal;
|
||||
word-break: break-all;
|
||||
}
|
||||
|
||||
th {
|
||||
background: @bg-color-light;
|
||||
color: @heading-color;
|
||||
font-weight: 600;
|
||||
height: 49px; // 设计 64 × 0.77
|
||||
padding-top: 0;
|
||||
padding-bottom: 0;
|
||||
background: @contract-table-head-bg;
|
||||
color: @contract-head-text;
|
||||
font-weight: 400; // 设计 400
|
||||
text-align: center; // 表头居中(设计实测)
|
||||
}
|
||||
|
||||
td {
|
||||
color: @text-color;
|
||||
height: 75px; // 行高 97 设计 × 0.77
|
||||
color: @contract-cell-text;
|
||||
}
|
||||
|
||||
tbody tr:last-child td {
|
||||
@@ -116,12 +128,23 @@ const SIGN_VARIANTS: Record<SignStatus, 'primary' | 'success' | 'warning' | 'dan
|
||||
tbody tr:hover td {
|
||||
background: @bg-color-light;
|
||||
}
|
||||
|
||||
// 列宽按设计稿栅格比例微调(10 列合计 100%,日期/编号列留足 nowrap 宽度)
|
||||
th:nth-child(1) { width: 11%; }
|
||||
th:nth-child(2) { width: 9%; }
|
||||
th:nth-child(3) { width: 10%; }
|
||||
th:nth-child(4) { width: 9%; }
|
||||
th:nth-child(5) { width: 10%; }
|
||||
th:nth-child(6) { width: 11%; }
|
||||
th:nth-child(7) { width: 7%; }
|
||||
th:nth-child(8) { width: 11%; }
|
||||
th:nth-child(9) { width: 11%; }
|
||||
th:nth-child(10) { width: 11%; }
|
||||
}
|
||||
|
||||
// 长名称列继承正文灰(设计 46 单元格统一 #333333)
|
||||
&__name {
|
||||
max-width: 200px;
|
||||
color: @heading-color;
|
||||
.ellipsis();
|
||||
color: @contract-cell-text;
|
||||
}
|
||||
|
||||
&__actions {
|
||||
@@ -130,8 +153,8 @@ const SIGN_VARIANTS: Record<SignStatus, 'primary' | 'success' | 'warning' | 'dan
|
||||
}
|
||||
|
||||
&__btn {
|
||||
font-size: @font-size-base;
|
||||
color: @primary-color;
|
||||
font-size: 13px;
|
||||
color: @contract-accent;
|
||||
transition: opacity 0.2s;
|
||||
|
||||
&:hover {
|
||||
@@ -143,16 +166,25 @@ const SIGN_VARIANTS: Record<SignStatus, 'primary' | 'success' | 'warning' | 'dan
|
||||
padding: 0 @spacing-sm;
|
||||
border: none;
|
||||
border-radius: @radius-sm;
|
||||
background: @primary-color;
|
||||
background: @contract-accent;
|
||||
color: @white;
|
||||
|
||||
&:hover {
|
||||
background: @primary-hover;
|
||||
background: @primary-color;
|
||||
opacity: 1;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// 设计 46 状态列为纯文字,不使用彩色胶囊
|
||||
:deep(.status-tag) {
|
||||
padding: 0;
|
||||
border-radius: 0;
|
||||
background: transparent;
|
||||
color: inherit;
|
||||
font-size: inherit;
|
||||
}
|
||||
|
||||
&__empty {
|
||||
padding: @spacing-xl 0;
|
||||
text-align: center;
|
||||
|
||||
@@ -36,41 +36,45 @@ const steps = [
|
||||
</template>
|
||||
|
||||
<style lang="less" scoped>
|
||||
// 四步签署指引(设计 39:小蓝圆序号 + 14/12 设计px 标题与说明,步距 63 设计px)
|
||||
.sign-steps {
|
||||
.flex(column, flex-start);
|
||||
gap: @spacing-lg;
|
||||
.flex(column, flex-start, stretch);
|
||||
gap: 17px; // 步骤间距(设计 22 × 0.77)
|
||||
|
||||
&__item {
|
||||
.flex(row, flex-start);
|
||||
gap: @spacing-base;
|
||||
.flex(row, flex-start, flex-start);
|
||||
gap: 11px; // 序号 → 文字(设计 14 × 0.77)
|
||||
}
|
||||
|
||||
&__index {
|
||||
.flex(row, center);
|
||||
flex-shrink: 0;
|
||||
width: 32px;
|
||||
height: 32px;
|
||||
width: 16px; // 序号圆(设计 21 × 0.77)
|
||||
height: 16px;
|
||||
border-radius: @radius-round;
|
||||
background: @primary-light;
|
||||
color: @primary-color;
|
||||
font-size: @font-size-base;
|
||||
font-weight: 600;
|
||||
background: @primary-strong;
|
||||
color: @white;
|
||||
font-size: 11px; // 设计 12 → 可读下限
|
||||
font-weight: 700;
|
||||
line-height: 1;
|
||||
}
|
||||
|
||||
&__body {
|
||||
.flex(column, flex-start);
|
||||
gap: @spacing-xs;
|
||||
.flex(column, flex-start, stretch);
|
||||
gap: 5px; // 标题 → 说明(设计 6 × 0.77)
|
||||
min-width: 0;
|
||||
}
|
||||
|
||||
&__title {
|
||||
font-size: @font-size-lg;
|
||||
font-weight: 600;
|
||||
font-size: 11px; // 设计 14 → 可读下限
|
||||
font-weight: 700;
|
||||
line-height: 1.4;
|
||||
color: @heading-color;
|
||||
}
|
||||
|
||||
&__desc {
|
||||
font-size: @font-size-base;
|
||||
line-height: 1.6;
|
||||
font-size: 11px; // 设计 12 → 可读下限
|
||||
line-height: 1.5;
|
||||
}
|
||||
}
|
||||
</style>
|
||||
|
||||
@@ -46,47 +46,74 @@ onMounted(load)
|
||||
|
||||
<template>
|
||||
<div class="contract-detail">
|
||||
<nav class="contract-detail__breadcrumb text-secondary">
|
||||
<RouterLink to="/contract" class="link">
|
||||
合同中心
|
||||
</RouterLink>
|
||||
<span> > </span>
|
||||
<span>合同详情</span>
|
||||
</nav>
|
||||
<div class="container">
|
||||
<nav class="contract-detail__breadcrumb text-secondary">
|
||||
<RouterLink to="/contract" class="link">
|
||||
合同中心
|
||||
</RouterLink>
|
||||
<span> > </span>
|
||||
<span>合同详情</span>
|
||||
</nav>
|
||||
|
||||
<ContractInfoCard
|
||||
v-if="current"
|
||||
:contract="current"
|
||||
@view-project="onViewProject"
|
||||
@preview="onPreview"
|
||||
@download="onDownload"
|
||||
/>
|
||||
<ContractInfoCard
|
||||
v-if="current"
|
||||
:contract="current"
|
||||
@view-project="onViewProject"
|
||||
@preview="onPreview"
|
||||
@download="onDownload"
|
||||
/>
|
||||
|
||||
<p v-else class="contract-detail__empty text-secondary">
|
||||
合同不存在或已下线
|
||||
</p>
|
||||
<p v-else class="contract-detail__empty text-secondary">
|
||||
合同不存在或已下线
|
||||
</p>
|
||||
|
||||
<div class="contract-detail__footer">
|
||||
<AppButton @click="onBack">
|
||||
返回
|
||||
</AppButton>
|
||||
<div class="contract-detail__footer">
|
||||
<AppButton @click="onBack">
|
||||
返回
|
||||
</AppButton>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<style lang="less" scoped>
|
||||
.contract-detail {
|
||||
.flex(column, flex-start);
|
||||
gap: @spacing-base;
|
||||
padding-top: @spacing-lg;
|
||||
padding-bottom: @spacing-xxl;
|
||||
|
||||
// 内容列(面包屑 → 信息卡 → 返回):区块间距 24(设计 26~30 × 0.77)
|
||||
.container {
|
||||
.flex(column, flex-start, stretch);
|
||||
gap: @spacing-lg;
|
||||
}
|
||||
|
||||
// 面包屑(设计 45:24 设计px × 0.77、#666666、字重 500)
|
||||
&__breadcrumb {
|
||||
font-size: @font-size-base;
|
||||
font-size: 18px;
|
||||
font-weight: 500;
|
||||
color: @contract-muted;
|
||||
}
|
||||
|
||||
&__footer {
|
||||
.flex(row, flex-start);
|
||||
.flex(row, flex-end);
|
||||
width: 100%;
|
||||
|
||||
// 「返回」按钮(设计 40/39:#024FFF 实底、白字、小圆角)
|
||||
:deep(.app-button) {
|
||||
height: 30px;
|
||||
padding: 0 24px; // 按钮宽约 90 设计 × 0.77
|
||||
border: none;
|
||||
border-radius: @radius-sm;
|
||||
background: @primary-strong;
|
||||
color: @white;
|
||||
font-size: 11px; // 设计 13 → 可读下限
|
||||
}
|
||||
|
||||
:deep(.app-button:hover) {
|
||||
border-color: transparent;
|
||||
background: @primary-color;
|
||||
color: @white;
|
||||
}
|
||||
}
|
||||
|
||||
&__empty {
|
||||
|
||||
@@ -43,53 +43,194 @@ onMounted(() => {
|
||||
|
||||
<template>
|
||||
<div class="contract">
|
||||
<header class="contract__head">
|
||||
<h1 class="contract__title">
|
||||
合同中心
|
||||
</h1>
|
||||
<p class="contract__slogan text-secondary">
|
||||
项目电子合同在线签署、归档与查询管理
|
||||
</p>
|
||||
</header>
|
||||
<!-- 顶部横幅:白底通栏 + 标题/副标语(设计 41 横幅区、46 标题规格) -->
|
||||
<div class="contract__head">
|
||||
<div class="container">
|
||||
<h1 class="contract__title">
|
||||
合同中心
|
||||
</h1>
|
||||
<p class="contract__slogan text-secondary">
|
||||
项目电子合同在线签署、归档与查询管理
|
||||
</p>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<FilterPanel
|
||||
v-model:keyword="keyword"
|
||||
keyword-placeholder="合同名称/合同编号搜索"
|
||||
@search="onSearch"
|
||||
@reset="onReset"
|
||||
/>
|
||||
<div class="container">
|
||||
<!-- 内容白卡:搜索行 + 表格 + 分页(设计 46/47 卡片) -->
|
||||
<div class="contract__card">
|
||||
<FilterPanel
|
||||
v-model:keyword="keyword"
|
||||
keyword-placeholder="合同名称/合同编号搜索"
|
||||
@search="onSearch"
|
||||
@reset="onReset"
|
||||
/>
|
||||
|
||||
<ContractTable
|
||||
:contracts="list"
|
||||
@view="onView"
|
||||
@sign="onSign"
|
||||
/>
|
||||
<ContractTable
|
||||
:contracts="list"
|
||||
@view="onView"
|
||||
@sign="onSign"
|
||||
/>
|
||||
|
||||
<PaginationBar
|
||||
:page="query.page"
|
||||
:page-size="query.pageSize"
|
||||
:total="total"
|
||||
@page-change="onPageChange"
|
||||
/>
|
||||
<PaginationBar
|
||||
:page="query.page"
|
||||
:page-size="query.pageSize"
|
||||
:total="total"
|
||||
@page-change="onPageChange"
|
||||
/>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<style lang="less" scoped>
|
||||
.contract {
|
||||
.flex(column, flex-start);
|
||||
gap: @spacing-base;
|
||||
padding-top: @spacing-xl;
|
||||
padding-bottom: @spacing-xxl;
|
||||
|
||||
// 横幅:设计 41/46 实测 y72..251(179 设计px → 138 CSS)白底通栏
|
||||
&__head {
|
||||
padding: 25px 0 33px;
|
||||
background: @white;
|
||||
|
||||
// 标题/副标语相对内容区左缩进 42 设计px × 0.77 ≈ 32(容器自带 16)
|
||||
.container {
|
||||
padding-left: 48px;
|
||||
}
|
||||
}
|
||||
|
||||
&__title {
|
||||
font-size: @font-size-xxl;
|
||||
font-weight: 600;
|
||||
color: @heading-color;
|
||||
font-size: @font-size-xxl; // 28px = 设计 36 × 0.77
|
||||
font-weight: 700;
|
||||
line-height: 1.4;
|
||||
color: @home-ink; // 复用同值 token(横幅标题设计实取 @contract-ink)
|
||||
}
|
||||
|
||||
&__slogan {
|
||||
margin-top: @spacing-xs;
|
||||
font-size: @font-size-base;
|
||||
margin-top: 12px; // 设计 15 × 0.77
|
||||
font-size: 18px; // 设计 24 × 0.77
|
||||
font-weight: 500;
|
||||
line-height: 1.5;
|
||||
color: @contract-muted;
|
||||
}
|
||||
}
|
||||
|
||||
// 内容白卡(设计 46:x70..1850 圆角白卡,无阴影)——显式 .contract 前缀抬高覆写优先级
|
||||
.contract .contract__card {
|
||||
margin-top: 15px; // 横幅底 → 卡片顶:设计 20 × 0.77
|
||||
padding: 40px 48px 44px; // 卡片内缩:设计 51/64/59 × 0.77
|
||||
border-radius: @radius-lg;
|
||||
background: @white;
|
||||
|
||||
// 搜索行并入卡片:去掉 FilterPanel 自带的卡面,按设计 41 重排控件
|
||||
:deep(.filter-panel) {
|
||||
margin-bottom: 30px; // 搜索行 → 表格:设计 39 × 0.77
|
||||
padding: 0;
|
||||
border-radius: 0;
|
||||
background: transparent;
|
||||
box-shadow: none;
|
||||
}
|
||||
|
||||
:deep(.filter-panel__body) {
|
||||
margin-top: 0;
|
||||
}
|
||||
|
||||
:deep(.filter-panel__bar) {
|
||||
gap: 6px;
|
||||
}
|
||||
|
||||
:deep(.filter-panel__input) {
|
||||
flex: 1;
|
||||
width: auto;
|
||||
height: 30px; // 设计 38 × 0.77
|
||||
border-color: transparent;
|
||||
background: @input-bg;
|
||||
font-size: 11px; // 设计 13 → 可读下限
|
||||
}
|
||||
|
||||
:deep(.filter-panel__input::placeholder) {
|
||||
color: @contract-placeholder;
|
||||
}
|
||||
|
||||
:deep(.filter-panel__input:focus) {
|
||||
border-color: @primary-strong;
|
||||
}
|
||||
|
||||
// 设计 41 按钮序为「重置 | 搜索」,组件内 DOM 序相反,用 order 对齐
|
||||
:deep(.filter-panel__btn) {
|
||||
order: 1;
|
||||
height: 30px;
|
||||
padding: 0 16px;
|
||||
border: none;
|
||||
background: @contract-reset-bg;
|
||||
color: @text-color;
|
||||
font-size: 11px; // 设计 12 → 可读下限
|
||||
}
|
||||
|
||||
:deep(.filter-panel__btn:hover) {
|
||||
border-color: transparent;
|
||||
color: @text-color;
|
||||
}
|
||||
|
||||
:deep(.filter-panel__btn--primary) {
|
||||
order: 2;
|
||||
background: @primary-strong;
|
||||
color: @white;
|
||||
}
|
||||
|
||||
:deep(.filter-panel__btn--primary:hover) {
|
||||
background: @primary-color;
|
||||
color: @white;
|
||||
}
|
||||
|
||||
// 分页(设计 46:右对齐、方角小页码、当前页实底蓝)
|
||||
:deep(.pagination) {
|
||||
justify-content: flex-end;
|
||||
gap: 8px; // 设计 10 × 0.77
|
||||
padding: 0;
|
||||
margin-top: 22px; // 表格底 → 分页:设计 28 × 0.77
|
||||
}
|
||||
|
||||
:deep(.pagination__btn) {
|
||||
min-width: 31px; // 设计 40 × 0.77
|
||||
height: 20px; // 设计 26 × 0.77
|
||||
padding: 0 4px;
|
||||
border: 1px solid @contract-line;
|
||||
border-radius: 0;
|
||||
background: @white;
|
||||
color: @contract-line;
|
||||
font-size: 11px; // 设计 14 → 可读下限
|
||||
}
|
||||
|
||||
:deep(.pagination__btn:hover:not(:disabled):not(.is-ellipsis)) {
|
||||
border-color: @contract-accent;
|
||||
color: @contract-accent;
|
||||
}
|
||||
|
||||
:deep(.pagination__btn.is-active) {
|
||||
border-color: @contract-accent;
|
||||
background: @contract-accent;
|
||||
color: @white;
|
||||
}
|
||||
|
||||
:deep(.pagination__btn.is-ellipsis) {
|
||||
border-color: transparent;
|
||||
background: transparent;
|
||||
color: @contract-muted;
|
||||
}
|
||||
|
||||
// 首尾「上一页/下一页」:设计为无框纯文字
|
||||
:deep(.pagination__btn:first-child),
|
||||
:deep(.pagination__btn:last-child) {
|
||||
min-width: auto;
|
||||
padding: 0 2px;
|
||||
border: none;
|
||||
background: transparent;
|
||||
color: @contract-muted;
|
||||
font-size: 12px;
|
||||
}
|
||||
|
||||
:deep(.pagination__btn:first-child:disabled),
|
||||
:deep(.pagination__btn:last-child:disabled) {
|
||||
opacity: 1;
|
||||
}
|
||||
}
|
||||
</style>
|
||||
|
||||
@@ -35,44 +35,76 @@ onMounted(load)
|
||||
|
||||
<template>
|
||||
<div class="contract-sign">
|
||||
<nav class="contract-sign__breadcrumb text-secondary">
|
||||
<RouterLink to="/contract" class="link">
|
||||
合同中心
|
||||
</RouterLink>
|
||||
<span> > </span>
|
||||
<RouterLink :to="`/contract/${contractId}`" class="link">
|
||||
合同详情
|
||||
</RouterLink>
|
||||
<span> > </span>
|
||||
<span>签署合同</span>
|
||||
</nav>
|
||||
<div class="container">
|
||||
<nav class="contract-sign__breadcrumb text-secondary">
|
||||
<RouterLink to="/contract" class="link">
|
||||
合同中心
|
||||
</RouterLink>
|
||||
<span> > </span>
|
||||
<RouterLink :to="`/contract/${contractId}`" class="link">
|
||||
合同详情
|
||||
</RouterLink>
|
||||
<span> > </span>
|
||||
<span>签署合同</span>
|
||||
</nav>
|
||||
|
||||
<ContractSignPanel
|
||||
:expires-in="signExpires"
|
||||
@refresh="onRefresh"
|
||||
/>
|
||||
<ContractSignPanel
|
||||
:expires-in="signExpires"
|
||||
@refresh="onRefresh"
|
||||
/>
|
||||
|
||||
<div class="contract-sign__footer">
|
||||
<AppButton @click="onBack">
|
||||
返回
|
||||
</AppButton>
|
||||
<div class="contract-sign__footer">
|
||||
<AppButton @click="onBack">
|
||||
返回
|
||||
</AppButton>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<style lang="less" scoped>
|
||||
.contract-sign {
|
||||
.flex(column, flex-start);
|
||||
gap: @spacing-base;
|
||||
padding-top: @spacing-lg;
|
||||
padding-bottom: @spacing-xxl;
|
||||
|
||||
// 内容列(面包屑 → 签署卡 → 返回):面包屑 → 卡片 12(设计 16 × 0.77)
|
||||
.container {
|
||||
.flex(column, flex-start, stretch);
|
||||
gap: 12px;
|
||||
}
|
||||
|
||||
// 面包屑(设计 39:12 设计px → 可读下限 11、#9CA3AF,当前项 #4B5563 加粗)
|
||||
&__breadcrumb {
|
||||
font-size: @font-size-base;
|
||||
font-size: 11px;
|
||||
color: @text-color-disabled;
|
||||
|
||||
> span:last-child {
|
||||
color: @text-color;
|
||||
font-weight: 500;
|
||||
}
|
||||
}
|
||||
|
||||
&__footer {
|
||||
.flex(row, flex-start);
|
||||
.flex(row, flex-end);
|
||||
width: 100%;
|
||||
margin-top: 19px; // 卡片底 → 按钮:设计 40 × 0.77(另计容器 12)
|
||||
|
||||
// 「返回」按钮(设计 39:#024FFF 实底、白字、小圆角)
|
||||
:deep(.app-button) {
|
||||
height: 30px;
|
||||
padding: 0 24px; // 按钮宽约 98 设计 × 0.77
|
||||
border: none;
|
||||
border-radius: @radius-sm;
|
||||
background: @primary-strong;
|
||||
color: @white;
|
||||
font-size: 11px; // 设计 13 → 可读下限
|
||||
}
|
||||
|
||||
:deep(.app-button:hover) {
|
||||
border-color: transparent;
|
||||
background: @primary-color;
|
||||
color: @white;
|
||||
}
|
||||
}
|
||||
}
|
||||
</style>
|
||||
|
||||
@@ -64,15 +64,19 @@ const emit = defineEmits<{
|
||||
&__inner {
|
||||
.flex(row, space-between, center);
|
||||
height: 72px;
|
||||
// 覆盖 .container 内缩:左 = 容器16 + 卡左内边距49 + 序号列46 = 111(对齐内容列),右 = 16 + 40
|
||||
gap: @spacing-base;
|
||||
padding-left: 111px;
|
||||
padding-right: 56px;
|
||||
}
|
||||
|
||||
&__tip {
|
||||
.flex(row, flex-start, center);
|
||||
gap: @spacing-sm;
|
||||
min-width: 0;
|
||||
font-size: @font-size-base;
|
||||
color: @text-color;
|
||||
font-size: 15px;
|
||||
font-weight: 500;
|
||||
color: @demand-heading;
|
||||
}
|
||||
|
||||
&__info {
|
||||
@@ -80,28 +84,32 @@ const emit = defineEmits<{
|
||||
flex-shrink: 0;
|
||||
width: 16px;
|
||||
height: 16px;
|
||||
border: 1px solid @primary-color;
|
||||
border: 1px solid @demand-accent;
|
||||
border-radius: 50%;
|
||||
font-size: 11px;
|
||||
font-style: normal;
|
||||
font-weight: 600;
|
||||
color: @primary-color;
|
||||
color: @demand-accent;
|
||||
}
|
||||
|
||||
&__actions {
|
||||
.flex(row, flex-end, center);
|
||||
gap: @spacing-base;
|
||||
// 设计稿按钮 232×63 设计px ≈ 179×48,间距 47 设计px ≈ 36px
|
||||
gap: 36px;
|
||||
flex-shrink: 0;
|
||||
}
|
||||
|
||||
// 设计稿三个按钮均为实底蓝 #075CFF + 白字
|
||||
&__btn {
|
||||
height: 36px;
|
||||
padding: 0 @spacing-lg;
|
||||
width: 179px;
|
||||
height: 48px;
|
||||
padding: 0;
|
||||
border: none;
|
||||
border-radius: @radius-round;
|
||||
border-radius: @radius-base;
|
||||
background: @demand-secondary-bg;
|
||||
font-size: @font-size-base;
|
||||
color: @heading-color;
|
||||
font-size: 15px;
|
||||
font-weight: 500;
|
||||
color: @white;
|
||||
cursor: pointer;
|
||||
transition: background 0.2s, opacity 0.2s;
|
||||
|
||||
@@ -115,13 +123,13 @@ const emit = defineEmits<{
|
||||
}
|
||||
|
||||
&--primary {
|
||||
// 设计稿按钮宽度(247px @1400 版面)由 min-width 兜住,短文案也不塌
|
||||
min-width: 240px;
|
||||
background: @primary-color;
|
||||
// 设计稿三个按钮等宽(232 设计px ≈ 179px),主按钮不额外加宽
|
||||
min-width: 179px;
|
||||
background: @demand-secondary-bg;
|
||||
color: @white;
|
||||
|
||||
&:hover:not(:disabled) {
|
||||
background: @primary-hover;
|
||||
background: darken(@demand-secondary-bg, 6%);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -208,41 +208,41 @@ function onDownload(file: DemandAttachment): void {
|
||||
<style lang="less" scoped>
|
||||
.demand-attach {
|
||||
.flex(column, flex-start, stretch);
|
||||
gap: @spacing-sm;
|
||||
gap: 11px;
|
||||
|
||||
&__head {
|
||||
.flex(row, flex-start, center);
|
||||
gap: @spacing-sm;
|
||||
gap: 15px;
|
||||
}
|
||||
|
||||
&__label {
|
||||
font-size: @font-size-base;
|
||||
font-weight: 600;
|
||||
color: @heading-color;
|
||||
font-size: 15px;
|
||||
font-weight: 500;
|
||||
color: @demand-heading;
|
||||
}
|
||||
|
||||
&__hint {
|
||||
flex: 1;
|
||||
min-width: 0;
|
||||
font-size: @font-size-sm;
|
||||
color: @text-color-secondary;
|
||||
color: @demand-line;
|
||||
}
|
||||
|
||||
&__pick {
|
||||
flex-shrink: 0;
|
||||
height: 28px;
|
||||
padding: 0 @spacing-base;
|
||||
border: 1px solid @border-color-dark;
|
||||
border: 1px solid @demand-line;
|
||||
border-radius: @radius-sm;
|
||||
background: @white;
|
||||
font-size: @font-size-sm;
|
||||
color: @text-color;
|
||||
color: @demand-line;
|
||||
cursor: pointer;
|
||||
transition: border-color 0.2s, color 0.2s;
|
||||
|
||||
&:hover:not(:disabled) {
|
||||
border-color: @primary-color;
|
||||
color: @primary-color;
|
||||
border-color: @demand-accent;
|
||||
color: @demand-accent;
|
||||
}
|
||||
|
||||
&:disabled {
|
||||
@@ -257,18 +257,21 @@ function onDownload(file: DemandAttachment): void {
|
||||
|
||||
&__list {
|
||||
.flex(column, flex-start, stretch);
|
||||
gap: @spacing-sm;
|
||||
// 设计稿:两条 90 设计px 灰条,间距 20 设计px ≈ 15px
|
||||
gap: 15px;
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
list-style: none;
|
||||
}
|
||||
|
||||
// 设计稿附件条:实底 #EDEDED、无描边、90 设计px ≈ 69px 高
|
||||
&__item {
|
||||
.flex(row, flex-start, center);
|
||||
gap: @spacing-sm;
|
||||
padding: @spacing-sm @spacing-base;
|
||||
gap: @spacing-base;
|
||||
min-height: 69px;
|
||||
padding: @spacing-base;
|
||||
border-radius: @radius-sm;
|
||||
background: @bg-color-light;
|
||||
background: @demand-upload-bg;
|
||||
}
|
||||
|
||||
&__badge {
|
||||
@@ -290,8 +293,8 @@ function onDownload(file: DemandAttachment): void {
|
||||
}
|
||||
|
||||
&__name {
|
||||
font-size: @font-size-base;
|
||||
color: @heading-color;
|
||||
font-size: 15px;
|
||||
color: @demand-ink;
|
||||
.ellipsis();
|
||||
}
|
||||
|
||||
|
||||
@@ -57,19 +57,19 @@ const emit = defineEmits<{ 'update:modelValue': [value: string] }>()
|
||||
}
|
||||
|
||||
&__grid {
|
||||
// auto-fill(不是 auto-fit):条目不足 5 个时保留空轨道,卡片尺寸与设计稿一致(约 251px),
|
||||
// auto-fill(不是 auto-fit):条目不足 5 个时保留空轨道,卡片尺寸与设计稿一致(303 设计px ≈ 233px),
|
||||
// 不会被拉伸变形;满 5 个时正好落在设计稿的 5 列上。
|
||||
display: grid;
|
||||
grid-template-columns: repeat(auto-fill, minmax(240px, 1fr));
|
||||
gap: @spacing-base;
|
||||
grid-template-columns: repeat(auto-fill, minmax(200px, 1fr));
|
||||
gap: 14px;
|
||||
}
|
||||
|
||||
&__card {
|
||||
position: relative;
|
||||
.flex(column, flex-start, stretch);
|
||||
gap: @spacing-xs;
|
||||
padding: @spacing-base;
|
||||
border: 1px solid @border-color;
|
||||
gap: 2px;
|
||||
padding: 12px 12px 8px;
|
||||
border: 1px solid @demand-line;
|
||||
border-radius: @radius-base;
|
||||
background: @white;
|
||||
text-align: left;
|
||||
@@ -80,53 +80,61 @@ const emit = defineEmits<{ 'update:modelValue': [value: string] }>()
|
||||
border-color: @demand-accent;
|
||||
}
|
||||
|
||||
// 选中:整卡蓝底(设计稿实取 #024FFF),文字反白
|
||||
&.is-active {
|
||||
border-color: @demand-accent;
|
||||
border-color: @demand-selected-bg;
|
||||
background: @demand-selected-bg;
|
||||
}
|
||||
}
|
||||
|
||||
/** 右上角选中标记:未选为空心圈,选中为实心蓝点 */
|
||||
/** 右上角选中标记(设计稿 30 设计px ≈ 23px):未选空心圈,选中为白环 + 蓝缝 + 白点 */
|
||||
&__check {
|
||||
position: absolute;
|
||||
top: 12px;
|
||||
right: 12px;
|
||||
width: 16px;
|
||||
height: 16px;
|
||||
border: 1px solid @border-color-dark;
|
||||
top: 22px;
|
||||
right: 19px;
|
||||
width: 23px;
|
||||
height: 23px;
|
||||
border: 1px solid @demand-radio-idle;
|
||||
border-radius: 50%;
|
||||
background: @white;
|
||||
transition: background 0.2s, border-color 0.2s, box-shadow 0.2s;
|
||||
transition: border-color 0.2s, box-shadow 0.2s;
|
||||
}
|
||||
|
||||
&__card.is-active &__check {
|
||||
border-color: @demand-accent;
|
||||
background: @demand-accent;
|
||||
border-color: @white;
|
||||
background: @white;
|
||||
box-shadow: inset 0 0 0 3px @demand-selected-bg;
|
||||
}
|
||||
|
||||
&__icon {
|
||||
margin-bottom: @spacing-xs;
|
||||
margin-bottom: 25px;
|
||||
}
|
||||
|
||||
/** 后端 Logo:与内联 SVG 同尺寸,保证两种来源视觉一致 */
|
||||
&__logo {
|
||||
width: 40px;
|
||||
height: 40px;
|
||||
margin-bottom: @spacing-xs;
|
||||
margin-bottom: 25px;
|
||||
object-fit: contain;
|
||||
}
|
||||
|
||||
&__name {
|
||||
font-size: @font-size-lg;
|
||||
font-weight: 600;
|
||||
color: @heading-color;
|
||||
font-size: @font-size-title;
|
||||
font-weight: 500;
|
||||
color: @demand-ink;
|
||||
}
|
||||
|
||||
&__desc {
|
||||
font-size: @font-size-sm;
|
||||
color: @text-color-secondary;
|
||||
line-height: 1.5;
|
||||
font-weight: 500;
|
||||
color: @demand-ink;
|
||||
line-height: 1.45;
|
||||
}
|
||||
|
||||
// 选中卡内文字反白(设计稿:标题/描述均为白色)
|
||||
&__card.is-active &__name,
|
||||
&__card.is-active &__desc {
|
||||
color: @white;
|
||||
}
|
||||
}
|
||||
</style>
|
||||
|
||||
@@ -81,25 +81,37 @@ function onRemark(event: Event): void {
|
||||
|
||||
&__row {
|
||||
.flex(row, flex-start, stretch);
|
||||
gap: @spacing-base;
|
||||
// 设计稿:两个 503 设计px 输入框(≈387px),间距 73 设计px ≈ 56px,整行不占满
|
||||
gap: 56px;
|
||||
}
|
||||
|
||||
&__field {
|
||||
.flex(column, flex-start, stretch);
|
||||
flex: 1 1 50%;
|
||||
gap: @spacing-sm;
|
||||
gap: 10px;
|
||||
min-width: 0;
|
||||
}
|
||||
|
||||
// 行内两列(用户名称 / 用户手机号)定宽;补充备注整行铺满
|
||||
&__row &__field {
|
||||
flex: 0 0 387px;
|
||||
}
|
||||
|
||||
&__label {
|
||||
font-size: @font-size-base;
|
||||
font-weight: 600;
|
||||
color: @heading-color;
|
||||
font-size: 15px;
|
||||
font-weight: 500;
|
||||
color: @demand-heading;
|
||||
}
|
||||
|
||||
&__input {
|
||||
.text-control();
|
||||
height: 36px;
|
||||
height: 38px;
|
||||
font-size: 15px;
|
||||
border-color: @demand-line;
|
||||
color: @demand-ink;
|
||||
|
||||
&::placeholder {
|
||||
color: @demand-line;
|
||||
}
|
||||
}
|
||||
|
||||
&__area {
|
||||
@@ -109,10 +121,17 @@ function onRemark(event: Event): void {
|
||||
|
||||
&__textarea {
|
||||
.text-control();
|
||||
min-height: 132px;
|
||||
padding: @spacing-sm @spacing-base 24px;
|
||||
min-height: 208px;
|
||||
padding: 10px 14px 24px;
|
||||
font-size: 15px;
|
||||
border-color: @demand-line;
|
||||
color: @demand-ink;
|
||||
line-height: 1.7;
|
||||
resize: vertical;
|
||||
|
||||
&::placeholder {
|
||||
color: @demand-line;
|
||||
}
|
||||
}
|
||||
|
||||
&__count {
|
||||
|
||||
@@ -198,24 +198,29 @@ function onBudgetManualBlur(event: Event): void {
|
||||
|
||||
&__field {
|
||||
.flex(column, flex-start, stretch);
|
||||
gap: @spacing-sm;
|
||||
gap: 10px;
|
||||
min-width: 0;
|
||||
}
|
||||
|
||||
&__row {
|
||||
.flex(row, flex-start, stretch);
|
||||
gap: @spacing-base;
|
||||
// 设计稿:预算列 892 设计px + 间距 61 设计px + 周期列 652 设计px(1605 总宽)
|
||||
gap: @spacing-xxl;
|
||||
|
||||
.demand-info__field {
|
||||
flex: 1 1 50%;
|
||||
width: 50%;
|
||||
flex: 687 1 0;
|
||||
width: auto;
|
||||
}
|
||||
|
||||
.demand-info__field:last-child {
|
||||
flex: 502 1 0;
|
||||
}
|
||||
}
|
||||
|
||||
&__label {
|
||||
font-size: @font-size-base;
|
||||
font-weight: 600;
|
||||
color: @heading-color;
|
||||
font-size: 15px;
|
||||
font-weight: 500;
|
||||
color: @demand-heading;
|
||||
}
|
||||
|
||||
&__required {
|
||||
@@ -225,7 +230,15 @@ function onBudgetManualBlur(event: Event): void {
|
||||
|
||||
&__input {
|
||||
.text-control();
|
||||
height: 36px;
|
||||
// 设计稿:49 设计px 高 ≈ 38px,20 设计px 字号 ≈ 15px,描边/占位 rgba(153,153,153)
|
||||
height: 38px;
|
||||
font-size: 15px;
|
||||
border-color: @demand-line;
|
||||
color: @demand-ink;
|
||||
|
||||
&::placeholder {
|
||||
color: @demand-line;
|
||||
}
|
||||
}
|
||||
|
||||
&__area {
|
||||
@@ -235,10 +248,18 @@ function onBudgetManualBlur(event: Event): void {
|
||||
|
||||
&__textarea {
|
||||
.text-control();
|
||||
min-height: 132px;
|
||||
padding: @spacing-sm @spacing-base 24px;
|
||||
// 设计稿:270 设计px 高 ≈ 208px,占位内缩 18/10 设计px ≈ 14/8px
|
||||
min-height: 208px;
|
||||
padding: 10px 14px 24px;
|
||||
font-size: 15px;
|
||||
border-color: @demand-line;
|
||||
color: @demand-ink;
|
||||
line-height: 1.7;
|
||||
resize: vertical;
|
||||
|
||||
&::placeholder {
|
||||
color: @demand-line;
|
||||
}
|
||||
}
|
||||
|
||||
&__count {
|
||||
@@ -251,21 +272,22 @@ function onBudgetManualBlur(event: Event): void {
|
||||
|
||||
&__budgets {
|
||||
.flex(row, flex-start, stretch);
|
||||
gap: @spacing-base;
|
||||
// 设计稿:5 个 165 设计px 胶囊、间距 17 设计px ≈ 13px
|
||||
gap: 13px;
|
||||
}
|
||||
|
||||
/** 预算控件外观:4 个胶囊按钮 + 第 5 个手填输入框共用同一套规格 */
|
||||
&__budget {
|
||||
flex: 1;
|
||||
min-width: 0;
|
||||
height: 36px;
|
||||
height: 38px;
|
||||
padding: 0 @spacing-sm;
|
||||
border: 1px solid @border-color;
|
||||
border: 1px solid @demand-line;
|
||||
border-radius: @radius-sm;
|
||||
background: @white;
|
||||
font-size: @font-size-base;
|
||||
font-size: 15px;
|
||||
font-family: inherit;
|
||||
color: @text-color;
|
||||
color: @demand-line;
|
||||
text-align: center;
|
||||
cursor: pointer;
|
||||
transition: all 0.2s;
|
||||
@@ -279,7 +301,7 @@ function onBudgetManualBlur(event: Event): void {
|
||||
&.is-active {
|
||||
border-color: @demand-accent;
|
||||
background: @demand-selected-bg;
|
||||
color: @demand-accent;
|
||||
color: @white;
|
||||
font-weight: 600;
|
||||
}
|
||||
}
|
||||
@@ -290,7 +312,7 @@ function onBudgetManualBlur(event: Event): void {
|
||||
|
||||
&::placeholder {
|
||||
font-weight: 400;
|
||||
color: @text-color-secondary;
|
||||
color: @demand-line;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -123,6 +123,8 @@ onMounted(() => {
|
||||
padding-top: @spacing-lg;
|
||||
// 固定底条 72px + 呼吸间距,避免遮住 ③ 卡片
|
||||
padding-bottom: 104px;
|
||||
// 设计稿:导航下方 179 设计px(≈138px)白色通栏横幅,其下为页面底色
|
||||
background: linear-gradient(to bottom, @white 0, @white 138px, @bg-color 138px);
|
||||
|
||||
&.is-loading {
|
||||
.demand {
|
||||
@@ -133,54 +135,76 @@ onMounted(() => {
|
||||
}
|
||||
|
||||
.demand {
|
||||
// 设计稿:页头下与首块间距 ≈ 20px
|
||||
// 设计稿:标题距横幅顶 32 设计px、副标题行距 15 设计px、横幅下留白 50 设计px
|
||||
&__head {
|
||||
.flex(column, flex-start, stretch);
|
||||
gap: @spacing-xs;
|
||||
margin-bottom: @spacing-base;
|
||||
gap: 11px;
|
||||
margin-bottom: 50px;
|
||||
}
|
||||
|
||||
&__title {
|
||||
font-size: @font-size-xxl;
|
||||
font-weight: 600;
|
||||
color: @heading-color;
|
||||
font-weight: 700;
|
||||
line-height: 1.45;
|
||||
color: @demand-ink;
|
||||
}
|
||||
|
||||
&__subtitle {
|
||||
font-size: @font-size-base;
|
||||
color: @text-color-secondary;
|
||||
font-size: 18px;
|
||||
font-weight: 500;
|
||||
color: @demand-subtitle;
|
||||
}
|
||||
|
||||
// 设计稿三段内容位于同一张白色大卡内:三张卡无缝拼接呈现同一张卡的观感
|
||||
&__card {
|
||||
padding: @spacing-lg;
|
||||
border-radius: @radius-base;
|
||||
padding: 24px 40px 24px 49px;
|
||||
border-radius: 0;
|
||||
background: @white;
|
||||
|
||||
// 设计稿块间距 18px
|
||||
// 三卡相连,不再留块间距
|
||||
& + & {
|
||||
margin-top: 18px;
|
||||
margin-top: 0;
|
||||
}
|
||||
|
||||
&:first-of-type {
|
||||
padding-top: 37px;
|
||||
border-radius: @radius-base @radius-base 0 0;
|
||||
}
|
||||
|
||||
&:last-of-type {
|
||||
padding-bottom: 40px;
|
||||
border-radius: 0 0 @radius-base @radius-base;
|
||||
}
|
||||
}
|
||||
|
||||
// 区块标题:序号落在卡左内边距列(x=134 设计px),标题文字对齐内容列(x=194)
|
||||
&__section {
|
||||
.flex(row, flex-start, center);
|
||||
gap: @spacing-sm;
|
||||
margin-bottom: @spacing-base;
|
||||
font-size: @font-size-lg;
|
||||
font-weight: 600;
|
||||
color: @heading-color;
|
||||
.flex(row, flex-start, baseline);
|
||||
gap: @spacing-xs;
|
||||
margin-bottom: 16px;
|
||||
font-size: @font-size-title;
|
||||
font-weight: 500;
|
||||
color: @demand-heading;
|
||||
}
|
||||
|
||||
/** 区块序号:实心蓝圆 + 白色数字 */
|
||||
// 内容列(卡片栅格 / 表单)与区块标题文字对齐到 x=194 设计列(60 设计px ≈ 46px)
|
||||
&__section + * {
|
||||
margin-left: 46px;
|
||||
}
|
||||
|
||||
// ① 段标题到卡片栅格的间距更大(56 设计px ≈ 43px)
|
||||
&__card:first-of-type &__section {
|
||||
margin-bottom: 40px;
|
||||
}
|
||||
|
||||
/** 区块序号:设计稿 48 设计px 蓝色数字(01/02/03) */
|
||||
&__index {
|
||||
.flex(row, center, center);
|
||||
width: 18px;
|
||||
height: 18px;
|
||||
border-radius: 50%;
|
||||
background: @primary-color;
|
||||
font-size: @font-size-sm;
|
||||
font-weight: 600;
|
||||
color: @white;
|
||||
flex-shrink: 0;
|
||||
width: 42px;
|
||||
font-size: 37px;
|
||||
font-weight: 500;
|
||||
line-height: 1;
|
||||
color: @demand-accent;
|
||||
}
|
||||
|
||||
&__required {
|
||||
|
||||
@@ -79,7 +79,14 @@ onMounted(() => {
|
||||
</div>
|
||||
<div class="bill-detail__field">
|
||||
<span class="bill-detail__label text-secondary">订单金额</span>
|
||||
<span class="bill-detail__value bill-detail__value--amount">¥{{ formatMoney(currentBill.amount) }}</span>
|
||||
<!-- 设计 31:金额随状态取色——已支付红 / 待支付橙 / 未到期深灰 -->
|
||||
<span
|
||||
class="bill-detail__value bill-detail__value--amount"
|
||||
:class="{
|
||||
'is-pending': currentBill.status === '待支付',
|
||||
'is-idle': currentBill.status === '未到期' || currentBill.status === '已取消',
|
||||
}"
|
||||
>¥{{ formatMoney(currentBill.amount) }}</span>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
@@ -143,17 +150,28 @@ onMounted(() => {
|
||||
|
||||
<style lang="less" scoped>
|
||||
.bill-detail {
|
||||
padding-top: @spacing-lg;
|
||||
padding-bottom: @spacing-xxl;
|
||||
width: 100%;
|
||||
max-width: @container-width;
|
||||
margin: 0 auto;
|
||||
padding: @spacing-lg @spacing-base @spacing-xxl;
|
||||
|
||||
// 设计 31:面包屑 13 设计px → 11px,前缀灰、当前页深灰
|
||||
&__breadcrumb {
|
||||
margin-bottom: @spacing-base;
|
||||
font-size: @font-size-base;
|
||||
font-size: 11px;
|
||||
color: @text-color-disabled;
|
||||
|
||||
> span:last-child {
|
||||
color: @text-color;
|
||||
}
|
||||
}
|
||||
|
||||
// 设计 31:白卡居中(对应设计三张窄卡的中轴布局),圆角 8、柔阴影
|
||||
&__card {
|
||||
padding: @spacing-lg;
|
||||
border-radius: @radius-lg;
|
||||
max-width: 440px;
|
||||
margin: 0 auto;
|
||||
padding: @spacing-base 20px 20px;
|
||||
border-radius: @radius-base;
|
||||
background: @white;
|
||||
box-shadow: @shadow-base;
|
||||
}
|
||||
@@ -164,69 +182,114 @@ onMounted(() => {
|
||||
}
|
||||
|
||||
&__card-title {
|
||||
font-size: @font-size-lg;
|
||||
font-weight: 600;
|
||||
font-size: 12px;
|
||||
font-weight: 700;
|
||||
color: @heading-color;
|
||||
}
|
||||
|
||||
// 状态徽标压成设计稿的深色粗体状态词
|
||||
:deep(.status-tag) {
|
||||
padding: 0;
|
||||
background: transparent;
|
||||
color: @heading-color;
|
||||
font-size: 12px;
|
||||
font-weight: 700;
|
||||
}
|
||||
|
||||
// 字段行:标签左(灰 11px)、值右(深色粗体)——设计 31 左右分栏
|
||||
&__fields {
|
||||
.flex(column, flex-start);
|
||||
gap: @spacing-sm;
|
||||
.flex(column, flex-start, stretch);
|
||||
gap: 12px;
|
||||
}
|
||||
|
||||
&__field {
|
||||
.flex(row, flex-start, center);
|
||||
.flex(row, space-between, center);
|
||||
gap: @spacing-base;
|
||||
font-size: @font-size-base;
|
||||
font-size: 11px;
|
||||
}
|
||||
|
||||
&__label {
|
||||
width: 80px;
|
||||
flex-shrink: 0;
|
||||
font-size: 11px;
|
||||
}
|
||||
|
||||
&__value {
|
||||
color: @heading-color;
|
||||
font-weight: 600;
|
||||
text-align: right;
|
||||
word-break: break-all;
|
||||
|
||||
// 设计 31:付款金额 已支付 #EF4444 / 待支付 #F59E0B / 未到期深灰,18 设计px → 14px 粗体
|
||||
&--amount {
|
||||
font-weight: 600;
|
||||
font-size: 14px;
|
||||
font-weight: 700;
|
||||
color: @danger-color;
|
||||
}
|
||||
|
||||
&.is-pending {
|
||||
color: @finance-pending;
|
||||
}
|
||||
|
||||
&.is-idle {
|
||||
color: @heading-color;
|
||||
}
|
||||
}
|
||||
|
||||
&__pay {
|
||||
margin-top: @spacing-lg;
|
||||
margin-top: @spacing-base;
|
||||
}
|
||||
|
||||
&__pay-info {
|
||||
margin-top: @spacing-lg;
|
||||
margin-top: @spacing-base;
|
||||
padding-top: @spacing-base;
|
||||
border-top: 1px solid @border-color;
|
||||
border-top: 1px solid @project-divider;
|
||||
}
|
||||
|
||||
&__sub-title {
|
||||
margin-bottom: @spacing-sm;
|
||||
font-size: @font-size-base;
|
||||
font-weight: 600;
|
||||
margin-bottom: 12px;
|
||||
font-size: 11px;
|
||||
font-weight: 700;
|
||||
color: @heading-color;
|
||||
}
|
||||
|
||||
&__tip {
|
||||
margin-top: @spacing-lg;
|
||||
padding: @spacing-base;
|
||||
border-radius: @radius-base;
|
||||
margin-top: @spacing-base;
|
||||
padding: 12px;
|
||||
border-radius: @radius-sm;
|
||||
background: @bg-color;
|
||||
font-size: @font-size-base;
|
||||
font-size: 11px;
|
||||
}
|
||||
|
||||
&__empty {
|
||||
padding: @spacing-xl 0;
|
||||
text-align: center;
|
||||
font-size: @font-size-base;
|
||||
font-size: 11px;
|
||||
}
|
||||
|
||||
&__back {
|
||||
margin-top: @spacing-lg;
|
||||
max-width: 440px;
|
||||
margin: @spacing-base auto 0;
|
||||
}
|
||||
|
||||
// 设计 31/32:按钮蓝底 #024FFF(返回/立即支付同色)
|
||||
:deep(.app-button--primary) {
|
||||
background: @primary-strong;
|
||||
|
||||
&:hover {
|
||||
background: @primary-color;
|
||||
}
|
||||
}
|
||||
|
||||
&__back :deep(.app-button--default) {
|
||||
border-color: @primary-strong;
|
||||
background: @primary-strong;
|
||||
color: @white;
|
||||
|
||||
&:hover {
|
||||
border-color: @primary-color;
|
||||
background: @primary-color;
|
||||
color: @white;
|
||||
}
|
||||
}
|
||||
}
|
||||
</style>
|
||||
|
||||
@@ -75,84 +75,208 @@ onMounted(() => {
|
||||
<span>账单明细</span>
|
||||
</nav>
|
||||
|
||||
<div class="bills__tabs">
|
||||
<button
|
||||
v-for="tab in STATUS_TABS"
|
||||
:key="tab.value"
|
||||
class="bills__tab"
|
||||
:class="{ 'is-active': query.status === tab.value }"
|
||||
@click="onTab(tab.value)"
|
||||
>
|
||||
{{ tab.label }}
|
||||
</button>
|
||||
<!-- 设计 30:状态分段 Tab 与搜索栏同排共处一张白卡 -->
|
||||
<div class="bills__toolbar">
|
||||
<div class="bills__tabs">
|
||||
<button
|
||||
v-for="tab in STATUS_TABS"
|
||||
:key="tab.value"
|
||||
class="bills__tab"
|
||||
:class="{ 'is-active': query.status === tab.value }"
|
||||
@click="onTab(tab.value)"
|
||||
>
|
||||
{{ tab.label }}
|
||||
</button>
|
||||
</div>
|
||||
|
||||
<FilterPanel
|
||||
v-model:keyword="keyword"
|
||||
keyword-placeholder="搜索账单名称 / 账单号 / 项目名称"
|
||||
@search="onSearch"
|
||||
@reset="onReset"
|
||||
/>
|
||||
</div>
|
||||
|
||||
<FilterPanel
|
||||
v-model:keyword="keyword"
|
||||
keyword-placeholder="搜索账单名称 / 账单号 / 项目名称"
|
||||
@search="onSearch"
|
||||
@reset="onReset"
|
||||
/>
|
||||
<div class="bills__board">
|
||||
<BillTable
|
||||
:bills="list"
|
||||
:selected-ids="selectedIds"
|
||||
@update:selection="selectedIds = $event"
|
||||
@view="onView"
|
||||
@pay="onPay"
|
||||
/>
|
||||
|
||||
<BillTable
|
||||
:bills="list"
|
||||
:selected-ids="selectedIds"
|
||||
@update:selection="selectedIds = $event"
|
||||
@view="onView"
|
||||
@pay="onPay"
|
||||
/>
|
||||
<PaginationBar
|
||||
:page="query.page"
|
||||
:page-size="query.pageSize"
|
||||
:total="total"
|
||||
@page-change="onPageChange"
|
||||
/>
|
||||
</div>
|
||||
|
||||
<BillSummaryBar
|
||||
:bills="list"
|
||||
:selected-ids="selectedIds"
|
||||
@batch-pay="onBatchPay"
|
||||
/>
|
||||
|
||||
<PaginationBar
|
||||
:page="query.page"
|
||||
:page-size="query.pageSize"
|
||||
:total="total"
|
||||
@page-change="onPageChange"
|
||||
/>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<style lang="less" scoped>
|
||||
.bills {
|
||||
.flex(column, flex-start);
|
||||
align-items: stretch;
|
||||
gap: @spacing-base;
|
||||
padding-top: @spacing-lg;
|
||||
padding-bottom: @spacing-xxl;
|
||||
width: 100%;
|
||||
max-width: @container-width;
|
||||
margin: 0 auto;
|
||||
padding: @spacing-lg @spacing-base @spacing-xxl;
|
||||
|
||||
// 设计 30:面包屑 13 设计px → 11px,前缀灰、当前页深灰
|
||||
&__breadcrumb {
|
||||
font-size: @font-size-base;
|
||||
font-size: 11px;
|
||||
color: @text-color-disabled;
|
||||
|
||||
> span:last-child {
|
||||
color: @text-color;
|
||||
}
|
||||
}
|
||||
|
||||
// 顶部工具条:Tab 分段组 + 搜索栏(一张白卡)
|
||||
&__toolbar {
|
||||
.flex(row, flex-start, center);
|
||||
gap: @spacing-base;
|
||||
padding: 10px @spacing-base;
|
||||
border-radius: @radius-base;
|
||||
background: @white;
|
||||
box-shadow: @shadow-base;
|
||||
|
||||
:deep(.filter-panel) {
|
||||
flex: 1;
|
||||
min-width: 0;
|
||||
padding: 0;
|
||||
background: transparent;
|
||||
box-shadow: none;
|
||||
border-radius: 0;
|
||||
}
|
||||
|
||||
:deep(.filter-panel__body) {
|
||||
margin-top: 0;
|
||||
}
|
||||
|
||||
:deep(.filter-panel__bar) {
|
||||
gap: @spacing-sm;
|
||||
}
|
||||
|
||||
:deep(.filter-panel__input) {
|
||||
order: 1;
|
||||
flex: 1;
|
||||
width: auto;
|
||||
height: 26px;
|
||||
border: none;
|
||||
border-radius: @radius-sm;
|
||||
background: @finance-field-bg;
|
||||
font-size: 11px;
|
||||
|
||||
&::placeholder {
|
||||
color: @contract-placeholder;
|
||||
}
|
||||
}
|
||||
|
||||
// 设计顺序:… 重置 搜索(FilterPanel 模板为搜索在前,用 order 调序)
|
||||
:deep(.filter-panel__btn--primary) {
|
||||
order: 3;
|
||||
height: 26px;
|
||||
padding: 0 14px;
|
||||
border: none;
|
||||
background: @primary-strong;
|
||||
font-size: 11px;
|
||||
|
||||
&:hover {
|
||||
background: @primary-color;
|
||||
}
|
||||
}
|
||||
|
||||
:deep(.filter-panel__btn:not(.filter-panel__btn--primary)) {
|
||||
order: 2;
|
||||
height: 26px;
|
||||
padding: 0 14px;
|
||||
border: none;
|
||||
background: @project-quiet-btn;
|
||||
color: @text-color;
|
||||
font-size: 11px;
|
||||
|
||||
&:hover {
|
||||
border: none;
|
||||
background: @border-color;
|
||||
color: @text-color;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// 状态 Tab:描边分段组,选中实底 #024FFF(设计 30)
|
||||
&__tabs {
|
||||
.flex(row, flex-start);
|
||||
gap: @spacing-sm;
|
||||
gap: 0;
|
||||
border: 1px solid @border-color;
|
||||
border-radius: @radius-sm;
|
||||
overflow: hidden;
|
||||
flex-shrink: 0;
|
||||
}
|
||||
|
||||
&__tab {
|
||||
height: 34px;
|
||||
padding: 0 @spacing-base;
|
||||
border: 1px solid @border-color;
|
||||
border-radius: @radius-base;
|
||||
height: 26px;
|
||||
padding: 0 14px;
|
||||
border: none;
|
||||
border-right: 1px solid @border-color;
|
||||
border-radius: 0;
|
||||
background: @white;
|
||||
color: @text-color;
|
||||
font-size: @font-size-base;
|
||||
font-size: 11px;
|
||||
transition: all 0.2s;
|
||||
|
||||
&:last-child {
|
||||
border-right: none;
|
||||
}
|
||||
|
||||
&:hover {
|
||||
border-color: @primary-color;
|
||||
color: @primary-color;
|
||||
color: @primary-strong;
|
||||
}
|
||||
|
||||
&.is-active {
|
||||
border-color: @primary-color;
|
||||
background: @primary-color;
|
||||
border-right-color: @primary-strong;
|
||||
background: @primary-strong;
|
||||
color: @white;
|
||||
}
|
||||
}
|
||||
|
||||
// 表格 + 分页共处白卡(设计 30:分页在卡片内右下角)
|
||||
&__board {
|
||||
border-radius: @radius-base;
|
||||
background: @white;
|
||||
box-shadow: @shadow-base;
|
||||
overflow: hidden;
|
||||
}
|
||||
|
||||
// 分页:右对齐小方格,选中浅蓝底蓝字(设计 30/35)
|
||||
.pagination {
|
||||
justify-content: flex-end;
|
||||
padding: 12px @spacing-base @spacing-base;
|
||||
}
|
||||
|
||||
:deep(.pagination__btn) {
|
||||
min-width: 24px;
|
||||
height: 24px;
|
||||
border-color: @border-color;
|
||||
border-radius: @radius-sm;
|
||||
color: @text-color-secondary;
|
||||
font-size: 11px;
|
||||
|
||||
&.is-active {
|
||||
border-color: @primary-strong;
|
||||
background: @finance-page-active;
|
||||
color: @primary-strong;
|
||||
}
|
||||
}
|
||||
}
|
||||
</style>
|
||||
|
||||
@@ -34,17 +34,22 @@ function onBatchPay(): void {
|
||||
</script>
|
||||
|
||||
<template>
|
||||
<!-- 设计 30:整幅白条——左「已选择 N 笔订单」+ 统计,右「合计:¥ 金额 + 立即支付」 -->
|
||||
<div class="bill-summary">
|
||||
<div class="bill-summary__stats">
|
||||
<span class="bill-summary__stat">总笔数:<strong>{{ totalCount }}</strong></span>
|
||||
<span class="bill-summary__stat">总金额:<strong>¥{{ formatMoney(totalAmount) }}</strong></span>
|
||||
<span class="bill-summary__stat">待支付:<strong>{{ pendingCount }}</strong></span>
|
||||
<div class="bill-summary__left">
|
||||
<span class="bill-summary__selected">
|
||||
已选择<strong>{{ selectedBills.length }}</strong>笔订单
|
||||
</span>
|
||||
<div class="bill-summary__stats">
|
||||
<span class="bill-summary__stat">总笔数:<strong>{{ totalCount }}</strong></span>
|
||||
<span class="bill-summary__stat">总金额:<strong>¥{{ formatMoney(totalAmount) }}</strong></span>
|
||||
<span class="bill-summary__stat">待支付:<strong>{{ pendingCount }}</strong></span>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="bill-summary__right">
|
||||
<span class="bill-summary__selected">
|
||||
已选择{{ selectedBills.length }}笔订单 · 合计:¥{{ formatMoney(selectedAmount) }}
|
||||
</span>
|
||||
<span class="bill-summary__label">合计:</span>
|
||||
<span class="bill-summary__amount">¥{{ formatMoney(selectedAmount) }}</span>
|
||||
<AppButton
|
||||
type="primary"
|
||||
:disabled="!canPay"
|
||||
@@ -59,30 +64,73 @@ function onBatchPay(): void {
|
||||
<style lang="less" scoped>
|
||||
.bill-summary {
|
||||
.flex(row, space-between, center);
|
||||
padding: @spacing-base @spacing-lg;
|
||||
border-radius: @radius-lg;
|
||||
gap: @spacing-base;
|
||||
margin: 0 -16px;
|
||||
padding: 10px @spacing-base;
|
||||
border-radius: 0;
|
||||
background: @white;
|
||||
box-shadow: @shadow-base;
|
||||
|
||||
&__left {
|
||||
.flex(row, flex-start, center);
|
||||
gap: @spacing-lg;
|
||||
min-width: 0;
|
||||
}
|
||||
|
||||
&__selected {
|
||||
font-size: 11px;
|
||||
color: @text-color;
|
||||
white-space: nowrap;
|
||||
|
||||
strong {
|
||||
margin: 0 2px;
|
||||
color: @danger-color;
|
||||
font-weight: 700;
|
||||
}
|
||||
}
|
||||
|
||||
&__stats {
|
||||
.flex(row, flex-start);
|
||||
.flex(row, flex-start, center);
|
||||
gap: @spacing-lg;
|
||||
font-size: @font-size-base;
|
||||
font-size: 11px;
|
||||
color: @text-color;
|
||||
|
||||
strong {
|
||||
color: @heading-color;
|
||||
font-weight: 600;
|
||||
}
|
||||
}
|
||||
|
||||
&__right {
|
||||
.flex(row, flex-end, center);
|
||||
gap: @spacing-base;
|
||||
gap: 6px;
|
||||
flex-shrink: 0;
|
||||
}
|
||||
|
||||
&__selected {
|
||||
font-size: @font-size-base;
|
||||
&__label {
|
||||
font-size: 11px;
|
||||
color: @text-color;
|
||||
}
|
||||
|
||||
// 合计金额:设计 30 实取 20 设计px → 15px 粗体红
|
||||
&__amount {
|
||||
margin-right: @spacing-sm;
|
||||
font-size: 15px;
|
||||
font-weight: 700;
|
||||
color: @danger-color;
|
||||
white-space: nowrap;
|
||||
}
|
||||
|
||||
// 「立即支付」:设计 30 实取橙色按钮
|
||||
:deep(.app-button--primary) {
|
||||
height: 28px;
|
||||
padding: 0 14px;
|
||||
background: @finance-summary-cta;
|
||||
color: @white;
|
||||
font-size: 11px;
|
||||
|
||||
&:hover {
|
||||
background: @warning-color;
|
||||
}
|
||||
}
|
||||
}
|
||||
</style>
|
||||
|
||||
@@ -118,31 +118,33 @@ const STATUS_VARIANTS: Record<BillStatus, 'warning' | 'success' | 'info' | 'dang
|
||||
</template>
|
||||
|
||||
<style lang="less" scoped>
|
||||
// 设计 30:表格贴满白卡(外层 .bills__board 提供卡底),全网格浅灰线 + 浅灰表头
|
||||
.bill-table {
|
||||
padding: @spacing-base;
|
||||
border-radius: @radius-lg;
|
||||
background: @white;
|
||||
box-shadow: @shadow-base;
|
||||
padding: 0;
|
||||
border-radius: 0;
|
||||
background: transparent;
|
||||
box-shadow: none;
|
||||
overflow-x: auto;
|
||||
|
||||
&__table {
|
||||
width: 100%;
|
||||
border-collapse: collapse;
|
||||
font-size: @font-size-base;
|
||||
font-size: 11px;
|
||||
color: @text-color;
|
||||
|
||||
th,
|
||||
td {
|
||||
padding: @spacing-sm @spacing-sm;
|
||||
padding: 11px 10px;
|
||||
text-align: left;
|
||||
white-space: nowrap;
|
||||
border-bottom: 1px solid @border-color;
|
||||
border: 1px solid @project-divider;
|
||||
}
|
||||
|
||||
th {
|
||||
background: @bg-color-light;
|
||||
color: @text-color-secondary;
|
||||
font-weight: 500;
|
||||
background: @finance-table-head-bg;
|
||||
color: @text-color;
|
||||
font-weight: 600;
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
tbody tr:hover {
|
||||
@@ -150,28 +152,54 @@ const STATUS_VARIANTS: Record<BillStatus, 'warning' | 'success' | 'info' | 'dang
|
||||
}
|
||||
}
|
||||
|
||||
&__check {
|
||||
width: 40px;
|
||||
// 列对齐按设计 30:序号/账单号/流水号/金额/状态/操作居中,名称类左对齐
|
||||
&__table th:nth-child(1),
|
||||
&__table th:nth-child(2),
|
||||
&__table td:nth-child(1),
|
||||
&__table td:nth-child(2),
|
||||
&__table th:nth-child(4),
|
||||
&__table td:nth-child(4),
|
||||
&__table th:nth-child(5),
|
||||
&__table td:nth-child(5),
|
||||
&__table th:nth-child(7),
|
||||
&__table td:nth-child(7),
|
||||
&__table th:nth-child(8),
|
||||
&__table td:nth-child(8),
|
||||
&__table th:nth-child(9),
|
||||
&__table td:nth-child(9) {
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
&__check {
|
||||
width: 44px;
|
||||
text-align: center;
|
||||
|
||||
input {
|
||||
width: 14px;
|
||||
height: 14px;
|
||||
accent-color: @primary-strong;
|
||||
vertical-align: middle;
|
||||
}
|
||||
}
|
||||
|
||||
// 金额列与正文同色(设计 30 实取 #4B5563 常规字重)
|
||||
&__amount {
|
||||
color: @heading-color;
|
||||
font-weight: 600;
|
||||
color: @text-color;
|
||||
font-weight: 400;
|
||||
}
|
||||
|
||||
&__ops {
|
||||
.flex(row, flex-start);
|
||||
gap: @spacing-sm;
|
||||
.flex(row, center, center);
|
||||
gap: 12px;
|
||||
}
|
||||
|
||||
&__link {
|
||||
color: @primary-color;
|
||||
font-size: @font-size-base;
|
||||
color: @primary-strong;
|
||||
font-size: 11px;
|
||||
transition: color 0.2s;
|
||||
|
||||
&:hover {
|
||||
color: @primary-hover;
|
||||
color: @primary-color;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -179,5 +207,14 @@ const STATUS_VARIANTS: Record<BillStatus, 'warning' | 'success' | 'info' | 'dang
|
||||
text-align: center;
|
||||
padding: @spacing-xl 0;
|
||||
}
|
||||
|
||||
// 状态列按设计 30 为纯文字(去底色徽标)
|
||||
:deep(.status-tag) {
|
||||
padding: 0;
|
||||
background: transparent;
|
||||
color: @text-color;
|
||||
font-size: 11px;
|
||||
line-height: 1.5;
|
||||
}
|
||||
}
|
||||
</style>
|
||||
|
||||
@@ -39,6 +39,25 @@ function percentOf(value: number): number {
|
||||
业务类型分布
|
||||
</h3>
|
||||
<div class="finance-chart__body">
|
||||
<!-- 设计 37:横向网格线 + 等宽柱条(柱高按占比换算) -->
|
||||
<div class="finance-chart__plot">
|
||||
<div class="finance-chart__grid" aria-hidden="true">
|
||||
<i class="finance-chart__line" />
|
||||
<i class="finance-chart__line" />
|
||||
<i class="finance-chart__line" />
|
||||
<i class="finance-chart__line" />
|
||||
<i class="finance-chart__line" />
|
||||
</div>
|
||||
<div class="finance-chart__bars">
|
||||
<span
|
||||
v-for="item in distribution"
|
||||
:key="item.name"
|
||||
class="finance-chart__bar"
|
||||
:style="{ height: `${Math.max(percentOf(item.value), 6)}%` }"
|
||||
/>
|
||||
</div>
|
||||
</div>
|
||||
<!-- 数据源色环:设计稿为柱状图,此处仅保留绑定(隐藏)以免游离变量 -->
|
||||
<div class="finance-chart__pie" :style="{ background: gradient }" />
|
||||
<ul class="finance-chart__legend">
|
||||
<li
|
||||
@@ -59,52 +78,100 @@ function percentOf(value: number): number {
|
||||
</template>
|
||||
|
||||
<style lang="less" scoped>
|
||||
// 设计 37:白卡 + 蓝色竖条标题(15 设计px → 12px/700)+ 柱状图 + 横排图例
|
||||
.finance-chart {
|
||||
padding: @spacing-lg;
|
||||
border-radius: @radius-lg;
|
||||
padding: 20px @spacing-lg @spacing-lg;
|
||||
border-radius: @radius-base;
|
||||
background: @white;
|
||||
box-shadow: @shadow-base;
|
||||
|
||||
&__title {
|
||||
position: relative;
|
||||
padding-left: 10px;
|
||||
margin-bottom: @spacing-base;
|
||||
font-size: @font-size-lg;
|
||||
font-weight: 600;
|
||||
font-size: 12px;
|
||||
font-weight: 700;
|
||||
color: @heading-color;
|
||||
|
||||
&::before {
|
||||
content: '';
|
||||
position: absolute;
|
||||
top: 50%;
|
||||
left: 0;
|
||||
width: 4px;
|
||||
height: 14px;
|
||||
border-radius: @radius-round;
|
||||
background: @primary-strong;
|
||||
transform: translateY(-50%);
|
||||
}
|
||||
}
|
||||
|
||||
&__body {
|
||||
.flex(row, center, center);
|
||||
gap: @spacing-xl;
|
||||
.flex(column, center, center);
|
||||
gap: @spacing-base;
|
||||
}
|
||||
|
||||
&__plot {
|
||||
position: relative;
|
||||
width: 100%;
|
||||
height: 184px;
|
||||
}
|
||||
|
||||
&__grid {
|
||||
.flex(column, space-between);
|
||||
position: absolute;
|
||||
inset: 0;
|
||||
}
|
||||
|
||||
&__line {
|
||||
display: block;
|
||||
width: 100%;
|
||||
height: 1px;
|
||||
background: @finance-chart-grid;
|
||||
}
|
||||
|
||||
&__bars {
|
||||
.flex(row, space-around, flex-end);
|
||||
position: absolute;
|
||||
inset: 0;
|
||||
padding: 0 60px;
|
||||
}
|
||||
|
||||
&__bar {
|
||||
display: block;
|
||||
width: 40px;
|
||||
border-radius: 2px 2px 0 0;
|
||||
background: @finance-chart-bar;
|
||||
}
|
||||
|
||||
// 设计稿无色环:绑定保留但不参与展示
|
||||
&__pie {
|
||||
width: 180px;
|
||||
height: 180px;
|
||||
border-radius: @radius-round;
|
||||
flex-shrink: 0;
|
||||
display: none;
|
||||
}
|
||||
|
||||
&__legend {
|
||||
.flex(column, flex-start);
|
||||
gap: @spacing-base;
|
||||
.flex(row, center, center);
|
||||
gap: @spacing-lg;
|
||||
list-style: none;
|
||||
padding: 0;
|
||||
}
|
||||
|
||||
&__legend-item {
|
||||
.flex(row, flex-start, center);
|
||||
gap: @spacing-sm;
|
||||
font-size: @font-size-base;
|
||||
color: @text-color;
|
||||
gap: 6px;
|
||||
font-size: 11px;
|
||||
color: @text-color-secondary;
|
||||
}
|
||||
|
||||
&__dot {
|
||||
width: 10px;
|
||||
height: 10px;
|
||||
width: 8px;
|
||||
height: 8px;
|
||||
border-radius: @radius-round;
|
||||
flex-shrink: 0;
|
||||
}
|
||||
|
||||
&__name {
|
||||
min-width: 72px;
|
||||
min-width: 0;
|
||||
}
|
||||
|
||||
&__value {
|
||||
|
||||
@@ -63,33 +63,39 @@ const emit = defineEmits<{
|
||||
</template>
|
||||
|
||||
<style lang="less" scoped>
|
||||
// 设计 37:整卡为蓝紫渐变(累计消费总额白字),右上角白色操作链接
|
||||
.finance-overview {
|
||||
.flex(row, space-between, center);
|
||||
padding: @spacing-lg;
|
||||
border-radius: @radius-lg;
|
||||
background: @white;
|
||||
.flex(column, flex-start, stretch);
|
||||
flex: 1 1 500px;
|
||||
min-width: 0;
|
||||
padding: 14px @spacing-lg 16px;
|
||||
border-radius: @radius-base;
|
||||
background: @finance-hero-gradient;
|
||||
box-shadow: @shadow-base;
|
||||
|
||||
&__main {
|
||||
.flex(column, flex-start);
|
||||
gap: @spacing-sm;
|
||||
.flex(column, flex-start, flex-start);
|
||||
gap: 6px;
|
||||
}
|
||||
|
||||
&__label {
|
||||
font-size: @font-size-base;
|
||||
color: @white;
|
||||
font-size: 11px;
|
||||
}
|
||||
|
||||
&__amount {
|
||||
font-size: 36px;
|
||||
font-weight: 600;
|
||||
color: @heading-color;
|
||||
line-height: 1.2;
|
||||
color: @white;
|
||||
font-size: 29px;
|
||||
font-weight: 700;
|
||||
line-height: 1.15;
|
||||
}
|
||||
|
||||
&__meta {
|
||||
.flex(row, flex-start, center);
|
||||
gap: @spacing-base;
|
||||
font-size: @font-size-base;
|
||||
margin-top: 4px;
|
||||
font-size: 11px;
|
||||
color: fade(@white, 85%);
|
||||
}
|
||||
|
||||
&__periods {
|
||||
@@ -98,38 +104,52 @@ const emit = defineEmits<{
|
||||
}
|
||||
|
||||
&__period {
|
||||
height: 28px;
|
||||
height: 22px;
|
||||
padding: 0 @spacing-sm;
|
||||
border: 1px solid @border-color;
|
||||
border: 1px solid fade(@white, 45%);
|
||||
border-radius: @radius-sm;
|
||||
background: @white;
|
||||
color: @text-color;
|
||||
font-size: @font-size-sm;
|
||||
background: fade(@white, 16%);
|
||||
color: @white;
|
||||
font-size: 11px;
|
||||
transition: all 0.2s;
|
||||
|
||||
&:hover {
|
||||
border-color: @primary-color;
|
||||
color: @primary-color;
|
||||
border-color: @white;
|
||||
background: fade(@white, 30%);
|
||||
color: @white;
|
||||
}
|
||||
}
|
||||
|
||||
&__month {
|
||||
font-size: @font-size-sm;
|
||||
font-size: 11px;
|
||||
color: fade(@white, 85%);
|
||||
}
|
||||
|
||||
// 待支付小徽标压到渐变上:半透明白底 + 白字
|
||||
:deep(.status-tag) {
|
||||
background: fade(@white, 20%);
|
||||
color: @white;
|
||||
font-size: 11px;
|
||||
}
|
||||
|
||||
// 操作链接置顶右对齐(对应设计右上角「2026年账单 ›」位置)
|
||||
&__actions {
|
||||
.flex(row, flex-start);
|
||||
order: -1;
|
||||
align-self: stretch;
|
||||
.flex(row, flex-end, center);
|
||||
gap: @spacing-base;
|
||||
margin-bottom: 4px;
|
||||
}
|
||||
|
||||
&__action {
|
||||
font-size: @font-size-base;
|
||||
color: @primary-color;
|
||||
font-size: 11px;
|
||||
color: fade(@white, 92%);
|
||||
cursor: pointer;
|
||||
transition: color 0.2s;
|
||||
|
||||
&:hover {
|
||||
color: @primary-hover;
|
||||
color: @white;
|
||||
text-decoration: underline;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -16,95 +16,84 @@ const emit = defineEmits<{
|
||||
</script>
|
||||
|
||||
<template>
|
||||
<!-- 设计 35/36:一行一张宽卡——左上默认徽标、右上操作按钮,下方三栏字段 -->
|
||||
<div class="invoice-title-card">
|
||||
<div class="invoice-title-card__head">
|
||||
<span class="invoice-title-card__label text-secondary">发票抬头</span>
|
||||
<StatusTag
|
||||
:label="invoiceTitle.type"
|
||||
:variant="invoiceTitle.type === '企业单位' ? 'primary' : 'info'"
|
||||
/>
|
||||
<div class="invoice-title-card__top">
|
||||
<StatusTag v-if="invoiceTitle.isDefault" label="默认" variant="success" />
|
||||
</div>
|
||||
<p class="invoice-title-card__title">
|
||||
{{ invoiceTitle.title }}
|
||||
</p>
|
||||
<div class="invoice-title-card__tax">
|
||||
<span class="invoice-title-card__label text-secondary">税号</span>
|
||||
<span class="invoice-title-card__tax-no">{{ invoiceTitle.taxNo }}</span>
|
||||
<div class="invoice-title-card__actions">
|
||||
<button
|
||||
class="invoice-title-card__btn"
|
||||
@click="emit('setDefault', invoiceTitle.id)"
|
||||
>
|
||||
{{ invoiceTitle.isDefault ? '取消默认' : '设为默认' }}
|
||||
</button>
|
||||
<button class="invoice-title-card__btn is-danger" @click="emit('delete', invoiceTitle.id)">
|
||||
删除
|
||||
</button>
|
||||
<button class="invoice-title-card__btn" @click="emit('edit', invoiceTitle)">
|
||||
编辑
|
||||
</button>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="invoice-title-card__actions">
|
||||
<button
|
||||
class="invoice-title-card__btn"
|
||||
@click="emit('setDefault', invoiceTitle.id)"
|
||||
>
|
||||
{{ invoiceTitle.isDefault ? '取消默认' : '设为默认' }}
|
||||
</button>
|
||||
<button class="invoice-title-card__btn" @click="emit('edit', invoiceTitle)">
|
||||
编辑
|
||||
</button>
|
||||
<button class="invoice-title-card__btn is-danger" @click="emit('delete', invoiceTitle.id)">
|
||||
删除
|
||||
</button>
|
||||
<div class="invoice-title-card__cols">
|
||||
<div class="invoice-title-card__col">
|
||||
<StatusTag
|
||||
:label="invoiceTitle.type"
|
||||
:variant="invoiceTitle.type === '企业单位' ? 'primary' : 'info'"
|
||||
/>
|
||||
</div>
|
||||
<div class="invoice-title-card__col">
|
||||
<span class="invoice-title-card__label text-secondary">发票抬头</span>
|
||||
<p class="invoice-title-card__title">
|
||||
{{ invoiceTitle.title }}
|
||||
</p>
|
||||
</div>
|
||||
<div class="invoice-title-card__col">
|
||||
<span class="invoice-title-card__label text-secondary">税号</span>
|
||||
<span class="invoice-title-card__tax-no">{{ invoiceTitle.taxNo }}</span>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<style lang="less" scoped>
|
||||
.invoice-title-card {
|
||||
padding: @spacing-base;
|
||||
border: 1px solid @border-color;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
gap: 16px;
|
||||
padding: 14px 20px;
|
||||
border: none;
|
||||
border-radius: @radius-base;
|
||||
background: @white;
|
||||
.flex(column, flex-start);
|
||||
gap: @spacing-sm;
|
||||
box-shadow: @shadow-base;
|
||||
|
||||
&__head {
|
||||
.flex(row, flex-start, center);
|
||||
gap: @spacing-sm;
|
||||
}
|
||||
|
||||
&__label {
|
||||
font-size: @font-size-sm;
|
||||
}
|
||||
|
||||
&__title {
|
||||
font-size: @font-size-lg;
|
||||
font-weight: 600;
|
||||
color: @heading-color;
|
||||
word-break: break-all;
|
||||
}
|
||||
|
||||
&__tax {
|
||||
.flex(row, flex-start, center);
|
||||
gap: @spacing-sm;
|
||||
}
|
||||
|
||||
&__tax-no {
|
||||
font-size: @font-size-base;
|
||||
color: @text-color;
|
||||
word-break: break-all;
|
||||
// 顶行:默认徽标居左、操作按钮居右(设计 35 同一行)
|
||||
&__top {
|
||||
.flex(row, space-between, center);
|
||||
min-height: 24px;
|
||||
}
|
||||
|
||||
&__actions {
|
||||
.flex(row, flex-start);
|
||||
.flex(row, flex-end, center);
|
||||
gap: @spacing-sm;
|
||||
margin-top: @spacing-xs;
|
||||
}
|
||||
|
||||
// 描边小按钮:浅灰边白底 11px(设计 35 实取)
|
||||
&__btn {
|
||||
height: 28px;
|
||||
padding: 0 @spacing-sm;
|
||||
border: 1px solid @border-color-dark;
|
||||
height: 24px;
|
||||
padding: 0 10px;
|
||||
border: 1px solid @border-color;
|
||||
border-radius: @radius-sm;
|
||||
background: @white;
|
||||
color: @text-color;
|
||||
font-size: @font-size-sm;
|
||||
font-size: 11px;
|
||||
cursor: pointer;
|
||||
transition: all 0.2s;
|
||||
|
||||
&:hover:not(:disabled) {
|
||||
border-color: @primary-color;
|
||||
color: @primary-color;
|
||||
border-color: @primary-strong;
|
||||
color: @primary-strong;
|
||||
}
|
||||
|
||||
&.is-danger:hover:not(:disabled) {
|
||||
@@ -112,5 +101,49 @@ const emit = defineEmits<{
|
||||
color: @danger-color;
|
||||
}
|
||||
}
|
||||
|
||||
// 三栏字段:列起点按设计 35(x97 / x579 / x1061,卡内 0 / 371 / 742 CSS)
|
||||
&__cols {
|
||||
display: grid;
|
||||
grid-template-columns: minmax(0, 371px) minmax(0, 371px) minmax(0, 1fr);
|
||||
gap: @spacing-base;
|
||||
}
|
||||
|
||||
&__col {
|
||||
.flex(column, flex-start, flex-start);
|
||||
gap: 6px;
|
||||
min-width: 0;
|
||||
}
|
||||
|
||||
// 标签 11 设计px → 11px 灰;值 14 设计px → 11px 粗体深色
|
||||
&__label {
|
||||
font-size: 11px;
|
||||
}
|
||||
|
||||
&__title,
|
||||
&__tax-no {
|
||||
font-size: 11px;
|
||||
font-weight: 700;
|
||||
color: @heading-color;
|
||||
word-break: break-all;
|
||||
}
|
||||
|
||||
// 抬头类型值:去掉徽标底色,按设计为纯文字
|
||||
:deep(.status-tag) {
|
||||
padding: 0;
|
||||
background: transparent;
|
||||
color: @heading-color;
|
||||
font-size: 11px;
|
||||
font-weight: 700;
|
||||
align-self: flex-start;
|
||||
}
|
||||
|
||||
// 「默认」徽标:设计 35 为实底蓝底白字小胶囊
|
||||
:deep(.status-tag--success) {
|
||||
padding: 2px 8px;
|
||||
background: @primary-strong;
|
||||
color: @white;
|
||||
font-weight: 500;
|
||||
}
|
||||
}
|
||||
</style>
|
||||
|
||||
@@ -53,8 +53,7 @@ const qrSvg = computed(() => {
|
||||
qr.addData(props.content)
|
||||
qr.make()
|
||||
return qr.createSvgTag({ cellSize: 4, margin: 2, scalable: true })
|
||||
}
|
||||
catch {
|
||||
} catch {
|
||||
return ''
|
||||
}
|
||||
})
|
||||
@@ -98,12 +97,8 @@ function onBoxClick(): void {
|
||||
<Teleport to="body">
|
||||
<div v-if="visible" class="wx-qr" @click.self="close">
|
||||
<div class="wx-qr__panel">
|
||||
<h3 class="wx-qr__title">
|
||||
微信扫码支付
|
||||
</h3>
|
||||
<p class="wx-qr__amount">
|
||||
¥{{ formatMoney(amount) }}
|
||||
</p>
|
||||
<h3 class="wx-qr__title">微信扫码支付</h3>
|
||||
<p class="wx-qr__amount">¥{{ formatMoney(amount) }}</p>
|
||||
|
||||
<div
|
||||
class="wx-qr__box"
|
||||
@@ -115,25 +110,21 @@ function onBoxClick(): void {
|
||||
<div v-else class="wx-qr__mask">
|
||||
<span class="wx-qr__mask-icon">⟳</span>
|
||||
<span class="wx-qr__mask-text">
|
||||
{{ expired ? '二维码已过期' : '二维码生成中' }}<br>点击刷新
|
||||
{{ expired ? '二维码已过期' : '二维码生成中' }}<br />点击刷新
|
||||
</span>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<p class="wx-qr__status">
|
||||
<template v-if="!expired">
|
||||
请使用手机微信 <strong>[扫一扫]</strong> 扫描上方二维码,
|
||||
二维码 <strong class="wx-qr__count">{{ countdownText }}</strong> 后失效
|
||||
</template>
|
||||
<template v-else>
|
||||
二维码已过期,请点击二维码或下方按钮刷新
|
||||
请使用手机微信 <strong>[扫一扫]</strong> 扫描上方二维码, 二维码
|
||||
<strong class="wx-qr__count">{{ countdownText }}</strong> 后失效
|
||||
</template>
|
||||
<template v-else> 二维码已过期,请点击二维码或下方按钮刷新 </template>
|
||||
</p>
|
||||
|
||||
<div class="wx-qr__actions">
|
||||
<button class="wx-qr__btn" @click="refresh">
|
||||
刷新二维码
|
||||
</button>
|
||||
<button class="wx-qr__btn" @click="refresh">刷新二维码</button>
|
||||
<button class="wx-qr__btn wx-qr__btn--cta" @click="onPaid">
|
||||
我已完成支付
|
||||
</button>
|
||||
|
||||
@@ -36,75 +36,99 @@ onMounted(() => {
|
||||
</p>
|
||||
</header>
|
||||
|
||||
<FinanceOverview
|
||||
:stats="stats"
|
||||
@period-change="onPeriodChange"
|
||||
@export="onExport"
|
||||
/>
|
||||
<div class="finance__top">
|
||||
<FinanceOverview
|
||||
:stats="stats"
|
||||
@period-change="onPeriodChange"
|
||||
@export="onExport"
|
||||
/>
|
||||
|
||||
<div class="finance__entries">
|
||||
<RouterLink to="/finance/invoices" class="finance__entry">
|
||||
<span class="finance__entry-icon">🧾</span>
|
||||
<span class="finance__entry-name">发票申请</span>
|
||||
</RouterLink>
|
||||
<RouterLink to="/finance/bills" class="finance__entry">
|
||||
<span class="finance__entry-icon">📋</span>
|
||||
<span class="finance__entry-name">账单明细</span>
|
||||
</RouterLink>
|
||||
<button class="finance__entry" @click="onExport">
|
||||
<span class="finance__entry-icon">📊</span>
|
||||
<span class="finance__entry-name">报表导出</span>
|
||||
</button>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<FinanceChart :distribution="stats?.distribution ?? []" />
|
||||
|
||||
<div class="finance__entries">
|
||||
<RouterLink to="/finance/invoices" class="finance__entry">
|
||||
<span class="finance__entry-icon">🧾</span>
|
||||
<span class="finance__entry-name">发票申请</span>
|
||||
</RouterLink>
|
||||
<RouterLink to="/finance/bills" class="finance__entry">
|
||||
<span class="finance__entry-icon">📋</span>
|
||||
<span class="finance__entry-name">账单明细</span>
|
||||
</RouterLink>
|
||||
<button class="finance__entry" @click="onExport">
|
||||
<span class="finance__entry-icon">📊</span>
|
||||
<span class="finance__entry-name">报表导出</span>
|
||||
</button>
|
||||
</div>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<style lang="less" scoped>
|
||||
.finance {
|
||||
.flex(column, flex-start);
|
||||
align-items: stretch;
|
||||
gap: @spacing-base;
|
||||
padding-top: @spacing-xl;
|
||||
padding-bottom: @spacing-xxl;
|
||||
width: 100%;
|
||||
max-width: @container-width;
|
||||
margin: 0 auto;
|
||||
padding: 40px @spacing-base @spacing-xxl;
|
||||
|
||||
// 设计 37:页头标题 22 设计px × 0.77 ≈ 17px 加粗,副标语 13 设计px → 11px 居中
|
||||
&__title {
|
||||
font-size: @font-size-xxl;
|
||||
font-weight: 600;
|
||||
font-size: 17px;
|
||||
font-weight: 700;
|
||||
color: @heading-color;
|
||||
}
|
||||
|
||||
&__slogan {
|
||||
margin-top: @spacing-xs;
|
||||
font-size: @font-size-base;
|
||||
font-size: 11px;
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
// 顶部行:左「累计消费」渐变卡 + 右快捷入口白卡(设计 37 同排并列)
|
||||
&__top {
|
||||
.flex(row, flex-start, stretch);
|
||||
gap: @spacing-base;
|
||||
flex-wrap: wrap;
|
||||
}
|
||||
|
||||
&__entries {
|
||||
.flex(row, flex-start);
|
||||
.flex(row, space-around, center);
|
||||
flex: 0 0 500px;
|
||||
gap: @spacing-base;
|
||||
padding: @spacing-base @spacing-lg;
|
||||
border-radius: @radius-base;
|
||||
background: @white;
|
||||
box-shadow: @shadow-base;
|
||||
}
|
||||
|
||||
&__entry {
|
||||
.flex(row, center, center);
|
||||
.flex(column, center, center);
|
||||
gap: @spacing-sm;
|
||||
width: 200px;
|
||||
height: 72px;
|
||||
border: 1px solid @border-color;
|
||||
border-radius: @radius-base;
|
||||
background: @white;
|
||||
width: auto;
|
||||
height: auto;
|
||||
border: none;
|
||||
border-radius: 0;
|
||||
background: transparent;
|
||||
color: @text-color;
|
||||
font-size: @font-size-lg;
|
||||
font-size: 11px;
|
||||
cursor: pointer;
|
||||
transition: all 0.2s;
|
||||
transition: color 0.2s;
|
||||
|
||||
&:hover {
|
||||
border-color: @primary-color;
|
||||
color: @primary-color;
|
||||
border: none;
|
||||
color: @primary-strong;
|
||||
}
|
||||
}
|
||||
|
||||
&__entry-icon {
|
||||
font-size: @font-size-xl;
|
||||
.flex(row, center, center);
|
||||
width: 36px;
|
||||
height: 36px;
|
||||
border-radius: @radius-base;
|
||||
background: @bg-color;
|
||||
font-size: 18px;
|
||||
}
|
||||
}
|
||||
</style>
|
||||
|
||||
@@ -146,24 +146,52 @@ onMounted(() => {
|
||||
<style lang="less" scoped>
|
||||
.invoice-titles {
|
||||
.flex(column, flex-start);
|
||||
align-items: stretch;
|
||||
gap: @spacing-base;
|
||||
padding-top: @spacing-lg;
|
||||
padding-bottom: @spacing-xxl;
|
||||
width: 100%;
|
||||
max-width: @container-width;
|
||||
margin: 0 auto;
|
||||
padding: @spacing-lg @spacing-base @spacing-xxl;
|
||||
|
||||
// 设计 35/36:面包屑 13 设计px → 11px,前缀灰、当前页深灰
|
||||
&__breadcrumb {
|
||||
font-size: @font-size-base;
|
||||
font-size: 11px;
|
||||
color: @text-color-disabled;
|
||||
|
||||
> span:last-child {
|
||||
color: @text-color;
|
||||
}
|
||||
}
|
||||
|
||||
// 顶部「发票管理」白卡条(设计 35:蓝竖条标题 + 右侧按钮组)
|
||||
&__head {
|
||||
.flex(row, space-between, center);
|
||||
flex-wrap: wrap;
|
||||
gap: @spacing-base;
|
||||
padding: 14px 20px;
|
||||
border-radius: @radius-base;
|
||||
background: @white;
|
||||
box-shadow: @shadow-base;
|
||||
}
|
||||
|
||||
&__title {
|
||||
font-size: @font-size-xl;
|
||||
font-weight: 600;
|
||||
position: relative;
|
||||
padding-left: 10px;
|
||||
font-size: 12px;
|
||||
font-weight: 700;
|
||||
color: @heading-color;
|
||||
|
||||
&::before {
|
||||
content: '';
|
||||
position: absolute;
|
||||
top: 50%;
|
||||
left: 0;
|
||||
width: 4px;
|
||||
height: 14px;
|
||||
border-radius: @radius-round;
|
||||
background: @primary-strong;
|
||||
transform: translateY(-50%);
|
||||
}
|
||||
}
|
||||
|
||||
&__filters {
|
||||
@@ -172,36 +200,51 @@ onMounted(() => {
|
||||
}
|
||||
|
||||
&__filter {
|
||||
height: 34px;
|
||||
padding: 0 @spacing-base;
|
||||
height: 26px;
|
||||
padding: 0 14px;
|
||||
border: 1px solid @border-color;
|
||||
border-radius: @radius-base;
|
||||
border-radius: @radius-sm;
|
||||
background: @white;
|
||||
color: @text-color;
|
||||
font-size: @font-size-base;
|
||||
font-size: 11px;
|
||||
transition: all 0.2s;
|
||||
|
||||
&:hover {
|
||||
border-color: @primary-color;
|
||||
color: @primary-color;
|
||||
border-color: @primary-strong;
|
||||
color: @primary-strong;
|
||||
}
|
||||
|
||||
&.is-active {
|
||||
border-color: @primary-color;
|
||||
background: @primary-color;
|
||||
border-color: @primary-strong;
|
||||
background: @primary-strong;
|
||||
color: @white;
|
||||
}
|
||||
}
|
||||
|
||||
// 「+ 新增抬头」:设计 35 实底 #024FFF 小按钮
|
||||
:deep(.app-button--primary) {
|
||||
height: 26px;
|
||||
padding: 0 12px;
|
||||
border-radius: @radius-sm;
|
||||
background: @primary-strong;
|
||||
font-size: 11px;
|
||||
|
||||
&:hover {
|
||||
background: @primary-color;
|
||||
}
|
||||
}
|
||||
|
||||
// 抬头卡纵排铺满(设计 35 一行一张)
|
||||
&__grid {
|
||||
.flex(row, flex-start);
|
||||
flex-wrap: wrap;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
gap: @spacing-base;
|
||||
}
|
||||
|
||||
&__empty {
|
||||
padding: @spacing-xl 0;
|
||||
font-size: @font-size-base;
|
||||
font-size: 11px;
|
||||
text-align: center;
|
||||
}
|
||||
}
|
||||
</style>
|
||||
|
||||
@@ -213,12 +213,21 @@ onMounted(() => {
|
||||
<style lang="less" scoped>
|
||||
.invoices {
|
||||
.flex(column, flex-start);
|
||||
align-items: stretch;
|
||||
gap: @spacing-base;
|
||||
padding-top: @spacing-lg;
|
||||
padding-bottom: @spacing-xxl;
|
||||
width: 100%;
|
||||
max-width: @container-width;
|
||||
margin: 0 auto;
|
||||
padding: @spacing-lg @spacing-base @spacing-xxl;
|
||||
|
||||
// 与财务中心其他页一致:面包屑 11px、前缀灰当前页深灰
|
||||
&__breadcrumb {
|
||||
font-size: @font-size-base;
|
||||
font-size: 11px;
|
||||
color: @text-color-disabled;
|
||||
|
||||
> span:last-child {
|
||||
color: @text-color;
|
||||
}
|
||||
}
|
||||
|
||||
&__title-card {
|
||||
@@ -230,7 +239,7 @@ onMounted(() => {
|
||||
}
|
||||
|
||||
&__title-main {
|
||||
.flex(column, flex-start);
|
||||
.flex(column, flex-start, stretch);
|
||||
gap: @spacing-xs;
|
||||
}
|
||||
|
||||
|
||||
@@ -52,12 +52,12 @@ onMounted(() => {
|
||||
<h2 class="pay-result__title">
|
||||
支付成功
|
||||
</h2>
|
||||
<p class="pay-result__amount">
|
||||
付款金额 ¥{{ formatMoney(result.amount) }}
|
||||
</p>
|
||||
<p class="pay-result__count text-secondary">
|
||||
共{{ result.bills.length }}个订单
|
||||
</p>
|
||||
<p class="pay-result__amount">
|
||||
付款金额 ¥{{ formatMoney(result.amount) }}
|
||||
</p>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
@@ -109,130 +109,171 @@ onMounted(() => {
|
||||
|
||||
<style lang="less" scoped>
|
||||
.pay-result {
|
||||
padding-top: @spacing-lg;
|
||||
padding-bottom: @spacing-xxl;
|
||||
width: 100%;
|
||||
max-width: @container-width;
|
||||
margin: 0 auto;
|
||||
padding: @spacing-lg @spacing-base @spacing-xxl;
|
||||
|
||||
// 设计 32:面包屑 13 设计px → 11px,前缀灰、当前页深灰
|
||||
&__breadcrumb {
|
||||
margin-bottom: @spacing-base;
|
||||
font-size: @font-size-base;
|
||||
font-size: 11px;
|
||||
color: @text-color-disabled;
|
||||
|
||||
> span:last-child {
|
||||
color: @text-color;
|
||||
}
|
||||
}
|
||||
|
||||
// 设计 32:内容为居中窄列,直接坐在页面底色上(无外层大卡)
|
||||
&__card {
|
||||
padding: @spacing-xl @spacing-lg;
|
||||
border-radius: @radius-lg;
|
||||
background: @white;
|
||||
box-shadow: @shadow-base;
|
||||
width: 300px;
|
||||
max-width: 100%;
|
||||
margin: 0 auto;
|
||||
padding: 0;
|
||||
border-radius: 0;
|
||||
background: transparent;
|
||||
box-shadow: none;
|
||||
}
|
||||
|
||||
// 头部:大绿圆勾 + 标题 + 「共 N 个订单 / 付款金额」同一行
|
||||
&__head {
|
||||
.flex(row, flex-start, center);
|
||||
gap: @spacing-base;
|
||||
padding-bottom: @spacing-lg;
|
||||
border-bottom: 1px solid @border-color;
|
||||
.flex(column, center, center);
|
||||
gap: 12px;
|
||||
padding-bottom: 16px;
|
||||
border-bottom: 1px solid @project-divider;
|
||||
}
|
||||
|
||||
&__check {
|
||||
.flex(row, center);
|
||||
width: 56px;
|
||||
height: 56px;
|
||||
width: 76px;
|
||||
height: 76px;
|
||||
border-radius: @radius-round;
|
||||
background: fade(@success-color, 12%);
|
||||
color: @success-color;
|
||||
font-size: 32px;
|
||||
font-weight: 600;
|
||||
background: @finance-result-circle;
|
||||
color: @white;
|
||||
font-size: 42px;
|
||||
font-weight: 400;
|
||||
line-height: 1;
|
||||
flex-shrink: 0;
|
||||
}
|
||||
|
||||
&__head-text {
|
||||
display: flex;
|
||||
flex-wrap: wrap;
|
||||
justify-content: center;
|
||||
align-items: baseline;
|
||||
gap: 6px;
|
||||
}
|
||||
|
||||
&__title {
|
||||
font-size: @font-size-xl;
|
||||
font-weight: 600;
|
||||
flex-basis: 100%;
|
||||
text-align: center;
|
||||
font-size: 17px;
|
||||
font-weight: 700;
|
||||
color: @heading-color;
|
||||
}
|
||||
|
||||
&__amount {
|
||||
margin-top: @spacing-xs;
|
||||
font-size: @font-size-lg;
|
||||
font-size: 14px;
|
||||
color: @danger-color;
|
||||
font-weight: 600;
|
||||
font-weight: 700;
|
||||
}
|
||||
|
||||
&__count {
|
||||
margin-top: @spacing-xs;
|
||||
font-size: @font-size-base;
|
||||
font-size: 11px;
|
||||
}
|
||||
|
||||
// 支付信息:标签左灰、值右粗(设计 32 竖排行)
|
||||
&__grid {
|
||||
.flex(row, flex-start, flex-start);
|
||||
gap: @spacing-xxl;
|
||||
margin-top: @spacing-lg;
|
||||
.flex(column, flex-start, stretch);
|
||||
gap: 14px;
|
||||
margin-top: 16px;
|
||||
}
|
||||
|
||||
&__grid-item {
|
||||
.flex(column, flex-start);
|
||||
gap: @spacing-xs;
|
||||
.flex(row, space-between, center);
|
||||
gap: @spacing-base;
|
||||
}
|
||||
|
||||
&__grid-label {
|
||||
font-size: @font-size-sm;
|
||||
font-size: 11px;
|
||||
color: @text-color-secondary;
|
||||
}
|
||||
|
||||
&__grid-value {
|
||||
font-size: @font-size-base;
|
||||
font-size: 11px;
|
||||
font-weight: 700;
|
||||
color: @heading-color;
|
||||
text-align: right;
|
||||
word-break: break-all;
|
||||
}
|
||||
|
||||
&__bills {
|
||||
margin-top: @spacing-lg;
|
||||
padding-top: @spacing-base;
|
||||
border-top: 1px solid @border-color;
|
||||
margin-top: 16px;
|
||||
}
|
||||
|
||||
&__sub-title {
|
||||
margin-bottom: @spacing-sm;
|
||||
font-size: @font-size-base;
|
||||
font-weight: 600;
|
||||
margin-bottom: 8px;
|
||||
font-size: 11px;
|
||||
font-weight: 700;
|
||||
color: @heading-color;
|
||||
}
|
||||
|
||||
// 已支付订单行卡:白底圆角(设计 32 实取)
|
||||
&__bill-list {
|
||||
.flex(column, flex-start);
|
||||
gap: @spacing-sm;
|
||||
.flex(column, flex-start, stretch);
|
||||
gap: 6px;
|
||||
list-style: none;
|
||||
padding: 0;
|
||||
margin: 0;
|
||||
}
|
||||
|
||||
&__bill {
|
||||
.flex(row, flex-start, center);
|
||||
gap: @spacing-base;
|
||||
padding: @spacing-sm;
|
||||
border-radius: @radius-sm;
|
||||
background: @bg-color-light;
|
||||
font-size: @font-size-base;
|
||||
gap: 8px;
|
||||
padding: 10px;
|
||||
border-radius: 6px;
|
||||
background: @white;
|
||||
font-size: 11px;
|
||||
color: @text-color;
|
||||
}
|
||||
|
||||
&__bill-name {
|
||||
color: @heading-color;
|
||||
font-weight: 700;
|
||||
}
|
||||
|
||||
&__bill-no {
|
||||
flex: 1;
|
||||
font-size: 11px;
|
||||
color: @text-color-disabled;
|
||||
}
|
||||
|
||||
&__bill-amount {
|
||||
font-weight: 600;
|
||||
font-weight: 700;
|
||||
color: @heading-color;
|
||||
white-space: nowrap;
|
||||
}
|
||||
|
||||
// 返回按钮右对齐(设计 32 在列右下)
|
||||
&__footer {
|
||||
margin-top: @spacing-lg;
|
||||
display: flex;
|
||||
justify-content: flex-end;
|
||||
margin-top: 16px;
|
||||
}
|
||||
|
||||
:deep(.app-button--primary) {
|
||||
background: @primary-strong;
|
||||
|
||||
&:hover {
|
||||
background: @primary-color;
|
||||
}
|
||||
}
|
||||
|
||||
&__empty {
|
||||
padding: @spacing-xl 0;
|
||||
text-align: center;
|
||||
font-size: @font-size-base;
|
||||
font-size: 11px;
|
||||
}
|
||||
}
|
||||
</style>
|
||||
|
||||
@@ -74,29 +74,42 @@ onMounted(() => {
|
||||
<span>扫码支付</span>
|
||||
</nav>
|
||||
|
||||
<div class="pay__body">
|
||||
<section class="pay__left card">
|
||||
<QrCodePanel
|
||||
:expires-in="payment?.qrExpiresInSeconds ?? 300"
|
||||
@refresh="onRefresh"
|
||||
/>
|
||||
<p class="pay__safe text-secondary">
|
||||
安全提示:本页面已通过安全验证,请勿向他人泄露付款码
|
||||
</p>
|
||||
<AppButton @click="dialogVisible = true">
|
||||
切换支付方式
|
||||
</AppButton>
|
||||
</section>
|
||||
<!-- 设计 33/34:单张大白卡——左(渠道说明 + 切换)/ 中(金额 + 二维码)/ 右(步骤 + 订单明细 + 安全提示) -->
|
||||
<div class="pay__body card">
|
||||
<section class="pay__left">
|
||||
<div class="pay__left-top">
|
||||
<p class="pay__method">
|
||||
{{ methodLabel }} · 请使用手机微信 <strong>[扫一扫]</strong> 扫描下方二维码完成支付
|
||||
</p>
|
||||
<AppButton class="pay__switch" @click="dialogVisible = true">
|
||||
切换支付方式
|
||||
</AppButton>
|
||||
</div>
|
||||
|
||||
<section class="pay__right card">
|
||||
<div class="pay__amount-block">
|
||||
<p class="pay__amount-label text-secondary">
|
||||
支付金额
|
||||
</p>
|
||||
<p class="pay__amount">¥{{ formatMoney(payment?.amount ?? currentBill?.amount ?? 0) }}</p>
|
||||
<p class="pay__method">
|
||||
{{ methodLabel }} · 请使用手机微信 <strong>[扫一扫]</strong> 扫描下方二维码完成支付
|
||||
</p>
|
||||
</div>
|
||||
|
||||
<QrCodePanel
|
||||
:expires-in="payment?.qrExpiresInSeconds ?? 300"
|
||||
@refresh="onRefresh"
|
||||
/>
|
||||
</section>
|
||||
|
||||
<section class="pay__right">
|
||||
<div class="pay__steps">
|
||||
<h4 class="pay__sub-title">
|
||||
扫码支付操作步骤
|
||||
</h4>
|
||||
<ol class="pay__step-list">
|
||||
<li v-for="(step, index) in steps" :key="step" class="pay__step">
|
||||
<span class="pay__step-index">{{ index + 1 }}</span>
|
||||
<span>{{ step }}</span>
|
||||
</li>
|
||||
</ol>
|
||||
</div>
|
||||
|
||||
<div class="pay__detail">
|
||||
@@ -123,29 +136,22 @@ onMounted(() => {
|
||||
</ul>
|
||||
</div>
|
||||
|
||||
<div class="pay__steps">
|
||||
<h4 class="pay__sub-title">
|
||||
扫码支付操作步骤
|
||||
</h4>
|
||||
<ol class="pay__step-list">
|
||||
<li v-for="(step, index) in steps" :key="step" class="pay__step">
|
||||
<span class="pay__step-index">{{ index + 1 }}</span>
|
||||
<span>{{ step }}</span>
|
||||
</li>
|
||||
</ol>
|
||||
</div>
|
||||
|
||||
<div class="pay__footer">
|
||||
<AppButton type="primary" size="lg" @click="onPaid">
|
||||
完成支付
|
||||
</AppButton>
|
||||
<AppButton @click="router.push('/finance/bills')">
|
||||
返回
|
||||
</AppButton>
|
||||
</div>
|
||||
<p class="pay__safe">
|
||||
安全提示:本页面已通过安全验证,请勿向他人泄露付款码
|
||||
</p>
|
||||
</section>
|
||||
</div>
|
||||
|
||||
<!-- 设计 33:操作按钮在大卡右下方 -->
|
||||
<div class="pay__footer">
|
||||
<AppButton type="primary" size="lg" @click="onPaid">
|
||||
完成支付
|
||||
</AppButton>
|
||||
<AppButton @click="router.push('/finance/bills')">
|
||||
返回
|
||||
</AppButton>
|
||||
</div>
|
||||
|
||||
<PayMethodDialog
|
||||
v-model:visible="dialogVisible"
|
||||
:method="method"
|
||||
@@ -156,136 +162,224 @@ onMounted(() => {
|
||||
|
||||
<style lang="less" scoped>
|
||||
.pay {
|
||||
padding-top: @spacing-lg;
|
||||
padding-bottom: @spacing-xxl;
|
||||
width: 100%;
|
||||
max-width: @container-width;
|
||||
margin: 0 auto;
|
||||
padding: @spacing-lg @spacing-base @spacing-xxl;
|
||||
|
||||
// 设计 33:面包屑 13 设计px → 11px,前缀灰、当前页深灰
|
||||
&__breadcrumb {
|
||||
margin-bottom: @spacing-base;
|
||||
font-size: @font-size-base;
|
||||
font-size: 11px;
|
||||
color: @text-color-disabled;
|
||||
|
||||
> span:last-child {
|
||||
color: @text-color;
|
||||
}
|
||||
}
|
||||
|
||||
// 设计 33:整页单张大白卡,左中右三区
|
||||
&__body {
|
||||
.flex(row, flex-start);
|
||||
gap: @spacing-base;
|
||||
align-items: flex-start;
|
||||
.flex(row, flex-start, flex-start);
|
||||
gap: 24px;
|
||||
padding: 24px 32px;
|
||||
border-radius: @radius-base;
|
||||
background: @white;
|
||||
box-shadow: @shadow-base;
|
||||
}
|
||||
|
||||
&__left {
|
||||
.flex(column, center, center);
|
||||
gap: @spacing-base;
|
||||
width: 320px;
|
||||
flex-shrink: 0;
|
||||
padding: @spacing-lg;
|
||||
border-radius: @radius-lg;
|
||||
background: @white;
|
||||
box-shadow: @shadow-base;
|
||||
}
|
||||
|
||||
&__safe {
|
||||
font-size: @font-size-sm;
|
||||
text-align: center;
|
||||
line-height: 1.6;
|
||||
}
|
||||
|
||||
&__right {
|
||||
flex: 1;
|
||||
padding: @spacing-lg;
|
||||
border-radius: @radius-lg;
|
||||
background: @white;
|
||||
box-shadow: @shadow-base;
|
||||
min-width: 0;
|
||||
gap: @spacing-base;
|
||||
}
|
||||
|
||||
// 左区顶行:渠道说明靠左、切换支付方式胶囊靠右(设计 33 右上角)
|
||||
&__left-top {
|
||||
.flex(row, space-between, center);
|
||||
align-self: stretch;
|
||||
gap: @spacing-base;
|
||||
}
|
||||
|
||||
&__method {
|
||||
font-size: 12px;
|
||||
color: @text-color;
|
||||
|
||||
strong {
|
||||
color: @primary-strong;
|
||||
}
|
||||
}
|
||||
|
||||
&__switch {
|
||||
flex-shrink: 0;
|
||||
}
|
||||
|
||||
:deep(.pay__switch.app-button--default) {
|
||||
height: 24px;
|
||||
padding: 0 10px;
|
||||
border: 1px solid fade(@primary-strong, 30%);
|
||||
background: fade(@primary-strong, 10%);
|
||||
color: @primary-strong;
|
||||
font-size: 11px;
|
||||
|
||||
&:hover {
|
||||
border-color: @primary-strong;
|
||||
background: fade(@primary-strong, 18%);
|
||||
color: @primary-strong;
|
||||
}
|
||||
}
|
||||
|
||||
// 中区:支付金额标签 15 设计px → 12px,金额 34 设计px → 26px 粗体红
|
||||
&__amount-block {
|
||||
padding-bottom: @spacing-base;
|
||||
border-bottom: 1px solid @border-color;
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
&__amount-label {
|
||||
font-size: @font-size-base;
|
||||
font-size: 12px;
|
||||
color: @text-color;
|
||||
}
|
||||
|
||||
&__amount {
|
||||
margin: @spacing-xs 0;
|
||||
font-size: 32px;
|
||||
font-weight: 600;
|
||||
margin-top: 4px;
|
||||
font-size: 26px;
|
||||
font-weight: 700;
|
||||
color: @danger-color;
|
||||
line-height: 1.2;
|
||||
}
|
||||
|
||||
&__method {
|
||||
font-size: @font-size-base;
|
||||
color: @text-color;
|
||||
|
||||
strong {
|
||||
color: @primary-color;
|
||||
}
|
||||
// 二维码占位(QrCodePanel 内部压成设计稿的灰色方块)
|
||||
:deep(.qr-panel__box) {
|
||||
border: none;
|
||||
background: @contract-qr-bg;
|
||||
border-radius: @radius-base;
|
||||
}
|
||||
|
||||
&__detail,
|
||||
&__steps {
|
||||
margin-top: @spacing-base;
|
||||
// 倒计时行 → 浅红胶囊(设计 33「二维码将在 04:32 后失效」)
|
||||
:deep(.qr-panel__status) {
|
||||
font-size: 11px;
|
||||
color: @danger-color;
|
||||
background: fade(@danger-color, 8%);
|
||||
border-radius: @radius-round;
|
||||
padding: 5px 14px;
|
||||
}
|
||||
|
||||
:deep(.qr-panel__count) {
|
||||
color: @danger-color;
|
||||
font-weight: 700;
|
||||
}
|
||||
|
||||
// 右区:步骤 + 订单明细 + 安全提示(设计 33 右列 400 设计px ≈ 310px)
|
||||
&__right {
|
||||
flex: 0 0 310px;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
gap: @spacing-base;
|
||||
}
|
||||
|
||||
&__sub-title {
|
||||
margin-bottom: @spacing-sm;
|
||||
font-size: @font-size-base;
|
||||
font-weight: 600;
|
||||
margin-bottom: 12px;
|
||||
font-size: 15px;
|
||||
font-weight: 700;
|
||||
color: @heading-color;
|
||||
|
||||
// 「订单明细」小节按设计 33 降为 13 设计px → 11px
|
||||
}
|
||||
|
||||
&__detail-list {
|
||||
.flex(column, flex-start);
|
||||
gap: @spacing-sm;
|
||||
&__detail &__sub-title {
|
||||
font-size: 11px;
|
||||
}
|
||||
|
||||
&__detail-item {
|
||||
.flex(row, flex-start, center);
|
||||
gap: @spacing-base;
|
||||
font-size: @font-size-base;
|
||||
color: @heading-color;
|
||||
}
|
||||
|
||||
&__detail-label {
|
||||
width: 72px;
|
||||
flex-shrink: 0;
|
||||
}
|
||||
|
||||
&__detail-amount {
|
||||
font-weight: 600;
|
||||
color: @danger-color;
|
||||
&__steps &__sub-title {
|
||||
font-size: 15px;
|
||||
}
|
||||
|
||||
// 三步指引:序号实底蓝圆 024FFF,步骤文字 14 设计px → 11px
|
||||
&__step-list {
|
||||
.flex(column, flex-start);
|
||||
gap: @spacing-sm;
|
||||
.flex(column, flex-start, stretch);
|
||||
gap: 12px;
|
||||
padding-left: 0;
|
||||
list-style: none;
|
||||
}
|
||||
|
||||
&__step {
|
||||
.flex(row, flex-start, center);
|
||||
.flex(row, flex-start, flex-start);
|
||||
gap: @spacing-sm;
|
||||
font-size: @font-size-base;
|
||||
font-size: 11px;
|
||||
line-height: 1.7;
|
||||
color: @text-color;
|
||||
}
|
||||
|
||||
&__step-index {
|
||||
.flex(row, center);
|
||||
width: 22px;
|
||||
height: 22px;
|
||||
width: 16px;
|
||||
height: 16px;
|
||||
margin-top: 1px;
|
||||
border-radius: @radius-round;
|
||||
background: @primary-light;
|
||||
color: @primary-color;
|
||||
font-size: @font-size-sm;
|
||||
background: @primary-strong;
|
||||
color: @white;
|
||||
font-size: 11px;
|
||||
font-weight: 700;
|
||||
flex-shrink: 0;
|
||||
}
|
||||
|
||||
&__footer {
|
||||
// 订单明细:浅灰底板 + 白底行卡(设计 33 实取 #F7F8F9 / #FFFFFF)
|
||||
&__detail-list {
|
||||
.flex(column, flex-start, stretch);
|
||||
gap: 6px;
|
||||
margin: 0;
|
||||
padding: 6px;
|
||||
list-style: none;
|
||||
border-radius: 6px;
|
||||
background: @bg-color;
|
||||
}
|
||||
|
||||
&__detail-item {
|
||||
.flex(row, flex-start, center);
|
||||
gap: @spacing-sm;
|
||||
padding: 8px 10px;
|
||||
border-radius: @radius-sm;
|
||||
background: @white;
|
||||
font-size: 11px;
|
||||
color: @heading-color;
|
||||
}
|
||||
|
||||
&__detail-label {
|
||||
width: 56px;
|
||||
flex-shrink: 0;
|
||||
font-size: 11px;
|
||||
}
|
||||
|
||||
&__detail-amount {
|
||||
margin-left: auto;
|
||||
font-weight: 700;
|
||||
color: @danger-color;
|
||||
}
|
||||
|
||||
// 安全提示横幅:浅绿底 + 绿字(设计 33 实取 #D2EEDC / #16A34A)
|
||||
&__safe {
|
||||
padding: 8px 12px;
|
||||
border-radius: @radius-sm;
|
||||
background: @finance-safe-bg;
|
||||
color: @success-color;
|
||||
font-size: 11px;
|
||||
font-weight: 600;
|
||||
line-height: 1.6;
|
||||
}
|
||||
|
||||
// 卡下操作区:右对齐(设计 33 返回按钮在卡右下)
|
||||
&__footer {
|
||||
.flex(row, flex-end, center);
|
||||
gap: @spacing-base;
|
||||
margin-top: @spacing-lg;
|
||||
padding-top: @spacing-base;
|
||||
border-top: 1px solid @border-color;
|
||||
margin-top: @spacing-base;
|
||||
}
|
||||
|
||||
:deep(.app-button--primary) {
|
||||
background: @primary-strong;
|
||||
|
||||
&:hover {
|
||||
background: @primary-color;
|
||||
}
|
||||
}
|
||||
}
|
||||
</style>
|
||||
|
||||
@@ -161,7 +161,7 @@ function onClose(): void {
|
||||
z-index: 1000;
|
||||
.flex(row, center);
|
||||
padding: @spacing-base;
|
||||
background: rgba(0, 0, 0, 0.45);
|
||||
background: fade(@black, 45%);
|
||||
|
||||
&__panel {
|
||||
.flex(column, flex-start, stretch);
|
||||
@@ -248,28 +248,29 @@ function onClose(): void {
|
||||
box-shadow: @shadow-base;
|
||||
}
|
||||
|
||||
// tone 底色与首页快捷入口一致(按蓝湖设计稿采样)
|
||||
&--purple {
|
||||
background: #f0eaff;
|
||||
background: @home-quick-purple;
|
||||
}
|
||||
|
||||
&--green {
|
||||
background: #e7f8ec;
|
||||
background: @home-quick-green;
|
||||
}
|
||||
|
||||
&--blue {
|
||||
background: @primary-light;
|
||||
background: @home-quick-peach;
|
||||
}
|
||||
|
||||
&--amber {
|
||||
background: #fff3e0;
|
||||
background: @home-quick-pink;
|
||||
}
|
||||
|
||||
&--red {
|
||||
background: #ffeceb;
|
||||
background: fade(@danger-color, 15%);
|
||||
}
|
||||
|
||||
&--cyan {
|
||||
background: #e4f6fa;
|
||||
background: @home-quick-blue;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -78,6 +78,16 @@ onBeforeUnmount(stop)
|
||||
>
|
||||
›
|
||||
</button>
|
||||
|
||||
<!-- 设计稿底部居中的指示条(长条=当前,圆点=其余) -->
|
||||
<div class="home-banner__dots">
|
||||
<span
|
||||
v-for="(slide, index) in slides"
|
||||
:key="`dot-${slide.id ?? index}`"
|
||||
class="home-banner__dot"
|
||||
:class="{ 'is-active': index === current }"
|
||||
/>
|
||||
</div>
|
||||
</template>
|
||||
</section>
|
||||
</template>
|
||||
@@ -85,11 +95,10 @@ onBeforeUnmount(stop)
|
||||
<style lang="less" scoped>
|
||||
.home-banner {
|
||||
position: relative;
|
||||
height: 240px;
|
||||
// 设计稿头图通栏 1920×661 设计px → 高 509 CSS,紧贴顶栏无圆角
|
||||
height: 509px;
|
||||
overflow: hidden;
|
||||
border-radius: @radius-lg;
|
||||
background: @bg-color;
|
||||
box-shadow: @shadow-base;
|
||||
background: @home-banner-bg;
|
||||
|
||||
&__img {
|
||||
display: block;
|
||||
@@ -105,7 +114,7 @@ onBeforeUnmount(stop)
|
||||
height: 32px;
|
||||
transform: translateY(-50%);
|
||||
border-radius: @radius-round;
|
||||
background: rgba(31, 39, 51, 0.35);
|
||||
background: fade(@black, 35%);
|
||||
color: @white;
|
||||
font-size: @font-size-xl;
|
||||
line-height: 1;
|
||||
@@ -124,5 +133,29 @@ onBeforeUnmount(stop)
|
||||
&:hover &__arrow {
|
||||
opacity: 1;
|
||||
}
|
||||
|
||||
&__dots {
|
||||
position: absolute;
|
||||
bottom: 48px;
|
||||
left: 50%;
|
||||
transform: translateX(-50%);
|
||||
.flex(row, center, center);
|
||||
gap: 10px;
|
||||
}
|
||||
|
||||
&__dot {
|
||||
width: 4px;
|
||||
height: 4px;
|
||||
border-radius: @radius-round;
|
||||
background: @home-banner-dot;
|
||||
transition: width 0.2s;
|
||||
|
||||
// 当前页:设计稿 44×5 设计px 长条
|
||||
&.is-active {
|
||||
width: 34px;
|
||||
height: 4px;
|
||||
border-radius: @radius-round;
|
||||
}
|
||||
}
|
||||
}
|
||||
</style>
|
||||
|
||||
@@ -30,10 +30,12 @@ defineProps<Props>()
|
||||
<!-- TODO(蓝湖): 替换业务图标切图 -->
|
||||
{{ line.name.slice(0, 2) }}
|
||||
</span>
|
||||
<h4 class="home-business__name">
|
||||
{{ line.name }}
|
||||
</h4>
|
||||
<!-- 设计稿卡片右上角选择圆环 -->
|
||||
<span class="home-business__check" aria-hidden="true" />
|
||||
</div>
|
||||
<h4 class="home-business__name">
|
||||
{{ line.name }}
|
||||
</h4>
|
||||
<p class="home-business__desc">
|
||||
{{ line.desc }}
|
||||
</p>
|
||||
@@ -45,15 +47,25 @@ defineProps<Props>()
|
||||
|
||||
<style lang="less" scoped>
|
||||
.home-business {
|
||||
// 设计稿区块卡 1680×400 设计px:白底 + #E2E2E2 描边(内容区内左右缩 50 设计px)
|
||||
max-width: 1294px;
|
||||
margin-right: auto;
|
||||
margin-left: auto;
|
||||
padding: 34px 54px 40px;
|
||||
border: 1px solid @home-section-border;
|
||||
border-radius: @radius-lg;
|
||||
background: @white;
|
||||
|
||||
&__head {
|
||||
.flex(row, space-between);
|
||||
margin-bottom: @spacing-base;
|
||||
margin-bottom: 36px;
|
||||
}
|
||||
|
||||
&__title {
|
||||
font-size: @font-size-xl;
|
||||
font-weight: 600;
|
||||
color: @heading-color;
|
||||
// 设计稿栏目标题 36 设计px / 700 / #121212
|
||||
font-size: @font-size-xxl;
|
||||
font-weight: 700;
|
||||
color: @home-ink;
|
||||
}
|
||||
|
||||
&__slogan {
|
||||
@@ -63,111 +75,128 @@ defineProps<Props>()
|
||||
&__grid {
|
||||
display: grid;
|
||||
grid-template-columns: repeat(4, 1fr);
|
||||
gap: @spacing-base;
|
||||
// 设计稿卡片间距 22 设计px ≈ 17 CSS
|
||||
gap: 17px;
|
||||
}
|
||||
|
||||
&__card {
|
||||
.flex(column, flex-start);
|
||||
gap: @spacing-base;
|
||||
padding: @spacing-lg;
|
||||
border-radius: @radius-lg;
|
||||
background: @primary-light;
|
||||
box-shadow: @shadow-base;
|
||||
gap: 0;
|
||||
// 设计稿业务卡 368×206 设计px:白底 / #999 描边 / 小圆角
|
||||
padding: 22px 16px 6px;
|
||||
border: 1px solid @home-business-border;
|
||||
border-radius: @radius-base;
|
||||
background: @white;
|
||||
transition: transform 0.2s, box-shadow 0.2s;
|
||||
|
||||
&:hover {
|
||||
box-shadow: @shadow-lg;
|
||||
box-shadow: @shadow-base;
|
||||
transform: translateY(-2px);
|
||||
}
|
||||
}
|
||||
|
||||
&__card-head {
|
||||
.flex(row, flex-start);
|
||||
gap: @spacing-sm;
|
||||
.flex(row, space-between, flex-start);
|
||||
width: 100%;
|
||||
}
|
||||
|
||||
&__icon {
|
||||
.flex(row, center);
|
||||
flex-shrink: 0;
|
||||
width: 40px;
|
||||
height: 40px;
|
||||
width: 44px;
|
||||
height: 44px;
|
||||
border-radius: @radius-base;
|
||||
background: @white;
|
||||
color: @primary-color;
|
||||
font-size: @font-size-base;
|
||||
background: transparent;
|
||||
color: @primary-strong;
|
||||
font-size: @font-size-lg;
|
||||
font-weight: 600;
|
||||
}
|
||||
|
||||
// 右上角选择圆环(31 设计px ≈ 24 CSS)
|
||||
&__check {
|
||||
position: relative;
|
||||
flex-shrink: 0;
|
||||
width: 24px;
|
||||
height: 24px;
|
||||
border: 1px solid @home-ring;
|
||||
border-radius: @radius-round;
|
||||
|
||||
&::after {
|
||||
content: '';
|
||||
position: absolute;
|
||||
inset: 0;
|
||||
width: 14px;
|
||||
height: 14px;
|
||||
margin: auto;
|
||||
border-radius: @radius-round;
|
||||
background: @white;
|
||||
opacity: 0;
|
||||
}
|
||||
}
|
||||
|
||||
&__name {
|
||||
font-size: @font-size-lg;
|
||||
font-weight: 600;
|
||||
color: @heading-color;
|
||||
margin-top: 16px;
|
||||
// 设计稿卡片标题 28 设计px / 500 / #121212
|
||||
font-size: @font-size-title;
|
||||
font-weight: 500;
|
||||
color: @home-ink;
|
||||
}
|
||||
|
||||
&__desc {
|
||||
min-height: 40px;
|
||||
margin-top: 4px;
|
||||
font-size: @font-size-sm;
|
||||
color: @text-color-secondary;
|
||||
font-weight: 500;
|
||||
color: @home-ink;
|
||||
.multi-ellipsis(2);
|
||||
}
|
||||
|
||||
&__more {
|
||||
align-self: flex-end;
|
||||
margin-top: auto;
|
||||
font-size: @font-size-sm;
|
||||
color: @text-color-secondary;
|
||||
transition: color 0.2s;
|
||||
}
|
||||
|
||||
// 四类业务各自的主题色(与设计稿一致:卡片浅色底 + 同色系图标/文案)
|
||||
// 设计稿:首张「互联网软件」为 #024FFF 选中实底 + 白字白环;其余白底描边
|
||||
&__card--internet {
|
||||
background: #e8f0ff;
|
||||
border-color: @primary-strong;
|
||||
background: @primary-strong;
|
||||
|
||||
.home-business__icon {
|
||||
color: #3370ff;
|
||||
color: @white;
|
||||
}
|
||||
|
||||
.home-business__check {
|
||||
border-color: @white;
|
||||
|
||||
&::after {
|
||||
opacity: 1;
|
||||
}
|
||||
}
|
||||
|
||||
.home-business__name,
|
||||
.home-business__desc,
|
||||
.home-business__more {
|
||||
color: #598bff;
|
||||
color: @white;
|
||||
}
|
||||
}
|
||||
|
||||
&__card--hardware {
|
||||
background: #e7f8ec;
|
||||
|
||||
.home-business__icon {
|
||||
color: #22b14c;
|
||||
}
|
||||
|
||||
.home-business__desc,
|
||||
.home-business__more {
|
||||
color: #34c724;
|
||||
color: @tag-hardware;
|
||||
}
|
||||
}
|
||||
|
||||
&__card--iot {
|
||||
background: #f0eaff;
|
||||
|
||||
.home-business__icon {
|
||||
color: #7c4dff;
|
||||
}
|
||||
|
||||
.home-business__desc,
|
||||
.home-business__more {
|
||||
color: #9a7bff;
|
||||
color: @tag-iot;
|
||||
}
|
||||
}
|
||||
|
||||
&__card--manufacturing {
|
||||
background: #fff2e4;
|
||||
|
||||
.home-business__icon {
|
||||
color: #ff8f1f;
|
||||
}
|
||||
|
||||
.home-business__desc,
|
||||
.home-business__more {
|
||||
color: #ffa94d;
|
||||
color: @tag-manufacturing;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -85,71 +85,99 @@ function switchCategory(value: BusinessType | 'all'): void {
|
||||
|
||||
<style lang="less" scoped>
|
||||
.home-cases {
|
||||
// 设计稿区块卡 1680×446 设计px:白底 + #E2E2E2 描边(内容区内左右缩 50 设计px)
|
||||
max-width: 1294px;
|
||||
margin-right: auto;
|
||||
margin-left: auto;
|
||||
padding: 32px 54px 44px;
|
||||
border: 1px solid @home-section-border;
|
||||
border-radius: @radius-lg;
|
||||
background: @white;
|
||||
|
||||
&__head {
|
||||
.flex(row, space-between);
|
||||
gap: @spacing-base;
|
||||
margin-bottom: @spacing-base;
|
||||
.flex(row, flex-start);
|
||||
gap: 20px;
|
||||
margin-bottom: 36px;
|
||||
}
|
||||
|
||||
&__title {
|
||||
font-size: @font-size-xl;
|
||||
font-weight: 600;
|
||||
color: @heading-color;
|
||||
// 设计稿栏目标题 36 设计px / 700 / #121212
|
||||
font-size: @font-size-xxl;
|
||||
font-weight: 700;
|
||||
color: @home-ink;
|
||||
}
|
||||
|
||||
&__tabs {
|
||||
.flex(row, center);
|
||||
flex: 1;
|
||||
gap: @spacing-sm;
|
||||
// 设计稿分类紧跟标题左侧排布(间距 36 设计px ≈ 28)
|
||||
gap: 28px;
|
||||
}
|
||||
|
||||
&__tab {
|
||||
height: 30px;
|
||||
padding: 0 @spacing-base;
|
||||
border-radius: @radius-round;
|
||||
background: @white;
|
||||
color: @text-color;
|
||||
position: relative;
|
||||
height: auto;
|
||||
padding: 0;
|
||||
border: 0;
|
||||
background: transparent;
|
||||
// 设计稿分类 16 设计px / 500 / #121212(激活 #085DFF + 下划线)
|
||||
color: @home-ink;
|
||||
font-size: @font-size-sm;
|
||||
transition: all 0.2s;
|
||||
font-weight: 500;
|
||||
transition: color 0.2s;
|
||||
|
||||
&.is-active {
|
||||
background: @primary-color;
|
||||
color: @white;
|
||||
background: transparent;
|
||||
color: @home-tab-active;
|
||||
|
||||
// 设计稿激活下划线 29×2 设计px(#1F67EF)
|
||||
&::after {
|
||||
content: '';
|
||||
position: absolute;
|
||||
right: 0;
|
||||
bottom: -6px;
|
||||
left: 0;
|
||||
height: 2px;
|
||||
background: @primary-color;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
&__more {
|
||||
font-size: @font-size-base;
|
||||
margin-left: auto;
|
||||
font-size: @font-size-sm;
|
||||
}
|
||||
|
||||
&__grid {
|
||||
display: grid;
|
||||
grid-template-columns: repeat(4, 1fr);
|
||||
gap: @spacing-base;
|
||||
// 设计稿案例卡间距 24 设计px ≈ 18 CSS
|
||||
gap: 18px;
|
||||
}
|
||||
|
||||
&__card {
|
||||
overflow: hidden;
|
||||
border-radius: @radius-lg;
|
||||
// 设计稿案例卡 368×248 设计px:白底 + #E0DEDE 描边 + 0 4 10 黑 8% 投影
|
||||
border: 1px solid @home-case-border;
|
||||
border-radius: @radius-base;
|
||||
background: @white;
|
||||
box-shadow: @shadow-base;
|
||||
box-shadow: 0 4px 10px fade(@black, 8%);
|
||||
cursor: pointer;
|
||||
transition: transform 0.2s, box-shadow 0.2s;
|
||||
|
||||
&:hover {
|
||||
box-shadow: @shadow-lg;
|
||||
box-shadow: 0 6px 14px fade(@black, 12%);
|
||||
transform: translateY(-2px);
|
||||
|
||||
.home-cases__view {
|
||||
background: @primary-color;
|
||||
color: @white;
|
||||
color: @primary-color;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
&__cover {
|
||||
position: relative;
|
||||
height: 130px;
|
||||
// 设计稿封面区 128 设计px 高 ≈ 99 CSS
|
||||
height: 100px;
|
||||
overflow: hidden;
|
||||
}
|
||||
|
||||
@@ -171,43 +199,46 @@ function switchCategory(value: BusinessType | 'all'): void {
|
||||
border-radius: @radius-sm;
|
||||
background: @primary-color;
|
||||
color: @white;
|
||||
font-size: @font-size-sm;
|
||||
font-size: 11px;
|
||||
|
||||
&--hardware {
|
||||
background: #22b14c;
|
||||
background: @tag-hardware;
|
||||
}
|
||||
|
||||
&--iot {
|
||||
background: #7c4dff;
|
||||
background: @tag-iot;
|
||||
}
|
||||
|
||||
&--manufacturing {
|
||||
background: #ff8f1f;
|
||||
background: @tag-manufacturing;
|
||||
}
|
||||
|
||||
&--other {
|
||||
background: @text-color-secondary;
|
||||
background: @tag-other;
|
||||
}
|
||||
}
|
||||
|
||||
&__body {
|
||||
padding: @spacing-base;
|
||||
padding: 12px 15px 6px;
|
||||
}
|
||||
|
||||
&__name {
|
||||
margin-bottom: @spacing-sm;
|
||||
font-size: @font-size-lg;
|
||||
font-weight: 600;
|
||||
color: @heading-color;
|
||||
margin-bottom: 8px;
|
||||
// 设计稿案例名 16 设计px / 500 / #333333
|
||||
font-size: @font-size-sm;
|
||||
font-weight: 500;
|
||||
color: @home-body;
|
||||
.multi-ellipsis(1);
|
||||
}
|
||||
|
||||
&__meta {
|
||||
display: grid;
|
||||
grid-template-columns: 1fr 1fr;
|
||||
gap: 4px @spacing-sm;
|
||||
font-size: @font-size-sm;
|
||||
color: @text-color-secondary;
|
||||
// 设计稿元信息 10 设计px → 可读下限 11px / #333333
|
||||
gap: 3px @spacing-sm;
|
||||
font-size: 11px;
|
||||
line-height: 1.5;
|
||||
color: @home-body;
|
||||
|
||||
li {
|
||||
.ellipsis();
|
||||
@@ -217,13 +248,13 @@ function switchCategory(value: BusinessType | 'all'): void {
|
||||
&__view {
|
||||
display: block;
|
||||
width: fit-content;
|
||||
margin: @spacing-base 0 0 auto;
|
||||
padding: 2px @spacing-base;
|
||||
border: 1px solid @primary-color;
|
||||
border-radius: @radius-sm;
|
||||
color: @primary-color;
|
||||
margin: 10px 0 0 auto;
|
||||
padding: 0;
|
||||
border: 0;
|
||||
// 设计稿「查看详情>」12 设计px / #024FFF(无按钮描边)
|
||||
color: @primary-strong;
|
||||
font-size: @font-size-sm;
|
||||
transition: all 0.2s;
|
||||
transition: color 0.2s;
|
||||
}
|
||||
}
|
||||
</style>
|
||||
|
||||
@@ -87,14 +87,16 @@ function onMore(): void {
|
||||
|
||||
<style lang="less" scoped>
|
||||
.home-quick {
|
||||
position: relative;
|
||||
.flex(column, flex-start, stretch);
|
||||
flex-shrink: 0;
|
||||
width: 320px;
|
||||
gap: @spacing-base;
|
||||
padding: @spacing-lg;
|
||||
// 设计稿右卡 722×245 设计px → 556 宽;白底 + 浅灰描边
|
||||
width: 556px;
|
||||
gap: 0;
|
||||
padding: 14px 31px 21px;
|
||||
border: 1px solid @home-card-border;
|
||||
border-radius: @radius-lg;
|
||||
background: @white;
|
||||
box-shadow: @shadow-base;
|
||||
|
||||
&__head {
|
||||
.flex(row, flex-start);
|
||||
@@ -102,25 +104,28 @@ function onMore(): void {
|
||||
}
|
||||
|
||||
&__head-icon {
|
||||
color: @heading-color;
|
||||
font-size: @font-size-lg;
|
||||
color: @home-ink;
|
||||
font-size: @font-size-xl;
|
||||
}
|
||||
|
||||
&__title {
|
||||
font-size: @font-size-lg;
|
||||
font-weight: 600;
|
||||
color: @heading-color;
|
||||
// 设计稿卡内标题 36 设计px / 700 / #121212
|
||||
font-size: @font-size-xxl;
|
||||
font-weight: 700;
|
||||
color: @home-ink;
|
||||
}
|
||||
|
||||
&__list {
|
||||
.flex(row, space-between, flex-start);
|
||||
gap: @spacing-sm;
|
||||
.flex(row, flex-start, flex-start);
|
||||
// 设计稿入口间距 127 设计px(图标 90 + 间隙 37)≈ 70 + 28
|
||||
gap: 28px;
|
||||
margin-top: 16px;
|
||||
}
|
||||
|
||||
&__item {
|
||||
.flex(column, flex-start, center);
|
||||
gap: @spacing-sm;
|
||||
flex: 1;
|
||||
gap: 8px;
|
||||
flex: none;
|
||||
transition: transform 0.2s;
|
||||
|
||||
&:hover {
|
||||
@@ -130,55 +135,63 @@ function onMore(): void {
|
||||
|
||||
&__icon {
|
||||
.flex(row, center);
|
||||
width: 44px;
|
||||
height: 44px;
|
||||
// 设计稿图标块 90×90 设计px ≈ 70 CSS
|
||||
width: 70px;
|
||||
height: 70px;
|
||||
border-radius: @radius-base;
|
||||
font-size: @font-size-xl;
|
||||
font-size: 28px;
|
||||
|
||||
// 底色按设计稿采样(tone → 设计稿色)
|
||||
&--amber {
|
||||
background: #fff3e0;
|
||||
background: @home-quick-pink;
|
||||
}
|
||||
|
||||
&--blue {
|
||||
background: @primary-light;
|
||||
background: @home-quick-peach;
|
||||
}
|
||||
|
||||
&--green {
|
||||
background: #e7f8ec;
|
||||
background: @home-quick-green;
|
||||
}
|
||||
|
||||
&--purple {
|
||||
background: #f0eaff;
|
||||
background: @home-quick-purple;
|
||||
}
|
||||
|
||||
&--red {
|
||||
background: #ffeceb;
|
||||
background: fade(@danger-color, 15%);
|
||||
}
|
||||
|
||||
&--cyan {
|
||||
background: #e4f6fa;
|
||||
background: @home-quick-blue;
|
||||
}
|
||||
}
|
||||
|
||||
&__img {
|
||||
width: 24px;
|
||||
height: 24px;
|
||||
width: 32px;
|
||||
height: 32px;
|
||||
object-fit: contain;
|
||||
}
|
||||
|
||||
&__label {
|
||||
font-size: @font-size-sm;
|
||||
color: @text-color;
|
||||
// 设计稿入口文字 18 设计px / 500 / #121212
|
||||
font-size: @font-size-base;
|
||||
font-weight: 500;
|
||||
color: @home-ink;
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
&__more {
|
||||
align-self: flex-end;
|
||||
// 设计稿「更多」箭头位于卡片右侧垂直居中
|
||||
position: absolute;
|
||||
top: 50%;
|
||||
right: 31px;
|
||||
padding: 0;
|
||||
border: 0;
|
||||
transform: translateY(-50%);
|
||||
background: transparent;
|
||||
font-size: @font-size-sm;
|
||||
color: @text-color-secondary;
|
||||
color: @home-ring;
|
||||
cursor: pointer;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -29,11 +29,11 @@ defineProps<Props>()
|
||||
<style lang="less" scoped>
|
||||
.home-contents {
|
||||
&__block {
|
||||
margin-bottom: @spacing-lg;
|
||||
padding: @spacing-lg @spacing-xl;
|
||||
// 设计稿区块卡 1780×593 设计px:白底、无描边投影
|
||||
margin-bottom: @spacing-base;
|
||||
padding: 24px 32px 32px;
|
||||
border-radius: @radius-lg;
|
||||
background: @white;
|
||||
box-shadow: @shadow-base;
|
||||
|
||||
&:last-child {
|
||||
margin-bottom: 0;
|
||||
@@ -41,30 +41,18 @@ defineProps<Props>()
|
||||
}
|
||||
|
||||
&__title {
|
||||
position: relative;
|
||||
margin-bottom: @spacing-base;
|
||||
padding-left: @spacing-sm;
|
||||
font-size: @font-size-xl;
|
||||
font-weight: 600;
|
||||
color: @heading-color;
|
||||
|
||||
&::before {
|
||||
content: '';
|
||||
position: absolute;
|
||||
top: 50%;
|
||||
left: 0;
|
||||
width: 3px;
|
||||
height: 16px;
|
||||
border-radius: @radius-round;
|
||||
background: @primary-color;
|
||||
transform: translateY(-50%);
|
||||
}
|
||||
// 设计稿栏目标题 36 设计px / 700 / #121212(无竖条)
|
||||
margin-bottom: 36px;
|
||||
font-size: @font-size-xxl;
|
||||
font-weight: 700;
|
||||
color: @home-ink;
|
||||
}
|
||||
|
||||
&__rich {
|
||||
// 设计稿正文 16 设计px / #222222
|
||||
font-size: @font-size-sm;
|
||||
line-height: 1.9;
|
||||
color: @text-color;
|
||||
line-height: 1.8;
|
||||
color: @home-paragraph;
|
||||
word-break: break-word;
|
||||
|
||||
:deep(p) {
|
||||
@@ -85,7 +73,8 @@ defineProps<Props>()
|
||||
:deep(video) {
|
||||
display: block;
|
||||
max-width: 100%;
|
||||
margin: 0 auto @spacing-base;
|
||||
// 设计稿视频/图片通栏贴卡内边距,圆角与卡片呼应
|
||||
margin: 0 auto @spacing-lg;
|
||||
border-radius: @radius-base;
|
||||
}
|
||||
|
||||
@@ -96,7 +85,7 @@ defineProps<Props>()
|
||||
margin: @spacing-base 0 @spacing-sm;
|
||||
font-size: @font-size-base;
|
||||
font-weight: 600;
|
||||
color: @heading-color;
|
||||
color: @home-ink;
|
||||
}
|
||||
|
||||
:deep(table) {
|
||||
|
||||
@@ -44,54 +44,65 @@ function isImageIcon(icon?: string): boolean {
|
||||
|
||||
<style lang="less" scoped>
|
||||
.home-service-types {
|
||||
margin-bottom: @spacing-lg;
|
||||
padding: @spacing-lg @spacing-xl;
|
||||
// 设计稿区块卡 1780×287 设计px:白底、无描边投影
|
||||
margin-bottom: @spacing-base;
|
||||
padding: 18px 32px 24px;
|
||||
border-radius: @radius-lg;
|
||||
background: @white;
|
||||
box-shadow: @shadow-base;
|
||||
|
||||
&__title {
|
||||
position: relative;
|
||||
margin-bottom: @spacing-lg;
|
||||
padding-left: @spacing-sm;
|
||||
font-size: @font-size-xl;
|
||||
font-weight: 600;
|
||||
color: @heading-color;
|
||||
|
||||
&::before {
|
||||
content: '';
|
||||
position: absolute;
|
||||
top: 50%;
|
||||
left: 0;
|
||||
width: 3px;
|
||||
height: 16px;
|
||||
border-radius: @radius-round;
|
||||
background: @primary-color;
|
||||
transform: translateY(-50%);
|
||||
}
|
||||
// 设计稿栏目标题 36 设计px / 700 / #121212(无竖条)
|
||||
margin-bottom: 40px;
|
||||
font-size: @font-size-xxl;
|
||||
font-weight: 700;
|
||||
color: @home-ink;
|
||||
}
|
||||
|
||||
&__list {
|
||||
display: grid;
|
||||
grid-template-columns: repeat(auto-fill, minmax(104px, 1fr));
|
||||
gap: @spacing-lg @spacing-base;
|
||||
.flex(row, flex-start);
|
||||
gap: 0;
|
||||
}
|
||||
|
||||
&__item {
|
||||
.flex(column, center);
|
||||
gap: @spacing-sm;
|
||||
// 设计稿条目横向间距 182 设计px → 定宽 140 居中
|
||||
width: 140px;
|
||||
// 设计稿圆底(550..618)与文字(665)之间 41 设计px ≈ 32 CSS
|
||||
gap: 32px;
|
||||
}
|
||||
|
||||
&__icon {
|
||||
.flex(row, center);
|
||||
width: 56px;
|
||||
height: 56px;
|
||||
border-radius: @radius-base;
|
||||
// 设计稿为 60 设计px 彩色圆底 + 白色图形
|
||||
width: 52px;
|
||||
height: 52px;
|
||||
border-radius: @radius-round;
|
||||
background: @primary-light;
|
||||
color: @primary-color;
|
||||
font-size: @font-size-lg;
|
||||
color: @white;
|
||||
font-size: @font-size-xl;
|
||||
font-weight: 600;
|
||||
overflow: hidden;
|
||||
|
||||
// 每类业务圆底色按设计稿采样(顺序:Web应用/小程序/APP/二次开发/桌面工具)
|
||||
.home-service-types__item:nth-child(1) & {
|
||||
background: @home-service-web;
|
||||
}
|
||||
|
||||
.home-service-types__item:nth-child(2) & {
|
||||
background: @home-service-mp;
|
||||
}
|
||||
|
||||
.home-service-types__item:nth-child(3) & {
|
||||
background: @home-service-app;
|
||||
}
|
||||
|
||||
.home-service-types__item:nth-child(4) & {
|
||||
background: @home-service-dev;
|
||||
}
|
||||
|
||||
.home-service-types__item:nth-child(5) & {
|
||||
background: @home-service-pc;
|
||||
}
|
||||
}
|
||||
|
||||
&__img {
|
||||
@@ -101,8 +112,9 @@ function isImageIcon(icon?: string): boolean {
|
||||
}
|
||||
|
||||
&__label {
|
||||
// 设计稿条目文字 16 设计px / #333333
|
||||
font-size: @font-size-sm;
|
||||
color: @text-color;
|
||||
color: @home-body;
|
||||
text-align: center;
|
||||
.ellipsis();
|
||||
}
|
||||
|
||||
@@ -31,26 +31,33 @@ const items = [
|
||||
<style lang="less" scoped>
|
||||
.home-stats {
|
||||
.flex(row, flex-end);
|
||||
gap: @spacing-base;
|
||||
// 设计稿方块间距 30 设计px ≈ 23 CSS
|
||||
gap: 23px;
|
||||
|
||||
&__item {
|
||||
.flex(column, center, center);
|
||||
gap: @spacing-xs;
|
||||
min-width: 84px;
|
||||
padding: @spacing-base;
|
||||
border-radius: @radius-lg;
|
||||
background: rgba(255, 255, 255, 0.92);
|
||||
gap: 0;
|
||||
// 设计稿统计方块 112×112 设计px → 86×86 CSS,#024FFF 实底
|
||||
width: 86px;
|
||||
height: 86px;
|
||||
min-width: 86px;
|
||||
padding: 0;
|
||||
border-radius: @radius-sm;
|
||||
background: @primary-strong;
|
||||
}
|
||||
|
||||
&__value {
|
||||
font-size: @font-size-xxl;
|
||||
font-weight: 600;
|
||||
color: @primary-color;
|
||||
// 设计稿数字 48 设计px / 500 / 白
|
||||
font-size: 37px;
|
||||
font-weight: 500;
|
||||
line-height: 1.2;
|
||||
color: @white;
|
||||
}
|
||||
|
||||
&__label {
|
||||
font-size: @font-size-sm;
|
||||
color: @text-color-secondary;
|
||||
font-weight: 500;
|
||||
color: @white;
|
||||
}
|
||||
}
|
||||
</style>
|
||||
|
||||
@@ -37,23 +37,26 @@ const greeting = computed(() => {
|
||||
&__greeting {
|
||||
.flex(row, flex-start);
|
||||
gap: @spacing-sm;
|
||||
font-size: @font-size-xxl;
|
||||
font-weight: 600;
|
||||
color: @white;
|
||||
// 设计稿「中午好」52 设计px / 700 / #2C2C2C
|
||||
font-size: 40px;
|
||||
font-weight: 700;
|
||||
color: @home-welcome;
|
||||
}
|
||||
|
||||
&__wave {
|
||||
.flex(row, center);
|
||||
width: 32px;
|
||||
height: 32px;
|
||||
width: 36px;
|
||||
height: 36px;
|
||||
border-radius: @radius-round;
|
||||
background: rgba(255, 255, 255, 0.25);
|
||||
background: fade(@black, 4%);
|
||||
font-size: @font-size-lg;
|
||||
}
|
||||
|
||||
&__summary {
|
||||
font-size: @font-size-lg;
|
||||
color: rgba(255, 255, 255, 0.9);
|
||||
// 设计稿副文案 24 设计px / 400 / #2C2C2C
|
||||
font-size: 18px;
|
||||
font-weight: 400;
|
||||
color: @home-welcome;
|
||||
}
|
||||
}
|
||||
</style>
|
||||
|
||||
@@ -73,44 +73,55 @@ onMounted(load)
|
||||
padding-bottom: @spacing-xxl;
|
||||
|
||||
&__breadcrumb {
|
||||
margin-bottom: @spacing-base;
|
||||
font-size: @font-size-base;
|
||||
margin-bottom: 36px;
|
||||
// 设计稿面包屑 24 设计px / 500 / #666666
|
||||
font-size: 18px;
|
||||
font-weight: 500;
|
||||
color: @home-breadcrumb;
|
||||
|
||||
.link {
|
||||
color: @home-breadcrumb;
|
||||
}
|
||||
}
|
||||
|
||||
// 设计稿头图卡 1780×219 设计px:浅蓝渐变底、左上图标块 + 标题 + 副标题
|
||||
&__hero {
|
||||
.flex(row, flex-start);
|
||||
gap: @spacing-base;
|
||||
margin-bottom: @spacing-xl;
|
||||
padding: @spacing-xl;
|
||||
.flex(column, flex-start);
|
||||
gap: 18px;
|
||||
margin-bottom: @spacing-base;
|
||||
padding: 19px 22px 24px;
|
||||
border-radius: @radius-lg;
|
||||
background: @white;
|
||||
box-shadow: @shadow-base;
|
||||
background: @home-detail-hero-bg;
|
||||
}
|
||||
|
||||
&__logo {
|
||||
.flex(row, center);
|
||||
width: 56px;
|
||||
height: 56px;
|
||||
width: 62px;
|
||||
height: 62px;
|
||||
border-radius: @radius-lg;
|
||||
background: @primary-light;
|
||||
color: @primary-color;
|
||||
background: @home-detail-logo-bg;
|
||||
color: @primary-strong;
|
||||
font-size: @font-size-xl;
|
||||
font-weight: 600;
|
||||
}
|
||||
|
||||
&__intro {
|
||||
.flex(column, flex-start);
|
||||
gap: @spacing-xs;
|
||||
gap: 6px;
|
||||
}
|
||||
|
||||
&__name {
|
||||
font-size: @font-size-xxl;
|
||||
// 设计稿详情标题 26 设计px / #333333
|
||||
font-size: @font-size-xl;
|
||||
font-weight: 600;
|
||||
color: @heading-color;
|
||||
color: @home-body;
|
||||
}
|
||||
|
||||
&__slogan {
|
||||
font-size: @font-size-base;
|
||||
// 设计稿副标题 14 设计px → 可读下限 11px / #333333
|
||||
font-size: 11px;
|
||||
font-weight: 400;
|
||||
color: @home-body;
|
||||
}
|
||||
|
||||
&__cta {
|
||||
|
||||
@@ -27,9 +27,8 @@ onMounted(() => {
|
||||
|
||||
<template>
|
||||
<div class="home">
|
||||
<div class="container">
|
||||
<HomeBanner :banners="banners" />
|
||||
</div>
|
||||
<!-- 设计稿头图为通栏(0..1920),故不包 .container -->
|
||||
<HomeBanner :banners="banners" />
|
||||
|
||||
<div class="container home__dashboard">
|
||||
<section class="home__dashboard-main">
|
||||
@@ -55,23 +54,30 @@ onMounted(() => {
|
||||
<style lang="less" scoped>
|
||||
.home {
|
||||
.flex(column, flex-start);
|
||||
gap: @spacing-xl;
|
||||
padding-top: @spacing-xl;
|
||||
// 设计稿区块间距 19~20 设计px ≈ 16 CSS;头图紧贴顶栏
|
||||
gap: @spacing-base;
|
||||
padding-top: 0;
|
||||
padding-bottom: @spacing-xxl;
|
||||
|
||||
&__dashboard {
|
||||
.flex(row, space-between, stretch);
|
||||
gap: @spacing-base;
|
||||
// 设计稿左右卡间距 36 设计px ≈ 28 CSS
|
||||
gap: 28px;
|
||||
// 设计稿区块行 1680 设计px 宽(内容区内左右各缩 50 设计px)≈ 1294 CSS
|
||||
max-width: 1326px;
|
||||
margin-right: auto;
|
||||
margin-left: auto;
|
||||
}
|
||||
|
||||
&__dashboard-main {
|
||||
.flex(row, space-between, center);
|
||||
flex: 1;
|
||||
gap: @spacing-lg;
|
||||
padding: @spacing-xl;
|
||||
// 设计稿欢迎卡(120,754,922,245):白底 + 浅灰描边,内边距 61/106/66/73 设计px
|
||||
padding: 46px 56px 46px 82px;
|
||||
border: 1px solid @home-card-border;
|
||||
border-radius: @radius-lg;
|
||||
background: linear-gradient(120deg, @primary-color, #6a5cff);
|
||||
box-shadow: @shadow-base;
|
||||
background: @white;
|
||||
}
|
||||
}
|
||||
</style>
|
||||
|
||||
@@ -54,7 +54,7 @@ const localAgree = computed({
|
||||
</div>
|
||||
<label class="login-form__agree">
|
||||
<input v-model="localAgree" type="checkbox">
|
||||
<span>已阅读并同意《用户协议》和《隐私政策》</span>
|
||||
<span>已阅读并同意<em>《用户协议》</em>和<em>《隐私政策》</em></span>
|
||||
</label>
|
||||
<button class="login-form__submit" type="submit">
|
||||
登 录
|
||||
@@ -65,55 +65,64 @@ const localAgree = computed({
|
||||
<style lang="less" scoped>
|
||||
.login-form {
|
||||
.flex(column, flex-start);
|
||||
gap: @spacing-base;
|
||||
gap: @spacing-lg;
|
||||
|
||||
&__field {
|
||||
width: 100%;
|
||||
}
|
||||
|
||||
// 设计稿:输入框 40 设计px ≈ 32px 高、13 设计px 字号(可读下限 11px)、白底浅描边
|
||||
&__input {
|
||||
width: 100%;
|
||||
height: 44px;
|
||||
padding: 0 @spacing-base;
|
||||
height: 32px;
|
||||
padding: 0 12px;
|
||||
border: 1px solid @border-color;
|
||||
border-radius: @radius-base;
|
||||
background: @bg-color-light;
|
||||
font-size: @font-size-base;
|
||||
border-radius: 6px;
|
||||
background: @white;
|
||||
font-size: 11px;
|
||||
color: @heading-color;
|
||||
outline: none;
|
||||
transition: border-color 0.2s;
|
||||
box-sizing: border-box;
|
||||
|
||||
&:focus {
|
||||
border-color: @primary-color;
|
||||
border-color: @primary-strong;
|
||||
}
|
||||
|
||||
&::placeholder {
|
||||
color: @text-color-secondary;
|
||||
color: @heading-color;
|
||||
}
|
||||
}
|
||||
|
||||
&__agree {
|
||||
.flex(row, flex-start);
|
||||
gap: @spacing-xs;
|
||||
font-size: @font-size-sm;
|
||||
font-size: 11px;
|
||||
color: @text-color-secondary;
|
||||
cursor: pointer;
|
||||
|
||||
input {
|
||||
margin-top: 2px;
|
||||
accent-color: @primary-color;
|
||||
margin-top: 1px;
|
||||
accent-color: @primary-strong;
|
||||
}
|
||||
|
||||
// 设计稿:《用户协议》《隐私政策》为强调蓝,其余为次级灰
|
||||
em {
|
||||
font-style: normal;
|
||||
color: @primary-strong;
|
||||
}
|
||||
}
|
||||
|
||||
// 设计稿:登录按钮 44 设计px ≈ 34px 高、#024FFF 实底
|
||||
&__submit {
|
||||
width: 100%;
|
||||
height: 44px;
|
||||
height: 34px;
|
||||
border: none;
|
||||
border-radius: @radius-base;
|
||||
background: @primary-color;
|
||||
border-radius: 6px;
|
||||
background: @primary-strong;
|
||||
color: @white;
|
||||
font-size: @font-size-lg;
|
||||
font-size: 12px;
|
||||
font-weight: 500;
|
||||
letter-spacing: 2px;
|
||||
cursor: pointer;
|
||||
transition: background 0.2s;
|
||||
|
||||
@@ -73,7 +73,7 @@ function onSubmit(): void {
|
||||
</div>
|
||||
<label class="sms-login__agree">
|
||||
<input v-model="localAgree" type="checkbox">
|
||||
<span>已阅读并同意《用户协议》和《隐私政策》</span>
|
||||
<span>已阅读并同意<em>《用户协议》</em>和<em>《隐私政策》</em></span>
|
||||
</label>
|
||||
<button class="sms-login__submit" type="submit">
|
||||
登 录
|
||||
@@ -84,55 +84,64 @@ function onSubmit(): void {
|
||||
<style lang="less" scoped>
|
||||
.sms-login {
|
||||
.flex(column, flex-start);
|
||||
gap: @spacing-base;
|
||||
gap: @spacing-lg;
|
||||
|
||||
&__field {
|
||||
width: 100%;
|
||||
}
|
||||
|
||||
// 设计稿:输入框 40 设计px ≈ 32px 高、13 设计px 字号(可读下限 11px)、白底浅描边
|
||||
&__input {
|
||||
width: 100%;
|
||||
height: 44px;
|
||||
padding: 0 @spacing-base;
|
||||
height: 32px;
|
||||
padding: 0 12px;
|
||||
border: 1px solid @border-color;
|
||||
border-radius: @radius-base;
|
||||
background: @bg-color-light;
|
||||
font-size: @font-size-base;
|
||||
border-radius: 6px;
|
||||
background: @white;
|
||||
font-size: 11px;
|
||||
color: @heading-color;
|
||||
outline: none;
|
||||
transition: border-color 0.2s;
|
||||
box-sizing: border-box;
|
||||
|
||||
&:focus {
|
||||
border-color: @primary-color;
|
||||
border-color: @primary-strong;
|
||||
}
|
||||
|
||||
&::placeholder {
|
||||
color: @text-color-secondary;
|
||||
color: @heading-color;
|
||||
}
|
||||
}
|
||||
|
||||
&__agree {
|
||||
.flex(row, flex-start);
|
||||
gap: @spacing-xs;
|
||||
font-size: @font-size-sm;
|
||||
font-size: 11px;
|
||||
color: @text-color-secondary;
|
||||
cursor: pointer;
|
||||
|
||||
input {
|
||||
margin-top: 2px;
|
||||
accent-color: @primary-color;
|
||||
margin-top: 1px;
|
||||
accent-color: @primary-strong;
|
||||
}
|
||||
|
||||
// 设计稿:《用户协议》《隐私政策》为强调蓝,其余为次级灰
|
||||
em {
|
||||
font-style: normal;
|
||||
color: @primary-strong;
|
||||
}
|
||||
}
|
||||
|
||||
// 设计稿:登录按钮 44 设计px ≈ 34px 高、#024FFF 实底
|
||||
&__submit {
|
||||
width: 100%;
|
||||
height: 44px;
|
||||
height: 34px;
|
||||
border: none;
|
||||
border-radius: @radius-base;
|
||||
background: @primary-color;
|
||||
border-radius: 6px;
|
||||
background: @primary-strong;
|
||||
color: @white;
|
||||
font-size: @font-size-lg;
|
||||
font-size: 12px;
|
||||
font-weight: 500;
|
||||
letter-spacing: 2px;
|
||||
cursor: pointer;
|
||||
transition: background 0.2s;
|
||||
|
||||
@@ -89,13 +89,7 @@ async function onGetCode(target: string): Promise<void> {
|
||||
<main class="auth-page__main">
|
||||
<div class="auth-page__card">
|
||||
<div class="auth-page__tabs">
|
||||
<button
|
||||
class="auth-page__tab"
|
||||
:class="{ 'is-active': activeTab === 'account' }"
|
||||
@click="activeTab = 'account'"
|
||||
>
|
||||
账号密码登录
|
||||
</button>
|
||||
<!-- 设计稿 Tab 顺序:手机验证码登录在前、账号密码登录在后 -->
|
||||
<button
|
||||
class="auth-page__tab"
|
||||
:class="{ 'is-active': activeTab === 'sms' }"
|
||||
@@ -103,6 +97,13 @@ async function onGetCode(target: string): Promise<void> {
|
||||
>
|
||||
手机验证码登录
|
||||
</button>
|
||||
<button
|
||||
class="auth-page__tab"
|
||||
:class="{ 'is-active': activeTab === 'account' }"
|
||||
@click="activeTab = 'account'"
|
||||
>
|
||||
账号密码登录
|
||||
</button>
|
||||
</div>
|
||||
|
||||
<LoginForm
|
||||
@@ -131,48 +132,59 @@ async function onGetCode(target: string): Promise<void> {
|
||||
|
||||
<style lang="less" scoped>
|
||||
.auth-page {
|
||||
position: relative;
|
||||
display: flex;
|
||||
min-height: 100vh;
|
||||
background: @bg-color;
|
||||
// 设计稿:右侧表单区为纯白底,无卡片描边/阴影
|
||||
background: @white;
|
||||
|
||||
&__brand {
|
||||
flex: 0 0 44%;
|
||||
.flex(row, center, center);
|
||||
background: linear-gradient(135deg, @primary-color 0%, #1b4fd8 100%);
|
||||
// 设计稿:左侧品牌渐变面板约占 786/1920 ≈ 41%
|
||||
flex: 0 0 41%;
|
||||
.flex(row, flex-start, stretch);
|
||||
background: linear-gradient(135deg, @auth-gradient-from 0%, @auth-gradient-to 100%);
|
||||
color: @white;
|
||||
}
|
||||
|
||||
&__brand-inner {
|
||||
.flex(column, flex-start);
|
||||
gap: @spacing-lg;
|
||||
padding: @spacing-xxl;
|
||||
.flex(column, space-between, flex-start);
|
||||
width: 100%;
|
||||
// 设计稿:文字列起点 x=257 ≈ 面板宽 32.7%;主标距顶 ≈ 28%、标语底边距底 ≈ 30%
|
||||
padding: 26vh 48px 30vh 32%;
|
||||
}
|
||||
|
||||
&__logo {
|
||||
font-size: 32px;
|
||||
font-size: 31px;
|
||||
font-weight: 700;
|
||||
letter-spacing: 2px;
|
||||
line-height: 1.4;
|
||||
line-height: 1.45;
|
||||
// 设计稿文本框 432 设计px:定宽让 11 字在「虫子智造研发 / 一体化平台」处折行
|
||||
max-width: 200px;
|
||||
}
|
||||
|
||||
&__slogan {
|
||||
font-size: @font-size-xl;
|
||||
opacity: 0.85;
|
||||
letter-spacing: 6px;
|
||||
font-size: 17px;
|
||||
font-weight: 600;
|
||||
letter-spacing: 8px;
|
||||
}
|
||||
|
||||
// 设计稿:「游客模式」为右上角白底上的深色纯文本,无边框
|
||||
&__guest {
|
||||
margin-top: @spacing-xl;
|
||||
padding: @spacing-sm @spacing-base;
|
||||
border: 1px solid rgba(255, 255, 255, 0.6);
|
||||
border-radius: @radius-base;
|
||||
color: @white;
|
||||
font-size: @font-size-base;
|
||||
position: absolute;
|
||||
top: 18px;
|
||||
right: 16px;
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
border: none;
|
||||
border-radius: 0;
|
||||
color: @heading-color;
|
||||
font-size: 11px;
|
||||
text-decoration: none;
|
||||
transition: background 0.2s;
|
||||
transition: color 0.2s;
|
||||
|
||||
&:hover {
|
||||
background: rgba(255, 255, 255, 0.15);
|
||||
background: transparent;
|
||||
color: @primary-strong;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -184,46 +196,48 @@ async function onGetCode(target: string): Promise<void> {
|
||||
|
||||
&__card {
|
||||
.flex(column, flex-start);
|
||||
gap: @spacing-lg;
|
||||
// 设计稿:表单列宽 688 设计px ≈ 530px,标题/Tab/输入/按钮纵向节奏 ≈ 41px
|
||||
gap: 41px;
|
||||
width: 100%;
|
||||
max-width: 420px;
|
||||
padding: @spacing-xl @spacing-lg;
|
||||
border-radius: @radius-lg;
|
||||
background: @white;
|
||||
box-shadow: @shadow-lg;
|
||||
max-width: 530px;
|
||||
padding: 0;
|
||||
border-radius: 0;
|
||||
background: transparent;
|
||||
box-shadow: none;
|
||||
}
|
||||
|
||||
&__tabs {
|
||||
.flex(row, center);
|
||||
gap: @spacing-lg;
|
||||
border-bottom: 1px solid @border-color;
|
||||
// 设计稿:Tab 左对齐于表单列,仅激活项带 2px 蓝色下划线(无整行分隔线)
|
||||
.flex(row, flex-start);
|
||||
gap: @spacing-sm;
|
||||
border-bottom: none;
|
||||
}
|
||||
|
||||
&__tab {
|
||||
padding: @spacing-sm 0;
|
||||
padding: 0 0 4px;
|
||||
border: none;
|
||||
border-bottom: 2px solid transparent;
|
||||
background: transparent;
|
||||
font-size: @font-size-lg;
|
||||
color: @text-color-secondary;
|
||||
font-size: 11px;
|
||||
color: @text-color;
|
||||
cursor: pointer;
|
||||
transition: all 0.2s;
|
||||
|
||||
&.is-active {
|
||||
border-bottom-color: @primary-color;
|
||||
color: @primary-color;
|
||||
border-bottom-color: @primary-strong;
|
||||
color: @primary-strong;
|
||||
font-weight: 600;
|
||||
}
|
||||
}
|
||||
|
||||
&__switch {
|
||||
text-align: center;
|
||||
font-size: @font-size-base;
|
||||
font-size: 11px;
|
||||
color: @text-color-secondary;
|
||||
}
|
||||
|
||||
&__link {
|
||||
color: @primary-color;
|
||||
color: @primary-strong;
|
||||
|
||||
&:hover {
|
||||
color: @primary-hover;
|
||||
|
||||
@@ -103,7 +103,7 @@ onBeforeUnmount(() => {
|
||||
>
|
||||
<label class="auth-page__agree">
|
||||
<input v-model="agree" type="checkbox">
|
||||
<span>已阅读并同意《用户协议》和《隐私政策》</span>
|
||||
<span>已阅读并同意<em>《用户协议》</em>和<em>《隐私政策》</em></span>
|
||||
</label>
|
||||
<button class="auth-page__submit" type="submit">
|
||||
注 册
|
||||
@@ -120,48 +120,59 @@ onBeforeUnmount(() => {
|
||||
|
||||
<style lang="less" scoped>
|
||||
.auth-page {
|
||||
position: relative;
|
||||
display: flex;
|
||||
min-height: 100vh;
|
||||
background: @bg-color;
|
||||
// 设计稿:右侧表单区为纯白底,无卡片描边/阴影
|
||||
background: @white;
|
||||
|
||||
&__brand {
|
||||
flex: 0 0 44%;
|
||||
.flex(row, center, center);
|
||||
background: linear-gradient(135deg, @primary-color 0%, #1b4fd8 100%);
|
||||
// 设计稿:左侧品牌渐变面板约占 786/1920 ≈ 41%
|
||||
flex: 0 0 41%;
|
||||
.flex(row, flex-start, stretch);
|
||||
background: linear-gradient(135deg, @auth-gradient-from 0%, @auth-gradient-to 100%);
|
||||
color: @white;
|
||||
}
|
||||
|
||||
&__brand-inner {
|
||||
.flex(column, flex-start);
|
||||
gap: @spacing-lg;
|
||||
padding: @spacing-xxl;
|
||||
.flex(column, space-between, flex-start);
|
||||
width: 100%;
|
||||
// 设计稿:文字列起点 x=257 ≈ 面板宽 32.7%;主标距顶 ≈ 28%、标语底边距底 ≈ 30%
|
||||
padding: 26vh 48px 30vh 32%;
|
||||
}
|
||||
|
||||
&__logo {
|
||||
font-size: 32px;
|
||||
font-size: 31px;
|
||||
font-weight: 700;
|
||||
letter-spacing: 2px;
|
||||
line-height: 1.4;
|
||||
line-height: 1.45;
|
||||
// 设计稿文本框 432 设计px:定宽让 11 字在「虫子智造研发 / 一体化平台」处折行
|
||||
max-width: 200px;
|
||||
}
|
||||
|
||||
&__slogan {
|
||||
font-size: @font-size-xl;
|
||||
opacity: 0.85;
|
||||
letter-spacing: 6px;
|
||||
font-size: 17px;
|
||||
font-weight: 600;
|
||||
letter-spacing: 8px;
|
||||
}
|
||||
|
||||
// 设计稿:「游客模式」为右上角白底上的深色纯文本,无边框
|
||||
&__guest {
|
||||
margin-top: @spacing-xl;
|
||||
padding: @spacing-sm @spacing-base;
|
||||
border: 1px solid rgba(255, 255, 255, 0.6);
|
||||
border-radius: @radius-base;
|
||||
color: @white;
|
||||
font-size: @font-size-base;
|
||||
position: absolute;
|
||||
top: 18px;
|
||||
right: 16px;
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
border: none;
|
||||
border-radius: 0;
|
||||
color: @heading-color;
|
||||
font-size: 11px;
|
||||
text-decoration: none;
|
||||
transition: background 0.2s;
|
||||
transition: color 0.2s;
|
||||
|
||||
&:hover {
|
||||
background: rgba(255, 255, 255, 0.15);
|
||||
background: transparent;
|
||||
color: @primary-strong;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -173,76 +184,89 @@ onBeforeUnmount(() => {
|
||||
|
||||
&__card {
|
||||
.flex(column, flex-start);
|
||||
gap: @spacing-base;
|
||||
// 设计稿:表单列宽 688 设计px ≈ 530px,标题/输入/按钮纵向节奏 ≈ 41px
|
||||
gap: 41px;
|
||||
width: 100%;
|
||||
max-width: 420px;
|
||||
padding: @spacing-xl @spacing-lg;
|
||||
border-radius: @radius-lg;
|
||||
background: @white;
|
||||
box-shadow: @shadow-lg;
|
||||
max-width: 530px;
|
||||
padding: 0;
|
||||
border-radius: 0;
|
||||
background: transparent;
|
||||
box-shadow: none;
|
||||
}
|
||||
|
||||
// 设计稿:标题(34 设计px ≈ 26px)到首个输入框 ≈ 62px
|
||||
&__title {
|
||||
font-size: @font-size-xl;
|
||||
font-weight: 600;
|
||||
margin-bottom: 21px;
|
||||
font-size: 26px;
|
||||
font-weight: 700;
|
||||
color: @heading-color;
|
||||
}
|
||||
|
||||
&__form {
|
||||
.flex(column, flex-start);
|
||||
gap: @spacing-base;
|
||||
gap: @spacing-lg;
|
||||
width: 100%;
|
||||
}
|
||||
|
||||
// 设置密码 → 密码强度条 ≈ 9px,强度条 → 提示 ≈ 9px(组件内)
|
||||
&__pwd-wrap {
|
||||
.flex(column, flex-start);
|
||||
gap: @spacing-xs;
|
||||
gap: 9px;
|
||||
width: 100%;
|
||||
}
|
||||
|
||||
// 设计稿:输入框 40 设计px ≈ 32px 高、13 设计px 字号(可读下限 11px)、白底浅描边
|
||||
&__input {
|
||||
width: 100%;
|
||||
height: 44px;
|
||||
padding: 0 @spacing-base;
|
||||
height: 32px;
|
||||
padding: 0 12px;
|
||||
border: 1px solid @border-color;
|
||||
border-radius: @radius-base;
|
||||
background: @bg-color-light;
|
||||
font-size: @font-size-base;
|
||||
border-radius: 6px;
|
||||
background: @white;
|
||||
font-size: 11px;
|
||||
color: @heading-color;
|
||||
outline: none;
|
||||
transition: border-color 0.2s;
|
||||
box-sizing: border-box;
|
||||
|
||||
&:focus {
|
||||
border-color: @primary-color;
|
||||
border-color: @primary-strong;
|
||||
}
|
||||
|
||||
&::placeholder {
|
||||
color: @text-color-secondary;
|
||||
color: @heading-color;
|
||||
}
|
||||
}
|
||||
|
||||
&__agree {
|
||||
.flex(row, flex-start);
|
||||
gap: @spacing-xs;
|
||||
font-size: @font-size-sm;
|
||||
font-size: 11px;
|
||||
color: @text-color-secondary;
|
||||
cursor: pointer;
|
||||
|
||||
input {
|
||||
margin-top: 2px;
|
||||
accent-color: @primary-color;
|
||||
margin-top: 1px;
|
||||
accent-color: @primary-strong;
|
||||
}
|
||||
|
||||
// 设计稿:《用户协议》《隐私政策》为强调蓝,其余为次级灰
|
||||
em {
|
||||
font-style: normal;
|
||||
color: @primary-strong;
|
||||
}
|
||||
}
|
||||
|
||||
// 设计稿:注册按钮 44 设计px ≈ 34px 高、#024FFF 实底
|
||||
&__submit {
|
||||
width: 100%;
|
||||
height: 44px;
|
||||
height: 34px;
|
||||
border: none;
|
||||
border-radius: @radius-base;
|
||||
background: @primary-color;
|
||||
border-radius: 6px;
|
||||
background: @primary-strong;
|
||||
color: @white;
|
||||
font-size: @font-size-lg;
|
||||
font-size: 12px;
|
||||
font-weight: 500;
|
||||
letter-spacing: 2px;
|
||||
cursor: pointer;
|
||||
transition: background 0.2s;
|
||||
@@ -252,14 +276,16 @@ onBeforeUnmount(() => {
|
||||
}
|
||||
}
|
||||
|
||||
// 设计稿:按钮 → 底部切换链接仅约 13px
|
||||
&__switch {
|
||||
margin-top: -26px;
|
||||
text-align: center;
|
||||
font-size: @font-size-base;
|
||||
font-size: 11px;
|
||||
color: @text-color-secondary;
|
||||
}
|
||||
|
||||
&__link {
|
||||
color: @primary-color;
|
||||
color: @primary-strong;
|
||||
|
||||
&:hover {
|
||||
color: @primary-hover;
|
||||
|
||||
@@ -118,7 +118,7 @@ onBeforeUnmount(() => {
|
||||
>
|
||||
<label class="auth-page__agree">
|
||||
<input v-model="agree" type="checkbox">
|
||||
<span>已阅读并同意《用户协议》和《隐私政策》</span>
|
||||
<span>已阅读并同意<em>《用户协议》</em>和<em>《隐私政策》</em></span>
|
||||
</label>
|
||||
<button class="auth-page__submit" type="submit">
|
||||
确认修改
|
||||
@@ -135,48 +135,59 @@ onBeforeUnmount(() => {
|
||||
|
||||
<style lang="less" scoped>
|
||||
.auth-page {
|
||||
position: relative;
|
||||
display: flex;
|
||||
min-height: 100vh;
|
||||
background: @bg-color;
|
||||
// 设计稿:右侧表单区为纯白底,无卡片描边/阴影
|
||||
background: @white;
|
||||
|
||||
&__brand {
|
||||
flex: 0 0 44%;
|
||||
.flex(row, center, center);
|
||||
background: linear-gradient(135deg, @primary-color 0%, #1b4fd8 100%);
|
||||
// 设计稿:左侧品牌渐变面板约占 786/1920 ≈ 41%
|
||||
flex: 0 0 41%;
|
||||
.flex(row, flex-start, stretch);
|
||||
background: linear-gradient(135deg, @auth-gradient-from 0%, @auth-gradient-to 100%);
|
||||
color: @white;
|
||||
}
|
||||
|
||||
&__brand-inner {
|
||||
.flex(column, flex-start);
|
||||
gap: @spacing-lg;
|
||||
padding: @spacing-xxl;
|
||||
.flex(column, space-between, flex-start);
|
||||
width: 100%;
|
||||
// 设计稿:文字列起点 x=257 ≈ 面板宽 32.7%;主标距顶 ≈ 28%、标语底边距底 ≈ 30%
|
||||
padding: 26vh 48px 30vh 32%;
|
||||
}
|
||||
|
||||
&__logo {
|
||||
font-size: 32px;
|
||||
font-size: 31px;
|
||||
font-weight: 700;
|
||||
letter-spacing: 2px;
|
||||
line-height: 1.4;
|
||||
line-height: 1.45;
|
||||
// 设计稿文本框 432 设计px:定宽让 11 字在「虫子智造研发 / 一体化平台」处折行
|
||||
max-width: 200px;
|
||||
}
|
||||
|
||||
&__slogan {
|
||||
font-size: @font-size-xl;
|
||||
opacity: 0.85;
|
||||
letter-spacing: 6px;
|
||||
font-size: 17px;
|
||||
font-weight: 600;
|
||||
letter-spacing: 8px;
|
||||
}
|
||||
|
||||
// 设计稿:「游客模式」为右上角白底上的深色纯文本,无边框
|
||||
&__guest {
|
||||
margin-top: @spacing-xl;
|
||||
padding: @spacing-sm @spacing-base;
|
||||
border: 1px solid rgba(255, 255, 255, 0.6);
|
||||
border-radius: @radius-base;
|
||||
color: @white;
|
||||
font-size: @font-size-base;
|
||||
position: absolute;
|
||||
top: 18px;
|
||||
right: 16px;
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
border: none;
|
||||
border-radius: 0;
|
||||
color: @heading-color;
|
||||
font-size: 11px;
|
||||
text-decoration: none;
|
||||
transition: background 0.2s;
|
||||
transition: color 0.2s;
|
||||
|
||||
&:hover {
|
||||
background: rgba(255, 255, 255, 0.15);
|
||||
background: transparent;
|
||||
color: @primary-strong;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -188,70 +199,82 @@ onBeforeUnmount(() => {
|
||||
|
||||
&__card {
|
||||
.flex(column, flex-start);
|
||||
gap: @spacing-base;
|
||||
// 设计稿:表单列宽 688 设计px ≈ 530px,标题/输入/按钮纵向节奏 ≈ 41px
|
||||
gap: 41px;
|
||||
width: 100%;
|
||||
max-width: 420px;
|
||||
padding: @spacing-xl @spacing-lg;
|
||||
border-radius: @radius-lg;
|
||||
background: @white;
|
||||
box-shadow: @shadow-lg;
|
||||
max-width: 530px;
|
||||
padding: 0;
|
||||
border-radius: 0;
|
||||
background: transparent;
|
||||
box-shadow: none;
|
||||
}
|
||||
|
||||
// 设计稿:标题(34 设计px ≈ 26px)到首个输入框 ≈ 62px
|
||||
&__title {
|
||||
font-size: @font-size-xl;
|
||||
font-weight: 600;
|
||||
margin-bottom: 21px;
|
||||
font-size: 26px;
|
||||
font-weight: 700;
|
||||
color: @heading-color;
|
||||
}
|
||||
|
||||
&__form {
|
||||
.flex(column, flex-start);
|
||||
gap: @spacing-base;
|
||||
gap: @spacing-lg;
|
||||
width: 100%;
|
||||
}
|
||||
|
||||
// 设计稿:输入框 40 设计px ≈ 32px 高、13 设计px 字号(可读下限 11px)、白底浅描边
|
||||
&__input {
|
||||
width: 100%;
|
||||
height: 44px;
|
||||
padding: 0 @spacing-base;
|
||||
height: 32px;
|
||||
padding: 0 12px;
|
||||
border: 1px solid @border-color;
|
||||
border-radius: @radius-base;
|
||||
background: @bg-color-light;
|
||||
font-size: @font-size-base;
|
||||
border-radius: 6px;
|
||||
background: @white;
|
||||
font-size: 11px;
|
||||
color: @heading-color;
|
||||
outline: none;
|
||||
transition: border-color 0.2s;
|
||||
box-sizing: border-box;
|
||||
|
||||
&:focus {
|
||||
border-color: @primary-color;
|
||||
border-color: @primary-strong;
|
||||
}
|
||||
|
||||
&::placeholder {
|
||||
color: @text-color-secondary;
|
||||
color: @heading-color;
|
||||
}
|
||||
}
|
||||
|
||||
&__agree {
|
||||
.flex(row, flex-start);
|
||||
gap: @spacing-xs;
|
||||
font-size: @font-size-sm;
|
||||
font-size: 11px;
|
||||
color: @text-color-secondary;
|
||||
cursor: pointer;
|
||||
|
||||
input {
|
||||
margin-top: 2px;
|
||||
accent-color: @primary-color;
|
||||
margin-top: 1px;
|
||||
accent-color: @primary-strong;
|
||||
}
|
||||
|
||||
// 设计稿:《用户协议》《隐私政策》为强调蓝,其余为次级灰
|
||||
em {
|
||||
font-style: normal;
|
||||
color: @primary-strong;
|
||||
}
|
||||
}
|
||||
|
||||
// 设计稿:确认修改按钮 44 设计px ≈ 34px 高、#024FFF 实底
|
||||
&__submit {
|
||||
width: 100%;
|
||||
height: 44px;
|
||||
height: 34px;
|
||||
border: none;
|
||||
border-radius: @radius-base;
|
||||
background: @primary-color;
|
||||
border-radius: 6px;
|
||||
background: @primary-strong;
|
||||
color: @white;
|
||||
font-size: @font-size-lg;
|
||||
font-size: 12px;
|
||||
font-weight: 500;
|
||||
letter-spacing: 2px;
|
||||
cursor: pointer;
|
||||
transition: background 0.2s;
|
||||
@@ -261,14 +284,16 @@ onBeforeUnmount(() => {
|
||||
}
|
||||
}
|
||||
|
||||
// 设计稿:按钮 → 底部切换链接仅约 13px
|
||||
&__switch {
|
||||
margin-top: -26px;
|
||||
text-align: center;
|
||||
font-size: @font-size-base;
|
||||
font-size: 11px;
|
||||
color: @text-color-secondary;
|
||||
}
|
||||
|
||||
&__link {
|
||||
color: @primary-color;
|
||||
color: @primary-strong;
|
||||
|
||||
&:hover {
|
||||
color: @primary-hover;
|
||||
|
||||
@@ -41,10 +41,10 @@ const emojiMap: Record<MessageType, string> = {
|
||||
|
||||
<style lang="less" scoped>
|
||||
.message-item {
|
||||
position: relative; // 未读徽标相对行定位(压图标右上角)
|
||||
.flex(row, flex-start);
|
||||
gap: @spacing-base;
|
||||
padding: @spacing-base;
|
||||
border-radius: @radius-base;
|
||||
gap: @spacing-base; // 图标→标题 22 × 0.77
|
||||
padding: 14px 17px; // 行内边距 23/22 × 0.77
|
||||
background: @white;
|
||||
cursor: pointer;
|
||||
transition: background 0.2s;
|
||||
@@ -53,17 +53,24 @@ const emojiMap: Record<MessageType, string> = {
|
||||
background: @bg-color-light;
|
||||
}
|
||||
|
||||
// 类型图标圆:设计 43 直径 40 × 0.77,实取 #3B82F6
|
||||
&__emoji {
|
||||
flex-shrink: 0;
|
||||
font-size: @font-size-xl;
|
||||
line-height: 1.4;
|
||||
.flex(row, center);
|
||||
width: 31px;
|
||||
height: 31px;
|
||||
border-radius: @radius-round;
|
||||
background: @message-icon-bg;
|
||||
font-size: 15px;
|
||||
line-height: 1;
|
||||
}
|
||||
|
||||
&__body {
|
||||
.flex(column, flex-start);
|
||||
gap: @spacing-xs;
|
||||
.flex(column, flex-start, stretch);
|
||||
gap: 5px; // 标题→摘要 6 × 0.77
|
||||
flex: 1;
|
||||
min-width: 0;
|
||||
margin-top: 6px; // 标题比图标顶下移 9 × 0.77
|
||||
}
|
||||
|
||||
&__head {
|
||||
@@ -72,27 +79,33 @@ const emojiMap: Record<MessageType, string> = {
|
||||
width: 100%;
|
||||
}
|
||||
|
||||
// 设计 43:标题 14 → 可读下限 11 / 600 / #1F2937(所有行均半粗)
|
||||
&__title {
|
||||
font-size: @font-size-lg;
|
||||
font-size: 11px;
|
||||
font-weight: 600;
|
||||
color: @heading-color;
|
||||
.ellipsis();
|
||||
}
|
||||
|
||||
&__time {
|
||||
flex-shrink: 0;
|
||||
font-size: @font-size-sm;
|
||||
font-size: 11px; // 设计 12 → 可读下限 11
|
||||
color: @text-color-disabled; // 设计 43 时间 @text-color-disabled(覆盖 text-secondary)
|
||||
}
|
||||
|
||||
// 设计 43:摘要 12 → 可读下限 11 / #6B7280(text-secondary)
|
||||
&__summary {
|
||||
font-size: @font-size-base;
|
||||
font-size: 11px;
|
||||
.ellipsis();
|
||||
}
|
||||
|
||||
// 未读徽标:设计 43 红圆压图标右上(≈ 直径 20 × 0.77)
|
||||
&__dot {
|
||||
flex-shrink: 0;
|
||||
align-self: center;
|
||||
width: 8px;
|
||||
height: 8px;
|
||||
position: absolute;
|
||||
top: 12px;
|
||||
left: 42px;
|
||||
width: 15px;
|
||||
height: 15px;
|
||||
border-radius: @radius-round;
|
||||
background: @danger-color;
|
||||
}
|
||||
|
||||
@@ -29,16 +29,22 @@ const emit = defineEmits<{ view: [id: string] }>()
|
||||
|
||||
<style lang="less" scoped>
|
||||
.message-list {
|
||||
.flex(column, flex-start);
|
||||
gap: @spacing-sm;
|
||||
padding: @spacing-sm;
|
||||
border-radius: @radius-lg;
|
||||
background: @bg-color;
|
||||
.flex(column, flex-start, stretch);
|
||||
gap: 0; // 行紧排,行间以分割线分隔(设计 43)
|
||||
padding: 0;
|
||||
border-radius: @radius-base;
|
||||
background: @white; // 设计 43 列表卡白底直压页面灰底
|
||||
overflow: hidden; // 悬停底色收敛在卡圆角内
|
||||
|
||||
// 行分割线:设计 43 实取 #F0F1F3(矩形 1/2,跨满卡内容宽)
|
||||
.message-item + .message-item {
|
||||
border-top: 1px solid @project-divider;
|
||||
}
|
||||
|
||||
&__empty {
|
||||
padding: @spacing-xxl 0;
|
||||
padding: 40px 0;
|
||||
text-align: center;
|
||||
font-size: @font-size-base;
|
||||
font-size: 11px; // 设计 43 空态文字 → 可读下限 11
|
||||
}
|
||||
}
|
||||
</style>
|
||||
|
||||
@@ -46,50 +46,52 @@ function countOf(value: MessageType | 'all', counts: Counts): number {
|
||||
|
||||
<style lang="less" scoped>
|
||||
.message-tabs {
|
||||
.flex(row, flex-start);
|
||||
gap: @spacing-sm;
|
||||
padding: @spacing-sm @spacing-base;
|
||||
border-radius: @radius-lg;
|
||||
.flex(column, flex-start, stretch);
|
||||
padding: 18px 0; // 卡上内边距 24 × 0.77
|
||||
min-height: 338px; // 设计左卡高 439 × 0.77
|
||||
border-radius: @radius-base;
|
||||
background: @white;
|
||||
box-shadow: @shadow-base;
|
||||
box-shadow: none; // 设计 43:白卡直压页面底色,无阴影无描边
|
||||
|
||||
&__tab {
|
||||
.flex(row, center);
|
||||
gap: @spacing-xs;
|
||||
height: 32px;
|
||||
padding: 0 @spacing-base;
|
||||
border-radius: @radius-round;
|
||||
.flex(row, space-between);
|
||||
gap: @spacing-sm;
|
||||
height: 32px; // 分类行间距 41 × 0.77
|
||||
padding: 0 18px 0 25px; // 左 33 / 右 23 × 0.77
|
||||
border-radius: 0;
|
||||
background: transparent;
|
||||
color: @text-color;
|
||||
font-size: @font-size-base;
|
||||
color: @text-color; // 设计 43 未选中 @text-color
|
||||
font-size: 11px; // 设计 13 → 可读下限 11
|
||||
font-weight: 400;
|
||||
transition: all 0.2s;
|
||||
|
||||
&:hover {
|
||||
color: @primary-color;
|
||||
color: @primary-strong;
|
||||
}
|
||||
|
||||
&.is-active {
|
||||
background: @primary-light;
|
||||
color: @primary-color;
|
||||
background: transparent; // 设计 43 选中无胶囊底
|
||||
color: @primary-strong; // 设计 43 选中 @primary-strong
|
||||
font-weight: 600;
|
||||
}
|
||||
}
|
||||
|
||||
&__count {
|
||||
min-width: 18px;
|
||||
height: 18px;
|
||||
padding: 0 5px;
|
||||
min-width: 15px; // 徽标直径 20 × 0.77
|
||||
height: 15px;
|
||||
padding: 0 4px;
|
||||
border-radius: @radius-round;
|
||||
background: @bg-color;
|
||||
color: @text-color-secondary;
|
||||
font-size: @font-size-sm;
|
||||
line-height: 18px;
|
||||
background: @danger-color; // 设计 43 红底 ≈ #F54343
|
||||
color: @white;
|
||||
font-size: 11px; // 设计 10 → 可读下限 11
|
||||
line-height: 15px;
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
.is-active &__count {
|
||||
background: @primary-color;
|
||||
background: @danger-color; // 设计 43 选中项徽标仍为红底
|
||||
color: @white;
|
||||
font-weight: 600;
|
||||
}
|
||||
}
|
||||
</style>
|
||||
|
||||
@@ -101,84 +101,113 @@ onMounted(load)
|
||||
|
||||
<style lang="less" scoped>
|
||||
.message-detail {
|
||||
padding-top: @spacing-lg;
|
||||
padding-bottom: @spacing-xxl;
|
||||
max-width: @container-width;
|
||||
margin: 0 auto;
|
||||
padding: @spacing-lg @spacing-base @spacing-xxl;
|
||||
|
||||
// 设计 42:面包屑 12 → 11,#9CA3AF;末段「消息详情」#4B5563 / 500
|
||||
&__breadcrumb {
|
||||
margin-bottom: @spacing-base;
|
||||
font-size: @font-size-base;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
gap: 4px;
|
||||
margin-bottom: 12px; // 面包屑→卡片 15 × 0.77
|
||||
font-size: 11px;
|
||||
color: @text-color-disabled;
|
||||
|
||||
.link {
|
||||
color: @text-color-disabled;
|
||||
}
|
||||
|
||||
span:last-child {
|
||||
color: @text-color;
|
||||
font-weight: 500;
|
||||
}
|
||||
}
|
||||
|
||||
// 设计 42:白卡直压页面灰底,无阴影
|
||||
&__card {
|
||||
padding: @spacing-xl;
|
||||
padding: 32px 36px 34px; // 卡内边距 42/48/44 × 0.77
|
||||
border-radius: @radius-lg;
|
||||
background: @white;
|
||||
box-shadow: @shadow-base;
|
||||
box-shadow: none;
|
||||
}
|
||||
|
||||
// 设计 42:主标题 20 → 15 / 700 / 居中 / #1F2937
|
||||
&__title {
|
||||
font-size: @font-size-xl;
|
||||
font-weight: 600;
|
||||
font-size: 15px;
|
||||
font-weight: 700;
|
||||
color: @heading-color;
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
// 设计 42:发布时间 12 → 11 / #9CA3AF / 居中
|
||||
&__time {
|
||||
margin-top: @spacing-sm;
|
||||
font-size: @font-size-sm;
|
||||
margin-top: 11px; // 14 × 0.77
|
||||
font-size: 11px;
|
||||
color: @text-color-disabled;
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
// 设计 42:富文本 13 → 11 / #4B5563 / 居中 / 行高 24.7 × 0.77
|
||||
&__content {
|
||||
margin-top: @spacing-lg;
|
||||
padding: @spacing-base;
|
||||
border-radius: @radius-base;
|
||||
background: @bg-color-light;
|
||||
margin-top: 24px; // 时间→正文 32 × 0.77
|
||||
background: transparent;
|
||||
color: @text-color;
|
||||
font-size: @font-size-base;
|
||||
line-height: 1.8;
|
||||
font-size: 11px;
|
||||
line-height: 1.9;
|
||||
text-align: center;
|
||||
white-space: pre-wrap;
|
||||
word-break: break-word;
|
||||
}
|
||||
|
||||
&__attachments {
|
||||
margin-top: @spacing-lg;
|
||||
margin-top: 20px; // 正文→附件 26 × 0.77
|
||||
|
||||
&-title {
|
||||
margin-bottom: @spacing-sm;
|
||||
font-size: @font-size-lg;
|
||||
font-weight: 600;
|
||||
color: @heading-color;
|
||||
margin-bottom: 8px;
|
||||
font-size: 11px;
|
||||
font-weight: 400;
|
||||
color: @text-color-disabled;
|
||||
}
|
||||
}
|
||||
|
||||
&__file-list {
|
||||
.flex(column, flex-start);
|
||||
.flex(column, flex-start, stretch);
|
||||
gap: @spacing-sm;
|
||||
}
|
||||
|
||||
// 附件行:设计 42 实取底 #F7F8FA、圆角小卡、无描边
|
||||
&__file {
|
||||
.flex(row, space-between);
|
||||
gap: @spacing-base;
|
||||
padding: @spacing-sm @spacing-base;
|
||||
border: 1px solid @border-color;
|
||||
border-radius: @radius-base;
|
||||
background: @bg-color-light;
|
||||
align-items: center;
|
||||
width: fit-content;
|
||||
max-width: 100%;
|
||||
padding: 10px 14px; // 附件盒 13/15 × 0.77
|
||||
border: none;
|
||||
border-radius: 6px;
|
||||
background: @finance-row-bg;
|
||||
list-style: none;
|
||||
}
|
||||
|
||||
&__file-info {
|
||||
.flex(column, flex-start);
|
||||
gap: 2px;
|
||||
.flex(column, flex-start, flex-start);
|
||||
gap: 3px;
|
||||
min-width: 0;
|
||||
}
|
||||
|
||||
// 设计 42:文件名 12 → 11 / 700 / #1F2937
|
||||
&__file-name {
|
||||
font-size: @font-size-base;
|
||||
font-size: 11px;
|
||||
font-weight: 700;
|
||||
color: @heading-color;
|
||||
.ellipsis();
|
||||
}
|
||||
|
||||
// 设计 42:大小 12 → 11 / #9CA3AF
|
||||
&__file-meta {
|
||||
font-size: @font-size-sm;
|
||||
font-size: 11px;
|
||||
color: @text-color-disabled;
|
||||
}
|
||||
|
||||
&__file-actions {
|
||||
@@ -188,24 +217,40 @@ onMounted(load)
|
||||
}
|
||||
|
||||
&__file-btn {
|
||||
font-size: @font-size-sm;
|
||||
color: @primary-color;
|
||||
transition: opacity 0.2s;
|
||||
font-size: 11px;
|
||||
color: @text-color-secondary;
|
||||
transition: color 0.2s;
|
||||
|
||||
&:hover {
|
||||
opacity: 0.75;
|
||||
color: @primary-strong;
|
||||
}
|
||||
}
|
||||
|
||||
// 返回:设计 42 右下角 #024FFF 小按钮
|
||||
&__actions {
|
||||
.flex(row, flex-start);
|
||||
margin-top: @spacing-lg;
|
||||
.flex(row, flex-end);
|
||||
margin-top: 32px; // 附件→返回 43 × 0.77
|
||||
|
||||
.app-button {
|
||||
height: 24px; // 31 × 0.77
|
||||
padding: 0 16px;
|
||||
border-radius: 6px;
|
||||
background: @primary-strong;
|
||||
color: @white;
|
||||
font-size: 11px; // 13 → 可读下限 11
|
||||
font-weight: 500;
|
||||
|
||||
&:hover {
|
||||
background: @primary-strong;
|
||||
color: @white;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
&__empty {
|
||||
padding: @spacing-xxl 0;
|
||||
text-align: center;
|
||||
font-size: @font-size-base;
|
||||
font-size: 11px;
|
||||
}
|
||||
}
|
||||
</style>
|
||||
|
||||
@@ -55,73 +55,201 @@ onMounted(() => {
|
||||
<template>
|
||||
<div class="message">
|
||||
<header class="message__head">
|
||||
<div class="message__head-text">
|
||||
<h1 class="message__title">
|
||||
消息中心
|
||||
</h1>
|
||||
<p class="message__subtitle text-secondary">
|
||||
统一接收项目进度、售后工单、账单待办等站内消息,重要业务动态实时提醒
|
||||
</p>
|
||||
</div>
|
||||
<AppButton
|
||||
type="default"
|
||||
:disabled="unreadCount === 0"
|
||||
@click="onMarkAllRead"
|
||||
>
|
||||
全部已读
|
||||
</AppButton>
|
||||
<h1 class="message__title">
|
||||
消息中心
|
||||
</h1>
|
||||
</header>
|
||||
<p class="message__subtitle text-secondary">
|
||||
统一接收项目进度、售后工单、账单待办等站内消息,重要业务动态实时提醒
|
||||
</p>
|
||||
|
||||
<MessageTabs
|
||||
:active="query.type"
|
||||
:counts="tabCounts"
|
||||
@tab-change="onTabChange"
|
||||
/>
|
||||
<div class="message__body">
|
||||
<MessageTabs
|
||||
class="message__tabs"
|
||||
:active="query.type"
|
||||
:counts="tabCounts"
|
||||
@tab-change="onTabChange"
|
||||
/>
|
||||
|
||||
<FilterPanel
|
||||
v-model:keyword="keyword"
|
||||
keyword-placeholder="搜索消息标题、内容"
|
||||
@search="onSearch"
|
||||
@reset="onReset"
|
||||
/>
|
||||
<div class="message__main">
|
||||
<div class="message__toolbar">
|
||||
<FilterPanel
|
||||
class="message__filter"
|
||||
v-model:keyword="keyword"
|
||||
keyword-placeholder="搜索消息标题、内容"
|
||||
@search="onSearch"
|
||||
@reset="onReset"
|
||||
/>
|
||||
<AppButton
|
||||
class="message__mark-read"
|
||||
type="default"
|
||||
:disabled="unreadCount === 0"
|
||||
@click="onMarkAllRead"
|
||||
>
|
||||
全部已读
|
||||
</AppButton>
|
||||
</div>
|
||||
|
||||
<MessageList :messages="list" @view="onView" />
|
||||
<MessageList :messages="list" @view="onView" />
|
||||
|
||||
<PaginationBar
|
||||
:page="query.page"
|
||||
:page-size="query.pageSize"
|
||||
:total="total"
|
||||
@page-change="onPageChange"
|
||||
/>
|
||||
<PaginationBar
|
||||
class="message__pagination"
|
||||
:page="query.page"
|
||||
:page-size="query.pageSize"
|
||||
:total="total"
|
||||
@page-change="onPageChange"
|
||||
/>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<style lang="less" scoped>
|
||||
.message {
|
||||
.flex(column, flex-start);
|
||||
.flex(column, flex-start, stretch);
|
||||
gap: @spacing-base;
|
||||
padding-top: @spacing-xl;
|
||||
padding-bottom: @spacing-xxl;
|
||||
max-width: @container-width;
|
||||
margin: 0 auto;
|
||||
padding: @spacing-xl @spacing-base @spacing-xxl;
|
||||
|
||||
&__head {
|
||||
.flex(row, space-between);
|
||||
gap: @spacing-base;
|
||||
}
|
||||
|
||||
&__head-text {
|
||||
.flex(column, flex-start);
|
||||
gap: @spacing-xs;
|
||||
min-width: 0;
|
||||
.flex(row, flex-start);
|
||||
margin-bottom: -10px; // 标题→副标题净距 8 × 0.77(叠加父级 gap 16)
|
||||
}
|
||||
|
||||
// 设计 43:标题 22 × 0.77,700,#1F2937
|
||||
&__title {
|
||||
font-size: @font-size-xxl;
|
||||
font-weight: 600;
|
||||
font-size: 17px;
|
||||
font-weight: 700;
|
||||
color: @heading-color;
|
||||
}
|
||||
|
||||
// 设计 43:副标题整行居中,13 → 可读下限 11,#6B7280(text-secondary)
|
||||
&__subtitle {
|
||||
font-size: @font-size-base;
|
||||
text-align: center;
|
||||
font-size: 11px;
|
||||
}
|
||||
|
||||
&__body {
|
||||
.flex(row, flex-start);
|
||||
gap: 26px; // 左右栏间距 34 × 0.77
|
||||
align-items: flex-start;
|
||||
}
|
||||
|
||||
&__tabs {
|
||||
flex-shrink: 0;
|
||||
width: 156px; // 左分类卡宽 202 × 0.77
|
||||
}
|
||||
|
||||
&__main {
|
||||
.flex(column, flex-start, stretch);
|
||||
gap: 15px; // 卡片纵向间距 19 × 0.77
|
||||
flex: 1;
|
||||
min-width: 0;
|
||||
}
|
||||
|
||||
// 搜索行白卡:设计 43 x243..1897 / y370..435,输入与「全部已读」同卡
|
||||
&__toolbar {
|
||||
.flex(row, flex-start);
|
||||
align-items: center;
|
||||
gap: 11px;
|
||||
padding: 10px 17px; // 卡内边距 22/16 × 0.77
|
||||
border-radius: @radius-base;
|
||||
background: @white;
|
||||
}
|
||||
|
||||
& .message__filter {
|
||||
flex: 1;
|
||||
min-width: 0;
|
||||
padding: 0;
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
// 「全部已读」:设计 43 白底浅描边 12 → 11 / 500 #4B5563
|
||||
& .message__mark-read {
|
||||
flex-shrink: 0;
|
||||
height: 26px; // 34 × 0.77
|
||||
padding: 0 16px;
|
||||
border: 1px solid @border-color;
|
||||
border-radius: 6px;
|
||||
background: @white;
|
||||
color: @text-color;
|
||||
font-size: 11px;
|
||||
font-weight: 500;
|
||||
|
||||
&:hover:not(:disabled) {
|
||||
border-color: @primary-color;
|
||||
background: @white;
|
||||
color: @primary-color;
|
||||
}
|
||||
}
|
||||
|
||||
& .message__pagination {
|
||||
justify-content: flex-end;
|
||||
align-self: stretch;
|
||||
padding: 0;
|
||||
}
|
||||
|
||||
// FilterPanel 内部按设计 43 覆写(灰底输入框 / 灰重置 / 蓝搜索,重置在前)
|
||||
.message__filter {
|
||||
:deep(.filter-panel__bar) {
|
||||
gap: 6px;
|
||||
}
|
||||
|
||||
:deep(.filter-panel__body) {
|
||||
margin-top: 0;
|
||||
}
|
||||
|
||||
:deep(.filter-panel__input) {
|
||||
order: 0;
|
||||
flex: 0 1 349px; // 输入框宽 453 × 0.77
|
||||
max-width: 349px;
|
||||
height: 29px; // 38 × 0.77
|
||||
margin-right: 2px; // 叠加 bar gap 6 ≈ 输入→按钮 8 × 0.77
|
||||
padding: 0 10px;
|
||||
border: none;
|
||||
border-radius: 6px;
|
||||
background: @finance-field-bg; // 设计 43 实取 @input-bg
|
||||
color: @text-color;
|
||||
font-size: 11px; // 设计 13 → 可读下限 11
|
||||
|
||||
&::placeholder {
|
||||
color: @contract-placeholder; // 设计 43 实取 #B3B9C4
|
||||
}
|
||||
|
||||
&:focus {
|
||||
border: none;
|
||||
}
|
||||
}
|
||||
|
||||
:deep(.filter-panel__btn) {
|
||||
order: 1;
|
||||
min-width: 46px; // 重置 57 × 0.77
|
||||
height: 29px;
|
||||
padding: 0 12px;
|
||||
border: none;
|
||||
border-radius: 6px;
|
||||
background: @contract-reset-bg; // 设计 43 重置底 #EEF0F3
|
||||
color: @text-color;
|
||||
font-size: 11px;
|
||||
font-weight: 500;
|
||||
|
||||
&:hover {
|
||||
background: @contract-reset-bg;
|
||||
color: @text-color;
|
||||
}
|
||||
}
|
||||
|
||||
:deep(.filter-panel__btn--primary) {
|
||||
order: 2;
|
||||
background: @primary-strong; // 设计 43 搜索底 @primary-strong
|
||||
color: @white;
|
||||
|
||||
&:hover {
|
||||
background: @primary-strong;
|
||||
color: @white;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
</style>
|
||||
|
||||
@@ -15,6 +15,7 @@ import AboutPanel from './cpns/AboutPanel.vue'
|
||||
</template>
|
||||
|
||||
<style lang="less" scoped>
|
||||
// 设计 19(关于我们):面板内标题蓝条,正文各区块平铺
|
||||
.about-page {
|
||||
.flex(column, flex-start);
|
||||
gap: @spacing-base;
|
||||
@@ -22,16 +23,27 @@ import AboutPanel from './cpns/AboutPanel.vue'
|
||||
|
||||
&__head {
|
||||
width: 100%;
|
||||
padding: @spacing-base @spacing-xl;
|
||||
border-radius: @radius-lg;
|
||||
background: @white;
|
||||
box-shadow: @shadow-base;
|
||||
padding: 0;
|
||||
}
|
||||
|
||||
&__title {
|
||||
font-size: @font-size-lg;
|
||||
font-weight: 600;
|
||||
position: relative;
|
||||
padding-left: 12px;
|
||||
font-size: 12px; // 设计 15 → 12
|
||||
font-weight: 700;
|
||||
color: @heading-color;
|
||||
line-height: 20px;
|
||||
|
||||
&::before {
|
||||
content: '';
|
||||
position: absolute;
|
||||
left: 0;
|
||||
top: 3px;
|
||||
width: 3px;
|
||||
height: 14px;
|
||||
border-radius: 2px;
|
||||
background: @primary-strong;
|
||||
}
|
||||
}
|
||||
}
|
||||
</style>
|
||||
|
||||
@@ -83,10 +83,10 @@ onMounted(() => {
|
||||
</h3>
|
||||
<StatusTag v-if="address.isDefault" label="默认" variant="success" />
|
||||
</div>
|
||||
<ul class="address-card__meta text-secondary">
|
||||
<li>联系方式:{{ address.phone }}</li>
|
||||
<li>所在地区:{{ address.region }}</li>
|
||||
<li>详细地址:{{ address.detailAddress }}</li>
|
||||
<ul class="address-card__meta">
|
||||
<li><span>联系方式:</span>{{ address.phone }}</li>
|
||||
<li><span>所在地区:</span>{{ address.region }}</li>
|
||||
<li><span>详细地址:</span>{{ address.detailAddress }}</li>
|
||||
</ul>
|
||||
<div class="address-card__actions">
|
||||
<button
|
||||
@@ -143,6 +143,7 @@ onMounted(() => {
|
||||
</template>
|
||||
|
||||
<style lang="less" scoped>
|
||||
// 设计 20(地址管理):标题蓝条、整行白卡描边、字段标签灰/值深、白底描边小按钮、分页靠右
|
||||
.address-page {
|
||||
.flex(column, flex-start);
|
||||
gap: @spacing-base;
|
||||
@@ -151,21 +152,33 @@ onMounted(() => {
|
||||
&__head {
|
||||
.flex(row, space-between, center);
|
||||
width: 100%;
|
||||
padding: @spacing-base @spacing-xl;
|
||||
border-radius: @radius-lg;
|
||||
background: @white;
|
||||
box-shadow: @shadow-base;
|
||||
padding: 0;
|
||||
}
|
||||
|
||||
&__title {
|
||||
font-size: @font-size-lg;
|
||||
font-weight: 600;
|
||||
position: relative;
|
||||
padding-left: 12px;
|
||||
font-size: 12px; // 设计 15 → 12
|
||||
font-weight: 700;
|
||||
color: @heading-color;
|
||||
line-height: 20px;
|
||||
|
||||
&::before {
|
||||
content: '';
|
||||
position: absolute;
|
||||
left: 0;
|
||||
top: 3px;
|
||||
width: 3px;
|
||||
height: 14px;
|
||||
border-radius: 2px;
|
||||
background: @primary-strong;
|
||||
}
|
||||
}
|
||||
|
||||
// 设计 20:列表整行铺满(单列),分页靠右
|
||||
&__grid {
|
||||
display: grid;
|
||||
grid-template-columns: repeat(2, 1fr);
|
||||
grid-template-columns: 1fr;
|
||||
gap: @spacing-base;
|
||||
width: 100%;
|
||||
}
|
||||
@@ -174,66 +187,133 @@ onMounted(() => {
|
||||
grid-column: 1 / -1;
|
||||
padding: @spacing-xxl 0;
|
||||
text-align: center;
|
||||
font-size: @font-size-base;
|
||||
font-size: 11px;
|
||||
}
|
||||
|
||||
:deep(.pagination) {
|
||||
justify-content: flex-end;
|
||||
padding: 0;
|
||||
}
|
||||
|
||||
:deep(.pagination__btn.is-active) {
|
||||
border-color: @profile-page-active-bg;
|
||||
background: @profile-page-active-bg;
|
||||
color: @primary-strong;
|
||||
}
|
||||
|
||||
// 顶部「+ 新增地址」:小号蓝底按钮(设计 20 实取 #024FFF)
|
||||
.app-button--primary {
|
||||
height: 24px;
|
||||
padding: 0 10px;
|
||||
border: none;
|
||||
border-radius: @profile-radius;
|
||||
background: @primary-strong;
|
||||
color: @white;
|
||||
font-size: 11px;
|
||||
font-weight: 500;
|
||||
|
||||
&:hover {
|
||||
border: none;
|
||||
background: darken(@primary-strong, 6%);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
.address-card {
|
||||
.flex(column, flex-start);
|
||||
gap: @spacing-sm;
|
||||
padding: @spacing-base @spacing-lg;
|
||||
border-radius: @radius-lg;
|
||||
.flex(row, flex-start, center);
|
||||
gap: @spacing-lg;
|
||||
padding: @spacing-base;
|
||||
border: 1px solid @profile-card-border;
|
||||
border-radius: @radius-base;
|
||||
background: @white;
|
||||
box-shadow: @shadow-base;
|
||||
|
||||
&__head {
|
||||
.flex(row, space-between, center);
|
||||
gap: @spacing-sm;
|
||||
.flex(row, flex-start, center);
|
||||
gap: @spacing-xs;
|
||||
flex-shrink: 0;
|
||||
flex-direction: column-reverse; // 设计 20:「默认」标签在上、姓名在下
|
||||
align-items: flex-start;
|
||||
}
|
||||
|
||||
// 设计 20:字段值 13 设计px w600 深灰
|
||||
&__name {
|
||||
font-size: @font-size-lg;
|
||||
font-size: 11px;
|
||||
font-weight: 600;
|
||||
color: @heading-color;
|
||||
}
|
||||
|
||||
// 设计 20:标签 11 设计px 灰、值 13 设计px w600 深;整行横向排布
|
||||
&__meta {
|
||||
.flex(column, flex-start);
|
||||
gap: @spacing-xs;
|
||||
.flex(row, flex-start);
|
||||
gap: @spacing-xl;
|
||||
flex: 1;
|
||||
min-width: 0;
|
||||
list-style: none;
|
||||
font-size: @font-size-base;
|
||||
font-size: 11px;
|
||||
|
||||
li {
|
||||
flex: 1;
|
||||
min-width: 0;
|
||||
color: @heading-color;
|
||||
font-weight: 600;
|
||||
|
||||
.ellipsis();
|
||||
}
|
||||
|
||||
span {
|
||||
display: block;
|
||||
margin-bottom: @spacing-xs;
|
||||
color: @text-color-secondary;
|
||||
font-weight: 400;
|
||||
}
|
||||
}
|
||||
|
||||
&__actions {
|
||||
.flex(row, center);
|
||||
gap: @spacing-base;
|
||||
margin-top: auto;
|
||||
padding-top: @spacing-sm;
|
||||
border-top: 1px solid @border-color;
|
||||
width: 100%;
|
||||
gap: @spacing-sm;
|
||||
flex-shrink: 0;
|
||||
width: auto;
|
||||
margin-top: 0;
|
||||
padding-top: 0;
|
||||
border-top: none;
|
||||
}
|
||||
|
||||
// 设计 20:操作按钮 = 白底灰描边、12 设计px w500 灰字
|
||||
&__btn {
|
||||
font-size: @font-size-base;
|
||||
color: @primary-color;
|
||||
transition: opacity 0.2s;
|
||||
height: 24px;
|
||||
padding: 0 10px;
|
||||
border: 1px solid @profile-line;
|
||||
border-radius: @profile-radius;
|
||||
background: @white;
|
||||
color: @text-color;
|
||||
font-size: 11px;
|
||||
font-weight: 500;
|
||||
transition: all 0.2s;
|
||||
|
||||
&:hover:not(:disabled) {
|
||||
opacity: 0.75;
|
||||
border-color: @primary-strong;
|
||||
color: @primary-strong;
|
||||
opacity: 1;
|
||||
}
|
||||
|
||||
&--muted {
|
||||
color: @text-color-disabled;
|
||||
color: @text-color;
|
||||
cursor: not-allowed;
|
||||
opacity: 0.6;
|
||||
}
|
||||
|
||||
&--danger {
|
||||
color: @danger-color;
|
||||
color: @text-color;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// 「默认」标签:设计 20 实取蓝底 #024FFF 白字
|
||||
.address-card .status-tag {
|
||||
padding: 2px 8px;
|
||||
background: @primary-strong;
|
||||
color: @white;
|
||||
font-size: 11px;
|
||||
font-weight: 500;
|
||||
}
|
||||
</style>
|
||||
|
||||
@@ -82,35 +82,36 @@ const advantages = [
|
||||
</template>
|
||||
|
||||
<style lang="less" scoped>
|
||||
// 设计 19(关于我们):区块标题 14 设计px w700、正文 13 设计px 灰、平铺无卡片底
|
||||
.about-panel {
|
||||
.flex(column, flex-start);
|
||||
gap: @spacing-base;
|
||||
gap: @spacing-lg;
|
||||
|
||||
&__section {
|
||||
.flex(column, flex-start);
|
||||
gap: @spacing-sm;
|
||||
padding: @spacing-lg @spacing-xl;
|
||||
border-radius: @radius-lg;
|
||||
background: @white;
|
||||
box-shadow: @shadow-base;
|
||||
padding: 0;
|
||||
background: transparent;
|
||||
box-shadow: none;
|
||||
}
|
||||
|
||||
&__title {
|
||||
font-size: @font-size-lg;
|
||||
font-weight: 600;
|
||||
font-size: 11px; // 设计 14 → 11
|
||||
font-weight: 700;
|
||||
color: @heading-color;
|
||||
}
|
||||
|
||||
&__text {
|
||||
font-size: @font-size-base;
|
||||
font-size: 11px;
|
||||
color: @text-color;
|
||||
line-height: 1.8;
|
||||
line-height: 1.9;
|
||||
}
|
||||
|
||||
// 设计 19:优势项为「标题 + 描述」同排平铺,标题亦为灰色加粗
|
||||
&__advantages {
|
||||
display: grid;
|
||||
grid-template-columns: repeat(2, 1fr);
|
||||
gap: @spacing-base;
|
||||
grid-template-columns: 1fr;
|
||||
gap: @spacing-sm;
|
||||
width: 100%;
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
@@ -118,21 +119,22 @@ const advantages = [
|
||||
}
|
||||
|
||||
&__advantage {
|
||||
.flex(column, flex-start);
|
||||
gap: @spacing-xs;
|
||||
padding: @spacing-base;
|
||||
border-radius: @radius-base;
|
||||
background: @bg-color-light;
|
||||
.flex(row, flex-start);
|
||||
gap: @spacing-sm;
|
||||
padding: 0;
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
&__advantage-title {
|
||||
font-size: @font-size-base;
|
||||
font-weight: 600;
|
||||
color: @primary-color;
|
||||
flex-shrink: 0;
|
||||
font-size: 11px;
|
||||
font-weight: 700;
|
||||
color: @text-color;
|
||||
}
|
||||
|
||||
&__advantage-desc {
|
||||
font-size: @font-size-sm;
|
||||
font-size: 11px;
|
||||
color: @text-color;
|
||||
line-height: 1.7;
|
||||
}
|
||||
|
||||
@@ -142,18 +144,19 @@ const advantages = [
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
list-style: none;
|
||||
font-size: @font-size-base;
|
||||
font-size: 11px;
|
||||
color: @text-color;
|
||||
|
||||
span {
|
||||
color: @text-color-secondary;
|
||||
color: @text-color;
|
||||
}
|
||||
}
|
||||
|
||||
&__link {
|
||||
color: @primary-color;
|
||||
color: @text-color;
|
||||
|
||||
&:hover {
|
||||
color: @primary-strong;
|
||||
text-decoration: underline;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -123,28 +123,47 @@ function onSave(): void {
|
||||
</template>
|
||||
|
||||
<style lang="less" scoped>
|
||||
// 与个人中心其它弹窗同规格(设计 22~27):白卡 700px、蓝条标题、白底描边输入、等宽双按钮
|
||||
.address-dialog {
|
||||
position: fixed;
|
||||
inset: 0;
|
||||
z-index: 1000;
|
||||
.flex(row, center);
|
||||
background: rgba(0, 0, 0, 0.45);
|
||||
background: transparent;
|
||||
overflow-y: auto;
|
||||
|
||||
&__panel {
|
||||
width: 480px;
|
||||
width: 700px;
|
||||
max-width: calc(100vw - 32px);
|
||||
padding: @spacing-lg;
|
||||
max-height: calc(100vh - 48px);
|
||||
overflow-y: auto;
|
||||
padding: @spacing-base;
|
||||
border-radius: @radius-lg;
|
||||
background: @white;
|
||||
box-shadow: @shadow-lg;
|
||||
.flex(column, flex-start);
|
||||
gap: @spacing-base;
|
||||
.scrollbar();
|
||||
}
|
||||
|
||||
&__title {
|
||||
font-size: @font-size-lg;
|
||||
font-weight: 600;
|
||||
position: relative;
|
||||
padding-left: 12px;
|
||||
font-size: 12px;
|
||||
font-weight: 700;
|
||||
color: @heading-color;
|
||||
line-height: 20px;
|
||||
|
||||
&::before {
|
||||
content: '';
|
||||
position: absolute;
|
||||
left: 0;
|
||||
top: 3px;
|
||||
width: 3px;
|
||||
height: 14px;
|
||||
border-radius: 2px;
|
||||
background: @primary-strong;
|
||||
}
|
||||
}
|
||||
|
||||
&__field {
|
||||
@@ -154,41 +173,77 @@ function onSave(): void {
|
||||
}
|
||||
|
||||
&__label {
|
||||
font-size: @font-size-base;
|
||||
font-size: 11px;
|
||||
font-weight: 500;
|
||||
color: @heading-color;
|
||||
}
|
||||
|
||||
&__input,
|
||||
&__textarea {
|
||||
width: 100%;
|
||||
padding: 0 @spacing-base;
|
||||
border: 1px solid @border-color;
|
||||
border-radius: @radius-base;
|
||||
background: @bg-color-light;
|
||||
font-size: @font-size-base;
|
||||
padding: 0 12px;
|
||||
border: 1px solid @profile-input-border;
|
||||
border-radius: @profile-radius;
|
||||
background: @white;
|
||||
font-size: 11px;
|
||||
color: @text-color;
|
||||
outline: none;
|
||||
transition: border-color 0.2s;
|
||||
box-sizing: border-box;
|
||||
|
||||
&:focus {
|
||||
border-color: @primary-color;
|
||||
border-color: @primary-strong;
|
||||
}
|
||||
|
||||
&::placeholder {
|
||||
color: @heading-color;
|
||||
}
|
||||
}
|
||||
|
||||
&__input {
|
||||
height: 40px;
|
||||
height: 32px;
|
||||
}
|
||||
|
||||
&__textarea {
|
||||
padding: @spacing-sm @spacing-base;
|
||||
padding: 8px 12px;
|
||||
line-height: 1.6;
|
||||
resize: vertical;
|
||||
}
|
||||
|
||||
&__footer {
|
||||
.flex(row, flex-end);
|
||||
.flex(row, flex-start);
|
||||
gap: @spacing-sm;
|
||||
width: 100%;
|
||||
}
|
||||
|
||||
.app-button {
|
||||
flex: 1;
|
||||
height: 36px;
|
||||
font-size: 12px;
|
||||
font-weight: 500;
|
||||
border-radius: @profile-radius;
|
||||
}
|
||||
|
||||
.app-button--primary {
|
||||
border-color: @primary-strong;
|
||||
background: @primary-strong;
|
||||
|
||||
&:hover {
|
||||
border-color: darken(@primary-strong, 6%);
|
||||
background: darken(@primary-strong, 6%);
|
||||
}
|
||||
}
|
||||
|
||||
.app-button--default {
|
||||
border: none;
|
||||
background: @profile-quiet-btn;
|
||||
color: @text-color;
|
||||
|
||||
&:hover {
|
||||
border: none;
|
||||
background: darken(@profile-quiet-btn, 4%);
|
||||
color: @text-color;
|
||||
}
|
||||
}
|
||||
}
|
||||
</style>
|
||||
|
||||
@@ -132,7 +132,7 @@ function onSubmit(): void {
|
||||
|
||||
<label v-if="!isIdentity" class="bind-dialog__agree">
|
||||
<input v-model="agree" type="checkbox">
|
||||
<span>我已阅读并同意《用户协议》和《隐私政策》</span>
|
||||
<span>我已阅读并同意<em>《用户协议》</em>和<em>《隐私政策》</em></span>
|
||||
</label>
|
||||
|
||||
<div class="bind-dialog__footer">
|
||||
@@ -149,35 +149,68 @@ function onSubmit(): void {
|
||||
</template>
|
||||
|
||||
<style lang="less" scoped>
|
||||
// 设计 23~27(绑定/换绑/身份验证弹窗):与修改密码弹窗同规格 —— 白卡 700px、蓝条标题、
|
||||
// 白底描边输入、底部等宽双按钮;设计稿无蒙层压暗,遮罩透明。
|
||||
.bind-dialog {
|
||||
position: fixed;
|
||||
inset: 0;
|
||||
z-index: 1000;
|
||||
.flex(row, center);
|
||||
background: rgba(0, 0, 0, 0.45);
|
||||
background: transparent;
|
||||
overflow-y: auto;
|
||||
|
||||
&__panel {
|
||||
width: 440px;
|
||||
width: 700px; // 设计 900 × 0.77
|
||||
max-width: calc(100vw - 32px);
|
||||
padding: @spacing-lg;
|
||||
max-height: calc(100vh - 48px);
|
||||
overflow-y: auto;
|
||||
padding: @spacing-base;
|
||||
border-radius: @radius-lg;
|
||||
background: @white;
|
||||
box-shadow: @shadow-lg;
|
||||
.flex(column, flex-start);
|
||||
gap: @spacing-base;
|
||||
.scrollbar();
|
||||
}
|
||||
|
||||
// 设计 22~26:蓝条 + 标题 15 设计px w700 深灰
|
||||
&__title {
|
||||
font-size: @font-size-lg;
|
||||
font-weight: 600;
|
||||
position: relative;
|
||||
padding-left: 12px;
|
||||
font-size: 12px;
|
||||
font-weight: 700;
|
||||
color: @heading-color;
|
||||
line-height: 20px;
|
||||
|
||||
&::before {
|
||||
content: '';
|
||||
position: absolute;
|
||||
left: 0;
|
||||
top: 3px;
|
||||
width: 3px;
|
||||
height: 14px;
|
||||
border-radius: 2px;
|
||||
background: @primary-strong;
|
||||
}
|
||||
}
|
||||
|
||||
// 设计 23:身份验证标题为纯蓝字 14 设计px(无蓝条)
|
||||
&__title:has(+ .bind-dialog__desc) {
|
||||
padding-left: 0;
|
||||
font-size: 11px;
|
||||
color: @primary-strong;
|
||||
|
||||
&::before {
|
||||
display: none;
|
||||
}
|
||||
}
|
||||
|
||||
// 设计 23:说明为纯灰字(非底色块)
|
||||
&__desc {
|
||||
padding: @spacing-sm @spacing-base;
|
||||
border-radius: @radius-base;
|
||||
background: @bg-color-light;
|
||||
font-size: @font-size-sm;
|
||||
padding: 0;
|
||||
background: transparent;
|
||||
color: @text-color-secondary;
|
||||
font-size: 11px;
|
||||
line-height: 1.6;
|
||||
}
|
||||
|
||||
@@ -188,42 +221,85 @@ function onSubmit(): void {
|
||||
}
|
||||
|
||||
&__label {
|
||||
font-size: @font-size-base;
|
||||
font-size: 11px;
|
||||
font-weight: 500;
|
||||
color: @heading-color;
|
||||
}
|
||||
|
||||
&__input {
|
||||
width: 100%;
|
||||
height: 40px;
|
||||
padding: 0 @spacing-base;
|
||||
border: 1px solid @border-color;
|
||||
border-radius: @radius-base;
|
||||
background: @bg-color-light;
|
||||
font-size: @font-size-base;
|
||||
height: 32px;
|
||||
padding: 0 12px;
|
||||
border: 1px solid @profile-input-border;
|
||||
border-radius: @profile-radius;
|
||||
background: @white;
|
||||
font-size: 11px;
|
||||
color: @text-color;
|
||||
outline: none;
|
||||
transition: border-color 0.2s;
|
||||
box-sizing: border-box;
|
||||
|
||||
&:focus {
|
||||
border-color: @primary-color;
|
||||
border-color: @primary-strong;
|
||||
}
|
||||
|
||||
&::placeholder {
|
||||
color: @heading-color;
|
||||
}
|
||||
}
|
||||
|
||||
&__agree {
|
||||
.flex(row, flex-start, center);
|
||||
gap: @spacing-sm;
|
||||
font-size: @font-size-sm;
|
||||
color: @text-color;
|
||||
font-size: 11px;
|
||||
color: @text-color-secondary;
|
||||
cursor: pointer;
|
||||
|
||||
input {
|
||||
accent-color: @primary-color;
|
||||
accent-color: @primary-strong;
|
||||
}
|
||||
|
||||
em {
|
||||
font-style: normal;
|
||||
color: @primary-strong;
|
||||
}
|
||||
}
|
||||
|
||||
// 设计 24/25/26:底部等宽双按钮,次级 #EEF0F3、主色 #024FFF
|
||||
&__footer {
|
||||
.flex(row, flex-end);
|
||||
.flex(row, flex-start);
|
||||
gap: @spacing-sm;
|
||||
width: 100%;
|
||||
}
|
||||
|
||||
.app-button {
|
||||
flex: 1;
|
||||
height: 36px;
|
||||
font-size: 12px;
|
||||
font-weight: 500;
|
||||
border-radius: @profile-radius;
|
||||
}
|
||||
|
||||
.app-button--primary {
|
||||
border-color: @primary-strong;
|
||||
background: @primary-strong;
|
||||
|
||||
&:hover {
|
||||
border-color: darken(@primary-strong, 6%);
|
||||
background: darken(@primary-strong, 6%);
|
||||
}
|
||||
}
|
||||
|
||||
.app-button--default {
|
||||
border: none;
|
||||
background: @profile-quiet-btn;
|
||||
color: @text-color;
|
||||
|
||||
&:hover {
|
||||
border: none;
|
||||
background: darken(@profile-quiet-btn, 4%);
|
||||
color: @text-color;
|
||||
}
|
||||
}
|
||||
}
|
||||
</style>
|
||||
|
||||
@@ -103,7 +103,7 @@ function onSubmit(): void {
|
||||
|
||||
<label class="change-pwd-dialog__agree">
|
||||
<input v-model="agree" type="checkbox">
|
||||
<span>我已阅读并同意《用户协议》和《隐私政策》</span>
|
||||
<span>我已阅读并同意<em>《用户协议》</em>和<em>《隐私政策》</em></span>
|
||||
</label>
|
||||
|
||||
<div class="change-pwd-dialog__footer">
|
||||
@@ -120,28 +120,49 @@ function onSubmit(): void {
|
||||
</template>
|
||||
|
||||
<style lang="less" scoped>
|
||||
// 设计 22(修改密码弹窗):白卡 900×~540 设计px、蓝条标题、白底描边输入 40 设计px、
|
||||
// 整行蓝色主按钮;设计稿无蒙层压暗(页面原样可见),故遮罩透明。
|
||||
.change-pwd-dialog {
|
||||
position: fixed;
|
||||
inset: 0;
|
||||
z-index: 1000;
|
||||
.flex(row, center);
|
||||
background: rgba(0, 0, 0, 0.45);
|
||||
background: transparent;
|
||||
overflow-y: auto;
|
||||
|
||||
&__panel {
|
||||
width: 440px;
|
||||
width: 700px; // 设计 900 × 0.77
|
||||
max-width: calc(100vw - 32px);
|
||||
padding: @spacing-lg;
|
||||
max-height: calc(100vh - 48px);
|
||||
overflow-y: auto;
|
||||
padding: @spacing-base;
|
||||
border-radius: @radius-lg;
|
||||
background: @white;
|
||||
box-shadow: @shadow-lg;
|
||||
.flex(column, flex-start);
|
||||
gap: @spacing-base;
|
||||
.scrollbar();
|
||||
}
|
||||
|
||||
// 设计 22:蓝条(#024FFF 4×20 设计px)+ 标题 15 设计px w700
|
||||
&__title {
|
||||
font-size: @font-size-lg;
|
||||
font-weight: 600;
|
||||
position: relative;
|
||||
padding-left: 12px;
|
||||
font-size: 12px;
|
||||
font-weight: 700;
|
||||
color: @heading-color;
|
||||
line-height: 20px;
|
||||
|
||||
&::before {
|
||||
content: '';
|
||||
position: absolute;
|
||||
left: 0;
|
||||
top: 3px;
|
||||
width: 3px;
|
||||
height: 14px;
|
||||
border-radius: 2px;
|
||||
background: @primary-strong;
|
||||
}
|
||||
}
|
||||
|
||||
&__field {
|
||||
@@ -150,28 +171,37 @@ function onSubmit(): void {
|
||||
width: 100%;
|
||||
}
|
||||
|
||||
// 设计 22:标签 13 设计px w500 深灰
|
||||
&__label {
|
||||
font-size: @font-size-base;
|
||||
font-size: 11px;
|
||||
font-weight: 500;
|
||||
color: @heading-color;
|
||||
}
|
||||
|
||||
// 设计 22:白底、#DDE1E7 描边、40 设计px ≈ 32px 高、13 设计px 字
|
||||
&__input {
|
||||
width: 100%;
|
||||
height: 40px;
|
||||
padding: 0 @spacing-base;
|
||||
border: 1px solid @border-color;
|
||||
border-radius: @radius-base;
|
||||
background: @bg-color-light;
|
||||
font-size: @font-size-base;
|
||||
height: 32px;
|
||||
padding: 0 12px;
|
||||
border: 1px solid @profile-input-border;
|
||||
border-radius: @profile-radius;
|
||||
background: @white;
|
||||
font-size: 11px;
|
||||
color: @text-color;
|
||||
outline: none;
|
||||
transition: border-color 0.2s;
|
||||
box-sizing: border-box;
|
||||
|
||||
&:focus {
|
||||
border-color: @primary-color;
|
||||
border-color: @primary-strong;
|
||||
}
|
||||
|
||||
&::placeholder {
|
||||
color: @heading-color;
|
||||
}
|
||||
|
||||
&:read-only {
|
||||
color: @text-color-secondary;
|
||||
color: @text-color;
|
||||
cursor: not-allowed;
|
||||
}
|
||||
}
|
||||
@@ -179,19 +209,55 @@ function onSubmit(): void {
|
||||
&__agree {
|
||||
.flex(row, flex-start, center);
|
||||
gap: @spacing-sm;
|
||||
font-size: @font-size-sm;
|
||||
color: @text-color;
|
||||
font-size: 11px;
|
||||
color: @text-color-secondary;
|
||||
cursor: pointer;
|
||||
|
||||
input {
|
||||
accent-color: @primary-color;
|
||||
accent-color: @primary-strong;
|
||||
}
|
||||
|
||||
em {
|
||||
font-style: normal;
|
||||
color: @primary-strong;
|
||||
}
|
||||
}
|
||||
|
||||
// 设计 24:底部两枚等宽整行按钮 —— 次级 #EEF0F3 灰底、主色 #024FFF
|
||||
&__footer {
|
||||
.flex(row, flex-end);
|
||||
.flex(row, flex-start);
|
||||
gap: @spacing-sm;
|
||||
width: 100%;
|
||||
}
|
||||
|
||||
.app-button {
|
||||
flex: 1;
|
||||
height: 36px;
|
||||
font-size: 12px;
|
||||
font-weight: 500;
|
||||
border-radius: @profile-radius;
|
||||
}
|
||||
|
||||
.app-button--primary {
|
||||
border-color: @primary-strong;
|
||||
background: @primary-strong;
|
||||
|
||||
&:hover {
|
||||
border-color: darken(@primary-strong, 6%);
|
||||
background: darken(@primary-strong, 6%);
|
||||
}
|
||||
}
|
||||
|
||||
.app-button--default {
|
||||
border: none;
|
||||
background: @profile-quiet-btn;
|
||||
color: @text-color;
|
||||
|
||||
&:hover {
|
||||
border: none;
|
||||
background: darken(@profile-quiet-btn, 4%);
|
||||
color: @text-color;
|
||||
}
|
||||
}
|
||||
}
|
||||
</style>
|
||||
|
||||
@@ -114,13 +114,14 @@ function onReset(): void {
|
||||
</template>
|
||||
|
||||
<style lang="less" scoped>
|
||||
// 设计 18(意见反馈表单):表单直接铺在白面板上(无内嵌卡)、标签 13 设计px w500、
|
||||
// 白底 #DDE1E7 描边输入、计数灰字、附件区白底描边
|
||||
.feedback-form {
|
||||
.flex(column, flex-start);
|
||||
gap: @spacing-base;
|
||||
padding: @spacing-lg @spacing-xl;
|
||||
border-radius: @radius-lg;
|
||||
background: @white;
|
||||
box-shadow: @shadow-base;
|
||||
padding: 0;
|
||||
background: transparent;
|
||||
box-shadow: none;
|
||||
|
||||
&__field {
|
||||
.flex(column, flex-start);
|
||||
@@ -129,7 +130,8 @@ function onReset(): void {
|
||||
}
|
||||
|
||||
&__label {
|
||||
font-size: @font-size-base;
|
||||
font-size: 11px;
|
||||
font-weight: 500;
|
||||
color: @heading-color;
|
||||
}
|
||||
|
||||
@@ -138,52 +140,51 @@ function onReset(): void {
|
||||
color: @danger-color;
|
||||
}
|
||||
|
||||
&__input {
|
||||
&__input,
|
||||
&__textarea {
|
||||
width: 100%;
|
||||
height: 40px;
|
||||
padding: 0 @spacing-base;
|
||||
border: 1px solid @border-color;
|
||||
border-radius: @radius-base;
|
||||
background: @bg-color-light;
|
||||
font-size: @font-size-base;
|
||||
padding: 0 12px;
|
||||
border: 1px solid @profile-input-border;
|
||||
border-radius: @profile-radius;
|
||||
background: @white;
|
||||
font-size: 11px;
|
||||
color: @text-color;
|
||||
outline: none;
|
||||
transition: border-color 0.2s;
|
||||
box-sizing: border-box;
|
||||
|
||||
&:focus {
|
||||
border-color: @primary-color;
|
||||
border-color: @primary-strong;
|
||||
}
|
||||
|
||||
&::placeholder {
|
||||
color: @heading-color;
|
||||
}
|
||||
}
|
||||
|
||||
&__input {
|
||||
height: 32px; // 设计 40 × 0.77
|
||||
}
|
||||
|
||||
&__textarea {
|
||||
width: 100%;
|
||||
padding: @spacing-sm @spacing-base;
|
||||
border: 1px solid @border-color;
|
||||
border-radius: @radius-base;
|
||||
background: @bg-color-light;
|
||||
font-size: @font-size-base;
|
||||
padding: 8px 12px;
|
||||
line-height: 1.6;
|
||||
outline: none;
|
||||
transition: border-color 0.2s;
|
||||
resize: vertical;
|
||||
box-sizing: border-box;
|
||||
|
||||
&:focus {
|
||||
border-color: @primary-color;
|
||||
}
|
||||
}
|
||||
|
||||
// 设计 18:字数统计 11 设计px 灰字
|
||||
&__counter {
|
||||
align-self: flex-end;
|
||||
font-size: @font-size-sm;
|
||||
color: @text-color-disabled;
|
||||
font-size: 11px;
|
||||
}
|
||||
|
||||
&__tip {
|
||||
padding: @spacing-sm @spacing-base;
|
||||
border-radius: @radius-base;
|
||||
border-radius: @profile-radius;
|
||||
background: @primary-light;
|
||||
color: @primary-color;
|
||||
font-size: @font-size-sm;
|
||||
color: @primary-strong;
|
||||
font-size: 11px;
|
||||
line-height: 1.6;
|
||||
}
|
||||
|
||||
@@ -191,5 +192,40 @@ function onReset(): void {
|
||||
.flex(row, flex-start);
|
||||
gap: @spacing-sm;
|
||||
}
|
||||
|
||||
// 附件区:设计 18 白底 + #DDE1E7 描边
|
||||
:deep(.upload-area) {
|
||||
min-height: 56px;
|
||||
border: 1px solid @profile-input-border;
|
||||
background: @white;
|
||||
|
||||
&:hover,
|
||||
&.is-dragging {
|
||||
background: @bg-color-light;
|
||||
}
|
||||
}
|
||||
|
||||
:deep(.upload-area__hint) {
|
||||
color: @text-color-disabled;
|
||||
font-size: 11px;
|
||||
}
|
||||
|
||||
.app-button {
|
||||
height: 32px;
|
||||
padding: 0 16px;
|
||||
border-radius: @profile-radius;
|
||||
font-size: 12px;
|
||||
font-weight: 500;
|
||||
}
|
||||
|
||||
.app-button--primary {
|
||||
border-color: @primary-strong;
|
||||
background: @primary-strong;
|
||||
|
||||
&:hover {
|
||||
border-color: darken(@primary-strong, 6%);
|
||||
background: darken(@primary-strong, 6%);
|
||||
}
|
||||
}
|
||||
}
|
||||
</style>
|
||||
|
||||
@@ -42,26 +42,25 @@ defineProps<Props>()
|
||||
</template>
|
||||
|
||||
<style lang="less" scoped>
|
||||
// 设计 16(帮助中心 FAQ):分类标题居中 14 设计px w700、Q 加粗深灰、A 13 设计px 灰,
|
||||
// 无卡片底色/描边,平铺在面板上
|
||||
.help-faq {
|
||||
.flex(column, flex-start);
|
||||
gap: @spacing-base;
|
||||
|
||||
&__group {
|
||||
border-radius: @radius-lg;
|
||||
background: @white;
|
||||
box-shadow: @shadow-base;
|
||||
overflow: hidden;
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
&__summary {
|
||||
.flex(row, flex-start, center);
|
||||
padding: @spacing-base @spacing-xl;
|
||||
font-size: @font-size-lg;
|
||||
font-weight: 600;
|
||||
.flex(row, center, center);
|
||||
justify-content: center;
|
||||
padding: 0;
|
||||
font-size: 11px; // 设计 14 → 11
|
||||
font-weight: 700;
|
||||
color: @heading-color;
|
||||
cursor: pointer;
|
||||
list-style: none;
|
||||
transition: background 0.2s;
|
||||
user-select: none;
|
||||
|
||||
&::-webkit-details-marker {
|
||||
@@ -69,52 +68,46 @@ defineProps<Props>()
|
||||
}
|
||||
|
||||
&::after {
|
||||
content: '▾';
|
||||
margin-left: auto;
|
||||
font-size: @font-size-base;
|
||||
color: @text-color-secondary;
|
||||
transition: transform 0.2s;
|
||||
content: none;
|
||||
}
|
||||
|
||||
&:hover {
|
||||
background: @bg-color-light;
|
||||
background: transparent;
|
||||
color: @primary-strong;
|
||||
}
|
||||
}
|
||||
|
||||
&__group[open] > .help-faq__summary::after {
|
||||
transform: rotate(180deg);
|
||||
}
|
||||
|
||||
&__list {
|
||||
.flex(column, flex-start);
|
||||
gap: @spacing-base;
|
||||
gap: 6px;
|
||||
margin: 0;
|
||||
padding: 0 @spacing-xl @spacing-lg;
|
||||
padding: @spacing-sm 0 0;
|
||||
list-style: none;
|
||||
border-top: 1px solid @border-color;
|
||||
border-top: none;
|
||||
}
|
||||
|
||||
&__item {
|
||||
.flex(column, flex-start);
|
||||
gap: @spacing-xs;
|
||||
padding-top: @spacing-base;
|
||||
padding-top: 0;
|
||||
}
|
||||
|
||||
&__q {
|
||||
font-size: @font-size-base;
|
||||
font-weight: 600;
|
||||
font-size: 11px;
|
||||
font-weight: 700;
|
||||
color: @heading-color;
|
||||
}
|
||||
|
||||
&__a {
|
||||
font-size: @font-size-base;
|
||||
font-size: 11px;
|
||||
color: @text-color;
|
||||
line-height: 1.7;
|
||||
}
|
||||
|
||||
&__empty {
|
||||
padding: @spacing-xxl 0;
|
||||
text-align: center;
|
||||
font-size: @font-size-base;
|
||||
font-size: 11px;
|
||||
}
|
||||
}
|
||||
</style>
|
||||
|
||||
@@ -22,42 +22,65 @@ const WORK_TIME = '工作日 8:00-12:00 14:00-18:00'
|
||||
</template>
|
||||
|
||||
<style lang="less" scoped>
|
||||
// 设计 14(专属客服热线):面板内整行浅蓝卡(#D6E4FB)、蓝色圆形图标、
|
||||
// 标题 19 设计px w700、号码 24 设计px 蓝色 w700、时间 12 设计px 灰
|
||||
.hotline-panel {
|
||||
.flex(row, center);
|
||||
padding: @spacing-xxl 0;
|
||||
.flex(row, flex-start);
|
||||
padding: 0;
|
||||
|
||||
&__card {
|
||||
.flex(column, center);
|
||||
gap: @spacing-base;
|
||||
width: 480px;
|
||||
display: grid;
|
||||
grid-template-columns: auto 1fr;
|
||||
grid-template-areas:
|
||||
'icon title'
|
||||
'icon number'
|
||||
'icon time';
|
||||
column-gap: @spacing-base;
|
||||
align-content: center;
|
||||
width: 100%;
|
||||
max-width: 100%;
|
||||
padding: @spacing-xxl @spacing-xl;
|
||||
border-radius: @radius-lg;
|
||||
background: @white;
|
||||
box-shadow: @shadow-lg;
|
||||
text-align: center;
|
||||
padding: @spacing-lg;
|
||||
border-radius: @radius-base;
|
||||
background: @profile-hotline-bg;
|
||||
text-align: left;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
// 设计 14 实取:#024FFF 蓝色圆底(直径约 64 设计px)
|
||||
&__icon {
|
||||
font-size: @font-size-xxl * 2;
|
||||
.flex(row, center);
|
||||
grid-area: icon;
|
||||
flex-shrink: 0;
|
||||
width: 49px;
|
||||
height: 49px;
|
||||
margin: 0;
|
||||
border-radius: @radius-round;
|
||||
background: @primary-strong;
|
||||
font-size: @font-size-lg;
|
||||
line-height: 1;
|
||||
}
|
||||
|
||||
&__title {
|
||||
font-size: @font-size-xl;
|
||||
font-weight: 600;
|
||||
grid-area: title;
|
||||
align-self: end;
|
||||
font-size: 15px; // 设计 19 → 15
|
||||
font-weight: 700;
|
||||
color: @heading-color;
|
||||
}
|
||||
|
||||
&__number {
|
||||
font-size: @font-size-xxl + @spacing-sm;
|
||||
grid-area: number;
|
||||
font-size: 18px; // 设计 24 → 18
|
||||
font-weight: 700;
|
||||
color: @primary-color;
|
||||
line-height: 1.2;
|
||||
color: @primary-strong;
|
||||
line-height: 1.3;
|
||||
}
|
||||
|
||||
&__time {
|
||||
font-size: @font-size-base;
|
||||
grid-area: time;
|
||||
align-self: start;
|
||||
color: @text-color-secondary;
|
||||
font-size: 11px; // 设计 12 → 11
|
||||
}
|
||||
}
|
||||
</style>
|
||||
|
||||
@@ -22,11 +22,11 @@ const menus: MenuItem[] = [
|
||||
<ul class="profile-sider__menu">
|
||||
<li v-for="item in menus" :key="item.to">
|
||||
<RouterLink :to="item.to" class="profile-sider__item">
|
||||
<span class="profile-sider__icon">{{ item.icon }}</span>
|
||||
<span class="profile-sider__label">{{ item.label }}</span>
|
||||
</RouterLink>
|
||||
</li>
|
||||
</ul>
|
||||
|
||||
<div class="profile-sider__footer">
|
||||
<RouterLink
|
||||
to="/profile/hotline"
|
||||
@@ -47,50 +47,50 @@ const menus: MenuItem[] = [
|
||||
|
||||
&__menu {
|
||||
.flex(column, flex-start);
|
||||
gap: 2px;
|
||||
gap: 0;
|
||||
list-style: none;
|
||||
}
|
||||
|
||||
// 设计 14/28:纯文字菜单,选中项浅蓝底 + 蓝色加粗,行距 36 × 0.77 ≈ 28
|
||||
&__item {
|
||||
.flex(row, flex-start);
|
||||
gap: @spacing-sm;
|
||||
height: 44px;
|
||||
padding: 0 @spacing-base;
|
||||
border-radius: @radius-base;
|
||||
.flex(row, flex-start, center);
|
||||
height: 28px;
|
||||
padding: 0 @spacing-sm;
|
||||
border-radius: @profile-radius;
|
||||
color: @text-color;
|
||||
font-size: @font-size-base;
|
||||
font-size: 11px;
|
||||
line-height: 1;
|
||||
transition: all 0.2s;
|
||||
|
||||
&:hover {
|
||||
background: @primary-light;
|
||||
color: @primary-color;
|
||||
color: @primary-strong;
|
||||
}
|
||||
|
||||
&.router-link-active {
|
||||
background: @primary-light;
|
||||
color: @primary-color;
|
||||
background: @profile-nav-active-bg;
|
||||
color: @primary-strong;
|
||||
font-weight: 600;
|
||||
}
|
||||
}
|
||||
|
||||
&__icon {
|
||||
font-size: @font-size-lg;
|
||||
line-height: 1;
|
||||
&__label {
|
||||
white-space: nowrap;
|
||||
}
|
||||
|
||||
&__footer {
|
||||
padding: @spacing-base;
|
||||
border-top: 1px solid @border-color;
|
||||
text-align: center;
|
||||
padding: @spacing-sm @spacing-sm 0;
|
||||
border-top: 1px solid @project-divider;
|
||||
}
|
||||
|
||||
&__hotline {
|
||||
font-size: @font-size-sm;
|
||||
display: inline-block;
|
||||
font-size: 11px;
|
||||
color: @text-color-secondary;
|
||||
transition: color 0.2s;
|
||||
|
||||
&:hover {
|
||||
color: @primary-color;
|
||||
color: @primary-strong;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -50,63 +50,68 @@ function save(): void {
|
||||
</template>
|
||||
|
||||
<style lang="less" scoped>
|
||||
// 设计 14:左列紫渐变用户卡(渐变实取 #5459E8 → #D2BDF3),内容居中
|
||||
.profile-user-card {
|
||||
.flex(row, flex-start);
|
||||
gap: @spacing-base;
|
||||
padding: @spacing-lg @spacing-xl;
|
||||
.flex(column, center);
|
||||
gap: @spacing-xs; // 设计 14:头像与文字块间距约 4px
|
||||
padding: @spacing-base @spacing-sm; // 设计:上 20 / 下 25 设计px ≈ 16
|
||||
border-radius: @radius-lg;
|
||||
background: @white;
|
||||
box-shadow: @shadow-base;
|
||||
background: linear-gradient(170deg, @profile-user-from 0%, @profile-user-to 100%);
|
||||
|
||||
&__avatar {
|
||||
.flex(row, center);
|
||||
flex-shrink: 0;
|
||||
width: 64px;
|
||||
height: 64px;
|
||||
width: 42px; // 设计 54 × 0.77
|
||||
height: 42px;
|
||||
border-radius: @radius-round;
|
||||
background: linear-gradient(135deg, @primary-color, @primary-hover);
|
||||
background: @profile-user-avatar;
|
||||
color: @white;
|
||||
font-size: @font-size-xxl;
|
||||
font-size: @font-size-lg;
|
||||
font-weight: 600;
|
||||
}
|
||||
|
||||
&__info {
|
||||
.flex(column, flex-start);
|
||||
.flex(column, center);
|
||||
gap: @spacing-xs;
|
||||
min-width: 0;
|
||||
width: 100%;
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
// 卡内为深色底:名称/号码一律白字(设计 14 实取 #FFFFFF)
|
||||
&__name {
|
||||
width: 240px;
|
||||
height: 34px;
|
||||
padding: 0 @spacing-sm;
|
||||
width: 100%;
|
||||
height: 16px; // 设计 19 × 0.77
|
||||
padding: 0 @spacing-xs;
|
||||
border: 1px solid transparent;
|
||||
border-radius: @radius-base;
|
||||
border-radius: @profile-radius;
|
||||
background: transparent;
|
||||
font-size: @font-size-xl;
|
||||
font-size: 11px;
|
||||
font-weight: 600;
|
||||
color: @heading-color;
|
||||
color: @white;
|
||||
text-align: center;
|
||||
outline: none;
|
||||
transition: all 0.2s;
|
||||
|
||||
&:hover {
|
||||
border-color: @border-color;
|
||||
border-color: fade(@white, 55%);
|
||||
}
|
||||
|
||||
&:focus {
|
||||
border-color: @primary-color;
|
||||
background: @bg-color-light;
|
||||
border-color: @white;
|
||||
background: fade(@white, 12%);
|
||||
}
|
||||
|
||||
&::placeholder {
|
||||
font-size: @font-size-lg;
|
||||
font-size: 11px;
|
||||
font-weight: 400;
|
||||
color: @text-color-disabled;
|
||||
color: fade(@white, 75%);
|
||||
}
|
||||
}
|
||||
|
||||
&__phone {
|
||||
font-size: @font-size-base;
|
||||
font-size: 11px;
|
||||
color: @white;
|
||||
}
|
||||
}
|
||||
</style>
|
||||
|
||||
@@ -59,13 +59,14 @@ const STATUS_VARIANTS: Record<QualificationStatus, 'success' | 'warning' | 'dang
|
||||
</template>
|
||||
|
||||
<style lang="less" scoped>
|
||||
// 设计 17(资质列表行):白卡灰描边、字段标签灰/值深 w600、状态为纯文字、白底描边操作按钮
|
||||
.qual-card {
|
||||
.flex(column, flex-start);
|
||||
gap: @spacing-sm;
|
||||
padding: @spacing-base;
|
||||
border-radius: @radius-lg;
|
||||
border: 1px solid @profile-card-border;
|
||||
border-radius: @radius-base;
|
||||
background: @white;
|
||||
box-shadow: @shadow-base;
|
||||
|
||||
&__head {
|
||||
.flex(row, space-between, flex-start);
|
||||
@@ -73,7 +74,7 @@ const STATUS_VARIANTS: Record<QualificationStatus, 'success' | 'warning' | 'dang
|
||||
}
|
||||
|
||||
&__name {
|
||||
font-size: @font-size-lg;
|
||||
font-size: 11px; // 设计 13 → 11
|
||||
font-weight: 600;
|
||||
color: @heading-color;
|
||||
.multi-ellipsis(2);
|
||||
@@ -83,42 +84,77 @@ const STATUS_VARIANTS: Record<QualificationStatus, 'success' | 'warning' | 'dang
|
||||
.flex(column, flex-start);
|
||||
gap: @spacing-xs;
|
||||
list-style: none;
|
||||
font-size: @font-size-base;
|
||||
color: @text-color;
|
||||
font-size: 11px;
|
||||
color: @heading-color;
|
||||
|
||||
li {
|
||||
.ellipsis();
|
||||
font-weight: 600;
|
||||
}
|
||||
|
||||
span {
|
||||
color: @text-color-secondary;
|
||||
font-weight: 400;
|
||||
}
|
||||
}
|
||||
|
||||
&__actions {
|
||||
.flex(row, center);
|
||||
gap: @spacing-base;
|
||||
gap: @spacing-sm;
|
||||
margin-top: auto;
|
||||
padding-top: @spacing-sm;
|
||||
border-top: 1px solid @border-color;
|
||||
border-top: 1px solid @profile-card-border;
|
||||
width: 100%;
|
||||
}
|
||||
|
||||
// 设计 17:操作按钮 = 白底灰描边、12 设计px w500 灰字
|
||||
&__btn {
|
||||
font-size: @font-size-base;
|
||||
color: @primary-color;
|
||||
transition: opacity 0.2s;
|
||||
height: 24px;
|
||||
padding: 0 10px;
|
||||
border: 1px solid @profile-line;
|
||||
border-radius: @profile-radius;
|
||||
background: @white;
|
||||
color: @text-color;
|
||||
font-size: 11px;
|
||||
font-weight: 500;
|
||||
transition: all 0.2s;
|
||||
|
||||
&:hover {
|
||||
opacity: 0.75;
|
||||
border-color: @primary-strong;
|
||||
color: @primary-strong;
|
||||
opacity: 1;
|
||||
}
|
||||
|
||||
&--danger {
|
||||
color: @danger-color;
|
||||
color: @text-color;
|
||||
}
|
||||
|
||||
&--warning {
|
||||
color: @warning-color;
|
||||
color: @text-color;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// 设计 17:状态为纯文字(已认证/审核中深灰、未通过红),无底色胶囊
|
||||
.qual-card .status-tag {
|
||||
padding: 0;
|
||||
background: transparent;
|
||||
font-size: 12px; // 设计 15 → 12
|
||||
font-weight: 700;
|
||||
|
||||
&--success {
|
||||
background: transparent;
|
||||
color: @heading-color;
|
||||
}
|
||||
|
||||
&--warning {
|
||||
background: transparent;
|
||||
color: @heading-color;
|
||||
}
|
||||
|
||||
&--danger {
|
||||
background: transparent;
|
||||
color: @danger-color;
|
||||
}
|
||||
}
|
||||
</style>
|
||||
|
||||
@@ -184,20 +184,21 @@ function onSave(): void {
|
||||
</template>
|
||||
|
||||
<style lang="less" scoped>
|
||||
// 与个人中心其它弹窗同规格(设计 22~27):白卡 700px、蓝条标题、白底描边输入、等宽双按钮
|
||||
.qual-dialog {
|
||||
position: fixed;
|
||||
inset: 0;
|
||||
z-index: 1000;
|
||||
.flex(row, center);
|
||||
background: rgba(0, 0, 0, 0.45);
|
||||
background: transparent;
|
||||
overflow-y: auto;
|
||||
|
||||
&__panel {
|
||||
width: 520px;
|
||||
width: 700px;
|
||||
max-width: calc(100vw - 32px);
|
||||
max-height: calc(100vh - 48px);
|
||||
overflow-y: auto;
|
||||
padding: @spacing-lg;
|
||||
padding: @spacing-base;
|
||||
border-radius: @radius-lg;
|
||||
background: @white;
|
||||
box-shadow: @shadow-lg;
|
||||
@@ -207,9 +208,23 @@ function onSave(): void {
|
||||
}
|
||||
|
||||
&__title {
|
||||
font-size: @font-size-lg;
|
||||
font-weight: 600;
|
||||
position: relative;
|
||||
padding-left: 12px;
|
||||
font-size: 12px;
|
||||
font-weight: 700;
|
||||
color: @heading-color;
|
||||
line-height: 20px;
|
||||
|
||||
&::before {
|
||||
content: '';
|
||||
position: absolute;
|
||||
left: 0;
|
||||
top: 3px;
|
||||
width: 3px;
|
||||
height: 14px;
|
||||
border-radius: 2px;
|
||||
background: @primary-strong;
|
||||
}
|
||||
}
|
||||
|
||||
&__field {
|
||||
@@ -219,25 +234,30 @@ function onSave(): void {
|
||||
}
|
||||
|
||||
&__label {
|
||||
font-size: @font-size-base;
|
||||
font-size: 11px;
|
||||
font-weight: 500;
|
||||
color: @heading-color;
|
||||
}
|
||||
|
||||
&__input {
|
||||
width: 100%;
|
||||
height: 40px;
|
||||
padding: 0 @spacing-base;
|
||||
border: 1px solid @border-color;
|
||||
border-radius: @radius-base;
|
||||
background: @bg-color-light;
|
||||
font-size: @font-size-base;
|
||||
height: 32px;
|
||||
padding: 0 12px;
|
||||
border: 1px solid @profile-input-border;
|
||||
border-radius: @profile-radius;
|
||||
background: @white;
|
||||
font-size: 11px;
|
||||
color: @text-color;
|
||||
outline: none;
|
||||
transition: border-color 0.2s;
|
||||
box-sizing: border-box;
|
||||
|
||||
&:focus {
|
||||
border-color: @primary-color;
|
||||
border-color: @primary-strong;
|
||||
}
|
||||
|
||||
&::placeholder {
|
||||
color: @heading-color;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -248,17 +268,47 @@ function onSave(): void {
|
||||
|
||||
&__sep {
|
||||
flex-shrink: 0;
|
||||
font-size: @font-size-sm;
|
||||
font-size: 11px;
|
||||
}
|
||||
|
||||
&__hint {
|
||||
font-size: @font-size-sm;
|
||||
font-size: 11px;
|
||||
}
|
||||
|
||||
&__footer {
|
||||
.flex(row, flex-end);
|
||||
.flex(row, flex-start);
|
||||
gap: @spacing-sm;
|
||||
width: 100%;
|
||||
}
|
||||
|
||||
.app-button {
|
||||
flex: 1;
|
||||
height: 36px;
|
||||
font-size: 12px;
|
||||
font-weight: 500;
|
||||
border-radius: @profile-radius;
|
||||
}
|
||||
|
||||
.app-button--primary {
|
||||
border-color: @primary-strong;
|
||||
background: @primary-strong;
|
||||
|
||||
&:hover {
|
||||
border-color: darken(@primary-strong, 6%);
|
||||
background: darken(@primary-strong, 6%);
|
||||
}
|
||||
}
|
||||
|
||||
.app-button--default {
|
||||
border: none;
|
||||
background: @profile-quiet-btn;
|
||||
color: @text-color;
|
||||
|
||||
&:hover {
|
||||
border: none;
|
||||
background: darken(@profile-quiet-btn, 4%);
|
||||
color: @text-color;
|
||||
}
|
||||
}
|
||||
}
|
||||
</style>
|
||||
|
||||
@@ -42,13 +42,14 @@ const risks = [
|
||||
<div class="security-panel">
|
||||
<!-- 修改密码 -->
|
||||
<section class="security-panel__row">
|
||||
<span class="security-panel__icon security-panel__icon--pwd" aria-hidden="true" />
|
||||
<div class="security-panel__main">
|
||||
<h3 class="security-panel__title">
|
||||
修改密码
|
||||
</h3>
|
||||
<p class="security-panel__status">
|
||||
<span class="security-panel__badge security-panel__badge--ok">已设置</span>
|
||||
<span class="security-panel__note text-secondary">上次修改:{{ profile?.passwordModifiedAt }}</span>
|
||||
<span class="security-panel__note">上次修改:{{ profile?.passwordModifiedAt }}</span>
|
||||
</p>
|
||||
</div>
|
||||
<AppButton type="default" @click="emit('changePassword')">
|
||||
@@ -58,6 +59,7 @@ const risks = [
|
||||
|
||||
<!-- 绑定手机 -->
|
||||
<section class="security-panel__row">
|
||||
<span class="security-panel__icon security-panel__icon--phone" aria-hidden="true" />
|
||||
<div class="security-panel__main">
|
||||
<h3 class="security-panel__title">
|
||||
绑定手机
|
||||
@@ -65,7 +67,7 @@ const risks = [
|
||||
<p class="security-panel__status">
|
||||
<span class="security-panel__badge security-panel__badge--ok">已绑定 {{ profile?.phone }}</span>
|
||||
</p>
|
||||
<p class="security-panel__note text-secondary">
|
||||
<p class="security-panel__note">
|
||||
注:换绑新手机号之后,可以用新的手机号及当前密码登录
|
||||
</p>
|
||||
</div>
|
||||
@@ -76,6 +78,7 @@ const risks = [
|
||||
|
||||
<!-- 绑定邮箱 -->
|
||||
<section class="security-panel__row">
|
||||
<span class="security-panel__icon security-panel__icon--email" aria-hidden="true" />
|
||||
<div class="security-panel__main">
|
||||
<h3 class="security-panel__title">
|
||||
绑定邮箱
|
||||
@@ -115,7 +118,7 @@ const risks = [
|
||||
</h3>
|
||||
|
||||
<div class="security-panel__block">
|
||||
<h4 class="security-panel__block-title">
|
||||
<h4 class="security-panel__block-title security-panel__block-title--ok">
|
||||
注销条件
|
||||
</h4>
|
||||
<ul class="security-panel__checks">
|
||||
@@ -126,7 +129,7 @@ const risks = [
|
||||
</div>
|
||||
|
||||
<div class="security-panel__block">
|
||||
<h4 class="security-panel__block-title">
|
||||
<h4 class="security-panel__block-title security-panel__block-title--risk">
|
||||
注销风险提示
|
||||
</h4>
|
||||
<ol class="security-panel__risks">
|
||||
@@ -138,7 +141,7 @@ const risks = [
|
||||
|
||||
<label class="security-panel__agree">
|
||||
<input v-model="agree" type="checkbox">
|
||||
<span>已阅读并同意《账号注销协议》</span>
|
||||
<span>已阅读并同意<em>《账号注销协议》</em></span>
|
||||
</label>
|
||||
|
||||
<AppButton
|
||||
@@ -154,25 +157,47 @@ const risks = [
|
||||
</template>
|
||||
|
||||
<style lang="less" scoped>
|
||||
// 设计 28:白卡行 + 浅灰描边、图标块 44×44 设计px、标题 14 设计px w600、副文 11 设计px
|
||||
.security-panel {
|
||||
.flex(column, flex-start);
|
||||
gap: @spacing-base;
|
||||
|
||||
&__row {
|
||||
.flex(row, space-between, flex-start);
|
||||
.flex(row, flex-start, center);
|
||||
gap: @spacing-base;
|
||||
padding: @spacing-lg @spacing-xl;
|
||||
border-radius: @radius-lg;
|
||||
padding: @spacing-base;
|
||||
border: 1px solid @profile-card-border;
|
||||
border-radius: @radius-base;
|
||||
background: @white;
|
||||
box-shadow: @shadow-base;
|
||||
}
|
||||
|
||||
// 设计 28 实取图标块底色:#C7D2FE / #FDEBEB / #FEE2E2
|
||||
&__icon {
|
||||
flex-shrink: 0;
|
||||
width: 34px; // 设计 44 × 0.77
|
||||
height: 34px;
|
||||
border-radius: @radius-base;
|
||||
|
||||
&--pwd {
|
||||
background: @profile-icon-pwd;
|
||||
}
|
||||
|
||||
&--phone {
|
||||
background: @profile-icon-phone;
|
||||
}
|
||||
|
||||
&--email {
|
||||
background: @profile-icon-email;
|
||||
}
|
||||
}
|
||||
|
||||
&__main {
|
||||
flex: 1;
|
||||
min-width: 0;
|
||||
}
|
||||
|
||||
&__title {
|
||||
font-size: @font-size-lg;
|
||||
font-size: 11px; // 设计 14 → 10.8,取可读下限 11
|
||||
font-weight: 600;
|
||||
color: @heading-color;
|
||||
}
|
||||
@@ -181,26 +206,29 @@ const risks = [
|
||||
.flex(row, flex-start, center);
|
||||
flex-wrap: wrap;
|
||||
gap: @spacing-sm;
|
||||
margin-top: @spacing-sm;
|
||||
font-size: @font-size-base;
|
||||
margin-top: @spacing-xs;
|
||||
font-size: 11px;
|
||||
}
|
||||
|
||||
// 设计 28:已设置/已绑定 = 浅绿底绿字胶囊,未绑定 = 纯灰字
|
||||
&__badge {
|
||||
padding: 2px @spacing-sm;
|
||||
padding: 2px 8px;
|
||||
border-radius: @radius-sm;
|
||||
background: @bg-color;
|
||||
background: transparent;
|
||||
color: @text-color-secondary;
|
||||
font-size: @font-size-sm;
|
||||
font-size: 11px;
|
||||
font-weight: 500;
|
||||
|
||||
&--ok {
|
||||
background: fade(@success-color, 12%);
|
||||
background: @tag-success-bg;
|
||||
color: @success-color;
|
||||
}
|
||||
}
|
||||
|
||||
&__note {
|
||||
margin-top: @spacing-xs;
|
||||
font-size: @font-size-sm;
|
||||
color: @text-color-disabled;
|
||||
font-size: 11px;
|
||||
line-height: 1.6;
|
||||
}
|
||||
|
||||
@@ -210,18 +238,48 @@ const risks = [
|
||||
flex-shrink: 0;
|
||||
}
|
||||
|
||||
// 行内操作按钮:白底灰描边小按钮(设计 20/17 操作按钮同规格)
|
||||
.app-button {
|
||||
height: 28px;
|
||||
padding: 0 12px;
|
||||
border: 1px solid @profile-line;
|
||||
border-radius: @profile-radius;
|
||||
background: @white;
|
||||
color: @text-color;
|
||||
font-size: 11px;
|
||||
font-weight: 500;
|
||||
|
||||
&:hover:not(:disabled) {
|
||||
border-color: @primary-strong;
|
||||
color: @primary-strong;
|
||||
background: @white;
|
||||
}
|
||||
}
|
||||
|
||||
.app-button--text {
|
||||
border-color: transparent;
|
||||
background: transparent;
|
||||
color: @text-color;
|
||||
|
||||
&:hover:not(:disabled) {
|
||||
border-color: transparent;
|
||||
background: transparent;
|
||||
color: @primary-strong;
|
||||
}
|
||||
}
|
||||
|
||||
&__danger {
|
||||
.flex(column, flex-start);
|
||||
gap: @spacing-base;
|
||||
padding: @spacing-lg @spacing-xl;
|
||||
border: 1px solid fade(@danger-color, 35%);
|
||||
border-radius: @radius-lg;
|
||||
padding: @spacing-lg;
|
||||
border: 1px solid @profile-card-border;
|
||||
border-radius: @radius-base;
|
||||
background: @white;
|
||||
}
|
||||
|
||||
&__danger-title {
|
||||
font-size: @font-size-lg;
|
||||
font-weight: 600;
|
||||
font-size: 12px; // 设计 15 → 12
|
||||
font-weight: 700;
|
||||
color: @danger-color;
|
||||
}
|
||||
|
||||
@@ -230,10 +288,18 @@ const risks = [
|
||||
gap: @spacing-sm;
|
||||
}
|
||||
|
||||
// 设计 29:注销条件标题绿、注销风险提示标题红
|
||||
&__block-title {
|
||||
font-size: @font-size-base;
|
||||
font-size: 11px;
|
||||
font-weight: 600;
|
||||
color: @heading-color;
|
||||
|
||||
&--ok {
|
||||
color: @success-color;
|
||||
}
|
||||
|
||||
&--risk {
|
||||
color: @danger-color;
|
||||
}
|
||||
}
|
||||
|
||||
&__checks {
|
||||
@@ -243,7 +309,7 @@ const risks = [
|
||||
}
|
||||
|
||||
&__check {
|
||||
font-size: @font-size-base;
|
||||
font-size: 11px;
|
||||
color: @text-color;
|
||||
}
|
||||
|
||||
@@ -255,10 +321,10 @@ const risks = [
|
||||
|
||||
&__risks {
|
||||
margin: 0;
|
||||
padding-left: @spacing-lg;
|
||||
padding-left: @spacing-base;
|
||||
.flex(column, flex-start);
|
||||
gap: @spacing-xs;
|
||||
font-size: @font-size-base;
|
||||
font-size: 11px;
|
||||
color: @text-color;
|
||||
line-height: 1.6;
|
||||
}
|
||||
@@ -266,25 +332,40 @@ const risks = [
|
||||
&__agree {
|
||||
.flex(row, flex-start, center);
|
||||
gap: @spacing-sm;
|
||||
font-size: @font-size-base;
|
||||
color: @text-color;
|
||||
font-size: 11px;
|
||||
color: @text-color-secondary;
|
||||
cursor: pointer;
|
||||
|
||||
input {
|
||||
accent-color: @danger-color;
|
||||
accent-color: @primary-strong;
|
||||
}
|
||||
|
||||
em {
|
||||
font-style: normal;
|
||||
color: @primary-strong;
|
||||
}
|
||||
}
|
||||
|
||||
// AppButton 根元素可被父级 scoped 命中:danger 描边按钮
|
||||
// 注销账号:白底灰描边整行按钮(设计 28 实取文字 #9CA3AF、15 设计px)
|
||||
&__delete-btn {
|
||||
border-color: @danger-color !important;
|
||||
color: @danger-color !important;
|
||||
width: 100%;
|
||||
height: 36px;
|
||||
border: 1px solid @profile-line !important;
|
||||
background: @white !important;
|
||||
color: @text-color-disabled !important;
|
||||
font-size: 12px;
|
||||
font-weight: 500;
|
||||
|
||||
&:hover:not(:disabled) {
|
||||
background: fade(@danger-color, 8%) !important;
|
||||
border-color: @danger-color !important;
|
||||
background: @white !important;
|
||||
color: @danger-color !important;
|
||||
}
|
||||
|
||||
&:disabled {
|
||||
opacity: 1;
|
||||
cursor: not-allowed;
|
||||
}
|
||||
}
|
||||
}
|
||||
</style>
|
||||
|
||||
@@ -96,6 +96,7 @@ onMounted(() => {
|
||||
</template>
|
||||
|
||||
<style lang="less" scoped>
|
||||
// 收藏列表无独立设计稿:与个人中心面板一致 —— 分类条平铺在白面板上,选中态用主色 token
|
||||
.favorites-page {
|
||||
.flex(column, flex-start);
|
||||
gap: @spacing-base;
|
||||
@@ -106,33 +107,42 @@ onMounted(() => {
|
||||
flex-wrap: wrap;
|
||||
gap: @spacing-sm;
|
||||
width: 100%;
|
||||
padding: @spacing-base @spacing-lg;
|
||||
border-radius: @radius-lg;
|
||||
background: @white;
|
||||
box-shadow: @shadow-base;
|
||||
padding: 0;
|
||||
}
|
||||
|
||||
&__cat {
|
||||
height: 32px;
|
||||
height: 28px;
|
||||
padding: 0 @spacing-base;
|
||||
border: 1px solid @border-color;
|
||||
border: 1px solid @profile-line;
|
||||
border-radius: @radius-round;
|
||||
background: @white;
|
||||
color: @text-color;
|
||||
font-size: @font-size-sm;
|
||||
font-size: 11px;
|
||||
transition: all 0.2s;
|
||||
|
||||
&:hover {
|
||||
border-color: @primary-color;
|
||||
color: @primary-color;
|
||||
border-color: @primary-strong;
|
||||
color: @primary-strong;
|
||||
}
|
||||
|
||||
&.is-active {
|
||||
border-color: @primary-color;
|
||||
background: @primary-light;
|
||||
color: @primary-color;
|
||||
border-color: @primary-strong;
|
||||
background: @profile-nav-active-bg;
|
||||
color: @primary-strong;
|
||||
font-weight: 600;
|
||||
}
|
||||
}
|
||||
|
||||
// 分页与地址/资质页保持同一激活态(设计 20 实取 #D1E0FE + #024FFF 字)
|
||||
:deep(.pagination) {
|
||||
justify-content: flex-end;
|
||||
padding: 0;
|
||||
}
|
||||
|
||||
:deep(.pagination__btn.is-active) {
|
||||
border-color: @profile-page-active-bg;
|
||||
background: @profile-page-active-bg;
|
||||
color: @primary-strong;
|
||||
}
|
||||
}
|
||||
</style>
|
||||
|
||||
@@ -58,6 +58,7 @@ function onPreview(file: FileInfo): void {
|
||||
</template>
|
||||
|
||||
<style lang="less" scoped>
|
||||
// 设计 18(意见反馈):面板内标题蓝条 + 副文案,表单直接铺在面板上
|
||||
.feedback-page {
|
||||
.flex(column, flex-start);
|
||||
gap: @spacing-base;
|
||||
@@ -67,20 +68,31 @@ function onPreview(file: FileInfo): void {
|
||||
.flex(column, flex-start);
|
||||
gap: @spacing-xs;
|
||||
width: 100%;
|
||||
padding: @spacing-base @spacing-xl;
|
||||
border-radius: @radius-lg;
|
||||
background: @white;
|
||||
box-shadow: @shadow-base;
|
||||
padding: 0;
|
||||
}
|
||||
|
||||
&__title {
|
||||
font-size: @font-size-lg;
|
||||
font-weight: 600;
|
||||
position: relative;
|
||||
padding-left: 12px;
|
||||
font-size: 12px; // 设计 15 → 12
|
||||
font-weight: 700;
|
||||
color: @heading-color;
|
||||
line-height: 20px;
|
||||
|
||||
&::before {
|
||||
content: '';
|
||||
position: absolute;
|
||||
left: 0;
|
||||
top: 3px;
|
||||
width: 3px;
|
||||
height: 14px;
|
||||
border-radius: 2px;
|
||||
background: @primary-strong;
|
||||
}
|
||||
}
|
||||
|
||||
&__sub {
|
||||
font-size: @font-size-base;
|
||||
font-size: 11px;
|
||||
}
|
||||
}
|
||||
</style>
|
||||
|
||||
@@ -28,6 +28,7 @@ onMounted(() => {
|
||||
</template>
|
||||
|
||||
<style lang="less" scoped>
|
||||
// 设计 16(帮助中心):面板内标题蓝条 + 副文案,FAQ 平铺在面板上
|
||||
.help-page {
|
||||
.flex(column, flex-start);
|
||||
gap: @spacing-base;
|
||||
@@ -37,20 +38,31 @@ onMounted(() => {
|
||||
.flex(column, flex-start);
|
||||
gap: @spacing-xs;
|
||||
width: 100%;
|
||||
padding: @spacing-base @spacing-xl;
|
||||
border-radius: @radius-lg;
|
||||
background: @white;
|
||||
box-shadow: @shadow-base;
|
||||
padding: 0;
|
||||
}
|
||||
|
||||
&__title {
|
||||
font-size: @font-size-lg;
|
||||
font-weight: 600;
|
||||
position: relative;
|
||||
padding-left: 12px;
|
||||
font-size: 12px; // 设计 15 → 12
|
||||
font-weight: 700;
|
||||
color: @heading-color;
|
||||
line-height: 20px;
|
||||
|
||||
&::before {
|
||||
content: '';
|
||||
position: absolute;
|
||||
left: 0;
|
||||
top: 3px;
|
||||
width: 3px;
|
||||
height: 14px;
|
||||
border-radius: 2px;
|
||||
background: @primary-strong;
|
||||
}
|
||||
}
|
||||
|
||||
&__sub {
|
||||
font-size: @font-size-base;
|
||||
font-size: 11px;
|
||||
}
|
||||
}
|
||||
</style>
|
||||
|
||||
@@ -21,10 +21,9 @@ onMounted(() => {
|
||||
<template>
|
||||
<div class="profile">
|
||||
<div class="profile__container">
|
||||
<ProfileUserCard :profile="profile" @save-nickname="onSaveNickname" />
|
||||
|
||||
<div class="profile__body">
|
||||
<aside class="profile__aside">
|
||||
<ProfileUserCard :profile="profile" @save-nickname="onSaveNickname" />
|
||||
<ProfileSider />
|
||||
</aside>
|
||||
<main class="profile__main">
|
||||
@@ -44,30 +43,32 @@ onMounted(() => {
|
||||
width: @container-width;
|
||||
max-width: calc(100% - @spacing-xl);
|
||||
margin: 0 auto;
|
||||
padding-top: @spacing-xl;
|
||||
padding-top: @spacing-lg;
|
||||
}
|
||||
|
||||
&__body {
|
||||
.flex(row, flex-start);
|
||||
gap: @spacing-base;
|
||||
margin-top: @spacing-base;
|
||||
align-items: flex-start;
|
||||
}
|
||||
|
||||
// 左列(设计14):紫渐变用户卡 + 菜单,直接坐在页面底色上,无外层白卡
|
||||
&__aside {
|
||||
width: 220px;
|
||||
width: 114px; // 设计 148 × 0.77
|
||||
flex-shrink: 0;
|
||||
border-radius: @radius-lg;
|
||||
background: @white;
|
||||
box-shadow: @shadow-base;
|
||||
overflow: hidden;
|
||||
}
|
||||
|
||||
&__main {
|
||||
flex: 1;
|
||||
min-width: 0;
|
||||
.flex(column, flex-start);
|
||||
gap: @spacing-base;
|
||||
}
|
||||
|
||||
// 右侧内容面板(设计14/28):整块白卡,内缩 16px 承载各页面
|
||||
&__main {
|
||||
flex: 1;
|
||||
min-width: 0;
|
||||
min-height: 400px;
|
||||
padding: @spacing-base;
|
||||
border-radius: @radius-base;
|
||||
background: @white;
|
||||
box-shadow: @shadow-base;
|
||||
}
|
||||
}
|
||||
</style>
|
||||
|
||||
@@ -112,6 +112,7 @@ onMounted(() => {
|
||||
</template>
|
||||
|
||||
<style lang="less" scoped>
|
||||
// 设计 17(资质列表):标题蓝条、整行白卡单列、分页靠右
|
||||
.qual-page {
|
||||
.flex(column, flex-start);
|
||||
gap: @spacing-base;
|
||||
@@ -120,21 +121,32 @@ onMounted(() => {
|
||||
&__head {
|
||||
.flex(row, space-between, center);
|
||||
width: 100%;
|
||||
padding: @spacing-base @spacing-xl;
|
||||
border-radius: @radius-lg;
|
||||
background: @white;
|
||||
box-shadow: @shadow-base;
|
||||
padding: 0;
|
||||
}
|
||||
|
||||
&__title {
|
||||
font-size: @font-size-lg;
|
||||
font-weight: 600;
|
||||
position: relative;
|
||||
padding-left: 12px;
|
||||
font-size: 12px; // 设计 15 → 12
|
||||
font-weight: 700;
|
||||
color: @heading-color;
|
||||
line-height: 20px;
|
||||
|
||||
&::before {
|
||||
content: '';
|
||||
position: absolute;
|
||||
left: 0;
|
||||
top: 3px;
|
||||
width: 3px;
|
||||
height: 14px;
|
||||
border-radius: 2px;
|
||||
background: @primary-strong;
|
||||
}
|
||||
}
|
||||
|
||||
&__grid {
|
||||
display: grid;
|
||||
grid-template-columns: repeat(2, 1fr);
|
||||
grid-template-columns: 1fr;
|
||||
gap: @spacing-base;
|
||||
width: 100%;
|
||||
}
|
||||
@@ -143,7 +155,35 @@ onMounted(() => {
|
||||
grid-column: 1 / -1;
|
||||
padding: @spacing-xxl 0;
|
||||
text-align: center;
|
||||
font-size: @font-size-base;
|
||||
font-size: 11px;
|
||||
}
|
||||
|
||||
:deep(.pagination) {
|
||||
justify-content: flex-end;
|
||||
padding: 0;
|
||||
}
|
||||
|
||||
:deep(.pagination__btn.is-active) {
|
||||
border-color: @profile-page-active-bg;
|
||||
background: @profile-page-active-bg;
|
||||
color: @primary-strong;
|
||||
}
|
||||
|
||||
// 顶部「+ 新增资质」:小号蓝底按钮(设计 17 实取 #024FFF)
|
||||
.app-button--primary {
|
||||
height: 24px;
|
||||
padding: 0 10px;
|
||||
border: none;
|
||||
border-radius: @profile-radius;
|
||||
background: @primary-strong;
|
||||
color: @white;
|
||||
font-size: 11px;
|
||||
font-weight: 500;
|
||||
|
||||
&:hover {
|
||||
border: none;
|
||||
background: darken(@primary-strong, 6%);
|
||||
}
|
||||
}
|
||||
}
|
||||
</style>
|
||||
|
||||
@@ -187,6 +187,15 @@ onMounted(() => {
|
||||
|
||||
<template>
|
||||
<div class="container after-sales">
|
||||
<!-- 设计 12:页面顶部面包屑(与项目详情页同款) -->
|
||||
<nav class="after-sales__breadcrumb">
|
||||
<RouterLink to="/project" class="link">
|
||||
项目中心
|
||||
</RouterLink>
|
||||
<span> > </span>
|
||||
<span>项目详情</span>
|
||||
</nav>
|
||||
|
||||
<header class="after-sales__header">
|
||||
<h1 class="after-sales__title">
|
||||
申请售后
|
||||
@@ -235,7 +244,7 @@ onMounted(() => {
|
||||
<select
|
||||
id="after-sales-project"
|
||||
v-model="selectedProjectId"
|
||||
class="after-sales__select"
|
||||
class="after-sales__select after-sales__select--filled"
|
||||
>
|
||||
<option value="">
|
||||
请选择项目
|
||||
@@ -258,13 +267,13 @@ onMounted(() => {
|
||||
rows="5"
|
||||
placeholder="请详细描述您的问题..."
|
||||
/>
|
||||
<span class="after-sales__count text-secondary">{{ descriptionCount }}字</span>
|
||||
<span class="after-sales__count">{{ descriptionCount }}字</span>
|
||||
</div>
|
||||
|
||||
<div class="after-sales__field">
|
||||
<div class="after-sales__field-head">
|
||||
<label class="after-sales__label">附件上传</label>
|
||||
<span class="after-sales__field-hint text-secondary">支持图片/文档/压缩包,大小不超过1G</span>
|
||||
<span class="after-sales__field-hint">支持图片/文档/压缩包,大小不超过1G</span>
|
||||
<AppButton
|
||||
class="after-sales__upload-btn"
|
||||
size="sm"
|
||||
@@ -307,13 +316,13 @@ onMounted(() => {
|
||||
rows="4"
|
||||
placeholder="其他需要说明的事项..."
|
||||
/>
|
||||
<span class="after-sales__count text-secondary">{{ remarkCount }}字</span>
|
||||
<span class="after-sales__count">{{ remarkCount }}字</span>
|
||||
</div>
|
||||
</section>
|
||||
|
||||
<!-- 底部操作条(设计稿:左侧提示 + 右侧 取消 / 重置 / 申请售后) -->
|
||||
<footer class="after-sales__footer">
|
||||
<p class="after-sales__footer-tip text-secondary">
|
||||
<p class="after-sales__footer-tip">
|
||||
<span class="after-sales__footer-icon" aria-hidden="true">i</span>
|
||||
提交后我们的专业顾问将在一个工作日内与您联系,为您提供一对一服务
|
||||
</p>
|
||||
@@ -338,92 +347,131 @@ onMounted(() => {
|
||||
gap: @spacing-base;
|
||||
padding-top: @spacing-lg;
|
||||
padding-bottom: @spacing-xxl;
|
||||
// 设计 12:整页白底(蓝湖实测页面底 #FFFFFF)
|
||||
background: @white;
|
||||
|
||||
// 面包屑(设计 24px × 0.77 ≈ 18px,#666666,字重 500)
|
||||
&__breadcrumb {
|
||||
font-size: 18px;
|
||||
font-weight: 500;
|
||||
color: @project-breadcrumb;
|
||||
}
|
||||
|
||||
&__header {
|
||||
.flex(column, flex-start, stretch);
|
||||
gap: @spacing-xs;
|
||||
padding: @spacing-sm 0 @spacing-base;
|
||||
gap: 6px;
|
||||
padding: 16px 0 0;
|
||||
}
|
||||
|
||||
// 设计 12:主标题 22 设计px × 0.77 ≈ 17px / 700
|
||||
&__title {
|
||||
font-size: @font-size-title;
|
||||
font-weight: 600;
|
||||
font-size: 17px;
|
||||
font-weight: 700;
|
||||
color: @heading-color;
|
||||
}
|
||||
|
||||
// 设计 12:副标题 13 设计px × 0.77 ≈ 11px、整行居中
|
||||
&__subtitle {
|
||||
font-size: @font-size-sm;
|
||||
font-size: 11px;
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
// ── 三段卡片(设计稿:白底圆角 + 序号圆标标题) ──
|
||||
// ── 三段卡片(设计 12:白底 + 1px #F0F1F3 描边 + 圆角,无阴影) ──
|
||||
&__card {
|
||||
.flex(column, flex-start, stretch);
|
||||
gap: @spacing-lg;
|
||||
padding: @spacing-lg @spacing-xl;
|
||||
gap: @spacing-base;
|
||||
padding: 20px 24px;
|
||||
border: 1px solid @project-divider;
|
||||
border-radius: @radius-lg;
|
||||
background: @white;
|
||||
box-shadow: @shadow-base;
|
||||
box-sizing: border-box;
|
||||
}
|
||||
|
||||
// 设计 12:卡片标题 15 设计px × 0.77 ≈ 12px / 700 + 圆形序号
|
||||
&__card-title {
|
||||
.flex(row, flex-start, center);
|
||||
gap: @spacing-sm;
|
||||
font-size: @font-size-lg;
|
||||
font-weight: 600;
|
||||
gap: 12px;
|
||||
font-size: 12px;
|
||||
font-weight: 700;
|
||||
color: @heading-color;
|
||||
}
|
||||
|
||||
// 设计 12:序号圆 ≈26 设计px × 0.77、蓝底白字 12px / 700
|
||||
&__step {
|
||||
.flex(row, center);
|
||||
width: 26px;
|
||||
height: 26px;
|
||||
width: 20px;
|
||||
height: 20px;
|
||||
border-radius: @radius-round;
|
||||
background: @primary-color;
|
||||
background: @project-accent;
|
||||
color: @white;
|
||||
font-size: @font-size-sm;
|
||||
font-weight: 600;
|
||||
font-size: 12px;
|
||||
font-weight: 700;
|
||||
line-height: 1;
|
||||
}
|
||||
|
||||
&__field {
|
||||
.flex(column, flex-start, stretch);
|
||||
gap: @spacing-sm;
|
||||
gap: 4px;
|
||||
position: relative;
|
||||
}
|
||||
|
||||
// 设计 12:标签与提示同行,间距 14 设计px × 0.77
|
||||
&__field-head {
|
||||
.flex(row, flex-start, center);
|
||||
gap: @spacing-sm;
|
||||
gap: 11px;
|
||||
}
|
||||
|
||||
// 设计 12:提示 11 设计px #9CA3AF
|
||||
&__field-hint {
|
||||
font-size: @font-size-sm;
|
||||
font-size: 11px;
|
||||
color: @text-color-disabled;
|
||||
}
|
||||
|
||||
// 「上传文件」推到行尾
|
||||
// 「上传文件」推到行尾(设计 12:浅灰底按钮)
|
||||
&__upload-btn {
|
||||
margin-left: auto;
|
||||
}
|
||||
|
||||
&__label {
|
||||
font-size: @font-size-base;
|
||||
font-weight: 600;
|
||||
color: @heading-color;
|
||||
&__field-head :deep(.after-sales__upload-btn) {
|
||||
height: 28px;
|
||||
border: none;
|
||||
border-radius: 6px;
|
||||
background: @project-quiet-btn;
|
||||
color: @text-color;
|
||||
font-size: 12px;
|
||||
|
||||
&:hover {
|
||||
border-color: transparent;
|
||||
background: @project-quiet-btn;
|
||||
color: @text-color;
|
||||
}
|
||||
}
|
||||
|
||||
// 设计 12:字段标签整行**居中**,13 设计px × 0.77 ≈ 11px / 500
|
||||
&__label {
|
||||
font-size: 11px;
|
||||
font-weight: 500;
|
||||
color: @heading-color;
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
// 设计 12:星号与标签同色同字重(标注层整串同色)
|
||||
&__required {
|
||||
margin-left: 2px;
|
||||
color: @danger-color;
|
||||
font-weight: 400;
|
||||
color: inherit;
|
||||
font-weight: inherit;
|
||||
}
|
||||
|
||||
// 设计 12:「售后类型」白底描边,「项目名称」灰底只读态(--filled)
|
||||
&__select {
|
||||
width: 100%;
|
||||
height: 40px;
|
||||
padding: 0 36px 0 @spacing-base;
|
||||
height: 36px;
|
||||
padding: 0 36px 0 12px;
|
||||
border: 1px solid @border-color;
|
||||
border-radius: @radius-base;
|
||||
background-color: @bg-color-light;
|
||||
border-radius: 6px;
|
||||
background-color: @white;
|
||||
color: @text-color;
|
||||
font-size: @font-size-base;
|
||||
font-size: 11px;
|
||||
appearance: none;
|
||||
outline: none;
|
||||
cursor: pointer;
|
||||
@@ -434,57 +482,77 @@ onMounted(() => {
|
||||
background-size: 12px 12px;
|
||||
transition: border-color 0.2s;
|
||||
|
||||
&::placeholder {
|
||||
color: @text-color-disabled;
|
||||
}
|
||||
|
||||
&:focus {
|
||||
border-color: @primary-color;
|
||||
}
|
||||
|
||||
// 设计 12:项目名称 = 灰底填充(#F3F4F6),无描边
|
||||
&--filled {
|
||||
border-color: transparent;
|
||||
background-color: @input-bg;
|
||||
}
|
||||
}
|
||||
|
||||
// 「项目名称」与「售后类型」共用同一个下拉样式(见上方 &__select)
|
||||
&__textarea {
|
||||
width: 100%;
|
||||
padding: @spacing-sm @spacing-base;
|
||||
height: 104px;
|
||||
padding: 10px 12px;
|
||||
border: 1px solid @border-color;
|
||||
border-radius: @radius-base;
|
||||
background: @bg-color-light;
|
||||
border-radius: 6px;
|
||||
background: @white;
|
||||
color: @text-color;
|
||||
font-size: @font-size-base;
|
||||
font-size: 11px;
|
||||
line-height: 1.6;
|
||||
resize: vertical;
|
||||
outline: none;
|
||||
box-sizing: border-box;
|
||||
transition: border-color 0.2s;
|
||||
|
||||
&::placeholder {
|
||||
color: @text-color-disabled;
|
||||
}
|
||||
|
||||
&:focus {
|
||||
border-color: @primary-color;
|
||||
}
|
||||
}
|
||||
|
||||
// 设计 12:字数统计在文本域**内部右下角**
|
||||
&__count {
|
||||
align-self: flex-end;
|
||||
font-size: @font-size-sm;
|
||||
position: absolute;
|
||||
right: 12px;
|
||||
bottom: 8px;
|
||||
font-size: 11px;
|
||||
color: @text-color-disabled;
|
||||
}
|
||||
|
||||
&__file-input {
|
||||
display: none;
|
||||
}
|
||||
|
||||
// ── 底部固定操作条 ──
|
||||
// ── 底部固定操作条(设计 12:顶部分隔线 #F0F1F3、白底、左提示右三键) ──
|
||||
&__footer {
|
||||
position: sticky;
|
||||
bottom: 0;
|
||||
z-index: 10;
|
||||
.flex(row, space-between, center);
|
||||
gap: @spacing-base;
|
||||
margin-top: @spacing-sm;
|
||||
padding: @spacing-base @spacing-xl;
|
||||
border-top: 1px solid @border-color;
|
||||
margin-top: 8px;
|
||||
padding: 12px 0;
|
||||
border-top: 1px solid @project-divider;
|
||||
background: @white;
|
||||
box-shadow: 0 -2px 8px rgba(0, 0, 0, 0.04);
|
||||
}
|
||||
|
||||
&__footer-tip {
|
||||
.flex(row, flex-start, center);
|
||||
gap: @spacing-xs;
|
||||
font-size: @font-size-sm;
|
||||
gap: 6px;
|
||||
font-size: 12px;
|
||||
color: @text-color;
|
||||
}
|
||||
|
||||
&__footer-icon {
|
||||
@@ -501,8 +569,71 @@ onMounted(() => {
|
||||
|
||||
&__footer-actions {
|
||||
.flex(row, flex-end, center);
|
||||
gap: @spacing-sm;
|
||||
gap: 12px;
|
||||
flex-shrink: 0;
|
||||
|
||||
// 设计 12:取消 / 重置 = 浅灰底灰字,申请售后 = #024FFF 蓝底白字
|
||||
:deep(.app-button) {
|
||||
height: 32px;
|
||||
border-radius: 6px;
|
||||
font-size: 11px;
|
||||
}
|
||||
|
||||
:deep(.app-button--default) {
|
||||
border: none;
|
||||
background: @project-quiet-btn;
|
||||
color: @text-color;
|
||||
|
||||
&:hover {
|
||||
border-color: transparent;
|
||||
background: @project-quiet-btn;
|
||||
color: @text-color;
|
||||
}
|
||||
}
|
||||
|
||||
:deep(.app-button--primary) {
|
||||
background: @project-accent;
|
||||
|
||||
&:hover {
|
||||
background: @primary-color;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// 设计 12:附件行 = #F7F8FA 圆角行、灰字操作(公共 FileList,仅本页覆写外观)
|
||||
:deep(.file-list) {
|
||||
gap: 12px;
|
||||
}
|
||||
|
||||
:deep(.file-list__item) {
|
||||
padding: 6px 14px;
|
||||
border: none;
|
||||
border-radius: 6px;
|
||||
background: @finance-row-bg;
|
||||
}
|
||||
|
||||
:deep(.file-list__name) {
|
||||
font-size: 11px;
|
||||
line-height: 15px;
|
||||
}
|
||||
|
||||
:deep(.file-list__meta) {
|
||||
font-size: 11px;
|
||||
line-height: 15px;
|
||||
color: @text-color-disabled;
|
||||
}
|
||||
|
||||
:deep(.file-list__actions) {
|
||||
gap: 12px;
|
||||
}
|
||||
|
||||
:deep(.file-list__btn) {
|
||||
font-size: 12px;
|
||||
color: @text-color-secondary;
|
||||
}
|
||||
|
||||
:deep(.file-list__btn--danger) {
|
||||
color: @danger-color;
|
||||
}
|
||||
}
|
||||
</style>
|
||||
|
||||
@@ -76,12 +76,8 @@ function onDeleteFile(): void {
|
||||
|
||||
<!-- 规则 3:已完成 + 已提交售后 → 工单横幅 + 售后信息 + 取消售后 -->
|
||||
<template v-else-if="hasTicket && afterSales">
|
||||
<!-- 设计 10:整宽浅红提示横幅,只有标题 + 说明两行,无图标 -->
|
||||
<div class="project-after-sales__banner">
|
||||
<span class="project-after-sales__banner-icon" aria-hidden="true">
|
||||
<svg viewBox="0 0 24 24" width="22" height="22" fill="currentColor">
|
||||
<path d="M6 2h7l5 5v13a2 2 0 0 1-2 2H6a2 2 0 0 1-2-2V4a2 2 0 0 1 2-2Zm7 1.6V8h4.4L13 3.6ZM8 12.2h8v1.6H8v-1.6Zm0 3.6h8v1.6H8v-1.6Z" />
|
||||
</svg>
|
||||
</span>
|
||||
<div class="project-after-sales__banner-text">
|
||||
<h3 class="project-after-sales__banner-title">
|
||||
售后工单处理中
|
||||
@@ -113,7 +109,7 @@ function onDeleteFile(): void {
|
||||
<div class="project-after-sales__field">
|
||||
<div class="project-after-sales__field-head">
|
||||
<span class="project-after-sales__label">附件上传</span>
|
||||
<span class="project-after-sales__field-hint text-secondary">支持图片/文档/压缩包,大小不超过1G</span>
|
||||
<span class="project-after-sales__field-hint">支持图片/文档/压缩包,大小不超过1G</span>
|
||||
</div>
|
||||
<FileList
|
||||
v-if="afterSales.attachments.length > 0"
|
||||
@@ -146,7 +142,7 @@ function onDeleteFile(): void {
|
||||
</div>
|
||||
<div class="project-after-sales__actions">
|
||||
<button
|
||||
class="project-after-sales__btn project-after-sales__btn--primary"
|
||||
class="project-after-sales__btn project-after-sales__btn--apply"
|
||||
@click="emit('apply')"
|
||||
>
|
||||
申请售后
|
||||
@@ -159,29 +155,17 @@ function onDeleteFile(): void {
|
||||
<style lang="less" scoped>
|
||||
.project-after-sales {
|
||||
.flex(column, flex-start, stretch);
|
||||
gap: @spacing-lg;
|
||||
padding: @spacing-lg @spacing-xl;
|
||||
border-radius: @radius-lg;
|
||||
background: @white;
|
||||
box-shadow: @shadow-base;
|
||||
gap: @spacing-base;
|
||||
// 设计 10:售后信息区块直接落在白底页面上,无外层卡片
|
||||
padding: 0;
|
||||
|
||||
// ── 顶部工单横幅:浅红底 + 红色图标块(设计稿) ──
|
||||
// ── 顶部工单横幅:浅红底、无图标块(设计 10 实取 #FDEEEE) ──
|
||||
&__banner {
|
||||
.flex(row, flex-start, center);
|
||||
gap: @spacing-base;
|
||||
padding: @spacing-base @spacing-lg;
|
||||
border-radius: @radius-base;
|
||||
background: fade(@danger-color, 8%);
|
||||
}
|
||||
|
||||
&__banner-icon {
|
||||
.flex(row, center);
|
||||
flex-shrink: 0;
|
||||
width: 44px;
|
||||
height: 44px;
|
||||
border-radius: @radius-base;
|
||||
background: @danger-color;
|
||||
color: @white;
|
||||
margin-bottom: 16px;
|
||||
padding: 12px 20px;
|
||||
border-radius: 6px;
|
||||
background: @project-banner-bg;
|
||||
}
|
||||
|
||||
&__banner-text {
|
||||
@@ -190,59 +174,72 @@ function onDeleteFile(): void {
|
||||
min-width: 0;
|
||||
}
|
||||
|
||||
// 设计 10:标题 17 设计px × 0.77 ≈ 13px / 700 红
|
||||
&__banner-title {
|
||||
font-size: @font-size-lg;
|
||||
font-weight: 600;
|
||||
color: @heading-color;
|
||||
line-height: 1.2;
|
||||
font-size: 13px;
|
||||
font-weight: 700;
|
||||
color: @project-banner-title;
|
||||
line-height: 1.3;
|
||||
}
|
||||
|
||||
// 设计 10:说明 13 设计px × 0.77 ≈ 11px #4B5563
|
||||
&__banner-desc {
|
||||
font-size: @font-size-sm;
|
||||
color: @text-color-secondary;
|
||||
font-size: 11px;
|
||||
color: @text-color;
|
||||
}
|
||||
|
||||
// ── 「售后信息」区块标题:竖条 + 15px 缩进(与其它页签一致) ──
|
||||
// ── 「售后信息」区块标题:竖条 + 缩进(与其它页签一致) ──
|
||||
&__title {
|
||||
.section-title();
|
||||
margin-top: 0;
|
||||
padding-left: 9px;
|
||||
font-size: 12px;
|
||||
font-weight: 700;
|
||||
|
||||
margin-top: @spacing-xs;
|
||||
&::before {
|
||||
width: 3px;
|
||||
height: 15px;
|
||||
}
|
||||
}
|
||||
|
||||
&__field {
|
||||
.flex(column, flex-start, stretch);
|
||||
gap: @spacing-sm;
|
||||
gap: 6px;
|
||||
}
|
||||
|
||||
// 设计 10:标签与提示同行,间距 14 设计px × 0.77
|
||||
&__field-head {
|
||||
.flex(row, flex-start, baseline);
|
||||
gap: @spacing-sm;
|
||||
gap: 11px;
|
||||
}
|
||||
|
||||
// 设计 10:提示 11 设计px #9CA3AF
|
||||
&__field-hint {
|
||||
font-size: @font-size-sm;
|
||||
font-size: 11px;
|
||||
color: @text-color-disabled;
|
||||
}
|
||||
|
||||
// 设计 10:字段标签 13 设计px × 0.77 ≈ 11px / 500
|
||||
&__label {
|
||||
font-size: @font-size-base;
|
||||
font-weight: 600;
|
||||
font-size: 11px;
|
||||
font-weight: 500;
|
||||
color: @heading-color;
|
||||
}
|
||||
|
||||
// 只读展示(设计稿里是灰底带边框的框,不是输入控件)
|
||||
// 只读展示(设计 10:灰底圆角实底框,无描边)
|
||||
&__readonly {
|
||||
min-height: 40px;
|
||||
padding: 0 @spacing-base;
|
||||
border: 1px solid @border-color;
|
||||
border-radius: @radius-base;
|
||||
background: @bg-color-light;
|
||||
min-height: 36px;
|
||||
padding: 0 12px;
|
||||
border: none;
|
||||
border-radius: 6px;
|
||||
background: @input-bg;
|
||||
color: @text-color;
|
||||
font-size: @font-size-base;
|
||||
line-height: 40px;
|
||||
font-size: 11px;
|
||||
line-height: 36px;
|
||||
|
||||
&--block {
|
||||
min-height: 96px;
|
||||
padding: @spacing-sm @spacing-base;
|
||||
min-height: 104px;
|
||||
padding: 12px;
|
||||
line-height: 1.7;
|
||||
white-space: pre-wrap;
|
||||
word-break: break-word;
|
||||
@@ -263,18 +260,22 @@ function onDeleteFile(): void {
|
||||
font-size: @font-size-base;
|
||||
}
|
||||
|
||||
// 设计 10:按钮组贴右,间距 34 设计px × 0.77
|
||||
&__actions {
|
||||
.flex(row, flex-end, center);
|
||||
gap: @spacing-sm;
|
||||
gap: 24px;
|
||||
margin-top: 8px;
|
||||
}
|
||||
|
||||
// 设计 10:高 ≈36 设计px × 0.77、圆角 ≈8 设计px、文字 15 设计px × 0.77
|
||||
&__btn {
|
||||
height: 36px;
|
||||
padding: 0 @spacing-lg;
|
||||
border-radius: @radius-base;
|
||||
font-size: @font-size-base;
|
||||
height: 28px;
|
||||
padding: 0 14px;
|
||||
border-radius: 6px;
|
||||
font-size: 12px;
|
||||
transition: all 0.2s;
|
||||
|
||||
// 「取消售后」= 品牌蓝(设计 10 实取 #1F67EF)
|
||||
&--primary {
|
||||
border: none;
|
||||
background: @primary-color;
|
||||
@@ -284,6 +285,53 @@ function onDeleteFile(): void {
|
||||
background: @primary-hover;
|
||||
}
|
||||
}
|
||||
|
||||
// 「申请售后」= 红(设计 10 实取 #E3464B)
|
||||
&--apply {
|
||||
border: none;
|
||||
background: @project-apply;
|
||||
color: @white;
|
||||
|
||||
&:hover {
|
||||
background: fade(@project-apply, 88%);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// 设计 10:附件行 = #F7F8FA 圆角行、灰字操作(公共 FileList,仅本页覆写外观)
|
||||
:deep(.file-list) {
|
||||
gap: 12px;
|
||||
}
|
||||
|
||||
:deep(.file-list__item) {
|
||||
padding: 6px 14px;
|
||||
border: none;
|
||||
border-radius: 6px;
|
||||
background: @finance-row-bg;
|
||||
}
|
||||
|
||||
:deep(.file-list__name) {
|
||||
font-size: 11px;
|
||||
line-height: 15px;
|
||||
}
|
||||
|
||||
:deep(.file-list__meta) {
|
||||
font-size: 11px;
|
||||
line-height: 15px;
|
||||
color: @text-color-disabled;
|
||||
}
|
||||
|
||||
:deep(.file-list__actions) {
|
||||
gap: 12px;
|
||||
}
|
||||
|
||||
:deep(.file-list__btn) {
|
||||
font-size: 12px;
|
||||
color: @text-color-secondary;
|
||||
}
|
||||
|
||||
:deep(.file-list__btn--danger) {
|
||||
color: @danger-color;
|
||||
}
|
||||
}
|
||||
</style>
|
||||
|
||||
@@ -30,7 +30,7 @@ const emit = defineEmits<{
|
||||
>
|
||||
<div class="project-files__info">
|
||||
<span class="project-files__name" :title="file.name">{{ file.name }}</span>
|
||||
<span class="project-files__meta text-secondary">
|
||||
<span class="project-files__meta">
|
||||
{{ formatFileSize(file.size) }} · {{ file.uploadTime }}
|
||||
</span>
|
||||
</div>
|
||||
@@ -60,27 +60,36 @@ const emit = defineEmits<{
|
||||
.project-files {
|
||||
.flex(column, flex-start, stretch);
|
||||
gap: @spacing-base;
|
||||
padding: @spacing-lg @spacing-xl;
|
||||
border-radius: @radius-lg;
|
||||
background: @white;
|
||||
box-shadow: @shadow-base;
|
||||
// 设计 11:项目文件区块直接落在白底页面上,无卡片
|
||||
padding: 0;
|
||||
|
||||
&__title {
|
||||
.section-title();
|
||||
// 设计 11:竖条 4×20 设计px、文字 15 设计px/700
|
||||
padding-left: 9px;
|
||||
font-size: 12px;
|
||||
font-weight: 700;
|
||||
|
||||
&::before {
|
||||
width: 3px;
|
||||
height: 15px;
|
||||
}
|
||||
}
|
||||
|
||||
&__list {
|
||||
.flex(column, flex-start, stretch);
|
||||
gap: @spacing-sm;
|
||||
// 设计 11:行间距 15 设计px × 0.77
|
||||
gap: 12px;
|
||||
}
|
||||
|
||||
// 设计 11:整行通铺 #F7F8FA 浅底、圆角 ≈8 设计px,无描边
|
||||
&__item {
|
||||
.flex(row, space-between);
|
||||
gap: @spacing-base;
|
||||
padding: @spacing-sm @spacing-base;
|
||||
border: 1px solid @border-color;
|
||||
border-radius: @radius-base;
|
||||
background: @bg-color-light;
|
||||
padding: 6px 16px;
|
||||
border: none;
|
||||
border-radius: 6px;
|
||||
background: @finance-row-bg;
|
||||
}
|
||||
|
||||
&__info {
|
||||
@@ -89,25 +98,31 @@ const emit = defineEmits<{
|
||||
min-width: 0;
|
||||
}
|
||||
|
||||
// 设计 11:文件名 13 设计px、副行 11 设计px #9CA3AF
|
||||
&__name {
|
||||
font-size: @font-size-base;
|
||||
font-size: 11px;
|
||||
line-height: 15px;
|
||||
color: @heading-color;
|
||||
.ellipsis();
|
||||
}
|
||||
|
||||
&__meta {
|
||||
font-size: @font-size-sm;
|
||||
font-size: 11px;
|
||||
line-height: 15px;
|
||||
color: @text-color-disabled;
|
||||
}
|
||||
|
||||
&__actions {
|
||||
.flex(row, center);
|
||||
gap: @spacing-sm;
|
||||
// 设计 11:「预览 / 下载」间距 14 设计px × 0.77
|
||||
gap: 12px;
|
||||
flex-shrink: 0;
|
||||
}
|
||||
|
||||
// 设计 11:行内操作是灰色纯文字(非蓝色),删除保持警示红
|
||||
&__btn {
|
||||
font-size: @font-size-sm;
|
||||
color: @primary-color;
|
||||
font-size: 12px;
|
||||
color: @text-color-secondary;
|
||||
transition: opacity 0.2s;
|
||||
|
||||
&:hover {
|
||||
|
||||
@@ -122,26 +122,9 @@ function fileMeta(file: FileInfo): string {
|
||||
</div>
|
||||
<div class="project-finance__file-actions">
|
||||
<button class="project-finance__act" type="button" @click="emit('preview', file)">
|
||||
<svg width="14" height="14" viewBox="0 0 16 16" fill="none" aria-hidden="true">
|
||||
<path
|
||||
d="M1.5 8s2.4-4.5 6.5-4.5S14.5 8 14.5 8s-2.4 4.5-6.5 4.5S1.5 8 1.5 8Z"
|
||||
stroke="currentColor"
|
||||
stroke-width="1.2"
|
||||
/>
|
||||
<circle cx="8" cy="8" r="1.8" stroke="currentColor" stroke-width="1.2" />
|
||||
</svg>
|
||||
预览
|
||||
</button>
|
||||
<button class="project-finance__act" type="button" @click="emit('download', file)">
|
||||
<svg width="14" height="14" viewBox="0 0 16 16" fill="none" aria-hidden="true">
|
||||
<path
|
||||
d="M8 2v8m0 0 3-3m-3 3L5 7M3 13h10"
|
||||
stroke="currentColor"
|
||||
stroke-width="1.2"
|
||||
stroke-linecap="round"
|
||||
stroke-linejoin="round"
|
||||
/>
|
||||
</svg>
|
||||
下载
|
||||
</button>
|
||||
</div>
|
||||
@@ -168,26 +151,9 @@ function fileMeta(file: FileInfo): string {
|
||||
</div>
|
||||
<div class="project-finance__file-actions">
|
||||
<button class="project-finance__act" type="button" @click="emit('preview', contractFile)">
|
||||
<svg width="14" height="14" viewBox="0 0 16 16" fill="none" aria-hidden="true">
|
||||
<path
|
||||
d="M1.5 8s2.4-4.5 6.5-4.5S14.5 8 14.5 8s-2.4 4.5-6.5 4.5S1.5 8 1.5 8Z"
|
||||
stroke="currentColor"
|
||||
stroke-width="1.2"
|
||||
/>
|
||||
<circle cx="8" cy="8" r="1.8" stroke="currentColor" stroke-width="1.2" />
|
||||
</svg>
|
||||
预览
|
||||
</button>
|
||||
<button class="project-finance__act" type="button" @click="emit('download', contractFile)">
|
||||
<svg width="14" height="14" viewBox="0 0 16 16" fill="none" aria-hidden="true">
|
||||
<path
|
||||
d="M8 2v8m0 0 3-3m-3 3L5 7M3 13h10"
|
||||
stroke="currentColor"
|
||||
stroke-width="1.2"
|
||||
stroke-linecap="round"
|
||||
stroke-linejoin="round"
|
||||
/>
|
||||
</svg>
|
||||
下载
|
||||
</button>
|
||||
</div>
|
||||
@@ -202,14 +168,20 @@ function fileMeta(file: FileInfo): string {
|
||||
.project-finance {
|
||||
.flex(column, flex-start, stretch);
|
||||
gap: @spacing-base;
|
||||
padding: @spacing-lg @spacing-xl;
|
||||
border-radius: @radius-lg;
|
||||
background: @white;
|
||||
box-shadow: @shadow-base;
|
||||
// 设计 09:合同财务区块直接落在白底页面上,无外层卡片
|
||||
padding: 0;
|
||||
|
||||
// 区块标题:与「项目进度/项目文件/售后信息」同款(16px/600 + 左侧蓝色竖条)
|
||||
// 区块标题:与「项目进度/项目文件/售后信息」同款(12px/700 + 左侧蓝色竖条)
|
||||
&__title {
|
||||
.section-title();
|
||||
padding-left: 9px;
|
||||
font-size: 12px;
|
||||
font-weight: 700;
|
||||
|
||||
&::before {
|
||||
width: 3px;
|
||||
height: 15px;
|
||||
}
|
||||
}
|
||||
|
||||
// 只读回落态(后端未重启、响应无 bills)的说明行
|
||||
@@ -222,23 +194,26 @@ function fileMeta(file: FileInfo): string {
|
||||
// 设计稿:卡片**竖排单列、定宽左对齐**(不是横排多列网格)
|
||||
&__plans {
|
||||
.flex(column, flex-start, flex-start);
|
||||
gap: @spacing-sm;
|
||||
// 设计 09:卡片间距 13 设计px × 0.77
|
||||
gap: 10px;
|
||||
}
|
||||
|
||||
// 设计 09:白底 + 1px #F0F1F3 描边、圆角 ≈13 设计px,定宽竖排
|
||||
&__plan {
|
||||
.flex(column, flex-start, stretch);
|
||||
gap: @spacing-sm;
|
||||
width: @finance-card-width;
|
||||
padding: 12px;
|
||||
padding: 14px 15px;
|
||||
border: 1px solid @project-divider;
|
||||
border-radius: @finance-card-radius;
|
||||
background: @white;
|
||||
// 设计稿用阴影立卡片、**不描边**;阴影比页面默认更淡,只做「浮起」暗示
|
||||
box-shadow: @finance-card-shadow;
|
||||
box-sizing: border-box;
|
||||
|
||||
// 三态配色(徽标实底白字 + 金额同色)
|
||||
// 三态配色(浅底徽标 + 同色系金额)
|
||||
&.is-paid {
|
||||
.project-finance__badge {
|
||||
background: @finance-paid;
|
||||
background: @tag-success-bg;
|
||||
color: @finance-paid;
|
||||
}
|
||||
|
||||
.project-finance__amount {
|
||||
@@ -248,7 +223,8 @@ function fileMeta(file: FileInfo): string {
|
||||
|
||||
&.is-pending {
|
||||
.project-finance__badge {
|
||||
background: @finance-pending;
|
||||
background: @tag-warning-bg;
|
||||
color: @tag-warning-text;
|
||||
}
|
||||
|
||||
.project-finance__amount {
|
||||
@@ -258,7 +234,8 @@ function fileMeta(file: FileInfo): string {
|
||||
|
||||
&.is-idle {
|
||||
.project-finance__badge {
|
||||
background: @finance-idle;
|
||||
background: @tag-info-bg;
|
||||
color: @text-color-secondary;
|
||||
}
|
||||
|
||||
.project-finance__amount {
|
||||
@@ -272,27 +249,27 @@ function fileMeta(file: FileInfo): string {
|
||||
gap: @spacing-sm;
|
||||
}
|
||||
|
||||
// 设计 09:期次标题 14 设计px × 0.77 ≈ 11px / 700
|
||||
&__plan-name {
|
||||
font-size: @font-size-base;
|
||||
font-size: 11px;
|
||||
font-weight: 700;
|
||||
letter-spacing: 0.8px;
|
||||
color: @heading-color;
|
||||
.ellipsis();
|
||||
}
|
||||
|
||||
// 状态徽标:实底白字的小圆角块(设计 48×22 / 圆角 4 / 10 设计px 字号)
|
||||
// 状态徽标:浅底彩色字(设计 09:约 57×22 设计px、圆角 4 设计px、11px 字)
|
||||
&__badge {
|
||||
.flex(row, center, center);
|
||||
flex-shrink: 0;
|
||||
padding: 2px @spacing-sm;
|
||||
padding: 3px 10px;
|
||||
border-radius: @radius-sm;
|
||||
font-size: 11px;
|
||||
line-height: 16px;
|
||||
color: @white;
|
||||
white-space: nowrap;
|
||||
}
|
||||
|
||||
&__plan-body {
|
||||
.flex(row, space-between, flex-start);
|
||||
.flex(row, space-between, center);
|
||||
gap: @spacing-base;
|
||||
}
|
||||
|
||||
@@ -303,29 +280,30 @@ function fileMeta(file: FileInfo): string {
|
||||
}
|
||||
|
||||
&__field {
|
||||
font-size: @font-size-sm;
|
||||
line-height: 17px;
|
||||
font-size: 11px;
|
||||
line-height: 16px;
|
||||
color: @finance-meta-color;
|
||||
.ellipsis();
|
||||
}
|
||||
|
||||
// 金额:设计稿在卡片**右侧**、字号最大且随状态变色(不是左下角恒定深色)
|
||||
// 金额:设计稿在卡片**右侧**、字号最大且随状态变色(20 设计px × 0.77 ≈ 15px)
|
||||
&__amount {
|
||||
flex-shrink: 0;
|
||||
font-size: @font-size-xl;
|
||||
font-size: 15px;
|
||||
font-weight: 700;
|
||||
line-height: 28px;
|
||||
line-height: 22px;
|
||||
white-space: nowrap;
|
||||
}
|
||||
|
||||
// 「立即支付」:设计稿是卡内**满宽**金色胶囊(不是右下角的小蓝按钮)
|
||||
// 「立即支付」:设计稿是卡内**满宽**金色按钮,通铺到卡片左右下缘
|
||||
&__pay {
|
||||
height: 22px;
|
||||
height: 28px;
|
||||
margin: 0 -15px -14px;
|
||||
border: none;
|
||||
border-radius: @radius-round;
|
||||
border-radius: 0 0 @finance-card-radius @finance-card-radius;
|
||||
background: @finance-pending;
|
||||
color: @white;
|
||||
font-size: @font-size-sm;
|
||||
font-size: 12px;
|
||||
cursor: pointer;
|
||||
transition: background 0.2s;
|
||||
|
||||
@@ -338,17 +316,18 @@ function fileMeta(file: FileInfo): string {
|
||||
|
||||
&__files {
|
||||
.flex(column, flex-start, stretch);
|
||||
gap: @spacing-sm;
|
||||
gap: 12px;
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
list-style: none;
|
||||
}
|
||||
|
||||
// 设计稿:整行通铺浅灰底、无描边无圆角(区别于卡片)
|
||||
// 设计稿:整行通铺 #F7F8FA 浅底、圆角 ≈8 设计px(区别于卡片)
|
||||
&__file {
|
||||
.flex(row, space-between, center);
|
||||
gap: @spacing-sm;
|
||||
padding: @spacing-sm @spacing-base;
|
||||
padding: 6px 14px;
|
||||
border-radius: 6px;
|
||||
background: @finance-row-bg;
|
||||
}
|
||||
|
||||
@@ -357,9 +336,9 @@ function fileMeta(file: FileInfo): string {
|
||||
.flex(row, center, center);
|
||||
flex-shrink: 0;
|
||||
width: 34px;
|
||||
height: 34px;
|
||||
height: 20px;
|
||||
border-radius: @radius-sm;
|
||||
font-size: 10px;
|
||||
font-size: 11px;
|
||||
font-weight: 700;
|
||||
letter-spacing: 0.2px;
|
||||
}
|
||||
@@ -372,27 +351,30 @@ function fileMeta(file: FileInfo): string {
|
||||
}
|
||||
|
||||
&__file-name {
|
||||
font-size: @font-size-base;
|
||||
font-size: 11px;
|
||||
line-height: 15px;
|
||||
color: @heading-color;
|
||||
.ellipsis();
|
||||
}
|
||||
|
||||
&__file-meta {
|
||||
font-size: @font-size-sm;
|
||||
color: @text-color-secondary;
|
||||
font-size: 11px;
|
||||
line-height: 15px;
|
||||
color: @text-color-disabled;
|
||||
}
|
||||
|
||||
&__file-actions {
|
||||
.flex(row, flex-end, center);
|
||||
gap: @spacing-base;
|
||||
gap: 12px;
|
||||
flex-shrink: 0;
|
||||
}
|
||||
|
||||
// 设计 09:行内操作是灰色纯文字(非蓝色)
|
||||
&__act {
|
||||
.flex(row, center, center);
|
||||
gap: 4px;
|
||||
font-size: @font-size-sm;
|
||||
color: @text-color;
|
||||
font-size: 12px;
|
||||
color: @text-color-secondary;
|
||||
cursor: pointer;
|
||||
transition: color 0.2s;
|
||||
|
||||
|
||||
@@ -67,56 +67,57 @@ function businessTypeText(project: Project): string {
|
||||
<style lang="less" scoped>
|
||||
.project-info-card {
|
||||
.flex(row, flex-start, center);
|
||||
gap: @spacing-base;
|
||||
padding: @spacing-lg;
|
||||
border-radius: @radius-lg;
|
||||
background: @white;
|
||||
box-shadow: @shadow-base;
|
||||
gap: 14px;
|
||||
// 设计 09:标识 + 文字 + 右侧状态直接排在白底页面上,无卡片底/阴影/内边距
|
||||
padding: 0;
|
||||
|
||||
&__logo {
|
||||
.flex(row, center, center);
|
||||
flex-shrink: 0;
|
||||
width: 56px;
|
||||
height: 56px;
|
||||
border-radius: 14px;
|
||||
background: @white;
|
||||
box-shadow: @shadow-base;
|
||||
// 设计 09:方块 ≈56 设计px × 0.77,浅灰底、圆角 ≈12 设计px × 0.77
|
||||
width: 44px;
|
||||
height: 44px;
|
||||
border-radius: 12px;
|
||||
background: @project-logo-bg;
|
||||
}
|
||||
|
||||
// 设计 09:方块内只有蓝色「</>」文字,无描边徽标框
|
||||
&__logo-badge {
|
||||
.flex(row, center, center);
|
||||
width: 34px;
|
||||
height: 34px;
|
||||
border: 2px solid @project-accent;
|
||||
border-radius: 10px;
|
||||
width: auto;
|
||||
height: auto;
|
||||
border: none;
|
||||
border-radius: 0;
|
||||
color: @project-accent;
|
||||
font-family: Consolas, Menlo, 'Courier New', monospace;
|
||||
font-size: @font-size-base;
|
||||
font-weight: 700;
|
||||
letter-spacing: -1px;
|
||||
font-family: inherit;
|
||||
font-size: 15px;
|
||||
font-weight: 400;
|
||||
letter-spacing: 0;
|
||||
}
|
||||
|
||||
&__main {
|
||||
.flex(column, flex-start, stretch);
|
||||
flex: 1;
|
||||
min-width: 0;
|
||||
gap: @spacing-sm;
|
||||
gap: 6px;
|
||||
}
|
||||
|
||||
// 设计 09:主标题 19 设计px × 0.77 ≈ 15px / 700
|
||||
&__name {
|
||||
font-size: @font-size-title;
|
||||
font-weight: 600;
|
||||
font-size: 15px;
|
||||
font-weight: 700;
|
||||
line-height: 1.2;
|
||||
color: @heading-color;
|
||||
.ellipsis();
|
||||
}
|
||||
|
||||
// 设计稿:三个字段是**单行**「标签:值」,等距排布
|
||||
// 设计稿:三个字段是**单行**「标签:值」,等距排布(11px 小字号不跟缩)
|
||||
&__meta {
|
||||
.flex(row, flex-start, center);
|
||||
flex-wrap: wrap;
|
||||
gap: @spacing-lg;
|
||||
font-size: @font-size-sm;
|
||||
gap: 20px;
|
||||
font-size: 11px;
|
||||
font-weight: 500;
|
||||
color: @heading-color;
|
||||
}
|
||||
|
||||
@@ -128,12 +129,14 @@ function businessTypeText(project: Project): string {
|
||||
&__label {
|
||||
color: @text-color-secondary;
|
||||
font-style: normal;
|
||||
font-weight: 400;
|
||||
}
|
||||
|
||||
// 设计 09:右侧状态是纯文字,16 设计px × 0.77 ≈ 12px / 700
|
||||
&__status {
|
||||
flex-shrink: 0;
|
||||
font-size: @font-size-title;
|
||||
font-weight: 600;
|
||||
font-size: 12px;
|
||||
font-weight: 700;
|
||||
|
||||
&.is-active {
|
||||
color: @project-accent;
|
||||
|
||||
@@ -50,7 +50,7 @@ function linkDone(index: number): boolean {
|
||||
</span>
|
||||
<span class="project-milestones__name">{{ node.name }}</span>
|
||||
<!-- 设计稿:已完成节点显示完成时间,其余显示状态文案 -->
|
||||
<span class="project-milestones__sub text-secondary">{{ node.time || node.status }}</span>
|
||||
<span class="project-milestones__sub">{{ node.time || node.status }}</span>
|
||||
</li>
|
||||
</ol>
|
||||
|
||||
@@ -61,25 +61,32 @@ function linkDone(index: number): boolean {
|
||||
</template>
|
||||
|
||||
<style lang="less" scoped>
|
||||
// 节点列宽 = 设计稿相邻节点中心距(237 设计px × 0.77 ≈ 182px)
|
||||
@milestone-node-width: 182px;
|
||||
@milestone-dot-size: 32px;
|
||||
// 节点列宽 = 设计稿相邻节点中心距(356 设计px × 0.77 ≈ 274px)
|
||||
@milestone-node-width: 274px;
|
||||
@milestone-dot-size: 18px;
|
||||
|
||||
.project-milestones {
|
||||
.flex(column, flex-start, stretch);
|
||||
padding: @spacing-lg;
|
||||
border-radius: @radius-lg;
|
||||
background: @white;
|
||||
box-shadow: @shadow-base;
|
||||
// 设计 13:里程碑区块直接落在白底页面上,无卡片
|
||||
padding: 0;
|
||||
|
||||
&__title {
|
||||
.section-title();
|
||||
// 设计 13:竖条 4×20 设计px、文字 15 设计px/700
|
||||
padding-left: 9px;
|
||||
font-size: 12px;
|
||||
font-weight: 700;
|
||||
|
||||
&::before {
|
||||
width: 3px;
|
||||
height: 15px;
|
||||
}
|
||||
}
|
||||
|
||||
// 设计稿:轨迹从卡片左侧正文位起、**固定节距**左对齐(不铺满整宽)
|
||||
// 设计稿:轨迹从容器左缘起、**固定节距**左对齐(不铺满整宽)
|
||||
&__track {
|
||||
.flex(row, flex-start, flex-start);
|
||||
margin-top: @spacing-lg;
|
||||
margin-top: 16px;
|
||||
padding-bottom: @spacing-xs;
|
||||
overflow-x: auto;
|
||||
.scrollbar();
|
||||
@@ -99,7 +106,7 @@ function linkDone(index: number): boolean {
|
||||
left: calc(50% + @milestone-dot-size / 2);
|
||||
width: calc(100% - @milestone-dot-size);
|
||||
height: 2px;
|
||||
background: @milestone-idle;
|
||||
background: @milestone-line;
|
||||
}
|
||||
|
||||
&.is-link-done:not(:last-child)::after {
|
||||
@@ -113,12 +120,15 @@ function linkDone(index: number): boolean {
|
||||
z-index: 1;
|
||||
width: @milestone-dot-size;
|
||||
height: @milestone-dot-size;
|
||||
border: 2px solid @milestone-idle;
|
||||
border: 3px solid @milestone-idle;
|
||||
border-radius: @radius-round;
|
||||
background: @white;
|
||||
box-sizing: border-box;
|
||||
|
||||
// 设计 13:已完成圆点略小(20 设计px)、实心绿
|
||||
.is-done & {
|
||||
width: 16px;
|
||||
height: 16px;
|
||||
border-color: @milestone-done;
|
||||
background: @milestone-done;
|
||||
}
|
||||
@@ -130,39 +140,40 @@ function linkDone(index: number): boolean {
|
||||
}
|
||||
|
||||
&__check {
|
||||
width: 16px;
|
||||
height: 16px;
|
||||
width: 10px;
|
||||
height: 10px;
|
||||
}
|
||||
|
||||
&__name {
|
||||
margin-top: @spacing-sm;
|
||||
max-width: 100%;
|
||||
font-size: @font-size-base;
|
||||
font-weight: 600;
|
||||
font-size: 12px;
|
||||
font-weight: 400;
|
||||
text-align: center;
|
||||
color: @text-color-secondary;
|
||||
color: @text-color;
|
||||
.multi-ellipsis(2);
|
||||
|
||||
.is-done & {
|
||||
color: @milestone-done;
|
||||
color: @success-color;
|
||||
}
|
||||
|
||||
.is-active & {
|
||||
color: @project-accent;
|
||||
font-weight: 600;
|
||||
}
|
||||
}
|
||||
|
||||
&__sub {
|
||||
margin-top: @spacing-xs;
|
||||
max-width: 100%;
|
||||
font-size: @font-size-sm;
|
||||
font-size: 11px;
|
||||
text-align: center;
|
||||
color: @text-color-disabled;
|
||||
.multi-ellipsis(2);
|
||||
}
|
||||
|
||||
&__empty {
|
||||
margin-top: @spacing-base;
|
||||
padding-left: 21px;
|
||||
font-size: @font-size-base;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -37,8 +37,8 @@ function clampPercent(value: number): number {
|
||||
</div>
|
||||
|
||||
<div class="project-progress__range">
|
||||
<span class="text-secondary">开始时间:{{ props.startTime || '—' }}</span>
|
||||
<span class="text-secondary">结束时间:{{ props.endTime || '—' }}</span>
|
||||
<span>开始时间:{{ props.startTime || '—' }}</span>
|
||||
<span>结束时间:{{ props.endTime || '—' }}</span>
|
||||
</div>
|
||||
</section>
|
||||
</template>
|
||||
@@ -46,36 +46,43 @@ function clampPercent(value: number): number {
|
||||
<style lang="less" scoped>
|
||||
.project-progress {
|
||||
.flex(column, flex-start, stretch);
|
||||
padding: @spacing-lg;
|
||||
border-radius: @radius-lg;
|
||||
background: @white;
|
||||
box-shadow: @shadow-base;
|
||||
// 设计 13:开发进度区块直接落在白底页面上,无卡片
|
||||
padding: 0;
|
||||
|
||||
&__title {
|
||||
.section-title();
|
||||
// 设计 13:竖条 4×20 设计px、文字 15 设计px/700,条→文间距 8 设计px
|
||||
padding-left: 9px;
|
||||
font-size: 12px;
|
||||
font-weight: 700;
|
||||
|
||||
&::before {
|
||||
width: 3px;
|
||||
height: 15px;
|
||||
}
|
||||
}
|
||||
|
||||
// 设计稿:正文块相对标题再右缩进一级(设计 27 设计px × 0.77 ≈ 21px)
|
||||
// 设计 13:正文与容器左缘对齐(只有标题被竖条顶出一级)
|
||||
&__head {
|
||||
.flex(row, space-between, center);
|
||||
margin-top: @spacing-base;
|
||||
padding-left: 21px;
|
||||
margin-top: 20px;
|
||||
}
|
||||
|
||||
&__label {
|
||||
font-size: @font-size-sm;
|
||||
font-size: 12px;
|
||||
}
|
||||
|
||||
// 设计 13:「65%」20 设计px × 0.77 ≈ 15px / 700
|
||||
&__percent {
|
||||
font-size: @font-size-title;
|
||||
font-weight: 600;
|
||||
font-size: 15px;
|
||||
font-weight: 700;
|
||||
color: @project-accent;
|
||||
}
|
||||
|
||||
&__track {
|
||||
position: relative;
|
||||
height: 5px;
|
||||
margin: @spacing-base 0 0 21px;
|
||||
margin: 12px 0 0;
|
||||
border-radius: @radius-round;
|
||||
background: @project-track;
|
||||
}
|
||||
@@ -87,11 +94,12 @@ function clampPercent(value: number): number {
|
||||
transition: width 0.3s;
|
||||
}
|
||||
|
||||
// 设计 13:末端白底蓝环圆点 ≈15 设计px × 0.77
|
||||
&__knob {
|
||||
position: absolute;
|
||||
top: 50%;
|
||||
width: 16px;
|
||||
height: 16px;
|
||||
width: 12px;
|
||||
height: 12px;
|
||||
border: 2px solid @project-accent;
|
||||
border-radius: @radius-round;
|
||||
background: @white;
|
||||
@@ -101,8 +109,10 @@ function clampPercent(value: number): number {
|
||||
|
||||
&__range {
|
||||
.flex(row, space-between, center);
|
||||
margin-top: @spacing-lg;
|
||||
font-size: @font-size-sm;
|
||||
margin-top: 10px;
|
||||
font-size: 11px;
|
||||
// 设计 13:起止时间 (156,163,175)
|
||||
color: @text-color-disabled;
|
||||
}
|
||||
}
|
||||
</style>
|
||||
|
||||
@@ -22,7 +22,7 @@ defineProps<Props>()
|
||||
>
|
||||
<span class="project-team__avatar">{{ member.avatarChar }}</span>
|
||||
<span class="project-team__name">{{ member.name || '—' }}</span>
|
||||
<span class="project-team__role text-secondary">{{ member.role }}</span>
|
||||
<span class="project-team__role">{{ member.role }}</span>
|
||||
</li>
|
||||
</ul>
|
||||
|
||||
@@ -33,27 +33,33 @@ defineProps<Props>()
|
||||
</template>
|
||||
|
||||
<style lang="less" scoped>
|
||||
// 设计稿实测:头像直径 90 设计px、相邻头像中心距 183 设计px → ×0.77 得 69px / 141px
|
||||
@team-avatar-size: 68px;
|
||||
@team-avatar-gap: 72px;
|
||||
// 设计稿实测:头像直径 64 设计px、相邻头像中心距 99 设计px → ×0.77 得 49px / 76px(取整 48 / 间距 28)
|
||||
@team-avatar-size: 48px;
|
||||
@team-avatar-gap: 28px;
|
||||
|
||||
.project-team {
|
||||
.flex(column, flex-start, stretch);
|
||||
padding: @spacing-lg;
|
||||
border-radius: @radius-lg;
|
||||
background: @white;
|
||||
box-shadow: @shadow-base;
|
||||
// 设计 13:项目团队区块直接落在白底页面上,无卡片
|
||||
padding: 0;
|
||||
|
||||
&__title {
|
||||
.section-title();
|
||||
// 设计 13:竖条 4×20 设计px、文字 15 设计px/700
|
||||
padding-left: 9px;
|
||||
font-size: 12px;
|
||||
font-weight: 700;
|
||||
|
||||
&::before {
|
||||
width: 3px;
|
||||
height: 15px;
|
||||
}
|
||||
}
|
||||
|
||||
&__list {
|
||||
.flex(row, flex-start, flex-start);
|
||||
flex-wrap: wrap;
|
||||
gap: @spacing-base @team-avatar-gap;
|
||||
margin-top: @spacing-lg;
|
||||
padding-left: 18px;
|
||||
margin-top: 16px;
|
||||
}
|
||||
|
||||
&__item {
|
||||
@@ -61,6 +67,7 @@ defineProps<Props>()
|
||||
width: @team-avatar-size;
|
||||
}
|
||||
|
||||
// 设计 13:头像 = 品牌蓝实底圆 + 白色单字(16 设计px × 0.77 ≈ 12px)
|
||||
&__avatar {
|
||||
.flex(row, center, center);
|
||||
width: @team-avatar-size;
|
||||
@@ -68,14 +75,15 @@ defineProps<Props>()
|
||||
border-radius: @radius-round;
|
||||
background: @team-avatar-bg;
|
||||
color: @white;
|
||||
font-size: @font-size-title;
|
||||
font-weight: 500;
|
||||
font-size: 12px;
|
||||
font-weight: 400;
|
||||
}
|
||||
|
||||
// 设计 13:姓名 16 设计px/600,角色 12 设计px #9CA3AF
|
||||
&__name {
|
||||
margin-top: @spacing-sm;
|
||||
margin-top: 16px;
|
||||
max-width: 100%;
|
||||
font-size: @font-size-lg;
|
||||
font-size: 12px;
|
||||
font-weight: 600;
|
||||
color: @heading-color;
|
||||
text-align: center;
|
||||
@@ -85,14 +93,14 @@ defineProps<Props>()
|
||||
&__role {
|
||||
margin-top: @spacing-xs;
|
||||
max-width: 100%;
|
||||
font-size: @font-size-sm;
|
||||
font-size: 12px;
|
||||
text-align: center;
|
||||
color: @text-color-disabled;
|
||||
.ellipsis();
|
||||
}
|
||||
|
||||
&__empty {
|
||||
margin-top: @spacing-base;
|
||||
padding-left: 18px;
|
||||
font-size: @font-size-base;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -211,26 +211,33 @@ onMounted(load)
|
||||
gap: @spacing-base;
|
||||
padding-top: @spacing-lg;
|
||||
padding-bottom: @spacing-xxl;
|
||||
// 设计 09/10/11/13:详情内容区是整片白底、无卡片(蓝湖实测页面底 #FFFFFF)
|
||||
background: @white;
|
||||
|
||||
// 面包屑(设计 24px × 0.77 ≈ 18px,#666666,字重 500)
|
||||
&__breadcrumb {
|
||||
font-size: @font-size-sm;
|
||||
font-size: 18px;
|
||||
font-weight: 500;
|
||||
color: @project-breadcrumb;
|
||||
}
|
||||
|
||||
// 设计稿:页签无白底容器,仅一行文字 + 激活项 2px 下划线;相邻间距实测 ≈50px
|
||||
// 设计稿:页签无白底容器,仅一行文字 + 激活项下划线,下缘 1px 通栏分割线;
|
||||
// 首个页签文字与内容区左缘对齐(间距 = 86 设计px 节距 − 文字宽 ≈ 22px)
|
||||
&__tabs {
|
||||
.flex(row, flex-start, center);
|
||||
gap: 50px;
|
||||
padding: 0 @spacing-base;
|
||||
gap: 22px;
|
||||
border-bottom: 1px solid @project-divider;
|
||||
}
|
||||
|
||||
&__tab {
|
||||
position: relative;
|
||||
padding: 0 0 @spacing-sm;
|
||||
padding: 0 0 16px;
|
||||
border: none;
|
||||
background: transparent;
|
||||
color: @text-color;
|
||||
font-size: @font-size-base;
|
||||
line-height: 20px;
|
||||
font-size: 11px;
|
||||
font-weight: 400;
|
||||
line-height: 14px;
|
||||
transition: color 0.2s;
|
||||
|
||||
&:hover {
|
||||
@@ -245,6 +252,7 @@ onMounted(load)
|
||||
|
||||
&.is-active {
|
||||
color: @project-accent;
|
||||
font-weight: 600;
|
||||
|
||||
&::after {
|
||||
content: '';
|
||||
|
||||
@@ -31,49 +31,55 @@ const emit = defineEmits<{ download: [] }>()
|
||||
<style lang="less" scoped>
|
||||
.chat-file-card {
|
||||
.flex(row, center);
|
||||
gap: @spacing-sm;
|
||||
min-width: 220px;
|
||||
gap: 8px; // 图标→文件名 11 × 0.77
|
||||
min-width: 181px; // 设计 38 文件卡宽 235 × 0.77
|
||||
max-width: 320px;
|
||||
padding: @spacing-sm @spacing-base;
|
||||
border: 1px solid @border-color;
|
||||
border-radius: @radius-base;
|
||||
padding: 10px 12px; // 卡内边距 13/15 × 0.77
|
||||
border: 1px solid @project-divider; // 设计 38 卡描边 ≈ @project-divider
|
||||
border-radius: 6px;
|
||||
background: @white;
|
||||
|
||||
&__icon {
|
||||
font-size: @font-size-xl;
|
||||
flex-shrink: 0;
|
||||
font-size: 14px;
|
||||
line-height: 1;
|
||||
}
|
||||
|
||||
&__info {
|
||||
.flex(column, flex-start);
|
||||
gap: 2px;
|
||||
.flex(column, flex-start, flex-start);
|
||||
gap: 4px;
|
||||
flex: 1;
|
||||
min-width: 0;
|
||||
}
|
||||
|
||||
// 设计 38:文件名 12 → 11 / 700 / #1F2937
|
||||
&__name {
|
||||
font-size: @font-size-base;
|
||||
font-size: 11px;
|
||||
font-weight: 700;
|
||||
color: @heading-color;
|
||||
.ellipsis();
|
||||
}
|
||||
|
||||
// 设计 38:大小 12 → 11 / #9CA3AF
|
||||
&__size {
|
||||
font-size: @font-size-sm;
|
||||
font-size: 11px;
|
||||
color: @text-color-disabled;
|
||||
}
|
||||
|
||||
&__download {
|
||||
flex-shrink: 0;
|
||||
height: 26px;
|
||||
padding: 0 @spacing-sm;
|
||||
border: 1px solid @primary-color;
|
||||
border-radius: @radius-sm;
|
||||
height: 22px;
|
||||
padding: 0 8px;
|
||||
border: 1px solid @border-color;
|
||||
border-radius: 4px;
|
||||
background: @white;
|
||||
color: @primary-color;
|
||||
font-size: @font-size-sm;
|
||||
color: @text-color-secondary;
|
||||
font-size: 11px;
|
||||
transition: all 0.2s;
|
||||
|
||||
&:hover {
|
||||
background: @primary-light;
|
||||
border-color: @primary-strong;
|
||||
color: @primary-strong;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -86,42 +86,49 @@ function onFileChange(event: Event): void {
|
||||
|
||||
<style lang="less" scoped>
|
||||
.chat-input {
|
||||
.flex(column, flex-start);
|
||||
gap: @spacing-sm;
|
||||
padding: @spacing-base;
|
||||
border-top: 1px solid @border-color;
|
||||
.flex(column, flex-start, stretch);
|
||||
gap: 16px; // 输入框→提示行 23 × 0.77
|
||||
padding: 12px 16px 24px; // 上 13 / 左右 21 / 下 36 × 0.77
|
||||
border-top: 1px solid @project-divider; // 设计 38 分割线 @project-divider
|
||||
background: @white;
|
||||
|
||||
// 设计 38:文本域灰底无描边,占位文案 #1F2937(13 → 11)
|
||||
&__textarea {
|
||||
width: 100%;
|
||||
padding: @spacing-sm @spacing-base;
|
||||
border: 1px solid @border-color;
|
||||
border-radius: @radius-base;
|
||||
background: @bg-color-light;
|
||||
color: @text-color;
|
||||
font-size: @font-size-base;
|
||||
height: 57px; // 文本域高 74 × 0.77(覆盖 rows 固有高)
|
||||
padding: 11px 10px;
|
||||
border: none;
|
||||
border-radius: 6px;
|
||||
background: @finance-row-bg; // 设计 38 实取 @finance-row-bg
|
||||
color: @heading-color;
|
||||
font-size: 11px;
|
||||
line-height: 1.6;
|
||||
resize: none;
|
||||
outline: none;
|
||||
transition: border-color 0.2s;
|
||||
transition: background 0.2s;
|
||||
box-sizing: border-box;
|
||||
|
||||
&:focus {
|
||||
border-color: @primary-color;
|
||||
border: none;
|
||||
background: @finance-row-bg;
|
||||
}
|
||||
|
||||
&::placeholder {
|
||||
color: @text-color-disabled;
|
||||
color: @heading-color; // 设计 38 占位即标注 @heading-color
|
||||
}
|
||||
}
|
||||
|
||||
&__bar {
|
||||
.flex(row, space-between);
|
||||
gap: @spacing-base;
|
||||
align-items: center;
|
||||
width: 100%;
|
||||
}
|
||||
|
||||
// 设计 38:提示 11 / #9CA3AF(覆盖 text-secondary)
|
||||
&__hint {
|
||||
font-size: @font-size-sm;
|
||||
font-size: 11px;
|
||||
color: @text-color-disabled;
|
||||
}
|
||||
|
||||
&__actions {
|
||||
@@ -131,22 +138,38 @@ function onFileChange(event: Event): void {
|
||||
|
||||
&__attach {
|
||||
.flex(row, center);
|
||||
width: 32px;
|
||||
height: 32px;
|
||||
border: 1px solid @border-color;
|
||||
border-radius: @radius-base;
|
||||
background: @white;
|
||||
font-size: @font-size-lg;
|
||||
width: 28px;
|
||||
height: 28px;
|
||||
border: none;
|
||||
border-radius: @radius-sm;
|
||||
background: transparent;
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
transition: all 0.2s;
|
||||
|
||||
&:hover {
|
||||
border-color: @primary-color;
|
||||
background: @bg-color-light;
|
||||
}
|
||||
}
|
||||
|
||||
&__file {
|
||||
display: none;
|
||||
}
|
||||
|
||||
// 「发送」:设计 38 #024FFF 小按钮(12 → 11 / 500)
|
||||
.app-button {
|
||||
height: 24px; // 31 × 0.77
|
||||
padding: 0 14px;
|
||||
border-radius: 6px;
|
||||
background: @primary-strong;
|
||||
color: @white;
|
||||
font-size: 11px;
|
||||
font-weight: 500;
|
||||
|
||||
&:hover {
|
||||
background: @primary-strong;
|
||||
color: @white;
|
||||
}
|
||||
}
|
||||
}
|
||||
</style>
|
||||
|
||||
@@ -38,70 +38,84 @@ const emit = defineEmits<{ download: [] }>()
|
||||
|
||||
<style lang="less" scoped>
|
||||
.chat-message-item {
|
||||
.flex(row, flex-start);
|
||||
gap: @spacing-sm;
|
||||
.flex(row, flex-start, flex-start); // 头像与气泡顶对齐(设计 38)
|
||||
gap: 9px; // 头像→气泡 12 × 0.77
|
||||
|
||||
// 设计 38:头像直径 36 × 0.77;客服 #024FFF,用户 #8D99AE
|
||||
&__avatar {
|
||||
flex-shrink: 0;
|
||||
.flex(row, center);
|
||||
width: 36px;
|
||||
height: 36px;
|
||||
width: 28px;
|
||||
height: 28px;
|
||||
border-radius: @radius-round;
|
||||
background: @primary-light;
|
||||
color: @primary-color;
|
||||
font-size: @font-size-base;
|
||||
font-weight: 600;
|
||||
background: @primary-strong;
|
||||
color: @white;
|
||||
font-size: 12px; // 16 → 12
|
||||
font-weight: 400;
|
||||
|
||||
&--user {
|
||||
background: fade(@success-color, 15%);
|
||||
color: @success-color;
|
||||
background: @service-user-avatar;
|
||||
color: @white;
|
||||
}
|
||||
}
|
||||
|
||||
&__main {
|
||||
.flex(column, flex-start);
|
||||
gap: @spacing-xs;
|
||||
max-width: 70%;
|
||||
.flex(column, flex-start, flex-start);
|
||||
gap: 4px;
|
||||
max-width: 320px; // 气泡最宽 ≈ 设计 410 × 0.77
|
||||
}
|
||||
|
||||
// 设计 38:客服气泡白底轻影;13 → 11 / #1F2937
|
||||
&__bubble {
|
||||
position: relative;
|
||||
padding: @spacing-sm @spacing-base;
|
||||
border-radius: @radius-base;
|
||||
padding: 9px 12px; // 内边距 12/15 × 0.77
|
||||
border-radius: 8px;
|
||||
background: @white;
|
||||
box-shadow: @shadow-base;
|
||||
color: @text-color;
|
||||
font-size: @font-size-base;
|
||||
line-height: 1.7;
|
||||
color: @heading-color;
|
||||
font-size: 11px;
|
||||
line-height: 1.75;
|
||||
white-space: pre-wrap;
|
||||
word-break: break-word;
|
||||
}
|
||||
|
||||
&__time {
|
||||
font-size: @font-size-sm;
|
||||
// 文件消息:文件卡自身成卡,气泡去内边距/底色/影(设计 38 单层卡)
|
||||
&__bubble:has(.chat-file-card) {
|
||||
padding: 0;
|
||||
background: transparent;
|
||||
box-shadow: none;
|
||||
}
|
||||
|
||||
// 设计 38:消息时间 11 / #9CA3AF
|
||||
&__time {
|
||||
font-size: 11px;
|
||||
color: @text-color-disabled;
|
||||
}
|
||||
|
||||
// 设计 38:「未读」挂在文件卡左下外侧,10 → 11 / #9CA3AF,无底色
|
||||
&__unread {
|
||||
position: absolute;
|
||||
top: -8px;
|
||||
right: -6px;
|
||||
padding: 0 6px;
|
||||
border-radius: @radius-round;
|
||||
background: @danger-color;
|
||||
color: @white;
|
||||
font-size: @font-size-sm;
|
||||
line-height: 16px;
|
||||
top: 100%;
|
||||
left: 0;
|
||||
margin-top: 6px;
|
||||
padding: 0;
|
||||
background: transparent;
|
||||
color: @text-color-disabled;
|
||||
font-size: 11px;
|
||||
font-weight: 400;
|
||||
line-height: 1.3;
|
||||
}
|
||||
|
||||
&--user {
|
||||
.flex(row, flex-end);
|
||||
.flex(row, flex-end, flex-start);
|
||||
|
||||
.chat-message-item__main {
|
||||
align-items: flex-end;
|
||||
}
|
||||
|
||||
// 设计 38:我方气泡 #024FFF 白字
|
||||
.chat-message-item__bubble {
|
||||
background: @primary-color;
|
||||
background: @primary-strong;
|
||||
color: @white;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -42,16 +42,21 @@ watch(
|
||||
|
||||
<template>
|
||||
<div class="chat-window">
|
||||
<div class="chat-window__header">
|
||||
<span class="chat-window__header-avatar" />
|
||||
<span class="chat-window__header-name">专属客服</span>
|
||||
</div>
|
||||
|
||||
<div ref="scrollRef" class="chat-window__scroll">
|
||||
<template v-for="(item, index) in messages" :key="item.id">
|
||||
<div v-if="index === 0" class="chat-window__divider text-secondary">
|
||||
—— 历史消息 ——
|
||||
</div>
|
||||
<ChatMessageItem
|
||||
:message="item"
|
||||
:unread="isUnread(index)"
|
||||
@download="onDownload"
|
||||
/>
|
||||
<div v-if="index === 0" class="chat-window__divider text-secondary">
|
||||
—— 历史消息 ——
|
||||
</div>
|
||||
</template>
|
||||
</div>
|
||||
|
||||
@@ -61,35 +66,57 @@ watch(
|
||||
|
||||
<style lang="less" scoped>
|
||||
.chat-window {
|
||||
.flex(column, flex-start);
|
||||
.flex(column, flex-start, stretch);
|
||||
border-radius: @radius-lg;
|
||||
background: @bg-color;
|
||||
background: @white;
|
||||
box-shadow: @shadow-base;
|
||||
overflow: hidden;
|
||||
|
||||
// 设计 38:顶栏白底,高 60 × 0.77,下缘 #F0F1F3 分割线
|
||||
&__header {
|
||||
.flex(row, flex-start);
|
||||
gap: 11px; // 头像→文字 14 × 0.77
|
||||
height: 46px;
|
||||
padding: 0 16px; // 21 × 0.77
|
||||
border-bottom: 1px solid @project-divider;
|
||||
background: @white;
|
||||
}
|
||||
|
||||
// 设计 38:头像直径 36 × 0.77,实取 #024FFF
|
||||
&__header-avatar {
|
||||
flex-shrink: 0;
|
||||
width: 28px;
|
||||
height: 28px;
|
||||
border-radius: @radius-round;
|
||||
background: @primary-strong;
|
||||
}
|
||||
|
||||
// 设计 38:「专属客服」14 → 11 / 700 / #1F2937
|
||||
&__header-name {
|
||||
align-self: center;
|
||||
font-size: 11px;
|
||||
font-weight: 700;
|
||||
color: @heading-color;
|
||||
}
|
||||
|
||||
&__scroll {
|
||||
.flex(column, flex-start);
|
||||
gap: @spacing-base;
|
||||
.flex(column, flex-start, stretch);
|
||||
gap: 56px; // 消息组纵向间距(设计 38 组间 69~82 × 0.77)
|
||||
max-height: 60vh;
|
||||
min-height: 320px;
|
||||
padding: @spacing-lg;
|
||||
min-height: 347px; // 消息区高 451 × 0.77
|
||||
padding: 22px 16px; // 上 29 / 左右 21 × 0.77
|
||||
background: @bg-color-light; // 设计 38 消息区实取 #FAFBFC
|
||||
overflow-y: auto;
|
||||
.scrollbar();
|
||||
}
|
||||
|
||||
// 设计 38:时间分割文字 11 / #9CA3AF,短横已含在文案内,无两侧线
|
||||
&__divider {
|
||||
.flex(row, center);
|
||||
gap: @spacing-base;
|
||||
font-size: @font-size-sm;
|
||||
flex-shrink: 0;
|
||||
margin-bottom: -42px; // 分割线→首条 14(抵消组间距 56)
|
||||
font-size: 11px;
|
||||
color: @text-color-disabled;
|
||||
text-align: center;
|
||||
|
||||
&::before,
|
||||
&::after {
|
||||
content: '';
|
||||
flex: 1;
|
||||
height: 1px;
|
||||
background: @border-color;
|
||||
}
|
||||
}
|
||||
}
|
||||
</style>
|
||||
|
||||
@@ -42,20 +42,33 @@ onMounted(() => {
|
||||
|
||||
<style lang="less" scoped>
|
||||
.service {
|
||||
.flex(column, flex-start);
|
||||
gap: @spacing-base;
|
||||
padding-top: @spacing-xl;
|
||||
padding-bottom: @spacing-xxl;
|
||||
.flex(column, flex-start, stretch);
|
||||
gap: @spacing-base; // 头部→聊天卡 19 × 0.77
|
||||
max-width: @container-width;
|
||||
min-height: calc(100vh - @header-height);
|
||||
margin: 0 auto;
|
||||
padding: 25px @spacing-base @spacing-xxl; // 标题上留白 32 × 0.77
|
||||
background: @white; // 设计 38 页面底色为纯白
|
||||
|
||||
&__title {
|
||||
font-size: @font-size-xxl;
|
||||
font-weight: 600;
|
||||
color: @heading-color;
|
||||
// 设计 38:头部文案左缩进 42 × 0.77(标题 x112 相对内容边 x70)
|
||||
&__head {
|
||||
padding-left: 32px;
|
||||
}
|
||||
|
||||
// 设计 38:大标题 36 → 28 / 700 / #121212
|
||||
&__title {
|
||||
font-size: @font-size-xxl;
|
||||
font-weight: 700;
|
||||
color: @home-ink;
|
||||
}
|
||||
|
||||
// 设计 38:副标题 24 → 18 / 500 / #666666
|
||||
&__subtitle {
|
||||
margin-top: @spacing-xs;
|
||||
font-size: @font-size-base;
|
||||
margin-top: 12px; // 标题→副标题 15 × 0.77
|
||||
font-size: 18px;
|
||||
font-weight: 500;
|
||||
line-height: 1.5;
|
||||
color: @contract-muted;
|
||||
}
|
||||
}
|
||||
</style>
|
||||
|
||||
Reference in New Issue
Block a user