I implemented a feature that allows collapsing sections within a table body. There is an "add" button represented by the "+" sign, and when clicked, it adds a new collapse section with content. I want to display the name of the data row (e.g., "iPhone") which should then appear as the title of the new collapse section.
It's functioning well, but I'm facing an issue: the title of the created collapse is displaying as "object MouseEvent".https://i.sstatic.net/SQrIq.png
CollapseSection.vue
<template>
<div class="accordion" role="tablist">
<b-button block v-b-toggle.accordion-1 class="collapse-btn" align-h="between">
{{ selectText }}
<b-icon :icon="visible ? 'caret-down' : 'caret-up'" class="icon"></b-icon>
</b-button>
<b-card no-body class="mb-1">
<b-collapse id="accordion-1" v-model="visible" accordion="my-accordion" role="tabpanel">
<SearchField></SearchField>
<b-card-body>
<!-- CONTENT WOULD APPEAR INSIDE THIS SLOT -->
<slot name="content" :addItem="addItem">
</slot>
</b-card-body>
</b-collapse>
</b-card>
<!-- DYNAMIC CONTENT COLLAPSE WHEN CLICK ON ADD BUTTON -->
<div v-for="(item, index) in items" :key="index">
<b-button block v-b-toggle="'accordion-' + (index + 2)" class="collapse-btn">
{{ item.name }}
<b-icon :icon="visible ? 'caret-down' : 'caret-up'" class="icon"></b-icon>
</b-button>
<b-card no-body class="mb-1">
<b-collapse :id="'accordion-' + (index + 2)" accordion="my-accordion" role="tabpanel">
<b-card-body>
<!-- CONTENT WOULD APPEAR INSIDE THIS SLOT -->
<slot name="createdContent">
</slot>
</b-card-body>
</b-collapse>
</b-card>
</div>
</div>
</template>
<script>
import SearchField from "@/components/UI/SearchField.vue";
export default {
name: "CollapseButton",
components: {SearchField},
props: {
selectText: {
type: String,
default: () => "Select",
},
},
data() {
return {
isConfiguring: false,
configuringItem: null,
items: [],
visible: false,
}
},
methods: {
addItem(name) {
const item = { name };
this.items.push(item);
this.isConfiguring = true;
this.configuringItem = item;
this.$emit('item-added', item);
}
},
}
</script>
DataTable.vue
<template>
<tbody>
<tr v-for="(item, itemIndex) in data" :key="itemIndex">
<td>
<slot></slot>
</td>
<td v-for="(label, labelIndex) in labels" :key="labelIndex">
{{ item[label.field] }}
</td>
</tr>
</tbody
</template>
<script>
export default {
name: "DataTable",
components: {ActionColumn},
props: {
labels: {
type: Array,
required: true,
},
data: {
type: Array,
required: true,
},
},
methods: {
addItem(name) {
this.$emit('add-item', name);
}
}
}
</script>
NewLab.vue
<CollapseSection select-text="Select Images">
<template #content="{ addItem }">
<DataTable :labels="labels" :data="data" :showAdd="true">
<b-icon icon="plus" class="add-btn" @click="addItem(data.name)">
</b-icon>
</DataTable>
</template>
<template #createdContent>
<CollapseTabContent>
</CollapseTabContent>
</template>
</CollapseSection>
<script>
const labels = [
{text: "Name", field: 'name'},
{text: "Description", field: 'description'},
]
const data = [
{name: 'Windows 1', description: 'Password Cracking'},
{name: 'Windows 13', description: 'SIEM and MISP machine'},
{name: 'Windows 15', description: 'AD auditing lab'},
{name: 'Windows 31', description: 'Threat Hunting and Investigation'},
];
export default {
name: "NewLab",
components: {DataTable, CollapseSection},
data() {
return {
labels: labels,
data: data,
};
},
</script>