1

やあ、ブルートゥース経由のアンドロイドマルチプレイヤーゲームに取り組んでいます。4人のプレイヤーが互いに接続してゲームをプレイするマルチプレイヤーLUDOゲームです。

3 番目と 4 番目のプレーヤーの接続でスタックしています。

private OnMaxConnectionsReachedListener maxConnectionsListener = new OnMaxConnectionsReachedListener() {
    public void OnMaxConnectionsReached() {

    }
};

private OnIncomingConnectionListener connectedListener = new OnIncomingConnectionListener() {
    public void OnIncomingConnection(String device) {
        //rivalDevice = device;
        if(index < 1000)
        {
            clients[index] = device;
            index++;
            Log.d("Khawar", "Khawar"+device);
            if(index == 1)
            {
                //blue.setText(clients[0]);
                mConnection.sendMessage(clients[0], "ConnectionList--Ludofyp309509--"+server+"--Ludofyp309509--"+clients[0]);
            }
            else if(index == 2)
            {
                //blue.setText(clients[0]);
                //red.setText(clients[1]);
                mConnection.sendMessage(clients[0], "ConnectionList--Ludofyp309509--"+server+"--Ludofyp309509--"+clients[0]+"--Ludofyp309509--"+clients[1]);
                mConnection.sendMessage(clients[1], "ConnectionList--Ludofyp309509--"+server+"--Ludofyp309509--"+clients[0]+"--Ludofyp309509--"+clients[1]);
            }
            else if(index==3)
            {
                //blue.setText(clients[0]);
                //red.setText(clients[1]);
                //yellow.setText(clients[2]);
                mConnection.sendMessage(clients[0], "ConnectionList--Ludofyp309509--"+server+"--Ludofyp309509--"+clients[0]+"--Ludofyp309509--"+clients[1]+"--Ludofyp309509--"+clients[2]);
                mConnection.sendMessage(clients[1], "ConnectionList--Ludofyp309509--"+server+"--Ludofyp309509--"+clients[0]+"--Ludofyp309509--"+clients[1]+"--Ludofyp309509--"+clients[2]);
                mConnection.sendMessage(clients[2], "ConnectionList--Ludofyp309509--"+server+"--Ludofyp309509--"+clients[0]+"--Ludofyp309509--"+clients[1]+"--Ludofyp309509--"+clients[2]);
            }
        }
        //Toast.makeText(getBaseContext(), "Client found" + device , Toast.LENGTH_LONG).show();
      //  WindowManager w = getWindowManager();
      //  Display d = w.getDefaultDisplay();
       // int width = d.getWidth();
        //int height = d.getHeight();
    }
};

private OnConnectionLostListener disconnectedListener = new OnConnectionLostListener() {
    public void OnConnectionLost(String device) {
        class displayConnectionLostAlert implements Runnable {
            public void run() {
                Builder connectionLostAlert = new Builder(self);

                connectionLostAlert.setTitle("Connection lost");
                connectionLostAlert
                        .setMessage("Your connection with the other player has been lost.");

                connectionLostAlert.setPositiveButton("Ok", new OnClickListener() {
                    public void onClick(DialogInterface dialog, int which) {
                        finish();
                    }
                });
                connectionLostAlert.setCancelable(false);
                try {
                connectionLostAlert.show();
                } catch (BadTokenException e){
                    Log.v("TAG", "Exception throws here");
                }
            }
        }
        self.runOnUiThread(new displayConnectionLostAlert());
    }
};

private OnConnectionServiceReadyListener serviceReadyListener = new OnConnectionServiceReadyListener() {
    public void OnConnectionServiceReady() {
        if (mType == 0) {
            mConnection.startServer(1, connectedListener, maxConnectionsListener,
                    dataReceivedListener, disconnectedListener);
            self.setTitle("LudoOverAndroid: " + mConnection.getName() + "-" + mConnection.getAddress());
            server = mConnection.getAddress();
            green.setText(server);
            Log.v("1", server);
      //      Intent Game = new Intent(self, Board.class);
            // .putExtra("TYPE", 1);
        //     startActivity(Game);

        } else {

            self.setTitle("LudoOverAndroid: " + mConnection.getName() + "-" + mConnection.getAddress());
            Intent serverListIntent = new Intent(self, ServerListActivity.class);
            startActivityForResult(serverListIntent, SERVER_LIST_RESULT_CODE);
            clients[index] = mConnection.getAddress();
         //   Intent Game = new Intent(self, Board.class);
            // .putExtra("TYPE", 1);
         //    startActivity(Game);

        }
    }
};

