初始版本提交

This commit is contained in:
yaoyn
2024-02-05 09:15:37 +08:00
parent b52d4414be
commit 445292105f
1848 changed files with 236859 additions and 75 deletions

View File

@ -0,0 +1,230 @@
<template>
<a-modal :visible="true" title="订单" :width="800" :footer="null" @cancel="cancel">
<div class="model-box">
<a-form
:model="formState"
name="basic"
:label-col="{ span: 3 }"
:wrapper-col="{ span: 23 }"
autocomplete="off"
@finish="submit"
>
<a-form-item
label="订单编号"
name="OrderNum"
:rules="[{ required: true, message: '请输入订单编号' }]"
>
<a-input v-model:value="formState.OrderNum" />
</a-form-item>
<a-form-item
label="订单名称"
name="OrderName"
:rules="[{ required: true, message: '请输入订单名称' }]"
>
<a-input v-model:value="formState.OrderName" />
</a-form-item>
<a-form-item
label="订单总金额"
name="OrderPriceCount"
:rules="[{ required: true, message: '请输入订单总金额' }]"
>
<a-input-number disabled style="width: 100%" v-model:value="formState.OrderPriceCount" />
</a-form-item>
<a-form-item
label="订单负责人"
name="OrderManager"
:rules="[{ required: true, message: '请输入订单负责人' }]"
>
<a-input disabled v-model:value="data.userName" />
</a-form-item>
<div class="btn-box">
<SelectGoods style="margin-right: 20px" @submit="addGoods" />
<SelectUser
class="select-box"
:selectedIds="[data.userID]"
:multiple="false"
@change="getRuleUserIds"
@changeNames="getRuleUserNames"
>
<a-button type="primary"> 选择负责人 </a-button>
</SelectUser>
</div>
<a-table
bordered
:data-source="dataSource"
:columns="columns"
:pagination="{
hideOnSinglePage: true,
}"
>
<template #bodyCell="{ column, record }">
<template v-if="column.dataIndex === 'ProductAmount'">
<div class="editable-cell">
<a-input-number v-model:value="record.ProductAmount" @change="save(record)" />
</div>
</template>
<template v-else-if="column.dataIndex === 'operation'">
<a-popconfirm
v-if="dataSource.length"
title="确定删除?"
@confirm="onDelete(record.ProductID)"
>
<a>删除</a>
</a-popconfirm>
</template>
</template>
</a-table>
<a-form-item>
<a-button type="primary" html-type="submit" style="margin: 10px 0">提交</a-button>
</a-form-item>
</a-form>
</div>
</a-modal>
</template>
<script setup lang="ts">
import { onMounted, reactive, ref } from 'vue';
import type { PropType, Ref } from 'vue';
import { SelectUser } from '/@/components/SelectOrganizational/index';
import SelectGoods from './SelectGoods.vue';
import { add, edit } from './api/index';
import { notification } from 'ant-design-vue';
const emits = defineEmits(['cancel']);
const props = defineProps({
data: {
type: Object as PropType<any>,
},
});
const data = reactive({ key: '', userID: '', userName: '', OrderID: '' });
const formState = reactive({
OrderNum: '',
OrderName: '',
OrderManager: '',
OrderPriceCount: 0,
});
interface DataItem {
ProductID: string;
key: string;
ProductName: string;
ProductUnitPrice: number;
ProductAmount: number;
ProductPriceCount: number;
}
const dataSource: Ref<DataItem[]> = ref([]);
const columns = [
{
title: '商品名称',
dataIndex: 'ProductName',
},
{
title: '单价',
dataIndex: 'ProductUnitPrice',
},
{
title: '数量',
dataIndex: 'ProductAmount',
},
{
title: '合计',
dataIndex: 'ProductPriceCount',
},
{
title: '操作',
dataIndex: 'operation',
},
];
onMounted(() => {
if (props.data.OrderID) {
data.OrderID = props.data.OrderID;
formState.OrderName = props.data.OrderName;
formState.OrderNum = props.data.OrderNum;
formState.OrderManager = props.data.OrderManager;
data.userID = formState.OrderManager;
data.userName = props.data.OrderManagerName;
formState.OrderPriceCount = props.data.OrderPriceCount;
if (props.data.OrderProduct.length > 0) {
dataSource.value = props.data.OrderProduct;
}
}
});
const save = (item: DataItem) => {
item.ProductPriceCount = item.ProductAmount * item.ProductUnitPrice;
changeOrderPriceCount();
};
const onDelete = (key: string) => {
dataSource.value = dataSource.value.filter((item) => item.ProductID !== key);
changeOrderPriceCount();
};
function changeOrderPriceCount() {
if (dataSource.value.length > 0) {
formState.OrderPriceCount = dataSource.value.reduce(function (a, b) {
return a + b.ProductPriceCount;
}, 0);
} else {
formState.OrderPriceCount = 0;
}
}
function getRuleUserIds(val) {
data.userID = val[0];
formState.OrderManager = val[0];
}
function getRuleUserNames(val) {
data.userName = val;
}
function addGoods(list) {
let demo = list.map((ele) => {
ele['ProductPriceCount'] = 0;
ele['ProductAmount'] = 0;
return ele;
});
dataSource.value.push(...demo);
}
async function submit() {
let res = false;
if (data.OrderID) {
let params = {
...formState,
OrderID: data.OrderID,
OrderProduct: dataSource.value,
};
try {
res = await edit(params);
} catch (error) {}
} else {
let params = {
...formState,
OrderProduct: dataSource.value,
};
try {
res = await add(params);
} catch (error) {}
}
if (res) {
notification.success({
message: '提示',
description: '添加成功',
}); //提示消息
cancel();
} else {
notification.error({
message: '提示',
description: '添加失败',
}); //提示消息
}
}
function cancel() {
emits('cancel');
}
</script>
<style scoped>
.model-box {
padding: 20px 30px;
}
.btn-box {
display: flex;
margin: 10px 0;
}
</style>

