main
张同海 1 year ago
parent 6d9f6fa2ea
commit a7de1cd841

@ -8,8 +8,15 @@
"lint": "vue-cli-service lint"
},
"dependencies": {
"axios": "^1.4.0",
"core-js": "^3.8.3",
"vue": "^3.2.13"
"element-plus": "^2.3.9",
"node-sass": "^9.0.0",
"sass": "^1.66.1",
"sass-loader": "^13.3.2",
"vue": "^3.2.13",
"vue-router": "^4.2.4",
"vuex": "^4.1.0"
},
"devDependencies": {
"@babel/core": "^7.12.16",

@ -1,26 +1,31 @@
<template>
<img alt="Vue logo" src="./assets/logo.png">
<HelloWorld msg="Welcome to Your Vue.js App"/>
<div>
<router-view></router-view>
</div>
</template>
<script>
import HelloWorld from './components/HelloWorld.vue'
// import { GetSASCCODE } from "./api/Index";
export default {
name: 'App',
components: {
HelloWorld
}
}
name: "App",
components: {},
methods: {
// FnApi() {
// GetSASCCODE().then((res) => {
// console.log(res);
// });
// },
},
};
</script>
<style>
#app {
* {
font-family: Avenir, Helvetica, Arial, sans-serif;
-webkit-font-smoothing: antialiased;
-moz-osx-font-smoothing: grayscale;
text-align: center;
color: #2c3e50;
margin-top: 60px;
/* font-size: 16px; */
margin: 0px;
padding: 0px;
}
</style>

@ -0,0 +1,20 @@
<template>
<h1 @click="FnClick">{{ name }}</h1>
</template>
<script>
import { ref } from "vue";
export default {
name: "ViewAbout",
setup(msg) {
console.log(msg);
const name = ref("About");
const FnClick = () => {
console.log(name.value);
};
return {
name,
FnClick,
};
},
};
</script>