上記は接続を確立するサンプルコードです。しかし、接続サービス クラスには次のコードがあります。

       public int connect(String srcApp, String device) throws RemoteException {
        if (mApp.length() > 0) {
            Log.v("a", "connection service->connect->mApp.length");
            return Connection.FAILURE;
        }
        mApp = srcApp;
        BluetoothDevice myBtServer = mBtAdapter.getRemoteDevice(device);
        BluetoothSocket myBSock = null;
        Log.v("a", "Yaah aya hay aik baar nahe bar bar :");
        for (int i = 0; i < Connection.MAX_SUPPORTED && myBSock == null; i++) {
            for (int j = 0; j < 3 && myBSock == null; j++) {
                myBSock = getConnectedSocket(myBtServer, mUuid.get(i));
                if (myBSock == null) {
                    try {
                        Log.v("a", "connection service->connect->myBSock==NULL thread sleep");
                        Thread.sleep(200);
                    } catch (InterruptedException e) {
                        Log.e(TAG, "InterruptedException in connect", e);
                    }
                }
            }
        }
        if (myBSock == null) {
            Log.v("a", "connection service->connect->myBSock==NULLss");
            return Connection.FAILURE;
        }
        mBtSockets.put(device, myBSock);
        mBtDeviceAddresses.add(device);
        Thread mBtStreamWatcherThread = new Thread(new BtStreamWatcher(device));
        mBtStreamWatcherThread.start();
        mBtStreamWatcherThreads.put(device, mBtStreamWatcherThread);
        return Connection.SUCCESS;
    }

モバイルが 3 番目または 4 番目のデバイスに接続すると、myBSock==null が返されます。ただし、コードが正しく機能する場合は、デバイスのアドレスを返す必要があり、mBtDeviceAddresses.add(device); を追加する必要があります。サーバーリストに。

問題の解決にご協力ください。

前もって感謝します

4

2 に答える 2

4
package com.switching.bluetooth;

import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;
import java.util.ArrayList;
import java.util.UUID;

import android.bluetooth.BluetoothAdapter;
import android.bluetooth.BluetoothDevice;
import android.bluetooth.BluetoothServerSocket;
import android.bluetooth.BluetoothSocket;
import android.content.Context;
import android.os.Bundle;
import android.os.Handler;
import android.os.Message;
import android.util.Log;

import com.switching.ServerMainActivity;

/**
 * This class does all the work for setting up and managing Bluetooth
 * connections with other devices. It has a thread that listens for incoming
 * connections, a thread for connecting with a device, and a thread for
 * performing data transmissions when connected.
 */
public class BluetoothService {
    // Debugging
    private static final String TAG = "BluetoothService iBT";
    private static final boolean D = true;

    // Name for the SDP record when creating server socket
    private static final String NAME = "i BT";

    // Unique UUID for this application
    private static UUID MY_UUID;

    // Member fields
    private final BluetoothAdapter mAdapter;
    private final Handler mHandler;
    private AcceptThread mAcceptThread;
    private ConnectThread mConnectThread;
    private ConnectedThread mConnectedThread;
    private int mState;

    private ArrayList<String> mDeviceAddresses;
    private ArrayList<String> mDeviceNames;
    private ArrayList<ConnectedThread> mConnThreads;
    private ArrayList<BluetoothSocket> mSockets;

    /**
     * A bluetooth piconet can support up to 7 connections. This array holds 7
     * unique UUIDs. When attempting to make a connection, the UUID on the
     * client must match one that the server is listening for. When accepting
     * incoming connections server listens for all 7 UUIDs. When trying to form
     * an outgoing connection, the client tries each UUID one at a time.
     */
    private ArrayList<UUID> mUuids;

