Successive transfer of bitmap via Bluetooth generate multiple inputstream.read()

六月ゝ 毕业季﹏ 提交于 2019-12-23 03:41:39

问题


I'm developing an android application that transfers images from one device to another. The received image will be stored in the local database of my application created by help of SQLite. To achieve my goals, I've converted the bitmap into byte[] and transferred it to another device by help of outputStream. I did achieve success from the above implementation but, failed in transferring the second image on the connected device.

The problem which I am facing is the following: The first transfer of any image is successful with a single outputStream.write() and single inputStream.read() but, the successive transfer of the same/another image fails with a single outputStream.Write() and multiple inoutStream.read() method calls.

I would like to know the fault in implementation of input and output streams in my code.

Thanks in advance.

The code for thread to start a connection is as follows:

        private class StartConnectionThread extends Thread{
    private final BluetoothSocket bluetoothSocket;
    private final BluetoothDevice bluetoothDevice;
    public StartConnectionThread(BluetoothDevice device){
        BluetoothSocket tempBluetoothSocket=null;
        bluetoothDevice=device;
        try
        {
            System.out.println(uuid);
            tempBluetoothSocket=device.createRfcommSocketToServiceRecord(uuid);
        }
        catch(IOException ioException)
        {

        } 
        bluetoothSocket=tempBluetoothSocket;
    }
    @Override
    public void run() {
        // TODO Auto-generated method stub
        System.out.println("StartConnectionThread Run");
        bluetoothAdapter.cancelDiscovery();
        try
        {
            try {
                Thread.sleep(2000);
            } catch (InterruptedException e) {
                // TODO Auto-generated catch block
                e.printStackTrace();
            }
            bluetoothSocket.connect();

        }
        catch(IOException ioException)
        {
            System.out.println(ioException);
            try
            {
                bluetoothSocket.close();
            }
            catch(IOException cancelIOException)
            {

            }
            return;
        }
        manageConnectedSocket(bluetoothSocket);
    }
    public void cancel()
    {
        try
        {
            bluetoothSocket.close();
        }
        catch(IOException ioException)
        {

        }
    }
}

The code for thread to accept a connection is as follows:

        private class AcceptConnectionThread extends Thread
{
    private final BluetoothServerSocket bluetoothServerSocket;
    public AcceptConnectionThread() {
        // TODO Auto-generated constructor stub
        System.out.println("constructor");
        BluetoothServerSocket tempBluetoothServerSocket=null;
        try
        {
            tempBluetoothServerSocket=bluetoothAdapter.listenUsingRfcommWithServiceRecord("My Souvenirs", uuid);
        }
        catch(IOException ioException)
        {
        } 
        bluetoothServerSocket=tempBluetoothServerSocket;
    }
    @Override
    public void run() {
        // TODO Auto-generated method stub
        System.out.println("AcceptConnectionThread Run");
        BluetoothSocket bluetoothSocket=null;
        while(true)
        {
            try
            {
                try {
                    Thread.sleep(2000);
                } catch (InterruptedException e) {
                    // TODO Auto-generated catch block
                    e.printStackTrace();
                }
                System.out.println(bluetoothServerSocket);
                if(bluetoothServerSocket!=null)
                {
                    bluetoothSocket=bluetoothServerSocket.accept();
                }
                else {
                    System.out.println("bluetoothserversocket==null");
                }
                System.out.println("accept");
            }
            catch(IOException ioException){
                System.out.println("exception after accept");
                System.out.println(ioException);
                break;
            }
            if(bluetoothSocket!=null)
            {
                manageConnectedSocket(bluetoothSocket);
                try {
                    bluetoothServerSocket.close();
                } catch (IOException e) {
                    // TODO Auto-generated catch block
                    e.printStackTrace();
                }
                break;
            }
        }
    }
    public void cancel()
    {
        try{
            bluetoothServerSocket.close();
        }
        catch(IOException ioException){

        }
    }

}

The code for manageConnectedSocket() method called in the above threads is as follows:

        public void manageConnectedSocket(BluetoothSocket bluetoothSocket)
{

    manageConnectedDevicesThread=new ManageConnectedDevicesThread(bluetoothSocket);
    Bitmap bitmap=BitmapFactory.decodeResource(getResources(), R.drawable.request);
    ByteArrayOutputStream baos= new ByteArrayOutputStream();
    bitmap.compress(Bitmap.CompressFormat.PNG,100,baos);
    byte[] bytes=baos.toByteArray();
    manageConnectedDevicesThread.write(bytes);
    System.out.println("manageConnectedSocket() method called");
    manageConnectedDevicesThread.start();
    System.out.println("success");      
    Intent intent=new Intent();
    intent.setAction("received");
    sendBroadcast(intent);
}