View File

@ -0,0 +1,111 @@
<template>
<div>
<a-button type="primary" @click="showModal">选择商品</a-button>
<a-modal
v-model:visible="data.visible"
:width="1000"
title="选择商品"
@ok="finish"
@cancel="cancel"
>
<div class="model-box" v-if="data.visible">
<a-table
:row-selection="rowSelection"
:pagination="{
hideOnSinglePage: true,
}"
rowKey="ProductID"
:columns="columns"
:data-source="data.tableList"
>
<template #bodyCell="{ column, text }">
<template v-if="column.dataIndex === 'name'">
<a>{{ text }}</a>
</template>
</template>
</a-table>
</div>
</a-modal>
</div>
</template>
<script setup lang="ts">
import { computed, onMounted, reactive } from 'vue';
import type { TableColumnType } from 'ant-design-vue';
import { getGoodsList } from './api/index';
import { notification } from 'ant-design-vue';
interface DataItem {
ProductName: string;
ProductAmount: number;
ProductUnitPrice: number;
}
const emits = defineEmits(['submit']);
const columns: TableColumnType<DataItem>[] = [
{
title: '商品名称',
dataIndex: 'ProductName',
},
{
title: '数量',
dataIndex: 'ProductAmount',
},
{
title: '单价',
dataIndex: 'ProductUnitPrice',
},
];
const data: {
visible: boolean;
tableList: DataItem[];
selectedRowKeys: string[];
selectedRows: DataItem[];
} = reactive({ visible: false, tableList: [], selectedRowKeys: [], selectedRows: [] });
onMounted(() => {
data.selectedRowKeys = [];
data.selectedRows = [];
data.visible = false;
});
async function getList() {
let res = await getGoodsList();
data.tableList = res;
}
const rowSelection = computed(() => {
return {
checkStrictly: true,
selectedRowKeys: data.selectedRowKeys,
onChange: (selectedRowKeys: string[], selectedRows: DataItem[]) => {
data.selectedRowKeys = selectedRowKeys;
data.selectedRows = selectedRows;
},
};
});
async function showModal() {
await getList();
data.visible = true;
}
function finish() {
console.log('data.selectedRows: ', data.selectedRows);
if (data.selectedRows.length > 0) {
emits('submit', data.selectedRows);
cancel();
} else {
notification.error({
message: '提示',
description: '请至少选择一个信息',
}); //提示消息
}
}
function cancel() {
data.selectedRowKeys = [];
data.selectedRows = [];
data.visible = false;
}
</script>
<style scoped>
.model-box {
padding: 20px 30px;
}
</style>

