diff --git a/app/build.gradle b/app/build.gradle
index 26a4072..be84649 100755
--- a/app/build.gradle
+++ b/app/build.gradle
@@ -1,13 +1,13 @@
apply plugin: 'com.android.application'
android {
- compileSdkVersion 23
- buildToolsVersion "23.0.2"
+ compileSdkVersion 25
+ buildToolsVersion "26.0.0"
defaultConfig {
applicationId "rumpold.de.androiddsky"
minSdkVersion 21
- targetSdkVersion 23
+ targetSdkVersion 25
versionCode 1
versionName "1.0"
}
@@ -22,6 +22,8 @@ android {
dependencies {
compile fileTree(dir: 'libs', include: ['*.jar'])
testCompile 'junit:junit:4.12'
- compile 'com.android.support:appcompat-v7:23.4.0'
- compile 'com.android.support:support-v4:23.4.0'
+
+ def supportLibVersion = "25.4.0"
+ compile "com.android.support:appcompat-v7:$supportLibVersion"
+ compile "com.android.support:support-v4:$supportLibVersion"
}
diff --git a/app/src/main/AndroidManifest.xml b/app/src/main/AndroidManifest.xml
index 7d1c75d..e343f86 100755
--- a/app/src/main/AndroidManifest.xml
+++ b/app/src/main/AndroidManifest.xml
@@ -21,5 +21,5 @@
-
+
\ No newline at end of file
diff --git a/app/src/main/java/de/rumpold/androiddsky/DSKY.java b/app/src/main/java/de/rumpold/androiddsky/DSKY.java
index d5b9dc3..991c8d4 100755
--- a/app/src/main/java/de/rumpold/androiddsky/DSKY.java
+++ b/app/src/main/java/de/rumpold/androiddsky/DSKY.java
@@ -7,8 +7,6 @@ import java.io.IOException;
import java.util.Arrays;
import java.util.HashMap;
import java.util.Map;
-import java.util.concurrent.ScheduledThreadPoolExecutor;
-import java.util.concurrent.TimeUnit;
import de.rumpold.androiddsky.network.YaAgcClient;
import de.rumpold.androiddsky.ui.DSKYActivity;
@@ -17,8 +15,7 @@ import de.rumpold.androiddsky.ui.DSKYActivity;
* Created by Adriano on 17.05.2016.
*/
public class DSKY {
- public static final String TAG = "TAG";
- public static final int UPDATE_RATE = 25;
+ private static final String TAG = "TAG";
private final DSKYActivity activity;
private final YaAgcClient client;
@@ -30,9 +27,10 @@ public class DSKY {
private char signR1;
private char signR2;
private char signR3;
- private String[] register1 = new String[5];
- private String[] register2 = new String[5];
- private String[] register3 = new String[5];
+
+ private char[] register1 = new char[5];
+ private char[] register2 = new char[5];
+ private char[] register3 = new char[5];
private boolean compActy;
private boolean uplinkActy;
@@ -47,9 +45,9 @@ public class DSKY {
private boolean oprErr;
private boolean stby;
private boolean restart;
- private final ScheduledThreadPoolExecutor executor;
private final Map keycodeMap = new HashMap<>();
+
{
keycodeMap.put("0", 16);
keycodeMap.put("1", 1);
@@ -69,17 +67,20 @@ public class DSKY {
keycodeMap.put("ENTR", 28);
keycodeMap.put("CLR", 30);
keycodeMap.put("NOUN", 31);
+ keycodeMap.put("PRO", 1 << 13);
}
public DSKY(DSKYActivity activity) {
this.activity = activity;
this.client = new YaAgcClient(this);
- this.executor = new ScheduledThreadPoolExecutor(1);
+ Arrays.fill(register1, ' ');
+ Arrays.fill(register2, ' ');
+ Arrays.fill(register3, ' ');
+ }
- Arrays.fill(register1, "");
- Arrays.fill(register2, "");
- Arrays.fill(register3, "");
+ public DSKYActivity getActivity() {
+ return activity;
}
public void connect() {
@@ -93,43 +94,39 @@ public class DSKY {
}
}
});
-
- executor.scheduleAtFixedRate(new Runnable() {
- @Override
- public void run() {
- activity.updateIndicator(R.id.lbl_gimbalLock, gimbalLock);
- activity.updateIndicator(R.id.lbl_noAtt, noAtt);
- activity.updateIndicator(R.id.lbl_uplinkActy, uplinkActy);
- activity.updateIndicator(R.id.lbl_prog, progError);
- activity.updateIndicator(R.id.lbl_tracker, tracker);
- activity.updateIndicator(R.id.lbl_oprErr, oprErr);
- activity.updateIndicator(R.id.lbl_stby, stby);
- activity.updateIndicator(R.id.lbl_keyRel, keyRel);
- activity.updateIndicator(R.id.lbl_restart, restart);
-
- activity.updateIndicator(R.id.lbl_compActy, compActy);
- activity.updateDisplay(R.id.lbl_progId, prog);
- activity.updateDisplay(R.id.lbl_verb, verb);
- activity.updateDisplay(R.id.lbl_noun, noun);
-
- activity.updateDisplay(R.id.lbl_R1, concat(register1));
- activity.updateDisplay(R.id.lbl_R2, concat(register2));
- activity.updateDisplay(R.id.lbl_R3, concat(register3));
-
-
- activity.updateDisplay(R.id.lbl_sign_R1, String.valueOf(signR1));
- activity.updateDisplay(R.id.lbl_sign_R2, String.valueOf(signR2));
- activity.updateDisplay(R.id.lbl_sign_R3, String.valueOf(signR3));
- }
- }, UPDATE_RATE, UPDATE_RATE, TimeUnit.MILLISECONDS);
}
- private String concat(String[] array) {
- final StringBuffer buffer = new StringBuffer();
- for (int i = 0; i < array.length; i++) {
- buffer.append(array[i]);
+ public void refreshDisplay() {
+ activity.updateIndicator(R.id.lbl_gimbalLock, gimbalLock);
+ activity.updateIndicator(R.id.lbl_noAtt, noAtt);
+ activity.updateIndicator(R.id.lbl_uplinkActy, uplinkActy);
+ activity.updateIndicator(R.id.lbl_prog, progError);
+ activity.updateIndicator(R.id.lbl_tracker, tracker);
+ activity.updateIndicator(R.id.lbl_oprErr, oprErr);
+ activity.updateIndicator(R.id.lbl_stby, stby);
+ activity.updateIndicator(R.id.lbl_keyRel, keyRel);
+ activity.updateIndicator(R.id.lbl_restart, restart);
+
+ activity.updateIndicator(R.id.lbl_compActy, compActy);
+ activity.updateDisplay(R.id.lbl_progId, prog);
+ activity.updateDisplay(R.id.lbl_verb, verb);
+ activity.updateDisplay(R.id.lbl_noun, noun);
+
+ activity.updateDisplay(R.id.lbl_R1, join(register1));
+ activity.updateDisplay(R.id.lbl_R2, join(register2));
+ activity.updateDisplay(R.id.lbl_R3, join(register3));
+
+ activity.updateDisplay(R.id.lbl_sign_R1, String.valueOf(signR1));
+ activity.updateDisplay(R.id.lbl_sign_R2, String.valueOf(signR2));
+ activity.updateDisplay(R.id.lbl_sign_R3, String.valueOf(signR3));
+ }
+
+ private static String join(char[] chars) {
+ final StringBuilder builder = new StringBuilder(chars.length);
+ for (char ch : chars) {
+ builder.append(ch);
}
- return buffer.toString();
+ return builder.toString();
}
public void disconnect() {
@@ -143,8 +140,6 @@ public class DSKY {
}
}
});
-
- executor.shutdownNow();
}
public void setCompActy(boolean compActy) {
@@ -211,46 +206,59 @@ public class DSKY {
this.verb = verb;
}
- public void setRegister1(int index, String digit) {
+ public void setRegister1(int index, char digit) {
Log.d(TAG, "setRegister1: " + index + ", " + digit);
this.register1[index] = digit;
}
- public void setRegister2(int index, String digit) {
+ public void setRegister2(int index, char digit) {
Log.d(TAG, "setRegister2: " + index + ", " + digit);
this.register2[index] = digit;
}
- public void setRegister3(int index, String digit) {
+ public void setRegister3(int index, char digit) {
Log.d(TAG, "setRegister3: " + index + ", " + digit);
this.register3[index] = digit;
}
- public void setSignR1(char signR1) {
- this.signR1 = signR1;
+ public void setSignR1(boolean signR1P, boolean signR1N) {
+ if (signR1N == signR1P) {
+ signR1 = ' ';
+ } else if (signR1P) {
+ signR1 = '+';
+ } else {
+ signR1 = '-';
+ }
}
- public void setSignR2(char signR2) {
- this.signR2 = signR2;
+ public void setSignR2(boolean signR2P, boolean signR2N) {
+ if (signR2N == signR2P) {
+ signR2 = ' ';
+ } else if (signR2P) {
+ signR2 = '+';
+ } else {
+ signR2 = '-';
+ }
}
- public void setSignR3(char signR3) {
- this.signR3 = signR3;
+ public void setSignR3(boolean signR3P, boolean signR3N) {
+ if (signR3N == signR3P) {
+ signR3 = ' ';
+ } else if (signR3P) {
+ signR3 = '+';
+ } else {
+ signR3 = '-';
+ }
}
public void buttonPressed(final String button) {
Log.d(TAG, "buttonPressed: " + button);
-
AsyncTask.execute(new Runnable() {
@Override
public void run() {
try {
- if ("PRO".equals(button)) {
- client.sendProceed();
- } else {
- final Integer keyCode = keycodeMap.get(button);
- client.sendKeyCode(keyCode);
- }
+ final Integer keyCode = keycodeMap.get(button);
+ client.sendKeyCode(keyCode);
} catch (IOException e) {
Log.w(TAG, "buttonPressed: Could not send key press", e);
}
diff --git a/app/src/main/java/de/rumpold/androiddsky/network/AgcPacket.java b/app/src/main/java/de/rumpold/androiddsky/network/AgcPacket.java
index aa3df89..e4ec049 100755
--- a/app/src/main/java/de/rumpold/androiddsky/network/AgcPacket.java
+++ b/app/src/main/java/de/rumpold/androiddsky/network/AgcPacket.java
@@ -1,13 +1,15 @@
package de.rumpold.androiddsky.network;
+import android.util.Log;
+
import java.nio.ByteBuffer;
-import java.nio.ByteOrder;
/**
* Created by Adriano on 17.05.2016.
*/
public class AgcPacket {
- public static final int PACKET_LENGTH = 4;
+ private static final int PACKET_LENGTH = 4;
+ private static final String TAG = AgcPacket.class.getSimpleName();
private final boolean u;
private final boolean t;
@@ -31,22 +33,13 @@ public class AgcPacket {
*/
public static AgcPacket parseAgcPacket(ByteBuffer bytes) {
try {
- bytes.rewind();
-
- /*final StringBuilder sb = new StringBuilder();
- for (byte b : bytes.array()) {
- sb.append(String.format("%8s", Integer.toBinaryString(((int) b) & 0xff)).replace(' ', '0'));
- sb.append(' ');
- }
- Log.d("AGCPacket", "AgcPacket: " + sb.toString());*/
-
- bytes.order(ByteOrder.BIG_ENDIAN);
if (bytes.remaining() != PACKET_LENGTH) {
// invalid packet length
- throw new IllegalArgumentException("packet length");
+ //throw new IllegalArgumentException("packet length, " + bytes.remaining() + " != " + PACKET_LENGTH);
+ return null;
}
- /* PARSE BYTE #1 */
+ /* PARSE BYTE #1 */
int byteNum = 0;
char c = (char) ((short) bytes.get() & 0xff);
validateByteHeader(c, byteNum);
@@ -56,7 +49,7 @@ public class AgcPacket {
boolean t = (c & 0b0001_0000) > 0;
int ioPort = c & 0b0000_1111;
- /* PARSE BYTE #2 */
+ /* PARSE BYTE #2 */
++byteNum;
c = (char) ((short) bytes.get() & 0xff);
validateByteHeader(c, byteNum);
@@ -64,14 +57,14 @@ public class AgcPacket {
ioPort = (ioPort << 3) | (c & 0b0011_1000) >> 3;
int dataCode = (c & 0b0000_0111);
- /* PARSE BYTE #3 */
+ /* PARSE BYTE #3 */
++byteNum;
c = (char) ((short) bytes.get() & 0xff);
validateByteHeader(c, byteNum);
dataCode = (dataCode << 6) | (c & 0b0011_1111);
- /* PARSE BYTE #4 */
+ /* PARSE BYTE #4 */
++byteNum;
c = (char) ((short) bytes.get() & 0xff);
validateByteHeader(c, byteNum);
@@ -80,14 +73,16 @@ public class AgcPacket {
return new AgcPacket(dataCode, u, t, ioPort);
} catch (Exception e) {
+ Log.w(TAG, "parseAgcPacket: ", e);
return null;
}
}
private static void validateByteHeader(char c, int byteNum) {
- if ((c & 0b1100_0000) >> 6 != byteNum) {
+ final int header = (c & 0b1100_0000) >> 6;
+ if (header != byteNum) {
// invalid byte header
- throw new IllegalArgumentException("packet byte header in byte #" + byteNum);
+ throw new IllegalArgumentException("packet byte header in byte #" + byteNum + ", got " + header);
}
}
@@ -99,14 +94,6 @@ public class AgcPacket {
return ioPort;
}
- public boolean t() {
- return t;
- }
-
- public boolean u() {
- return u;
- }
-
@Override
public String toString() {
return "AgcPacket{" +
diff --git a/app/src/main/java/de/rumpold/androiddsky/network/YaAgcClient.java b/app/src/main/java/de/rumpold/androiddsky/network/YaAgcClient.java
index cfe4e1b..3ffdd7b 100755
--- a/app/src/main/java/de/rumpold/androiddsky/network/YaAgcClient.java
+++ b/app/src/main/java/de/rumpold/androiddsky/network/YaAgcClient.java
@@ -1,6 +1,7 @@
package de.rumpold.androiddsky.network;
import android.util.Log;
+import android.widget.Toast;
import java.io.IOException;
import java.net.InetSocketAddress;
@@ -13,32 +14,50 @@ import de.rumpold.androiddsky.DSKY;
* Created by Adriano on 17.05.2016.
*/
public class YaAgcClient {
- public static final int YAAGC_SERVER_PORT = 19698;
- private static final String TAG = "YaAGC client";
- public static final int KEYBOARD_CHANNEL = 015;
- private final DSKY dsky;
+ private static final String YAAGC_HOST = "192.168.178.67";
+ private static final int YAAGC_SERVER_PORT = 19698;
+ private static final String TAG = YaAgcClient.class.getSimpleName();
+ private static final int KEYBOARD_CHANNEL = 015;
+
+ private final DSKY dsky;
private SocketChannel agcChannel;
private Thread handler;
+ /* Last state of the +/- indicators for each register */
+ private boolean lastR1P = false;
+ private boolean lastR1N = false;
+ private boolean lastR2P = false;
+ private boolean lastR2N = false;
+ private boolean lastR3P = false;
+ private boolean lastR3N = false;
+
private class DSKYHandler implements Runnable {
@Override
public void run() {
- final ByteBuffer buf = ByteBuffer.allocate(4);
+ final ByteBuffer buf = ByteBuffer.allocate(64);
while (!Thread.interrupted()) {
try {
- buf.rewind();
if (!agcChannel.isConnected()) {
- Thread.sleep(500);
+ Thread.sleep(100);
continue;
}
-
- agcChannel.read(buf);
+ buf.rewind();
+ int numRead = agcChannel.read(buf);
buf.rewind();
- handleAgcPacket(AgcPacket.parseAgcPacket(buf));
+ final int subPacketCount = numRead / 4;
+ for (int index = 0; index < subPacketCount; ++index) {
+ final ByteBuffer subPacket = (ByteBuffer) buf.slice().limit(4);
+ handleAgcPacket(AgcPacket.parseAgcPacket(subPacket));
+
+ buf.position(buf.position() + 4);
+ }
} catch (IOException | InterruptedException e) {
- e.printStackTrace();
+ Toast.makeText(dsky.getActivity().getApplicationContext(),
+ "Connection failure",
+ Toast.LENGTH_SHORT).show();
+ Log.w(TAG, "Connection error", e);
}
}
}
@@ -50,7 +69,7 @@ public class YaAgcClient {
public void connect() throws IOException {
agcChannel = SocketChannel.open();
- agcChannel.connect(new InetSocketAddress("137.250.170.198", YAAGC_SERVER_PORT));
+ agcChannel.connect(new InetSocketAddress(YAAGC_HOST, YAAGC_SERVER_PORT));
handler = new Thread(new DSKYHandler(), "DSKY I/O Handler");
handler.start();
@@ -68,16 +87,11 @@ public class YaAgcClient {
agcChannel.close();
}
-
- public void sendProceed() throws IOException {
- sendChannelOutput(KEYBOARD_CHANNEL, 1 << 13);
- }
-
public void sendKeyCode(int keyCode) throws IOException {
sendChannelOutput(KEYBOARD_CHANNEL, keyCode);
}
- protected void sendChannelOutput(int channel, int data) throws IOException {
+ private void sendChannelOutput(int channel, int data) throws IOException {
final byte[] packet = new byte[]{
(byte) (((channel >> 3) & 0b1111) & 0xff),
(byte) ((0b0100_0000 | (channel & 0b111) << 3 | ((data >> 12) & 0b111)) & 0xff),
@@ -90,196 +104,216 @@ public class YaAgcClient {
agcChannel.write(buffer);
}
- protected String extractDigit(int digitCode) {
+ private char extractDigit(int digitCode) {
switch (digitCode) {
case 0:
- return " ";
+ return ' ';
case 21:
- return "0";
+ return '0';
case 3:
- return "1";
+ return '1';
case 25:
- return "2";
+ return '2';
case 27:
- return "3";
+ return '3';
case 15:
- return "4";
+ return '4';
case 30:
- return "5";
+ return '5';
case 28:
- return "6";
+ return '6';
case 19:
- return "7";
+ return '7';
case 29:
- return "8";
+ return '8';
case 31:
- return "9";
+ return '9';
default:
- throw new IllegalArgumentException("Invalid TAG digit code: " + digitCode);
+ throw new IllegalArgumentException("Invalid digit code: " + digitCode);
}
}
- protected void handleAgcPacket(AgcPacket packet) {
+ private void handleAgcPacket(AgcPacket packet) {
if (packet == null) {
return;
}
switch (packet.getIoPort()) {
- case 010: {
- // TAG 7-segment displays
- final int digitIdx = (packet.getDataCode() >> 11) & 0b1111;
- final int data = packet.getDataCode() & 0b1_11111_11111;
+ case 010:
+ handleChannel10(packet);
+ break;
- final int b = (data >> 10) & 0b1;
- final int c = (data >> 5) & 0b11111;
- final int d = data & 0b11111;
+ case 011:
+ handleChannel11(packet);
+ break;
+ }
- switch (digitIdx) {
- case 11: {
- // PROG digits
+ // Update register sign indicator displays
+ dsky.setSignR1(lastR1P, lastR1N);
+ dsky.setSignR2(lastR2P, lastR2N);
+ dsky.setSignR3(lastR3P, lastR3N);
- final String prog = extractDigit(c) + extractDigit(d);
- dsky.setProg(prog);
+ dsky.refreshDisplay();
+ }
- Log.d(TAG, "[DSKY PROG] " + prog);
- break;
- }
+ /**
+ * Handle changes of the indicator lights, transmitted on I/O channel 11
+ *
+ * @param packet
+ */
+ private void handleChannel11(AgcPacket packet) {
+ final boolean compActy = (packet.getDataCode() & 0b0000_0010) != 0;
+ final boolean uplinkActy = (packet.getDataCode() & 0b0000_0100) != 0;
+ final boolean temp = (packet.getDataCode() & 0b0000_1000) != 0;
- case 10: {
- // Verb digits
- final String verb = extractDigit(c) + extractDigit(d);
- dsky.setVerb(verb);
+ dsky.setCompActy(compActy);
+ dsky.setUplinkActy(uplinkActy);
+ dsky.setTemp(temp);
- Log.d(TAG, "[DSKY VERB] " + verb);
- break;
- }
+ Log.d(TAG, String.format("[DSKY indicators] compActy = %s, uplinkActy = %s, temp = %s",
+ compActy, uplinkActy, temp));
+ }
- case 9: {
- // Noun digits
- final String noun = extractDigit(c) + extractDigit(d);
- dsky.setNoun(noun);
+ /**
+ * Handle changes of display segments, transmitted on I/O channel 10
+ *
+ * @param packet
+ */
+ private void handleChannel10(AgcPacket packet) {
+ final int digitIdx = (packet.getDataCode() >> 11) & 0b1111;
+ final int data = packet.getDataCode() & 0b1_11111_11111;
- Log.d(TAG, "[DSKY NOUN] " + noun);
- break;
- }
+ final int b = (data >> 10) & 0b1;
+ final int c = (data >> 5) & 0b11111;
+ final int d = data & 0b11111;
- case 8: {
- // First digit of R1
- dsky.setRegister1(0, extractDigit(d));
- break;
- }
+ switch (digitIdx) {
+ case 11: {
+ // PROG digits
+ final String prog = "" + extractDigit(c) + extractDigit(d);
+ dsky.setProg(prog);
- case 7: {
- // 2nd & 3rd digit of R1, + sign R1
- dsky.setRegister1(1, extractDigit(c));
- dsky.setRegister1(2, extractDigit(d));
- dsky.setSignR1(b > 0 ? '+' : ' ');
- break;
- }
+ Log.d(TAG, "[DSKY PROG] " + prog);
+ break;
+ }
- case 6: {
- // 4th & 5th digit of R1, - sign R1
- dsky.setRegister1(3, extractDigit(c));
- dsky.setRegister1(4, extractDigit(d));
- dsky.setSignR1(b > 0 ? '-' : ' ');
- break;
- }
+ case 10: {
+ // Verb digits
+ final String verb = "" + extractDigit(c) + extractDigit(d);
+ dsky.setVerb(verb);
- case 5: {
- // 1st & 2nd digit of R2, + sign R2
- dsky.setRegister2(0, extractDigit(c));
- dsky.setRegister2(1, extractDigit(d));
- dsky.setSignR2(b > 0 ? '+' : ' ');
- break;
- }
+ Log.d(TAG, "[DSKY VERB] " + verb);
+ break;
+ }
- case 4: {
- // 3rd & 4th digit of R2, - sign R2
- dsky.setRegister2(2, extractDigit(c));
- dsky.setRegister2(3, extractDigit(d));
- dsky.setSignR2(b > 0 ? '-' : ' ');
- break;
- }
+ case 9: {
+ // Noun digits
+ final String noun = "" + extractDigit(c) + extractDigit(d);
+ dsky.setNoun(noun);
- case 3: {
- // 5th digit of R2, 1st digit of R3
- dsky.setRegister2(4, extractDigit(c));
- dsky.setRegister3(0, extractDigit(d));
- break;
- }
+ Log.d(TAG, "[DSKY NOUN] " + noun);
+ break;
+ }
- case 2: {
- // 2nd & 3rd digit of R3, + sign R3
- dsky.setRegister3(1, extractDigit(c));
- dsky.setRegister3(2, extractDigit(d));
- dsky.setSignR3(b > 0 ? '+' : ' ');
- break;
- }
+ case 8: {
+ // First digit of R1
+ dsky.setRegister1(0, extractDigit(d));
+ break;
+ }
- case 1: {
- // 4th & 5th digit of R3, - sign R3
- dsky.setRegister3(3, extractDigit(c));
- dsky.setRegister3(4, extractDigit(d));
- dsky.setSignR3(b > 0 ? '-' : ' ');
- break;
- }
-
- case 12: {
- // Indicators
- final boolean vel = (data & 0b0_00000_00100) > 0;
- final boolean noAtt = (data & 0b0_00000_01000) > 0;
- final boolean alt = (data & 0b0_00000_10000) > 0;
- final boolean gimbalLock = (data & 0b0_00001_00000) > 0;
- final boolean tracker = (data & 0b0_00100_00000) > 0;
- final boolean prog = (data & 0b0_01000_00000) > 0;
-
- dsky.setVel(vel);
- dsky.setNoAtt(noAtt);
- dsky.setAlt(alt);
- dsky.setGimbalLock(gimbalLock);
- dsky.setTracker(tracker);
- dsky.setProgError(prog);
-
- Log.d(TAG, String.format("[DSKY indicators] vel = %s, noAtt = %s, alt = %s, gimbalLock = %s, tracker = %s, prog = %s",
- vel, noAtt, alt, gimbalLock, tracker, prog));
- break;
- }
-
- default:
+ case 7: {
+ // 2nd & 3rd digit of R1, + sign R1
+ dsky.setRegister1(1, extractDigit(c));
+ dsky.setRegister1(2, extractDigit(d));
+ lastR1P = b > 0;
+ if (lastR1P) {
+ lastR1N = false;
}
-
break;
}
- case 011: {
- // TAG indicator lights
- final boolean compActy = (packet.getDataCode() & 0b0000_0010) != 0;
- final boolean uplinkActy = (packet.getDataCode() & 0b0000_0100) != 0;
- final boolean temp = (packet.getDataCode() & 0b0000_1000) != 0;
-
- dsky.setCompActy(compActy);
- dsky.setUplinkActy(uplinkActy);
- dsky.setTemp(temp);
-
- Log.d(TAG, String.format("[DSKY indicators] compActy = %s, uplinkActy = %s, temp = %s",
- compActy, uplinkActy, temp));
-
+ case 6: {
+ // 4th & 5th digit of R1, - sign R1
+ dsky.setRegister1(3, extractDigit(c));
+ dsky.setRegister1(4, extractDigit(d));
+ lastR1N = b > 0;
+ if (lastR1N) {
+ lastR1P = false;
+ }
break;
}
- default:
+ case 5: {
+ // 1st & 2nd digit of R2, + sign R2
+ dsky.setRegister2(0, extractDigit(c));
+ dsky.setRegister2(1, extractDigit(d));
+ lastR2P = b > 0;
+ break;
+ }
+
+ case 4: {
+ // 3rd & 4th digit of R2, - sign R2
+ dsky.setRegister2(2, extractDigit(c));
+ dsky.setRegister2(3, extractDigit(d));
+ lastR2N = b > 0;
+ break;
+ }
+
+ case 3: {
+ // 5th digit of R2, 1st digit of R3
+ dsky.setRegister2(4, extractDigit(c));
+ dsky.setRegister3(0, extractDigit(d));
+ break;
+ }
+
+ case 2: {
+ // 2nd & 3rd digit of R3, + sign R3
+ dsky.setRegister3(1, extractDigit(c));
+ dsky.setRegister3(2, extractDigit(d));
+ lastR3P = b > 0;
+ break;
+ }
+
+ case 1: {
+ // 4th & 5th digit of R3, - sign R3
+ dsky.setRegister3(3, extractDigit(c));
+ dsky.setRegister3(4, extractDigit(d));
+ lastR3N = b > 0;
+ break;
+ }
+
+ case 12: {
+ // Indicators
+ final boolean vel = (data & 0b0_00000_00100) > 0;
+ final boolean noAtt = (data & 0b0_00000_01000) > 0;
+ final boolean alt = (data & 0b0_00000_10000) > 0;
+ final boolean gimbalLock = (data & 0b0_00001_00000) > 0;
+ final boolean tracker = (data & 0b0_00100_00000) > 0;
+ final boolean prog = (data & 0b0_01000_00000) > 0;
+
+ dsky.setVel(vel);
+ dsky.setNoAtt(noAtt);
+ dsky.setAlt(alt);
+ dsky.setGimbalLock(gimbalLock);
+ dsky.setTracker(tracker);
+ dsky.setProgError(prog);
+
+ Log.d(TAG, String.format("[DSKY indicators] vel = %s, noAtt = %s, alt = %s, gimbalLock = %s, tracker = %s, prog = %s",
+ vel, noAtt, alt, gimbalLock, tracker, prog));
+ break;
+ }
}
}
}
\ No newline at end of file
diff --git a/app/src/main/java/de/rumpold/androiddsky/ui/DSKYActivity.java b/app/src/main/java/de/rumpold/androiddsky/ui/DSKYActivity.java
index adcb3a8..11118ad 100755
--- a/app/src/main/java/de/rumpold/androiddsky/ui/DSKYActivity.java
+++ b/app/src/main/java/de/rumpold/androiddsky/ui/DSKYActivity.java
@@ -1,13 +1,10 @@
package de.rumpold.androiddsky.ui;
-import android.annotation.SuppressLint;
-import android.graphics.Color;
import android.os.Bundle;
import android.os.Handler;
import android.support.annotation.IdRes;
-import android.support.v7.app.ActionBar;
import android.support.v7.app.AppCompatActivity;
-import android.view.MotionEvent;
+import android.view.HapticFeedbackConstants;
import android.view.View;
import android.widget.Button;
import android.widget.TextView;
@@ -20,91 +17,45 @@ import de.rumpold.androiddsky.R;
* status bar and navigation/system bar) with user interaction.
*/
public class DSKYActivity extends AppCompatActivity {
- /**
- * Whether or not the system UI should be auto-hidden after
- * {@link #AUTO_HIDE_DELAY_MILLIS} milliseconds.
- */
- private static final boolean AUTO_HIDE = true;
-
- /**
- * If {@link #AUTO_HIDE} is set, the number of milliseconds to wait after
- * user interaction before hiding the system UI.
- */
- private static final int AUTO_HIDE_DELAY_MILLIS = 3000;
-
/**
* Some older devices needs a small delay between UI widget updates
* and a change of the status and navigation bar.
*/
private static final int UI_ANIMATION_DELAY = 300;
- private final Handler mHideHandler = new Handler();
-
- private View mContentView;
- private final Runnable mHidePart2Runnable = new Runnable() {
- @SuppressLint("InlinedApi")
- @Override
- public void run() {
- // Delayed removal of status and navigation bar
-
- // Note that some of these constants are new as of API 16 (Jelly Bean)
- // and API 19 (KitKat). It is safe to use them, as they are inlined
- // at compile-time and do nothing on earlier devices.
- mContentView.setSystemUiVisibility(View.SYSTEM_UI_FLAG_LOW_PROFILE
- | View.SYSTEM_UI_FLAG_FULLSCREEN
- | View.SYSTEM_UI_FLAG_LAYOUT_STABLE
- | View.SYSTEM_UI_FLAG_IMMERSIVE_STICKY
- | View.SYSTEM_UI_FLAG_LAYOUT_HIDE_NAVIGATION
- | View.SYSTEM_UI_FLAG_HIDE_NAVIGATION);
- }
- };
- private View mControlsView;
- private final Runnable mShowPart2Runnable = new Runnable() {
- @Override
- public void run() {
- // Delayed display of UI elements
- ActionBar actionBar = getSupportActionBar();
- if (actionBar != null) {
- actionBar.show();
- }
- mControlsView.setVisibility(View.VISIBLE);
- }
- };
- private boolean mVisible;
- private final Runnable mHideRunnable = new Runnable() {
- @Override
- public void run() {
- hide();
- }
- };
+ private final Handler mViewHandler = new Handler();
private final DSKY dsky = new DSKY(this);
+ private int rightActiveColor;
+ private int activeColor;
+ private int passiveColor;
public void updateIndicator(@IdRes final int id, final boolean state) {
- mHideHandler.post(new Runnable() {
+ mViewHandler.post(new Runnable() {
@Override
public void run() {
TextView indicator = (TextView) findViewById(id);
- if (indicator != null) {
- if (state) {
- final int color;
- if ("right".equals(indicator.getTag())) {
- color = getResources().getColor(R.color.indicatorRightActive);
- } else {
- color = getResources().getColor(R.color.indicatorActive);
- }
+ if (indicator == null) {
+ return;
+ }
- indicator.setBackgroundColor(color);
+ if (state) {
+ final int color;
+ if ("right".equals(indicator.getTag())) {
+ color = rightActiveColor;
} else {
- indicator.setBackgroundColor(getResources().getColor(R.color.indicatorPassive));
+ color = activeColor;
}
+ indicator.setBackgroundColor(color);
+ } else {
+ indicator.setBackgroundColor(passiveColor);
}
}
});
}
public void updateDisplay(@IdRes final int id, final String value) {
- mHideHandler.post(new Runnable() {
+ mViewHandler.post(new Runnable() {
@Override
public void run() {
TextView display = (TextView) findViewById(id);
@@ -113,48 +64,27 @@ public class DSKYActivity extends AppCompatActivity {
});
}
- /**
- * Touch listener to use for in-layout UI controls to delay hiding the
- * system UI. This is to prevent the jarring behavior of controls going away
- * while interacting with activity UI.
- */
- private final View.OnTouchListener mDelayHideTouchListener = new View.OnTouchListener() {
- @Override
- public boolean onTouch(View view, MotionEvent motionEvent) {
- if (AUTO_HIDE) {
- delayedHide(AUTO_HIDE_DELAY_MILLIS);
- }
- return false;
- }
- };
-
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_dsky);
- mVisible = true;
- mControlsView = findViewById(R.id.controlBar);
- mContentView = findViewById(R.id.contentView);
+ // Colors
+ rightActiveColor = getResources().getColor(R.color.indicatorRightActive);
+ activeColor = getResources().getColor(R.color.indicatorActive);
+ passiveColor = getResources().getColor(R.color.indicatorPassive);
+ createButtonListeners();
+ }
- // Set up the user interaction to manually show or hide the system UI.
- mContentView.setOnClickListener(new View.OnClickListener() {
- @Override
- public void onClick(View view) {
- toggle();
- }
- });
-
- // Upon interacting with UI controls, delay any scheduled hide()
- // operations to prevent the jarring behavior of controls going away
- // while interacting with the UI.
-
- View.OnClickListener buttonListener = new View.OnClickListener() {
+ private void createButtonListeners() {
+ final View.OnClickListener buttonListener = new View.OnClickListener() {
@Override
public void onClick(View view) {
final Button button = (Button) view;
+ button.performHapticFeedback(HapticFeedbackConstants.VIRTUAL_KEY,
+ HapticFeedbackConstants.FLAG_IGNORE_GLOBAL_SETTING);
dsky.buttonPressed(button.getText().toString());
}
};
@@ -183,12 +113,6 @@ public class DSKYActivity extends AppCompatActivity {
@Override
protected void onPostCreate(Bundle savedInstanceState) {
super.onPostCreate(savedInstanceState);
-
- // Trigger the initial hide() shortly after the activity has been
- // created, to briefly hint to the user that UI controls
- // are available.
- delayedHide(100);
-
dsky.connect();
}
@@ -197,47 +121,4 @@ public class DSKYActivity extends AppCompatActivity {
super.onDestroy();
dsky.disconnect();
}
-
- private void toggle() {
- if (mVisible) {
- hide();
- } else {
- show();
- }
- }
-
- private void hide() {
- // Hide UI first
- ActionBar actionBar = getSupportActionBar();
- if (actionBar != null) {
- actionBar.hide();
- }
- mControlsView.setVisibility(View.GONE);
- mVisible = false;
-
- // Schedule a runnable to remove the status and navigation bar after a delay
- mHideHandler.removeCallbacks(mShowPart2Runnable);
- mHideHandler.postDelayed(mHidePart2Runnable, UI_ANIMATION_DELAY);
- }
-
- @SuppressLint("InlinedApi")
- private void show() {
- // Show the system bar
- mContentView.setSystemUiVisibility(View.SYSTEM_UI_FLAG_LAYOUT_FULLSCREEN
- | View.SYSTEM_UI_FLAG_LAYOUT_HIDE_NAVIGATION);
- mVisible = true;
-
- // Schedule a runnable to display UI elements after a delay
- mHideHandler.removeCallbacks(mHidePart2Runnable);
- mHideHandler.postDelayed(mShowPart2Runnable, UI_ANIMATION_DELAY);
- }
-
- /**
- * Schedules a call to hide() in [delay] milliseconds, canceling any
- * previously scheduled calls.
- */
- private void delayedHide(int delayMillis) {
- mHideHandler.removeCallbacks(mHideRunnable);
- mHideHandler.postDelayed(mHideRunnable, delayMillis);
- }
}
diff --git a/app/src/main/java/de/rumpold/androiddsky/util/BufferUtils.java b/app/src/main/java/de/rumpold/androiddsky/util/BufferUtils.java
new file mode 100644
index 0000000..ecc0db1
--- /dev/null
+++ b/app/src/main/java/de/rumpold/androiddsky/util/BufferUtils.java
@@ -0,0 +1,31 @@
+package de.rumpold.androiddsky.util;
+
+import android.util.Log;
+
+import org.apache.commons.lang3.StringUtils;
+
+import java.nio.ByteBuffer;
+
+/**
+ * Created by Adriano on 11.06.2017.
+ */
+
+public class BufferUtils {
+ private static void printBuffer(String tag, ByteBuffer buf) {
+ buf.rewind();
+ int index = 0;
+ while (buf.remaining() > 0) {
+ ++index;
+ final int b = (int) buf.get();
+ if (b == 0) {
+ continue;
+ }
+
+ final String bitString = StringUtils.leftPad(Integer.toBinaryString(b), 32, '0').substring(24);
+ Log.d(tag, "printBuffer: " + index + ": " + bitString);
+ }
+ Log.d(tag, "--------------------------------------------------");
+
+ buf.rewind();
+ }
+}
diff --git a/app/src/main/res/layout/activity_dsky.xml b/app/src/main/res/layout/activity_dsky.xml
index 574b328..5770f68 100755
--- a/app/src/main/res/layout/activity_dsky.xml
+++ b/app/src/main/res/layout/activity_dsky.xml
@@ -1,47 +1,26 @@
-
+
-
+
-
-
-
-
-
-
-
-
-
-
-
-
+ android:layout_height="wrap_content"
+ android:layout_gravity="center_horizontal|bottom" />
+
\ No newline at end of file
diff --git a/app/src/main/res/layout/layout_7seg.xml b/app/src/main/res/layout/layout_7seg.xml
index 6522e77..e3ce686 100755
--- a/app/src/main/res/layout/layout_7seg.xml
+++ b/app/src/main/res/layout/layout_7seg.xml
@@ -1,15 +1,10 @@
-
+
+ style="@style/number_label"
+ android:text="PROG" />
+ style="@style/number_display"
+ android:text="00" />
-
-
+
-
+
+ style="@style/number_label"
+ android:text="VERB" />
+ style="@style/number_display"
+ android:text="00" />
-
+
+ style="@style/number_label"
+ android:text="NOUN" />
+ style="@style/number_display"
+ android:text="00" />
-
-
+
+ android:layout_gravity="center"
+ android:layout_span="2">
+ style="@style/number_display"
+ android:text="+" />
+ style="@style/number_display"
+ android:text="00000" />
-
+
+ style="@style/number_display"
+ android:text="+" />
-
+ style="@style/number_display"
+ android:text="00000" />
-
-
+
+ android:layout_gravity="center"
+ android:layout_span="2">
+ style="@style/number_display"
+ android:text="+" />
+ style="@style/number_display"
+ android:text="00000" />
-
\ No newline at end of file
diff --git a/app/src/main/res/layout/layout_keyboard.xml b/app/src/main/res/layout/layout_keyboard.xml
index 0be5b1e..0e51afa 100755
--- a/app/src/main/res/layout/layout_keyboard.xml
+++ b/app/src/main/res/layout/layout_keyboard.xml
@@ -1,189 +1,153 @@
+ android:gravity="center"
+ android:orientation="horizontal">
+ android:gravity="center_vertical"
+ android:orientation="vertical">
+ style="@style/dsky_button"
+ android:text="VERB" />
+ style="@style/dsky_button"
+ android:text="NOUN" />
+ android:gravity="center_vertical"
+ android:orientation="vertical">
+ style="@style/dsky_button"
+ android:text="+" />
+ style="@style/dsky_button"
+ android:text="-" />
+ style="@style/dsky_button"
+ android:text="0" />
+ android:gravity="center_vertical"
+ android:orientation="vertical">
+ style="@style/dsky_button"
+ android:text="7" />
+ style="@style/dsky_button"
+ android:text="4" />
+ style="@style/dsky_button"
+ android:text="1" />
+ android:gravity="center_vertical"
+ android:orientation="vertical">
+ style="@style/dsky_button"
+ android:text="8" />
+ style="@style/dsky_button"
+ android:text="5" />
+ style="@style/dsky_button"
+ android:text="2" />
+ android:gravity="center_vertical"
+ android:orientation="vertical">
+ style="@style/dsky_button"
+ android:text="9" />
+ style="@style/dsky_button"
+ android:text="6" />
+ style="@style/dsky_button"
+ android:text="3" />
+ android:gravity="center_vertical"
+ android:orientation="vertical">
+ style="@style/dsky_button"
+ android:text="CLR" />
+ style="@style/dsky_button"
+ android:text="PRO" />
+ style="@style/dsky_button"
+ android:text="KEY\nREL" />
+ android:gravity="center_vertical"
+ android:orientation="vertical">
+ style="@style/dsky_button"
+ android:text="ENTR" />
+ style="@style/dsky_button"
+ android:text="RSET" />
\ No newline at end of file
diff --git a/app/src/main/res/values/colors.xml b/app/src/main/res/values/colors.xml
index f88203b..e148a3e 100755
--- a/app/src/main/res/values/colors.xml
+++ b/app/src/main/res/values/colors.xml
@@ -5,7 +5,7 @@
#FF4081
#e0e0e0
- #9aff57
+ #78e143
#ffd35c
#66000000
diff --git a/app/src/main/res/values/styles.xml b/app/src/main/res/values/styles.xml
index f9d35b1..0eee1ed 100755
--- a/app/src/main/res/values/styles.xml
+++ b/app/src/main/res/values/styles.xml
@@ -22,12 +22,17 @@
@@ -40,14 +45,30 @@
+
+
+
diff --git a/build.gradle b/build.gradle
index aff4f41..d488da3 100755
--- a/build.gradle
+++ b/build.gradle
@@ -5,7 +5,7 @@ buildscript {
jcenter()
}
dependencies {
- classpath 'com.android.tools.build:gradle:2.1.2'
+ classpath 'com.android.tools.build:gradle:2.3.3'
// NOTE: Do not place your application dependencies here; they belong
// in the individual module build.gradle files
@@ -15,6 +15,9 @@ buildscript {
allprojects {
repositories {
jcenter()
+ maven {
+ url("http://maven.google.com")
+ }
}
}