vue3+ts+element-plus跨页勾选,如何解决在弹框里面当我第一次勾选中数据我也使用了row-key和reserve-selection属性,以及监听selection-change事件来管理选中行,这样确实让我第一次勾选中的数据在第二次打开弹窗的时候可以实现跨页勾选,但是我该如何在第一次选中后第二次打开弹窗把第一次勾选的数据中的一条取消勾选,然后点击弹框的取消按钮当我再次打开弹窗的时候不会被改变,还有就是在我的页面中当我的表格点击删除数据的时候如何解决弹框的数据也被更改
这是封装的表格
<template>
<div class="table-wrapper" v-loading="loading">
<!-- 表格 -->
<el-table
center
:data="list"
style="width: 100%"
:row-key="getRowKey"
:header-cell-style="{
background: '#f9f9f9',
color: '#000000',
height: '45px'
}"
@selection-change="handleSelectionChange"
>
<el-table-column v-if="ids" type="selection" :reserve-selection="true" />
<slot />
</el-table>
<!-- 分页 -->
<div class="pagination">
<el-pagination
hide-on-single-page
:current-page="page"
:page-size="pageSize"
:page-sizes="[5, 10, 20, 50]"
layout="total, sizes, prev, pager, next, jumper"
:total="total"
@size-change="handleSizeChange"
@current-change="handleCurrentChange"
/>
</div>
<slot name="footer" />
</div>
</template>
<script lang="ts" setup>
import { ref, onMounted, defineProps, watch } from 'vue';
interface IProps {
listRequest: Function;
searchParams?: AnyObject;
}
const props = withDefaults(defineProps<IProps>(), { searchParams: () => ({}) });
const ids = defineModel('ids');
const idsAll = defineModel('idsAll');
const list = ref<AnyObject[]>([]); // 当前页面数据
const page = ref(1); // 当前页码
const pageSize = ref(10); // 每页条数
const total = ref(0); // 总条数
const loading = ref(true); // 加载状态
const getList = async () => {
loading.value = true;
props.listRequest!({
page: page.value,
pageSize: pageSize.value,
...props.searchParams
}).then((res: ListRes<AnyObject>) => {
loading.value = false;
console.log(res);
total.value = res.data.counts;
list.value = res.data.list;
});
};
onMounted(getList);
// 切换了每页条数
const handleSizeChange = (val: number) => {
// console.log(`${val} items per page`);
page.value = 1;
pageSize.value = val;
getList();
};
// 翻页:页码发生变化
const handleCurrentChange = (val: number) => {
// console.log(`current page: ${val}`);
page.value = val;
getList();
};
//多选
const handleSelectionChange = (val: any) => {
ids.value = val.map((item: any) => item.id);
};
// 获取row的key
const getRowKey = (row: any) => {
return row.id;
};
watch(
() => props.searchParams,
() => {
console.log('父组件传入的searchParams发生变化了', props.searchParams);
page.value = 1;
getList();
}
);
// 暴露内部属性方法
defineExpose({
getList
});
</script>
<style scoped>
.el-table {
margin-top: 20px;
}
.pagination {
margin-top: 20px;
display: flex;
justify-content: center;
}
</style>
这是我的页面
<template>
<!-- 后勤管理/创建采购申请 -->
<el-card>
<div class="btn">
<div class="btnstyle">
<el-button type="primary" size="large" @click="selectFoods"
>选择食材</el-button
>
<sup style="background-color: green" class="is-fixed">{{
TableData.length
}}</sup>
</div>
</div>
<!-- 备注/到货日期 -->
<div class="title-image">
<div v-if="TableData.length">
<el-table :data="TableData">
<el-table-column label="序号" prop="id"></el-table-column>
<el-table-column label="物料名称" prop="name"></el-table-column>
<el-table-column label="单位" prop="unit"></el-table-column>
<el-table-column label="供应商" prop="supplierName"></el-table-column>
<el-table-column label="批发价" prop="wholePrice"></el-table-column>
<el-table-column label="零售价" prop="sellPrice"></el-table-column>
<el-table-column
label="采购价"
prop="purchasePrice"
></el-table-column>
<el-table-column label="操作">
<template #default="{ row }">
<el-button type="danger" size="small" @click="deleteFood(row)"
>删除</el-button
>
</template>
</el-table-column>
</el-table>
</div>
<div>
合计:采购品种数{{ TableData.length }},采购总成本:{{ PriceFoods }} 元
</div>
<div class="image">
<el-form>
<el-form-item label="请输入备注">
<el-input
type="textarea"
v-model="formData.remarks"
placeholder="请输入"
style="width: 400px; height: 100px"
></el-input>
</el-form-item>
<el-form-item label="登记日期:" prop="addTime">
<el-date-picker
v-model="formData.receiveTime"
placeholder="请选择"
type="datetime"
unlink-panels
value-format="YYYY-MM-DD"
format="YYYY-MM-DD"
size="large"
></el-date-picker>
</el-form-item>
</el-form>
</div>
</div>
</el-card>
<div class="button-body">
<el-button @click="$router.go(-1)">返回</el-button>
<el-button @click="save" type="primary">保存</el-button>
<el-button @click="saveAndSubmit" type="primary">保存并提交</el-button>
</div>
<SelectFood v-model="isOpen" @sure="handleSure" />
</template>
<script setup lang="ts">
//跳转
import { useRouter, useRoute } from 'vue-router';
//选择食物弹窗
import SelectFood from './SelectFood.vue';
//API
import { getFoodInfo } from '@/apis/foods/apis';
import { submitPurchase } from '@/apis/purchase/apis';
import { ref, computed, reactive, onMounted } from 'vue';
//element-plus
import { ElMessageBox } from 'element-plus';
import { Message } from '@element-plus/icons-vue';
interface Food {
receiveTime: string;
remarks: string;
foods: any[];
}
// v-model
let formData = ref<Food>({
receiveTime: '',
remarks: '',
foods: []
});
const isOpen = ref(false);
const TableDataId = ref<any>([]);
const selectFoods = () => {
if(TableData){
TableData.value.forEach((row: any)=>{
TableDataId.value.push(row.id)
})
}
isOpen.value = true;
console.log('选择食材');
};
const router = useRouter();
const route = useRoute();
//保存
const save = () => {
formData.value.foods = TableData.value.map((item: any) => {
return {
...item,
foodName: item.name
};
});
sessionStorage.setItem('PurchaseInfo', JSON.stringify(formData.value));
console.log(formData.value);
router.go(-1);
};
//保存并提交
const saveAndSubmit = () => {
formData.value.foods = TableData.value.map((item: any) => {
return {
...item,
foodName: item.name
};
});
sessionStorage.setItem('PurchaseInfo', JSON.stringify(formData.value));
submitPurchase(formData.value).then((res) => {
console.log(res);
if (res.code === 10000) {
Message.success('添加成功');
router.go(-1);
}
});
};
//删除
const deleteFood = (row: any) => {
ElMessageBox.confirm('此操作将永久删除该数据, 是否继续?', '提示', {
confirmButtonText: '确定',
cancelButtonText: '取消',
type: 'warning'
}).then(() => {
TableData.value = TableData.value.filter((item: any) => item.id !== row.id);
PriceFoods.value = TableData.value.reduce((total: number, item: any) => {
return total + item.purchasePrice;
}, 0);
});
};
const PriceFoods = ref<any>(0);
const TableData = ref<any>([]);
const handleSure = (ids: any) => {
Promise.all(ids.map((item: any) => getFoodInfo(item))).then((res: any[]) => {
TableData.value = res.map((item) => item.data);
const totalPurchasePrice = computed(() => {
return TableData.value.reduce((total: number, item: any) => {
return total + item.purchasePrice;
}, 0);
});
PriceFoods.value = totalPurchasePrice;
});
};
onMounted(() => {
const PurchaseInfo = sessionStorage.getItem('PurchaseInfo');
if (PurchaseInfo) {
formData.value = JSON.parse(PurchaseInfo);
TableData.value = formData.value.foods;
console.log('formData', formData.value.foods instanceof Array);
PriceFoods.value = TableData.value.reduce((total: number, item: any) => {
return total + item.purchasePrice;
}, 0);
console.log('formData', PriceFoods.value);
}
});
</script>
<style lang="sass" scoped>
.btn
margin: 10px 0
.btnstyle
width: 95.6px
position: relative
--el-badge-size: 18px
.is-fixed
position: absolute
top: -10px
right: -10px
align-items: center
border: 1px solid #fff
border-radius: 10px
color: #fff
display: inline-flex
font-size: 12px
height: 18px
justify-content: center
white-space: nowrap
padding: 6px
.title-image
margin-top: 20px
.image
margin:50px 0px
.button-body
margin-top: 70px
text-align: center
</style>
这是我页面中的弹框
<template>
<!-- 选择食物 -->
<el-dialog v-model="isOpen" title="选择喜欢的食材">
<Table
:list-request="getFoods"
v-model:ids="ids"
v-model:idsAll="idsAll"
>
<el-table-column label="序号" prop="id"></el-table-column>
<el-table-column label="物料名称" prop="name"></el-table-column>
<el-table-column label="单位" prop="unit"></el-table-column>
<el-table-column label="供应商" prop="supplierName"></el-table-column>
<el-table-column label="批发价" prop="wholePrice"></el-table-column>
<el-table-column label="零售价" prop="sellPrice"></el-table-column>
<el-table-column label="采购价" prop="purchasePrice"></el-table-column>
<template #footer>
<div class="btn">
<el-button @click="Cancel">取消</el-button>
<el-button type="primary" @click="sure">确定</el-button>
</div>
</template>
</Table>
</el-dialog>
</template>
<script setup lang="ts">
//API
import { getFoods } from '@/apis/foods/apis';
//表格
import Table from '@/components/table/Table.vue';
//ref
import { ref } from 'vue';
const isOpen = defineModel({
type: Boolean,
default: false
});
const ids = ref<number[]>([]);
const idsAll = ref<number[]>([]);
//确定
const emit = defineEmits(['sure']);
const sure = () => {
console.log(ids.value);
emit('sure', ids.value);
isOpen.value = false;
};
//取消
const Cancel = () => {
isOpen.value = false;
};
</script>
<style lang="sass" scoped>
.btn
margin-top: 20px
display: flex
justify-content: flex-end
</style>