当前位置: 首页 > news >正文

vue3-admin商品管理后台项目(图库模块开发)

今天我们继续来进行图库模块的开发工作
首先是布局实现:
使用element提供的container布局容器
在这里插入图片描述
利用布局将其分为左右两块,一块是侧边栏,一块是主体部分,然后书写它的样式

<template>
    <el-container class="bg-white rounded" :style="{ height: (h + 'px') }">
      <el-header class="image-header">Header</el-header>
      <el-container>
        <el-aside width="220px" class="image-aside">
            <div class="top">
                <div v-for="i in 100" :key="i">{{ i }}</div>
            </div>
            <div class="bottom">
                分页区域
            </div>
        </el-aside>
        <el-main class="image-main">
            <div class="top">
                <div v-for="i in 100" :key="i">{{ i }}</div>
            </div>
            <div class="bottom">
                分页区域
            </div>
        </el-main>
      </el-container>
    </el-container>
</template>

<script setup>
// 拿到浏览器高度
const windowHeight = window.innerHeight || document.body.clientHeight;
// 减去header高度+导肮栏高度+padding
const h = windowHeight - 64 - 44 -40;
</script>

<style>
.image-header{
    border-bottom: 1px solid #eeeeee;
    @apply flex items-center;
}

.image-aside{
    border-right: 1px solid #eeeeee;
    position: relative;
}

.image-main{
    position: relative;
}

.image-aside .top, .image-main .top{
    /* 相对aside定义,撑满左右两边和上下 */
    position: absolute;
    top: 0;
    right: 0;
    left: 0;
    bottom: 50px;
    /* y轴方向上默认 */
    overflow-y: auto;
}

.image-aside .bottom, .image-main .bottom{
    position: absolute;
    bottom: 0;
    height: 50px;
    left: 0;
    right: 0;
    @apply flex items-center justify-center;
}
</style>

另外,在App.vue里面对其滚动条进行样式优化:

然后目前的效果就是:
在这里插入图片描述

因为后面很多部分要用到相同的侧边栏和主体部分,所以我们对这两块进行抽离:
在components文件夹下面创建ImageAside.vue和ImageMain.vue
然后抽离:
ImageAside.vue

<template>
    <el-aside width="220px" class="image-aside">
        <div class="top">
            <div v-for="i in 100" :key="i">{{ i }}</div>
        </div>
        <div class="bottom">
            分页区域
        </div>
    </el-aside>
</template>

<style>
.image-aside{
    border-right: 1px solid #eeeeee;
    position: relative;
}

.image-aside .top{
    /* 相对aside定义,撑满左右两边和上下 */
    position: absolute;
    top: 0;
    right: 0;
    left: 0;
    bottom: 50px;
    /* y轴方向上默认 */
    overflow-y: auto;
}

.image-aside .bottom{
    position: absolute;
    bottom: 0;
    height: 50px;
    left: 0;
    right: 0;
    @apply flex items-center justify-center;
}
</style>

ImageMain.vue

<template>
    <el-main class="image-main">
        <div class="top">
            <div v-for="i in 100" :key="i">{{ i }}</div>
        </div>
        <div class="bottom">
            分页区域
        </div>
    </el-main>
</template>

<style>
.image-main{
    position: relative;
}
.image-main .top{
    /* 相对aside定义,撑满左右两边和上下 */
    position: absolute;
    top: 0;
    right: 0;
    left: 0;
    bottom: 50px;
    /* y轴方向上默认 */
    overflow-y: auto;
}

.image-main .bottom{
    position: absolute;
    bottom: 0;
    height: 50px;
    left: 0;
    right: 0;
    @apply flex items-center justify-center;
}
</style>

此时的list.vue

<template>
    <el-container class="bg-white rounded" :style="{ height: (h + 'px') }">
      <el-header class="image-header">Header</el-header>
      <el-container>
        <!-- <el-aside width="220px" class="image-aside">
            <div class="top">
                <div v-for="i in 100" :key="i">{{ i }}</div>
            </div>
            <div class="bottom">
                分页区域
            </div>
        </el-aside> -->
        <ImageAside />
        <!-- <el-main class="image-main">
            <div class="top">
                <div v-for="i in 100" :key="i">{{ i }}</div>
            </div>
            <div class="bottom">
                分页区域
            </div>
        </el-main> -->
        <ImageMain />
      </el-container>
    </el-container>
