lizhanwei
2020-03-20 a4a126cc414793a3c06da7c1f80f50131fe05792
app/src/main/java/safeluck/drive/evaluation/fragment/RoadDriveMapFragment.java
@@ -1,10 +1,14 @@
package safeluck.drive.evaluation.fragment;
import android.content.Context;
import android.graphics.Bitmap;
import android.graphics.Canvas;
import android.graphics.Color;
import android.graphics.DashPathEffect;
import android.graphics.Paint;
import android.graphics.Path;
import android.graphics.PathEffect;
import android.graphics.RectF;
import android.os.Bundle;
import android.util.Log;
import android.view.LayoutInflater;
@@ -21,19 +25,28 @@
import com.google.gson.reflect.TypeToken;
import java.lang.reflect.Type;
import java.math.BigDecimal;
import java.util.ArrayList;
import java.util.List;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;
import java.util.concurrent.LinkedBlockingQueue;
import me.yokeyword.fragmentation.SupportFragment;
import safeluck.drive.evaluation.Constant;
import safeluck.drive.evaluation.bean.ExamMap;
import safeluck.drive.evaluation.bean.RealTimeCarPos;
import safeluck.drive.evaluation.bean.RoadExamMap;
import safeluck.drive.evaluation.cEventCenter.CEventCenter;
import safeluck.drive.evaluation.cEventCenter.ICEventListener;
import safeluck.drive.evaluation.util.FileUtil;
import static android.view.View.LAYER_TYPE_SOFTWARE;
public class RoadDriveMapFragment extends SupportFragment implements SurfaceHolder.Callback {
    private static final String TAG = RoadDriveMapFragment.class.getSimpleName();
    private static final int ALL_MAP = 100;//总图
    private SurfaceView mSurfaceView;
    private SurfaceHolder mSurfaceHolder;
@@ -44,15 +57,47 @@
    private Path mPath;
    private StringBuffer buffer;//存放地图的buffer
    private Gson gson = new Gson();
    private double gpsSpeed = 0;
    private int map_id = -1;
    private String osdHeading = null;
    private String osdMoveDirect = null;
    private String osdRtkSpeed = null;
    private String osdQf = null;
    double car[][] = {{8.278, 1.467}, {7.2780000000000009, 1.467}, {7.2780000000000009, -1.533}, {8.278, -1.533}
            , {9.278, -1.5330000000000004}, {9.277999999999999, 1.467000000000001}};
    double map[][]={};
    private LinkedBlockingQueue queue = new LinkedBlockingQueue(100);
    private int avaliableWidth,avaliableHeight;
    private int x = 50, y = 50, r = 10; // 圆的坐标和半径
    private int sinx = 0,siny =0 ;
    float [] pts={50,100,100,200,200,300,300,400};
    private ExecutorService generateData = Executors.newSingleThreadExecutor();//产生数据(主要是车辆数据)
    private ExecutorService drawThread = Executors.newSingleThreadExecutor();//绘制线程
    /**
     * 接收远程服务发过来的车辆位置信息
     */
    private ICEventListener icEventListener = new ICEventListener() {
        @Override
        public void onCEvent(String topic, final int msgCode, int resultCode, final Object obj) {
            generateData.execute(new Runnable() {
                @Override
                public void run() {
                    queue.offer(new MessageRemoteService(msgCode,obj));
                }
            });
        }
    };
    public static RoadDriveMapFragment newInstance(){
        return new RoadDriveMapFragment();
@@ -103,6 +148,7 @@
        flag = true;
        drawThread.execute(new DrawRunnable());
    }
@@ -117,62 +163,123 @@
        flag = false;
    }
    List<ExamMap> examMaps = new ArrayList<>();
    RoadExamMap examMaps ;
    /**
     * 主要是这个方法,进行坐标点计算,使用mPath画图,可能要用到Canvas
     * 最好只使用path
     */
    private void calculate() {
        int map_id = 863;
        int map_line = 0;
        double map[][]={};
        int map_line = 0,line = 0;
        MessageRemoteService messageRemoteService = (MessageRemoteService) queue.peek();
        if (messageRemoteService == null){
            Log.i(TAG,"messageRemoteService ==null");
        if (buffer == null){
            buffer = FileUtil.readAssetTxtFile(_mActivity, Constant.ROAD_MAP);
            Log.i(TAG,"ditu="+buffer.toString().trim());
        }
        Type type = new TypeToken<List<ExamMap>>(){}.getType();
        if (buffer != null){
            examMaps= gson.fromJson(buffer.toString().trim(), type);
        }
        for (int i = 0; i < examMaps.size(); i++) {
            ExamMap examMap = examMaps.get(i);
            if (map_id == examMap.getId()){
                List<ExamMap.PointBean> pointBeanList = examMap.getPoint();
                for(int j=0; j<pointBeanList.size();j++){
                    List<Double> xys = pointBeanList.get(j).getXy();
                    if(j==0){
                        map = new double[xys.size()/2][2];
                        for (int k=0; k<xys.size();k++){
                            if ((k % 2) == 0) {
                                map[map_line][0] = xys.get(k);
                                Log.i(TAG, "onCEvent: map新值=" + map[map_line][0] + " 位置:" + k);
                            } else {
                                double value = 0-xys.get(k);
                                map[map_line][1] = value;
                                map_line++;
                            }
                        }
                    }else{
                        MyLog.i(TAG,"暂时支持曲线");
                        break;
                    }
                }
                break;
            try {
                Thread.sleep(100);
            } catch (InterruptedException e) {
                e.printStackTrace();
            }
        }
        onDrawMap(map);
        messageRemoteService = (MessageRemoteService) queue.poll();
        if (messageRemoteService != null){
            MyLog.i(TAG, messageRemoteService.json);
            RealTimeCarPos timeCarPos = gson.fromJson((String) messageRemoteService.json, RealTimeCarPos.class);
            List<Double> points = timeCarPos.getPoint();
            switch (timeCarPos.getMove()){
                case 0:
                    osdMoveDirect = "停车";
                    break;
                case 1:
                    osdMoveDirect = "前进";
                    break;
                case -1:
                    osdMoveDirect = "后退";
                    break;
            }
            osdHeading="方向角"+String.valueOf(timeCarPos.getHeading());
            BigDecimal bd = new BigDecimal(timeCarPos.getSpeed());
            bd = bd.setScale(3, BigDecimal.ROUND_HALF_UP);
            osdRtkSpeed = "计算速度:" + bd;
            osdQf = "QF:" + String.valueOf(timeCarPos.getQf());
            car = new double[points.size()/2][2];
            for (int i = 0; i < points.size(); i++) {
                if ((i % 2) == 0) {
                    car[line][0] = points.get(i);
                } else {
                    double value = 0 - points.get(i);
                    car[line][1] = value;
                    line++;
                }
            }
            map_id = timeCarPos.getMap_id();
            List<Double> mainAnt = timeCarPos.getMain_ant();
            List<Integer> tire1 = timeCarPos.getLeft_front_tire();
            List<Integer> tire2 = timeCarPos.getRight_front_tire();
            List<Integer> tire3 = timeCarPos.getLeft_rear_tire();
            List<Integer> tire4 = timeCarPos.getRight_rear_tire();
            List<Integer> body = timeCarPos.getBody();
            List<Integer> tire = new ArrayList<>();
            tire.add(tire1.get(0));
            tire.add(tire2.get(0));
            tire.add(tire3.get(0));
            tire.add(tire4.get(0));
            if (buffer == null){
                buffer = FileUtil.readAssetTxtFile(_mActivity, Constant.ROAD_MAP);
                Log.i(TAG,"ditu="+buffer.toString().trim());
            }
            Type type = new TypeToken<RoadExamMap>(){}.getType();
            if (buffer != null){
                examMaps= gson.fromJson(buffer.toString().trim(), type);
            }
            if (examMaps!=null){
                points = examMaps.getPoints();
                if (points != null){
                    map = new double[points.size()/2][2];
                    for (int i = 0; i < points.size(); i++) {
                        if ((i % 2) == 0){
                            map[map_line][0] = points.get(i);
                        }else{
                            double value = 0-points.get(i);
                            map[map_line][1] = value;
                            map_line++;
                        }
                    }
                }
            }
            onDrawMap(map,examMaps.getMaps(),car,body,tire,mainAnt);
        }
//        mPaint.reset();
//        mPaint.setStyle(Paint.Style.FILL);
//        mPaint.setColor(Color.RED);
@@ -207,8 +314,8 @@
    }
private void onDrawMap(final double map[][]){
private void onDrawMap(final double[][] map, List<RoadExamMap.MapsBean> maps,final double[][] car,
                       List<Integer>body, List<Integer> tire,List<Double> mainAnt){
    double base_x = 300, base_y = 20;
    double max_x = 0, min_x = 0, max_y = 0, min_y = 0;
@@ -235,6 +342,21 @@
            }
        }
    }
    for (int i = 0; i < car.length; i++) {
        if (max_x < car[i][0]) {
            max_x = car[i][0];
        }
        if (min_x > car[i][0]) {
            min_x = car[i][0];
        }
        if (max_y < car[i][1]) {
            max_y = car[i][1];
        }
        if (min_y > car[i][1]) {
            min_y = car[i][1];
        }
    }
    long scale_x = Math.round((mCanvas.getWidth() - base_x - 10) / (max_x - min_x));
    long scale_y = Math.round((mCanvas.getHeight() - base_y - 10) / (max_y - min_y));
@@ -246,31 +368,108 @@
    mPaint.reset();
    mPaint.setAntiAlias(true);
    mPaint.setColor(Color.BLACK);
    mPaint.setStyle(Paint.Style.STROKE);
    mPaint.setColor(Color.BLUE);
    mPaint.setStrokeWidth(1.5f);
    mPaint.setStyle(Paint.Style.FILL_AND_STROKE);
    mCanvas.drawCircle((float) (base_x + (mainAnt.get(0) - min_x) * scale_x), (float) (base_y + (0 - mainAnt.get(1) - min_y) * scale_y), 2, mPaint);
    mPaint.setColor(Color.RED);
    mCanvas.drawCircle((float) (base_x + (car[tire.get(0)][0] - min_x) * scale_x), (float) (base_y + (car[tire.get(0)][1] - min_y) * scale_y), 2.5f, mPaint);
    mCanvas.drawCircle((float) (base_x + (car[tire.get(1)][0] - min_x) * scale_x), (float) (base_y + (car[tire.get(1)][1] - min_y) * scale_y), 2.5f, mPaint);
    mCanvas.drawCircle((float) (base_x + (car[tire.get(2)][0] - min_x) * scale_x), (float) (base_y + (car[tire.get(2)][1] - min_y) * scale_y), 2.5f, mPaint);
    mCanvas.drawCircle((float) (base_x + (car[tire.get(3)][0] - min_x) * scale_x), (float) (base_y + (car[tire.get(3)][1] - min_y) * scale_y), 2.5f, mPaint);
    mPaint.setStyle(Paint.Style.STROKE);
    mPaint.setColor(Color.BLACK);
    if (map.length > 9) {
        Log.d(TAG, "DrawMap X = " + String.format("%f", (float) (base_x + (map[0][0] - min_x) * scale_x)) + " Y = " + String.format("%f", (float) (base_y + (map[0][1] - min_y) * scale_y)));
        mPath.moveTo((float) (base_x + (map[0][0] - min_x) * scale_x), (float) (base_y + (map[0][1] - min_y) * scale_y));
        for (int i = 1; i < map.length; i++) {
            Log.d(TAG, "DrawMap to X = " + (float) (base_x + (map[i][0] - min_x) * scale_x) + " Y = " + (float) (base_y + (map[i][1] - min_y) * scale_y));
            mPath.lineTo((float) (base_x + (map[i][0] - min_x) * scale_x), (float) (base_y + (map[i][1] - min_y) * scale_y));
        }
        mPath.close();
        mCanvas.drawPath(mPath,mPaint);
    }
mPaint.reset();
        mPath = new Path();
    mPaint.setStyle(Paint.Style.STROKE);
    mPaint.setStrokeWidth(1.5f);
    mPaint.setColor(Color.RED);
    mPath.moveTo(300,150);
    mPath.lineTo(1015,150);
        if (maps != null&& maps.size()>0){
            for (int i = 0; i < maps.size(); i++) {
                RoadExamMap.MapsBean mapItem = maps.get(i);
                if (mapItem.getItem() == ALL_MAP){
                    List<List<Integer>> redLines= mapItem.getRed_line();
                    List<List<Integer>> greenLines = mapItem.getGreen_line();
                    mPaint.reset();
                    mPaint.setStyle(Paint.Style.STROKE);
                    mPaint.setStrokeWidth(1.5f);
                    mPaint.setAntiAlias(true);
                    mPaint.setColor(Color.RED);
                    Log.i(TAG,"redLinesSize"+redLines.size());
                    for (List<Integer> redline: redLines
                         ) {
                        for (int j = 0; j < redline.size(); j++) {
                            Log.i(TAG,"redLiSize"+redline.size());
                            int pos = redline.get(j);
                            if (j == 0){
                                mPath.moveTo((float) (base_x + (map[pos][0] - min_x) * scale_x), (float) (base_y + (map[pos][1] - min_y) * scale_y));
                            }
                            mPath.lineTo((float) (base_x + (map[pos][0] - min_x) * scale_x), (float) (base_y + (map[pos][1] - min_y) * scale_y));
                            Log.i(TAG,String.format("map[%d][0]=%f,map[%d][1]=%f,line to (%f,%f)",pos,map[pos][0],pos,map[pos][1],
                                    (float) (base_x + (map[pos][0] - min_x) * scale_x),(float) (base_y + (map[pos][1] - min_y) * scale_y)));
    mCanvas.drawPath(mPath,mPaint);
                        }
                    }
                    mCanvas.drawPath(mPath,mPaint);
                //画虚线(分道线)
                    mPaint.reset();
                    mPaint.setStyle(Paint.Style.STROKE);
                    mPaint.setStrokeWidth(1.5f);
                    mPaint.setAntiAlias(true);
                    mPaint.setColor(Color.WHITE);
                    mPath = new Path();
                    mPaint.setPathEffect(new DashPathEffect(new float[] {15, 15}, 0));
                    for (List<Integer> greenline:
                            greenLines){
                        for (int j = 0; j < greenline.size(); j++) {
                            int pos = greenline.get(j);
                            if (j == 0){
                                mPath.moveTo((float) (base_x + (map[pos][0] - min_x) * scale_x), (float) (base_y + (map[pos][1] - min_y) * scale_y));
                            }
                            mPath.lineTo((float) (base_x + (map[pos][0] - min_x) * scale_x), (float) (base_y + (map[pos][1] - min_y) * scale_y));
                            Log.i(TAG,String.format("map[%d][0]=%f,map[%d][1]=%f,line to (%f,%f)",pos,map[pos][0],pos,map[pos][1],
                                    (float) (base_x + (map[pos][0] - min_x) * scale_x),(float) (base_y + (map[pos][1] - min_y) * scale_y)));
                        }
                    }
                    mCanvas.drawPath(mPath,mPaint);
                }
            }
            mPath.moveTo((float) (base_x + (car[body.get(0)][0] - min_x) * scale_x), (float) (base_y + (car[body.get(0)][1] - min_y) * scale_y));
            for (int k = 1; k < body.size(); k++){
                Log.d(TAG, "for 循环 DrawMap to X = " + (float) (base_x + (car[body.get(k)][0] - min_x) * scale_x)+ " Y = " + (float) (base_y + (car[body.get(k)][1] - min_y) * scale_y));
                mPath.lineTo((float) (base_x + (car[body.get(k)][0] - min_x) * scale_x), (float) (base_y + (car[body.get(k)][1] - min_y) * scale_y));
            }
            mPath.close();
            mCanvas.drawPath(mPath, mPaint);
        }
    }
