Warning: file_get_contents(/data/phpspider/zhask/data//catemap/3/sockets/2.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Android 处理数据流并在后台创建记录_Android_Sockets_Android Broadcast_Android Bluetooth_Android Background - Fatal编程技术网

Android 处理数据流并在后台创建记录

Android 处理数据流并在后台创建记录,android,sockets,android-broadcast,android-bluetooth,android-background,Android,Sockets,Android Broadcast,Android Bluetooth,Android Background,我已经创建了一个应用程序,它可以很好地完成以下步骤- 使用蓝牙插座连接远程设备(SPP) 然后侦听来自远程蓝牙设备的流 在单独的线程中 然后,当数据流出现时,它将数据流传递给处理程序以对其进行解析 解析数据时,发送广播并创建记录 输入数据库 现在我想添加一个新功能- 当应用程序处于后台并“连接”到远程设备时,它需要继续处理数据流并创建记录 因此,一旦连接了套接字,我就将结果“connected”传递给onPostExecute()方法 重要提示: 1) 我所有与套接字相关的工作(套接字连接、

我已经创建了一个应用程序,它可以很好地完成以下步骤-

  • 使用蓝牙插座连接远程设备(
    SPP

  • 然后侦听来自远程蓝牙设备的流 在单独的线程中

  • 然后,当数据流出现时,它将数据流传递给处理程序以对其进行解析

  • 解析数据时,发送广播并创建记录 输入数据库

现在我想添加一个新功能-

当应用程序处于后台并“连接”到远程设备时,它需要继续处理数据流并创建记录

因此,一旦连接了套接字,我就将结果“connected”传递给
onPostExecute()
方法

重要提示:

1) 我所有与套接字相关的工作(套接字连接、套接字数据解析、数据处理程序)都在片段中

2) 一旦建立了连接,片段中的私有类(Thread-ConnectedThread.java)将继续侦听InputStream

3) 处理步骤2的读取的我的处理程序

4) 我已连接,因此可以从AsyncTask parseStream的onPostExecute()执行某些操作

5) 我在步骤4中调用了该服务,目的是在应用程序进入后台时执行该服务 和处理数据。但是,它将如何与片段通信,因为我的整个工作 数据处理在片段中。我真的需要它来处理数据还是应该打电话给

这里的广播接收机是否也可以在后台处理

我在这方面做了不少工作。我将与你分享我的经验中最有效的方法

-专用蓝牙服务,运行在它自己的独立进程中,用于处理连续的数据流


