[Android]Android开发(二)

登陆界面开发

  • 两个EditText分别输入username和passwd
  • 两个Button一个login登陆,一个reg注册
  • 一个CheckBox判断是否为司机

登陆按钮

一个文本为“登陆”的Button,绑定了点击事件

  • 从两个text拿到useername和passwd数据校验判空操作,界面做toast弹窗,同时拿到isDriver

  • 调用公用的的OBOJni接口单例实例的Login接口传入username,passwd,isDriver

  • 根据返回jason中的login_result字段的值判断,True

    • 通过OBOJni拿到getIsDriver(),字段为no,则intent对象跳转到PassengerMapActivity.class
    • 该字段不为no,则跳转到DriverMapActivity.class
  • login_result字段不为true,则toast弹窗显示“登陆失败-无法连接服务器”

      	 bt_login.setOnClickListener(new View.OnClickListener() {
      	            @Override
      	            public void onClick(View v) {
      	                String username = et_username.getText().toString();
      	                String passwd = et_passwd.getText().toString();
      	                Log.e(LogTag,"username:"+ username);
      	                Log.e(LogTag, "passwd:" + passwd);
                      if (username.length() == 0 || passwd.length() == 0) {
                          Toast.makeText(getApplicationContext(),
                                  "用户名或密码为空",Toast.LENGTH_SHORT).show();
                          return;
                      }
      
                  boolean login_result = OBOJni.getInstence().Login(username, passwd,isDriver);
                  Log.e(LogTag, "Login result is " + login_result);
    
                  if (login_result == true) {
                      if (OBOJni.getInstence().getIsDriver().equals("no")) {
                          Intent intent = new Intent();
                          intent.setClass(MainActivity.this, PassengerMapActivity.class);
                          startActivity(intent);
                      }
                      else {
                          Intent intent = new Intent();
                          intent.setClass(MainActivity.this, DriverMapActivity.class);
                          startActivity(intent);
                      }
                  }
                  else {
                      Toast.makeText(getApplicationContext(),
                              "登陆失败-无法连接服务器",Toast.LENGTH_SHORT).show();
                      Log.e(LogTag, "Login error!");
                  }
    
              }
          });
    

注册按钮

注册按钮绑定了点击事件后,点击后会跳转到注册界面RegActivity.class

        bt_reg.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                Intent intent = new Intent();
                intent.setClass(MainActivity.this, RegActivity.class);
                startActivity(intent);
            }
        });

界面源码

		package com.example.ace.obo;
		
		import android.content.Intent;
		import android.support.v7.app.AppCompatActivity;
		import android.os.Bundle;
		import android.util.Log;
		import android.view.View;
		import android.widget.Button;
		import android.widget.CheckBox;
		import android.widget.CompoundButton;
		import android.widget.EditText;
		import android.widget.Toast;
		
		public class MainActivity extends AppCompatActivity {
		
	    public static String LogTag="OBO-MainActivity";
	
	    private Button bt_login = null;
	    private Button bt_reg = null;
	    private EditText et_username = null;
	    private EditText et_passwd = null;
	    private CheckBox cb_isDriver_login = null;
	    private boolean isDriver = false;
	
	
	    @Override
	    protected void onCreate(Bundle savedInstanceState) {
	        super.onCreate(savedInstanceState);
	        setContentView(R.layout.activity_main);
	
	
	        bt_login = (Button)findViewById(R.id.bt_login);
	        bt_reg = (Button)findViewById(R.id.bt_reg);
	        et_username = (EditText)findViewById(R.id.et_username);
	        et_passwd = (EditText)findViewById(R.id.et_passwd);
	        cb_isDriver_login = (CheckBox)findViewById(R.id.login_cb_isDriver);
	
	        cb_isDriver_login.setOnCheckedChangeListener(new CompoundButton.OnCheckedChangeListener() {
	            @Override
	            public void onCheckedChanged(CompoundButton buttonView, boolean isChecked) {
	                if (isChecked) {
	                    isDriver = true;
	                }
	                else {
	                    isDriver = false;
	                }
	            }
	        });
	
	
	        //绑定登陆按钮的点击事件
	        bt_login.setOnClickListener(new View.OnClickListener() {
	            @Override
	            public void onClick(View v) {
	                String username = et_username.getText().toString();
	                String passwd = et_passwd.getText().toString();
	                Log.e(LogTag,"username:"+ username);
	                Log.e(LogTag, "passwd:" + passwd);
	
	                if (username.length() == 0 || passwd.length() == 0) {
	                    Toast.makeText(getApplicationContext(),
	                            "用户名或密码为空",Toast.LENGTH_SHORT).show();
	                    return;
	                }
	
	                boolean login_result = OBOJni.getInstence().Login(username, passwd,isDriver);
	                Log.e(LogTag, "Login result is " + login_result);
	
	                if (login_result == true) {
	                    if (OBOJni.getInstence().getIsDriver().equals("no")) {
	                        Intent intent = new Intent();
	                        intent.setClass(MainActivity.this, PassengerMapActivity.class);
	                        startActivity(intent);
	                    }
	                    else {
	                        Intent intent = new Intent();
	                        intent.setClass(MainActivity.this, DriverMapActivity.class);
	                        startActivity(intent);
	                    }
	                }
	                else {
	                    Toast.makeText(getApplicationContext(),
	                            "登陆失败-无法连接服务器",Toast.LENGTH_SHORT).show();
	                    Log.e(LogTag, "Login error!");
	                }
	
	            }
	        });
	
	
	        bt_reg.setOnClickListener(new View.OnClickListener() {
	            @Override
	            public void onClick(View v) {
	                Intent intent = new Intent();
	                intent.setClass(MainActivity.this, RegActivity.class);
	                startActivity(intent);
	            }
	        });
	    }
	}

注册界面开发

  • 六个EditText分别输入用户名,密码,密码(重复输入),电话,有限,身份证号码
  • 一个提交Button
  • 一个CheckBox判断是否为司机(变量isDriver ) OBOJni