@ -0,0 +1,741 @@
<template>
<div class="BookingAddMain">
<div class="BookingAddButtonBox">
<el-button type="primary" @click="ClickSave"> </el-button>
<el-button
type="primary"
plain
v-if="viweType == 'Edit'"
@click="ClickCopy"
>
复制
</el-button>
<el-button type="primary" plain> 存为模板 </el-button>
<el-button type="primary" plain> 状态历史 </el-button>
<el-button type="danger" v-if="viweType == 'Edit'" @click="ClicDelete">
删除
</el-button>
<el-button type="primary" plain v-if="viweType == 'Edit'">
发送订舱
</el-button>
</div>
<el-form class="FormBox" :model="form" label-width="90px">
<el-row>
<el-col :span="11" class="FormBoxUnit">
<el-row>
<el-col :span="24">
<p><span> </span>订单信息</p>
</el-col>
<el-col :span="8">
<el-form-item label="船公司">
<el-select
v-model="form.carrierCode"
:style="{ width: '100%' }"
@change="ChangecarrierCode"
>
<el-option
v-for="item in store.state.Data.Carrierlist"
:key="item.code"
:label="item.name"
:value="item.code"
/>
</el-select>
</el-form-item>
</el-col>
<el-col :span="8">
<el-form-item label="起运港">
<el-select
v-model="form.portLoadingCode"
:style="{ width: '100%' }"
@change="
(e) => {
store.state.Data.portloadlist.forEach((i) => {
if (e == i.code) {
form.portLoading = i.name;
}
});
}
"
>
<el-option
v-for="item in store.state.Data.portloadlist"
:key="item.code"
:label="item.name"
:value="item.code"
/>
</el-select>
</el-form-item>
</el-col>
<el-col :span="8">
<el-form-item label="目的地">
<el-select
v-model="form.portDischargeCode"
:style="{ width: '100%' }"
@change="
(e) => {
store.state.Data.portlist.forEach((i) => {
if (e == i.code) {
form.portDischarge = i.name;
}
});
}
"
>
<el-option
v-for="item in store.state.Data.portlist"
:key="item.code"
:label="item.name"
:value="item.code"
/>
</el-select>
</el-form-item>
</el-col>
<el-col :span="8">
<el-form-item label="开船日期">
<el-date-picker v-model="form.etd" type="date">
</el-date-picker>
</el-form-item>
</el-col>
<el-col :span="8">
<el-form-item label="船名">
<el-input v-model="form.vessel" />
<!-- <el-select v-model="form.vessel" :style="{ width: '100%' }">
<el-option
v-for="item in store.state.Data.vessellist"
:key="item.name"
:label="item.name"
:value="item.name"
/>
</el-select> -->
</el-form-item>
</el-col>
<el-col :span="8">
<el-form-item label="航次">
<el-input v-model="form.voyNoInner" />
</el-form-item>
</el-col>
<el-col :span="8">
<el-form-item label="约号">
<el-input v-model="form.contractNo" />
</el-form-item>
</el-col>
<el-col :span="8">
<el-form-item label="运输条款">
<el-select
v-model="form.transportClause"
:style="{ width: '100%' }"
>
<el-option
v-for="item in store.state.Data.servicelist"
:key="item.code"
:label="item.name"
:value="item.code"
/>
</el-select>
</el-form-item>
</el-col>
<el-col :span="8">
<el-form-item label="付费方式">
<el-select
v-model="form.paymentType"
:style="{ width: '100%' }"
>
<el-option
v-for="item in store.state.Data.frtlist"
:key="item.code"
:label="item.name"
:value="item.code"
/>
</el-select>
</el-form-item>
</el-col>
</el-row>
</el-col>
<el-col :span="12" class="FormBoxUnit">
<el-row>
<el-col :span="24">
<p><span> </span>所需服务项</p>
</el-col>
<el-checkbox-group
v-model="serviceItemList"
@change="
(e) => {
let RData = [];
console.log(e);
store.state.Data.cobServiceItemTenantList.forEach((item) => {
e.forEach((item2) => {
if (item.serviceCode == item2) {
RData.push({
code: item.serviceCode,
value: item.serviceName,
});
}
});
});
form.serviceItemList = RData;
}
"
>
<el-checkbox
v-for="item in store.state.Data.cobServiceItemTenantList"
:key="item.serviceCode"
:label="item.serviceCode"
>
{{ item.serviceName }}
</el-checkbox>
</el-checkbox-group>
</el-row>
</el-col>
<el-col :span="11" class="FormBoxUnit">
<el-row>
<el-col :span="24">
<p><span> </span>订舱信息</p>
</el-col>
<el-col :span="8">
<el-form-item label="发货人">
<el-input v-model="form.shipperCode" />
</el-form-item>
</el-col>
<el-col :span="8">
<el-form-item label-width="20">
<OpenBT :type="20" @SelectData="SelectData" />
</el-form-item>
</el-col>
<el-col :span="24">
<el-form-item>
<el-input v-model="form.shipper" :rows="4" type="textarea" />
</el-form-item>
</el-col>
<el-col :span="8">
<el-form-item label="收货人">
<el-input v-model="form.consigneeCode" />
</el-form-item>
</el-col>
<el-col :span="8">
<el-form-item label-width="20">
<OpenBT :type="10" @SelectData="SelectData" />
</el-form-item>
</el-col>
<el-col :span="24">
<el-form-item>
<el-input v-model="form.consignee" :rows="4" type="textarea" />
</el-form-item>
</el-col>
<el-col :span="8">
<el-form-item label="通知人">
<el-input v-model="form.notifyPartyCode" />
</el-form-item>
</el-col>
<el-col :span="8">
<el-form-item label-width="20">
<OpenBT :type="30" @SelectData="SelectData" />
</el-form-item>
</el-col>
<el-col :span="24">
<el-form-item>
<el-input
v-model="form.notifyParty"
:rows="4"
type="textarea"
/>
</el-form-item>
</el-col>
<!-- <el-col :span="8">
<el-form-item label="品名">
<el-input v-model="form.name" />
</el-form-item>
</el-col> -->
<!-- <el-col :span="16">
<el-form-item>
<el-input v-model="form.name" :rows="4" type="textarea" />
</el-form-item>
</el-col> -->
<el-col :span="24">
<el-form-item label="订舱要求">
<el-input v-model="form.soRemark" :rows="4" type="textarea" />
</el-form-item>
</el-col>
<el-col :span="24"></el-col>
<el-col :span="24"></el-col>
<el-col :span="24"></el-col>
</el-row>
</el-col>
<el-col :span="12" class="FormBoxUnit">
<el-row>
<el-col :span="24">
<p><span> </span>货物信息</p>
</el-col>
<el-col :span="8">
<el-form-item label="货物类型">
<!-- <el-input v-model="form.cargoId" /> -->
<el-select
v-model="form.cargoId"
:style="{ width: '100%' }"
@change="ChangeCargoId"
>
<el-option
v-for="item in cargoIdData"
:key="item.code"
:label="item.name"
:value="item.code"
/>
</el-select>
</el-form-item>
</el-col>
<el-col :span="8">
<el-form-item label="HS编码">
<el-input v-model="form.hcCode" />
</el-form-item>
</el-col>
<el-col :span="8">
<el-form-item label="毛重">
<el-input v-model="form.kgs">
<template #append>KGS</template>
</el-input>
</el-form-item>
</el-col>
<el-col :span="8">
<el-form-item label="尺寸">
<el-input v-model="form.cbm">
<template #append>CBM</template>
</el-input>
</el-form-item>
</el-col>
<el-col :span="8">
<el-form-item label="包装">
<!-- <el-input v-model="form.kindPkgs" /> -->
<el-select v-model="form.kindPkgs" :style="{ width: '100%' }">
<el-option
v-for="item in store.state.Data.packagelist"
:key="item.code"
:label="item.name"
:value="item.code"
/>
</el-select>
</el-form-item>
</el-col>
<el-col :span="8">
<el-form-item label="件数">
<el-input v-model="form.pkgs" />
</el-form-item>
</el-col>
<template v-if="form.cargoId == 'R'">
<el-col :span="24">
<span class="cargoS">冻柜信息</span>
</el-col>
<el-col :span="8">
<el-form-item label="温度">
<el-input v-model="form.cargoData.temperature" />
</el-form-item>
</el-col>
<el-col :span="8">
<el-form-item label="最低温度">
<el-input v-model="form.cargoData.minTemperature" />
</el-form-item>
</el-col>
<el-col :span="8">
<el-form-item label="最高温度">
<el-input v-model="form.cargoData.maxTemperature" />
</el-form-item>
</el-col>
<el-col :span="8">
<el-form-item label="通风量">
<el-input v-model="form.cargoData.ventilationRate" />
</el-form-item>
</el-col>
<el-col :span="8">
<el-form-item label="温度单位">
<!-- <el-input v-model="form.cargoData.temperatureUnit" /> -->
<el-select
v-model="form.cargoData.temperatureUnit"
:style="{ width: '100%' }"
>
<el-option label="摄氏" value="C" />
<el-option label="华氏" value="F" />
</el-select>
</el-form-item>
</el-col>
<!-- <el-col :span="8">
<el-form-item label="通风口开关">
<el-input v-model="form.cargoData." />
</el-form-item>
</el-col> -->
</template>
<template v-else-if="form.cargoId == 'D'">
<el-col :span="24">
<span class="cargoS">危险品信息</span>
</el-col>
<el-col :span="8">
<!-- CLASS(危险品分类) -->
<el-form-item label="类别">
<el-input v-model="form.cargoData.dangerClass" />
</el-form-item>
</el-col>
<!-- UN NO (危险品编号) -->
<el-col :span="8">
<el-form-item label="标签">
<el-input v-model="form.cargoData.dangerLable" />
</el-form-item>
</el-col>
<el-col :span="8">
<el-form-item label="联系电话">
<el-input v-model="form.cargoData.dangerLineTel" />
</el-form-item>
</el-col>
<el-col :span="8">
<el-form-item label="联系人">
<el-input v-model="form.cargoData.dangerLinkMan" />
</el-form-item>
</el-col>
<el-col :span="8">
<el-form-item label="页号">
<el-input v-model="form.cargoData.dangerPage" />
</el-form-item>
</el-col>
<el-col :span="8">
<el-form-item label="编号">
<el-input v-model="form.cargoData.dangerUnNo" />
</el-form-item>
</el-col>
</template>
<template v-else-if="form.cargoId == 'O'">
<el-col :span="24">
<span class="cargoS">超限货物OOG信息</span>
</el-col>
<el-col :span="8">
<el-form-item label="箱高">
<el-input v-model="form.cargoData.limitedContainerHeight" />
</el-form-item>
</el-col>
<el-col :span="8">
<el-form-item label="箱长">
<el-input v-model="form.cargoData.limitedContainerLength" />
</el-form-item>
</el-col>
<el-col :span="8">
<el-form-item label="箱宽">
<el-input v-model="form.cargoData.limitedContainerWidth" />
</el-form-item>
</el-col>
</template>
<el-col :span="24">
<el-form-item label="箱型数量">
<div>
<el-table
border
:data="form.ctnList"
style="width: 100%"
max-height="200"
>
<el-table-column
type="index"
label="序号"
width="60"
align="center"
/>
<el-table-column prop="ctnCode" label="箱型" width="180">
<template #default="scope">
<!-- <el-input v-model="scope.row.ctnCode" /> -->
<el-select
v-model="scope.row.ctnCode"
:style="{ width: '100%' }"
@change="
(e) => {
store.state.Data.Ctnlist.forEach((i) => {
if (e == i.code) {
scope.row.cntName = i.name;
}
});
}
"
>
<el-option
v-for="item in store.state.Data.Ctnlist"
:key="item.code"
:label="item.name"
:value="item.code"
/>
</el-select>
</template>
</el-table-column>
<el-table-column prop="ctnNum" label="数量">
<template #default="scope">
<el-input v-model="scope.row.ctnNum" />
</template>
</el-table-column>
<el-table-column
prop="address"
label="操作"
width="60"
align="center"
>
<template #default="scope">
<el-button
link
type="primary"
size="small"
@click="handleClick(scope)"
>
删除
</el-button>
</template>
</el-table-column>
</el-table>
</div>
</el-form-item>
<el-button
type="primary"
link
:style="{
marginLeft: '120px',
}"
@click="TableAdd"
>
<el-icon><Plus /></el-icon>
</el-button>
</el-col>
<!-- <el-col :span="5">
<el-upload
v-model:file-list="fileList"
class="upload-demo"
multiple
:limit="3"
:http-request="uploadApi"
>
<el-button type="primary">
<el-icon><UploadFilled /></el-icon>
上传文件
</el-button>
</el-upload>
</el-col> -->
</el-row>
</el-col>
</el-row>
</el-form>
</div>
</template>
<script>
import { onMounted, ref } from "vue";
import {
bookingCustomSave,
bookingCustomInfo,
Uploader,
bookingCustomDelete,
} from "@/api/Index";
import { useRouter } from "vue-router";
import { ElMessage } from "element-plus";
import { cargoIdData } from "./initData";
import OpenBT from "./OpenBT.vue";
import { useStore } from "vuex";
export default {
naem: "ViewBookingAdd",
components: {
OpenBT,
},
setup() {
console.log("setup");
const store = useStore();
const router = useRouter();
const form = ref({
name: "",
region: "",
date1: "",
date2: "",
delivery: false,
type: [],
resource: "",
desc: "",
ctnList: [],
});
const serviceItemList = ref([]);
store.state.Data.cobServiceItemTenantList.forEach((item) => {
console.log(item);
if (item.defaultSelected == 1) {
serviceItemList.value.push(item.serviceCode);
form.value.serviceItemList.push({
code: item.serviceCode,
value: item.serviceName,
});
}
});
const viweType = ref("");
onMounted(() => {
let query = router.currentRoute.value.query;
viweType.value = query.type;
if (query.type == "Edit" || query.type == "Copy") {
bookingCustomInfo({ id: query.id }).then((res) => {
form.value = { ...res.data };
if (query.type == "Copy") {
delete form.value.id;
}
});
}
});
const handleClick = (data) => {
setTimeout(() => {
form.value.ctnList.splice(data.$index, 1);
}, 100);
};
const TableAdd = () => {
console.log("TableAdd");
setTimeout(() => {
form.value.ctnList.push({});
}, 100);
};
const ClickSave = () => {
console.log(form.value);
let ApiData = form.value;
ApiData = { ...ApiData, ...form.value.cargoData };
bookingCustomSave(ApiData).then((res) => {
if (res.code == 200) {
console.log(res);
ElMessage({
message: "保存成功",
type: "success",
});
router.push("/Booking");
}
});
};
const fileList = ref([]);
const uploadApi = (param) => {
let formData = new FormData();
formData.append("file", param.file);
Uploader(formData).then((res) => {
console.log(res.data);
});
};
const ClickCopy = () => {
delete form.value.id;
viweType.value = "Copy";
};
const ClicDelete = () => {
bookingCustomDelete({ id: form.value.id }).then((res) => {
if (res.code == 200) {
console.log(res);
ElMessage({
message: "删除成功",
type: "success",
});
router.push("/Booking");
}
});
};
const ChangeCargoId = () => {
form.value.cargoData = {};
};
const ChangecarrierCode = (e) => {
store.state.Data.Carrierlist.forEach((item) => {
if (item.code == e) {
form.value.carrier = item.name;
}
});
};
const SelectData = (e) => {
console.log(e.type.value);
switch (e.type.value) {
case 10:
form.value.consigneeCode = e.Data[0].title;
form.value.consignee = e.Data[0].content;
break;
case 20:
form.value.shipperCode = e.Data[0].title;
form.value.shipper = e.Data[0].content;
break;
case 30:
form.value.notifyPartyCode = e.Data[0].title;
form.value.notifyParty = e.Data[0].content;
break;
default:
form.value.notifyPartySecondCode = e.Data[0].title;
form.value.notifyPartySecond = e.Data[0].content;
break;
}
};
return {
store,
form,
serviceItemList,
handleClick,
TableAdd,
ClickSave,
fileList,
uploadApi,
viweType,
ClickCopy,
ClicDelete,
cargoIdData,
ChangeCargoId,
ChangecarrierCode,
SelectData,
};
},
};
</script>
<style lang="scss" scoped>
.BookingAddMain {
height: calc(100vh - 130px);
box-sizing: border-box;
.BookingAddButtonBox {
margin-bottom: 22px;
}
.FormBox {
height: calc(100% - 70px);
padding: 0 10px;
overflow-y: auto;
.FormBoxUnit {
background: #ffffff;
border: 1px solid #eaf0f7;
box-shadow: 0 5px 10px -10px rgba(0, 0, 0, 0.2);
border-radius: 10px;
padding: 10px 20px;
margin: 5px;
p {
margin-left: 20px;
margin-bottom: 10px;
span {
display: inline-block;
width: 3px;
height: 12px;
background: #409eff;
margin-right: 5px;
}
}
}
}
}
</style>
<style>
.el-collapse {
position: relative;
border: none !important;
}
.el-collapse-item__wrap {
border: none !important;
}
.el-collapse .el-collapse-item__header {
margin-bottom: 20px;
padding-left: 37px;
background: #eff6fd;
font-family: PingFangSC-Medium;
font-size: 16px;
color: rgba(0, 0, 0, 0.88);
line-height: 28px;
font-weight: bold;
}
.el-collapse .el-collapse-item__header i {
position: absolute;
left: 10px;
color: #107ef2;
}
.cargoS {
font-size: 12px;
color: #c9c9c9;
margin-left: 23px;
}
</style>

