odin-codespace/calculator/js/script.js

206 lines
4.9 KiB
JavaScript
Raw Permalink Normal View History

let display = document.querySelector('.display');
2023-10-04 21:52:07 -04:00
const buttons = document.querySelectorAll('.btn');
2023-10-03 23:06:45 -04:00
2023-10-04 21:52:07 -04:00
const ops = {
firstNum: String(),
secondNum: String(),
operator: undefined,
2023-10-14 06:58:55 -04:00
lastOperator: undefined,
2023-10-04 21:52:07 -04:00
numFlag: false,
onSecondNumber: false,
stringLength: 8,
periodClicked: false,
2023-10-14 06:58:55 -04:00
result: String(),
2023-10-03 23:06:45 -04:00
2023-10-04 21:52:07 -04:00
toggleNumFlag: function() {
this.numFlag = !this.numFlag
},
clear: function(){
2023-10-05 23:44:22 -04:00
this.firstNum = String();
this.secondNum = String();
2023-10-04 21:52:07 -04:00
this.operator = undefined;
this.numFlag = false;
this.onSecondNumber = false;
2023-10-14 06:58:55 -04:00
this.result = String();
display.textContent = "0";
},
appendNumber: function(num) {
2023-10-12 20:54:41 -04:00
if(num === "0" && display.textContent.trim() === "0") return
if(!ops.numFlag && ops.checkLength(ops.firstNum)) {
ops.firstNum += num;
updateDisplay(ops.firstNum);
} else if(this.numFlag) {
if (this.checkLength(ops.secondNum)) {
ops.secondNum += num;
updateDisplay(ops.secondNum);
}
}
},
checkLength: function(string) {
return string.length < this.stringLength;
2023-10-04 21:52:07 -04:00
}
};
2023-10-03 14:05:11 -04:00
function add(x, y) {
2023-10-04 21:52:07 -04:00
return x + y;
2023-10-03 14:05:11 -04:00
}
function subtract(x, y) {
return x - y;
}
function multiply(x, y) {
return x * y;
}
function divede(x, y) {
2023-10-03 14:05:11 -04:00
if (x === 0) {
return 0
} else if (y === 0) {
alert("Cannot divide by 0!");
return "Error"
2023-10-03 14:05:11 -04:00
}
return x / y;
}
function operate(firstNum, secondNum, operator) {
switch (operator) {
case '+':
return add(firstNum, secondNum);
case '-':
return subtract(firstNum, secondNum);
case '*':
return multiply(firstNum, secondNum);
case '/':
return divede(firstNum, secondNum);
2023-10-03 14:05:11 -04:00
}
}
2023-10-03 23:06:45 -04:00
2023-10-05 23:44:22 -04:00
function handleOperation() {
2023-10-14 06:58:55 -04:00
const first = Number(ops.firstNum);
const second = Number(ops.secondNum);
2023-10-05 23:44:22 -04:00
let result = operate(first, second, ops.operator);
2023-10-14 06:58:55 -04:00
2023-10-12 17:32:20 -04:00
if (result === "error") {
ops.clear();
return;
}
2023-10-14 06:58:55 -04:00
2023-10-12 22:11:49 -04:00
result = roundThreeDecimals(result);
2023-10-05 23:44:22 -04:00
updateDisplay(result);
2023-10-14 06:58:55 -04:00
// store result
ops.result = result;
if (ops.lastOperator === '=') {
ops.firstNum = String();
ops.secondNum = String();
ops.numFlag = false;
2023-10-14 06:58:55 -04:00
ops.onSecondNumber = !ops.onSecondNumber;
} else {
2023-10-14 06:58:55 -04:00
ops.firstNum = ops.result;
ops.secondNum = "";
ops.onSecondNumber = true;
}
2023-10-14 06:58:55 -04:00
// ops.operator = undefined;
2023-10-05 23:44:22 -04:00
}
2023-10-03 23:06:45 -04:00
function updateDisplay(displayValue) {
display.textContent = displayValue;
2023-10-04 21:52:07 -04:00
}
2023-10-12 22:11:49 -04:00
function roundThreeDecimals(number) {
if (!Number.isInteger(number) && Number.isFinite(number)
) {
return parseFloat(number.toPrecision(3));
} else {
return number;
}
}
2023-10-05 22:24:31 -04:00
function handleOperatorClick(operatorClicked) {
2023-10-14 06:58:55 -04:00
ops.lastOperator = operatorClicked;
2023-10-05 22:24:31 -04:00
// TODO handle ops for = or clear
if (operatorClicked === 'cls') {
ops.clear();
return;
} else if (operatorClicked === '=') {
2023-10-14 06:58:55 -04:00
ops.lastOperator = '=';
handleOperation();
2023-10-14 06:58:55 -04:00
return;
2023-10-08 11:14:17 -04:00
} else if (operatorClicked === '+/-') {
negateNumber();
2023-10-14 07:29:07 -04:00
return;
2023-10-08 11:14:17 -04:00
} else if (operatorClicked === '%') {
percentageNumber();
2023-10-14 07:29:07 -04:00
return;
} else {
if(ops.secondNum && ops.numFlag){
2023-10-05 23:44:22 -04:00
handleOperation();
2023-10-14 07:29:07 -04:00
return;
2023-10-05 23:44:22 -04:00
}
2023-10-05 22:24:31 -04:00
}
2023-10-14 07:50:19 -04:00
2023-10-05 22:24:31 -04:00
ops.operator = operatorClicked;
//TODO fix this conditional should be if numFlag and a check if = or additional ops
2023-10-14 07:29:07 -04:00
if(!ops.onSecondNumber ){
ops.numFlag = true;
2023-10-14 07:50:19 -04:00
if (ops.result !== "" ) {
console.log('this is running the ops.result');
ops.firstNum = ops.result;
ops.onSecondNumber = true;
return
}
2023-10-14 07:29:07 -04:00
}
ops.onSecondNumber = !ops.onSecondNumber;
2023-10-05 22:24:31 -04:00
}
2023-10-04 21:52:07 -04:00
function calculator(event){
if(event.target.dataset.ops === "") {
2023-10-05 22:24:31 -04:00
handleOperatorClick(event.target.value);
} else if (event.target.value === '.') {
if (display.textContent.includes('.')) {
return
} else {
ops.appendNumber(event.target.value)
}
} else if(event.target.dataset.num === "") {
ops.appendNumber(event.target.value)
2023-10-03 23:06:45 -04:00
}
}
2023-10-08 11:14:17 -04:00
function negateNumber(){
// returns a negated number
let negated;
if (!ops.numFlag || !ops.onSecondNumber) {
negated = Number(ops.firstNum) * -1;
ops.firstNum = String(negated);
} else {
negated = Number(ops.secondNum) * -1;
ops.secondNum = String(negated);
}
updateDisplay(negated);
}
function percentageNumber() {
let percent;
2023-10-14 07:51:26 -04:00
if ((!ops.numFlag || !ops.onSecondNumber)) {
2023-10-08 11:14:17 -04:00
percent = Number(ops.firstNum) / 100;
ops.firstNum = String(percent);
2023-10-14 07:50:19 -04:00
} else if (ops.result !== "" ) {
percent = Number(ops.result) / 100;
2023-10-08 11:14:17 -04:00
} else {
percent = Number(ops.secondNum) / 100;
ops.secondNum = String(percent);
}
updateDisplay(percent);
}
2023-10-03 23:06:45 -04:00
buttons.forEach(btn => {
2023-10-04 21:52:07 -04:00
btn.addEventListener('click', calculator);
2023-10-12 22:11:49 -04:00
});