• Android BLE 蓝牙编程(四)


    接上篇,我们已经实现了短震,长震的功能了~

    现在我们需要实现点击后一直震动的功能

    开始我的想法是再循环中不断执行write方法,然而这个办法行不通。

    系统会报错。

    那要如何实现这个想法呢?其实很简单,使用service实现轮询就行

    那想到了解决方案就着手实现方法吧!!

    写个服务:

    package com.wbnq.ryadie.service;
    
    import android.app.AlarmManager;
    import android.app.IntentService;
    import android.app.PendingIntent;
    import android.app.Service;
    import android.bluetooth.BluetoothGatt;
    import android.bluetooth.BluetoothGattCharacteristic;
    import android.content.Intent;
    import android.os.IBinder;
    import android.os.SystemClock;
    import android.util.Log;
    
    import com.wbnq.ryadie.HexUtil;
    import com.wbnq.ryadie.OfflineApplication;
    import com.wbnq.ryadie.R;
    import com.wbnq.ryadie.StaticData;
    import com.wbnq.ryadie.broadcast.AlarmReceiver;
    
    import java.util.Date;
    
    import static com.wbnq.ryadie.StaticData.GATDATA;
    import static com.wbnq.ryadie.StaticData.GATPOWER;
    
    /**
     * Created by guwei on 16-9-20.
     */
    public class ReadData extends Service {
    
        BluetoothGatt bluetoothGatt;
        BluetoothGattCharacteristic bleGattCharacteristic;
    
        OfflineApplication application;
        boolean isrunning;
    
        public static final String TAG = "ReadData_service";
    
        //    @Nullable
        @Override
        public IBinder onBind(Intent intent) {
            return null;
        }
    
    
        @Override
        public int onStartCommand(Intent intent, int flags, int startId) {
            application = (OfflineApplication) getApplication();
    
            isrunning = application.getIsthreadrunning();
            //这里开辟一条线程,用来执行具体的逻辑操作:
            new Thread(new Runnable() {
                @Override
                public void run() {
                    Log.d("BackService", new Date().toString());
                    bleGattCharacteristic = application.getCharacteristic();
                    bluetoothGatt = application.getBluetoothGatt();
    
                    if (isrunning) {
                        Log.e(TAG, "run: 开始轮询服务");
                        //向设备发送获取数据的命令
                        write(GATDATA);
                        try {
                            Thread.sleep(200);
                        } catch (InterruptedException e) {
                            e.printStackTrace();
                        }
                        //向设备发送获取电量的命令
                        write(GATPOWER);
                    } else {
                        Log.e(TAG, "run: 停止轮询服务");
    
                    }
                }
            }).start();
    
            AlarmManager manager = (AlarmManager) getSystemService(ALARM_SERVICE);
            //这里是定时的,这里设置的是每隔两秒打印一次时间=-=,自己改
            int anHour = 20 * 1000;
            long triggerAtTime = SystemClock.elapsedRealtime() + anHour;
            Intent i = new Intent(this, AlarmReceiver.class);
            PendingIntent pi = PendingIntent.getBroadcast(this, 0, i, 0);
            manager.set(AlarmManager.ELAPSED_REALTIME_WAKEUP, triggerAtTime, pi);
            return super.onStartCommand(intent, flags, startId);
        }
    
        //向设备写入命令方法
        private void write(String commond) {
    
            Log.i(TAG, "write: in write 	 " + bluetoothGatt + "	" + bleGattCharacteristic);
    
            if (bleGattCharacteristic != null && bluetoothGatt != null) {
                bleGattCharacteristic.setValue(HexUtil.hexStringToBytes(commond));
                bluetoothGatt.writeCharacteristic(bleGattCharacteristic);
                commond = null;
            }
        }
    
        @Override
        public void onDestroy() {
            super.onDestroy();
            Log.e(TAG, "onDestroy: ");
        }
    }
    View Code

    不过服务里面想要执行写方法需要获取到主Activity下获取过的两个数据:

    bleGattCharacteristic

    bluetoothGatt

    这个要怎么传递过来呢?

    其实方法很多,我这里用个简单的

    全局变量Application 方法就行。

    package com.wbnq.ryadie;
    
    import android.app.Application;
    import android.bluetooth.BluetoothGatt;
    import android.bluetooth.BluetoothGattCharacteristic;
    
    /**
     * Created by guwei on 16-9-20.
     */
    public class OfflineApplication extends Application {
    
        private BluetoothGatt bluetoothGatt;
        private BluetoothGattCharacteristic characteristic;
    
    
        private Boolean isthreadrunning ;
    
    
        @Override
        public void onCreate() {
            super.onCreate();
            setBluetoothGatt(null);
            setCharacteristic(null);
            setIsthreadrunning(false);
        }
    
        public Boolean getIsthreadrunning() {
            return isthreadrunning;
        }
    
        public void setIsthreadrunning(Boolean isthreadrunning) {
            this.isthreadrunning = isthreadrunning;
        }
    
        public BluetoothGatt getBluetoothGatt() {
            return bluetoothGatt;
        }
    
        public void setBluetoothGatt(BluetoothGatt bluetoothGatt) {
            this.bluetoothGatt = bluetoothGatt;
        }
    
        public BluetoothGattCharacteristic getCharacteristic() {
            return characteristic;
        }
    
        public void setCharacteristic(BluetoothGattCharacteristic characteristic) {
            this.characteristic = characteristic;
        }
    }
    View Code

    名字我随便取的

    大家可以起个好理解的。

    如何设置全局变量呢?也很简单。

    首先获取到application:

     myapplication = (OfflineApplication) getApplication();

    然后设置相应的值:

    //设置全局变量的值
                    myapplication.setCharacteristic(bleGattCharacteristic);
                    myapplication.setBluetoothGatt(bluetoothGatt);

    这就是设置。

    获取呢?

    也很简单:

     bleGattCharacteristic = application.getCharacteristic();
     bluetoothGatt = application.getBluetoothGatt();

    很简单对吧?

    那么我如何开启服务呢?方法也很多。在这里我就使用广播的方式:

    广播接收器:

    package com.wbnq.ryadie.broadcast;
    
    import android.content.BroadcastReceiver;
    import android.content.Context;
    import android.content.Intent;
    import android.util.Log;
    
    import com.wbnq.ryadie.service.ReadData;
    
    /**
     * Created by guwei on 16-9-20.
     */
    public class AlarmReceiver extends BroadcastReceiver {
        String TAG = "AlarmReceiver";
    
        @Override
        public void onReceive(Context context, Intent intent ) {
            Intent i = new Intent(context, ReadData.class);
            context.startService(i);
    
    
            context.stopService(i);
            Log.e(TAG, "onReceive: onReceive");
        }
    }

    接收到广播后就调用start方法就好了!很简单对吧~

    别忘了想要使用广播,全局变量,服务都是需要注册的。

    <?xml version="1.0" encoding="utf-8"?>
    <manifest xmlns:android="http://schemas.android.com/apk/res/android"
        package="com.wbnq.ryadie">
    
        <uses-permission android:name="android.permission.BLUETOOTH" />
        <uses-permission android:name="android.permission.BLUETOOTH_ADMIN" />
    
        <!-- Android6.0 蓝牙扫描才需要-->
        <uses-permission-sdk-23 android:name="android.permission.ACCESS_COARSE_LOCATION" />
    
        <uses-permission android:name="android.permission.ACCESS_COARSE_LOCATION" />
        <uses-permission android:name="android.permission.ACCESS_FINE_LOCATION" />
    
    
        <application
            android:name=".OfflineApplication"
            android:allowBackup="true"
            android:icon="@mipmap/ic_launcher"
            android:label="@string/app_name"
            android:supportsRtl="true"
            android:theme="@style/AppTheme">
            <activity android:name=".MainActivity">
                <intent-filter>
                    <action android:name="android.intent.action.MAIN" />
    
                    <category android:name="android.intent.category.LAUNCHER" />
                </intent-filter>
            </activity>
            
            <service android:name="com.wbnq.ryadie.service.ReadData" />
    
            <receiver android:name=".broadcast.AlarmReceiver">
                <intent-filter>
                    <action android:name="com.guwei.READDATA"/>
                </intent-filter>
            </receiver>
        </application>
    
    
    </manifest>

    最后一步,找对地方发送广播~

     sendBroadcast(new Intent("com.guwei.READDATA"));

    恭喜你啦,现在你已经可以让你的手环震动到停不下来!~~

    哈哈

    下节我们来分析下服务的代码吧!

    本节写的很仓促,有错的地方欢迎指正!~~

  • 相关阅读:
    cron表达式
    mybatis中的#{}和${}
    mysql免安装版使用
    关于jpa添加一对多数据时外键值为空的问题
    关于时间格式化和格式转换
    属性和属性节点
    ErrorException: ORA-00904: : 标识符无效
    345. 反转字符串中的元音字母
    java 解决nginx代理的跨域访问问题
    633. 平方数之和
  • 原文地址:https://www.cnblogs.com/wobeinianqing/p/5886756.html
Copyright © 2020-2023  润新知