@ -0,0 +1,131 @@
<template>
<el-popover
:visible="visible"
placement="right"
:width="600"
trigger="click"
@show="FnShow"
ref="popoverRef"
>
<template #reference>
<el-button
type="primary"
@click="
() => {
visible = true;
}
"
>{{ Text() }}</el-button
>
</template>
<el-row :gutter="20">
<el-col :span="12">
<el-input v-model="Name" placeholder="请输入名称"></el-input>
</el-col>
<el-col :span="8">
<el-button @click="FnShow"></el-button>
</el-col>
</el-row>
<el-table ref="OpenTBTable" :data="gridData" height="300">
<el-table-column type="selection" width="55" />
<el-table-column property="title" label="代码" />
<el-table-column property="name" label="名称" />
<el-table-column property="addr" label="地址" />
<el-table-column property="countryName" label="国家" />
<el-table-column property="remark" label="备注" />
<el-table-column property="tel" label="电话" />
</el-table>
<el-row>
<el-col :span="6" :offset="18">
<el-button
type="primary"
size="small"
:style="{ marginTop: '10px' }"
@click="SData"
>
确定
</el-button>
<el-button
type="primary"
size="small"
:style="{ marginTop: '10px' }"
@click="
() => {
visible = false;
}
"
>
取消
</el-button>
</el-col>
</el-row>
</el-popover>
</template>
<script>
import { ref } from "vue";
import { bookingTemplateList } from "@/api/Index";
import { ElMessage } from "element-plus";
export default {
naem: "ViewOpenBT",
props: ["type"],
setup(props, ctx) {
const popoverRef = ref("");
const Type = ref(props.type);
const Name = ref("");
const gridData = ref([]);
const OpenTBTable = ref();
const visible = ref(false);
const Text = () => {
let RData = "";
switch (Type.value) {
case 10:
RData = "常用收货人";
break;
case 20:
RData = "常用发货人";
break;
case 30:
RData = "常用通知人";
break;
default:
RData = "常用第二通知人";
break;
}
return RData;
};
const FnShow = () => {
bookingTemplateList({
type: Type.value,
pageSize: 999,
name: Name.value,
}).then((res) => {
gridData.value = res.data.list;
console.log(res);
});
};
const SData = () => {
let SData = OpenTBTable.value.getSelectionRows();
if (SData.length == 1) {
ctx.emit("SelectData", { Data: SData, type: Type });
visible.value = false;
} else {
ElMessage({
message: "请选择一条数据",
type: "warning",
});
}
};
return {
popoverRef,
Type,
Name,
gridData,
OpenTBTable,
visible,
Text,
FnShow,
SData,
};
},
};
</script>

