Compare commits

...

10 Commits

Author SHA1 Message Date
wuteng
965daee2f2 Merge pull request 'app企业税号功能' (#3) from develop-virtualRecord into master
Reviewed-on: http://git.xdadan.loc/tanex/emis-app/pulls/3
2025-08-26 17:41:32 +08:00
wuteng
039fa742f1 app企业税号功能 2025-08-26 17:39:58 +08:00
linfso
5a4076c786 md 2025-08-15 13:59:56 +08:00
linfso
9b1b59dff5 md 2025-08-15 13:44:30 +08:00
linfso
4cd1092ff2 md 2025-08-15 13:43:29 +08:00
wuteng
17812e7aac Merge pull request 'develop-virtualRecord' (#2) from develop-virtualRecord into master
Reviewed-on: http://git.xdadan.loc/tanex/emis-app/pulls/2
2025-07-17 16:40:35 +08:00
wuteng
d9e9a226f3 操作员、运费参数调整 2025-07-17 16:35:16 +08:00
wuteng
7dd5f71575 操作员和计算运费接口参数调整 2025-07-15 18:34:00 +08:00
linfso
de950fcd28 md 2025-07-14 17:50:08 +08:00
linfso
39a0934e0c 账单优化 2025-07-09 09:22:28 +08:00
19 changed files with 737 additions and 88 deletions

View File

@ -74,5 +74,11 @@ export const listSimple = (data = {})=> {
return coreRequest(url.listSimple, data, {}, "GET")
}
export const getLbsRecordListByBillCode = (data = {})=> {
return coreRequest(url.getLbsRecordListByBillCode, data, {}, "GET")
}

View File

@ -82,5 +82,8 @@ export default {
getMyBizStatList: `/emis/emisWaybill/getMyBizStatList`, // 业务统计明细(区分国家)
getMasterEmisWaybills: `/emis/emisWaybill/getMasterEmisWaybills`, // 获取关联主单号
listSimple: `/emis/emisSite/listSimple`, // 获取网点列表
getLbsRecordListByBillCode: `/emis/emisTmsMapTrace/getLbsRecordListByBillCode`, // 获取运单lbs信息
}

View File

@ -1,9 +1,9 @@
let envMap = {
development: {
// apiHost: 'https://api-emis.tanex56.com/api/bizsvr',
// socketHost: 'wss://api-emis.tanex56.com/api/bizsvr',
apiHost: 'http://47.102.220.189:58089/api/bizsvr',
socketHost: 'ws://47.102.220.189:58089/api/bizsvr',
apiHost: 'https://api-emis.tanex56.com/api/bizsvr',
socketHost: 'wss://api-emis.tanex56.com/api/bizsvr',
// apiHost: 'http://47.102.220.189:58089/api/bizsvr',
// socketHost: 'ws://47.102.220.189:58089/api/bizsvr',
},
production: {
apiHost: 'https://api-emis.tanex56.com/api/bizsvr',

82
common/geo/XDGeoSdk.js Normal file
View File

@ -0,0 +1,82 @@
'use strict'
import * as turf from '@turf/turf';
import { deepClone } from '@/common/custom.js'
/*
中国边界数据 来源 阿里-高德
https://datav.aliyun.com/portal/school/atlas/area_selector
*/
import chinaBoundary from './china-boundary.json';
/*
XDGeoSdk
*/
class XDGeoSdk {
geoJson = null;
geoSimpleJson = null;
chinaPolygon = null;
chinaAreaBoundary = null;
chinaAreaMainLandBoundary = null;
chinaBox = null;
static instance = null;
constructor() {
this.instance = null
this.geoJson=chinaBoundary;
this.chinaAreaBoundary=deepClone(chinaBoundary.features[0].geometry.coordinates);
this.chinaAreaMainLandBoundary=this.chinaAreaBoundary[0][0];
this.chinaPolygon = chinaBoundary.features[0].geometry;
this.chinaBox=turf.bbox(this.chinaPolygon);
var options = {tolerance: 0.01, highQuality: false};
this.geoSimpleJson = turf.simplify(this.geoJson, options);
// console.log("===>this.chinaPolygon==>",this.chinaPolygon);
// console.log("===>geoSimpleJson==>",this.geoSimpleJson);
}
static getInstance() {
if (!this.instance) {
this.instance = new XDGeoSdk()
}
return this.instance
}
getChinaGeoJson(){
return this.geoJson;
// return this.geoSimpleJson;
}
getChinaPolygon(){
return this.chinaAreaBoundary;
}
getChinaMainLandPolygon(){
return this.chinaAreaMainLandBoundary;
}
isInChina(lat,lng) {
// [minLng, minLat, maxLng, maxLat]
const bbox = this.chinaBox;
const isInBbox = lng >= bbox[0] && lng <= bbox[2] && lat >= bbox[1] && lat <= bbox[3];
if (!isInBbox) {
return false;
}
const point = turf.point([lng, lat]);
const chinaPolygon = this.chinaPolygon;
let rst=turf.booleanPointInPolygon(point, chinaPolygon);
return rst;
}
}
export default XDGeoSdk;

File diff suppressed because one or more lines are too long

16
common/geo/chinaGeo.js Normal file
View File

@ -0,0 +1,16 @@
import XDGeoSdk from './XDGeoSdk';
const xdGeoSdk = XDGeoSdk.getInstance();
export function getChinaGeoJson() {
return xdGeoSdk.getChinaGeoJson();
}
export function getChinaPolygon() {
return xdGeoSdk.getChinaPolygon();
}
export function isInChina(lat,lng) {
return xdGeoSdk.isInChina(lat,lng)
}

View File

@ -0,0 +1,110 @@
<template>
<u-row justify="between">
<u-row @click="setClipboardData(modelInfo.billCode)">
<view>
<u-text v-if="modelInfo.billCode" :text="`运单号:${modelInfo.billCode}` " size="26"></u-text>
<u-text v-else :text="`订单号:${modelInfo.orderSn}` " size="26"></u-text>
</view>
<view class="pl-10">
<u-icon name="file-text" size="32" custom-style=""></u-icon>
</view>
</u-row>
<view>
<view v-if="showInfoBtn" @click="goto(`post/detail?billCode=${modelInfo.billCode}`)" class="com-tag-grey">
运单信息
</view>
<tpx-text-dic v-if="!showInfoBtn" :value="modelInfo.orderStatus" :list="dicData.emis_order_status" ></tpx-text-dic>
</view>
</u-row>
<view @click="goto(`post/detail?billCode=${modelInfo.billCode}`)">
<u-row custom-style="margin-top: 5rpx;" justify="center">
<u-col span="4">
<u-text :text="(sender.countryName + sender.provinceName)||'-'" size="30" :bold="true" align="center"></u-text>
<!-- <u-text :text="sender.name" size="26" color="#999" margin="20rpx 0 0 0"
align="center"></u-text> -->
</u-col>
<u-col span="4" justify="center" align="center" custom-style="text-align: center;">
<image style="width: 70rpx;height: 14rpx;" :src="getCdnUrl('post/toline.png')">
</image>
<!-- getCdnUrl('post/toline-grey.png') -->
<view class="mt-10">
<tpx-text-dic :value="modelInfo.waybillStatus" :list="dicData.emis_waybill_status" ></tpx-text-dic>
</view>
</u-col>
<u-col span="4">
<u-text :text="(reciever.countryName + reciever.provinceName)||'-'" size="30" :bold="true" align="center"></u-text>
<!-- <u-text :text="reciever.name" size="26" color="#999" margin="20rpx 0 0 0"
align="center"></u-text> -->
</u-col>
</u-row>
<u-text v-if="modelInfo.blSign!=1" :text="`下单时间:${modelInfo.sendDate}`" color="#999" size="24"
margin="10rpx 0 0 0"></u-text>
<u-text v-if="modelInfo.blSign==1" :text="`签收时间:${modelInfo.signDate}`" color="#999" size="24"
margin="10rpx 0 0 0"></u-text>
</view>
</template>
<script>
export default {
computed: {
modelInfo: {
get() {
return this.value
}
},
sender() {
let obj = JSON.parse(JSON.stringify(this.value?.sender || this.value || {}))
obj.countryName = obj.sendCountryName || obj.countryName
obj.provinceName = obj.sendProvinceName || obj.provinceName
obj.name = obj.sendName || obj.name
return obj
},
reciever() {
let obj = JSON.parse(JSON.stringify(this.value?.reciever || this.value || {}))
obj.countryName = obj.receiveCountryName || obj.countryName
obj.provinceName = obj.receiveProvinceName || obj.provinceName
obj.name = obj.receiveName || obj.name
return obj
},
dicData() {
return this.$store.getters.dicData
}
},
props: {
value: {
default () {
return {}
}
},
showInfoBtn: {
default () {
return true
}
},
},
data() {
return {}
},
created() {
},
onHide() {
},
unmounted() {
},
methods: {
}
}
</script>
<style scoped lang="scss">
</style>

View File

@ -19,6 +19,11 @@
<u-text :text="sendDetail" size="26" color="#999"></u-text>
<view v-if="modelInfo.sender" class="font-weight mt-10 font-24">{{modelInfo.sender.company}}</view>
</view>
<view v-if="modelInfo.sender && modelInfo.sender.enterpriseName">
<text class="font-weight pr-10 font-24">{{ modelInfo.sender.enterpriseName }}</text>
<text class="font-weight font-24">{{ modelInfo.sender.enterpriseTaxId }}</text>
</view>
</view>
<view v-if="!disabled" class="flex-column-center" style="flex-shrink:0;">
<image style="height: 32rpx;width: 28rpx;" :src="getCdnUrl(`post/adress.png`)">
@ -30,11 +35,11 @@
<u-line custom-style="height:100%;" direction="col" dashed="true"></u-line>
</view>
</u-row>
<view style="padding-left: 76rpx;">
<u-line margin="20rpx 0"></u-line>
</view>
<u-row @click="handleAddressChoose(2)" custom-style="position:relative;gap:30rpx;" align="top"
>
<view style="position: absolute;left: 20rpx;top: -20rpx;bottom: 100%;">

View File

@ -86,7 +86,7 @@
<view style="width: 360rpx;">
<tpx-input v-model:value="modelInfo.freight" :isWhite="true" _digit="4"
:disabled="modelInfo.calcFeeType!=3"
inputAlign="right" custom-style="height: 46rpx;" suffix="CNY"></tpx-input>
inputAlign="left" custom-style="height: 46rpx;" suffix="CNY"></tpx-input>
</view>
</u-row>
</view>
@ -100,43 +100,43 @@
</view>
</view>
<buns-edit-sheet percentHeight="40" :title="costModal.item.feeName" v-model:show="costModal.show" v-model:value="costModal.item" v-slot="tempObject" @onSure="handleCostItemSure" :okCloseModal="false">
<view v-if="costModal.show">
<tpx-select v-model:value="tempObject.value.currency" :list="costRateList"
@onChange="handleCurrencyChange" mode="drop"
>
<u-row custom-style="gap: 20rpx;margin-top:10rpx;" justify="between">
<text class="font-26 label-text">币种</text>
<tpx-text-dic :value="tempObject.value.currency" :list="costRateList"></tpx-text-dic>
</u-row>
</tpx-select>
<u-row custom-style="gap: 20rpx;margin-top:30rpx;">
<u-row custom-style="flex: 1">
<text class="font-26 label-text">首重费</text>
<tpx-input v-model:value="tempObject.value.initialWeightFee" _digit="4" :isWhite="true"
custom-style="width: 120rpx;height: 46rpx;" :suffix="tempObject.value.currency"></tpx-input>
</u-row>
<u-row custom-style="flex: 1">
<text class="font-26 label-text">续重单价</text>
<tpx-input v-model:value="tempObject.value.addWeightPrice" _digit="4" :isWhite="true"
custom-style="width: 120rpx;height: 46rpx;" :suffix="tempObject.value.currency"></tpx-input>
</u-row>
</u-row>
<u-row style="margin-top:30rpx;" justify="between">
<u-row custom-style="width:300rpx;">
<text class="label-text">应收</text>
<tpx-input v-model:value="tempObject.value.fee" _digit="4" :isWhite="true" custom-style="width: 120rpx;height: 46rpx;"
:suffix="tempObject.value.currency"></tpx-input>
</u-row>
<u-row custom-style="width:300rpx;">
<text :class="`font-26 label-text label-text-required `">实收</text>
<tpx-input v-model:value="tempObject.value.realFee" _digit="4" :isWhite="true" custom-style="width: 120rpx;height: 46rpx;"
:suffix="tempObject.value.currency"></tpx-input>
</u-row>
</u-row>
<view class="mt-30">
<tpx-input v-model:value="tempObject.value.remark" placeholder="费用描述" isWhite="true"></tpx-input>
</view>
<buns-edit-sheet percentHeight="40" :title="costModal.item.feeName" v-model:show="costModal.show" v-model:value="costModal.item" v-slot="tempObject" @onSure="handleCostItemSure" :okCloseModal="false">
<view v-if="costModal.show">
<tpx-select v-model:value="tempObject.value.currency" :list="costRateList"
@onChange="handleCurrencyChange" mode="drop"
>
<u-row custom-style="gap: 20rpx;margin-top:10rpx;" justify="between">
<text class="font-26 label-text">币种</text>
<tpx-text-dic :value="tempObject.value.currency" :list="costRateList"></tpx-text-dic>
</u-row>
</tpx-select>
<u-row custom-style="gap: 20rpx;margin-top:30rpx;">
<u-row custom-style="flex: 1">
<text class="font-26 label-text">首重费</text>
<tpx-input v-model:value="tempObject.value.initialWeightFee" _digit="4" :isWhite="true"
custom-style="width: 120rpx;height: 46rpx;" :suffix="tempObject.value.currency"></tpx-input>
</u-row>
<u-row custom-style="flex: 1">
<text class="font-26 label-text">续重单价</text>
<tpx-input v-model:value="tempObject.value.addWeightPrice" _digit="4" :isWhite="true"
custom-style="width: 120rpx;height: 46rpx;" :suffix="tempObject.value.currency"></tpx-input>
</u-row>
</u-row>
<u-row style="margin-top:30rpx;" justify="between">
<u-row custom-style="width:300rpx;">
<text class="label-text">应收</text>
<tpx-input v-model:value="tempObject.value.fee" _digit="4" :isWhite="true" custom-style="width: 120rpx;height: 46rpx;"
:suffix="tempObject.value.currency"></tpx-input>
</u-row>
<u-row custom-style="width:300rpx;">
<text :class="`font-26 label-text label-text-required `">实收</text>
<tpx-input v-model:value="tempObject.value.realFee" _digit="4" :isWhite="true" custom-style="width: 120rpx;height: 46rpx;"
:suffix="tempObject.value.currency"></tpx-input>
</u-row>
</u-row>
<view class="mt-30">
<tpx-input v-model:value="tempObject.value.remark" placeholder="费用描述" isWhite="true"></tpx-input>
</view>
</view>
</buns-edit-sheet>
</template>
@ -174,6 +174,7 @@
sendSiteCode: this.$store.getters.userInfo.ownerSiteCode,
dispatchUnderlingSiteCode: info.dispatchUnderlingSiteCode,
custNo: info.custNo,
startSiteCode: info.startSiteCode,
}
return param
}

View File

@ -26,6 +26,7 @@
</view>
<view v-for="(item, index) in modelInfo.cargoList" class="yditem">
<bpe-gooditem-filed-edit-tmp :value="item" :showMode="showMode" :submitVal="modelInfo"></bpe-gooditem-filed-edit-tmp>
<view class="ydi-lab mb-10">
<text class="font-weight">
<!-- {{item.goodsName}} -->
@ -34,7 +35,6 @@
<u-icon @click="handleDelGood(index)" name="trash" size="32"></u-icon>
</view>
</view>
<bpe-gooditem-filed-edit-tmp :value="item" :showMode="showMode" :submitVal="modelInfo"></bpe-gooditem-filed-edit-tmp>
</view>
<u-button @click="handleAddGood" custom-style="border-radius: 16rpx;height: 66rpx;" type="primary" plain="true">
@ -48,9 +48,9 @@
<view class="edm-input-item mt-20">
<u-row justify="between">
<text class="font-28 font-weight">包裹重量</text>
<text class="font-28 font-weight">实际重量</text>
<view>
<tpx-input v-model:value="modelInfo.billWeight" placeholder="" inputAlign="right" suffix="kg" _digit="4"></tpx-input>
<tpx-input v-model:value="modelInfo.billWeight" placeholder="" inputAlign="left" suffix="kg" _digit="4"></tpx-input>
</view>
</u-row>
</view>
@ -59,7 +59,7 @@
<u-row justify="between" align="top">
<text class="font-28 pt-20 font-weight">总体积</text>
<view v-if="totalVolume || true">
<tpx-input v-model:value="modelInfo.totalVolume" placeholder="" inputAlign="right" suffix="m³" _digit="4"></tpx-input>
<tpx-input v-model:value="modelInfo.totalVolume" placeholder="" inputAlign="left" suffix="m³" _digit="4"></tpx-input>
</view>
</u-row>
</view>
@ -68,7 +68,7 @@
<u-row justify="between" align="top">
<text class="font-28 pt-20 font-weight">货值</text>
<view>
<tpx-input v-model:value="modelInfo.realValue" placeholder="" inputAlign="right" suffix="美元" _digit="4"></tpx-input>
<tpx-input v-model:value="modelInfo.realValue" placeholder="" inputAlign="left" suffix="美元" _digit="4"></tpx-input>
</view>
</u-row>
</view>

View File

@ -2,18 +2,39 @@
<view class="">
<view class="jsfm-item">
<u-row justify="between" align="top">
<view style="width: 100%;">
<u-row justify="between" style="margin-bottom: 10px;">
<u-col span="3">
<text class="font-28 font-weight pr-10" align="center">长(cm)</text>
</u-col>
<u-col span="3">
<text class="font-28 font-weight pr-10" align="center">宽(cm)</text>
</u-col>
<u-col span="3">
<text class="font-28 font-weight pr-10" align="center">高(cm)</text>
</u-col>
<u-col span="3">
<text class="font-28 font-weight pr-10" align="center">件数</text>
</u-col>
</u-row>
</view>
</u-row>
<u-row justify="between" align="top">
<!-- <text class="font-28 pt-20 font-weight">尺寸</text> -->
<view style="width: 100%;">
<u-row justify="between">
<u-col span="3.7">
<tpx-input v-model:value="modelInfo.length" placeholder="长" inputAlign="right" suffix="cm" _digit="4"></tpx-input>
<u-col span="3">
<tpx-input v-model:value="modelInfo.length" placeholder="" inputAlign="center" suffix="" _digit="4" style="border-radius: 0px;"></tpx-input>
</u-col>
<u-col span="3.7">
<tpx-input v-model:value="modelInfo.width" placeholder="宽" inputAlign="right" suffix="cm" _digit="4"></tpx-input>
<u-col span="3">
<tpx-input v-model:value="modelInfo.width" placeholder="" inputAlign="center" suffix="" _digit="4" style="border-radius: 0px;"></tpx-input>
</u-col>
<u-col span="3.7">
<tpx-input v-model:value="modelInfo.height" placeholder="高" inputAlign="right" suffix="cm" _digit="4"></tpx-input>
<u-col span="3">
<tpx-input v-model:value="modelInfo.height" placeholder="" inputAlign="center" suffix="" _digit="4" style="border-radius: 0px;"></tpx-input>
</u-col>
<u-col span="3">
<tpx-input placeholder="" v-model:value="modelInfo.cargoQty" inputAlign="center" type="number" suffix="" :_maxNum="cargoQtyMaxNum" style="border-radius: 0px;"></tpx-input>
</u-col>
</u-row>
</view>
@ -21,14 +42,14 @@
</view>
<view class="jsfm-item">
<u-row justify="between">
<u-row>
<!-- <u-row>
<text class="font-28 font-weight pr-10">件数</text>
<view style="width: 200rpx;">
<tpx-input placeholder="请填写" v-model:value="modelInfo.cargoQty" inputAlign="right" type="number" suffix="件" :_maxNum="cargoQtyMaxNum"></tpx-input>
<tpx-input placeholder="件数" v-model:value="modelInfo.cargoQty" inputAlign="center" type="number" suffix="件" :_maxNum="cargoQtyMaxNum" style="border-radius: 0px;"></tpx-input>
</view>
</u-row>
</u-row> -->
<u-row>
<text class="font-28 font-weight pr-10">体积</text>
<text class="font-28 font-weight pr-10">体积:</text>
<view style="">
{{modelInfo.volume || '0'}}
<text class="clr-sub">m³</text>

View File

@ -0,0 +1,310 @@
<template>
<view class="map-container">
<view ref="mapContainer" id="mapContainer" class="map-view" :prop="traceList" :change:prop="mapModule.updateTraceData"></view>
</view>
</template>
<script>
// import {chinaGeo} from "@/common/geo/chinaGeo.js"
// import XDGeoSdk from '@/common/geo/XDGeoSdk';
export default {
props:{
dataList:{
type:Array
},
isSatellite:{
type:Boolean,
default: false
},
initZoom:{
type:Number,
default: 8
}
},
data() {
return {
// 传递给renderjs的数据
traceList:this.dataList,
};
},
watch:{
"dataList": {
handler (newValue, oldValue) {
this.traceList=this.dataList;
},
deep: true
},
},
methods: {
}
};
</script>
<!-- renderjs部分,负责处理地图DOM操作 -->
<script module="mapModule" lang="renderjs">
import * as maptalks from 'maptalks';
import dayjs from "dayjs";
export default {
data() {
return {
map: null,
lineArr:[],
marker: null,
polyline: null,
arrPoints:[],
posStart:[],
posEnd:[],
markerLayer: null,
traceLayer:null,
traceDataList:null,
containerId: `map-container-${Date.now()}-${Math.random().toString(36).substring(3,10)}`,
};
},
watch: {
},
mounted() {
// 初始化地图
this.initMap();
},
methods: {
updateTraceData(newValue, oldValue, ownerInstance, instance){
const plainData = JSON.parse(JSON.stringify(newValue));
this.traceDataList=plainData;
this.drawTrackerLine();
},
// 初始化地图
initMap() {
const that=this;
if(this.map == null){
try{
const IMAGE_VERSION="2025061801";
let tplUrl="https://gis.xdadan.com/g/m/{x}/{y}/{z}.png?v="+IMAGE_VERSION;
if(this.isSatellite){
tplUrl="https://gis.xdadan.com/g/y/{x}/{y}/{z}.png?v="+IMAGE_VERSION;
}
let option = {
crossOrigin: "Anonymous",
urlTemplate: tplUrl,
subdomains: ['0', '1', '2', '3'],
attribution: '',
}
let baseLayer = new maptalks.TileLayer('base', option)
this.map = new maptalks.Map("mapContainer", {
// 默认中心点点位
center: [118.81,32.07],
// 缩放层级
zoom: this.initZoom,
// 倾斜度
pitch: 0,
// 最小缩放层级
minZoom: 1,
// 最大缩放层级
maxZoom: 18,
fpsOnInteracting: 0,
// scaleControl: {
// 'position': {'bottom':'10px','right':'10px'},
// 'maxWidth': 100,
// 'metric': true,
// 'imperial': false
// },
// centerCross : true, // 地图中心显示红色十字符号
baseLayer:baseLayer
});
}catch(ex){
console.log("===>ex==>",ex);
}
let optV={
crossOrigin: "Anonymous",
};
this.traceLayer= new maptalks.VectorLayer('traceLayer',optV).addTo(this.map);
}
this.drawTrackerLine();
},
drawTrackerLine(){
if(this.map==null) {
return;
}
if(this.traceDataList==null){
return;
}
if(this.traceDataList.length<=0){
return ;
}
const that=this;
// 清除地图上的所有标记点
this.traceLayer.clear();
this.arrPoints=[];
this.lineArr=[];
let pointsLine=[];
let lastDayTime=null;
let lastDay=null;
let showTime=null;
let isNeedMark=0;
let isNeedAlarm = 0;
// let deviceNum=this.traceDataList[0].msisdn;
let markerBallUrl="https://lbs.jtrs56.com/static/xdico/green-ball.png";
// let deviceNum=this.dataList[0].deviceName;
for(let i=0;i<this.traceDataList.length;i++){
let itemOrig=this.traceDataList[i];
let lngOrig=itemOrig.longitude/1000000;
let latOrig=itemOrig.latitude/1000000
lastDayTime=itemOrig.createTime;
let lng=null;
let lat=null;
// if(this.layerType==1)
{
// if(isInChina(latOrig,lngOrig)){
// var gcj02Item=coordtransform.wgs84togcj02(lngOrig, latOrig);
// lng=gcj02Item[0];
// lat=gcj02Item[1];
// }else
{
lng=lngOrig;
lat=latOrig;
}
}
this.lineArr.push([lng,lat]);
let pointItem=[lng,lat];
pointsLine.push(pointItem);
this.arrPoints.push(pointItem);
}
// 起点标识
this.posStart=this.lineArr[0];
let startTimeTxt=dayjs(this.traceDataList[0].createTime).format('YYYY-MM-DD HH:mm')
// this.addTextLabel(this.traceLayer,startTimeTxt,[this.posStart[0], this.posStart[1]],[5,30]);
let startMarker = new maptalks.Marker([this.posStart[0], this.posStart[1]], {
cursor : 'pointer',
symbol: {
markerFile: "https://lbs.jtrs56.com/static/xdico/icon_start.png", // 图片地址 assets目录下的地址无法识别 --踩过坑
markerWidth: 28, // 图片大小
markerHeight: 28, // 图片大小
markerDx: 0,
markerDy: 0,
markerOpacity: 1 // 图片透明度
}
});
startMarker.setZIndex(101);
startMarker.addTo(this.traceLayer)
startMarker.on('click', function (e) {
that.showTraceInfo(startMarker,that.traceDataList[0],e);
return false;
})
this.posEnd=this.lineArr[this.lineArr.length-1];
let endTimeTxt=dayjs(this.traceDataList[this.traceDataList.length-1].createTime).format('YYYY-MM-DD HH:mm')
let endMarker = new maptalks.Marker([this.posEnd[0], this.posEnd[1]], {
cursor : 'pointer',
symbol: {
markerFile: "https://lbs.jtrs56.com/static/xdico/icon_end.png", // 图片地址 assets目录下的地址无法识别 --踩过坑
markerWidth: 28, // 图片大小
markerHeight: 28, // 图片大小
markerDx: 0,
markerDy: 0,
markerOpacity: 1 // 图片透明度
}
});
endMarker.setZIndex(101);
var line = new maptalks.LineString(this.lineArr, {
visible : true,
editable : false,
cursor : 'pointer',
draggable : false,
dragShadow : false, // display a shadow during dragging
drawOnAxis : null, // force dragging stick on a axis, can be: x, y
// 'arrowStyle' : 'classic',
// 'arrowPlacement' : 'vertex-last',
// 'markerLineWidth': 1,
// 'markerWidth': 4, // 箭头宽度
// 'markerHeight': 4, // 箭头高度
smoothness: 0.2,
symbol: {
'lineColor' : '#28F',
// 'lineColor' : '#b12d29',
'lineWidth' : 4,
'lineOpacity': 1, // 线透明度
'lineDasharray': null, // 虚线样式(如果不需要虚线则留空)
lineJoin: 'round', // miter, round, bevel
lineCap: 'round', // butt, round, square
}
})
line.setZIndex(10);
line.addTo(this.traceLayer)
this.map.fitExtent(this.traceLayer.getExtent(), 0);
},
}
};
</script>
<style scoped>
.map-container {
width: 100%;
height: 100vh;
position: relative;
}
.map-view {
width: 100%;
height: 100%;
}
.map-controls {
position: absolute;
bottom: 30px;
left: 50%;
transform: translateX(-50%);
display: flex;
gap: 10px;
padding: 10px;
background-color: rgba(255, 255, 255, 0.8);
border-radius: 8px;
z-index: 100;
}
button {
padding: 8px 16px;
background-color: #42b983;
color: white;
border: none;
border-radius: 4px;
font-size: 14px;
}
button:hover {
background-color: #359e75;
}
:deep .maptalks-attribution {
display: none !important;
}
</style>

View File

@ -3,7 +3,7 @@
"appid" : "__UNI__BCB0FB5",
"description" : "探路国际速运",
"versionName" : "1.0.2",
"versionCode" : 1062,
"versionCode" : 1066,
"transformPx" : false,
/* 5+App特有相关 */
"app-plus" : {
@ -104,20 +104,20 @@
"oauth" : {
"weixin" : {
"appid" : "wx79c800bfadd5b081",
"UniversalLinks" : ""
"UniversalLinks" : "https://emis.tanex56.com/static/ios"
}
},
"share" : {
"weixin" : {
"appid" : "wx79c800bfadd5b081",
"UniversalLinks" : ""
"UniversalLinks" : "https://emis.tanex56.com/static/ios"
}
},
"payment" : {
"weixin" : {
"__platform__" : [ "ios", "android" ],
"appid" : "wx79c800bfadd5b081",
"UniversalLinks" : ""
"UniversalLinks" : "https://emis.tanex56.com/static/ios"
}
}
},

View File

@ -14,11 +14,13 @@
"author": "",
"license": "MIT",
"dependencies": {
"dayjs": "^1.11.10",
"coordtransform": "^2.1.2",
"dayjs": "^1.11.13",
"file-saver": "2.0.5",
"js-base64": "3.7.7",
"maptalks": "^1.4.1",
"pdf-lib": "1.17.1",
"vconsole": "3.15.1",
"js-base64": "3.7.7"
"vconsole": "3.15.1"
},
"dcloudext": {
"category": [

View File

@ -34,6 +34,14 @@
<view class="mt-30">
<tpx-textarea v-model:value="submitParam.address" placeholder="详细地址(例如**街道**号**)"></tpx-textarea>
</view>
<view class="mt-30" v-if="submitParam.country=='0086'">
<tpx-input v-model:value="submitParam.enterpriseName" placeholder="企业名称"></tpx-input>
</view>
<view class="mt-30" v-if="submitParam.country=='0086'">
<tpx-input v-model:value="submitParam.enterpriseTaxId" placeholder="企业税号"></tpx-input>
</view>
<view class="mt-30">
<tpx-input v-model:value="submitParam.postCode" placeholder="邮编"></tpx-input>
@ -118,7 +126,7 @@
phone: { required: true, requiredMsg: '手机号不能为空' },
country: { required: true, requiredMsg: '国家不能为空' },
province: { required: true, requiredMsg: '省份不能为空' },
address: { required: true, requiredMsg: '详细地址不能为空' },
address: { required: true, requiredMsg: '详细地址不能为空' },
company: { required: true, requiredMsg: '公司名称不能为空' },
},
}

View File

@ -14,6 +14,8 @@ export const getAddressModels = () => {
"town": "", // 街道编号
"townName": "", // 街道名称
"address": "", // 详细地址
"enterpriseName": "", // 企业名称
"enterpriseTaxId":"", // 企业税号
"postCode": "", // 邮编
"email": null,
"company": "", // 公司

View File

@ -5,22 +5,37 @@
<template v-slot:body>
<div style="min-height: 100%;display: flex;flex-direction: column;">
<view style="position: relative;">
<map :markers="map.markers" :latitude="map.latitude" :longitude="map.longitude"
style="width: 750rpx;height: 400rpx;"
></map>
<maptalks-map
:dataList="dataList"
style="width: 750rpx;height: 70vh;"
></maptalks-map>
<!-- <map
:latitude="map.latitude"
:longitude="map.longitude"
:polyline="[...map.polyline]"
style="width: 750rpx;height: 400rpx;"
></map> -->
<!-- :markers="map.markers" -->
<!-- :polyline="map.polyline" -->
<view class="mp-base-block">
<bpd-send-reciever-tmp :value="modelInfo"></bpd-send-reciever-tmp>
<view style="position: absolute;top:5px;width: 95%;padding-left: 8px;padding-right: 8px">
<view class="mp-base-block" >
<bpd-map-reciever-panel :value="modelInfo"></bpd-map-reciever-panel>
</view>
</view>
<view class="mp-base-block blackbg" @click="makePhoneCall(modelInfo.takePieceEmployeePhone)">
<u-row justify="between">
<u-row>
<tpx-image :src="getCdnUrl('post/run.png')" width="30" height="30"></tpx-image>
<view class="ml-20">探路小哥 - {{modelInfo.takePieceEmployeeName}}</view>
<view style="position: absolute;top:60vh;width: 95%;padding-left: 8px;padding-right: 8px">
<view class="mp-base-block blackbg" @click="makePhoneCall(modelInfo.takePieceEmployeePhone)">
<u-row justify="between">
<u-row>
<tpx-image :src="getCdnUrl('post/run.png')" width="30" height="30"></tpx-image>
<view class="ml-20">探路小哥 - {{modelInfo.takePieceEmployeeName}}</view>
</u-row>
<tpx-image v-if="modelInfo.takePieceEmployeePhone" :src="getCdnUrl('post/call.png')" width="60" height="60"></tpx-image>
</u-row>
<tpx-image v-if="modelInfo.takePieceEmployeePhone" :src="getCdnUrl('post/call.png')" width="60" height="60"></tpx-image>
</u-row>
</view>
</view>
</view>
@ -50,9 +65,14 @@
</template>
<script>
import * as apiService from "@/common/api"
import BpdSendRecieverTmp from "@/components/buns-post-detail-templates/bpd-send-reciever-tmp"
import coordtransform from 'coordtransform';
import * as apiService from "@/common/api"
import BpdMapRecieverPanel from "@/components/buns-post-detail-templates/bpd-map-reciever-panel"
import maptalksMap from "@/components/map-talks/maptalks-panel"
// maptalksMap
export default {
props: {
@ -62,13 +82,14 @@
return this.$store.getters.dicData
},
},
components: { BpdSendRecieverTmp },
components: { BpdMapRecieverPanel,maptalksMap },
data() {
return {
queryOption: {
billCode: '', // 运单id
},
modelInfo: {},
dataList:[],
map: {
latitude: 23.106574, //纬度
longitude: 113.324587, //经度
@ -87,7 +108,13 @@
bgColor: '#B12D29',
padding: '10'
}
}]
}],
polyline: [{
points: [],
color: '#28f',
width: 6,
arrowLine: true,
}],
}
}
},
@ -106,7 +133,42 @@
let res = await apiService.getOrderDetail({billCode: this.queryOption.billCode, _loading: true})
// 通过对象合并才能修改父级 数据
Object.assign(this.modelInfo, res.data || {})
}
const resLbs = await apiService.getLbsRecordListByBillCode({
billCode: this.queryOption.billCode
});
// console.log("=resLbs==>",resLbs);
if (resLbs && resLbs.code === 200) {
let lbsRecordList=resLbs.data.lbsRecordList;
if( lbsRecordList && lbsRecordList.length>0){
let currentInfo=lbsRecordList[lbsRecordList.length-1];
this.map.latitude=this.cvtToWgs84(currentInfo.longitude, currentInfo.latitude)[1];
this.map.longitude=this.cvtToWgs84(currentInfo.longitude, currentInfo.latitude)[0];
this.dataList=lbsRecordList;
const points = lbsRecordList.map(item => ({
latitude: this.cvtToWgs84(item.longitude, item.latitude)[1],
longitude: this.cvtToWgs84(item.longitude, item.latitude)[0]
}));
// console.log("===>",points);
this.map.polyline[0].points = points;
}
}
},
cvtToWgs84(longitude, latitude) {
let lng = longitude / 1000000;
let lat = latitude / 1000000;
return coordtransform.wgs84togcj02(lng, lat);
}
}
}
</script>
@ -182,4 +244,7 @@
}
}
:deep .maptalks-attribution {
display: none !important;
}
</style>