</template>

<script setup>
// 引入公共侧边栏 
import ImageAside from "~/components/ImageAside.vue"
// 引入公共主体部分
import ImageMain from "~/components/ImageMain.vue"
// 拿到浏览器高度
const windowHeight = window.innerHeight || document.body.clientHeight;
// 减去header高度+导肮栏高度+padding
const h = windowHeight - 64 - 44 -40;
</script>

<style>
.image-header{
    border-bottom: 1px solid #eeeeee;
    @apply flex items-center;
}
</style>

抽离完成

然后我们进行图库分类组件开发:
除去之前的1-100,然后加上需要的按钮图标
此时的ImageAside.vue

<template>
    <el-aside width="220px" class="image-aside">
        <div class="top">

            <AsideList>
                分类标题
            </AsideList>

            <!-- 激活状态 -->
            <AsideList active>
                分类标题
            </AsideList>

        </div>
        <div class="bottom">
            分页区域
        </div>
    </el-aside>
</template>
<!-- 公共侧边栏部分抽离 -->

<script setup>
import AsideList from './AsideList.vue';
</script>

<style>
.image-aside{
    border-right: 1px solid #eeeeee;
    position: relative;
}

.image-aside .top{
    /* 相对aside定义,撑满左右两边和上下 */
    position: absolute;
    top: 0;
    right: 0;
    left: 0;
    bottom: 50px;
    /* y轴方向上默认 */
    overflow-y: auto;
}

.image-aside .bottom{
    position: absolute;
    bottom: 0;
    height: 50px;
    left: 0;
    right: 0;
    @apply flex items-center justify-center;
}


</style>

新建了一个AsideList.vue,用于抽离选项及按钮部分

<template>
    <!-- 非激活状态 -->
    <div class="aside-list" :class="{ 'active' : active }">
        <!-- 超出部分显示... -->
        <span class="truncate"><slot/></span>

        <!-- 两个按钮 -->
        <el-button class="ml-auto px-1" text type="primary" size="small" @click="$emit('edit')">
            <el-icon :size="12">
                <Edit />
            </el-icon>
        </el-button>

        <el-button text class="px-1" type="primary" size="small" @click="$emit('delete')">
            <el-icon :size="12">
                <Close />
            </el-icon>
        </el-button>
    </div>
</template>

<script setup>
defineProps({
    active:{
        type:Boolean,
        default:false
    }
})

// 暴露两个按钮
defineEmits(["edit","delete"])
</script>

<style>
.aside-list{
    border-bottom: 1px solid #f4f4f4;
    cursor: pointer;
    @apply flex items-center p-3 text-sm text-gray-600;
}

.aside-list:hover, .active{
    @apply bg-blue-50;
}
</style>

运行项目:
在这里插入图片描述

然后我们继续进行分页的实现:
首先在api文件夹里新建一个image_class.js进行页码接口的书写

import axios from "~/axios"

export function getImageClassList(page){
    return axios.get("/admin/image_class/" + page)
}

然后编辑ImageAside.vue,分页用的是element提供的分页,然后对页码进行动态绑定

<template>
    <!-- v-loading="loading"调用loading状态 -->
    <el-aside width="220px" class="image-aside" v-loading="loading">
        <div class="top">

            <AsideList :active="activeId == item.id" v-for="(item, index) in list" :key="index">
                {{ item.name }}
            </AsideList>

        </div>

        <!-- 分页 -->
        <div class="bottom">
            <el-pagination background layout="prev, next" :total="total" :current-page="currentPage" :page-size="limit" @current-change="getData"/>
        </div>
    </el-aside>
</template>
<!-- 公共侧边栏部分抽离 -->

<script setup>
import { ref } from 'vue';
import AsideList from './AsideList.vue';
import { getImageClassList } from "~/api/image_class.js"

// 加载动画
const loading = ref(false)
// 保存列表数据
const list = ref([])
// 激活状态
const activeId = ref(0)
//分页部分 
const currentPage = ref(1)
const total = ref(0)
// 每页默认显示10条
const limit = ref(10)