-在获取和处理数据时避免广播;特别是如果它是快速和大数据流。这是我过去在处理bt流时犯的一个错误。我意识到,它可能适用于少量或慢速流,但是,广播非常昂贵,当用IPC代替它们时,我看到了巨大的性能改进(UI线程我们需要以固定的时间间隔调用服务以从套接字获取数据吗?我已经实现了连接和处理片段中数据的逻辑,所以我需要像上面的代码那样将其转移到BluetoothManager类吗?服务应该在从该片段进行套接字连接之后启动,所以我认为BluetoothManager class需要重新实现。请查看我的更新!@VedPrakash,不,您不需要以固定的时间间隔呼叫该服务。该服务将通知(通过发送新消息)每当有新的数据可用时,主线程。@ VePraskash,我还补充说,你应该真正考虑到你的蓝牙工作流在一个片段中的影响。你在Android的生命周期控制下,无法正确地使用你的蓝牙工作流。从某个视图来看,需要转到此片段视图,以便向用户显示。然后用户可以关闭应用程序,数据将继续在后台流动。因此,我必须使用此片段。但是,查看您的代码,我同意“绑定”使用片段的范围。@VedPrakash,理想情况下,您应该将其绑定到片段的基本活动。更好的是,绑定任何活动,让后台服务处理数据并将其转发给绑定的任何人。这样,您可以将应用程序放在后台,关闭当前活动/片段,您仍然可以执行bl这是一个非常好的工作。而且,您不需要每次处理一段数据时都重新启动ConnectedThread。您只需要一个
public class EntryFragment extends Fragment{
    //More fragment code here then this
    public class ConnectedThread extends Thread {

        public ConnectedThread(BluetoothSocket socket) {
            //code initialization stuff
        }

         public void run() {
             // Keep listening to the InputStream until an exception occurs
             while (true) 
             {
                    // Read from the InputStream
                    if(mmInStream.available() > 0)
                    {
                       bytes = mmInStream.read(buffer);

                       mHandler.obtainMessage(MESSAGE_READ, 
                       bytes, -1, buffer).sendToTarget();
                    }              
              }   
          }
     }
    case MESSAGE_READ:

     //Call to AsyncTask to do background processing of data
     new parseStream(getActivity()).execute();
    break;
 @Override
 protected void onPostExecute(Void result) {
 //Database related work here

 //Result is connected so listen to data if app goes to background after this state
 if(result.equals("connected")) 
 { 
      Log.i(TAG, "CONNECTED TO Remote Device!");
      Toast.makeText(getActivity(),"CONNECTED TO Remote  
      Device!",Toast.LENGTH_SHORT).show();

      //Do something when connected
      setSetting("STATUS", "Connected");

      // Start the thread to manage the connection and perform transmissions
      mConnectedThread = new ConnectedThread(socket);
      mConnectedThread.start();

      //Do I need to call Service here to handle data ?????
      Intent serviceIntent= new Intent(context, DataProcessService.class);               
      getActivity().startService(serviceIntent);
   }
 }
public class BluetoothService extends Service {

     //
     // API keys for the messages being passed across ui thread <-> service
     //
     static final int REGISTER_CLIENT = 3;
     static final int NEW_DATA = 2;
     static final int WRITE_DATA = 1;
     static final int CONNECT_BT = 0;

      // manages actual connection
      private BluetoothManager btManager;

      // who is activity and ready to receive messages? 
      private Messenger clientToReply;

      public int onStartCommand(Intent intent, int flags, int startId) { 

           btManager = new BluetoothManager(this);

           return START_STICKY;//makes sure the service keeps running and get's back up if it gets terminated
      } 

     //
    // Send data back to your activity
    //
     public void sendDataToBoundClient(byte[] bytes) {
           Message msgToClient = new Message();
           msgToClient.what = NEW_DATA;

          Bundle bNewData = new Bundle();
          bNewData.putByteArray("newData", bytes);

          msgToClient.setData(bNewData);
          try {
                clientToReply.send(msgToClient); //send
            } catch (RemoteException e) {
                e.printStackTrace(); //couldn't send
            }
     }

     /**
      * Handles messages received from a bound Context
      */
     public class MessageHandler extends Handler {
       /* (non-Javadoc)
       * @see android.os.Handler#handleMessage(android.os.Message)
       */
        @Override
        public void handleMessage(Message msg) {

               switch (msg.what) {

                     case REGISTER_CLIENT: 
                         // now we know to whom to reply with our messages, callbacks or new data
                         clientToReply = msg.replyTo;
                         break;

                     case WRITE_DATA:
                         break;

                     case CONNECT_BT: 
                         // launches Connect & Connected Threads
                         // would follow the same pattern as in http://developer.android.com/guide/topics/connectivity/bluetooth.html#ConnectingAsAClient
                         btManager.connect(); 
                         break;
               }
        }
    }

}




 //
    // Check examples in http://developer.android.com/guide/topics/connectivity/bluetooth.html#ConnectingAsAClient
    //
    public class BluetoothManager {
        private ConnectThread connectThread; //thread to connect
        private ConnectedThread connectedThread; //thread manages connection

        private BluetoothService service;

        public BluetoothManager(BluetoothService service) {
             this.service = service;
        }

       //
       // stuff omitted...
       //

        public void connect() {
               connectThread = new ConnectThread();
               connectThread.start();
        }


       public void writeData(byte[] bytes) {
              connectedThread.write(bytes);
        }

       public void onDataRead(byte[] bytes) {
            // service knows how to forward this to the client (bound activity, for example)
            this.service.sendDataToBoundClient(bytes);
       }
    }

//
// Based on the example from http://developer.android.com/guide/components/bound-services.html#Messenger
//
public class ActivityMessenger extends Activity {
    /** Messenger for communicating with the service. */
    Messenger mService = null;

   // handle incoming messages
   protected Messenger messagesFromService = new Messenger(new IncomingHandler());

    /** Flag indicating whether we have called bind on the service. */
    boolean mBound;

    /**
     * Class for interacting with the main interface of the service.
     */
    private ServiceConnection mConnection = new ServiceConnection() {
        public void onServiceConnected(ComponentName className, IBinder service) {
            // This is called when the connection with the service has been
            // established, giving us the object we can use to
            // interact with the service.  We are communicating with the
            // service using a Messenger, so here we get a client-side
            // representation of that from the raw IBinder object.
            mService = new Messenger(service);
            mBound = true;
        }

        public void onServiceDisconnected(ComponentName className) {
            // This is called when the connection with the service has been
            // unexpectedly disconnected -- that is, its process crashed.
            mService = null;
            mBound = false;
        }
    };

    public void registerAsClient() {
        if (!mBound) return;
        // Create and send a message to the service, using a supported 'what' value
        Message msg = new Message();
        msg.what = BluetoothService.REGISTER_CLIENT;
        msg.replyTo = messagesFromService; // reply to "me"!

        try {
            mService.send(msg);
        } catch (RemoteException e) {
            e.printStackTrace();
        }
    }

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.main);
    }

    @Override
    protected void onStart() {
        super.onStart();
        // Bind to the service
        bindService(new Intent(this, MessengerService.class), mConnection,
            Context.BIND_AUTO_CREATE);
    }

    @Override
    protected void onStop() {
        super.onStop();
        // Unbind from the service
        if (mBound) {
            unbindService(mConnection);
            mBound = false;
        }
    }


    public class IncomingHandler extends Handler {

        @Override
        public void handleMessage(Message msg) {
                 switch (msg.what) {
                      case BluetoothService.NEW_DATA: 
                         Bundle data = msg.getData;
                         // handle your new data!
                         break;
                }
        }

    }

}
}
}