@mythpe/quasar-ui-qui 0.1.8 → 0.1.10

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@mythpe/quasar-ui-qui",
3
- "version": "0.1.8",
3
+ "version": "0.1.10",
4
4
  "description": "MyTh Quasar UI Kit App Extension",
5
5
  "author": {
6
6
  "name": "MyTh Ahmed Faiz",
@@ -48,54 +48,55 @@ const initMetaServer: MDatatableMetaServer = {
48
48
  total: null
49
49
  }
50
50
 
51
- interface Props {
51
+ type Props = {
52
52
  controlKey?: MDatatableProps['controlKey'];
53
53
  defaultItem?: MDatatableProps['defaultItem'];
54
54
  contextItems?: MDatatableProps['contextItems'];
55
55
  contextItemsLength?: MDatatableProps['contextItemsLength'];
56
- hideAutoMessage?: MDatatableProps['hideAutoMessage'];
56
+ hideAutoMessage?: boolean;
57
57
  headers: MDatatableProps['headers'];
58
58
  serviceName?: MDatatableProps['serviceName'];
59
59
  requestParams?: MDatatableProps['requestParams'];
60
- pdf?: MDatatableProps['pdf'];
61
- excel?: MDatatableProps['excel'];
60
+ pdf?: boolean;
61
+ excel?: boolean;
62
62
  exportUrl?: MDatatableProps['exportUrl'];
63
- hideSearch?: MDatatableProps['hideSearch'];
63
+ hideSearch?: boolean;
64
64
  searchDebounce?: MDatatableProps['searchDebounce'];
65
65
  withIndex?: MDatatableProps['withIndex'];
66
66
  withStore?: MDatatableProps['withStore'];
67
67
  withShow?: MDatatableProps['withShow'];
68
68
  withUpdate?: MDatatableProps['withUpdate'];
69
- hideAddBtn?: MDatatableProps['hideAddBtn'];
70
- hideUpdateBtn?: MDatatableProps['hideUpdateBtn'];
71
- hideShowBtn?: MDatatableProps['hideShowBtn'];
72
- hideDestroyBtn?: MDatatableProps['hideDestroyBtn'];
69
+ hideAddBtn?: boolean;
70
+ hideUpdateBtn?: boolean;
71
+ cloneBtn?: boolean;
72
+ hideShowBtn?: boolean;
73
+ hideDestroyBtn?: boolean;
73
74
  storeRoute?: MDatatableProps['storeRoute'];
74
- storeQueryParams?: MDatatableProps['storeQueryParams'];
75
+ storeQueryParams?: boolean;
75
76
  updateRoute?: MDatatableProps['updateRoute'];
76
- updateQueryParams?: MDatatableProps['updateQueryParams'];
77
+ updateQueryParams?: boolean;
77
78
  showRoute?: MDatatableProps['showRoute'];
78
- showQueryParams?: MDatatableProps['showQueryParams'];
79
- mouse?: MDatatableProps['mouse'];
80
- noRefreshBtn?: MDatatableProps['noRefreshBtn'];
81
- endReach?: MDatatableProps['endReach'];
82
- showSelection?: MDatatableProps['showSelection'];
83
- hideSelection?: MDatatableProps['hideSelection'];
84
- multiSelection?: MDatatableProps['multiSelection'];
85
- multiDestroy?: MDatatableProps['multiDestroy'];
79
+ showQueryParams?: boolean;
80
+ mouse?: boolean;
81
+ noRefreshBtn?: boolean;
82
+ endReach?: boolean;
83
+ showSelection?: boolean;
84
+ hideSelection?: boolean;
85
+ multiSelection?: boolean;
86
+ multiDestroy?: boolean;
86
87
  rowsPerPageOptions?: MDatatableProps['rowsPerPageOptions'];
87
88
  ignoreKeys?: MDatatableProps['ignoreKeys'];
88
89
  grid?: MDatatableProps['grid'];
89
90
  title?: MDatatableProps['title'];
90
- manageColumns?: MDatatableProps['manageColumns'];
91
+ manageColumns?: boolean;
91
92
  visibleColumns?: MDatatableProps['visibleColumns'];
92
93
  searchColumns?: MDatatableProps['searchColumns'];
93
- addTopBtn?: MDatatableProps['addTopBtn'];
94
- addListBtn?: MDatatableProps['addListBtn'];
95
- addFabBtn?: MDatatableProps['addFabBtn'];
96
- fullscreenBtn?: MDatatableProps['fullscreenBtn'];
97
- noBodyControl?: MDatatableProps['noBodyControl'];
98
- showCardControlHeader?: MDatatableProps['showCardControlHeader'];
94
+ addTopBtn?: boolean;
95
+ addListBtn?: boolean;
96
+ addFabBtn?: boolean;
97
+ fullscreenBtn?: boolean;
98
+ noBodyControl?: boolean;
99
+ showCardControlHeader?: boolean;
99
100
  dense?: MDatatableProps['dense'];
100
101
  bordered?: MDatatableProps['bordered'];
101
102
  flat?: MDatatableProps['flat'];
@@ -119,29 +120,30 @@ const props = withDefaults(defineProps<Props>(), {
119
120
  pdf: undefined,
120
121
  excel: undefined,
121
122
  exportUrl: undefined,
122
- hideSearch: undefined,
123
+ hideSearch: !1,
123
124
  searchDebounce: () => 600,
124
125
  withIndex: undefined,
125
126
  withStore: undefined,
126
127
  withShow: undefined,
127
128
  withUpdate: undefined,
128
- hideAddBtn: undefined,
129
- hideUpdateBtn: undefined,
130
- hideShowBtn: undefined,
131
- hideDestroyBtn: undefined,
129
+ hideAddBtn: !1,
130
+ hideUpdateBtn: !1,
131
+ cloneBtn: !1,
132
+ hideShowBtn: !1,
133
+ hideDestroyBtn: !1,
132
134
  storeRoute: undefined,
133
- storeQueryParams: undefined,
135
+ storeQueryParams: !1,
134
136
  updateRoute: undefined,
135
- updateQueryParams: undefined,
137
+ updateQueryParams: !1,
136
138
  showRoute: undefined,
137
- showQueryParams: undefined,
138
- mouse: undefined,
139
- noRefreshBtn: undefined,
140
- endReach: undefined,
141
- showSelection: undefined,
142
- hideSelection: undefined,
143
- multiSelection: undefined,
144
- multiDestroy: undefined,
139
+ showQueryParams: !1,
140
+ mouse: !1,
141
+ noRefreshBtn: !1,
142
+ endReach: !1,
143
+ showSelection: !1,
144
+ hideSelection: !1,
145
+ multiSelection: !1,
146
+ multiDestroy: !1,
145
147
  rowsPerPageOptions: () => [50, 250, 500, 0],
146
148
  ignoreKeys: undefined,
147
149
  grid: undefined,
@@ -351,19 +353,20 @@ const hasUpdateBtn = computed<boolean>(() => {
351
353
  if (props.hideUpdateBtn) {
352
354
  return !1
353
355
  }
354
- return !!slots.form || !!props.updateRoute || !!props.updateQueryParams
356
+ return !!slots.form || !!props.updateRoute || props.updateQueryParams
355
357
  })
358
+ const hasCloneBtn = computed<boolean>(() => Boolean(props.cloneBtn))
356
359
  const hasShowBtn = computed<boolean>(() => {
357
360
  if (props.hideShowBtn) {
358
361
  return !1
359
362
  }
360
- return !!slots.show || !!props.showRoute || !!props.showQueryParams
363
+ return !!slots.show || !!props.showRoute || props.showQueryParams
361
364
  })
362
365
  const hasDestroyBtn = computed<boolean>(() => !props.hideDestroyBtn)
363
366
  const hasFilterDialog = computed<boolean>(() => !!slots.filter)
364
367
  const hasMenu = computed<boolean>(() => {
365
- const pdf = !!props.pdf && getRows.value.length > 0
366
- const excel = !!props.excel && getRows.value.length > 0
368
+ const pdf = props.pdf && getRows.value.length > 0
369
+ const excel = props.excel && getRows.value.length > 0
367
370
  if (pdf || excel) {
368
371
  return !0
369
372
  }
@@ -1014,7 +1017,6 @@ const onRowContextmenu = (e: MouseEvent | Event, row: MDtItem, index: number | u
1014
1017
  }
1015
1018
  const contextmenuItemsProp = computed(() => props.contextItems)
1016
1019
  const contextmenuItems = computed<any>(() => ([
1017
- ...(contextmenuItemsProp.value || []),
1018
1020
  {
1019
1021
  name: 'show',
1020
1022
  label: pluginOptions.value?.dt?.contextmenu?.btnStyle?.showLabel ? 'labels.show' : undefined,
@@ -1024,6 +1026,13 @@ const contextmenuItems = computed<any>(() => ([
1024
1026
  showIf: hasShowBtn.value,
1025
1027
  order: 100
1026
1028
  },
1029
+ {
1030
+ name: 'clone',
1031
+ label: pluginOptions.value?.dt?.contextmenu?.btnStyle?.showLabel ? 'labels.clone' : undefined,
1032
+ click: onCloneItem,
1033
+ showIf: hasCloneBtn.value,
1034
+ order: 200
1035
+ },
1027
1036
  {
1028
1037
  name: 'update',
1029
1038
  label: pluginOptions.value?.dt?.contextmenu?.btnStyle?.showLabel ? 'labels.update' : undefined,
@@ -1031,7 +1040,7 @@ const contextmenuItems = computed<any>(() => ([
1031
1040
  openUpdateDialog(item, index)
1032
1041
  },
1033
1042
  showIf: hasUpdateBtn.value,
1034
- order: 200
1043
+ order: 300
1035
1044
  },
1036
1045
  {
1037
1046
  name: 'destroy',
@@ -1044,9 +1053,28 @@ const contextmenuItems = computed<any>(() => ([
1044
1053
  attr: {
1045
1054
  color: 'negative'
1046
1055
  },
1047
- order: 300
1048
- }
1056
+ order: 400
1057
+ },
1058
+ ...(contextmenuItemsProp.value || [])
1049
1059
  ].sort((a, b) => (a.order ?? 0) - (b.order ?? 0))))
1060
+ const onCloneItem = (item: MDtItem) => {
1061
+ item = toValue(item)
1062
+ confirmMessage()
1063
+ .onOk(() => {
1064
+ $q.loading.show()
1065
+ getMythApiServicesSchema().clone(item.id)
1066
+ .then(({ _message }) => {
1067
+ _message && alertSuccess(_message)
1068
+ refreshNoUpdate()
1069
+ })
1070
+ .catch(({ _message }) => {
1071
+ _message && alertError(_message)
1072
+ })
1073
+ .finally(() => {
1074
+ $q.loading.hide()
1075
+ })
1076
+ })
1077
+ }
1050
1078
  const endReach = computed<boolean>(() => Boolean(props.endReach))
1051
1079
  const rowsPerPageOptions = computed(() => props.rowsPerPageOptions)
1052
1080
  const getRowsPerPageOptions = computed<any[]>(() => endReach.value ? [0] : (rowsPerPageOptions.value || [0]))
@@ -1774,6 +1802,15 @@ defineOptions({
1774
1802
  v-bind="{...defaultTopBtnProps,...pluginOptions.dt?.topSelection?.btn}"
1775
1803
  @click="openUpdateDialogNoIndex(tableOptions.selected[0] as any)"
1776
1804
  />
1805
+ <MDtBtn
1806
+ v-if="hasCloneBtn && isSingleSelectedItem"
1807
+ key="clone-dt-selection-btn"
1808
+ :disable="tableOptions.loading"
1809
+ clone
1810
+ tooltip="labels.clone"
1811
+ v-bind="{...defaultTopBtnProps,...pluginOptions.dt?.topSelection?.btn}"
1812
+ @click="onCloneItem(tableOptions.selected[0] as any)"
1813
+ />
1777
1814
  <MDtBtn
1778
1815
  v-if="hasShowBtn && isSingleSelectedItem"
1779
1816
  key="show-dt-selection-btn"
@@ -1926,7 +1963,7 @@ defineOptions({
1926
1963
  <q-td :props="noBodyProps">
1927
1964
  <!--Control-->
1928
1965
  <q-btn-dropdown
1929
- v-if="contextmenuItems.length>contextItemsLength"
1966
+ v-if="contextmenuItems.length > contextItemsLength"
1930
1967
  v-close-popup
1931
1968
  :menu-offset="[0,10]"
1932
1969
  color="primary"
@@ -1934,24 +1971,16 @@ defineOptions({
1934
1971
  outline
1935
1972
  v-bind="pluginOptions.dt?.controlDropdown"
1936
1973
  >
1937
- <q-list>
1974
+ <q-list
1975
+ :dense="getProp('dense')"
1976
+ separator
1977
+ >
1938
1978
  <MDtContextmenuItems
1939
1979
  :index="noBodyProps.rowIndex"
1940
1980
  :item="noBodyProps.row"
1941
1981
  :items="contextmenuItems"
1942
1982
  display-mode="item"
1943
1983
  />
1944
- <!--<q-item-->
1945
- <!-- v-for="contextmenuItem in contextmenuItems"-->
1946
- <!-- :key="`dt-r${contextmenuItem.name}`"-->
1947
- <!-- v-close-popup-->
1948
- <!-- clickable-->
1949
- <!--&gt;-->
1950
- <!-- <pre>{{ contextmenuItem }}</pre>-->
1951
- <!-- <q-item-section>-->
1952
- <!-- <q-item-label>{{ contextmenuItem.label }}</q-item-label>-->
1953
- <!-- </q-item-section>-->
1954
- <!--</q-item>-->
1955
1984
  </q-list>
1956
1985
  </q-btn-dropdown>
1957
1986
  <MRow
@@ -18,6 +18,7 @@ interface Props {
18
18
  show?: boolean | undefined;
19
19
  update?: boolean | undefined;
20
20
  destroy?: boolean | undefined;
21
+ clone?: boolean | undefined;
21
22
  tooltip?: string | null | undefined;
22
23
  color?: string | undefined;
23
24
  icon?: string | undefined;
@@ -32,6 +33,7 @@ const props = withDefaults(defineProps<Props>(), {
32
33
  show: undefined,
33
34
  update: undefined,
34
35
  destroy: undefined,
36
+ clone: undefined,
35
37
  color: undefined,
36
38
  icon: undefined,
37
39
  tooltip: undefined,
@@ -46,7 +48,7 @@ type Events = {
46
48
  }
47
49
  const emit = defineEmits<Events>()
48
50
 
49
- const hasTooltip = computed(() => !!props.tooltip || !!props.show || !!props.update || !!props.destroy)
51
+ const hasTooltip = computed(() => !!props.tooltip || !!props.show || !!props.update || !!props.destroy || !!props.clone)
50
52
  const { __, props: pluginOptions } = useMyth()
51
53
  const getTooltip = computed(() => {
52
54
  if (props.tooltip !== undefined) {
@@ -57,6 +59,8 @@ const getTooltip = computed(() => {
57
59
  return __('labels.update')
58
60
  } else if (props.destroy) {
59
61
  return __('labels.destroy')
62
+ } else if (props.clone) {
63
+ return __('labels.clone')
60
64
  }
61
65
  return props.tooltip
62
66
  })
@@ -67,6 +71,8 @@ const getIcon = computed(() => {
67
71
  return 'ion-ios-create'
68
72
  } else if (props.destroy) {
69
73
  return 'ion-ios-trash'
74
+ } else if (props.clone) {
75
+ return 'ion-copy'
70
76
  }
71
77
  return props.icon
72
78
  })
@@ -83,18 +89,20 @@ const getColor = computed<string | undefined>(() => {
83
89
  }
84
90
  return props.color
85
91
  })
86
- // const getLabel = computed(() => {
87
- // if (props.label) {
88
- // return __(props.label)
89
- // } else if (props.show) {
90
- // return __('labels.show')
91
- // } else if (props.update) {
92
- // return __('labels.update')
93
- // } else if (props.destroy) {
94
- // return __('labels.destroy')
95
- // }
96
- // return props.label
97
- // })
92
+ const getLabel = computed(() => {
93
+ if (props.label !== undefined) {
94
+ return __(props.label)
95
+ } else if (props.show) {
96
+ return __('labels.show')
97
+ } else if (props.update) {
98
+ return __('labels.update')
99
+ } else if (props.destroy) {
100
+ return __('labels.destroy')
101
+ } else if (props.clone) {
102
+ return __('labels.clone')
103
+ }
104
+ return props.label
105
+ })
98
106
 
99
107
  defineOptions({
100
108
  name: 'MDtBtn',
@@ -111,6 +119,7 @@ defineOptions({
111
119
  @click="emit('click',$event)"
112
120
  >
113
121
  <q-item-section
122
+ v-if="!!getIcon"
114
123
  side
115
124
  v-bind="pluginOptions.dt?.MDtBtn?.item?.avatarProps"
116
125
  >
@@ -123,7 +132,7 @@ defineOptions({
123
132
  <q-item-section v-bind="pluginOptions.dt?.MDtBtn?.item?.labelSectionProps">
124
133
  <q-item-label v-bind="pluginOptions.dt?.MDtBtn?.item?.itemLabelProps">
125
134
  <slot>
126
- {{ label ? __(label) : label }}
135
+ {{ __(getLabel) }}
127
136
  </slot>
128
137
  </q-item-label>
129
138
  </q-item-section>
@@ -15,6 +15,7 @@ import type { MDatatableDialogsOptions, MDatatableProps } from '../../types'
15
15
  import type { UnwrapRef } from 'vue'
16
16
  import { computed } from 'vue'
17
17
  import { useMyth } from '../../composable'
18
+ import { useI18n } from 'vue-i18n'
18
19
 
19
20
  interface Props {
20
21
  items: MDatatableProps['contextItems'],
@@ -31,6 +32,7 @@ const props = withDefaults(defineProps<Props>(), {
31
32
  })
32
33
  const itemMode = computed(() => props.displayMode === 'item')
33
34
  const { __ } = useMyth()
35
+ const { te } = useI18n({ useScope: 'global' })
34
36
  defineOptions({
35
37
  name: 'MDtContextmenuItems',
36
38
  inheritAttrs: !1
@@ -46,9 +48,7 @@ defineOptions({
46
48
  <MDtBtn
47
49
  v-if="typeof m.showIf === 'function' ? m.showIf(item,index) : m.showIf"
48
50
  :[m.name]="!0"
49
- :label="itemMode && m.label === undefined ? __(m.tooltip || m.attr?.label || m.attr?.tooltip || m.name) : (m.label !== undefined ?
50
- __(m.label || m.name) :
51
- undefined)"
51
+ :label="itemMode&&m.label===undefined?(te(`labels.${m.name}`)?__(`labels.${m.name}`):__(m.tooltip || m.attr?.label || m.attr?.tooltip || m.name)):(m.label!==undefined?__(m.label || m.name):undefined)"
52
52
  :list-item="itemMode"
53
53
  :tooltip="m.tooltip !== undefined ? m.tooltip : (m.label === undefined ? `labels.${m.name}` : undefined)"
54
54
  dense
@@ -24,7 +24,7 @@ export const useMyth = () => {
24
24
  const $route = useRoute()
25
25
  // eslint-disable-next-line @typescript-eslint/ban-ts-comment
26
26
  // @ts-ignore
27
- const __ = (key: any, ...rest: unknown[]) => !key ? '' : te(`attributes.${key}`) ? t(`attributes.${key}`, ...rest) : te(key) ? t(key, ...rest) : key
27
+ const __ = (key: any, ...rest: unknown[]) => !key ? key : te(`attributes.${key}`) ? t(`attributes.${key}`, ...rest) : te(key) ? t(key, ...rest) : key
28
28
  const getPageTitle = (route?: RouteLocationNormalizedLoaded | number | string, number?: number | string): string => {
29
29
  if (typeof route !== 'object') {
30
30
  number = route
@@ -56,6 +56,8 @@ export const useMyth = () => {
56
56
  const pluralize = Str.pascalCase(lodash.pluralize(lastRouteName))
57
57
  const singular = Str.pascalCase(lodash.singularize(lastRouteName))
58
58
  const keys = lodash.filter(lodash.uniq([
59
+ `routes.${routeName}`,
60
+ `routes.${routePath}`,
59
61
  `${lastRouteName}Page.title`,
60
62
  `${lodash.camelCase(lastRouteName)}Page.title`,
61
63
  `choice.${pluralize}`,
@@ -71,14 +73,6 @@ export const useMyth = () => {
71
73
  let str: string | null = null
72
74
  let k: string | any
73
75
 
74
- if (te((k = `routes.${routeName}`)) && lodash.isString((str = t(k)))) {
75
- return str
76
- }
77
-
78
- if (te((k = `routes.${routePath}`)) && lodash.isString((str = t(k)))) {
79
- return str
80
- }
81
-
82
76
  for (const f in keys) {
83
77
  if (!(k = keys[f])) {
84
78
  continue
@@ -38,6 +38,8 @@ export type HelpersStubSchema = {
38
38
 
39
39
  update (id: UrlType, data?: ParamsType, config?: AxiosRequestConfig): Promise<ApiInterface>;
40
40
 
41
+ clone (id: UrlType, data?: ParamsType, config?: AxiosRequestConfig): Promise<ApiInterface>;
42
+
41
43
  destroy (id: UrlType, config?: AxiosRequestConfig): Promise<ApiInterface>;
42
44
 
43
45
  destroyAll (ids?: UrlType[], config?: AxiosRequestConfig): Promise<ApiInterface>;
@@ -114,6 +114,7 @@ export type MDatatableDialogsOptions<T extends MDDIP = MDDIP> = {
114
114
  export interface MDtBtnProps extends MBtnProps {
115
115
  show?: boolean;
116
116
  update?: boolean;
117
+ clone?: boolean;
117
118
  destroy?: boolean;
118
119
  tooltip?: string | undefined;
119
120
  color?: string;
@@ -226,6 +227,7 @@ export type MDatatableProps<I extends GenericFormValues = GenericFormValues> = O
226
227
  withUpdate?: string | string[];
227
228
  hideAddBtn?: boolean;
228
229
  hideUpdateBtn?: boolean;
230
+ cloneBtn?: boolean;
229
231
  hideShowBtn?: boolean;
230
232
  hideDestroyBtn?: boolean;
231
233
  storeRoute?: string | RouteLocationRaw;
@@ -87,6 +87,12 @@ export const Helpers = {
87
87
  data && Helpers.appendArray(formData, data)
88
88
  return axios().post(u, formData, config)
89
89
  },
90
+ async clone (id: UrlType, data?: ParamsType, config?: AxiosRequestConfig) {
91
+ const u = makeUrl(`${id}/Clone`)
92
+ const formData = new FormData()
93
+ data && Helpers.appendArray(formData, data)
94
+ return axios().post(u, formData, config)
95
+ },
90
96
  async destroy (id: UrlType, config?: AxiosRequestConfig) {
91
97
  const u = makeUrl(id)
92
98
  return axios().delete(u, config)