Merge pull request #67 from shariquerik/notes-view-controls
feat: Added view controls on Notes view
This commit is contained in:
commit
830c6de37e
@ -6,4 +6,14 @@ from frappe.model.document import Document
|
|||||||
|
|
||||||
|
|
||||||
class CRMNote(Document):
|
class CRMNote(Document):
|
||||||
pass
|
@staticmethod
|
||||||
|
def default_list_data():
|
||||||
|
rows = [
|
||||||
|
"name",
|
||||||
|
"title",
|
||||||
|
"content",
|
||||||
|
"reference_doctype",
|
||||||
|
"reference_docname",
|
||||||
|
"modified",
|
||||||
|
]
|
||||||
|
return {'columns': [], 'rows': rows}
|
||||||
|
|||||||
@ -2,7 +2,6 @@
|
|||||||
<Dialog
|
<Dialog
|
||||||
v-model="show"
|
v-model="show"
|
||||||
:options="{
|
:options="{
|
||||||
title: editMode ? 'Edit Note' : 'Create Note',
|
|
||||||
size: 'xl',
|
size: 'xl',
|
||||||
actions: [
|
actions: [
|
||||||
{
|
{
|
||||||
@ -13,6 +12,26 @@
|
|||||||
],
|
],
|
||||||
}"
|
}"
|
||||||
>
|
>
|
||||||
|
<template #body-title>
|
||||||
|
<div class="flex items-center gap-3">
|
||||||
|
<h3 class="text-2xl font-semibold leading-6 text-gray-900">
|
||||||
|
{{ editMode ? 'Edit Note' : 'Create Note' }}
|
||||||
|
</h3>
|
||||||
|
<Button
|
||||||
|
v-if="_note?.reference_docname"
|
||||||
|
variant="outline"
|
||||||
|
size="sm"
|
||||||
|
:label="
|
||||||
|
_note.reference_doctype == 'CRM Deal' ? 'Open Deal' : 'Open Lead'
|
||||||
|
"
|
||||||
|
@click="redirect()"
|
||||||
|
>
|
||||||
|
<template #suffix>
|
||||||
|
<ArrowUpRightIcon class="h-4 w-4" />
|
||||||
|
</template>
|
||||||
|
</Button>
|
||||||
|
</div>
|
||||||
|
</template>
|
||||||
<template #body-content>
|
<template #body-content>
|
||||||
<div class="flex flex-col gap-4">
|
<div class="flex flex-col gap-4">
|
||||||
<div>
|
<div>
|
||||||
@ -42,8 +61,10 @@
|
|||||||
</template>
|
</template>
|
||||||
|
|
||||||
<script setup>
|
<script setup>
|
||||||
|
import ArrowUpRightIcon from '@/components/Icons/ArrowUpRightIcon.vue'
|
||||||
import { TextEditor, call } from 'frappe-ui'
|
import { TextEditor, call } from 'frappe-ui'
|
||||||
import { ref, defineModel, nextTick, watch } from 'vue'
|
import { ref, defineModel, nextTick, watch } from 'vue'
|
||||||
|
import { useRouter } from 'vue-router';
|
||||||
|
|
||||||
const props = defineProps({
|
const props = defineProps({
|
||||||
note: {
|
note: {
|
||||||
@ -65,6 +86,8 @@ const notes = defineModel('reloadNotes')
|
|||||||
|
|
||||||
const emit = defineEmits(['after'])
|
const emit = defineEmits(['after'])
|
||||||
|
|
||||||
|
const router = useRouter()
|
||||||
|
|
||||||
const title = ref(null)
|
const title = ref(null)
|
||||||
const editMode = ref(false)
|
const editMode = ref(false)
|
||||||
let _note = ref({})
|
let _note = ref({})
|
||||||
@ -104,6 +127,16 @@ async function updateNote() {
|
|||||||
show.value = false
|
show.value = false
|
||||||
}
|
}
|
||||||
|
|
||||||
|
function redirect() {
|
||||||
|
if (!props.note?.reference_docname) return
|
||||||
|
let name = props.note.reference_doctype == 'CRM Deal' ? 'Deal' : 'Lead'
|
||||||
|
let params = { leadId: props.note.reference_docname }
|
||||||
|
if (name == 'Deal') {
|
||||||
|
params = { dealId: props.note.reference_docname }
|
||||||
|
}
|
||||||
|
router.push({ name: name, params: params })
|
||||||
|
}
|
||||||
|
|
||||||
watch(
|
watch(
|
||||||
() => show.value,
|
() => show.value,
|
||||||
(value) => {
|
(value) => {
|
||||||
|
|||||||
@ -2,7 +2,6 @@
|
|||||||
<Dialog
|
<Dialog
|
||||||
v-model="show"
|
v-model="show"
|
||||||
:options="{
|
:options="{
|
||||||
title: editMode ? 'Edit Task' : 'Create Task',
|
|
||||||
size: 'xl',
|
size: 'xl',
|
||||||
actions: [
|
actions: [
|
||||||
{
|
{
|
||||||
|
|||||||
@ -41,6 +41,7 @@
|
|||||||
/>
|
/>
|
||||||
<SortBy v-model="list" :doctype="doctype" @update="updateSort" />
|
<SortBy v-model="list" :doctype="doctype" @update="updateSort" />
|
||||||
<ColumnSettings
|
<ColumnSettings
|
||||||
|
v-if="!options.hideColumnsButton"
|
||||||
v-model="list"
|
v-model="list"
|
||||||
:doctype="doctype"
|
:doctype="doctype"
|
||||||
@update="(isDefault) => updateColumns(isDefault)"
|
@update="(isDefault) => updateColumns(isDefault)"
|
||||||
@ -97,6 +98,13 @@ const props = defineProps({
|
|||||||
type: Object,
|
type: Object,
|
||||||
default: {},
|
default: {},
|
||||||
},
|
},
|
||||||
|
options: {
|
||||||
|
type: Object,
|
||||||
|
default: {
|
||||||
|
hideColumnsButton: false,
|
||||||
|
defaultViewName: '',
|
||||||
|
},
|
||||||
|
},
|
||||||
})
|
})
|
||||||
|
|
||||||
const { $dialog } = globalStore()
|
const { $dialog } = globalStore()
|
||||||
@ -117,7 +125,7 @@ const showViewModal = ref(false)
|
|||||||
const currentView = computed(() => {
|
const currentView = computed(() => {
|
||||||
let _view = getView(route.query.view)
|
let _view = getView(route.query.view)
|
||||||
return {
|
return {
|
||||||
label: _view?.label || 'List View',
|
label: _view?.label || props.options?.defaultViewName || 'List View',
|
||||||
icon: _view?.icon || 'list',
|
icon: _view?.icon || 'list',
|
||||||
}
|
}
|
||||||
})
|
})
|
||||||
@ -232,7 +240,7 @@ function reload() {
|
|||||||
|
|
||||||
const defaultViews = [
|
const defaultViews = [
|
||||||
{
|
{
|
||||||
label: 'List View',
|
label: props.options?.defaultViewName || 'List View',
|
||||||
icon: 'list',
|
icon: 'list',
|
||||||
onClick() {
|
onClick() {
|
||||||
viewUpdated.value = false
|
viewUpdated.value = false
|
||||||
|
|||||||
@ -9,12 +9,21 @@
|
|||||||
</Button>
|
</Button>
|
||||||
</template>
|
</template>
|
||||||
</LayoutHeader>
|
</LayoutHeader>
|
||||||
|
<ViewControls
|
||||||
|
v-model="notes"
|
||||||
|
v-model:loadMore="loadMore"
|
||||||
|
doctype="CRM Note"
|
||||||
|
:options="{
|
||||||
|
hideColumnsButton: true,
|
||||||
|
defaultViewName: 'Notes View',
|
||||||
|
}"
|
||||||
|
/>
|
||||||
<div
|
<div
|
||||||
v-if="notes.data?.length"
|
v-if="notes.data?.data?.length"
|
||||||
class="grid grid-cols-4 gap-4 overflow-y-auto p-5"
|
class="grid grid-cols-4 gap-4 overflow-y-auto px-5 pb-3"
|
||||||
>
|
>
|
||||||
<div
|
<div
|
||||||
v-for="note in notes.data"
|
v-for="note in notes.data.data"
|
||||||
class="group flex h-56 cursor-pointer flex-col justify-between gap-2 rounded-lg border px-5 py-4 shadow-sm hover:bg-gray-50"
|
class="group flex h-56 cursor-pointer flex-col justify-between gap-2 rounded-lg border px-5 py-4 shadow-sm hover:bg-gray-50"
|
||||||
@click="editNote(note)"
|
@click="editNote(note)"
|
||||||
>
|
>
|
||||||
@ -61,6 +70,16 @@
|
|||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
<ListFooter
|
||||||
|
v-if="notes.data?.data?.length"
|
||||||
|
class="border-t px-5 py-2"
|
||||||
|
v-model="notes.data.page_length_count"
|
||||||
|
:options="{
|
||||||
|
rowCount: notes.data.row_count,
|
||||||
|
totalCount: notes.data.total_count,
|
||||||
|
}"
|
||||||
|
@loadMore="() => loadMore++"
|
||||||
|
/>
|
||||||
<div v-else class="flex h-full items-center justify-center">
|
<div v-else class="flex h-full items-center justify-center">
|
||||||
<div
|
<div
|
||||||
class="flex flex-col items-center gap-3 text-xl font-medium text-gray-500"
|
class="flex flex-col items-center gap-3 text-xl font-medium text-gray-500"
|
||||||
@ -84,14 +103,15 @@ import LayoutHeader from '@/components/LayoutHeader.vue'
|
|||||||
import UserAvatar from '@/components/UserAvatar.vue'
|
import UserAvatar from '@/components/UserAvatar.vue'
|
||||||
import NoteIcon from '@/components/Icons/NoteIcon.vue'
|
import NoteIcon from '@/components/Icons/NoteIcon.vue'
|
||||||
import NoteModal from '@/components/Modals/NoteModal.vue'
|
import NoteModal from '@/components/Modals/NoteModal.vue'
|
||||||
|
import ViewControls from '@/components/ViewControls.vue'
|
||||||
import { timeAgo, dateFormat, dateTooltipFormat } from '@/utils'
|
import { timeAgo, dateFormat, dateTooltipFormat } from '@/utils'
|
||||||
import {
|
import {
|
||||||
createListResource,
|
|
||||||
TextEditor,
|
TextEditor,
|
||||||
call,
|
call,
|
||||||
Dropdown,
|
Dropdown,
|
||||||
Tooltip,
|
Tooltip,
|
||||||
Breadcrumbs,
|
Breadcrumbs,
|
||||||
|
ListFooter,
|
||||||
} from 'frappe-ui'
|
} from 'frappe-ui'
|
||||||
import { ref } from 'vue'
|
import { ref } from 'vue'
|
||||||
import { usersStore } from '@/stores/users'
|
import { usersStore } from '@/stores/users'
|
||||||
@ -109,16 +129,8 @@ const breadcrumbs = [{ label: list.title, route: { name: 'Notes' } }]
|
|||||||
const showNoteModal = ref(false)
|
const showNoteModal = ref(false)
|
||||||
const currentNote = ref(null)
|
const currentNote = ref(null)
|
||||||
|
|
||||||
const notes = createListResource({
|
const notes = ref({})
|
||||||
type: 'list',
|
const loadMore = ref(1)
|
||||||
doctype: 'CRM Note',
|
|
||||||
cache: 'Notes',
|
|
||||||
fields: ['name', 'title', 'content', 'owner', 'modified'],
|
|
||||||
filters: {},
|
|
||||||
orderBy: 'modified desc',
|
|
||||||
pageLength: 20,
|
|
||||||
auto: true,
|
|
||||||
})
|
|
||||||
|
|
||||||
function createNote() {
|
function createNote() {
|
||||||
currentNote.value = {
|
currentNote.value = {
|
||||||
|
|||||||
@ -4,7 +4,7 @@
|
|||||||
<Breadcrumbs :items="breadcrumbs" />
|
<Breadcrumbs :items="breadcrumbs" />
|
||||||
</template>
|
</template>
|
||||||
<template #right-header>
|
<template #right-header>
|
||||||
<Button variant="solid" label="Create" @click="showTaskModal = true">
|
<Button variant="solid" label="Create" @click="createTask">
|
||||||
<template #prefix><FeatherIcon name="plus" class="h-4" /></template>
|
<template #prefix><FeatherIcon name="plus" class="h-4" /></template>
|
||||||
</Button>
|
</Button>
|
||||||
</template>
|
</template>
|
||||||
@ -107,4 +107,18 @@ function showTask(name) {
|
|||||||
}
|
}
|
||||||
showTaskModal.value = true
|
showTaskModal.value = true
|
||||||
}
|
}
|
||||||
|
|
||||||
|
function createTask() {
|
||||||
|
task.value = {
|
||||||
|
title: '',
|
||||||
|
description: '',
|
||||||
|
assigned_to: '',
|
||||||
|
due_date: '',
|
||||||
|
status: 'Backlog',
|
||||||
|
priority: 'Low',
|
||||||
|
reference_doctype: 'CRM Lead',
|
||||||
|
reference_docname: '',
|
||||||
|
}
|
||||||
|
showTaskModal.value = true
|
||||||
|
}
|
||||||
</script>
|
</script>
|
||||||
|
|||||||
Loading…
x
Reference in New Issue
Block a user