    // Constants that indicate the current connection state
    public static final int STATE_NONE = 0; // we're doing nothing
    public static final int STATE_LISTEN = 1; // now listening for incoming
                                                // connections
    public static final int STATE_CONNECTING = 2; // now initiating an outgoing
                                                    // connection
    public static final int STATE_CONNECTED = 3; // now connected to a remote
                                                    // device

    /**
     * Constructor. Prepares a new BluetoothChat session.
     * 
     * @param context
     *            The UI Activity Context
     * @param handler
     *            A Handler to send messages back to the UI Activity
     */
    public BluetoothService(Context context, Handler handler) {
        mAdapter = BluetoothAdapter.getDefaultAdapter();
        mState = STATE_NONE;
        mHandler = handler;

        initializeArrayLists();

        // 7 randomly-generated UUIDs. These must match on both server and
        // client.
        // mUuids.add(UUID.fromString("b7746a40-c758-4868-aa19-7ac6b3475dfc"));
        // mUuids.add(UUID.fromString("2d64189d-5a2c-4511-a074-77f199fd0834"));
        // mUuids.add(UUID.fromString("e442e09a-51f3-4a7b-91cb-f638491d1412"));
        // mUuids.add(UUID.fromString("a81d6504-4536-49ee-a475-7d96d09439e4"));
        // mUuids.add(UUID.fromString("aa91eab1-d8ad-448e-abdb-95ebba4a9b55"));
        // mUuids.add(UUID.fromString("4d34da73-d0a4-4f40-ac38-917e0a9dee97"));
        // mUuids.add(UUID.fromString("5e14d4df-9c8a-4db7-81e4-c937564c86e0"));
    }

    public static UUID getMY_UUID() {
        return MY_UUID;
    }

    public static void setMY_UUID(UUID mY_UUID) {
        MY_UUID = mY_UUID;
    }

    public boolean isDeviceConnectedAtPosition(int position) {
        if (mConnThreads.get(position) == null) {
            return false;
        }
        return true;
    }

    private void initializeArrayLists() {
        mDeviceAddresses = new ArrayList<String>(5);
        mDeviceNames = new ArrayList<String>(5);
        mConnThreads = new ArrayList<ConnectedThread>(5);
        mSockets = new ArrayList<BluetoothSocket>(5);
        mUuids = new ArrayList<UUID>(5);

        for (int i = 0; i < 5; i++) {
            mDeviceAddresses.add(null);
            mDeviceNames.add(null);
            mConnThreads.add(null);
            mSockets.add(null);
            mUuids.add(null);
        }

        Log.i(TAG, "mConnThreads.size() in Service Constructor--"
                + mConnThreads.size());
    }

    public ArrayList<String> getmDeviceNames() {
        return this.mDeviceNames;
    }

    public void setmDeviceNames(ArrayList<String> mDeviceNames) {
        this.mDeviceNames = mDeviceNames;
    }

    public ArrayList<String> getmDeviceAddresses() {
        return mDeviceAddresses;
    }

    public void setmDeviceAddresses(ArrayList<String> mDeviceAddresses) {
        this.mDeviceAddresses = mDeviceAddresses;
    }

    /**
     * Set the current state of the chat connection
     * 
     * @param state
     *            An integer defining the current connection state
     */
    private synchronized void setState(int state) {
        if (D)
            Log.d(TAG, "setState() " + mState + " -> " + state);
        mState = state;

        // Give the new state to the Handler so the UI Activity can update
        mHandler.obtainMessage(ServerMainActivity.MESSAGE_STATE_CHANGE, state,
                -1).sendToTarget();
    }

    /**
     * Return the current connection state.
     */
    public synchronized int getState() {
        return mState;
    }

    /**
     * Start the chat service. Specifically start AcceptThread to begin a
     * session in listening (server) mode. Called by the Activity onResume()
     */
    public synchronized void start() {
        if (D)
            Log.d(TAG, "start");

        // Cancel any thread attempting to make a connection
        if (mConnectThread != null) {
            mConnectThread.cancel();
            mConnectThread = null;
        }

        // Cancel any thread currently running a connection
        if (mConnectedThread != null) {
            mConnectedThread.cancel();
            mConnectedThread = null;
        }

        // Start the thread to listen on a BluetoothServerSocket
        if (mAcceptThread == null) {
            mAcceptThread = new AcceptThread();
            mAcceptThread.start();
        }
        setState(STATE_LISTEN);
    }

