v-sistec-features 1.10.5 → 1.11.0

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,7 +1,7 @@
1
1
  {
2
2
  "name": "v-sistec-features",
3
3
  "private": false,
4
- "version": "1.10.5",
4
+ "version": "1.11.0",
5
5
  "author": "Márlon Bento Azevedo (https://github.com/marlon-bento)",
6
6
  "repository": {
7
7
  "type": "git",
@@ -22,10 +22,8 @@
22
22
 
23
23
  <Search v-model:search="pagination.search" v-model:filter="pagination.filter" :list_filter="props.list_filter"
24
24
  :item_use="item_use" @search="reSearch" :deactivate_search_on_clear="props.deactivate_search_on_clear"
25
- :placeholder_search="props.placeholder_search"
26
- :deactivate_search_empty="props.deactivate_search_empty"
27
- @clicked-clear-search="$emit('clickedClearSearch')"
28
- />
25
+ :placeholder_search="props.placeholder_search" :deactivate_search_empty="props.deactivate_search_empty"
26
+ @clicked-clear-search="$emit('clickedClearSearch')" />
29
27
  </div>
30
28
  <slot name="item-selected-info" :selected_items="selected_items" :clearSelection="() => selected_items = []">
31
29
  <div v-if="(props.use_checkbox && selected_items.length > 0) && !props.deactivate_selected_info"
@@ -165,7 +163,10 @@
165
163
  </tr> -->
166
164
 
167
165
  <draggable v-model="draggableColumns" tag="tr" item-key="header" :animation="400"
168
- ghost-class="ghost-item" drag-class="dragging-item">
166
+ ghost-class="ghost-item" drag-class="dragging-item"
167
+ @start="isDraggingColumns = true"
168
+ @end="() => onDragEnd()"
169
+ >
169
170
  <template #header>
170
171
  <th v-if="props.use_expandable_items"></th>
171
172
  <th v-if="props.use_checkbox" class="w-1">
@@ -286,7 +287,7 @@
286
287
  </thead>
287
288
  <tbody>
288
289
  <template v-for="item in items" :key="item[props.item_key]">
289
- <TransitionGroup tag="tr" name="column-move">
290
+ <TransitionGroup tag="tr" :name="isDraggingColumns ? 'column-move' : ''" >
290
291
  <td v-if="props.use_expandable_items" class="w-1">
291
292
  <slot name="expand-button" :item="item" :is-expanded="is_item_expanded(item)"
292
293
  :expand_item_toggle="expand_item_toggle">
@@ -369,7 +370,7 @@
369
370
  <Transition :name="'expand-item-' + props.type_animation_expand"
370
371
  :css="!props.deactivate_animation_expand">
371
372
  <!-- mostra uma linha após cada item -->
372
- <tr v-if="is_item_expanded(item)" class="">
373
+ <tr :id="'expand-item-' + item[props.item_key]" v-if="is_item_expanded(item)" class="">
373
374
  <!-- se estiver usando checkbox existe uma coluna a mais -->
374
375
  <td :colspan="colspanExpandItems()">
375
376
  <slot name="after-row" :item="item">
@@ -421,6 +422,7 @@ import Search from './SearchDatatable.vue';
421
422
  import { useImagePreview } from '../composables/useImagePreview';
422
423
  import { dataTableApiKey, type ColumnConfiguration } from '../keys';
423
424
  import draggable from 'vuedraggable';
425
+ import { useExpandedItem } from '../composables/useExpandedItem';
424
426
 
425
427
  const {
426
428
  isHovering,
@@ -468,6 +470,8 @@ const props = withDefaults(defineProps<VDataTableProps>(), {
468
470
  placeholder_search: "Buscar...",
469
471
  deactivate_search_on_clear: false,
470
472
  use_expandable_items: false,
473
+ close_expanded_item_on_expand_new: false,
474
+ scroll_to_expanded_item: false,
471
475
  type_animation_expand: 'expand',
472
476
  deactivate_animation_expand: false,
473
477
  type_button_expand: 'arrow',
@@ -487,10 +491,11 @@ const columns = ref<ColumnConfiguration[]>([]);
487
491
  const items = ref<T[]>([]) as Ref<T[]>;
488
492
  const totalItems = ref<number>(0);
489
493
  const selected_items = ref<T[]>([]) as Ref<T[]>;
490
- const expanded_items = ref<any[]>([]);
491
494
  const selectAllCheckbox = ref<HTMLInputElement | null>(null);
492
495
  const isDelaying = ref<boolean>(false);
493
496
  const delayTimer = ref<ReturnType<typeof setTimeout> | null>(null);
497
+ // só ativa animação de arrastar colunas quando estiver arrastando
498
+ const isDraggingColumns = ref(false);
494
499
 
495
500
  /*--------- definição de páginação ---------------*/
496
501
  const pagination = ref<PaginationObject>({
@@ -505,6 +510,18 @@ const urlReativa = computed(() => {
505
510
  pagination.value.current_page = props.page_starts_at;
506
511
  return props.endpoint;
507
512
  });
513
+
514
+ const {
515
+ expanded_items,
516
+ expand_item_toggle,
517
+ is_item_expanded
518
+ } = useExpandedItem(
519
+ props.close_expanded_item_on_expand_new,
520
+ props.item_key,
521
+ props.deactivate_animation_expand,
522
+ props.scroll_to_expanded_item
523
+ );
524
+
508
525
  // =======================================================
509
526
  // 3. LÓGICA DA API (useFetch)
510
527
  // =======================================================
@@ -658,7 +675,11 @@ watch(response, (newResponse: any) => {
658
675
  // =======================================================
659
676
  // 6. MÉTODOS
660
677
  // =======================================================
661
-
678
+ function onDragEnd() {
679
+ setTimeout(() => {
680
+ isDraggingColumns.value = false;
681
+ }, 500);
682
+ }
662
683
  // Função para marcar ou desmarcar todos os itens da página atual
663
684
  function toggleSelectAll(): void {
664
685
  const pageItems = items.value;
@@ -811,19 +832,9 @@ function set_page(newPage: number): void {
811
832
  console.warn("Número de página inválido.");
812
833
  }
813
834
  }
814
- function expand_item_toggle(item: any): void {
815
- const identifier_item = item[props.item_key];
816
- const index = expanded_items.value.findIndex(expandedItem => expandedItem === identifier_item);
817
- if (index > -1) {
818
- expanded_items.value.splice(index, 1); // Remove se já existe
819
- } else {
820
- expanded_items.value.push(identifier_item); // Adiciona se não existe
821
- }
822
- }
823
- function is_item_expanded(item: any): boolean {
824
- const identifier_item = item[props.item_key];
825
- return expanded_items.value.some(expandedItem => expandedItem === identifier_item);
826
- }
835
+
836
+
837
+
827
838
  function close_all_expanded_items(): void {
828
839
  expanded_items.value = [];
829
840
  }
@@ -0,0 +1,77 @@
1
+ import { ref, nextTick } from 'vue';
2
+
3
+ export function useExpandedItem(
4
+ close_expanded_item_on_expand_new: boolean,
5
+ item_key: string,
6
+ deactivate_animation_expand?: boolean,
7
+ scroll_to_expanded_item?: boolean
8
+ ) {
9
+ const expanded_items = ref<any[]>([]);
10
+
11
+ function close_all_expanded_items() {
12
+ expanded_items.value = [];
13
+ }
14
+
15
+ function is_item_expanded(item: any): boolean {
16
+ const identifier_item = item[item_key];
17
+ return expanded_items.value.some((expandedItem: any) => expandedItem === identifier_item);
18
+ }
19
+
20
+ function expand_item_toggle(item: any): void {
21
+ const identifier_item = item[item_key];
22
+
23
+ // 1. Verificamos se já existe
24
+ const index = expanded_items.value.findIndex((expandedItem: any) => expandedItem === identifier_item);
25
+ const is_already_expanded = index > -1;
26
+
27
+ // 2. Lógica para fechar o item expandido ao abrir um novo
28
+ if (close_expanded_item_on_expand_new) {
29
+ close_all_expanded_items();
30
+
31
+ if (!is_already_expanded) {
32
+ expanded_items.value.push(identifier_item);
33
+ if (scroll_to_expanded_item){
34
+ scrollToExpadedItem(identifier_item);
35
+ }
36
+ }
37
+ }
38
+ // 3. Lógica padrão (multiplos)
39
+ else {
40
+ if (is_already_expanded) {
41
+ expanded_items.value.splice(index, 1);
42
+ } else {
43
+ expanded_items.value.push(identifier_item);
44
+ if (scroll_to_expanded_item){
45
+ scrollToExpadedItem(identifier_item);
46
+ }
47
+
48
+ }
49
+ }
50
+ }
51
+ function scrollToExpadedItem(identifier_item: any): void {
52
+ nextTick(() => {
53
+ if (deactivate_animation_expand) {
54
+
55
+ const rowElements: HTMLElement | null = document.querySelector('#expand-item-' + identifier_item)
56
+ if (rowElements) {
57
+ rowElements.scrollIntoView({ behavior: 'smooth', block: 'center' });
58
+ }
59
+ return;
60
+ } else {
61
+ setTimeout(() => {
62
+ const rowElements: HTMLElement | null = document.querySelector('#expand-item-' + identifier_item)
63
+ if (rowElements) {
64
+ rowElements.scrollIntoView({ behavior: 'smooth', block: 'center' });
65
+ }
66
+ }, 600); // espera a animação terminar
67
+ }
68
+ });
69
+
70
+ }
71
+ return {
72
+ expanded_items,
73
+ is_item_expanded,
74
+ expand_item_toggle,
75
+ close_all_expanded_items
76
+ };
77
+ }
@@ -55,6 +55,9 @@ export interface VDataTableProps {
55
55
  // Ativa a funcionalidade de seleção com checkboxes
56
56
  use_checkbox?: boolean;
57
57
  use_expandable_items?: boolean;
58
+ close_expanded_item_on_expand_new?: boolean;
59
+ scroll_to_expanded_item?: boolean;
60
+
58
61
  type_animation_expand?: 'fade' | 'expand' | 'none';
59
62
  deactivate_animation_expand?: boolean;
60
63
  type_button_expand?: 'arrow' | 'plus';