My solution was to use local sockets. I created an instance of a LocalServerSocket
in the constructor of my wallpaper's Engine
. Here's a quick implementation. Server runs on a separate thread and is directly tied to the lifecycle of MyEngine
. The thread will stop when continueSocket
is set to false
. This happens onDestroy
. Problem is that LocalServerSocket.accept()
blocks until there's something to do. The workaround is to send a message to our own server so it will run through the loop again and check continueSocket
(which is now false
), closing the server. Check the closeSocketServer
method. I have it running in onDestroy
in the example but you might want to use it elsewhere like onSurfaceDestroyed
and add your own sanity checks.
public class MyWallpaperService extends WallpaperService {
@Override
public Engine onCreateEngine() {
return new MyEngine();
}
private class MyEngine extends Engine {
private boolean continueSocket = true;
MyEngine() {
new Thread() {
@Override
public void run() {
try {
LocalServerSocket server = new LocalServerSocket("MyAddress");
Log.d("SERVER READY", "Server is ready.");
while(continueSocket) {
LocalSocket receiver = server.accept();
if(receiver != null) {
InputStream input = receiver.getInputStream();
byte[] data = IOUtils.toByteArray(input);
Log.d("GOT DATA", new String(data));
}
}
server.close();
} catch (IOException ex) {
Log.wtf("IOEXCEPTION", ex);
}
}
}.start();
}
@Override
public void onDestroy() {
closeSocketServer();
super.onDestroy();
}
private void closeSocketServer() {
continueSocket = false;
try {
LocalSocket socket = new LocalSocket();
socket.connect(new LocalSocketAddress("MyAddress"));
socket.getOutputStream().write(new byte[0]);
socket.getOutputStream().close();
socket.close();
} catch (IOException ex) {
//
}
}
}
}
And in my Activity
it can be as simple as this...
try {
LocalSocket sender = new LocalSocket();
sender.connect(new LocalSocketAddress("MyAddress"));
String data = "Hello world!";
Log.d("SENT DATA", data);
sender.getOutputStream().write(data.getBytes());
sender.getOutputStream().close();
sender.close();
} catch (IOException ex) {
Log.wtf("IOEXCEPTION", ex);
}
Logcat ends up looking like this:
D/SERVER READY﹕ Server is ready. (when the wallpaper starts up)
D/SENT DATA﹕ Hello world! (when the activity sends data)
D/GOT DATA﹕ Hello world! (when the wallpaper gets the data)