ソースを参照

Merge branch 'master' of http://111.33.136.149:3000/adc_pilot/modularization

fujiankuan 4 年 前
コミット
cf1d48ebb1

+ 1 - 1
src/driver/driver_cloud_grpc_client_BS/VehicleControl_service.proto

@@ -13,7 +13,7 @@ service VehicleControl {
   // 车辆远程控制
   rpc vehicleControl (Empty) returns (ControlReply) {}
   // 路径生成
-  rpc UploadMap(Empty) returns(UploadMapReply) {}
+  rpc UploadMap(Empty) returns(UploadMapReply) {}  //this service may change into uploadMap in future
   // 控制模式改变
   rpc changeCtrlMode(Empty) returns(CtrlModeReply) {}
 }

+ 2 - 2
src/driver/driver_cloud_grpc_client_BS/VehiclePatrol.proto

@@ -37,5 +37,5 @@ message PatrolRequest{
     string plateNumber = 18;
 }
 
-message Empty{
-}
+message Empty{ //this message need a id in future
+}

+ 1 - 1
src/driver/driver_cloud_grpc_client_BS/VehicleUpload_service.proto

@@ -10,7 +10,7 @@ option java_outer_classname = "VehicleService";
 import "VehicleUpload.proto";
 
 service DataExchange {
-  rpc uploadVehicleOInfo (UplinkRequest) returns (ResponseMessage) {}
+  rpc uploadVehicleInfo (UplinkRequest) returns (ResponseMessage) {}
   
   rpc uploadPath (UploadPathRequest) returns (Empty) {}
 }

+ 6 - 2
src/driver/driver_cloud_grpc_client_BS/driver_cloud_grpc_client_BS.pro

@@ -30,7 +30,9 @@ SOURCES += \
         VehicleUpload_service.grpc.pb.cc \
         VehicleUpload_service.pb.cc \
         main.cpp \
-        grpcclient.cpp
+        vehicle_control.cpp \
+        vehicle_patrol.cpp \
+        vehicle_upload.cpp
 
 # Default rules for deployment.
 qnx: target.path = /tmp/$${TARGET}/bin
@@ -72,6 +74,8 @@ HEADERS += \
         VehicleUpload.pb.h \
         VehicleUpload_service.grpc.pb.h \
         VehicleUpload_service.pb.h \
-        grpcclient.h
+        vehicle_control.h \
+        vehicle_patrol.h \
+        vehicle_upload.h
 
 #before compile in ubuntu20.04 : sudo apt install libyaml-cpp-dev libgrpc++-dev

+ 5 - 4
src/driver/driver_cloud_grpc_client_BS/driver_cloud_grpc_client_BS.yaml

@@ -3,9 +3,10 @@ upload_port : 10591
 patrol_port : 10592
 control_port : 20591
 
-uploadinterval : 100 //ms
-patrolinterval : 100
+uploadinterval : 500 //ms
+patrolinterval : 500
 controlinterval : 100
+uploadmapinterval : 1000
 
-ID : 1
-
+id : 1234567890123456789H
+plateNumber : 津A123456

+ 94 - 396
src/driver/driver_cloud_grpc_client_BS/main.cpp

@@ -1,309 +1,78 @@
 #include <QCoreApplication>
 
-#include "grpcclient.h"
-
 #include "ivversion.h"
 