@ -0,0 +1,238 @@
<template>
<div class="BookingMain">
<SearchBox
ref="SearchBox"
:SearchData="SearchBoxData"
@ClickSearch="ClickSearch"
@SearchOpen="SearchOpen"
/>
<TableBox
ref="TableBoxRef"
:TableData="TableData"
:ListApi="ListApi"
:SearchData="SearchData"
:ButtonData="ButtonData"
@ClickAdd="ClickAdd"
@ClickDelete="ClickDelete"
@ClickCopy="ClickCopy"
/>
</div>
</template>
<script>
import SearchBox from "@/components/SearchBox.vue";
import TableBox from "@/components/TableBox.vue";
import { Plus } from "@element-plus/icons-vue";
import { bookingCustomList, bookingCustomDelete } from "@/api/Index";
import { useRouter } from "vue-router";
import { ref, reactive } from "vue";
import { ElMessage } from "element-plus";
import { useStore } from "vuex";
export default {
name: "ViewBooking",
components: {
SearchBox,
TableBox,
},
setup() {
const store = useStore();
const bizStatusList = [
{ code: "0", name: "已录入" },
{ code: "1", name: "已审核" },
{ code: "3", name: "已提交" },
{ code: "4", name: "已驳回" },
];
const SearchBoxData = reactive([
{
title: "订舱编号",
EType: "Input",
DName: "billNo",
},
{
title: "业务状态",
EType: "Select",
DName: "bizStatus",
SelectList: bizStatusList,
},
{
title: "船公司",
EType: "Select",
DName: "carrierCode",
SelectList: store.state.Data.Carrierlist,
},
{
title: "开船日期",
EType: "DatePicker",
DName: "etdBegin",
DName2: "etdEnd",
},
{
title: "订舱日期",
EType: "DatePicker",
DName: "createTimeBegin",
DName2: "createTimeEnd",
},
]);
const TableData = reactive([
{
width: "55",
type: "selection",
},
{
label: "业务状态",
prop: "bizStatus",
width: "100",
StateChange: [
{
code: "0",
name: "已录入",
},
{
code: "1",
name: "已审核",
},
{
code: "3",
name: "已提交",
},
{
code: "4",
name: "已驳回",
},
],
},
{ label: "订舱编号", prop: "billNo" },
{ label: "船公司", prop: "carrier" },
{ label: "箱型*箱量", prop: "containerTotalInfo" },
{ label: "开船时间", prop: "etd" },
{ label: "付费方式", prop: "paymentType" },
{ label: "货物标识", prop: "cargoId" },
{ label: "船名", prop: "vessel" },
{ label: "航次", prop: "voyageNo" },
{
label: "操作",
prop: "operate",
operateData: [
{
name: "编辑",
Fn: (e) => {
router.push({
path: "/AddBooking",
query: {
type: "Edit",
id: e.id,
},
});
},
},
{
name: "删除",
Fn: (e) => {
ClickDelete(e);
},
},
],
},
]);
const SearchData = {
currentPage: 1,
pageSize: 10,
total: 0,
// ReportState: "0",
// MBLNO: "",
};
const ButtonData = [
{ text: "新建", type: "primary", icon: Plus, FnName: "ClickAdd" },
{ text: "复制", type: "primary", plain: true, FnName: "ClickCopy" },
{ text: "导入", type: "primary", plain: true },
{ text: "模板", type: "primary", plain: true },
{ text: "删除", type: "danger", FnName: "ClickDelete" },
{ text: "发送订舱", type: "primary", plain: true },
];
const TableBoxRef = ref();
const router = useRouter();
const ClickAdd = () => {
router.push({
path: "/AddBooking",
query: {
type: "Add",
},
});
console.log("新增");
};
const ListApi = bookingCustomList;
const ClickSearch = (e) => {
console.log(e.value);
TableBoxRef.value.Search(e.value);
};
const SearchOpen = (e) => {
TableBoxRef.value.height = e ? 450 : 562;
};
const ClickDelete = (e) => {
if (e) {
bookingCustomDelete({ id: e.id }).then((res) => {
if (res.data == 200) {
ClickSearch();
}
});
} else {
let table = TableBoxRef.value.$refs.Table.getSelectionRows();
if (table.length) {
table.forEach((item) => {
bookingCustomDelete({ id: item.id }).then((res) => {
if (res.data == 200) {
ClickSearch();
}
});
});
} else {
ElMessage({
message: "请至少选择一条数据",
type: "warning",
});
}
}
};
const ClickCopy = () => {
let table = TableBoxRef.value.$refs.Table.getSelectionRows();
if (table.length == 1) {
router.push({
path: "/AddBooking",
query: {
type: "Copy",
id: table[0].id,
},
});
} else {
ElMessage({
message: "请选择一条数据",
type: "warning",
});
}
};
return {
SearchBoxData,
TableBoxRef,
ClickSearch,
SearchOpen,
TableData,
SearchData,
ButtonData,
ListApi,
ClickAdd,
ClickDelete,
ClickCopy,
};
},
};
</script>
<style lang="scss" scoped>
.BookingMain {
width: 100%;
height: 100%;
display: flex;
flex-direction: column;
}
</style>

@ -0,0 +1,19 @@
let cargoIdData = [
{
name: "S 普通货",
code: "S",
},
{
name: "R 冻柜",
code: "R",
},
{
name: "D 危险品",
code: "D",
},
{
name: "O 超限箱",
code: "O",
},
];
export { cargoIdData };

File diff suppressed because it is too large Load Diff

@ -0,0 +1,19 @@
let cargoIdData = [
{
name: "S 普通货",
code: "S",
},
{
name: "R 冻柜",
code: "R",
},
{
name: "D 危险品",
code: "D",
},
{
name: "O 超限箱",
code: "O",
},
];
export { cargoIdData };