// 获取数据的方法
function getData(p = null) {
    // 拿到的页数,就是当前选中的页码
    // console.log(p)

    if(typeof p == "number"){
        currentPage.value = p
    }

    loading.value = true
    getImageClassList(currentPage.value)
        .then(res => {
            total.value = res.totalCount
            // console.log(res)
            // 拿到列表的值
            list.value = res.list
            // 默认选中第一个
            let item = list.value[0]
            if (item) {
                activeId.value = item.id
            }
        })
        .finally(() => {
            loading.value = false
        })
}

getData()

</script>

<style>
.image-aside {
    border-right: 1px solid #eeeeee;
    position: relative;
}

.image-aside .top {
    /* 相对aside定义,撑满左右两边和上下 */
    position: absolute;
    top: 0;
    right: 0;
    left: 0;
    bottom: 50px;
    /* y轴方向上默认 */
    overflow-y: auto;
}

.image-aside .bottom {
    position: absolute;
    bottom: 0;
    height: 50px;
    left: 0;
    right: 0;
    @apply flex items-center justify-center;
}
</style>

运行项目:
在这里插入图片描述
在这里插入图片描述

然后我们继续来进行新增图库分类的表单实现:
这主要是加上一个新增按钮以及引入抽屉组件:以及使用了element提供的input Number组件。
先来看image下面的list.vue

<template>
    <el-container class="bg-white rounded" :style="{ height: (h + 'px') }">
      <el-header class="image-header">
        <!-- 新增图片分类按钮 -->
        <el-button type="primary" size="samll" @click="handleOpenCreate">新增图片分类</el-button>
        
      </el-header>
      <el-container>
        <!-- <el-aside width="220px" class="image-aside">
            <div class="top">
                <div v-for="i in 100" :key="i">{{ i }}</div>
            </div>
            <div class="bottom">
                分页区域
            </div>
        </el-aside> -->
        <!-- 通过它拿到子组件节点 -->
        <ImageAside ref="ImageAsideRef"/>
        <!-- <el-main class="image-main">
            <div class="top">
                <div v-for="i in 100" :key="i">{{ i }}</div>
            </div>
            <div class="bottom">
                分页区域
            </div>
        </el-main> -->
        <ImageMain />
      </el-container>
    </el-container>
</template>

<script setup>
import { ref } from "vue";
// 引入公共侧边栏 
import ImageAside from "~/components/ImageAside.vue"
// 引入公共主体部分
import ImageMain from "~/components/ImageMain.vue"
// 拿到浏览器高度
const windowHeight = window.innerHeight || document.body.clientHeight;
// 减去header高度+导肮栏高度+padding
const h = windowHeight - 64 - 44 -40;

const ImageAsideRef = ref(null)
// 增加选项卡方法,调用打开抽屉的方法
const handleOpenCreate = () => ImageAsideRef.value.handleCreate()
</script>

<style>
.image-header{
    border-bottom: 1px solid #eeeeee;
    @apply flex items-center;
}
</style>

imageAside.vue

<template>
    <!-- v-loading="loading"调用loading状态 -->
    <el-aside width="220px" class="image-aside" v-loading="loading">
        <div class="top">

            <AsideList :active="activeId == item.id" v-for="(item, index) in list" :key="index">
                {{ item.name }}
            </AsideList>

        </div>

        <!-- 分页 -->
        <div class="bottom">
            <el-pagination background layout="prev, next" :total="total" :current-page="currentPage" :page-size="limit"
                @current-change="getData" />
        </div>
    </el-aside>

    <!-- 抽屉部分 -->
    <FormDrawer title="新增" ref="formDrawerRef" @submit="handleSubmit">
        <!-- 表单部分 -->
        <el-form :model="form" ref="formRef" :rules="rules" label-width="80px" :inline="false">
            <!-- 字段属于name字段,便于验证规则 -->
            <el-form-item label="分类名称" prop="name">
                <el-input v-model="form.name"></el-input>
            </el-form-item>

            <!-- 属于order字段 -->
            <el-form-item label="排序" prop="order">
                <el-input-number v-model="form.order" :min="0" :max="1000" />
            </el-form-item>
        </el-form>

    </FormDrawer>

</template>
<!-- 公共侧边栏部分抽离 -->