-/*
 #include <yaml-cpp/yaml.h>
-
-#include <QDateTime>
-
-#include <iostream>
-
-#include <vector>
-
-#include <memory>
-
-#include <QMutex>
-
-#include <thread>
-
-#include "modulecomm.h"
-
-#include "cloud.pb.h"
-
-#include <iostream>
-#include <memory>
-#include <string>
-
-#include <grpcpp/grpcpp.h>
-
-#include "uploadmsg.grpc.pb.h"
-
-
-using grpc::Channel;
-using grpc::ClientContext;
-using grpc::Status;
-
-
-void test()
+#include "vehicle_upload.h"
+#include "vehicle_control.h"
+#include "vehicle_patrol.h"
+
+#include <QFile>
+#include <QString>
+#include <QStringList>
+#include <QThread>
+
+std::string gstrserverip =  "139.9.235.66";//"123.57.212.138";
+std::string gstruploadPort = "10591";//"9000";
+std::string gstrpatrolPort = "10592";//"9000";
+std::string gstrcontrolPort = "20591";//"9000";
+std::string gstruploadInterval = "500";
+std::string gstrpatrolInterval = "500";
+std::string gstrcontrolInterval = "100";
+std::string gstruploadMapInterval = "500";
+std::string gstrid = "1234567890123456789H";
+std::string gstrplateNumber = "津A123456";
+
+class mainloop : public QThread
 {
-    std::string target_str = "0.0.0.0:50051";
-
-    auto cargs = grpc::ChannelArguments();
-    cargs.SetMaxReceiveMessageSize(1024 * 1024 * 1024); // 1 GB
-    cargs.SetMaxSendMessageSize(1024 * 1024 * 1024);
-
-    std::shared_ptr<Channel> channel = grpc::CreateCustomChannel(
-             target_str, grpc::InsecureChannelCredentials(),cargs);
-
-    std::unique_ptr<iv::Upload::Stub> stub_ = iv::Upload::NewStub(channel);
-
-
-    iv::UploadRequest request;
-
-
-
-    // Container for the data we expect from the server.
-    iv::UploadReply reply;
-
-    int nid = 0;
-
-    nid = 1;
-
-    while(1)
-    {
-
-
-
-
-        // Context for the client. It could be used to convey extra information to
-        // the server and/or tweak certain RPC behaviors.
-
-
-        ClientContext context ;
-        std::this_thread::sleep_for(std::chrono::milliseconds(100));
-        qint64 time1 = QDateTime::currentMSecsSinceEpoch();
-
-        request.set_id(nid);
-        request.set_ntime(time1);
-        nid++;
-        // The actual RPC.
-        Status status = stub_->upload(&context, request, &reply);
-        if (status.ok()) {
-            std::cout<<nid<<" upload successfully"<<std::endl;
-//            qint64 time2;
-
-//            memcpy(&time2,reply.data().data(),8);
-//            qint64 time3 = QDateTime::currentMSecsSinceEpoch();
-//            std::cout<<"reply data size is "<<reply.data().size()<<std::endl;
-//            std::cout<<" latency is "<<(time2 - time1)<<" 2 is "<<(time3 - time2)<<std::endl;
-//          return reply.message();
-        } else {
-          std::cout << status.error_code() << ": " << status.error_message()
-                    << std::endl;
-          std::cout<<"RPC failed"<<std::endl;
-          std::this_thread::sleep_for(std::chrono::milliseconds(900));
-
-//          delete pcontext;
-//          pcontext = new ClientContext;
-
-//          channel = grpc::CreateCustomChannel(
-//                   target_str, grpc::InsecureChannelCredentials(),cargs);
-
-//          stub_ = iv::Upload::NewStub(channel);
-        }
-    }
-}
-
-std::string gstrserverip =  "0.0.0.0";//"123.57.212.138";
-std::string gstrserverport = "50051";//"9000";
-std::string gstruploadinterval = "1000";
-void * gpa;
-QMutex gMutexMsg;
-std::thread * guploadthread;
-
-
-
-
-std::vector<iv::msgunit> mvectormsgunit;
-
-std::vector<iv::msgunit> mvectorctrlmsgunit;
-
-
-std::string gstrVIN = "AAAAAAAAAAAAAAAAA";
-std::string gstrqueryMD5 = "5d41402abc4b2a76b9719d911017c591";//"5d41402abc4b2a76b9719d911017c592";
-std::string gstrctrlMD5 = "5d41402abc4b2a76b9719d911017c591";
-
-
-
-int gindex = 0;
-
-void ListenData(const char * strdata,const unsigned int nSize,const unsigned int index,const QDateTime * dt,const char * strmemname)
+//    Q_OBJECT
+public:
+    mainloop(VehicleControlClient *pCC,DataExchangeClient *pUC);
+    void run();
+private:
+    VehicleControlClient *pControlClient;
+    DataExchangeClient *pUploadClient;
+};
+
+mainloop::mainloop(VehicleControlClient *pCC,DataExchangeClient *pUC)
 {
-
-    int nsize = mvectormsgunit.size();
-    int i;
-    for(i=0;i<nsize;i++)
-    {
-        if(strncmp(strmemname,mvectormsgunit[i].mstrmsgname,255) == 0)
-        {
-            gMutexMsg.lock();
-            char * strtem = new char[nSize];
-            memcpy(strtem,strdata,nSize);
-            mvectormsgunit[i].mpstrmsgdata.reset(strtem);
-            mvectormsgunit[i].mndatasize = nSize;
-            mvectormsgunit[i].mbRefresh = true;
-            gMutexMsg.unlock();
-            break;
-        }
-    }
+    pControlClient = pCC;
+    pUploadClient = pUC;
 }
 
-
-void sharectrlmsg(iv::cloud::cloudmsg * pxmsg)
+void mainloop::run()
 {
-    int i;
-    int nsize = pxmsg->xclouddata_size();
-    for(i=0;i<nsize;i++)
-    {
-        int j;
-        int nquerysize = mvectorctrlmsgunit.size();
-        for(j=0;j<nquerysize;j++)
+    while (1) {
+        msleep(100);
+//        if(pControlClient->get_isNeedMap() == true)
         {
-            if(strncmp(pxmsg->xclouddata(i).msgname().data(), mvectorctrlmsgunit[j].mstrmsgname,255) == 0)
+            std::cout<<"patrol path calculating"<<std::endl;
+            QFile mapfile("/home/samuel/Documents/path1.txt");
+            QVector<org::jeecg::defsDetails::grpc::MapPoint> somePoints;
+            if(mapfile.open(QIODevice::ReadOnly | QIODevice::Text))
             {
- //               qDebug("size is %d ",pxmsg->xclouddata(i).data().size());
-                iv::modulecomm::ModuleSendMsg(mvectorctrlmsgunit[j].mpa,pxmsg->xclouddata(i).data().data(),pxmsg->xclouddata(i).data().size());
-                break;
-            }
-        }
-    }
-}
-
-
-void threadupload()
-{
-    int nsize = mvectormsgunit.size();
-    int i;
-
-    int ninterval = atoi(gstruploadinterval.data());
-    if(ninterval<=0)ninterval = 100;
-
-    QTime xTime;
-    xTime.start();
-    int nlastsend = xTime.elapsed();
-
-    std::string target_str = gstrserverip+":";
-    target_str = target_str + gstrserverport ;//std::to_string()
-    auto cargs = grpc::ChannelArguments();
-    cargs.SetMaxReceiveMessageSize(1024 * 1024 * 1024); // 1 GB
-    cargs.SetMaxSendMessageSize(1024 * 1024 * 1024);
-
-    std::shared_ptr<Channel> channel = grpc::CreateCustomChannel(
-             target_str, grpc::InsecureChannelCredentials(),cargs);
-
-    std::unique_ptr<iv::Upload::Stub> stub_ = iv::Upload::NewStub(channel);
-
-
-    iv::UploadRequest request;
-
-    int nid = 0;
-
-    // Container for the data we expect from the server.
-    iv::UploadReply reply;
-
-    gpr_timespec timespec;
-      timespec.tv_sec = 30;//设置阻塞时间为2秒
-      timespec.tv_nsec = 0;
-      timespec.clock_type = GPR_TIMESPAN;
-
- //   ClientContext context;
-
-
-
-    while(true)
-    {
-        std::this_thread::sleep_for(std::chrono::milliseconds(1));
-        if((xTime.elapsed()-nlastsend)<ninterval)
-        {
-            continue;
-        }
-
-            bool bImportant = false;
-            int nkeeptime = 0;
-            iv::cloud::cloudmsg xmsg;
-            xmsg.set_xtime(QDateTime::currentMSecsSinceEpoch());
-            gMutexMsg.lock();
-            for(i=0;i<nsize;i++)
-            {
-                if(mvectormsgunit[i].mbRefresh)
+                while(!mapfile.atEnd())
                 {
-                    mvectormsgunit[i].mbRefresh = false;
-                    if(mvectormsgunit[i].mbImportant)
-                    {
-                        bImportant = true;
-                    }
-                    if(mvectormsgunit[i].mnkeeptime > nkeeptime)
-                    {
-                        nkeeptime = mvectormsgunit[i].mnkeeptime;
-                    }
-                    iv::cloud::cloudunit xcloudunit;
-                    xcloudunit.set_msgname(mvectormsgunit[i].mstrmsgname);
-                    xcloudunit.set_data(mvectormsgunit[i].mpstrmsgdata.get(),mvectormsgunit[i].mndatasize);
-                    iv::cloud::cloudunit * pcu = xmsg.add_xclouddata();
-                    pcu->CopyFrom(xcloudunit);
-                }
-
-            }
-            gMutexMsg.unlock();
-
-            int nbytesize = xmsg.ByteSize();
-            char * strbuf = new char[nbytesize];
-            std::shared_ptr<char> pstrbuf;
-            pstrbuf.reset(strbuf);
-            if(xmsg.SerializeToArray(strbuf,nbytesize))
-            {
-
-                ClientContext context ;
-                context.set_deadline(timespec);
-                qint64 time1 = QDateTime::currentMSecsSinceEpoch();
-
-                request.set_id(nid);
-                request.set_ntime(time1);
-                request.set_strquerymd5(gstrqueryMD5);
-                request.set_strctrlmd5(gstrctrlMD5);
-                request.set_strvin(gstrVIN);
-                request.set_xdata(strbuf,nbytesize);
-                request.set_kepptime(nkeeptime);
-                request.set_bimportant(bImportant);
-                nid++;
-                // The actual RPC.
-                Status status = stub_->upload(&context, request, &reply);
-                if (status.ok()) {
-                    std::cout<<nid<<" upload successfully"<<std::endl;
-                    if(reply.nres() == 1)
-                    {
-                        iv::cloud::cloudmsg xmsg;
-                        if(xmsg.ParseFromArray(reply.xdata().data(),reply.xdata().size()))
-                        {
-                            sharectrlmsg(&xmsg);
-                        }
-                    }
-                } else {
-                  std::cout << status.error_code() << ": " << status.error_message()
-                            << std::endl;
-                  std::cout<<"RPC failed"<<std::endl;
-                  if(status.error_code() == 4)
-                  {
-                      std::cout<<" RPC Exceed Time, Create New stub_"<<std::endl;
-                      channel = grpc::CreateCustomChannel(
-                               target_str, grpc::InsecureChannelCredentials(),cargs);
-
-                      stub_ = iv::Upload::NewStub(channel);
-                  }
-                  std::this_thread::sleep_for(std::chrono::milliseconds(900));
-
+                    QByteArray line = mapfile.readLine();
+                    QString map_str(line);
+                    QStringList oneline = map_str.split(",");
+                    org::jeecg::defsDetails::grpc::MapPoint onePoint;
+                    onePoint.set_index(oneline.at(0).toInt());
+                    onePoint.mutable_mappoint()->set_longitude(oneline.at(1).toDouble());
+                    onePoint.mutable_mappoint()->set_latitude(oneline.at(2).toDouble());
+                    onePoint.mutable_mappoint()->set_height(oneline.at(3).toDouble());
+                    somePoints.append(onePoint);
                 }
-
             }
-            nlastsend = xTime.elapsed();
-
+//            pUploadClient->updatePath(pControlClient->get_patrolPathID(),somePoints);
+            pUploadClient->updatePath("testpath1",somePoints);
+            pUploadClient->uploadPath();
+            pControlClient->set_isNeedMap(false);
+        }
+//        std::cout<<"thread running"<<std::endl;
     }
 }
 
-
 void dec_yaml(const char * stryamlpath)
 {
 
@@ -312,161 +81,90 @@ void dec_yaml(const char * stryamlpath)
     {
         config = YAML::LoadFile(stryamlpath);
     }
-    catch(YAML::BadFile e)
+    catch(...)
     {
-        qDebug("load error.");
+        qDebug("yaml file has some unknown code or load fail.");
         return;
     }
 
-    std::vector<std::string> vecmodulename;
-
-
     if(config["server"])
     {
         gstrserverip = config["server"].as<std::string>();
     }
-    if(config["port"])
+    if(config["uploadPort"])
     {
-        gstrserverport = config["port"].as<std::string>();
+        gstruploadPort = config["uploadPort"].as<std::string>();
     }
-    if(config["uploadinterval"])
+    if(config["patrolPort"])
     {
-        gstruploadinterval = config["uploadinterval"].as<std::string>();
+        gstrpatrolPort = config["patrolPort"].as<std::string>();
     }
-
-    if(config["VIN"])
+    if(config["controlPort"])
     {
-        gstrVIN = config["VIN"].as<std::string>();
+        gstrcontrolPort = config["controlPort"].as<std::string>();
     }
-
-    if(config["queryMD5"])
+    if(config["uploadInterval"])
     {
-        gstrqueryMD5 = config["queryMD5"].as<std::string>();
+        gstruploadInterval = config["uploadInterval"].as<std::string>();
     }
-    else
+    if(config["patrolInterval"])
     {
-        return;
+        gstrpatrolInterval = config["patrolInterval"].as<std::string>();
     }
-
-    if(config["ctrlMD5"])
+    if(config["controlinterval"])
     {
-        gstrctrlMD5 = config["ctrlMD5"].as<std::string>();
+        gstrcontrolInterval = config["controlinterval"].as<std::string>();
     }
-
-
-    std::string strmsgname;
-
-    if(config["uploadmessage"])
-    {
-
-        for(YAML::const_iterator it= config["uploadmessage"].begin(); it != config["uploadmessage"].end();++it)
-        {
-            std::string strtitle = it->first.as<std::string>();
-            std::cout<<strtitle<<std::endl;
-
-            if(config["uploadmessage"][strtitle]["msgname"]&&config["uploadmessage"][strtitle]["buffersize"]&&config["uploadmessage"][strtitle]["buffercount"])
-            {
-                iv::msgunit xmu;
-                strmsgname = config["uploadmessage"][strtitle]["msgname"].as<std::string>();
-                strncpy(xmu.mstrmsgname,strmsgname.data(),255);
-                xmu.mnBufferSize = config["uploadmessage"][strtitle]["buffersize"].as<int>();
-                xmu.mnBufferCount = config["uploadmessage"][strtitle]["buffercount"].as<int>();
-                if(config["uploadmessage"][strtitle]["bimportant"])
-                {
-                   std::string strimportant =    config["uploadmessage"][strtitle]["bimportant"].as<std::string>();
-                   if(strimportant == "true")
-                   {
-                       xmu.mbImportant = true;
-                   }
-                }
-                if(config["uploadmessage"][strtitle]["keeptime"])
-                {
-                   std::string strkeep =    config["uploadmessage"][strtitle]["keeptime"].as<std::string>();
-                   xmu.mnkeeptime = atoi(strkeep.data());
-                }
-                mvectormsgunit.push_back(xmu);
-            }
-        }
-    }
-    else
+    if(config["uploadmapinterval"])
     {
-
-
+        gstruploadMapInterval = config["uploadmapinterval"].as<std::string>();
     }
 
-    if(!config["ctrlMD5"])
+    if(config["id"])
     {
-       return;
+        gstrid = config["id"].as<std::string>();
     }
-
-    if(config["ctrlmessage"])
+    if(config["plateNumber"])
     {
-        std::string strnodename = "ctrlmessage";
-        for(YAML::const_iterator it= config[strnodename].begin(); it != config[strnodename].end();++it)
-        {
-            std::string strtitle = it->first.as<std::string>();
-            std::cout<<strtitle<<std::endl;
-
-            if(config[strnodename][strtitle]["msgname"]&&config[strnodename][strtitle]["buffersize"]&&config[strnodename][strtitle]["buffercount"])
-            {
-                iv::msgunit xmu;
-                strmsgname = config[strnodename][strtitle]["msgname"].as<std::string>();
-                strncpy(xmu.mstrmsgname,strmsgname.data(),255);
-                xmu.mnBufferSize = config[strnodename][strtitle]["buffersize"].as<int>();
-                xmu.mnBufferCount = config[strnodename][strtitle]["buffercount"].as<int>();
-                mvectorctrlmsgunit.push_back(xmu);
-            }
-        }
-    }
-    else
-    {
-
+        gstrplateNumber = config["plateNumber"].as<std::string>();
     }
 
     return;
-
 }
 
-
-*/
-
 int main(int argc, char *argv[])
 {
-    showversion("driver_cloud_grpc_client");
+    showversion("driver_cloud_grpc_client_BS");
     QCoreApplication a(argc, argv);
 
- //   std::thread * ptest = new std::thread(test);
-
- //   return a.exec();
-
     char stryamlpath[256];
     if(argc<2)
     {
-        snprintf(stryamlpath,255,"driver_cloud_grpc_client.yaml");
-//        strncpy(stryamlpath,abs_ymlpath,255);
+        snprintf(stryamlpath,255,"driver_cloud_grpc_client_BS.yaml");
     }
     else
     {
         strncpy(stryamlpath,argv[1],255);
     }
-//    dec_yaml(stryamlpath);
+    dec_yaml(stryamlpath);
+
+    std::string control_str = gstrserverip+":";
+    control_str = control_str + gstrcontrolPort ;
+
+    std::string patrol_str = gstrserverip+":";
+    patrol_str = patrol_str + gstrpatrolPort;
+
+    std::string upload_str = gstrserverip+":";
+    upload_str = upload_str + gstruploadPort ;
 
-    grpcclient * pgrpcclient = new grpcclient(stryamlpath);
-    pgrpcclient->start();
+    VehicleControlClient *vehiclecontrol = new VehicleControlClient(grpc::CreateChannel(control_str, grpc::InsecureChannelCredentials()));
 
-//    int i;
-//    for(i=0;i<mvectormsgunit.size();i++)
-//    {
-//        mvectormsgunit[i].mpa = iv::modulecomm::RegisterRecv(mvectormsgunit[i].mstrmsgname,ListenData);
-//    }
+    DataExchangeClient *vehicleupload = new DataExchangeClient(grpc::CreateChannel(upload_str, grpc::InsecureChannelCredentials()));
 
-//    for(i=0;i<mvectorctrlmsgunit.size();i++)
-//    {
-//        mvectorctrlmsgunit[i].mpa = iv::modulecomm::RegisterSend(mvectorctrlmsgunit[i].mstrmsgname,mvectorctrlmsgunit[i].mnBufferSize,
-//                                                                 mvectorctrlmsgunit[i].mnBufferCount);
-//    }
+    VehiclePatrolExceptionClient vehiclepatrol(grpc::CreateChannel(patrol_str, grpc::InsecureChannelCredentials()));
 
-//    guploadthread = new std::thread(threadupload);
+    mainloop loop(vehiclecontrol,vehicleupload);
+    loop.start();
 
     return a.exec();
 }

