diff --git a/OCH/taxi/unmanned-driver/src/main/java/com/mogo/och/taxi/ui/task/TaxiTaskModel.kt b/OCH/taxi/unmanned-driver/src/main/java/com/mogo/och/taxi/ui/task/TaxiTaskModel.kt index d013c8e749..369f8bf980 100644 --- a/OCH/taxi/unmanned-driver/src/main/java/com/mogo/och/taxi/ui/task/TaxiTaskModel.kt +++ b/OCH/taxi/unmanned-driver/src/main/java/com/mogo/och/taxi/ui/task/TaxiTaskModel.kt @@ -1,4 +1,4 @@ -package com.mogo.och.taxi.model +package com.mogo.och.taxi.ui.task import android.annotation.SuppressLint import android.content.Context @@ -7,6 +7,7 @@ import android.text.TextUtils import com.alibaba.android.arouter.launcher.ARouter import com.amap.api.maps.model.LatLng import com.mogo.aicloud.services.socket.IMogoOnMessageListener +import com.mogo.commons.AbsMogoApplication import com.mogo.commons.module.intent.IMogoIntentListener import com.mogo.commons.module.intent.IntentManager import com.mogo.commons.module.status.IMogoStatusChangedListener @@ -22,13 +23,9 @@ import com.mogo.eagle.core.function.api.autopilot.IMoGoAutopilotStatusListener import com.mogo.eagle.core.function.api.autopilot.IMoGoChassisLocationGCJ02Listener import com.mogo.eagle.core.function.api.autopilot.IMoGoPlanningRottingListener import com.mogo.eagle.core.function.call.autopilot.CallerAutoPilotControlManager -import com.mogo.eagle.core.function.call.autopilot.CallerAutoPilotControlManager.cancelAutoPilot -import com.mogo.eagle.core.function.call.autopilot.CallerAutoPilotControlManager.setIPCDemoMode -import com.mogo.eagle.core.function.call.autopilot.CallerAutoPilotControlManager.setIgnoreConditionDraw import com.mogo.eagle.core.function.call.autopilot.CallerAutoPilotStatusListenerManager import com.mogo.eagle.core.function.call.autopilot.CallerAutoPilotStatusListenerManager.updateAutopilotControlParameters import com.mogo.eagle.core.function.call.autopilot.CallerChassisLocationGCJ02ListenerManager -import com.mogo.eagle.core.function.call.autopilot.CallerChassisLocationGCJ02ListenerManager.addListener import com.mogo.eagle.core.function.call.autopilot.CallerChassisLocationGCJ02ListenerManager.getChassisLocationGCJ02 import com.mogo.eagle.core.function.call.autopilot.CallerPlanningRottingListenerManager import com.mogo.eagle.core.network.utils.GsonUtil @@ -43,96 +40,100 @@ import com.mogo.eagle.core.utilcode.util.NetworkUtils import com.mogo.eagle.core.utilcode.util.ToastUtils import com.mogo.eagle.core.utilcode.util.UiThreadHandler import com.mogo.och.common.module.biz.common.socketmessage.OCHSocketMessageManager -import com.mogo.och.common.module.biz.common.socketmessage.OCHSocketMessageManager.pushAppOperationalMsgBox -import com.mogo.och.common.module.biz.common.socketmessage.OCHSocketMessageManager.registerSocketMessageListener -import com.mogo.och.common.module.biz.common.socketmessage.OCHSocketMessageManager.releaseSocketMessageListener import com.mogo.och.common.module.biz.common.socketmessage.data.OCHOperationalMessage +import com.mogo.och.common.module.biz.constant.LoginStatusManager import com.mogo.och.common.module.biz.constant.OchCommonConst import com.mogo.och.common.module.biz.network.OchCommonServiceCallback import com.mogo.och.common.module.biz.provider.LoginService import com.mogo.och.common.module.callback.OchAdasStartFailureCallback -import com.mogo.och.common.module.manager.AbnormalFactorsLoopManager.startLoopAbnormalFactors -import com.mogo.och.common.module.manager.AbnormalFactorsLoopManager.stopLoopAbnormalFactors +import com.mogo.och.common.module.manager.AbnormalFactorsLoopManager import com.mogo.och.common.module.manager.OCHAdasAbilityManager import com.mogo.och.common.module.manager.distancemamager.IDistanceListener import com.mogo.och.common.module.manager.distancemamager.ITrajectoryListener -import com.mogo.och.common.module.manager.distancemamager.TrajectoryAndDistanceManager.addDistanceListener -import com.mogo.och.common.module.manager.distancemamager.TrajectoryAndDistanceManager.addTrajectoryListener +import com.mogo.och.common.module.manager.distancemamager.TrajectoryAndDistanceManager import com.mogo.och.common.module.manager.distancemamager.TrajectoryAndDistanceManager.setStationPoint import com.mogo.och.common.module.map.AmapNaviToDestinationModel import com.mogo.och.common.module.utils.CoordinateCalculateRouteUtil.coordinateConverterWgsToGcjLocations import com.mogo.och.common.module.voice.VoiceNotice -import com.mogo.och.taxi.bean.ContrailListRespBean import com.mogo.och.taxi.bean.OrderDetail +import com.mogo.och.taxi.bean.PrepareTaskRespBean +import com.mogo.och.taxi.bean.QueryCarOrderByNoRespBean import com.mogo.och.taxi.bean.QueryCurrentTaskRespBean -import com.mogo.och.taxi.bean.Site import com.mogo.och.taxi.bean.StartServiceRespBean +import com.mogo.och.taxi.bean.TrajectoryListRespBean import com.mogo.och.taxi.callback.IOCHTaxiAutopilotPlanningCallback import com.mogo.och.taxi.callback.ITaxiADASStatusCallback import com.mogo.och.taxi.callback.ITaxiControllerStatusCallback import com.mogo.och.taxi.callback.ITaxiOrderStatusCallback +import com.mogo.och.taxi.callback.ITaxiTaskCallback import com.mogo.och.taxi.constant.TaskStatusEnum +import com.mogo.och.taxi.constant.TaskTypeEnum +import com.mogo.och.taxi.constant.TaxiCarServingStatusManager import com.mogo.och.taxi.constant.TaxiOrderStatusEnum import com.mogo.och.taxi.constant.TaxiOrderStatusEnum.Companion.valueOf import com.mogo.och.taxi.constant.TaxiUnmannedConst import com.mogo.och.taxi.constant.TaxiUnmannedConst.Companion.BUSINESSTYPE -import com.mogo.och.taxi.constant.TaxiUnmannedConst.Companion.COUNTDOWN_INTERVAL -import com.mogo.och.taxi.network.CarServiceManager -import com.mogo.och.taxi.network.CarServiceManager.arriveSite -import com.mogo.och.taxi.network.CarServiceManager.startTask +import com.mogo.och.taxi.constant.TaxiUnmannedConst.Companion.START_AUTOPILOT_COUNTDOWN_INTERVAL +import com.mogo.och.taxi.network.TaxiTaskWithOrderServiceManager +import com.mogo.och.taxi.utils.RxJavaUtils import com.mogo.och.taxi.utils.TaxiAnalyticsManager import com.mogo.och.taxi.utils.TaxiTrajectoryManager import com.zhjt.service.chain.ChainLog -import io.reactivex.exceptions.UndeliverableException -import io.reactivex.functions.Consumer -import io.reactivex.plugins.RxJavaPlugins -import mogo.telematics.pad.MessagePad +import io.reactivex.Observable +import io.reactivex.android.schedulers.AndroidSchedulers +import io.reactivex.disposables.Disposable +import io.reactivex.schedulers.Schedulers import mogo.telematics.pad.MessagePad.ArrivalNotification import mogo.telematics.pad.MessagePad.GlobalPathResp import mogo_msg.MogoReportMsg.MogoReportMessage import system_master.SsmInfo import system_master.SystemStatusInfo -import java.io.IOException +import java.util.concurrent.TimeUnit /** * @author: wangmingjun * @date: 2023/7/25 */ @SuppressLint("StaticFieldLeak") -object TaxiModel { +object TaxiTaskModel { - private val TAG = TaxiModel::class.java.simpleName + private val TAG = SceneConstant.M_TAXI + TaxiTaskModel::class.java.simpleName - private var mContext: Context? = null + private lateinit var mContext: Context - private var mCurrentTaskAndOrder: QueryCurrentTaskRespBean.Result? = null //当前任务和订单 + private var mQueryTaskWithOrderDisposable: Disposable? = null - /** - * 标定站点的任务, 在没有到站之前, 轮询接口是没有的. - * 到站后, 轮询的任务会显示到站站点为这个虚拟站点,任务状态为到站 - */ - private var mUntruthTask: StartServiceRespBean.Result? = null // 前往出车点的伪任务, 后台并不算做真正的任务 + var loginService: LoginService? = null - private var mOrderContrails: MutableList? = - null // 运营单(接驾任务和送驾任务的轨迹集合) + //Model->Presenter:自动驾驶状态相关 + private var mADASStatusCallback: ITaxiADASStatusCallback? = null - private var mCurTaskContrail: ContrailListRespBean.Result? = null //当前在跑的任务的轨迹信息 + //Model->Presenter/ViewModel:VR mode等 + private var mControllerStatusCallback: ITaxiControllerStatusCallback? = null - private var mADASStatusCallback //Model->Presenter:自动驾驶状态相关 - : ITaxiADASStatusCallback? = null + //Model->Presenter/ViewModel:订单变更 + private var mOrderStatusCallback: ITaxiOrderStatusCallback? = null - private var mControllerStatusCallback //Model->Presenter:VR mode等 - : ITaxiControllerStatusCallback? = null - private var mOrderStatusCallback //Model->Presenter:订单变更 - : ITaxiOrderStatusCallback? = null private var mAutopilotPlanningCallback: IOCHTaxiAutopilotPlanningCallback? = null + private var mTaxiTaskCallback: ITaxiTaskCallback? = null + + //当前任务和订单 + private var mCurrentTaskWithOrder: QueryCurrentTaskRespBean.Result? = null + + //开始车辆到标定站点的特殊任务 + private var mDriveToNearestStationTask: StartServiceRespBean.Result? = null + + //运营单(接驾任务和送驾任务的轨迹集合) + private var mTaskTrajectoryList: MutableList = mutableListOf() + + //当前在跑的任务的轨迹信息 + private var mCurrentTaskTrajectory: TrajectoryListRespBean.Result? = null + @Volatile private var isRestartAutopilot = false - private val mRoutePoints: MutableList? = ArrayList() - - var loginService: LoginService? = null + private val mCurrentTaskRoutePointsGcj: MutableList = ArrayList() fun setMoGoAutopilotPlanningListener(moGoAutopilotPlanningCallback: IOCHTaxiAutopilotPlanningCallback?) { mAutopilotPlanningCallback = moGoAutopilotPlanningCallback @@ -150,51 +151,16 @@ object TaxiModel { mOrderStatusCallback = callback } + fun setTaskCallback(callback: ITaxiTaskCallback) { + mTaxiTaskCallback = callback + } + fun init(context: Context) { mContext = context.applicationContext - initListeners() loginService = ARouter.getInstance().build(OchCommonConst.LOGINSERVICE).navigation() as LoginService - - //2022.1.28 - // 调用Disposable.dispose() 时候会出现InterruptedException 导致出现崩溃 - // The exception could not be delivered to the consumer because it has already canceled/disposed the flow or the excTeption has nowhere to go to begin with - RxJavaPlugins.setErrorHandler(Consumer { e -> - var e = e - if (e is UndeliverableException) { - e = (e.cause)!! - d(SceneConstant.M_TAXI + TAG, "UndeliverableException") - } - if ((e is IOException)) { // - // fine, irrelevant network problem or API that throws on cancellation - d(SceneConstant.M_TAXI + TAG, "IOException") - return@Consumer - } - if (e is InterruptedException) { - // fine, some blocking code was interrupted by a dispose call - d(SceneConstant.M_TAXI + TAG, "InterruptedException") - return@Consumer - } - if ((e is NullPointerException) || (e is IllegalArgumentException)) { - // that's likely a bug in the application - d(SceneConstant.M_TAXI + TAG, "NullPointerException or IllegalArgumentException") - Thread.currentThread().uncaughtExceptionHandler?.uncaughtException( - Thread.currentThread(), - e - ) - return@Consumer - } - if (e is IllegalStateException) { - // that's a bug in RxJava or in a custom operator - d(SceneConstant.M_TAXI + TAG, "IllegalStateException") - Thread.currentThread().uncaughtExceptionHandler?.uncaughtException( - Thread.currentThread(), - e - ) - return@Consumer - } - d(SceneConstant.M_TAXI + TAG, "Undeliverable exception") - }) + initListeners() + RxJavaUtils.setErrorHandler(TAG) } fun release() { @@ -204,51 +170,30 @@ object TaxiModel { private fun initListeners() { // 2021.11.1重构自动驾驶 实现接口 IMoGoAutopilotStatusListener 注册监听 替换IMogoAdasOCHCallback接口 - CallerAutoPilotStatusListenerManager.addListener(TAG, mGoAutopilotStatusListener) - IntentManager.getInstance() - .registerIntentListener(ConnectivityManager.CONNECTIVITY_ACTION, mNetWorkIntentListener) + CallerAutoPilotStatusListenerManager.addListener(TAG, mMogoAutopilotStatusListener) + //定位监听, 传false是高德坐标系 + CallerChassisLocationGCJ02ListenerManager.addListener(TAG, 10, mMapLocationListener) + //2021.11.1 自动驾驶路线规划接口 + CallerPlanningRottingListenerManager.addListener(TAG, mMogoAutopilotPlanningListener) + //开启自驾后 异常信息返回 + OCHAdasAbilityManager.getInstance() + .setAdasStartFailureCallback(mAdasStartAutopilotFailureListener) + OCHSocketMessageManager.registerSocketMessageListener( + OCHSocketMessageManager.msgMonitorType, + mMogoOnSocketMessageListener + ) MogoStatusManager.getInstance().registerStatusChangedListener( TAG, StatusDescriptor.VR_MODE, mMogoStatusChangedListener ) - - //定位监听, 传false是高德坐标系 - addListener(TAG, 10, mMapLocationListener) - - //2021.11.1 自动驾驶路线规划接口 - CallerPlanningRottingListenerManager.addListener(TAG, moGoAutopilotPlanningListener) - - //开启自驾后 异常信息返回 - OCHAdasAbilityManager.getInstance().setAdasStartFailureCallback(mAdasStartFailureListener) - registerSocketMessageListener( - OCHSocketMessageManager.msgMonitorType, - mMogoOnMessageListener - ) - startLoopAbnormalFactors(mContext!!) - addDistanceListener(TAG, distanceListener) - addTrajectoryListener(TAG, trajectoryListener) + IntentManager.getInstance() + .registerIntentListener(ConnectivityManager.CONNECTIVITY_ACTION, mNetWorkIntentListener) + AbnormalFactorsLoopManager.startLoopAbnormalFactors(mContext) + TrajectoryAndDistanceManager.addDistanceListener(TAG, localCalculateDistanceListener) + TrajectoryAndDistanceManager.addTrajectoryListener(TAG, localCalculateTrajectoryListener) } - private val mMogoOnMessageListener = - object : IMogoOnMessageListener { - override fun target(): Class { - return OCHOperationalMessage::class.java - } - - override fun onMsgReceived(obj: OCHOperationalMessage) { - if (obj == null) { - d(SceneConstant.M_TAXI + TAG, "onMsgReceived = null") - return - } - d(SceneConstant.M_TAXI + TAG, "onMsgReceived = " + obj.message) - pushAppOperationalMsgBox( - obj.pushTimeStamp, - obj.message, OCHSocketMessageManager.OPERATION_SYSTEM - ) - } - } - private fun releaseListeners() { MogoStatusManager.getInstance().unregisterStatusChangedListener( TAG, @@ -258,516 +203,14 @@ object TaxiModel { // 注销地图监听 CallerChassisLocationGCJ02ListenerManager.removeListener(TAG) - releaseSocketMessageListener(OCHSocketMessageManager.msgMonitorType) - CallerAutoPilotStatusListenerManager.removeListener(mGoAutopilotStatusListener) - CallerPlanningRottingListenerManager.removeListener(moGoAutopilotPlanningListener) + OCHSocketMessageManager.releaseSocketMessageListener(OCHSocketMessageManager.msgMonitorType) + CallerAutoPilotStatusListenerManager.removeListener(mMogoAutopilotStatusListener) + CallerPlanningRottingListenerManager.removeListener(mMogoAutopilotPlanningListener) OCHAdasAbilityManager.getInstance().setAdasStartFailureCallback(null) - stopLoopAbnormalFactors() + AbnormalFactorsLoopManager.stopLoopAbnormalFactors() } - // 获取当前订单状态 - fun getCurOrderStatus(): TaxiOrderStatusEnum? { - if (mCurrentTaskAndOrder == null) TaxiOrderStatusEnum.None - val order: OrderDetail = mCurrentTaskAndOrder!!.order!! - return valueOf(order.orderStatus) - } - - fun getCurTaskStatus(): Int? { - if (mCurrentTaskAndOrder == null) TaskStatusEnum.None - return mCurrentTaskAndOrder?.currentStatus - } - - fun getCurTaskAndOrder(): QueryCurrentTaskRespBean.Result? { - return mCurrentTaskAndOrder - } - - fun getCurUntruthTask(): StartServiceRespBean.Result? { - return mUntruthTask - } - - fun getCurOrderContrails(): MutableList? { - return mOrderContrails - } - - fun getCurTaskContrail(): ContrailListRespBean.Result? { - return mCurTaskContrail - } - - //更新本地currentOrder信息,并保存订单到本地避免车机重启丢失数据 - private fun updateNativeCurrentOrder(data: QueryCurrentTaskRespBean.Result?) { - if (data == null) { - return - } - mCurrentTaskAndOrder = data - - SharedPrefsMgr.getInstance(mContext!!).putString( - TaxiUnmannedConst.SP_KEY_OCH_TAXI_ORDER, - GsonUtil.jsonFromObject(data) - ) - - val currentOrder = mCurrentTaskAndOrder!!.order - - if (currentOrder != null) { - if (currentOrder!!.orderStatus == TaxiOrderStatusEnum.OnTheWayToEnd.code) { - if (FunctionBuildConfig.isDemoMode) { - // 当美化模式(演示模式)开启时: 订单对应自动驾驶开启后,置true - FunctionBuildConfig.isIgnoreConditionsDrawAutopilotTrajectoryData = true - setIgnoreConditionDraw(true) - setIPCDemoMode(true) - d(SceneConstant.M_TAXI + TAG, "美化模式-ignore:置为true(更新本地order信息)") - } - updateAutopilotControlParameters() - } - if (currentOrder!!.orderStatus == TaxiOrderStatusEnum.ArriveAtEnd.code) { - if (FunctionBuildConfig.isDemoMode) { - d(SceneConstant.M_TAXI + TAG, "setIPCDemoMode:false") - setIPCDemoMode(false) - } - clearAutopilotControlParameters() - } - } else { - if (FunctionBuildConfig.isDemoMode) { - d(SceneConstant.M_TAXI + TAG, "setIPCDemoMode:false") - setIPCDemoMode(false) - } - clearAutopilotControlParameters() - } - } - - /** - * 将业务订单信息保存,鹰眼可取用 - */ - private fun updateAutopilotControlParameters() { - val parameters = initAutopilotControlParameters() - if (null == parameters) { - e(SceneConstant.M_TAXI + TAG, "AutopilotControlParameters is empty.") - return - } - d(SceneConstant.M_TAXI + TAG, "AutopilotControlParameters is update.") - updateAutopilotControlParameters(parameters) - } - - private fun clearAutopilotControlParameters() { - d(SceneConstant.M_TAXI + TAG, "AutopilotControlParameters is clear.") - updateAutopilotControlParameters(null) - } - - fun updateCurrentTaskAndOrder(result: QueryCurrentTaskRespBean.Result?) { - mCurrentTaskAndOrder = result - updateNativeCurrentOrder(result) - } - - fun updateUntruthTask(untruthTask: StartServiceRespBean.Result?) { - mUntruthTask = untruthTask - } - - //清除任务订单信息 - fun clearCurrentOCHOrder() { - mCurrentTaskAndOrder = null - clearAutopilotControlParameters() - TaxiTrajectoryManager.getInstance().syncTrajectoryInfo() - SharedPrefsMgr.getInstance(mContext!!).remove(TaxiUnmannedConst.SP_KEY_OCH_TAXI_ORDER) - isRestartAutopilot = false - if (FunctionBuildConfig.isDemoMode) { - // 当美化模式(演示模式)开启时: 取消或订单已完成时,置false - FunctionBuildConfig.isIgnoreConditionsDrawAutopilotTrajectoryData = false - setIgnoreConditionDraw(false) - setIPCDemoMode(false) - d(SceneConstant.M_TAXI + TAG, "美化模式-ignore:置为false(已完成or清除当前订单)") - } - } - - //检测当前任务 - fun checkCurrentTask(): Boolean { - return mCurrentTaskAndOrder != null && mCurrentTaskAndOrder!!.startSite != null - && mCurrentTaskAndOrder!!.endSite != null - } - - private fun checkCurrentOrder(): Boolean { - return mCurrentTaskAndOrder != null && mCurrentTaskAndOrder!!.order != null - } - - /** - * 以当前订单为基础,开启自动驾驶 - */ - @ChainLog( - linkChainLog = ChainConstant.CHAIN_TYPE_SOCKET_AUTOPILOT, - linkCode = ChainConstant.CHAIN_SOURCE_ADAS, - nodeAliasCode = ChainConstant.CHAIN_CODE_OCH_TAXI_START_AUTOPILOT, - paramIndexes = [-1] - ) - fun startAutoPilot() { - if (!checkCurrentTask()) { - e(SceneConstant.M_TAXI + TAG, "no order or order is empty.") - ToastUtils.showShort("当前订单不存在或异常!") - return - } - - if (mCurTaskContrail == null) { - e(SceneConstant.M_TAXI + TAG, "no order or order is empty.") - ToastUtils.showShort("轨迹信息不存在!") - } - - //根据开关和后台是否发布轨迹启动自驾 - if (FunctionBuildConfig.isPassStartAutopilotCommand && mCurTaskContrail != null && TextUtils.isEmpty( - mCurTaskContrail!!.csvFileUrl - ) - && TextUtils.isEmpty(mCurTaskContrail!!.csvFileUrlDPQP) - ) { - ToastUtils.showLong("无发布轨迹, 请发布后重试") - e( - SceneConstant.M_TAXI + TAG, "isPassStartAutopilotCommand = " + - FunctionBuildConfig.isPassStartAutopilotCommand - + "busRoutesResult.csvFileUrl = " + mCurTaskContrail!!.csvFileUrl - + "busRoutesResult.csvFileUrlDPQP = " + mCurTaskContrail!!.csvFileUrlDPQP - ) - return - } - e( - SceneConstant.M_TAXI + TAG, "isPassStartAutopilotCommand = " + - FunctionBuildConfig.isPassStartAutopilotCommand - ) - if (!FunctionBuildConfig.isDemoMode && !OCHAdasAbilityManager.getInstance().autopilotAbilityStatus) { - ToastUtils.showLong( - OCHAdasAbilityManager.getInstance().autopilotUnAbilityReason + - ", 请稍候重试" - ) - TaxiAnalyticsManager.getInstance().triggerUnableStartAPReasonEvent( - mCurrentTaskAndOrder!!.startSite!!.siteName, - mCurrentTaskAndOrder!!.endSite!!.siteName, - mCurrentTaskAndOrder!!.lineId.toString(), // todo 这里原来传的是订单号, 现在是任务没有订单号,传了路线id - OCHAdasAbilityManager.getInstance().autopilotUnAbilityReason - ) - return - } - - //点击开始自动驾驶按钮订单状态去流转, 不再与自动驾驶是否启动成功挂钩 - isRestartAutopilot = mCurrentTaskAndOrder!!.currentStatus != TaskStatusEnum.StartTask.code - - val parameters = initAutopilotControlParameters() - if (null == parameters) { - e(SceneConstant.M_TAXI + TAG, "AutopilotControlParameters is empty.") - return - } - CallerAutoPilotControlManager.startAutoPilot(parameters) - d( - SceneConstant.M_TAXI + TAG, "start autopilot with parameter: %s", - GsonUtil.jsonFromObject(parameters) - + " ,startSiteName=" + mCurrentTaskAndOrder?.startSite?.siteName - + " ,endSiteName=" + mCurrentTaskAndOrder?.endSite?.siteName - + "isRestartAutopilot = " + isRestartAutopilot - ) - TaxiAnalyticsManager.getInstance().triggerStartAutopilotEvent( - isRestartAutopilot, - false, - mCurrentTaskAndOrder!!.startSite!!.siteName, - mCurrentTaskAndOrder!!.endSite!!.siteName, - mCurrentTaskAndOrder!!.lineId, - if (mCurrentTaskAndOrder!!.order != null) mCurrentTaskAndOrder!!.order!!.orderNo else "" - ) - if (mControllerStatusCallback != null) { - mControllerStatusCallback!!.startOpenAutopilot() - } - } - - private fun initAutopilotControlParameters(): AutopilotControlParameters? { - if (!checkCurrentTask()) { - e(SceneConstant.M_TAXI + TAG, "no order or order is empty.") - return null - } - - if (mCurTaskContrail == null) { - e(SceneConstant.M_TAXI + TAG, "curTaskContrail is empty.") - return null - } - - val parameters = AutopilotControlParameters() - - val startWgsLon = mCurrentTaskAndOrder!!.startSite!!.wgs84Lon - val startWgsLat = mCurrentTaskAndOrder!!.startSite!!.wgs84Lat - val endWgsLon = mCurrentTaskAndOrder!!.endSite!!.wgs84Lon - val endWgsLat = mCurrentTaskAndOrder!!.endSite!!.wgs84Lat - parameters.vehicleType = BUSINESSTYPE - parameters.startName = mCurrentTaskAndOrder!!.startSite!!.siteName // 8.10 拼音首字母大写 改为直接传中文 - parameters.endName = mCurrentTaskAndOrder!!.endSite!!.siteName // 8.10 拼音首字母大写 改为直接传中文 - parameters.startLatLon = - AutopilotControlParameters.AutoPilotLonLat(startWgsLat, startWgsLon) - parameters.endLatLon = AutopilotControlParameters.AutoPilotLonLat(endWgsLat, endWgsLon) - if (parameters.autoPilotLine == null) { - parameters.autoPilotLine = AutopilotControlParameters.AutoPilotLine( - mCurTaskContrail!!.lineId, - mCurTaskContrail!!.lineName, - mCurTaskContrail!!.csvFileUrl, - mCurTaskContrail!!.csvFileMd5, - mCurTaskContrail!!.txtFileUrl, - mCurTaskContrail!!.txtFileMd5, - mCurTaskContrail!!.contrailSaveTime, - "", // todo 这里原来传的是carModel, 现在没有这个信息 - mCurTaskContrail!!.csvFileUrlDPQP, - mCurTaskContrail!!.csvFileMd5DPQP, - mCurTaskContrail!!.txtFileUrlDPQP, - mCurTaskContrail!!.txtFileMd5DPQP, - mCurTaskContrail!!.contrailSaveTimeDPQP - ) - } - return parameters - } - - //结束自动驾驶 - fun cancelAutopilot() { - try { - cancelAutoPilot() - d(SceneConstant.M_TAXI + TAG, "结束自动驾驶") - } catch (e: Exception) { - e.printStackTrace() - } - } - - //根据围栏判断,是否到达起点 - private fun judgeTaskStartStation(location: MogoLocation) { - if (checkCurrentTask()) { - val startSite = mCurrentTaskAndOrder!!.startSite ?: return - val startLon = startSite.gcjLon - val startLat = startSite.gcjLat - val distance = CoordinateUtils.calculateLineDistance( - startLon, startLat, - location.longitude, location.latitude - ).toDouble() - i(SceneConstant.M_TAXI + TAG, "judgeTaskStartStation() distance = $distance") - if (distance <= TaxiUnmannedConst.ARRIVE_AT_START_STATION_DISTANCE) { - arriveSite(startSite.siteId, false) - } - } - } - - //监听网络变化,避免启动机器时无网导致无法更新订单信息 - private val mNetWorkIntentListener: IMogoIntentListener = - IMogoIntentListener { intentStr, _ -> - d(SceneConstant.M_TAXI + TAG, "onIntentReceived = %s", intentStr) - if ((ConnectivityManager.CONNECTIVITY_ACTION == intentStr)) { - if (NetworkUtils.isConnected(mContext)) { - loginService!!.queryLoginStatusByNet() - } - } - } - - private val mAdasStartFailureListener: OchAdasStartFailureCallback = - object : OchAdasStartFailureCallback { - override fun onStartAutopilotFailure( - startFailedCode: String, - startFailedMessage: String - ) { - TaxiAnalyticsManager.getInstance() - .triggerStartAutopilotFailureEventByAdas(startFailedCode, startFailedMessage) - if (mADASStatusCallback != null && !FunctionBuildConfig.isDemoMode) { - e( - SceneConstant.M_TAXI + TAG, - "mAdasStartFailureListener = $startFailedMessage" - ) - mADASStatusCallback!!.onStartAdasFailure() - } - } - } - - private val mMogoStatusChangedListener: IMogoStatusChangedListener = - IMogoStatusChangedListener { descriptor, isTrue -> - - // VR mode变更回调 - if (StatusDescriptor.VR_MODE == descriptor) { - if (mControllerStatusCallback != null) { - mControllerStatusCallback!!.onVRModeChanged(isTrue) - } - } - } - - // 自车定位 - private val mMapLocationListener: IMoGoChassisLocationGCJ02Listener = - object : IMoGoChassisLocationGCJ02Listener { - override fun onChassisLocationGCJ02(mogoLocation: MogoLocation?) { - //位置变化时,通过围栏判断是否到达x点 - if (null == mogoLocation) return - - if (mUntruthTask != null) { - judgeUntruthStation(mUntruthTask, mogoLocation) - } - - if (checkCurrentTask() && mCurrentTaskAndOrder?.currentStatus == TaskStatusEnum.StartTask.code) { -// judgeTaskStartStation(mogoLocation) - judgeTaskEndSiteStation(mogoLocation) - } - - if (mControllerStatusCallback != null) { - mControllerStatusCallback!!.onCarLocationChanged(mogoLocation) - } - } - } - - private fun judgeUntruthStation( - virtualTask: StartServiceRespBean.Result?, - currentLocation: MogoLocation - ) { - if (mUntruthTask == null || virtualTask == null) return - val distance = CoordinateUtils.calculateLineDistance( - virtualTask.gcjLon, virtualTask.gcjLat, - currentLocation.longitude, currentLocation.latitude - ).toDouble() - i( - SceneConstant.M_TAXI + TAG, - "judgeEndStation() ${virtualTask.siteName} distance = $distance" - ) - if (distance <= TaxiUnmannedConst.ARRIVE_AT_START_STATION_DISTANCE) { // 15米内到站 - arriveSite(virtualTask.siteId, true) - } - } - - /** - * 到站(起点、终点) - * isArriveEndSite true 终点, false 起点 - */ - fun arriveSite(siteId: Long, isArriveEndSite: Boolean) { - i( - SceneConstant.M_TAXI + TAG, - "arriveSite ${siteId}" - ) - arriveSite(mContext!!, siteId, object : OchCommonServiceCallback { - override fun onSuccess(data: BaseData?) { - if (data == null || data.code != 0) return - d(SceneConstant.M_TAXI + TAG, GsonUtil.jsonFromObject(data)) - mUntruthTask = null - if (isArriveEndSite) { - cleanStation() - //2020.8.23 到站后不再调用取消自驾. 原因是取消自驾,D档位会溜车 -// cancelAutopilot() - } - } - - override fun onFail(code: Int, msg: String?) { - d(SceneConstant.M_TAXI + TAG, "$code $msg") - } - - }) - } - - private fun startTask(lineId: Long) { - startTask(mContext!!, lineId, object : OchCommonServiceCallback { - override fun onSuccess(data: BaseData?) { - d(SceneConstant.M_TAXI + TAG, GsonUtil.jsonFromObject(data)) - } - - override fun onFail(code: Int, msg: String?) { - d(SceneConstant.M_TAXI + TAG, "$code $msg") - } - - }) - } - - private fun judgeTaskEndSiteStation(currentLocation: MogoLocation) { - i(SceneConstant.M_TAXI + TAG, "judgeEndStation() judgeTaskEndSiteStation") - if (!checkCurrentTask()) { - return - } - val endSite = mCurrentTaskAndOrder!!.endSite ?: return - - val endLon = endSite.gcjLon - val endLat = endSite.gcjLat - val distance = CoordinateUtils.calculateLineDistance( - endLon, endLat, - currentLocation.longitude, currentLocation.latitude - ).toDouble() - i(SceneConstant.M_TAXI + TAG, "judgeEndStation() distance = $distance") - if (distance <= TaxiUnmannedConst.ARRIVE_AT_START_STATION_DISTANCE) { //1、当前位置和站点围栏15m内 - - //2、开始计算当前位置和站点的向量角度 < 90度 未经过 >90度 经过 - val stationAngle = DrivingDirectionUtils.getDegreeOfCar2Poi( - currentLocation.longitude, - currentLocation.latitude, - endLon, - endLat, currentLocation.heading.toInt() - ).toDouble() - i( - SceneConstant.M_TAXI + TAG, - "judgeEndStation() stationAngle = $stationAngle" - ) - - //3、刚过站且过站距离在15m内, 提交到站 - if (stationAngle > 90 && distance <= TaxiUnmannedConst.ARRIVE_AT_START_STATION_DISTANCE) { - if ((!checkCurrentTask() - || (getCurTaskStatus() == TaskStatusEnum.StartTask.code)) - ) { - i(SceneConstant.M_TAXI + TAG, "task null or TaskStatus = ${getCurTaskStatus()}") - return - } - i(SceneConstant.M_TAXI + TAG, "judgeEndStation() = 刚过站且在15m内") - arriveSite(endSite.siteId, true) - } - } - } - - - /** - * 查询当前任务的轨迹 - */ - fun queryTaskContrail(planningLines: Array?) { - if (planningLines == null) return - CarServiceManager.contrailList(mContext!!, planningLines, - object : OchCommonServiceCallback { - override fun onSuccess(data: ContrailListRespBean?) { - d(SceneConstant.M_TAXI + TAG, "queryTaskContrail: ${GsonUtil.jsonFromObject(data?.data)}") - if (data == null || data.code != 0) return - mCurTaskContrail = data.data?.get(0) - - TaxiTrajectoryManager.getInstance().syncTrajectoryInfo() - } - - override fun onFail(code: Int, msg: String?) { - d(SceneConstant.M_TAXI + TAG, "queryTaskContrail code=$code,msg=$msg") - } - - }) - } - fun setArriveAtUntruthStation() { - if (mUntruthTask == null) { - ToastUtils.showShort("无虚拟站点!") - return - } - arriveSite(mUntruthTask!!.siteId, false) - } - - fun setArriveAtEndStation() { - if (!checkCurrentTask()) { - ToastUtils.showShort("无任务!") - return - } -// arriveSite(mCurrentTaskAndOrder?.endSite!!.siteId, true) - arriveTerminal() - } - - fun toStartTask() { - if (!checkCurrentTask()) { - ToastUtils.showShort("无任务!") - return - } - - //当前订单状态若为20 , 则使用的lineId为订单信息的 - mCurrentTaskAndOrder?.let { startTask( - if (it.order != null && it.order!!.orderStatus >= TaxiOrderStatusEnum.ArriveAtStart.code) - it.order!!.orderLine - else - it.lineId - ) } - } - - /** - * 测试开启自动驾驶 - */ - fun setOnTheWayToEndStation() { - if (!checkCurrentOrder()) { - ToastUtils.showShort("订单状态不匹配该操作!") - } - startAutoPilot() - } - - private val mGoAutopilotStatusListener: IMoGoAutopilotStatusListener = + private val mMogoAutopilotStatusListener: IMoGoAutopilotStatusListener = object : IMoGoAutopilotStatusListener { override fun onAutopilotDockerInfo(dockerVersion: String) {} override fun onAutopilotRouteLineId(lineId: Long) {} @@ -779,48 +222,50 @@ object TaxiModel { override fun onAutopilotStatusResponse(autoPilotStatusInfo: AutopilotStatusInfo) {} override fun onAutopilotStatusResponse(state: Int) { if (state == IMoGoAutopilotStatusListener.STATUS_AUTOPILOT_RUNNING) { - if (mADASStatusCallback != null) { - mADASStatusCallback!!.onAutopilotRunning() - } - if ((mCurrentTaskAndOrder != null && mCurrentTaskAndOrder!!.order != null - && TaxiOrderStatusEnum.OnTheWayToEnd.code == mCurrentTaskAndOrder!!.order!!.orderStatus) - ) { + mADASStatusCallback?.onAutopilotRunning() + if ((QueryCurrentTaskRespBean.isOrderOnTheWayToEnd(mCurrentTaskWithOrder))) { TaxiAnalyticsManager.getInstance().triggerStartAutopilotEvent( isRestartAutopilot, true, - mCurrentTaskAndOrder!!.order!!.orderStartSite!!.siteName, - mCurrentTaskAndOrder!!.order!!.orderEndSite!!.siteName, - mCurrentTaskAndOrder!!.lineId, - mCurrentTaskAndOrder!!.order!!.orderNo + mCurrentTaskWithOrder!!.order!!.orderStartSite!!.siteName, + mCurrentTaskWithOrder!!.order!!.orderEndSite!!.siteName, + mCurrentTaskWithOrder!!.lineId, + mCurrentTaskWithOrder!!.order!!.orderNo ) if (FunctionBuildConfig.isDemoMode) { // 当美化模式(演示模式)开启时: 订单对应自动驾驶开启后,置true FunctionBuildConfig.isIgnoreConditionsDrawAutopilotTrajectoryData = true - setIgnoreConditionDraw(true) - setIPCDemoMode(true) + CallerAutoPilotControlManager.setIgnoreConditionDraw(true) + CallerAutoPilotControlManager.setIPCDemoMode(true) d( - SceneConstant.M_TAXI + TAG, + TAG, "美化模式-ignore:置为true(到达出发点且已开启自动驾驶)" ) } } } else if (state == IMoGoAutopilotStatusListener.STATUS_AUTOPILOT_ENABLE) { if ((FunctionBuildConfig.isDemoMode - && checkCurrentTask() - && ((getCurOrderStatus() === TaxiOrderStatusEnum.OnTheWayToEnd - || getCurOrderStatus() === TaxiOrderStatusEnum.ArriveAtEnd))) + && checkCurrentTaskCondition() + && (QueryCurrentTaskRespBean.isOrderOnTheWayToEnd( + mCurrentTaskWithOrder + ) + || QueryCurrentTaskRespBean.isOrderArriveAtEnd( + mCurrentTaskWithOrder + ))) ) { // 当美化模式(演示模式)开启时:且有订单、且为去往目的地状态,维持自动驾驶icon开启状态 return } - if (mADASStatusCallback != null) { - mADASStatusCallback!!.onAutopilotEnable() - } + mADASStatusCallback?.onAutopilotEnable() } else if (state == IMoGoAutopilotStatusListener.STATUS_AUTOPILOT_DISABLE) { if ((FunctionBuildConfig.isDemoMode - && checkCurrentTask() - && ((getCurOrderStatus() === TaxiOrderStatusEnum.OnTheWayToEnd - || getCurOrderStatus() === TaxiOrderStatusEnum.ArriveAtEnd))) + && checkCurrentTaskCondition() + && (QueryCurrentTaskRespBean.isOrderOnTheWayToEnd( + mCurrentTaskWithOrder + ) + || QueryCurrentTaskRespBean.isOrderArriveAtEnd( + mCurrentTaskWithOrder + ))) ) { // 当美化模式(演示模式)开启时:且有订单、且为去往目的地状态,维持自动驾驶icon开启状态 return @@ -830,47 +275,44 @@ object TaxiModel { } } else if (state == IMoGoAutopilotStatusListener.STATUS_PARALLEL_DRIVING) { if (FunctionBuildConfig.isDemoMode) { - if ((checkCurrentTask() - && (getCurOrderStatus() === TaxiOrderStatusEnum.OnTheWayToEnd - || getCurOrderStatus() === TaxiOrderStatusEnum.ArriveAtEnd)) - ) { //订单中 + if ((checkCurrentTaskCondition() + && (QueryCurrentTaskRespBean.isOrderOnTheWayToEnd( + mCurrentTaskWithOrder + ) + || QueryCurrentTaskRespBean.isOrderArriveAtEnd( + mCurrentTaskWithOrder + ))) + ) { //订单中 // 当美化模式(演示模式)开启时:且有订单、且为去往目的地状态,维持自动驾驶icon开启状态 } else { //美化模式下没订单,显示人工驾驶 - if (mADASStatusCallback != null) { - mADASStatusCallback!!.onAutopilotDisable() - } + mADASStatusCallback?.onAutopilotDisable() } return } - if (mADASStatusCallback != null) { - mADASStatusCallback!!.onParallelDrivingStatus() - } + mADASStatusCallback?.onParallelDrivingStatus() } } override fun onAutopilotSNRequest() {} override fun onAutopilotArriveAtStation(arrivalNotification: ArrivalNotification?) { - i( - SceneConstant.M_TAXI + TAG, - "onAutopilotArriveAtStation = " + arrivalNotification.toString() - ) - if (arrivalNotification == null || !checkCurrentTask() || - mCurrentTaskAndOrder!!.currentStatus == TaskStatusEnum.CompleteTask.code) { + i(TAG, "onAutopilotArriveAtStation = ${arrivalNotification.toString()}") + if (arrivalNotification == null || !checkCurrentTaskCondition() || + mCurrentTaskWithOrder?.currentStatus == TaskStatusEnum.CompleteTask.code + ) { i( - SceneConstant.M_TAXI + TAG, - "onAutopilotArriveAtStation = arrivalNotification or task null" + - "or task currentStatus = ${mCurrentTaskAndOrder!!.currentStatus}" + TAG, "onAutopilotArriveAtStation = arrivalNotification or task null" + + "or task currentStatus = ${mCurrentTaskWithOrder?.currentStatus}" ) return } - arriveTerminal() + autopilotArriveAtStation() if (FunctionBuildConfig.isDemoMode) { // 当美化模式(演示模式)开启时: 到达目的地,置false // 2022.10.08 到达目的地时候取消自动起自驾, 服务完成取消引导线和自动驾驶按钮状态 // FunctionBuildConfig.isIgnoreConditionsDrawAutopilotTrajectoryData = false; // CallerAutoPilotManager.INSTANCE.setIgnoreConditionDraw(false); - setIPCDemoMode(false) - d(SceneConstant.M_TAXI + TAG, "美化模式-ignore:置为false(到达目的地)") + CallerAutoPilotControlManager.setIPCDemoMode(false) + d(TAG, "美化模式-ignore:置为false(到达目的地)") } } @@ -879,119 +321,128 @@ object TaxiModel { override fun onSystemStatus(statusInf: SsmInfo.SsmStatusInf) {} } - private fun arriveTerminal() { - if (!checkCurrentTask()) return - i( - SceneConstant.M_TAXI + TAG, - "onAutopilotArriveAtStation = arriveTerminal() = ${mCurrentTaskAndOrder!!.endSite}" - ) - val endSite = mCurrentTaskAndOrder!!.endSite - if (endSite != null) { - arriveSite(endSite.siteId, true) + private val mMogoStatusChangedListener: IMogoStatusChangedListener = + IMogoStatusChangedListener { descriptor, isTrue -> + // VR mode变更回调 + if (StatusDescriptor.VR_MODE == descriptor) { + mControllerStatusCallback?.onVRModeChanged(isTrue) + } } - } - private val moGoAutopilotPlanningListener: IMoGoPlanningRottingListener = + // 自车定位 + private val mMapLocationListener: IMoGoChassisLocationGCJ02Listener = + object : IMoGoChassisLocationGCJ02Listener { + override fun onChassisLocationGCJ02(mogoLocation: MogoLocation?) { + //位置变化时,通过围栏判断是否到达x点 + if (null == mogoLocation) return + + if (mDriveToNearestStationTask != null) { + judgeUntruthStation(mDriveToNearestStationTask, mogoLocation) + } + + if (checkCurrentTaskCondition() + && mCurrentTaskWithOrder?.currentStatus == TaskStatusEnum.StartTask.code) { +// judgeTaskStartStation(mogoLocation) + judgeTaskEndSiteStation(mogoLocation) + } + + mControllerStatusCallback?.onCarLocationChanged(mogoLocation) + } + } + + private val mMogoAutopilotPlanningListener: IMoGoPlanningRottingListener = object : IMoGoPlanningRottingListener { override fun onAutopilotRotting(globalPathResp: GlobalPathResp?) { - if (null != globalPathResp && globalPathResp.wayPointsList != null) { + globalPathResp?.wayPointsList?.also { d( - SceneConstant.M_TAXI + TAG, ("getWayPointsList = " - + globalPathResp.wayPointsList.size) + TAG, "getWayPointsList.Size = ${globalPathResp.wayPointsList.size}" ) - } - if (null != globalPathResp && globalPathResp.wayPointsList.size > 0) { - updateOrderRouteInfo(globalPathResp.wayPointsList) + if (it.size > 0) { + // 本地计算全路径长度(实时更新剩余距离,剩余时间,预计到达时间) + if (checkCurrentTaskCondition()) { + d(TAG, "--------本地开始计算全路径数据---------- ") + //转换成高德坐标系 + if (mCurrentTaskRoutePointsGcj!!.size > 0) { + mCurrentTaskRoutePointsGcj.clear() + } + mCurrentTaskRoutePointsGcj.addAll( + coordinateConverterWgsToGcjLocations( + mContext, + it + ) + ) + // MAP返回route时关闭高德相关的 + AmapNaviToDestinationModel.getInstance(mContext).destroyAmaNavi() + mOrderStatusCallback?.onNaviToEnd(false, false) + } + } } } } - /** - * 设置路径规划起终点 - * - */ - fun setRouteLineMarker() { - val curTaskAndOrder = getCurTaskAndOrder() - if (curTaskAndOrder != null) { - if (curTaskAndOrder.startSite == null || curTaskAndOrder.endSite == null) { - cleanLineMarker() - return - } - val startStation = LatLng( - curTaskAndOrder.startSite!!.gcjLat, - curTaskAndOrder.startSite!!.gcjLon - ) - val endStation = LatLng( - curTaskAndOrder.endSite!!.gcjLat, - curTaskAndOrder.endSite!!.gcjLon - ) - if (mAutopilotPlanningCallback != null) { - mAutopilotPlanningCallback!!.setLineMarker(startStation, endStation) + private val mAdasStartAutopilotFailureListener: OchAdasStartFailureCallback = + object : OchAdasStartFailureCallback { + override fun onStartAutopilotFailure( + startFailedCode: String, + startFailedMessage: String + ) { + TaxiAnalyticsManager.getInstance() + .triggerStartAutopilotFailureEventByAdas(startFailedCode, startFailedMessage) + if (mADASStatusCallback != null && !FunctionBuildConfig.isDemoMode) { + e( + TAG, + "onStartAutopilotFailure: startFailedMessage=$startFailedMessage" + ) + mADASStatusCallback?.onStartAdasFailure() + } } } - } - private fun cleanLineMarker() { - if (mAutopilotPlanningCallback != null) { - mAutopilotPlanningCallback!!.setLineMarker(null, null) + private val mMogoOnSocketMessageListener = + object : IMogoOnMessageListener { + override fun target(): Class { + return OCHOperationalMessage::class.java + } + + override fun onMsgReceived(obj: OCHOperationalMessage) { + if (obj == null) { + d(TAG, "onMsgReceived = null") + return + } + d(TAG, "onMsgReceived = $obj.message") + OCHSocketMessageManager.pushAppOperationalMsgBox( + obj.pushTimeStamp, + obj.message, OCHSocketMessageManager.OPERATION_SYSTEM + ) + } } - } - /** - * 计算全路径长度,以及实时更新剩余距离,剩余时间,预计时间 - * - * @param models - */ - fun updateOrderRouteInfo(models: List) { - if (models.isEmpty()) return - if (mCurrentTaskAndOrder == null || mCurrentTaskAndOrder!!.startSite == null - || mCurrentTaskAndOrder!!.endSite == null) return - d(SceneConstant.M_TAXI + TAG, "--------计算出sumLength开始---------- ") - - //转换成高德坐标系 - if (mRoutePoints!!.size > 0) { - mRoutePoints.clear() + //监听网络变化,避免启动机器时无网导致无法更新订单信息 + private val mNetWorkIntentListener: IMogoIntentListener = + IMogoIntentListener { intentStr, _ -> + d(TAG, "mNetWorkIntentListener: onIntentReceived=$intentStr") + if ((ConnectivityManager.CONNECTIVITY_ACTION == intentStr)) { + if (NetworkUtils.isConnected(mContext)) { + loginService?.queryLoginStatusByNet() + } + } } - mRoutePoints.addAll(coordinateConverterWgsToGcjLocations(mContext, models)) - startDynamicCalculateRouteInfo() - } - private fun startDynamicCalculateRouteInfo() { - d( - SceneConstant.M_TAXI + TAG, - "--------mCurrentTaskAndOrder---------- $mCurrentTaskAndOrder" - ) - d(SceneConstant.M_TAXI + TAG, "--------mRoutePoints.size---------- " + mRoutePoints!!.size) - AmapNaviToDestinationModel.getInstance(mContext).destroyAmaNavi() - if (mOrderStatusCallback != null) { - mOrderStatusCallback!!.onNaviToEnd(false, false) - } - } - - private fun updateDistance(lastSumLength: Float) { - val lastTime = lastSumLength / TaxiUnmannedConst.TAXI_AVERAGE_SPEED * 3.6 //秒 - d( - SceneConstant.M_TAXI + "dynamicCalculateRouteInfo", - ("---lastSumLength: " + lastSumLength + "----lastTime : " + lastTime - + " thread = " + Thread.currentThread().name) - ) - if (mOrderStatusCallback != null) { - mOrderStatusCallback!!.onCurrentOrderDistToEndChanged( + private val localCalculateDistanceListener: IDistanceListener = object : IDistanceListener { + override fun distanceCallback(lastSumLength: Float) { + val lastTime = lastSumLength / TaxiUnmannedConst.TAXI_AVERAGE_SPEED * 3.6 //秒 + d( + TAG, + "dynamicCalculateRouteInfo: lastSumLength=$lastSumLength, lastTime=$lastTime, threadName=Thread.currentThread().name" + ) + mOrderStatusCallback?.onCurrentOrderDistToEndChanged( lastSumLength.toLong(), lastTime.toLong() ) } } - private val distanceListener: IDistanceListener = object : IDistanceListener { - override fun distanceCallback(distance: Float) { - updateDistance( - distance - ) - } - } - - private val trajectoryListener: ITrajectoryListener = + private val localCalculateTrajectoryListener: ITrajectoryListener = object : ITrajectoryListener { override fun trajectoryCallback( routeArrivied: MutableList, @@ -1028,15 +479,730 @@ object TaxiModel { } } + private fun autopilotArriveAtStation() { + if (!checkCurrentTaskCondition()) return + i( + TAG, + "autopilotArriveAtStation = ${mCurrentTaskWithOrder?.endSite}" + ) + mCurrentTaskWithOrder?.endSite?.also { + submitArriveSite(it.siteId, true) + } + } + + /** + * 到站(起点、终点)上报后端 + * @siteId : 站点id + * @isArriveAtEndSite: true 终点, false 起点 + */ + fun submitArriveSite(siteId: Long, isArriveAtEndSite: Boolean) { + i(TAG, message = "submitArriveSite: siteId=$siteId isArriveAtEndSite=$isArriveAtEndSite") + TaxiTaskWithOrderServiceManager.arriveSite( + mContext, + siteId, + object : OchCommonServiceCallback { + override fun onSuccess(data: BaseData?) { + if (data == null || data.code != 0) return + d(TAG, "submitArriveSite-onSuccess data=" + GsonUtil.jsonFromObject(data)) + mDriveToNearestStationTask = null + if (isArriveAtEndSite) { + updateLocalCalculateStation() + //到站后不再调用取消自驾. 原因是取消自驾,D档位会溜车 + //cancelAutopilot() + } + } + + override fun onFail(code: Int, msg: String?) { + d(TAG, "code=$code msg=$msg") + } + }) + } + + /** + * 检测当前任务的必备条件: + * 1.有当前任务 + * 2.有任务起点 + * 3.有任务终点 + */ + fun checkCurrentTaskCondition(): Boolean { + return mCurrentTaskWithOrder != null && mCurrentTaskWithOrder!!.startSite != null + && mCurrentTaskWithOrder!!.endSite != null + } + + fun startQueryCurrentTaskWithOrderLoop() { + if (mQueryTaskWithOrderDisposable != null + && !mQueryTaskWithOrderDisposable!!.isDisposed + ) { + return + } + i(TAG, "startQueryCurrentTaskWithOrderLoop()") + mQueryTaskWithOrderDisposable = Observable.interval( + TaxiUnmannedConst.LOOP_DELAY, + TaxiUnmannedConst.LOOP_PERIOD_2S, + TimeUnit.MILLISECONDS + ) + .map { aLong: Long -> aLong + 1 } + .subscribeOn(Schedulers.io()) + .observeOn(AndroidSchedulers.mainThread()) + .subscribe { queryCurrentTaskOnce() } + } + + fun stopQueryCurrentTaskWithOrderLoop() { + if (mQueryTaskWithOrderDisposable != null) { + i(TAG, "stopQueryCurrentTaskWithOrderLoop()") + mQueryTaskWithOrderDisposable?.dispose() + mQueryTaskWithOrderDisposable = null + } + } + + /** + * 查询当前车辆的任务和对应绑定的订单 + */ + private fun queryCurrentTaskOnce() { + if (!LoginStatusManager.isLogin()) { + d(TAG, "queryCurrentTaskOnce: 当前未登陆,跳过本次查询") + return + } + + TaxiTaskWithOrderServiceManager.queryCurrentTask( + AbsMogoApplication.getApp().applicationContext, + object : OchCommonServiceCallback { + override fun onSuccess(data: QueryCurrentTaskRespBean?) { + if (data?.data == null) { + d( + TAG, + "queryCurrentTaskOnce onSuccess: data.code != 0 || data === null || data.data === null" + ) + return + } + val result: QueryCurrentTaskRespBean.Result = data.data!! + d( + TAG, + "queryCurrentTaskOnce onSuccess:result=${GsonUtil.jsonFromObject(result)}" + ) + d( + TAG, + "queryCurrentTaskOnce onSuccess:mCurrentTaskWithOrder=${ + GsonUtil.jsonFromObject(mCurrentTaskWithOrder) + }" + ) + + //本地根据订单 orderNo 去查询下(乘客取消订单) + if (mCurrentTaskWithOrder != null + && mCurrentTaskWithOrder?.order != null + && result != null && result.order == null + ) { + d( + TAG, + "queryCurrentTaskOnce: result order is empty, query order by orderNo!" + ) + queryOrderByOrderNo(mCurrentTaskWithOrder!!.order!!.orderNo) + return + } + + //订单或者伪任务更新, 都去刷新下界面 + if (mCurrentTaskWithOrder == null + || mCurrentTaskWithOrder!! != result + ) { + d(TAG, "queryCurrentTaskOnce: 更新本地数据") + mCurrentTaskWithOrder = result + + if (result.endSite == null && result.order == null) { + mCurrentTaskWithOrder = null + } + + //当前任务完成且订单状态到达乘客上车点, 则立马去拉取任务 不再等30s,否则送驾任务要等30s后才能去执行 + if (result?.currentStatus == TaskStatusEnum.CompleteTask.code) { + mTaxiTaskCallback?.onTaskCompleted( + QueryCurrentTaskRespBean.isOrderArriveAtStart( + result + ), + result.endSite!!.siteId + ) + } + + updateLocalCalculateStation() + + //达到终点后查询全程里程和用时 + if (QueryCurrentTaskRespBean.isOrderArriveAtEnd(result)) { + d(TAG, "queryCurrentTaskOnce ArriveAtEnd") + mTaxiTaskCallback?.onOrderArriveAtEnd(result.order!!.orderNo) + } + + //根据lineId集合去查轨迹集合, 返回的只是接驾任务的line集合, 没有送驾任务 + var linesIds = arrayListOf() + linesIds.add(result.lineId) // 当前任务的 + result.order?.also { + linesIds.addAll(it.planningLines) // 接驾 + linesIds.add(it.orderLine) //送驾 + } + queryTaskTrajectoryByLineIds(linesIds.toTypedArray(), result.lineId) + + //自动去启动自驾 + if (result.currentStatus == TaskStatusEnum.GetTask.code && + result.taskType <= TaskTypeEnum.ToOrderStartTask.code + ) { + if (result.order == null || result.order!!.orderStatus < TaxiOrderStatusEnum.ArriveAtStart.code) { + d(TAG, "queryCurrentTaskOnce autoStartDriving") + autoStartDriving() + } + } + + mTaxiTaskCallback?.onTaskWithOrderDataChanged(mCurrentTaskWithOrder) + } + } + + override fun onFail(code: Int, msg: String?) { + d(TAG, "queryCurrentTaskOnce onFail: code=$code, msg=$msg") + } + }) + } + + fun updateLocalCalculateStation() { + if (mCurrentTaskWithOrder == null) return + if (mCurrentTaskWithOrder!!.startSite != null && mCurrentTaskWithOrder!!.endSite != null + && mCurrentTaskWithOrder!!.currentStatus <= TaskStatusEnum.StartTask.code + ) { + val curTaskAndOrder = getCurTaskAndOrder() ?: return + if (curTaskAndOrder.startSite != null && curTaskAndOrder.endSite != null) { + val startStation = MogoLocation() + startStation.longitude = curTaskAndOrder.startSite!!.gcjLon + startStation.latitude = curTaskAndOrder.startSite!!.gcjLat + val endStation = MogoLocation() + endStation.longitude = curTaskAndOrder.endSite!!.gcjLon + endStation.latitude = curTaskAndOrder.endSite!!.gcjLat + setStationPoint(startStation, endStation, curTaskAndOrder.lineId) + } + } else { + setStationPoint(null, null, -1L) + } + } + + fun queryOrderByOrderNo(orderNo: String) { + TaxiTaskWithOrderServiceManager.queryCarOrderByOrderNo(mContext, orderNo, + object : OchCommonServiceCallback { + override fun onSuccess(data: QueryCarOrderByNoRespBean?) { + d(TAG, "queryOrderByOrderNo onSuccess: data=${GsonUtil.jsonFromObject(data)}") + if (data == null) return + when (data.data.orderStatus) { + TaxiOrderStatusEnum.Cancel.code -> { + mTaxiTaskCallback?.onOrderCancel() + //更新本地标志位 + mCurrentTaskWithOrder?.order = null + } + + TaxiOrderStatusEnum.ArriveAtEnd.code -> { + mTaxiTaskCallback?.onOrderTotalMileAndDurationChanged( + data.data.mileage, + data.data.duration.toInt() + ) + } + + TaxiOrderStatusEnum.JourneyCompleted.code -> { + mTaxiTaskCallback?.onOrderJourneyCompleted() + //更新本地标志位 + mCurrentTaskWithOrder?.order = null + } + } + } + + override fun onFail(code: Int, msg: String?) { + d( + TAG, + "queryOrderByOrderNo: code=$code,msg=$msg" + ) + } + }) + } + + fun prepareNextTask(siteId: Long) { + TaxiTaskWithOrderServiceManager.prepareTask( + mContext, + siteId, + object : OchCommonServiceCallback { + override fun onSuccess(data: PrepareTaskRespBean?) { + d( + TAG, + "prepareNextTask onSuccess:${GsonUtil.jsonFromObject(data)}, " + + "isCarServingStatus = ${TaxiCarServingStatusManager.isCarServingStatus()}" + ) + if (data?.data == null) return + //去下载轨迹, 下发给工控机下载 +// queryTaskTrajectoryByLineIds( +// Array(1) { data.data!!.lineId }, +// data.data!!.lineId +// ) + } + + override fun onFail(code: Int, msg: String?) { + d(TAG, "prepareNextTask onFail: code=$code ,msg=$msg") + if (LoginStatusManager.isLogin() && TaxiCarServingStatusManager.isCarServingStatus()) { + startPrepareTask120S(siteId) + } + } + }) + } + + fun startPrepareTask120S(siteId: Long) { + UiThreadHandler.postDelayed({ + prepareNextTask(siteId) + }, TaxiUnmannedConst.TIMER_PREPARE_TASK_INTERVAL_120S) + } + + /** + * 查询当前任务的轨迹 + */ + fun queryTaskTrajectoryByLineIds(planningLineIds: Array, currentTaskLineId: Long) { + TaxiTaskWithOrderServiceManager.queryTrajectoryByLindIds( + mContext, + planningLineIds, + object : OchCommonServiceCallback { + override fun onSuccess(data: TrajectoryListRespBean?) { + d( + TAG, + "queryTaskTrajectoryByLineIds onSuccess: ${GsonUtil.jsonFromObject(data?.data)}" + ) + data?.data?.also { + mTaskTrajectoryList.addAll(it) + mCurrentTaskTrajectory = it.first { currentTaskLineId == it.lineId } + } + mTaxiTaskCallback?.onTaskTrajectoryDataChanged(data) + } + + override fun onFail(code: Int, msg: String?) { + d(TAG, "queryTaskTrajectoryByLineIds onFail: code=$code, msg=$msg") + } + }) + } + + // 获取当前订单状态 + fun getCurOrderStatus(): TaxiOrderStatusEnum? { + if (mCurrentTaskWithOrder == null) TaxiOrderStatusEnum.None + val order: OrderDetail = mCurrentTaskWithOrder!!.order!! + return valueOf(order.orderStatus) + } + + private fun getCurTaskStatus(): Int? { + if (mCurrentTaskWithOrder == null) TaskStatusEnum.None + return mCurrentTaskWithOrder?.currentStatus + } + + fun getCurTaskAndOrder(): QueryCurrentTaskRespBean.Result? { + return mCurrentTaskWithOrder + } + + fun getCurUntruthTask(): StartServiceRespBean.Result? { + return mDriveToNearestStationTask + } + + fun getCurrentOrderTrajectoryList(): MutableList? { + return mTaskTrajectoryList + } + + fun getCurrentTaskTrajectory(): TrajectoryListRespBean.Result? { + return mCurrentTaskTrajectory + } + + //更新本地currentOrder信息,并保存订单到本地避免车机重启丢失数据 + private fun updateNativeCurrentOrder(data: QueryCurrentTaskRespBean.Result?) { + if (data == null) { + return + } + mCurrentTaskWithOrder = data + + SharedPrefsMgr.getInstance(mContext!!).putString( + TaxiUnmannedConst.SP_KEY_OCH_TAXI_ORDER, + GsonUtil.jsonFromObject(data) + ) + + val currentOrder = mCurrentTaskWithOrder!!.order + + if (currentOrder != null) { + if (currentOrder!!.orderStatus == TaxiOrderStatusEnum.OnTheWayToEnd.code) { + if (FunctionBuildConfig.isDemoMode) { + // 当美化模式(演示模式)开启时: 订单对应自动驾驶开启后,置true + FunctionBuildConfig.isIgnoreConditionsDrawAutopilotTrajectoryData = true + CallerAutoPilotControlManager.setIgnoreConditionDraw(true) + CallerAutoPilotControlManager.setIPCDemoMode(true) + d(TAG, "美化模式-ignore:置为true(更新本地order信息)") + } + updateAutopilotControlParameters() + } + if (currentOrder!!.orderStatus == TaxiOrderStatusEnum.ArriveAtEnd.code) { + if (FunctionBuildConfig.isDemoMode) { + d(TAG, "setIPCDemoMode:false") + CallerAutoPilotControlManager.setIPCDemoMode(false) + } + clearAutopilotControlParameters() + } + } else { + if (FunctionBuildConfig.isDemoMode) { + d(TAG, "setIPCDemoMode:false") + CallerAutoPilotControlManager.setIPCDemoMode(false) + } + clearAutopilotControlParameters() + } + } + + /** + * 将业务订单信息保存,鹰眼可取用 + */ + private fun updateAutopilotControlParameters() { + val parameters = initAutopilotControlParameters() + if (null == parameters) { + e(TAG, "AutopilotControlParameters is empty.") + return + } + d(TAG, "AutopilotControlParameters is update.") + updateAutopilotControlParameters(parameters) + } + + private fun clearAutopilotControlParameters() { + d(TAG, "AutopilotControlParameters is clear.") + updateAutopilotControlParameters(null) + } + + fun updateUntruthTask(untruthTask: StartServiceRespBean.Result?) { + mDriveToNearestStationTask = untruthTask + } + + //清除任务订单信息 + fun clearCurrentOCHOrder() { + mCurrentTaskWithOrder = null + clearAutopilotControlParameters() + TaxiTrajectoryManager.getInstance().syncTrajectoryInfo() + SharedPrefsMgr.getInstance(mContext!!).remove(TaxiUnmannedConst.SP_KEY_OCH_TAXI_ORDER) + isRestartAutopilot = false + if (FunctionBuildConfig.isDemoMode) { + // 当美化模式(演示模式)开启时: 取消或订单已完成时,置false + FunctionBuildConfig.isIgnoreConditionsDrawAutopilotTrajectoryData = false + CallerAutoPilotControlManager.setIgnoreConditionDraw(false) + CallerAutoPilotControlManager.setIPCDemoMode(false) + d(TAG, "美化模式-ignore:置为false(已完成or清除当前订单)") + } + } + + private fun checkCurrentOrder(): Boolean { + return mCurrentTaskWithOrder != null && mCurrentTaskWithOrder!!.order != null + } + + /** + * 以当前订单为基础,开启自动驾驶 + */ + @ChainLog( + linkChainLog = ChainConstant.CHAIN_TYPE_SOCKET_AUTOPILOT, + linkCode = ChainConstant.CHAIN_SOURCE_ADAS, + nodeAliasCode = ChainConstant.CHAIN_CODE_OCH_TAXI_START_AUTOPILOT, + paramIndexes = [-1] + ) + fun startAutoPilot() { + if (!checkCurrentTaskCondition()) { + e(TAG, "no order or order is empty.") + ToastUtils.showShort("当前订单不存在或异常!") + return + } + + if (mCurrentTaskTrajectory == null) { + e(TAG, "no order or order is empty.") + ToastUtils.showShort("轨迹信息不存在!") + } + + //根据开关和后台是否发布轨迹启动自驾 + if (FunctionBuildConfig.isPassStartAutopilotCommand && mCurrentTaskTrajectory != null && TextUtils.isEmpty( + mCurrentTaskTrajectory!!.csvFileUrl + ) + && TextUtils.isEmpty(mCurrentTaskTrajectory!!.csvFileUrlDPQP) + ) { + ToastUtils.showLong("无发布轨迹, 请发布后重试") + e( + TAG, "isPassStartAutopilotCommand = " + + FunctionBuildConfig.isPassStartAutopilotCommand + + "busRoutesResult.csvFileUrl = " + mCurrentTaskTrajectory!!.csvFileUrl + + "busRoutesResult.csvFileUrlDPQP = " + mCurrentTaskTrajectory!!.csvFileUrlDPQP + ) + return + } + e( + TAG, "isPassStartAutopilotCommand = " + + FunctionBuildConfig.isPassStartAutopilotCommand + ) + if (!FunctionBuildConfig.isDemoMode && !OCHAdasAbilityManager.getInstance().autopilotAbilityStatus) { + ToastUtils.showLong( + OCHAdasAbilityManager.getInstance().autopilotUnAbilityReason + + ", 请稍候重试" + ) + TaxiAnalyticsManager.getInstance().triggerUnableStartAPReasonEvent( + mCurrentTaskWithOrder!!.startSite!!.siteName, + mCurrentTaskWithOrder!!.endSite!!.siteName, + mCurrentTaskWithOrder!!.lineId.toString(), // todo 这里原来传的是订单号, 现在是任务没有订单号,传了路线id + OCHAdasAbilityManager.getInstance().autopilotUnAbilityReason + ) + return + } + + //点击开始自动驾驶按钮订单状态去流转, 不再与自动驾驶是否启动成功挂钩 + isRestartAutopilot = mCurrentTaskWithOrder!!.currentStatus != TaskStatusEnum.StartTask.code + + val parameters = initAutopilotControlParameters() + if (null == parameters) { + e(TAG, "AutopilotControlParameters is empty.") + return + } + CallerAutoPilotControlManager.startAutoPilot(parameters) + d( + TAG, "start autopilot with parameter: %s", + GsonUtil.jsonFromObject(parameters) + + " ,startSiteName=" + mCurrentTaskWithOrder?.startSite?.siteName + + " ,endSiteName=" + mCurrentTaskWithOrder?.endSite?.siteName + + "isRestartAutopilot = " + isRestartAutopilot + ) + TaxiAnalyticsManager.getInstance().triggerStartAutopilotEvent( + isRestartAutopilot, + false, + mCurrentTaskWithOrder!!.startSite!!.siteName, + mCurrentTaskWithOrder!!.endSite!!.siteName, + mCurrentTaskWithOrder!!.lineId, + if (mCurrentTaskWithOrder!!.order != null) mCurrentTaskWithOrder!!.order!!.orderNo else "" + ) + if (mControllerStatusCallback != null) { + mControllerStatusCallback!!.startOpenAutopilot() + } + } + + private fun initAutopilotControlParameters(): AutopilotControlParameters? { + if (!checkCurrentTaskCondition()) { + e(TAG, "no order or order is empty.") + return null + } + + if (mCurrentTaskTrajectory == null) { + e(TAG, "curTaskContrail is empty.") + return null + } + + val parameters = AutopilotControlParameters() + + val startWgsLon = mCurrentTaskWithOrder!!.startSite!!.wgs84Lon + val startWgsLat = mCurrentTaskWithOrder!!.startSite!!.wgs84Lat + val endWgsLon = mCurrentTaskWithOrder!!.endSite!!.wgs84Lon + val endWgsLat = mCurrentTaskWithOrder!!.endSite!!.wgs84Lat + parameters.vehicleType = BUSINESSTYPE + parameters.startName = mCurrentTaskWithOrder!!.startSite!!.siteName // 8.10 拼音首字母大写 改为直接传中文 + parameters.endName = mCurrentTaskWithOrder!!.endSite!!.siteName // 8.10 拼音首字母大写 改为直接传中文 + parameters.startLatLon = + AutopilotControlParameters.AutoPilotLonLat(startWgsLat, startWgsLon) + parameters.endLatLon = AutopilotControlParameters.AutoPilotLonLat(endWgsLat, endWgsLon) + if (parameters.autoPilotLine == null) { + parameters.autoPilotLine = AutopilotControlParameters.AutoPilotLine( + mCurrentTaskTrajectory!!.lineId, + mCurrentTaskTrajectory!!.lineName, + mCurrentTaskTrajectory!!.csvFileUrl, + mCurrentTaskTrajectory!!.csvFileMd5, + mCurrentTaskTrajectory!!.txtFileUrl, + mCurrentTaskTrajectory!!.txtFileMd5, + mCurrentTaskTrajectory!!.contrailSaveTime, + "", // todo 这里原来传的是carModel, 现在没有这个信息 + mCurrentTaskTrajectory!!.csvFileUrlDPQP, + mCurrentTaskTrajectory!!.csvFileMd5DPQP, + mCurrentTaskTrajectory!!.txtFileUrlDPQP, + mCurrentTaskTrajectory!!.txtFileMd5DPQP, + mCurrentTaskTrajectory!!.contrailSaveTimeDPQP + ) + } + return parameters + } + + //结束自动驾驶 + fun cancelAutopilot() { + try { + CallerAutoPilotControlManager.cancelAutoPilot() + d(TAG, "结束自动驾驶") + } catch (e: Exception) { + e.printStackTrace() + } + } + + //根据围栏判断,是否到达起点 + private fun judgeTaskStartStation(location: MogoLocation) { + if (checkCurrentTaskCondition()) { + val startSite = mCurrentTaskWithOrder!!.startSite ?: return + val startLon = startSite.gcjLon + val startLat = startSite.gcjLat + val distance = CoordinateUtils.calculateLineDistance( + startLon, startLat, + location.longitude, location.latitude + ).toDouble() + i(TAG, "judgeTaskStartStation() distance = $distance") + if (distance <= TaxiUnmannedConst.ARRIVE_AT_START_STATION_DISTANCE) { + submitArriveSite(startSite.siteId, false) + } + } + } + + + private fun judgeUntruthStation( + virtualTask: StartServiceRespBean.Result?, + currentLocation: MogoLocation + ) { + if (mDriveToNearestStationTask == null || virtualTask == null) return + val distance = CoordinateUtils.calculateLineDistance( + virtualTask.gcjLon, virtualTask.gcjLat, + currentLocation.longitude, currentLocation.latitude + ).toDouble() + i( + TAG, + "judgeEndStation() ${virtualTask.siteName} distance = $distance" + ) + if (distance <= TaxiUnmannedConst.ARRIVE_AT_START_STATION_DISTANCE) { // 15米内到站 + submitArriveSite(virtualTask.siteId, true) + } + } + + private fun startTask(lineId: Long) { + TaxiTaskWithOrderServiceManager.startTask( + mContext, + lineId, + object : OchCommonServiceCallback { + override fun onSuccess(data: BaseData?) { + d(TAG, GsonUtil.jsonFromObject(data)) + } + + override fun onFail(code: Int, msg: String?) { + d(TAG, "$code $msg") + } + + }) + } + + private fun judgeTaskEndSiteStation(currentLocation: MogoLocation) { + if (!checkCurrentTaskCondition()) { + return + } + val endSite = mCurrentTaskWithOrder!!.endSite ?: return + + val endLon = endSite.gcjLon + val endLat = endSite.gcjLat + val distance = CoordinateUtils.calculateLineDistance( + endLon, endLat, + currentLocation.longitude, currentLocation.latitude + ).toDouble() + i(TAG, "judgeEndStation() distance = $distance") + if (distance <= TaxiUnmannedConst.ARRIVE_AT_START_STATION_DISTANCE) { //1、当前位置和站点围栏15m内 + + //2、开始计算当前位置和站点的向量角度 < 90度 未经过 >90度 经过 + val stationAngle = DrivingDirectionUtils.getDegreeOfCar2Poi( + currentLocation.longitude, + currentLocation.latitude, + endLon, + endLat, currentLocation.heading.toInt() + ).toDouble() + i( + TAG, + "judgeEndStation() stationAngle = $stationAngle" + ) + + //3、刚过站且过站距离在15m内, 提交到站 + if (stationAngle > 90 && distance <= TaxiUnmannedConst.ARRIVE_AT_START_STATION_DISTANCE) { + if ((!checkCurrentTaskCondition() + || (getCurTaskStatus() == TaskStatusEnum.StartTask.code)) + ) { + i(TAG, "task null or TaskStatus = ${getCurTaskStatus()}") + return + } + i(TAG, "judgeEndStation() = 刚过站且在15m内") + submitArriveSite(endSite.siteId, true) + } + } + } + + + fun setArriveAtUntruthStation() { + if (mDriveToNearestStationTask == null) { + ToastUtils.showShort("无虚拟站点!") + return + } + submitArriveSite(mDriveToNearestStationTask!!.siteId, false) + } + + fun setArriveAtEndStation() { + if (!checkCurrentTaskCondition()) { + ToastUtils.showShort("无任务!") + return + } +// arriveSite(mCurrentTaskAndOrder?.endSite!!.siteId, true) + autopilotArriveAtStation() + } + + fun toStartTask() { + if (!checkCurrentTaskCondition()) { + ToastUtils.showShort("无任务!") + return + } + + //当前订单状态若为20 , 则使用的lineId为订单信息的 + mCurrentTaskWithOrder?.let { + startTask( + if (it.order != null && it.order!!.orderStatus >= TaxiOrderStatusEnum.ArriveAtStart.code) + it.order!!.orderLine + else + it.lineId + ) + } + } + + /** + * 测试开启自动驾驶 + */ + fun setOnTheWayToEndStation() { + if (!checkCurrentOrder()) { + ToastUtils.showShort("订单状态不匹配该操作!") + } + startAutoPilot() + } + + + /** + * 设置路径规划起终点 + */ + fun setRouteLineMarker() { + val curTaskAndOrder = getCurTaskAndOrder() + if (curTaskAndOrder != null) { + if (curTaskAndOrder.startSite == null || curTaskAndOrder.endSite == null) { + cleanLineMarker() + return + } + val startStation = LatLng( + curTaskAndOrder.startSite!!.gcjLat, + curTaskAndOrder.startSite!!.gcjLon + ) + val endStation = LatLng( + curTaskAndOrder.endSite!!.gcjLat, + curTaskAndOrder.endSite!!.gcjLon + ) + if (mAutopilotPlanningCallback != null) { + mAutopilotPlanningCallback!!.setLineMarker(startStation, endStation) + } + } + } + + private fun cleanLineMarker() { + if (mAutopilotPlanningCallback != null) { + mAutopilotPlanningCallback!!.setLineMarker(null, null) + } + } + // 登出 fun logout() { - loginService!!.loginOut(getChassisLocationGCJ02().latitude, getChassisLocationGCJ02().longitude) + loginService!!.loginOut( + getChassisLocationGCJ02().latitude, + getChassisLocationGCJ02().longitude + ) } //导航去订单终点目的地 fun startNaviToEndStation(isShow: Boolean) { - if (mRoutePoints == null) return - if (mRoutePoints.size > 0) { //使用自驾轨迹 + if (mCurrentTaskRoutePointsGcj == null) return + if (mCurrentTaskRoutePointsGcj.size > 0) { //使用自驾轨迹 if (mOrderStatusCallback != null) { mOrderStatusCallback!!.onNaviToEnd(false, isShow) } @@ -1045,45 +1211,15 @@ object TaxiModel { mOrderStatusCallback!!.onNaviToEnd(true, true) } else { UiThreadHandler.postDelayed({ - if (mRoutePoints.size == 0 && mOrderStatusCallback != null) { + if (mCurrentTaskRoutePointsGcj.size == 0 && mOrderStatusCallback != null) { mOrderStatusCallback!!.onNaviToEnd(true, false) } }, 2000L) } } } - fun updateStation() { - if (mCurrentTaskAndOrder == null) return - if (mCurrentTaskAndOrder!!.startSite != null && mCurrentTaskAndOrder!!.endSite != null - && mCurrentTaskAndOrder!!.currentStatus <= TaskStatusEnum.StartTask.code){ - setStation() - }else{ - cleanStation() - } - } - private fun setStation() { - val curTaskAndOrder = getCurTaskAndOrder() ?: return - if (curTaskAndOrder.startSite != null && curTaskAndOrder.endSite != null) { - val startStation = MogoLocation() - startStation.longitude = curTaskAndOrder.startSite!!.gcjLon - startStation.latitude = curTaskAndOrder.startSite!!.gcjLat - val endStation = MogoLocation() - endStation.longitude = curTaskAndOrder.endSite!!.gcjLon - endStation.latitude = curTaskAndOrder.endSite!!.gcjLat - setStationPoint(startStation, endStation, curTaskAndOrder.lineId) - } - } - - private fun cleanStation() { - setStationPoint(null, null, -1L) - } - - fun updateOrderContrails(contrails: MutableList?) { - mOrderContrails = contrails - } - - fun autoStartDriving(){ + fun autoStartDriving() { //启动动画+文字 if (mControllerStatusCallback != null) { mControllerStatusCallback!!.startOpenAutopilotNonManual() @@ -1093,6 +1229,6 @@ object TaxiModel { toStartTask() //状态流转 startAutoPilot() //自驾开启 VoiceNotice.showNotice("车辆正在自动开启自动驾驶") - },COUNTDOWN_INTERVAL) // 10s后开启自驾, 状态流转 + }, START_AUTOPILOT_COUNTDOWN_INTERVAL) // 10s后开启自驾, 状态流转 } } \ No newline at end of file diff --git a/OCH/taxi/unmanned-driver/src/main/java/com/mogo/och/taxi/utils/TaxiTrajectoryManager.java b/OCH/taxi/unmanned-driver/src/main/java/com/mogo/och/taxi/utils/TaxiTrajectoryManager.java index 34d7c687d8..5d7e67e1d4 100644 --- a/OCH/taxi/unmanned-driver/src/main/java/com/mogo/och/taxi/utils/TaxiTrajectoryManager.java +++ b/OCH/taxi/unmanned-driver/src/main/java/com/mogo/och/taxi/utils/TaxiTrajectoryManager.java @@ -6,14 +6,15 @@ import com.mogo.eagle.core.data.autopilot.AutopilotControlParameters; import com.mogo.eagle.core.function.call.autopilot.CallerAutoPilotControlManager; import com.mogo.eagle.core.utilcode.mogo.logger.CallerLogger; import com.mogo.eagle.core.utilcode.util.GsonUtils; -import com.mogo.och.taxi.bean.ContrailListRespBean; +import com.mogo.och.taxi.bean.TrajectoryListRespBean; import com.mogo.och.taxi.bean.OrderDetail; import com.mogo.och.taxi.bean.QueryCurrentTaskRespBean; -import com.mogo.och.taxi.bean.Site; import com.mogo.och.taxi.constant.TaskStatusEnum; import com.mogo.och.taxi.constant.TaxiUnmannedConst; -import com.mogo.och.taxi.model.TaxiModel; +import com.mogo.och.taxi.ui.task.TaxiTaskModel; +import java.util.ArrayList; +import java.util.Arrays; import java.util.List; import java.util.concurrent.TimeUnit; @@ -67,7 +68,7 @@ public class TaxiTrajectoryManager { * 同步订单信息 */ public void syncTrajectoryInfo() { - QueryCurrentTaskRespBean.Result taskAndOrder = TaxiModel.INSTANCE.getCurTaskAndOrder(); + QueryCurrentTaskRespBean.Result taskAndOrder = TaxiTaskModel.INSTANCE.getCurTaskAndOrder(); if (taskAndOrder == null || taskAndOrder.getCurrentStatus() >= TaskStatusEnum.StartTask.getCode()) { CallerLogger.d(M_TAXI + TAG, "syncTrajectoryInfo() stop."); stopTrajReqLoop(); @@ -116,7 +117,7 @@ public class TaxiTrajectoryManager { } private void setupAutoPilotLine() { - QueryCurrentTaskRespBean.Result taskAndOrder = TaxiModel.INSTANCE.getCurTaskAndOrder(); + QueryCurrentTaskRespBean.Result taskAndOrder = TaxiTaskModel.INSTANCE.getCurTaskAndOrder(); if (taskAndOrder == null || taskAndOrder.getEndSite() == null) { CallerLogger.e(M_TAXI + TAG, @@ -129,7 +130,7 @@ public class TaxiTrajectoryManager { * 4、若不存在,说明当前的执行的任务是与订单无关的演练任务,通知下载加载当前任务的轨迹以及预加载订单轨迹集合的第一个 */ - final ContrailListRespBean.Result curTaskContrail = TaxiModel.INSTANCE.getCurTaskContrail(); + final TrajectoryListRespBean.Result curTaskContrail = TaxiTaskModel.INSTANCE.getCurrentTaskTrajectory(); if (curTaskContrail == null) return; long curLineId = taskAndOrder.getLineId(); @@ -157,29 +158,28 @@ public class TaxiTrajectoryManager { } final OrderDetail orderDetail = taskAndOrder.getOrder(); - ContrailListRespBean.Result preloadContrail = null; //预加载的轨迹 - int preLoadIndex = -1; - - //包含接驾任务和送驾任务的轨迹, 且集合是有顺序的 , 最后一个是送驾任务轨迹 - final List orderContrails = TaxiModel.INSTANCE.getCurOrderContrails(); + TrajectoryListRespBean.Result preloadContrail = null; //预加载的轨迹 + final List orderContrails = TaxiTaskModel.INSTANCE.getCurrentOrderTrajectoryList(); if (orderDetail != null && orderContrails != null && orderContrails.size() != 0 ){ - for (int i = 0; i< orderContrails.size() ; i++){ - if (orderContrails.get(i).getLineId() == curLineId){ //预加载轨迹是curLineId索引的下一个 - int index = i + 1; - if (orderContrails.size() == index){ - //说明找到的是集合最后一个, 最后一个为送驾轨迹,即送驾轨迹和当前的任务轨迹是一样的,不再预加载 - preLoadIndex = index; - break; - }else if (orderContrails.size()-1 >= index){ - preloadContrail = orderContrails.get(index); - preLoadIndex = index; - break; + + List lineIds = new ArrayList<>(); + lineIds.addAll(Arrays.asList(orderDetail.getPlanningLines())); // 接驾 + lineIds.add(orderDetail.getOrderLine());//送驾 + + if (lineIds.contains(curLineId)){ //当前任务在lineIds集合里 + //计算预加载的下一个轨迹 + int preLoadIndex = lineIds.indexOf(curLineId) + 1; + if (lineIds.size() -1 >= preLoadIndex){ + long preLoadLineId = lineIds.get(preLoadIndex); + for (int i = 0; i< orderContrails.size() ; i++){ + if (orderContrails.get(i).getLineId() == preLoadLineId){ + preloadContrail = orderContrails.get(i); + break; + } } } - } - - if (preLoadIndex == -1){ //说明当前任务轨迹在接驾/送驾轨迹集合里没有, 直接加载轨迹集合第一个 + }else {//说明当前任务轨迹在接驾/送驾轨迹集合里没有, 直接加载轨迹集合第一个 preloadContrail = orderContrails.get(0); } }