0

In popular frameworks like PrimeVue or ElementPlus there is some sort of hack with slots when they are used like params for parent component, for example in DataTables. I'm trying to do something similar, but stuck with reactivity...

Currently in my parent component I have this:

<script setup>
import {onMounted, useSlots, watch, h, computed} from 'vue';
import { useDataTableStore } from '@/components/DataTable/DataTableStore';

const dataTableStore = useDataTableStore();
const slots = useSlots();

const props = defineProps({
    data: {
        type: Array,
        required: true,
    },
});

onMounted(() => {
    dataTableStore.orderAll = props.orderAll;
    dataTableStore.searchAll = props.searchAll;

    slots.default().forEach(s => {
        dataTableStore.columns.push({
            title: s.props.title,
            prop: s.props.prop ?? s.props.title,
            order: s.props.order ?? false,
            search: s.props.search ?? false,
            searchType: s.props['search-type'] ?? 'text',
            searchOptions: s.props['search-options'] ?? []
        });
    });
});
</script>

The main problem is that the props of slots are not reactive.

<DataTable
    :data="packagesStore.packages"
    :columns="columns"
    :search-all="true"
    :order-all="true"
    @on-filter="onFilter"
>
    <DataTableColumn
        title="Nr."
        prop="number"
        :search="false"
    />
    <DataTableColumn
        title="Wood"
        prop="wood.id"
        search-type="select"
        :search-options="classificatorsStore.quality"
    />
</DataTable/>
Kin
  • 4,466
  • 13
  • 54
  • 106

1 Answers1

0

The problem that you don't even use the reactivity of the props. My bet computed could suit you:

const props = defineProps({
    data: {
        type: Array,
        required: true,
    },
});

const dataTableStore = computed(() => ({

    // why these props? we have only props.data as declared in defineProps()
    orderAll: props.orderAll, 
    searchAll: props.searchAll,

    // not sure about that, you can't have multiple slots with the same name I guess
    // needs investigation
    columns: slots.default().map(s => {
        return {
            title: s.props.title,
            prop: s.props.prop ?? s.props.title,
            order: s.props.order ?? false,
            search: s.props.search ?? false,
            searchType: s.props['search-type'] ?? 'text',
            searchOptions: s.props['search-options'] ?? []
        };
    });
}));
Alexander Nenashev
  • 8,775
  • 2
  • 6
  • 17