update: 更新收货入库细节

This commit is contained in:
admin 2024-04-16 09:52:13 +08:00
parent b1534cf31e
commit 02ff0c44fe
15 changed files with 562 additions and 43 deletions

View File

@ -83,21 +83,23 @@ const getList = (v?: boolean) => {
if (state.type === "1") {
ReceiveApi.getOrderPage(params).then((res) => {
if (res.code === 200) {
pageList.isLoading = false;
(pageList as any).list = (res.data.list as any).map((item: any) => {
return { ...item, isChecked: false };
});
pageList.total = (res.data as any).total;
pageList.isLoading = false;
}
});
} else if (state.type === "2") {
ShipmentApi.getOrderPage(params).then((res) => {
if (res.code === 200) {
pageList.isLoading = false;
(pageList as any).list = (res.data.list as any).map((item: any) => {
return { ...item, isChecked: false };
});
pageList.total = (res.data as any).total;
pageList.isLoading = false;
}
});
}

View File

@ -150,7 +150,7 @@ const rules = reactive({
});
const contrlModalParams = reactive<any>({
isShowSplTime: false,
spltime: "",
spltime: Number(new Date()),
user: {
isShow: false,
title: "标题",

View File

@ -180,7 +180,7 @@ const rules2 = reactive({
});
const contrlModalParams = reactive<any>({
isShowSplTime: false,
spltime: "",
spltime: Number(new Date()),
user: {
isShow: false,
title: "标题",

View File

@ -110,7 +110,7 @@ const model1 = reactive<any>({
order: {
buttonType: 0,
fileLists: [],
splTime: "",
splTime:'',
subtractType: 1,
},
});
@ -166,7 +166,7 @@ const rules = reactive({
});
const contrlModalParams = reactive<any>({
isShowSplTime: false,
spltime: "",
spltime: Number(new Date()),
device: {
isShow: false,
title: "标题",

View File

@ -162,7 +162,7 @@ const rules = reactive({
});
const contrlModalParams = reactive<any>({
isShowSplTime: false,
spltime: "",
spltime: Number(new Date()),
device: {
isShow: false,
title: "标题",

View File

@ -109,13 +109,11 @@ const getList = (v?: boolean) => {
pageList.isLoading = true;
SupplierApi.getSupplierTypePage(params).then((res: any) => {
if (res.code === 200) {
if (res.code === 200) {
pageList.isLoading = false;
(pageList as any).list = (pageList as any).list = pageList.list.concat(
res.data.list
);
pageList.total = (res.data as any).total;
}
pageList.isLoading = false;
(pageList as any).list = (pageList as any).list = pageList.list.concat(
res.data.list
);
pageList.total = (res.data as any).total;
}
});
};

View File

@ -0,0 +1,122 @@
<template>
<u-popup :show="show" mode="left" :closeable="true" @close="handleClose">
<view class="c-dialog-filter">
<view class="title">{{ isShipment ? "出货" : "收货" }}产品</view>
<view class="dialog-product-layout">
<text
v-for="(item, index) in state.list"
:class="{ active: state.current === item.id }"
@click="handleSelect(item)"
:key="index"
>{{isShipment ? item.shmProductsName : item.reProductsName }}</text
>
</view>
<!-- <view class="btn-confirm">
<view class="btn">
<u-button type="primary" :text="'确认'"></u-button>
</view>
</view> -->
</view>
</u-popup>
</template>
<script setup lang="ts">
import { ReceiveProductApi, GoodsApi } from "@/services";
const props = defineProps<{
show: boolean;
isShipment: boolean;
}>();
const emit = defineEmits(["handleDialog", "changeProduct"]);
const handleClose = () => {
emit("handleDialog", false);
};
const state = reactive<any>({
list: [],
current: -1,
});
const handleSelect = (item: any) => {
state.current = item.id;
emit("changeProduct", item);
emit("handleDialog", false);
};
const getList = () => {
if (props.isShipment) {
GoodsApi.getShipmentProductList().then((res) => {
if (res.code === 200) {
state.list = res.data;
}
});
} else {
ReceiveProductApi.getAllReProducts().then((res) => {
if (res.code === 200) {
state.list = res.data;
}
});
}
};
onMounted(() => {
getList();
});
</script>
<style lang="scss" scoped>
.c-dialog-filter {
width: 95vw;
padding: 25rpx;
.title {
font-weight: 500;
font-size: 32rpx;
color: #000000;
text-align: center;
}
}
// dialog
.dialog-product-layout {
box-shadow: 0rpx 0rpx 10rpx 0rpx rgba(5, 68, 37, 0.12);
border-radius: 13rpx;
margin: 42rpx 25rpx;
padding: 19rpx;
display: flex;
justify-content: flex-start;
align-items: center;
flex-flow: row wrap;
max-height: 70vh;
overflow: auto;
text {
font-weight: 400;
font-size: 26rpx;
color: #999999;
background: #ffffff;
border-radius: 6rpx;
border: 1px solid rgba(153, 153, 153, 0.64);
text-align: center;
cursor: pointer;
padding: 0rpx 20rpx;
margin-bottom: 20rpx;
margin-left: 10rpx;
margin-right: 10rpx;
}
.active {
border-color: $u-primary;
color: $u-primary;
}
}
.btn-confirm {
box-shadow: 0rpx 0rpx 10rpx 0rpx rgba(0, 56, 93, 0.12);
border-radius: 13rpx 13rpx 0rpx 0rpx;
position: absolute;
bottom: 0rpx;
width: 100%;
left: 0rpx;
padding: 27.56rpx;
.btn {
text-align: center;
::v-deep button {
width: 80%;
border-radius: 43rpx;
}
}
}
</style>

View File

@ -0,0 +1,241 @@
<template>
<u-popup :show="show" mode="left" :closeable="true" @close="handleClose">
<view class="c-dialog-filter">
<view class="title">{{isShipment? '客户' : '供应商'}}筛选</view>
<view class="search">
<u-search
:placeholder="`请输入${isShipment? '客户' : '供应商'}名称 / 卡号搜索`"
v-model="keyword"
@search="handleSearch()"
></u-search>
</view>
<view class="dialog-product-layout">
<!-- 自定义索引列表 -->
<view class="address-book-container">
<!-- 左侧通讯录 -->
<scroll-view
class="scroll-container"
:scroll-y="true"
:scroll-into-view="toView"
:scroll-with-animation="true"
>
<view
class="address-book"
v-for="(item, index) in addressBook"
:key="index"
:id="item.name"
>
<view class="address-book-index">{{ item.name }}</view>
<view
class="contact-container"
v-for="(cItem, index) in item.list"
:key="index"
>
<!-- <img
class="contact-img"
src="http://www.lixia.gov.cn/picture/0/s_97b76c734a6f40f8abba95615cbff1e1.jpg"
alt=""
/> -->
<view
class="contact-detail-container"
@click="handleClick(cItem)"
>
<view class="contact-name">{{ cItem.name }}</view>
<view class="contact-address">{{ cItem.cardCode }}</view>
<!-- <view class="contact-phone">{{ item.phone }}</view> -->
</view>
</view>
</view>
</scroll-view>
<!-- 右侧字母导航条 -->
<view class="letter-nav">
<view
class="item"
:class="{ active: toView === item }"
v-for="(item, index) in indexList"
:key="index"
@click="toSelectIndex(item)"
>{{ item }}</view
>
</view>
</view>
</view>
</view>
</u-popup>
</template>
<script setup lang="ts">
import { CustomerApi, SupplierApi } from "@/services";
const props = defineProps<{
show: boolean;
isShipment: boolean;
}>();
const emit = defineEmits(["handleDialog", "changeUser"]);
const handleClose = () => {
emit("handleDialog", false);
};
const keyword = ref("");
const indexList = [
"A",
"B",
"C",
"D",
"E",
"F",
"G",
"H",
"I",
"J",
"K",
"L",
"M",
"N",
"O",
"P",
"Q",
"R",
"S",
"T",
"U",
"V",
"W",
"X",
"Y",
"Z",
"#",
];
const toView = ref("");
const addressBook = ref();
// [
// {
// id: "A",
// data: [
// {
// zh_title: "",
// en_title: "aa",
// address: "910289591",
// phone: "111111",
// },
// {
// zh_title: "",
// en_title: "aaaaa",
// address: "ALL",
// phone: "222222",
// },
// ],
// }
// ];
const toSelectIndex = (item: any) => {
toView.value = item;
};
const handleClick = (item: any) => {
emit("changeUser", item);
emit("handleDialog", false);
};
const handleSearch = () => {
getList();
};
const getList = () => {
if (props.isShipment) {
CustomerApi.getCustomUserListLettera({ name: keyword.value }).then(
(res: any) => {
if (res.code === 200) {
addressBook.value = res.data.reduce((pre: any, curr: any) => {
if (curr.list.length > 0) {
pre.push(curr);
}
return pre;
}, []);
}
}
);
} else {
SupplierApi.getSupplierUserListLettera({ name: keyword.value }).then(
(res: any) => {
if (res.code === 200) {
addressBook.value = res.data.reduce((pre: any, curr: any) => {
if (curr.list.length > 0) {
pre.push(curr);
}
return pre;
}, []);
}
}
);
}
};
watch(
() => props.isShipment,
(newValue, oldValue) => {
getList();
}
);
onMounted(() => {
getList();
});
</script>
<style lang="scss" scoped>
.c-dialog-filter {
width: 95vw;
padding: 25rpx;
.title {
font-weight: 500;
font-size: 32rpx;
color: #000000;
text-align: center;
}
.search {
margin: 30rpx 0px;
}
}
.dialog-product-layout {
height: 80vh;
.address-book-container {
height: 100%;
}
.address-book-index {
font-size: 24rpx;
}
.contact-img {
width: 20px;
height: 20px;
}
.scroll-container {
height: 100%;
}
.letter-nav {
position: fixed;
right: 25rpx;
top: 100px;
font-size: 22rpx;
text-align: center;
.item:hover,
.active {
color: $u-primary;
}
}
.contact-container {
display: flex;
align-items: center;
margin: 2%;
}
.contact-detail-container {
display: flex;
align-items: center;
justify-content: space-between;
width: 80%;
font-size: 22rpx;
.contact-address {
color: rgba(0, 0, 0, 0.65);
}
}
}
</style>

View File

@ -23,15 +23,18 @@
v-model="(model1.order as any)[item.key]"
:placeholder="`请输入${item.name}`"
></u-textarea>
<u-input
v-if="item.type === 'select' || item.type === 'input'"
<!-- v-model="(model1.order as any)[item.key]" -->
<up-input
v-model="(model1.order as any)[item.key]"
v-if="item.type === 'select' || item.type === 'input'"
:placeholder="`${item.type === 'select' ? '选择' : '输入'}${
item.name
}`"
:clearable="true"
:customStyle="{}"
border="none"
:value="(model1.order as any)[item.key]"
@change="(e:any) => {hanldeInput(e, item)}"
>
<template #suffix>
<text v-if="item.key === 'subtractNum'">
@ -41,6 +44,18 @@
{{ item.unit }}
</text>
</template>
</up-input>
<!-- 自定义selectui -->
<u-input
v-if="item.type === 'selectCustom'"
v-model="(model1.order as any)[item.key]"
:placeholder="`请选择${item.name}`"
:clearable="true"
:customStyle="{}"
border="none"
disabled
disabledColor="#ffffff"
>
</u-input>
<!-- @afterRead="afterRead"
@delete="deletePic" -->
@ -68,7 +83,10 @@
:customStyle="{ marginRight: '10px' }"
></u-radio>
</u-radio-group>
<template #right v-if="item.type === 'select'">
<template
#right
v-if="item.type === 'select' || item.type === 'selectCustom'"
>
<u-icon name="arrow-right"></u-icon>
</template>
</u-form-item>
@ -90,6 +108,23 @@
<u-button text="暂不定价" @click="handleBack()"></u-button>
<u-button type="primary" text="保存" @click="save()"></u-button>
</view>
<!-- 供应商选择弹框 -->
<SupplierDialog
ref="supplierDialog"
:show="showDialog.showSupplier"
@handleDialog="(v:boolean) => {handleDialog('showSupplier', v)}"
@changeUser="changeUser"
:isShipment="false"
></SupplierDialog>
<!-- 收货产品弹框 -->
<ProductDialog
:show="showDialog.showProduct"
@handleDialog="(v:boolean) => {handleDialog('showProduct', v)}"
@changeProduct="changeProduct"
ref="productRef"
:isShipment="false"
></ProductDialog>
</template>
<script setup lang="ts">
import type { ComType } from "@/types/global";
@ -102,6 +137,66 @@ import {
import _ from "underscore";
import { onLoad } from "@dcloudio/uni-app";
import { ImagesType, OrderType } from "@/utils/enum";
import SupplierDialog from "../components/SupplierDialog.vue";
import ProductDialog from "../components/ProductDialog.vue";
import valid from "@/utils/validate";
import { countDots } from "@/utils";
//
const showDialog = <
{
[key: string]: boolean;
}
>reactive({
showSupplier: false,
showProduct: false,
});
const handleDialog = (key: string, v: boolean) => {
showDialog[key] = v;
};
const changeUser = (obj: any) => {
model1.order.userName = obj.name; //
model1.order.userId = obj.id; // Id,
};
//
const changeProduct = (obj: any) => {
model1.order.productName = obj.reProductsName; //
model1.order.productId = obj.id; // Id,
};
//
const hanldeInput = (e: any, item: any) => {
if (item.key === "price" || item.key === "grossWeight") {
const tempPrice = e?.replace(valid.valid_decimal.pattern, "");
if (countDots(tempPrice).length > 1) {
uni.showToast({
title: "请输入正确的" + item.name,
icon: "none",
});
}
setTimeout(() => {
model1.order[item.key] = tempPrice;
}, 100);
}
if (item.key === "subtractNum") {
const temp = e?.replace(valid.valid_decimal.pattern, "");
if (
model1.order.buttonType === 1 &&
(parseInt(temp) > 100 || parseInt(temp) < 0)
) {
uni.showToast({
title: `${item.name}正确范围是0-100`,
icon: "none",
});
}
setTimeout(() => {
model1.order[item.key] = temp;
}, 100);
}
};
const model1 = reactive<{ order: Order }>({
order: {
id: 0,
@ -118,6 +213,7 @@ const model1 = reactive<{ order: Order }>({
scaleStatus: 1,
},
});
const rules = reactive({
"order.userName": {
type: "string",
@ -131,12 +227,14 @@ const rules = reactive({
message: "请选择收货产品名称",
trigger: ["blur", "change"],
},
"order.price": {
type: "number",
required: true,
message: "请输入单价",
trigger: ["blur", "change"],
},
"order.price": [
{
type: "number",
required: true,
message: "单价为空或单价输入错误",
trigger: ["blur", "change"],
},
],
"order.grossWeight": {
type: "number",
required: true,
@ -158,7 +256,7 @@ const rules = reactive({
});
const contrlModalParams = reactive<ComType>({
isShowSplTime: false,
spltime: "",
spltime: Number(new Date()),
userSelect: {
isShow: false,
title: "标题",
@ -175,13 +273,13 @@ const formAttrList = reactive<ComType>([
{
name: "供应商",
key: "userName",
type: "select",
type: "selectCustom",
unit: "",
childKey: "userSelect",
required: true,
fn: () => {
contrlModalParams.userSelect.isShow = true;
contrlModalParams.userSelect.title = "供应商";
// handleDialog("showSupplier", true);
uni.hideKeyboard();
},
},
{
@ -193,13 +291,15 @@ const formAttrList = reactive<ComType>([
{
name: "收货产品",
key: "productName",
type: "select",
type: "selectCustom",
unit: "",
childKey: "productSelect",
required: true,
fn: () => {
contrlModalParams.productSelect.isShow = true;
contrlModalParams.productSelect.title = "收货产品";
handleDialog("showProduct", true);
uni.hideKeyboard();
// contrlModalParams.productSelect.isShow = true;
// contrlModalParams.productSelect.title = "";
},
},
{
@ -362,6 +462,10 @@ const handleDelete = (e: any) => {
*/
const form = ref();
const check = () => {
// if (valid.carNo.pattern.test(model1.order.carNumber)) {
// console.log('********')
// return false;
// }
return new Promise((resolve) => {
form.value
.validate()
@ -378,6 +482,34 @@ const check = () => {
});
};
const save = () => {
if (model1.order.carNumber) {
if (!valid.carNo.pattern.test(model1.order.carNumber)) {
uni.showToast({ icon: "none", title: "请输入正确的车牌号" });
return;
}
}
if (
model1.order.price &&
model1.order.price[model1.order.price.length - 1] === "."
) {
uni.showToast({
title: "请输入正确的单价",
icon: "none",
});
return;
}
if (
model1.order.grossWeight?.toString() &&
model1.order.grossWeight?.toString()[
model1.order.grossWeight?.toString().length - 1
] === "."
) {
uni.showToast({
title: "请输入正确的毛重",
icon: "none",
});
return;
}
check().then((res) => {
if (res) {
startSave();
@ -449,6 +581,7 @@ const prePage = ref("");
onLoad((option) => {
model1.order.id = parseInt((option as any).id);
prePage.value = (option as any).prePage;
if (model1.order.id) {
ReceiveApi.getDetailById({ id: model1.order.id }).then((res) => {
if (res.code === 200) {
@ -460,6 +593,10 @@ onLoad((option) => {
res.data.weighingMethod !== null ? res.data.weighingMethod : 0,
multiCategory:
res.data.multiCategory !== null ? res.data.multiCategory : 0,
subtractNum:
res.data.buttonType === 0
? res.data.buckleMiscellaneous
: res.data.points,
fileLists: model1.order.fileLists.map((item: any) => {
return { ...item, fileID: item.id };
}),

View File

@ -202,6 +202,10 @@ const updateStatus = (status: number) => {
.map((item) => {
return { ...item, scaleStatus: status };
});
if(list.length === 0) {
uni.showToast({icon: 'none', title: '请至少选择一个收货单'})
return
}
ReceiveApi.updateOrderIn({ orderInPos: list }).then((res) => {
if (res.code === 200) {
resetPageList();
@ -234,11 +238,11 @@ const getList = (v?: boolean) => {
userName: keyword.value
}).then((res) => {
if (res.code === 200) {
pageList.isLoading = false;
(pageList as any).list = (res.data.list as any).map((item: any) => {
return { ...item, isChecked: false };
});
pageList.total = (res.data as any).total;
pageList.isLoading = false;
}
});
};

View File

@ -232,11 +232,12 @@ const getList = (v?: boolean) => {
userName: keyword.value,
}).then((res) => {
if (res.code === 200) {
pageList.isLoading = false;
(pageList as any).list = (res.data.list as any).map((item: any) => {
return { ...item, isChecked: false };
});
pageList.total = (res.data as any).total;
pageList.isLoading = false;
}
});
};

View File

@ -115,13 +115,11 @@ const getList = (v?: boolean) => {
scaleStatus: state.scaleStatus,
}).then((res) => {
if (res.code === 200) {
if (res.code === 200) {
pageList.isLoading = false;
pageList.isLoading = false;
(pageList as any).list = (pageList as any).list = (
pageList as any
).list.concat(res.data.list);
pageList.total = (res.data as any).total;
}
}
});
};

View File

@ -18,7 +18,7 @@ interface Order {
productName?: string; //undefined
imagesId?: number | undefined; //弃用
imageUrls?: string; //弃用
carNumber?: string; //车牌号
carNumber: string; //车牌号
receiptNumber?: string; //收货单号
grossWeight?: number; //毛重
tare?: string; //皮重

View File

@ -199,3 +199,8 @@ export function signFigures (num:number, rank = 6) {
}
return (ans * sign)
}
// 判断字符串中有几个.
export function countDots(str:any) {
return (str.match(/\./g) || []).length;
}

View File

@ -1,18 +1,29 @@
const valid = {
mobile: {
pattern: /^1(3\d|4[5-9]|5[0-35-9]|6[567]|7[0-8]|8\d|9[0-35-9])\d{8}$/,
message: '请输入正确的手机号码',
message: "请输入正确的手机号码",
},
password: {
pattern: /^((?=.*[a-z])(?=.*[A-Z])(?=.*[0-9])(?=.*[!;:@#$%?^&*_-]))([a-zA-Z0-9!;:@#$%?^&*_-]){6,16}$/,
message: '密码必须包含大小写字母、数字、特殊字符',
pattern:
/^((?=.*[a-z])(?=.*[A-Z])(?=.*[0-9])(?=.*[!;:@#$%?^&*_-]))([a-zA-Z0-9!;:@#$%?^&*_-]){6,16}$/,
message: "密码必须包含大小写字母、数字、特殊字符",
},
username: /^[a-zA-Z]{4,12}$/, //长度4~12英文大小写字母
email: /^(\w+(_|-|.)*)+@(\w+(-)?)+(.\w{2,})+$/,//用户名 @ 域名域名后缀至少2个字符
email: /^(\w+(_|-|.)*)+@(\w+(-)?)+(.\w{2,})+$/, //用户名 @ 域名域名后缀至少2个字符
valid_number: /[^\d]/g,
// valid_password: /^(?![a-zA-Z]+$)(?![A-Z0-9]+$)(?![A-Z\\W_]+$)(?![a-z0-9]+$)(?![a-z\\W_]+$)(?![0-9\\W_]+$)[A-Za-z\d`~!@#$%^&*()_+<>?:"{},.\/\\;'[\]]{6,20}$/, // 8位 大小写 数字 和下划线
valid_no_space: /\s+/g, //不可输入空格
valid_no_cn:/[\u4E00-\u9FA5]/g, // 不可输入中文
valid_no_cn: /[\u4E00-\u9FA5]/g, // 不可输入中文
valid_number_en: /^[a-zA-Z0-9]+$/, // 只能输入数字和英文
}
export default valid
carNo: {
// /^[京津沪渝冀豫云辽黑湘皖鲁新苏浙赣鄂桂甘晋蒙陕吉闽贵粤青藏川宁琼使领A-Z]{1}[A-Z]{1}[A-Z0-9]{4}[A-Z0-9挂学警港澳]{1}$/
// /^[\x{4e00}-\x{9fa5}]{1}[A-Z]{1}[A-Z0-9]{5}$/u
pattern: /^([京津沪渝冀豫云辽黑湘皖鲁新苏浙赣鄂桂甘晋蒙陕吉闽贵粤青藏川宁琼使领A-Z]{1}[a-zA-Z](([京津沪渝冀豫云辽黑湘皖鲁新苏浙赣鄂桂甘晋蒙陕吉闽贵粤青藏川宁琼ABCDEFGHJK]((?![IO])[a-zA-Z0-9](?![IO]))[0-9]{4})|([0-9]{5}[ABCDEFGHJK]))|[京津沪渝冀豫云辽黑湘皖鲁新苏浙赣鄂桂甘晋蒙陕吉闽贵粤青藏川宁琼使领A-Z0-9]{1}[A-Z0-9]{1}[A-Z0-9应]{4,5}[A-Z0-9挂学警港澳领使急]{1})$/,
message: "请输入正确的车牌号",
},
valid_decimal: {
pattern: /[^0-9.]/g,
message: "请输入正确的数字",
}
};
export default valid;