+ 2 - 2
src/driver/driver_cloud_grpc_client_BS/prototocpp.txt

@@ -1,3 +1,3 @@
-protoc -I . --plugin=protoc-gen-grpc=/home/samuel/grpc/cmake/build/grpc_cpp_plugin --grpc_out=. driver_cloud_grpc_client_BS.proto
+protoc -I . --plugin=protoc-gen-grpc=/home/samuel/grpc/cmake/build/grpc_cpp_plugin --grpc_out=. VehicleUpload.proto VehiclePatrol.proto VehicleControl.proto VehicleUpload_service.proto VehiclePatrol_service.proto VehicleControl_service.proto
 
-protoc -I . --cpp_out=. driver_cloud_grpc_client_BS.proto 
+protoc -I . --cpp_out=. VehicleUpload.proto VehiclePatrol.proto VehicleControl.proto VehicleUpload_service.proto VehiclePatrol_service.proto VehicleControl_service.proto 

+ 201 - 0
src/driver/driver_cloud_grpc_client_BS/vehicle_control.cpp

@@ -0,0 +1,201 @@
+#include "vehicle_control.h"
+
+extern std::string gstrserverip;
+extern std::string gstrcontrolPort;
+extern std::string gstrcontrolInterval;
+extern std::string gstruploadMapInterval;
+extern std::string gstrid;
+extern std::string gstrplateNumber;
+
+using org::jeecg::defsControl::grpc::Empty; ///< other message
+using org::jeecg::defsControl::grpc::GPSPoint;
+using org::jeecg::defsControl::grpc::MapPoint;
+
+using org::jeecg::defsControl::grpc::CtrlMode; ///< other enum
+using org::jeecg::defsControl::grpc::ShiftStatus;
+
+VehicleControlClient::VehicleControlClient(std::shared_ptr<Channel> channel)
+{
+    stub_ = VehicleControl::NewStub(channel);
+
+    controlTimer = new QTimer();
+    connect(controlTimer,SIGNAL(timeout()),this,SLOT(controlTimeout()));
+//    controlTimer->start(std::atoi(gstrcontrolInterval.c_str()));
+
+    uploadMapTimer = new QTimer();
+    connect(uploadMapTimer,SIGNAL(timeout()),this,SLOT(uploadMapTimeout()));
+    uploadMapTimer->start(std::atoi(gstruploadMapInterval.c_str()));
+}
+
+VehicleControlClient::~VehicleControlClient(void)
+{
+    delete controlTimer;
+    delete uploadMapTimer;
+}
+
+std::string VehicleControlClient::vehicleControl(void)
+{
+    // Data we are sending to the server.
+    Empty request;
+    request.set_id(gstrid);
+
+    // Container for the data we expect from the server.
+    ControlReply reply;
+
+    // Context for the client. It could be used to convey extra information to
+    // the server and/or tweak certain RPC behaviors.
+    ClientContext context;
+
+    // The actual RPC.
+    Status status = stub_ -> vehicleControl(&context,request,&reply);
+
+    // Act upon its status.
+    if (status.ok()) {
+        if(reply.id() == gstrid)
+        {
+            shiftCMD = reply.shiftcmd();
+            steeringWheelAngleCMD = reply.steeringwheelanglecmd();
+            throttleCMD = reply.throttlecmd();
+            brakeCMD = reply.brakecmd();
+        }
+        return "vehicleControl RPC successed";
+    } else {
+        std::cout << status.error_code() << ": " << status.error_message()
+                  << std::endl;
+        return "vehicleControl RPC failed";
+    }
+}
+
+std::string VehicleControlClient::uploadMap(void)
+{
+    // Data we are sending to the server.
+    Empty request;
+    request.set_id(gstrid);
+
+    // Container for the data we expect from the server.
+    UploadMapReply reply;
+
+    // Context for the client. It could be used to convey extra information to
+    // the server and/or tweak certain RPC behaviors.
+    ClientContext context;
+
+    // The actual RPC.
+    Status status = stub_ -> UploadMap(&context,request,&reply);
+
+    // Act upon its status.
+    if (status.ok()) {
+        if(reply.id() == gstrid)
+        {
+            std::cout<<reply.id()<<std::endl;
+            isNeedMap = false;
+            patrolPathID = "noPath";
+            POIPoints.clear();
+
+            isNeedMap = reply.isneedmap();
+            std::cout<<reply.isneedmap()<<std::endl;
+            patrolPathID = reply.patrolpathid();
+            std::cout<<reply.patrolpathid()<<std::endl;
+            for(int i = 0;i < reply.mappoints_size();i++)
+            {
+                POIPoints.append(reply.mappoints(i));
+                std::cout<<reply.mappoints(i).index()<<std::endl;
+            }
+        }
+        return "UploadMap RPC successed";
+    } else {
+        std::cout << status.error_code() << ": " << status.error_message()
+                  << std::endl;
+        return "UploadMap RPC failed";
+    }
+}
+
+std::string VehicleControlClient::changeCtrlMode(void)
+{
+    // Data we are sending to the server.
+    Empty request;
+    request.set_id(gstrid);
+
+    // Container for the data we expect from the server.
+    CtrlModeReply reply;
+
+    // Context for the client. It could be used to convey extra information to
+    // the server and/or tweastd::cout<<"shift:"<<shiftCMD<<std::endl;k certain RPC behaviors.
+    ClientContext context;
+
+    // The actual RPC.
+    Status status = stub_ -> changeCtrlMode(&context,request,&reply);
+
+    // Act upon its status.
+    if (status.ok()) {
+        if(reply.id() == gstrid)
+        {
+            modeCMD = reply.modecmd();
+        }
+        return "changeCtrlMode RPC successed";
+    } else {
+        std::cout << status.error_code() << ": " << status.error_message()
+                  << std::endl;
+        return "changeCtrlMode RPC failed";
+    }
+}
+
+void VehicleControlClient::updateControlData(void)
+{
+    std::cout<<"shift:"<<shiftCMD<<std::endl;
+    std::cout<<"steeringWheelAngle:"<<steeringWheelAngleCMD<<std::endl;
+    std::cout<<"throttle:"<<throttleCMD<<std::endl;
+    std::cout<<"brake:"<<brakeCMD<<std::endl;
+}
+
+void VehicleControlClient::updateMapPOIData(void)
+{
+    std::cout<<"isNeedMap:"<<isNeedMap<<std::endl;
+    std::cout<<"patrolPathID:"<<patrolPathID<<std::endl;
+}
+
+void VehicleControlClient::updateCtrolMode(void)
+{
+    std::cout<<"modeCMD:"<<modeCMD<<std::endl;
+}
+
+void VehicleControlClient::controlTimeout(void)
+{
+    std::string reply = changeCtrlMode();
+    std::cout<< reply <<std::endl;
+    updateCtrolMode();
+
+    reply = vehicleControl();
+    std::cout<< reply <<std::endl;
+    if(modeCMD == CtrlMode::CMD_REMOTE)
+    {
+        updateControlData();
+    }
+}
+
+void VehicleControlClient::uploadMapTimeout(void)
+{
+    if(isNeedMap == false)
+    {
+        std::string reply = uploadMap();
+        std::cout<< reply <<std::endl;
+        if(isNeedMap == true)
+        {
+            updateMapPOIData();
+        }
+    }
+}
+
+std::string VehicleControlClient::get_patrolPathID(void)
+{
+    return patrolPathID;
+}
+
+bool VehicleControlClient::get_isNeedMap(void)
+{
+    return isNeedMap;
+}
+
+void VehicleControlClient::set_isNeedMap(bool needMapStatus)
+{
+    isNeedMap = needMapStatus;
+}

+ 67 - 0
src/driver/driver_cloud_grpc_client_BS/vehicle_control.h

@@ -0,0 +1,67 @@
+#ifndef VEHICLE_CONTROL_H
+#define VEHICLE_CONTROL_H
+
+#include <QObject>
+#include <QTimer>
+#include <QVector>
+
+#include <iostream>
+#include <memory>
+#include <string>
+
+#include <grpcpp/grpcpp.h>
+
+#include "VehicleControl_service.grpc.pb.h"
+#include "VehicleControl.grpc.pb.h"
+
+using grpc::Channel;
+using grpc::ClientContext;
+using grpc::Status;
+
+using org::jeecg::defsControl::grpc::VehicleControl; ///< service name
+
+using org::jeecg::defsControl::grpc::ControlReply; ///< rpc fuction parameter and return
+using org::jeecg::defsControl::grpc::UploadMapReply;
+using org::jeecg::defsControl::grpc::CtrlModeReply;
+
+class VehicleControlClient : public QObject{
+    Q_OBJECT
+
+public:
+    VehicleControlClient(std::shared_ptr<Channel> channel);
+
+    ~VehicleControlClient(void);
+
+    std::string vehicleControl(void);
+    std::string uploadMap(void);
+    std::string changeCtrlMode(void);
+    void updateControlData(void);
+    void updateMapPOIData(void);
+    void updateCtrolMode(void);
+    std::string get_patrolPathID(void);
+    bool get_isNeedMap(void);
+    void set_isNeedMap(bool needMapStatus);
+
+private:
+    std::unique_ptr<VehicleControl::Stub> stub_;
+
+    org::jeecg::defsControl::grpc::ShiftStatus shiftCMD;
+    double steeringWheelAngleCMD;
+    double throttleCMD;
+    double brakeCMD;
+
+    bool isNeedMap = false;
+    std::string patrolPathID;
+    QVector<org::jeecg::defsControl::grpc::MapPoint> POIPoints;
+
+    org::jeecg::defsControl::grpc::CtrlMode modeCMD;
+
+    QTimer *controlTimer;
+    QTimer *uploadMapTimer;
+
+private slots:
+    void controlTimeout(void);
+    void uploadMapTimeout(void);
+};
+
+#endif // VEHICLE_CONTROL_H

+ 131 - 0
src/driver/driver_cloud_grpc_client_BS/vehicle_patrol.cpp