    /**
     * Start the ConnectThread to initiate a connection to a remote device.
     * 
     * @param device
     *            The BluetoothDevice to connect
     */
    public synchronized void connect(BluetoothDevice device,
            int selectedPosition) {

        if (getPositionIndexOfDevice(device) == -1) {
            if (D)
                Log.d(TAG, "connect to: " + device);

            // Cancel any thread attempting to make a connection
            if (mState == STATE_CONNECTING) {
                if (mConnectThread != null) {
                    mConnectThread.cancel();
                    mConnectThread = null;
                }
            }

            // Cancel any thread currently running a connection
            if (mConnThreads.get(selectedPosition) != null) {
                mConnThreads.get(selectedPosition).cancel();
                // mConnectedThread = null;
                mConnThreads.set(selectedPosition, null);
            }

            // Create a new thread and attempt to connect to each UUID
            // one-by-one.
            try {

                // String
                // s="00001101-0000-1000-8000"+device.getAddress().split(":");
                ConnectThread mConnectThread = new ConnectThread(device,
                        UUID.fromString("00001101-0000-1000-8000-"
                                + device.getAddress().replace(":", "")),
                        selectedPosition);
                Log.i(TAG, "uuid-string at server side"
                        + ("00001101-0000-1000-8000" + device.getAddress()
                                .replace(":", "")));
                mConnectThread.start();
                setState(STATE_CONNECTING);
            } catch (Exception e) {
            }
        } else {
            Message msg = mHandler
                    .obtainMessage(ServerMainActivity.MESSAGE_TOAST);
            Bundle bundle = new Bundle();
            bundle.putString(ServerMainActivity.TOAST,
                    "This device " + device.getName() + " Already Connected");
            msg.setData(bundle);
            mHandler.sendMessage(msg);
        }
    }

    /**
     * Start the ConnectedThread to begin managing a Bluetooth connection
     * 
     * @param socket
     *            The BluetoothSocket on which the connection was made
     * @param device
     *            The BluetoothDevice that has been connected
     */
    public synchronized void connected(BluetoothSocket socket,
            BluetoothDevice device, int selectedPosition) {
        if (D)
            Log.d(TAG, "connected");
        /*
         * // Cancel the thread that completed the connection if (mConnectThread
         * != null) { mConnectThread.cancel(); mConnectThread = null; }
         * 
         * // Cancel any thread currently running a connection if
         * (mConnectedThread != null) { mConnectedThread.cancel();
         * mConnectedThread = null; }
         * 
         * // Cancel the accept thread because we only want to connect to one //
         * device if (mAcceptThread != null) { mAcceptThread.cancel();
         * mAcceptThread = null; }
         */
        // Start the thread to manage the connection and perform transmissions
        ConnectedThread mConnectedThread = new ConnectedThread(socket);
        mConnectedThread.start();
        // Add each connected thread to an array
        mConnThreads.set(selectedPosition, mConnectedThread);

        // Send the name of the connected device back to the UI Activity
        Message msg = mHandler
                .obtainMessage(ServerMainActivity.MESSAGE_DEVICE_NAME);
        Bundle bundle = new Bundle();
        bundle.putString(ServerMainActivity.DEVICE_NAME, device.getName());
        msg.setData(bundle);
        mHandler.sendMessage(msg);
        setState(STATE_CONNECTED);
    }

    /**
     * Stop all threads
     */
    public synchronized void stop() {
        if (D)
            Log.d(TAG, "stop");
        if (mConnectThread != null) {
            mConnectThread.cancel();
            mConnectThread = null;
        }
        if (mConnectedThread != null) {
            mConnectedThread.cancel();
            mConnectedThread = null;
        }
        if (mAcceptThread != null) {
            mAcceptThread.cancel();
            mAcceptThread = null;
        }

        for (int i = 0; i < 5; i++) {
            mDeviceNames.set(i, null);
            mDeviceAddresses.set(i, null);
            mSockets.set(i, null);
            if (mConnThreads.get(i) != null) {
                mConnThreads.get(i).cancel();
                mConnThreads.set(i, null);
            }
        }

        setState(STATE_NONE);
    }

