fix: show call log details in modal
This commit is contained in:
parent
ceb54a2d36
commit
d9a2d7098a
@ -69,6 +69,10 @@ class CRMCallLog(Document):
|
||||
"duration",
|
||||
"from",
|
||||
"to",
|
||||
"note",
|
||||
"recording_url",
|
||||
"reference_doctype",
|
||||
"reference_docname",
|
||||
"creation",
|
||||
]
|
||||
return {'columns': columns, 'rows': rows}
|
||||
|
||||
23
frontend/src/components/Icons/CheckCircleIcon.vue
Normal file
23
frontend/src/components/Icons/CheckCircleIcon.vue
Normal file
@ -0,0 +1,23 @@
|
||||
<template>
|
||||
<svg
|
||||
width="16"
|
||||
height="16"
|
||||
viewBox="0 0 16 16"
|
||||
fill="none"
|
||||
xmlns="http://www.w3.org/2000/svg"
|
||||
>
|
||||
<g clip-path="url(#clip0_3668_69185)">
|
||||
<path
|
||||
fill-rule="evenodd"
|
||||
clip-rule="evenodd"
|
||||
d="M14.25 8C14.25 11.4518 11.4518 14.25 8 14.25C4.54822 14.25 1.75 11.4518 1.75 8C1.75 4.54822 4.54822 1.75 8 1.75C11.4518 1.75 14.25 4.54822 14.25 8ZM15.25 8C15.25 12.0041 12.0041 15.25 8 15.25C3.99594 15.25 0.75 12.0041 0.75 8C0.75 3.99594 3.99594 0.75 8 0.75C12.0041 0.75 15.25 3.99594 15.25 8ZM11.2909 5.98482C11.4666 5.77175 11.4363 5.45663 11.2232 5.28096C11.0101 5.1053 10.695 5.13561 10.5193 5.34868L7.07001 9.53239L5.72845 7.79857C5.55946 7.58018 5.24543 7.54012 5.02703 7.70911C4.80863 7.8781 4.76858 8.19214 4.93756 8.41053L6.66217 10.6394C6.7552 10.7596 6.89788 10.831 7.04988 10.8334C7.20188 10.8357 7.3467 10.7688 7.4434 10.6515L11.2909 5.98482Z"
|
||||
fill="currentColor"
|
||||
/>
|
||||
</g>
|
||||
<defs>
|
||||
<clipPath id="clip0_3668_69185">
|
||||
<rect width="16" height="16" fill="white" />
|
||||
</clipPath>
|
||||
</defs>
|
||||
</svg>
|
||||
</template>
|
||||
@ -3,10 +3,7 @@
|
||||
:columns="columns"
|
||||
:rows="rows"
|
||||
:options="{
|
||||
getRowRoute: (row) => ({
|
||||
name: 'Call Log',
|
||||
params: { callLogId: row.name },
|
||||
}),
|
||||
onRowClick: (row) => emit('showCallLog', row.name),
|
||||
selectable: options.selectable,
|
||||
showTooltip: options.showTooltip,
|
||||
resizeColumn: options.resizeColumn,
|
||||
|
||||
185
frontend/src/components/Modals/CallLogModal.vue
Normal file
185
frontend/src/components/Modals/CallLogModal.vue
Normal file
@ -0,0 +1,185 @@
|
||||
<template>
|
||||
<Dialog v-model="show">
|
||||
<template #body-title>
|
||||
<div class="flex items-center gap-3">
|
||||
<h3 class="text-2xl font-semibold leading-6 text-gray-900">
|
||||
{{ __('Call Details') }}
|
||||
</h3>
|
||||
</div>
|
||||
</template>
|
||||
<template #body-content>
|
||||
<div class="flex flex-col gap-3.5">
|
||||
<div
|
||||
v-for="field in detailFields"
|
||||
:key="field.name"
|
||||
class="flex h-7 items-center gap-2 text-base text-gray-800"
|
||||
>
|
||||
<div class="grid w-7 place-content-center">
|
||||
<component :is="field.icon" />
|
||||
</div>
|
||||
<div v-if="field.name == 'receiver'" class="flex items-center gap-1">
|
||||
<Avatar
|
||||
:image="field.value.caller.image"
|
||||
:label="field.value.caller.label"
|
||||
size="sm"
|
||||
/>
|
||||
<div class="ml-1 flex flex-col gap-1">
|
||||
{{ field.value.caller.label }}
|
||||
</div>
|
||||
<FeatherIcon
|
||||
name="arrow-right"
|
||||
class="mx-1 h-4 w-4 text-gray-600"
|
||||
/>
|
||||
<Avatar
|
||||
:image="field.value.receiver.image"
|
||||
:label="field.value.receiver.label"
|
||||
size="sm"
|
||||
/>
|
||||
<div class="ml-1 flex flex-col gap-1">
|
||||
{{ field.value.receiver.label }}
|
||||
</div>
|
||||
</div>
|
||||
<Tooltip v-else-if="field.tooltip" :text="field.tooltip">
|
||||
{{ field.value }}
|
||||
</Tooltip>
|
||||
<div v-else-if="field.name == 'recording_url'">
|
||||
<audio class="audio-control" controls :src="field.value"></audio>
|
||||
</div>
|
||||
<div v-else :class="field.color ? `text-${field.color}-600` : ''">
|
||||
{{ field.value }}
|
||||
</div>
|
||||
<div v-if="field.link">
|
||||
<ArrowUpRightIcon
|
||||
class="h-4 w-4 shrink-0 cursor-pointer text-gray-600 hover:text-gray-800"
|
||||
@click="() => field.link()"
|
||||
/>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</template>
|
||||
</Dialog>
|
||||
</template>
|
||||
|
||||
<script setup>
|
||||
import ArrowUpRightIcon from '@/components/Icons/ArrowUpRightIcon.vue'
|
||||
import DurationIcon from '@/components/Icons/DurationIcon.vue'
|
||||
import ContactsIcon from '@/components/Icons/ContactsIcon.vue'
|
||||
import LeadsIcon from '@/components/Icons/LeadsIcon.vue'
|
||||
import Dealsicon from '@/components/Icons/DealsIcon.vue'
|
||||
import CalendarIcon from '@/components/Icons/CalendarIcon.vue'
|
||||
import NoteIcon from '@/components/Icons/NoteIcon.vue'
|
||||
import CheckCircleIcon from '@/components/Icons/CheckCircleIcon.vue'
|
||||
// import NoteModal from '@/components/Modals/NoteModal.vue'
|
||||
import { FeatherIcon, Avatar, Tooltip, createResource } from 'frappe-ui'
|
||||
import { ref, computed, h } from 'vue'
|
||||
import { useRouter } from 'vue-router'
|
||||
|
||||
const props = defineProps({
|
||||
callLog: {
|
||||
type: Object,
|
||||
default: {},
|
||||
},
|
||||
})
|
||||
|
||||
const show = defineModel()
|
||||
const router = useRouter()
|
||||
|
||||
const detailFields = computed(() => {
|
||||
let details = [
|
||||
{
|
||||
icon: h(FeatherIcon, {
|
||||
name: props.callLog.type.icon,
|
||||
class: 'h-3.5 w-3.5',
|
||||
}),
|
||||
name: 'type',
|
||||
value: props.callLog.type.label + ' Call',
|
||||
},
|
||||
{
|
||||
icon: ContactsIcon,
|
||||
name: 'receiver',
|
||||
value: {
|
||||
receiver: props.callLog.receiver,
|
||||
caller: props.callLog.caller,
|
||||
},
|
||||
},
|
||||
{
|
||||
icon:
|
||||
props.callLog.reference_doctype == 'CRM Lead' ? LeadsIcon : Dealsicon,
|
||||
name: 'reference_doctype',
|
||||
value: props.callLog.reference_doctype == 'CRM Lead' ? 'Lead' : 'Deal',
|
||||
link: () => {
|
||||
if (props.callLog.reference_doctype == 'CRM Lead') {
|
||||
router.push({
|
||||
name: 'Lead',
|
||||
params: { leadId: props.callLog.reference_docname },
|
||||
})
|
||||
} else {
|
||||
router.push({
|
||||
name: 'Deal',
|
||||
params: { dealId: props.callLog.reference_docname },
|
||||
})
|
||||
}
|
||||
},
|
||||
},
|
||||
{
|
||||
icon: CalendarIcon,
|
||||
name: 'creation',
|
||||
value: props.callLog.creation.label,
|
||||
tooltip: props.callLog.creation.label,
|
||||
},
|
||||
{
|
||||
icon: DurationIcon,
|
||||
name: 'duration',
|
||||
value: props.callLog.duration.label,
|
||||
},
|
||||
{
|
||||
icon: CheckCircleIcon,
|
||||
name: 'status',
|
||||
value: props.callLog.status.label,
|
||||
color: props.callLog.status.color,
|
||||
},
|
||||
{
|
||||
icon: h(FeatherIcon, {
|
||||
name: 'play',
|
||||
class: 'h-3.5 w-3.5',
|
||||
}),
|
||||
name: 'recording_url',
|
||||
value: props.callLog.recording_url,
|
||||
},
|
||||
{
|
||||
icon: NoteIcon,
|
||||
name: 'note',
|
||||
value: props.callLog.note,
|
||||
},
|
||||
]
|
||||
|
||||
return details.filter((detail) => detail.value)
|
||||
})
|
||||
|
||||
async function updateNote(_note) {
|
||||
if (_note.title || _note.content) {
|
||||
let d = await call('frappe.client.set_value', {
|
||||
doctype: 'CRM Note',
|
||||
name: _callLog.data?.note,
|
||||
fieldname: _note,
|
||||
})
|
||||
if (d.name) {
|
||||
_callLog.reload()
|
||||
}
|
||||
}
|
||||
}
|
||||
</script>
|
||||
|
||||
<style scoped>
|
||||
.audio-control {
|
||||
height: 40px;
|
||||
outline: none;
|
||||
border-radius: 10px;
|
||||
border: 1px solid gray;
|
||||
cursor: pointer;
|
||||
}
|
||||
|
||||
.audio-control::-webkit-media-controls-panel {
|
||||
background-color: white;
|
||||
}
|
||||
</style>
|
||||
@ -31,6 +31,7 @@
|
||||
rowCount: callLogs.data.row_count,
|
||||
totalCount: callLogs.data.total_count,
|
||||
}"
|
||||
@showCallLog="showCallLog"
|
||||
@loadMore="() => loadMore++"
|
||||
@columnWidthUpdated="() => triggerResize++"
|
||||
@updatePageCount="(count) => (updatedPageCount = count)"
|
||||
@ -47,6 +48,11 @@
|
||||
<span>{{ __('No Logs Found') }}</span>
|
||||
</div>
|
||||
</div>
|
||||
<CallLogModal
|
||||
v-model="showCallLogModal"
|
||||
v-model:reloadCallLogs="callLogs"
|
||||
:callLog="callLog"
|
||||
/>
|
||||
</template>
|
||||
|
||||
<script setup>
|
||||
@ -55,6 +61,7 @@ import PhoneIcon from '@/components/Icons/PhoneIcon.vue'
|
||||
import LayoutHeader from '@/components/LayoutHeader.vue'
|
||||
import ViewControls from '@/components/ViewControls.vue'
|
||||
import CallLogsListView from '@/components/ListViews/CallLogsListView.vue'
|
||||
import CallLogModal from '@/components/Modals/CallLogModal.vue'
|
||||
import {
|
||||
secondsToDuration,
|
||||
dateFormat,
|
||||
@ -139,6 +146,44 @@ const rows = computed(() => {
|
||||
})
|
||||
})
|
||||
|
||||
const showCallLogModal = ref(false)
|
||||
|
||||
const callLog = ref({
|
||||
name: '',
|
||||
caller: '',
|
||||
receiver: '',
|
||||
duration: '',
|
||||
type: '',
|
||||
status: '',
|
||||
from: '',
|
||||
to: '',
|
||||
note: '',
|
||||
recording_url: '',
|
||||
reference_doctype: '',
|
||||
reference_docname: '',
|
||||
creation: '',
|
||||
})
|
||||
|
||||
function showCallLog(name) {
|
||||
let d = rows.value?.find((row) => row.name === name)
|
||||
callLog.value = {
|
||||
name: d.name,
|
||||
caller: d.caller,
|
||||
receiver: d.receiver,
|
||||
duration: d.duration,
|
||||
type: d.type,
|
||||
status: d.status,
|
||||
from: d.from,
|
||||
to: d.to,
|
||||
note: d.note,
|
||||
recording_url: d.recording_url,
|
||||
reference_doctype: d.reference_doctype,
|
||||
reference_docname: d.reference_docname,
|
||||
creation: d.creation,
|
||||
}
|
||||
showCallLogModal.value = true
|
||||
}
|
||||
|
||||
const statusLabelMap = {
|
||||
Completed: 'Completed',
|
||||
Initiated: 'Initiated',
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user