update AIChart, customer followup, media selector
This commit is contained in:
@@ -34,8 +34,8 @@
|
||||
</t-cell>
|
||||
</t-cell-group>
|
||||
<card-container v-entrance-transition="140">
|
||||
<photo-scroller
|
||||
class="photo-scroller"
|
||||
<media-selector
|
||||
class="media-selector"
|
||||
:model-value="photoList"
|
||||
:photo-items="photoItemList"
|
||||
:show-viewer-actions="canUpdateCustomer"
|
||||
@@ -98,6 +98,9 @@
|
||||
<t-cell-group theme="card">
|
||||
<t-cell title="邀请客户" :note="inviteeCountText" arrow @click="toInviteeList" />
|
||||
</t-cell-group>
|
||||
<t-cell-group v-if="canReadFollowUpReminder" title="客户跟进" theme="card">
|
||||
<t-cell title="跟进提醒" note="查看客户提醒" arrow @click="toFollowUpReminderList" />
|
||||
</t-cell-group>
|
||||
<t-button
|
||||
v-can="permissionCodes.customer.delete"
|
||||
class="delete-action"
|
||||
@@ -142,7 +145,7 @@ import TagAPI from "@/api/TagAPI";
|
||||
import BodyAreaSelector from "@/components/BodyAreaSelector.vue";
|
||||
import CustomerRemoveDialog from "@/pages/customer/component/CustomerRemoveDialog.vue";
|
||||
import CustomerProfileCard from "@/components/CustomerProfileCard.vue";
|
||||
import PhotoScroller from "@/components/PhotoScroller.vue";
|
||||
import MediaSelector from "@/components/mediaSelector/MediaSelector.vue";
|
||||
import TagSelector from "@/components/TagSelector.vue";
|
||||
import CustomerTagCard from "@/pages/customer/component/CustomerTagCard.vue";
|
||||
import { useNavBarStore } from "@/store/navBarStore";
|
||||
@@ -177,6 +180,7 @@ const canReadSalesOrder = computed(() => userStore.hasPermissions(permissionCode
|
||||
const canReadTag = computed(() => userStore.hasPermissions(corePermissionCodes.tag.read));
|
||||
const canApplyTag = computed(() => userStore.hasPermissions(corePermissionCodes.tag.apply));
|
||||
const canUpdateCustomer = computed(() => userStore.hasPermissions(permissionCodes.customer.update));
|
||||
const canReadFollowUpReminder = computed(() => userStore.hasPermissions(permissionCodes.customerFollowUpReminder.read));
|
||||
|
||||
// ---------- 资料 ----------
|
||||
|
||||
@@ -389,6 +393,16 @@ async function toInviteeList(): Promise<void> {
|
||||
await router.push(`/management/customers/${customer.value.id}/invitees`);
|
||||
}
|
||||
|
||||
async function toFollowUpReminderList(): Promise<void> {
|
||||
if (!customer.value?.id || !canReadFollowUpReminder.value) {
|
||||
return;
|
||||
}
|
||||
await router.push({
|
||||
name: "CustomerFollowUpReminderList",
|
||||
query: { customerId: customer.value.id }
|
||||
});
|
||||
}
|
||||
|
||||
async function toEventRecordList(): Promise<void> {
|
||||
if (!canReadEventRecord.value || !customer.value?.id) {
|
||||
return;
|
||||
@@ -531,7 +545,7 @@ onUnmounted(() => navBarStore.clearRight());
|
||||
}
|
||||
}
|
||||
|
||||
:deep(.photo-scroller) {
|
||||
:deep(.media-selector) {
|
||||
padding: 1rem;
|
||||
}
|
||||
|
||||
|
||||
@@ -71,7 +71,7 @@
|
||||
</t-form-item>
|
||||
<t-form-item label-width="0">
|
||||
<div class="photo">
|
||||
<photo-scroller
|
||||
<media-selector
|
||||
v-model="photoList"
|
||||
v-model:photo-items="photoItemList"
|
||||
:edit-mode="true"
|
||||
@@ -80,8 +80,10 @@
|
||||
:show-viewer-actions="!isCustomerBound"
|
||||
:add-actions="photoAddActions"
|
||||
:loading="isPhotoUploading"
|
||||
@add-photo="openPhotoPicker('PHOTO')"
|
||||
@add-point-card="openPhotoPicker('POINT_CARD')"
|
||||
@add="openPhotoPicker('OTHER')"
|
||||
@capture-photo="capturePhoto"
|
||||
@capture-video="captureVideo"
|
||||
@add-point-card="capturePointCard"
|
||||
@add-other="openPhotoPicker('OTHER')"
|
||||
/>
|
||||
<div class="tips orange" v-if="!hasCustomerDeletePermission">当前账户权限编辑客户需要上传照片和积分卡</div>
|
||||
@@ -176,7 +178,23 @@
|
||||
ref="photoInputRef"
|
||||
class="file-input"
|
||||
type="file"
|
||||
accept="*/*"
|
||||
@change="handlePhotoSelected"
|
||||
>
|
||||
<input
|
||||
ref="photoCameraInputRef"
|
||||
class="file-input"
|
||||
type="file"
|
||||
accept="image/*"
|
||||
capture="environment"
|
||||
@change="handlePhotoSelected"
|
||||
>
|
||||
<input
|
||||
ref="videoInputRef"
|
||||
class="file-input"
|
||||
type="file"
|
||||
accept="video/*"
|
||||
capture="environment"
|
||||
@change="handlePhotoSelected"
|
||||
>
|
||||
<customer-selector
|
||||
@@ -213,7 +231,7 @@ import BodyAreaSelector from "@/components/BodyAreaSelector.vue";
|
||||
import CodeScanner from "@/components/CodeScanner.vue";
|
||||
import CustomerProfileCard from "@/components/CustomerProfileCard.vue";
|
||||
import CustomerSelector from "@/components/CustomerSelector.vue";
|
||||
import PhotoScroller from "@/components/PhotoScroller.vue";
|
||||
import MediaSelector from "@/components/mediaSelector/MediaSelector.vue";
|
||||
import TagSelector from "@/components/TagSelector.vue";
|
||||
import CustomerTagCard from "@/pages/customer/component/CustomerTagCard.vue";
|
||||
import { useCurrentStoreStore } from "@/store/currentStoreStore";
|
||||
@@ -442,6 +460,30 @@ function openPhotoPicker(target: CustomerAttachmentType): void {
|
||||
photoInputRef.value?.click();
|
||||
}
|
||||
|
||||
function capturePhoto(): void {
|
||||
if (isCustomerBound.value) {
|
||||
return;
|
||||
}
|
||||
photoPickerTarget.value = "PHOTO";
|
||||
photoCameraInputRef.value?.click();
|
||||
}
|
||||
|
||||
function capturePointCard(): void {
|
||||
if (isCustomerBound.value) {
|
||||
return;
|
||||
}
|
||||
photoPickerTarget.value = "POINT_CARD";
|
||||
photoCameraInputRef.value?.click();
|
||||
}
|
||||
|
||||
function captureVideo(): void {
|
||||
if (isCustomerBound.value) {
|
||||
return;
|
||||
}
|
||||
photoPickerTarget.value = "OTHER";
|
||||
videoInputRef.value?.click();
|
||||
}
|
||||
|
||||
watch(isCustomerBound, (value) => {
|
||||
navBarStore.setRightDisabled(value);
|
||||
if (!value) {
|
||||
@@ -485,6 +527,7 @@ async function loadDetail() {
|
||||
.map(item => ({
|
||||
attachment: item,
|
||||
attachType: normalizeAttachmentType(item.attachType),
|
||||
mimeType: item.mimeType,
|
||||
previewUrl: getAttachmentReadURL(item.id || ""),
|
||||
url: getAttachmentReadURL(item.id || "", 90)
|
||||
}));
|
||||
@@ -531,24 +574,14 @@ watch(() => formData.birthdate, (value) => {
|
||||
// ---------- 照片 ----------
|
||||
|
||||
const photoInputRef = ref<HTMLInputElement>();
|
||||
const photoCameraInputRef = ref<HTMLInputElement>();
|
||||
const videoInputRef = ref<HTMLInputElement>();
|
||||
const photoAddActions = [
|
||||
{
|
||||
icon: "user-avatar",
|
||||
text: "拍照片",
|
||||
emit: "add-photo",
|
||||
theme: "primary"
|
||||
},
|
||||
{
|
||||
icon: "cardmembership",
|
||||
text: "拍积分卡",
|
||||
emit: "add-point-card",
|
||||
theme: "primary"
|
||||
},
|
||||
{
|
||||
icon: "file-attachment",
|
||||
text: "其他文件",
|
||||
emit: "add-other",
|
||||
theme: "default"
|
||||
}
|
||||
] as const;
|
||||
const photoPickerTarget = ref<CustomerAttachmentType>("PHOTO");
|
||||
@@ -602,6 +635,7 @@ async function handlePhotoSelected(event: Event): Promise<void> {
|
||||
if (tempFile?.id) {
|
||||
photoItemList.value.push({
|
||||
attachType: photoPickerTarget.value,
|
||||
mimeType: file.type,
|
||||
tempFileId: tempFile.id,
|
||||
url: AttachmentAPI.getTempReadURL(tempFile.id)
|
||||
});
|
||||
|
||||
Reference in New Issue
Block a user