View File

@ -97,13 +97,13 @@
</view>
<view v-show="submitParam.pickupMethod == 1" class="yunf-input-item">
<tpx-select v-model:value="submitParam.operateEmployeeCode" v-model:resObject="caozuoRes" v-model:text="submitParam.operateEmployeeName" :getListFun="getOpStaffList" :transKeyVal="{valKey: 'empCode',titleKey: 'empName'}" placeholder="请选择操作员">
<tpx-select v-model:value="submitParam.operateEmployeeCode" v-model:resObject="caozuoRes" v-model:text="submitParam.operateEmployeeName" :getListFun="getOpStaffList" :transKeyVal="{valKey: 'empCode',titleKey: 'empName'}" :searchParam="operateEmployeeSearchParam" placeholder="请选择操作员">
<tpx-text-item label="操作员" :value="submitParam.operateEmployeeName"></tpx-text-item>
</tpx-select>
</view>
<view v-show="submitParam.pickupMethod == 2" class="yunf-input-item">
<tpx-select v-model:value="submitParam.takePieceEmployeeCode" v-model:resObject="shoupaiRes" v-model:text="submitParam.takePieceEmployeeName" :getListFun="getRSDStaffList" :transKeyVal="{valKey: 'empCode',titleKey: 'empName'}" placeholder="请选择收派员">
<tpx-select v-model:value="submitParam.takePieceEmployeeCode" v-model:resObject="shoupaiRes" v-model:text="submitParam.takePieceEmployeeName" :getListFun="getRSDStaffList" :transKeyVal="{valKey: 'empCode',titleKey: 'empName'}" :searchParam="takePieceEmployeeSearchParam" placeholder="请选择收派员">
<tpx-text-item label="收派员" :value="submitParam.takePieceEmployeeName"></tpx-text-item>
</tpx-select>
</view>
@ -214,7 +214,7 @@
<view class="yunf-input-item">
<tpx-text-item label="合同号">
<template v-slot:right>
<tpx-input v-model:value="submitParam.custOrderId" inputAlign="right"></tpx-input>
<tpx-input v-model:value="submitParam.custOrderId" inputAlign="left"></tpx-input>
</template>
</tpx-text-item>
</view>
@ -242,7 +242,7 @@
<view class="com-section mt-30" @click="handleDialogClick(goodChooseModal)">
<u-row justify="space-between">
<text>发货信息(进仓情况)</text>
<text>货物信息</text>
<u-icon name="edit-pen" size="42"></u-icon>
</u-row>
</view>
@ -368,6 +368,16 @@
sendSiteCode: this.submitParam.sendSiteCode,
}
},
operateEmployeeSearchParam(){
return {
ownerSiteCode: this.submitParam.startSiteCode,
}
},
takePieceEmployeeSearchParam(){
return {
ownerSiteCode: this.submitParam.startSiteCode,
}
}
},
data() {
return this.getDefaultData()

View File

@ -33,6 +33,13 @@
</view>
<view class="dt-block">
<view class="dt-tle">
<view class="t1">物流动态</view>
<view class="t2">
<u-button @click="goto(`post/locus?billCode=${searchParam.billCode}`)" shape="circle" :plain="true" custom-style="height: 50rpx;font-size:28rpx;">查看轨迹</u-button>
</view>
</view>
<u-line margin="20rpx 0 20rpx"></u-line>
<view class="mb-20">
<buns-locus-pos :billCode="searchParam.billCode" ref="lcusRef"></buns-locus-pos>
</view>