@ -0,0 +1,281 @@
<template>
<div class="BookingMain">
<SearchBox
ref="SearchBox"
:SearchData="SearchBoxData"
@ClickSearch="ClickSearch"
@SearchOpen="SearchOpen"
/>
<TableBox
ref="TableBoxRef"
:TableData="TableData"
:ListApi="ListApi"
:SearchData="SearchData"
:ButtonData="ButtonData"
@ClickAdd="ClickAdd"
@ClickDelete="ClickDelete"
/>
<el-dialog
v-model="dialogFormVisible"
title="新建收发通模板"
:before-close="dialogF"
>
<el-form :model="DialogForm" :label-width="100">
<el-row>
<el-col :span="12">
<el-form-item label="类型">
<!-- <el-input v-model="DialogForm.type" /> -->
<el-select v-model="DialogForm.type" multiple>
<el-option
v-for="item in TypeData"
:key="item.code"
:label="item.name"
:value="item.code"
/>
</el-select>
</el-form-item>
</el-col>
<el-col :span="12">
<el-form-item label="代码">
<el-input v-model="DialogForm.title" />
</el-form-item>
</el-col>
<el-col :span="12">
<el-form-item label="名称">
<el-input v-model="DialogForm.name" />
</el-form-item>
</el-col>
<el-col :span="12">
<el-form-item label="电话">
<el-input v-model="DialogForm.tel" />
</el-form-item>
</el-col>
<el-col :span="12">
<el-form-item label="国家">
<el-input v-model="DialogForm.countryName" />
</el-form-item>
</el-col>
<el-col :span="12">
<el-form-item label="地址">
<el-input v-model="DialogForm.addr" />
</el-form-item>
</el-col>
<el-col :span="12">
<el-form-item label="备注">
<el-input v-model="DialogForm.remark" />
</el-form-item>
</el-col>
<el-col :span="24">
<el-form-item label="模板内容">
<el-input
v-model="DialogForm.content"
:autosize="{ minRows: 2, maxRows: 4 }"
type="textarea"
/>
</el-form-item>
</el-col>
</el-row>
</el-form>
<template #footer>
<span class="dialog-footer">
<el-button @click="dialogF"></el-button>
<el-button type="primary" @click="dialogS"> </el-button>
</span>
</template>
</el-dialog>
</div>
</template>
<script>
import SearchBox from "@/components/SearchBox.vue";
import TableBox from "@/components/TableBox.vue";
import { Plus } from "@element-plus/icons-vue";
import {
bookingTemplateList,
bookingTemplateSave,
bookingTemplateDelete,
} from "@/api/Index";
import { ref, reactive } from "vue";
export default {
name: "ViewBooking",
components: {
SearchBox,
TableBox,
},
setup() {
const dialogFormVisible = ref(false);
const DialogForm = ref({});
const TypeData = [
{
code: "10",
name: "收货人",
},
{
code: "20",
name: "发货人",
},
{
code: "30",
name: "通知人",
},
{
code: "40",
name: "第二通知人",
},
];
const SearchBoxData = reactive([
{
title: "类型",
EType: "Select",
DName: "type",
SelectList: TypeData,
},
{
title: "代码",
EType: "Input",
DName: "title",
},
{
title: "名称",
EType: "Input",
DName: "name",
},
{
title: "地址",
EType: "Input",
DName: "addr",
},
{
title: "模板内容",
EType: "Input",
DName: "content",
},
]);
const ClickAdd = () => {
dialogFormVisible.value = true;
};
const ClickEdit = (e) => {
dialogFormVisible.value = true;
let R = [];
e.type.split("[").forEach((a) => {
if (a) {
a.split("]").forEach((b) => {
if (b) {
R.push(b);
}
});
}
});
return { ...e, type: R };
};
const TableData = reactive([
{
label: "类型",
prop: "type",
StateType: "multiple",
StateChange: TypeData,
},
{ label: "代码", prop: "title" },
{ label: "名称", prop: "name" },
{ label: "地址", prop: "addr" },
{ label: "国家", prop: "countryName" },
{ label: "备注", prop: "remark" },
{ label: "电话", prop: "tel" },
{
label: "操作",
prop: "operate",
operateData: [
{
name: "编辑",
Fn: (e) => {
DialogForm.value = ClickEdit(e);
},
},
{
name: "删除",
Fn: (e) => {
ClickDelete(e);
},
},
],
},
]);
const SearchData = {
currentPage: 1,
pageSize: 10,
total: 0,
// ReportState: "0",
// MBLNO: "",
};
const ButtonData = [
{ text: "新建", type: "primary", icon: Plus, FnName: "ClickAdd" },
];
const TableBoxRef = ref();
const ListApi = bookingTemplateList;
const ClickSearch = (e = {}) => {
console.log(e.value);
TableBoxRef.value.Search(e.value);
};
const SearchOpen = (e) => {
TableBoxRef.value.height = e ? 450 : 562;
};
const ClickDelete = (e) => {
bookingTemplateDelete({ id: e.id }).then((res) => {
if (res.code == 200) {
ClickSearch();
}
});
};
const dialogF = () => {
dialogFormVisible.value = false;
DialogForm.value = {};
};
const dialogS = () => {
let type = "";
console.log(DialogForm.value);
DialogForm.value.type.forEach((item) => {
if (type) {
type = `${type}[${item}]`;
} else {
type = `[${item}]`;
}
});
let ApiData = { ...DialogForm.value, type };
bookingTemplateSave(ApiData).then((res) => {
if (res.code == 200) {
dialogF();
ClickSearch();
}
});
};
return {
TypeData,
DialogForm,
dialogFormVisible,
SearchBoxData,
TableBoxRef,
ClickSearch,
SearchOpen,
TableData,
SearchData,
ButtonData,
ListApi,
ClickAdd,
ClickDelete,
dialogF,
dialogS,
};
},
};
</script>
<style lang="scss" scoped>
.BookingMain {
width: 100%;
height: 100%;
display: flex;
flex-direction: column;
}
</style>

@ -0,0 +1,19 @@
let cargoIdData = [
{
name: "S 普通货",
code: "S",
},
{
name: "R 冻柜",
code: "R",
},
{
name: "D 危险品",
code: "D",
},
{
name: "O 超限箱",
code: "O",
},
];
export { cargoIdData };

@ -0,0 +1,9 @@
<template>
<h1>Home</h1>
</template>
<script>
export default {
name: "ViewHome",
setup() {},
};
</script>

@ -0,0 +1,159 @@
<template>
<div class="LoginMain">
<div class="loginMBox">
<div class="loginImgBox">
<img class="loginImg" src="@/assets/login.png" alt="" />
</div>
<div class="loginBox">
<div class="LoginRTitle">
<img src="@/assets/logo.png" alt="" />
<span>济舱海工作平台</span>
</div>
<div class="fromBox">
<el-input
class="CsUserNmaeI CsI"
v-model="LoginData.account"
size="large"
placeholder="用户名"
/>
<el-input
class="CsPasswordI CsI"
type="password"
v-model="LoginData.password"
size="large"
placeholder="密码"
/>
<el-button
class="CsLoginB"
size="large"
type="primary"
@click="Login"
>
登录
</el-button>
<el-button class="CsSignB" type="primary" link>注册用户</el-button>
</div>
</div>
</div>
</div>
<!-- <h1 @click="FnClick">{{ name }}</h1> -->
</template>
<script>
import { UserLogin, UserGetLoginUser } from "@/api/Index";
import { ref, reactive } from "vue";
import { useRouter } from "vue-router";
import { useStore } from "vuex";
export default {
name: "ViewLogin",
setup(msg) {
const router = useRouter();
const store = useStore();
const LoginData = reactive({
account: "",
password: "",
});
console.log(msg);
const name = ref("Login");
const FnClick = () => {
console.log(name.value);
};
const Login = () => {
UserLogin(LoginData).then((res) => {
if (res.code == 200) {
console.log(store, res);
store.commit("XGetUser", {
token: `Bearer ${res.data}`,
// userInfo: res.data.userInfo,
});
UserGetLoginUser().then((res) => {
console.log(res);
if (res.code == 200) {
store.commit("XGetUser", {
userInfo: res.data,
});
router.push("/");
store.dispatch("GetInitData");
}
});
}
});
};
return {
name,
FnClick,
// -----------------
LoginData,
Login,
};
},
};
</script>
<style lang="scss" scoped>
.LoginMain {
height: 100vw;
height: 100vh;
background: #f0f3f9;
display: flex;
align-items: center;
justify-content: center;
.loginMBox {
display: flex;
align-items: center;
justify-content: center;
width: 1140px;
height: 586px;
padding: 70px 75px;
box-sizing: border-box;
background: #ffffff;
box-shadow: 0 2px 14px 0 rgba(0, 0, 0, 0.1);
border-radius: 30px;
.loginImgBox {
flex: 1;
.loginImg {
width: 425px;
height: 385px;
}
}
.loginBox {
flex: 1;
height: 100%;
display: flex;
flex-direction: column;
align-items: center;
.LoginRTitle {
display: flex;
align-items: center;
margin-bottom: 55px;
img {
width: 56px;
height: 56px;
}
span {
display: inline-block;
height: 56px;
line-height: 56px;
margin-left: 26px;
font-family: PingFangSC-Regular !important;
font-size: 35px !important;
color: #0486fe;
text-align: center;
font-weight: 400;
}
}
.fromBox {
width: 240px;
.CsI {
margin-bottom: 40px;
}
.CsLoginB {
width: 100%;
margin-bottom: 21px;
}
.CsSignB {
margin-left: 180px;
}
}
}
}
}
</style>

