diff --git a/sub-operation-service/src/assets/images/warehouseLogistics/consignee.png b/sub-operation-service/src/assets/images/warehouseLogistics/consignee.png new file mode 100644 index 0000000..5731ba9 Binary files /dev/null and b/sub-operation-service/src/assets/images/warehouseLogistics/consignee.png differ diff --git a/sub-operation-service/src/assets/images/warehouseLogistics/goods.png b/sub-operation-service/src/assets/images/warehouseLogistics/goods.png new file mode 100644 index 0000000..c67c870 Binary files /dev/null and b/sub-operation-service/src/assets/images/warehouseLogistics/goods.png differ diff --git a/sub-operation-service/src/assets/images/warehouseLogistics/shipper.png b/sub-operation-service/src/assets/images/warehouseLogistics/shipper.png new file mode 100644 index 0000000..4c83219 Binary files /dev/null and b/sub-operation-service/src/assets/images/warehouseLogistics/shipper.png differ diff --git a/sub-operation-service/src/views/warehouseLogistics/logistics/detail.vue b/sub-operation-service/src/views/warehouseLogistics/logistics/detail.vue index 01beb65..733ff7e 100644 --- a/sub-operation-service/src/views/warehouseLogistics/logistics/detail.vue +++ b/sub-operation-service/src/views/warehouseLogistics/logistics/detail.vue @@ -2,65 +2,128 @@
@@ -75,15 +138,44 @@ import { logisticDetail } from '@/apis/warehouseLogistics.js'; const route = useRoute(); const router = useRouter(); +import img1 from './images/big-xiangshi.png'; const state = reactive({ query: {}, - data: {}, + data: { + imageUrl: img1, + typeId: 1, + typeName: '普通仓储', + title: '长途大车', + operationUnit: '昌盛伟业运输有限公司 ', + pricingUnit: '元/㎡·月', + storageArea: '8,600㎡', + usableArea: '2,300㎡', + location: '孟定镇中缅大道8号', + price: '¥12元/㎡/月', + contacts: '张强', + contactNumber: '13356846589', + serviceTimes: '206次', + }, + carInfor: { + title: '长途大车', + licensePlate: '云AL6AB7', + conductor: '15m', + vehicleNature: '物流公司', + vehicleModel: '厢式', + maximumPayload: '1000吨', + freeTime: '2025.05.05', + price: '¥20元/吨/公里', + }, }); +const dialogVisible = ref(false); +const reservation = () => { + dialogVisible.value = true; +}; + const toBack = (level) => { router.go(level); }; - const queryDetail = () => { logisticDetail(state.query.id).then((res) => { if (res.code === 200) { @@ -97,10 +189,15 @@ const queryDetail = () => { onMounted(() => { state.query.id = route.query.id; - queryDetail(); + // queryDetail(); }); diff --git a/sub-operation-service/src/views/warehouseLogistics/logistics/images/car1.png b/sub-operation-service/src/views/warehouseLogistics/logistics/images/car1.png new file mode 100644 index 0000000..1019223 Binary files /dev/null and b/sub-operation-service/src/views/warehouseLogistics/logistics/images/car1.png differ diff --git a/sub-operation-service/src/views/warehouseLogistics/logistics/images/car2.png b/sub-operation-service/src/views/warehouseLogistics/logistics/images/car2.png new file mode 100644 index 0000000..5c65181 Binary files /dev/null and b/sub-operation-service/src/views/warehouseLogistics/logistics/images/car2.png differ diff --git a/sub-operation-service/src/views/warehouseLogistics/logistics/images/car3.png b/sub-operation-service/src/views/warehouseLogistics/logistics/images/car3.png new file mode 100644 index 0000000..351f577 Binary files /dev/null and b/sub-operation-service/src/views/warehouseLogistics/logistics/images/car3.png differ diff --git a/sub-operation-service/src/views/warehouseLogistics/logistics/index.vue b/sub-operation-service/src/views/warehouseLogistics/logistics/index.vue index 79dabbf..1e97f4a 100644 --- a/sub-operation-service/src/views/warehouseLogistics/logistics/index.vue +++ b/sub-operation-service/src/views/warehouseLogistics/logistics/index.vue @@ -18,25 +18,20 @@
-
- - - - - - - - +
+ +
-
+
查询 + 在线寄货
diff --git a/sub-operation-service/src/views/warehouseLogistics/logistics/match.vue b/sub-operation-service/src/views/warehouseLogistics/logistics/match.vue index f148081..07bb1e3 100644 --- a/sub-operation-service/src/views/warehouseLogistics/logistics/match.vue +++ b/sub-operation-service/src/views/warehouseLogistics/logistics/match.vue @@ -2,74 +2,82 @@
@@ -79,33 +87,76 @@ import { ref, reactive, watch, onMounted } from 'vue'; import { getAssetsFile } from '@/utils'; import { useRoute, useRouter } from 'vue-router'; import Common from '../components/common.vue'; -import { logisticDetail } from '@/apis/warehouseLogistics.js'; +import { warehouseDetail } from '@/apis/warehouseLogistics.js'; const route = useRoute(); const router = useRouter(); -const state = reactive({ - query: {}, - data: {}, -}); +const tab1 = reactive(['全部', '距离最近', '价格最便宜']); +const currentTab1 = ref(0); +const handleTab1Click = (item, index) => { + currentTab1.value = index; +}; + +import img1 from './images/car1.png'; +import img2 from './images/car2.png'; +import img3 from './images/car3.png'; +const allData = ref([ + { + imageUrl: img1, + title: '长途货车', + operationUnit: '昌盛伟业运输有限公司 ', + phoneNumber: '15684968769', + pricingUnit: '元/㎡·月', + location: '孟定镇中缅大道8号', + cargoVolume: '61.2m³', + price: '¥19元/吨/公里', + distance: '9.1km', + }, + { + imageUrl: img2, + title: '长途货车', + operationUnit: '昌盛伟业运输有限公司', + phoneNumber: '13375869426', + pricingUnit: '元/吨·天', + location: '绿色食品园区二期', + cargoVolume: '63m³', + price: '¥20元/吨/公里', + distance: '10.3km', + }, + { + imageUrl: img3, + title: '长途货车', + operationUnit: '昌盛伟业运输有限公司', + phoneNumber: '15958621375', + pricingUnit: '元/托·月', + location: '耿马糖厂东侧', + cargoVolume: '63m³', + price: '¥20元/吨/公里', + distance: '12.6km', + }, +]); const toBack = (level) => { router.go(level); }; +const param = ref({ + id: '100', +}); const queryDetail = () => { - logisticDetail(state.query.id).then((res) => { + warehouseDetail(param).then((res) => { if (res.code === 200) { - state.data = res.data; - for (let i in state.data) { - state.data[i].tag = state.data[i].tags.split(','); + allData.value = res.data; + for (let i in allData.value) { + allData.value[i].tag = allData.value[i].tags.split(','); } } }); }; onMounted(() => { - state.query.id = route.query.id; + param.value.id = route.query.id ?? '100'; // queryDetail(); }); @@ -116,238 +167,129 @@ onMounted(() => { font-weight: bold; cursor: pointer; } -/* 根据需要添加样式,这里仅提供基础样式 */ -// 基础颜色配置 -$primary-color: #25bf82; // 主色调 -$text-dark: #25bf82; // 深色文字 -$text-regular: #606266; // 常规文字 -$border-color: #dcdfe6; // 边框颜色 -// 弹窗整体样式 -:deep(.custom-inquiry-dialog) { - border-radius: 8px; - box-shadow: 0 4px 12px rgba(0, 0, 0, 0.15); - - .el-dialog__header { - padding: 20px; - border-bottom: 1px solid #f2f6fc; - .el-dialog__title { - font-size: 18px; - color: $text-dark; - font-weight: 600; - } - } - - .el-dialog__body { - padding: 20px 28px; - } - - .el-form-item__label { - color: $text-regular; - font-size: 14px; - padding-bottom: 6px; - } -} - -.info-section { - padding: 0px 50px; - margin-bottom: 24px; - .info-item { - margin-bottom: 12px; - .label { - color: $text-regular; - margin-right: 8px; - font-size: 20px; - } - .value { - color: $text-dark; - font-weight: 500; - font-size: 20px; - } - } -} - -// 输入框样式覆盖 -:deep(.el-input) { - .el-input__inner { - height: 40px; - line-height: 40px; - border-radius: 4px; - &:focus { - border-color: $primary-color; - } - } - .el-input__suffix { - color: $text-regular; - right: 12px; - } -} - -// 下拉菜单样式 -:deep(.custom-select-dropdown) { - .el-select-dropdown__item { - color: $text-regular; - &.selected { - color: $primary-color; - } - } -} - -// 按钮组样式 -.dialog-footer { - text-align: right; - .el-button { - padding: 10px 24px; - border-radius: 4px; - font-size: 14px; - } - .cancel-btn { - color: $text-regular; - &:hover { - color: $primary-color; - border-color: $primary-color; - } - } - .submit-btn { - color: #fff; - background: $primary-color; - &:hover { - background: mix($primary-color, #fff, 85%); - } - } -} -.bac { - background: rgba(37, 191, 130, 0.1); - border: 1px solid rgba(37, 191, 130, 0.5); - border-radius: 8px; - padding: 2px 5px; -} - -.image-box { - width: 300px; - height: 300px; -} - -.text-gray-500 { - height: 300px; - display: flex; - flex-direction: column; - justify-content: space-between; - align-items: start !important; - font-size: 20px !important; - color: #000000 !important; - padding-top: 30px; -} - -.text-gray-600 { - font-size: 20px; - color: #000000 !important; -} - -.flex-1 { - width: 40%; - height: 300px; - flex-direction: column; - display: flex; - align-items: flex-start; - justify-content: space-evenly; -} - -.max-w-7xl { - max-width: 80rem; +.storage-content { + padding: 20px 20px 0 20px; + margin-top: 20px; + border-radius: 14px; background-color: #fff; - border-radius: 10px; - .storage-image { - width: 100%; +} +.content-custom-title { + font-size: 20px; + font-weight: bold; + text-align: left; + margin-bottom: 10px; +} + +.tabs { + //height: 160px; + line-height: 50px; + display: flex; + flex-direction: column; + font-size: 18px; + align-items: flex-start; + justify-content: space-between; + margin-bottom: 10px; +} +.tabs0 { + padding: 0; +} +.tab { + // height: 100px; + width: 850px; + display: flex; + align-items: center; + justify-content: flex-start; + overflow-x: auto; + overflow: auto; /* 启用滚动 */ + white-space: nowrap; /* 强制单行显示 */ + -ms-overflow-style: none; /* IE/Edge 兼容 */ + scrollbar-width: none; /* 隐藏滚动条 */ + .tab_list { + color: #999999; + font-size: 20px; + font-weight: 400; + } + .tab_list_li { + margin-left: 40px; + color: #666; + font-size: 18px; + font-weight: 400; + transition: color 0.3s ease; + } + .tab_list_li:first-child { + margin-left: 0px; + } + .tab_list_li.active { + color: #25bf82; + font-weight: bold; } } - -.mx-auto { - margin-left: auto; - margin-right: auto; +.cursor { + cursor: pointer; } - -.p-4 { - padding: 1rem; - padding-bottom: 0; -} - -.flex { - display: flex; -} - -.items-center { - align-items: center; -} - -.mb-4 { - margin-bottom: 1rem; -} - -.mr-4 { - margin-right: 1rem; -} - -.text-green-500 { +.active { color: #25bf82; + font-weight: bold; } -.text-lg { - font-size: 1.125rem; +.resource-item { + width: 100%; + min-height: 300px; + display: flex; + flex-direction: column; + margin-bottom: 20px; text-align: left; -} - -.font-bold { - font-weight: 700; -} - -.rounded-lg { - border-radius: 0.5rem; - background-color: #f5f5f5; -} - -.shadow { - box-shadow: - 0 4px 6px -1px rgba(0, 0, 0, 0.1), - 0 2px 4px -1px rgba(0, 0, 0, 0.06); -} - -.text-xl { - font-size: 24px; -} - -.text-gray-600 { - color: #757575; -} - -.text-gray-700 { - color: #000000; - font-size: 18px; -} - -.text-sm { - font-size: 0.875rem; -} - -.space-x-2 { - gap: 0.5rem; -} - -.bg-green-500 { - background-color: #4caf50; -} - -.py-2 { - padding-top: 0.5rem; - padding-bottom: 0.5rem; -} - -.px-4 { - padding-left: 1rem; - padding-right: 1rem; -} - -.mt-4 { - margin-top: 1rem; + .resource-item-img { + width: 100%; + height: 250px; + border-radius: 14px; + position: relative; + overflow: hidden; + background-color: rgb(102 102 102 / 10%); + img { + position: absolute; + top: 50%; + left: 50%; + transform: translate(-50%, -50%); + min-width: 100%; + min-height: 100%; + object-fit: cover; + } + } + .center-title { + color: #666; + font-size: 18px; + font-weight: bold; + text-align: left; + margin-top: 10px; + margin-bottom: 10px; + .highlight { + color: #25bf82; + } + } + .resource-custom-text { + margin-bottom: 10px; + font-size: 16px; + color: #25bf82; + } + .center-text { + font-size: 16px; + display: flex; + margin-bottom: 10px; + .center-text-lable { + color: #666; + width: 86px; + line-height: 20px; + } + .flex-1 { + flex: 1; + line-height: 20px; + text-align: left; + overflow: hidden; + white-space: nowrap; + text-overflow: ellipsis; + } + } } diff --git a/sub-operation-service/src/views/warehouseLogistics/logistics/shipping.vue b/sub-operation-service/src/views/warehouseLogistics/logistics/shipping.vue index 0b8f2d2..dcef41a 100644 --- a/sub-operation-service/src/views/warehouseLogistics/logistics/shipping.vue +++ b/sub-operation-service/src/views/warehouseLogistics/logistics/shipping.vue @@ -2,72 +2,155 @@
@@ -78,6 +161,8 @@ import { getAssetsFile } from '@/utils'; import { useRoute, useRouter } from 'vue-router'; import Common from '../components/common.vue'; import { logisticDetail } from '@/apis/warehouseLogistics.js'; +import { ElMessage } from 'element-plus'; +import { getRegion } from '@/apis/common'; const route = useRoute(); const router = useRouter(); @@ -87,7 +172,226 @@ const state = reactive({ data: {}, }); -const application = () => { +const unifiedWidth = '300px'; +const formSize = 'large'; +const formRef = ref(null); +const formInline = reactive({ + shipperName: '', //发货人 + shipperPhone: '', //联系电话 + selectedAddress: [], //选中的区域(编码数组) + detailAddress: '', //详细地址 + + consigneeName: '', //收货人姓名 + consigneePhone: '', //收货人电话 + consigneeArea: '', //收货人区域(编码数组) + consigneeAddress: '', //收货人详细地址 + + goodsName: '', //货物名称 + goodsType: '', //货物类型 + goodsWeight: '', //货物重量 + goodsVolume: '', //货物体积 + goodsQuantity: '', //货物数量 + goodsHeight: '', //货物高度 + goodsLength: '', //货物长度 +}); +const dialogRules = reactive({ + // 发货人信息 + shipperName: [ + { required: true, message: '请输入发货人姓名', trigger: 'blur' }, + { min: 2, max: 20, message: '姓名长度在2到20个字符', trigger: 'blur' }, + ], + shipperPhone: [ + { required: true, message: '请输入发货人电话', trigger: 'blur' }, + { + pattern: /^1[3-9]\d{9}$|^0\d{2,3}-?\d{7,8}$/, + message: '请输入正确的手机号或固话(如010-12345678)', + trigger: 'blur', + }, + ], + + // 发货地址(级联选择器+详细地址) + selectedAddress: [ + { + required: true, + validator: (_, value, callback) => { + if (!value || value.length !== 3) { + callback(new Error('请选择完整的省市区')); + } else { + callback(); + } + }, + trigger: 'change', + }, + ], + detailAddress: [ + { required: true, message: '请输入详细地址', trigger: 'blur' }, + { min: 3, max: 100, message: '地址长度在3到100个字符', trigger: 'blur' }, + ], + + // 收货人信息 + consigneeName: [ + { required: true, message: '请输入收货人姓名', trigger: 'blur' }, + { min: 2, max: 20, message: '姓名长度在2到20个字符', trigger: 'blur' }, + ], + consigneePhone: [ + { required: true, message: '请输入收货人电话', trigger: 'blur' }, + { + pattern: /^1[3-9]\d{9}$|^0\d{2,3}-?\d{7,8}$/, + message: '请输入正确的手机号或固话(如010-12345678)', + trigger: 'blur', + }, + ], + + // 收货地址(级联选择器+详细地址) + consigneeArea: [ + { + required: true, + validator: (_, value, callback) => { + if (!value || value.length !== 3) { + callback(new Error('请选择完整的省市区')); + } else { + callback(); + } + }, + trigger: 'change', + }, + ], + consigneeAddress: [ + { required: true, message: '请输入详细地址', trigger: 'blur' }, + { min: 3, max: 100, message: '地址长度在3到100个字符', trigger: 'blur' }, + ], + + // 货物信息 + goodsName: [ + { required: true, message: '请输入货物名称', trigger: 'blur' }, + { min: 2, max: 50, message: '名称长度在2到50个字符', trigger: 'blur' }, + ], + goodsType: [{ required: true, message: '请选择货物类型', trigger: 'change' }], + goodsWeight: [ + { + required: true, + validator: (_, value, callback) => { + if (!value) { + callback(new Error('请输入货物重量')); + } else if (!/^\d+(\.\d{1,2})?$/.test(value)) { + callback(new Error('请输入有效数字(最多两位小数)')); + } else if (Number(value) <= 0) { + callback(new Error('重量必须大于0')); + } else { + callback(); + } + }, + trigger: 'blur', + }, + ], + goodsVolume: [ + { + required: true, + validator: (_, value, callback) => { + if (!value) { + callback(new Error('请输入货物体积')); + } else if (value && !/^\d+(\.\d{1,2})?$/.test(value)) { + callback(new Error('请输入有效数字(最多两位小数)')); + } else { + callback(); + } + }, + trigger: 'blur', + }, + ], + goodsQuantity: [ + { + required: true, + validator: (_, value, callback) => { + if (!value) { + callback(new Error('请输入货物数量')); + } else if (!/^\d+$/.test(value)) { + callback(new Error('请输入正整数')); + } else if (Number(value) <= 0) { + callback(new Error('数量必须大于0')); + } else { + callback(); + } + }, + trigger: 'blur', + }, + ], + goodsHeight: [ + { + required: true, + validator: (_, value, callback) => { + if (!value) { + callback(new Error('请输入货物高度')); + } else if (value && !/^\d+(\.\d{1,2})?$/.test(value)) { + callback(new Error('请输入有效数字(最多两位小数)')); + } else if (value && Number(value) <= 0) { + callback(new Error('高度必须大于0')); + } else { + callback(); + } + }, + trigger: 'blur', + }, + ], + goodsLength: [ + { + required: true, + validator: (_, value, callback) => { + if (!value) { + callback(new Error('请输入货物长度')); + } else if (value && !/^\d+(\.\d{1,2})?$/.test(value)) { + callback(new Error('请输入有效数字(最多两位小数)')); + } else if (value && Number(value) <= 0) { + callback(new Error('长度必须大于0')); + } else { + callback(); + } + }, + trigger: 'blur', + }, + ], +}); +const resetForm = ref({ ...formInline }); +// 级联选择器配置 +const cascaderProps = ref({ + label: 'areaName', // 选项标签字段名 + value: 'areaCode', // 选项值字段名 + children: 'areaChildVOS', // 子选项字段名 + emitPath: true, + expandTrigger: 'hover', +}); +// 省市区数据(示例) +const addressOptions = ref([]); +const getArea = async () => { + const res = await getRegion(); + if (res.code === 200) { + addressOptions.value = res.data; + } else { + ElMessage.error(res.message); + } +}; +const goodsList = ref([ + { + id: 1, + name: '普通货物', + }, + { + id: 2, + name: '特殊货物', + }, + { + id: 3, + name: '冷藏货物', + }, +]); + +const application = async () => { + // await formRef.value.validate(); + // ElMessage.success('提交成功'); + // console.log(formInline); + // 发起请求 + + // 请求返回成功后跳转(资源分配)页面 router.push({ name: 'logistics-match', }); @@ -111,9 +415,15 @@ const queryDetail = () => { onMounted(() => { state.query.id = route.query.id; // queryDetail(); + getArea(); }); diff --git a/sub-operation-service/src/views/warehouseLogistics/warehouse/allocation.vue b/sub-operation-service/src/views/warehouseLogistics/warehouse/allocation.vue index 2be9280..bf0dcdb 100644 --- a/sub-operation-service/src/views/warehouseLogistics/warehouse/allocation.vue +++ b/sub-operation-service/src/views/warehouseLogistics/warehouse/allocation.vue @@ -8,7 +8,7 @@ > 发布需求 > - 资源分配 + 资源匹配
耿马县农业公司
@@ -96,7 +96,7 @@ import { warehouseDetail } from '@/apis/warehouseLogistics.js'; const route = useRoute(); const router = useRouter(); -const tab1 = reactive(['全部', '距离最近仓储', '价格最便宜仓储']); +const tab1 = reactive(['全部', '距离最近', '价格最便宜']); const currentTab1 = ref(0); const handleTab1Click = (item, index) => { currentTab1.value = index; @@ -227,7 +227,7 @@ onMounted(() => { font-size: 18px; align-items: flex-start; justify-content: space-between; - // padding: 0 20px; + margin-bottom: 10px; } .tabs0 { padding: 0; @@ -299,6 +299,7 @@ onMounted(() => { font-size: 18px; font-weight: bold; text-align: left; + margin-top: 10px; margin-bottom: 10px; .highlight { color: #25bf82;