Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 2 additions & 2 deletions .gitmodules
Original file line number Diff line number Diff line change
@@ -1,8 +1,8 @@
[submodule "externals/x-ray"]
path = externals/x-ray
url = git@github.com:inckie/x-ray.git
url = https://github.com/inckie/x-ray.git
shallow = true
[submodule "externals/glass-enterprise-samples"]
path = externals/glass-enterprise-samples
url = git@github.com:inckie/glass-enterprise-samples.git
url = https://github.com/inckie/glass-enterprise-samples.git
branch = feat/update-project
4 changes: 4 additions & 0 deletions glass-ee/src/main/AndroidManifest.xml
Original file line number Diff line number Diff line change
Expand Up @@ -23,6 +23,10 @@
tools:ignore="MockLocation,ProtectedPermissions" />
<!-- Tilt To Wake -->
<uses-permission android:name="android.permission.WAKE_LOCK" />
<!-- Bluetooth -->
<uses-permission android:name="android.permission.BLUETOOTH" />
<uses-permission android:name="android.permission.BLUETOOTH_ADMIN" />
<uses-permission android:name="android.permission.BLUETOOTH_CONNECT" />
<!-- Barcode scanner -->
<uses-permission android:name="android.permission.CAMERA" />
<!-- Voice commands -->
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -92,9 +92,9 @@ class WiFiClient(private val hostIP: String? = null) : IRPCClient {
return
}
}
while (inputStream.available() > 0) {
while (serializer.isReady || inputStream.available() > 0) {
val message = serializer.readMessage()
if (message.service == null) {
if (message?.service == null) {
return
}
handler.onDataReceived(message)
Expand Down
1 change: 1 addition & 0 deletions glass-xe/src/main/AndroidManifest.xml
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,7 @@
<uses-permission android:name="android.permission.CHANGE_WIFI_STATE" />
<uses-permission android:name="android.permission.INTERNET" />
<uses-permission android:name="android.permission.BLUETOOTH" />
<uses-permission android:name="android.permission.BLUETOOTH_ADMIN" />
<uses-permission android:name="android.permission.CAMERA" />
<uses-permission android:name="android.permission.ACCESS_FINE_LOCATION" />
<uses-permission android:name="android.permission.ACCESS_COARSE_LOCATION" />
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,7 @@
import com.damn.anotherglass.shared.utility.DisconnectReceiver;
import com.damn.anotherglass.shared.utility.Sleep;

import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;
import java.util.Set;
Expand Down Expand Up @@ -48,6 +49,7 @@ public Connection(Context context, RPCMessageListener listener) {
mHandler = new RPCHandler(listener);
}

@SuppressLint("MissingPermission")
@Override
public void run() {
try {
Expand All @@ -56,6 +58,7 @@ public void run() {
// return;
// }
BluetoothAdapter bt = BluetoothAdapter.getDefaultAdapter();
bt.cancelDiscovery();
Set<BluetoothDevice> pairedDevices = bt.getBondedDevices();
if (null == pairedDevices || pairedDevices.isEmpty()) {
Log.e(TAG, "No paired devices found, aborting the connection");
Expand All @@ -68,6 +71,8 @@ public void run() {
break;
}
}
} catch (IOException e) {
Log.w(TAG, "Connection lost: " + e.getMessage());
} catch (Exception e) {
Log.e(TAG, "Connection exception", e);
} finally {
Expand Down Expand Up @@ -97,35 +102,52 @@ public void shutdown() {

@SuppressLint("MissingPermission")
private void runLoop(@NonNull BluetoothDevice device) throws Exception {
try (BluetoothSocket socket = device.createInsecureRfcommSocketToServiceRecord(Constants.uuid)) {
socket.connect();
BluetoothSocket socket = null;
try {
try {
socket = device.createInsecureRfcommSocketToServiceRecord(Constants.uuid);
socket.connect();
} catch (Exception e) {
Log.w(TAG, "Standard connection failed, trying fallback: " + e.getMessage());
if (socket != null)
socket.close();
Sleep.sleep(500);
socket = (BluetoothSocket) device.getClass().getMethod("createRfcommSocket", int.class).invoke(device, 1);
socket.connect();
}
Log.i(TAG, "Client has connected to " + device.getName());
AtomicBoolean active = new AtomicBoolean(true);
try (DisconnectReceiver ignored = new DisconnectReceiver(mContext, device, () -> active.getAndSet(false))) {
try (OutputStream outputStream = socket.getOutputStream();
InputStream inputStream = socket.getInputStream()) {
IMessageSerializer serializer = SerializerProvider.getSerializer(inputStream, outputStream);
mConnected = true;
mHandler.onConnectionStarted(device.getName());
while (active.get()) {
while (null != mQueue.peek()) {
RPCMessage message = mQueue.take();
serializer.writeMessage(message);
Log.v(TAG, "Message " + message.service + "/" + message.type + " was sent");
if (null == message.service) {
Log.d(TAG, "Shutdown requested");
return;
}
try (DisconnectReceiver ignored = new DisconnectReceiver(mContext, device, () -> active.getAndSet(false));
OutputStream outputStream = socket.getOutputStream();
InputStream inputStream = socket.getInputStream()) {
IMessageSerializer serializer = SerializerProvider.getSerializer(inputStream, outputStream);
mConnected = true;
mHandler.onConnectionStarted(device.getName());
while (active.get()) {
while (null != mQueue.peek()) {
RPCMessage message = mQueue.take();
serializer.writeMessage(message);
Log.v(TAG, "Message " + message.service + "/" + message.type + " was sent");
if (null == message.service) {
Log.d(TAG, "Shutdown requested");
return;
}
while (inputStream.available() > 0) {
RPCMessage objectReceived = serializer.readMessage();
mHandler.onDataReceived(objectReceived);
Log.v(TAG, "Message " + objectReceived.service + "/" + objectReceived.type + " was received");
}
while (serializer.isReady() || inputStream.available() > 0) {
RPCMessage objectReceived = serializer.readMessage();
if (null == objectReceived || null == objectReceived.service) {
Log.d(TAG, "Remote shutdown or connection lost");
return;
}
Sleep.sleep(100);
mHandler.onDataReceived(objectReceived);
Log.v(TAG, "Message " + objectReceived.service + "/" + objectReceived.type + " was received");
}
Sleep.sleep(100);
}
}
} finally {
if (socket != null)
socket.close();
}
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -14,16 +14,78 @@
public class NotificationViewBuilder {

public static CardBuilder buildView(Context context, NotificationData data) {
// basic
CardBuilder builder = new CardBuilder(context, CardBuilder.Layout.AUTHOR)
.setHeading(data.title)
.setSubheading(data.packageName) // todo: should be application name
.setText(data.text);
// basic layout selection
CardBuilder.Layout layout;
if (null != data.image && null != data.image.bytes) {
layout = CardBuilder.Layout.CAPTION;
} else if (null != data.icon && null != data.icon.bytes) {
layout = CardBuilder.Layout.COLUMNS;
} else if (null != data.messages && !data.messages.isEmpty()) {
layout = CardBuilder.Layout.COLUMNS;
} else {
layout = CardBuilder.Layout.TEXT;
}

CardBuilder builder = new CardBuilder(context, layout);

// handle text / conversation
StringBuilder text = new StringBuilder();
if (null != data.conversationTitle) {
text.append(data.conversationTitle).append("\n");
if (null != data.title && !data.isGroupConversation) {
// For 1-on-1, title is redundant if conversationTitle is present
} else if (null != data.title) {
text.append(data.title).append(": ");
}
} else if (null != data.title) {
text.append(data.title).append("\n");
}

// icon
if (null != data.messages && !data.messages.isEmpty()) {
for (NotificationData.Message msg : data.messages) {
if (text.length() > 0 && text.charAt(text.length() - 1) != '\n') {
text.append("\n");
}
if (null != msg.sender && (data.isGroupConversation || !msg.sender.equals(data.title))) {
text.append(msg.sender).append(": ");
}
text.append(msg.text);
}
} else if (null != data.text) {
if (text.length() > 0 && text.charAt(text.length() - 1) != '\n') {
text.append("\n");
}
text.append(data.text);
}
builder.setText(text.toString());
builder.setFootnote(null != data.appName ? data.appName : data.packageName);

// icon (App Icon)
if (null != data.icon && null != data.icon.bytes) {
Bitmap bitmap = BitmapFactory.decodeByteArray(data.icon.bytes, 0, data.icon.bytes.length);
builder.setIcon(bitmap);

// In COLUMNS layout, if we have no images but have an icon,
// putting the icon in addImage makes it a nice large side-image
if (layout == CardBuilder.Layout.COLUMNS && (null == data.messages || data.messages.isEmpty())) {
builder.addImage(bitmap);
}
}

// image (Background or Mosaic)
if (null != data.image && null != data.image.bytes) {
Bitmap bitmap = BitmapFactory.decodeByteArray(data.image.bytes, 0, data.image.bytes.length);
builder.addImage(bitmap);
} else if (null != data.messages && !data.messages.isEmpty()) {
// Mosaic of senders
int added = 0;
for (NotificationData.Message msg : data.messages) {
if (null != msg.senderIcon && null != msg.senderIcon.bytes) {
Bitmap bitmap = BitmapFactory.decodeByteArray(msg.senderIcon.bytes, 0, msg.senderIcon.bytes.length);
builder.addImage(bitmap);
if (++added >= 5) break; // Glass mosaic limit
}
}
}

// time
Expand Down
13 changes: 13 additions & 0 deletions gradle/gradle-daemon-jvm.properties
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@
#This file is generated by updateDaemonJvm
toolchainUrl.FREE_BSD.AARCH64=https\://api.foojay.io/disco/v3.0/ids/56a19bc915b9ba2eb62ba7554c61b919/redirect
toolchainUrl.FREE_BSD.X86_64=https\://api.foojay.io/disco/v3.0/ids/398ffe3949748bfb1d5636f023d228fd/redirect
toolchainUrl.LINUX.AARCH64=https\://api.foojay.io/disco/v3.0/ids/56a19bc915b9ba2eb62ba7554c61b919/redirect
toolchainUrl.LINUX.X86_64=https\://api.foojay.io/disco/v3.0/ids/398ffe3949748bfb1d5636f023d228fd/redirect
toolchainUrl.MAC_OS.AARCH64=https\://api.foojay.io/disco/v3.0/ids/e99bae143b75f9a10ead10248f02055e/redirect
toolchainUrl.MAC_OS.X86_64=https\://api.foojay.io/disco/v3.0/ids/04e088f8677de3b384108493cc9481d0/redirect
toolchainUrl.UNIX.AARCH64=https\://api.foojay.io/disco/v3.0/ids/56a19bc915b9ba2eb62ba7554c61b919/redirect
toolchainUrl.UNIX.X86_64=https\://api.foojay.io/disco/v3.0/ids/398ffe3949748bfb1d5636f023d228fd/redirect
toolchainUrl.WINDOWS.AARCH64=https\://api.foojay.io/disco/v3.0/ids/e55dccbfe27cb97945148c61a39c89c5/redirect
toolchainUrl.WINDOWS.X86_64=https\://api.foojay.io/disco/v3.0/ids/dbd05c4936d573642f94cd149e1356c8/redirect
toolchainVendor=JETBRAINS
toolchainVersion=21
1 change: 1 addition & 0 deletions mobile/src/main/AndroidManifest.xml
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,7 @@
<uses-permission android:name="android.permission.ACCESS_WIFI_STATE" />
<!-- Bluetooth host -->
<uses-permission android:name="android.permission.BLUETOOTH" />
<uses-permission android:name="android.permission.BLUETOOTH_ADMIN" />
<uses-permission android:name="android.permission.BLUETOOTH_CONNECT" />
<!-- GPS extension -->
<uses-permission android:name="android.permission.ACCESS_FINE_LOCATION" />
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -151,9 +151,9 @@ private void runLoop(BluetoothSocket socket) throws Exception {
OutputStream outputStream = socket.getOutputStream()) {
IMessageSerializer serializer = SerializerProvider.getSerializer(inputStream, outputStream);
while (mActive) {
while (inputStream.available() > 0) {
while (serializer.isReady() || inputStream.available() > 0) {
RPCMessage objectReceived = serializer.readMessage();
if (null == objectReceived.service)
if (null == objectReceived || null == objectReceived.service)
return; // shutdown requested
mHandler.onDataReceived(objectReceived);
}
Expand Down
4 changes: 2 additions & 2 deletions mobile/src/main/java/com/damn/anotherglass/core/WiFiHost.kt
Original file line number Diff line number Diff line change
Expand Up @@ -110,9 +110,9 @@ class WiFiHost(listener: RPCMessageListener) : IRPCHost {
return // disconnect requested
}
}
while (mActive && inputStream.available() > 0) {
while (mActive && (serializer.isReady || inputStream.available() > 0)) {
val message = serializer.readMessage()
if (message.service == null) {
if (message?.service == null) {
return // client disconnected
}
mHandler.onDataReceived(message)
Expand Down
Loading