The code for thread to manage the connected devices is as follows:

        private class ManageConnectedDevicesThread extends Thread
{
    private final BluetoothSocket connectedBluetoothSocket;
    InputStream tempInputStream=null;
    OutputStream tempOutputStream=null;
    public ManageConnectedDevicesThread(BluetoothSocket socket) {
        // TODO Auto-generated constructor stub
        connectedBluetoothSocket=socket;
        try
        {
            tempInputStream=socket.getInputStream();
            tempOutputStream=socket.getOutputStream();
        }
        catch(IOException ioException)
        {

        }
        inputStream=tempInputStream;
        outputStream=tempOutputStream;
    }
    @Override
    public void run() {
        // TODO Auto-generated method stub
        System.out.println("ManageConnectedDevicesThread Run");
        Bitmap bitmap=BitmapFactory.decodeResource(getResources(), R.drawable.ic_launcher);
        ByteArrayOutputStream baos= new ByteArrayOutputStream();
        bitmap.compress(Bitmap.CompressFormat.PNG,100,baos);
        byte[] buffer=new byte[1024*8];
        int bytes;
        while(true)
        {
            try
            {
                bytes=inputStream.read(buffer);
                handler.obtainMessage(MESSAGE_READ,bytes,-1,buffer).sendToTarget();
                System.out.println("handler");
            }
            catch(IOException ioException)
            {
                System.out.println("for handler:" +ioException);
                break;
            }
        }
    }
    public void write(byte[] bytes)
    {
        try
        {
            outputStream.write(bytes,0,bytes.length);
        }
        catch(IOException ioException){
            System.out.println("exception in write statement of managing connections");
        }

    }


    public void close()
    {
        try {   
            connectedBluetoothSocket.close();
        } catch (IOException e) {
            // TODO: handle exception
        }
    }
}

The code for handler implemented in my application is as follows:

    private final Handler handler=new Handler(){
public void handleMessage(Message msg) {
    switch (msg.what) {

    case MESSAGE_READ:
        byte[] readBuf = (byte[]) msg.obj;
        // construct a string from the valid bytes in the buffer
        String readMessage = new String(readBuf, 0, msg.arg1);
        byte[] b=readMessage.getBytes();
        if(sendingDeviceFlag==0)
        {
            Intent intent=new Intent();
            intent.setAction("received");
            sendBroadcast(intent);
            bluetoothDatabase.open();
            bluetoothDatabase.insert_slam(readMessage, readBuf);
            writeCount++;
            System.out.println("write count = "+writeCount);
            Cursor cursor=bluetoothDatabase.getSlam();
            if(cursor!=null)
            {
                cursor.moveToFirst();
                while(cursor.moveToNext())
                {
                    byte[] barray=cursor.getBlob(cursor.getColumnIndex("img"));
                    Bitmap bitmap1=BitmapFactory.decodeByteArray(barray, 0, barray.length);
                    imageView.setImageBitmap(bitmap1);
                }
                System.out.println("Count = "+cursor.getCount());
            }
            else {
                System.out.println("cursor null");
            }
            bluetoothDatabase.close();              
        }

        break;
    }
    };

The code to reset the connection is as follows:

        void resetConnection()  
{
    if(inputStream!=null)
    {
        try {
            inputStream.close();
        } catch (IOException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        }   
    }
    if(outputStream!=null)
    {
        try {
            outputStream.close();
        } catch (IOException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        }   
    }
    if(startConnectionThread!=null) //my changes
    {
        System.out.println("start wala active tha");    
        startConnectionThread.cancel(); 
    }
    if(acceptConnectionThread!=null)    
    {
        System.out.println("accept wala active tha");   
        acceptConnectionThread.cancel();    
        acceptConnectionThread.interrupt();
        acceptConnectionThread=new AcceptConnectionThread();
        acceptConnectionThread.start();
    }
    if(manageConnectedDevicesThread!=null)
    {
        System.out.println("manage wala active tha");   
        manageConnectedDevicesThread.close();   
    }
}
    }

The user will click on the paired or found device in a listview to send the image. The code for the click event on listview is as follows:

            devicesListView.setOnItemClickListener(new OnItemClickListener() {

        @Override
        public void onItemClick(AdapterView<?> arg0, View arg1, int arg2,
                long arg3) {
            // TODO Auto-generated method stub
            if(startConnectionThread!=null)
            {
                Bitmap bitmap=BitmapFactory.decodeResource(getResources(), R.drawable.request);
                ByteArrayOutputStream baos= new ByteArrayOutputStream();
                bitmap.compress(Bitmap.CompressFormat.PNG,100,baos);
                byte[] bytes=baos.toByteArray();
                manageConnectedDevicesThread.write(bytes);
                Intent intent=new Intent();
                intent.setAction("received");
                sendBroadcast(intent);
            }
            else {
                System.out.println("click on list view");
                sendingDeviceFlag=1;
                writeCount=0;
                System.out.println("after reset");
                bluetoothAdapter.cancelDiscovery();
                String address=new String();
                address=arrayAdapter.getItem(arg2);
                selectedBluetoothDevice=bluetoothAdapter.getRemoteDevice(address.substring(address.length()-17));
                startConnectionThread=new StartConnectionThread(selectedBluetoothDevice);
                startConnectionThread.start();
            }
        }
    });

来源:https://stackoverflow.com/questions/21568601/successive-transfer-of-bitmap-via-bluetooth-generate-multiple-inputstream-read

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!