//mPaint.reset();
//        mPath = new Path();
//    mPaint.setStyle(Paint.Style.STROKE);
//    mPaint.setStrokeWidth(1.5f);
//
//    for (int i = 0; i < map.length; i++) {
//        if (i<map.length-3){
//            mPath.moveTo((float) (base_x + (map[i][0] - min_x) * scale_x), (float) (base_y + (map[i][1] - min_y) * scale_y));
//            mPath.lineTo((float) (base_x + (map[i+3][0] - min_x) * scale_x), (float) (base_y + (map[i+3][1] - min_y) * scale_y));
//        }else{
//            break;
//        }
//
//        i++;
//    }
//    mCanvas.drawPath(mPath,mPaint);
}
    /**
@@ -314,4 +513,40 @@
        }
    }
    class MessageRemoteService{
        public int msgCode;
        public String json;
        public MessageRemoteService(int msgCode, Object obj) {
            this.json = (String) obj;
            this.msgCode = msgCode;
        }
    }
    @Override
    public void onAttach(Context context) {
        super.onAttach(context);
        CEventCenter.onBindEvent(true, icEventListener, Constant.REAL_TIME_POS_CAR_TOPIC);
        CEventCenter.onBindEvent(true, speedListener, Constant.BIND_RTK_SPEED_TOPIC);
    }
    @Override
    public void onDetach() {
        super.onDetach();
        generateData.shutdown();
        drawThread.shutdown();
        CEventCenter.onBindEvent(false, icEventListener, Constant.REAL_TIME_POS_CAR_TOPIC);
        CEventCenter.onBindEvent(false, speedListener, Constant.BIND_RTK_SPEED_TOPIC);
    }
    private ICEventListener speedListener = new ICEventListener() {
        @Override
        public void onCEvent(String topic, int msgCode, int resultCode, Object obj) {
            if (msgCode == Constant.RTK_INFO){
                gpsSpeed = (double)obj;
            }
        }
    };
}