    /**
     * Write to the ConnectedThread in an unsynchronized manner
     * 
     * @param out
     *            The bytes to write
     * @see ConnectedThread#write(byte[])
     */
    public void write(byte[] out) {
        // When writing, try to write out to all connected threads
        for (int i = 0; i < mConnThreads.size(); i++) {
            try {
                // Create temporary object
                ConnectedThread r;
                // Synchronize a copy of the ConnectedThread
                synchronized (this) {
                    if (mState != STATE_CONNECTED)
                        return;
                    r = mConnThreads.get(i);
                }
                // Perform the write unsynchronized
                r.write(out);
            } catch (Exception e) {
            }
        }
    }

    /**
     * Indicate that the connection attempt failed and notify the UI Activity.
     */
    private void connectionFailed() {
        setState(STATE_LISTEN);
        // Send a failure message back to the Activity
        Message msg = mHandler.obtainMessage(ServerMainActivity.MESSAGE_TOAST);
        Bundle bundle = new Bundle();
        bundle.putString(ServerMainActivity.TOAST, "Unable to connect device");
        msg.setData(bundle);
        mHandler.sendMessage(msg);

    }

    /**
     * Indicate that the connection was lost and notify the UI Activity.
     */
    private void connectionLost(BluetoothDevice device) {
        // setState(STATE_LISTEN);
        int positionIndex = getPositionIndexOfDevice(device);
        if (positionIndex != -1) {
            Log.i(TAG, "getPositionIndexOfDevice(device) ==="
                    + mDeviceAddresses.get(getPositionIndexOfDevice(device)));
            mDeviceAddresses.set(positionIndex, null);
            mDeviceNames.set(positionIndex, null);
            mConnThreads.set(positionIndex, null);

            Message msg = mHandler
                    .obtainMessage(ServerMainActivity.MESSAGE_TOAST);
            Bundle bundle = new Bundle();
            bundle.putString(ServerMainActivity.TOAST,
                    "Device connection was lost from " + device.getName());
            msg.setData(bundle);
            mHandler.sendMessage(msg);
        }
        // Send a failure message back to the Activity
    }

    private class AcceptThread extends Thread {
        // The local server socket
        private final BluetoothServerSocket mmServerSocket;

        public AcceptThread() {
            BluetoothServerSocket tmp = null;
            // Create a new listening server socket
            try {

                if (mAdapter.isEnabled()) {
                    BluetoothService.setMY_UUID(UUID
                            .fromString("00001101-0000-1000-8000-"
                                    + mAdapter.getAddress().replace(":", "")));
                }
                Log.i(TAG, "MY_UUID.toString()=="
                        + BluetoothService.getMY_UUID().toString());

                tmp = mAdapter.listenUsingRfcommWithServiceRecord(NAME,
                        BluetoothService.getMY_UUID());
            } catch (IOException e) {
                Log.e(TAG, "listen() failed", e);
            }
            mmServerSocket = tmp;
        }

        public void run() {
            if (D)
                Log.d(TAG, "BEGIN mAcceptThread" + this);
            setName("AcceptThread");
            BluetoothSocket socket = null;
            Log.i(TAG, "mState in acceptThread==" + mState);
            // Listen to the server socket if we're not connected
            while (mState != STATE_CONNECTED) {
                try {
                    // This is a blocking call and will only return on a
                    // successful connection or an exception
                    socket = mmServerSocket.accept();
                } catch (IOException e) {
                    Log.e(TAG, "accept() failed", e);
                    break;
                }

                // If a connection was accepted
                if (socket != null) {
                    synchronized (BluetoothService.this) {
                        switch (mState) {
                        case STATE_LISTEN:
                        case STATE_CONNECTING:
                            // Situation normal. Start the connected thread.
                            connected(socket, socket.getRemoteDevice(),getAvailablePositionIndexForNewConnection(socket.getRemoteDevice()));
                            break;
                        case STATE_NONE:
                        case STATE_CONNECTED:
                            // Either not ready or already connected. Terminate
                            // new socket.
                            try {
                                socket.close();
                            } catch (IOException e) {
                                Log.e(TAG, "Could not close unwanted socket", e);
                            }
                            break;
                        }
                    }
                }
            }
            if (D)
                Log.i(TAG, "END mAcceptThread");
        }

