1、完善配载
2、调整客商 3、调整临时额度 4、新增表头拖拽排序
This commit is contained in:
@@ -2179,7 +2179,12 @@
|
||||
<template #default="{ row }">{{ formatFileSize(row.size) }}</template>
|
||||
</el-table-column>
|
||||
<el-table-column prop="uploadUserName" label="上传人" width="140" />
|
||||
<el-table-column prop="uploadTime" label="上传时间" width="180" sortable/>
|
||||
<el-table-column
|
||||
prop="uploadTime"
|
||||
label="上传时间"
|
||||
:width="config.detailAttachmentUploadTimeWidth || 180"
|
||||
sortable
|
||||
/>
|
||||
</el-table>
|
||||
</section-card>
|
||||
</div>
|
||||
|
||||
@@ -138,9 +138,9 @@
|
||||
>
|
||||
<el-option
|
||||
v-for="item in carrierOptions"
|
||||
:key="item.id || item.customerName || item.carrierName"
|
||||
:label="item.customerName || item.carrierName || item.name"
|
||||
:value="item.customerName || item.carrierName || item.name"
|
||||
:key="item.id || item.fullName || item.customerName || item.carrierName"
|
||||
:label="item.fullName || item.customerName || item.carrierName || item.name"
|
||||
:value="item.fullName || item.customerName || item.carrierName || item.name"
|
||||
/>
|
||||
</el-select>
|
||||
</el-form-item>
|
||||
@@ -214,7 +214,7 @@
|
||||
<div class="loading-manage-page__search-actions">
|
||||
<el-button type="primary" @click="handleSearch">查询</el-button>
|
||||
<el-button @click="handleResetSearch">重置</el-button>
|
||||
<el-link type="primary" @click="searchExpanded = !searchExpanded">{{ searchExpanded ? '收起筛选' : '展开筛选' }}</el-link>
|
||||
<el-link type="primary" @click="searchExpanded = !searchExpanded">{{ searchExpanded ? '收起' : '展开' }}</el-link>
|
||||
</div>
|
||||
</div>
|
||||
</el-form>
|
||||
@@ -350,7 +350,29 @@
|
||||
@closed="resetLoadingDialog"
|
||||
>
|
||||
<div v-loading="dialogLoading" class="loading-manage-dialog__body">
|
||||
<div v-if="dialogReadonly" class="loading-detail">
|
||||
<section-card title="配载单详情">
|
||||
<div class="loading-detail__summary">
|
||||
<div class="loading-detail__heading">配载单详情</div>
|
||||
<div>{{ dialogForm.loadingNo || '-' }}</div>
|
||||
<div><el-tag :type="detailStatusType">{{ statusText(dialogForm) }}</el-tag></div>
|
||||
<div><el-tag type="warning">{{ dialogForm.transportType || '-' }}</el-tag></div>
|
||||
</div>
|
||||
<div class="loading-detail__task-row">
|
||||
<div class="loading-detail__field"><span class="loading-detail__label">任务信息</span><span class="loading-detail__value">{{ taskSummary }}</span></div>
|
||||
<div class="loading-detail__field"><span class="loading-detail__label">附件</span><span class="loading-detail__value"><el-link v-for="file in detailAttachments" :key="file.url || file.name" type="primary" @click="previewAttachment(file)">{{ file.name }}</el-link><span v-if="!detailAttachments.length">-</span></span></div>
|
||||
</div>
|
||||
</section-card>
|
||||
<section-card>
|
||||
<template #title><span class="loading-detail__route-title">运输路线<el-link type="primary" @click="openRouteChangeDialog">变更运输路线</el-link></span></template>
|
||||
<div v-if="routeNodes.length" class="loading-detail__steps"><div v-for="(node, index) in routeNodes" :key="node.key || index" class="loading-detail__step"><div class="loading-detail__step-line"><span :class="['loading-detail__step-dot', index === 0 ? 'start' : index === routeNodes.length - 1 ? 'end' : 'middle']">{{ index === 0 ? '起' : index === routeNodes.length - 1 ? '终' : '经' }}</span></div><div class="loading-detail__step-address">{{ node.address }}</div><div class="loading-detail__step-tags"><el-tag v-for="tag in node.tags || []" :key="tag" size="small">{{ tag }}</el-tag></div></div></div><el-empty v-else description="暂无路线" :image-size="60" />
|
||||
</section-card>
|
||||
<section-card title="货物信息"><el-table :data="cargoRows" border height="220"><el-table-column type="index" label="序号" width="70"/><el-table-column prop="projectName" label="项目名称" min-width="140"/><el-table-column prop="cargoName" label="货物名称" min-width="140"/><el-table-column prop="cargoType" label="货物类型" min-width="120"/><el-table-column prop="packageType" label="包装" min-width="100"/><el-table-column prop="weight" label="重量(吨)" min-width="110"/><el-table-column prop="volume" label="体积(方)" min-width="110"/><el-table-column prop="quantity" label="数量" min-width="90"/><el-table-column prop="materialCode" label="物料编码" min-width="120"/><el-table-column prop="equipmentCode" label="设备编码" min-width="120"/><el-table-column prop="brand" label="品牌" min-width="120"/><el-table-column prop="specificationModel" label="规格型号" min-width="140"/><el-table-column prop="remark" label="备注" min-width="160"/><el-table-column prop="unitPrice" label="货物单价(元)" min-width="140"/><el-table-column prop="planDate" label="计划日期" min-width="130"/></el-table></section-card>
|
||||
<section-card title="关联运单信息"><el-table :data="selectedWaybillRows" border><el-table-column type="index" label="序号" width="70"/><el-table-column prop="waybillNo" label="运单号" min-width="150"><template #default="{ row }"><el-link type="primary">{{ row.waybillNo || '-' }}</el-link></template></el-table-column><el-table-column label="配载单号" min-width="150"><template #default>{{ dialogForm.loadingNo || '-' }}</template></el-table-column><el-table-column prop="projectName" label="项目名称" min-width="150"/><el-table-column prop="customerName" label="客户" min-width="140"/><el-table-column prop="departureAddress" label="发货地址" min-width="220" show-overflow-tooltip/><el-table-column prop="arrivalAddress" label="到货地址" min-width="220" show-overflow-tooltip/></el-table></section-card>
|
||||
<div class="loading-detail__bottom-grid"><section-card title="运输节点"><el-timeline v-if="processNodes.length"><el-timeline-item v-for="(item, index) in processNodes" :key="item.id || index" :timestamp="item.time || ''">{{ item.name || item.nodeName || item.label }}</el-timeline-item></el-timeline><el-empty v-else description="暂无运输节点" :image-size="50"/></section-card><section-card title="物流轨迹"><template #extra><div class="loading-detail__track-actions"><el-button plain @click="handleTrackAction('playback')">轨迹回放</el-button><el-button plain @click="handleTrackAction('locate')">实时定位</el-button></div></template><div ref="detailAmap" class="loading-detail__map"></div></section-card></div>
|
||||
</div>
|
||||
<el-form
|
||||
v-else
|
||||
ref="loadingFormRef"
|
||||
:model="dialogForm"
|
||||
:disabled="dialogReadonly"
|
||||
@@ -358,102 +380,9 @@
|
||||
label-width="auto"
|
||||
class="loading-manage-dialog__form"
|
||||
>
|
||||
<section-card title="配载基本信息">
|
||||
<div class="loading-manage-dialog__grid">
|
||||
<el-form-item label="配载单号">
|
||||
<el-input v-model="dialogForm.loadingNo" disabled placeholder="系统自动生成" />
|
||||
</el-form-item>
|
||||
<el-form-item label="运输类型" required>
|
||||
<el-select
|
||||
v-model="dialogForm.transportType"
|
||||
filterable
|
||||
clearable
|
||||
placeholder="请选择"
|
||||
@visible-change="visible => visible && loadTransportTypeOptions()"
|
||||
>
|
||||
<el-option
|
||||
v-for="item in transportTypeOptions"
|
||||
:key="item.value"
|
||||
:label="item.label"
|
||||
:value="item.value"
|
||||
/>
|
||||
</el-select>
|
||||
</el-form-item>
|
||||
<el-form-item label="项目名称">
|
||||
<el-input v-model="dialogForm.projectName" readonly placeholder="从待配载运单带出" />
|
||||
</el-form-item>
|
||||
<el-form-item label="客户名称">
|
||||
<el-input v-model="dialogForm.customerName" readonly placeholder="从待配载运单带出" />
|
||||
</el-form-item>
|
||||
<el-form-item label="原始单号">
|
||||
<el-input v-model="dialogForm.originalNo" readonly placeholder="从待配载运单带出" />
|
||||
</el-form-item>
|
||||
<el-form-item label="运单批次号">
|
||||
<el-input v-model="dialogForm.batchNo" clearable placeholder="请输入" />
|
||||
</el-form-item>
|
||||
<el-form-item label="数据来源">
|
||||
<el-select v-model="dialogForm.dataSource" clearable placeholder="请选择">
|
||||
<el-option
|
||||
v-for="item in dataSourceOptions"
|
||||
:key="item.value"
|
||||
:label="item.label"
|
||||
:value="item.value"
|
||||
/>
|
||||
</el-select>
|
||||
</el-form-item>
|
||||
<el-form-item label="计划名称">
|
||||
<el-select
|
||||
v-model="dialogForm.planName"
|
||||
clearable
|
||||
filterable
|
||||
remote
|
||||
reserve-keyword
|
||||
:remote-method="loadPlanOptions"
|
||||
:loading="planLoading"
|
||||
placeholder="请输入"
|
||||
@visible-change="visible => visible && loadPlanOptions(dialogForm.planName)"
|
||||
>
|
||||
<el-option
|
||||
v-for="item in planOptions"
|
||||
:key="item.id || item.planName"
|
||||
:label="item.planName"
|
||||
:value="item.planName"
|
||||
/>
|
||||
</el-select>
|
||||
</el-form-item>
|
||||
<el-form-item label="开始日期">
|
||||
<el-date-picker
|
||||
v-model="dialogForm.startDate"
|
||||
type="date"
|
||||
format="YYYY-MM-DD"
|
||||
value-format="YYYY-MM-DD"
|
||||
placeholder="请选择"
|
||||
/>
|
||||
</el-form-item>
|
||||
<el-form-item label="结束日期">
|
||||
<el-date-picker
|
||||
v-model="dialogForm.endDate"
|
||||
type="date"
|
||||
format="YYYY-MM-DD"
|
||||
value-format="YYYY-MM-DD"
|
||||
placeholder="请选择"
|
||||
/>
|
||||
</el-form-item>
|
||||
<el-form-item label="配载子单号" class="loading-manage-dialog__span-2">
|
||||
<el-input
|
||||
v-model="dialogForm.loadingSubNos"
|
||||
readonly
|
||||
type="textarea"
|
||||
:rows="2"
|
||||
placeholder="添加待配载运单后自动生成"
|
||||
/>
|
||||
</el-form-item>
|
||||
</div>
|
||||
</section-card>
|
||||
|
||||
<section-card title="筛选待配载运单">
|
||||
<template #extra>
|
||||
<el-link v-if="!dialogReadonly" type="primary" @click="loadCandidateWaybills">筛选</el-link>
|
||||
<el-link v-if="!dialogReadonly" type="primary" @click="openCandidateSearch">筛选</el-link>
|
||||
</template>
|
||||
<div class="loading-manage-dialog__candidate-search" v-if="candidateSearchVisible">
|
||||
<el-row :gutter="16">
|
||||
@@ -584,9 +513,9 @@
|
||||
>
|
||||
<el-option
|
||||
v-for="item in carrierOptions"
|
||||
:key="item.id || item.customerName || item.carrierName"
|
||||
:label="item.customerName || item.carrierName || item.name"
|
||||
:value="item.customerName || item.carrierName || item.name"
|
||||
:key="item.id || item.fullName || item.customerName || item.carrierName"
|
||||
:label="item.fullName || item.customerName || item.carrierName || item.name"
|
||||
:value="item.fullName || item.customerName || item.carrierName || item.name"
|
||||
/>
|
||||
</el-select>
|
||||
</el-form-item>
|
||||
@@ -641,15 +570,12 @@
|
||||
</el-col>
|
||||
</el-row>
|
||||
</div>
|
||||
<div class="loading-manage-dialog__selected-summary">
|
||||
<span>已选择 {{ selectedWaybillRows.length }} 条运单</span>
|
||||
</div>
|
||||
<el-table
|
||||
ref="candidateTableRef"
|
||||
v-loading="candidateLoading"
|
||||
:data="candidateRows"
|
||||
border
|
||||
height="260"
|
||||
height="287"
|
||||
row-key="id"
|
||||
@selection-change="candidateSelectionChange"
|
||||
>
|
||||
@@ -723,7 +649,13 @@
|
||||
show-overflow-tooltip
|
||||
/>
|
||||
</el-table>
|
||||
<div class="loading-manage-dialog__pagination">
|
||||
<div class="loading-manage-dialog__table-toolbar">
|
||||
<el-button
|
||||
type="primary"
|
||||
:disabled="!candidateSelection.length || candidateAdding"
|
||||
:loading="candidateAdding"
|
||||
@click="addSelectedWaybills"
|
||||
>添加配载</el-button>
|
||||
<el-pagination
|
||||
v-model:current-page="candidatePage.currentPage"
|
||||
v-model:page-size="candidatePage.pageSize"
|
||||
@@ -736,64 +668,66 @@
|
||||
</div>
|
||||
</section-card>
|
||||
|
||||
<section-card title="待配载列表">
|
||||
<el-table
|
||||
:data="selectedWaybillRows"
|
||||
border
|
||||
class="loading-manage-dialog__selected-table"
|
||||
>
|
||||
<el-table-column type="index" label="序号" width="70" align="center" />
|
||||
<el-table-column prop="waybillNo" label="运单号" min-width="150">
|
||||
<template #default="{ row }">
|
||||
<el-link type="primary">{{ row.waybillNo }}</el-link>
|
||||
</template>
|
||||
</el-table-column>
|
||||
<el-table-column prop="projectName" label="项目名称" min-width="160" />
|
||||
<el-table-column
|
||||
prop="departureAddress"
|
||||
label="发货地"
|
||||
min-width="220"
|
||||
show-overflow-tooltip
|
||||
/>
|
||||
<el-table-column
|
||||
prop="arrivalAddress"
|
||||
label="到货地"
|
||||
min-width="220"
|
||||
show-overflow-tooltip
|
||||
/>
|
||||
<el-table-column label="操作" width="110" fixed="right">
|
||||
<template #default="{ $index }">
|
||||
<el-link
|
||||
v-if="!dialogReadonly"
|
||||
type="primary"
|
||||
@click="removeSelectedWaybill($index)"
|
||||
>移除</el-link>
|
||||
</template>
|
||||
</el-table-column>
|
||||
</el-table>
|
||||
</section-card>
|
||||
<div class="loading-manage-dialog__waybill-route-layout">
|
||||
<section-card title="待配载列表">
|
||||
<el-table
|
||||
:data="selectedWaybillRows"
|
||||
border
|
||||
class="loading-manage-dialog__selected-table"
|
||||
>
|
||||
<el-table-column type="index" label="序号" width="70" align="center" />
|
||||
<el-table-column prop="waybillNo" label="运单号" min-width="150">
|
||||
<template #default="{ row }">
|
||||
<el-link type="primary">{{ row.waybillNo }}</el-link>
|
||||
</template>
|
||||
</el-table-column>
|
||||
<el-table-column prop="projectName" label="项目名称" min-width="160" />
|
||||
<el-table-column
|
||||
prop="departureAddress"
|
||||
label="发货地"
|
||||
min-width="220"
|
||||
show-overflow-tooltip
|
||||
/>
|
||||
<el-table-column
|
||||
prop="arrivalAddress"
|
||||
label="到货地"
|
||||
min-width="220"
|
||||
show-overflow-tooltip
|
||||
/>
|
||||
<el-table-column label="操作" width="110" fixed="right">
|
||||
<template #default="{ $index }">
|
||||
<el-link
|
||||
v-if="!dialogReadonly"
|
||||
type="danger"
|
||||
@click="removeSelectedWaybill($index)"
|
||||
>删除</el-link>
|
||||
</template>
|
||||
</el-table-column>
|
||||
</el-table>
|
||||
</section-card>
|
||||
|
||||
<section-card title="路线信息">
|
||||
<div class="loading-manage-dialog__route-list" v-if="routeNodes.length">
|
||||
<div
|
||||
v-for="(node, index) in routeNodes"
|
||||
:key="node.key"
|
||||
class="loading-manage-dialog__route-item"
|
||||
draggable="true"
|
||||
@dragstart="handleRouteDragStart(index)"
|
||||
@dragover.prevent
|
||||
@drop="handleRouteDrop(index)"
|
||||
>
|
||||
<el-icon class="loading-manage-dialog__route-handle"><Rank /></el-icon>
|
||||
<span class="loading-manage-dialog__route-type">{{ routeTypeText(index) }}</span>
|
||||
<span class="loading-manage-dialog__route-address">{{ node.address }}</span>
|
||||
<span class="loading-manage-dialog__route-tags">
|
||||
<el-tag v-for="tag in node.tags" :key="tag" size="small">{{ tag }}</el-tag>
|
||||
</span>
|
||||
</div>
|
||||
</div>
|
||||
<el-empty v-else description="添加待配载运单后自动生成路线" :image-size="72" />
|
||||
</section-card>
|
||||
<section-card title="线路编辑">
|
||||
<div class="loading-manage-dialog__route-list" v-if="routeNodes.length">
|
||||
<div
|
||||
v-for="(node, index) in routeNodes"
|
||||
:key="node.key"
|
||||
class="loading-manage-dialog__route-item"
|
||||
draggable="true"
|
||||
@dragstart="handleRouteDragStart(index)"
|
||||
@dragover.prevent
|
||||
@drop="handleRouteDrop(index)"
|
||||
>
|
||||
<el-icon class="loading-manage-dialog__route-handle"><Rank /></el-icon>
|
||||
<span class="loading-manage-dialog__route-type">{{ routeTypeText(index) }}</span>
|
||||
<span class="loading-manage-dialog__route-address">{{ node.address }}</span>
|
||||
<span class="loading-manage-dialog__route-tags">
|
||||
<el-tag v-for="tag in node.tags" :key="tag" size="small">{{ tag }}</el-tag>
|
||||
</span>
|
||||
</div>
|
||||
</div>
|
||||
<el-empty v-else description="添加待配载运单后自动生成路线" :image-size="72" />
|
||||
</section-card>
|
||||
</div>
|
||||
|
||||
<section-card title="货物信息">
|
||||
<el-table :data="cargoRows" border class="loading-manage-dialog__cargo-table">
|
||||
@@ -805,11 +739,13 @@
|
||||
<el-table-column prop="weight" label="重量(吨)" min-width="120" />
|
||||
<el-table-column prop="volume" label="体积(方)" min-width="120" />
|
||||
<el-table-column prop="quantity" label="数量" min-width="100" />
|
||||
<el-table-column prop="planDate" label="计划日期" min-width="130" sortable/>
|
||||
<el-table-column prop="unitPrice" label="货物单价(元)" min-width="150" />
|
||||
<el-table-column prop="materialCode" label="物料编码" min-width="130" />
|
||||
<el-table-column prop="equipmentCode" label="设备编码" min-width="130" />
|
||||
<el-table-column prop="brand" label="品牌" min-width="120" />
|
||||
<el-table-column prop="specificationModel" label="规格型号" min-width="140" />
|
||||
<el-table-column prop="remark" label="备注" min-width="180" show-overflow-tooltip />
|
||||
<el-table-column prop="unitPrice" label="货物单价(元)" min-width="150" />
|
||||
<el-table-column prop="planDate" label="计划日期" min-width="130" sortable />
|
||||
</el-table>
|
||||
</section-card>
|
||||
|
||||
@@ -837,9 +773,9 @@
|
||||
>
|
||||
<el-option
|
||||
v-for="item in carrierOptions"
|
||||
:key="item.id || item.customerName || item.carrierName"
|
||||
:label="item.customerName || item.carrierName || item.name"
|
||||
:value="item.customerName || item.carrierName || item.name"
|
||||
:key="item.id || item.fullName || item.customerName || item.carrierName"
|
||||
:label="item.fullName || item.customerName || item.carrierName || item.name"
|
||||
:value="item.fullName || item.customerName || item.carrierName || item.name"
|
||||
/>
|
||||
</el-select>
|
||||
</el-form-item>
|
||||
@@ -939,6 +875,30 @@
|
||||
</div>
|
||||
</template>
|
||||
</el-dialog>
|
||||
<el-dialog v-model="routeChangeVisible" title="变更运输路线" append-to-body destroy-on-close width="78%" class="loading-route-change-dialog">
|
||||
<el-tabs v-model="routeChangeTab">
|
||||
<el-tab-pane label="变更路线" name="change">
|
||||
<section-card title="关联子运单地址">
|
||||
<el-table :data="routeChangeRows" border>
|
||||
<el-table-column type="index" label="序号" width="70" />
|
||||
<el-table-column prop="waybillNo" label="运单号" min-width="150"><template #default="{ row }"><el-link type="primary">{{ row.waybillNo || '-' }}</el-link></template></el-table-column>
|
||||
<el-table-column prop="projectName" label="项目名称" min-width="160" />
|
||||
<el-table-column label="发货地" min-width="310"><template #default="{ row }"><div class="loading-route-change-dialog__original">原:{{ row.originalDepartureAddress || '-' }}</div><el-input v-model="row.departureAddress" placeholder="请选择或输入地址" @input="updateRouteChangeNodes"><template #suffix><el-icon class="loading-route-change-dialog__location" @click="openCommonAddressDialog(row, 'departure')"><Location /></el-icon></template></el-input></template></el-table-column>
|
||||
<el-table-column label="到货地" min-width="310"><template #default="{ row }"><div class="loading-route-change-dialog__original">原:{{ row.originalArrivalAddress || '-' }}</div><el-input v-model="row.arrivalAddress" placeholder="请选择或输入地址" @input="updateRouteChangeNodes"><template #suffix><el-icon class="loading-route-change-dialog__location" @click="openCommonAddressDialog(row, 'arrival')"><Location /></el-icon></template></el-input></template></el-table-column>
|
||||
</el-table>
|
||||
</section-card>
|
||||
<section-card title="路线编辑"><template #extra><span class="loading-route-change-dialog__hint">拖拽调整顺序</span></template><div v-if="routeChangeNodes.length" class="loading-route-change-dialog__route-list"><div v-for="(node, index) in routeChangeNodes" :key="node.key || index" class="loading-route-change-dialog__route-item" draggable="true" @dragstart="handleRouteChangeDragStart(index)" @dragover.prevent @drop="handleRouteChangeDrop(index)"><span class="loading-route-change-dialog__route-type">{{ routeChangeTypeText(index) }}</span><span>{{ node.address }}</span><span class="loading-route-change-dialog__tags"><el-tag v-for="tag in node.tags || []" :key="tag" size="small">{{ tag }}</el-tag></span><el-icon><Rank /></el-icon></div></div><el-empty v-else description="暂无路线" :image-size="60" /></section-card>
|
||||
<el-form label-width="auto"><el-form-item label="变更备注"><el-input v-model="routeChangeRemark" type="textarea" :rows="1" maxlength="200" show-word-limit placeholder="请输入" /></el-form-item></el-form>
|
||||
</el-tab-pane>
|
||||
<el-tab-pane label="变更记录" name="records"><el-table :data="routeChangeRecords" border><el-table-column prop="changeTime" label="变更时间" min-width="170"/><el-table-column prop="changeUser" label="变更人" min-width="120"/><el-table-column prop="content" label="变更内容" min-width="360"><template #default="{ row }"><div class="loading-route-change-dialog__record-content">{{ row.content || '-' }}</div></template></el-table-column><el-table-column prop="remark" label="备注" min-width="200" show-overflow-tooltip/></el-table><el-empty v-if="!routeChangeRecords.length" description="暂无变更记录" :image-size="60"/></el-tab-pane>
|
||||
</el-tabs>
|
||||
<template #footer><el-button @click="routeChangeVisible = false">关闭</el-button><el-button v-if="routeChangeTab === 'change'" type="primary" @click="confirmRouteChange">确认变更</el-button></template>
|
||||
</el-dialog>
|
||||
<el-dialog v-model="commonAddressVisible" title="选择常用地址" append-to-body width="900px" class="loading-common-address-dialog">
|
||||
<div class="loading-common-address-dialog__toolbar"><el-input v-model="commonAddressQuery.addressName" clearable placeholder="请输入地址名称" @keyup.enter="loadCommonAddresses"/><el-button type="primary" @click="loadCommonAddresses">查询</el-button></div>
|
||||
<el-table v-loading="commonAddressLoading" :data="commonAddressRows" border @row-dblclick="selectCommonAddress"><el-table-column prop="addressName" label="地址名称" min-width="180"/><el-table-column prop="regionName" label="区域" min-width="180"/><el-table-column prop="detailAddress" label="详细地址" min-width="260"/><el-table-column label="操作" width="90"><template #default="{ row }"><el-link type="primary" @click="selectCommonAddress(row)">选择</el-link></template></el-table-column></el-table>
|
||||
<template #footer><el-pagination v-model:current-page="commonAddressPage.currentPage" v-model:page-size="commonAddressPage.pageSize" layout="total, prev, pager, next" :total="commonAddressPage.total" @current-change="loadCommonAddresses"/><el-button @click="commonAddressVisible = false">关闭</el-button></template>
|
||||
</el-dialog>
|
||||
</basic-container>
|
||||
</template>
|
||||
|
||||
@@ -956,6 +916,8 @@ import {
|
||||
import { getParentOptions as getCargoTypeOptions } from '@/api/base/cargo-type';
|
||||
import { getList as getCustomerList } from '@/api/vehicle/customer-archive';
|
||||
import { getList as getDriverList } from '@/api/transportCapacity/driver';
|
||||
import { getList as getProcessConfigList } from '@/api/business/process-config';
|
||||
import { getList as getCommonAddressList } from '@/api/base/common-address';
|
||||
import {
|
||||
carrierTypeOptions,
|
||||
loadingManageConfig,
|
||||
@@ -963,11 +925,14 @@ import {
|
||||
loadingStatusOptions,
|
||||
} from '@/option/business/loading-manage';
|
||||
import { ElMessage, ElMessageBox } from 'element-plus';
|
||||
import { Rank, Refresh, Setting } from '@element-plus/icons-vue';
|
||||
import { Location, Rank, Refresh, Setting } from '@element-plus/icons-vue';
|
||||
import dayjs from 'dayjs';
|
||||
|
||||
const defaultTransportType = '公路整车';
|
||||
const defaultCandidateTransportType = '公路运输';
|
||||
const defaultTransportType = '';
|
||||
const defaultCandidateTransportType = '';
|
||||
const AMAP_KEY = '653b7cf105ad7fb8ec9b2f5198ade315';
|
||||
const AMAP_SECURITY_CODE = '5aab65c632e48ebae0d0e28f5b28e21a';
|
||||
let detailAmapLoader;
|
||||
|
||||
const createSearchForm = () => ({
|
||||
loadingNo: '',
|
||||
@@ -1091,6 +1056,7 @@ export default {
|
||||
data() {
|
||||
return {
|
||||
Rank,
|
||||
Location,
|
||||
Refresh,
|
||||
Setting,
|
||||
loading: false,
|
||||
@@ -1102,7 +1068,7 @@ export default {
|
||||
total: 0,
|
||||
pageSizes: [10, 20, 50, 100],
|
||||
},
|
||||
searchExpanded: true,
|
||||
searchExpanded: false,
|
||||
searchForm: createSearchForm(),
|
||||
selectionRows: [],
|
||||
dialogVisible: false,
|
||||
@@ -1110,9 +1076,10 @@ export default {
|
||||
dialogLoading: false,
|
||||
dialogSaving: '',
|
||||
dialogForm: createDialogForm(),
|
||||
candidateSearchVisible: true,
|
||||
candidateSearchVisible: false,
|
||||
candidateQuery: createCandidateSearchForm(),
|
||||
candidateLoading: false,
|
||||
candidateAdding: false,
|
||||
candidateRows: [],
|
||||
candidateSelection: [],
|
||||
candidatePage: {
|
||||
@@ -1142,6 +1109,21 @@ export default {
|
||||
statusOptions: loadingStatusOptions,
|
||||
dataSourceOptions: loadingManageConfig.dataSourceOptions,
|
||||
config: loadingManageConfig,
|
||||
processNodes: [],
|
||||
routeChangeVisible: false,
|
||||
routeChangeTab: 'change',
|
||||
routeChangeRows: [],
|
||||
routeChangeNodes: [],
|
||||
routeChangeRemark: '',
|
||||
routeChangeRecords: [],
|
||||
routeChangeDragIndex: -1,
|
||||
commonAddressVisible: false,
|
||||
commonAddressLoading: false,
|
||||
commonAddressRows: [],
|
||||
commonAddressQuery: { addressName: '' },
|
||||
commonAddressPage: { currentPage: 1, pageSize: 10, total: 0 },
|
||||
commonAddressTarget: null,
|
||||
detailAmap: null,
|
||||
};
|
||||
},
|
||||
computed: {
|
||||
@@ -1158,6 +1140,20 @@ export default {
|
||||
};
|
||||
return titleMap[this.dialogMode] || '配载管理';
|
||||
},
|
||||
detailStatusType() {
|
||||
const typeMap = { pending: 'success', running: 'success', completed: 'info', cancelled: 'info', draft: 'warning' };
|
||||
return typeMap[this.dialogForm.businessStatus] || 'info';
|
||||
},
|
||||
taskSummary() {
|
||||
return [this.dialogForm.carrierName, this.dialogForm.driverName, this.dialogForm.vehicleNo]
|
||||
.filter(Boolean)
|
||||
.join(' / ') || '-';
|
||||
},
|
||||
detailAttachments() {
|
||||
return parseJsonArray(this.dialogForm.attachmentsJson || this.dialogForm.attachmentJson).map(item =>
|
||||
typeof item === 'string' ? { name: item.split('/').pop(), url: item } : { name: item.name || item.fileName || '附件', url: item.url || item.link || item.fileUrl }
|
||||
);
|
||||
},
|
||||
},
|
||||
mounted() {
|
||||
this.loadTransportTypeOptions();
|
||||
@@ -1294,6 +1290,9 @@ export default {
|
||||
this.dialogForm.loadingSubNos
|
||||
);
|
||||
this.restoreRouteAndCargo();
|
||||
this.restoreRouteChangeRecords();
|
||||
await this.loadProcessNodes();
|
||||
this.$nextTick(() => this.initDetailAmap());
|
||||
await this.loadCandidateWaybills();
|
||||
} else {
|
||||
this.dialogForm = createDialogForm();
|
||||
@@ -1310,6 +1309,8 @@ export default {
|
||||
this.dialogLoading = false;
|
||||
},
|
||||
resetDialogData() {
|
||||
this.detailAmap?.destroy?.();
|
||||
this.detailAmap = null;
|
||||
this.dialogForm = createDialogForm();
|
||||
this.candidateQuery = createCandidateSearchForm();
|
||||
this.candidateRows = [];
|
||||
@@ -1319,7 +1320,8 @@ export default {
|
||||
this.cargoRows = [];
|
||||
this.candidatePage.currentPage = 1;
|
||||
this.candidatePage.total = 0;
|
||||
this.candidateSearchVisible = true;
|
||||
this.candidateSearchVisible = false;
|
||||
this.processNodes = [];
|
||||
},
|
||||
clearLoadingDialog() {
|
||||
this.resetDialogData();
|
||||
@@ -1333,6 +1335,164 @@ export default {
|
||||
: this.buildRouteNodes(this.selectedWaybillRows);
|
||||
this.cargoRows = cargoRows.length ? cargoRows : this.buildCargoRows(this.selectedWaybillRows);
|
||||
},
|
||||
restoreRouteChangeRecords() {
|
||||
try {
|
||||
const taskInfo = JSON.parse(this.dialogForm.taskInfoJson || '{}');
|
||||
this.routeChangeRecords = Array.isArray(taskInfo.routeChangeRecords)
|
||||
? [...taskInfo.routeChangeRecords].sort((a, b) => String(b.changeTime).localeCompare(String(a.changeTime)))
|
||||
: [];
|
||||
} catch (error) {
|
||||
this.routeChangeRecords = [];
|
||||
}
|
||||
},
|
||||
async loadProcessNodes() {
|
||||
const waybillProcess = parseJsonArray(this.selectedWaybillRows[0]?.processJson);
|
||||
if (waybillProcess.length) {
|
||||
this.processNodes = waybillProcess;
|
||||
return;
|
||||
}
|
||||
try {
|
||||
const rows = unwrapRecords(await getProcessConfigList(1, 20, { projectId: this.dialogForm.projectId, status: 1 }));
|
||||
const config = rows.find(item => item.nodeConfigJson) || {};
|
||||
this.processNodes = parseJsonArray(config.nodeConfigJson);
|
||||
} catch (error) {
|
||||
this.processNodes = [];
|
||||
}
|
||||
},
|
||||
previewAttachment(file) {
|
||||
if (!file.url) {
|
||||
ElMessage.info('暂无可预览的附件地址');
|
||||
return;
|
||||
}
|
||||
window.open(file.url, '_blank', 'noopener,noreferrer');
|
||||
},
|
||||
loadDetailAmap() {
|
||||
if (window.AMap?.Map) return Promise.resolve();
|
||||
if (!detailAmapLoader) {
|
||||
detailAmapLoader = new Promise((resolve, reject) => {
|
||||
window._AMapSecurityConfig = { securityJsCode: AMAP_SECURITY_CODE };
|
||||
const script = document.createElement('script');
|
||||
script.src = `https://webapi.amap.com/maps?v=2.0&key=${AMAP_KEY}`;
|
||||
script.async = true;
|
||||
script.onload = resolve;
|
||||
script.onerror = () => reject(new Error('高德地图组件加载失败'));
|
||||
document.body.appendChild(script);
|
||||
});
|
||||
}
|
||||
return detailAmapLoader;
|
||||
},
|
||||
initDetailAmap() {
|
||||
if (!this.$refs.detailAmap) return;
|
||||
this.loadDetailAmap()
|
||||
.then(() => {
|
||||
if (!this.detailAmap) {
|
||||
this.detailAmap = new window.AMap.Map(this.$refs.detailAmap, {
|
||||
center: [116.40769, 39.89945],
|
||||
zoom: 11,
|
||||
});
|
||||
window.AMap.plugin(['AMap.ToolBar'], () => this.detailAmap?.addControl(new window.AMap.ToolBar()));
|
||||
} else {
|
||||
this.detailAmap.resize?.();
|
||||
}
|
||||
})
|
||||
.catch(() => ElMessage.warning('高德地图加载失败'));
|
||||
},
|
||||
handleTrackAction(action) {
|
||||
ElMessage.info(action === 'playback' ? '暂无可回放的物流轨迹' : '暂无车辆实时定位数据');
|
||||
},
|
||||
openRouteChangeDialog() {
|
||||
this.routeChangeTab = 'change';
|
||||
this.routeChangeRemark = '';
|
||||
this.routeChangeRows = this.selectedWaybillRows.map(row => ({
|
||||
...row,
|
||||
originalDepartureAddress: row.departureAddress || row.departureName || '',
|
||||
originalArrivalAddress: row.arrivalAddress || row.arrivalName || '',
|
||||
departureAddress: row.departureAddress || row.departureName || '',
|
||||
arrivalAddress: row.arrivalAddress || row.arrivalName || '',
|
||||
}));
|
||||
this.routeChangeNodes = this.buildRouteNodes(this.routeChangeRows);
|
||||
this.routeChangeVisible = true;
|
||||
},
|
||||
routeChangeTypeText(index) {
|
||||
if (index === 0) return '起';
|
||||
if (index === this.routeChangeNodes.length - 1) return '终';
|
||||
return '经';
|
||||
},
|
||||
handleRouteChangeDragStart(index) {
|
||||
this.routeChangeDragIndex = index;
|
||||
},
|
||||
handleRouteChangeDrop(index) {
|
||||
if (this.routeChangeDragIndex < 0 || this.routeChangeDragIndex === index) return;
|
||||
const nodes = [...this.routeChangeNodes];
|
||||
const [node] = nodes.splice(this.routeChangeDragIndex, 1);
|
||||
nodes.splice(index, 0, node);
|
||||
this.routeChangeNodes = nodes;
|
||||
this.routeChangeDragIndex = -1;
|
||||
},
|
||||
updateRouteChangeNodes() {
|
||||
this.routeChangeNodes = this.buildRouteNodes(this.routeChangeRows);
|
||||
},
|
||||
openCommonAddressDialog(row, field) {
|
||||
this.commonAddressTarget = { row, field };
|
||||
this.commonAddressQuery = { addressName: '' };
|
||||
this.commonAddressPage.currentPage = 1;
|
||||
this.commonAddressVisible = true;
|
||||
this.loadCommonAddresses();
|
||||
},
|
||||
async loadCommonAddresses() {
|
||||
this.commonAddressLoading = true;
|
||||
try {
|
||||
const page = unwrapPage(await getCommonAddressList(this.commonAddressPage.currentPage, this.commonAddressPage.pageSize, { ...this.commonAddressQuery, allDept: 0 }));
|
||||
this.commonAddressRows = page.records;
|
||||
this.commonAddressPage.total = page.total;
|
||||
} finally {
|
||||
this.commonAddressLoading = false;
|
||||
}
|
||||
},
|
||||
selectCommonAddress(address) {
|
||||
const target = this.commonAddressTarget;
|
||||
if (!target) return;
|
||||
target.row[`${target.field}Address`] = [address.regionName, address.detailAddress || address.addressName].filter(Boolean).join('') || address.addressName || '';
|
||||
this.updateRouteChangeNodes();
|
||||
this.commonAddressVisible = false;
|
||||
},
|
||||
async confirmRouteChange() {
|
||||
const changeRows = this.routeChangeRows.filter(row => row.departureAddress !== row.originalDepartureAddress || row.arrivalAddress !== row.originalArrivalAddress);
|
||||
if (!changeRows.length && !this.routeChangeRemark) {
|
||||
ElMessage.warning('请修改地址或填写变更备注');
|
||||
return;
|
||||
}
|
||||
const content = changeRows.map(row => `${row.waybillNo || '运单'}:发货地 ${row.originalDepartureAddress} → ${row.departureAddress};到货地 ${row.originalArrivalAddress} → ${row.arrivalAddress}`).join(';') || '调整运输路线顺序';
|
||||
this.routeChangeRecords.unshift({ changeTime: dayjs().format('YYYY-MM-DD HH:mm:ss'), changeUser: '当前用户', content, remark: this.routeChangeRemark });
|
||||
let taskInfo = {};
|
||||
try {
|
||||
taskInfo = JSON.parse(this.dialogForm.taskInfoJson || '{}');
|
||||
} catch (error) {
|
||||
taskInfo = {};
|
||||
}
|
||||
this.dialogForm.taskInfoJson = JSON.stringify({
|
||||
...(typeof taskInfo === 'object' && !Array.isArray(taskInfo) ? taskInfo : {}),
|
||||
routeChangeRecords: this.routeChangeRecords,
|
||||
});
|
||||
this.selectedWaybillRows = this.routeChangeRows.map(({ originalDepartureAddress, originalArrivalAddress, ...row }) => row);
|
||||
this.routeNodes = this.routeChangeNodes;
|
||||
this.syncRouteAddressFields();
|
||||
try {
|
||||
await loadingApi.changeRoute({
|
||||
id: this.dialogForm.id,
|
||||
routeJson: JSON.stringify(this.routeNodes),
|
||||
departureAddress: this.dialogForm.departureAddress,
|
||||
transitAddress: this.dialogForm.transitAddress,
|
||||
arrivalAddress: this.dialogForm.arrivalAddress,
|
||||
taskInfoJson: this.dialogForm.taskInfoJson,
|
||||
});
|
||||
this.routeChangeVisible = false;
|
||||
ElMessage.success('路线变更已保存');
|
||||
} catch (error) {
|
||||
this.restoreRouteChangeRecords();
|
||||
throw error;
|
||||
}
|
||||
},
|
||||
async restoreWaybillRows(idsJson, loadingSubNos) {
|
||||
const ids = parseJsonArray(idsJson).filter(Boolean);
|
||||
if (ids.length) {
|
||||
@@ -1369,6 +1529,10 @@ export default {
|
||||
this.candidateLoading = false;
|
||||
}
|
||||
},
|
||||
openCandidateSearch() {
|
||||
this.candidateSearchVisible = true;
|
||||
this.loadCandidateWaybills();
|
||||
},
|
||||
handleCandidateSearch() {
|
||||
this.candidatePage.currentPage = 1;
|
||||
this.loadCandidateWaybills();
|
||||
@@ -1390,20 +1554,38 @@ export default {
|
||||
candidateSelectionChange(rows) {
|
||||
this.candidateSelection = rows || [];
|
||||
},
|
||||
addSelectedWaybills() {
|
||||
const exists = new Set(this.selectedWaybillRows.map(row => String(row.id || row.waybillNo)));
|
||||
const nextRows = [...this.selectedWaybillRows];
|
||||
this.candidateSelection.forEach(row => {
|
||||
const key = String(row.id || row.waybillNo);
|
||||
if (!exists.has(key)) {
|
||||
nextRows.push(row);
|
||||
exists.add(key);
|
||||
}
|
||||
});
|
||||
this.selectedWaybillRows = nextRows;
|
||||
this.rebuildSummaryFromWaybills();
|
||||
this.$refs.candidateTableRef?.clearSelection?.();
|
||||
this.candidateSelection = [];
|
||||
async addSelectedWaybills() {
|
||||
this.candidateAdding = true;
|
||||
try {
|
||||
const selectedRows = await Promise.all(
|
||||
this.candidateSelection.map(async row => {
|
||||
if (!row.id) return row;
|
||||
try {
|
||||
const res = await getWaybillDetail(row.id);
|
||||
return { ...row, ...(res.data?.data || res.data || {}) };
|
||||
} catch (error) {
|
||||
return row;
|
||||
}
|
||||
})
|
||||
);
|
||||
const exists = new Set(
|
||||
this.selectedWaybillRows.map(row => String(row.id || row.waybillNo))
|
||||
);
|
||||
const nextRows = [...this.selectedWaybillRows];
|
||||
selectedRows.forEach(row => {
|
||||
const key = String(row.id || row.waybillNo);
|
||||
if (!exists.has(key)) {
|
||||
nextRows.push(row);
|
||||
exists.add(key);
|
||||
}
|
||||
});
|
||||
this.selectedWaybillRows = nextRows;
|
||||
this.rebuildSummaryFromWaybills();
|
||||
this.$refs.candidateTableRef?.clearSelection?.();
|
||||
this.candidateSelection = [];
|
||||
} finally {
|
||||
this.candidateAdding = false;
|
||||
}
|
||||
},
|
||||
removeSelectedWaybill(index) {
|
||||
this.selectedWaybillRows.splice(index, 1);
|
||||
@@ -1444,17 +1626,18 @@ export default {
|
||||
},
|
||||
buildRouteNodes(rows) {
|
||||
const nodeMap = new Map();
|
||||
const appendNode = (address, tag) => {
|
||||
if (!address) return;
|
||||
if (!nodeMap.has(address)) nodeMap.set(address, { address, tags: [] });
|
||||
nodeMap.get(address).tags.push(tag);
|
||||
};
|
||||
rows.forEach((row, rowIndex) => {
|
||||
const departure = row.departureAddress || row.departureName;
|
||||
appendNode(departure, `装${rowIndex + 1}`);
|
||||
});
|
||||
rows.forEach((row, rowIndex) => {
|
||||
const arrival = row.arrivalAddress || row.arrivalName;
|
||||
if (departure) {
|
||||
if (!nodeMap.has(departure)) nodeMap.set(departure, { address: departure, tags: [] });
|
||||
nodeMap.get(departure).tags.push(`装${rowIndex + 1}`);
|
||||
}
|
||||
if (arrival) {
|
||||
if (!nodeMap.has(arrival)) nodeMap.set(arrival, { address: arrival, tags: [] });
|
||||
nodeMap.get(arrival).tags.push(`卸${rowIndex + 1}`);
|
||||
}
|
||||
appendNode(arrival, `卸${rowIndex + 1}`);
|
||||
});
|
||||
return [...nodeMap.values()].map((node, index) => ({
|
||||
...node,
|
||||
@@ -1489,7 +1672,7 @@ export default {
|
||||
},
|
||||
buildCargoRows(rows) {
|
||||
return rows.flatMap(row => {
|
||||
const goodsRows = parseJsonArray(row.goodsJson);
|
||||
const goodsRows = parseJsonArray(row.goodsList || row.goodsRows || row.goodsJson);
|
||||
if (goodsRows.length) {
|
||||
return goodsRows.map(item => this.normalizeCargoRow(row, item));
|
||||
}
|
||||
@@ -1509,6 +1692,9 @@ export default {
|
||||
unitPrice: item.unitPrice || waybill.unitPrice || '',
|
||||
materialCode: item.materialCode || '',
|
||||
equipmentCode: item.equipmentCode || '',
|
||||
brand: item.brand || item.brandName || waybill.brand || '',
|
||||
specificationModel:
|
||||
item.specificationModel || item.specModel || item.specification || waybill.specificationModel || '',
|
||||
remark: item.remark || '',
|
||||
};
|
||||
},
|
||||
@@ -1694,9 +1880,6 @@ export default {
|
||||
label: item.dictValue || item.label || item.name,
|
||||
value: item.dictKey || item.value || item.dictValue || item.name,
|
||||
}));
|
||||
if (!this.transportTypeOptions.length) {
|
||||
this.transportTypeOptions = [{ label: defaultTransportType, value: defaultTransportType }];
|
||||
}
|
||||
},
|
||||
async loadProjectOptions(keyword = '') {
|
||||
this.projectLoading = true;
|
||||
@@ -1710,7 +1893,7 @@ export default {
|
||||
this.customerLoading = true;
|
||||
try {
|
||||
this.customerOptions = unwrapRecords(
|
||||
await getCustomerList(1, 20, { customerName: keyword })
|
||||
await getCustomerList(1, 20, { customerName: keyword, customerType: '承运商' })
|
||||
);
|
||||
} finally {
|
||||
this.customerLoading = false;
|
||||
@@ -1892,10 +2075,17 @@ export default {
|
||||
margin-bottom: 8px;
|
||||
}
|
||||
|
||||
.loading-manage-dialog__waybill-route-layout {
|
||||
display: grid;
|
||||
grid-template-columns: minmax(0, 2fr) minmax(320px, 1fr);
|
||||
gap: 16px;
|
||||
align-items: start;
|
||||
margin-bottom: 16px;
|
||||
}
|
||||
|
||||
.loading-manage-dialog__candidate-actions,
|
||||
.loading-manage-dialog__collapsed-search,
|
||||
.loading-manage-dialog__table-toolbar,
|
||||
.loading-manage-dialog__pagination,
|
||||
.loading-manage-dialog__footer {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
@@ -1908,16 +2098,18 @@ export default {
|
||||
margin: 10px 0;
|
||||
}
|
||||
|
||||
.loading-manage-dialog__pagination {
|
||||
padding: 10px 0 4px;
|
||||
}
|
||||
|
||||
.loading-manage-dialog__route-list {
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
gap: 8px;
|
||||
}
|
||||
|
||||
@media (max-width: 1200px) {
|
||||
.loading-manage-dialog__waybill-route-layout {
|
||||
grid-template-columns: 1fr;
|
||||
}
|
||||
}
|
||||
|
||||
.loading-manage-dialog__route-item {
|
||||
display: grid;
|
||||
grid-template-columns: 28px 36px minmax(0, 1fr) auto;
|
||||
@@ -1998,4 +2190,33 @@ export default {
|
||||
--el-table-border-color: #eff1f7;
|
||||
}
|
||||
}
|
||||
|
||||
.loading-detail {
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
gap: 8px;
|
||||
color: #303133;
|
||||
.loading-detail__summary { display: flex; align-items: center; flex-wrap: wrap; gap: 24px; padding: 4px 0 16px; }
|
||||
.loading-detail__heading { font-size: 20px; font-weight: 600; margin-right: 8px; }
|
||||
.loading-detail__route-title { display: inline-flex; align-items: center; gap: 16px; }
|
||||
.loading-detail__label { color: #909399; margin-right: 10px; }
|
||||
.loading-detail__task-row { display: grid; grid-template-columns: 1fr 1fr; gap: 24px; padding-bottom: 4px; }
|
||||
.loading-detail__field { display: flex; flex-direction: column; align-items: flex-start; gap: 8px; }
|
||||
.loading-detail__field .loading-detail__label { margin-right: 0; }
|
||||
.loading-detail__value { display: flex; flex-wrap: wrap; gap: 8px; text-align: left; }
|
||||
.loading-detail__steps { display: flex; align-items: flex-start; overflow-x: auto; padding: 8px 4px 16px; }
|
||||
.loading-detail__step { position: relative; min-width: 190px; flex: 1; text-align: center; }
|
||||
.loading-detail__step:not(:last-child)::after { position: absolute; z-index: 0; top: 16px; left: calc(50% + 25px); width: calc(100% - 50px); height: 2px; content: ''; background: #606266; }
|
||||
.loading-detail__step-line { display: flex; align-items: center; justify-content: center; }
|
||||
.loading-detail__step-dot { position: relative; z-index: 1; display: inline-flex; width: 34px; height: 34px; align-items: center; justify-content: center; color: #fff; border-radius: 4px; font-weight: 600; }
|
||||
.loading-detail__step-dot.start { background: #409eff; }.loading-detail__step-dot.middle { background: #67c23a; }.loading-detail__step-dot.end { background: #e6a23c; }
|
||||
.loading-detail__step-address { margin-top: 8px; font-weight: 600; white-space: nowrap; overflow: hidden; text-overflow: ellipsis; }
|
||||
.loading-detail__step-tags { display: flex; justify-content: center; gap: 4px; margin-top: 6px; }
|
||||
.loading-detail__bottom-grid { display: grid; grid-template-columns: 1fr 1fr; gap: 8px; }
|
||||
.loading-detail__track-actions { display: flex; gap: 8px; }
|
||||
.loading-detail__map { width: 100%; min-height: 260px; border: 1px solid #eff1f7; }
|
||||
}
|
||||
.loading-route-change-dialog { .loading-route-change-dialog__original { color: #a8abb2; line-height: 20px; margin-bottom: 4px; }.loading-route-change-dialog__location { cursor: pointer; color: #909399; }.loading-route-change-dialog__hint { color: #909399; }.loading-route-change-dialog__route-list { display: flex; flex-direction: column; gap: 8px; }.loading-route-change-dialog__route-item { display: grid; grid-template-columns: 34px minmax(0, 1fr) auto 24px; align-items: center; gap: 12px; padding: 10px 12px; background: #f5f6f7; cursor: move; }.loading-route-change-dialog__route-type { width: 30px; height: 30px; border-radius: 50%; background: #dcdfe6; text-align: center; line-height: 30px; }.loading-route-change-dialog__tags { display: flex; gap: 4px; }.loading-route-change-dialog__record-content { white-space: normal; overflow-wrap: anywhere; line-height: 22px; } }
|
||||
.loading-common-address-dialog__toolbar { display: flex; gap: 8px; margin-bottom: 12px; }.loading-common-address-dialog__toolbar .el-input { flex: 1; }
|
||||
@media (max-width: 900px) { .loading-detail__task-row, .loading-detail__bottom-grid { grid-template-columns: 1fr; } }
|
||||
</style>
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
<template>
|
||||
<business-crud-page :api="api" :config="config" :crud-option="option" :menu-width="270" />
|
||||
<business-crud-page :api="api" :config="config" :crud-option="option" :menu-width="320" />
|
||||
</template>
|
||||
|
||||
<script>
|
||||
|
||||
Reference in New Issue
Block a user