diff --git a/.classpath b/.classpath deleted file mode 100644 index c3ae608..0000000 --- a/.classpath +++ /dev/null @@ -1,13 +0,0 @@ - - - - - - - - - - - - - diff --git a/.gitea/workflows/build.yml b/.gitea/workflows/build.yml index 640324e..f94c223 100644 --- a/.gitea/workflows/build.yml +++ b/.gitea/workflows/build.yml @@ -12,8 +12,43 @@ jobs: steps: - uses: actions/checkout@v4 + - name: Set up JDK 20 uses: actions/setup-java@v5 with: java-version: '20' distribution: 'temurin' + + - name: Create output directories + run: | + mkdir -p out/production/Calc + mkdir -p dist + + - name: Compile Java files + run: | + javac -encoding UTF-8 -cp "lib/flatlaf-3.7.jar" -d out/production/Calc \ + $(find src/main/java -name "*.java") + + - name: Copy resources + run: | + if [ -d "src/main/resources" ]; then + cp -r src/main/resources/* out/production/Calc/ 2>/dev/null || true + fi + + - name: Create manifest + run: | + echo "Manifest-Version: 1.0" > manifest.txt + echo "Main-Class: dev.sillyangel.calc.Calculator" >> manifest.txt + echo "Class-Path: lib/flatlaf-3.7.jar" >> manifest.txt + + - name: Create JAR + run: | + cd out/production/Calc + jar cfm ../../../dist/CalcShortforCalculator.jar ../../../manifest.txt . + cd ../../.. + + - name: Upload JAR artifact + uses: actions/upload-artifact@v4 + with: + name: CalcShortforCalculator + path: dist/CalcShortforCalculator.jar diff --git a/.idea/.gitignore b/.idea/.gitignore new file mode 100644 index 0000000..ab1f416 --- /dev/null +++ b/.idea/.gitignore @@ -0,0 +1,10 @@ +# Default ignored files +/shelf/ +/workspace.xml +# Ignored default folder with query files +/queries/ +# Datasource local storage ignored files +/dataSources/ +/dataSources.local.xml +# Editor-based HTTP Client requests +/httpRequests/ diff --git a/.idea/copilot.data.migration.agent.xml b/.idea/copilot.data.migration.agent.xml new file mode 100644 index 0000000..4ea72a9 --- /dev/null +++ b/.idea/copilot.data.migration.agent.xml @@ -0,0 +1,6 @@ + + + + + \ No newline at end of file diff --git a/.idea/copilot.data.migration.ask.xml b/.idea/copilot.data.migration.ask.xml new file mode 100644 index 0000000..7ef04e2 --- /dev/null +++ b/.idea/copilot.data.migration.ask.xml @@ -0,0 +1,6 @@ + + + + + \ No newline at end of file diff --git a/.idea/copilot.data.migration.edit.xml b/.idea/copilot.data.migration.edit.xml new file mode 100644 index 0000000..8648f94 --- /dev/null +++ b/.idea/copilot.data.migration.edit.xml @@ -0,0 +1,6 @@ + + + + + \ No newline at end of file diff --git a/.idea/discord.xml b/.idea/discord.xml new file mode 100644 index 0000000..a98cb47 --- /dev/null +++ b/.idea/discord.xml @@ -0,0 +1,7 @@ + + + + + \ No newline at end of file diff --git a/.idea/libraries/lib.xml b/.idea/libraries/lib.xml new file mode 100644 index 0000000..50a7940 --- /dev/null +++ b/.idea/libraries/lib.xml @@ -0,0 +1,10 @@ + + + + + + + + + + \ No newline at end of file diff --git a/.idea/misc.xml b/.idea/misc.xml new file mode 100644 index 0000000..df223ec --- /dev/null +++ b/.idea/misc.xml @@ -0,0 +1,6 @@ + + + + + + \ No newline at end of file diff --git a/.idea/modules.xml b/.idea/modules.xml new file mode 100644 index 0000000..fcc99a6 --- /dev/null +++ b/.idea/modules.xml @@ -0,0 +1,8 @@ + + + + + + + + \ No newline at end of file diff --git a/.idea/vcs.xml b/.idea/vcs.xml new file mode 100644 index 0000000..35eb1dd --- /dev/null +++ b/.idea/vcs.xml @@ -0,0 +1,6 @@ + + + + + + \ No newline at end of file diff --git a/.project b/.project deleted file mode 100644 index e3c80f1..0000000 --- a/.project +++ /dev/null @@ -1,28 +0,0 @@ - - - CalculatorButBetter - - - - - - org.eclipse.jdt.core.javabuilder - - - - - - org.eclipse.jdt.core.javanature - - - - 1763046761202 - - 30 - - org.eclipse.core.resources.regexFilterMatcher - node_modules|\.git|__CREATED_BY_JAVA_LANGUAGE_SERVER__ - - - - \ No newline at end of file diff --git a/.settings/org.eclipse.core.resources.prefs b/.settings/org.eclipse.core.resources.prefs deleted file mode 100644 index 4824b80..0000000 --- a/.settings/org.eclipse.core.resources.prefs +++ /dev/null @@ -1,2 +0,0 @@ -eclipse.preferences.version=1 -encoding/=UTF-8 diff --git a/.settings/org.eclipse.jdt.core.prefs b/.settings/org.eclipse.jdt.core.prefs deleted file mode 100644 index 96811c2..0000000 --- a/.settings/org.eclipse.jdt.core.prefs +++ /dev/null @@ -1,12 +0,0 @@ -eclipse.preferences.version=1 -org.eclipse.jdt.core.compiler.codegen.methodParameters=do not generate -org.eclipse.jdt.core.compiler.codegen.targetPlatform=20 -org.eclipse.jdt.core.compiler.codegen.unusedLocal=preserve -org.eclipse.jdt.core.compiler.compliance=20 -org.eclipse.jdt.core.compiler.debug.lineNumber=generate -org.eclipse.jdt.core.compiler.debug.localVariable=generate -org.eclipse.jdt.core.compiler.debug.sourceFile=generate -org.eclipse.jdt.core.compiler.problem.enablePreviewFeatures=disabled -org.eclipse.jdt.core.compiler.problem.reportPreviewFeatures=warning -org.eclipse.jdt.core.compiler.release=enabled -org.eclipse.jdt.core.compiler.source=20 diff --git a/Calc.iml b/Calc.iml new file mode 100644 index 0000000..84f2e50 --- /dev/null +++ b/Calc.iml @@ -0,0 +1,15 @@ + + + + + + + + + + + + + + + \ No newline at end of file diff --git a/Screenshot 2025-11-13 122107.png b/Screenshot 2025-11-13 122107.png deleted file mode 100644 index 578e37c..0000000 Binary files a/Screenshot 2025-11-13 122107.png and /dev/null differ diff --git a/out/production/Calc/images/appIcon1024.png b/out/production/Calc/images/appIcon1024.png new file mode 100644 index 0000000..4ec4073 Binary files /dev/null and b/out/production/Calc/images/appIcon1024.png differ diff --git a/out/production/Calc/images/appIcon16.png b/out/production/Calc/images/appIcon16.png new file mode 100644 index 0000000..722b159 Binary files /dev/null and b/out/production/Calc/images/appIcon16.png differ diff --git a/out/production/Calc/images/appIcon256.png b/out/production/Calc/images/appIcon256.png new file mode 100644 index 0000000..2ee9105 Binary files /dev/null and b/out/production/Calc/images/appIcon256.png differ diff --git a/out/production/Calc/images/appIcon32.png b/out/production/Calc/images/appIcon32.png new file mode 100644 index 0000000..3be391b Binary files /dev/null and b/out/production/Calc/images/appIcon32.png differ diff --git a/out/production/Calc/images/appIcon48.png b/out/production/Calc/images/appIcon48.png new file mode 100644 index 0000000..c8ae601 Binary files /dev/null and b/out/production/Calc/images/appIcon48.png differ diff --git a/out/production/Calc/images/appIcon512.png b/out/production/Calc/images/appIcon512.png new file mode 100644 index 0000000..dfb2671 Binary files /dev/null and b/out/production/Calc/images/appIcon512.png differ diff --git a/out/production/Calc/thebesticonintheworldcreatedinphotoshop.psd b/out/production/Calc/thebesticonintheworldcreatedinphotoshop.psd new file mode 100644 index 0000000..eaf3126 Binary files /dev/null and b/out/production/Calc/thebesticonintheworldcreatedinphotoshop.psd differ diff --git a/src/main/java/dev/sillyangel/calc/Calculator.java b/src/main/java/dev/sillyangel/calc/Calculator.java index 18b9b6b..32c30a4 100644 --- a/src/main/java/dev/sillyangel/calc/Calculator.java +++ b/src/main/java/dev/sillyangel/calc/Calculator.java @@ -44,7 +44,7 @@ public class Calculator extends JFrame implements KeyListener { protected double result; private String[] CalculatorModes = new String[] {"Standard", "Scientific", "Data calculation"}; private JComboBox modeselect; - + public static void main(String[] args) { FlatMacDarkLaf.setup(); try { @@ -76,22 +76,22 @@ public class Calculator extends JFrame implements KeyListener { icons.add(Toolkit.getDefaultToolkit().getImage(Calculator.class.getResource("/images/appIcon512.png"))); icons.add(Toolkit.getDefaultToolkit().getImage(Calculator.class.getResource("/images/appIcon1024.png"))); setIconImages(icons); - + setTitle("angel's awesome calculator"); setBounds(100, 100, 368, 556); setFocusable(true); addKeyListener(this); - + contentPane = new JPanel(); contentPane.setBorder(new EmptyBorder(5, 5, 5, 5)); setContentPane(contentPane); - + display = new JTextField(); display.setEditable(false); display.setFont(new Font("Segoe UI", Font.PLAIN, 22)); display.setColumns(10); JPanel buttonPanel = new JPanel(); - + addComponentListener(new ComponentAdapter() { @Override public void componentResized(ComponentEvent e) { @@ -99,7 +99,7 @@ public class Calculator extends JFrame implements KeyListener { System.out.println("Window resized to " + size.width + "x" + size.height); } }); - + JPanel panel = new JPanel(); GroupLayout gl_contentPane = new GroupLayout(contentPane); gl_contentPane.setHorizontalGroup( @@ -119,10 +119,10 @@ public class Calculator extends JFrame implements KeyListener { .addPreferredGap(ComponentPlacement.RELATED) .addComponent(display, GroupLayout.PREFERRED_SIZE, 78, GroupLayout.PREFERRED_SIZE) .addGap(27) - .addComponent(buttonPanel, GroupLayout.PREFERRED_SIZE, 359, GroupLayout.PREFERRED_SIZE) + .addComponent(buttonPanel, GroupLayout.PREFERRED_SIZE, 359, GroupLayout.PREFERRED_SIZE) .addContainerGap(199, Short.MAX_VALUE)) ); - + buttonPanel.setLayout(new GridLayout(0, 4, 0, 0)); modeselect = new JComboBox<>(CalculatorModes); @@ -134,22 +134,26 @@ public class Calculator extends JFrame implements KeyListener { } }); modeselect.setEditable(false); - - JButton btnNewButton_1 = new JButton("New button"); - JLabel lblNewLabel = new JLabel("New label"); + modeselect.setFocusable(false); + + JButton btnNewButton_1 = new JButton("New button"); + btnNewButton_1.setFocusable(false); + JLabel lblNewLabel = new JLabel("New label"); + lblNewLabel.setFocusable(false); + - panel.add(modeselect); panel.add(lblNewLabel); panel.add(btnNewButton_1); - JButton empty_4 = new JButton(""); - JButton empty_1 = new JButton(""); - JButton empty_2 = new JButton(""); - JButton empty = new JButton(""); - JButton empty_3 = new JButton(""); - - JButton btnErase = new JButton("DEL"); + JButton btnPercent = new JButton("%"); + JButton btnClearEntry = new JButton("CE"); + JButton btnReciprocal = new JButton("1/x"); + JButton btnSquare = new JButton("x²"); + JButton btnSquareRoot = new JButton("√x"); + + // Use FlatLaf Tree.icon.collapsed as backspace-like icon (or just use text) + JButton btnBackspace = new JButton("⌫"); JButton btnClear = new JButton("C"); JButton btnPlusMin = new JButton("+/-"); JButton btnDot = new JButton("."); @@ -162,7 +166,7 @@ public class Calculator extends JFrame implements KeyListener { JButton btn4 = new JButton("4"); JButton btn5 = new JButton("5"); JButton btn6 = new JButton("6"); // why was 6 afraid of 7... because 7 8 9 :sob: - JButton btn7 = new JButton("7"); // 67! + JButton btn7 = new JButton("7"); // 67! JButton btn8 = new JButton("8"); JButton btn9 = new JButton("9"); @@ -174,9 +178,9 @@ public class Calculator extends JFrame implements KeyListener { btnDot.addActionListener(new ActionListener() { public void actionPerformed(ActionEvent e) { String n = display.getText(); // get the text on the display - if (n.contains(".")) return; // if it already contains a "." skip rest of this + if (n.contains(".")) return; // if it already contains a "." skip rest of this processDigit(e.getActionCommand()); - + } }); @@ -185,19 +189,25 @@ public class Calculator extends JFrame implements KeyListener { math(); } }); - - btnErase.addActionListener(new ActionListener() { + + btnBackspace.addActionListener(new ActionListener() { public void actionPerformed(ActionEvent e) { - clear(); + backspace(); } }); - + + btnClearEntry.addActionListener(new ActionListener() { + public void actionPerformed(ActionEvent e) { + clearEntry(); + } + }); + btnClear.addActionListener(new ActionListener() { public void actionPerformed(ActionEvent e) { - clear(); + clearAll(); } }); - + btnPlus.addActionListener(new ActionListener() { public void actionPerformed(ActionEvent e) { setOperator(e.getActionCommand()); @@ -208,8 +218,8 @@ public class Calculator extends JFrame implements KeyListener { public void actionPerformed(ActionEvent e) { setOperator(e.getActionCommand()); } - }); - + }); + btnMul.addActionListener(new ActionListener() { public void actionPerformed(ActionEvent e) { setOperator(e.getActionCommand()); @@ -245,13 +255,13 @@ public class Calculator extends JFrame implements KeyListener { processDigit(e.getActionCommand()); } }); - + btn4.addActionListener(new ActionListener() { public void actionPerformed(ActionEvent e) { processDigit(e.getActionCommand()); } }); - + btn5.addActionListener(new ActionListener() { public void actionPerformed(ActionEvent e) { processDigit(e.getActionCommand()); @@ -268,37 +278,62 @@ public class Calculator extends JFrame implements KeyListener { processDigit(e.getActionCommand()); } }); - + btn8.addActionListener(new ActionListener() { public void actionPerformed(ActionEvent e) { processDigit(e.getActionCommand()); } }); - + btn9.addActionListener(new ActionListener() { public void actionPerformed(ActionEvent e) { processDigit(e.getActionCommand()); } }); - + btnPlusMin.addActionListener(new ActionListener() { public void actionPerformed(ActionEvent e) { String tmp = display.getText(); if (tmp == null || tmp.isEmpty()) return; char first = tmp.charAt(0); if (first == '-') { - tmp = tmp.substring(1, tmp.length()); + tmp = tmp.substring(1, tmp.length()); display.setText(tmp); } else { display.setText("-" + tmp); } } }); - - - btnErase.setFont(new Font("Segoe UI", Font.PLAIN, 29)); + btnPercent.addActionListener(new ActionListener() { + public void actionPerformed(ActionEvent e) { + setOperator("%"); + } + }); + + btnReciprocal.addActionListener(new ActionListener() { + public void actionPerformed(ActionEvent e) { + reciprocal(); + } + }); + + btnSquare.addActionListener(new ActionListener() { + public void actionPerformed(ActionEvent e) { + square(); + } + }); + + btnSquareRoot.addActionListener(new ActionListener() { + public void actionPerformed(ActionEvent e) { + squareRoot(); + } + }); + + + + btnBackspace.setFont(new Font("Segoe UI", Font.PLAIN, 29)); btnClear.setFont(new Font("Segoe UI", Font.PLAIN, 29)); + btnClearEntry.setFont(new Font("Segoe UI", Font.PLAIN, 29)); btnPlusMin.setFont(new Font("Segoe UI", Font.PLAIN, 29)); btnEq.setFont(new Font("Segoe UI", Font.PLAIN, 29)); btnDot.setFont(new Font("Segoe UI", Font.PLAIN, 29)); @@ -316,20 +351,44 @@ public class Calculator extends JFrame implements KeyListener { btnMin.setFont(new Font("Segoe UI", Font.PLAIN, 29)); btnDiv.setFont(new Font("Segoe UI", Font.PLAIN, 29)); btnPlus.setFont(new Font("Segoe UI", Font.PLAIN, 29)); + btnPercent.setFont(new Font("Segoe UI", Font.PLAIN, 29)); + btnReciprocal.setFont(new Font("Segoe UI", Font.PLAIN, 29)); + btnSquare.setFont(new Font("Segoe UI", Font.PLAIN, 29)); + btnSquareRoot.setFont(new Font("Segoe UI", Font.PLAIN, 29)); - empty.setEnabled(false); - empty_1.setEnabled(false); - empty_2.setEnabled(false); - empty_3.setEnabled(false); - empty_4.setEnabled(false); + // Make all buttons non-focusable so keyboard input always goes to the frame + btnBackspace.setFocusable(false); + btnClear.setFocusable(false); + btnClearEntry.setFocusable(false); + btnPlusMin.setFocusable(false); + btnEq.setFocusable(false); + btnDot.setFocusable(false); + btn0.setFocusable(false); + btn1.setFocusable(false); + btn2.setFocusable(false); + btn3.setFocusable(false); + btn4.setFocusable(false); + btn5.setFocusable(false); + btn6.setFocusable(false); + btn7.setFocusable(false); + btn8.setFocusable(false); + btn9.setFocusable(false); + btnMul.setFocusable(false); + btnMin.setFocusable(false); + btnDiv.setFocusable(false); + btnPlus.setFocusable(false); + btnPercent.setFocusable(false); + btnReciprocal.setFocusable(false); + btnSquare.setFocusable(false); + btnSquareRoot.setFocusable(false); - buttonPanel.add(empty); - buttonPanel.add(empty_3); + buttonPanel.add(btnPercent); + buttonPanel.add(btnClearEntry); buttonPanel.add(btnClear); - buttonPanel.add(btnErase); - buttonPanel.add(empty_4); - buttonPanel.add(empty_1); - buttonPanel.add(empty_2); + buttonPanel.add(btnBackspace); + buttonPanel.add(btnReciprocal); + buttonPanel.add(btnSquare); + buttonPanel.add(btnSquareRoot); buttonPanel.add(btnDiv); buttonPanel.add(btn7); buttonPanel.add(btn8); @@ -347,7 +406,7 @@ public class Calculator extends JFrame implements KeyListener { buttonPanel.add(btn0); buttonPanel.add(btnDot); buttonPanel.add(btnEq); - + contentPane.setLayout(gl_contentPane); } @@ -362,7 +421,7 @@ public class Calculator extends JFrame implements KeyListener { } } - void clear() { + void backspace() { String tmp = display.getText(); if (tmp.length()>1) // if there is more than 1 character display.setText( tmp.substring(0, tmp.length()-1) ); @@ -370,11 +429,56 @@ public class Calculator extends JFrame implements KeyListener { display.setText(""); } + void clearEntry() { + // Clear only the current display (entry) + display.setText(""); + } + + void clearAll() { + // Clear everything including operands and operator + display.setText(""); + operand1 = ""; + operand2 = ""; + operator = ""; + resultVisible = false; + } + + void reciprocal() { + String tmp = display.getText(); + if (tmp == null || tmp.isEmpty()) return; + double value = Double.parseDouble(tmp); + if (value != 0) { + result = 1.0 / value; + display.setText("" + result); + resultVisible = true; + } + } + + void square() { + String tmp = display.getText(); + if (tmp == null || tmp.isEmpty()) return; + double value = Double.parseDouble(tmp); + result = value * value; + display.setText("" + result); + resultVisible = true; + } + + void squareRoot() { + String tmp = display.getText(); + if (tmp == null || tmp.isEmpty()) return; + double value = Double.parseDouble(tmp); + if (value >= 0) { + result = Math.sqrt(value); + display.setText("" + result); + resultVisible = true; + } + } + void processDigit(String actionCommand) { if (resultVisible == true) { display.setText(""); resultVisible = false; - } + } // if (actionCommand == "+") { // btnDiv.setForeground(new Color(0, 0, 0)); // btnMul.setForeground(new Color(0, 0, 0)); @@ -397,19 +501,19 @@ public class Calculator extends JFrame implements KeyListener { // btnMin.setForeground(new Color(30, 144, 255)); // } display.setText(display.getText() + actionCommand); - + } void setOperator(String daop) { operand1 = display.getText(); operator = daop; display.setText(""); } - + void math() { operand2 = display.getText(); double op1 = Double.parseDouble(operand1); double op2 = Double.parseDouble(operand2); - + if (operator == "+") { result = op1+op2; } else if (operator == "-") { @@ -418,25 +522,27 @@ public class Calculator extends JFrame implements KeyListener { result = op1*op2; } else if (operator == "/") { result = op1/op2; + } else if (operator == "%") { + result = op1 % op2; } else { result = op2; System.out.println("Op: " + op1); System.out.println("Op2: " + op2); } - + operator = ""; operand1 = ""; operand2 = ""; - + // btnDiv.setForeground(new Color(0, 0, 0)); // btnMul.setForeground(new Color(0, 0, 0)); // btnPlus.setForeground(new Color(0, 0, 0)); // btnMin.setForeground(new Color(0, 0, 0)); - + resultVisible = true; display.setText(""+result); } - + // Implement the keyPressed method @Override public void keyPressed(KeyEvent e) { @@ -445,14 +551,14 @@ public class Calculator extends JFrame implements KeyListener { if (KeyEvent.getKeyText(keyCode) == "Enter") { math(); } else if (e.getKeyCode() == KeyEvent.VK_BACK_SPACE) { - clear(); + backspace(); } } // Implement the keyReleased method @Override public void keyReleased(KeyEvent e) { -// int keyCode = e.getKeyCode(); +// int keyCode = e.getKeyCode(); // System.out.println("Key Released: " + KeyEvent.getKeyText(keyCode)); } @@ -477,6 +583,6 @@ public class Calculator extends JFrame implements KeyListener { if (c == '=') { math(); } - + } -} \ No newline at end of file +} diff --git a/src/main/java/flatlaf-3.7-javadoc.jar b/src/main/java/flatlaf-3.7-javadoc.jar deleted file mode 100644 index 029d6ca..0000000 Binary files a/src/main/java/flatlaf-3.7-javadoc.jar and /dev/null differ diff --git a/src/main/java/flatlaf-3.7.jar b/src/main/java/flatlaf-3.7.jar deleted file mode 100644 index 6706d56..0000000 Binary files a/src/main/java/flatlaf-3.7.jar and /dev/null differ