Binary file not shown.

View File

@ -0,0 +1,99 @@
import { httpRequest } from '/@/api/sys/api';
import { defHttp } from '/@/utils/http/axios';
import { ErrorMessageMode } from '/#/axios';
enum Api {
Page = 'wbw/getOrderTableData',
DeleteOrderUrl = 'wbw/deleteOrderData',
OrderDetail = 'wbw/getOrderProductData',
GoodsList = 'wbw/getProductData',
Order = '/order',
}
/**
* @description: 查询订单列表
*/
export async function getOrderList(params: { keyword: string; userID: string }) {
// key 关键字 userID 用户id
const url =
Api.Page +
'' +
'?key=' +
(params.keyword ? params.keyword : '') +
'&userID=' +
(params.userID ? params.userID : '');
return httpRequest(
{
requestUrl: url,
requestType: 'get',
},
{},
);
}
/**
* @description: 查询商品列表
*/
export async function getGoodsList() {
return httpRequest(
{
requestUrl: Api.GoodsList,
requestType: 'get',
},
{},
);
}
/**
* @description: 删除订单
*/
export async function deleteOrder(id) {
const url = Api.DeleteOrderUrl + '?OrderID=' + id;
return httpRequest(
{
requestUrl: url,
requestType: 'get',
},
{},
);
}
/**
* @description: 查询订单列表
*/
export async function getOrderDetail(id) {
const url = Api.OrderDetail + '?OrderID=' + id;
return httpRequest(
{
requestUrl: url,
requestType: 'get',
},
{},
);
}
/**
* @description: 新增
*/
export async function add(params: any, mode: ErrorMessageMode = 'modal') {
return defHttp.post<boolean>(
{
url: Api.Order,
params: params,
},
{
errorMessageMode: mode,
},
);
}
/**
* @description: 新增
*/
export async function edit(params: any, mode: ErrorMessageMode = 'modal') {
return defHttp.put<boolean>(
{
url: Api.Order,
params: params,
},
{
errorMessageMode: mode,
},
);
}

View File