@@ -0,0 +1,131 @@
+#include "vehicle_patrol.h"
+#include <QDateTime>
+#include <QFile>
+
+extern std::string gstrserverip;
+extern std::string gstrpatrolPort;
+extern std::string gstrpatrolInterval;
+extern std::string gstrid;
+extern std::string gstrplateNumber;
+
+using org::jeecg::defsPatrol::grpc::Empty;
+using org::jeecg::defsPatrol::grpc::GPSPoint;
+
+VehiclePatrolExceptionClient::VehiclePatrolExceptionClient(std::shared_ptr<Channel> channel)
+{
+    stub_ = VehiclePatrolException::NewStub(channel);
+
+    patrolTimer = new QTimer();
+    connect(patrolTimer,SIGNAL(timeout()),this,SLOT(patrolTimeout()));
+//    patrolTimer->start(std::atoi(gstrpatrolInterval.c_str()));
+}
+
+VehiclePatrolExceptionClient::~VehiclePatrolExceptionClient(void)
+{
+    delete patrolTimer;
+}
+
+std::string VehiclePatrolExceptionClient::uploadVehiclePatrolInfo(void)
+{
+    // Data we are sending to the server.
+    PatrolRequest request;
+    request.set_id(id);
+    request.set_istvr(isTVR);
+    request.set_violationstatus(violationStatus);
+    request.set_vehiclelicensenumber(vehicleLicenseNumber);
+    request.set_violationimage(violationImage.data(),violationImage.size());
+    request.mutable_violationposition()->CopyFrom(violationPosition);
+
+    request.set_isfsm(isFSM);
+    request.set_firestatus(fireStatus);
+    request.set_fireimage(fireImage.data(),fireImage.size());
+    request.set_firetime(fireTime);
+    request.mutable_fireposition()->CopyFrom(firePosition);
+
+    request.set_istsgm(isTSGM);
+    request.set_gatestatus(gateStatus);
+    request.set_gateimage(gateImage.data(),gateImage.size());
+    request.set_gatetime(gateTime);
+    request.mutable_gateposition()->CopyFrom(gatePosition);
+
+    request.set_platenumber(plateNumber);
+
+    // Container for the data we expect from the server.
+    Empty reply;
+
+    // Context for the client. It could be used to convey extra information to
+    // the server and/or tweak certain RPC behaviors.
+    ClientContext context;
+
+    // The actual RPC.
+    Status status = stub_ -> uploadVehiclePatrolInfo(&context,request,&reply);
+
+    // Act upon its status.
+    if (status.ok()) {
+
+        return "uploadVehiclePatrolInfo RPC successed";
+    } else {
+        std::cout << status.error_code() << ": " << status.error_message()
+                  << std::endl;
+        return "uploadVehiclePatrolInfo RPC failed";
+    }
+}
+
+void VehiclePatrolExceptionClient::updatePatrolData(void)
+{
+    id = gstrid;
+    isTVR = true;
+    violationStatus = 2;
+    vehicleLicenseNumber = "津B654321";
+
+//    QFile xFile;
+//    xFile.setFileName("/home/samuel/Pictures/123.jpg");
+//    if(xFile.open(QIODevice::ReadOnly))
+//    {
+//        violationImage = xFile.readAll();
+//    }
+//    xFile.close();
+
+    violationTime = QDateTime::currentMSecsSinceEpoch();
+    violationPosition.set_height(0.1);
+    violationPosition.set_latitude(39.0666552);
+    violationPosition.set_longitude(117.3542963);
+
+    isFSM = true;
+    fireStatus = 1;
+
+//    xFile.setFileName("/home/samuel/Pictures/123.jpg");
+//    if(xFile.open(QIODevice::ReadOnly))
+//    {
+//        fireImage = xFile.readAll();
+//    }
+//    xFile.close();
+
+    fireTime = QDateTime::currentMSecsSinceEpoch();
+    firePosition.set_height(0.1);
+    firePosition.set_latitude(39.0667552);
+    firePosition.set_longitude(117.3542963);
+
+    isTSGM = true;
+    gateStatus = 2;
+
+//    xFile.setFileName("/home/samuel/Pictures/123.jpg");
+//    if(xFile.open(QIODevice::ReadOnly))
+//    {
+//        gateImage = xFile.readAll();
+//    }
+//    xFile.close();
+
+    gateTime = QDateTime::currentMSecsSinceEpoch();
+    gatePosition.set_height(0.1);
+    gatePosition.set_latitude(39.0665552);
+    gatePosition.set_longitude(117.3542963);
+
+    plateNumber = gstrplateNumber;
+}
+
+void VehiclePatrolExceptionClient::patrolTimeout(void)
+{
+    updatePatrolData();
+    uploadVehiclePatrolInfo();
+}

+ 68 - 0
src/driver/driver_cloud_grpc_client_BS/vehicle_patrol.h

@@ -0,0 +1,68 @@
+#ifndef VEHICLE_PATROL_H
+#define VEHICLE_PATROL_H
+
+#include <QObject>
+#include <QTimer>
+#include <QVector>
+
+#include <iostream>
+#include <memory>
+#include <string>
+
+#include <grpcpp/grpcpp.h>
+
+#include "VehiclePatrol_service.grpc.pb.h"
+#include "VehiclePatrol.grpc.pb.h"
+
+using grpc::Channel;
+using grpc::ClientContext;
+using grpc::Status;
+
+using org::jeecg::defsPatrol::grpc::VehiclePatrolException; ///< service name
+
+using org::jeecg::defsPatrol::grpc::PatrolRequest;
+
+class VehiclePatrolExceptionClient : public QObject{
+    Q_OBJECT
+
+public:
+    VehiclePatrolExceptionClient(std::shared_ptr<Channel> channel);
+
+    ~VehiclePatrolExceptionClient(void);
+
+    std::string uploadVehiclePatrolInfo(void);
+    void updatePatrolData(void);
+
+private:
+    std::unique_ptr<VehiclePatrolException::Stub> stub_;
+
+    std::string id;
+
+    bool isTVR; //Traffic Violation Recognition
+    int32_t violationStatus; //0 no violation 1 overspeed 2 illegal parking 3 direction wrong 4 run the red light
+    std::string vehicleLicenseNumber;
+    QByteArray violationImage;
+    uint64_t violationTime; //time when get violationImage
+    org::jeecg::defsPatrol::grpc::GPSPoint violationPosition; //positon when get violationImage
+
+    bool isFSM; //Fire and Smoke Monitor
+    int32_t fireStatus; //0 no fire 1 has fire
+    QByteArray fireImage;
+    uint64_t fireTime; //time when get fireImage
+    org::jeecg::defsPatrol::grpc::GPSPoint firePosition; //positon when get fireImage
+
+    bool isTSGM; //Turn Stile Gate Monitor
+    int32_t gateStatus; //0 no gate 1 gate close 2 gate open
+    QByteArray gateImage;
+    uint64_t gateTime; //time when get gateImage
+    org::jeecg::defsPatrol::grpc::GPSPoint gatePosition; //positon when get gateImage
+
+    std::string plateNumber;
+
+    QTimer *patrolTimer;
+
+private slots:
+    void patrolTimeout(void);
+};
+
+#endif // VEHICLE_PATROL_H

+ 207 - 0
src/driver/driver_cloud_grpc_client_BS/vehicle_upload.cpp

@@ -0,0 +1,207 @@
+#include "vehicle_upload.h"
+#include <QDateTime>
+#include <QFile>
+
+extern std::string gstrserverip;
+extern std::string gstruploadPort;
+extern std::string gstruploadInterval;
+extern std::string gstrid;
+extern std::string gstrplateNumber;
+
+
+using org::jeecg::defsDetails::grpc::Empty; ///< other message
+using org::jeecg::defsDetails::grpc::GPSPoint;
+using org::jeecg::defsDetails::grpc::MapPoint;
+
+using org::jeecg::defsDetails::grpc::ShiftStatus; ///< other enum
+using org::jeecg::defsDetails::grpc::CtrlMode;
+
+DataExchangeClient::DataExchangeClient(std::shared_ptr<Channel> channel)
+{
+    stub_ = DataExchange::NewStub(channel);
+
+    uploadTimer = new QTimer();
+    connect(uploadTimer,SIGNAL(timeout()),this,SLOT(uploadTimeout()));
+    uploadTimer->start(std::atoi(gstruploadInterval.c_str()));
+}
+
+DataExchangeClient::~DataExchangeClient(void)
+{
+    delete uploadTimer;
+}
+
+std::string DataExchangeClient::uploadVehicleInfo(void)
+{
+
+    // Data we are sending to the server.
+    UplinkRequest request;
+    request.set_id(id);
+    request.set_timestamp(timeStamp);
+    request.set_soc(SOC);
+    request.set_statusfeedback(statusFeedback);
+    request.set_mileage(mileage);
+    request.set_speed(speed);
+    request.set_shiftfeedback(shiftFeedback);
+    request.set_steeringwheelanglefeedback(steeringWheelAngleFeedback);
+    request.set_throttlefeedback(throttleFeedback);
+    request.set_brakefeedback(brakeFeedback);
+    request.set_gpsrtkstatus(GPSRTKStatus);
+    request.mutable_positionfeedback()->CopyFrom(positionFeedback);
+    request.set_pitch(pitch);
+    request.set_roll(roll);
+    request.set_heading(heading);
+    request.set_cameraimagefront(cameraImageFront.data(),cameraImageFront.size());
+    request.set_cameraimagerear(cameraImageRear.data(),cameraImageRear.size());
+    request.set_cameraimageleft(cameraImageLeft.data(),cameraImageLeft.size());
+    request.set_cameraimageright(cameraImageRight.data(),cameraImageRight.size());
+    request.set_sensorstatusgpsimu(sensorStatusGPSIMU);
+    request.set_sensorstatuslidar(sensorStatusLidar);
+    request.set_sensorstatusradar(sensorStatusRadar);
+    request.set_sensorstatuscamfront(sensorStatusCamFront);
+    request.set_sensorstatuscamrear(sensorStatusCamRear);
+    request.set_sensorstatuscamleft(sensorStatusCamLeft);
+    request.set_sensorstatuscamright(sensorStatusCamRight);
+    request.set_isarrived(isArrived);
+    request.set_platenumber(plateNumber);
+    request.set_modefeedback(modeFeedback);
+
+    // Container for the data we expect from the server.
+    ResponseMessage reply;
+
+    // Context for the client. It could be used to convey extra information to
+    // the server and/or tweak certain RPC behaviors.
+    ClientContext context;
+
+    // The actual RPC.
+    Status status = stub_ -> uploadVehicleInfo(&context, request, &reply);
+
+    // Act upon its status.
+    if (status.ok()) {
+        destinationPosition.CopyFrom(reply.destinationposition());
+//        std::cout<<"lat:"<<destinationPosition.latitude()<<"lon:"<<destinationPosition.longitude()<<"height:"<<destinationPosition.height()<<std::endl;
+        return "uploadVehicleInfo RPC successed";
+    } else {
+        std::cout << status.error_code() << ": " << status.error_message()
+                  << std::endl;
+        return "uploadVehicleInfo RPC failed";
+    }
+}
+
+std::string DataExchangeClient::uploadPath(void)
+{
+    // Data we are sending to the server.
+    UploadPathRequest request;
+    request.set_id(id);
+    request.set_patrolpathid(patrolPathID);
+    for(int i = 0;i < pathPoints.size();i++)
+    {
+        request.add_pathpoints();
+        request.mutable_pathpoints(i)->operator =(pathPoints.at(i));
+    }
+
+    // Container for the data we expect from the server.
+    Empty reply;
+
+    // Context for the client. It could be used to convey extra information to
+    // the server and/or tweak certain RPC behaviors.
+    ClientContext context;
+
+    // The actual RPC.
+    Status status = stub_ -> uploadPath(&context,request,&reply);
+
+    // Act upon its status.
+    if (status.ok()) {
+        if(reply.id() == gstrid)
+        {
+            std::cout<<"Path uploaded by car id:"<<reply.id()<<std::endl;
+        }
+        return "uploadPath RPC successed";
+    } else {
+        std::cout << status.error_code() << ": " << status.error_message()
+                  << std::endl;
+        return "uploadPath RPC failed";
+    }
+}
+
+void DataExchangeClient::updateData(void)
+{
+    id = gstrid;
+    timeStamp = QDateTime::currentMSecsSinceEpoch();
+    SOC = 86.5;
+    statusFeedback = VehicleStatus::STATUS_REMOTE;
+    mileage = 123.45; // kilometer
+    speed = 0.1; // m/s
+    shiftFeedback = ShiftStatus::SHIFT_DRIVE;
+    steeringWheelAngleFeedback = 1.23; //+/-540 degree
+    throttleFeedback = 0.12;
+    brakeFeedback = 0.34;
+    GPSRTKStatus = 6; //GPS-RTK status 0-6 6 is best
+    positionFeedback.set_latitude(39.0666552);
+    positionFeedback.set_longitude(117.3540963);
+    positionFeedback.set_height(0.84);
+    pitch = 0.03;
+    roll = 0.02;
+    heading = 198.4;
+
+//    QFile xFile;
+//    xFile.setFileName("/home/samuel/Pictures/123.jpg");
+//    if(xFile.open(QIODevice::ReadOnly))
+//    {
+//        cameraImageFront = xFile.readAll();
+//    }
+//    xFile.close();
+
+//    xFile.setFileName("/home/samuel/Pictures/123.jpg");
+//    if(xFile.open(QIODevice::ReadOnly))
+//    {
+//        cameraImageRear = xFile.readAll();
+//    }
+//    xFile.close();
+
+//    xFile.setFileName("/home/samuel/Pictures/123.jpg");
+//    if(xFile.open(QIODevice::ReadOnly))
+//    {
+//        cameraImageLeft = xFile.readAll();
+//    }
+//    xFile.close();
+
+//    xFile.setFileName("/home/samuel/Pictures/123.jpg");
+//    if(xFile.open(QIODevice::ReadOnly))
+//    {
+//        cameraImageRight = xFile.readAll();
+//    }
+//    xFile.close();
+
+    sensorStatusGPSIMU = false; //0 GPS-IMU ok 1 GPS-IMU error
+    sensorStatusLidar = false;
+    sensorStatusRadar = false;
+    sensorStatusCamFront = false;
+    sensorStatusCamRear = false;
+    sensorStatusCamLeft = false;
+    sensorStatusCamRight = false;
+
+    isArrived = 0; //0 no destination 1 not arrived 2 arrived
+
+    plateNumber = gstrplateNumber;
+
+    modeFeedback = CtrlMode::CMD_REMOTE; //mode Feedback
+}
+
+void DataExchangeClient::updatePath(std::string pathID, QVector<MapPoint> points)
+{
+    id = gstrid;
+    patrolPathID = pathID;
+    pathPoints.clear();
+    for(int i = 0;i < points.size();i++)
+    {
+        pathPoints.append(points.value(i));
+//        std::cout<<pathPoints.at(i).index()<<std::endl;
+    }
+}
+
+void DataExchangeClient::uploadTimeout(void)
+{
+    updateData();
+    std::string reply = uploadVehicleInfo();
+    std::cout<< reply <<std::endl;
+}

