在不同的页面中,会有很多公共的页面在不同的父页面中出现,但是又不尽相同。这个时候我们可以多个组件,但是最优秀的方式是我们可以封装一个组件,然后使用插槽动态改变一些又区别的地方。举例如下:
为了解决这中情况,我们通常可以抽离成一个组件,在不同的布局部分使用插槽,要动态的控制布局。
button-search.vue子组件
<template>
<div class="d-flex align-items-center">
<!-- 左边 -->
<slot name="left"></slot>
<!-- 右边 -->
<div class="ml-auto" v-show="!superSearch">
<slot name="right">
<el-input v-model="keyword" :placeholder="placeholder" size="mini" style="width:150px;" class="mr-2"></el-input>
<el-button type="info" size="mini"
@click="$emit('search',keyword)">搜索</el-button>
<el-button size="mini"
@click="superSearch = true">高级搜索</el-button>
</slot>
<el-card class="box-card bg-light my-3" v-show="superSearch">
<div slot="header" class="clearfix" style="margin: -10px;">
<span>高级搜索</span>
<el-button style="float: right; padding: 3px 0"
type="text" @click="closeSuperSearch">收起</el-button>
<!-- 表单 -->
<slot name="form"></slot>
</el-card>
</template>
<script>
export default {
props: {
placeholder: {
type: String,
default: ""
data() {
return {
keyword: "",
superSearch:false
methods: {
closeSuperSearch() {
this.superSearch = false
</script>
<style>
</style>
list.vue父组件
<template>
<div class="bg-white px-3" style="margin: -20px;margin-top: -1rem;">
<el-tabs v-model="tabIndex" @tab-click="handleClick">
<el-tab-pane :label="tab.name" :key="tabI" v-for="(tab,tabI) in tabbars">
<button-search ref="buttonSearch" placeholder="要搜索的商品名称" @search="searchEvent">
<!-- 左边 -->
<template #left>
<el-button type="success" size="mini">发布商品</el-button>
<el-button type="danger" size="mini">批量删除</el-button>
</template>
<!-- 高级搜索表单 -->
<template #form>
<el-form inline ref="form" :model="form" label-width="80px">
<el-form-item label="商品名称" class="mb-0">
<el-input v-model="form.name" placeholder="商品名称" size="mini"></el-input>
</el-form-item>
<el-form-item label="商品编码" class="mb-0">
<el-input v-model="form.code" placeholder="商品编码" size="mini"></el-input>
</el-form-item>
<el-form-item label="商品类型" class="mb-0">
<el-select v-model="form.type" size="mini" placeholder="请选择商品类型">
<el-option label="区域一" value="shanghai"></el-option>
<el-option label="区域二" value="beijing"></el-option>
</el-select>
</el-form-item>
<el-form-item label="商品分类" class="mb-0">
<el-input v-model="form.category" placeholder="商品分类" size="mini"></el-input>
</el-form-item>
<el-form-item class="mb-0">
<el-button type="info" size="mini" @click="searchEvent">搜索</el-button>
<el-button size="mini" @click="clearSearch">清空筛选条件</el-button>
</el-form-item>
</el-form>
</template>
</button-search>
</el-tab-pane>
</el-tabs>
</template>
<script>
import buttonSearch from "@/components/common/button-search.vue";
export default {
components: {
buttonSearch
data() {
return {
tabIndex: 0,
tabbars: [
{ name: "审核中" },
{ name: "出售中" },
{ name: "已下架" },
{ name: "库存预警" },
{ name: "回收站" }
form: {
name: "",
code: "",
type: "",
category: ""
methods: {
// 加载数据
handleClick(tab, event) {
console.log(tab.index);
// 清空筛选条件
clearSearch() {
this.form = {
name: "",
code: "",
type: "",
category: ""
this.$refs.buttonSearch[this.tabIndex].closeSuperSearch();
// 搜索事件
searchEvent(e = false) {
// 简单搜索
if (typeof e === "string") {
return console.log("简单搜索", e);
// 高级搜索
console.log("高级搜索");
</script>
<style>
</style>
思路分析:
在子组件button-search.vue中,我们可以使用<slot name="left"></slot>作为一个插槽,在父组件list.vue中,可以使用模板插入不同的内容。这样,便可以实现不同的样式布局。
<template #left>
<el-button type="success" size="mini">发布商品</el-button>
<el-button type="danger" size="mini">批量删除</el-button>
</template>