kalkulator/static/assets/js/calculator-logic.js

165 lines
5.1 KiB
JavaScript
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

const buttons = document.querySelectorAll('.button');
const displayText = document.querySelector('.display-text');
let currentInput = '';
let characterSpans = []; // Array to track all spans for proper positioning
let isResultDisplayed = false; // Track if the result is displayed
let resultSpan; // For showing the result
buttons.forEach(button => {
button.addEventListener('click', () => {
const value = button.textContent;
if (value === 'AC') {
resetCalculator();
} else if (value === 'H') {
toggleHistory();
} else if (value === '') {
toggleSettings();
} else if (value === '=') {
calculateResult();
} else {
if (isResultDisplayed) {
resetCalculator(); // Reset after "=" is pressed
}
if (currentInput === 'Error') currentInput = ''; // Clear on error
currentInput += value;
appendCharacter(value); // Append with animation
}
});
});
function appendCharacter(char) {
// Create new span element for the character
const newChar = document.createElement('span');
newChar.textContent = char;
displayText.appendChild(newChar);
characterSpans.push(newChar); // Add the new span to the array
// Move all characters smoothly
updateCharacterPositions();
// Animate the new character in from the right
anime({
targets: newChar,
opacity: [0, 1],
translateY: [0, -25], // Animating into place
scale: [0, 1],
duration: 500,
easing: 'easeOutExpo'
});
}
function updateCharacterPositions() {
const totalWidth = displayText.offsetWidth; // Width of the display
let currentOffset = totalWidth; // Start from the rightmost edge
// Loop through characters in reverse (so newest appears at the right)
for (let i = characterSpans.length - 1; i >= 0; i--) {
const span = characterSpans[i];
const spanWidth = span.offsetWidth; // Get the width of each character
currentOffset -= spanWidth; // Move left by the width of the character + some margin
anime({
targets: span,
right: (totalWidth - currentOffset - spanWidth) + 'px', // Keep them aligned right
duration: 300,
easing: 'easeOutQuint'
});
}
}
function calculateResult() {
const equation = characterSpans.map(span => span.textContent).join('');
let result;
try {
result = eval(equation.replace('÷', '/').replaceAll('×', '*')).toString();
} catch (error) {
result = 'Error';
}
characterSpans.forEach(span => {
span.style.fontSize = '1.5rem';
});
const totalWidth = displayText.offsetWidth; // Width of the display
let currentOffset = totalWidth; // Start from the rightmost edge
// Animate the equation upwards
// Loop through characters in reverse (so newest appears at the right)
for (let i = characterSpans.length - 1; i >= 0; i--) {
const span = characterSpans[i];
const spanWidth = span.offsetWidth; // Get the width of each character
currentOffset -= spanWidth; // Move left by the width of the character + some margin
anime({
targets: span,
translateY: -45,
opacity: [1, 0.4],
right: (totalWidth - currentOffset - spanWidth) + 'px', // Keep them aligned right
duration: 800,
easing: 'easeOutExpo'
});
}
resultSpan = document.createElement('span'); // Create a new span for the result
resultSpan.textContent = `= ${result}`;
displayText.appendChild(resultSpan);
// Animate the result to appear from below
anime({
targets: resultSpan,
opacity: [0, 1],
translateY: [50, -10], // Animating upwards
translateX: -5,
scale: [0, 1],
duration: 500,
easing: 'easeOutExpo'
});
// Set a flag to reset on the next key press
isResultDisplayed = true;
}
function toggleHistory() {
$('body').toggleClass('history-open');
if ($('body').hasClass('history-open')) { // If the history was just opened
// Animate it's elements
console.log('a')
anime({
targets: '.history-container span',
translateY: [-100, 0],
opacity: [0, 1],
duration: 400,
delay: anime.stagger(100, { start: 200, direction: 'reverse' }),
easing: 'easeOutQuart'
})
}
}
function toggleSettings() {
$('body').toggleClass('settings-open');
}
$('#history').on('click', toggleHistory);
function clearDisplay() {
// Remove all current characters (spans)
characterSpans.forEach(span => span.remove());
characterSpans = [];
}
function resetCalculator() {
currentInput = '';
characterSpans = [];
displayText.innerHTML = ''; // Clear the display
isResultDisplayed = false; // Reset the result display flag
}
function updateDisplay(value) {
// Clear existing spans and reset positions
displayText.innerHTML = '';
characterSpans = [];
[...value].forEach(char => {
appendCharacter(char); // Append each character
});
}