        public void cancel() {
            if (D)
                Log.d(TAG, "cancel " + this);
            try {
                mmServerSocket.close();
            } catch (IOException e) {
                Log.e(TAG, "close() of server failed", e);
            }
        }
    }

    /**
     * This thread runs while listening for incoming connections. It behaves
     * like a server-side client. It runs until a connection is accepted (or
     * until cancelled).
     */
    // private class AcceptThread extends Thread {
    // BluetoothServerSocket serverSocket = null;
    //
    // public AcceptThread() {
    // }
    //
    // public void run() {
    // if (D)
    // Log.d(TAG, "BEGIN mAcceptThread" + this);
    // setName("AcceptThread");
    // BluetoothSocket socket = null;
    // try {
    // // Listen for all 7 UUIDs
    // serverSocket = mAdapter.listenUsingRfcommWithServiceRecord(
    // NAME, MY_UUID);
    // socket = serverSocket.accept();
    // if (socket != null) {
    // String address = socket.getRemoteDevice().getAddress();
    // mSockets.add(socket);
    // mDeviceAddresses.add(address);
    // mDeviceNames.add(socket.getRemoteDevice().getName());
    // // connected(socket, socket.getRemoteDevice());
    // }
    // } catch (IOException e) {
    // Log.e(TAG, "accept() failed", e);
    // }
    // if (D)
    // Log.i(TAG, "END mAcceptThread");
    // }
    //
    // public void cancel() {
    // if (D)
    // Log.d(TAG, "cancel " + this);
    // try {
    // serverSocket.close();
    // } catch (IOException e) {
    // Log.e(TAG, "close() of server failed", e);
    // }
    // }
    // }

    /**
     * This thread runs while attempting to make an outgoing connection with a
     * device. It runs straight through; the connection either succeeds or
     * fails.
     */
    private class ConnectThread extends Thread {
        private final BluetoothSocket mmSocket;
        private final BluetoothDevice mmDevice;
        private UUID tempUuid;
        private int selectedPosition;

        public ConnectThread(BluetoothDevice device, UUID uuidToTry,
                int selectedPosition) {
            mmDevice = device;
            BluetoothSocket tmp = null;
            tempUuid = uuidToTry;
            this.selectedPosition = selectedPosition;
            // Get a BluetoothSocket for a connection with the
            // given BluetoothDevice
            try {
                tmp = device.createRfcommSocketToServiceRecord(uuidToTry);
            } catch (IOException e) {
                Log.e(TAG, "create() failed", e);
            }
            mmSocket = tmp;
        }

        public void run() {
            Log.i(TAG, "BEGIN mConnectThread");
            setName("ConnectThread");

            // Always cancel discovery because it will slow down a connection
            mAdapter.cancelDiscovery();

            // Make a connection to the BluetoothSocket
            try {
                // This is a blocking call and will only return on a
                // successful connection or an exception
                mmSocket.connect();
            } catch (IOException e) {
                // if
                // (tempUuid.toString().contentEquals(mUuids.get(6).toString()))
                // {
                connectionFailed();
                // }
                // Close the socket
                try {
                    mmSocket.close();
                } catch (IOException e2) {
                    Log.e(TAG,
                            "unable to close() socket during connection failure",
                            e2);
                }
                // Start the service over to restart listening mode
                BluetoothService.this.start();
                return;
            }

            // Reset the ConnectThread because we're done
            synchronized (BluetoothService.this) {
                mConnectThread = null;
            }
            mDeviceAddresses.set(selectedPosition, mmDevice.getAddress());
            mDeviceNames.set(selectedPosition, mmDevice.getName());
            // Start the connected thread
            connected(mmSocket, mmDevice, selectedPosition);
        }

        public void cancel() {
            try {
                mmSocket.close();
            } catch (IOException e) {
                Log.e(TAG, "close() of connect socket failed", e);
            }
        }
    }

    /**
     * This thread runs during a connection with a remote device. It handles all
     * incoming and outgoing transmissions.
     */
    private class ConnectedThread extends Thread {
        private final BluetoothSocket mmSocket;
        private final InputStream mmInStream;
        private final OutputStream mmOutStream;

