340 lines
11 KiB
TypeScript
340 lines
11 KiB
TypeScript
import { Button, Notification, toast } from '@/components/ui'
|
||
import { GridDto, UiCommandButtonPositionTypeEnum } from '@/proxy/form/models'
|
||
import { dynamicFetch } from '@/services/form.service'
|
||
import { useLocalization } from '@/utils/hooks/useLocalization'
|
||
import { usePermission } from '@/utils/hooks/usePermission'
|
||
import { DataGridTypes } from 'devextreme-react/data-grid'
|
||
import { ToolbarItem } from 'devextreme/ui/data_grid_types'
|
||
import { useEffect, useState } from 'react'
|
||
import { useDialogContext } from '../shared/DialogContext'
|
||
import { usePWA } from '@/utils/hooks/usePWA'
|
||
import { layoutTypes, ListViewLayoutType } from '../admin/listForm/edit/types'
|
||
|
||
type ToolbarModalData = {
|
||
open: boolean
|
||
content?: JSX.Element
|
||
}
|
||
|
||
// https://js.devexpress.com/Documentation/ApiReference/UI_Components/dxDataGrid/Configuration/toolbar/
|
||
// item.name > Accepted Values: 'addRowButton', 'applyFilterButton', 'columnChooserButton', 'exportButton', 'groupPanel', 'revertButton', 'saveButton', 'searchPanel'
|
||
const useToolbar = ({
|
||
gridDto,
|
||
listFormCode,
|
||
getSelectedRowKeys,
|
||
getSelectedRowsData,
|
||
refreshData,
|
||
getFilter,
|
||
layout,
|
||
expandAll,
|
||
collapseAll,
|
||
}: {
|
||
gridDto?: GridDto
|
||
listFormCode: string
|
||
getSelectedRowKeys: () => void
|
||
getSelectedRowsData: () => any
|
||
refreshData: () => void
|
||
getFilter: () => void
|
||
layout: ListViewLayoutType | string
|
||
expandAll?: () => void
|
||
collapseAll?: () => void
|
||
}): {
|
||
toolbarData: ToolbarItem[]
|
||
toolbarModalData: ToolbarModalData | undefined
|
||
setToolbarModalData: (data: ToolbarModalData | undefined) => void
|
||
} => {
|
||
const dialog: any = useDialogContext()
|
||
const { translate } = useLocalization()
|
||
const { checkPermission } = usePermission()
|
||
const isPwaMode = usePWA()
|
||
|
||
const [toolbarData, setToolbarData] = useState<ToolbarItem[]>([])
|
||
const [toolbarModalData, setToolbarModalData] = useState<ToolbarModalData>()
|
||
|
||
const grdOpt = gridDto?.gridOptions
|
||
|
||
function getToolbarData() {
|
||
const items: ToolbarItem[] = []
|
||
|
||
if (!gridDto || !grdOpt) {
|
||
setToolbarData(items)
|
||
return
|
||
}
|
||
|
||
// Add searchPanel
|
||
if (grdOpt.searchPanelDto?.visible) {
|
||
items.push({
|
||
locateInMenu: 'auto',
|
||
showText: 'inMenu',
|
||
name: 'searchPanel',
|
||
})
|
||
}
|
||
|
||
items.push({
|
||
widget: 'dxButton',
|
||
name: 'refreshButton',
|
||
options: {
|
||
icon: 'refresh',
|
||
onClick: refreshData,
|
||
text: translate('::ListForms.ListForm.Refresh'),
|
||
},
|
||
location: 'after',
|
||
})
|
||
|
||
// Add Expand All button for TreeList
|
||
if (layout === layoutTypes.tree && grdOpt.treeOptionDto?.parentIdExpr) {
|
||
items.push({
|
||
widget: 'dxButton',
|
||
name: 'expandAllButton',
|
||
options: {
|
||
icon: 'plus',
|
||
text: translate('::ListForms.ListFormEdit.ExpandAll'),
|
||
onClick: expandAll,
|
||
},
|
||
location: 'after',
|
||
})
|
||
|
||
// Add Collapse All button for TreeList
|
||
items.push({
|
||
widget: 'dxButton',
|
||
name: 'collapseAllButton',
|
||
options: {
|
||
icon: 'minus',
|
||
text: translate('::ListForms.ListFormEdit.CollapseAll'),
|
||
onClick: collapseAll,
|
||
},
|
||
location: 'after',
|
||
})
|
||
}
|
||
|
||
// field chooser panel
|
||
if (grdOpt.columnOptionDto?.columnChooserEnabled) {
|
||
items.push({
|
||
locateInMenu: 'auto',
|
||
showText: 'inMenu',
|
||
name: 'columnChooserButton',
|
||
})
|
||
}
|
||
|
||
// Add InsertNewRecord button
|
||
if (grdOpt.editingOptionDto?.allowAdding && checkPermission(grdOpt.permissionDto?.c)) {
|
||
items.push({
|
||
locateInMenu: 'auto',
|
||
showText: 'always',
|
||
name: 'addRowButton',
|
||
location: 'after',
|
||
})
|
||
}
|
||
|
||
// Add group panel
|
||
if (grdOpt.groupPanelDto?.visible) {
|
||
items.push({
|
||
locateInMenu: 'auto',
|
||
showText: 'inMenu',
|
||
name: 'groupPanel',
|
||
})
|
||
}
|
||
|
||
// Add DeleteSelectedRecords button
|
||
// coklu silme icin
|
||
if (grdOpt.editingOptionDto?.allowDeleting && checkPermission(grdOpt.permissionDto?.d)) {
|
||
items.push({
|
||
location: 'after',
|
||
widget: 'dxButton',
|
||
locateInMenu: 'auto',
|
||
showText: 'inMenu',
|
||
name: 'deleteSelectedRecords',
|
||
options: {
|
||
text: translate('::ListForms.ListForm.DeleteSelectedRecords'),
|
||
icon: 'trash',
|
||
visible: false,
|
||
onClick() {
|
||
if (!grdOpt.deleteServiceAddress) {
|
||
return
|
||
}
|
||
|
||
dynamicFetch(grdOpt.deleteServiceAddress, 'POST', null, {
|
||
keys: getSelectedRowKeys(),
|
||
listFormCode,
|
||
}).then(() => {
|
||
refreshData()
|
||
})
|
||
},
|
||
},
|
||
})
|
||
|
||
// Add DeleteAllRecords button
|
||
// butun kayitlari (filtreli) icin
|
||
if (grdOpt.editingOptionDto?.allowAllDeleting) {
|
||
const buttonDeleteAll: DataGridTypes.ToolbarItem = {
|
||
location: 'after',
|
||
widget: 'dxButton',
|
||
name: 'deleteAllRecords',
|
||
options: {
|
||
text: translate('::ListForms.ListForm.DeleteAllRecords'),
|
||
hint: translate('::ListForms.ListForm.DeleteAllRecords'),
|
||
icon: 'trash',
|
||
visible: true,
|
||
onClick() {
|
||
const parameters = {
|
||
listFormCode,
|
||
filter: JSON.stringify(getFilter()),
|
||
onlyTotalCountQuery: true,
|
||
createDeleteQuery: false,
|
||
}
|
||
|
||
dynamicFetch('list-form-select/select', 'GET', parameters).then((r: any) => {
|
||
setToolbarModalData({
|
||
open: true,
|
||
content: (
|
||
<>
|
||
<h5 className="mb-4">Delete All Records</h5>
|
||
|
||
<p>Are you sure to delete all {r.data.totalCount} records?</p>
|
||
|
||
<div className="text-right mt-6">
|
||
<Button
|
||
className="ltr:mr-2 rtl:ml-2"
|
||
variant="plain"
|
||
onClick={() => setToolbarModalData(undefined)}
|
||
>
|
||
Cancel
|
||
</Button>
|
||
<Button
|
||
variant="solid"
|
||
onClick={() => {
|
||
//delete parameters.onlyTotalCountQuery
|
||
parameters.createDeleteQuery = true // tumunu silme islemi parametresi > set
|
||
dynamicFetch('list-form-select/select', 'GET', parameters).then(() => {
|
||
toast.push(
|
||
<Notification type="success" duration={2000}>
|
||
{'Tüm kayıtlar silindi.'}
|
||
</Notification>,
|
||
{
|
||
placement: 'top-end',
|
||
},
|
||
)
|
||
|
||
refreshData()
|
||
|
||
setToolbarModalData(undefined)
|
||
})
|
||
}}
|
||
>
|
||
Save
|
||
</Button>
|
||
</div>
|
||
</>
|
||
),
|
||
})
|
||
})
|
||
},
|
||
},
|
||
}
|
||
items.push(buttonDeleteAll)
|
||
}
|
||
}
|
||
|
||
// #region Toolbar icin kullanici tanimli dinamik butonlari ekler
|
||
for (let i = 0; i < grdOpt.commandColumnDto.length; i++) {
|
||
const action = grdOpt.commandColumnDto[i]
|
||
|
||
// action.buttonPosition == 1 ise Toolbar butonudur, burada sadece Toolbar butonunu eklenir
|
||
if (action.buttonPosition !== UiCommandButtonPositionTypeEnum.Toolbar) {
|
||
continue
|
||
}
|
||
|
||
if (checkPermission(action.authName)) {
|
||
const buttonCustom: DataGridTypes.ToolbarItem = {
|
||
location: 'after',
|
||
widget: 'dxButton',
|
||
name: action.hint,
|
||
options: {
|
||
hint: action.hint,
|
||
text: action.text,
|
||
icon: action.icon,
|
||
visible: true,
|
||
onClick(e: any) {
|
||
if (typeof e.event?.preventDefault === 'function') {
|
||
e?.event?.preventDefault()
|
||
}
|
||
if (action.url) {
|
||
let url = action.url
|
||
// griddeki secili satirlari al
|
||
const selectedRowsData = getSelectedRowsData()
|
||
// constsa her bir secili satir icin donguye gir
|
||
for (let i = 0; i < selectedRowsData.length; i++) {
|
||
// secili satirin objesine ait property verilerini al
|
||
const keys = Object.keys(selectedRowsData[i])
|
||
// secili satirin her bir property si icin donguye gir
|
||
for (let j = 0; j < keys.length; j++) {
|
||
// secili satirin j indexine sahip property ismini al
|
||
const fieldName = keys[j]
|
||
// secili satirin j indexine sahip property isminin degerini al
|
||
const fieldValue = selectedRowsData[i][fieldName]
|
||
// url icerisindeki {PropertyName} seklindeki anahtarlari secili satirdaki uyusan propertyler ile degistir
|
||
url = url.replace(`@${fieldName}`, fieldValue)
|
||
}
|
||
break // Url cagirmak icin kullanilacak parametreler sadece secili olan ilk satirdan alinir!
|
||
}
|
||
window.open(url, isPwaMode ? '_self' : action.urlTarget)
|
||
} else if (action.dialogName) {
|
||
if (action.dialogParameters) {
|
||
var dynamicMap = JSON.parse(action.dialogParameters)
|
||
for (const [key, value] of Object.entries<string>(dynamicMap)) {
|
||
dynamicMap[key] = value.startsWith('@')
|
||
? e.row.data[value.replace('@', '')]
|
||
: value
|
||
}
|
||
dialog.setConfig({
|
||
component: action.dialogName,
|
||
props: dynamicMap,
|
||
})
|
||
}
|
||
} else if (action.onClick) {
|
||
eval(action.onClick)
|
||
}
|
||
},
|
||
},
|
||
}
|
||
items.push(buttonCustom)
|
||
}
|
||
}
|
||
// #endregion
|
||
|
||
// batch editing icin kaydet ve geri al butonu
|
||
if (
|
||
grdOpt.editingOptionDto?.allowUpdating &&
|
||
grdOpt.editingOptionDto?.mode == 'batch' &&
|
||
checkPermission(grdOpt.permissionDto?.u)
|
||
) {
|
||
items.push({
|
||
locateInMenu: 'auto',
|
||
showText: 'inMenu',
|
||
name: 'saveButton',
|
||
})
|
||
|
||
items.push({
|
||
locateInMenu: 'auto',
|
||
showText: 'inMenu',
|
||
name: 'revertButton',
|
||
})
|
||
}
|
||
// #endregion
|
||
|
||
setToolbarData(items)
|
||
}
|
||
|
||
useEffect(() => {
|
||
if (!gridDto && !listFormCode) return
|
||
|
||
getToolbarData()
|
||
}, [gridDto, listFormCode])
|
||
|
||
return {
|
||
toolbarData,
|
||
toolbarModalData,
|
||
setToolbarModalData,
|
||
}
|
||
}
|
||
|
||
export { useToolbar }
|