Partage
  • Partager sur Facebook
  • Partager sur Twitter

Bluetooth avec plusieurs fragments Android Studio

Sujet résolu
Anonyme
    19 mars 2018 à 11:20:33

    Bonjour à tous, 

    Pour un projet, je dois créer une application Android qui devra communiquer avec une Raspberry via le bluetooth. Cependant, comme j'ai plusieurs "pages" sur l'application, j'ai réaliser un Navigation Drawer qui me permet d'utiliser des fragments. Mais c'est là que j'ai un problème avec ma communication bluetooth:

    - dans un des fragments, j'établis la communication avec un appareil:

    package com.gxabt.uliege.microspectro_v1.Controllers.Fragments;
    
    import android.Manifest;
    import android.app.Fragment;
    import android.bluetooth.BluetoothAdapter;
    import android.bluetooth.BluetoothDevice;
    import android.content.BroadcastReceiver;
    import android.content.Context;
    import android.content.Intent;
    import android.content.IntentFilter;
    import android.os.Build;
    import android.os.Bundle;
    import android.support.v4.content.LocalBroadcastManager;
    import android.util.Log;
    import android.view.LayoutInflater;
    import android.view.View;
    import android.view.ViewGroup;
    import android.widget.AdapterView;
    import android.widget.Button;
    import android.widget.ListView;
    
    import com.gxabt.uliege.microspectro_v1.Models.BluetoothConnectionService;
    import com.gxabt.uliege.microspectro_v1.Models.DeviceListAdapter;
    import com.gxabt.uliege.microspectro_v1.R;
    
    import java.nio.charset.Charset;
    import java.util.ArrayList;
    import java.util.Set;
    import java.util.UUID;
    
    
    public class ConnectionFragment extends Fragment implements AdapterView.OnItemClickListener {
        private static final String TAG = "ConnectionFragment";
        private static final UUID MY_UUID_INSECURE = UUID.fromString("00001105-0000-1000-8000-00805F9B34FB");
    
        public ArrayList<BluetoothDevice> mBTDevices;
        public Set<BluetoothDevice> mDeviceBonded;
        public DeviceListAdapter mDeviceListAdapter;
    
        BluetoothConnectionService mBluetoothConnection;
        BluetoothAdapter mBluetoothAdapter;
        BluetoothDevice mBTDevice;
        ListView lvDevices;
        Button btnStartConnection;
        Button btnSearch;
        StringBuilder message;
    
        public static ConnectionFragment newInstance() {
            return (new ConnectionFragment());
        }
    
        @Override
        public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
            View rootView = inflater.inflate(R.layout.fragment_connection, container, false);
    
            mBTDevices = new ArrayList<>();
    
            mBluetoothAdapter = BluetoothAdapter.getDefaultAdapter();
    
            mDeviceBonded = mBluetoothAdapter.getBondedDevices();
    
            lvDevices = (ListView) rootView.findViewById(R.id.list_devices);
    
            for (BluetoothDevice bt : mDeviceBonded)
            {
                mBTDevices.add(bt);
            }
    
            mDeviceListAdapter = new DeviceListAdapter(getActivity(), R.layout.device_adapteur_view, mBTDevices);
            lvDevices.setAdapter(mDeviceListAdapter);
    
            IntentFilter filter = new IntentFilter(BluetoothDevice.ACTION_BOND_STATE_CHANGED);
            getActivity().registerReceiver(mBroadcastReceiverBound, filter);
            lvDevices.setOnItemClickListener(ConnectionFragment.this);
    
            btnStartConnection = (Button) rootView.findViewById(R.id.fragment_connect_btn_start);
            btnStartConnection.setOnClickListener(new View.OnClickListener()
            {
                @Override
                public void onClick(View view) {
                    startConnection();
                }
            });
    
            btnSearch = (Button) rootView.findViewById(R.id.fragment_connect_btn_search);
            btnSearch.setOnClickListener(new View.OnClickListener()
            {
                @Override
                public void onClick(View view)
                {
                    Log.d(TAG, "btnDiscover: Looking for unpaired devices...");
    
                    if (mBluetoothAdapter.isDiscovering()) {
                        mBluetoothAdapter.cancelDiscovery();
                        Log.d(TAG, "btnDiscover: Canceling discovery.");
    
                        //Check BT permissions in manifest
                        checkBTPermissions();
    
                        mBluetoothAdapter.startDiscovery();
                        IntentFilter discoverDevicesIntent = new IntentFilter(BluetoothDevice.ACTION_FOUND);
                        getActivity().registerReceiver(mBroadcastReceiverDiscover, discoverDevicesIntent);
                    }
                    if (!mBluetoothAdapter.isDiscovering()) {
                        //Check BT permissions in manifest
                        checkBTPermissions();
    
                        mBluetoothAdapter.startDiscovery();
                        IntentFilter discoverDevicesIntent = new IntentFilter(BluetoothDevice.ACTION_FOUND);
                        getActivity().registerReceiver(mBroadcastReceiverDiscover, discoverDevicesIntent);
                    }
                }
            });
    
            message = new StringBuilder();
            LocalBroadcastManager.getInstance(getActivity()).registerReceiver(mReceiver, new IntentFilter("incomingMessage"));
    
            return rootView;
        }
    
    
        public void startBTConnection(BluetoothDevice device, UUID uuid) {
            Log.d(TAG, "startBTConnection: Initializing RFCOM Bluetooth Connection");
    
            mBluetoothConnection.startClient(device, uuid);
            String msg = "bp_reprod";
            byte[] bytes = msg.getBytes(Charset.defaultCharset());
            mBluetoothConnection.write(bytes);
        }
    
        //Remember the connection will fail and app will crash if you haven't paired first
        public void startConnection()
        {
            startBTConnection(mBTDevice, MY_UUID_INSECURE);
        }
    
        /**
         *   Discover new devices.
         *   This broadcast receiver is use for listening devices that are not yet paired.
         */
        private final BroadcastReceiver mBroadcastReceiverDiscover = new BroadcastReceiver() {
            @Override
            public void onReceive(Context context, Intent intent) {
                final String action = intent.getAction();
                Log.d(TAG, "onReciver: ACTION FOUND.");
    
                if (action.equals(BluetoothDevice.ACTION_FOUND)) {
                    BluetoothDevice device = intent.getParcelableExtra(BluetoothDevice.EXTRA_DEVICE);
                    Log.d(TAG, "onReceive: " + device.getName() + " : " + device.getAddress());
    
                    int i = 0;
                    for (; i < mBTDevices.size(); i++) {
                        if (device.getAddress().equals(mBTDevices.get(i).getAddress())) {
                            break;
                        }
                    }
    
                    if (i == mBTDevices.size()) {
                        mBTDevices.add(device);
                    }
    
                    mDeviceListAdapter = new DeviceListAdapter(context, R.layout.device_adapteur_view, mBTDevices);
                    lvDevices.setAdapter(mDeviceListAdapter);
                }
            }
        };
    
        /**
         *   Bounding devices.
         */
        private final BroadcastReceiver mBroadcastReceiverBound = new BroadcastReceiver() {
            @Override
            public void onReceive(Context context, Intent intent) {
                final String action = intent.getAction();
    
                if (action.equals(BluetoothDevice.ACTION_BOND_STATE_CHANGED)) {
                    BluetoothDevice mDevice = intent.getParcelableExtra(BluetoothDevice.EXTRA_DEVICE);
                    // Case 1: bounded already
                    if (mDevice.getBondState() == BluetoothDevice.BOND_BONDED) {
                        Log.d(TAG, "BroadcastReceiver: BOND_BONDED.");
    
                        mBTDevice = mDevice;
                    }
                    // Case 2: creating a bone
                    if (mDevice.getBondState() == BluetoothDevice.BOND_BONDING) {
                        Log.d(TAG, "BroadcastReceiver: BOND_BONDING.");
                    }
                    // Case 3: breaking a bond
                    if (mDevice.getBondState() == BluetoothDevice.BOND_NONE) {
                        Log.d(TAG, "BroadcastReceiver: BOND_NONE.");
                    }
                }
            }
        };
    
        BroadcastReceiver mReceiver = new BroadcastReceiver() {
            @Override
            public void onReceive(Context context, Intent intent) {
                String text = intent.getStringExtra("theMessage");
    
                message.append(text + "\n");
            }
        };
        /**
         *   Check permissions method.
         *   This method is required for all devices running API23+.
         *   Android must programmatically check the permissions for Bluetooth.
         *   Putting the proper permissions in the manifest is not enough.
         *
         *   NOTE: This will only execute on version >LOLLIPOP because it is not needed otherwise.
         */
        public void checkBTPermissions() {
            if (Build.VERSION.SDK_INT > Build.VERSION_CODES.LOLLIPOP) {
                int permissionCheck = this.getActivity().checkSelfPermission("Manifest.permission.ACCESS_FINE_LOCATION");
                permissionCheck += this.getActivity().checkSelfPermission("Manifest.permission.ACCESS_COARSE_LOCATION");
                if (permissionCheck != 0) {
                    this.requestPermissions(new String[]{Manifest.permission.ACCESS_FINE_LOCATION, Manifest.permission.ACCESS_COARSE_LOCATION}, 1001); //Any number
                }
            } else {
                Log.d(TAG, "checkBTPermissions: No need to check permissions. SDK version < LOLLIPOP.");
            }
        }
    
        /**
         *   Bounding device - item click
         */
        @Override
        public void onItemClick(AdapterView<?> adapterView, View view, int i, long l) {
            //First cancel discovery because its very memory intensive.
            mBluetoothAdapter.cancelDiscovery();
            Log.d(TAG, "onItemClick: You Clicked on a device.");
            String deviceName = mBTDevices.get(i).getName();
            String deviceAddress = mBTDevices.get(i).getAddress();
    
            Log.d(TAG, "onItemClick: " + deviceName);
            Log.d(TAG, "onItemClick: " + deviceAddress);
    
            //Create the bond
            //NOTE: Requires API 17+
            if (Build.VERSION.SDK_INT > Build.VERSION_CODES.ICE_CREAM_SANDWICH_MR1) {
                Log.d(TAG, "Trying to pair with " + deviceName);
                mBTDevices.get(i).createBond();
    
                mBTDevice = mBTDevices.get(i);
                mBluetoothConnection = new BluetoothConnectionService(getActivity());
            }
        }
    }

    - Dans un autre fragment, je dois envoyé une information à la Raspberry par l'appui d'un bouton (cette action devra être réalisée dans plusieurs fragments, mais pour tester, vaut mieux développer que sur un seul)

    package com.gxabt.uliege.microspectro_v1.Controllers.Fragments;
    
    import android.app.Fragment;
    import android.os.Bundle;
    import android.view.LayoutInflater;
    import android.view.View;
    import android.view.ViewGroup;
    import android.widget.Button;
    
    import com.gxabt.uliege.microspectro_v1.Controllers.Activities.MainActivity;
    import com.gxabt.uliege.microspectro_v1.Models.BluetoothConnectionService;
    import com.gxabt.uliege.microspectro_v1.R;
    
    import java.nio.charset.Charset;
    
    public class ReproductionFragment extends Fragment
    {
        Button btnReprod;
        BluetoothConnectionService mBluetoothConnection;
        MainActivity sendData;
    
        public static ReproductionFragment newInstance()
        {
            return (new ReproductionFragment());
        }
    
        @Override
        public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState)
        {
            View rootView = inflater.inflate(R.layout.fragment_reproduction, container, false);
    
            btnReprod = (Button) rootView.findViewById(R.id.fragment_reprod_btn_reprod);
            mBluetoothConnection = new BluetoothConnectionService(getActivity());
            btnReprod.setOnClickListener(new View.OnClickListener()
            {
                @Override
                public void onClick(View view)
                {
                    String msg = "bp_reprod";
                    byte[] bytes = msg.getBytes(Charset.defaultCharset());
                    try
                    {
                        mBluetoothConnection.write(bytes);
                    }
                    catch (NullPointerException e)
                    {
                        e.printStackTrace();
                    }
                }
            });
    
            return rootView;
        }
    }

    Pour la connexion à la raspberry, je n'ai aucuns problème (donc le premier code fonctionne bien) mais lorsque je change de fragment, et que je clique sur le bouton qui me permet d'envoyer l'information j'ai un message d'erreur :

    03-19 11:11:02.134 8790-8790/com.gxabt.uliege.microspectro_v1 W/System.err: java.lang.NullPointerException
    03-19 11:11:02.134 8790-8790/com.gxabt.uliege.microspectro_v1 W/System.err:     at com.gxabt.uliege.microspectro_v1.Models.BluetoothConnectionService.write(BluetoothConnectionService.java:367)
    03-19 11:11:02.134 8790-8790/com.gxabt.uliege.microspectro_v1 W/System.err:     at com.gxabt.uliege.microspectro_v1.Controllers.Fragments.ReproductionFragment$1.onClick(ReproductionFragment.java:46)
    03-19 11:11:02.134 8790-8790/com.gxabt.uliege.microspectro_v1 W/System.err:     at android.view.View.performClick(View.java:4147)
    03-19 11:11:02.134 8790-8790/com.gxabt.uliege.microspectro_v1 W/System.err:     at android.view.View$PerformClick.run(View.java:17161)
    03-19 11:11:02.134 8790-8790/com.gxabt.uliege.microspectro_v1 W/System.err:     at android.os.Handler.handleCallback(Handler.java:615)
    03-19 11:11:02.134 8790-8790/com.gxabt.uliege.microspectro_v1 W/System.err:     at android.os.Handler.dispatchMessage(Handler.java:92)
    03-19 11:11:02.134 8790-8790/com.gxabt.uliege.microspectro_v1 W/System.err:     at android.os.Looper.loop(Looper.java:213)
    03-19 11:11:02.134 8790-8790/com.gxabt.uliege.microspectro_v1 W/System.err:     at android.app.ActivityThread.main(ActivityThread.java:4786)
    03-19 11:11:02.134 8790-8790/com.gxabt.uliege.microspectro_v1 W/System.err:     at java.lang.reflect.Method.invokeNative(Native Method)
    03-19 11:11:02.134 8790-8790/com.gxabt.uliege.microspectro_v1 W/System.err:     at java.lang.reflect.Method.invoke(Method.java:511)
    03-19 11:11:02.134 8790-8790/com.gxabt.uliege.microspectro_v1 W/System.err:     at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:789)
    03-19 11:11:02.134 8790-8790/com.gxabt.uliege.microspectro_v1 W/System.err:     at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:556)
    03-19 11:11:02.134 8790-8790/com.gxabt.uliege.microspectro_v1 W/System.err:     at dalvik.system.NativeStart.main(Native Method)

    Je pense que c'est une initialisation dans le deuxième fragment qui fait tout planter mais je ne sais pas quoi. Pouvez-vous m'aider ?

    Merci. 

    -
    Edité par Anonyme 19 mars 2018 à 11:54:47

    • Partager sur Facebook
    • Partager sur Twitter
      8 avril 2019 à 14:22:05

      Bonjour,

      Je dois faire une application dans le même esprit. As-tu trouvé une solution à ton problème? 

      • Partager sur Facebook
      • Partager sur Twitter

      Bluetooth avec plusieurs fragments Android Studio

      × Après avoir cliqué sur "Répondre" vous serez invité à vous connecter pour que votre message soit publié.
      × Attention, ce sujet est très ancien. Le déterrer n'est pas forcément approprié. Nous te conseillons de créer un nouveau sujet pour poser ta question.
      • Editeur
      • Markdown