<script setup>
import { reactive } from 'vue';
import { ref } from 'vue';
import AsideList from './AsideList.vue';
import { getImageClassList } from "~/api/image_class.js";
// 引入抽屉组件 
import FormDrawer from "./FormDrawer.vue";

// 加载动画
const loading = ref(false)
// 保存列表数据
const list = ref([])
// 激活状态
const activeId = ref(0)
//分页部分 
const currentPage = ref(1)
const total = ref(0)
// 每页默认显示10条
const limit = ref(10)

// 获取数据的方法
function getData(p = null) {
    // 拿到的页数,就是当前选中的页码
    // console.log(p)

    if (typeof p == "number") {
        currentPage.value = p
    }

    loading.value = true
    getImageClassList(currentPage.value)
        .then(res => {
            total.value = res.totalCount
            // console.log(res)
            // 拿到列表的值
            list.value = res.list
            // 默认选中第一个
            let item = list.value[0]
            if (item) {
                activeId.value = item.id
            }
        })
        .finally(() => {
            loading.value = false
        })
}

getData()

// 初始化
const formDrawerRef = ref(null);
// 拿到子组件的open方法打开抽屉组件
const handleCreate = () => formDrawerRef.value.open()


// 定义form,指定字段
const form = reactive({
    name: "",
    order: 50
})

// 验证规则
const rules = {
    name: [
        {
            required: true,
            message: "图库分类名称不能为空",
            // 失去焦点的时候触发
            trigger: "blur",
        },
    ]
}

// 定义表单的ref,因为要触发验证
const formRef = ref(null)

const handleSubmit = () => {
    // console.log("提交表单")
    formRef.value.validate((valid)=>{
        // 没有验证通过就直接返回
        if(!valid) return
        console.log("提交成功")
    })
}

// 暴露出去
defineExpose({
    handleCreate
});

</script>

<style>
.image-aside {
    border-right: 1px solid #eeeeee;
    position: relative;
}

.image-aside .top {
    /* 相对aside定义,撑满左右两边和上下 */
    position: absolute;
    top: 0;
    right: 0;
    left: 0;
    bottom: 50px;
    /* y轴方向上默认 */
    overflow-y: auto;
}

.image-aside .bottom {
    position: absolute;
    bottom: 0;
    height: 50px;
    left: 0;
    right: 0;
    @apply flex items-center justify-center;
}
</style>

直接看效果:
在这里插入图片描述
然后我们来进行新增图库分类功能的交互开发:
要用到api文档的增加图库分类接口:
在image_class.js里面书写接口

// 图片选项数据
import axios from "~/axios"
// 获取图库分类的选项
export function getImageClassList(page){
    return axios.get("/admin/image_class/" + page)
}

// 新增图库分类接口
export function createImageClass(data){
    return axios.post("/admin/image_class",data)
}

然后imageAside.vue

<template>
    <!-- v-loading="loading"调用loading状态 -->
    <el-aside width="220px" class="image-aside" v-loading="loading">
        <div class="top">

            <AsideList :active="activeId == item.id" v-for="(item, index) in list" :key="index">
                {{ item.name }}
            </AsideList>

        </div>

        <!-- 分页 -->
        <div class="bottom">
            <el-pagination background layout="prev, next" :total="total" :current-page="currentPage" :page-size="limit"
                @current-change="getData" />
        </div>
    </el-aside>

    <!-- 抽屉部分 -->
    <FormDrawer title="新增" ref="formDrawerRef" @submit="handleSubmit">
        <!-- 表单部分 -->
        <el-form :model="form" ref="formRef" :rules="rules" label-width="80px" :inline="false">
            <!-- 字段属于name字段,便于验证规则 -->
            <el-form-item label="分类名称" prop="name">
                <el-input v-model="form.name"></el-input>
            </el-form-item>

            <!-- 属于order字段 -->
            <el-form-item label="排序" prop="order">
                <el-input-number v-model="form.order" :min="0" :max="1000" />
            </el-form-item>
        </el-form>

    </FormDrawer>

</template>
<!-- 公共侧边栏部分抽离 -->

