diff --git a/core/function-impl/mogo-core-function-datacenter/src/main/java/com/mogo/eagle/core/function/datacenter/autopilot/MoGoAutopilotControlProvider.kt b/core/function-impl/mogo-core-function-datacenter/src/main/java/com/mogo/eagle/core/function/datacenter/autopilot/MoGoAutopilotControlProvider.kt index 6186e5f1cf..e77a084027 100644 --- a/core/function-impl/mogo-core-function-datacenter/src/main/java/com/mogo/eagle/core/function/datacenter/autopilot/MoGoAutopilotControlProvider.kt +++ b/core/function-impl/mogo-core-function-datacenter/src/main/java/com/mogo/eagle/core/function/datacenter/autopilot/MoGoAutopilotControlProvider.kt @@ -83,6 +83,7 @@ import com.zhjt.service.chain.ChainLog import io.netty.channel.Channel import mogo.telematics.pad.MessagePad import mogo.yycp.paralleldriving.protocol.ParallelDrivingRequest +import system_master.SsmInfo import java.util.* import java.util.concurrent.TimeUnit @@ -1508,4 +1509,36 @@ class MoGoAutopilotControlProvider : return AdasManager.getInstance().sendSimulationWireFailure(isTrigger)>-1 } + /** + * SSM发送OTA升级提示请求响应 + * @param token 域控发送OTA升级请求中的Token {@link SsmInfo.OtaDownloadRequest#getOtaToken()} + * @param ifUpgrade {@link SsmInfo.IfUpgrade#IMMEDIATELY}:立即 + * {@link SsmInfo.IfUpgrade#DELAY}:推迟 + */ + override fun sendSsmFuncOtaDownloadResponse( + token: String, + ifUpgrade: SsmInfo.IfUpgrade + ): Boolean { + return AdasManager.getInstance().sendSsmFuncOtaDownloadResponse(token, ifUpgrade)>-1 + } + + /** + * 查询OTA状态 + * @param token 域控发送OTA升级请求中的Token {@link SsmInfo.OtaDownloadRequest#getOtaToken()} + * 如果没有可以传null或"" + */ + override fun sendSsmFuncOtaStatusQuery(token: String): Boolean { + return AdasManager.getInstance().sendSsmFuncOtaStatusQuery(token)>-1 + } + + /** + * 人工接管时获取前方和后方摄像头数据 + * 一次请求域控回调次两次摄像头数据 根据{@link MessagePad.CaptureImgOnTakeOver#getUuid()}进行区分是否是哪次请求 + * 例如下发uuid = 1 域控正常会回调两次响应接口 两次的uuid都是1,通过isFront区分是前方还是后方摄像头 + * 域控响应接口{@link OnAdasListener#onCaptureImgOnTakeOver(MessagePad.Header, boolean, MessagePad.CaptureImgOnTakeOver)} + */ + override fun sendCaptureImgReqOnTakeOver(uuid: Long): Boolean { + return AdasManager.getInstance().sendCaptureImgReqOnTakeOver(uuid)>-1 + } + } \ No newline at end of file diff --git a/core/function-impl/mogo-core-function-datacenter/src/main/java/com/mogo/eagle/core/function/datacenter/autopilot/adapter/MoGoAdasListenerImpl.kt b/core/function-impl/mogo-core-function-datacenter/src/main/java/com/mogo/eagle/core/function/datacenter/autopilot/adapter/MoGoAdasListenerImpl.kt index 426052a342..35f34a1d8f 100644 --- a/core/function-impl/mogo-core-function-datacenter/src/main/java/com/mogo/eagle/core/function/datacenter/autopilot/adapter/MoGoAdasListenerImpl.kt +++ b/core/function-impl/mogo-core-function-datacenter/src/main/java/com/mogo/eagle/core/function/datacenter/autopilot/adapter/MoGoAdasListenerImpl.kt @@ -83,6 +83,8 @@ import com.mogo.eagle.core.function.call.autopilot.CallerSweeperFutianCloudTaskL import com.mogo.eagle.core.function.call.autopilot.CallerTakeoverListenerManager import com.mogo.eagle.core.function.call.autopilot.CallerV2XListenerManager import com.mogo.eagle.core.function.call.autopilot.CallerV2nNioEventListenerManager +import com.mogo.eagle.core.function.call.devatools.CallerCaptureImgManager +import com.mogo.eagle.core.function.call.devatools.CallerOTAManager import com.mogo.eagle.core.function.call.msgbox.CallerMsgBoxManager import com.mogo.eagle.core.function.call.obu.CallerObuMapMathListenerManager import com.mogo.eagle.core.function.call.obu.CallerObuWarningRsiListenerManager @@ -425,6 +427,67 @@ class MoGoAdasListenerImpl : OnAdasListener { override fun onWarn(header: MessagePad.Header, warn: MessagePad.Warn?) { } + /** + * SSM发送OTA升级提示请求 + * + * @param header 头 + * @param token PadSsmMsg唯一消息ID + * @param timestamp 消息发送时间 单位:毫秒 + * @param request 数据 null表示 PadSsmMsg中的消息体为null + */ + override fun onOtaDownloadRequest( + header: MessagePad.Header?, + token: Long, + timestamp: Long, + request: SsmInfo.OtaDownloadRequest? + ) { + if(request != null){ + CallerOTAManager.invokeOtaDownloadRequest(request) + } + } + +// /** +// * SSM上报OTA下载进度, 开始升级后定频上报 +// * +// * @param header 头 +// * @param token PadSsmMsg唯一消息ID +// * @param timestamp 消息发送时间 单位:毫秒 +// * @param progress 数据 null表示 PadSsmMsg中的消息体为null +// */ +// override fun onOtaLoadingProgress( +// header: MessagePad.Header?, +// token: Long, +// timestamp: Long, +// progress: SsmInfo.OtaLoadingProgess? +// ) { +// if(progress != null){ +// CallerOTAManager.invokeOtaLoadingProgress(progress) +// } +// } + + /** + * SSM上报OTA状态和查询OTA状态 + * 冷启动状态变更上报以及查询状态 + * 如果是查询到的结果,{@link SsmInfo.OtaStatus#getOtaInfo()}中的{@link SsmInfo.OtaDownloadRequest#getOtaToken()}==""表示不存在升级任务 + * + * @param header 头 + * @param token PadSsmMsg唯一消息ID + * @param timestamp 消息发送时间 单位:毫秒 + * @param isQuery 是否是查询 ture:查询响应的结果 false:表示状态变动域控主动推送 + * @param status 数据 null表示 PadSsmMsg中的消息体为null + */ + override fun onOtaStatus( + header: MessagePad.Header?, + token: Long, + timestamp: Long, + isQuery: Boolean, + status: SsmInfo.OtaStatus? + ) { + if(status != null){ + CallerOTAManager.invokeOtaStatus(status) + } + } + /** * 冷启动状态变更上报以及查询状态 * @@ -1283,6 +1346,21 @@ class MoGoAdasListenerImpl : OnAdasListener { } } + /** + * 接管时前方和后方摄像头数据请求的响应 + * + * @param header 头 + * @param isFront true:前方摄像头 false:后方摄像头 + * @param data 数据 + */ + override fun onCaptureImgOnTakeOver( + header: MessagePad.Header, + isFront: Boolean, + data: MessagePad.CaptureImgOnTakeOver + ) { + CallerCaptureImgManager.invokeCaptureImgOnTakeOver(isFront, data) + } + /** * 是否可以启动自动驾驶 * 使用方法查看:app_ipc_monitoring/uiMainActivity/onAutopilotAbility diff --git a/core/function-impl/mogo-core-function-devatools/src/main/java/com/zhjt/mogo_core_function_devatools/DevaToolsProvider.kt b/core/function-impl/mogo-core-function-devatools/src/main/java/com/zhjt/mogo_core_function_devatools/DevaToolsProvider.kt index a728266da4..5401c0a2cf 100644 --- a/core/function-impl/mogo-core-function-devatools/src/main/java/com/zhjt/mogo_core_function_devatools/DevaToolsProvider.kt +++ b/core/function-impl/mogo-core-function-devatools/src/main/java/com/zhjt/mogo_core_function_devatools/DevaToolsProvider.kt @@ -73,6 +73,7 @@ import com.zhjt.mogo_core_function_devatools.mofang.MoGoMoFangProviderImpl import com.zhjt.mogo_core_function_devatools.monitor.MonitorManager import com.zhjt.mogo_core_function_devatools.monitor.db.MonitorDb import com.zhjt.mogo_core_function_devatools.monitor.db.MonitorDb.Companion.getDb +import com.zhjt.mogo_core_function_devatools.ota.OTAUpgradeManager import com.zhjt.mogo_core_function_devatools.perf.MoGoCpuUsageProviderImpl import com.zhjt.mogo_core_function_devatools.report.IPCReportManager.Companion.iPCReportManager import com.zhjt.mogo_core_function_devatools.scene.SceneManager.Companion.sceneManager @@ -204,6 +205,7 @@ class DevaToolsProvider : IDevaToolsProvider, IAppStateListener { // apmEnvProvider.init(if(DebugConfig.isDebug()) "0" else "1", "${ DebugConfig.getNetMode() }", mDockerVersion ?: "") BadCaseManager.init(mContext!!) ColdStartManager.init(mContext!!) + OTAUpgradeManager.init(mContext!!) if (DebugConfig.isDebug()) { SdtManager.init(mContext!!, true, DetectResultImpl()) } diff --git a/core/function-impl/mogo-core-function-devatools/src/main/java/com/zhjt/mogo_core_function_devatools/badcase/BadCaseManager.kt b/core/function-impl/mogo-core-function-devatools/src/main/java/com/zhjt/mogo_core_function_devatools/badcase/BadCaseManager.kt index 4506bca906..99cd8717db 100644 --- a/core/function-impl/mogo-core-function-devatools/src/main/java/com/zhjt/mogo_core_function_devatools/badcase/BadCaseManager.kt +++ b/core/function-impl/mogo-core-function-devatools/src/main/java/com/zhjt/mogo_core_function_devatools/badcase/BadCaseManager.kt @@ -5,6 +5,7 @@ import android.annotation.SuppressLint import android.app.Activity import android.content.Context import android.graphics.Bitmap +import android.graphics.BitmapFactory import android.os.Environment import android.os.SystemClock import android.util.Log @@ -42,6 +43,7 @@ import com.mogo.eagle.core.function.api.autopilot.IMoGoChassisStatesListener import com.mogo.eagle.core.function.api.autopilot.IMoGoTakeoverListener import com.mogo.eagle.core.function.api.datacenter.IDataCenterBizListener import com.mogo.eagle.core.function.api.datacenter.msgbox.IMsgBoxListener +import com.mogo.eagle.core.function.api.devatools.ICaptureImgListener import com.mogo.eagle.core.function.api.devatools.IMoGoDevaToolsListener import com.mogo.eagle.core.function.api.map.deva.IMoGoMapScreenListener import com.mogo.eagle.core.function.call.autopilot.CallerAutoPilotControlManager @@ -52,6 +54,7 @@ import com.mogo.eagle.core.function.call.autopilot.CallerChassisLocationWGS84Lis import com.mogo.eagle.core.function.call.autopilot.CallerChassisStatesListenerManager import com.mogo.eagle.core.function.call.autopilot.CallerTakeoverListenerManager import com.mogo.eagle.core.function.call.datacenter.CallerDataCenterBizListener +import com.mogo.eagle.core.function.call.devatools.CallerCaptureImgManager import com.mogo.eagle.core.function.call.devatools.CallerDevaToolsListenerManager import com.mogo.eagle.core.function.call.map.CallerMapScreenListenerManager import com.mogo.eagle.core.function.call.map.CallerMapUIServiceManager @@ -72,6 +75,7 @@ import com.zhjt.mogo_core_function_devatools.badcase.util.RecordBitmapUtils import com.zhjt.mogo_core_function_devatools.ext.enqueuePop import com.zhjt.mogo_core_function_devatools.workorder.ReportTypeWindow import me.jessyan.autosize.utils.AutoSizeUtils +import mogo.telematics.pad.MessagePad import record_cache.RecordPanelOuterClass import java.io.File import java.util.Random @@ -81,7 +85,7 @@ internal object BadCaseManager : LifecycleEventObserver, IMoGoAutopilotRecordLis IMoGoChassisLocationGCJ02Listener, IMsgBoxListener, IMoGoDevaToolsListener, IMogoStatusChangedListener, IMoGoMapScreenListener, IMoGoChassisStatesListener, IMoGoAutopilotStatusListener, - IDataCenterBizListener, IMoGoTakeoverListener { + IDataCenterBizListener, IMoGoTakeoverListener, ICaptureImgListener { const val TAG = "BadCase" @@ -91,6 +95,7 @@ internal object BadCaseManager : LifecycleEventObserver, IMoGoAutopilotRecordLis private var record: AutoPilotRecord? = null private var recordKey: Long = 0 //主动录制bag包key + private var takeOverBagId: Long = 0 //接管录包Bag Id(key) @SuppressLint("StaticFieldLeak") private var reportTypeWindow: ReportTypeWindow ?= null @@ -116,6 +121,8 @@ internal object BadCaseManager : LifecycleEventObserver, IMoGoAutopilotRecordLis //消息盒子监听,获取FM和Report信息 CallerMsgBoxListenerManager.addListener(TAG,this) CallerDevaToolsListenerManager.addListener(TAG, this) + //接管时前方和后方摄像头数据请求响应回调监听 + CallerCaptureImgManager.addListener(TAG, this) // 云socket连接状态 MogoStatusManager.getInstance() .registerStatusChangedListener(TAG, StatusDescriptor.CLOUD_SOCKET, this) @@ -297,8 +304,6 @@ internal object BadCaseManager : LifecycleEventObserver, IMoGoAutopilotRecordLis }else{ //进行录包,但不展示录包弹窗 BadCaseConfig.notDisplayBagWindow = true - //高精地图屏幕截图 - CallerMapScreenListenerManager.addListener(TAG,this) val recordKey = Random(SystemClock.elapsedRealtime()).nextInt().toLong() CallerAutoPilotControlManager.recordPackage(BadCaseConfig.type,recordKey.toInt(), BadCaseConfig.totalDuration, BadCaseConfig.previousDuration) @@ -416,8 +421,6 @@ internal object BadCaseManager : LifecycleEventObserver, IMoGoAutopilotRecordLis //保存录包状态 recordSet.add(recordPanel.key.toString()) BadCaseConfig.setInitiativeRecordSet(recordSet) - //开启高精地图截图 - CallerMapUIServiceManager.getMapUIController()?.getMapScreenShot() //将当次主动录包设置标签还原 BadCaseConfig.notDisplayBagWindow = false } @@ -457,6 +460,13 @@ internal object BadCaseManager : LifecycleEventObserver, IMoGoAutopilotRecordLis val latLon = LatLonPoint(CallerChassisLocationWGS84ListenerManager.getChassisLocationWGS84().latitude, CallerChassisLocationWGS84ListenerManager.getChassisLocationWGS84().longitude) val q = RegeocodeQuery(latLon,200f,GeocodeSearch.AMAP) geocodeSearch.getFromLocationAsyn(q) + takeOverBagId = recordPanel.key + //触发域控前后120度摄像头截图和高精地图截图 + CallerAutoPilotControlManager.sendCaptureImgReqOnTakeOver(recordPanel.key) + //高精地图屏幕截图 + CallerMapScreenListenerManager.addListener(TAG,this) + //开启高精地图截图 + CallerMapUIServiceManager.getMapUIController()?.getMapScreenShot() } } } @@ -578,42 +588,16 @@ internal object BadCaseManager : LifecycleEventObserver, IMoGoAutopilotRecordLis override fun onMapScreen(bitmap: Bitmap) { super.onMapScreen(bitmap) - //在截图上保存即时信息 - val time = "时间:${millis2String(System.currentTimeMillis(), TimeUtils.getHourMinSecondFormat())}" - val lineId = "路线ID:${CallerAutoPilotStatusListenerManager.getLineId()}" - val state = when(CallerAutoPilotStatusListenerManager.getState()){ - 0->"自驾状态:不可自驾" - 1->"自驾状态:可自驾" - 2->"自驾状态:自驾中" - 7->"自驾状态:平行驾驶中" - else->"自驾状态:未知" - } - val speed = "当前车速:${BadCaseConfig.currentSpeed}" - val site = if(CallerAutoPilotStatusListenerManager.getLineStartName().isNullOrEmpty() || CallerAutoPilotStatusListenerManager.getLineEndName().isNullOrEmpty()){ - "路线起始点:无" - }else{ - "路线起点:${CallerAutoPilotStatusListenerManager.getLineStartName()};终点:${CallerAutoPilotStatusListenerManager.getLineEndName()}" - } - val outBitmap = RecordBitmapUtils.drawTextOnBitmap(bitmap,time,lineId,state,speed,site, - BadCaseConfig.gpsStatus,BadCaseConfig.tracingStatus,BadCaseConfig.socketStatus - ,BadCaseConfig.newFMInfoMsg,BadCaseConfig.newReportEntity) - //图片保存本地 val currentDay = millis2String(System.currentTimeMillis(), TimeUtils.getMdFormat()) val fileDir: String = Environment.getExternalStorageDirectory().absolutePath + File.separator+ "MapScreen" + File.separator+ currentDay + File.separator - val fileName = "$recordKey.png" + val fileName = "$takeOverBagId.png" val path = fileDir + fileName if (!File(fileDir).exists()) { File(fileDir).mkdirs() } - if(outBitmap != null){ - RecordBitmapUtils.bitmap2Path(outBitmap,path) - }else{ - RecordBitmapUtils.bitmap2Path(bitmap,path) - } - //遍历是否有非当日的文件并删除 - RecordBitmapUtils.deleteExpiredFile(currentDay) + RecordBitmapUtils.bitmap2Path(bitmap,path) //注销高精地图截图监听回调 CallerMapScreenListenerManager.removeListener(TAG) } @@ -648,4 +632,30 @@ internal object BadCaseManager : LifecycleEventObserver, IMoGoAutopilotRecordLis } + /** + * 接管时前方和后方摄像头数据请求的响应 + * @param isFront true:前方摄像头 false:后方摄像头 + * @param data 数据 + */ + override fun onCaptureImgOnTakeOver(isFront: Boolean, data: MessagePad.CaptureImgOnTakeOver) { + super.onCaptureImgOnTakeOver(isFront, data) + //将byte字节流转为Bitmap + val bitmap = BitmapFactory.decodeByteArray(data.data.toByteArray(),0,data.toByteArray().size) + //图片保存本地 + val currentDay = millis2String(System.currentTimeMillis(), TimeUtils.getMdFormat()) + val imageName = if(isFront){ + "FrontCamera" + }else{ + "RearCamera" + } + val fileDir: String = Environment.getExternalStorageDirectory().absolutePath + File.separator+ + imageName + File.separator+ currentDay + File.separator + val fileName = "$takeOverBagId.png" + val path = fileDir + fileName + if (!File(fileDir).exists()) { + File(fileDir).mkdirs() + } + RecordBitmapUtils.bitmap2Path(bitmap,path) + } + } diff --git a/core/function-impl/mogo-core-function-devatools/src/main/java/com/zhjt/mogo_core_function_devatools/badcase/biz/InitiativeBadCaseWindow.kt b/core/function-impl/mogo-core-function-devatools/src/main/java/com/zhjt/mogo_core_function_devatools/badcase/biz/InitiativeBadCaseWindow.kt index 8cf0176c4a..e76b7a819e 100644 --- a/core/function-impl/mogo-core-function-devatools/src/main/java/com/zhjt/mogo_core_function_devatools/badcase/biz/InitiativeBadCaseWindow.kt +++ b/core/function-impl/mogo-core-function-devatools/src/main/java/com/zhjt/mogo_core_function_devatools/badcase/biz/InitiativeBadCaseWindow.kt @@ -6,7 +6,6 @@ import android.graphics.Bitmap import android.graphics.Color import android.graphics.PixelFormat import android.os.Bundle -import android.os.Environment import android.os.Handler import android.os.SystemClock import android.util.DisplayMetrics @@ -36,12 +35,9 @@ import com.mogo.eagle.core.function.api.autopilot.IMoGoAutopilotRecordListener import com.mogo.eagle.core.function.api.devatools.badcase.BadCaseNetListener import com.mogo.eagle.core.function.api.map.deva.IMoGoMapScreenListener import com.mogo.eagle.core.function.call.autopilot.CallerAutoPilotControlManager -import com.mogo.eagle.core.function.call.autopilot.CallerAutoPilotStatusListenerManager import com.mogo.eagle.core.function.call.autopilot.CallerAutopilotRecordListenerManager import com.mogo.eagle.core.function.call.autopilot.CallerChassisLocationWGS84ListenerManager.getChassisLocationWGS84 import com.mogo.eagle.core.function.call.devatools.CallerDevaToolsNetManager -import com.mogo.eagle.core.function.call.map.CallerMapScreenListenerManager -import com.mogo.eagle.core.function.call.map.CallerMapUIServiceManager import com.mogo.eagle.core.utilcode.mogo.logger.CallerLogger import com.mogo.eagle.core.utilcode.mogo.logger.scene.SceneConstant.Companion.M_DEVA import com.mogo.eagle.core.utilcode.mogo.toast.TipToast @@ -75,7 +71,6 @@ import record_cache.RecordPanelOuterClass import java.io.File import java.util.* import kotlin.collections.ArrayList -import kotlin.math.absoluteValue /** @@ -198,7 +193,7 @@ class InitiativeBadCaseWindow constructor(activity: Activity) : View.OnTouchList BadCaseNetManager.badCaseNetManager.getRecordOption(1,AppConfigInfo.iPCMacAddress) // BadCaseNetManager.badCaseNetManager.getRecordOption(1,"48:b0:2d:3a:9c:8f") //高精地图屏幕截图 - CallerMapScreenListenerManager.addListener(this.hashCode().toString(),this) +// CallerMapScreenListenerManager.addListener(this.hashCode().toString(),this) //采集结果回调监听 CallerAutopilotRecordListenerManager.addListener(this.hashCode().toString(),this) //主动录包采集原因回调监听 @@ -561,7 +556,7 @@ class InitiativeBadCaseWindow constructor(activity: Activity) : View.OnTouchList //注销采集原因回调监听 CallerDevaToolsNetManager.removeListener(this.hashCode().toString()) //注销高精地图截图监听回调 - CallerMapScreenListenerManager.removeListener(this.hashCode().toString()) +// CallerMapScreenListenerManager.removeListener(this.hashCode().toString()) if (mFloatLayout.parent != null){ mWindowManager!!.removeView(mFloatLayout) @@ -580,8 +575,8 @@ class InitiativeBadCaseWindow constructor(activity: Activity) : View.OnTouchList //保存录包状态 recordSet.add(recordPanel.key.toString()) BadCaseConfig.setInitiativeRecordSet(recordSet) - //开启高精地图截图 - CallerMapUIServiceManager.getMapUIController()?.getMapScreenShot() +// //开启高精地图截图 +// CallerMapUIServiceManager.getMapUIController()?.getMapScreenShot() } if(recordFileName==null){ recordFileName = recordPanel.filename @@ -702,44 +697,44 @@ class InitiativeBadCaseWindow constructor(activity: Activity) : View.OnTouchList * 高精地图截图回调 */ override fun onMapScreen(bitmap: Bitmap) { - //在截图上保存即时信息 - val time = "时间:${millis2String(System.currentTimeMillis(), TimeUtils.getHourMinSecondFormat())}" - val lineId = "路线ID:${CallerAutoPilotStatusListenerManager.getLineId()}" - val state = when(CallerAutoPilotStatusListenerManager.getState()){ - 0->"自驾状态:不可自驾" - 1->"自驾状态:可自驾" - 2->"自驾状态:自驾中" - 7->"自驾状态:平行驾驶中" - else->"自驾状态:未知" - } - val speed = "当前车速:${BadCaseConfig.currentSpeed}" - val site = if(CallerAutoPilotStatusListenerManager.getLineStartName().isNullOrEmpty() || CallerAutoPilotStatusListenerManager.getLineEndName().isNullOrEmpty()){ - "路线起始点:无" - }else{ - "路线起点:${CallerAutoPilotStatusListenerManager.getLineStartName()};终点:${CallerAutoPilotStatusListenerManager.getLineEndName()}" - } - - val outBitmap = RecordBitmapUtils.drawTextOnBitmap(bitmap,time,lineId,state,speed,site, - BadCaseConfig.gpsStatus,BadCaseConfig.tracingStatus,BadCaseConfig.socketStatus - ,BadCaseConfig.newFMInfoMsg,BadCaseConfig.newReportEntity) - - //图片保存本地 - val currentDay = millis2String(System.currentTimeMillis(), TimeUtils.getMdFormat()) - val fileDir: String = Environment.getExternalStorageDirectory().absolutePath + File.separator+ - "MapScreen" + File.separator+ currentDay + File.separator - val fileName = "$recordKey.png" - val path = fileDir + fileName - if (!File(fileDir).exists()) { - File(fileDir).mkdirs() - } - if(outBitmap != null){ - RecordBitmapUtils.bitmap2Path(outBitmap,path) - }else{ - RecordBitmapUtils.bitmap2Path(bitmap,path) - } - screenSavePath = path - //遍历是否有非当日的文件并删除 - RecordBitmapUtils.deleteExpiredFile(currentDay) +// //在截图上保存即时信息 +// val time = "时间:${millis2String(System.currentTimeMillis(), TimeUtils.getHourMinSecondFormat())}" +// val lineId = "路线ID:${CallerAutoPilotStatusListenerManager.getLineId()}" +// val state = when(CallerAutoPilotStatusListenerManager.getState()){ +// 0->"自驾状态:不可自驾" +// 1->"自驾状态:可自驾" +// 2->"自驾状态:自驾中" +// 7->"自驾状态:平行驾驶中" +// else->"自驾状态:未知" +// } +// val speed = "当前车速:${BadCaseConfig.currentSpeed}" +// val site = if(CallerAutoPilotStatusListenerManager.getLineStartName().isNullOrEmpty() || CallerAutoPilotStatusListenerManager.getLineEndName().isNullOrEmpty()){ +// "路线起始点:无" +// }else{ +// "路线起点:${CallerAutoPilotStatusListenerManager.getLineStartName()};终点:${CallerAutoPilotStatusListenerManager.getLineEndName()}" +// } +// +// val outBitmap = RecordBitmapUtils.drawTextOnBitmap(bitmap,time,lineId,state,speed,site, +// BadCaseConfig.gpsStatus,BadCaseConfig.tracingStatus,BadCaseConfig.socketStatus +// ,BadCaseConfig.newFMInfoMsg,BadCaseConfig.newReportEntity) +// +// //图片保存本地 +// val currentDay = millis2String(System.currentTimeMillis(), TimeUtils.getMdFormat()) +// val fileDir: String = Environment.getExternalStorageDirectory().absolutePath + File.separator+ +// "MapScreen" + File.separator+ currentDay + File.separator +// val fileName = "$recordKey.png" +// val path = fileDir + fileName +// if (!File(fileDir).exists()) { +// File(fileDir).mkdirs() +// } +// if(outBitmap != null){ +// RecordBitmapUtils.bitmap2Path(outBitmap,path) +// }else{ +// RecordBitmapUtils.bitmap2Path(bitmap,path) +// } +// screenSavePath = path +// //遍历是否有非当日的文件并删除 +// RecordBitmapUtils.deleteExpiredFile(currentDay) } } \ No newline at end of file diff --git a/core/function-impl/mogo-core-function-devatools/src/main/java/com/zhjt/mogo_core_function_devatools/badcase/biz/PassiveBadCaseWindow.kt b/core/function-impl/mogo-core-function-devatools/src/main/java/com/zhjt/mogo_core_function_devatools/badcase/biz/PassiveBadCaseWindow.kt index 8fec467ed1..883ca30e6c 100644 --- a/core/function-impl/mogo-core-function-devatools/src/main/java/com/zhjt/mogo_core_function_devatools/badcase/biz/PassiveBadCaseWindow.kt +++ b/core/function-impl/mogo-core-function-devatools/src/main/java/com/zhjt/mogo_core_function_devatools/badcase/biz/PassiveBadCaseWindow.kt @@ -37,7 +37,6 @@ import com.mogo.eagle.core.function.call.autopilot.CallerAutoPilotControlManager import com.mogo.eagle.core.function.call.autopilot.CallerAutoPilotStatusListenerManager import com.mogo.eagle.core.function.call.autopilot.CallerChassisLocationWGS84ListenerManager import com.mogo.eagle.core.function.call.devatools.CallerDevaToolsNetManager -import com.mogo.eagle.core.function.call.map.CallerMapScreenListenerManager import com.mogo.eagle.core.function.call.map.CallerMapUIServiceManager import com.mogo.eagle.core.function.call.msgbox.CallerMsgBoxManager import com.mogo.eagle.core.utilcode.mogo.logger.CallerLogger @@ -180,7 +179,7 @@ class PassiveBadCaseWindow constructor(activity: Activity) : View.OnTouchListene BadCaseNetManager.badCaseNetManager.getRecordOption(2,AppConfigInfo.iPCMacAddress) // BadCaseNetManager.badCaseNetManager.getRecordOption(2,"48:b0:2d:3a:9c:8f") //高精地图屏幕截图 - CallerMapScreenListenerManager.addListener(this.hashCode().toString(),this) +// CallerMapScreenListenerManager.addListener(this.hashCode().toString(),this) CallerDevaToolsNetManager.addListener(this.hashCode().toString(),this) if(BadCaseConfig.windowNum<1){ BadCaseConfig.windowNum = 1 @@ -530,7 +529,7 @@ class PassiveBadCaseWindow constructor(activity: Activity) : View.OnTouchListene fun hideFloatWindow() { //注销高精地图截图监听回调 - CallerMapScreenListenerManager.removeListener(this.hashCode().toString()) +// CallerMapScreenListenerManager.removeListener(this.hashCode().toString()) //注销采集原因回调监听 CallerDevaToolsNetManager.removeListener(this.hashCode().toString()) // 移除 ADAS车辆状态&定位 监听 @@ -552,7 +551,7 @@ class PassiveBadCaseWindow constructor(activity: Activity) : View.OnTouchListene receiveTime = msgBoxBean.timestamp.toString() stat = recordBagMsg.stat.toString() //获取高精地图截图 - CallerMapUIServiceManager.getMapUIController()?.getMapScreenShot() +// CallerMapUIServiceManager.getMapUIController()?.getMapScreenShot() } fun setClickListener(clickListener: ClickListener) { @@ -589,42 +588,42 @@ class PassiveBadCaseWindow constructor(activity: Activity) : View.OnTouchListene */ override fun onMapScreen(bitmap: Bitmap) { //在截图上保存即时信息 - val time = "时间:${millis2String(System.currentTimeMillis(), TimeUtils.getHourMinSecondFormat())}" - val lineId = "路线ID:${CallerAutoPilotStatusListenerManager.getLineId()}" - val state = when(CallerAutoPilotStatusListenerManager.getState()){ - 0->"自驾状态:不可自驾" - 1->"自驾状态:可自驾" - 2->"自驾状态:自驾中" - 7->"自驾状态:平行驾驶中" - else->"自驾状态:未知" - } - val speed = "当前车速:${BadCaseConfig.currentSpeed}" - val site = if(CallerAutoPilotStatusListenerManager.getLineStartName().isNullOrEmpty() || CallerAutoPilotStatusListenerManager.getLineEndName().isNullOrEmpty()){ - "路线起始点:无" - }else{ - "路线起点:${CallerAutoPilotStatusListenerManager.getLineStartName()};终点:${CallerAutoPilotStatusListenerManager.getLineEndName()}" - } - - val outBitmap = RecordBitmapUtils.drawTextOnBitmap(bitmap,time,lineId,state,speed,site, - BadCaseConfig.gpsStatus,BadCaseConfig.tracingStatus,BadCaseConfig.socketStatus - ,BadCaseConfig.newFMInfoMsg,BadCaseConfig.newReportEntity) - //图片保存本地 - val currentDay = millis2String(System.currentTimeMillis(), TimeUtils.getMdFormat()) - val fileDir: String = Environment.getExternalStorageDirectory().absolutePath + File.separator+ - "MapScreen" + File.separator+ currentDay + File.separator - val fileName = "$recordKey.png" - val path = fileDir + fileName - if (!File(fileDir).exists()) { - File(fileDir).mkdirs() - } - if(outBitmap != null){ - RecordBitmapUtils.bitmap2Path(outBitmap,path) - }else{ - RecordBitmapUtils.bitmap2Path(bitmap,path) - } - screenSavePath = path - //遍历是否有非当日的文件并删除 - RecordBitmapUtils.deleteExpiredFile(currentDay) +// val time = "时间:${millis2String(System.currentTimeMillis(), TimeUtils.getHourMinSecondFormat())}" +// val lineId = "路线ID:${CallerAutoPilotStatusListenerManager.getLineId()}" +// val state = when(CallerAutoPilotStatusListenerManager.getState()){ +// 0->"自驾状态:不可自驾" +// 1->"自驾状态:可自驾" +// 2->"自驾状态:自驾中" +// 7->"自驾状态:平行驾驶中" +// else->"自驾状态:未知" +// } +// val speed = "当前车速:${BadCaseConfig.currentSpeed}" +// val site = if(CallerAutoPilotStatusListenerManager.getLineStartName().isNullOrEmpty() || CallerAutoPilotStatusListenerManager.getLineEndName().isNullOrEmpty()){ +// "路线起始点:无" +// }else{ +// "路线起点:${CallerAutoPilotStatusListenerManager.getLineStartName()};终点:${CallerAutoPilotStatusListenerManager.getLineEndName()}" +// } +// +// val outBitmap = RecordBitmapUtils.drawTextOnBitmap(bitmap,time,lineId,state,speed,site, +// BadCaseConfig.gpsStatus,BadCaseConfig.tracingStatus,BadCaseConfig.socketStatus +// ,BadCaseConfig.newFMInfoMsg,BadCaseConfig.newReportEntity) +// //图片保存本地 +// val currentDay = millis2String(System.currentTimeMillis(), TimeUtils.getMdFormat()) +// val fileDir: String = Environment.getExternalStorageDirectory().absolutePath + File.separator+ +// "MapScreen" + File.separator+ currentDay + File.separator +// val fileName = "$recordKey.png" +// val path = fileDir + fileName +// if (!File(fileDir).exists()) { +// File(fileDir).mkdirs() +// } +// if(outBitmap != null){ +// RecordBitmapUtils.bitmap2Path(outBitmap,path) +// }else{ +// RecordBitmapUtils.bitmap2Path(bitmap,path) +// } +// screenSavePath = path +// //遍历是否有非当日的文件并删除 +// RecordBitmapUtils.deleteExpiredFile(currentDay) } /** diff --git a/core/function-impl/mogo-core-function-devatools/src/main/java/com/zhjt/mogo_core_function_devatools/ota/OTAUpgradeConfig.kt b/core/function-impl/mogo-core-function-devatools/src/main/java/com/zhjt/mogo_core_function_devatools/ota/OTAUpgradeConfig.kt new file mode 100644 index 0000000000..1b096fc60a --- /dev/null +++ b/core/function-impl/mogo-core-function-devatools/src/main/java/com/zhjt/mogo_core_function_devatools/ota/OTAUpgradeConfig.kt @@ -0,0 +1,11 @@ +package com.zhjt.mogo_core_function_devatools.ota + +/** + * OTA升级配置 + */ +object OTAUpgradeConfig { + + @JvmField + var otaToken: String = "" + +} \ No newline at end of file diff --git a/core/function-impl/mogo-core-function-devatools/src/main/java/com/zhjt/mogo_core_function_devatools/ota/OTAUpgradeManager.kt b/core/function-impl/mogo-core-function-devatools/src/main/java/com/zhjt/mogo_core_function_devatools/ota/OTAUpgradeManager.kt new file mode 100644 index 0000000000..40982ff2a0 --- /dev/null +++ b/core/function-impl/mogo-core-function-devatools/src/main/java/com/zhjt/mogo_core_function_devatools/ota/OTAUpgradeManager.kt @@ -0,0 +1,205 @@ +package com.zhjt.mogo_core_function_devatools.ota + +import android.content.Context +import android.util.Log +import com.mogo.eagle.core.data.deva.ota.OtaUpgradeInfo +import com.mogo.eagle.core.function.api.autopilot.IMoGoAutopilotStatusListener +import com.mogo.eagle.core.function.api.datacenter.IDataCenterBizListener +import com.mogo.eagle.core.function.api.devatools.IOTAListener +import com.mogo.eagle.core.function.call.autopilot.CallerAutoPilotControlManager +import com.mogo.eagle.core.function.call.autopilot.CallerAutoPilotStatusListenerManager +import com.mogo.eagle.core.function.call.datacenter.CallerDataCenterBizListener +import com.mogo.eagle.core.function.call.devatools.CallerOTAManager +import com.mogo.eagle.core.function.call.hmi.CallerHmiManager +import org.json.JSONArray +import org.json.JSONObject +import system_master.SsmInfo + +/** + * OTA升级管理类 + */ +object OTAUpgradeManager: IMoGoAutopilotStatusListener, IDataCenterBizListener, IOTAListener { + + const val TAG = "OTAUpgradeManager" + + fun init(context: Context){ + CallerAutoPilotStatusListenerManager.addListener(TAG, this) + CallerDataCenterBizListener.addListener(TAG,this) + CallerOTAManager.addListener(TAG,this) + //查询OTA状态 + CallerAutoPilotControlManager.sendSsmFuncOtaStatusQuery(OTAUpgradeConfig.otaToken) + } + + /** + * 自动驾驶状态信息 + * @param state 状态信息 + * 0-不可自动驾驶,adas与工控机没有链接,或工控机异常 + * 1-可自动驾驶,目前处于人工干预状态 + * 2-自动驾驶中 + * 7-平行驾驶中 + */ + override fun onAutopilotStatusResponse(state: Int) { + super.onAutopilotStatusResponse(state) + + } + + /** + * 是否有订单 + * @param inOrder true有订单 false没有订单 + */ + override fun invokeOrderStatus(inOrder: Boolean) { + super.invokeOrderStatus(inOrder) + + } + + /** + * SSM发送OTA升级提示请求,主动触发 + * @param request SSM发送OTA升级提示内容 + */ + override fun onOtaDownloadRequest(request: SsmInfo.OtaDownloadRequest) { + super.onOtaDownloadRequest(request) + Log.i(TAG,"onOtaDownloadRequest otaToken"+request.otaToken) + Log.i(TAG,"onOtaDownloadRequest productName"+request.productName) + if(request.otaToken.isNotEmpty()){ + if(OTAUpgradeConfig.otaToken != request.otaToken){ + OTAUpgradeConfig.otaToken = request.otaToken + //触发升级提示 + CallerHmiManager.showOTAUpgradeDialog() + }else{ + //展示OTA升级提示 + CallerHmiManager.showOTAUpgradeTipView(true) + } + }else{ + //隐藏OTA升级提示 + CallerHmiManager.showOTAUpgradeTipView(false) + } + //解析JSON + var upgradeComplete = true + val otaUpgradeList = ArrayList() + val productArray = JSONArray(request.productName) + if(productArray.length() > 0){ + for(index in 0 until productArray.length()){ + val productInfo = productArray[index] as JSONObject + val token = productInfo.optString("token") + val productStatus = productInfo.optInt("status") + val failReason = productInfo.optString("fail_reason") + val upgradeReason = productInfo.optString("upgrade_reason") + val taskId = productInfo.optInt("task_id") + val taskItemId = productInfo.optInt("task_item_id") + val otaType = productInfo.optInt("ota_type") + val productName = productInfo.optString("product_name") + val needRestart = productInfo.optBoolean("need_restart") + val isDelay = productInfo.optBoolean("is_delay") + val curSize = productInfo.optDouble("cur_size") + val totalSize = productInfo.optDouble("total_size") + + Log.i(TAG, "index=$index") + Log.i(TAG, "token=$token") + Log.i(TAG, "status=$productStatus") + Log.i(TAG, "fail_reason=$failReason") + Log.i(TAG, "upgrade_reason=$upgradeReason") + Log.i(TAG, "task_id=$taskId") + Log.i(TAG, "task_item_id=$taskItemId") + Log.i(TAG, "ota_type=$otaType") + Log.i(TAG, "product_name=$productName") + Log.i(TAG, "need_restart=$needRestart") + Log.i(TAG, "is_delay=$isDelay") + Log.i(TAG, "cur_size=$curSize") + Log.i(TAG, "total_size=$totalSize") + + //// 状态 0:默认(未开始), 1:下载中, 2:下载完成, 3:升级完成, 4:升级失败 + if(productStatus == 0 || productStatus == 1 || productStatus == 2){ + upgradeComplete = false + } + + val otaUpgradeInfo = OtaUpgradeInfo(token, productStatus,failReason,upgradeReason, + taskId,taskItemId,otaType,productName,needRestart,isDelay,curSize,totalSize) + otaUpgradeList.add(otaUpgradeInfo) + } + CallerHmiManager.showOTADownloadStatusDialog(otaUpgradeList) + if(upgradeComplete){ + OTAUpgradeConfig.otaToken = "" + } + } + + } + + + /** + * SSM上报OTA状态和查询OTA状态 + * 冷启动状态变更上报以及查询状态 + * 如果是查询到的结果,{@link SsmInfo.OtaStatus#getOtaInfo()} + * 中的{@link SsmInfo.OtaDownloadRequest#getOtaToken()}==""表示不存在升级任务 + * @param status 冷启动状态变更上报以及查询状态 + */ + override fun onOtaStatus(status: SsmInfo.OtaStatus) { + super.onOtaStatus(status) + Log.i(TAG,"onOtaStatus status.otaInfo.otaToken"+status.otaInfo.otaToken) + Log.i(TAG,"onOtaStatus status.otaInfo.productName"+status.otaInfo.productName) + + if(status.otaInfo.otaToken.isNotEmpty()){ + if(OTAUpgradeConfig.otaToken != status.otaInfo.otaToken){ + OTAUpgradeConfig.otaToken = status.otaInfo.otaToken + //触发升级提示 + CallerHmiManager.showOTAUpgradeDialog() + }else{ + //展示OTA升级提示 + CallerHmiManager.showOTAUpgradeTipView(true) + } + }else{ + //隐藏OTA升级提示 + CallerHmiManager.showOTAUpgradeTipView(false) + } + + //解析JSON + val otaUpgradeList = ArrayList() + val productArray = JSONArray(status.otaInfo.productName) + var upgradeComplete = true + if(productArray.length() > 0){ + for(index in 0 until productArray.length()){ + val productInfo = productArray[index] as JSONObject + val token = productInfo.optString("token") + val productStatus = productInfo.optInt("status") + val failReason = productInfo.optString("fail_reason") + val upgradeReason = productInfo.optString("upgrade_reason") + val taskId = productInfo.optInt("task_id") + val taskItemId = productInfo.optInt("task_item_id") + val otaType = productInfo.optInt("ota_type") + val productName = productInfo.optString("product_name") + val needRestart = productInfo.optBoolean("need_restart") + val isDelay = productInfo.optBoolean("is_delay") + val curSize = productInfo.optDouble("cur_size") + val totalSize = productInfo.optDouble("total_size") + + Log.i(TAG, "index=$index") + Log.i(TAG, "token=$token") + Log.i(TAG, "status=$productStatus") + Log.i(TAG, "fail_reason=$failReason") + Log.i(TAG, "upgrade_reason=$upgradeReason") + Log.i(TAG, "task_id=$taskId") + Log.i(TAG, "task_item_id=$taskItemId") + Log.i(TAG, "ota_type=$otaType") + Log.i(TAG, "product_name=$productName") + Log.i(TAG, "need_restart=$needRestart") + Log.i(TAG, "is_delay=$isDelay") + Log.i(TAG, "cur_size=$curSize") + Log.i(TAG, "total_size=$totalSize") + //// 状态 0:默认(未开始), 1:下载中, 2:下载完成, 3:升级完成, 4:升级失败 + if(productStatus == 0 || productStatus == 1 || productStatus == 2){ + upgradeComplete = false + } + + val otaUpgradeInfo = OtaUpgradeInfo(token, productStatus,failReason,upgradeReason, + taskId,taskItemId,otaType,productName,needRestart,isDelay,curSize,totalSize) + otaUpgradeList.add(otaUpgradeInfo) + } + CallerHmiManager.showOTADownloadStatusDialog(otaUpgradeList) + if(upgradeComplete){ + OTAUpgradeConfig.otaToken = "" + } + } + + } + + +} \ No newline at end of file diff --git a/core/function-impl/mogo-core-function-devatools/src/main/res/layout/item_ota_download_status.xml b/core/function-impl/mogo-core-function-devatools/src/main/res/layout/item_ota_download_status.xml new file mode 100644 index 0000000000..a51a5f5ad1 --- /dev/null +++ b/core/function-impl/mogo-core-function-devatools/src/main/res/layout/item_ota_download_status.xml @@ -0,0 +1,27 @@ + + + + + + + + \ No newline at end of file diff --git a/core/function-impl/mogo-core-function-hmi/src/main/java/com/mogo/eagle/core/function/hmi/ui/MoGoHmiProvider.kt b/core/function-impl/mogo-core-function-hmi/src/main/java/com/mogo/eagle/core/function/hmi/ui/MoGoHmiProvider.kt index 66f4a3c2a7..30acd2f51d 100644 --- a/core/function-impl/mogo-core-function-hmi/src/main/java/com/mogo/eagle/core/function/hmi/ui/MoGoHmiProvider.kt +++ b/core/function-impl/mogo-core-function-hmi/src/main/java/com/mogo/eagle/core/function/hmi/ui/MoGoHmiProvider.kt @@ -29,6 +29,7 @@ import com.mogo.eagle.core.data.constants.MogoServicePaths.PATH_FRAGMENT_HMI import com.mogo.eagle.core.data.deva.bindingcar.IPCUpgradeStateInfo import com.mogo.eagle.core.data.deva.bizconfig.FuncBizConfig.Companion.BIZ_RTS import com.mogo.eagle.core.data.deva.bizconfig.FuncBizConfig.Companion.V2I +import com.mogo.eagle.core.data.deva.ota.OtaUpgradeInfo import com.mogo.eagle.core.data.enums.EventTypeEnumNew import com.mogo.eagle.core.data.enums.WarningDirectionEnum import com.mogo.eagle.core.data.map.Infrastructure @@ -58,6 +59,9 @@ import com.mogo.eagle.core.function.hmi.ui.setting.StatusView import com.mogo.eagle.core.function.hmi.ui.setting.ToolsView.Companion.toolsView import com.mogo.eagle.core.function.hmi.ui.tools.AdUpgradeDialog import com.mogo.eagle.core.function.hmi.ui.tools.ModifyBindingCarDialog +import com.mogo.eagle.core.function.hmi.ui.tools.OTADownloadStatusDialog +import com.mogo.eagle.core.function.hmi.ui.tools.OTAUpgradeDialog +import com.mogo.eagle.core.function.hmi.ui.tools.OTAUpgradeTipView import com.mogo.eagle.core.function.hmi.ui.tools.ToBindingCarDialog import com.mogo.eagle.core.function.hmi.ui.tools.UpgradeAppDialog import com.mogo.eagle.core.function.hmi.ui.utils.HmiActionLog @@ -659,4 +663,59 @@ class MoGoHmiProvider : IMoGoHmiProvider { CallerHmiViewControlListenerManager.invokeColdStartProcessView() } + var otaUpgradeDialog: OTAUpgradeDialog ?= null + var otaDownloadStatusDialog: OTADownloadStatusDialog ?= null + var otaUpgradeTipView: OTAUpgradeTipView ?= null + + /** + * 展示OTA升级弹窗 + */ + override fun showOTAUpgradeDialog() { + ThreadUtils.runOnUiThread{ + context?.let { + if(otaUpgradeDialog == null){ + otaUpgradeDialog = OTAUpgradeDialog(it) + } + if(otaUpgradeDialog?.isShowing == false){ + otaUpgradeDialog?.show() + } + } + } + } + + /** + * 展示OTA升级下载状态弹窗 + */ + override fun showOTADownloadStatusDialog(list: List) { + ThreadUtils.runOnUiThread{ + if(otaDownloadStatusDialog?.isShowing == true){ + return@runOnUiThread + } + context?.let { + if(otaDownloadStatusDialog == null){ + otaDownloadStatusDialog = OTADownloadStatusDialog(it) + } + otaDownloadStatusDialog?.notifyDownloadStatus(list) + } + } + } + + /** + * 展示OTA升级提示 + * @param visible 设置是否可见 + */ + override fun showOTAUpgradeTipView(visible: Boolean) { + ThreadUtils.runOnUiThread{ + if(otaUpgradeDialog?.isShowing == true){ + return@runOnUiThread + } + if(otaUpgradeTipView == null){ + context?.let { + otaUpgradeTipView = OTAUpgradeTipView(it) + } + } + otaUpgradeTipView?.setDisplayStatus(visible) + } + } + } \ No newline at end of file diff --git a/core/function-impl/mogo-core-function-hmi/src/main/java/com/mogo/eagle/core/function/hmi/ui/tools/OTADownloadStatusDialog.kt b/core/function-impl/mogo-core-function-hmi/src/main/java/com/mogo/eagle/core/function/hmi/ui/tools/OTADownloadStatusDialog.kt new file mode 100644 index 0000000000..b4b57af05c --- /dev/null +++ b/core/function-impl/mogo-core-function-hmi/src/main/java/com/mogo/eagle/core/function/hmi/ui/tools/OTADownloadStatusDialog.kt @@ -0,0 +1,46 @@ +package com.mogo.eagle.core.function.hmi.ui.tools + +import android.content.Context +import androidx.lifecycle.LifecycleObserver +import androidx.recyclerview.widget.LinearLayoutManager +import com.mogo.eagle.core.data.deva.ota.OtaUpgradeInfo +import com.mogo.eagle.core.function.hmi.R +import com.mogo.eagle.core.function.hmi.dialog.BaseFloatDialog +import com.mogo.eagle.core.function.hmi.ui.tools.adapter.OTADownloadStatusAdapter +import kotlinx.android.synthetic.main.dialog_ota_download_status.rvDownloadStatus + +/** + * OTA升级下载状态对话框 + */ +class OTADownloadStatusDialog(context: Context) : + BaseFloatDialog(context,TAG), LifecycleObserver { + + companion object { + private const val TAG = "OTADownloadStatusDialog" + } + + private var otaDownloadStatusAdapter: OTADownloadStatusAdapter ?= null + + + init{ + setContentView(R.layout.dialog_ota_download_status) + setCanceledOnTouchOutside(false) + initView() + } + + private fun initView(){ + val linearLayoutManager = LinearLayoutManager(context) + linearLayoutManager.orientation = LinearLayoutManager.VERTICAL + otaDownloadStatusAdapter = OTADownloadStatusAdapter(context) + rvDownloadStatus.adapter = otaDownloadStatusAdapter + rvDownloadStatus.layoutManager = linearLayoutManager + } + + fun notifyDownloadStatus(list: List){ + if(!this.isShowing){ + show() + } + otaDownloadStatusAdapter?.setData(list) + } + +} \ No newline at end of file diff --git a/core/function-impl/mogo-core-function-hmi/src/main/java/com/mogo/eagle/core/function/hmi/ui/tools/OTAUpgradeDialog.kt b/core/function-impl/mogo-core-function-hmi/src/main/java/com/mogo/eagle/core/function/hmi/ui/tools/OTAUpgradeDialog.kt new file mode 100644 index 0000000000..2c61ff5235 --- /dev/null +++ b/core/function-impl/mogo-core-function-hmi/src/main/java/com/mogo/eagle/core/function/hmi/ui/tools/OTAUpgradeDialog.kt @@ -0,0 +1,88 @@ +package com.mogo.eagle.core.function.hmi.ui.tools + +import android.content.Context +import android.os.CountDownTimer +import android.widget.TextView +import androidx.lifecycle.LifecycleObserver +import com.mogo.eagle.core.function.call.autopilot.CallerAutoPilotControlManager +import com.mogo.eagle.core.function.hmi.R +import com.mogo.eagle.core.function.hmi.dialog.BaseFloatDialog +import com.mogo.eagle.core.utilcode.util.ThreadUtils +import com.zhjt.mogo_core_function_devatools.ota.OTAUpgradeConfig +import kotlinx.android.synthetic.main.dialog_ota_upgrade.tv_upgrade_countdown +import kotlinx.android.synthetic.main.dialog_ota_upgrade.tv_upgrade_later +import kotlinx.android.synthetic.main.dialog_ota_upgrade.tv_upgrade_now +import system_master.SsmInfo + +/** + * OTA升级对话框 + */ +class OTAUpgradeDialog(context: Context) : + BaseFloatDialog(context,TAG), LifecycleObserver { + + companion object { + private const val TAG = "OTAUpgradeDialog" + private const val UPGRADE_WAITING_TIME = 300000L //升级确认等待时间 + private const val WAITING_TICK_TIME = 1000L //等待确认间隔时间 + } + + private var clickListener: ClickListener? = null + private var upgradeWaitingTimer: CountDownTimer ?= null //等待升级确认计时器 + + init{ + setContentView(R.layout.dialog_ota_upgrade) + setCanceledOnTouchOutside(false) + initView() + } + + private fun initView(){ + //立即升级 + tv_upgrade_now.setOnClickListener { + CallerAutoPilotControlManager.sendSsmFuncOtaDownloadResponse(OTAUpgradeConfig.otaToken,SsmInfo.IfUpgrade.IMMEDIATELY) + dismiss() + } + //稍后升级 + tv_upgrade_later.setOnClickListener { + CallerAutoPilotControlManager.sendSsmFuncOtaDownloadResponse(OTAUpgradeConfig.otaToken,SsmInfo.IfUpgrade.DELAY) + dismiss() + } + upgradeWaitingTimer = object: CountDownTimer(UPGRADE_WAITING_TIME,WAITING_TICK_TIME){ + override fun onTick(millisUntilFinished: Long) { + ThreadUtils.runOnUiThread { + tv_upgrade_countdown.text = millisUntilFinished.toInt().toString() + } + } + + override fun onFinish() { + //立即升级 + CallerAutoPilotControlManager.sendSsmFuncOtaDownloadResponse(OTAUpgradeConfig.otaToken,SsmInfo.IfUpgrade.IMMEDIATELY) + ThreadUtils.runOnUiThread { + dismiss() + } + } + + } + upgradeWaitingTimer?.start() + } + + fun setClickListener(clickListener: ClickListener) { + this.clickListener = clickListener + } + + interface ClickListener{ + //立即升级 + fun upgradeNow() + //稍后升级 + fun upgradeLater() + } + + override fun onAttachedToWindow() { + super.onAttachedToWindow() + } + + override fun onDetachedFromWindow() { + super.onDetachedFromWindow() + upgradeWaitingTimer?.cancel() + } + +} \ No newline at end of file diff --git a/core/function-impl/mogo-core-function-hmi/src/main/java/com/mogo/eagle/core/function/hmi/ui/tools/OTAUpgradeTipView.kt b/core/function-impl/mogo-core-function-hmi/src/main/java/com/mogo/eagle/core/function/hmi/ui/tools/OTAUpgradeTipView.kt new file mode 100644 index 0000000000..fb4a06670e --- /dev/null +++ b/core/function-impl/mogo-core-function-hmi/src/main/java/com/mogo/eagle/core/function/hmi/ui/tools/OTAUpgradeTipView.kt @@ -0,0 +1,57 @@ +package com.mogo.eagle.core.function.hmi.ui.tools + +import android.content.Context +import android.util.AttributeSet +import android.view.LayoutInflater +import android.view.View +import androidx.constraintlayout.widget.ConstraintLayout +import com.mogo.eagle.core.function.call.hmi.CallerHmiManager +import com.mogo.eagle.core.function.hmi.R +import kotlinx.android.synthetic.main.view_ota_upgrade_tip.view.btn_upgrade + +/** + * OTA升级任务标记提示 + */ +class OTAUpgradeTipView @JvmOverloads constructor( + context: Context, + attrs: AttributeSet? = null, + defStyleAttr: Int = 0 +) : ConstraintLayout(context, attrs, defStyleAttr){ + + companion object { + private const val TAG = "OTAUpgradeTipView" + } + + init { + LayoutInflater.from(context).inflate(R.layout.view_ota_upgrade_tip, this, true) + initView() + } + + private fun initView(){ + btn_upgrade.setOnClickListener { + //打开升级弹窗 + CallerHmiManager.showOTAUpgradeDialog() + } + } + + /** + * 设置视图是否可见 + * @param visible 是否可见 + */ + fun setDisplayStatus(visible: Boolean){ + if(visible){ + if(this@OTAUpgradeTipView.visibility == View.VISIBLE){ + return + }else{ + this@OTAUpgradeTipView.visibility = View.VISIBLE + } + }else{ + if(this@OTAUpgradeTipView.visibility != View.VISIBLE){ + return + }else{ + this@OTAUpgradeTipView.visibility = View.GONE + } + } + } + +} \ No newline at end of file diff --git a/core/function-impl/mogo-core-function-hmi/src/main/java/com/mogo/eagle/core/function/hmi/ui/tools/adapter/OTADownloadStatusAdapter.kt b/core/function-impl/mogo-core-function-hmi/src/main/java/com/mogo/eagle/core/function/hmi/ui/tools/adapter/OTADownloadStatusAdapter.kt new file mode 100644 index 0000000000..308f67eab8 --- /dev/null +++ b/core/function-impl/mogo-core-function-hmi/src/main/java/com/mogo/eagle/core/function/hmi/ui/tools/adapter/OTADownloadStatusAdapter.kt @@ -0,0 +1,63 @@ +package com.mogo.eagle.core.function.hmi.ui.tools.adapter + +import android.content.Context +import android.view.LayoutInflater +import android.view.View +import android.view.ViewGroup +import android.widget.ProgressBar +import android.widget.TextView +import androidx.recyclerview.widget.RecyclerView +import com.mogo.eagle.core.data.deva.ota.OtaUpgradeInfo +import com.mogo.eagle.core.function.hmi.R + +/** + * OTA升级下载状态适配器 + */ +class OTADownloadStatusAdapter(private val context: Context): RecyclerView.Adapter() { + + private var data: List ?= null + + fun setData(list: List){ + this.data = list + notifyDataSetChanged() + } + + override fun onCreateViewHolder(parent: ViewGroup, viewType: Int): DownloadStatusHolder { + val view = LayoutInflater.from(parent.context) + .inflate(R.layout.item_ota_download_status, parent, false) + return DownloadStatusHolder(view) + } + + override fun onBindViewHolder(holder: DownloadStatusHolder, position: Int) { + data?.let { + val otaUpgradeInfo = it[position] + holder.pbDownloadProgress.progress = (otaUpgradeInfo.cur_size*100/otaUpgradeInfo.total_size).toInt() +// 0:默认(未开始), 1:下载中, 2:下载完成, 3:升级完成, 4:升级失败 + holder.tvDownloadStatus.text = when (otaUpgradeInfo.status) { + 1 -> { + "下载中" + } + 2 -> { + "下载完成" + } + 3 -> { + "升级完成" + } + 4 -> { + "升级失败" + } + else -> { + "默认(未开始)" + } + } + } + } + + override fun getItemCount() = data?.size ?: 0 + + class DownloadStatusHolder(itemView: View) : RecyclerView.ViewHolder(itemView){ + var pbDownloadProgress: ProgressBar = itemView.findViewById(R.id.pbDownloadProgress) + var tvDownloadStatus: TextView = itemView.findViewById(R.id.tvDownloadStatus) + } + +} \ No newline at end of file diff --git a/core/function-impl/mogo-core-function-hmi/src/main/java/com/mogo/eagle/core/function/hmi/ui/widget/ColdStartView.kt b/core/function-impl/mogo-core-function-hmi/src/main/java/com/mogo/eagle/core/function/hmi/ui/widget/ColdStartView.kt index bcae1b7776..f321dc2ba4 100644 --- a/core/function-impl/mogo-core-function-hmi/src/main/java/com/mogo/eagle/core/function/hmi/ui/widget/ColdStartView.kt +++ b/core/function-impl/mogo-core-function-hmi/src/main/java/com/mogo/eagle/core/function/hmi/ui/widget/ColdStartView.kt @@ -300,6 +300,14 @@ class ColdStartView @JvmOverloads constructor( Log.i(TAG,"节点自上报冷启动状态="+it.eventStatus) Log.i(TAG,"旧冷启动状态="+it.processStatus) Log.i(TAG,"旧冷启动超时原因="+it.processTimeoutReason) + Log.i(TAG,"硬件故障Node数量="+it.hardwareNodeCount) + it.hardwareNodeList.forEach {startFlt-> + Log.i(TAG,"硬件故障 startFlt.fltId="+ startFlt.fltId) + } + Log.i(TAG,"其他故障数量="+it.otherFltsCount) + it.otherFltsList.forEach {startFlt-> + Log.i(TAG,"其他故障 startFlt.fltId="+startFlt.fltId) + } ThreadUtils.runOnUiThread { tvColdStartContent.text = getColdStartEventStatus(it.eventStatus) if(it.eventStatus == SsmInfo.CSState.COLD_START_READY){ @@ -327,6 +335,12 @@ class ColdStartView @JvmOverloads constructor( val nodeInfo = ColdStartNodeInfo(node.nodeName,node.eventCode,getColdStartNodeStatus(node.status),node.desc) nodeList.add(nodeInfo) } + + Log.i(TAG,"nodeName="+node.nodeName+" status="+node.status+" desc="+node.desc+" eventCode="+node.eventCode) + Log.i(TAG,"node.haveFltCount="+node.haveFltCount) + node.haveFltList.forEach {str-> + Log.i(TAG, "故障码=$str") + } } it.nodeList.forEach {node-> if(node.status == SsmInfo.NodeStatus.NODE_STARTING){ diff --git a/core/function-impl/mogo-core-function-hmi/src/main/res/layout/dialog_ota_download_status.xml b/core/function-impl/mogo-core-function-hmi/src/main/res/layout/dialog_ota_download_status.xml new file mode 100644 index 0000000000..2c85291729 --- /dev/null +++ b/core/function-impl/mogo-core-function-hmi/src/main/res/layout/dialog_ota_download_status.xml @@ -0,0 +1,16 @@ + + + + + + \ No newline at end of file diff --git a/core/function-impl/mogo-core-function-hmi/src/main/res/layout/dialog_ota_upgrade.xml b/core/function-impl/mogo-core-function-hmi/src/main/res/layout/dialog_ota_upgrade.xml new file mode 100644 index 0000000000..c00170b3db --- /dev/null +++ b/core/function-impl/mogo-core-function-hmi/src/main/res/layout/dialog_ota_upgrade.xml @@ -0,0 +1,96 @@ + + + + + + + + + + + + + + + + \ No newline at end of file diff --git a/core/function-impl/mogo-core-function-hmi/src/main/res/layout/view_map_container.xml b/core/function-impl/mogo-core-function-hmi/src/main/res/layout/view_map_container.xml index 4ffae3c307..cd59a5e469 100644 --- a/core/function-impl/mogo-core-function-hmi/src/main/res/layout/view_map_container.xml +++ b/core/function-impl/mogo-core-function-hmi/src/main/res/layout/view_map_container.xml @@ -141,6 +141,15 @@ app:layout_constraintRight_toRightOf="parent" app:layout_constraintTop_toTopOf="parent" /> + + + + +