Advertisement

android 获取蓝牙信号强度,连接后获取蓝牙RSSI信号强度

阅读量:

在连接到某款智能手机(如Android设备)时(或手机),能够实时捕捉并记录周围环境中的蓝牙信号;进一步地,在完成设备配对之后(或完成配对操作),系统会自动采集并存储对应的RSSI值数据。


第一种:基于扫瞄的方法

优势在于其内置支持。
然而,在操作过程中存在两个主要缺陷:一方面 scan 过程所需时间较长;另一方面操作过程中缺乏对中间步骤的监控。
为了持续进行测量操作,则需要不断地执行 scan 过程。
在连接建立的过程中无法实现蓝牙扫描功能。

第二种:基于连接的方法

在必要条件下,在完成两个蓝牙设备的连接后,在完成之后进行RSSI测量,在完成之后能够实现便于后续的测量工作,并且其间隔时间较为短暂。

复制代码
    package com.example.health;
    
    import android.app.Activity;
    import android.app.ProgressDialog;
    import android.bluetooth.BluetoothAdapter;
    import android.bluetooth.BluetoothDevice;
    import android.bluetooth.BluetoothManager;
    import android.content.BroadcastReceiver;
    import android.content.ComponentName;
    import android.content.Context;
    import android.content.DialogInterface;
    import android.content.Intent;
    import android.content.IntentFilter;
    import android.content.ServiceConnection;
    import android.content.SharedPreferences;
    import android.os.Bundle;
    import android.os.Handler;
    import android.os.IBinder;
    import android.support.annotation.NonNull;
    import android.support.design.widget.NavigationView;
    import android.support.v4.app.Fragment;
    import android.support.v4.app.FragmentManager;
    import android.support.v4.app.FragmentPagerAdapter;
    import android.support.v4.view.GravityCompat;
    import android.support.v4.view.ViewPager;
    import android.support.v4.widget.DrawerLayout;
    import android.support.v7.app.AlertDialog;
    import android.support.v7.app.AppCompatActivity;
    import android.text.TextUtils;
    import android.util.Log;
    import android.view.MenuItem;
    import android.view.View;
    import android.widget.ImageView;
    import android.widget.TextView;
    import android.widget.Toast;
    
    import com.example.health.db.Config;
    import com.example.health.fragment.FriendsFragment;
    import com.example.health.fragment.HomeFragment;
    import com.example.health.fragment.TestFragment;
    import com.example.health.service.UartService;
    import com.google.gson.Gson;
    
    import org.json.JSONObject;
    
    import java.io.UnsupportedEncodingException;
    import java.text.DateFormat;
    import java.text.SimpleDateFormat;
    import java.util.ArrayList;
    import java.util.Date;
    import java.util.HashMap;
    import java.util.List;
    import java.util.Map;
    import java.util.Timer;
    import java.util.TimerTask;
    
    import butterknife.BindView;
    import butterknife.ButterKnife;
    import butterknife.OnClick;
    
    public class Main extends AppCompatActivity implements NavigationView.OnNavigationItemSelectedListener ,Config.HttpData{
    
    private final static String TAG = "Main";
    //    private static final int REQUEST_SELECT_DEVICE = 1;
    private static final int REQUEST_ENABLE_BT = 2;
    private static final int UART_PROFILE_CONNECTED = 20;
    private static final int UART_PROFILE_DISCONNECTED = 21;
    @BindView(R.id.tv_main)
    TextView tvMain;
    @BindView(R.id.tv_test)
    TextView tvTest;
    @BindView(R.id.tv_friend)
    TextView tvFriend;
    @BindView(R.id.viewPager)
    ViewPager viewPager;
    @BindView(R.id.nav_view)
    NavigationView navView;
    @BindView(R.id.iv_light)
    ImageView ivLight;
    @BindView(R.id.iv_buy)
    ImageView ivBuy;
    private int mState = UART_PROFILE_DISCONNECTED;
    private UartService mService = null;
    private BluetoothAdapter mBtAdapter = null;
    private BluetoothAdapter mBluetoothAdapter;
    
    private HomeFragment homeFragment;
    private FriendsFragment friendsFragment;
    private TestFragment testFragment;
    private List<Fragment> fragments;
    
    SharedPreferences sp;
    ProgressDialog mProgressDialog;
    Gson gson;
    List<BluetoothDevice> deviceList;
    Map<String, Integer> devRssiValues;
    private static final long SCAN_PERIOD = 10000; //10 seconds
    private Handler mHandler;
    private boolean mScanning;
    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main2);
        ButterKnife.bind(this);
        mHandler = new Handler();
        initView();
        gson=new Gson();
        mProgressDialog=new ProgressDialog(this);
        sp=getSharedPreferences("health",MODE_PRIVATE);
        Config.service_ip = sp.getString("ip", "");
        Config.service_port = Integer.parseInt(sp.getString("port", "-1"));
        Config.HOST="http://"+Config.service_ip+":"+Config.service_port+"/";
        Config.phone=sp.getString("phone","");
        Config.step=sp.getInt(dataformat2.format(new Date()),0);
        Config.isOpen=sp.getBoolean("isOpen",true);
        int hour1 = sp.getInt("hour1",8);
        int hour2 = sp.getInt("hour2",12);
        int hour3 = sp.getInt("hour3",20);
        int time1 = sp.getInt("time1",0);
        int time2 = sp.getInt("time2",0);
        int time3 = sp.getInt("time3",0);
        Date date=new Date();
        date.setHours(hour1);
        date.setMinutes(time1);
        date.setSeconds(0);
        Config.time1=date.getTime();
        date.setHours(hour2);
        date.setMinutes(time2);
        Config.time2=date.getTime();
        date.setHours(hour3);
        date.setMinutes(time3);
        Config.time3=date.getTime();
    
        Config.service_port = Integer.parseInt(sp.getString("port", "-1"));
        Config.userid = sp.getString("userid", "-1");
        Log.e(TAG,"userid"+sp.getString("userid", "-1"));
        if(Config.phone.isEmpty()||Config.phone==""){
            Toast.makeText(Main.this, "请填写报警联系人", Toast.LENGTH_SHORT).show();
        }
        if(Config.service_ip.isEmpty()||Config.service_ip==""){
            Toast.makeText(Main.this, "请填写服务器IP", Toast.LENGTH_SHORT).show();
        }
        if(Config.service_port==-1){
            Toast.makeText(Main.this, "请填写服务器端口号", Toast.LENGTH_SHORT).show();
        }
        mBtAdapter = BluetoothAdapter.getDefaultAdapter();
        final BluetoothManager bluetoothManager =
                (BluetoothManager) getSystemService(Context.BLUETOOTH_SERVICE);
        mBluetoothAdapter = bluetoothManager.getAdapter();
    
        if (mBtAdapter == null) {
            Toast.makeText(this, "Bluetooth is not available", Toast.LENGTH_LONG).show();
            finish();
            return;
        }
        service_init();
        navView.setNavigationItemSelectedListener(this);
    }
    
    private void populate() {
        Log.e(TAG,"正在搜索蓝牙");
        deviceList = new ArrayList<BluetoothDevice>();
        devRssiValues = new HashMap<String, Integer>();
        mHandler.postDelayed(new Runnable() {
            @Override
            public void run() {
                mScanning = false;
                mBluetoothAdapter.stopLeScan(mLeScanCallback);
            }
        }, SCAN_PERIOD);
        mBluetoothAdapter.startLeScan(mLeScanCallback);
    }
    //获取到搜索的蓝牙节点
    private BluetoothAdapter.LeScanCallback mLeScanCallback =
            new BluetoothAdapter.LeScanCallback() {
    
                @Override
                public void onLeScan(final BluetoothDevice device, final int rssi, byte[] scanRecord) {
                    if(device.getName().equals("Intelligent insole")) {
                        String deviceAddress = device.getAddress();
                        Config.mDevice = BluetoothAdapter.getDefaultAdapter().getRemoteDevice(deviceAddress);
                        //  获得到连接的蓝牙设备
                        mService.connect(deviceAddress);
                    }
                }
            };
    
    private void initView() {
        homeFragment = new HomeFragment();
        testFragment = new TestFragment();
        friendsFragment = new FriendsFragment();
        fragments = new ArrayList<>();
        fragments.add(homeFragment);
        fragments.add(testFragment);
        fragments.add(friendsFragment);
        MyFragmentAdapter adapter = new MyFragmentAdapter(getSupportFragmentManager());
        viewPager.setAdapter(adapter);
        viewPager.setOffscreenPageLimit(3);
        viewPager.addOnPageChangeListener(new ViewPager.OnPageChangeListener() {
            @Override
            public void onPageScrolled(int position, float positionOffset, int positionOffsetPixels) {
            }
    
            @Override
            public void onPageSelected(int position) {
                if (position == 0) {
                    ivBuy.setVisibility(View.VISIBLE);
                    ivLight.setVisibility(View.INVISIBLE);
                    setUnSelected();
                    tvMain.setSelected(true);
                } else if (position == 1) {
                    ivBuy.setVisibility(View.INVISIBLE);
                    ivLight.setVisibility(View.VISIBLE);
                    setUnSelected();
                    tvTest.setSelected(true);
                } else if (position == 2) {
                    setUnSelected();
                    tvFriend.setSelected(true);
                    ivBuy.setVisibility(View.INVISIBLE);
                    ivLight.setVisibility(View.INVISIBLE);
                }
            }
    
            @Override
            public void onPageScrollStateChanged(int state) {
    
            }
        });
        tvMain.setSelected(true);
    }
    
    public void setUnSelected() {
        tvMain.setSelected(false);
        tvTest.setSelected(false);
        tvFriend.setSelected(false);
    }
    
    
    class MyFragmentAdapter extends FragmentPagerAdapter {
    
        public MyFragmentAdapter(FragmentManager fm) {
            super(fm);
        }
    
        @Override
        public Fragment getItem(int position) {
            return fragments.get(position);
        }
    
        @Override
        public int getCount() {
            return fragments.size();
        }
    }
    
    //UART service connected/disconnected
    private ServiceConnection mServiceConnection = new ServiceConnection() {
        public void onServiceConnected(ComponentName className, IBinder rawBinder) {
            mService = ((UartService.LocalBinder) rawBinder).getService();
            Log.d(TAG, "onServiceConnected mService= " + mService);
            if (!mService.initialize()) {
                Log.e(TAG, "Unable to initialize Bluetooth");
                finish();
            }
            mService.addCallback(Main.this);
        }
    
        public void onServiceDisconnected(ComponentName classname) {
            mService = null;
        }
    };
    
    private void service_init() {
        Intent bindIntent = new Intent(this, UartService.class);
        bindService(bindIntent, mServiceConnection, Context.BIND_AUTO_CREATE);
        registerReceiver(UARTStatusChangeReceiver, makeGattUpdateIntentFilter());
    
        if (!mBtAdapter.isEnabled()) {
            Log.i(TAG, "onClick - BT not enabled yet");
            Intent enableIntent = new Intent(BluetoothAdapter.ACTION_REQUEST_ENABLE);
            startActivityForResult(enableIntent, REQUEST_ENABLE_BT);
        } else {
            if (!Config.isConnect&&!Config.userid.equals("-1")) {
                populate();
            } else {
                if (Config.mDevice != null) {
                    mService.disconnect();
                    Config.isConnect = false;
                }
            }
        }
    }
    
    private static IntentFilter makeGattUpdateIntentFilter() {
        final IntentFilter intentFilter = new IntentFilter();
        intentFilter.addAction(UartService.ACTION_GATT_CONNECTED);
        intentFilter.addAction(UartService.ACTION_GATT_DISCONNECTED);
        intentFilter.addAction(UartService.ACTION_GATT_SERVICES_DISCOVERED);
        intentFilter.addAction(UartService.ACTION_DATA_AVAILABLE);
        intentFilter.addAction(UartService.DEVICE_DOES_NOT_SUPPORT_UART);
        return intentFilter;
    }
    
    @Override
    protected void onResume() {
        super.onResume();
        if(mService!=null) {
            byte[] value = new byte[0];
            try {
                //send data to service
                value = ("t" + dataformat1.format(Config.time1) + "|" + dataformat1.format(Config.time2) + "|" + dataformat1.format(Config.time3)).getBytes("GBK");
                Log.e(TAG, "" + (mService == null));
                mService.writeRXCharacteristic(value);
            } catch (Exception e) {
                e.printStackTrace();
            }
        }
    }
    
    @Override
    public void onActivityResult(int requestCode, int resultCode, Intent data) {
        switch (requestCode) {
            case REQUEST_ENABLE_BT:
                // When the request to enable Bluetooth returns
                if (resultCode == Activity.RESULT_OK) {
                    Toast.makeText(this, "蓝牙打开成功", Toast.LENGTH_SHORT).show();
                } else {
                    // User did not enable Bluetooth or an error occurred
                    Log.d(TAG, "BT not enabled");
                    Toast.makeText(this, "蓝牙打开存在问题", Toast.LENGTH_SHORT).show();
                    finish();
                }
                break;
            default:
                Log.e(TAG, "wrong request code");
                break;
        }
    }
    
    @OnClick({R.id.iv_light, R.id.iv_buy, R.id.tv_main, R.id.tv_test, R.id.tv_friend,R.id.iv_search})
    public void onViewClicked(View view) {
        switch (view.getId()) {
            case R.id.iv_buy:
                Toast.makeText(Main.this, "购买成功!", Toast.LENGTH_SHORT).show();
                break;
            case R.id.iv_search:
                populate();
                break;
            case R.id.tv_main:
                ivBuy.setVisibility(View.VISIBLE);
                ivLight.setVisibility(View.INVISIBLE);
                setUnSelected();
                tvMain.setSelected(true);
                viewPager.setCurrentItem(0);
                break;
            case R.id.tv_test:
                ivBuy.setVisibility(View.INVISIBLE);
                ivLight.setVisibility(View.VISIBLE);
                setUnSelected();
                tvTest.setSelected(true);
                viewPager.setCurrentItem(1);
                break;
            case R.id.tv_friend:
                ivBuy.setVisibility(View.INVISIBLE);
                ivLight.setVisibility(View.INVISIBLE);
                setUnSelected();
                tvFriend.setSelected(true);
                viewPager.setCurrentItem(2);
                break;
        }
    }
    
    @Override
    public boolean onNavigationItemSelected(@NonNull MenuItem item) {
    
        switch (item.getItemId()) {
            case R.id.nav_user:
                Intent user;
                if (Config.userid.equals("-1")){
                    user = new Intent(this, LoginActivity.class);
                } else {
                    user = new Intent(this, UserInfoActivity.class);
                }
                startActivity(user);
                break;
            case R.id.nav_set:
                Intent set;
                set = new Intent(this, SetActivity.class);
                startActivity(set);
                break;
            case R.id.nav_info:
                Intent info = new Intent(this, InfoActivity.class);
                info.putExtra("title", "关于");
                info.putExtra("content", getString(R.string.info));
                startActivity(info);
                break;
            case R.id.nav_smile:
                Intent smile = new Intent(this, InfoActivity.class);
                smile.putExtra("title", "团队信息");
                smile.putExtra("content", getString(R.string.smile));
                startActivity(smile);
                break;
            case R.id.nav_up:
                Toast.makeText(this, "当前已是最新版本", Toast.LENGTH_SHORT).show();
                break;
            case R.id.nav_out:
                Config.user = null;
                Config.userid="-1";
                SharedPreferences.Editor editor=sp.edit();
                editor.putString("userid","-1");
                editor.commit();
                break;
    
    
        }
        DrawerLayout drawer = (DrawerLayout) findViewById(R.id.drawer_layout);
        drawer.closeDrawer(GravityCompat.START);
        return true;
    }
    
    @Override
    public void onStop() {
        super.onStop();
        mBluetoothAdapter.stopLeScan(mLeScanCallback);
    
    }
    
    @Override
    public void onBackPressed() {
        if (mState == UART_PROFILE_CONNECTED) {
            Intent startMain = new Intent(Intent.ACTION_MAIN);
            startMain.addCategory(Intent.CATEGORY_HOME);
            startMain.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
            startActivity(startMain);
            showMessage("退出后蓝牙连接未断开");
        }
        else {
            new AlertDialog.Builder(this)
                    .setIcon(android.R.drawable.ic_dialog_alert)
                    .setTitle(R.string.popup_title)
                    .setMessage(R.string.popup_message)
                    .setPositiveButton(R.string.popup_yes, new DialogInterface.OnClickListener()
                    {
                        @Override
                        public void onClick(DialogInterface dialog, int which) {
                            finish();
                        }
                    })
                    .setNegativeButton(R.string.popup_no, null)
                    .show();
        }
    }
    
    @Override
    protected void onDestroy() {
        super.onDestroy();
        unregisterReceiver(UARTStatusChangeReceiver);
        unbindService(mServiceConnection);
        mBluetoothAdapter.stopLeScan(mLeScanCallback);
        if (mService != null) {
            mService.close();
            Config.isConnect=false;
            mService = null;
            Config.mDevice=null;
        }
    }
    SimpleDateFormat dataformat=new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
    SimpleDateFormat dataformat2=new SimpleDateFormat("yyyyMMdd");
    SimpleDateFormat dataformat1=new SimpleDateFormat("HH:mm");
    Timer timer=new Timer();
    private final BroadcastReceiver UARTStatusChangeReceiver = new BroadcastReceiver() {
    
        public void onReceive(Context context, Intent intent) {
            String action = intent.getAction();
            Log.e(TAG,"action:"+action);
            //*********************//
            if (action.equals(UartService.ACTION_GATT_CONNECTED)) {
                runOnUiThread(new Runnable() {
                    public void run() {
                        // 连接成功  mDevice.getName()
                        upDateDeivceInfo();
                        Log.d(TAG, "UART_CONNECT_MSG");
                        ivLight.setImageResource(R.mipmap.lamp_active);
                        mState = UART_PROFILE_CONNECTED;
                        Config.isConnect = true;
                        timer=new Timer();
                        timer.schedule(new TimerTask() {
                            @Override
                            public void run() {
                                byte[] value = new byte[0];
                                try {
                                    //send data to service
                                    value = ("n"+dataformat.format(new Date())).getBytes("GBK");
                                    Log.e(TAG,""+(mService==null));
                                    mService.writeRXCharacteristic(value);
                                } catch (Exception e) {
                                    e.printStackTrace();
                                }
                            }
                        },1000,5000);
                    }
    
                });
            }
    
            //*********************//
            if (action.equals(UartService.ACTION_GATT_DISCONNECTED)) {
                runOnUiThread(new Runnable() {
                    public void run() {
                        String currentDateTimeString = DateFormat.getTimeInstance().format(new Date());
                        Log.d(TAG, "UART_DISCONNECT_MSG");
                        // 连接断开  mDevice.getName()
                        if(timer!=null) {
                            timer.cancel();
                            timer = null;
                        }
                        Config.isConnect = false;
                        ivLight.setImageResource(R.mipmap.lamp_off);
    
                        mState = UART_PROFILE_DISCONNECTED;
                        mService.close();
                        //setUiState();
    
                    }
                });
            }
    
    
            //*********************//
            if (action.equals(UartService.ACTION_GATT_SERVICES_DISCOVERED)) {
                mService.enableTXNotification();
            }
            //*********************//
            if (action.equals(UartService.ACTION_DATA_AVAILABLE)) {
    
                final byte[] txValue = intent.getByteArrayExtra(UartService.EXTRA_DATA);
                runOnUiThread(new Runnable() {
                    public void run() {
                        try {
                            String text = new String(txValue, "GBK");
                            //TODO  接收到数据   text
                            Log.e(TAG,"接收到数据:"+text);
                            if(text.startsWith("n")){
                                if(timer!=null) {
                                    timer.cancel();
                                    timer=null;
                                }
                                byte[] value = new byte[0];
                                try {
                                    //send data to service
                                    value = ("t"+dataformat1.format(Config.time1)+"|"+dataformat1.format(Config.time2)+"|"+dataformat1.format(Config.time3)).getBytes("GBK");
                                    Log.e(TAG,""+(mService==null));
                                    mService.writeRXCharacteristic(value);
                                } catch (Exception e) {
                                    e.printStackTrace();
                                }
                            }
    
                        } catch (Exception e) {
                            Log.e(TAG, e.toString());
                        }
                    }
                });
            }
            //*********************//
            if (action.equals(UartService.DEVICE_DOES_NOT_SUPPORT_UART)) {
                showMessage("参数错误,未连接。重启app或将蓝牙设备距离手机近些");
                mService.disconnect();
            }
    
    
        }
    };
    
    private void showMessage(String msg) {
        Toast.makeText(this, msg, Toast.LENGTH_SHORT).show();
    
    }
    private void upDateDeivceInfo() {
        if(!Config.userid.equals("-1")) {
            com.loopj.android.http.RequestParams params = new com.loopj.android.http.RequestParams();
            params.put("name", Config.mDevice.getName());
            params.put("mac", Config.mDevice.getAddress());
            params.put("userid", Config.userid);
            mProgressDialog.setMessage("正在提交设备信息");
            Config.getFromPC(this, this, mProgressDialog, Config.HOST + Config.Upload_device, params);
        }else{
            Toast.makeText(Main.this, "当前未登录", Toast.LENGTH_SHORT).show();
        }
    }
    @Override
    public void doUI(String url, String s) {
    }
    }

全部评论 (0)

还没有任何评论哟~