package org.schmivits.testbluetoothclientserver;
import java.io.IOException;
import java.io.OutputStream;
import java.util.concurrent.BlockingQueue;
import java.util.concurrent.LinkedBlockingQueue;
import android.bluetooth.BluetoothSocket;
import android.widget.TextView;
public class DataServant extends RpcThread {
private static final long WRITE_PAUSE = 20L;
private static final long WRITE_TIMEOUT = 1000L;
private final BlockingQueue<String> mData = new LinkedBlockingQueue<String>();
private final BluetoothSocket mTargetSocket;
private final DataSourceStream mSource;
private final DataSourceStream.Listener mListener = new DataSourceStream.Listener() {
@Override public void data(String s) {
try { mData.put(s); } catch (InterruptedException e) { }
}
};
public DataServant(TextView view, BluetoothSocket socket, DataSourceStream source) {
super(view);
report("Created DataServant");
mTargetSocket = socket;
mSource = source;
source.addListener(mListener);
}
@Override
public void run() {
try {
OutputStream os = mTargetSocket.getOutputStream();
long timeoutStart = 0L;
report("DataServant entering servant loop");
while (!isInterrupted()) {
if (mData.size() > 0) {
String s = null;
synchronized (mData) {
if (mData.size() > 0) { s = mData.take(); }
}
if (s != null) {
os.write(s.getBytes());
os.write('\n');
os.flush();
timeoutStart = 0L;
}
} else {
if (timeoutStart == 0L) {
timeoutStart = System.currentTimeMillis();
} else if (System.currentTimeMillis() - timeoutStart > WRITE_TIMEOUT) {
report("DataServant timeout");
destroy();
return;
}
Thread.sleep(WRITE_PAUSE);
}
}
} catch (InterruptedException e) {
report("DataServant interrupted");
destroy();
return;
} catch (IOException e) {
report("DataServant IOException " + e);
destroy();
return;
}
}
@Override
public void destroy() {
mSource.removeListener(mListener);
try { mTargetSocket.close(); } catch (IOException e) { }
report("Destroyed DataServant");
super.destroy();
}
}