Question:
I am trying to make an application that connects to a Bluetooth module and then be able to navigate between different activities connected to the module.
The problem is that the connection in the main activity is fine but when I launch another activity the connection is lost.
Any ideas how I could keep the connection alive or how to reconnect in the new activity ?
This is my code:
public class Pantalla_Principal extends AppCompatActivity {
Handler bluetoothIn;
final int handlerState = 0;
TextView CajaDeInformacion = null;
Button BotonPruebaDeConexion, BotonConfigurar, BotonSeleccionar, BotonEliminar, BotonSalir;
public StringBuilder recDataString = new StringBuilder();
public Pantalla_Principal.ConnectedThread mConnectedThread;
public static final UUID BTMODULEUUID = UUID.fromString("00001101-0000-1000-8000-00805F9B34FB");
public static String address;
public static String Dispositivo;
BluetoothDevice device;
BluetoothAdapter myBluetooth = null;
BluetoothSocket btSocket = null;
public static String EXTRA_ADDRESS = "device_address";
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_pantalla__principal);
final Intent intent = this.getIntent();
address = intent.getStringExtra(Pantalla_Conexion.EXTRA_ADDRESS);
CajaDeInformacion = (TextView) findViewById(R.id.CajaDePruebas);
BotonConfigurar = (Button) findViewById(R.id.BotonConfigurar);
BotonSeleccionar = (Button) findViewById(R.id.BotonSeleccionar);
BotonEliminar = (Button) findViewById(R.id.BotonEliminar);
BotonPruebaDeConexion = (Button) findViewById(R.id.BotonPruebaDeConexion);
BotonSalir = (Button) findViewById(R.id.BotonSalir);
BotonPruebaDeConexion.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
if (btSocket != null) {
try {
btSocket.getOutputStream().write("Hola".toString().getBytes());
} catch (IOException e) {
Mensaje("Error");
}
}
}
});
BotonConfigurar.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
Intent PantallaConfigurar = new Intent(Pantalla_Principal.this, Pantalla_Configuracion.class);
startActivity(PantallaConfigurar);
finish();
}
});
BotonSeleccionar.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
Intent PantallaTelevisores = new Intent(Pantalla_Principal.this, Plantilla_Televisores.class);
PantallaTelevisores.putExtra(EXTRA_ADDRESS, address);
PantallaTelevisores.putExtra(Dispositivo,device);
//PantallaTelevisores.putExtra("Dispositivo",device)
startActivity(PantallaTelevisores);
}
});
BotonSalir.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
if (btSocket != null) {
try {
Mensaje("Conexion Finalizada");
btSocket.close();
finish();
} catch (IOException e) {
Mensaje("Error");
}
}
}
});
this.bluetoothIn = new Handler() {
public void handleMessage(Message msg) {
if (msg.what == 0) {
String readMessage = (String) msg.obj;
Pantalla_Principal.this.recDataString.append(readMessage);
Pantalla_Principal.this.CajaDeInformacion.setText(" ");
Pantalla_Principal.this.CajaDeInformacion.setText(recDataString);
}
}
};
this.myBluetooth = BluetoothAdapter.getDefaultAdapter();
this.checkBTState();
}
public BluetoothSocket createBluetoothSocket(BluetoothDevice device) throws IOException {
return device.createRfcommSocketToServiceRecord(BTMODULEUUID);
}
private void Mensaje(String s) {
Toast.makeText(getApplicationContext(), s, Toast.LENGTH_LONG).show();
}
public void onResume() {
super.onResume();
BluetoothDevice device = myBluetooth.getRemoteDevice(address);
try {
this.btSocket = this.createBluetoothSocket(device);
} catch (IOException var7) {
Toast.makeText(this.getBaseContext(), "Socket creation failed", 1).show();
}
try {
this.btSocket.connect();
} catch (IOException var6) {
try {
this.btSocket.close();
} catch (IOException var5) {
;
}
}
this.mConnectedThread = new Pantalla_Principal.ConnectedThread(this.btSocket);
this.mConnectedThread.start();
}
public void onPause() {
super.onPause();
try {
this.btSocket.close();
} catch (IOException var2) {
;
}
}
public void onStop() {
super.onStop();
try {
this.btSocket.close();
} catch (IOException var2) {
;
}
}
public void checkBTState() {
if (this.myBluetooth == null) {
Toast.makeText(this.getBaseContext(), "Device does not support bluetooth", 1).show();
} else if (!this.myBluetooth.isEnabled()) {
Intent enableBtIntent = new Intent("android.bluetooth.adapter.action.REQUEST_ENABLE");
this.startActivityForResult(enableBtIntent, 1);
}
}
public class ConnectedThread extends Thread {
private final InputStream mmInStream;
private final OutputStream mmOutStream;
public ConnectedThread(BluetoothSocket socket) {
InputStream tmpIn = null;
OutputStream tmpOut = null;
try {
tmpIn = socket.getInputStream();
tmpOut = socket.getOutputStream();
} catch (IOException var6) {
;
}
this.mmInStream = tmpIn;
this.mmOutStream = tmpOut;
}
public void run() {
byte[] buffer = new byte[256];
while (true) {
try {
int bytes = this.mmInStream.read(buffer);
String readMessage = new String(buffer, 0, bytes);
Pantalla_Principal.this.bluetoothIn.obtainMessage(0, bytes, -1, readMessage).sendToTarget();
} catch (IOException var4) {
return;
}
}
}
}
}
Answer:
If you look at the lifecycle of an activity in Android , there are two important steps: onResume
and onPause
.
When an activity is in the Resumed
state, it is in the foreground, allowing the user to interact with it.
When an activity is in the Paused state, we could say that said activity is not in the foreground, but that there is another activity that is active.
If you look at your implementation:
public void onResume() {
super.onResume();
BluetoothDevice device = myBluetooth.getRemoteDevice(address);
try {
this.btSocket = this.createBluetoothSocket(device);
} catch (IOException var7) {
Toast.makeText(this.getBaseContext(), "Socket creation failed", 1).show();
}
try {
this.btSocket.connect();
} catch (IOException var6) {
try {
this.btSocket.close();
} catch (IOException var5) {
;
}
}
this.mConnectedThread = new Pantalla_Principal.ConnectedThread(this.btSocket);
this.mConnectedThread.start();
}
public void onPause() {
super.onPause();
try {
this.btSocket.close();
} catch (IOException var2) {
;
}
}
In the onResume
step you start the bluetooth connection
this.btSocket = this.createBluetoothSocket(device);
And in the onPause
step you close it.
this.btSocket.close();
So in another activity you could create these two steps to use the connection. However, my recommendation is that you separate the connection from the activities, for example using an Android Service.