<script setup>
import { reactive } from 'vue';
import { ref } from 'vue';
import AsideList from './AsideList.vue';
import { getImageClassList, createImageClass } from "~/api/image_class.js";
// 引入抽屉组件 
import FormDrawer from "./FormDrawer.vue";
// 引入util.js里面的消息提示方法
import { toast } from "~/composables/util.js"

// 加载动画
const loading = ref(false)
// 保存列表数据
const list = ref([])
// 激活状态
const activeId = ref(0)
//分页部分 
const currentPage = ref(1)
const total = ref(0)
// 每页默认显示10条
const limit = ref(10)

// 获取数据的方法
function getData(p = null) {
    // 拿到的页数,就是当前选中的页码
    // console.log(p)

    if (typeof p == "number") {
        currentPage.value = p
    }

    loading.value = true
    getImageClassList(currentPage.value)
        .then(res => {
            total.value = res.totalCount
            // console.log(res)
            // 拿到列表的值
            list.value = res.list
            // 默认选中第一个
            let item = list.value[0]
            if (item) {
                activeId.value = item.id
            }
        })
        .finally(() => {
            loading.value = false
        })
}

getData()

// 初始化
const formDrawerRef = ref(null);
// 拿到子组件的open方法打开抽屉组件
const handleCreate = () => formDrawerRef.value.open()


// 定义form,指定字段
const form = reactive({
    name: "",
    order: 50
})

// 验证规则
const rules = {
    name: [
        {
            required: true,
            message: "图库分类名称不能为空",
            // 失去焦点的时候触发
            trigger: "blur",
        },
    ]
}

// 定义表单的ref,因为要触发验证
const formRef = ref(null)

const handleSubmit = () => {
    // console.log("提交表单")
    formRef.value.validate((valid)=>{
        // 没有验证通过就直接返回
        if(!valid) return
        // 提交按钮loading状态
        formDrawerRef.value.showLoading()
        // console.log("提交成功")
        // 验证通过之后调用接口方法
        // 要传的是name和order,而form里面有,我们直接放form就行
        createImageClass(form)
        .then(res=>{
            toast("新增成功")
            // 新增成功后重新加载数据
            getData(1)
            // 关闭弹框
            formDrawerRef.value.close()
        })
        .finally(()=>{
            formDrawerRef.value.hideLoading()
        })
    })
}

// 暴露出去
defineExpose({
    handleCreate
});

</script>

<style>
.image-aside {
    border-right: 1px solid #eeeeee;
    position: relative;
}

.image-aside .top {
    /* 相对aside定义,撑满左右两边和上下 */
    position: absolute;
    top: 0;
    right: 0;
    left: 0;
    bottom: 50px;
    /* y轴方向上默认 */
    overflow-y: auto;
}

.image-aside .bottom {
    position: absolute;
    bottom: 0;
    height: 50px;
    left: 0;
    right: 0;
    @apply flex items-center justify-center;
}
</style>

在这里插入图片描述
在这里插入图片描述
可以看到我们增加一项456之后就成功了。

然后我们来实现修改图库分类功能交互开发:
在image_class.js里面写上修改接口:

// 图片选项数据
import axios from "~/axios"
// 获取图库分类的选项
export function getImageClassList(page){
    return axios.get("/admin/image_class/" + page)
}

// 新增图库分类接口
export function createImageClass(data){
    return axios.post("/admin/image_class",data)
}

// 修改商品分类接口
export function updateImageClass(id,data){
    return axios.post("/admin/image_class/"+id, data)
}

然后在ImgeAside.vue里面加上handleEdit事件,因为前面已经通过$emit定义了。
在这里插入图片描述
ImageAside.vue

<template>
    <!-- v-loading="loading"调用loading状态 -->
    <el-aside width="220px" class="image-aside" v-loading="loading">
        <div class="top">

            <!-- handleEdit是修改的绑定事件 -->
            <AsideList :active="activeId == item.id" v-for="(item, index) in list" :key="index" @edit="handleEdit(item)">
                {{ item.name }}
            </AsideList>

        </div>

        <!-- 分页 -->
        <div class="bottom">
            <el-pagination background layout="prev, next" :total="total" :current-page="currentPage" :page-size="limit"
                @current-change="getData" />
        </div>
    </el-aside>

    <!-- 抽屉部分 -->
    <!-- 标题动态绑定 -->
    <FormDrawer :title="drawerTitle" ref="formDrawerRef" @submit="handleSubmit">
        <!-- 表单部分 -->
        <el-form :model="form" ref="formRef" :rules="rules" label-width="80px" :inline="false">
            <!-- 字段属于name字段,便于验证规则 -->
            <el-form-item label="分类名称" prop="name">
                <el-input v-model="form.name"></el-input>
            </el-form-item>

            <!-- 属于order字段 -->
            <el-form-item label="排序" prop="order">
                <el-input-number v-model="form.order" :min="0" :max="1000" />
            </el-form-item>
        </el-form>

    </FormDrawer>