@ -0,0 +1,160 @@
<template>
<div class="IndexMainBox">
<el-container>
<el-header class="IndexHeader">
<img class="Logo" src="@/assets/logo.png" alt="" />
<span class="JCH">济舱海工作平台</span>
<el-popover placement="bottom" trigger="click">
<template #reference>
<span class="UserName">
<el-icon><ArrowDownBold /></el-icon>
{{
$store.state.User.userInfo.name
? $store.state.User.userInfo.name
: "用户名"
}}
</span>
</template>
<el-button link @click="LogOut">
<el-icon :style="{ marginRight: '20px' }"><SwitchButton /></el-icon>
退出登录
</el-button>
</el-popover>
</el-header>
<el-container class="IndexContainer">
<el-aside class="IndexAside">
<el-menu
default-active="2"
class="el-menu-vertical-demo"
@open="handleOpen"
@close="handleClose"
router
>
<el-menu-item index="/About">
<el-icon><setting /></el-icon>
<span>About</span>
</el-menu-item>
<el-menu-item index="/Booking">
<el-icon><setting /></el-icon>
<span>客户订舱</span>
</el-menu-item>
<el-menu-item index="/BookingOrder">
<el-icon><setting /></el-icon>
<span>订舱台账 </span>
</el-menu-item>
<el-menu-item index="/BookingTemplate">
<el-icon><setting /></el-icon>
<span>收发通模板</span>
</el-menu-item>
</el-menu>
</el-aside>
<el-main class="IndexMain">
<el-breadcrumb separator="/" class="IndexMainBreadcrumb">
<el-breadcrumb-item :to="{ path: '/' }">首页</el-breadcrumb-item>
<!-- <el-breadcrumb-item :to="{ path: '/About' }">
</el-breadcrumb-item> -->
</el-breadcrumb>
<div class="IndexMainView">
<router-view />
</div>
</el-main>
</el-container>
</el-container>
</div>
</template>
<script>
import { useRouter } from "vue-router";
import { useStore } from "vuex";
export default {
name: "ViewWebC",
setup() {
const router = useRouter();
const store = useStore();
const handleOpen = (key, keyPath) => {
console.log(key, keyPath);
};
const handleClose = (key, keyPath) => {
console.log(key, keyPath);
};
const LogOut = () => {
store.commit("XGetUser", {
token: "",
userInfo: {},
});
router.push("/login");
};
return {
handleOpen,
handleClose,
LogOut,
};
},
};
</script>
<style lang="scss" scoped>
.IndexMainBox {
width: 100vw;
height: 100vh;
.IndexHeader {
height: 75px;
display: flex;
align-items: center;
padding-left: 30px;
padding-right: 126px;
background: #1f263e;
.Logo {
width: 32px;
height: 32px;
}
.JCH {
flex: 1;
margin-left: 23px;
font-family: PingFangSC-Regular;
font-size: 20px;
color: #ffffff;
letter-spacing: 0;
text-align: left;
font-weight: 400;
}
.UserName {
font-family: PingFangSC-Regular;
font-size: 16px;
color: #ffffff;
letter-spacing: 0;
text-align: right;
font-weight: 400;
cursor: pointer;
i {
margin-right: 20px;
}
}
}
.IndexContainer {
height: calc(100vh - 75px);
.IndexAside {
width: 200px;
background: #ffffff;
box-shadow: 0 2px 14px 0 rgba(0, 0, 0, 0.1);
}
.IndexMain {
background: #e9ecf5;
padding: 0 20px 0 30px;
box-sizing: border-box;
.IndexMainBreadcrumb {
padding: 12px;
}
.IndexMainView {
height: calc(100vh - 130px);
// padding: 18px 30px;
// box-sizing: border-box;
// background: #ffffff;
// border: 1px solid #eaf0f7;
// box-shadow: 0 5px 10px -10px rgba(0, 0, 0, 0.2);
// border-radius: 10px;
}
}
}
}
</style>

@ -0,0 +1,261 @@
import request from "@/utils/axios";
// 用户登录
const UserLogin = (data) => {
return request({
data: {
url: "/api/bookingAip/user/login",
method: "post",
data,
// headers: { Authorization: localStorage.getItem("token") },
},
});
};
// 用户信息
const UserGetLoginUser = (data) => {
return request({
data: {
url: "/api/bookingAip/user/getLoginUser",
method: "get",
data,
// headers: { Authorization: localStorage.getItem("token") },
},
});
};
// 获取客户订单列表
const bookingCustomList = (params) => {
return request({
data: {
url: "/api/bookingAip/bookingCustom/list",
method: "get",
params,
// headers: { Authorization: localStorage.getItem("token") },
},
});
};
// 保存客户订单
const bookingCustomSave = (data) => {
return request({
data: {
url: "/api/bookingAip/bookingCustom/save",
method: "post",
data,
// headers: { Authorization: localStorage.getItem("token") },
},
});
};
// 查询客户订单详情
const bookingCustomInfo = (params) => {
return request({
data: {
url: "/api/bookingAip/bookingCustom/info",
method: "get",
params,
// headers: { Authorization: localStorage.getItem("token") },
},
});
};
// 上传文件/图片
const Uploader = (data) => {
return request({
data: {
url: "/api/bookingaip/file/Uploader/annexpic",
method: "post",
data,
headers: {
Authorization: localStorage.getItem("token"),
"Content-Type": "multipart/form-data",
},
},
});
};
// 删除客户订单
const bookingCustomDelete = (data) => {
return request({
data: {
url: "/api/bookingAip/bookingCustom/delete",
method: "post",
data,
// headers: { Authorization: localStorage.getItem("token") },
},
});
};
// 获取收发通模板列表
const bookingTemplateList = (params) => {
return request({
data: {
url: "/api/bookingAip/bookingTemplate/list",
method: "get",
params,
// headers: { Authorization: localStorage.getItem("token") },
},
});
};
// 保存
const bookingTemplateSave = (data) => {
return request({
data: {
url: "/api/bookingAip/bookingTemplate/save",
method: "post",
data,
// headers: { Authorization: localStorage.getItem("token") },
},
});
};
// 删除
const bookingTemplateDelete = (data) => {
return request({
data: {
url: "/api/bookingAip/bookingTemplate/delete",
method: "post",
data,
// headers: { Authorization: localStorage.getItem("token") },
},
});
};
// 查询订单详情
const bookingOrderInfo = (params) => {
return request({
data: {
url: "/api/bookingAip/bookingOrder/info",
method: "get",
params,
// headers: { Authorization: localStorage.getItem("token") },
},
});
};
// 获取订舱台账列表
const bookingOrderList = (params) => {
return request({
data: {
url: "/api/bookingAip/bookingOrder/list",
method: "get",
params,
// headers: { Authorization: localStorage.getItem("token") },
},
});
};
// 船公司信息
const GetCarrierlist = (params) => {
return request({
data: {
url: "/api/commondb/carrierlist",
method: "get",
params,
// headers: { Authorization: localStorage.getItem("token") },
},
});
};
// 箱型信息
const GetCtnlist = (params) => {
return request({
data: {
url: "/api/commondb/ctn",
method: "get",
params,
// headers: { Authorization: localStorage.getItem("token") },
},
});
};
// 起始港信息
const Getportloadlist = (params) => {
return request({
data: {
url: "/api/commondb/portloadlist",
method: "get",
params,
// headers: { Authorization: localStorage.getItem("token") },
},
});
};
// 目的港信息
const Getportlist = (params) => {
return request({
data: {
url: "/api/commondb/portlist",
method: "get",
params,
// headers: { Authorization: localStorage.getItem("token") },
},
});
};
// 运输条款信息
const Getservicelist = (params) => {
return request({
data: {
url: "/api/commondb/service",
method: "get",
params,
// headers: { Authorization: localStorage.getItem("token") },
},
});
};
// 付费方式信息
const Getfrtlist = (params) => {
return request({
data: {
url: "/api/commondb/frt",
method: "get",
params,
// headers: { Authorization: localStorage.getItem("token") },
},
});
};
// 船名列表信息
const Getvessellist = (params) => {
return request({
data: {
url: "/api/commondb/vessellist",
method: "get",
params,
// headers: { Authorization: localStorage.getItem("token") },
},
});
};
// 获取包装信息
const Getpackagelist = (params) => {
return request({
data: {
url: "/api/commondb/package",
method: "get",
params,
// headers: { Authorization: localStorage.getItem("token") },
},
});
};
// 获取客户订单服务列表
const cobServiceItemTenantList = (params) => {
return request({
data: {
url: "/api/bookingAip/cobServiceItemTenant/list",
method: "get",
params,
// headers: { Authorization: localStorage.getItem("token") },
},
});
};
export {
UserLogin,
UserGetLoginUser,
bookingCustomList,
bookingCustomSave,
bookingCustomInfo,
Uploader,
bookingCustomDelete,
bookingTemplateList,
bookingTemplateSave,
bookingTemplateDelete,
bookingOrderInfo,
bookingOrderList,
GetCarrierlist,
GetCtnlist,
Getportloadlist,
Getportlist,
Getservicelist,
Getfrtlist,
Getvessellist,
Getpackagelist,
cobServiceItemTenantList,
};