        public ConnectedThread(BluetoothSocket socket) {
            Log.d(TAG, "create ConnectedThread");
            mmSocket = socket;
            InputStream tmpIn = null;
            OutputStream tmpOut = null;

            // Get the BluetoothSocket input and output streams
            try {
                tmpIn = socket.getInputStream();
                tmpOut = socket.getOutputStream();
            } catch (IOException e) {
                Log.e(TAG, "temp sockets not created", e);
            }

            mmInStream = tmpIn;
            mmOutStream = tmpOut;
        }

        public void run() {
            Log.i(TAG, "BEGIN mConnectedThread");
            byte[] buffer = new byte[1024];
            int bytes;

            // Keep listening to the InputStream while connected
            while (true) {
                try {
                    // Read from the InputStream
                    bytes = mmInStream.read(buffer);
                    // Send the obtained bytes to the UI Activity
                    mHandler.obtainMessage(
                            ServerMainActivity.MESSAGE_READ,
                            bytes,
                            getPositionIndexOfDevice(mmSocket.getRemoteDevice()),
                            buffer).sendToTarget();
                    Log.i("**********read", "read Called........");
                } catch (IOException e) {
                    Log.e(TAG, "disconnected", e);
                    connectionLost(mmSocket.getRemoteDevice());
                    break;
                }
            }
        }

        /**
         * Write to the connected OutStream.
         * 
         * @param buffer
         *            The bytes to write
         */
        public void write(byte[] buffer) {
            try {
                mmOutStream.write(buffer);

                // Share the sent message back to the UI Activity
                mHandler.obtainMessage(ServerMainActivity.MESSAGE_WRITE, -1,
                        -1, buffer).sendToTarget();
            } catch (IOException e) {
                Log.e(TAG, "Exception during write", e);
            }
        }

        public void cancel() {
            try {
                mmSocket.close();
            } catch (IOException e) {
                Log.e(TAG, "close() of connect socket failed", e);
            }
        }
    }

    public int getPositionIndexOfDevice(BluetoothDevice device) {
        for (int i = 0; i < mDeviceAddresses.size(); i++) {
            if (mDeviceAddresses.get(i) != null
                    && mDeviceAddresses.get(i).equalsIgnoreCase(
                            device.getAddress()))
                return i;
        }
        return -1;
    }

    public int getAvailablePositionIndexForNewConnection(BluetoothDevice device) {      
        if (getPositionIndexOfDevice(device) == -1) {
            for (int i = 0; i < mDeviceAddresses.size(); i++) {
                if (mDeviceAddresses.get(i) == null) {
                    return i;
                }
            }
        }
        return -1;
    }
}
于 2012-11-22T10:25:37.760 に答える
1

関連する量の作業の後、パス中にいくつかのトリッキーなバグに直面した後、成功して実装しました。たとえば、接続試行中のタイムアウトの問題を回避するために、ハンドシェイクプロトコル(そのようなもの)を実装する必要がありました。

さて、2 つのデバイス間の通信を実装する BluetoothChat の例 (Android SDK サンプル) を見始めました。そこで、複数の接続を許可するように変更しました。コードが大きくなったので、私が使用したアプローチについて説明します。

基本的に、アプリを実行しているすべてのデバイスがサーバーまたはクライアントになることができます。したがって、それぞれが常に BluetoothServerSocket(AcceptThread) を実行しているため、このようにして、各デバイスは常にリクエスト接続を受信できます。

接続したいデバイスは、ConnectThread を開始します。このスレッドは、検出プロセスの後、または getBondedDevicesを使用して PairedDevicesの BluetoothDevice を選択した場合に開始されます。

接続が確立されると、その接続を表す新しい Thread(ConnectedThread) を作成します。デバイスの役割 (マスターまたはスレーブ) に応じて異なる動作をさせたい場合は、MasterThread や SlaveThread のような ConnectedThread サブクラスを持つことができます。

Android のドキュメントには、Bluetooth を使用する方法に関する適切な説明があります: http://developer.android.com/guide/topics/connectivity/bluetooth.html

于 2012-11-23T20:46:11.913 に答える