</template>
<!-- 公共侧边栏部分抽离 -->

<script setup>
import { reactive } from 'vue';
import { ref } from 'vue';
import AsideList from './AsideList.vue';
import { getImageClassList, createImageClass, updateImageClass } from "~/api/image_class.js";
// 引入抽屉组件 
import FormDrawer from "./FormDrawer.vue";
// 引入util.js里面的消息提示方法
import { toast } from "~/composables/util.js"
import { computed } from '@vue/reactivity';

// 加载动画
const loading = ref(false)
// 保存列表数据
const list = ref([])
// 激活状态
const activeId = ref(0)
//分页部分 
const currentPage = ref(1)
const total = ref(0)
// 每页默认显示10条
const limit = ref(10)

// 获取数据的方法
function getData(p = null) {
    // 拿到的页数,就是当前选中的页码
    // console.log(p)

    if (typeof p  == "number") {
        currentPage.value = p
    }

    loading.value = true
    getImageClassList(currentPage.value)
        .then(res => {
            total.value = res.totalCount
            // console.log(res)
            // 拿到列表的值
            list.value = res.list
            // 默认选中第一个
            let item = list.value[0]
            if (item) {
                activeId.value = item.id
            }
        })
        .finally(() => {
            loading.value = false
        })
}

getData()

// 当前图库分类的id,默认等于0
const editId = ref(0)

// 标题修改 >0是修改,否则是新增
const drawerTitle = computed(()=>editId.value ? "修改" : "新增")

// 初始化
const formDrawerRef = ref(null);

// 定义form,指定字段
const form = reactive({
    name: "",
    order: 50
})

// 验证规则
const rules = {
    name: [
        {
            required: true,
            message: "图库分类名称不能为空",
            // 失去焦点的时候触发
            trigger: "blur",
        },
    ]
}

// 定义表单的ref,因为要触发验证
const formRef = ref(null)

const handleSubmit = () => {
    // console.log("提交表单")
    formRef.value.validate((valid)=>{
        // 没有验证通过就直接返回
        if(!valid) return
        // 提交按钮loading状态
        formDrawerRef.value.showLoading()
        // console.log("提交成功")
        // 验证通过之后调用接口方法
        // 要传的是name和order,而form里面有,我们直接放form就行
        // createImageClass(form)

        // 如果>0,那么就是修改,如果不是,那么就是新增
        const fun = editId.value ? updateImageClass(editId.value,form) : createImageClass(form)

        fun.then(res=>{
            toast(drawerTitle.value + "成功")
            // 新增成功后重新加载数据
            // 如果是修改传当前页页码就行,否则就回到第一页
            getData(editId.value ? currentPage.value : 1)
            // 关闭弹框
            formDrawerRef.value.close()
        })
        .finally(()=>{
            formDrawerRef.value.hideLoading()
        })
    })
}

// 新增方法 拿到子组件的open方法打开抽屉组件
const handleCreate = () => {
    // 新增的方法肯定是没有顺序id的
    editId.value = 0
    // 新增这里每新增也要初始化,不然其他的名称和order就会每次显示在新增这里
    form.name = ""
    form.order = 50
    formDrawerRef.value.open()
} 

// 编辑方法
const handleEdit = (row) =>{
    // 修改的value等于当前对象的id
    editId.value = row.id
    // row能拿到里面的name值,和order值
    // console.log(row)
    form.name = row.name
    form.order = row.order
    // 打开抽屉进行编辑修改选项
    formDrawerRef.value.open()
}

// 暴露出去
defineExpose({
    handleCreate
});

</script>