+ 91 - 0
src/driver/driver_cloud_grpc_client_BS/vehicle_upload.h

@@ -0,0 +1,91 @@
+#ifndef VEHICLE_UPLOAD_H
+#define VEHICLE_UPLOAD_H
+
+#include <QObject>
+#include <QTimer>
+#include <QVector>
+
+#include <iostream>
+#include <memory>
+#include <string>
+
+#include <grpcpp/grpcpp.h>
+
+#include "VehicleUpload_service.grpc.pb.h"
+#include "VehicleUpload.grpc.pb.h"
+
+using grpc::Channel;
+using grpc::ClientContext;
+using grpc::Status;
+
+using org::jeecg::defsDetails::grpc::DataExchange; ///< service name
+
+using org::jeecg::defsDetails::grpc::UplinkRequest; ///< rpc fuction parameter and return
+using org::jeecg::defsDetails::grpc::ResponseMessage;
+using org::jeecg::defsDetails::grpc::UploadPathRequest;
+
+using org::jeecg::defsDetails::grpc::VehicleStatus; ///< other enum
+
+class DataExchangeClient : public QObject{
+    Q_OBJECT
+
+public:
+    DataExchangeClient(std::shared_ptr<Channel> channel);
+
+    ~DataExchangeClient(void);
+
+    std::string uploadVehicleInfo(void);
+    std::string uploadPath(void);
+    void updateData(void);
+    void updatePath(std::string pathID,QVector<org::jeecg::defsDetails::grpc::MapPoint> points);
+
+private:
+    std::unique_ptr<DataExchange::Stub> stub_;
+
+    std::string id;
+    uint64_t timeStamp;
+    double SOC; //0.0-100.0%
+    VehicleStatus statusFeedback = VehicleStatus::STATUS_EMERGENCY_STOP;
+    double mileage; // kilometer
+    double speed; // m/s
+    org::jeecg::defsDetails::grpc::ShiftStatus shiftFeedback;
+    double steeringWheelAngleFeedback; //+/-540 degree
+    double throttleFeedback;
+    double brakeFeedback;
+    int32_t GPSRTKStatus; //GPS-RTK status 0-6 6 is best
+    org::jeecg::defsDetails::grpc::GPSPoint positionFeedback;
+    double pitch;
+    double roll;
+    double heading;
+
+    QByteArray cameraImageFront;
+    QByteArray cameraImageRear;
+    QByteArray cameraImageLeft;
+    QByteArray cameraImageRight;
+
+    bool sensorStatusGPSIMU; //0 GPS-IMU ok 1 GPS-IMU error
+    bool sensorStatusLidar;
+    bool sensorStatusRadar;
+    bool sensorStatusCamFront;
+    bool sensorStatusCamRear;
+    bool sensorStatusCamLeft;
+    bool sensorStatusCamRight;
+
+    int32_t isArrived; //0 no destination 1 not arrived 2 arrived
+
+    std::string plateNumber;
+
+    org::jeecg::defsDetails::grpc::CtrlMode modeFeedback = org::jeecg::defsDetails::grpc::CtrlMode::CMD_EMERGENCY_STOP; //mode Feedback
+
+    org::jeecg::defsDetails::grpc::GPSPoint destinationPosition;
+
+    std::string patrolPathID;
+    QVector<org::jeecg::defsDetails::grpc::MapPoint> pathPoints;
+
+    QTimer *uploadTimer;
+
+private slots:
+    void uploadTimeout(void);
+};
+
+#endif // VEHICLE_UPLOAD_H

+ 224 - 0
src/tool/map_lanetoxodr/mainwindow.cpp

@@ -54,6 +54,9 @@ MainWindow::MainWindow(QWidget *parent) :
 
     scene = new QGraphicsScene;
 
+    mpscene = new  QGraphicsScene;//(-300, -300, 600, 600);
+    mpscene->setBackgroundBrush(Qt::darkGreen);
+
 
  //    painter->begin(image);
 
