diff --git a/app/src/main/java/xdsopl/robot36/Decoder.java b/app/src/main/java/xdsopl/robot36/Decoder.java index 2df3b4c..f03eae7 100644 --- a/app/src/main/java/xdsopl/robot36/Decoder.java +++ b/app/src/main/java/xdsopl/robot36/Decoder.java @@ -12,6 +12,7 @@ public class Decoder { private final Demodulator demodulator; private final float[] scanLineBuffer; + private final int[] pixelBuffer; private final int[] scopePixels; private final int[] last5msSyncPulses; private final int[] last9msSyncPulses; @@ -35,6 +36,7 @@ public class Decoder { this.scopePixels = scopePixels; this.scopeWidth = scopeWidth; this.scopeHeight = scopeHeight; + pixelBuffer = new int[scopeWidth]; demodulator = new Demodulator(sampleRate); double scanLineMaxSeconds = 5; int scanLineMaxSamples = (int) Math.round(scanLineMaxSeconds * sampleRate); @@ -92,17 +94,6 @@ public class Decoder { return stdDev; } - private void processOneLine(int prevPulseIndex, int scanLineSamples) { - if (prevPulseIndex < 0 || prevPulseIndex + scanLineSamples >= scanLineBuffer.length) - return; - for (int i = 0; i < scopeWidth; ++i) { - int position = (i * scanLineSamples) / scopeWidth + prevPulseIndex; - int intensity = (int) Math.round(255 * Math.sqrt(scanLineBuffer[position])); - int pixelColor = 0xff000000 | 0x00010101 * intensity; - scopePixels[scopeWidth * curLine + i] = pixelColor; - } - } - private Mode detectMode(ArrayList modes, int line) { Mode bestMode = rawMode; int bestDist = Integer.MAX_VALUE; @@ -116,6 +107,12 @@ public class Decoder { return bestMode; } + private void slideOneLine() { + System.arraycopy(pixelBuffer, 0, scopePixels, scopeWidth * curLine, scopeWidth); + System.arraycopy(pixelBuffer, 0, scopePixels, scopeWidth * (curLine + scopeHeight), scopeWidth); + curLine = (curLine + 1) % scopeHeight; + } + private boolean processSyncPulse(ArrayList modes, int[] pulses, int[] lines, int index) { for (int i = 1; i < lines.length; ++i) lines[i - 1] = lines[i]; @@ -135,10 +132,12 @@ public class Decoder { int extrapolate = endPulse / meanSamples; int firstPulse = endPulse - extrapolate * meanSamples; for (int pulseIndex = firstPulse; pulseIndex < endPulse; pulseIndex += meanSamples) - processOneLine(pulseIndex, meanSamples); + if (mode.decodeScanLine(pixelBuffer, scanLineBuffer, pulseIndex, meanSamples)) + slideOneLine(); } for (int i = 0; i < lines.length; ++i) - processOneLine(pulses[i], lines[i]); + if (mode.decodeScanLine(pixelBuffer, scanLineBuffer, pulses[i], lines[i])) + slideOneLine(); int shift = pulses[pulses.length - 1]; adjustSyncPulses(last5msSyncPulses, shift); adjustSyncPulses(last9msSyncPulses, shift); @@ -147,9 +146,6 @@ public class Decoder { curSample = 0; for (int i = shift; i < endSample; ++i) scanLineBuffer[curSample++] = scanLineBuffer[i]; - for (int i = 0; i < scopeWidth; ++i) - scopePixels[scopeWidth * (curLine + scopeHeight) + i] = scopePixels[scopeWidth * curLine + i]; - curLine = (curLine + 1) % scopeHeight; return true; } diff --git a/app/src/main/java/xdsopl/robot36/Martin.java b/app/src/main/java/xdsopl/robot36/Martin.java index c5d3121..6b062e5 100644 --- a/app/src/main/java/xdsopl/robot36/Martin.java +++ b/app/src/main/java/xdsopl/robot36/Martin.java @@ -27,4 +27,17 @@ public class Martin implements Mode { public int getScanLineSamples() { return scanLineSamples; } + + @Override + public boolean decodeScanLine(int[] pixelBuffer, float[] scanLineBuffer, int prevPulseIndex, int scanLineSamples) { + if (prevPulseIndex < 0 || prevPulseIndex + scanLineSamples >= scanLineBuffer.length) + return false; + for (int i = 0; i < pixelBuffer.length; ++i) { + int position = (i * scanLineSamples) / pixelBuffer.length + prevPulseIndex; + int intensity = (int) Math.round(255 * Math.sqrt(scanLineBuffer[position])); + int pixelColor = 0xff000000 | 0x00010101 * intensity; + pixelBuffer[i] = pixelColor; + } + return true; + } } diff --git a/app/src/main/java/xdsopl/robot36/Mode.java b/app/src/main/java/xdsopl/robot36/Mode.java index fdfbb11..d726b50 100644 --- a/app/src/main/java/xdsopl/robot36/Mode.java +++ b/app/src/main/java/xdsopl/robot36/Mode.java @@ -8,5 +8,8 @@ package xdsopl.robot36; public interface Mode { String getName(); + int getScanLineSamples(); + + boolean decodeScanLine(int[] pixelBuffer, float[] scanLineBuffer, int prevPulseIndex, int scanLineSamples); } diff --git a/app/src/main/java/xdsopl/robot36/PaulDon.java b/app/src/main/java/xdsopl/robot36/PaulDon.java index f324ab2..a25e02d 100644 --- a/app/src/main/java/xdsopl/robot36/PaulDon.java +++ b/app/src/main/java/xdsopl/robot36/PaulDon.java @@ -27,4 +27,17 @@ public class PaulDon implements Mode { public int getScanLineSamples() { return scanLineSamples; } + + @Override + public boolean decodeScanLine(int[] pixelBuffer, float[] scanLineBuffer, int prevPulseIndex, int scanLineSamples) { + if (prevPulseIndex < 0 || prevPulseIndex + scanLineSamples >= scanLineBuffer.length) + return false; + for (int i = 0; i < pixelBuffer.length; ++i) { + int position = (i * scanLineSamples) / pixelBuffer.length + prevPulseIndex; + int intensity = (int) Math.round(255 * Math.sqrt(scanLineBuffer[position])); + int pixelColor = 0xff000000 | 0x00010101 * intensity; + pixelBuffer[i] = pixelColor; + } + return true; + } } diff --git a/app/src/main/java/xdsopl/robot36/Raw.java b/app/src/main/java/xdsopl/robot36/Raw.java index dedd465..c5a03df 100644 --- a/app/src/main/java/xdsopl/robot36/Raw.java +++ b/app/src/main/java/xdsopl/robot36/Raw.java @@ -20,4 +20,17 @@ public class Raw implements Mode { public int getScanLineSamples() { return -1; } + + @Override + public boolean decodeScanLine(int[] pixelBuffer, float[] scanLineBuffer, int prevPulseIndex, int scanLineSamples) { + if (prevPulseIndex < 0 || prevPulseIndex + scanLineSamples >= scanLineBuffer.length) + return false; + for (int i = 0; i < pixelBuffer.length; ++i) { + int position = (i * scanLineSamples) / pixelBuffer.length + prevPulseIndex; + int intensity = (int) Math.round(255 * Math.sqrt(scanLineBuffer[position])); + int pixelColor = 0xff000000 | 0x00010101 * intensity; + pixelBuffer[i] = pixelColor; + } + return true; + } } diff --git a/app/src/main/java/xdsopl/robot36/Robot_36_Color.java b/app/src/main/java/xdsopl/robot36/Robot_36_Color.java index 1e6e4aa..9bd91f2 100644 --- a/app/src/main/java/xdsopl/robot36/Robot_36_Color.java +++ b/app/src/main/java/xdsopl/robot36/Robot_36_Color.java @@ -29,4 +29,17 @@ public class Robot_36_Color implements Mode { public int getScanLineSamples() { return scanLineSamples; } + + @Override + public boolean decodeScanLine(int[] pixelBuffer, float[] scanLineBuffer, int prevPulseIndex, int scanLineSamples) { + if (prevPulseIndex < 0 || prevPulseIndex + scanLineSamples >= scanLineBuffer.length) + return false; + for (int i = 0; i < pixelBuffer.length; ++i) { + int position = (i * scanLineSamples) / pixelBuffer.length + prevPulseIndex; + int intensity = (int) Math.round(255 * Math.sqrt(scanLineBuffer[position])); + int pixelColor = 0xff000000 | 0x00010101 * intensity; + pixelBuffer[i] = pixelColor; + } + return true; + } } diff --git a/app/src/main/java/xdsopl/robot36/Robot_72_Color.java b/app/src/main/java/xdsopl/robot36/Robot_72_Color.java index db8788f..303a1fe 100644 --- a/app/src/main/java/xdsopl/robot36/Robot_72_Color.java +++ b/app/src/main/java/xdsopl/robot36/Robot_72_Color.java @@ -29,4 +29,17 @@ public class Robot_72_Color implements Mode { public int getScanLineSamples() { return scanLineSamples; } + + @Override + public boolean decodeScanLine(int[] pixelBuffer, float[] scanLineBuffer, int prevPulseIndex, int scanLineSamples) { + if (prevPulseIndex < 0 || prevPulseIndex + scanLineSamples >= scanLineBuffer.length) + return false; + for (int i = 0; i < pixelBuffer.length; ++i) { + int position = (i * scanLineSamples) / pixelBuffer.length + prevPulseIndex; + int intensity = (int) Math.round(255 * Math.sqrt(scanLineBuffer[position])); + int pixelColor = 0xff000000 | 0x00010101 * intensity; + pixelBuffer[i] = pixelColor; + } + return true; + } } diff --git a/app/src/main/java/xdsopl/robot36/Scottie.java b/app/src/main/java/xdsopl/robot36/Scottie.java index a48ec16..05b9730 100644 --- a/app/src/main/java/xdsopl/robot36/Scottie.java +++ b/app/src/main/java/xdsopl/robot36/Scottie.java @@ -27,4 +27,17 @@ public class Scottie implements Mode { public int getScanLineSamples() { return scanLineSamples; } + + @Override + public boolean decodeScanLine(int[] pixelBuffer, float[] scanLineBuffer, int prevPulseIndex, int scanLineSamples) { + if (prevPulseIndex < 0 || prevPulseIndex + scanLineSamples >= scanLineBuffer.length) + return false; + for (int i = 0; i < pixelBuffer.length; ++i) { + int position = (i * scanLineSamples) / pixelBuffer.length + prevPulseIndex; + int intensity = (int) Math.round(255 * Math.sqrt(scanLineBuffer[position])); + int pixelColor = 0xff000000 | 0x00010101 * intensity; + pixelBuffer[i] = pixelColor; + } + return true; + } } diff --git a/app/src/main/java/xdsopl/robot36/Wraase_SC2_180.java b/app/src/main/java/xdsopl/robot36/Wraase_SC2_180.java index 2985714..db77bf0 100644 --- a/app/src/main/java/xdsopl/robot36/Wraase_SC2_180.java +++ b/app/src/main/java/xdsopl/robot36/Wraase_SC2_180.java @@ -26,4 +26,17 @@ public class Wraase_SC2_180 implements Mode { public int getScanLineSamples() { return scanLineSamples; } + + @Override + public boolean decodeScanLine(int[] pixelBuffer, float[] scanLineBuffer, int prevPulseIndex, int scanLineSamples) { + if (prevPulseIndex < 0 || prevPulseIndex + scanLineSamples >= scanLineBuffer.length) + return false; + for (int i = 0; i < pixelBuffer.length; ++i) { + int position = (i * scanLineSamples) / pixelBuffer.length + prevPulseIndex; + int intensity = (int) Math.round(255 * Math.sqrt(scanLineBuffer[position])); + int pixelColor = 0xff000000 | 0x00010101 * intensity; + pixelBuffer[i] = pixelColor; + } + return true; + } }