diff --git a/ui/src/views/form/FormButtons.tsx b/ui/src/views/form/FormButtons.tsx
index 4aa3045..f0da2f3 100644
--- a/ui/src/views/form/FormButtons.tsx
+++ b/ui/src/views/form/FormButtons.tsx
@@ -15,13 +15,14 @@ import {
} from 'react-icons/fa'
import { useNavigate } from 'react-router-dom'
import { GridColumnData } from '../list/GridColumnData'
-import { useToolbar } from '../list/useToolbar'
+import { isWorkflowToolbarItemDisabled, useToolbar } from '../list/useToolbar'
import { PermissionResults, RowMode } from './types'
import { GridDto } from '@/proxy/form/models'
import { ROUTES_ENUM } from '@/routes/route.constant'
import { usePermission } from '@/utils/hooks/usePermission'
import { usePWA } from '@/utils/hooks/usePWA'
import { layoutTypes } from '../admin/listForm/edit/types'
+import { useStoreState } from '@/store'
const FormButtons = (props: {
isSubForm?: boolean
@@ -68,7 +69,7 @@ const FormButtons = (props: {
const { translate } = useLocalization()
const layout = layoutTypes.grid
- const { toolbarData } = useToolbar({
+ const { toolbarData, toolbarModalData, setToolbarModalData } = useToolbar({
gridDto,
listFormCode,
getSelectedRowKeys,
@@ -78,6 +79,52 @@ const FormButtons = (props: {
layout,
})
+ const currentUser = useStoreState((state) => state.auth.user)
+ const selectedRowData = getSelectedRowsData()?.[0]
+ const rowEvent = {
+ row: {
+ data: selectedRowData,
+ key: id,
+ rowType: 'data',
+ isEditing: mode === 'edit',
+ },
+ }
+
+ const resolveVisible = (visible: unknown) => {
+ if (typeof visible !== 'function') {
+ return visible !== false
+ }
+
+ try {
+ return Boolean(visible(rowEvent))
+ } catch (error) {
+ console.error('Button visibility evaluation error:', error)
+ return false
+ }
+ }
+
+ const isToolbarButtonVisible = (item: any) =>
+ item.widget === 'dxButton' &&
+ !toolbarExcludedNames.includes(item.name) &&
+ resolveVisible(item.visible) &&
+ resolveVisible(item.options?.visible)
+
+ const isCommandButtonVisible = (item: any) =>
+ typeof item !== 'string' &&
+ !commandExcludedNames.includes(item.name) &&
+ resolveVisible(item.visible)
+
+ const isToolbarButtonDisabled = (item: any) => {
+ const workflowDisabled = isWorkflowToolbarItemDisabled(
+ item.name,
+ gridDto.gridOptions.workflowDto,
+ selectedRowData ? [selectedRowData] : [],
+ currentUser,
+ )
+
+ return workflowDisabled ?? Boolean(item.options?.disabled)
+ }
+
const openDynamicGridReport = () => {
if (!id) return
@@ -116,22 +163,16 @@ const FormButtons = (props: {
}
const toolbarExcludedNames = ['deleteAllRecords', 'deleteSelectedRecords', 'refreshButton']
- const hasVisibleToolbarButtons = toolbarData?.some(
- (item) => item.widget == 'dxButton' && !toolbarExcludedNames.includes(item.name!),
- )
+ const hasVisibleToolbarButtons = toolbarData?.some(isToolbarButtonVisible)
const commandExcludedNames = ['edit', 'delete', 'detail']
- const hasVisibleCommandButtons = commandColumnData?.buttons?.some(
- (item) => typeof item !== 'string' && !commandExcludedNames.includes(item.name!),
- )
+ const hasVisibleCommandButtons = commandColumnData?.buttons?.some(isCommandButtonVisible)
return (
<>
{toolbarData
- ?.filter(
- (item) => item.widget == 'dxButton' && !toolbarExcludedNames.includes(item.name!),
- )
+ ?.filter(isToolbarButtonVisible)
.map((item, i) => {
const IconComp = navigationIcon[item.options?.icon]
const hasValidIcon =
@@ -145,7 +186,8 @@ const FormButtons = (props: {
variant="default"
size="sm"
icon={hasValidIcon ? : null}
- onClick={item.options?.onClick}
+ disabled={isToolbarButtonDisabled(item)}
+ onClick={(e) => item.options?.onClick?.({ ...e, ...rowEvent })}
>
{item.options?.text}
@@ -155,7 +197,7 @@ const FormButtons = (props: {
{hasVisibleToolbarButtons && }
{commandColumnData?.buttons
- ?.filter((item) => typeof item !== 'string' && !commandExcludedNames.includes(item.name!))
+ ?.filter(isCommandButtonVisible)
.map((item: any, i) => {
return (
)}
+