Я пытаюсь в основном отобразить некоторые дочерние данные в модальном слоте. По сути, родительский компонент - это страница, дочерний компонент - это таблица, а слот - модальный. Для каждой нажатой строки таблицы появляется модальное окно с данными таблиц в нем. Как бы вы посоветовали это сделать
Может как то так?
<template>
<div>
<table>
<row v-for="item in items" @click="onRowClick(item)"
....show some data
</row>
</table>
<modal v-if="activeItem" :item="activeItem" @onClose="onModalClose" />
</div>
</template>
<script>
export default {
name: 'child',
props: ["items"]
data() {
return {
activeItem: null
}
},
methods: {
onRowClick(item) {
this.activeItem = item;
},
onModalClose() {
this.activeItem = null;
}
}
}
</script>
Я не понимаю, откуда у этого слота гибкость?
Ну, он не такой гибкий, как слот, но выполняет свою работу :)
Если вам действительно нужно разработать свой дочерний компонент / компонент таблицы таким образом, чтобы можно было использовать его в разных местах и изменить внешний вид его части (детали строки в вашем случае), то вам подойдут слоты. ...
Слоты
Слоты - это точки распространения контента. Когда вы размещаете слот внутри своего компонента, вы говорите: «Мой родительский компонент может предоставить частичный шаблон. Когда этот шаблон отображается (в области родительского компонента - важно, потому что этот шаблон имеет доступ только к родительским данным / methods и т. д.), я возьму полученный результат и помещу его в это точное место внутри моего собственного шаблона ". Использование обычного слота похоже на передачу HTML в ваш компонент.
У меня вопрос: как я могу получить доступ к дочерним данным (и функциям) в моем компоненте слота?
Вы должны предоставить шаблону слота доступ к некоторым дочерним данным явно. Допустим, у вашего дочернего компонента есть свойство item
. Вы можете определить в нем слот с ограниченным объемом следующим образом:
<slot name="rowExpander" :itemProp="item"></slot>
... и используйте его внутри родителя следующим образом:
<template v-slot:rowExpander="slotProps">
<MyRowExpanderComponent :item="slotProps.itemProp" />
</template>
Или с помощью деструктурирования ES2015
<template v-slot:rowExpander="{ itemProp }">
<MyRowExpanderComponent :item="itemProp" />
</template>
В слот с заданной областью можно передать практически все - data / props / method / computed, вы даже можете использовать свойства экземпляра, такие как $data
или $props
:
<slot name="rowExpander" :childProps="$props"></slot>
Невозможно передать сам дочерний экземпляр:
<slot name="rowExpander" :child="this"></slot>
(в основном потому, что this
не определен внутри шаблона - я думаю, это можно сделать, если вы напишете свой компонент без шаблона с помощью функции рендеринга, но это другая история)
Важно понимать, что шаблон слота с ограниченной областью видимости - это просто обычный шаблон Vue. Он имеет доступ ко всем свойствам экземпляра компонента, в котором он определен (родительский) и дополнительно к объекту slotProps
. Когда вы используете компонент внутри шаблона слота с ограниченной областью видимости, этот компонент не имеет доступа ко всем дочерним данным или slotProps
автоматически - вам все равно нужно передать его ему явно ( как в моем MyRowExpanderComponent
примере выше)
27.11.2019