@@ -370,6 +373,16 @@ void MainWindow::ExecPainter()
 void MainWindow::paintEvent(QPaintEvent *)
 {
 
+    if(mnViewMode == 1)
+    {
+        if(mbRefresh)
+        {
+            UpdateScene();
+        }
+        myview->setScene(mpscene);
+        myview->show();
+        return;
+    }
     if(mbRefresh)
     {
         ExecPainter();
@@ -422,6 +435,21 @@ void MainWindow::CreateTab1View(QTabWidget * p)
     int nLEWidth = mnFontHeight * 6;
     int nLEHeight = mnFontHeight * 3/2;
 
+    pLabel = new QLabel(pGroup);
+    pLabel->setText("View Mode");
+    pLabel->setGeometry(nXPos,nYPos,nLEWidth,nLEHeight);
+    nXPos = nXPos + nSpace;
+
+    pCB = new QComboBox(pGroup);
+    pCB->addItem("Line");
+    pCB->addItem("Scene");
+    pCB->setCurrentIndex(0);
+    pCB->setGeometry(nXPos,nYPos,nLEWidth,nLEHeight);
+    connect(pCB,SIGNAL(currentIndexChanged(int)),this,SLOT(onViewModeChange(int)));
+
+    nXPos = 10;
+    nYPos = nYPos + mnFontHeight * 3;
+
     pLabel = new QLabel(pGroup);
     pLabel->setText("Lat0");
     pLabel->setGeometry(nXPos,nYPos,nLEWidth,nLEHeight);
@@ -5030,3 +5058,199 @@ void MainWindow::on_actionSplit_Road_triggered()
 {
 
 }
+
+void MainWindow::UpdateScene()
+{
+
+    int i;
+    int nsize = mvectorviewitem.size();
+    for(i=0;i<nsize;i++)
+    {
+        mpscene->removeItem(mvectorviewitem.at(i));
+        delete mvectorviewitem.at(i);
+    }
+    mvectorviewitem.clear();
+
+    nsize = mxodr.GetRoadCount();
+    for(i=0;i<nsize;i++)
+    {
+        UpdateSceneRoad(mxodr.GetRoad(i));
+//        qDebug("update road %d",i);
+    }
+    mbRefresh = false;
+}
+
+void MainWindow::UpdateSceneRoad(Road *pRoad)
+{
+    RoadDigit xrd(pRoad,0.5);
+    std::vector<iv::RoadDigitUnit> * pvectorrdu =  xrd.GetRDU();
+    int nsize = pvectorrdu->size();
+    int i;
+    double flmw = 0.15;
+    for(i=0;i<(nsize-1);i++)
+    {
+        std::vector<iv::LanePoint> xvepre = pvectorrdu->at(i).mvectorLanePoint;
+        std::vector<iv::LanePoint> xvenxt = pvectorrdu->at(i+1).mvectorLanePoint;
+        if((xvepre.size()<2)||(xvenxt.size()<2)||(xvenxt.size() != xvepre.size()))
+        {
+            continue;
+        }
+        unsigned int k;
+        for(k=0;k<(xvepre.size()-1);k++)
+        {
+            QPainterPath xpath;
+            xpath.moveTo(xvepre.at(k).mfX,xvepre.at(k).mfY*(-1));
+            xpath.lineTo(xvenxt.at(k).mfX,xvenxt.at(k).mfY*(-1));
+            xpath.lineTo(xvenxt.at(k+1).mfX,xvenxt.at(k+1).mfY*(-1));
+            xpath.lineTo(xvepre.at(k+1).mfX,xvepre.at(k+1).mfY*(-1));
+            xpath.closeSubpath();
+            QGraphicsPathItem * pitem = new QGraphicsPathItem;
+            pitem->setPath(xpath);
+            pitem->setPos(mfViewMoveX,mfViewMoveY);
+            int nlanetype = xvepre.at(k).mnlanetype;
+            if(xvepre.at(k).mnlane<=0)nlanetype = xvepre.at(k+1).mnlanetype;
+            QColor brushcolor = Qt::darkGray;
+            switch (nlanetype) {
+            case 2:
+                brushcolor = Qt::darkGray;
+                break;
+            case 8:
+                brushcolor = Qt::red;
+                break;
+            case 9:
+                brushcolor = QColor(0xB2,0xB2,0xD6);
+                break;
+            default:
+                brushcolor = Qt::darkGreen;
+                break;
+            }
+            pitem->setBrush(brushcolor);
+            pitem->setPen(QPen(brushcolor,0.001));
+            mpscene->addItem(pitem);
+            mvectorviewitem.push_back(pitem);
+        }
+    }
+
+    for(i=0;i<(nsize-1);i++)
+    {
+        std::vector<iv::LanePoint> xvepre = pvectorrdu->at(i).mvectorLanePoint;
+        std::vector<iv::LanePoint> xvenxt = pvectorrdu->at(i+1).mvectorLanePoint;
+        if(xvenxt.size() != xvepre.size())
+        {
+            continue;
+        }
+        unsigned int k;
+        for(k=0;k<(xvepre.size());k++)
+        {
+            QPainterPath xpath;
+            int ncolor = -3;
+            int nmarktype = xvepre[k].mnlanemarktype;
+            if(nmarktype >= 0)
+            {
+                if(nmarktype<2)
+                {
+                    if((nmarktype == 0)||(roadviewitem::IsDrawMark(xvepre[k].mS)))
+                    {
+                        xpath.moveTo(xvepre[k].mfX + 0.5*flmw * cos(xvenxt[k].mfhdg - M_PI/2.0),
+                                     (xvepre[k].mfY+0.5*flmw * sin(xvenxt[k].mfhdg - M_PI/2.0))*(-1.0));
+                        xpath.lineTo(xvenxt[k].mfX+ 0.5*flmw * cos(xvepre[k].mfhdg - M_PI/2.0),
+                                     (xvenxt[k].mfY+0.5*flmw * sin(xvepre[k].mfhdg - M_PI/2.0))*(-1.0));
+                        xpath.lineTo(xvenxt[k].mfX + 0.5*flmw * cos(xvenxt[k].mfhdg + M_PI/2.0),
+                                     (xvenxt[k].mfY+0.5*flmw * sin(xvenxt[k].mfhdg + M_PI/2.0))*(-1.0));
+                        xpath.lineTo(xvepre[k].mfX+ 0.5*flmw * cos(xvepre[k].mfhdg + M_PI/2.0),
+                                     (xvepre[k].mfY+0.5*flmw * sin(xvepre[k].mfhdg + M_PI/2.0))*(-1.0));
+                        xpath.closeSubpath();
+                        ncolor = xvepre[k].mnlanecolor;
+
+
+                    }
+                }
+                else
+                {
+                    if((nmarktype == 2)||(nmarktype == 3)||(roadviewitem::IsDrawMark(xvepre[k].mS)))
+                    {
+                        xpath.moveTo(xvepre[k].mfX + flmw * cos(xvenxt[k].mfhdg + M_PI/2.0),
+                                     (xvepre[k].mfY+flmw * sin(xvenxt[k].mfhdg + M_PI/2.0))*(-1.0));
+                        xpath.lineTo(xvenxt[k].mfX+ flmw * cos(xvepre[k].mfhdg + M_PI/2.0),
+                                     (xvenxt[k].mfY+flmw * sin(xvepre[k].mfhdg + M_PI/2.0))*(-1.0));
+
+                        xpath.lineTo(xvenxt[k].mfX + 2*flmw * cos(xvenxt[k].mfhdg + M_PI/2.0),
+                                     (xvenxt[k].mfY+2*flmw * sin(xvenxt[k].mfhdg + M_PI/2.0))*(-1.0));
+                        xpath.lineTo(xvepre[k].mfX+ 2*flmw * cos(xvepre[k].mfhdg + M_PI/2.0),
+                                     (xvepre[k].mfY+2*flmw * sin(xvepre[k].mfhdg + M_PI/2.0))*(-1.0));
+                        xpath.closeSubpath();
+                        ncolor = xvepre[k].mnlanecolor;
+                    }
+                    if((nmarktype == 2)||(nmarktype == 4)||(roadviewitem::IsDrawMark(xvepre[k].mS)))
+                    {
+                        xpath.moveTo(xvepre[k].mfX + flmw * cos(xvenxt[k].mfhdg - M_PI/2.0),
+                                     (xvepre[k].mfY+flmw * sin(xvenxt[k].mfhdg - M_PI/2.0))*(-1.0));
+                        xpath.lineTo(xvenxt[k].mfX+ flmw * cos(xvepre[k].mfhdg - M_PI/2.0),
+                                     (xvenxt[k].mfY+flmw * sin(xvepre[k].mfhdg - M_PI/2.0))*(-1.0));
+
+                        xpath.lineTo(xvenxt[k].mfX + 2*flmw * cos(xvenxt[k].mfhdg - M_PI/2.0),
+                                     (xvenxt[k].mfY+2*flmw * sin(xvenxt[k].mfhdg - M_PI/2.0))*(-1.0));
+                        xpath.lineTo(xvepre[k].mfX+ 2*flmw * cos(xvepre[k].mfhdg - M_PI/2.0),
+                                     (xvepre[k].mfY+2*flmw * sin(xvepre[k].mfhdg - M_PI/2.0))*(-1.0));
+                        xpath.closeSubpath();
+                        ncolor = xvepre[k].mnlanecolor;
+                    }
+                }
+            }
+
+            if(ncolor != -3)
+            {
+                QGraphicsPathItem * pitem = new QGraphicsPathItem;
+                pitem->setPath(xpath);
+                QColor brushcolor;
+                switch (ncolor) {
+                case 0:
+                    brushcolor = Qt::white;
+                    break;
+                case 1:
+                    brushcolor = Qt::blue;
+                    break;
+                case 2:
+                    brushcolor = Qt::green;
+                    break;
+                case 3:
+                    brushcolor = Qt::red;
+                    break;
+                case 4:
+                    brushcolor = Qt::white;
+                    break;
+                case 5:
+                    brushcolor = Qt::yellow;
+                    break;
+                case 6:
+                    brushcolor = Qt::yellow; //orange use yellow replace
+                    break;
+                default:
+                    brushcolor = Qt::white;
+                    break;
+                }
+                pitem->setBrush(brushcolor);
+                pitem->setPen(QPen(brushcolor,0.001));
+                pitem->setPos(mfViewMoveX,mfViewMoveY);
+                mpscene->addItem(pitem);
+                mvectorviewitem.push_back(pitem);
+            }
+
+
+
+
+//               }
+
+        }
+
+
+    }
+
+}
+
+void MainWindow::onViewModeChange(int index)
+{
+    mnViewMode = index;
+    mbRefresh = true;
+    update();
+}

+ 14 - 0
src/tool/map_lanetoxodr/mainwindow.h

@@ -67,6 +67,8 @@ using namespace Eigen;
 
 #include "xodrmake.h"
 
+#include "roaddigit.h"
+
 namespace Ui {
 class MainWindow;
 }
@@ -88,6 +90,9 @@ private:
     QTimer *timer;
     QGraphicsScene *scene;
 
+    QGraphicsScene * mpscene;
+
+
 public:
     static void ComboToString(std::string strroadid,QComboBox * pCB);
 
@@ -185,6 +190,8 @@ private slots:
 
     void on_actionSplit_Road_triggered();
 
+    void onViewModeChange(int index);
+
 private:
 
 
@@ -385,6 +392,13 @@ private:
     void updateCBRoad();
     void updateJunction();
 
+    int mnViewMode = 0; //Use Scene
+
+    void UpdateScene();
+    void UpdateSceneRoad(Road * pRoad);
+
+    std::vector<QGraphicsPathItem *> mvectorviewitem;
+
 
 };
 

+ 2 - 0
src/tool/map_lanetoxodr/map_lanetoxodr.pro

@@ -41,6 +41,7 @@ SOURCES += \
     ivxodrtool.cpp \
         main.cpp \
         mainwindow.cpp \
+    roaddigit.cpp \
     roadeditdialog.cpp \
     roadviewitem.cpp \
     speeddialog.cpp \
@@ -89,6 +90,7 @@ HEADERS += \
     ivxodrtool.h \
         mainwindow.h \
     rawtype.h \
+    roaddigit.h \
     roadeditdialog.h \
     roadviewitem.h \
     speeddialog.h \

+ 263 - 0
src/tool/map_lanetoxodr/roaddigit.cpp

@@ -0,0 +1,263 @@
+#include "roaddigit.h"
+
+#include <math.h>
+#include "xodrfunc.h"
+
+
+RoadDigit::RoadDigit(Road * pRoad,double fspace)
+{
+    mpRoad = pRoad;
+    UpdateSpace(fspace);
+}
+
+std::vector<iv::RoadDigitUnit> * RoadDigit::GetRDU()
+{
+    return &mvectorRDU;
+}
+
+void RoadDigit::UpdateSpace(double fspace)
+{
+    if(mpRoad == 0)return;
+    CalcLine(fspace);
+    CalcLane();
+}
+
+void RoadDigit::CalcLine(double fspace)
+{
+    unsigned int j;
+    iv::RoadDigitUnit rdu;
+
+
+    bool bLastGeo = false;
+    for(j=0;j<mpRoad->GetGeometryBlockCount();j++)
+    {
+
+        GeometryBlock * pgeob = mpRoad->GetGeometryBlock(j);
+        double x,y;
+        double x_center,y_center;
+        double R;
+        RoadGeometry * pg;
+        GeometryArc * parc;
+        GeometryParamPoly3 * ppp3;
+        GeometrySpiral *pSpiral;
+        double rel_x,rel_y,rel_hdg;
+        pg = pgeob->GetGeometryAt(0);
+        x = pg->GetX();
+        y = pg->GetY();
+
+        if(j == (mpRoad->GetGeometryBlockCount() -1))
+        {
+            bLastGeo = true;
+        }
+
+        switch (pg->GetGeomType()) {
+        case 0:
+        {
+
+            rdu.mS = pg->GetS();
+            rdu.mX = pg->GetX();
+            rdu.mY = pg->GetY();
+            rdu.mfHdg = pg->GetHdg();
+            mvectorRDU.push_back(rdu);
+            int ncount = pg->GetLength() /fspace;
+            if(ncount<2)ncount = 2;
+            double fstep;
+            if(ncount > 0)fstep = pg->GetLength()/ncount;
+            int i;
+            if(bLastGeo )ncount = ncount+1;
+            for(i=1;i<ncount;i++)
+            {
+                double xtem,ytem;
+                xtem = x + (i*fstep)*cos(pg->GetHdg());
+                ytem = y + (i*fstep)*sin(pg->GetHdg());
+
+                rdu.mS = pg->GetS() + i*fstep;
+                rdu.mX = xtem;
+                rdu.mY = ytem;
+                rdu.mfHdg = pg->GetHdg();
+                mvectorRDU.push_back(rdu);
+
+            }
+        }
+            break;
+
+        case 1:
+            pSpiral = (GeometrySpiral * )pg;
+            {
+               int ncount = pSpiral->GetLength()/fspace;
+               if(ncount < 5)ncount = 5;
+               double sstep = pSpiral->GetLength()/((double)ncount);
+               int k;
+               double x0,y0,hdg0,s0;
+               x0 = pSpiral->GetX();
+               y0 = pSpiral->GetY();
+               s0 = pSpiral->GetS();
+               hdg0 = pSpiral->GetHdg() ;
+
+               rdu.mS = s0;
+               rdu.mX = x0;
+               rdu.mY = y0;
+               rdu.mfHdg = hdg0;
+               mvectorRDU.push_back(rdu);
+
+
+               pSpiral->GetCoords(s0,rel_x,rel_y,rel_hdg);
+
+               if(bLastGeo )ncount = ncount+1;
+               for(k=1;k<ncount;k++)
+               {
+                   pSpiral->GetCoords(s0+sstep*k,rel_x,rel_y,rel_hdg);
+
+                   rdu.mS = s0 + sstep * k;
+                   rdu.mX = rel_x;
+                   rdu.mY = rel_y;
+                   rdu.mfHdg = rel_hdg;
+                   mvectorRDU.push_back(rdu);
+
+            }
+        }
+
+            break;
+        case 2:
+            {
+            parc = (GeometryArc *)pg;
+            R = abs(1.0/parc->GetCurvature());
+            if(parc->GetCurvature() > 0)
+            {
+                x_center = pg->GetX() + R *cos(pg->GetHdg() + M_PI/2.0);
+                y_center = pg->GetY() + R * sin(pg->GetHdg() + M_PI/2.0);
+            }
+            else
+            {
+                x_center = pg->GetX() + R *cos(pg->GetHdg() -M_PI/2.0);
+                y_center = pg->GetY() + R * sin(pg->GetHdg() - M_PI/2.0);
+            }
+
+            rdu.mS = pg->GetS();
+            rdu.mX = pg->GetX();
+            rdu.mY = pg->GetY();
+            rdu.mfHdg = pg->GetHdg();
+            mvectorRDU.push_back(rdu);
+
+            int k;
+            int ncount = parc->GetLength() /fspace;
+            if(ncount< 5)ncount = 5;
+            double curv = parc->GetCurvature();
+            double hdgstep;
+            double hdg0 = parc->GetHdg();
+            double hdgnow = parc->GetHdg();
+            if(ncount > 0) hdgstep= (parc->GetLength()/R)/ncount;
+
+            double x_draw,y_draw;
+
+            if(curv > 0)
+            {
+                hdgnow =  hdg0 ;
+                x_draw = x_center + R *cos(hdgnow - M_PI/2.0);
+                y_draw = y_center + R * sin(hdgnow - M_PI/2.0);
+            }
+            else
+            {
+                hdgnow = hdg0;
+                x_draw = x_center + R *cos(hdgnow  + M_PI/2.0);
+                y_draw = y_center + R * sin(hdgnow + M_PI/2.0);
+            }
+
+
+            if(bLastGeo )ncount = ncount+1;
+            for(k=1;k<ncount;k++)
+            {
+
+
+                if(curv > 0)
+                {
+                    hdgnow =  hdg0 + k*hdgstep;
+                    x_draw = x_center + R *cos(hdgnow - M_PI/2.0);
+                    y_draw = y_center + R * sin(hdgnow - M_PI/2.0);
+                }
+                else
+                {
+                    hdgnow = hdg0 - k * hdgstep;
+                    x_draw = x_center + R *cos(hdgnow  + M_PI/2.0);
+                    y_draw = y_center + R * sin(hdgnow + M_PI/2.0);
+                }
+
+                rdu.mS = pg->GetS() + hdgstep * k* R;
+                rdu.mX = x_draw;
+                rdu.mY = y_draw;
+                rdu.mfHdg = hdgnow;
+                mvectorRDU.push_back(rdu);
+
+
+
+            }
+            }
+            break;
+        case 4:
+            {
+            ppp3 = (GeometryParamPoly3 * )pg;
+            int ncount = ppp3->GetLength() /fspace;
+            if(ncount < 5)ncount = 5;
+            double sstep;
+            if(ncount > 0)sstep = ppp3->GetLength()/ncount;
+            else sstep = 10000.0;
+            double s = 0;
+            double xtem,ytem;
+            xtem = ppp3->GetuA() +  ppp3->GetuB() * s +  ppp3->GetuC() * s*s +  ppp3->GetuD() * s*s*s;
+            ytem = ppp3->GetvA() + ppp3->GetvB() * s + ppp3->GetvC() * s*s + ppp3->GetvD() * s*s*s;
+            x = xtem*cos(ppp3->GetHdg()) - ytem * sin(ppp3->GetHdg()) + ppp3->GetX();
+            y = xtem*sin(ppp3->GetHdg()) + ytem * cos(ppp3->GetHdg()) + ppp3->GetY();
+            s = s+ sstep;
+
+            rdu.mS = pg->GetS();
+            rdu.mX = pg->GetX();
+            rdu.mY = pg->GetY();
+            rdu.mfHdg = pg->GetHdg();
+            mvectorRDU.push_back(rdu);
+
+            double flastx = pg->GetX();
+            double flasty = pg->GetY();
+            while(s <= ppp3->GetLength())
+            {
+
+                xtem = ppp3->GetuA() +  ppp3->GetuB() * s +  ppp3->GetuC() * s*s +  ppp3->GetuD() * s*s*s;
+                ytem = ppp3->GetvA() + ppp3->GetvB() * s + ppp3->GetvC() * s*s + ppp3->GetvD() * s*s*s;
+                x = xtem*cos(ppp3->GetHdg()) - ytem * sin(ppp3->GetHdg()) + ppp3->GetX();
+                y = xtem*sin(ppp3->GetHdg()) + ytem * cos(ppp3->GetHdg()) + ppp3->GetY();
+
+                rdu.mS = pg->GetS() + s;
+                rdu.mX = x;
+                rdu.mY = y;
+                rdu.mfHdg = xodrfunc::CalcHdg(QPointF(flastx,flasty),QPointF(x,y));
+                mvectorRDU.push_back(rdu);
+
+                s = s+ sstep;
+
+
+            }
+            }
+            break;
+        default:
+            break;
+        }
+
+//         painter->drawPoint((int)(x*mnfac),(int)(y*(-1.0*mnfac)));
+
+    }
+
+}
+
+void RoadDigit::CalcLane()
+{
+    int i;
+    int ncount = mvectorRDU.size();
+    for(i=0;i<ncount;i++)
+    {
+
+        std::vector<iv::LanePoint> xvectorlp2 = xodrfunc::GetAllLanePoint(mpRoad,mvectorRDU[i].mS,
+                                                                          mvectorRDU[i].mX,mvectorRDU[i].mY,mvectorRDU[i].mfHdg);
+        mvectorRDU[i].mvectorLanePoint = xvectorlp2;
+    }
+}
+
+

+ 56 - 0
src/tool/map_lanetoxodr/roaddigit.h

@@ -0,0 +1,56 @@
+#ifndef ROADDIGIT_H
+#define ROADDIGIT_H
+
+#include "OpenDrive/OpenDrive.h"
+
+#include <vector>
+
+#include "xodrfunc.h"
+
+namespace iv {
+
+
+struct lanexy
+{
+    int nLane;
+    double mX;
+    double mY;
+    double mCenterX;
+    double mCenterY;
+    int mType = 0;
+    int mnMarkColor;
+    int mMarkType = -1;  //if -1 no mark
+    int mnChange = 0;
+    std::vector<int> mvectorsignal;
+};
+
+struct RoadDigitUnit
+{
+    double mS;
+    double mX;
+    double mY;
+    double mfHdg;
+    std::vector<iv::LanePoint> mvectorLanePoint;
+};
+
+}
+
+class RoadDigit
+{
+public:
+    RoadDigit(Road * pRoad,double fspace);
+
+private:
+    std::vector<iv::RoadDigitUnit> mvectorRDU;
+    Road * mpRoad = 0;
+
+private:
+    void CalcLine(double fspace);
+    void CalcLane();
+
+public:
+    std::vector<iv::RoadDigitUnit> * GetRDU();
+    void UpdateSpace(double fspace);
+};
+
+#endif // ROADDIGIT_H

+ 207 - 2
src/tool/map_lanetoxodr/roadeditdialog.cpp

@@ -312,6 +312,19 @@ void RoadEditDialog::on_comboBox_Road_activated(const QString &arg1)
 
 }
 
