diff --git a/res/font_ex.rft b/res/font_ex.rft
index 1f79a6e9..18475d17 100644
Binary files a/res/font_ex.rft and b/res/font_ex.rft differ
diff --git a/src/org/warp/picalculator/TestGPU.java b/src/org/warp/picalculator/TestGPU.java
index 8ea9b711..c88deb0e 100644
--- a/src/org/warp/picalculator/TestGPU.java
+++ b/src/org/warp/picalculator/TestGPU.java
@@ -10,6 +10,7 @@ import org.warp.picalculator.gui.expression.BlockContainer;
import org.warp.picalculator.gui.expression.BlockDivision;
import org.warp.picalculator.gui.expression.Caret;
import org.warp.picalculator.gui.expression.CaretState;
+import org.warp.picalculator.gui.expression.containers.NormalInputContainer;
import org.warp.picalculator.gui.graphicengine.BinaryFont;
import org.warp.picalculator.gui.graphicengine.Skin;
import org.warp.picalculator.gui.graphicengine.cpu.CPUEngine;
@@ -20,7 +21,7 @@ import org.warp.picalculator.gui.screens.MarioScreen;
import org.warp.picalculator.math.MathContext;
import org.warp.picalculator.math.MathematicalSymbols;
import org.warp.picalculator.math.functions.Expression;
-import org.warp.picalculator.math.parser.InputParser;
+import org.warp.picalculator.math.parser.MathParser;
import java.lang.management.ManagementFactory;
import java.lang.management.OperatingSystemMXBean;
@@ -48,7 +49,7 @@ public class TestGPU {
private final Renderer r;
private final GraphicEngine d;
- private final BlockContainer c;
+ private final NormalInputContainer c;
public Scene(GraphicEngine d) throws IOException, Error {
this.d = d;
@@ -62,22 +63,21 @@ public class TestGPU {
//New expression framework test
- c = new BlockContainer(false, 0, 200);
- BlockDivision bd = new BlockDivision();
- c.addBlock(bd);
- bd.getUpperContainer().addBlock(new BlockChar('5'));
- bd.getUpperContainer().addBlock(new BlockChar(MathematicalSymbols.MULTIPLICATION));
- bd.getUpperContainer().addBlock(new BlockChar('2'));
- bd.getLowerContainer().addBlock(new BlockChar('2'));
- bd.recomputeDimensions();
- c.addBlock(new BlockChar(MathematicalSymbols.MULTIPLICATION));
- c.addBlock(new BlockChar('2'));
- c.addBlock(new BlockChar('2'));
- c.addBlock(new BlockChar('b'));
+ c = new NormalInputContainer(false, 0, 200);
+ c.typeChar(MathematicalSymbols.DIVISION);
+ c.typeChar('5');
+ c.typeChar(MathematicalSymbols.MULTIPLICATION);
+ c.typeChar('2');
+ c.moveRight();
+ c.typeChar('2');
+ c.moveRight();
+ c.typeChar(MathematicalSymbols.MULTIPLICATION);
+ c.typeChar('2');
+ c.typeChar('2');
c.recomputeDimensions();
- Expression expr = InputParser.parseInput(new MathContext(), c);
- System.out.println(expr.toString());
+ Expression expr = MathParser.parseInput(new MathContext(), c.root);
+ System.out.println("Parsed input:"+expr.toString());
d.start(this);
@@ -119,7 +119,7 @@ public class TestGPU {
r.glFillRect(162, 2.5f, 160, 160, 0, 0, 16, 16);
//New expression framework test
- c.draw(d, r, 10, 220, new Caret(CaretState.VISIBLE_ON, 10));
+ c.draw(d, r, 10, 220);
}
}
diff --git a/src/org/warp/picalculator/device/PIDisplay.java b/src/org/warp/picalculator/device/PIDisplay.java
index dd2068cb..1910e5b0 100644
--- a/src/org/warp/picalculator/device/PIDisplay.java
+++ b/src/org/warp/picalculator/device/PIDisplay.java
@@ -25,16 +25,6 @@ import org.warp.picalculator.device.graphicengine.RAWFont;
import org.warp.picalculator.device.graphicengine.Screen;
import com.pi4j.wiringpi.Gpio;
-/**
- * STB Truetype oversampling demo.
- *
- *
- * This is a Java port of https:/
- * /github
- * .com/nothings/stb/blob/master/tests/oversample/main.c.
- *
- */
public final class PIDisplay {
public static PIDisplay INSTANCE;
private static float brightness;
diff --git a/src/org/warp/picalculator/gui/DisplayManager.java b/src/org/warp/picalculator/gui/DisplayManager.java
index 8b91a077..cd1be4ef 100644
--- a/src/org/warp/picalculator/gui/DisplayManager.java
+++ b/src/org/warp/picalculator/gui/DisplayManager.java
@@ -356,7 +356,7 @@ public final class DisplayManager implements RenderingLoop {
Main.screenSize[1] = engine.getHeight();
}
};
-
+
public void loop() {
try {
load_skin();
diff --git a/src/org/warp/picalculator/gui/expression/Block.java b/src/org/warp/picalculator/gui/expression/Block.java
index 85967e38..b1d2ffb8 100644
--- a/src/org/warp/picalculator/gui/expression/Block.java
+++ b/src/org/warp/picalculator/gui/expression/Block.java
@@ -5,7 +5,7 @@ import org.warp.picalculator.gui.graphicengine.Renderer;
import org.warp.picalculator.math.parser.features.interfaces.Feature;
public abstract class Block implements GraphicalElement {
-
+
protected boolean small;
protected int width;
protected int height;
@@ -20,6 +20,10 @@ public abstract class Block implements GraphicalElement {
*/
public abstract void draw(GraphicEngine ge, Renderer r, int x, int y, Caret caret);
+ public abstract boolean putBlock(Caret caret, Block newBlock);
+
+ public abstract boolean delBlock(Caret caret);
+
@Override
public abstract void recomputeDimensions();
@@ -44,4 +48,5 @@ public abstract class Block implements GraphicalElement {
public abstract void setSmall(boolean small);
+ public abstract int getClassID();
}
diff --git a/src/org/warp/picalculator/gui/expression/BlockChar.java b/src/org/warp/picalculator/gui/expression/BlockChar.java
index 18c87c50..04f3e6a0 100644
--- a/src/org/warp/picalculator/gui/expression/BlockChar.java
+++ b/src/org/warp/picalculator/gui/expression/BlockChar.java
@@ -6,7 +6,9 @@ import org.warp.picalculator.math.parser.features.FeatureChar;
import org.warp.picalculator.math.parser.features.interfaces.Feature;
public class BlockChar extends Block {
-
+
+ public static final int CLASS_ID = 0x00000001;
+
private final char ch;
public BlockChar(char ch) {
@@ -21,6 +23,16 @@ public class BlockChar extends Block {
r.glDrawCharLeft(x, y, ch);
}
+ @Override
+ public boolean putBlock(Caret caret, Block newBlock) {
+ return false;
+ }
+
+ @Override
+ public boolean delBlock(Caret caret) {
+ return false;
+ }
+
@Override
public void recomputeDimensions() {
width = BlockContainer.getDefaultCharWidth(small);
@@ -38,4 +50,9 @@ public class BlockChar extends Block {
return ch;
}
+ @Override
+ public int getClassID() {
+ return CLASS_ID;
+ }
+
}
diff --git a/src/org/warp/picalculator/gui/expression/BlockContainer.java b/src/org/warp/picalculator/gui/expression/BlockContainer.java
index 51235657..332975c5 100644
--- a/src/org/warp/picalculator/gui/expression/BlockContainer.java
+++ b/src/org/warp/picalculator/gui/expression/BlockContainer.java
@@ -11,6 +11,8 @@ import org.warp.picalculator.gui.graphicengine.gpu.GPUFont;
public class BlockContainer implements GraphicalElement {
+ private static boolean initialized = false;
+
private final int minWidth;
private final int minHeight;
private final ObjectArrayList content;
@@ -18,32 +20,54 @@ public class BlockContainer implements GraphicalElement {
private int width;
private int height;
private int line;
+ public final boolean withBorder;
public BlockContainer() {
- this(false, BlockContainer.getDefaultCharWidth(true), BlockContainer.getDefaultCharHeight(true));
+ this(false, BlockContainer.getDefaultCharWidth(false), BlockContainer.getDefaultCharHeight(false), true);
}
public BlockContainer(boolean small) {
- this(small, BlockContainer.getDefaultCharWidth(true), BlockContainer.getDefaultCharHeight(true));
+ this(small, BlockContainer.getDefaultCharWidth(small), BlockContainer.getDefaultCharHeight(small), true);
}
- public BlockContainer(boolean small, int minWidth, int minHeight) {
- this(small, minWidth, minHeight, new ObjectArrayList<>());
+ public BlockContainer(boolean small, boolean withBorder) {
+ this(small, BlockContainer.getDefaultCharWidth(small), BlockContainer.getDefaultCharHeight(small), withBorder);
}
- public BlockContainer(boolean small, int minWidth, int minHeight, ObjectArrayList content) {
+ public BlockContainer(boolean small, int minWidth, int minHeight, boolean withBorder) {
+ this(small, minWidth, minHeight, new ObjectArrayList<>(), withBorder);
+ }
+
+ public BlockContainer(boolean small, int minWidth, int minHeight, ObjectArrayList content, boolean withBorder) {
this.small = small;
this.minWidth = minWidth;
this.minHeight = minHeight;
+ this.withBorder = withBorder;
for (Block b: content) {
- b.setSmall(small);
+ if (b.isSmall() != small) {
+ b.setSmall(small);
+ }
}
this.content = content;
recomputeDimensions();
}
+
+ public void addBlock(int position, Block b) {
+ if (b.isSmall() != small) {
+ b.setSmall(small);
+ }
+ if (position >= content.size()) {
+ content.add(b);
+ } else {
+ content.add(position, b);
+ }
+ recomputeDimensions();
+ }
- public void addBlock(Block b) {
- b.setSmall(small);
+ public void appendBlock(Block b) {
+ if (b.isSmall() != small) {
+ b.setSmall(small);
+ }
content.add(b);
recomputeDimensions();
}
@@ -76,25 +100,81 @@ public class BlockContainer implements GraphicalElement {
* @param caret Position of the caret.
*/
public void draw(GraphicEngine ge, Renderer r, int x, int y, Caret caret) {
- int paddingX = 0;
+ int paddingX = 1;
if (caret.getRemaining() == 0) {
if (content.size() > 0) {
- BlockContainer.drawCaret(ge, r, caret, x, y, content.get(0).getHeight());
+ BlockContainer.drawCaret(ge, r, caret, x, y+line-content.get(0).line, content.get(0).height);
} else {
BlockContainer.drawCaret(ge, r, caret, x, y, height);
}
}
- for (Block b : content) {
- caret.skip(1);
- b.draw(ge, r, x+paddingX, y+line-b.getLine(), caret);
- paddingX += b.getWidth();
- if (caret.getRemaining() == 0) BlockContainer.drawCaret(ge, r, caret, x + paddingX, y+line-b.getLine(), b.height);
+ if (withBorder && content.size() == 0) {
+ r.glDrawLine(x+paddingX, y, x+paddingX+width-1, y);
+ r.glDrawLine(x+paddingX, y, x+paddingX, y+height-1);
+ r.glDrawLine(x+paddingX+width-1, y, x+paddingX+width-1, y+height-1);
+ r.glDrawLine(x+paddingX, y+height-1, x+paddingX+width-1, y+height-1);
+ } else {
+ for (Block b : content) {
+ caret.skip(1);
+ b.draw(ge, r, x+paddingX, y+line-b.line, caret);
+ paddingX += b.getWidth();
+ if (caret.getRemaining() == 0) BlockContainer.drawCaret(ge, r, caret, x + paddingX, y+line-b.line, b.height);
+ paddingX += 1;
+ }
}
caret.skip(1);
}
+ public boolean putBlock(Caret caret, Block newBlock) {
+ boolean added = false;
+
+ if (caret.getRemaining() == 0) {
+ this.addBlock(0, newBlock);
+ added = true;
+ }
+
+ int pos = 0;
+ for (Block b : content) {
+ caret.skip(1);
+ pos++;
+ added = added|b.putBlock(caret, newBlock);
+ if (caret.getRemaining() == 0) {
+ this.addBlock(pos, newBlock);
+ added = true;
+ }
+ }
+ caret.skip(1);
+ if (added) {
+ recomputeDimensions();
+ }
+ return added;
+ }
+
+ public boolean delBlock(Caret caret) {
+ boolean removed = false;
+
+ int pos = 0;
+ for (Block b : content) {
+ caret.skip(1);
+ pos++;
+ int deltaCaret = caret.getRemaining();
+ removed = removed|b.delBlock(caret);
+ if (caret.getRemaining() == 0 || (removed == false && deltaCaret >= 0 && caret.getRemaining() < 0)) {
+ this.removeAt(pos-1);
+ caret.setPosition(caret.getPosition()-deltaCaret);
+ removed = true;
+ }
+ }
+ caret.skip(1);
+ if (removed) {
+ recomputeDimensions();
+ }
+ return removed;
+ }
+
+
@Override
public void recomputeDimensions() {
int l = 0; //Line
@@ -103,7 +183,7 @@ public class BlockContainer implements GraphicalElement {
int h = 0; //Height
for (Block b : content) {
- w += b.getWidth();
+ w += b.getWidth() + 1;
final int bl = b.getLine();
final int bh = b.getHeight();
final int bh2 = bh - bl;
@@ -115,6 +195,10 @@ public class BlockContainer implements GraphicalElement {
}
}
+ if (content.size() > 0) {
+ w -= 1;
+ }
+
h = h2 + l;
line = l;
@@ -127,6 +211,7 @@ public class BlockContainer implements GraphicalElement {
height = h;
} else {
height = minHeight;
+ line = height/2;
}
}
@@ -156,29 +241,35 @@ public class BlockContainer implements GraphicalElement {
defFontSizes[1] = big.getCharacterHeight();
defFontSizes[2] = small.getCharacterWidth();
defFontSizes[3] = small.getCharacterHeight();
+ initialized = true;
}
public static BinaryFont getDefaultFont(boolean small) {
+ checkInitialized();
return defFonts[small?1:0];
}
-
public static int getDefaultColor() {
return defColor;
}
public static int getDefaultCharWidth(boolean b) {
+ checkInitialized();
return defFontSizes[b?2:0];
}
public static int getDefaultCharHeight(boolean b) {
+ checkInitialized();
return defFontSizes[b?3:1];
}
public static void drawCaret(GraphicEngine ge, Renderer r, Caret caret, int x, int y, int height) {
- r.glColor(getDefaultColor());
- r.glDrawLine(x, y, x, y-1+height);
- r.glDrawLine(x+1, y, x+1, y-1+height);
+ if (caret.getState() == CaretState.VISIBLE_ON) {
+ r.glColor(getDefaultColor());
+ r.glDrawLine(x, y, x, y-1+height);
+ r.glDrawLine(x+1, y, x+1, y-1+height);
+ r.glDrawLine(x+2, y, x+2, y-1+height);
+ }
}
public void setSmall(boolean small) {
@@ -190,4 +281,8 @@ public class BlockContainer implements GraphicalElement {
return content.clone();
}
+ private static void checkInitialized() {
+ if (!initialized) throw new ExceptionInInitializerError("Please initialize BlockContainer by running the method BlockContainer.initialize(...) first!");
+ }
+
}
\ No newline at end of file
diff --git a/src/org/warp/picalculator/gui/expression/BlockDivision.java b/src/org/warp/picalculator/gui/expression/BlockDivision.java
index c73805d5..a2c3870c 100644
--- a/src/org/warp/picalculator/gui/expression/BlockDivision.java
+++ b/src/org/warp/picalculator/gui/expression/BlockDivision.java
@@ -8,6 +8,8 @@ import org.warp.picalculator.math.parser.features.interfaces.Feature;
import it.unimi.dsi.fastutil.objects.ObjectArrayList;
public class BlockDivision extends Block {
+
+ public static final int CLASS_ID = 0x00000002;
private final BlockContainer containerUp;
private final BlockContainer containerDown;
@@ -27,17 +29,39 @@ public class BlockDivision extends Block {
BlockContainer.getDefaultFont(small).use(ge);
r.glColor(BlockContainer.getDefaultColor());
containerUp.draw(ge, r, x+1+paddingLeftUpper, y, caret);
- r.glDrawLine(x, y+h1+1, x+width, y+h1+1);
+ r.glDrawLine(x, y+h1+1, x+width-1, y+h1+1);
containerDown.draw(ge, r, x+1+paddingLeftLower, y + h1+3, caret);
}
+ @Override
+ public boolean putBlock(Caret caret, Block newBlock) {
+ boolean added = false;
+ added = added|containerUp.putBlock(caret, newBlock);
+ added = added|containerDown.putBlock(caret, newBlock);
+ if (added) {
+ recomputeDimensions();
+ }
+ return added;
+ }
+
+ @Override
+ public boolean delBlock(Caret caret) {
+ boolean removed = false;
+ removed = removed|containerUp.delBlock(caret);
+ removed = removed|containerDown.delBlock(caret);
+ if (removed) {
+ recomputeDimensions();
+ }
+ return removed;
+ }
+
@Override
public void recomputeDimensions() {
final int w1 = containerUp.getWidth();
final int w2 = containerDown.getWidth();
final int h1 = containerUp.getHeight();
final int h2 = containerDown.getHeight();
- width = (w1>w2?w1:w2) + 2;
+ width = (w1>w2?w1:w2) + 4;
height = h1+3+h2;
line = h1+1;
this.h1 = h1;
@@ -49,6 +73,9 @@ public class BlockDivision extends Block {
paddingLeftUpper = (w2 - w1) / 2;
paddingLeftLower = 0;
}
+ } else {
+ paddingLeftUpper = 0;
+ paddingLeftLower = 0;
}
}
@@ -67,4 +94,9 @@ public class BlockDivision extends Block {
public BlockContainer getLowerContainer() {
return containerDown;
}
+
+ @Override
+ public int getClassID() {
+ return CLASS_ID;
+ }
}
diff --git a/src/org/warp/picalculator/gui/expression/BlockSquareRoot.java b/src/org/warp/picalculator/gui/expression/BlockSquareRoot.java
new file mode 100644
index 00000000..74dd0581
--- /dev/null
+++ b/src/org/warp/picalculator/gui/expression/BlockSquareRoot.java
@@ -0,0 +1,87 @@
+package org.warp.picalculator.gui.expression;
+
+import org.warp.picalculator.Main;
+import org.warp.picalculator.gui.graphicengine.GraphicEngine;
+import org.warp.picalculator.gui.graphicengine.Renderer;
+import org.warp.picalculator.math.parser.features.interfaces.Feature;
+
+import it.unimi.dsi.fastutil.objects.ObjectArrayList;
+
+public class BlockSquareRoot extends Block {
+
+ public static final int CLASS_ID = 0x00000002;
+
+ private final BlockContainer containerNumber;
+
+ private int h1;
+
+ public BlockSquareRoot() {
+ this.containerNumber = new BlockContainer(false);
+ recomputeDimensions();
+ }
+
+ @Override
+ public void draw(GraphicEngine ge, Renderer r, int x, int y, Caret caret) {
+ BlockContainer.getDefaultFont(small).use(ge);
+ r.glColor(BlockContainer.getDefaultColor());
+ r.glDrawLine(x, y+height-10+1, x, y+height-10+2); // /
+ r.glDrawLine(x+1, y+height-10, x+1, y+height-10+1); // /
+ r.glDrawLine(x+2, y+height-10+2, x+2, y+height-10+6); // \
+ r.glDrawLine(x+3, y+height-10+7, x+3, y+height-10+9); // \
+ r.glDrawLine(x+5, y+height-h1-1-2, x+width-1, y+height-h1-1-2); // ----
+ r.glDrawLine(x+5, y+height-h1-1-2, x+5, y+height-(h1-2)/3f*2f-1); // |
+ r.glDrawLine(x+4, y+height-(h1-2)/3f*2f-1, x+4, y+height-(h1-2)/3f-1); // |
+ r.glDrawLine(x+3, y+height-(h1-2)/3f-1, x+3, y+height-1); // |
+ containerNumber.draw(ge, r, x+7, y+3, caret);
+ }
+
+ @Override
+ public boolean putBlock(Caret caret, Block newBlock) {
+ boolean added = false;
+ added = added|containerNumber.putBlock(caret, newBlock);
+ if (added) {
+ recomputeDimensions();
+ }
+ return added;
+ }
+
+ @Override
+ public boolean delBlock(Caret caret) {
+ boolean removed = false;
+ removed = removed|containerNumber.delBlock(caret);
+ if (removed) {
+ recomputeDimensions();
+ }
+ return removed;
+ }
+
+ @Override
+ public void recomputeDimensions() {
+ final int w1 = containerNumber.getWidth();
+ h1 = containerNumber.getHeight();
+ final int l1 = containerNumber.getLine();
+ width = 8+w1+2;
+ height = 3+h1;
+ line = 3+l1;
+ if (height < 9) {
+ height = 9;
+ line+=(9-(3+h1));
+ }
+ }
+
+ @Override
+ public void setSmall(boolean small) {
+ this.small = small;
+ this.containerNumber.setSmall(small);
+ recomputeDimensions();
+ }
+
+ public BlockContainer getNumberContainer() {
+ return containerNumber;
+ }
+
+ @Override
+ public int getClassID() {
+ return CLASS_ID;
+ }
+}
diff --git a/src/org/warp/picalculator/gui/expression/Caret.java b/src/org/warp/picalculator/gui/expression/Caret.java
index 5bbdca50..736e5c89 100644
--- a/src/org/warp/picalculator/gui/expression/Caret.java
+++ b/src/org/warp/picalculator/gui/expression/Caret.java
@@ -5,7 +5,7 @@ public class Caret {
private int pos;
private int remaining;
private CaretState state;
-
+
public Caret(CaretState state, int pos) {
this.state = state;
this.pos = pos;
@@ -27,4 +27,26 @@ public class Caret {
public CaretState getState() {
return state;
}
+
+ public void flipState() {
+ if (this.state == CaretState.VISIBLE_ON) {
+ this.state = CaretState.VISIBLE_OFF;
+ } else if (this.state == CaretState.VISIBLE_OFF) {
+ this.state = CaretState.VISIBLE_ON;
+ }
+ }
+
+ public void turnOn() {
+ if (this.state == CaretState.VISIBLE_OFF) {
+ this.state = CaretState.VISIBLE_ON;
+ }
+ }
+
+ public void setPosition(int i) {
+ this.pos = i;
+ }
+
+ public void resetRemaining() {
+ remaining = pos;
+ }
}
diff --git a/src/org/warp/picalculator/gui/expression/containers/InlineInputContainer.java b/src/org/warp/picalculator/gui/expression/containers/InlineInputContainer.java
new file mode 100644
index 00000000..d55f3b10
--- /dev/null
+++ b/src/org/warp/picalculator/gui/expression/containers/InlineInputContainer.java
@@ -0,0 +1,12 @@
+package org.warp.picalculator.gui.expression.containers;
+
+import org.warp.picalculator.gui.expression.Block;
+import org.warp.picalculator.gui.expression.BlockChar;
+import org.warp.picalculator.math.MathematicalSymbols;
+
+public class InlineInputContainer extends InputContainer {
+ @Override
+ public Block parseChar(char c) {
+ return new BlockChar(MathematicalSymbols.DIVISION);
+ }
+}
diff --git a/src/org/warp/picalculator/gui/expression/containers/InputContainer.java b/src/org/warp/picalculator/gui/expression/containers/InputContainer.java
new file mode 100644
index 00000000..8a23aeb0
--- /dev/null
+++ b/src/org/warp/picalculator/gui/expression/containers/InputContainer.java
@@ -0,0 +1,136 @@
+package org.warp.picalculator.gui.expression.containers;
+
+import org.warp.picalculator.gui.expression.Block;
+import org.warp.picalculator.gui.expression.BlockContainer;
+import org.warp.picalculator.gui.expression.Caret;
+import org.warp.picalculator.gui.expression.CaretState;
+import org.warp.picalculator.gui.expression.GraphicalElement;
+import org.warp.picalculator.gui.expression.layouts.InputLayout;
+import org.warp.picalculator.gui.graphicengine.GraphicEngine;
+import org.warp.picalculator.gui.graphicengine.Renderer;
+
+public abstract class InputContainer implements GraphicalElement, InputLayout {
+ public final BlockContainer root;
+ private Caret caret;
+ private static final float CARET_DURATION = 0.5f;
+ private float caretTime;
+
+ public InputContainer() {
+ caret = new Caret(CaretState.VISIBLE_ON, 0);
+ root = new BlockContainer(false, false);
+ }
+
+ public InputContainer(boolean small) {
+ caret = new Caret(CaretState.VISIBLE_ON, 0);
+ root = new BlockContainer(small, false);
+ }
+
+ public InputContainer(boolean small, int minWidth, int minHeight) {
+ caret = new Caret(CaretState.VISIBLE_ON, 0);
+ root = new BlockContainer(small, false);
+ }
+
+ public void typeChar(char c) {
+ Block b = parseChar(c);
+ if (b != null) {
+ caret.resetRemaining();
+ if (root.putBlock(caret, b)) {
+ caret.setPosition(caret.getPosition()+1);
+ root.recomputeDimensions();
+ }
+ }
+ caretTime = 0;
+ caret.turnOn();
+ }
+
+ public void typeChar(String c) {
+ typeChar(c.charAt(0));
+ }
+
+ public void del() {
+ caret.resetRemaining();
+ if (root.delBlock(caret)) {
+ root.recomputeDimensions();
+ }
+ if (caret.getPosition() > 0) {
+ caret.setPosition(caret.getPosition()-1);
+ }
+ caret.turnOn();
+ caretTime = 0;
+ }
+
+ public void moveLeft() {
+ if (caret.getPosition() > 0) {
+ caret.setPosition(caret.getPosition()-1);
+ }
+ caret.turnOn();
+ caretTime = 0;
+ }
+
+ public void moveRight() {
+ caret.setPosition(caret.getPosition()+1);
+ caret.turnOn();
+ caretTime = 0;
+ }
+
+ @Override
+ public void recomputeDimensions() {
+ root.recomputeDimensions();
+ }
+
+ @Override
+ public int getWidth() {
+ return root.getWidth();
+ }
+
+ @Override
+ public int getHeight() {
+ return root.getHeight();
+ }
+
+ @Override
+ public int getLine() {
+ return root.getLine();
+ }
+
+ /**
+ *
+ * @param delta Time, in seconds
+ * @return true if something changed
+ */
+ public boolean beforeRender(float delta) {
+ boolean somethingChanged = false;
+ caretTime += delta;
+ if (caretTime >= CARET_DURATION) {
+ while (caretTime >= CARET_DURATION) {
+ caretTime -= CARET_DURATION;
+ caret.flipState();
+ somethingChanged = true;
+ }
+ }
+ return somethingChanged;
+ }
+
+ /**
+ *
+ * @param ge Graphic Engine class.
+ * @param r Graphic Renderer class of ge.
+ * @param x Position relative to the window.
+ * @param y Position relative to the window.
+ */
+ public void draw(GraphicEngine ge, Renderer r, int x, int y) {
+ caret.resetRemaining();
+ root.draw(ge, r, x, y, caret);
+
+ int remaining = caret.getRemaining();
+ if (remaining >= 0) {
+ caret.setPosition(caret.getPosition()-remaining-1);
+ }
+ }
+
+ public void clear() {
+ caret = new Caret(CaretState.VISIBLE_ON, 0);
+ root.clear();
+ recomputeDimensions();
+ }
+}
diff --git a/src/org/warp/picalculator/gui/expression/containers/NormalInputContainer.java b/src/org/warp/picalculator/gui/expression/containers/NormalInputContainer.java
new file mode 100644
index 00000000..a2ae198a
--- /dev/null
+++ b/src/org/warp/picalculator/gui/expression/containers/NormalInputContainer.java
@@ -0,0 +1,35 @@
+package org.warp.picalculator.gui.expression.containers;
+
+import org.warp.picalculator.gui.expression.Block;
+import org.warp.picalculator.gui.expression.BlockChar;
+import org.warp.picalculator.gui.expression.BlockDivision;
+import org.warp.picalculator.gui.expression.BlockSquareRoot;
+import org.warp.picalculator.math.MathematicalSymbols;
+
+public class NormalInputContainer extends InputContainer {
+ @Override
+ public Block parseChar(char c) {
+ switch(c) {
+ case MathematicalSymbols.DIVISION:
+ return new BlockDivision();
+ case MathematicalSymbols.SQUARE_ROOT:
+ return new BlockSquareRoot();
+ case MathematicalSymbols.MULTIPLICATION:
+ case MathematicalSymbols.SUM:
+ case MathematicalSymbols.SUBTRACTION:
+ case '0':
+ case '1':
+ case '2':
+ case '3':
+ case '4':
+ case '5':
+ case '6':
+ case '7':
+ case '8':
+ case '9':
+ return new BlockChar(c);
+ default:
+ return new BlockChar(c);
+ }
+ }
+}
diff --git a/src/org/warp/picalculator/gui/expression/containers/NormalOutputContainer.java b/src/org/warp/picalculator/gui/expression/containers/NormalOutputContainer.java
new file mode 100644
index 00000000..081f2f46
--- /dev/null
+++ b/src/org/warp/picalculator/gui/expression/containers/NormalOutputContainer.java
@@ -0,0 +1,5 @@
+package org.warp.picalculator.gui.expression.containers;
+
+public class NormalOutputContainer extends OutputContainer {
+
+}
diff --git a/src/org/warp/picalculator/gui/expression/containers/OutputContainer.java b/src/org/warp/picalculator/gui/expression/containers/OutputContainer.java
new file mode 100644
index 00000000..221ea519
--- /dev/null
+++ b/src/org/warp/picalculator/gui/expression/containers/OutputContainer.java
@@ -0,0 +1,71 @@
+package org.warp.picalculator.gui.expression.containers;
+
+import org.warp.picalculator.gui.expression.Block;
+import org.warp.picalculator.gui.expression.BlockContainer;
+import org.warp.picalculator.gui.expression.Caret;
+import org.warp.picalculator.gui.expression.CaretState;
+import org.warp.picalculator.gui.expression.GraphicalElement;
+import org.warp.picalculator.gui.expression.layouts.InputLayout;
+import org.warp.picalculator.gui.graphicengine.GraphicEngine;
+import org.warp.picalculator.gui.graphicengine.Renderer;
+
+public abstract class OutputContainer implements GraphicalElement, OutputLayout {
+ public final BlockContainer root;
+ private final Caret caret = new Caret(CaretState.HIDDEN, 0);
+
+ public OutputContainer() {
+ root = new BlockContainer();
+ }
+
+ public OutputContainer(boolean small) {
+ root = new BlockContainer(small);
+ }
+
+ public OutputContainer(boolean small, int minWidth, int minHeight) {
+ root = new BlockContainer(small);
+ }
+
+ @Override
+ public void recomputeDimensions() {
+ root.recomputeDimensions();
+ }
+
+ @Override
+ public int getWidth() {
+ return root.getWidth();
+ }
+
+ @Override
+ public int getHeight() {
+ return root.getHeight();
+ }
+
+ @Override
+ public int getLine() {
+ return root.getLine();
+ }
+
+ /**
+ *
+ * @param delta Time, in seconds
+ */
+ public void beforeRender(double delta) {
+
+ }
+
+ /**
+ *
+ * @param ge Graphic Engine class.
+ * @param r Graphic Renderer class of ge.
+ * @param x Position relative to the window.
+ * @param y Position relative to the window.
+ */
+ public void draw(GraphicEngine ge, Renderer r, int x, int y) {
+ root.draw(ge, r, x, y, caret);
+ }
+
+ public void clear() {
+ root.clear();
+ recomputeDimensions();
+ }
+}
diff --git a/src/org/warp/picalculator/gui/expression/containers/OutputLayout.java b/src/org/warp/picalculator/gui/expression/containers/OutputLayout.java
new file mode 100644
index 00000000..fbb9d375
--- /dev/null
+++ b/src/org/warp/picalculator/gui/expression/containers/OutputLayout.java
@@ -0,0 +1,5 @@
+package org.warp.picalculator.gui.expression.containers;
+
+public interface OutputLayout {
+
+}
diff --git a/src/org/warp/picalculator/gui/expression/layouts/InputLayout.java b/src/org/warp/picalculator/gui/expression/layouts/InputLayout.java
new file mode 100644
index 00000000..04550bbe
--- /dev/null
+++ b/src/org/warp/picalculator/gui/expression/layouts/InputLayout.java
@@ -0,0 +1,7 @@
+package org.warp.picalculator.gui.expression.layouts;
+
+import org.warp.picalculator.gui.expression.Block;
+
+public interface InputLayout {
+ public Block parseChar(char c);
+}
diff --git a/src/org/warp/picalculator/gui/graphicengine/cpu/CPUEngine.java b/src/org/warp/picalculator/gui/graphicengine/cpu/CPUEngine.java
index 293a1fc2..7f9f1f56 100644
--- a/src/org/warp/picalculator/gui/graphicengine/cpu/CPUEngine.java
+++ b/src/org/warp/picalculator/gui/graphicengine/cpu/CPUEngine.java
@@ -269,17 +269,23 @@ public class CPUEngine implements GraphicEngine {
}
if (iy0 == iy1) {
for (int x = 0; x <= ix1 - ix0; x++) {
- canvas2d[ix0 + x + iy0 * size[0]] = color;
+ if ((ix0+x < size[0]) & (iy0 < size[1])) {
+ canvas2d[ix0 + x + iy0 * size[0]] = color;
+ }
}
} else if (ix0 == ix1) {
for (int y = 0; y <= iy1 - iy0; y++) {
- canvas2d[ix0 + (iy0 + y) * size[0]] = color;
+ if ((ix0 < size[0]) & (iy0+y < size[1])) {
+ canvas2d[ix0 + (iy0 + y) * size[0]] = color;
+ }
}
} else {
final int m = (iy1 - iy0) / (ix1 - ix0);
for (int texx = 0; texx <= ix1 - ix0; texx++) {
if (ix0 + texx < size[0] && iy0 + (m * texx) < size[1]) {
- canvas2d[(ix0 + texx) + (iy0 + (m * texx)) * size[0]] = color;
+ if ((ix0 + texx < size[0]) & ((iy0 + (m * texx)) < size[1])) {
+ canvas2d[(ix0 + texx) + (iy0 + (m * texx)) * size[0]] = color;
+ }
}
}
}
diff --git a/src/org/warp/picalculator/gui/graphicengine/gpu/GPUEngine.java b/src/org/warp/picalculator/gui/graphicengine/gpu/GPUEngine.java
index cb71e2a4..276687f6 100644
--- a/src/org/warp/picalculator/gui/graphicengine/gpu/GPUEngine.java
+++ b/src/org/warp/picalculator/gui/graphicengine/gpu/GPUEngine.java
@@ -49,7 +49,7 @@ public class GPUEngine implements org.warp.picalculator.gui.graphicengine.Graphi
public void setDisplayMode(int ww, int wh) {
this.size[0] = ww;
this.size[1] = wh;
- wnd.window.setSize(ww, wh);
+ wnd.window.setSize(Utils.debugOn?ww*2:ww, Utils.debugOn?wh*2:wh);
}
@Override
diff --git a/src/org/warp/picalculator/gui/graphicengine/gpu/GPURenderer.java b/src/org/warp/picalculator/gui/graphicengine/gpu/GPURenderer.java
index da347e7b..2f5e23dc 100644
--- a/src/org/warp/picalculator/gui/graphicengine/gpu/GPURenderer.java
+++ b/src/org/warp/picalculator/gui/graphicengine/gpu/GPURenderer.java
@@ -24,7 +24,7 @@ import com.jogamp.opengl.util.texture.TextureIO;
public class GPURenderer implements Renderer {
- public GL2ES1 gl;
+ public static GL2ES1 gl;
private final DeallocationHelper deallocationHelper = new DeallocationHelper();
FloatBuffer fbVertices;
@@ -192,10 +192,10 @@ public class GPURenderer implements Renderer {
final FileInputStream f = new FileInputStream("test.png");
final TextureData tx_dat = TextureIO.newTextureData(gl.getGLProfile(), f, false, TextureIO.PNG);
final Texture tex = new Texture(gl, tx_dat);
- tex.setTexParameteri(gl, GL.GL_TEXTURE_MIN_FILTER, GL.GL_LINEAR);
+ tex.setTexParameteri(gl, GL.GL_TEXTURE_MIN_FILTER, GL.GL_NEAREST);
tex.setTexParameteri(gl, GL.GL_TEXTURE_MAG_FILTER, GL.GL_NEAREST);
- tex.setTexParameteri(gl, GL.GL_TEXTURE_WRAP_S, GL.GL_CLAMP_TO_EDGE);
- tex.setTexParameteri(gl, GL.GL_TEXTURE_WRAP_T, GL.GL_CLAMP_TO_EDGE);
+// tex.setTexParameteri(gl, GL.GL_TEXTURE_WRAP_S, GL.GL_CLAMP_TO_EDGE);
+// tex.setTexParameteri(gl, GL.GL_TEXTURE_WRAP_T, GL.GL_CLAMP_TO_EDGE);
return tex;
}
@@ -208,7 +208,10 @@ public class GPURenderer implements Renderer {
final ByteArrayOutputStream os = new ByteArrayOutputStream();
ImageIO.write(img, "png", os);
final InputStream fis = new ByteArrayInputStream(os.toByteArray());
- return TextureIO.newTexture(fis, false, TextureIO.PNG);
+ Texture tex = TextureIO.newTexture(fis, false, TextureIO.PNG);
+ tex.setTexParameteri(gl, GL.GL_TEXTURE_MIN_FILTER, GL.GL_NEAREST);
+ tex.setTexParameteri(gl, GL.GL_TEXTURE_MAG_FILTER, GL.GL_NEAREST);
+ return tex;
}
@Override
diff --git a/src/org/warp/picalculator/gui/graphicengine/gpu/NEWTWindow.java b/src/org/warp/picalculator/gui/graphicengine/gpu/NEWTWindow.java
index 56d22152..663a6efc 100644
--- a/src/org/warp/picalculator/gui/graphicengine/gpu/NEWTWindow.java
+++ b/src/org/warp/picalculator/gui/graphicengine/gpu/NEWTWindow.java
@@ -54,6 +54,7 @@ import java.awt.event.ComponentListener;
import java.nio.ByteBuffer;
import java.util.Collection;
+import org.warp.picalculator.Utils;
import org.warp.picalculator.device.Keyboard;
import org.warp.picalculator.device.Keyboard.Key;
import org.warp.picalculator.gui.DisplayManager;
@@ -278,7 +279,7 @@ class NEWTWindow implements GLEventListener {
//Transparency
gl.glEnable(GL2ES1.GL_BLEND);
gl.glBlendFunc(GL2ES1.GL_SRC_ALPHA, GL2ES1.GL_ONE_MINUS_SRC_ALPHA);
- gl.glShadeModel(GL2ES1.GL_SMOOTH);
+ gl.glShadeModel(GL2ES1.GL_FLAT);
try {
renderer.currentTex = ((GPUSkin) disp.loadSkin("test.png")).t;
@@ -295,8 +296,8 @@ class NEWTWindow implements GLEventListener {
@Override
public void reshape(GLAutoDrawable glad, int x, int y, int width, int height) {
- disp.size[0] = width;
- disp.size[1] = height;
+ disp.size[0] = Utils.debugOn?width/2:width;
+ disp.size[1] = Utils.debugOn?height/2:height;
final GL2ES1 gl = glad.getGL().getGL2ES1();
float max_wh, min_wh;
if (width == 0) {
@@ -318,7 +319,7 @@ class NEWTWindow implements GLEventListener {
gl.glMatrixMode(GLMatrixFunc.GL_PROJECTION);
gl.glLoadIdentity();
- gl.glOrtho(0.0, width, height, 0.0, -1, 1);
+ gl.glOrtho(0.0, Utils.debugOn?width/2:width, Utils.debugOn?height/2:height, 0.0, -1, 1);
gl.glMatrixMode(GLMatrixFunc.GL_MODELVIEW);
gl.glLoadIdentity();
diff --git a/src/org/warp/picalculator/gui/screens/MathInputScreen.java b/src/org/warp/picalculator/gui/screens/MathInputScreen.java
index ba0b652a..995950ea 100644
--- a/src/org/warp/picalculator/gui/screens/MathInputScreen.java
+++ b/src/org/warp/picalculator/gui/screens/MathInputScreen.java
@@ -1,5 +1,6 @@
package org.warp.picalculator.gui.screens;
+import java.io.IOException;
import java.io.PrintWriter;
import java.io.StringWriter;
import it.unimi.dsi.fastutil.objects.ObjectArrayList;
@@ -16,6 +17,11 @@ import org.warp.picalculator.Utils;
import org.warp.picalculator.device.Keyboard;
import org.warp.picalculator.device.Keyboard.Key;
import org.warp.picalculator.gui.DisplayManager;
+import org.warp.picalculator.gui.expression.BlockContainer;
+import org.warp.picalculator.gui.expression.containers.InputContainer;
+import org.warp.picalculator.gui.expression.containers.NormalInputContainer;
+import org.warp.picalculator.gui.expression.containers.NormalOutputContainer;
+import org.warp.picalculator.gui.expression.containers.OutputContainer;
import org.warp.picalculator.gui.graphicengine.BinaryFont;
import org.warp.picalculator.gui.graphicengine.Renderer;
import org.warp.picalculator.math.AngleMode;
@@ -32,114 +38,50 @@ import org.warp.picalculator.math.functions.Number;
public class MathInputScreen extends Screen {
- public volatile String currentExpression = "";
- public volatile String newExpression = "";
- public volatile int caretPos = 0;
- public volatile boolean showCaret = true;
- public volatile float showCaretDelta = 0f;
public MathContext calc;
- public boolean autoscroll;
- public int scrollX = 0;
+ public InputContainer userInput;
+ public OutputContainer result;
public int errorLevel = 0; // 0 = nessuno, 1 = risultato, 2 = tutto
boolean mustRefresh = true;
- boolean firstStep = true;
public MathInputScreen() {
super();
canBeInHistory = true;
-
- calc = new MathContext();
}
@Override
public void created() throws InterruptedException {
-
+ calc = new MathContext();
+
+ try {
+ BlockContainer.initializeFonts(DisplayManager.engine.loadFont("ex"), DisplayManager.engine.loadFont("big"));
+ } catch (IOException e) {
+ e.printStackTrace();
+ System.exit(1);
+ }
+
+ userInput = new NormalInputContainer();
+ result = new NormalOutputContainer();
+
+ calc.init();
}
@Override
public void init() throws InterruptedException {
/* Fine caricamento */
-
- // Parentesi f = new
- // Parentesi("(Ⓐ(2X)*3Y)/(5Z^2)+(Ⓐ(11A)*13B)/(7CZ)=19XZ");
- // PARENTESI CON CALCOLI
- // Funzione f = new Sottrazione(new Somma(new Parentesi("Ⓐ9/2+Ⓐ7/2",
- // "").calcola(), new Termine("3.5")), new
- // Parentesi("3*2√14","").calcola());
- // PARENTESI CON DUE NUMERI FRAZIONALI COMPLETI CON INCOGNITE:
- // Funzione f = new
- // Parentesi("(Ⓐ(2X)*3Y)/(5Z^2)+(Ⓐ(11A)*13B)/(7CZ)", "");
- // PARENTESI CON DUE NUMERI FRAZIONALI DISALLINEATI GRAFICAMENTE:
- // Funzione f = new Parentesi("((5^2-1)/2)/5-5/(5/2)=2", "");
- // TERMINE DI PROVA COMPLETO:
- // Funzione f = new Termine(new NumeroAvanzato(new Rational(3, 2),
- // new Rational(7, 1), new Incognite(new Incognita('X',
- // Rational.ONE)), new Incognite(new Incognita('Y', Rational.ONE)),
- // new Incognite(new Incognita('z', Rational.ONE))));
- // PARENTESI REALISTICA CON INCOGNITE:
- // Funzione f = new Equazione(new
- // Parentesi("X^2+(MX-M+4)^2-4X-4(MX-M+4)^2+7", ""), new
- // Termine("0"));
- // POTENZA:
- // Funzione f = new Parentesi("(MX-M+4)^2", "");
- // NUMERO SEMPLICE LUNGO:
- // Funzione f = new Parentesi("-1219999799999996934.42229", "");
- // :
- // Funzione f = new Parentesi("5Y+XY=2", "")
-
-// calcola("((5^2+3√(100/0.1))+Ⓐ(7)+9/15*2√(26/2))/21");
- calc.init();
-// interpreta("{(5X*(15X/3X))+(25X/(5X*(15X/3X)))=15{X=5"); //TODO RIMUOVERE
-
- // long start = System.nanoTime();
- // Termine result =
- // Calculator.calcolarisultato("((5Ⓑ2+3√(100/0.1))*Ⓐ7+9/15*2√(26/2))/21");
- // long end = System.nanoTime();
- // long timeElapsed = end-start;
- // System.out.println("RESULT: " + result);
- // System.out.println("DECIMAl RESULT: " +
- // result.getTerm().toBigDecimal());
- // System.out.println("Time elapsed: " + (double) timeElapsed /
- // 1000000 + " milliseconds\n");
- //
- //
- // start = System.nanoTime();
- // RisultatoEquazione eresult =
- // Calculator.calcolaequazione("((5Ⓑ2+3√(100/0.1))*Ⓐ7+9/15*2√(26/2))/21=(175*(2√7)+3*(2√13))/105");
- // end = System.nanoTime();
- // timeElapsed = end-start;
- // System.out.println("Is an equation: " + eresult.isAnEquation);
- // System.out.println("L-R: " + eresult.LR);
- // System.out.println("Time elapsed: " + (double) timeElapsed /
- // 1000000 + " milliseconds\n");
}
-
- public void interpreta(boolean temporary) throws Error {
- final String eqn = newExpression;
- if (!temporary) {
- currentExpression = eqn;
- }
-
- calc.parseInputString(eqn);
- }
-
+
@Override
public void beforeRender(float dt) {
- showCaretDelta += dt;
- if (showCaretDelta >= 0.5f) {
- mustRefresh = true;
- showCaret = !showCaret;
- showCaretDelta = 0f;
- }
- if (caretPos > newExpression.length()) {
- caretPos = newExpression.length();
- }
if (DisplayManager.error == null) {
DisplayManager.renderer.glClearColor(0xFFc5c2af);
} else {
DisplayManager.renderer.glClearColor(0xFFDC3C32);
}
+ if (userInput.beforeRender(dt)) {
+ mustRefresh = true;
+ }
}
private static final BinaryFont fontBig = Utils.getFont(false);
@@ -165,71 +107,11 @@ public class MathInputScreen extends Screen {
final int textColor = 0xFF000000;
final int padding = 4;
DisplayManager.renderer.glColor(textColor);
- final int caretRealPos = MathematicalSymbols.getGraphicRepresentation(newExpression.substring(0, caretPos)).length() * (fontBig.getCharacterWidth() + 1);
- final String inputTextWithoutCaret = MathematicalSymbols.getGraphicRepresentation(newExpression);
- final boolean tooLongI = padding + fontBig.getStringWidth(newExpression) + padding >= Main.screenSize[0];
- int scrollI = 0;
- if (tooLongI) {
- scrollI = -scrollX;
- if (-scrollI >= Main.screenSize[0]) {
- scrollI += Main.screenSize[0];
- } else {
- scrollI = 0;
- }
- }
- DisplayManager.renderer.glDrawStringLeft(padding + scrollI, padding + 20, inputTextWithoutCaret);
- if (showCaret) {
- DisplayManager.renderer.glDrawStringLeft(padding + scrollI + caretRealPos, padding + 20, "|");
- }
- if (tooLongI) {
- DisplayManager.renderer.glColor(DisplayManager.renderer.glGetClearColor());
- DisplayManager.renderer.glFillColor(Main.screenSize[0] - 16 - 2, padding + 20, fontBig.getCharacterHeight(), Main.screenSize[0]);
- DisplayManager.renderer.glColor(textColor);
- DisplayManager.drawSkinPart(Main.screenSize[0] - 16, padding + 20 + fontBig.getCharacterHeight() / 2 - 16 / 2, 304, 0, 304 + 16, 16);
- }
- if (calc.f != null) {
- int topSpacing = 0;
- final Iterator iter = calc.f.iterator();
- while (iter.hasNext()) {
- final Function fnc = iter.next();
- try {
- final boolean tooLong = padding + fnc.getWidth() + padding >= Main.screenSize[0];
- int scrollA = 0;
- if (tooLong) {
- scrollA = -scrollX;
- if (-scrollA >= Main.screenSize[0]) {
- scrollA += Main.screenSize[0];
- } else {
- scrollA = 0;
- }
- }
- final int y = padding + 20 + padding + fontBig.getCharacterHeight() + 1 + topSpacing;
- fnc.draw(padding + scrollA, y, null, null);
- if (tooLong) {
- DisplayManager.renderer.glColor(DisplayManager.renderer.glGetClearColor());
- DisplayManager.renderer.glFillColor(Main.screenSize[0] - 16 - 2, y, fnc.getHeight(), Main.screenSize[0]);
- DisplayManager.renderer.glColor(textColor);
- DisplayManager.drawSkinPart(Main.screenSize[0] - 16, y + fnc.getHeight() / 2 - 16 / 2, 304, 0, 304 + 16, 16);
- }
- } catch (final NullPointerException e) {
- iter.remove();
- }
- topSpacing += fnc.getHeight() + 2;
- }
- }
- if (calc.f2 != null) {
- int bottomSpacing = 0;
- for (final Function f : calc.f2) {
- bottomSpacing += f.getHeight() + 2;
- f.draw(DisplayManager.engine.getWidth() - 2 - f.getWidth(), DisplayManager.engine.getHeight() - bottomSpacing, null, null);
- }
- if (calc.resultsCount > 1 && calc.resultsCount != calc.f2.size()) {
- final String resultsCountText = calc.resultsCount + " total results".toUpperCase();
- DisplayManager.renderer.glColor(0xFF9AAEA0);
- Utils.getFont(true).use(DisplayManager.engine);
- bottomSpacing += fontBig.getCharacterHeight() + 2;
- DisplayManager.renderer.glDrawStringRight(DisplayManager.engine.getWidth() - 2, DisplayManager.engine.getHeight() - bottomSpacing, resultsCountText);
- }
+
+ userInput.draw(DisplayManager.engine, DisplayManager.renderer, padding, padding + 20);
+
+ if (!result.root.getContent().isEmpty()) {
+ result.draw(DisplayManager.engine, DisplayManager.renderer, DisplayManager.engine.getWidth() - 2, DisplayManager.engine.getHeight() - 2);
}
}
@@ -247,141 +129,142 @@ public class MathInputScreen extends Screen {
public boolean keyPressed(Key k) {
switch (k) {
case STEP:
- if (newExpression.length() > 0) {
- if (firstStep) {
- try {
- try {
- interpreta(true);
- showVariablesDialog(() -> {
- currentExpression = newExpression;
- calc.f2 = calc.f;
- firstStep = false;
- step();
- });
- } catch (final Exception ex) {
- if (Utils.debugOn) {
- ex.printStackTrace();
- }
- throw new Error(Errors.SYNTAX_ERROR);
- }
- } catch (final Error e) {
- final StringWriter sw = new StringWriter();
- final PrintWriter pw = new PrintWriter(sw);
- e.printStackTrace(pw);
- d.errorStackTrace = sw.toString().toUpperCase().replace("\t", " ").replace("\r", "").split("\n");
- DisplayManager.error = e.id.toString();
- System.err.println(e.id);
- }
- } else {
- step();
- }
- }
- return true;
+// if (newExpression.length() > 0) {
+// if (firstStep) {
+// try {
+// try {
+// interpreta(true);
+// showVariablesDialog(() -> {
+// currentExpression = newExpression;
+// calc.f2 = calc.f;
+// firstStep = false;
+// step();
+// });
+// } catch (final Exception ex) {
+// if (Utils.debugOn) {
+// ex.printStackTrace();
+// }
+// throw new Error(Errors.SYNTAX_ERROR);
+// }
+// } catch (final Error e) {
+// final StringWriter sw = new StringWriter();
+// final PrintWriter pw = new PrintWriter(sw);
+// e.printStackTrace(pw);
+// d.errorStackTrace = sw.toString().toUpperCase().replace("\t", " ").replace("\r", "").split("\n");
+// DisplayManager.error = e.id.toString();
+// System.err.println(e.id);
+// }
+// } else {
+// step();
+// }
+// }
+// return true;
case SIMPLIFY:
- if (DisplayManager.error != null) {
- Utils.debug.println("Resetting after error...");
- DisplayManager.error = null;
- currentExpression = null;
- calc.f = null;
- calc.f2 = null;
- calc.resultsCount = 0;
- return true;
- } else {
- try {
- try {
- if (!firstStep) {
- step();
- } else {
- if (newExpression != currentExpression && newExpression.length() > 0) {
- changeEquationScreen();
- interpreta(true);
- showVariablesDialog(() -> {
- currentExpression = newExpression;
- simplify();
- });
- }
- }
- } catch (final Exception ex) {
- if (Utils.debugOn) {
- ex.printStackTrace();
- }
- throw new Error(Errors.SYNTAX_ERROR);
- }
- } catch (final Error e) {
- final StringWriter sw = new StringWriter();
- final PrintWriter pw = new PrintWriter(sw);
- e.printStackTrace(pw);
- d.errorStackTrace = sw.toString().toUpperCase().replace("\t", " ").replace("\r", "").split("\n");
- DisplayManager.error = e.id.toString();
- System.err.println(e.id);
- }
- return true;
- }
+// if (DisplayManager.error != null) {
+// Utils.debug.println("Resetting after error...");
+// DisplayManager.error = null;
+// currentExpression = null;
+// calc.f = null;
+// calc.f2 = null;
+// calc.resultsCount = 0;
+// return true;
+// } else {
+// try {
+// try {
+// if (!firstStep) {
+// step();
+// } else {
+// if (newExpression != currentExpression && newExpression.length() > 0) {
+// changeEquationScreen();
+// interpreta(true);
+// showVariablesDialog(() -> {
+// currentExpression = newExpression;
+// simplify();
+// });
+// }
+// }
+// } catch (final Exception ex) {
+// if (Utils.debugOn) {
+// ex.printStackTrace();
+// }
+// throw new Error(Errors.SYNTAX_ERROR);
+// }
+// } catch (final Error e) {
+// final StringWriter sw = new StringWriter();
+// final PrintWriter pw = new PrintWriter(sw);
+// e.printStackTrace(pw);
+// d.errorStackTrace = sw.toString().toUpperCase().replace("\t", " ").replace("\r", "").split("\n");
+// DisplayManager.error = e.id.toString();
+// System.err.println(e.id);
+// }
+// return true;
+// }
+ return true;
case NUM0:
- typeChar("0");
+ typeChar('0');
return true;
case NUM1:
- typeChar("1");
+ typeChar('1');
return true;
case NUM2:
- typeChar("2");
+ typeChar('2');
return true;
case NUM3:
- typeChar("3");
+ typeChar('3');
return true;
case NUM4:
- typeChar("4");
+ typeChar('4');
return true;
case NUM5:
- typeChar("5");
+ typeChar('5');
return true;
case NUM6:
- typeChar("6");
+ typeChar('6');
return true;
case NUM7:
- typeChar("7");
+ typeChar('7');
return true;
case NUM8:
- typeChar("8");
+ typeChar('8');
return true;
case NUM9:
- typeChar("9");
+ typeChar('9');
return true;
case PLUS:
- typeChar("+");
+ typeChar('+');
return true;
case MINUS:
- typeChar("-");
+ typeChar('-');
return true;
case PLUS_MINUS:
- typeChar("±");
+ typeChar('±');
return true;
case MULTIPLY:
- typeChar("*");
+ typeChar('*');
return true;
case DIVIDE:
- typeChar("/");
+ typeChar('/');
return true;
case PARENTHESIS_OPEN:
- typeChar("(");
+ typeChar('(');
return true;
case PARENTHESIS_CLOSE:
- typeChar(")");
+ typeChar(')');
return true;
case DOT:
- typeChar(".");
+ typeChar('.');
return true;
case EQUAL:
- typeChar("=");
+ typeChar('=');
return true;
case SQRT:
- typeChar("Ⓐ");
+ typeChar('Ⓐ');
return true;
case ROOT:
- typeChar("√");
+ typeChar('√');
return true;
case POWER_OF_2:
- typeChar(MathematicalSymbols.POWER + "2");
+ typeChar(MathematicalSymbols.POWER_OF_TWO);
return true;
case POWER_OF_x:
typeChar(MathematicalSymbols.POWER);
@@ -390,10 +273,10 @@ public class MathInputScreen extends Screen {
typeChar(MathematicalSymbols.PI);
return true;
case LETTER_X:
- typeChar(MathematicalSymbols.variables()[23]);
+ typeChar(MathematicalSymbols.variables[23]);
return true;
case LETTER_Y:
- typeChar(MathematicalSymbols.variables()[24]);
+ typeChar(MathematicalSymbols.variables[24]);
return true;
case SINE:
typeChar(MathematicalSymbols.SINE);
@@ -414,84 +297,56 @@ public class MathInputScreen extends Screen {
typeChar(MathematicalSymbols.ARC_TANGENT);
return true;
case DELETE:
- if (newExpression.length() > 0) {
- if (caretPos > 0) {
- caretPos -= 1;
- newExpression = newExpression.substring(0, caretPos) + newExpression.substring(caretPos + 1, newExpression.length());
- } else {
- newExpression = newExpression.substring(1);
- }
- try {
- interpreta(true);
- } catch (final Error e) {}
- }
- firstStep = true;
+ userInput.del();
+ mustRefresh = true;
return true;
case LEFT:
- if (caretPos > 0) {
- caretPos -= 1;
- } else {
- caretPos = newExpression.length();
- }
- scrollX = fontBig.getStringWidth(newExpression.substring(0, caretPos) + "|||");
- showCaret = true;
- showCaretDelta = 0L;
+ userInput.moveLeft();
+ mustRefresh = true;
return true;
case RIGHT:
- if (caretPos < newExpression.length()) {
- caretPos += 1;
- } else {
- caretPos = 0;
- }
- scrollX = fontBig.getStringWidth(newExpression.substring(0, caretPos) + "|||");
- showCaret = true;
- showCaretDelta = 0L;
+ userInput.moveRight();
+ mustRefresh = true;
return true;
case RESET:
+ userInput.clear();
+ result.clear();
if (DisplayManager.error != null) {
Utils.debug.println("Resetting after error...");
DisplayManager.error = null;
- return true;
- } else {
- caretPos = 0;
- newExpression = "";
- firstStep = false;
- if (calc.f != null) {
- calc.f = new ObjectArrayList<>();
- }
- return true;
}
+ return true;
case SURD_MODE:
- calc.exactMode = !calc.exactMode;
- if (calc.exactMode == false) {
- calc.f2 = solveExpression(calc.f2);
- } else {
- currentExpression = "";
- Keyboard.keyPressed(Key.SIMPLIFY);
- }
+// calc.exactMode = !calc.exactMode;
+// if (calc.exactMode == false) {
+// calc.f2 = solveExpression(calc.f2);
+// } else {
+// currentExpression = "";
+// Keyboard.keyPressed(Key.SIMPLIFY);
+// }
return true;
case debug1:
DisplayManager.INSTANCE.setScreen(new EmptyScreen());
return true;
case HISTORY_BACK:
- if (DisplayManager.INSTANCE.canGoBack()) {
- if (currentExpression != null && currentExpression.length() > 0 & DisplayManager.sessions[DisplayManager.currentSession + 1] instanceof MathInputScreen) {
- newExpression = currentExpression;
- try {
- interpreta(true);
- } catch (final Error e) {}
- }
- }
+// if (DisplayManager.INSTANCE.canGoBack()) {
+// if (currentExpression != null && currentExpression.length() > 0 & DisplayManager.sessions[DisplayManager.currentSession + 1] instanceof MathInputScreen) {
+// newExpression = currentExpression;
+// try {
+// interpreta(true);
+// } catch (final Error e) {}
+// }
+// }
return false;
case HISTORY_FORWARD:
- if (DisplayManager.INSTANCE.canGoForward()) {
- if (currentExpression != null && currentExpression.length() > 0 & DisplayManager.sessions[DisplayManager.currentSession - 1] instanceof MathInputScreen) {
- newExpression = currentExpression;
- try {
- interpreta(true);
- } catch (final Error e) {}
- }
- }
+// if (DisplayManager.INSTANCE.canGoForward()) {
+// if (currentExpression != null && currentExpression.length() > 0 & DisplayManager.sessions[DisplayManager.currentSession - 1] instanceof MathInputScreen) {
+// newExpression = currentExpression;
+// try {
+// interpreta(true);
+// } catch (final Error e) {}
+// }
+// }
return false;
case debug_DEG:
if (calc.angleMode.equals(AngleMode.DEG) == false) {
@@ -660,20 +515,11 @@ public class MathInputScreen extends Screen {
}
}
- public void typeChar(String chr) {
- final int len = chr.length();
- newExpression = newExpression.substring(0, caretPos) + chr + newExpression.substring(caretPos, newExpression.length());
- caretPos += len;
- scrollX = fontBig.getStringWidth(newExpression.substring(0, caretPos) + "|||");
- showCaret = true;
- showCaretDelta = 0L;
- firstStep = true;
- try {
- interpreta(true);
- } catch (final Error e) {}
-// f.clear(); //TODO: I removed this line to prevent input blanking when pressing EQUALS button and cloning this screen, but I must see why I created this part of code.
+ public void typeChar(char chr) {
+ userInput.typeChar(chr);
+ mustRefresh = true;
}
-
+
@Override
public boolean keyReleased(Key k) {
return false;
@@ -751,21 +597,11 @@ public class MathInputScreen extends Screen {
public MathInputScreen clone() {
final MathInputScreen es = this;
final MathInputScreen es2 = new MathInputScreen();
- es2.scrollX = es.scrollX;
- es2.newExpression = es.newExpression;
- es2.currentExpression = es.currentExpression;
- es2.showCaret = es.showCaret;
- es2.showCaretDelta = es.showCaretDelta;
- es2.caretPos = es.caretPos;
-// es2.calc.f = Utils.cloner.deepClone(es.calc.f);
-// es2.calc.f2 = Utils.cloner.deepClone(es.calc.f2);
-// es2.calc.resultsCount = es.calc.resultsCount;
- es2.autoscroll = es.autoscroll;
es2.errorLevel = es.errorLevel;
es2.mustRefresh = es.mustRefresh;
- es2.firstStep = es.firstStep;
-// es2.calc.variablesValues = Utils.cloner.deepClone(es.calc.variablesValues);
es2.calc = Utils.cloner.deepClone(es.calc);
+ es2.userInput = Utils.cloner.deepClone(es.userInput);
+ es2.result = Utils.cloner.deepClone(es.result);
return es2;
}
diff --git a/src/org/warp/picalculator/math/MathContext.java b/src/org/warp/picalculator/math/MathContext.java
index b3644c7f..ac8da5e2 100644
--- a/src/org/warp/picalculator/math/MathContext.java
+++ b/src/org/warp/picalculator/math/MathContext.java
@@ -102,18 +102,6 @@ public class MathContext {
}
}
- public void parseInputString(String eqn) throws Error {
- final ObjectArrayList fncs = new ObjectArrayList<>();
- if (eqn.length() > 0) {
- try {
- fncs.add(parseString(eqn.replace("sqrt", MathematicalSymbols.SQUARE_ROOT).replace("^", MathematicalSymbols.POWER)));
- } catch (final Exception ex) {
-
- }
- }
- f = fncs;
- }
-
/*public void solve(EquationScreen equationScreen, char letter) throws Error {
if (Calculator.currentSession == 0 && Calculator.sessions[0] instanceof EquationScreen) {
EquationScreen es = (EquationScreen) Calculator.sessions[0];
diff --git a/src/org/warp/picalculator/math/MathematicalSymbols.java b/src/org/warp/picalculator/math/MathematicalSymbols.java
index 61ead678..21c768fb 100644
--- a/src/org/warp/picalculator/math/MathematicalSymbols.java
+++ b/src/org/warp/picalculator/math/MathematicalSymbols.java
@@ -16,6 +16,7 @@ public class MathematicalSymbols {
public static final char PARENTHESIS_OPEN = '(';
public static final char PARENTHESIS_CLOSE = ')';
public static final char POWER = 'Ⓑ';
+ public static final char POWER_OF_TWO = 'Ⓘ';
public static final char EQUATION = '=';
public static final char SYSTEM = '{';
public static final char SINE = 'Ⓒ';
@@ -29,7 +30,7 @@ public class MathematicalSymbols {
public static final char[] functionsNSN = new char[] { NTH_ROOT, POWER };
- public static final char[] functionsSN = new char[] { SQUARE_ROOT, MINUS, SINE, COSINE, TANGENT, ARC_SINE, ARC_COSINE, ARC_TANGENT };
+ public static final char[] functionsSN = new char[] { SQUARE_ROOT, POWER_OF_TWO, MINUS, SINE, COSINE, TANGENT, ARC_SINE, ARC_COSINE, ARC_TANGENT };
public static final char[] functions = concat(functionsNSN, functionsSN);
diff --git a/src/org/warp/picalculator/math/functions/Division.java b/src/org/warp/picalculator/math/functions/Division.java
index f0b44106..2458c3d8 100644
--- a/src/org/warp/picalculator/math/functions/Division.java
+++ b/src/org/warp/picalculator/math/functions/Division.java
@@ -96,4 +96,9 @@ public class Division extends FunctionOperator {
public FunctionOperator clone() {
return new Division(this.getMathContext(), this.getParameter1(), this.getParameter2());
}
+
+ @Override
+ public String toString() {
+ return "("+this.getParameter1()+")/("+this.getParameter2()+")";
+ }
}
\ No newline at end of file
diff --git a/src/org/warp/picalculator/math/functions/Multiplication.java b/src/org/warp/picalculator/math/functions/Multiplication.java
index 283f89d6..fc572f2b 100644
--- a/src/org/warp/picalculator/math/functions/Multiplication.java
+++ b/src/org/warp/picalculator/math/functions/Multiplication.java
@@ -106,10 +106,6 @@ public class Multiplication extends FunctionOperator {
@Override
public String toString() {
- if (parameter1 != null && parameter2 != null) {
- return parameter1.toString()+"*"+parameter2.toString();
- } else {
- return super.toString();
- }
+ return "("+parameter1.toString()+")*("+parameter2.toString()+")";
}
}
\ No newline at end of file
diff --git a/src/org/warp/picalculator/math/parser/InputParser.java b/src/org/warp/picalculator/math/parser/MathParser.java
similarity index 85%
rename from src/org/warp/picalculator/math/parser/InputParser.java
rename to src/org/warp/picalculator/math/parser/MathParser.java
index b536e865..3a25e814 100644
--- a/src/org/warp/picalculator/math/parser/InputParser.java
+++ b/src/org/warp/picalculator/math/parser/MathParser.java
@@ -7,6 +7,7 @@ import org.warp.picalculator.gui.expression.BlockChar;
import org.warp.picalculator.gui.expression.BlockContainer;
import org.warp.picalculator.gui.expression.BlockDivision;
import org.warp.picalculator.math.Function;
+import org.warp.picalculator.math.FunctionOperator;
import org.warp.picalculator.math.FunctionSingle;
import org.warp.picalculator.math.MathContext;
import org.warp.picalculator.math.MathematicalSymbols;
@@ -30,7 +31,7 @@ import com.sun.org.apache.xpath.internal.functions.Function2Args;
import it.unimi.dsi.fastutil.objects.ObjectArrayList;
import it.unimi.dsi.fastutil.objects.ObjectListIterator;
-public class InputParser {
+public class MathParser {
public static Expression parseInput(MathContext context, BlockContainer root) throws Error {
Expression result;
@@ -57,15 +58,19 @@ public class InputParser {
Feature result;
- if (block instanceof BlockChar) {
- result = new FeatureChar(((BlockChar) block).getChar());
- } else if (block instanceof BlockDivision) {
- BlockDivision bd = (BlockDivision) block;
- Function upper = parseContainer(context, bd.getUpperContainer());
- Function lower = parseContainer(context, bd.getLowerContainer());
- result = new FeatureDivision(upper, lower);
- } else {
- throw new Error(Errors.SYNTAX_ERROR);
+ int blockType = block.getClassID();
+ switch (blockType) {
+ case BlockChar.CLASS_ID:
+ result = new FeatureChar(((BlockChar) block).getChar());
+ break;
+ case BlockDivision.CLASS_ID:
+ BlockDivision bd = (BlockDivision) block;
+ Function upper = parseContainer(context, bd.getUpperContainer());
+ Function lower = parseContainer(context, bd.getLowerContainer());
+ result = new FeatureDivision(upper, lower);
+ break;
+ default:
+ throw new Error(Errors.SYNTAX_ERROR);
}
return result;
@@ -108,17 +113,31 @@ public class InputParser {
}
//Phase 2
- stackIterator = process.iterator();
+ stackIterator = process.listIterator();
while (stackIterator.hasNext()) {
Function f = stackIterator.next();
+ final int curIndex = stackIterator.previousIndex();
if (f instanceof Multiplication || f instanceof Division) {
-
+ if (curIndex-1>=0 && stackIterator.hasNext()) {
+ Function next = process.get(curIndex+1);
+ Function prev = process.get(curIndex-1);
+ stackIterator.set(
+ f.setParameter(0, prev)
+ .setParameter(1, next)
+ );
+ process.remove(curIndex+1);
+ process.remove(curIndex-1);
+ } else {
+ if (f.getParameter(0) == null || f.getParameter(1) == null) {
+ throw new Error(Errors.MISSING_ARGUMENTS, "There is a function at the end without any argument specified.");
+ }
+ }
}
}
//Phase 3
- stackIterator = process.iterator();
+ stackIterator = process.listIterator();
while (stackIterator.hasNext()) {
Function f = stackIterator.next();