diff --git a/.settings/org.eclipse.jdt.core.prefs b/.settings/org.eclipse.jdt.core.prefs
index 96cf561c..588e59de 100644
--- a/.settings/org.eclipse.jdt.core.prefs
+++ b/.settings/org.eclipse.jdt.core.prefs
@@ -1,6 +1,9 @@
eclipse.preferences.version=1
+org.eclipse.jdt.core.compiler.codegen.inlineJsrBytecode=enabled
org.eclipse.jdt.core.compiler.codegen.targetPlatform=1.8
org.eclipse.jdt.core.compiler.compliance=1.8
+org.eclipse.jdt.core.compiler.problem.assertIdentifier=error
+org.eclipse.jdt.core.compiler.problem.enumIdentifier=error
org.eclipse.jdt.core.compiler.problem.forbiddenReference=warning
org.eclipse.jdt.core.compiler.source=1.8
org.eclipse.jdt.core.javaFormatter=org.eclipse.jdt.core.defaultJavaFormatter
diff --git a/pom.xml b/pom.xml
index c73b8d98..6846218d 100755
--- a/pom.xml
+++ b/pom.xml
@@ -5,7 +5,7 @@
org.warp.picalculator
warppi-calculator
jar
- 0.7-SNAPSHOT
+ 0.8-SNAPSHOT
WarpPI Calculator
http://warp.ovh
@@ -40,14 +40,14 @@
-
- 1_teavm-dev
- https://dl.bintray.com/konsoletyper/teavm
-
- true
-
- default
-
+
+ 1_teavm-dev
+ https://dl.bintray.com/konsoletyper/teavm
+
+ true
+
+ default
+
@@ -100,6 +100,13 @@
ecj
4.6.1
+
@@ -109,8 +116,8 @@
maven-compiler-plugin
2.3.2
-
- 1.8
+
+ ${maven.compiler.target}
UTF-8
${buildprops.exclude1}
@@ -170,8 +177,8 @@
org/warp/picalculator/gui/graphicengine/headless8/*
org/warp/picalculator/gui/graphicengine/framebuffer/*
-
- 1.8
+
+ ${maven.compiler.target}
UTF-8
@@ -230,11 +237,6 @@
commons-lang3
3.8
-
- io.reactivex.rxjava2
- rxjava
- 2.2.1
-
diff --git a/src/js-specific/java/org/warp/picalculator/ConsoleUtils.java b/src/js-specific/java/org/warp/picalculator/ConsoleUtils.java
index 21c9999f..7b174970 100644
--- a/src/js-specific/java/org/warp/picalculator/ConsoleUtils.java
+++ b/src/js-specific/java/org/warp/picalculator/ConsoleUtils.java
@@ -43,7 +43,7 @@ public class ConsoleUtils {
}
}
- public void println(int level, String str) {
+ public void println(int level, Object str) {
if (StaticVars.outputLevel >= level) {
final String time = getTimeString();
if (StaticVars.outputLevel == 0) {
@@ -64,7 +64,7 @@ public class ConsoleUtils {
}
}
- public void println(int level, String prefix, String str) {
+ public void println(int level, Object prefix, Object str) {
if (StaticVars.outputLevel >= level) {
final String time = getTimeString();
if (StaticVars.outputLevel == 0) {
@@ -75,7 +75,7 @@ public class ConsoleUtils {
}
}
- public void println(int level, String... parts) {
+ public void println(int level, Object... parts) {
if (StaticVars.outputLevel >= level) {
final String time = getTimeString();
String output = "";
diff --git a/src/js-specific/java/org/warp/picalculator/deps/DAtomicInteger.java b/src/js-specific/java/org/warp/picalculator/deps/DAtomicInteger.java
index 3df2ceef..8177b840 100644
--- a/src/js-specific/java/org/warp/picalculator/deps/DAtomicInteger.java
+++ b/src/js-specific/java/org/warp/picalculator/deps/DAtomicInteger.java
@@ -36,7 +36,6 @@
package org.warp.picalculator.deps;
import java.util.function.IntUnaryOperator;
import java.util.function.IntBinaryOperator;
-import sun.misc.Unsafe;
/**
* An {@code int} value that may be updated atomically. See the
diff --git a/src/js-specific/java/org/warp/picalculator/gui/graphicengine/html/HtmlEngine.java b/src/js-specific/java/org/warp/picalculator/gui/graphicengine/html/HtmlEngine.java
index 60ecd2ad..cac24bd0 100644
--- a/src/js-specific/java/org/warp/picalculator/gui/graphicengine/html/HtmlEngine.java
+++ b/src/js-specific/java/org/warp/picalculator/gui/graphicengine/html/HtmlEngine.java
@@ -24,6 +24,8 @@ import org.warp.picalculator.Utils;
import org.warp.picalculator.deps.DSemaphore;
import org.warp.picalculator.deps.StorageUtils;
import org.warp.picalculator.device.Keyboard;
+import org.warp.picalculator.flow.BehaviorSubject;
+import org.warp.picalculator.flow.Observable;
import org.warp.picalculator.gui.graphicengine.BinaryFont;
import org.warp.picalculator.gui.graphicengine.GraphicEngine;
import org.warp.picalculator.gui.graphicengine.Renderer;
@@ -43,6 +45,7 @@ public class HtmlEngine implements GraphicEngine {
private HtmlRenderer renderer;
private int width = -1, height = -1;
private final int frameTime = (int) (1000d/10d);
+ private final BehaviorSubject onResize = BehaviorSubject.create();
@Override
public int[] getSize() {
@@ -194,11 +197,6 @@ public class HtmlEngine implements GraphicEngine {
}
}
- @Override
- public boolean wasResized() {
- return false;
- }
-
@Override
public int getWidth() {
if (width == -1) {
@@ -293,4 +291,9 @@ public class HtmlEngine implements GraphicEngine {
return true;
}
+ @Override
+ public Observable onResize() {
+ return onResize;
+ }
+
}
diff --git a/src/main/java/org/warp/picalculator/StaticVars.java b/src/main/java/org/warp/picalculator/StaticVars.java
index 2586eee0..94fb218c 100644
--- a/src/main/java/org/warp/picalculator/StaticVars.java
+++ b/src/main/java/org/warp/picalculator/StaticVars.java
@@ -1,13 +1,10 @@
package org.warp.picalculator;
-import java.util.Iterator;
-import java.util.concurrent.CompletableFuture;
+import java.util.function.Function;
import org.warp.picalculator.boot.StartupArguments;
-
-import io.reactivex.Maybe;
-import io.reactivex.Observable;
-import io.reactivex.subjects.BehaviorSubject;
+import org.warp.picalculator.flow.Observable;
+import org.warp.picalculator.flow.BehaviorSubject;
public class StaticVars {
public static final boolean enableVBO = true;
@@ -17,19 +14,19 @@ public class StaticVars {
public static boolean haxMode = true;
public static final boolean zoomed = true;
public static int[] screenPos = new int[] { 0, 0 };
- public static final int[] screenSize = new int[] { 480, 320 };
+ public static final int[] screenSize = new int[] {480, 320};
public static boolean debugOn;
public static int outputLevel = 0;
public static boolean debugWindow2x = false;
- public static BehaviorSubject windowZoom = BehaviorSubject.createDefault(2F);
- public static Observable windowZoom$ = windowZoom.map((val) -> {
+ public static BehaviorSubject windowZoom = BehaviorSubject.create(2F);
+ public static Function windowZoomFunction = (val) -> {
if (StaticVars.debugOn & StaticVars.debugWindow2x) {
return val + 1;
} else {
return val;
}
- });
- public static Iterator windowZoomValue = windowZoom$.blockingMostRecent(2F).iterator();
+ };
+ public static Observable windowZoom$ = windowZoom.map(windowZoomFunction);
public static StartupArguments startupArguments;
private StaticVars() {
diff --git a/src/main/java/org/warp/picalculator/boot/Main.java b/src/main/java/org/warp/picalculator/boot/Main.java
index 24790456..c6032bbe 100644
--- a/src/main/java/org/warp/picalculator/boot/Main.java
+++ b/src/main/java/org/warp/picalculator/boot/Main.java
@@ -1,15 +1,9 @@
package org.warp.picalculator.boot;
-import java.io.IOException;
import java.util.Arrays;
-import java.util.stream.Stream;
-
import org.warp.picalculator.ConsoleUtils;
import org.warp.picalculator.PICalculator;
-import org.warp.picalculator.Utils;
-import org.warp.picalculator.device.PIHardwareDisplay;
-import org.warp.picalculator.gui.CalculatorHUD;
-import org.warp.picalculator.gui.screens.LoadingScreen;
+import org.warp.picalculator.flow.TestFlow;
public class Main {
public static void main(String[] args) throws Exception {
diff --git a/src/main/java/org/warp/picalculator/device/Keyboard.java b/src/main/java/org/warp/picalculator/device/Keyboard.java
index b37a8451..8f6be7bd 100755
--- a/src/main/java/org/warp/picalculator/device/Keyboard.java
+++ b/src/main/java/org/warp/picalculator/device/Keyboard.java
@@ -813,7 +813,7 @@ public class Keyboard {
refresh = true;
break;
case ZOOM_MODE:
- float newZoom = (StaticVars.windowZoom.blockingLatest().iterator().next().floatValue() % 3) + 1;
+ float newZoom = (StaticVars.windowZoom.getLastValue() % 3) + 1;
StaticVars.windowZoom.onNext(newZoom);
ConsoleUtils.out.println(ConsoleUtils.OUTPUTLEVEL_DEBUG_MIN, "Keyboard", "Zoom: " + newZoom);
// StaticVars.windowZoom = ((StaticVars.windowZoom - 0.5f) % 2f) + 1f;
diff --git a/src/main/java/org/warp/picalculator/flow/Action0.java b/src/main/java/org/warp/picalculator/flow/Action0.java
new file mode 100644
index 00000000..ce01c6fa
--- /dev/null
+++ b/src/main/java/org/warp/picalculator/flow/Action0.java
@@ -0,0 +1,5 @@
+package org.warp.picalculator.flow;
+
+public interface Action0 {
+ void call();
+}
diff --git a/src/main/java/org/warp/picalculator/flow/Action1.java b/src/main/java/org/warp/picalculator/flow/Action1.java
new file mode 100644
index 00000000..947f046c
--- /dev/null
+++ b/src/main/java/org/warp/picalculator/flow/Action1.java
@@ -0,0 +1,5 @@
+package org.warp.picalculator.flow;
+
+public interface Action1 {
+ void call(T t);
+}
diff --git a/src/main/java/org/warp/picalculator/flow/Action2.java b/src/main/java/org/warp/picalculator/flow/Action2.java
new file mode 100644
index 00000000..446e103a
--- /dev/null
+++ b/src/main/java/org/warp/picalculator/flow/Action2.java
@@ -0,0 +1,5 @@
+package org.warp.picalculator.flow;
+
+public interface Action2 {
+ void call(T t, U u);
+}
diff --git a/src/main/java/org/warp/picalculator/flow/BehaviorSubject.java b/src/main/java/org/warp/picalculator/flow/BehaviorSubject.java
new file mode 100644
index 00000000..36e9dbda
--- /dev/null
+++ b/src/main/java/org/warp/picalculator/flow/BehaviorSubject.java
@@ -0,0 +1,98 @@
+package org.warp.picalculator.flow;
+
+import java.util.LinkedList;
+import java.util.List;
+
+public class BehaviorSubject extends Subject {
+
+ private T lastValue;
+ private boolean lastValueSet;
+
+ protected BehaviorSubject() {
+ super();
+ lastValue = null;
+ lastValueSet = false;
+ }
+
+ protected BehaviorSubject(T initialValue) {
+ super();
+ lastValue = initialValue;
+ lastValueSet = true;
+ }
+
+ public final static BehaviorSubject create() {
+ return new BehaviorSubject<>();
+ }
+
+ public final static BehaviorSubject create(T initialValue) {
+ return new BehaviorSubject(initialValue);
+ }
+
+ @Override
+ public void onComplete() {
+ for (Subscriber super T> sub : this.subscribers) {
+ sub.onComplete();
+ }
+ }
+
+ @Override
+ public void onError(Throwable e) {
+ for (Subscriber super T> sub : this.subscribers) {
+ sub.onError(e);
+ };
+ }
+
+ @Override
+ public void onNext(T t) {
+ lastValue = t;
+ lastValueSet = true;
+ for (Subscriber super T> sub : this.subscribers) {
+ sub.onNext(t);
+ }
+ }
+
+ @Override
+ Throwable getThrowable() {
+ // TODO Auto-generated method stub
+ return null;
+ }
+
+ @Override
+ boolean hasComplete() {
+ // TODO Auto-generated method stub
+ return false;
+ }
+
+ @Override
+ boolean hasObservers() {
+ // TODO Auto-generated method stub
+ return false;
+ }
+
+ @Override
+ boolean hasThrowable() {
+ // TODO Auto-generated method stub
+ return false;
+ }
+
+ @Override
+ Subject toSerialized() {
+ // TODO Auto-generated method stub
+ return null;
+ }
+
+ @Override
+ public void onSubscribe(Disposable d) {
+ @SuppressWarnings("unchecked")
+ DisposableOfSubscriber ds = (DisposableOfSubscriber) d;
+ Subscriber super T> s = ds.getSubscriber();
+ if (lastValueSet) {
+ s.onNext(lastValue);
+ }
+ }
+
+ public T getLastValue() {
+ return lastValue;
+ }
+
+}
diff --git a/src/main/java/org/warp/picalculator/flow/Consumer.java b/src/main/java/org/warp/picalculator/flow/Consumer.java
new file mode 100644
index 00000000..4911a9a4
--- /dev/null
+++ b/src/main/java/org/warp/picalculator/flow/Consumer.java
@@ -0,0 +1,30 @@
+package org.warp.picalculator.flow;
+
+import java.util.Objects;
+
+public interface Consumer {
+
+ /**
+ * Performs this operation on the given argument.
+ *
+ * @param t the input argument
+ */
+ void accept(T t);
+
+ /**
+ * Returns a composed {@code Consumer} that performs, in sequence, this
+ * operation followed by the {@code after} operation. If performing either
+ * operation throws an exception, it is relayed to the caller of the
+ * composed operation. If performing this operation throws an exception,
+ * the {@code after} operation will not be performed.
+ *
+ * @param after the operation to perform after this operation
+ * @return a composed {@code Consumer} that performs in sequence this
+ * operation followed by the {@code after} operation
+ * @throws NullPointerException if {@code after} is null
+ */
+ default Consumer andThen(Consumer super T> after) {
+ Objects.requireNonNull(after);
+ return (T t) -> { accept(t); after.accept(t); };
+ }
+}
\ No newline at end of file
diff --git a/src/main/java/org/warp/picalculator/flow/Disposable.java b/src/main/java/org/warp/picalculator/flow/Disposable.java
new file mode 100644
index 00000000..39aac5e5
--- /dev/null
+++ b/src/main/java/org/warp/picalculator/flow/Disposable.java
@@ -0,0 +1,7 @@
+package org.warp.picalculator.flow;
+
+public interface Disposable {
+ public void dispose();
+
+ public boolean isDisposed();
+}
diff --git a/src/main/java/org/warp/picalculator/flow/IntervalsManager.java b/src/main/java/org/warp/picalculator/flow/IntervalsManager.java
new file mode 100644
index 00000000..78794922
--- /dev/null
+++ b/src/main/java/org/warp/picalculator/flow/IntervalsManager.java
@@ -0,0 +1,48 @@
+package org.warp.picalculator.flow;
+
+import java.util.LinkedList;
+import java.util.List;
+
+import org.warp.picalculator.PlatformUtils;
+
+public class IntervalsManager {
+ private static List intervals = new LinkedList<>();
+
+ static {
+ startChecker();
+ }
+
+ private IntervalsManager() {
+
+ }
+
+ public static void register(ObservableInterval t) {
+ synchronized (intervals) {
+ if (!intervals.contains(t)) {
+ intervals.add(t);
+ }
+ }
+ }
+
+ private static void startChecker() {
+ Thread t = new Thread(() -> {
+ try {
+ while (true) {
+ Thread.sleep(1000);
+ for (ObservableInterval interval : intervals) {
+ if (interval.running) {
+ if (interval.subscribers.size() <= 0) {
+ interval.stopInterval();
+ }
+ }
+ }
+ }
+ } catch (InterruptedException e) {
+ e.printStackTrace();
+ }
+ });
+ PlatformUtils.setDaemon(t);
+ PlatformUtils.setThreadName(t, "Intervals Manager");
+ t.start();
+ }
+}
diff --git a/src/main/java/org/warp/picalculator/flow/Observable.java b/src/main/java/org/warp/picalculator/flow/Observable.java
new file mode 100644
index 00000000..8cab3803
--- /dev/null
+++ b/src/main/java/org/warp/picalculator/flow/Observable.java
@@ -0,0 +1,166 @@
+package org.warp.picalculator.flow;
+
+import java.util.LinkedList;
+import java.util.List;
+import java.util.concurrent.TimeUnit;
+import java.util.function.Function;
+
+import org.apache.commons.lang3.tuple.Pair;
+
+public abstract class Observable implements ObservableSource {
+
+ protected List> subscribers = new LinkedList<>();
+
+ public Disposable subscribe() {
+ return null;
+ }
+ public Disposable subscribe(Action1 super T> onNext) {
+ return subscribe(createSubscriber(onNext));
+ }
+ protected Observable.DisposableOfSubscriber createDisposable(Subscriber super T> sub) {
+ return new DisposableOfSubscriber(sub);
+ }
+ public Disposable subscribe(Action1 super T> onNext, Action1 onError) {
+ return subscribe(createSubscriber(onNext, onError));
+ }
+ public Disposable subscribe(Action1 super T> onNext, Action1 onError, Action0 onCompleted) {
+ return subscribe(createSubscriber(onNext, onError, onCompleted));
+ }
+ public void subscribe(Observer super T> obs) {
+ subscribe(createSubscriber(obs));
+ }
+ public Disposable subscribe(Subscriber super T> sub) {
+ subscribers.add(sub);
+ return createDisposable(sub);
+ }
+
+ protected Subscriber createSubscriber(Action1 super T> onNext) {
+ return new Subscriber() {
+ @Override public void onSubscribe(Subscription s) {}
+ public void onNext(T t) {
+ onNext.call(t);
+ }
+ };
+ }
+
+ protected Subscriber createSubscriber(Action1 super T> onNext, Action1 onError) {
+ return new Subscriber() {
+ @Override public void onSubscribe(Subscription s) {}
+ public void onNext(T t) {
+ onNext.call(t);
+ }
+ @Override
+ public void onError(Throwable t) {
+ onError.call(t);
+ }
+ };
+ }
+
+ protected Subscriber createSubscriber(Action1 super T> onNext, Action1 onError, Action0 onCompl) {
+ return new Subscriber() {
+ @Override public void onSubscribe(Subscription s) {}
+ public void onNext(T t) {
+ onNext.call(t);
+ }
+ @Override
+ public void onError(Throwable t) {
+ onError.call(t);
+ }
+ @Override
+ public void onComplete() {
+ onCompl.call();
+ }
+ };
+ }
+
+ protected Subscriber createSubscriber(Observer super T> obs) {
+ return new Subscriber() {
+ @Override public void onSubscribe(Subscription s) {}
+ public void onNext(T t) {
+ obs.onNext(t);
+ }
+ @Override
+ public void onError(Throwable t) {
+ obs.onError(t);
+ }
+ @Override
+ public void onComplete() {
+ obs.onComplete();
+ }
+ };
+ }
+
+ public static final Observable merge(Observable a, Observable b) {
+ return new ObservableMerged<>(a, b);
+ }
+
+ @Deprecated
+ public static final Observable of(Observable a) {
+ return null;
+ }
+
+ public final Observable map(Function f) {
+ return new ObservableMap(this, f);
+ }
+
+ public static final Observable> combineLatest(Observable a, Observable b) {
+ return new ObservableCombinedLatest<>(a, b);
+ }
+
+ public static final Observable> combineChanged(Observable a, Observable b) {
+ return new ObservableCombinedChanged<>(a, b);
+ }
+
+ public static final Observable> zip(Observable a, Observable b) {
+ return new ObservableZipped<>(a, b);
+ }
+
+ public static final Observable interval(long interval) {
+ return new ObservableInterval(interval);
+ }
+
+ protected class DisposableOfSubscriber implements Disposable {
+
+ private final Subscriber super T> sub;
+
+ public DisposableOfSubscriber(Subscriber super T> sub) {
+ this.sub = sub;
+ }
+
+ protected Subscriber super T> getSubscriber() {
+ return sub;
+ }
+
+ protected Observable getObservable() {
+ return Observable.this;
+ }
+
+ @Override
+ public void dispose() {
+ if (isDisposed()) {
+ throw new RuntimeException("Already disposed!");
+ }
+ subscribers.remove(sub);
+ Observable.this.onDisposed(sub);
+ }
+
+ @Override
+ public boolean isDisposed() {
+ return !subscribers.contains(sub);
+ }
+
+ }
+
+ public Observable doOnNext(Action1 onNext) {
+ Subject onNextSubject = BehaviorSubject.create();
+ this.subscribe((val) -> {
+ onNext.call(val);
+ onNextSubject.onNext(val);
+ });
+ return onNextSubject;
+ }
+
+ public void onDisposed(Subscriber super T> sub) {
+
+ }
+}
diff --git a/src/main/java/org/warp/picalculator/flow/ObservableCombinedChanged.java b/src/main/java/org/warp/picalculator/flow/ObservableCombinedChanged.java
new file mode 100644
index 00000000..17a0d50c
--- /dev/null
+++ b/src/main/java/org/warp/picalculator/flow/ObservableCombinedChanged.java
@@ -0,0 +1,72 @@
+package org.warp.picalculator.flow;
+
+import java.util.function.Function;
+
+import org.apache.commons.lang3.tuple.Pair;
+
+public class ObservableCombinedChanged extends Observable> {
+ private volatile boolean initialized = false;
+ private Observable a;
+ private Observable b;
+ private Disposable disposableA;
+ private Disposable disposableB;
+ private Subject> pairSubject;
+ private Subject mapSubject;
+
+ public ObservableCombinedChanged(Observable a, Observable b) {
+ super();
+ this.a = a;
+ this.b = b;
+ this.pairSubject = SimpleSubject.create();
+ }
+
+ private void initialize() {
+ this.disposableA = a.subscribe((t) -> {
+ for (Subscriber super Pair> sub : this.subscribers) {
+ sub.onNext(Pair.of(t, null));
+ }
+ }, (e) -> {
+ for (Subscriber super Pair> sub : this.subscribers) {
+ sub.onError(e);
+ };
+ }, () -> {
+ for (Subscriber super Pair> sub : this.subscribers) {
+ sub.onComplete();
+ };
+ });
+ this.disposableB = b.subscribe((t) -> {
+ for (Subscriber super Pair> sub : this.subscribers) {
+ sub.onNext(Pair.of(null, t));
+ };
+ }, (e) -> {
+ for (Subscriber super Pair> sub : this.subscribers) {
+ sub.onError(e);
+ };
+ }, () -> {
+ for (Subscriber super Pair> sub : this.subscribers) {
+ sub.onComplete();
+ };
+ });
+ }
+
+ private void chechInitialized() {
+ if (!initialized) {
+ initialized = true;
+ initialize();
+ }
+ }
+
+ @Override
+ public Disposable subscribe(Subscriber super Pair> sub) {
+ Disposable disp = super.subscribe(sub);
+ chechInitialized();
+ return disp;
+ }
+
+ @Override
+ public void onDisposed(Subscriber super Pair> sub) {
+ super.onDisposed(sub);
+ this.disposableA.dispose();
+ this.disposableB.dispose();
+ }
+}
diff --git a/src/main/java/org/warp/picalculator/flow/ObservableCombinedLatest.java b/src/main/java/org/warp/picalculator/flow/ObservableCombinedLatest.java
new file mode 100644
index 00000000..63095a6f
--- /dev/null
+++ b/src/main/java/org/warp/picalculator/flow/ObservableCombinedLatest.java
@@ -0,0 +1,84 @@
+package org.warp.picalculator.flow;
+
+import java.util.function.Function;
+
+import org.apache.commons.lang3.tuple.Pair;
+
+public class ObservableCombinedLatest extends Observable> {
+ private volatile boolean initialized = false;
+ private Observable a;
+ private Observable b;
+ private Disposable disposableA;
+ private Disposable disposableB;
+ private volatile T lastA;
+ private volatile U lastB;
+ private volatile boolean didAOneTime;
+ private volatile boolean didBOneTime;
+ private Subject> pairSubject;
+ private Subject mapSubject;
+
+ public ObservableCombinedLatest(Observable a, Observable b) {
+ super();
+ this.a = a;
+ this.b = b;
+ this.pairSubject = SimpleSubject.create();
+ }
+
+ private void initialize() {
+ this.disposableA = a.subscribe((t) -> {
+ lastA = t;
+ didAOneTime = true;
+ receivedNext();
+ }, (e) -> {
+ for (Subscriber super Pair> sub : this.subscribers) {
+ sub.onError(e);
+ };
+ }, () -> {
+ for (Subscriber super Pair> sub : this.subscribers) {
+ sub.onComplete();
+ };
+ });
+ this.disposableB = b.subscribe((t) -> {
+ lastB = t;
+ didBOneTime = true;
+ receivedNext();
+ }, (e) -> {
+ for (Subscriber super Pair> sub : this.subscribers) {
+ sub.onError(e);
+ };
+ }, () -> {
+ for (Subscriber super Pair> sub : this.subscribers) {
+ sub.onComplete();
+ };
+ });
+ }
+
+ private void receivedNext() {
+ if (didAOneTime && didBOneTime) {
+ this.subscribers.forEach(sub -> {
+ sub.onNext(Pair.of(lastA, lastB));
+ });
+ }
+ }
+
+ private void chechInitialized() {
+ if (!initialized) {
+ initialized = true;
+ initialize();
+ }
+ }
+
+ @Override
+ public Disposable subscribe(Subscriber super Pair> sub) {
+ Disposable disp = super.subscribe(sub);
+ chechInitialized();
+ return disp;
+ }
+
+ @Override
+ public void onDisposed(Subscriber super Pair> sub) {
+ super.onDisposed(sub);
+ this.disposableA.dispose();
+ this.disposableB.dispose();
+ }
+}
diff --git a/src/main/java/org/warp/picalculator/flow/ObservableInterval.java b/src/main/java/org/warp/picalculator/flow/ObservableInterval.java
new file mode 100644
index 00000000..8279ae8e
--- /dev/null
+++ b/src/main/java/org/warp/picalculator/flow/ObservableInterval.java
@@ -0,0 +1,71 @@
+package org.warp.picalculator.flow;
+
+import java.util.function.Function;
+
+import org.apache.commons.lang3.tuple.Pair;
+import org.warp.picalculator.PlatformUtils;
+
+public class ObservableInterval extends Observable {
+ private final long interval;
+ volatile boolean running;
+ volatile Thread timeThread;
+
+ protected ObservableInterval(long interval) {
+ super();
+ this.interval = interval;
+ try {
+ startInterval();
+ } catch (InterruptedException e) {
+ e.printStackTrace();
+ }
+ }
+
+ void stopInterval() {
+ if (running) {
+ running = false;
+ this.timeThread.interrupt();
+ }
+ }
+
+ @Override
+ public Disposable subscribe(Subscriber super Long> sub) {
+ try {
+ startInterval();
+ } catch (InterruptedException e) {
+ e.printStackTrace();
+ }
+ return super.subscribe(sub);
+ }
+
+ void startInterval() throws InterruptedException {
+ if (running == false) {
+ while (timeThread != null) {
+ Thread.sleep(100);
+ }
+ timeThread = new Thread(() -> {
+ try {
+ while(!Thread.interrupted()) {
+ for (Subscriber super Long> sub : this.subscribers) {
+ sub.onNext(System.currentTimeMillis());
+ }
+ Thread.sleep(interval);
+ }
+ } catch (InterruptedException e) {}
+ timeThread = null;
+ });
+ PlatformUtils.setThreadName(timeThread, "ObservableTimer");
+ timeThread.start();
+ running = true;
+ }
+ }
+
+ public static ObservableInterval create(long l) {
+ return new ObservableInterval(l);
+ }
+
+ @Override
+ public void onDisposed(Subscriber super Long> sub) {
+ super.onDisposed(sub);
+ stopInterval();
+ }
+}
diff --git a/src/main/java/org/warp/picalculator/flow/ObservableMap.java b/src/main/java/org/warp/picalculator/flow/ObservableMap.java
new file mode 100644
index 00000000..1e9258d0
--- /dev/null
+++ b/src/main/java/org/warp/picalculator/flow/ObservableMap.java
@@ -0,0 +1,55 @@
+package org.warp.picalculator.flow;
+
+import java.util.function.Function;
+
+import org.apache.commons.lang3.tuple.Pair;
+
+public class ObservableMap extends Observable {
+ private Observable originalObservable;
+ private Function mapAction;
+ private volatile boolean initialized = false;
+ private Disposable mapDisposable;
+ private Subject mapSubject;
+
+ public ObservableMap(Observable originalObservable, Function mapAction) {
+ super();
+ this.originalObservable = originalObservable;
+ this.mapAction = mapAction;
+ this.mapSubject = SimpleSubject.create();
+ }
+
+ private void initialize() {
+ this.mapDisposable = originalObservable.subscribe((t) -> {
+ for (Subscriber super U> sub : this.subscribers) {
+ sub.onNext(mapAction.apply(t));
+ };
+ }, (e) -> {
+ for (Subscriber super U> sub : this.subscribers) {
+ sub.onError(e);
+ };
+ }, () -> {
+ for (Subscriber super U> sub : this.subscribers) {
+ sub.onComplete();
+ };
+ });
+ }
+
+ private void chechInitialized() {
+ if (!initialized) {
+ initialized = true;
+ initialize();
+ }
+ }
+
+ @Override
+ public Disposable subscribe(Subscriber super U> sub) {
+ Disposable disp = super.subscribe(sub);
+ chechInitialized();
+ return disp;
+ }
+ @Override
+ public void onDisposed(Subscriber super U> sub) {
+ super.onDisposed(sub);
+ mapDisposable.dispose();
+ }
+}
diff --git a/src/main/java/org/warp/picalculator/flow/ObservableMerged.java b/src/main/java/org/warp/picalculator/flow/ObservableMerged.java
new file mode 100644
index 00000000..a7aa41bb
--- /dev/null
+++ b/src/main/java/org/warp/picalculator/flow/ObservableMerged.java
@@ -0,0 +1,71 @@
+package org.warp.picalculator.flow;
+
+import java.util.function.Function;
+
+import org.apache.commons.lang3.tuple.Pair;
+
+public class ObservableMerged extends Observable {
+ private Observable originalObservableA;
+ private Observable originalObservableB;
+ private volatile boolean initialized = false;
+ private Disposable mapDisposableA;
+ private Disposable mapDisposableB;
+ private Subject mapSubject;
+
+ public ObservableMerged(Observable originalObservableA, Observable originalObservableB) {
+ super();
+ this.originalObservableA = originalObservableA;
+ this.originalObservableB = originalObservableB;
+ this.mapSubject = SimpleSubject.create();
+ }
+
+ private void initialize() {
+ this.mapDisposableA = originalObservableA.subscribe((t) -> {
+ for (Subscriber super T> sub : this.subscribers) {
+ sub.onNext(t);
+ };
+ }, (e) -> {
+ for (Subscriber super T> sub : this.subscribers) {
+ sub.onError(e);
+ };
+ }, () -> {
+ for (Subscriber super T> sub : this.subscribers) {
+ sub.onComplete();
+ };
+ });
+ this.mapDisposableB = originalObservableB.subscribe((t) -> {
+ for (Subscriber super T> sub : this.subscribers) {
+ sub.onNext(t);
+ };
+ }, (e) -> {
+ for (Subscriber super T> sub : this.subscribers) {
+ sub.onError(e);
+ };
+ }, () -> {
+ for (Subscriber super T> sub : this.subscribers) {
+ sub.onComplete();
+ };
+ });
+ }
+
+ private void chechInitialized() {
+ if (!initialized) {
+ initialized = true;
+ initialize();
+ }
+ }
+
+ @Override
+ public Disposable subscribe(Subscriber super T> sub) {
+ Disposable disp = super.subscribe(sub);
+ chechInitialized();
+ return disp;
+ }
+
+ @Override
+ public void onDisposed(Subscriber super T> sub) {
+ super.onDisposed(sub);
+ this.mapDisposableA.dispose();
+ this.mapDisposableB.dispose();
+ }
+}
diff --git a/src/main/java/org/warp/picalculator/flow/ObservableSource.java b/src/main/java/org/warp/picalculator/flow/ObservableSource.java
new file mode 100644
index 00000000..48ad441a
--- /dev/null
+++ b/src/main/java/org/warp/picalculator/flow/ObservableSource.java
@@ -0,0 +1,5 @@
+package org.warp.picalculator.flow;
+
+public interface ObservableSource {
+ public void subscribe(Observer super T> observer);
+}
diff --git a/src/main/java/org/warp/picalculator/flow/ObservableZipped.java b/src/main/java/org/warp/picalculator/flow/ObservableZipped.java
new file mode 100644
index 00000000..526f9772
--- /dev/null
+++ b/src/main/java/org/warp/picalculator/flow/ObservableZipped.java
@@ -0,0 +1,86 @@
+package org.warp.picalculator.flow;
+
+import java.util.function.Function;
+
+import org.apache.commons.lang3.tuple.Pair;
+
+public class ObservableZipped extends Observable> {
+ private volatile boolean initialized = false;
+ private Observable a;
+ private Observable b;
+ private Disposable disposableA;
+ private Disposable disposableB;
+ private volatile T lastA;
+ private volatile U lastB;
+ private volatile boolean didA;
+ private volatile boolean didB;
+ private Subject> pairSubject;
+ private Subject mapSubject;
+
+ public ObservableZipped(Observable a, Observable b) {
+ super();
+ this.a = a;
+ this.b = b;
+ this.pairSubject = SimpleSubject.create();
+ }
+
+ private void initialize() {
+ this.disposableA = a.subscribe((t) -> {
+ lastA = t;
+ didA = true;
+ receivedNext();
+ }, (e) -> {
+ for (Subscriber super Pair> sub : this.subscribers) {
+ sub.onError(e);
+ };
+ }, () -> {
+ for (Subscriber super Pair> sub : this.subscribers) {
+ sub.onComplete();
+ };
+ });
+ this.disposableB = b.subscribe((t) -> {
+ lastB = t;
+ didB = true;
+ receivedNext();
+ }, (e) -> {
+ for (Subscriber super Pair> sub : this.subscribers) {
+ sub.onError(e);
+ };
+ }, () -> {
+ for (Subscriber super Pair> sub : this.subscribers) {
+ sub.onComplete();
+ };
+ });
+ }
+
+ private void receivedNext() {
+ if (didA && didB) {
+ didA = false;
+ didB = false;
+ for (Subscriber super Pair> sub : this.subscribers) {
+ sub.onNext(Pair.of(lastA, lastB));
+ };
+ }
+ }
+
+ private void chechInitialized() {
+ if (!initialized) {
+ initialized = true;
+ initialize();
+ }
+ }
+
+ @Override
+ public Disposable subscribe(Subscriber super Pair> sub) {
+ Disposable disp = super.subscribe(sub);
+ chechInitialized();
+ return disp;
+ }
+
+ @Override
+ public void onDisposed(Subscriber super Pair> sub) {
+ super.onDisposed(sub);
+ this.disposableA.dispose();
+ this.disposableB.dispose();
+ }
+}
diff --git a/src/main/java/org/warp/picalculator/flow/Observer.java b/src/main/java/org/warp/picalculator/flow/Observer.java
new file mode 100644
index 00000000..4dd096bd
--- /dev/null
+++ b/src/main/java/org/warp/picalculator/flow/Observer.java
@@ -0,0 +1,8 @@
+package org.warp.picalculator.flow;
+
+public interface Observer {
+ public void onComplete();
+ public void onError(Throwable e);
+ public void onNext(T t);
+ public void onSubscribe(Disposable d);
+}
diff --git a/src/main/java/org/warp/picalculator/flow/SimpleSubject.java b/src/main/java/org/warp/picalculator/flow/SimpleSubject.java
new file mode 100644
index 00000000..f67f621d
--- /dev/null
+++ b/src/main/java/org/warp/picalculator/flow/SimpleSubject.java
@@ -0,0 +1,72 @@
+package org.warp.picalculator.flow;
+
+import java.util.LinkedList;
+import java.util.List;
+
+import org.apache.commons.lang3.tuple.Pair;
+
+public class SimpleSubject extends Subject {
+
+ protected SimpleSubject() {
+ }
+
+ public final static SimpleSubject create() {
+ return new SimpleSubject<>();
+ }
+
+ @Override
+ public void onComplete() {
+ for (Subscriber super T> sub : this.subscribers) {
+ sub.onComplete();
+ };
+ }
+
+ @Override
+ public void onError(Throwable e) {
+ for (Subscriber super T> sub : this.subscribers) {
+ sub.onError(e);
+ };
+ }
+
+ @Override
+ public void onNext(T t) {
+ for (Subscriber super T> sub : this.subscribers) {
+ sub.onNext(t);
+ };
+ }
+
+ @Override
+ Throwable getThrowable() {
+ // TODO Auto-generated method stub
+ return null;
+ }
+
+ @Override
+ boolean hasComplete() {
+ // TODO Auto-generated method stub
+ return false;
+ }
+
+ @Override
+ boolean hasObservers() {
+ // TODO Auto-generated method stub
+ return false;
+ }
+
+ @Override
+ boolean hasThrowable() {
+ // TODO Auto-generated method stub
+ return false;
+ }
+
+ @Override
+ Subject toSerialized() {
+ // TODO Auto-generated method stub
+ return null;
+ }
+
+ @Override
+ public void onSubscribe(Disposable d) {
+ }
+
+}
diff --git a/src/main/java/org/warp/picalculator/flow/Subject.java b/src/main/java/org/warp/picalculator/flow/Subject.java
new file mode 100644
index 00000000..29bfd868
--- /dev/null
+++ b/src/main/java/org/warp/picalculator/flow/Subject.java
@@ -0,0 +1,36 @@
+package org.warp.picalculator.flow;
+
+public abstract class Subject extends Observable implements Observer {
+ abstract Throwable getThrowable();
+ abstract boolean hasComplete();
+ abstract boolean hasObservers();
+ abstract boolean hasThrowable();
+ abstract Subject toSerialized();
+
+ @Override
+ public Disposable subscribe(Action1 super T> onNext) {
+ return subscribe(createSubscriber(onNext));
+ }
+
+ @Override
+ public Disposable subscribe(Action1 super T> onNext, Action1 onError) {
+ return subscribe(createSubscriber(onNext, onError));
+ }
+
+ @Override
+ public Disposable subscribe(Action1 super T> onNext, Action1 onError, Action0 onCompl) {
+ return subscribe(createSubscriber(onNext, onError, onCompl));
+ }
+
+ @Override
+ public void subscribe(Observer super T> obs) {
+ subscribe(createSubscriber(obs));
+ }
+
+ @Override
+ public Disposable subscribe(Subscriber super T> sub) {
+ Disposable disp = super.subscribe(sub);
+ this.onSubscribe(disp);
+ return disp;
+ }
+}
diff --git a/src/main/java/org/warp/picalculator/flow/Subscriber.java b/src/main/java/org/warp/picalculator/flow/Subscriber.java
new file mode 100644
index 00000000..2da92954
--- /dev/null
+++ b/src/main/java/org/warp/picalculator/flow/Subscriber.java
@@ -0,0 +1,8 @@
+package org.warp.picalculator.flow;
+
+public interface Subscriber {
+ default void onComplete() {}
+ default void onError(Throwable t) {}
+ void onNext(T t);
+ void onSubscribe(Subscription s);
+}
diff --git a/src/main/java/org/warp/picalculator/flow/Subscription.java b/src/main/java/org/warp/picalculator/flow/Subscription.java
new file mode 100644
index 00000000..b5ad231b
--- /dev/null
+++ b/src/main/java/org/warp/picalculator/flow/Subscription.java
@@ -0,0 +1,6 @@
+package org.warp.picalculator.flow;
+
+public interface Subscription {
+ void cancel();
+ void request(long n);
+}
diff --git a/src/main/java/org/warp/picalculator/flow/TestFlow.java b/src/main/java/org/warp/picalculator/flow/TestFlow.java
new file mode 100644
index 00000000..5c378629
--- /dev/null
+++ b/src/main/java/org/warp/picalculator/flow/TestFlow.java
@@ -0,0 +1,138 @@
+package org.warp.picalculator.flow;
+
+import org.apache.commons.lang3.tuple.Pair;
+
+public class TestFlow {
+ public static void main(String[] args) {
+ try {
+
+ BehaviorSubject subject0 = BehaviorSubject.create(0f);
+
+ Disposable s00 = subject0.subscribe((val) -> {
+ System.out.println(val);
+ });
+ Thread.sleep(100);
+ subject0.onNext(1f);
+ subject0.onNext(2f);
+ subject0.onNext(3f);
+ subject0.onNext(4f);
+ subject0.onNext(5f);
+ subject0.onNext(60f);
+ s00.dispose();
+ subject0.onNext(60f);
+ subject0.onNext(7f);
+
+
+ subject0.onComplete();
+ System.out.println("items sent.");
+
+ Subject subject1 = BehaviorSubject.create(0f);
+
+ Disposable s01 = subject1.map((val) -> val + 1).subscribe((val) -> {
+ System.out.println(val);
+ });
+ Thread.sleep(100);
+ subject1.onNext(1f);
+ subject1.onNext(2f);
+ subject1.onNext(3f);
+ subject1.onNext(4f);
+ subject1.onNext(5f);
+ subject1.onNext(60f);
+ s01.dispose();
+ subject1.onNext(60f);
+ subject1.onNext(7f);
+
+ subject1.onComplete();
+ System.out.println("items sent.");
+
+ BehaviorSubject subjectA = BehaviorSubject.create();
+ BehaviorSubject subjectB = BehaviorSubject.create();
+ Observable observable = Observable.merge(subjectA, subjectB);
+
+ Disposable s1 = observable.subscribe((val) -> {
+ System.out.println(val);
+ });
+ Thread.sleep(100);
+ subjectA.onNext(1f);
+ subjectA.onNext(2f);
+ subjectA.onNext(3f);
+ subjectA.onNext(4f);
+ subjectA.onNext(5f);
+ subjectB.onNext(60f);
+ s1.dispose();
+ subjectB.onNext(60f);
+ subjectA.onNext(7f);
+
+ subjectB.onComplete();
+ subjectA.onComplete();
+ Thread.sleep(100);
+ System.out.println("no more news subscribers left, closing publisher..");
+
+ BehaviorSubject subjectC = BehaviorSubject.create();
+ BehaviorSubject subjectD = BehaviorSubject.create();
+ Observable> observableCombined = Observable.combineLatest(subjectC, subjectD);
+ System.out.println("Combined observable: " + observableCombined.toString());
+ Disposable s2 = observableCombined.subscribe((val) -> {
+ System.out.println(val);
+ });
+ Thread.sleep(100);
+ subjectC.onNext(1f);
+ subjectC.onNext(2f);
+ subjectC.onNext(3f);
+ subjectC.onNext(4f);
+ subjectC.onNext(5f);
+ subjectD.onNext(60f);
+ subjectD.onNext(60f);
+ subjectC.onNext(7f);
+ s2.dispose();
+
+ subjectD.onComplete();
+ subjectC.onComplete();
+ System.out.println("items sent.");
+
+ ObservableInterval timA = ObservableInterval.create(100L);
+ Disposable d = timA.subscribe((t) -> {
+ System.out.println(t);
+ });
+
+ Thread.sleep(500);
+ d.dispose();
+ System.out.println("items sent.");
+
+ ObservableInterval subjectE = ObservableInterval.create(100L);
+ BehaviorSubject subjectF = BehaviorSubject.create();
+ Observable> observableZipped = Observable.zip(subjectE, subjectF);
+ System.out.println("Zipped observable: " + observableZipped.toString());
+ Disposable s3 = observableZipped.subscribe((val) -> {
+ System.out.println(val);
+ });
+ Thread.sleep(100);
+ subjectF.onNext(1f);
+ Thread.sleep(100);
+ subjectF.onNext(2f);
+ Thread.sleep(100);
+ subjectF.onNext(3f);
+ Thread.sleep(100);
+ subjectF.onNext(4f);
+ Thread.sleep(100);
+ subjectF.onNext(5f);
+ Thread.sleep(100);
+ subjectF.onNext(60f);
+ Thread.sleep(100);
+ subjectF.onNext(60f);
+ Thread.sleep(100);
+ subjectF.onNext(7f);
+ Thread.sleep(500);
+ s3.dispose();
+
+ subjectF.onComplete();
+ System.out.println("items sent.");
+
+
+
+ } catch (Exception ex) {
+ ex.printStackTrace();
+ }
+ }
+
+}
diff --git a/src/main/java/org/warp/picalculator/gui/DisplayManager.java b/src/main/java/org/warp/picalculator/gui/DisplayManager.java
index 725f1c18..67d3353f 100755
--- a/src/main/java/org/warp/picalculator/gui/DisplayManager.java
+++ b/src/main/java/org/warp/picalculator/gui/DisplayManager.java
@@ -22,6 +22,7 @@ import org.warp.picalculator.event.TouchEvent;
import org.warp.picalculator.event.TouchEventListener;
import org.warp.picalculator.event.TouchMoveEvent;
import org.warp.picalculator.event.TouchStartEvent;
+import org.warp.picalculator.flow.Observable;
import org.warp.picalculator.gui.graphicengine.BinaryFont;
import org.warp.picalculator.gui.graphicengine.GraphicEngine;
import org.warp.picalculator.gui.graphicengine.Renderer;
@@ -30,8 +31,6 @@ import org.warp.picalculator.gui.graphicengine.Skin;
import org.warp.picalculator.gui.graphicengine.nogui.NoGuiEngine;
import org.warp.picalculator.gui.screens.Screen;
-import io.reactivex.Observable;
-import io.reactivex.Scheduler;
import it.unimi.dsi.fastutil.longs.Long2ObjectMap.Entry;
import it.unimi.dsi.fastutil.objects.ObjectArrayList;
@@ -401,9 +400,9 @@ public final class DisplayManager implements RenderingLoop {
DSystem.exit(0);
}
- Observable workTimer = Observable.interval(tickDuration, TimeUnit.MILLISECONDS);
+ Observable workTimer = Observable.interval(tickDuration);
- Observable.combineLatest(workTimer, engine.onResize(), (time, windowSize) -> windowSize).subscribe((windowSize) -> {
+ Observable.combineChanged(workTimer, engine.onResize()).subscribe((pair) -> {
double dt = 0;
final long newtime = System.nanoTime();
if (precTime == -1) {
@@ -413,8 +412,11 @@ public final class DisplayManager implements RenderingLoop {
}
precTime = newtime;
- StaticVars.screenSize[0] = windowSize[0];
- StaticVars.screenSize[1] = windowSize[1];
+ if (pair.getRight() != null) {
+ Integer[] windowSize = pair.getRight();
+ StaticVars.screenSize[0] = windowSize[0];
+ StaticVars.screenSize[1] = windowSize[1];
+ }
screen.beforeRender((float) (dt / 1000d));
});
diff --git a/src/main/java/org/warp/picalculator/gui/graphicengine/GraphicEngine.java b/src/main/java/org/warp/picalculator/gui/graphicengine/GraphicEngine.java
index 9ba81524..998ab473 100755
--- a/src/main/java/org/warp/picalculator/gui/graphicengine/GraphicEngine.java
+++ b/src/main/java/org/warp/picalculator/gui/graphicengine/GraphicEngine.java
@@ -3,7 +3,7 @@ package org.warp.picalculator.gui.graphicengine;
import java.io.IOException;
import java.util.List;
-import io.reactivex.Observable;
+import org.warp.picalculator.flow.Observable;
public interface GraphicEngine {
diff --git a/src/main/java/org/warp/picalculator/gui/graphicengine/cpu/CPUEngine.java b/src/main/java/org/warp/picalculator/gui/graphicengine/cpu/CPUEngine.java
index 93e02f48..704eff6a 100644
--- a/src/main/java/org/warp/picalculator/gui/graphicengine/cpu/CPUEngine.java
+++ b/src/main/java/org/warp/picalculator/gui/graphicengine/cpu/CPUEngine.java
@@ -8,14 +8,13 @@ import java.util.concurrent.Semaphore;
import org.warp.picalculator.StaticVars;
import org.warp.picalculator.Utils;
import org.warp.picalculator.device.HardwareDevice;
+import org.warp.picalculator.flow.Observable;
import org.warp.picalculator.gui.DisplayManager;
import org.warp.picalculator.gui.graphicengine.BinaryFont;
import org.warp.picalculator.gui.graphicengine.GraphicEngine;
import org.warp.picalculator.gui.graphicengine.RenderingLoop;
import org.warp.picalculator.gui.graphicengine.Skin;
-import io.reactivex.Observable;
-
public class CPUEngine implements GraphicEngine {
private SwingWindow INSTANCE;
diff --git a/src/main/java/org/warp/picalculator/gui/graphicengine/cpu/SwingWindow.java b/src/main/java/org/warp/picalculator/gui/graphicengine/cpu/SwingWindow.java
index c80a5bb2..65757a03 100755
--- a/src/main/java/org/warp/picalculator/gui/graphicengine/cpu/SwingWindow.java
+++ b/src/main/java/org/warp/picalculator/gui/graphicengine/cpu/SwingWindow.java
@@ -29,11 +29,11 @@ import org.warp.picalculator.event.TouchEndEvent;
import org.warp.picalculator.event.TouchMoveEvent;
import org.warp.picalculator.event.TouchPoint;
import org.warp.picalculator.event.TouchStartEvent;
+import org.warp.picalculator.flow.BehaviorSubject;
+import org.warp.picalculator.flow.Observable;
import org.warp.picalculator.gui.DisplayManager;
import org.warp.picalculator.gui.graphicengine.RenderingLoop;
-import io.reactivex.Observable;
-import io.reactivex.subjects.BehaviorSubject;
import it.unimi.dsi.fastutil.objects.ObjectArrayList;
public class SwingWindow extends JFrame {
@@ -55,7 +55,8 @@ public class SwingWindow extends JFrame {
// Transparent 16 x 16 pixel cursor image.
final BufferedImage cursorImg = new BufferedImage(16, 16, BufferedImage.TYPE_INT_ARGB);
- mult = StaticVars.windowZoomValue.next().intValue();
+ mult = StaticVars.windowZoomFunction.apply(StaticVars.windowZoom.getLastValue()).intValue();
+
if (StaticVars.debugOn) {
if (Utils.debugThirdScreen) {
this.setLocation(2880, 900);
diff --git a/src/main/java/org/warp/picalculator/gui/graphicengine/framebuffer/FBEngine.java b/src/main/java/org/warp/picalculator/gui/graphicengine/framebuffer/FBEngine.java
index d400ed5e..bddebd79 100644
--- a/src/main/java/org/warp/picalculator/gui/graphicengine/framebuffer/FBEngine.java
+++ b/src/main/java/org/warp/picalculator/gui/graphicengine/framebuffer/FBEngine.java
@@ -10,6 +10,8 @@ import org.warp.picalculator.MmapByteBuffer;
import org.warp.picalculator.StaticVars;
import org.warp.picalculator.TestJNI;
import org.warp.picalculator.Utils;
+import org.warp.picalculator.flow.BehaviorSubject;
+import org.warp.picalculator.flow.Observable;
import org.warp.picalculator.gui.graphicengine.BinaryFont;
import org.warp.picalculator.gui.graphicengine.GraphicEngine;
import org.warp.picalculator.gui.graphicengine.Renderer;
@@ -18,9 +20,6 @@ import org.warp.picalculator.gui.graphicengine.Skin;
import org.warp.picalculator.gui.graphicengine.cpu.CPUFont;
import org.warp.picalculator.gui.graphicengine.cpu.CPUSkin;
-import io.reactivex.Observable;
-import io.reactivex.subjects.BehaviorSubject;
-
public class FBEngine implements GraphicEngine {
private static final int FB_DISPLAY_WIDTH = 320;
@@ -59,7 +58,7 @@ public class FBEngine implements GraphicEngine {
@Override
public void create(Runnable onInitialized) {
- onResize = BehaviorSubject.createDefault(new Integer[] {SIZE[0], SIZE[1]});
+ onResize = BehaviorSubject.create(new Integer[] {SIZE[0], SIZE[1]});
realFb = jni.retrieveBuffer();
final long fbLen = realFb.getLength();
fb = (MappedByteBuffer) ByteBuffer.allocateDirect((int) fbLen);
diff --git a/src/main/java/org/warp/picalculator/gui/graphicengine/gpu/GPUEngine.java b/src/main/java/org/warp/picalculator/gui/graphicengine/gpu/GPUEngine.java
index 984428dd..87058a20 100755
--- a/src/main/java/org/warp/picalculator/gui/graphicengine/gpu/GPUEngine.java
+++ b/src/main/java/org/warp/picalculator/gui/graphicengine/gpu/GPUEngine.java
@@ -10,6 +10,7 @@ import java.util.concurrent.Semaphore;
import org.warp.picalculator.StaticVars;
import org.warp.picalculator.Utils;
+import org.warp.picalculator.flow.Observable;
import org.warp.picalculator.gui.graphicengine.BinaryFont;
import org.warp.picalculator.gui.graphicengine.GraphicEngine;
import org.warp.picalculator.gui.graphicengine.RenderingLoop;
@@ -18,10 +19,6 @@ import org.warp.picalculator.gui.graphicengine.Skin;
import com.jogamp.opengl.GLProfile;
import com.jogamp.opengl.util.texture.Texture;
-import io.reactivex.Observable;
-import io.reactivex.processors.BehaviorProcessor;
-import io.reactivex.subjects.BehaviorSubject;
-
public class GPUEngine implements GraphicEngine {
private volatile boolean initialized = false;
@@ -63,8 +60,6 @@ public class GPUEngine implements GraphicEngine {
@Override
public void setDisplayMode(int ww, int wh) {
- size[0] = ww;
- size[1] = wh;
wnd.setSize(ww, wh);
}
@@ -89,7 +84,7 @@ public class GPUEngine implements GraphicEngine {
@Override
public Observable onResize() {
- return wnd.onResize;
+ return wnd.onResizeEvent;
}
@Override
diff --git a/src/main/java/org/warp/picalculator/gui/graphicengine/gpu/NEWTWindow.java b/src/main/java/org/warp/picalculator/gui/graphicengine/gpu/NEWTWindow.java
index d69d0fc7..fdfb05aa 100755
--- a/src/main/java/org/warp/picalculator/gui/graphicengine/gpu/NEWTWindow.java
+++ b/src/main/java/org/warp/picalculator/gui/graphicengine/gpu/NEWTWindow.java
@@ -28,12 +28,8 @@
package org.warp.picalculator.gui.graphicengine.gpu;
-import java.nio.file.WatchService;
-import java.util.ArrayList;
import java.util.List;
-import org.apache.commons.lang3.tuple.Pair;
-import org.warp.picalculator.ConsoleUtils;
import org.warp.picalculator.StaticVars;
import org.warp.picalculator.device.HardwareDevice;
import org.warp.picalculator.device.Keyboard;
@@ -42,11 +38,11 @@ import org.warp.picalculator.event.TouchEndEvent;
import org.warp.picalculator.event.TouchMoveEvent;
import org.warp.picalculator.event.TouchPoint;
import org.warp.picalculator.event.TouchStartEvent;
-import org.warp.picalculator.gui.DisplayManager;
+import org.warp.picalculator.flow.BehaviorSubject;
+import org.warp.picalculator.flow.SimpleSubject;
+import org.warp.picalculator.flow.Subject;
import org.warp.picalculator.gui.graphicengine.GraphicEngine;
-import com.jogamp.newt.event.GestureHandler.GestureEvent;
-import com.jogamp.newt.event.GestureHandler.GestureListener;
import com.jogamp.newt.event.KeyEvent;
import com.jogamp.newt.event.KeyListener;
import com.jogamp.newt.event.MouseEvent;
@@ -67,15 +63,6 @@ import com.jogamp.opengl.fixedfunc.GLPointerFunc;
import com.jogamp.opengl.util.Animator;
import com.jogamp.opengl.util.texture.Texture;
-import io.reactivex.Observable;
-import io.reactivex.ObservableSource;
-import io.reactivex.Observer;
-import io.reactivex.disposables.Disposable;
-import io.reactivex.processors.BehaviorProcessor;
-import io.reactivex.subjects.BehaviorSubject;
-import io.reactivex.subjects.PublishSubject;
-import io.reactivex.subjects.ReplaySubject;
-import io.reactivex.subjects.Subject;
import it.unimi.dsi.fastutil.objects.ObjectArrayList;
/**
@@ -95,26 +82,46 @@ class NEWTWindow implements GLEventListener {
public volatile boolean refreshViewport;
public List touches = new ObjectArrayList<>();
- final BehaviorSubject onResize = BehaviorSubject.create();
+ final BehaviorSubject onRealResize;
+ final BehaviorSubject onResizeEvent = BehaviorSubject.create();
private BehaviorSubject onZoom = BehaviorSubject.create();
- private Subject onGLContext = PublishSubject.create();
+ private Subject onGLContext = SimpleSubject.create();
public NEWTWindow(GPUEngine disp) {
this.disp = disp;
renderer = disp.getRenderer();
- realWindowSize = new int[] { 1, 1 };
+ disp.size[0] = StaticVars.screenSize[0];
+ disp.size[1] = StaticVars.screenSize[1];
+ realWindowSize = new int[] { StaticVars.screenSize[0], StaticVars.screenSize[1] };
+ windowZoom = StaticVars.windowZoomFunction.apply(StaticVars.windowZoom.getLastValue());
+ onRealResize = BehaviorSubject.create(new Integer[] {(int) (StaticVars.screenSize[0] * windowZoom), (int) (StaticVars.screenSize[1] * windowZoom)});
- Observable.zip(onZoom, onGLContext, (gl,zoom)->{return Pair.of(gl, zoom);}).subscribe((pair) -> {
- windowZoom = pair.getLeft();
- onDisplayChanged(pair.getRight(), true, false);
+ onRealResize.subscribe((realSize) -> {
+ System.err.println("[[[SET REALWINDOWZOOM");
+ realWindowSize[0] = realSize[0];
+ realWindowSize[1] = realSize[1];
+ disp.size[0] = realSize[0] / (int) windowZoom;
+ disp.size[1] = realSize[1] / (int) windowZoom;
+ System.err.println("[[["+realWindowSize[0]);
+ System.err.println("[[["+windowZoom);
+ System.err.println("[[["+disp.size[0]);
+ onResizeEvent.onNext(new Integer[] {disp.size[0], disp.size[1]});
+ refreshViewport = true;
});
- Observable.zip(onResize, onGLContext, (gl,size)->{return Pair.of(gl, size);}).subscribe((pair) -> {
- final Integer[] size = pair.getLeft();
- realWindowSize[0] = size[0];
- realWindowSize[1] =size[1];
- disp.size[0] = size[0];
- disp.size[1] = size[1];
- onDisplayChanged(pair.getRight(), false, true);
+ StaticVars.windowZoom$.subscribe((zoom) -> {onZoom.onNext(zoom);});
+ onZoom.subscribe((z)-> {
+ if (windowZoom != 0) {
+ windowZoom = z;
+ disp.size[0] = (int) (realWindowSize[0] / windowZoom);
+ disp.size[1] = (int) (realWindowSize[1] / windowZoom);
+ StaticVars.screenSize[0] = disp.size[0];
+ StaticVars.screenSize[1] = disp.size[1];
+ System.err.println("[[[SET WINDOWZOOM");
+ System.err.println("[[["+realWindowSize[0]);
+ System.err.println("[[["+windowZoom);
+ System.err.println("[[[A:"+disp.size[0]);
+ refreshViewport = true;
+ }
});
}
@@ -472,8 +479,6 @@ class NEWTWindow implements GLEventListener {
} catch (final Exception e) {
e.printStackTrace();
}
- StaticVars.windowZoom$.subscribe((zoom) -> {onZoom.onNext(zoom);});
- onResize.onNext(new Integer[] {disp.size[0], disp.size[1]});
if (onInitialized != null) {
onInitialized.run();
@@ -489,21 +494,7 @@ class NEWTWindow implements GLEventListener {
@Override
public void reshape(GLAutoDrawable glad, int x, int y, int width, int height) {
- onResize.onNext(new Integer[] {width, height});
- }
-
- private void onDisplayChanged(GL2ES1 gl, boolean zoomChanged, boolean sizeChanged) {
- disp.size[0] = (int) (realWindowSize[0] / windowZoom);
- disp.size[1] = (int) (realWindowSize[1] / windowZoom);
-
- if (zoomChanged) {
- final boolean linear = (windowZoom % ((int) windowZoom)) != 0f;
- for (final Texture t : disp.registeredTextures) {
- t.setTexParameteri(gl, GL.GL_TEXTURE_MAG_FILTER, linear ? GL.GL_LINEAR : GL.GL_NEAREST);
- t.setTexParameteri(gl, GL.GL_TEXTURE_MIN_FILTER, GL.GL_LINEAR);
- }
- }
- refreshViewport = true;
+ onRealResize.onNext(new Integer[] {width, height});
}
@Override
@@ -512,18 +503,9 @@ class NEWTWindow implements GLEventListener {
GPURenderer.gl = gl;
onGLContext.onNext(gl);
- Boolean linear = null;
- while (!disp.unregisteredTextures.isEmpty()) {
- if (linear == null) {
- linear = (windowZoom % ((int) windowZoom)) != 0f;
- }
- final Texture t = disp.unregisteredTextures.pop();
- t.setTexParameteri(gl, GL.GL_TEXTURE_MAG_FILTER, GL.GL_NEAREST);
- t.setTexParameteri(gl, GL.GL_TEXTURE_MIN_FILTER, GL.GL_LINEAR);
- disp.registeredTextures.addLast(t);
- }
-
+ boolean linear = (windowZoom % ((int) windowZoom)) != 0f;
if (refreshViewport) {
+ System.err.println("[[[REFVP");
refreshViewport = false;
gl.glViewport(0, 0, realWindowSize[0], realWindowSize[1]);
@@ -534,6 +516,17 @@ class NEWTWindow implements GLEventListener {
gl.glMatrixMode(GLMatrixFunc.GL_MODELVIEW);
gl.glLoadIdentity();
+
+ for (final Texture t : disp.registeredTextures) {
+ t.setTexParameteri(gl, GL.GL_TEXTURE_MAG_FILTER, linear ? GL.GL_LINEAR : GL.GL_NEAREST);
+ t.setTexParameteri(gl, GL.GL_TEXTURE_MIN_FILTER, GL.GL_LINEAR);
+ }
+ }
+ while (disp.unregisteredTextures.isEmpty() == false) {
+ final Texture t = disp.unregisteredTextures.pop();
+ t.setTexParameteri(gl, GL.GL_TEXTURE_MAG_FILTER, linear ? GL.GL_LINEAR : GL.GL_NEAREST);
+ t.setTexParameteri(gl, GL.GL_TEXTURE_MIN_FILTER, GL.GL_LINEAR);
+ disp.registeredTextures.addLast(t);
}
gl.glEnableClientState(GLPointerFunc.GL_COLOR_ARRAY);
@@ -554,12 +547,16 @@ class NEWTWindow implements GLEventListener {
}
- public void setSize(final int width, final int height) {
+ void setSize(final int width, final int height) {
int zoom = (int) windowZoom;
if (zoom == 0) {
- zoom = onZoom.blockingFirst().intValue();
+ zoom = onZoom.getLastValue().intValue();
+ }
+ if (zoom == 0) {
+ zoom = 1;
}
window.setSize(width * zoom, height * zoom);
+ onRealResize.onNext(new Integer[] {width * zoom, height * zoom});
}
@Override
diff --git a/src/main/java/org/warp/picalculator/gui/graphicengine/headless24bit/Headless24bitEngine.java b/src/main/java/org/warp/picalculator/gui/graphicengine/headless24bit/Headless24bitEngine.java
index 2ed0ec9e..57a5e606 100644
--- a/src/main/java/org/warp/picalculator/gui/graphicengine/headless24bit/Headless24bitEngine.java
+++ b/src/main/java/org/warp/picalculator/gui/graphicengine/headless24bit/Headless24bitEngine.java
@@ -9,11 +9,10 @@ import org.warp.picalculator.StaticVars;
import org.warp.picalculator.Utils;
import org.warp.picalculator.device.Keyboard;
import org.warp.picalculator.event.Key;
+import org.warp.picalculator.flow.DObservable;
import org.warp.picalculator.gui.graphicengine.Renderer;
import org.warp.picalculator.gui.graphicengine.RenderingLoop;
-import io.reactivex.Observable;
-
public class Headless24bitEngine implements org.warp.picalculator.gui.graphicengine.GraphicEngine {
private final Headless24bitRenderer r = new Headless24bitRenderer();
@@ -140,7 +139,7 @@ public class Headless24bitEngine implements org.warp.picalculator.gui.graphiceng
}
@Override
- public Observable onResize() {
+ public DObservable onResize() {
return null;
}
diff --git a/src/main/java/org/warp/picalculator/gui/graphicengine/headless256/Headless256Engine.java b/src/main/java/org/warp/picalculator/gui/graphicengine/headless256/Headless256Engine.java
index a139685f..48fc30ef 100755
--- a/src/main/java/org/warp/picalculator/gui/graphicengine/headless256/Headless256Engine.java
+++ b/src/main/java/org/warp/picalculator/gui/graphicengine/headless256/Headless256Engine.java
@@ -9,12 +9,11 @@ import org.warp.picalculator.StaticVars;
import org.warp.picalculator.Utils;
import org.warp.picalculator.device.Keyboard;
import org.warp.picalculator.event.Key;
+import org.warp.picalculator.flow.DObservable;
import org.warp.picalculator.gui.graphicengine.Renderer;
import org.warp.picalculator.gui.graphicengine.RenderingLoop;
import org.warp.picalculator.gui.graphicengine.headless24bit.Headless24bitRenderer;
-import io.reactivex.Observable;
-
public class Headless256Engine implements org.warp.picalculator.gui.graphicengine.GraphicEngine {
private final Headless256Renderer r = new Headless256Renderer();
@@ -139,7 +138,7 @@ public class Headless256Engine implements org.warp.picalculator.gui.graphicengin
}
@Override
- public Observable onResize() {
+ public DObservable onResize() {
return null;
}
diff --git a/src/main/java/org/warp/picalculator/gui/graphicengine/headless8/Headless8Engine.java b/src/main/java/org/warp/picalculator/gui/graphicengine/headless8/Headless8Engine.java
index a20f0b05..12938038 100644
--- a/src/main/java/org/warp/picalculator/gui/graphicengine/headless8/Headless8Engine.java
+++ b/src/main/java/org/warp/picalculator/gui/graphicengine/headless8/Headless8Engine.java
@@ -9,12 +9,11 @@ import org.warp.picalculator.StaticVars;
import org.warp.picalculator.Utils;
import org.warp.picalculator.device.Keyboard;
import org.warp.picalculator.event.Key;
+import org.warp.picalculator.flow.DObservable;
import org.warp.picalculator.gui.graphicengine.Renderer;
import org.warp.picalculator.gui.graphicengine.RenderingLoop;
import org.warp.picalculator.gui.graphicengine.headless24bit.Headless24bitRenderer;
-import io.reactivex.Observable;
-
public class Headless8Engine implements org.warp.picalculator.gui.graphicengine.GraphicEngine {
private final Headless8Renderer r = new Headless8Renderer();
@@ -139,7 +138,7 @@ public class Headless8Engine implements org.warp.picalculator.gui.graphicengine.
}
@Override
- public Observable onResize() {
+ public DObservable onResize() {
return null;
}
diff --git a/src/main/java/org/warp/picalculator/gui/graphicengine/nogui/NoGuiEngine.java b/src/main/java/org/warp/picalculator/gui/graphicengine/nogui/NoGuiEngine.java
index 966ef8f2..cb4e377b 100644
--- a/src/main/java/org/warp/picalculator/gui/graphicengine/nogui/NoGuiEngine.java
+++ b/src/main/java/org/warp/picalculator/gui/graphicengine/nogui/NoGuiEngine.java
@@ -5,14 +5,13 @@ import java.util.concurrent.Semaphore;
import org.warp.picalculator.Utils;
import org.warp.picalculator.deps.DSemaphore;
+import org.warp.picalculator.flow.Observable;
import org.warp.picalculator.gui.graphicengine.BinaryFont;
import org.warp.picalculator.gui.graphicengine.GraphicEngine;
import org.warp.picalculator.gui.graphicengine.Renderer;
import org.warp.picalculator.gui.graphicengine.RenderingLoop;
import org.warp.picalculator.gui.graphicengine.Skin;
-import io.reactivex.Observable;
-
public class NoGuiEngine implements GraphicEngine {
private boolean initialized;
diff --git a/src/main/java/org/warp/picalculator/gui/screens/LoadingScreen.java b/src/main/java/org/warp/picalculator/gui/screens/LoadingScreen.java
index 6c837992..db98f338 100755
--- a/src/main/java/org/warp/picalculator/gui/screens/LoadingScreen.java
+++ b/src/main/java/org/warp/picalculator/gui/screens/LoadingScreen.java
@@ -26,7 +26,7 @@ public class LoadingScreen extends Screen {
@Override
public void initialized() throws InterruptedException {
- previousZoomValue = StaticVars.windowZoomValue.next();
+ previousZoomValue = StaticVars.windowZoomFunction.apply(StaticVars.windowZoom.getLastValue());
StaticVars.windowZoom.onNext(1f);
}