feat: add root command and fix calc-02 exponent shortcuts

This commit is contained in:
2026-05-15 23:05:43 +02:00
parent cb45efff43
commit b45cfe8091
4 changed files with 16 additions and 6 deletions
+2
View File
@@ -4,3 +4,5 @@
- Read `.memory/state.md` for current state. - Read `.memory/state.md` for current state.
- Keep names and commands in English. - Keep names and commands in English.
- Update memory files based on events: engine, demo, API, commands, exports, docs, or tasks. - Update memory files based on events: engine, demo, API, commands, exports, docs, or tasks.
- Core arithmetic now includes `root` for y-th roots, and `samples/calc-02/` uses it for `y√x`.
- `samples/calc-02/` in portrait mode remains the active responsive demo.
+2 -2
View File
@@ -1,9 +1,9 @@
# State # State
- Core engine: `src/rpn-calculator.js` - Core engine: `src/rpn-calculator.js`
- Active demo: `samples/calc-02/` responsive HP48GX layout with HP48-like X-line editing; display-adjacent button row stays in 4 columns - Active demo: `samples/calc-02/` responsive HP48GX layout with portrait/landscape support; display-adjacent button row stays in 4 columns
- Mode button shows the current angle mode only; selecting a mode uses a popup menu - Mode button shows the current angle mode only; selecting a mode uses a popup menu
- Public API: `push`, `pop`, `clear`, `swap`, `remove`, `edit`, `isValidIndex`, `input`, `command`, `getOperationsByCategory`, `getConstants` - Public API: `push`, `pop`, `clear`, `swap`, `remove`, `edit`, `isValidIndex`, `input`, `command`, `getOperationsByCategory`, `getConstants`
- Config: `maxSize`, `base`, `angleMode`, `enabledCommands` - Config: `maxSize`, `base`, `angleMode`, `enabledCommands`
- Commands: arithmetic, stack, trigonometry, constants `pi` and `e` - Commands: arithmetic, stack, trigonometry, constants `pi` and `e`; arithmetic now includes `root` for y-th roots
- Demo actions: keyboard focus is kept on the hidden input on desktop so typing keeps working; the keypad layout places Enter in the bottom-left, ± in the former Enter position, and Esc before Clear for safety; paste parses clipboard text as a number before pushing it to the stack; Ctrl+V is supported via the hidden input paste event; backspace is ignored when the stack is empty; operation errors are shown as an overlay bar on top of the calculator with a shorter timeout and darker red - Demo actions: keyboard focus is kept on the hidden input on desktop so typing keeps working; the keypad layout places Enter in the bottom-left, ± in the former Enter position, and Esc before Clear for safety; paste parses clipboard text as a number before pushing it to the stack; Ctrl+V is supported via the hidden input paste event; backspace is ignored when the stack is empty; operation errors are shown as an overlay bar on top of the calculator with a shorter timeout and darker red
- Exports: browser `window.RpnCalculator`, CommonJS `module.exports` - Exports: browser `window.RpnCalculator`, CommonJS `module.exports`
+6 -4
View File
@@ -7,7 +7,7 @@ A browser-friendly RPN calculator built around a small, generic JavaScript API.
This project provides: This project provides:
- a reusable JavaScript RPN engine in `src/rpn-calculator.js` - a reusable JavaScript RPN engine in `src/rpn-calculator.js`
- a browser demo in `samples/dev/` - browser demos in `samples/dev/` and `samples/calc-02/`
- a command system centralized in a single operation dictionary - a command system centralized in a single operation dictionary
- a small public API focused on stack operations and generic command dispatch - a small public API focused on stack operations and generic command dispatch
@@ -24,7 +24,7 @@ The main class is `RpnCalculator`.
- `samples/calc-01/index.js`: demo UI and keyboard logic - `samples/calc-01/index.js`: demo UI and keyboard logic
- `samples/calc-02/index.html`: new responsive HP48GX-style demo entry point - `samples/calc-02/index.html`: new responsive HP48GX-style demo entry point
- `samples/calc-02/index.css`: new responsive demo styles - `samples/calc-02/index.css`: new responsive demo styles
- `samples/calc-02/index.js`: new demo UI and keyboard logic - `samples/calc-02/index.js`: responsive HP48GX-style demo UI and keyboard logic
- `samples/calc-XX/`: placeholder name for future demo variants - `samples/calc-XX/`: placeholder name for future demo variants
## Public API ## Public API
@@ -110,6 +110,7 @@ calc.command('e');
- `div` alias: `/` - `div` alias: `/`
- `mod` alias: `%` - `mod` alias: `%`
- `pow` aliases: `^`, `y^x` - `pow` aliases: `^`, `y^x`
- `root` aliases: `y√x`, `yroot`, `nroot`
- `sqr` - `sqr`
- `neg` - `neg`
- `sqrt` alias: `sqrt(x)` - `sqrt` alias: `sqrt(x)`
@@ -134,6 +135,7 @@ calc.command('e');
- `sqrt` accepts alias `sqrt(x)` - `sqrt` accepts alias `sqrt(x)`
- `recip` accepts alias `1/x` - `recip` accepts alias `1/x`
- `div` and `recip` throw `Division by zero` when needed - `div` and `recip` throw `Division by zero` when needed
- `root` computes the y-th root as `x^(1/y)` and throws `Invalid input for root` for invalid inputs
- `sqrt` throws `Invalid input for sqrt` for negative values - `sqrt` throws `Invalid input for sqrt` for negative values
- `asin` and `acos` throw explicit domain errors outside `[-1, 1]` - `asin` and `acos` throw explicit domain errors outside `[-1, 1]`
- `log` throws `Invalid input for log` for values `<= 0` - `log` throws `Invalid input for log` for values `<= 0`
@@ -270,8 +272,8 @@ It keeps the calculator screen focused and updates the visible stack window as t
## Calc 02 demo ## Calc 02 demo
`samples/calc-02/` is a new responsive HP48GX-inspired demo. `samples/calc-02/` is a responsive HP48GX-inspired demo.
It adapts its layout to the browser window and switches between the supplied portrait and landscape arrangements. It adapts its layout to the browser window, supports portrait and landscape arrangements, and includes the `y√x` root operation.
## Exports ## Exports
+6
View File
@@ -243,11 +243,17 @@ function execute(name) {
} }
} else if (name === 'pow10') { } else if (name === 'pow10') {
pushEditingValueIfNeeded(); pushEditingValueIfNeeded();
const exponent = calc.stack[0];
calc.remove(0);
calc.push(10); calc.push(10);
calc.push(exponent);
calc.command('pow'); calc.command('pow');
} else if (name === 'exp') { } else if (name === 'exp') {
pushEditingValueIfNeeded(); pushEditingValueIfNeeded();
const exponent = calc.stack[0];
calc.remove(0);
calc.push(Math.E); calc.push(Math.E);
calc.push(exponent);
calc.command('pow'); calc.command('pow');
} else { } else {
pushEditingValueIfNeeded(); pushEditingValueIfNeeded();