注册按钮

  • 绑定了点击事件,在点击事件内部的逻辑

  • 对每一个从控件拿到的值做非空(两次密码做对比)校验并做非法的toast弹窗提示

  • 调用OBOJni接口提交注册信息

      注意这段代码的逻辑,调用JNI成功会返回true	
      if(OBOJni.getInstence().Reg(username,passwd1,tel,email, id_card,isDriver) == true) 
    
  • 注册成功,判断OBOJni.getInstence().getIsDriver().equals(“no”),成立则跳转到司机界面PassengerMapActivity.class,否则跳转到DriverMapActivity.class

  • 注册失败直接toast弹窗显示 “链接服务器失败”

  • 代码

    bt_reg_submit.setOnClickListener(new View.OnClickListener() {
              @Override
              public void onClick(View v) {
                  //注册提交按钮被点击
                  String username = et_reg_username.getText().toString().trim();
                  String passwd1 = et_reg_passwd1.getText().toString().trim();
                  String passwd2 = et_reg_passwd2.getText().toString().trim();
                  String tel = et_reg_tel.getText().toString().trim();
                  String email = et_reg_email.getText().toString().trim();
                  String id_card = et_reg_id_card.getText().toString().trim();
    
                  if (username.length() = = 0) {
                      Toast.makeText(getApplicationContext(),
                              "用户名为空或者非法",Toast.LENGTH_SHORT).show();
                      return;
                  }
    
                  if (passwd1.length() = = 0 || passwd2.length() = = 0) {
                      Toast.makeText(getApplicationContext(),
                              "密码非法",Toast.LENGTH_SHORT).show();
                      return;
                  }
    
                  if (!passwd1.equals(passwd2)) {
                      Toast.makeText(getApplicationContext(),
                              "两次输入的密码不一样",Toast.LENGTH_SHORT).show();
                      return;
                  }
    
                  if (tel.length() = = 0) {
                      Toast.makeText(getApplicationContext(),
                              "电话号码为空",Toast.LENGTH_SHORT).show();
                      return;
                  }
    
                  if (email.length()= =0) {
                      Toast.makeText(getApplicationContext(),
                              "email为空",Toast.LENGTH_SHORT).show();
                      return;
                  }
    
                  if (id_card.length() = = 0) {
                      Toast.makeText(getApplicationContext(),
                              "身份证号为空",Toast.LENGTH_SHORT).show();
                      return;
                  }
    
                  if(OBOJni.getInstence().Reg(username,passwd1,tel,email, id_card,isDriver) == true) {
                      Log.e(LogTag, "Sessionid = "+ OBOJni.getInstence().getSessionid());
    
                      if (OBOJni.getInstence().getIsDriver().equals("no")) {
                          Intent intent = new Intent();
                          intent.setClass(RegActivity.this, PassengerMapActivity.class);
                          startActivity(intent);
                      }
                      else {
                          Intent intent = new Intent();
                          intent.setClass(RegActivity.this, DriverMapActivity.class);
                          startActivity(intent);
                      }
    
                  }
                  else {
                      Toast.makeText(getApplicationContext(),
                              "链接服务器失败",Toast.LENGTH_SHORT).show();
                  }
              }
          });
    

界面源码

	public class RegActivity extends AppCompatActivity {
	
	    public static String LogTag="OBO-RegActivity";
	
	
	    private EditText et_reg_username = null;
	    private EditText et_reg_passwd1 = null;
	    private EditText et_reg_passwd2 = null;
	    private EditText et_reg_tel = null;
	    private EditText et_reg_email = null;
	    private EditText et_reg_id_card = null;
	    private Button   bt_reg_submit = null;
	    private CheckBox cb_reg_isDriver = null;
	    private boolean isDriver = false;
	
	    @Override
	    protected void onCreate(Bundle savedInstanceState) {
	        super.onCreate(savedInstanceState);
	        setContentView(R.layout.activity_reg);
	
	
	        et_reg_username = (EditText)findViewById(R.id.et_reg_username);
	        et_reg_passwd1 = (EditText)findViewById(R.id.et_reg_passwd1);
	        et_reg_passwd2 = (EditText)findViewById(R.id.et_reg_passwd2);
	        et_reg_tel = (EditText)findViewById(R.id.et_reg_tel);
	        et_reg_email =(EditText)findViewById(R.id.et_reg_email);
	        et_reg_id_card = (EditText)findViewById(R.id.et_reg_id_card);
	        bt_reg_submit =(Button)findViewById(R.id.bt_reg_submit);
	        cb_reg_isDriver = (CheckBox)findViewById(R.id.cb_is_driver);
	
	
	
	
	        cb_reg_isDriver.setOnCheckedChangeListener(new CompoundButton.OnCheckedChangeListener() {
	            @Override
	            public void onCheckedChanged(CompoundButton buttonView, boolean isChecked) {
	                if (isChecked) {
	                    isDriver = true;
	                }
	                else {
	                    isDriver = false;
	                }
	            }
	        });
	
	
	        bt_reg_submit.setOnClickListener(new View.OnClickListener() {
	            @Override
	            public void onClick(View v) {
	                //注册提交按钮被点击
	                String username = et_reg_username.getText().toString().trim();
	                String passwd1 = et_reg_passwd1.getText().toString().trim();
	                String passwd2 = et_reg_passwd2.getText().toString().trim();
	                String tel = et_reg_tel.getText().toString().trim();
	                String email = et_reg_email.getText().toString().trim();
	                String id_card = et_reg_id_card.getText().toString().trim();
	
	                if (username.length() == 0) {
	                    Toast.makeText(getApplicationContext(),
	                            "用户名为空或者非法",Toast.LENGTH_SHORT).show();
	                    return;
	                }
	
	                if (passwd1.length() == 0 || passwd2.length() == 0) {
	                    Toast.makeText(getApplicationContext(),
	                            "密码非法",Toast.LENGTH_SHORT).show();
	                    return;
	                }
	
	                if (!passwd1.equals(passwd2)) {
	                    Toast.makeText(getApplicationContext(),
	                            "两次输入的密码不一样",Toast.LENGTH_SHORT).show();
	                    return;
	                }
	
	                if (tel.length() == 0) {
	                    Toast.makeText(getApplicationContext(),
	                            "电话号码为空",Toast.LENGTH_SHORT).show();
	                    return;
	                }
	
	                if (email.length()==0) {
	                    Toast.makeText(getApplicationContext(),
	                            "email为空",Toast.LENGTH_SHORT).show();
	                    return;
	                }
	
	                if (id_card.length() == 0) {
	                    Toast.makeText(getApplicationContext(),
	                            "身份证号为空",Toast.LENGTH_SHORT).show();
	                    return;
	                }
	
	                if(OBOJni.getInstence().Reg(username,passwd1,tel,email, id_card,isDriver) == true) {
	                    Log.e(LogTag, "Sessionid = "+ OBOJni.getInstence().getSessionid());
	
	                    if (OBOJni.getInstence().getIsDriver().equals("no")) {
	                        Intent intent = new Intent();
	                        intent.setClass(RegActivity.this, PassengerMapActivity.class);
	                        startActivity(intent);
	                    }
	                    else {
	                        Intent intent = new Intent();
	                        intent.setClass(RegActivity.this, DriverMapActivity.class);
	                        startActivity(intent);
	                    }
	
	                }
	                else {
	                    Toast.makeText(getApplicationContext(),
	                            "链接服务器失败",Toast.LENGTH_SHORT).show();
	                }
	            }
	        });
	    }
	}

司机界面

  • MapView 一个地图控件,地图容器
  • AMap 高德地图接口
  • UiSettings 地图内置UI及手势控制器等,如指南针是否可见等
  • AMapLocationClient 定位服务类。此类提供单次定位、持续定位、地理围栏、最后位置相关功能
  • AMapLocationClientOption 定位参数设置

地图容器mapView

在司机界面有一大块地图容器,用来放置高德地图(获取mMap操作对象),初始化该容器的同时开启了定位服务,初始化搜索布局

	 @Override
	    protected void onCreate(Bundle savedInstanceState) {
	        super.onCreate(savedInstanceState);
	        setContentView(R.layout.activity_driver_map);
	
	        //初始化mapView 容器
	        _mapView = (MapView) findViewById(R.id.driver_map);
	        //启动mapView显示主地图
	        _mapView.onCreate(savedInstanceState);
	
	
	        //获取mMap操作对象
	        if (_amap == null) {
	            _amap = _mapView.getMap();
	
	            if (_uiSettings == null) {
	                _uiSettings = _amap.getUiSettings();
	            }
	        }
	
	        /* -------------- 初始化搜索布局 -------------- */
	        initSearchBarLayout();
	
	        //开始定位业务
	        doLocation();
	    }

