feat: migrate CRM screens to Ant Design Vue and expand home dashboard
Preserve the local Ant UI work across views/components and add the new home dashboard chart panels before merging latest main.
This commit is contained in:
@@ -4,8 +4,20 @@ import { RouterLink } from 'vue-router';
|
||||
import axios from 'axios';
|
||||
import { api } from '@/lib/api';
|
||||
import { rewriteGregorianDates } from '@/lib/jalali';
|
||||
import UiIcon from '@/components/UiIcon.vue';
|
||||
import { brand, type AskMentoResponse, type AskMentoSourceDto } from '@mento/shared';
|
||||
import {
|
||||
Alert as AAlert,
|
||||
Button as AButton,
|
||||
Card as ACard,
|
||||
Flex as AFlex,
|
||||
Input as AInput,
|
||||
Space as ASpace,
|
||||
Tag as ATag,
|
||||
Typography,
|
||||
} from 'ant-design-vue';
|
||||
import { ThunderboltOutlined } from '@ant-design/icons-vue';
|
||||
|
||||
const { Paragraph: ATypographyParagraph } = Typography;
|
||||
|
||||
const props = defineProps<{
|
||||
personId?: string;
|
||||
@@ -65,127 +77,53 @@ function insertAnswer() {
|
||||
</script>
|
||||
|
||||
<template>
|
||||
<section class="ask">
|
||||
<form @submit.prevent="submit">
|
||||
<UiIcon name="sparkle" :size="16" class="ico" />
|
||||
<input
|
||||
v-model="question"
|
||||
type="search"
|
||||
<a-flex vertical :gap="8" :style="{ minWidth: 0 }">
|
||||
<a-flex :gap="8" align="center" :style="{ width: '100%' }">
|
||||
<a-input
|
||||
v-model:value="question"
|
||||
allow-clear
|
||||
:placeholder="placeholder || brand.askPlaceholderFa"
|
||||
/>
|
||||
<button type="submit" :disabled="asking || question.trim().length < 2">
|
||||
{{ asking ? '…' : 'بپرس' }}
|
||||
</button>
|
||||
</form>
|
||||
<p v-if="error" class="error">{{ error }}</p>
|
||||
<div v-else-if="result" class="answer">
|
||||
<p>{{ result.answer }}</p>
|
||||
<div v-if="result.sources.length" class="sources">
|
||||
:style="{ flex: 1, minWidth: 0 }"
|
||||
@pressEnter="submit"
|
||||
>
|
||||
<template #prefix>
|
||||
<ThunderboltOutlined />
|
||||
</template>
|
||||
</a-input>
|
||||
<a-button
|
||||
type="primary"
|
||||
:disabled="asking || question.trim().length < 2"
|
||||
:loading="asking"
|
||||
@click="submit"
|
||||
>
|
||||
بپرس
|
||||
</a-button>
|
||||
</a-flex>
|
||||
|
||||
<a-alert v-if="error" type="error" show-icon :message="error" />
|
||||
|
||||
<a-card v-else-if="result" :bordered="false">
|
||||
<a-typography-paragraph :style="{ marginBottom: 0 }">
|
||||
{{ result.answer }}
|
||||
</a-typography-paragraph>
|
||||
<a-space v-if="result.sources.length" wrap :size="6" :style="{ marginTop: '8px' }">
|
||||
<RouterLink
|
||||
v-for="source in result.sources"
|
||||
:key="`${source.type}-${source.id}`"
|
||||
:to="sourceTo(source)"
|
||||
>
|
||||
{{ source.label }}
|
||||
<a-tag color="cyan" :bordered="false">{{ source.label }}</a-tag>
|
||||
</RouterLink>
|
||||
</div>
|
||||
<button
|
||||
</a-space>
|
||||
<a-button
|
||||
v-if="allowInsert && result.answer.trim()"
|
||||
type="button"
|
||||
class="insert-btn"
|
||||
type="primary"
|
||||
block
|
||||
:style="{ marginTop: '8px' }"
|
||||
@click="insertAnswer"
|
||||
>
|
||||
درج در پیام
|
||||
</button>
|
||||
</div>
|
||||
</section>
|
||||
</a-button>
|
||||
</a-card>
|
||||
</a-flex>
|
||||
</template>
|
||||
|
||||
<style scoped>
|
||||
.ask {
|
||||
display: grid;
|
||||
gap: 0.55rem;
|
||||
min-width: 0;
|
||||
}
|
||||
|
||||
form {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
gap: 0.45rem;
|
||||
background: #fff;
|
||||
border: 1px solid #e2e8f0;
|
||||
border-radius: var(--radius);
|
||||
padding: 0.35rem 0.4rem 0.35rem 0.7rem;
|
||||
}
|
||||
|
||||
.ico {
|
||||
color: #0f766e;
|
||||
flex-shrink: 0;
|
||||
}
|
||||
|
||||
input {
|
||||
flex: 1;
|
||||
min-width: 0;
|
||||
border: 0;
|
||||
background: transparent;
|
||||
font: inherit;
|
||||
padding: 0.45rem 0;
|
||||
}
|
||||
|
||||
button {
|
||||
border: 0;
|
||||
border-radius: var(--radius);
|
||||
background: #14b8a6;
|
||||
color: #fff;
|
||||
font: inherit;
|
||||
font-weight: 700;
|
||||
padding: 0.45rem 0.8rem;
|
||||
cursor: pointer;
|
||||
}
|
||||
|
||||
button:disabled {
|
||||
opacity: 0.55;
|
||||
cursor: wait;
|
||||
}
|
||||
|
||||
.answer {
|
||||
background: #f0fdfa;
|
||||
border-radius: var(--radius);
|
||||
padding: 0.7rem 0.85rem;
|
||||
}
|
||||
|
||||
.answer p {
|
||||
margin: 0;
|
||||
color: #134e4a;
|
||||
font-size: 0.88rem;
|
||||
line-height: 1.7;
|
||||
}
|
||||
|
||||
.sources {
|
||||
display: flex;
|
||||
flex-wrap: wrap;
|
||||
gap: 0.35rem;
|
||||
margin-top: 0.55rem;
|
||||
}
|
||||
|
||||
.sources a {
|
||||
font-size: 0.74rem;
|
||||
font-weight: 700;
|
||||
color: #0f766e;
|
||||
background: #fff;
|
||||
border-radius: 999px;
|
||||
padding: 0.18rem 0.55rem;
|
||||
}
|
||||
|
||||
.insert-btn {
|
||||
margin-top: 0.65rem;
|
||||
width: 100%;
|
||||
background: #0f766e;
|
||||
}
|
||||
|
||||
.error {
|
||||
margin: 0;
|
||||
color: #b91c1c;
|
||||
font-size: 0.84rem;
|
||||
}
|
||||
</style>
|
||||
|
||||
Reference in New Issue
Block a user