@ -0,0 +1,27 @@
CREATE TABLE `t_order` (
`OrderID` varchar(50) NOT NULL,
`OrderNum` varchar(200) NOT NULL,
`OrderName` varchar(300) NOT NULL,
`OrderManager` varchar(50) NOT NULL,
`OrderAddTime` datetime DEFAULT NULL,
`OrderModifyTime` datetime DEFAULT NULL,
`OrderPriceCount` decimal(10,0) DEFAULT NULL,
PRIMARY KEY (`OrderID`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_0900_ai_ci;
CREATE TABLE `t_order_product` (
`ID` varchar(50) NOT NULL,
`OrderID` varchar(50) NOT NULL,
`ProductID` varchar(50) NOT NULL,
`ProductAmount` decimal(10,0) NOT NULL,
`ProductPriceCount` decimal(10,0) DEFAULT NULL,
PRIMARY KEY (`ID`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_0900_ai_ci;
CREATE TABLE `t_product` (
`ProductID` varchar(50) NOT NULL,
`ProductNum` varchar(200) NOT NULL,
`ProductName` varchar(300) NOT NULL,
`ProductUnitPrice` decimal(10,0) NOT NULL,
`AddTime` datetime DEFAULT NULL,
PRIMARY KEY (`ProductID`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_0900_ai_ci;

View File

@ -0,0 +1,209 @@
<template>
<PageLayout
:title="t('订单列表')"
:searchConfig="searchConfig"
@search="search"
:layoutOne="true"
>
<template #search> </template>
<template #operation>
<div class="button-box">
<a-button @click.stop="handleAdd">{{ t('新增') }}</a-button>
</div>
</template>
<template #right>
<div v-if="data.dataSource.length > 0">
<a-table
bordered
:pagination="{
hideOnSinglePage: true,
}"
:data-source="data.dataSource"
:columns="configColumns"
>
<template #bodyCell="{ column, record }">
<template v-if="column.dataIndex === 'operation'">
<Icon
icon="clarity:note-edit-line"
class="edit-icon"
@click.stop="handleEdit(record)"
/>
<a-popconfirm title="确定删除吗?" @confirm="handleDelete(record)">
<Icon icon="ant-design:delete-outlined" class="delete-icon" @click.stop="" />
</a-popconfirm>
</template>
</template>
</a-table>
</div>
<div v-else>
<EmptyBox />
</div>
<Form v-if="data.visible" @cancel="cancelForm" :data="data.editData" />
</template>
</PageLayout>
</template>
<script lang="ts" setup>
import { onMounted, reactive } from 'vue';
import { PageLayout, EmptyBox } from '/@/components/ModalPanel';
import { useI18n } from '/@/hooks/web/useI18n';
import { BasicColumn } from '/@/components/Table';
import { getOrderList, getOrderDetail, deleteOrder } from './api/index';
import { Icon } from '/@/components/Icon/index';
import Form from './Form.vue';
import { notification } from 'ant-design-vue';
const { t } = useI18n();
interface DataItem {
OrderNum: number;
OrderName: string;
OrderPriceCount: number;
OrderManager: string;
}
const defaultFormData: DataItem = {
OrderNum: 0,
OrderName: '',
OrderPriceCount: 0,
OrderManager: '',
};
const configColumns: BasicColumn[] = [
{
title: t('订单名称'),
dataIndex: 'OrderName',
align: 'left',
},
{
title: t('订单编码'),
dataIndex: 'OrderNum',
width: 120,
align: 'left',
},
{
title: t('订单总金额'),
dataIndex: 'OrderPriceCount',
width: 120,
align: 'left',
},
{
title: t('负责人'),
dataIndex: 'OrderManagerName',
width: 120,
align: 'left',
},
{
title: '操作',
dataIndex: 'operation',
width: 120,
},
];
const searchConfig = [
{
field: 'keyword',
label: t('关键字'),
type: 'input',
},
{
field: 'userID',
label: t('负责人'),
type: 'user',
},
];
let data: {
visible: boolean;
dataSource: Array<DataItem>;
editData: DataItem;
params: {
keyword: string;
userID: string;
};
} = reactive({
visible: false,
dataSource: [],
editData: defaultFormData,
params: {
keyword: '',
userID: '',
},
});
onMounted(() => {
data.dataSource = [];
getList();
});
async function getList() {
let res = await getOrderList({
keyword: data.params.keyword,
userID: data.params.userID,
});
data.dataSource = res;
}
function search(params?: any) {
data.params.keyword = '';
data.params.userID = '';
if (params.keyword) {
data.params.keyword = params.keyword;
}
if (params.userID) {
data.params.userID = params.userID[0];
}
data.dataSource = [];
getList();
}
function handleAdd() {
data.editData = defaultFormData;
data.visible = true;
}
async function handleEdit(record) {
try {
let res = await getOrderDetail(record.OrderID);
data.editData = res;
data.visible = true;
} catch (error) {}
}
async function handleDelete(record) {
try {
let res = await deleteOrder(record.OrderID);
if (res) {
notification.success({
message: '提示',
description: '删除成功',
}); //提示消息
cancelForm();
} else {
notification.error({
message: '提示',
description: '删除失败',
}); //提示消息
}
} catch (error) {}
}
function cancelForm() {
data.visible = false;
getList();
}
</script>
<style lang="less" scoped>
.list-box {
display: flex;
flex-wrap: wrap;
.item {
position: relative;
margin: 8px;
width: 258px;
height: 184px;
overflow: hidden;
border-radius: 4px;
padding-bottom: 36px;
box-shadow: 0 3px 6px 1px rgb(0 0 0 / 16%);
}
}
.page-box {
position: absolute;
bottom: 20px;
right: 20px;
}
:deep(.search) {
margin-bottom: 8px;
}
</style>