MenuDrawer.vue 3.5 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105
  1. <template>
  2. <BasicDrawer v-bind="$attrs" @register="registerDrawer" showFooter :width="adaptiveWidth" :title="getTitle" @ok="handleSubmit">
  3. <BasicForm @register="registerForm" class="menuForm" />
  4. </BasicDrawer>
  5. </template>
  6. <script lang="ts" setup>
  7. import { ref, computed, unref, useAttrs } from 'vue';
  8. import { BasicForm, useForm } from '/@/components/Form/index';
  9. import { formSchema, ComponentTypes } from './menu.data';
  10. import { BasicDrawer, useDrawerInner } from '/@/components/Drawer';
  11. import { list, saveOrUpdateMenu } from './menu.api';
  12. import { useDrawerAdaptiveWidth } from '/@/hooks/jeecg/useAdaptiveWidth';
  13. // 声明Emits
  14. const emit = defineEmits(['success', 'register']);
  15. const { adaptiveWidth } = useDrawerAdaptiveWidth();
  16. const attrs = useAttrs();
  17. const isUpdate = ref(true);
  18. const menuType = ref(0);
  19. const isButton = (type) => type === 2;
  20. const [registerForm, { setProps, resetFields, setFieldsValue, updateSchema, validate, clearValidate }] = useForm({
  21. labelCol: {
  22. md: { span: 4 },
  23. sm: { span: 6 },
  24. },
  25. wrapperCol: {
  26. md: { span: 20 },
  27. sm: { span: 18 },
  28. },
  29. schemas: formSchema,
  30. showActionButtonGroup: false,
  31. });
  32. const [registerDrawer, { setDrawerProps, closeDrawer }] = useDrawerInner(async (data) => {
  33. await resetFields();
  34. setDrawerProps({ confirmLoading: false });
  35. isUpdate.value = !!data?.isUpdate;
  36. menuType.value = data?.record?.menuType;
  37. //获取下拉树信息
  38. const treeData = await list({kind: 3});
  39. updateSchema([
  40. {
  41. field: 'parentId',
  42. componentProps: { treeData },
  43. },
  44. {
  45. field: 'name',
  46. label: isButton(unref(menuType)) ? '按钮/权限' : '菜单名称',
  47. },
  48. {
  49. field: 'url',
  50. required: !isButton(unref(menuType)),
  51. componentProps: {
  52. onChange: (e) => onUrlChange(e.target.value),
  53. },
  54. },
  55. ]);
  56. // 无论新增还是编辑,都可以设置表单值
  57. if (typeof data.record === 'object') {
  58. let values = { ...data.record };
  59. setFieldsValue(values);
  60. onUrlChange(values.url);
  61. }
  62. //禁用表单
  63. setProps({ disabled: !attrs.showFooter });
  64. });
  65. //获取弹窗标题
  66. const getTitle = computed(() => (!unref(isUpdate) ? '新增菜单' : '编辑菜单'));
  67. //提交事件
  68. async function handleSubmit() {
  69. try {
  70. const values = await validate();
  71. // iframe兼容
  72. if (ComponentTypes.IFrame === values.component) {
  73. values.component = values.frameSrc;
  74. }
  75. setDrawerProps({ confirmLoading: true });
  76. //提交表单
  77. await saveOrUpdateMenu({...values, kind: 3}, unref(isUpdate));
  78. closeDrawer();
  79. emit('success');
  80. } finally {
  81. setDrawerProps({ confirmLoading: false });
  82. }
  83. }
  84. /** url 变化时,动态设置组件名称placeholder */
  85. function onUrlChange(url) {
  86. let placeholder = '';
  87. if (url != null && url != '') {
  88. if (url.startsWith('/')) {
  89. url = url.substring(1);
  90. }
  91. url = url.replaceAll('/', '-');
  92. // 特殊标记
  93. url = url.replaceAll(':', '@');
  94. placeholder = `${url}`;
  95. } else {
  96. placeholder = '请输入组件名称';
  97. }
  98. updateSchema([{ field: 'componentName', componentProps: { placeholder } }]);
  99. }
  100. </script>