<style>
.image-aside {
    border-right: 1px solid #eeeeee;
    position: relative;
}

.image-aside .top {
    /* 相对aside定义,撑满左右两边和上下 */
    position: absolute;
    top: 0;
    right: 0;
    left: 0;
    bottom: 50px;
    /* y轴方向上默认 */
    overflow-y: auto;
}

.image-aside .bottom {
    position: absolute;
    bottom: 0;
    height: 50px;
    left: 0;
    right: 0;
    @apply flex items-center justify-center;
}
</style>

编辑前面新增的456为45678910,发现能修改成功。

在这里插入图片描述
在这里插入图片描述
至此,修改功能书写结束。

我们继续进行删除功能书写:
先在image_class.js里面书写删除接口:

// 图片选项数据
import axios from "~/axios"
// 获取图库分类的选项
export function getImageClassList(page){
    return axios.get("/admin/image_class/" + page)
}

// 新增图库分类接口
export function createImageClass(data){
    return axios.post("/admin/image_class",data)
}

// 修改商品分类接口
export function updateImageClass(id,data){
    return axios.post("/admin/image_class/"+id, data)
}

// 删除商品分类接口
export function deleteImageClass(id){
    return axios.post(`/admin/image_class/${id}/delete`)
}

在AsideList.vue里面的删除按钮加上element提供的删除确认框
在这里插入图片描述
监听改成监听confirm,这是element里面删除确认框的规定用法:

<template>
    <!-- 非激活状态 -->
    <div class="aside-list" :class="{ 'active': active }">
        <!-- 超出部分显示... -->
        <span class="truncate">
            <slot />
        </span>

        <!-- 两个按钮 -->
        <el-button class="ml-auto px-1" text type="primary" size="small" @click="$emit('edit')">
            <el-icon :size="12">
                <Edit />
            </el-icon>
        </el-button>

        <!-- 加上了删除确认框 -->
        <el-popconfirm title="是否要删除该分类?" confirmButtonText="确认" cancelButtonText="取消" @confirm="$emit('delete')">
            <!-- 使用的是element里面的提示确认框基础用法插槽 -->
            <template #reference>
                <el-button text class="px-1" type="primary" size="small">
                    <el-icon :size="12">
                        <Close />
                    </el-icon>
                </el-button>
            </template>
        </el-popconfirm>
    </div>
</template>

<script setup>
defineProps({
    active: {
        type: Boolean,
        default: false
    }
})

// 暴露两个按钮
defineEmits(["edit", "delete"])
</script>

<style>
.aside-list {
    border-bottom: 1px solid #f4f4f4;
    cursor: pointer;
    @apply flex items-center p-3 text-sm text-gray-600;
}

.aside-list:hover,
.active {
    @apply bg-blue-50;
}
</style>

在ImageAside.vue里面:
在这里插入图片描述
加上handleDelete方法:
在这里插入图片描述
到这里删除模块就结束了。
来看效果:
在这里插入图片描述

在这里插入图片描述
到此删除我们就已经完成了,今天先到这,明天继续。

项目gitee地址

相关文章:

  • 网站诊断seo当前数据是指/百度云网盘资源搜索引擎入口
  • 沈阳高端网站制作/seo站长工具查询系统
  • 建设网站硬件/网站优化检测
  • 亿星网站建设/泰州seo网络公司
  • 专做美容师招聘网站/深圳seo技术
  • 牡丹区住房城乡建设局网站/项目推广
  • 【torchvision.datasets.ImageFolder类的使用】
  • 【C++】 容器区别
  • 【Qt】边学边写之Qt教程(零基础)
  • Python3,爬虫有多简单,一个库,一行代码,就OK, 你确定不来试试?
  • 【HTML5期末大作业】制作一个简单HTML我的班级网页(HTML+CSS+JS)
  • 12、乐趣国学—践行《弟子规》的“信”懂得处世之道(下篇)
  • 【JavaWeb】-JDBC详解、数据库连接池的认识
  • 推理证明RANSAC算法中迭代次数为何总设置为100,一看就懂,不懂请打我
  • 用于验证的verilog语法--1
  • 用keras的cnn做人脸分类
  • 通关 MySQL获奖名单已公布
  • 16 【react-router 6】