搜索菜单栏

  • 该搜索菜单栏里面重要的是一个Button

      _bt_getOrder = (Button)findViewById(R.id.bt_getOrder)
    
  • 司机的状态机绑定在一个_bt_status用来同步更新搜索菜单栏Button的状态

      _bt_status = getResources().getString(R.string.DRIVER_BUTTON_STATUS_IDLE);
    
  • 初始化搜索菜单栏,初始化时,司机是没有订单的,在状态机中为idle状态,将_bt_status也赋值为DRIVER_BUTTON_STATUS_IDLE

     _bt_status = getResources().getString(R.string.DRIVER_BUTTON_STATUS_IDLE);
    

接单按钮逻辑与司机状态机

首先给改Button绑定了点击事件,每次点击时会根据司机状态机更改该搜索菜单栏的文本,同时有一些业务逻辑

  • 点击事件发生,若此时_bt_status为R.string.DRIVER_BUTTON_STATUS_IDLE,代表司机为idle,设置bt_status为READY,同时将Button“开始接单“”的文本置换为“停止接单”

      if (wei.toString().equals(getResources().getString(R.string.DRIVER_BUTTON_STATUS_IDLE))) {
             //司机为idle状态, 更变司机为ready状态,此刻代表司机已经 决定开始接单
      
            //更变司机的ready状态
          OBOJni.getInstence().setStatus(getResources().getString(R.string.DRIVER_STATUS_READY))
          _bt_status = getResources().getString(R.string.DRIVER_BUTTON_STATUS_READY);
           //这段代码的逻辑是,一开始文本为“开始接单”(初始化或者完成一旦后),司机为READY状态,_bt_status也为DRIVER_STATUS_Ready,此时已经是搜索菜单栏已经是处于等待乘客下单的状态了_getOrder_这个按钮应该文本设置为“停止接单”,因为在搜索菜单弹窗前,司机可随时选择下班了去你妈的工作
          _bt_getOrder.setText("停止接单");
       }
    
  • 点击事件发生,若此时_bt_status为DRIVER_BUTTON_STATUS_READY,已经是READY状态司机,点击按钮时,代表想要停止接单,则点击了文本早就由“开始接单变”为“停止接单”的Button

       else if (_bt_status.toString().equals(getResources().getString(R.string.DRIVER_BUTTON_STATUS_READY))) {
             //司机已经为确定停止接单
      
             //更变司机为idle状态
                 OBOJni.getInstence().setStatus(getResources().getString(R.string.DRIVER_STATUS_IDLE));
                 _bt_status = getResources().getString(R.string.DRIVER_BUTTON_STATUS_IDLE);
                 _bt_getOrder.setText("开始接单")
    
  • 注意一点,当司机点击“开始接单”后,一旦由用户下单,此时搜索菜单会弹窗显示是否接单接单,点击接单后会把司机状态置为Catching,表示去接客人,同时会把Button的文本改为“乘客已上车”在接到乘客后司机手动点击

  • 点击事件发生,若此时_bt_status为DRIVER_BUTTON_STATUS_CATCHING,已经是CATCHING状态司机,点击按钮代表已经接到了乘客,则点击文本为“乘客上车的”的Button,设置_bt_status为Driving,Button文本变为“已到达目的地”

      else if (_bt_status.toString().equals(getResources().getString(R.string.DRIVER_BUTTON_STATUS_CATCHING))) {
                      //说明已经有乘客上车
    
                      //更变司机为driving状态
                      OBOJni.getInstence().setStatus(getResources().getString(R.string.DRIVER_STATUS_DRIVE));
                      _autoSend = "yes";
    
                      _bt_status = getResources().getString(R.string.DRIVER_BUTTON_STATUS_DRIVE);
                      _bt_getOrder.setText("已抵达目的地");
    
                  }
    
  • 点击事件发生时,若此时_bt_status为DRIVER_BUTTON_STATUS_DrivING,司机状态为Driving,点击按钮表示送达乘客,则点击文本为“已抵达目的地”的Button,设置_bt_status_为Idle,同时Button文本变为“开始接单”

       else if (_bt_status.toString().equals(getResources().getString(R.string.DRIVER_BUTTON_STATUS_DRIVE))) {
                          //说明乘客已抵达目的地
      
                      //生成最终订单 完成订单
    
                      OBOJni.getInstence().FinishOrder();
    
                      //更变司机为idle状态
                      OBOJni.getInstence().setStatus(getResources().getString(R.string.DRIVER_STATUS_IDLE));
                      _bt_status = getResources().getString(R.string.DRIVER_BUTTON_STATUS_IDLE);
                      _bt_getOrder.setText("开始接单");
                  }
    

将代表司机的覆盖物加载地图上

定位服务接口

  • 实现实时定位,拿到司机经纬度
  • 调用OBOJni.getInstence().DriverLocationChanged定时自动上传司机的经纬度

注意定位服务中,针对司机的状态也会有不同的业务逻辑,这是设置的定位回调监听(即一旦定位后要处理的逻辑)

  • 如果正处于Dringving或者Catching状态时,得到乘客的坐标并给该座标加上覆盖物代表乘客

      		 if (OBOJni.getInstence().getStatus().equals(getResources().getString(R.string.DRIVER_STATUS_DRIVE)) ||
      		                                OBOJni.getInstence().getStatus().equals(getResources().getString(R.string.DRIVER_STATUS_CATCH))) 
    
  • 如果司机READY且司机信息中的orderid为0,并且乘客下单选择了该名司机,弹窗提示司机是否接单 ,如果选择“是”改变Button文本为“乘客已上车” _bt_status 改为CATCHING;否则文本改为“开始接单”_bt_status 改为“IDLE”
    - 这里之所以要判断orderid为0,是因为可能存在高德后台已经为该司机在redis中分配了orderid,但是司机还未点击接客,状态机仍未READY但是此时已经不能接客

      else if (OBOJni.getInstence().getStatus().toString().equals(getResources().getString(R.string.DRIVER_STATUS_READY)) &&
                                  !OBOJni.getInstence().getOrderid().toString().equals("NONE")) {
                                  //已经有乘客下单,并且选择该司机,提示司机是否接受订单
                                  Log.e("DriverMap", "已经有乘客下单");
                                  AlertDialog.Builder builder = new AlertDialog.Builder(DriverMapActivity.this);
                                  builder.setTitle("确认" );
                                  builder.setMessage("确定接单吗?" );
      
                                  builder.setPositiveButton("是", new DialogInterface.OnClickListener() {
                                              @Override
                                              public void onClick(DialogInterface dialog, int which) {
                                                  OBOJni.getInstence().setStatus(getResources().getString(R.string.DRIVER_STATUS_CATCH));
                                                  _bt_status = getResources().getString(R.string.DRIVER_BUTTON_STATUS_CATCHING);
                                                  _bt_getOrder.setText("乘客已上车");
                                              }
                                  });
                                  builder.setNegativeButton("否", new DialogInterface.OnClickListener() {
                                              @Override
                                              public void onClick(DialogInterface dialog, int which) {
                                                  OBOJni.getInstence().setStatus(getResources().getString(R.string.DRIVER_STATUS_IDLE));
                                                  _bt_status = getResources().getString(R.string.DRIVER_BUTTON_STATUS_IDLE);
                                                  _bt_getOrder.setText("开始接单");
      
                                              }
                                  });
                                  builder.show();
    
  • 如果乘客状态未Drinving,且此时Orderid为0,将Button文本置为“开始接单”,并将状态设置为IDLE
    else if (OBOJni.getInstence().getStatus().toString().equals(getResources().getString(R.string.DRIVER_STATUS_DRIVE)) &&
    OBOJni.getInstence().getOrderid().toString().equals(“NONE”)) {
    //该订单已经完成,更改司机为"idle"状态
    OBOJni.getInstence().setStatus(getResources().getString(R.string.DRIVER_STATUS_IDLE));
    }

    package com.example.ace.obo;

    import android.content.DialogInterface;
    import android.support.v7.app.AlertDialog;
    import android.support.v7.app.AppCompatActivity;
    import android.os.Bundle;
    import android.util.Log;
    import android.view.View;
    import android.widget.AutoCompleteTextView;
    import android.widget.Button;
    import android.widget.TextView;
    import android.widget.Toast;

    import com.amap.api.location.AMapLocation;
    import com.amap.api.location.AMapLocationClient;
    import com.amap.api.location.AMapLocationClientOption;
    import com.amap.api.location.AMapLocationListener;
    import com.amap.api.maps.AMap;
    import com.amap.api.maps.CameraUpdateFactory;
    import com.amap.api.maps.MapView;
    import com.amap.api.maps.UiSettings;
    import com.amap.api.maps.model.BitmapDescriptorFactory;
    import com.amap.api.maps.model.CameraPosition;
    import com.amap.api.maps.model.LatLng;
    import com.amap.api.maps.model.Marker;
    import com.amap.api.maps.model.MarkerOptions;
    import com.amap.api.services.core.LatLonPoint;

    public class DriverMapActivity extends AppCompatActivity {

      private MapView _mapView = null;
      private AMap _amap  = null;
      private UiSettings _uiSettings = null;
      private AMapLocationClient _amapLocationClient = null;
      private AMapLocationClientOption _amapLocationClientOption = null;
    
      private boolean _postMyLocationCenter = true;
      private String _autoSend = "no";
      private String _bt_status = null;
    
      //ui
      private Button _bt_getOrder = null;
      //司机自己的位置覆盖物
      private Marker _locationMarker = null;
      //已经接单的乘客覆盖物
      private Marker _passengerMarker = null;
    
      @Override
      protected void onCreate(Bundle savedInstanceState) {
          super.onCreate(savedInstanceState);
          setContentView(R.layout.activity_driver_map);
    
          //初始化mapView 容器
          _mapView = (MapView) findViewById(R.id.driver_map);
          //启动mapView显示主地图
          _mapView.onCreate(savedInstanceState);
    
    
          //获取mMap操作对象
          if (_amap == null) {
              _amap = _mapView.getMap();
    
              if (_uiSettings == null) {
                  _uiSettings = _amap.getUiSettings();
              }
          }
    
          /* -------------- 初始化搜索布局 -------------- */
          initSearchBarLayout();
    
          //开始定位业务
          doLocation();
      }
    
      //初始化搜索菜单栏
      public void initSearchBarLayout() {
    
    
          _bt_getOrder = (Button)findViewById(R.id.bt_getOrder);
    
          _bt_status = getResources().getString(R.string.DRIVER_BUTTON_STATUS_IDLE);
    
          _bt_getOrder.setOnClickListener(new View.OnClickListener() {
              @Override
              public void onClick(View v) {
    
                  if (wei.toString().equals(getResources().getString(R.string.DRIVER_BUTTON_STATUS_IDLE))) {
                      //司机为idle状态, 更变司机为ready状态,此刻代表司机已经 决定开始接单
    
                      //更变司机的ready状态
                      OBOJni.getInstence().setStatus(getResources().getString(R.string.DRIVER_STATUS_READY));
                      _bt_status = getResources().getString(R.string.DRIVER_BUTTON_STATUS_READY);
                      _bt_getOrder.setText("停止接单");
                  }
                  else if (_bt_status.toString().equals(getResources().getString(R.string.DRIVER_BUTTON_STATUS_READY))) {
                      //司机已经为确定停止接单
    
                      //更变司机为idle状态
                      OBOJni.getInstence().setStatus(getResources().getString(R.string.DRIVER_STATUS_IDLE));
                      _bt_status = getResources().getString(R.string.DRIVER_BUTTON_STATUS_IDLE);
                      _bt_getOrder.setText("开始接单");
                  }
                  else if (_bt_status.toString().equals(getResources().getString(R.string.DRIVER_BUTTON_STATUS_CATCHING))) {
                      //说明已经有乘客上车
    
                      //更变司机为driving状态
                      OBOJni.getInstence().setStatus(getResources().getString(R.string.DRIVER_STATUS_DRIVE));
                      _autoSend = "yes";
    
                      _bt_status = getResources().getString(R.string.DRIVER_BUTTON_STATUS_DRIVE);
                      _bt_getOrder.setText("已抵达目的地");
    
                  }
                  else if (_bt_status.toString().equals(getResources().getString(R.string.DRIVER_BUTTON_STATUS_DRIVE))) {
                      //说明乘客已抵达目的地
    
                      //生成最终订单 完成订单
    
                      OBOJni.getInstence().FinishOrder();
    
                      //更变司机为idle状态
                      OBOJni.getInstence().setStatus(getResources().getString(R.string.DRIVER_STATUS_IDLE));
                      _bt_status = getResources().getString(R.string.DRIVER_BUTTON_STATUS_IDLE);
                      _bt_getOrder.setText("开始接单");
                  }
    
              }
          });
      }
    
    
      //在指定坐标添加一个 覆盖物 图标
      public void addDriverMakerToMap( double latitude, double longitude)
      {
          //添加Marker显示定位位置
          if (_locationMarker == null) {
              //如果是空的添加一个新的,icon方法就是设置定位图标,可以自定义
              _locationMarker = _amap.addMarker(new MarkerOptions()
                      .position(new LatLng(latitude, longitude))
                      .icon(BitmapDescriptorFactory.fromResource(R.drawable.location_marker)));
              Log.e("Amap", "首次添加Drivermarker. 到 "+ latitude+", "+longitude);
          } else {
              //已经添加过了,修改位置即可
              _locationMarker.setPosition(new LatLng(latitude, longitude));
              Log.e("Amap", "重新设置Drivermarker位置 到 "+ latitude+", "+longitude);
          }
      }
    
      //在指定坐标添加一个 覆盖物 图标
      public void addPassengerMakerToMap( double latitude, double longitude)
      {
          //添加Marker显示定位位置
          if (_passengerMarker == null) {
              //如果是空的添加一个新的,icon方法就是设置定位图标,可以自定义
              _passengerMarker = _amap.addMarker(new MarkerOptions()
                      .position(new LatLng(latitude, longitude))
                      .icon(BitmapDescriptorFactory.fromResource(R.drawable.location_marker)));
              Log.e("Amap", "首次添加PassengerMarker. 到 "+ latitude+", "+longitude);
          } else {
              //已经添加过了,修改位置即可
              _passengerMarker.setPosition(new LatLng(latitude, longitude));
              Log.e("Amap", "重新设置PassengerMarker位置 到 "+ latitude+", "+longitude);
          }
      }
    
      // ============ 开启定位服务接口 ============
      public void doLocation() {
    
          /*--------------  定位接口操作(start) ------------ */
    
          /*------1 获取客户端定位对象 ---- */
          _amapLocationClient = new AMapLocationClient(getApplicationContext());
    
    
          /*------2 配置定位属性 -------*/
          //初始化AMapLocationClientOption对象
    
          _amapLocationClientOption = new AMapLocationClientOption();
    
          //设定持续定位
          //设置定位间隔,单位毫秒,默认为2000ms,最低1000ms
          _amapLocationClientOption.setInterval(2000);
    
          //_amapLocationClientOption.setOnceLocation(true);
    
          //给定位客户端对象设置定位参数
          _amapLocationClient.setLocationOption(_amapLocationClientOption);
    
    
          /* -----3 设置定位回调监听 ---- */
          _amapLocationClient.setLocationListener(new AMapLocationListener() {
              @Override
              public void onLocationChanged(AMapLocation aMapLocation) {
                  if (aMapLocation != null) {
                      if (aMapLocation.getErrorCode() == 0) {
                          //可在其中解析amapLocation获取相应内容。
                          Log.e("Amap", "address: " + aMapLocation.getAddress());
    
    
    
                          //取出经纬度
                          LatLng latLng = new LatLng(aMapLocation.getLatitude(),
                                  aMapLocation.getLongitude());
    
                          /*
                          //添加Marker显示定位位置
                          if (_locationMarker == null) {
                              //如果是空的添加一个新的,icon方法就是设置定位图标,可以自定义
                              _locationMarker = _amap.addMarker(new MarkerOptions()
                                      .position(latLng)
                                      .icon(BitmapDescriptorFactory.fromResource(R.drawable.location_marker)));
                          } else {
                              //已经添加过了,修改位置即可
                              _locationMarker.setPosition(latLng);
                          }
                          */
                          addDriverMakerToMap(aMapLocation.getLatitude(),aMapLocation.getLongitude());
    
                          // 以自我为中心 只执行一次
                          if (_postMyLocationCenter == true) {
                              //得到当前坐标点
                              CameraPosition cp = _amap.getCameraPosition();
                              //然后可以移动到定位点,使用animateCamera就有动画效果
                              _amap.animateCamera(CameraUpdateFactory.newLatLngZoom(latLng, cp.zoom));
                              _postMyLocationCenter = false;
                          }
    
    
                          //开始上传司机地理位置信息 locationChanged业务
                          OBOJni.getInstence().DriverLocationChanged(aMapLocation.getLongitude()+"",
                                  aMapLocation.getLatitude()+"",
                                  aMapLocation.getAddress()+"",
                                  _autoSend);
    
    
                          if (_autoSend.equals("yes") == true) {
                              _autoSend = "no";
                          }
    
                          if (OBOJni.getInstence().getStatus().equals(getResources().getString(R.string.DRIVER_STATUS_DRIVE)) ||
                                  OBOJni.getInstence().getStatus().equals(getResources().getString(R.string.DRIVER_STATUS_CATCH))) {
                              //正在拉客,或者 寻找乘客, 可以得到乘客坐标地址
    
                              Log.e("Amap", "ptemp_longitude = " + OBOJni.getInstence().getPtempLongitude());
                              Log.e("Amap", "ptemp_latitude = " + OBOJni.getInstence().getPtempLatitude());
    
                              //将乘客的坐标地址临时添加覆盖物
                              addPassengerMakerToMap(Double.parseDouble(OBOJni.getInstence().getPtempLatitude()),
                                           Double.parseDouble(OBOJni.getInstence().getPtempLongitude()));
                          }
    
    
    
                          else if (OBOJni.getInstence().getStatus().toString().equals(getResources().getString(R.string.DRIVER_STATUS_READY)) &&
                              !OBOJni.getInstence().getOrderid().toString().equals("NONE")) {
                              //已经有乘客下单,并且选择该司机,提示司机是否接受订单
                              Log.e("DriverMap", "已经有乘客下单");
                              AlertDialog.Builder builder = new AlertDialog.Builder(DriverMapActivity.this);
                              builder.setTitle("确认" );
                              builder.setMessage("确定接单吗?" );
    
                              builder.setPositiveButton("是", new DialogInterface.OnClickListener() {
                                          @Override
                                          public void onClick(DialogInterface dialog, int which) {
                                              OBOJni.getInstence().setStatus(getResources().getString(R.string.DRIVER_STATUS_CATCH));
                                              _bt_status = getResources().getString(R.string.DRIVER_BUTTON_STATUS_CATCHING);
                                              _bt_getOrder.setText("乘客已上车");
                                          }
                              });
                              builder.setNegativeButton("否", new DialogInterface.OnClickListener() {
                                          @Override
                                          public void onClick(DialogInterface dialog, int which) {
                                              OBOJni.getInstence().setStatus(getResources().getString(R.string.DRIVER_STATUS_IDLE));
                                              _bt_status = getResources().getString(R.string.DRIVER_BUTTON_STATUS_IDLE);
                                              _bt_getOrder.setText("开始接单");
    
                                          }
                              });
                              builder.show();
    
                          }
                          else if (OBOJni.getInstence().getStatus().toString().equals(getResources().getString(R.string.DRIVER_STATUS_DRIVE)) &&
                                  OBOJni.getInstence().getOrderid().toString().equals("NONE")) {
                              //该订单已经完成,更改司机为"idle"状态
                              OBOJni.getInstence().setStatus(getResources().getString(R.string.DRIVER_STATUS_IDLE));
                          }
    
    
                      } else {
                          //定位失败时,可通过ErrCode(错误码)信息来确定失败的原因,errInfo是错误信息,详见错误码表。
                          Log.e("Amap", "location Error, ErrCode:"
                                  + aMapLocation.getErrorCode() + ", errInfo:"
                                  + aMapLocation.getErrorInfo());
                      }
                  }
              }
          });
    
    
    
          /*--- 4 启动定位---*/
          _amapLocationClient.startLocation();
      }
      /*--------------  定位接口操作(end) ------------ */
    
    
      @Override
      protected void onResume() {
          super.onResume();
          _mapView.onResume();
      }
    
      @Override
      protected void onDestroy() {
          super.onDestroy();
          _mapView.onDestroy();
      }
    
      @Override
      protected void onPause() {
          super.onPause();
          _mapView.onPause();
      }
    
      @Override
      protected void onSaveInstanceState(Bundle outState) {
          super.onSaveInstanceState(outState);
    
          _mapView.onSaveInstanceState(outState);
      }
    

    }

总结

在司机界面的Button会根据点击事件的发生判断当前当前的业务状态改变Button的文本;而定位服务在定时定位(将司机的位置发给后端服务器)的基础上设置了定位回调监听函数,会根据前后端交互拿到的司机的状态机和Orderid字段执行不同的业务逻辑,也会改变Button的文本

乘客界面开发

  • 一个MapView 地图容器
  • 一个AMap 高德地图接口
  • AMapLocationClient
  • AMapLocationClientOption
  • Marker 定位标志
  • UiSettings
  • AutoCompleteTextView
  • TextView 用于输入地址
  • Button 下单按钮

搜索菜单栏

  • 绑定按钮并绑定监听事件:对拿到输入的地址信息做热点搜索
  • 热点搜索会显示多个兴趣点供用户选择并且会在用户设置后进行包括公交,步行,驾车的路线规划

定位服务

  • 获取客户端定位对象,设置每隔2000ms的定位间隔

设置监听回调做业务逻辑处理

  • 解析amapLocation获取当前坐标取出经纬度以及其他内容,做以自我为中心的定位
    -开始根据乘客的状态机做业务逻辑处理

  • 如过乘客状态为wait,则上传乘客地理位置信息,wait是已经下单的逻辑,

      if (OBOJni.getInstence().getStatus().toString().equals(getResources().getString(R.string.PASSENGER_STATUS_WAIT))) {
      
                                  OBOJni.getInstence().PassengerLocationChanged(aMapLocation.getLongitude()+"",
                                                                                aMapLocation.getLatitude()+"",
                                                                                aMapLocation.getAddress()+"",
                                                                                _endPoint.getLongitude()+"",
                                                                                _endPoint.getLatitude()+"",
                                                                                _finalAddr);
      							//注意这个字段,在没有司机的情况下
                                  _driverGet = false;
                              } else {
      							//此处逻辑代表是乘客为wait但是已经下单成功得到司机接单
                                  OBOJni.getInstence().PassengerLocationChanged(aMapLocation.getLongitude()+"",
                                          aMapLocation.getLatitude()+"",
                                          aMapLocation.getAddress()+"",
                                          "",
                                          "",
                                          "");
                              }
    
  • 如果乘客状态为IDLE

    • 如果没有司机,则此时将下单Button文本置为“开始约车”
    • 有司机,则将文本状态改为等待司机接单
  • 乘客状态为wait,将Button文本置为“司机已确认接单,等待司机”

  • 乘客状态为Travel,将Button文本置为“司机已确认上车,正在行驶中…”

      package com.example.ace.obo;
      
      import android.support.v7.app.AppCompatActivity;
      import android.os.Bundle;
      import android.text.Editable;
      import android.text.TextWatcher;
      import android.util.Log;
      import android.view.View;
      import android.widget.ArrayAdapter;
      import android.widget.AutoCompleteTextView;
      import android.widget.Button;
      import android.widget.TextView;
      
      import com.amap.api.location.AMapLocation;
      import com.amap.api.location.AMapLocationClient;
      import com.amap.api.location.AMapLocationClientOption;
      import com.amap.api.location.AMapLocationListener;
      import com.amap.api.maps.AMap;
      import com.amap.api.maps.CameraUpdateFactory;
      import com.amap.api.maps.MapView;
      import com.amap.api.maps.UiSettings;
      import com.amap.api.maps.model.BitmapDescriptorFactory;
      import com.amap.api.maps.model.CameraPosition;
      import com.amap.api.maps.model.LatLng;
      import com.amap.api.maps.model.Marker;
      import com.amap.api.maps.model.MarkerOptions;
      import com.amap.api.maps.overlay.DrivingRouteOverlay;
      import com.amap.api.services.core.LatLonPoint;
      import com.amap.api.services.core.PoiItem;
      import com.amap.api.services.help.Inputtips;
      import com.amap.api.services.help.InputtipsQuery;
      import com.amap.api.services.help.Tip;
      import com.amap.api.services.poisearch.PoiResult;
      import com.amap.api.services.poisearch.PoiSearch;
      import com.amap.api.services.route.BusRouteResult;
      import com.amap.api.services.route.DrivePath;
      import com.amap.api.services.route.DriveRouteResult;
      import com.amap.api.services.route.RideRouteResult;
      import com.amap.api.services.route.RouteSearch;
      import com.amap.api.services.route.WalkRouteResult;
      
      import java.util.ArrayList;
      import java.util.Date;
      import java.util.List;
      
      public class PassengerMapActivity extends AppCompatActivity {
      
          private MapView _mapView = null;
          private AMap _amap = null;
          private AMapLocationClient _amapLocationClient = null;
          private AMapLocationClientOption _amapLocationClientOption = null;
          private Marker locationMarker = null;
          private UiSettings _uiSettings = null;
          private boolean postMyLocationCenter = true;
      
          //ui
          private AutoCompleteTextView autotv_finalAddr = null;
          private Button bt_startOrder = null;
          private TextView tv_passenger_info = null;
      
          //地理数据
          private String _city = null;
          //起始出发坐标点
          private LatLonPoint _startPoint = null;
          //终止目的地坐标点
          private LatLonPoint _endPoint = null;
          //起始地点
          private String _startAddr = null;
          //终止地点
          private String _finalAddr = null;
      
          //是否有司机接单
          private boolean _driverGet = false;
          private String bt_status = null;
      
          @Override
          protected void onCreate(Bundle savedInstanceState) {
              super.onCreate(savedInstanceState);
              setContentView(R.layout.activity_passenger_map);
      
              //初始化mapView 容器
              _mapView = (MapView) findViewById(R.id.passenger_map);
              //启动mapView显示主地图
              _mapView.onCreate(savedInstanceState);
      
      
              //获取mMap操作对象
              if (_amap == null) {
                  _amap = _mapView.getMap();
      
                  if (_uiSettings == null) {
                      _uiSettings = _amap.getUiSettings();
                  }
              }
      
              /* -------------- 初始化搜索布局 -------------- */
              initSearchBarLayout();
      
              //开始定位业务
              doLocation();
      
          }
      
      
          //初始化搜索菜单栏
          public void initSearchBarLayout() {
      
              autotv_finalAddr = (AutoCompleteTextView)findViewById(R.id.autotv_passgener_finalAddr);
              bt_startOrder = (Button)findViewById(R.id.bt_startOrder);
              tv_passenger_info = (TextView)findViewById(R.id.tv_passgener_info);
      
              bt_status = getString(R.string.PASSENGER_BUTTON_STATUS_IDLE);
      
              bt_startOrder.setOnClickListener(new View.OnClickListener() {
                  @Override
                  public void onClick(View v) {
      
                      if (OBOJni.getInstence().getStatus().toString().equals(getString(R.string.DRIVER_STATUS_IDLE))) {
                          _finalAddr = autotv_finalAddr.getText().toString().trim();
                          if (_finalAddr == null) {
                              return;
                          }
      
                          doSearchPoi(_finalAddr);
      
                      }
      
                  }
              });
      
              /*--------  设置关键字模糊搜索 --------*/
              setAutoCompleteAddress();
          }
      
      
          public void doSearchPoi(String targetAddr) {
                      /* ---------------  获取POI数据 (begin)-----------------*/
              //1 定义查询条件
      
              // 参数1 查询关键字
              // 参数2 隶属范围, 如果填"" 表示不关心
              // 参数3 查询关键字地点所属城市
              PoiSearch.Query poiSearchQuery = new PoiSearch.Query(targetAddr,"", _city);
      
              //2 根据查询条件 创建 查询句柄
              PoiSearch poiSearch = new PoiSearch(getApplicationContext(), poiSearchQuery);
      
              //3 设置搜索回调
              poiSearch.setOnPoiSearchListener(new PoiSearch.OnPoiSearchListener() {
                  @Override
                  public void onPoiSearched(PoiResult poiResult, int i) {
                      //针对搜索 PoiItem集合的回调
                      if (i != 1000) {
                          Log.e("Amap", "onPoiSearched error");
                          return;
                      }
                      //获取搜索poi集合
                      List<PoiItem> poiList = poiResult.getPois();
      
                      int listnum = poiList.size();
                      for (int index = 0;index < listnum; index++) {
                          PoiItem item = poiList.get(index);
      
                          Log.e("Amap", index +
                                  " onPoiSearched  distance:"
                                  +item.getDistance()+
                                  " [AdName]: "
                                  +item.getAdName() +
                                  " [AdCode]: "
                                  +item.getAdCode()+
                                  " [AdBusinessArea]: "
                                  +item.getBusinessArea()+
                                  " [Direction]: "
                                  +item.getDirection() +
                                  " [Enter]: "
                                  +item.getEnter() +
                                  " [Title]: "
                                  +item.getTitle() +
                                  " [PoiId]: "
                                  +item.getPoiId());
                      }
      
                      /* 1. 取出第一个兴趣点 添加到 _endPoint中*/
                      PoiItem poi = poiList.get(0);
                      _endPoint = poi.getLatLonPoint();
      
                      // Log.e("Amap", "StartPoint "+_startPoint.getLatitude() +", "+_startPoint.getLongitude());
      
      
                      // =========== 得到规划路线 ==========
                      // -------(1) 得到路线搜索句柄 ----------
                      RouteSearch routeSearch = new RouteSearch(getApplication());
                      // -------(2) 设置路径源点和目的坐标点
                      RouteSearch.FromAndTo ft = new RouteSearch.FromAndTo(_startPoint,_endPoint);
      
                      Log.e("Amap", "StartPoint "+_startPoint.getLatitude() +", "+_startPoint.getLongitude());
                      Log.e("Amap", "EndPoint " + _endPoint.getLatitude() +", " +_endPoint.getLongitude());
                      // fromAndTo包含路径规划的起点和终点,drivingMode表示驾车模式
                      // 第三个参数表示途经点(最多支持16个),
                      // 第四个参数表示避让区域(最多支持32个),第五个参数表示避让道路
                      // -------(3) 设置查询条件 -----------
                      RouteSearch.DriveRouteQuery driver_query
                              = new RouteSearch.DriveRouteQuery(ft, RouteSearch.DrivingDefault, null, null, "");
      
                      // -------(4) 设置查询条件回调(主要在地图上绘图) -----------
                      routeSearch.setRouteSearchListener(new RouteSearch.OnRouteSearchListener() {
                          @Override
                          public void onBusRouteSearched(BusRouteResult busRouteResult, int i) {
                              //公交查询路线规划完成
                          }
      
                          @Override
                          public void onDriveRouteSearched(DriveRouteResult driveRouteResult, int rCode) {
                              //驾车查询路线规划完成
                              Log.e("Amap", "++++ calc end " + rCode);
      
                              if (rCode != 1000) {
                                  Log.e("Amap", "onDriveRouteSearched error rcode = "+rCode);
                                  return ;
                              }
      
                              // 主要在地图上 描绘出路径
                              // 首先清楚地图上之前绘图
                              _amap.clear();
      
                              //这里面可能会有很多种查询的路径,我们默认使用第一个driveRouteResult.getPaths().get(0)
                              DrivePath drivePath = driveRouteResult.getPaths().get(0);
                              //开始绘图 创建路径覆盖物
                              DrivingRouteOverlay drivingRouteOverlay = new DrivingRouteOverlay(
                                      getApplication(),
                                      _amap,
                                      drivePath,
                                      _startPoint,
                                      _endPoint,
                                      null
                              );
      
                              //将路径中转图标去掉,否则影响视图效果
                              drivingRouteOverlay.setNodeIconVisibility(false);
      
                              //将路线覆盖物添加到地图中
                              drivingRouteOverlay.removeFromMap();
                              drivingRouteOverlay.addToMap();
      
                              //以最适应的缩进展示效果
                              drivingRouteOverlay.zoomToSpan();
      
                              tv_passenger_info.setText("约"+driveRouteResult.getTaxiCost()+" 元");
                             // drivePath.getDuration(); //时间
      
                              bt_startOrder.setText("等待司机接单...");
      
                              //给服务器发送请求下单消息
                              _driverGet = OBOJni.getInstence().StartOrder(_startPoint.getLongitude()+"",
                                                              _startPoint.getLatitude()+"",
                                                              _startAddr,
                                                              _endPoint.getLongitude()+"",
                                                              _endPoint.getLatitude()+"",
                                                              _finalAddr,
                                                              driveRouteResult.getTaxiCost()+"");
      
      
                              Log.e("PassgerMap", "StartOrder: longitude:"+_startPoint.getLongitude() +", latitude:"+_startPoint.getLatitude());
                          }
      
                          @Override
                          public void onWalkRouteSearched(WalkRouteResult walkRouteResult, int i) {
                              //步行查询路线规划完成
                          }
      
                          @Override
                          public void onRideRouteSearched(RideRouteResult rideRouteResult, int i) {
                              //骑行查询路线规划完成
                          }
                      });
      
                      //--------(5) 启动路线规划查询
                      routeSearch.calculateDriveRouteAsyn(driver_query);
                  }
      
      
      
                  @Override
                  public void onPoiItemSearched(PoiItem poiItem, int i) {
                      //针对搜索 出每个PoiItem的回调
      
                      if (i != 1000) {
                          Log.e("Amap", "onPoiItemSearched error");
                          return;
                      }
      
                  }
      
              });
      
              //4 开始异步搜索
              poiSearch.searchPOIAsyn();
      
              /* ---------------  获取POI数据 (end)-----------------*/
          }
      
          // ============ 开启定位服务接口 ============
          public void doLocation() {
      
              /*--------------  定位接口操作(start) ------------ */
      
              /*------1 获取客户端定位对象 ---- */
              _amapLocationClient = new AMapLocationClient(getApplicationContext());
      
      
              /*------2 配置定位属性 -------*/
              //初始化AMapLocationClientOption对象
      
              _amapLocationClientOption = new AMapLocationClientOption();
      
              //设定持续定位
              //设置定位间隔,单位毫秒,默认为2000ms,最低1000ms
              _amapLocationClientOption.setInterval(2000);
      
              //_amapLocationClientOption.setOnceLocation(true);
      
              //给定位客户端对象设置定位参数
              _amapLocationClient.setLocationOption(_amapLocationClientOption);
      
      
              /* -----3 设置定位回调监听 ---- */
              _amapLocationClient.setLocationListener(new AMapLocationListener() {
                  @Override
                  public void onLocationChanged(AMapLocation aMapLocation) {
                      if (aMapLocation != null) {
                          if (aMapLocation.getErrorCode() == 0) {
                              //可在其中解析amapLocation获取相应内容。
                              Log.e("Amap", "address: " + aMapLocation.getAddress());
      
                              //获取当前所属城市
                              _city = aMapLocation.getCity();
                              _startAddr = aMapLocation.getAddress();
      
                              //获取当前坐标
                              if (_startPoint == null) {
                                  _startPoint = new LatLonPoint(0, 0);
                              }
      
                              _startPoint.setLatitude(aMapLocation.getLatitude());
                              _startPoint.setLongitude(aMapLocation.getLongitude());
      
      
                              //取出经纬度
                              LatLng latLng = new LatLng(aMapLocation.getLatitude(),
                                      aMapLocation.getLongitude());
      
                              //添加Marker显示定位位置
                              if (locationMarker == null) {
                                  //如果是空的添加一个新的,icon方法就是设置定位图标,可以自定义
                                  locationMarker = _amap.addMarker(new MarkerOptions()
                                          .position(latLng)
                                          .icon(BitmapDescriptorFactory.fromResource(R.drawable.location_marker)));
                              } else {
                                  //已经添加过了,修改位置即可
                                  locationMarker.setPosition(latLng);
                              }
      
                              // 以自我为中心 只执行一次
                              if (postMyLocationCenter == true) {
                                  //得到当前坐标点
                                  CameraPosition cp = _amap.getCameraPosition();
                                  //然后可以移动到定位点,使用animateCamera就有动画效果
                                  _amap.animateCamera(CameraUpdateFactory.newLatLngZoom(latLng, cp.zoom));
                                  postMyLocationCenter = false;
                              }
      
      
                              //开始上传乘客地理位置信息 locationChanged业务
                              if (OBOJni.getInstence().getStatus().toString().equals(getResources().getString(R.string.PASSENGER_STATUS_WAIT))) {
      
                                  OBOJni.getInstence().PassengerLocationChanged(aMapLocation.getLongitude()+"",
                                                                                aMapLocation.getLatitude()+"",
                                                                                aMapLocation.getAddress()+"",
                                                                                _endPoint.getLongitude()+"",
                                                                                _endPoint.getLatitude()+"",
                                                                                _finalAddr);
                                  _driverGet = false;
                              }
                              else {
      
                                  OBOJni.getInstence().PassengerLocationChanged(aMapLocation.getLongitude()+"",
                                          aMapLocation.getLatitude()+"",
                                          aMapLocation.getAddress()+"",
                                          "",
                                          "",
                                          "");
                              }
      
                              //设置乘客按钮文本
                              if(OBOJni.getInstence().getStatus().toString().equals(getString(R.string.PASSENGER_STATUS_IDLE))) {
                                  if (_driverGet == false) {
                                      bt_startOrder.setText("开始约车");
                                  }
                                  else {
                                      bt_startOrder.setText("等待司机接单...");
                                  }
                              }
                              else if (OBOJni.getInstence().getStatus().toString().equals(getString(R.string.PASSENGER_STATUS_WAIT))) {
                                  bt_startOrder.setText("司机已经接单,等待司机...");
                              }
                              else if (OBOJni.getInstence().getStatus().toString().equals(getString(R.string.PASSENGER_STATUS_TRAVEL))) {
                                  bt_startOrder.setText("司机已确认上车,正在行驶中...");
                              }
      
      
      
                              } else {
                              //定位失败时,可通过ErrCode(错误码)信息来确定失败的原因,errInfo是错误信息,详见错误码表。
                              Log.e("Amap", "location Error, ErrCode:"
                                      + aMapLocation.getErrorCode() + ", errInfo:"
                                      + aMapLocation.getErrorInfo());
                          }
                      }
                  }
              });
      
      
      
              /*--- 4 启动定位---*/
              _amapLocationClient.startLocation();
          }
          /*--------------  定位接口操作(end) ------------ */
      
      
          void setAutoCompleteAddress() {
      
              //默认2个字才会开启匹配列表显示,这里改为1个字就开始显示
              autotv_finalAddr.setThreshold(1);
      
              autotv_finalAddr.addTextChangedListener(new TextWatcher() {
                  //控件内容 改变之前会触发此回调
                  @Override
                  public void beforeTextChanged(CharSequence s, int start, int count, int after) {
      
                  }
      
                  //当ui控件的内容发生改变,会触发此回调
                  @Override
                  public void onTextChanged(CharSequence s, int start, int before, int count) {
                      //得到用户输入的 关键字
                      final String keyword = autotv_finalAddr.getText().toString().trim();
      
      
                      if (keyword ==null || keyword.length() == 0) {
                          return;
                      }
      
                      Log.e("Amap", "乘客匹配到的模糊关键字是 " + keyword);
      
      
                      /*
                      得到根据此模糊关键字搜索到的全部模糊匹配的地址 集合
                      此集合由高德地图提供,不需要我们自己写模糊算法
                      */
      
                      // 得到查询条件
                      InputtipsQuery query = new InputtipsQuery(keyword, _city);
                      // 得到查询点搜索句柄(实际上高德地图会根据 搜索关键字 来定位匹配的地址)
                      Inputtips search = new Inputtips(getApplicationContext(), query);
      
                      // 设置 定位监听回调
                      search.setInputtipsListener(new Inputtips.InputtipsListener() {
                          @Override
                          public void onGetInputtips(List<Tip> list, int rCode) {
                              // 高德地图会将全部定位到的 地址 放在list列表中,每个元素类型是Tip
      
                              // 下面就是将全部的地址信息,放在我们的_autotv_keyword控件中
      
                              // 1 首先将Tip list信息封装到一个 ArrayList<String>中
      
                              ArrayList<String> resultList = new ArrayList<String>();
                              for (int i = 0;i < list.size(); i++) {
                                  resultList.add(list.get(i).getName());
                                  Log.e("Amap", "根据 " + keyword + "匹配到的结果" + list.get(i).toString());
      
                              }
      
                              // 2 创建一个根据ArrayList<String>的ArrayAdapter<String>
                              ArrayAdapter<String> resultAdapter = new ArrayAdapter<String>(
                                      getApplicationContext(),
                                      android.R.layout.simple_list_item_1,
                                      resultList
                              );
      
                              // 3 将这个Adapter设置给AutoCompleteTextView控件
                              autotv_finalAddr.setAdapter(resultAdapter);
      
                              // 4 启动通知 ,一旦这个Adapter数据内容发生改变,告知控件
                              resultAdapter.notifyDataSetChanged();
                          }
                      });
      
                      // 开始 定位
                      search.requestInputtipsAsyn();
                  }
      
                  //控件内容 改变之后会触发此回调
                  @Override
                  public void afterTextChanged(Editable s) {
      
                  }
              });
          }
      
          @Override
          protected void onResume() {
              super.onResume();
              _mapView.onResume();
          }
      
          @Override
          protected void onDestroy() {
              super.onDestroy();
              _mapView.onDestroy();
          }
      
          @Override
          protected void onPause() {
              super.onPause();
              _mapView.onPause();
          }
      
          @Override
          protected void onSaveInstanceState(Bundle outState) {
              super.onSaveInstanceState(outState);
      
              _mapView.onSaveInstanceState(outState);
          }
      }
    

总结

乘客界面主要是调用高德地图接口实现乘客的自我为中心定位,输入目的地址的热点搜索线路规划,下单按钮只需乘客的点击一次,之后都是根据乘客状态被动切换显示打车业务逻辑的进度

OBOJni.java

OBOJni这个类作为单例模式类实现,提供了许多静态方法作为业务逻辑接口

  • 通用的:登陆,注册,设置获得button状态,获得会话id,获得订单id,获得IsDriver字段,获得临时经纬度,获得重点经纬度,结束订单JNI接口

  • 司机相关的司机端定位,

  • 乘客相关的乘客端定位,开始下单接口

      package com.example.ace.obo;
      
      /**
       * Created by Ace on 2016/11/18.
       */
      
      public class OBOJni {
      
      public static OBOJni getInstence() {
          if (obj == null) {
              obj = new OBOJni();
          }
    
          return obj;
      }
    
      protected static OBOJni obj = null;
    
    
      static {
          // libOBOjni.so
          System.loadLibrary("OBOjni");
      }
    
      //登陆 JNI模块
      public native boolean Login(String username, String passwd, boolean isDriver);
    
      //注册 JNI模块
      public native boolean Reg(String username,
                                String passwd,
                                String tel,
                                String email,
                                String idcard,
                                boolean isDriver);
      //开始下单 JNI模块
      public native boolean StartOrder(String src_longitude,
                                       String src_latitude,
                                       String src_address,
                                       String dst_longitude,
                                       String dst_latitude,
                                       String dst_address,
                                       String RMB);
    
      //司机端定位发生改变,上传地理位置信息 JNI模块
      public native  boolean DriverLocationChanged(String longitude,
                                                   String latitude,
                                                   String address,
                                                   String autoSend);
    
      //乘客端定位发生改变,上传地理位置信息 JNI模块
      public native  boolean PassengerLocationChanged(String longitude,
                                                      String latitude,
                                                      String address,
                                                      String dst_longitude,
                                                      String dst_latitude,
                                                      String dst_address);
    
      public native boolean FinishOrder();
    
      public native void setStatus(String status);
    
      public native String getOrderid();
      public native String getSessionid();
      public native String getStatus();
      public native String getIsDriver();
      public native String getPtempLongitude();
      public native String getPtempLatitude();
      public native String getDtempLongitude();
      public native String getDtempLatitude();
    
      public native void testLibcurl();
    

    }

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值