@it-enterprise/forcebpm-ui-kit 1.0.2-beta.21 → 1.0.2-beta.22
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/index.js +15 -0
- package/package.json +29 -6
- package/plugin.js +13 -24
- package/src/FAvatar.vue +27 -70
- package/src/FConfirmModal.vue +5 -21
- package/src/FContextMenu.vue +33 -57
- package/src/FDialog.vue +264 -0
- package/src/FNoData.vue +0 -1
- package/src/FNotify.vue +18 -62
- package/src/FPreLoader.vue +5 -10
- package/src/FSearchPanel.vue +188 -0
- package/src/FShare.vue +3 -16
- package/src/FTruncate.vue +121 -0
- package/src/FUserRoles.vue +195 -0
- package/src/f-date-picker/FDatePicker.vue +322 -0
- package/src/f-date-picker/FMenuDatePicker.vue +337 -0
- package/src/f-date-picker/FTextFieldDate.vue +498 -0
- package/src/f-toolbar/FFilterPanel.vue +62 -0
- package/src/f-toolbar/FSortPanel.vue +47 -0
- package/src/f-toolbar/FTabPanel.vue +123 -0
- package/src/f-toolbar/FToolbar.vue +131 -0
- package/src/f-toolbar/FViewerPanel.vue +71 -0
- package/src/forcebpmIcon.js +69 -0
- package/src/locales/en.json +24 -24
- package/src/locales/ru.json +24 -24
- package/src/locales/uk.json +24 -24
- package/src/scss/buttons.scss +1 -43
- package/src/scss/card.scss +6 -0
- package/src/scss/expansion.scss +0 -5
- package/src/scss/index.scss +0 -2
- package/src/scss/input.scss +49 -6
- package/src/scss/overlay.scss +3 -3
- package/src/scss/pagination.scss +1 -5
- package/src/scss/skeleton.scss +1 -68
- package/src/scss/snackbar.scss +1 -1
- package/src/scss/tables.scss +141 -145
- package/src/scss/checkbox.scss +0 -25
|
@@ -0,0 +1,337 @@
|
|
|
1
|
+
<script setup>
|
|
2
|
+
// FMenuDatePicker
|
|
3
|
+
import { ref, computed, watch, nextTick } from 'vue'
|
|
4
|
+
import moment from 'moment'
|
|
5
|
+
import FDatePicker from './FDatePicker.vue'
|
|
6
|
+
import FTextFieldDate from './FTextFieldDate.vue'
|
|
7
|
+
|
|
8
|
+
const props = defineProps({
|
|
9
|
+
title: {
|
|
10
|
+
type: String,
|
|
11
|
+
default: null,
|
|
12
|
+
validator(value, props) {
|
|
13
|
+
if (!props.isInput && !props.isRange) {
|
|
14
|
+
console.warn('title cannot be used with isInput=false and isRange=false')
|
|
15
|
+
return false
|
|
16
|
+
}
|
|
17
|
+
return true
|
|
18
|
+
}
|
|
19
|
+
},
|
|
20
|
+
prependText: {
|
|
21
|
+
type: String,
|
|
22
|
+
default: null
|
|
23
|
+
},
|
|
24
|
+
type: {
|
|
25
|
+
type: String,
|
|
26
|
+
default: 'date',
|
|
27
|
+
validator: value => ['date', 'datetime'].includes(value)
|
|
28
|
+
},
|
|
29
|
+
color: {
|
|
30
|
+
type: String,
|
|
31
|
+
default: 'secondary'
|
|
32
|
+
},
|
|
33
|
+
disabled: {
|
|
34
|
+
type: Boolean,
|
|
35
|
+
default: false
|
|
36
|
+
},
|
|
37
|
+
isRange: {
|
|
38
|
+
type: Boolean,
|
|
39
|
+
default: false
|
|
40
|
+
},
|
|
41
|
+
isInput: {
|
|
42
|
+
type: Boolean,
|
|
43
|
+
default: true
|
|
44
|
+
},
|
|
45
|
+
clearable: {
|
|
46
|
+
type: Boolean,
|
|
47
|
+
default: false
|
|
48
|
+
},
|
|
49
|
+
isTodayMin: {
|
|
50
|
+
type: Boolean,
|
|
51
|
+
default: false
|
|
52
|
+
},
|
|
53
|
+
menu: {
|
|
54
|
+
type: Boolean,
|
|
55
|
+
default: false
|
|
56
|
+
},
|
|
57
|
+
menuProps: {
|
|
58
|
+
type: Object,
|
|
59
|
+
default: () => ({
|
|
60
|
+
top: true
|
|
61
|
+
})
|
|
62
|
+
},
|
|
63
|
+
allowedDates: {
|
|
64
|
+
type: Function,
|
|
65
|
+
default: () => true
|
|
66
|
+
}
|
|
67
|
+
})
|
|
68
|
+
|
|
69
|
+
const modelValue = defineModel({
|
|
70
|
+
type: [String, Date, Object],
|
|
71
|
+
default: ''
|
|
72
|
+
})
|
|
73
|
+
|
|
74
|
+
const localMenu = ref(props.menu)
|
|
75
|
+
const textDate = ref(null)
|
|
76
|
+
const textFromDate = ref(null)
|
|
77
|
+
const textToDate = ref(null)
|
|
78
|
+
const date = ref(props.isRange ? { from: null, to: null } : null)
|
|
79
|
+
const FORMAT_DATE = props.type === 'date' ? 'YYYY-MM-DD' : 'YYYY-MM-DD HH:mm'
|
|
80
|
+
|
|
81
|
+
const emit = defineEmits(['save', 'cancel', 'update:menu'])
|
|
82
|
+
|
|
83
|
+
const isInputDate = computed(() => {
|
|
84
|
+
return props.title ? Boolean(textDate.value && date.value) : true
|
|
85
|
+
})
|
|
86
|
+
|
|
87
|
+
const isInputRangeDate = computed(() => {
|
|
88
|
+
return props.title ? Boolean(textFromDate.value && textToDate.value && date.value) : true
|
|
89
|
+
})
|
|
90
|
+
|
|
91
|
+
const isValidDate = computed(() => {
|
|
92
|
+
return props.isRange ? moment(textFromDate.value).isValid() && moment(textToDate.value).isValid() : moment(textDate.value).isValid()
|
|
93
|
+
})
|
|
94
|
+
|
|
95
|
+
const initDate = () => {
|
|
96
|
+
if (
|
|
97
|
+
modelValue.value &&
|
|
98
|
+
(moment.isMoment(modelValue.value) ||
|
|
99
|
+
((typeof modelValue.value === 'string' || modelValue.value instanceof Date) && moment(modelValue.value).isValid()))
|
|
100
|
+
) {
|
|
101
|
+
const formattedValue = moment(modelValue.value).format(FORMAT_DATE)
|
|
102
|
+
textDate.value = formattedValue
|
|
103
|
+
date.value = formattedValue
|
|
104
|
+
return
|
|
105
|
+
}
|
|
106
|
+
|
|
107
|
+
if (modelValue.value && props.isRange && typeof modelValue.value === 'object' && modelValue.value.from && modelValue.value.to) {
|
|
108
|
+
date.value = {
|
|
109
|
+
from: moment(modelValue.value.from).isValid() ? moment(modelValue.value.from).format(FORMAT_DATE) : modelValue.value.from,
|
|
110
|
+
to: moment(modelValue.value.to).isValid() ? moment(modelValue.value.to).format(FORMAT_DATE) : modelValue.value.to
|
|
111
|
+
}
|
|
112
|
+
textFromDate.value = date.value.from
|
|
113
|
+
textToDate.value = date.value.to
|
|
114
|
+
} else {
|
|
115
|
+
textDate.value = null
|
|
116
|
+
textFromDate.value = null
|
|
117
|
+
textToDate.value = null
|
|
118
|
+
date.value = props.isRange ? { from: null, to: null } : null
|
|
119
|
+
}
|
|
120
|
+
}
|
|
121
|
+
|
|
122
|
+
const menuAllowedDates = val => {
|
|
123
|
+
if (props.isTodayMin) {
|
|
124
|
+
return moment(val).isSameOrAfter(moment(), 'day')
|
|
125
|
+
} else {
|
|
126
|
+
return props.allowedDates(val)
|
|
127
|
+
}
|
|
128
|
+
}
|
|
129
|
+
const rangeFromAllowedDates = val => {
|
|
130
|
+
return moment(val).isSameOrBefore(moment(date.value.to), 'day')
|
|
131
|
+
}
|
|
132
|
+
const rangeToAllowedDates = val => {
|
|
133
|
+
return moment(val).isSameOrAfter(moment(date.value.from), 'day')
|
|
134
|
+
}
|
|
135
|
+
|
|
136
|
+
const textFieldFromDateHandler = value => {
|
|
137
|
+
textFromDate.value = value
|
|
138
|
+
if (date.value) {
|
|
139
|
+
date.value.from = value || null
|
|
140
|
+
modelValue.value = date.value
|
|
141
|
+
}
|
|
142
|
+
}
|
|
143
|
+
|
|
144
|
+
const textFieldToDateHandler = value => {
|
|
145
|
+
textToDate.value = value
|
|
146
|
+
if (date.value) {
|
|
147
|
+
date.value.to = value || null
|
|
148
|
+
modelValue.value = date.value
|
|
149
|
+
}
|
|
150
|
+
}
|
|
151
|
+
|
|
152
|
+
const textFieldDateHandler = value => {
|
|
153
|
+
textDate.value = value
|
|
154
|
+
date.value = value || null
|
|
155
|
+
modelValue.value = date.value
|
|
156
|
+
}
|
|
157
|
+
|
|
158
|
+
const clearDate = () => {
|
|
159
|
+
textFromDate.value = null
|
|
160
|
+
textToDate.value = null
|
|
161
|
+
textDate.value = null
|
|
162
|
+
date.value = null
|
|
163
|
+
modelValue.value = date.value
|
|
164
|
+
}
|
|
165
|
+
|
|
166
|
+
const cancel = () => {
|
|
167
|
+
initDate()
|
|
168
|
+
localMenu.value = false
|
|
169
|
+
}
|
|
170
|
+
|
|
171
|
+
const menuHandler = val => {
|
|
172
|
+
emit('update:menu', val)
|
|
173
|
+
|
|
174
|
+
if (val === false) {
|
|
175
|
+
nextTick(() => {
|
|
176
|
+
cancel()
|
|
177
|
+
})
|
|
178
|
+
}
|
|
179
|
+
}
|
|
180
|
+
|
|
181
|
+
const save = () => {
|
|
182
|
+
localMenu.value = false
|
|
183
|
+
|
|
184
|
+
if (props.isRange) {
|
|
185
|
+
if (date.value && date.value.from && date.value.to) {
|
|
186
|
+
modelValue.value = date.value
|
|
187
|
+
emit('save', date.value)
|
|
188
|
+
}
|
|
189
|
+
} else {
|
|
190
|
+
if (date.value) {
|
|
191
|
+
const formattedValue = typeof date.value === 'string' ? date.value : moment(date.value).format(FORMAT_DATE)
|
|
192
|
+
modelValue.value = formattedValue
|
|
193
|
+
emit('save', formattedValue)
|
|
194
|
+
}
|
|
195
|
+
}
|
|
196
|
+
}
|
|
197
|
+
|
|
198
|
+
watch(modelValue, initDate, { immediate: true })
|
|
199
|
+
|
|
200
|
+
watch(
|
|
201
|
+
() => props.menu,
|
|
202
|
+
newVal => {
|
|
203
|
+
localMenu.value = newVal
|
|
204
|
+
}
|
|
205
|
+
)
|
|
206
|
+
</script>
|
|
207
|
+
|
|
208
|
+
<template>
|
|
209
|
+
<div class="f-menu-date-picker d-flex align-center">
|
|
210
|
+
<template v-if="isInput">
|
|
211
|
+
<div v-if="isRange && isInputRangeDate" class="d-flex align-center f-menu-date-picker-range-input">
|
|
212
|
+
<!-- From input date -->
|
|
213
|
+
<div class="d-flex align-center">
|
|
214
|
+
<FTextFieldDate
|
|
215
|
+
v-model="textFromDate"
|
|
216
|
+
:type="type"
|
|
217
|
+
:color="color"
|
|
218
|
+
:disabled="disabled"
|
|
219
|
+
:allowed-dates="rangeFromAllowedDates"
|
|
220
|
+
@blur="textFieldFromDateHandler"
|
|
221
|
+
/>
|
|
222
|
+
</div>
|
|
223
|
+
|
|
224
|
+
<FIcon icon="ctx-arrow-next" :color="color" class="mx-1" />
|
|
225
|
+
|
|
226
|
+
<!-- To input date -->
|
|
227
|
+
<div class="d-flex align-center">
|
|
228
|
+
<FTextFieldDate
|
|
229
|
+
v-model="textToDate"
|
|
230
|
+
:type="type"
|
|
231
|
+
:color="color"
|
|
232
|
+
:disabled="disabled"
|
|
233
|
+
:allowed-dates="rangeToAllowedDates"
|
|
234
|
+
@blur="textFieldToDateHandler"
|
|
235
|
+
/>
|
|
236
|
+
</div>
|
|
237
|
+
</div>
|
|
238
|
+
|
|
239
|
+
<template v-else-if="isInputDate">
|
|
240
|
+
<!-- Prepend text -->
|
|
241
|
+
<span v-if="prependText" :class="`text-${color}`" class="f-menu-date-picker-prepend-text mr-1">{{ prependText }}:</span>
|
|
242
|
+
|
|
243
|
+
<!-- Input date -->
|
|
244
|
+
<FTextFieldDate
|
|
245
|
+
v-model="textDate"
|
|
246
|
+
:type="type"
|
|
247
|
+
:color="color"
|
|
248
|
+
:disabled="disabled"
|
|
249
|
+
:allowed-dates="menuAllowedDates"
|
|
250
|
+
@blur="textFieldDateHandler"
|
|
251
|
+
/>
|
|
252
|
+
</template>
|
|
253
|
+
</template>
|
|
254
|
+
|
|
255
|
+
<!-- Select date -->
|
|
256
|
+
<v-menu
|
|
257
|
+
v-model="localMenu"
|
|
258
|
+
v-bind="menuProps"
|
|
259
|
+
persistent
|
|
260
|
+
min-width="auto"
|
|
261
|
+
offset="0, -6"
|
|
262
|
+
location="bottom right"
|
|
263
|
+
content-class="f-menu-date-picker-content"
|
|
264
|
+
:disabled="disabled"
|
|
265
|
+
:close-on-content-click="false"
|
|
266
|
+
@update:model-value="menuHandler"
|
|
267
|
+
>
|
|
268
|
+
<template #activator="{ props: propsMenu }">
|
|
269
|
+
<div v-bind="propsMenu" class="f-menu-date-picker-activator">
|
|
270
|
+
<span v-if="!isInputDate && !isInputRangeDate" class="d-flex align-center">
|
|
271
|
+
<!-- Prepend text -->
|
|
272
|
+
<span v-if="prependText" :class="`text-${color}`" class="f-menu-date-picker-prepend-text mr-1">{{ prependText }}:</span>
|
|
273
|
+
<!-- Title -->
|
|
274
|
+
<span :class="disabled ? 'is-disabled' : `text-${color}`" class="f-menu-date-picker-title">{{ title }}</span>
|
|
275
|
+
</span>
|
|
276
|
+
|
|
277
|
+
<!-- Icon -->
|
|
278
|
+
<v-tooltip location="top" offset="8" :disabled="disabled" :text="$t('tooltip.calendar')">
|
|
279
|
+
<template #activator="{ props: propsTooltip }">
|
|
280
|
+
<FIcon icon="calendar" :color="color" class="ml-1" :class="disabled ? 'cursor-default' : 'cursor-pointer'" v-bind="propsTooltip" />
|
|
281
|
+
</template>
|
|
282
|
+
</v-tooltip>
|
|
283
|
+
</div>
|
|
284
|
+
</template>
|
|
285
|
+
|
|
286
|
+
<FDatePicker
|
|
287
|
+
v-model="date"
|
|
288
|
+
is-actions
|
|
289
|
+
:is-range="isRange"
|
|
290
|
+
:type="type"
|
|
291
|
+
:color="color"
|
|
292
|
+
:allowed-dates="menuAllowedDates"
|
|
293
|
+
@save="save"
|
|
294
|
+
@cancel="cancel"
|
|
295
|
+
/>
|
|
296
|
+
</v-menu>
|
|
297
|
+
|
|
298
|
+
<!-- Clear date -->
|
|
299
|
+
<v-tooltip v-if="clearable && isValidDate && !disabled" location="top" offset="12" :text="$t('tooltip.clearDate')">
|
|
300
|
+
<template #activator="{ props: propsClear }">
|
|
301
|
+
<v-btn v-bind="propsClear" variant="text" size="16" class="ml-1 pt-1 f-menu-date-picker-clear-btn" @click="clearDate">
|
|
302
|
+
<FIcon icon="times" color="secondary" size="12" />
|
|
303
|
+
</v-btn>
|
|
304
|
+
</template>
|
|
305
|
+
</v-tooltip>
|
|
306
|
+
</div>
|
|
307
|
+
</template>
|
|
308
|
+
|
|
309
|
+
<style lang="scss" scoped>
|
|
310
|
+
.f-menu-date-picker {
|
|
311
|
+
.f-menu-date-picker-prepend-text {
|
|
312
|
+
font-size: 1.1em;
|
|
313
|
+
}
|
|
314
|
+
.f-menu-date-picker-activator {
|
|
315
|
+
display: flex;
|
|
316
|
+
position: relative;
|
|
317
|
+
bottom: 2px;
|
|
318
|
+
.f-menu-date-picker-title {
|
|
319
|
+
font-size: 1.1em;
|
|
320
|
+
position: relative;
|
|
321
|
+
&::after {
|
|
322
|
+
content: '';
|
|
323
|
+
display: block;
|
|
324
|
+
position: absolute;
|
|
325
|
+
bottom: 0;
|
|
326
|
+
min-height: 0.5px;
|
|
327
|
+
height: 0.5px;
|
|
328
|
+
width: 100%;
|
|
329
|
+
background: currentColor;
|
|
330
|
+
}
|
|
331
|
+
&.is-disabled::after {
|
|
332
|
+
content: none;
|
|
333
|
+
}
|
|
334
|
+
}
|
|
335
|
+
}
|
|
336
|
+
}
|
|
337
|
+
</style>
|