+bool RoadEditDialog::IsDrawMark(double s)
+{
+    const double dotdis = 10.0;
+    const double dotlen = 5.0;
+
+    double  y = fmod(s,dotdis);
+    if(y>dotlen)return true;
+    else
+    {
+        return false;
+    }
+}
+
 void RoadEditDialog::on_comboBox_Road_currentIndexChanged(int index)
 {
     Road * pRoad = mpxodr->GetRoad(index);
@@ -332,6 +345,14 @@ void RoadEditDialog::on_comboBox_Road_currentIndexChanged(int index)
     }
     mvectorroadview.clear();
 
+    nsize = mvectorviewitem.size();
+    for(i=0;i<nsize;i++)
+    {
+        scene->removeItem(mvectorviewitem.at(i));
+        delete mvectorviewitem.at(i);
+    }
+    mvectorviewitem.clear();
+
 
     double froad_xmin,froad_ymin,froad_xmax,froad_ymax;
     ServiceXODRTool.GetRoadMaxMin(pRoad,froad_xmin,froad_ymin,froad_xmax,froad_ymax);
@@ -364,9 +385,9 @@ void RoadEditDialog::on_comboBox_Road_currentIndexChanged(int index)
 
     prvw->setPos(mfViewMoveX,mfViewMoveY);
  //       prvw->setPos((froad_xmax - froad_xmin)/2.0, (froad_ymax-froad_ymin)/2.0);
-    mvectorroadview.push_back(prvw);
+//    mvectorroadview.push_back(prvw);
     prvw->setratio(1.0);
-    scene->addItem(prvw);
+//    scene->addItem(prvw);
 
     mnSelGeo = -1;
 
@@ -380,6 +401,190 @@ void RoadEditDialog::on_comboBox_Road_currentIndexChanged(int index)
         ui->comboBox_Geo->addItem(QString("Geo ")+QString::number(i));
     }
 