Binary file not shown.

After

Width:  |  Height:  |  Size: 28 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 6.7 KiB

After

Width:  |  Height:  |  Size: 10 KiB

@ -0,0 +1,183 @@
<template>
<div class="SearchBOXMain">
<el-row>
<el-col class="SearchFirst">
<div class="SearchFirstL">
<p @click="Open">
<el-icon v-if="OpenType"><ArrowUp /></el-icon>
<el-icon v-else><ArrowDown /></el-icon>
订单查询
</p>
<!-- <p>
<el-icon><Setting /></el-icon>
</p> -->
</div>
<div>
<el-button @click="Reset"></el-button>
<el-button type="primary" @click="Search"></el-button>
</div>
</el-col>
<el-col class="SearchSecond" v-if="OpenType">
<el-row>
<el-col
:span="6"
class="SearchSecondUnit"
v-for="item in search_data"
:key="item.DName"
>
<span> {{ item.title }} </span>
<el-input
v-if="item.EType == 'Input'"
class="ECs"
v-model="Data[item.DName]"
:placeholder="`请输入${item.title}`"
/>
<el-select
v-else-if="item.EType == 'Select'"
class="ECs"
v-model="Data[item.DName]"
:placeholder="`请选择${item.title}`"
size="large"
>
<el-option
v-for="e in item.SelectList"
:key="e.code"
:label="e.name"
:value="e.code"
/>
</el-select>
<el-row class="ECs" v-else-if="item.EType == 'DatePicker'">
<el-col :span="11">
<el-date-picker
v-model="Data[item.DName]"
size="large"
type="date"
:style="{ width: '100%' }"
value-format="YYYY-MM-DD"
/>
</el-col>
<el-col :span="2"> <p class="CsHeng">-</p></el-col>
<el-col :span="11">
<el-date-picker
v-model="Data[item.DName2]"
size="large"
type="date"
:style="{ width: '100%' }"
value-format="YYYY-MM-DD"
/>
</el-col>
</el-row>
</el-col>
</el-row>
</el-col>
</el-row>
</div>
</template>
<script>
import { ref, reactive } from "@vue/reactivity";
export default {
name: "SearchBox",
props: ["SearchData"],
setup(props, ctx) {
const search_data = reactive(props.SearchData);
console.log(search_data);
const Data = ref({});
const OpenType = ref(false);
const Open = () => {
OpenType.value = !OpenType.value;
ctx.emit("SearchOpen", OpenType.value);
};
const Search = () => {
ctx.emit("ClickSearch", Data);
};
const Reset = () => {
Data.value = {};
};
return {
Open,
OpenType,
search_data,
Data,
Search,
Reset,
};
},
};
</script>
<style lang="scss" scoped>
.SearchBOXMain {
background: #ffffff;
border: 1px solid #eaf0f7;
box-shadow: 0 5px 10px -10px rgba(0, 0, 0, 0.2);
border-radius: 10px;
padding: 20px 30px;
box-sizing: border-box;
margin-bottom: 12px;
.SearchFirst {
display: flex;
justify-content: space-between;
.SearchFirstL {
display: flex;
p {
cursor: pointer;
&:nth-child(1) {
font-family: PingFangSC-Medium;
font-size: 16px;
color: rgba(0, 0, 0, 0.88);
line-height: 28px;
font-weight: 500;
.el-icon {
color: #107ff2;
margin-right: 11px;
font-weight: bolder;
}
}
&:nth-child(2) {
margin-left: 15px;
font-family: PingFangSC-Regular;
font-size: 14px;
color: #1989fa;
letter-spacing: 0;
text-align: center;
font-weight: 400;
line-height: 28px;
.el-icon {
color: #1989fa;
margin-right: 8px;
font-weight: bolder;
font-size: 14px;
line-height: 28px;
}
}
}
}
}
.SearchSecond {
.SearchSecondUnit {
display: flex;
margin: 8px 0;
span {
width: 100px;
margin-right: 12px;
font-family: PingFangSC-Regular;
font-size: 16px;
color: #000000;
letter-spacing: 0;
text-align: right;
line-height: 36px;
font-weight: 400;
}
.CsHeng {
height: 40px;
line-height: 40px;
text-align: center;
}
.ECs {
width: 325px;
}
}
}
}
</style>

@ -0,0 +1,174 @@
<template>
<div class="TableBoxMain">
<div class="TableButtonBox">
<div>
<el-button
v-for="item in button_data"
:key="item.text"
:type="item.type"
:icon="item.icon"
:plain="item.plain"
@click="ClickButton(item.FnName)"
>
{{ item.text }}
</el-button>
</div>
<div>
<el-button type="primary" link>
<el-icon><RefreshRight /></el-icon>
</el-button>
</div>
</div>
<el-table
:data="TData"
style="width: 100%"
:height="height"
v-loading="loading"
ref="Table"
>
<el-table-column
v-for="item in table_data"
:key="item.prop"
:prop="item.prop"
:label="item.label"
align="center"
:width="item.width"
:type="item.type"
>
<template #default="scope" v-if="item.type != 'selection'">
<span v-if="item.StateChange">{{
RData(scope.row[item.prop], item)
}}</span>
<span v-else-if="item.prop == 'operate'">
<el-button
v-for="button in item.operateData"
:key="button.name"
:type="button.type ? button.type : 'primary'"
text
@click="ClickOperateButton(button, scope.row)"
>
{{ button.name }}
</el-button>
</span>
<span v-else>{{ scope.row[item.prop] }}</span>
</template>
</el-table-column>
</el-table>
<el-pagination
class="pagination"
background
@current-change="handleCurrentChange"
:current-page="search_data.currentPage"
:page-size="search_data.pageSize"
layout="total, prev, pager, next"
:total="search_data.total"
/>
</div>
</template>
<script>
import { ref, reactive } from "@vue/reactivity";
export default {
name: "TableBox",
props: ["TableData", "SearchData", "ButtonData", "ListApi"],
setup(props, ctx) {
const height = ref(562);
const table_data = reactive(props.TableData);
const search_data = reactive(props.SearchData);
const button_data = reactive(props.ButtonData);
const TData = ref([]);
const loading = ref(false);
const Search = (data) => {
let ApiData = { ...search_data, ...data };
console.log("查询", data);
TData.value = [];
loading.value = true;
props.ListApi(ApiData).then((res) => {
if (res.code == 200) {
TData.value = res.data.list;
search_data.total = res.data.pagination.total;
loading.value = false;
}
});
};
Search();
const handleCurrentChange = (val) => {
search_data.currentPage = val;
Search();
};
const ClickButton = (FnName) => {
ctx.emit(FnName);
};
const RData = (data, item) => {
let R = "-";
if (item.StateType == "multiple") {
R = "";
data.split("[").forEach((a) => {
if (a) {
a.split("]").forEach((b) => {
if (b) {
item.StateChange.forEach((el) => {
if (b == el.code) {
R = R ? `${R},${el.name}` : el.name;
}
});
}
});
}
});
} else {
item.StateChange.forEach((el) => {
if (data == el.code) {
R = el.name;
}
});
}
return R;
};
const ClickOperateButton = (data, e) => {
data.Fn(e);
};
return {
Search,
table_data,
search_data,
button_data,
TData,
loading,
handleCurrentChange,
height,
ClickButton,
RData,
ClickOperateButton,
};
},
};
</script>
<style lang="scss" scoped>
.TableBoxMain {
flex: 1;
background: #ffffff;
border: 1px solid #eaf0f7;
box-shadow: 0 5px 10px -10px rgba(0, 0, 0, 0.2);
border-radius: 10px;
padding: 20px 30px;
box-sizing: border-box;
// overflow: auto;
.TableButtonBox {
margin-bottom: 10px;
display: flex;
align-items: center;
div {
&:first-child {
flex: 1;
}
}
}
}
.pagination {
display: flex;
justify-content: flex-end;
margin-top: 1rem;
margin-right: 2rem;
}
</style>

