lanan-app/components/orderCard/OrderCardNew.vue
2025-10-17 15:25:04 +08:00

2275 lines
63 KiB
Vue
Raw Permalink Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

<template>
<view>
<view class="orderCard" @click="onShowDetail">
<!-- <view class="orderCardHeader">
<text class="orderCardType">{{ getRescueTypeStr() }}</text>
<text class="orderCardTitle">{{ orderData.rescuePosition }}</text>
</view> -->
<view class="orderCardEditView">
<view class="orderCardTopTitle">工单信息</view>
<view style="display: flex; justify-content: center; align-items: center;">
<!-- <view
v-if="hasRoleNew('jiuyuan') || ( !hasRoleNew('jiuyuan')) && hasRoleNew('ddzx') && orderData.dispatchLevel == 2"> -->
<view v-if="showRevokeButton || checkPermi(['rescue_dispatch_process_btn'])">
<view @click.stop="viewDispatchDetails" class="orderCardViewDispatchBtn"
style="margin-right: 12rpx;">
调度流程</view>
</view>
<!-- <view v-if="hasRoleNew('jiuyuan', 'ddzx', 'second_dispatcher') && orderData.rescueStatus < 4"> -->
<view v-if="showRevokeButton || checkPermi(['rescue_dispatch_info_btn'])">
<view @click.stop="revokeId" class="orderCardRevorkBtn" style="margin-right: 12rpx;">撤销工单</view>
</view>
<!-- <view v-if="hasRoleNew('jiuyuan', 'ddzx', 'second_dispatcher') && orderData.rescueStatus >= 4">
<view @click.stop="" class="orderCardRevorkDisabledBtn" style="margin-right: 12rpx;">撤销工单</view>
</view> -->
<view v-if="showRevokeButton || checkPermi(['rescue_dispatch_info_btn'])" class="orderCardEditBtn"
@click.stop="editOrder">编辑工单</view>
</view>
</view>
<view class="orderInfoContainer" v-if="isExpanded === false && activeTab === -1">
<!-- <view class="orderInfoContainer" v-if="!isExpanded"> -->
<view class="infoRow">
<text class="infoLabel">开始时间:</text>
<text class="infoValue">{{ formatTimestamp(orderData.rescueStartTime) || '暂无数据' }}</text>
</view>
<view class="infoRow">
<text class="infoLabel">完成时间:</text>
<text class="infoValue">{{ formatTimestamp(orderData.rescueEndTime) || '暂无数据' }}</text>
</view>
<view class="infoRow">
<text class="infoLabel">调度:</text>
<text class="infoValue">{{ orderData.secondDispatchName || '暂无数据' }}</text>
</view>
<view class="infoRow">
<text class="infoLabel">司机:</text>
<text class="infoValue">{{ orderData.driverName || '暂无数据' }}</text>
</view>
<view class="infoRow">
<text class="infoLabel">救援车辆:</text>
<text class="infoValue">{{ orderData.driverCarNum || '暂无数据' }}</text>
</view>
<view class="infoRow">
<text class="infoLabel">渠道:</text>
<text class="infoValue">{{ orderData.channel || '暂无数据' }}</text>
</view>
<view class="infoRow">
<text class="infoLabel">来源:</text>
<text class="infoValue">{{ orderData.source || '暂无数据' }}</text>
</view>
<view class="infoRow">
<text class="infoLabel">救援类型:</text>
<text class="infoValue">{{ orderData.rescueTypeStr || '暂无数据' }}</text>
</view>
<view class="infoRow">
<text class="infoLabel">客户姓名:</text>
<text class="infoValue">{{ orderData.connectionName || '暂无数据' }}</text>
</view>
<view class="infoRow">
<text class="infoLabel">客户电话:</text>
<text class="infoValue">{{ orderData.connectionPhone || '暂无数据' }}</text>
</view>
<view class="infoRow">
<text class="infoLabel">客户车牌号:</text>
<text class="infoValue">{{ orderData.licenseNum || '暂无数据' }}</text>
</view>
<view class="infoRow">
<text class="infoLabel">救援状态:</text>
<text class="infoValue">{{ orderData.rescueStatusStr || '暂无数据' }}</text>
</view>
<view class="infoRow">
<text class="infoLabel">财务状态:</text>
<text class="infoValue">{{ orderData.orderStatusStr || '暂无数据' }}</text>
</view>
</view>
<view class="orderInfoContainer" v-if="activeTab === 0 || isExpanded">
<view class="infoRow">
<text class="infoLabel" style="color: black; font-weight: bold; font-size: 32rpx;">司机信息</text>
</view>
<view class="infoRow">
<text class="infoLabel">司机姓名:</text>
<text class="infoValue">{{ orderData.driverName || '暂无数据' }}</text>
</view>
<view class="infoRow">
<text class="infoLabel">司机手机号:</text>
<text class="infoValue">{{ orderData.driverPhoneNum || '暂无数据' }}</text>
</view>
<view class="infoRow">
<text class="infoLabel">救援车辆:</text>
<text class="infoValue">{{ orderData.driverCarNum || '暂无数据' }}</text>
</view>
<view class="infoRow">
<text class="infoLabel">救援类型:</text>
<text class="infoValue">{{ orderData.rescueTypeStr || '暂无数据' }}</text>
</view>
<view class="infoRow">
<text class="infoLabel">开始时间:</text>
<text class="infoValue">{{ formatTimestamp(orderData.rescueStartTime) || '暂无数据' }}</text>
</view>
<view class="infoRow">
<text class="infoLabel">完成时间:</text>
<text class="infoValue">{{ formatTimestamp(orderData.rescueEndTime) || '暂无数据' }}</text>
</view>
<!-- <view class="timeInfoRow"> -->
<view class="infoRow">
<text class="infoLabel">耗时:</text>
<text
class="infoValue">{{ calculateDuration(orderData.rescueStartTime, orderData.rescueEndTime) }}</text>
</view>
</view>
<view class="orderInfoContainer" v-if="activeTab === 1 || isExpanded">
<view class="infoRow" :style="isExpanded ? 'margin-top: 20rpx;' : ''">
<text class="infoLabel" style="color: black; font-weight: bold; font-size: 32rpx;">业务信息</text>
</view>
<view class="infoRow">
<text class="infoLabel">渠道:</text>
<text class="infoValue">{{ orderData.channel || '暂无数据' }}</text>
</view>
<view class="infoRow">
<text class="infoLabel">来源:</text>
<text class="infoValue">{{ orderData.source || '暂无数据' }}</text>
</view>
<view class="infoRow">
<!-- <text class="infoLabel">故障车经办人:</text> -->
<text class="infoLabel">客户:</text>
<text class="infoValue">{{ orderData.connectionName || '暂无数据' }}</text>
</view>
<view class="infoRow">
<!-- <text class="infoLabel">经办人电话:</text> -->
<text class="infoLabel">客户电话:</text>
<text class="infoValue">{{ orderData.connectionPhone || '暂无数据' }}</text>
</view>
<view class="infoRow">
<text class="infoLabel">调度:</text>
<text class="infoValue">{{ orderData.secondDispatchName || '暂无数据' }}</text>
</view>
<view class="infoRow">
<text class="infoLabel">当前状态</text>
<text class="infoValue">{{ orderData.rescueStatusStr || '暂无数据' }}</text>
</view>
<view class="infoRow">
<text class="infoLabel">收款状态:</text>
<text class="infoValue">{{ orderData.orderStatusStr || '暂无数据' }}</text>
</view>
<view class="infoRow">
<text class="infoLabel">收款人:</text>
<text class="infoValue">{{ orderData.paymentName || '暂无数据' }}</text>
</view>
<view class="infoRow">
<text class="infoLabel">收款时间:</text>
<text class="infoValue">{{ formatTimestamp(orderData.paymentTime) || '暂无数据' }}</text>
</view>
</view>
<view class="orderInfoContainer" v-if="activeTab === 2 || isExpanded">
<view class="infoRow" :style="isExpanded ? 'margin-top: 20rpx;' : ''">
<text class="infoLabel" style="color: black; font-weight: bold; font-size: 32rpx;">客户信息</text>
</view>
<view class="infoRow">
<text class="infoLabel">车牌号:</text>
<text class="infoValue">{{ orderData.licenseNum || '暂无数据' }}</text>
</view>
<view class="infoRow">
<!-- <text class="infoLabel">故障车经办人:</text> -->
<text class="infoLabel">客户:</text>
<text class="infoValue">{{ orderData.connectionName || '暂无数据' }}</text>
</view>
<view class="infoRow">
<text class="infoLabel">联系电话:</text>
<text class="infoValue">{{ orderData.connectionPhone || '暂无数据' }}</text>
</view>
<view class="infoRow">
<text class="infoLabel">品牌:</text>
<text class="infoValue">{{ orderData.carBrand || '暂无数据' }}</text>
</view>
<view class="infoRow">
<text class="infoLabel">规格:</text>
<text class="infoValue">{{ orderData.carTypeStr || '暂无数据' }}</text>
</view>
<view class="infoRow">
<text class="infoLabel">是否为新能源:</text>
<text
class="infoValue">{{ orderData.ifNewEnergy === '1' ? '是' : orderData.ifNewEnergy === '0' ? '否' : '暂无数据' }}</text>
</view>
<view class="infoRow">
<text class="infoLabel">故障类型:</text>
<text class="infoValue">{{ orderData.faultType || '暂无数据' }}</text>
</view>
<view class="infoRow">
<text class="infoLabel">故障现象:</text>
<text class="infoValue">{{ orderData.phenomenon || '暂无数据' }}</text>
</view>
<view class="infoRow">
<text class="infoLabel">故障现象备注:</text>
<text class="infoValue">{{ orderData.faultPhenomenon || '暂无数据' }}</text>
</view>
<view class="infoRow">
<text class="infoLabel">故障地点:</text>
<text class="infoValue">{{ orderData.rescuePosition || '暂无数据' }}</text>
</view>
<view class="infoRow">
<text class="infoLabel">救援需求:</text>
<text class="infoValue">{{ orderData.rescueNeeds || '暂无数据' }}</text>
</view>
<view class="infoRow">
<text class="infoLabel">预估下车地点:</text>
<text class="infoValue">{{ orderData.estimateDownCar || '暂无数据' }}</text>
</view>
<view class="infoRow">
<text class="infoLabel">预估费用:</text>
<text class="infoValue">{{ orderData.estimateMoney || '暂无数据' }}</text>
</view>
<view class="infoRow">
<text class="infoLabel">实际下车地点:</text>
<text class="infoValue">{{ orderData.estimateDownCar || '暂无数据' }}</text>
</view>
<view class="infoRow">
<text class="infoLabel">公里数:</text>
<text
class="infoValue">{{ orderData.startScale && orderData.endScale ? (orderData.endScale - orderData.startScale) : '暂无数据' }}</text>
</view>
<view class="infoRow">
<text class="infoLabel">实际费用:</text>
<text
class="infoValue">{{ orderData.setMoney != null ? (orderData.setMoney / 100) : '暂无数据' }}</text>
</view>
</view>
<view class="orderCardFooter">
<text class="orderCardDateTime">创建时间:{{ orderData.rescueTime || "" }}</text>
<view class="orderCardBtnGroup">
<!-- <template v-if="hasRoleNew('ddzx', 'second_dispatcher') && orderData.rescueStatus < 4">
<view @click.stop="revokeId" class="orderCardBtnRevork">撤销工单</view>
</template> -->
<template v-if="hasRoleNew('ddzx', 'second_dispatcher') && orderData.rescueStatus <= 2">
<!-- <view @click.stop="deleteId" class="orderCardBtnGroupItem"
style="background-color: #fff;color: #317DFA">
删除订单</view> -->
<!-- <view @click.stop="showDispatcherOptions" class="orderCardBtnGroupItem"> 指派 </view> -->
<view @click.stop="showDispatcherOptions" class="orderCardBtnGroupItemZp"
:class="{ 'loading': assignLoading }">
<text v-if="!assignLoading">指派</text>
<uni-load-more v-else status="loading" :contentText="false" color="#fff"
:showIcon="true"></uni-load-more>
</view>
</template>
<template v-if="orderData.rescueStatus > 2">
<view @click.stop="gettel" class="orderCardBtnGroupItem">联系司机</view>
</template>
<!-- <template v-if="orderData.orderStatus == 3 && orderData.isWeiXiu!=='1'">
<view @click.stop="showRepair" class="orderCardBtnGroupItem">转维修</view>
</template> -->
</view>
</view>
<!-- <view style="display: flex; flex-direction: row; justify-content: space-between; align-items: center;">
<view class="confirm-order-btn-container-gz"
v-if="orderData.feeType == 1 || (orderData.feeType == 2 && orderData.currentRecordStep >= 4)">
<view class="confirm-order-btn-gz" @click.stop="showAgreeModal" v-if="orderData.feeType == 1">同意挂账
</view>
<view class="confirm-order-btn-gz confirm-hang-account-gz" @click.stop="showConfirmHangAccountModal"
v-if="orderData.feeType == 2 && orderData.currentRecordStep >= 4 && !orderData.orderSigningChargeId && !orderData.orderSigningChargeName && orderData.setMoney">
确认挂账信息</view>
<view class="confirm-order-btn-gz confirm-hang-account-ygz"
@click.stop="showLookConfirmHangAccountModal"
v-if="orderData.feeType == 2 && orderData.currentRecordStep >= 4 && orderData.orderSigningChargeId && orderData.orderSigningChargeName">
已确认挂账信息</view>
</view>
<view class="confirm-order-btn-container" v-if="orderData.rescueStatus == 4">
<view class="confirm-order-btn" @click.stop="showConfirmModal">确认订单完成</view>
</view>
</view> -->
<view class="button-group-container-two-1"
v-if="orderData.secondDispatchId == userinfo.id || hasRoleNew('jiuyuan') || checkPermi(['rescue_dispatch_process_btn'])">
<!-- 调度流程相关按钮 -->
<view class="hang-account-btn-group-1">
<view class="hang-account-btn agree" @click.stop="gotoDispatchProcess(orderData.id)">
调度流程记录
</view>
</view>
<!-- <view class="hang-account-btn-group-1" :class="{ 'collapsed': !showDriverProcess }"
:style="{ maxWidth: showDriverProcess ? '100%' : '0', opacity: showDriverProcess ? 1 : 0 }"
v-if="hasRoleNew('ddzx', 'jiuyuan')">
<view class="hang-account-btn agree" @click.stop="gotoDispatchAgentDriverExecute(orderData.id)">
代司机记录流程
</view>
</view> -->
<!-- <view class="hang-account-btn-group-1"
:class="{ 'collapsed': !showDriverProcess, 'disabled-button': !(orderData.rescueStatus == '3' || orderData.rescueStatus == '4') }"
:style="{ maxWidth: showDriverProcess ? '100%' : '0', opacity: showDriverProcess ? 1 : 0 }"
v-if="hasRoleNew('ddzx', 'jiuyuan')">
<view class="hang-account-btn agree"
@click.stop="!(orderData.rescueStatus == '3' || orderData.rescueStatus == '4') ? '' : gotoDispatchAgentDriverExecute(orderData.id)"
:class="{ 'disabled': !(orderData.rescueStatus == '3' || orderData.rescueStatus == '4') }">
代司机记录流程
</view>
</view> -->
<view class="hang-account-btn-group-1" :class="{ 'collapsed': !showDriverProcess }"
:style="{ maxWidth: showDriverProcess ? '100%' : '0', opacity: showDriverProcess ? 1 : 0 }"
v-if="hasRoleNew('ddzx', 'jiuyuan') || checkPermi(['rescue_dispatch_process_btn'])">
<view
v-if="orderData.rescueStatus == '2' || orderData.rescueStatus == '3' || orderData.rescueStatus == '4'"
class="hang-account-btn agree" @click.stop="gotoDispatchAgentDriverExecute(orderData.id)">
代司机记录流程
</view>
<view v-else class="hang-account-btn disabled" @click.stop>
代司机记录流程
</view>
</view>
<view class="expand-collapse-arrow" @click.stop="toggleDriverProcess"
v-if="hasRoleNew('ddzx', 'jiuyuan') || checkPermi(['rescue_dispatch_process_btn'])">
<u-icon :name="showDriverProcess ? 'arrow-right' : 'arrow-left'" color="#317DFA" size="20"></u-icon>
</view>
</view>
<view class="hang-account-btn-group" style="margin-right: 90rpx;"
:style="{ width: hasRoleNew('ddzx', 'jiuyuan') ? '' : '100%' }"
v-if="orderData.feeType == 1 || (orderData.feeType != 1 && orderData.currentRecordStep >= 6)">
<view class="hang-account-btn agree" @click.stop="showAgreeModal"
v-if="orderData.feeType == 1 && orderData.rescueStatus != '1'">
同意挂账
</view>
</view>
<!-- <view class="button-group-container">
<view class="hang-account-btn-group"
v-if="orderData.feeType == 1 || (orderData.feeType == 2 && orderData.currentRecordStep >= 6)">
<view class="hang-account-btn agree" @click.stop="showAgreeModal"
v-if="orderData.feeType == 1 && orderData.rescueStatus != '1'">
同意挂账
</view>
<view class="hang-account-btn confirm" @click.stop="showConfirmHangAccountModal"
v-if="orderData.feeType == 2 && orderData.currentRecordStep >= 6 && !orderData.orderSigningChargeId && !orderData.orderSigningChargeName && orderData.setMoney">
确认挂账信息
</view>
<view class="hang-account-btn confirmed" @click.stop="showLookConfirmHangAccountModal"
v-if="orderData.feeType == 2 && orderData.currentRecordStep >= 6 && orderData.orderSigningChargeId && orderData.orderSigningChargeName">
已确认挂账信息
</view>
</view>
<view class="complete-order-btn" v-if="orderData.rescueStatus == 4">
<view class="complete-btn" @click.stop="showConfirmModal">确认订单完成</view>
</view>
</view> -->
<view class="expand-control" @click.stop="toggleExpand">
<text class="expand-text">{{ isExpanded ? '收起' : '展开' }}全部信息</text>
<u-icon :name="isExpanded ? 'arrow-up' : 'arrow-down'" color="#317DFA" size="16"></u-icon>
</view>
</view>
<!-- 遮罩层和加载动画 -->
<view v-if="showLoadingOverlay" class="loading-overlay">
<view class="loading-content">
<uni-load-more status="loading" :contentText="false" color="#317DFA" :showIcon="true"></uni-load-more>
<text class="loading-text">正在处理中...</text>
</view>
</view>
<!-- 指派选项弹窗 -->
<u-action-sheet :show="showDispatcherOptionsSheet" :actions="dispatcherActions" title="请选择指派类型"
@select="onDispatcherOptionSelect" @close="showDispatcherOptionsSheet = false"></u-action-sheet>
<!-- <u-picker :show="show" :columns="columns" @confirm="confirms" @cancel="cancels" keyName="realName"></u-picker> -->
<u-picker :show="show" :columns="columns" @confirm="confirms" @cancel="cancels" keyName="realName"></u-picker>
<!-- <u-picker :show="firstShow" :columns="firstColumns" @confirm="confirms" @cancel="cancels"
keyName="nickname"></u-picker> -->
<!-- <u-picker :show="secondShow" :columns="secondColumns" @confirm="secondConfirms" @cancel="secondCancels"
keyName="nickname"></u-picker> -->
<u-picker :show="secondShow" :columns="secondColumns" @confirm="secondConfirms" @cancel="secondCancels"
keyName="nickname"></u-picker>
<u-modal :show="showDelete" title="是否确认删除" :showCancelButton="true" @confirm="deleteOk"
@cancel="deleteCancel"></u-modal>
<u-modal :show="showRevoke" title="是否确认撤销" :showCancelButton="true" @confirm="revokeOk"
@cancel="revokeCancel"></u-modal>
<u-modal :show="toRepairShow" title="转维修" :showCancelButton="true" @confirm="toRepair"
@cancel="()=>{toRepairShow=false}">
<u-form labelPosition="left" :model="formData" ref="uForm">
<u-form-item label="姓名" borderBottom>
<u--input placeholder="请输入车主姓名" v-model="formData.name" border="none"></u--input>
</u-form-item>
<u-form-item label="联系电话" borderBottom>
<u--input placeholder="请输入车主联系电话" v-model="formData.phone" border="none"></u--input>
</u-form-item>
<u-form-item label="品牌" borderBottom @click="pinpaiShow = true;" ref="item1">
<u-input v-model="formData.brandName" disabled disabledColor="#ffffff" placeholder="请选择车辆品牌"
border="none"></u-input>
<u-icon slot="right" name="arrow-right"></u-icon>
</u-form-item>
<u-form-item label="型号" borderBottom>
<u--input placeholder="请输入车辆型号" v-model="formData.brandAndModel[1]" border="none"></u--input>
</u-form-item>
<u-form-item label="服务顾问" borderBottom @click="fuwuShow = true;" ref="item1">
<u-input v-model="formData.adviserName" disabled disabledColor="#ffffff" placeholder="请选择服务顾问"
border="none"></u-input>
<u-icon slot="right" name="arrow-right"></u-icon>
</u-form-item>
</u-form>
</u-modal>
<!-- 确认订单完成弹窗 -->
<u-modal :show="showConfirmComplete" title="确认订单完成" :showCancelButton="true" @confirm="confirmComplete"
@cancel="cancelComplete">
<view class="confirm-modal-content">
<text class="modal-label">备注信息(可选):</text>
<u--textarea v-model="completeRemark" placeholder="请输入备注信息" border="bottom" autoHeight
class="remark-input"></u--textarea>
</view>
</u-modal>
<!-- 同意挂账弹窗 -->
<u-modal :show="showAgreeHangAccount" title="同意挂账" :showCancelButton="true" @confirm="agreeHangAccount"
@cancel="cancelAgreeHangAccount">
<view class="modal-content">
<text>是否同意该订单挂账?</text>
</view>
</u-modal>
<!-- 确认挂账信息弹窗 -->
<u-modal :show="showConfirmHangAccount" :showConfirmButton="false" :showCancelButton="false">
<view class="modal-content">
<text class="modal-title">确认挂账信息</text>
<view class="amount-display">
<text class="amount-label">挂账金额:</text>
<view class="amount-value">{{ orderData.setMoney != null ? (orderData.setMoney / 100) : '0' }}
元</view>
</view>
<view class="amount-display">
<text class="amount-label">救援司机:</text>
<view class="amount-value-two">{{ orderData.driverName }}</view>
</view>
<view class="amount-display">
<text class="amount-label">挂账负责人:</text>
<view class="amount-value-two">{{ orderData.orderSigningPersonName }}</view>
</view>
<view class="amount-display">
<text class="amount-label">故障车牌号:</text>
<view class="amount-value-two">{{ orderData.licenseNum }}</view>
</view>
<view class="confirm-modal-content">
<text class="modal-label">备注信息(可选):</text>
<u--textarea v-model="completeRemark" placeholder="请输入备注信息" border="bottom" autoHeight
class="remark-input"></u--textarea>
</view>
<view class="hang-account-buttons">
<view class="hang-account-btn cancel" @click="cancelConfirmHangAccount">取消</view>
<view class="hang-account-btn received" @click="confirmHangAccountReceived">确认</view>
</view>
</view>
</u-modal>
<!-- 查看 -->
<u-modal :show="showLookConfirmHangAccount" :showConfirmButton="false" :showCancelButton="false">
<view class="modal-content">
<text class="modal-title">已确认挂账信息</text>
<view class="amount-display">
<text class="amount-label">挂账金额</text>
<view class="amount-value">{{ orderData.setMoney != null ? (orderData.setMoney / 100) : '0' }}
</view>
</view>
<view class="amount-display">
<text class="amount-label">救援司机</text>
<view class="amount-value-two">{{ orderData.driverName }}</view>
</view>
<view class="amount-display">
<text class="amount-label">故障车牌号</text>
<view class="amount-value-two">{{ orderData.licenseNum }}</view>
</view>
<view class="amount-display">
<text class="amount-label">挂账负责人</text>
<view class="amount-value-two">{{ orderData.orderSigningPersonName }}</view>
</view>
<view class="amount-display">
<text class="amount-label">挂账信息确认人</text>
<view class="amount-value-two">{{ orderData.orderSigningChargeName }}</view>
</view>
<view class="confirm-modal-content">
<text class="modal-label">备注信息:</text>
<view class="amount-value-two">{{ orderData.orderSigningRemark }}</view>
</view>
<view class="hang-account-buttons" style="margin-top: 20px;">
<view class="hang-account-btn received" @click="cancelLookConfirmHangAccount">关闭</view>
</view>
</view>
</u-modal>
<!-- 救援类型选择弹窗 -->
<u-modal :show="showRescueTypeSelect" title="选择救援类型" :showCancelButton="true" @confirm="confirmRescueType"
@cancel="cancelRescueType">
<view class="rescue-type-modal">
<view class="rescue-type-grid">
<!-- <view v-for="item in busiTypeList" :key="item.index" class="rescue-type-item"
@click="selectRescueType(item.index)">
<image :src="item.icon" class="rescue-type-icon"></image>
<text class="rescue-type-label">{{ item.label }}</text>
</view> -->
<view v-for="item in busiTypeList" :key="item.index" class="rescue-type-item"
:class="{ 'rescue-type-item--selected': selectedRescueTypeIndex === item.index }"
@click="selectRescueType(item)">
<image :src="item.icon" class="rescue-type-icon"></image>
<text class="rescue-type-label">{{ item.label }}</text>
</view>
</view>
</view>
</u-modal>
<u-picker :show="pinpaiShow" :columns="[brandList]" :keyName="'brandName'" @confirm="onPinpaiConfirm"
@cancel="()=>{pinpaiShow=false}"></u-picker>
<u-picker :show="fuwuShow" :columns="[staffList]" :keyName="'name'" @confirm="onFuwuConfirm"
@cancel="()=>{fuwuShow=false}"></u-picker>
</view>
</template>
<script>
import request from '../../utils/request';
import {
getTenantId,
hasRole,
hasRoleNew
} from "@/utils/auth";
import {
getDictDataById
} from "@/utils/utils";
import {
checkPermi,
checkRole
} from "@/utils/permission";
export default {
props: {
orderData: {
type: Object,
default: () => {
return {}
}
},
activeTab: Number,
status: {
type: [String, Number],
default: ''
},
brandList: [],
staffList: []
},
data() {
return {
columns: [],
firstColumns: [],
secondColumns: [],
// secondDriverColumns: [],
id: '',
show: false,
firstShow: false,
secondShow: false,
showDelete: false,
showRevoke: false,
toRepairShow: false,
pinpaiShow: false,
fuwuShow: false,
formData: {
brandAndModel: []
},
sectionRoadName: '未知',
isExpanded: false,
showDispatcherOptionsSheet: false, // 控制选项弹窗显示
// 标记是否是二级调度员直接指派
isSecondDispatcherDirect: false,
dispatcherActions: [ // 指派选项
{
name: '二级调度',
value: 'second'
},
{
name: '司机',
value: 'driver'
}
],
userinfo: {},
// 新增确认订单完成相关数据
showConfirmComplete: false,
completeRemark: '',
showAgreeHangAccount: false, // 控制同意挂账弹窗显示
showConfirmHangAccount: false, // 控制确认挂账信息弹窗显示
showLookAgreeHangAccount: false,
showLookConfirmHangAccount: false,
assignLoading: false, // 指派按钮加载状态
showRescueTypeSelect: false, // 控制救援类型选择弹窗显示
busiTypeList: [{
label: '拖车',
index: 1,
icon: require('@/static/icons/order/tuoche.png')
},
{
label: '送油',
index: 2,
icon: require('@/static/icons/order/songyou.png')
},
{
label: '搭电',
index: 3,
icon: require('@/static/icons/order/dadian.png')
},
{
label: '换胎',
index: 4,
icon: require('@/static/icons/order/huantai.png')
},
{
label: '扣车',
index: 5,
icon: require('@/static/icons/order/tuoche.png')
}
],
selectedRescueType: null, // 选中的救援类型
isUpdatingRescueType: false, // 是否正在更新救援类型
selectedRescueTypeIndex: null,
showDriverProcess: false, // 控制代司机流程记录的显示
showLoadingOverlay: false, // 新增:控制遮罩显示
}
},
created() {
// this.fetchSectionRoadName();
// this.getFirstDispatcher()
// this.getSecondDispatcher()
this.userinfo = uni.getStorageSync('userInfo')
console.log('userinfo', this.userinfo)
},
watch: {
activeTab(newVal) {
console.log('选项卡切换了:', newVal);
}
},
computed: {
showRevokeButton() {
// 拥有 ddzx 或 second_dispatcher 且是 secondDispatchId
const case1 = (this.hasRoleNew('ddzx') || this.hasRoleNew('second_dispatcher')) &&
this.userinfo.id == this.orderData.secondDispatchId;
// 拥有 jiuyuan
const case2 = this.hasRoleNew('jiuyuan');
// 拥有 ddzx 且 dispatchLevel 为 2
const case3 = this.hasRoleNew('ddzx') && this.orderData.dispatchLevel == 2;
// 三种情况满足任意一种就显示
return case1 || case2 || case3;
}
},
methods: {
hasRole,
hasRoleNew,
checkPermi,
checkRole,
toggleDriverProcess() {
this.showDriverProcess = !this.showDriverProcess;
},
toggleExpand() {
this.isExpanded = !this.isExpanded;
if (!this.isExpanded) {
this.$emit('update:activeTab', -1);
}
},
onPinpaiConfirm(e) {
console.log(e)
this.formData.brandName = e.value[0].brandName
this.formData.brandAndModel[0] = e.value[0].id
this.pinpaiShow = false
},
onFuwuConfirm(e) {
this.formData.adviserName = e.value[0].name
this.formData.adviserId = e.value[0].id
this.formData.userId = e.value[0].userId
this.fuwuShow = false
},
showRepair() {
if (this.orderData.connectionName) {
this.formData.name = this.orderData.connectionName
}
if (this.orderData.connectionPhone) {
this.formData.phone = this.orderData.connectionPhone
}
this.toRepairShow = true
},
toRepair() {
let data = JSON.parse(JSON.stringify(this.formData))
data.id = this.orderData.id
console.log(data, 'data');
request({
url: '/app/rescueInfo/toRepair',
method: 'post',
params: data
}).then((res) => {
if (res.code == 200) {
uni.showToast({
title: '操作成功'
})
this.toRepairShow = false
this.$emit('refresh')
}
})
},
onShowDetail() {
uni.navigateTo({
url: '/pages/details/details?id=' + this.orderData.id
})
},
getzhipai() {
console.log('getzhipai: ', this.getzhipai);
if (hasRole('second_dispatcher')) {
this.getSecondDriverlist()
} else {
this.getsjlist()
}
this.show = true
},
getSecondList() {
this.getSecondDispatcher()
this.secondShow = true
},
dispatcherSelect() {
this.firstShow = true
},
// 显示指派选项弹窗
/* showDispatcherOptions() {
// 如果是二级调度员,直接指派司机
if (hasRoleNew('second_dispatcher')) {
this.isSecondDispatcherDirect = true; // 标记为二级调度员直接指派
this.getzhipai(); // 直接显示司机选择
} else {
this.isSecondDispatcherDirect = false; // 标记为正常流程
this.showDispatcherOptionsSheet = true;
console.log('hasRole', hasRole('ddzx'))
}
}, */
async showDispatcherOptions() {
// 检查是否需要显示救援类型选择
console.log('this.orderData.rescueType', this.orderData.rescueType)
console.log('this.orderData.rescueStatus', this.orderData.rescueStatus)
if (this.orderData.rescueType == '8' && this.orderData.rescueStatus == '1') {
this.showRescueTypeSelect = true;
return;
}
// 如果是二级调度员,直接指派司机
if (hasRoleNew('second_dispatcher')) {
this.isSecondDispatcherDirect = true;
this.getzhipai();
} else {
this.isSecondDispatcherDirect = false;
this.showDispatcherOptionsSheet = true;
}
},
// 选择救援类型
selectRescueType(item) {
this.selectedRescueType = item.index;
this.selectedRescueTypeIndex = item.index; // 记录选中的索引
},
// 确认救援类型
async confirmRescueType() {
if (!this.selectedRescueType) {
uni.showToast({
title: '请选择救援类型',
icon: 'none'
});
return;
}
this.isUpdatingRescueType = true;
try {
// 调用API更新救援类型
const result = await request({
url: '/app/driver/updateRescueInfoAndDetails',
method: 'put',
data: {
id: this.orderData.id,
rescueType: this.selectedRescueType,
rescueStatus: '2',
}
});
if (result.code == 200) {
uni.showToast({
title: '救援类型已更新'
});
// 关闭救援类型选择弹窗
this.showRescueTypeSelect = false;
this.selectedRescueTypeIndex = null; // 可选:确认后清空选中状态
// 刷新订单数据
this.$emit('refresh');
// 延迟一下再显示指派弹窗,确保数据已更新
setTimeout(() => {
// 显示指派选项
if (hasRoleNew('second_dispatcher')) {
this.isSecondDispatcherDirect = true;
this.getzhipai();
} else {
this.isSecondDispatcherDirect = false;
this.showDispatcherOptionsSheet = true;
}
}, 500);
} else {
uni.showToast({
title: result.msg || '更新失败',
icon: 'none'
});
}
} catch (error) {
console.error('更新救援类型失败:', error);
uni.showToast({
title: '更新失败,请重试',
icon: 'none'
});
} finally {
this.isUpdatingRescueType = false;
}
},
// 取消选择救援类型
cancelRescueType() {
this.showRescueTypeSelect = false;
this.selectedRescueType = null;
this.selectedRescueTypeIndex = null; // 取消时清空选中状态
},
// 处理指派选项选择
onDispatcherOptionSelect(e) {
if (e.value === 'second') {
// 显示二级调度
this.getSecondList()
} else if (e.value === 'driver') {
// 显示司机
this.getzhipai()
}
this.showDispatcherOptionsSheet = false;
},
getsjlist() {
this.columns = []
request({
url: '/app/rescueInfo/driverInMap?searchValue=',
method: 'get',
}).then((res) => {
this.columns.push(res.data)
})
},
getSecondDriverlist() {
this.columns = []
request({
url: '/app/rescueInfo/secondDriverInMap?searchValue=',
method: 'get',
}).then((res) => {
this.columns.push(res.data)
})
},
getFirstDispatcher() {
this.firstColumns = []
const tenantId = getTenantId()
request({
url: `/company/staff/staffListByRoleCode?tenantId=${tenantId}&code=ddzx`,
method: 'get',
}).then((res) => {
this.firstColumns.push(res.data)
console.log('firstRes', res)
})
},
getSecondDispatcher() {
this.secondColumns = []
const tenantId = getTenantId()
request({
url: `/company/staff/staffListByRoleCode?tenantId=${tenantId}&code=second_dispatcher`,
method: 'get',
}).then((res) => {
this.secondColumns.push(res.data)
console.log('secondRes', res)
})
},
/* confirms(e) {
console.log(e);
let data = {
rescueId: this.orderData.id,
driverId: e.value[0].id
}
request({
url: '/system/rescueInfo/designateDriver',
method: 'post',
params: data
}).then((res) => {
console.log('确认司机', res);
if (res.code == 200) {
uni.showToast({
title: '指派成功'
})
this.$emit('refresh')
}
})
this.show = false
}, */
async confirms(e) {
if (this.assignLoading) return;
console.log(e);
// 开始加载
this.assignLoading = true;
this.confirmButtonDisabled = true;
this.showLoadingOverlay = true; // 显示遮罩
try {
// 先执行指派司机接口
let data = {
rescueId: this.orderData.id,
driverId: e.value[0].id
}
const assignResult = await request({
url: '/system/rescueInfo/designateDriver',
method: 'post',
params: data
});
console.log('确认司机', assignResult);
if (assignResult.code == 200) {
// 如果角色为ddzx再执行编辑接口
if (hasRole('ddzx')) {
let editData = {
...this.orderData,
secondDispatchId: this.userinfo.id,
secondDispatchName: this.userinfo.nickname,
dispatchLevel: 1
}
const editResult = await request({
url: '/app/rescueInfo/edit',
method: 'post',
data: editData
});
console.log('ddzx更新二级调度信息', editResult);
if (editResult.code == 200) {
// 使用返回的msg信息如果没有则使用默认提示
uni.showToast({
title: assignResult.msg || '指派成功'
})
this.$emit('refresh')
} else {
// 显示错误信息
uni.showToast({
title: editResult.msg || '指派失败',
icon: 'none'
});
}
} else {
// 非ddzx角色直接显示成功使用返回的msg信息
uni.showToast({
title: assignResult.msg || '指派成功'
})
this.$emit('refresh')
}
} else {
// 显示错误信息
uni.showToast({
title: assignResult.msg || '指派失败',
icon: 'none'
});
}
} catch (error) {
console.error('指派操作失败', error);
uni.showToast({
title: assignResult.msg || '指派失败,请重试',
icon: 'none'
});
} finally {
// 无论成功失败,都关闭加载状态
this.assignLoading = false;
this.confirmButtonDisabled = false;
this.showLoadingOverlay = false; // 隐藏遮罩
this.show = false;
}
},
/* secondConfirms(e) {
let data = {
...this.orderData,
secondDispatchId: e.value[0].id,
secondDispatchName: e.value[0].nickname
}
request({
url: '/app/rescueInfo/edit',
method: 'post',
data: data
}).then((res) => {
console.log('确认司机', res);
if (res.code == 200) {
uni.showToast({
title: '指派成功'
})
this.$emit('refresh')
}
})
this.secondShow = false
}, */
async secondConfirms(e) {
if (this.confirmButtonDisabled) return;
this.assignLoading = true;
this.confirmButtonDisabled = true;
this.showLoadingOverlay = true; // 显示遮罩
try {
let data = {
...this.orderData,
secondDispatchId: e.value[0].id,
secondDispatchName: e.value[0].nickname,
dispatchLevel: 2
}
const res = await request({
url: '/app/rescueInfo/edit',
method: 'post',
data: data
});
console.log('确认二级调度', res);
if (res.code == 200) {
uni.showToast({
title: res.msg || '指派成功'
})
this.$emit('refresh')
} else {
// 显示错误信息
uni.showToast({
title: res.msg || '指派失败',
icon: 'none'
});
}
} catch (error) {
console.error('指派失败', error);
uni.showToast({
title: res.msg || '指派失败,请重试',
icon: 'none'
});
} finally {
this.assignLoading = false;
this.confirmButtonDisabled = false;
this.showLoadingOverlay = false; // 隐藏遮罩
this.secondShow = false;
}
},
cancels() {
this.assignLoading = false; // 重置加载状态
this.confirmButtonDisabled = false;
this.showLoadingOverlay = false; // 隐藏遮罩
this.show = false;
// 只有正常流程(非二级调度员直接指派)才重新打开指派类型选择
if (!this.isSecondDispatcherDirect) {
this.showDispatcherOptions();
} else {
// 二级调度员直接指派时,直接关闭,不重新打开选择框
this.isSecondDispatcherDirect = false; // 重置状态
}
},
secondCancels() {
this.assignLoading = false; // 重置加载状态
this.confirmButtonDisabled = false;
this.showLoadingOverlay = false; // 隐藏遮罩
this.secondShow = false;
this.showDispatcherOptions();
},
deleteId() {
this.showDelete = true
return
},
deleteOk() {
request({
url: "/app/rescueInfo/delRescueInfo?id=" + this.orderData.id,
method: 'post',
}).then(res => {
if (res.code == 200) {
uni.showToast({
title: "删除成功"
})
this.$emit('deleteOk')
}
})
this.showDelete = false
},
deleteCancel() {
console.log("取消");
this.showDelete = false
},
revokeId() {
this.showRevoke = true
return
},
revokeOk() {
request({
url: "/app/rescueInfo/revokeRescueInfo?id=" + this.orderData.id,
method: 'put'
}).then(res => {
if (res.code == 200) {
uni.showToast({
title: "撤销成功"
})
this.$emit('revokeOk')
}
})
this.showRevoke = false
},
revokeCancel() {
console.log("取消");
this.showRevoke = false
},
gettel() {
uni.makePhoneCall({
phoneNumber: this.orderData.driverPhoneNum
});
},
// 显示确认订单完成弹窗
showConfirmModal() {
this.completeRemark = '';
this.showConfirmComplete = true;
},
// 取消确认
cancelComplete() {
this.completeRemark = '';
this.showConfirmComplete = false;
},
// 确认订单完成
async confirmComplete() {
console.log('this.orderData', this.orderData)
if (this.orderData.feeType == 2 && !this.orderData.secondDispatchId && !this.orderData
.secondDispatchName) {
uni.showToast({
title: '请先确认挂账信息',
icon: 'none'
});
return;
}
let saveData = {
rescueInfoId: this.orderData.id,
title: '调度 · 确认订单已完成',
remark: this.completeRemark,
autoRemark: '确认人: ' + this.userinfo.nickname
}
let rescueData = {
id: this.orderData.id,
feeType: this.orderData.feeType,
carType: this.orderData.carType,
isWeiXiu: this.orderData.isWeiXiu,
rescueType: this.orderData.rescueType,
isAppointment: this.orderData.isAppointment,
isKouChe: this.orderData.isKouChe,
rescuePosition: this.orderData.rescuePosition,
rescueStatus: '5',
}
try {
// 等待两个API调用完成
const [saveResult, rescueResult] = await Promise.all([
this.saveConfirmMsg(saveData),
this.rescueInfoEdit(rescueData)
]);
if (saveResult && rescueResult) {
uni.showToast({
title: '订单完成确认成功',
icon: 'success'
});
this.$emit('refresh');
} else {
uni.showToast({
title: '操作失败,请重试',
icon: 'none'
});
}
} catch (error) {
console.error('确认订单完成失败:', error);
uni.showToast({
title: '操作失败,请重试',
icon: 'none'
});
} finally {
this.completeRemark = '';
this.showConfirmComplete = false;
}
},
/* confirmComplete() {
console.log('this.orderData', this.orderData)
let saveData = {
rescueInfoId: this.orderData.id,
title: '调度 · 确认订单已完成',
remark: this.completeRemark,
autoRemark: '确认人: ' + this.userinfo.nickname
}
this.saveConfirmMsg(saveData)
let rescueData = {
id: this.orderData.id,
feeType: this.orderData.feeType,
carType: this.orderData.carType,
isWeiXiu: this.orderData.isWeiXiu,
rescueType: this.orderData.rescueType,
isAppointment: this.orderData.isAppointment,
isKouChe: this.orderData.isKouChe,
rescuePosition: this.orderData.rescuePosition,
rescueStatus: '5',
}
this.rescueInfoEdit(rescueData)
this.completeRemark = '';
this.showConfirmComplete = false;
}, */
// 更新救援信息
rescueInfoEdit(rescueData) {
return new Promise((resolve, reject) => {
request({
url: '/app/rescueInfo/edit',
method: 'post',
data: rescueData
}).then((res) => {
console.log(res);
if (res.code == 200) {
resolve(true);
} else {
resolve(false);
}
}).catch((error) => {
console.error('rescueInfoEdit error:', error);
reject(error);
});
});
},
/* rescueInfoEdit(rescueData) {
request({
url: '/app/rescueInfo/edit',
method: 'post',
data: rescueData
}).then((res) => {
console.log(res);
if (res.code == 200) {
uni.showToast({
title: '修改成功',
icon: 'none'
})
this.show = false
this.getrescueDetail(this.detailsData.id)
}
})
}, */
// 更新订单信息
orderInfoEdit(orderData) {
return new Promise((resolve, reject) => {
request({
url: '/rescue/orderInfo/edit',
method: 'post',
data: orderData
}).then((res) => {
console.log(res);
if (res.code == 200) {
resolve(true);
} else {
resolve(false);
}
}).catch((error) => {
console.error('orderInfoEdit error:', error);
reject(error);
});
});
},
/* orderInfoEdit(orderData) {
request({
url: '/rescue/orderInfo/edit',
method: 'post',
data: orderData
}).then((res) => {
console.log(res);
})
}, */
// 存储节点信息
saveConfirmMsg(saveData) {
return new Promise((resolve, reject) => {
request({
url: '/app/driver/uploadDetailByDriver',
method: 'post',
data: saveData
}).then((res) => {
console.log(res);
if (res.code == 200) {
resolve(true);
} else {
resolve(false);
}
}).catch((error) => {
console.error('saveConfirmMsg error:', error);
reject(error);
});
});
},
/* saveConfirmMsg(saveData) {
request({
url: '/app/driver/uploadDetailByDriver',
method: 'post',
data: saveData
}).then((res) => {
console.log(res);
})
}, */
// 显示同意挂账弹窗
showAgreeModal() {
this.showAgreeHangAccount = true;
},
// 同意挂账
async agreeHangAccount() {
console.log('同意挂账', this.orderData.id);
let rescueData = {
id: this.orderData.id,
feeType: '2',
carType: this.orderData.carType,
isWeiXiu: this.orderData.isWeiXiu,
rescueType: this.orderData.rescueType,
isAppointment: this.orderData.isAppointment,
isKouChe: this.orderData.isKouChe,
rescuePosition: this.orderData.rescuePosition,
rescueStatus: this.orderData.rescueStatus,
}
let orderData = {
id: this.orderData.orderId,
payType: 'qd'
}
try {
// 等待两个API调用完成
const [rescueResult, orderResult] = await Promise.all([
this.rescueInfoEdit(rescueData),
this.orderInfoEdit(orderData)
]);
if (rescueResult && orderResult) {
uni.showToast({
title: '同意挂账成功',
icon: 'success'
});
this.$emit('refresh');
} else {
uni.showToast({
title: '操作失败,请重试',
icon: 'none'
});
}
} catch (error) {
console.error('同意挂账失败:', error);
uni.showToast({
title: '操作失败,请重试',
icon: 'none'
});
} finally {
this.showAgreeHangAccount = false;
}
},
/* agreeHangAccount() {
console.log('同意挂账', this.orderData.id);
let rescueData = {
id: this.orderData.id,
feeType: '2',
carType: this.orderData.carType,
isWeiXiu: this.orderData.isWeiXiu,
rescueType: this.orderData.rescueType,
isAppointment: this.orderData.isAppointment,
isKouChe: this.orderData.isKouChe,
rescuePosition: this.orderData.rescuePosition,
rescueStatus: this.orderData.rescueStatus,
}
this.rescueInfoEdit(rescueData)
let orderData = {
id: this.orderData.orderId,
payType: 'qd'
}
this.orderInfoEdit(orderData)
this.showAgreeHangAccount = false;
}, */
// 取消同意挂账
cancelAgreeHangAccount() {
this.showAgreeHangAccount = false;
},
// 显示确认挂账信息弹窗
showConfirmHangAccountModal() {
this.showConfirmHangAccount = true;
},
// 取消查看同意挂账
cancelLookAgreeHangAccount() {
this.showLookAgreeHangAccount = false;
},
// 显示查看确认挂账信息弹窗
showLookConfirmHangAccountModal() {
this.showLookConfirmHangAccount = true;
},
// 确认挂账信息
async confirmHangAccountReceived() {
console.log('确认挂账信息', this.orderData.id);
let orderData = {
id: this.orderData.orderId,
orderSigningChargeId: this.userinfo.id,
orderSigningChargeName: this.userinfo.nickname,
orderSigningRemark: this.completeRemark,
}
try {
const result = await this.orderInfoEdit(orderData);
if (result) {
uni.showToast({
title: '确认挂账信息成功',
icon: 'success'
});
this.$emit('refresh');
} else {
uni.showToast({
title: '操作失败,请重试',
icon: 'none'
});
}
} catch (error) {
console.error('确认挂账信息失败:', error);
uni.showToast({
title: '操作失败,请重试',
icon: 'none'
});
} finally {
this.showConfirmHangAccount = false;
this.completeRemark = '';
}
},
/* confirmHangAccountReceived() {
console.log('确认挂账信息', this.orderData.id);
let orderData = {
id: this.orderData.orderId,
orderSigningChargeId: this.userinfo.id,
orderSigningChargeName: this.userinfo.nickname,
orderSigningRemark: this.completeRemark,
}
this.orderInfoEdit(orderData)
this.showConfirmHangAccount = false;
this.completeRemark = ''
}, */
// 取消确认挂账
cancelConfirmHangAccount() {
this.showConfirmHangAccount = false;
this.completeRemark = '';
},
// 取消确认挂账
cancelLookConfirmHangAccount() {
this.showLookConfirmHangAccount = false;
},
// 判断是否为数字ID
isNumeric(value) {
return /^\d+$/.test(value);
},
// 格式化时间戳
formatTimestamp(timestamp) {
if (!timestamp) return null;
const date = new Date(timestamp);
const year = date.getFullYear();
const month = (date.getMonth() + 1).toString().padStart(2, '0');
const day = date.getDate().toString().padStart(2, '0');
const hours = date.getHours().toString().padStart(2, '0');
const minutes = date.getMinutes().toString().padStart(2, '0');
return `${year}-${month}-${day} ${hours}:${minutes}`;
},
// 计算耗时
calculateDuration(startTime, endTime) {
if (!startTime) return '暂无数据';
if (!endTime) return '暂无数据'
const start = new Date(startTime);
const end = endTime ? new Date(endTime) : new Date();
// 计算时间差(毫秒)
const diffMs = end - start;
// 如果结束时间小于开始时间,返回未知
if (diffMs < 0) return '时间数据异常';
// 转换为小时、分钟
const hours = Math.floor(diffMs / (1000 * 60 * 60));
const minutes = Math.floor((diffMs % (1000 * 60 * 60)) / (1000 * 60));
if (hours > 0) {
return `${hours}小时${minutes}分钟`;
} else {
return `${minutes}分钟`;
}
},
editOrder() {
// 将订单数据转换为JSON字符串进行传递
const orderDataStr = JSON.stringify(this.orderData);
uni.navigateTo({
url: `/pages/rescue/initiateEdit?data=${encodeURIComponent(orderDataStr)}&rescueType=${this.orderData.rescueType}`
});
},
// 调度流程查看
viewDispatchDetails() {
uni.navigateTo({
url: '/pages/details/dispatchDetails?id=' + this.orderData.id
});
},
gotoDispatchProcess(id) {
uni.navigateTo({
url: '/pages/process/dispatchProcess?id=' + id
});
},
gotoDispatchAgentDriverExecute(id) {
uni.navigateTo({
url: '/pages/process/dispatchAgentDriverExecute?id=' + id
});
},
// 获取渠道名称
/* async fetchSectionRoadName() {
const rawValue = this.orderData.sectionRoad;
if (!rawValue) {
this.sectionRoadName = '暂无数据';
return;
}
// 如果是数字,按 ID 查询字典
if (this.isNumeric(rawValue)) {
console.log('rawValue', rawValue)
try {
const dictData = await getDictDataById(rawValue);
this.sectionRoadName = dictData.label || rawValue;
} catch (error) {
console.error("字典查询失败,使用原始值:", error);
this.sectionRoadName = rawValue;
}
} else {
// 非数字,直接使用文字
this.sectionRoadName = rawValue;
}
}, */
}
}
</script>
<style lang="scss" scoped>
.orderCard {
background-color: #fff;
padding: 24rpx;
border-radius: 16rpx;
display: flex;
flex-direction: column;
row-gap: 22rpx;
box-shadow: 2rpx 4rpx 8rpx rgba(0, 0, 0, 0.1);
}
.orderInfoContainer {
display: flex;
flex-direction: column;
gap: 12rpx;
}
.infoRow {
display: flex;
font-size: 34rpx;
line-height: 1.5;
}
.infoLabel {
color: #666;
width: 250rpx;
}
.infoValue {
color: #333;
flex: 1;
}
.orderCardHeader {
line-height: 1.5;
.orderCardType {
background-color: #EAF1FE;
color: #317DFA;
padding: 8rpx 16rpx;
border-radius: 16rpx 0 16rpx 0;
font-size: 24rpx;
margin-right: 12rpx;
line-height: 1;
}
.orderCardTitle {
color: #000;
font-weight: bold;
}
}
.orderCardFooter {
display: flex;
justify-content: space-between;
align-items: center;
.orderCardDateTime {
color: #919191;
font-size: 24rpx;
}
.orderCardBtnGroup {
display: flex;
align-items: center;
column-gap: 16rpx;
}
.orderCardBtnGroupItem {
background-color: #317DFA;
color: #fff;
border: 1px solid #317DFA;
padding: 10rpx 20rpx;
border-radius: 28rpx;
}
.orderCardBtnGroupItemZp {
background-color: #317DFA;
color: #fff;
border: 1px solid #317DFA;
padding: 20rpx 50rpx;
border-radius: 28rpx;
font-size: 34rpx;
}
.orderCardBtnRevork {
/* display: flex;
justify-content: center;
align-items: center; */
background-color: red;
color: #fff;
border: 1px solid red;
padding: 10rpx 20rpx;
border-radius: 28rpx;
// width: 160rpx;
}
}
.orderCardEditView {
width: 100%;
margin: 10rpx 0 0 0;
display: flex;
justify-content: space-between;
align-items: center;
}
.orderCardTopTitle {
font-size: 36rpx;
font-weight: bold;
color: #000;
}
.orderCardEditBtn {
display: flex;
justify-content: center;
align-items: center;
background-color: #317DFA;
color: #fff;
border: 1px solid #317DFA;
padding: 6rpx 16rpx;
border-radius: 28rpx;
font-size: 28rpx;
}
.orderCardRevorkBtn {
display: flex;
justify-content: center;
align-items: center;
background-color: red;
color: #fff;
border: 1px solid red;
padding: 6rpx 16rpx;
border-radius: 28rpx;
// width: 160rpx;
font-size: 28rpx;
}
.orderCardViewDispatchBtn {
display: flex;
justify-content: center;
align-items: center;
background-color: #67c23a;
color: #fff;
border: 1px solid #67c23a;
padding: 6rpx 16rpx;
border-radius: 28rpx;
// width: 160rpx;
font-size: 28rpx;
}
.orderCardRevorkDisabledBtn {
display: flex;
justify-content: center;
align-items: center;
background-color: #CCCCCC;
color: #FFFFFF;
border: 1px solid #CCCCCC;
padding: 6rpx 16rpx;
border-radius: 28rpx;
// width: 160rpx;
font-size: 28rpx;
}
/* 司机信息部分样式 */
.driverInfoHeader {
display: flex;
justify-content: space-between;
align-items: center;
margin-bottom: 16rpx;
.driverName {
font-size: 32rpx;
// font-weight: bold;
color: black;
}
.driverPhone {
font-size: 28rpx;
color: black;
}
}
.driverCarInfo {
display: flex;
justify-content: space-between;
align-items: center;
margin-bottom: 24rpx;
border-top: 4rpx dashed #e2e5ea;
padding-top: 12rpx;
.carNumber {
font-size: 28rpx;
font-weight: bold;
color: #333;
}
.rescueType {
// background-color: #EAF1FE;
color: black;
padding: 8rpx 16rpx;
border-radius: 16rpx;
font-size: 28rpx;
}
}
.timeInfoContainer {
display: flex;
flex-direction: column;
gap: 12rpx;
.timeInfoRow {
display: flex;
justify-content: space-between;
font-size: 26rpx;
.timeLabel {
color: #666;
}
.timeValue {
color: #333;
}
}
}
// 展开控制按钮样式
.expand-control {
display: flex;
justify-content: center;
align-items: center;
margin-top: 20rpx;
padding: 16rpx;
border-top: 1rpx solid #eee;
color: #317DFA;
.expand-text {
font-size: 28rpx;
margin-right: 10rpx;
}
}
/* 确认订单完成按钮样式 */
.confirm-order-btn-container {
display: flex;
justify-content: center;
}
.confirm-order-btn {
background-color: #317DFA;
color: #fff;
padding: 16rpx 32rpx;
border-radius: 28rpx;
font-size: 28rpx;
text-align: center;
width: 100%;
box-shadow: 0 4rpx 8rpx rgba(49, 125, 250, 0.3);
}
.confirm-order-btn:active {
background-color: #2563c8;
}
/* 弹窗内容样式 */
.confirm-modal-content {
padding: 20rpx;
width: 100%;
}
.modal-label {
display: flex;
width: 100%;
justify-content: start;
margin-bottom: 20rpx;
font-size: 28rpx;
color: #333;
}
.remark-input {
margin-top: 10rpx;
}
//、、、、、、、、、、、、、、、、、、、、、、
.confirm-order-btn-container-gz {
display: flex;
justify-content: space-between;
margin-top: 20rpx;
gap: 20rpx;
.confirm-order-btn-gz {
flex: 1;
background-color: #317DFA;
color: #fff;
padding: 16rpx 32rpx;
border-radius: 28rpx;
font-size: 28rpx;
text-align: center;
}
.confirm-hang-account-gz {
background-color: #19be6b;
}
.confirm-hang-account-ygz {
background-color: #b5bbbf;
}
.confirm-order-btn-gz:active {
background-color: #2563c8;
}
.confirm-hang-account-gz:active {
background-color: #18b566;
}
}
// 弹窗内容样式
.modal-content {
padding: 20rpx;
display: flex;
flex-direction: column;
align-items: center;
width: 100%;
}
.modal-title {
font-size: 32rpx;
font-weight: bold;
margin-bottom: 30rpx;
}
.amount-display {
display: flex;
justify-content: start;
align-items: center;
margin-bottom: 40rpx;
width: 100%;
.amount-label {
font-size: 30rpx;
color: #333;
}
.amount-value {
font-size: 36rpx;
font-weight: bold;
color: #fa3534;
}
.amount-value-two {
font-size: 36rpx;
color: #000000;
}
}
.hang-account-buttons {
display: flex;
justify-content: space-between;
width: 100%;
gap: 20rpx;
.hang-account-btn {
flex: 1;
padding: 20rpx 0;
border-radius: 12rpx;
text-align: center;
font-size: 28rpx;
&.received {
background-color: #19be6b;
color: #fff;
}
&.not-received {
background-color: #ff9900;
color: #fff;
}
&.cancel {
background-color: #f2f2f2;
color: #333;
}
}
}
// 按钮组容器
.button-group-container {
display: flex;
justify-content: space-between;
align-items: center;
gap: 20rpx;
margin-top: 20rpx;
flex-wrap: wrap;
}
.button-group-container-two {
display: flex;
justify-content: space-between;
align-items: center;
gap: 20rpx;
margin-top: 10rpx;
flex-wrap: wrap;
}
// 挂账按钮组
.hang-account-btn-group {
display: flex;
flex: 1;
min-width: 0;
.hang-account-btn {
flex: 1;
padding: 16rpx 24rpx;
border-radius: 28rpx;
font-size: 32rpx;
text-align: center;
white-space: nowrap;
overflow: hidden;
text-overflow: ellipsis;
// 不同状态下的样式
&.agree {
background-color: #317DFA;
color: #fff;
box-shadow: 0 4rpx 8rpx rgba(49, 125, 250, 0.3);
}
&.confirm {
background-color: #19be6b;
color: #fff;
box-shadow: 0 4rpx 8rpx rgba(25, 190, 107, 0.3);
}
&.confirmed {
background-color: #b5bbbf;
color: #fff;
cursor: default;
}
// 活动状态
&:active:not(.confirmed) {
opacity: 0.8;
transform: translateY(2rpx);
}
}
}
// 完成订单按钮
.complete-order-btn {
flex-shrink: 0;
flex: 1;
.complete-btn {
background-color: #317DFA;
color: #fff;
padding: 16rpx 32rpx;
border-radius: 28rpx;
font-size: 32rpx;
text-align: center;
white-space: nowrap;
box-shadow: 0 4rpx 8rpx rgba(49, 125, 250, 0.3);
&:active {
background-color: #2563c8;
transform: translateY(2rpx);
}
}
}
.orderCardBtnGroupItem {
&.loading {
opacity: 0.7;
pointer-events: none; // 防止重复点击
}
}
// 确保加载指示器居中
.uni-load-more {
display: flex;
justify-content: center;
align-items: center;
:deep(.uni-load-more__content) {
margin: 0;
}
}
.rescue-type-modal {
padding: 20rpx;
}
.rescue-type-grid {
display: grid;
grid-template-columns: repeat(3, 1fr);
gap: 30rpx;
margin-top: 20rpx;
}
.rescue-type-item {
display: flex;
flex-direction: column;
align-items: center;
padding: 40rpx;
border-radius: 12rpx;
background-color: #d5d5d5;
// transition: all 0.3s;
&:active {
background-color: #e6f3ff;
}
&--selected {
background-color: #e6f3ff !important;
border: 2rpx solid #317DFA;
}
}
.rescue-type-icon {
width: 80rpx;
height: 80rpx;
margin-bottom: 16rpx;
}
.rescue-type-label {
font-size: 24rpx;
color: #333;
}
// 按钮组容器 - 添加过渡效果
.button-group-container-two-1 {
display: flex;
justify-content: space-between;
align-items: center;
gap: 20rpx;
margin-top: 10rpx;
flex-wrap: nowrap; // 改为不换行
position: relative;
overflow: hidden;
transition: all 0.3s ease;
}
// 代司机流程记录按钮容器 - 添加过渡效果
.hang-account-btn-group-1 {
transition: all 0.3s ease;
overflow: hidden;
white-space: nowrap;
display: flex;
flex: 1;
min-width: 0;
.hang-account-btn {
flex: 1;
padding: 16rpx 24rpx;
border-radius: 28rpx;
font-size: 32rpx;
text-align: center;
white-space: nowrap;
overflow: hidden;
text-overflow: ellipsis;
// 不同状态下的样式
&.agree {
background-color: #317DFA;
color: #fff;
// box-shadow: 0 4rpx 8rpx rgba(49, 125, 250, 0.3);
}
&.confirm {
background-color: #19be6b;
color: #fff;
// box-shadow: 0 4rpx 8rpx rgba(25, 190, 107, 0.3);
}
&.confirmed {
background-color: #b5bbbf;
color: #fff;
cursor: default;
}
// 活动状态
&:active:not(.confirmed) {
opacity: 0.8;
transform: translateY(2rpx);
}
}
}
// 展开/收起箭头
.expand-collapse-arrow {
display: flex;
align-items: center;
justify-content: center;
width: 50rpx;
height: 80rpx;
border-radius: 10rpx;
background-color: #e6f3ff;
cursor: pointer;
flex-shrink: 0;
transition: all 0.3s ease;
&:active {
background-color: #e5e5e5;
transform: scale(0.95);
}
}
// 遮罩层样式
.loading-overlay {
position: fixed;
top: 0;
left: 0;
right: 0;
bottom: 0;
background-color: rgba(0, 0, 0, 0.6); // 加深背景色
display: flex;
justify-content: center;
align-items: center;
z-index: 99999 !important;
.loading-content {
background-color: #fff;
padding: 50rpx 60rpx;
border-radius: 20rpx;
display: flex;
flex-direction: column;
align-items: center;
justify-content: center;
min-width: 320rpx;
min-height: 220rpx;
box-shadow: 0 10rpx 30rpx rgba(0, 0, 0, 0.3);
.loading-text {
margin-top: 25rpx;
font-size: 30rpx;
color: #333;
font-weight: 500;
}
// 确保加载组件样式正确
:deep(.uni-load-more) {
display: flex;
justify-content: center;
align-items: center;
.uni-load-more__content {
margin: 0;
}
.uni-load-more__icon {
margin-right: 0;
}
}
}
}
// 禁用状态样式
.disabled-button {
pointer-events: none;
}
.hang-account-btn.disabled {
background-color: #b5bbbf !important;
color: #f2f2f2 !important;
cursor: not-allowed !important;
opacity: 0.6;
}
</style>