+    double flmw = 0.15;
+
+    RoadDigit xrd(mpCurRoad,0.1);
+    std::vector<iv::RoadDigitUnit> * pvectorrdu =  xrd.GetRDU();
+    nsize = pvectorrdu->size();
+
+    for(i=0;i<(nsize-1);i++)
+    {
+        std::vector<iv::LanePoint> xvepre = pvectorrdu->at(i).mvectorLanePoint;
+        std::vector<iv::LanePoint> xvenxt = pvectorrdu->at(i+1).mvectorLanePoint;
+        if((xvepre.size()<2)||(xvenxt.size()<2)||(xvenxt.size() != xvepre.size()))
+        {
+            continue;
+        }
+        unsigned int k;
+        for(k=0;k<(xvepre.size()-1);k++)
+        {
+            QPainterPath xpath;
+            xpath.moveTo(xvepre.at(k).mfX,xvepre.at(k).mfY*(-1));
+            xpath.lineTo(xvenxt.at(k).mfX,xvenxt.at(k).mfY*(-1));
+            xpath.lineTo(xvenxt.at(k+1).mfX,xvenxt.at(k+1).mfY*(-1));
+            xpath.lineTo(xvepre.at(k+1).mfX,xvepre.at(k+1).mfY*(-1));
+            xpath.closeSubpath();
+            QGraphicsPathItem * pitem = new QGraphicsPathItem;
+            pitem->setPath(xpath);
+            pitem->setPos(mfViewMoveX,mfViewMoveY);
+            int nlanetype = xvepre.at(k).mnlanetype;
+            if(xvepre.at(k).mnlane<=0)nlanetype = xvepre.at(k+1).mnlanetype;
+            QColor brushcolor = Qt::darkGray;
+            switch (nlanetype) {
+            case 2:
+                brushcolor = Qt::darkGray;
+                break;
+            case 8:
+                brushcolor = Qt::red;
+                break;
+            case 9:
+                brushcolor = QColor(0xB2,0xB2,0xD6);
+                break;
+            default:
+                brushcolor = Qt::darkGreen;
+                break;
+            }
+            pitem->setBrush(brushcolor);
+            pitem->setPen(QPen(brushcolor,0.001));
+            scene->addItem(pitem);
+            mvectorviewitem.push_back(pitem);
+        }
+    }
+
+    for(i=0;i<(nsize-1);i++)
+    {
+        std::vector<iv::LanePoint> xvepre = pvectorrdu->at(i).mvectorLanePoint;
+        std::vector<iv::LanePoint> xvenxt = pvectorrdu->at(i+1).mvectorLanePoint;
+        if(xvenxt.size() != xvepre.size())
+        {
+            continue;
+        }
+        unsigned int k;
+        for(k=0;k<(xvepre.size());k++)
+        {
+            QPainterPath xpath;
+            int ncolor = -3;
+            int nmarktype = xvepre[k].mnlanemarktype;
+            if(nmarktype >= 0)
+            {
+                if(nmarktype<2)
+                {
+                    if((nmarktype == 0)||(IsDrawMark(xvepre[k].mS)))
+                    {
+                        xpath.moveTo(xvepre[k].mfX + 0.5*flmw * cos(xvenxt[k].mfhdg - M_PI/2.0),
+                                     (xvepre[k].mfY+0.5*flmw * sin(xvenxt[k].mfhdg - M_PI/2.0))*(-1.0));
+                        xpath.lineTo(xvenxt[k].mfX+ 0.5*flmw * cos(xvepre[k].mfhdg - M_PI/2.0),
+                                     (xvenxt[k].mfY+0.5*flmw * sin(xvepre[k].mfhdg - M_PI/2.0))*(-1.0));
+                        xpath.lineTo(xvenxt[k].mfX + 0.5*flmw * cos(xvenxt[k].mfhdg + M_PI/2.0),
+                                     (xvenxt[k].mfY+0.5*flmw * sin(xvenxt[k].mfhdg + M_PI/2.0))*(-1.0));
+                        xpath.lineTo(xvepre[k].mfX+ 0.5*flmw * cos(xvepre[k].mfhdg + M_PI/2.0),
+                                     (xvepre[k].mfY+0.5*flmw * sin(xvepre[k].mfhdg + M_PI/2.0))*(-1.0));
+                        xpath.closeSubpath();
+                        ncolor = xvepre[k].mnlanecolor;
+
+
+                    }
+                }
+                else
+                {
+                    if((nmarktype == 2)||(nmarktype == 3)||(IsDrawMark(xvepre[k].mS)))
+                    {
+                        xpath.moveTo(xvepre[k].mfX + flmw * cos(xvenxt[k].mfhdg + M_PI/2.0),
+                                     (xvepre[k].mfY+flmw * sin(xvenxt[k].mfhdg + M_PI/2.0))*(-1.0));
+                        xpath.lineTo(xvenxt[k].mfX+ flmw * cos(xvepre[k].mfhdg + M_PI/2.0),
+                                     (xvenxt[k].mfY+flmw * sin(xvepre[k].mfhdg + M_PI/2.0))*(-1.0));
+
+                        xpath.lineTo(xvenxt[k].mfX + 2*flmw * cos(xvenxt[k].mfhdg + M_PI/2.0),
+                                     (xvenxt[k].mfY+2*flmw * sin(xvenxt[k].mfhdg + M_PI/2.0))*(-1.0));
+                        xpath.lineTo(xvepre[k].mfX+ 2*flmw * cos(xvepre[k].mfhdg + M_PI/2.0),
+                                     (xvepre[k].mfY+2*flmw * sin(xvepre[k].mfhdg + M_PI/2.0))*(-1.0));
+                        xpath.closeSubpath();
+                        ncolor = xvepre[k].mnlanecolor;
+                    }
+                    if((nmarktype == 2)||(nmarktype == 4)||(IsDrawMark(xvepre[k].mS)))
+                    {
+                        xpath.moveTo(xvepre[k].mfX + flmw * cos(xvenxt[k].mfhdg - M_PI/2.0),
+                                     (xvepre[k].mfY+flmw * sin(xvenxt[k].mfhdg - M_PI/2.0))*(-1.0));
+                        xpath.lineTo(xvenxt[k].mfX+ flmw * cos(xvepre[k].mfhdg - M_PI/2.0),
+                                     (xvenxt[k].mfY+flmw * sin(xvepre[k].mfhdg - M_PI/2.0))*(-1.0));
+
+                        xpath.lineTo(xvenxt[k].mfX + 2*flmw * cos(xvenxt[k].mfhdg - M_PI/2.0),
+                                     (xvenxt[k].mfY+2*flmw * sin(xvenxt[k].mfhdg - M_PI/2.0))*(-1.0));
+                        xpath.lineTo(xvepre[k].mfX+ 2*flmw * cos(xvepre[k].mfhdg - M_PI/2.0),
+                                     (xvepre[k].mfY+2*flmw * sin(xvepre[k].mfhdg - M_PI/2.0))*(-1.0));
+                        xpath.closeSubpath();
+                        ncolor = xvepre[k].mnlanecolor;
+                    }
+                }
+            }
+
+            if(ncolor != -3)
+            {
+                QGraphicsPathItem * pitem = new QGraphicsPathItem;
+                pitem->setPath(xpath);
+                QColor brushcolor;
+                switch (ncolor) {
+                case 0:
+                    brushcolor = Qt::white;
+                    break;
+                case 1:
+                    brushcolor = Qt::blue;
+                    break;
+                case 2:
+                    brushcolor = Qt::green;
+                    break;
+                case 3:
+                    brushcolor = Qt::red;
+                    break;
+                case 4:
+                    brushcolor = Qt::white;
+                    break;
+                case 5:
+                    brushcolor = Qt::yellow;
+                    break;
+                case 6:
+                    brushcolor = Qt::yellow; //orange use yellow replace
+                    break;
+                default:
+                    brushcolor = Qt::white;
+                    break;
+                }
+                pitem->setBrush(brushcolor);
+                pitem->setPen(QPen(brushcolor,0.001));
+                pitem->setPos(mfViewMoveX,mfViewMoveY);
+                scene->addItem(pitem);
+                mvectorviewitem.push_back(pitem);
+            }
+
+
+
+
+//               }
+
+        }
+
+
+    }
+
+//    for(i=0;i<(nsize-1);i++)
+//    {
+//        QPainterPath xpath;
+//        std::vector<iv::LanePoint> * pvectorLP1 = &pvectorrdu->at(i).mvectorLanePoint;
+//        std::vector<iv::LanePoint> * pvectorLP2 = &pvectorrdu->at(i+1).mvectorLanePoint;
+//        xpath.moveTo(pvectorLP1->at(0).mfX,pvectorLP1->at(0).mfY*(-1));
+//        xpath.lineTo(pvectorLP2->at(0).mfX,pvectorLP2->at(0).mfY*(-1));
+//        xpath.lineTo(pvectorLP2->at(pvectorLP2->size()-1).mfX,pvectorLP2->at(pvectorLP2->size()-1).mfY*(-1));
+//        xpath.lineTo(pvectorLP1->at(pvectorLP1->size()-1).mfX,pvectorLP1->at(pvectorLP1->size()-1).mfY*(-1));
+//        xpath.closeSubpath();
+//        QGraphicsPathItem * pitem = new QGraphicsPathItem;
+//        pitem->setPath(xpath);
+//        pitem->setPos(mfViewMoveX,mfViewMoveY);
+//        pitem->setBrush(Qt::darkGray);
+//        pitem->setPen(QPen(Qt::darkGray,0.001));
+//        scene->addItem(pitem);
+//        mvectorviewitem.push_back(pitem);
+//    }
+
     update();
 }
 

+ 7 - 0
src/tool/map_lanetoxodr/roadeditdialog.h

@@ -20,6 +20,8 @@
 #include "dialogroadrotate.h"
 #include "dialogroadmirror.h"
 
+#include "roaddigit.h"
+
 namespace Ui {
 class RoadEditDialog;
 }
@@ -60,6 +62,9 @@ private slots:
 
     void on_pushButton_MirrorRoad_clicked();
 
+private:
+    bool IsDrawMark(double s);
+
 private:
     Ui::RoadEditDialog *ui;
     OpenDrive * mpxodr;
@@ -76,6 +81,8 @@ private:
 
     std::vector<roadviewitem *> mvectorroadview;
 
+    std::vector<QGraphicsPathItem *> mvectorviewitem;
+
     double mfViewMoveX = 0;
     double mfViewMoveY = 0;
 };

+ 2 - 0
src/tool/map_lanetoxodr/roadviewitem.cpp

@@ -12,6 +12,8 @@ roadviewitem::roadviewitem(Road * pRoad)
 {
     mpRoad = pRoad;
     mbNeedCalc = true;
+    QGraphicsPathItem x;
+
 }
 
 QRectF roadviewitem::boundingRect() const

+ 2 - 2
src/tool/map_lanetoxodr/roadviewitem.h

@@ -101,8 +101,8 @@ private:
     bool mbShowLane = true;
     bool mbShowLine = false;
     bool mbShowRoadID = true;
-
-    bool IsDrawMark(double s);
+public:
+    static bool IsDrawMark(double s);
 };
 
 #endif // ROADVIEWITEM_H

+ 9 - 1
src/tool/map_lanetoxodr/xodrfunc.cpp

@@ -601,6 +601,7 @@ std::vector<iv::LanePoint> xodrfunc::GetAllLanePoint(Road *pRoad,  const double
     int nLSCount = pRoad->GetLaneSectionCount();
     double s_section = 0;
 
+
     std::vector<iv::LanePoint> xvectorlanepoint;
     for(i=0;i<nLSCount;i++)
     {
@@ -627,7 +628,7 @@ std::vector<iv::LanePoint> xodrfunc::GetAllLanePoint(Road *pRoad,  const double
             int nlanetype = 2; //driving
             int nlanecolor = 0;
             int k;
-            double s_lane = 0;
+            double s_lane = s-s_section;
             for(k=0;k<pLane->GetLaneRoadMarkCount();k++)
             {
                  LaneRoadMark * plrm = pLane->GetLaneRoadMark(k);
@@ -638,6 +639,13 @@ std::vector<iv::LanePoint> xodrfunc::GetAllLanePoint(Road *pRoad,  const double
                          continue;
                      }
                  }
+                 else
+                 {
+                     if(s_lane<plrm->GetS())
+                     {
+                         continue;
+                     }
+                 }
                  if(plrm->GetType() == "solid")
                  {
                      nlanemarktype = 0;