@ -1,4 +1,35 @@
import { createApp } from 'vue'
import App from './App.vue'
createApp(App).mount('#app')
import { createApp } from "vue";
import App from "./App.vue";
import router from "./router";
import store from "./store";
import ElementUI, { ElMessage } from "element-plus";
import * as ElementPlusIconsVue from "@element-plus/icons-vue";
import zhCn from "element-plus/dist/locale/zh-cn.mjs";
import "element-plus/dist/index.css";
import axios from "axios";
router.beforeEach((to, from, next) => {
if (!store.state.User.token) {
if (to.path == "/login") {
next();
} else {
ElMessage({
message: "登录信息过期,请重新登录!",
type: "warning",
});
next("/login");
}
} else {
next();
}
});
const app = createApp(App);
for (const [key, component] of Object.entries(ElementPlusIconsVue)) {
app.component(key, component);
}
app.config.globalProperties.$axios = axios;
app.use(ElementUI, {
locale: zhCn,
});
app.use(store);
app.use(router);
app.mount("#app");

@ -0,0 +1,27 @@
import { createRouter, createWebHistory } from "vue-router";
import WebC from "../Views/WebC";
import Login from "../Views/Login";
import Booking from "../Views/Booking";
import AddBooking from "../Views/Booking/AddBooking.vue";
import BookingTemplate from "../Views/BookingTemplate";
import BookingOrder from "../Views/BookingOrder";
import About from "../Views/About.vue";
const router = createRouter({
history: createWebHistory(),
routes: [
{
path: "/",
component: WebC,
children: [
{ path: "/about", component: About },
{ path: "/booking", component: Booking },
{ path: "/AddBooking", component: AddBooking },
{ path: "/BookingTemplate", component: BookingTemplate },
{ path: "/BookingOrder", component: BookingOrder },
],
},
{ path: "/login", component: Login },
],
});
export default router;

@ -0,0 +1,93 @@
import { createStore } from "vuex";
import {
GetCarrierlist,
GetCtnlist,
Getportloadlist,
Getportlist,
Getservicelist,
Getfrtlist,
Getvessellist,
Getpackagelist,
cobServiceItemTenantList,
} from "@/api/Index";
export default createStore({
state: {
User: {
token: "",
userInfo: {},
},
Data: {},
},
mutations: {
XGetUser(state, payload) {
state.User = { ...state.User, ...payload };
},
XGetData(state, payload) {
state.Data = { ...state.Data, ...payload };
},
},
actions: {
GetInitData(store) {
console.log("GetInitData");
GetCarrierlist().then((res) => {
let RData = [];
res.data.forEach((item) => {
item.name = item.cnName;
RData.push(item);
});
store.commit("XGetData", { Carrierlist: RData });
});
GetCtnlist().then((res) => {
let RData = [];
res.data.forEach((item) => {
item.name = item.code;
RData.push(item);
});
store.commit("XGetData", { Ctnlist: RData });
});
Getportloadlist().then((res) => {
let RData = [];
res.data.forEach((item) => {
item.name = item.cnName;
RData.push(item);
});
store.commit("XGetData", { portloadlist: RData });
});
Getportlist().then((res) => {
let RData = [];
res.data.forEach((item) => {
item.name = item.cnName;
RData.push(item);
});
store.commit("XGetData", { portlist: RData });
});
Getservicelist().then((res) => {
let RData = [];
res.data.forEach((item) => {
item.name = item.cnName;
RData.push(item);
});
store.commit("XGetData", { servicelist: RData });
});
Getfrtlist().then((res) => {
let RData = [];
res.data.forEach((item) => {
item.name = item.cnName;
RData.push(item);
});
store.commit("XGetData", { frtlist: RData });
});
Getvessellist().then((res) => {
store.commit("XGetData", { vessellist: res.data });
});
Getpackagelist().then((res) => {
store.commit("XGetData", { packagelist: res.data });
});
cobServiceItemTenantList().then((res) => {
console.log("cobServiceItemTenantList", res);
store.commit("XGetData", { cobServiceItemTenantList: res.data });
});
},
},
modules: {},
});

@ -0,0 +1,56 @@
import axios from "axios";
import { ElMessage } from "element-plus";
import router from "../router";
import store from "@/store";
export default ({ data }) => {
let baseURL = "";
// let baseURL = "";
// if (data.url == "/user/login") {
// // baseURL = "http://60.209.125.238:35101"; //测试
// baseURL = "http://djy-identity.myshipping.net"; //正式
// } else {
// baseURL = process.env.VUE_APP_AXIOS_BASEURL;
// }
const server = axios.create({
baseURL,
timeout: 60000,
headers: { Authorization: store.state.User.token },
});
server.interceptors.request.use(
function (config) {
return config;
},
function (error) {
// Do something with request error
return Promise.reject(error);
}
);
server.interceptors.response.use(
(req) => {
if (req.data.code !== 200) {
if (req.data.code == 602) {
store.commit("XGetUser", {
token: "",
userInfo: {},
});
ElMessage({
message: "登录信息过期,请重新登录!",
type: "warning",
});
router.push("/login");
} else {
ElMessage({
message: req.data.message,
type: "warning",
});
}
}
return req.data;
},
(err) => {
return err;
}
);
return server(data);
};

@ -1,4 +1,25 @@
const { defineConfig } = require('@vue/cli-service')
const { defineConfig } = require("@vue/cli-service");
module.exports = defineConfig({
transpileDependencies: true
})
transpileDependencies: true,
publicPath: "/", //这个必须,引入静态资源需要从根路径引入,否则会找不到静态资源
devServer: {
// history模式下的url会请求到服务器端但是服务器端并没有这一个资源文件就会返回404所以需要配置这一项
historyApiFallback: {
index: "/index.html", //与output的publicPath
},
host: "localhost",
port: 8080, // 端口号
https: false, // https:{type:Boolean}
open: false, // 配置后自动启动浏览器
proxy: {
// 跨域处理
"/api": {
target: "http://47.104.222.4:8210/api", //目标接口域名
changeOrigin: true, //是否跨域
pathRewrite: {
"^/api": "", //重写接口
},
},
},
},
});

Loading…
Cancel
Save