<section class="calculator-wrap">
  <div class="title-wrapper">
    <h1 class="calc-title">Casio 9000</h1>
  </div>
  <div class="calculator-inner">
    <form method="GET" name="form" action="#" id="calculator" data-calc-mode="initial" autocomplete="off">
        <input type="text" id="calc-display" value="0">
        <div class="buttons-wrap">
          <div class="button-numbers">  
            <button id="btn-1" value="1" data-btn-val="1">1</button>
            <button id="btn-2" value="2" data-btn-val="2">2</button>
            <button id="btn-3" value="3" data-btn-val="3">3</button>
            <button id="btn-4" value="4" data-btn-val="4">4</button>
            <button id="btn-5" value="5" data-btn-val="5">5</button>
            <button id="btn-6" value="6" data-btn-val="6">6</button>
            <button id="btn-7" value="7" data-btn-val="7">7</button>
            <button id="btn-8" value="8" data-btn-val="8">8</button>
            <button id="btn-9" value="9" data-btn-val="9">9</button>
            <button id="btn-0" value="0" data-btn-val="0">0</button>
            <button id="percentage-btn" data-operator="percentage">%</button>
            <button id="decimal-btn" data-operator="decimal">.</button>
          </div>
          <div class="buttons-operators"> 
            <button id="add-btn" data-operator="add">+</button>
            <button id="subtract-btn" data-operator="subtract">-</button>
            <button id="divide-btn" data-operator="divide">/</button>
            <button id="multiply-btn" data-operator="multiply">*</button>
          </div>
        </div>
        <div class="buttons-methods">
          <button id="clear-btn" data-operator="clear">C</button>
          <button id="calc-btn" data-operator="equals">=</button>
        </div>
      </form>
  </div>  
</section>

<p class="colophon">
  Another CodePen by <a href="https://richardhuf.com.au">Richard Huf</a>
</p>
@import url('https://fonts.googleapis.com/css?family=Source+Code+Pro');

$font-google: 'Source Code Pro', monospace;
$font-google-2: 'Orbitron', monospace;

// VARS

// Color vars
// $color1: #F4DF42;
$color1: #42F4D1;
$color2: #000;

// MIXINS

// Global box shadow mixin
// Set some default values that can be altered
@mixin global-box-shadow($x: 3px, $y: 3px) {
  box-shadow: #{$x} #{$y} 0 $color2;
}

* {
  box-sizing: border-box;
}

body {
  background: linear-gradient(to bottom, $color1 0%, $color1 85%, $color2 85%);
  background-size: cover;
  font-family: $font-google;
  padding: 16px;
}

a:link,
a:visited {
  color: $color2;
}

a:hover,
a:active {
   text-decoration: none; 
}

.calculator-wrap {
  cursor: grab;  
  width: 40vmax;
  min-width: 300px;
  margin: 20px auto;  
}

.calculator-inner {
  @include global-box-shadow(6px, 6px);
  background-color: $color1;
  border: 3px solid $color2;
  border-top: none;
  display: block;
  padding: 20px;
  position: relative;
  z-index: 2;
  
  &.ui-draggable-dragging,
  &:active {
    cursor: grabbing;
  }
}

.calc-title {
  background: mix($color1, $color2, 80%);
  color: $color2;
  margin: -20px -20px 0;
  padding: 20px;
  border: 2px solid $color2;
  @include global-box-shadow(6px, 6px);

  text-transform: uppercase;
  text-align: center;
  width: 100%;
  transform: skew(-8deg) translateX(1.7rem);

}

#calc-display {
  @include global-box-shadow;
  border: 2px solid $color2;
  background-color: transparent;
  font-family: $font-google-2;
  border-radius: 2px;
  display: block;
  margin-bottom: 10px;
  padding: 12px 12px;
  width: 100%;
}

.buttons-wrap {
  display: flex;  
}

.buttons-operators {
  align-items: flex-start;
  display: flex;
  flex-wrap: wrap;
  justify-content: space-around;
}

.button-numbers {
  width: 72%;
  margin-right: 3%;
  display: flex;
  flex-direction: row;
  flex-wrap: wrap;
  justify-content: space-between;
  
  button {
    width: 30%;
    
    &:nth-child(3n) {
      margin-right: 0;
    }
  }
}

.buttons-operators {
  display: flex;
  width: 25%;
  
  button {
    background: mix($color1, $color2, 80%);
    font-size: 1.25em;
    flex-basis: 100%;
  }
}

.buttons-methods {
  display: flex;
  flex-direction: row;
  align-items: stretch;
  flex-wrap: nowrap;
  justify-content: space-between;
  
  button {
    background: mix($color1, $color2, 80%);
    font-size: 1.25em;
    width: 48.5%;
  }
}

button {
  @include global-box-shadow;
  appearance: none;
  background-color: transparent;
  border: 2px solid $color2;
  font-weight: 900;
  font-family: $font-google-2;
  font-size: 16px;
  margin-bottom: 8px;
  outline: none;
  padding: 8px;

  &:active {
    box-shadow: none;
    transform: translateX(3px) translateY(3px);
    outline: none;
  }
}


[id="calculator"]:before {
  color: $color2;
  content: 'DEBUG: Mode = ' attr(data-calc-mode);
  font-family: $font-google;
  font-size: 12px;
  text-transform: uppercase;
  position: absolute;
  bottom: 7px;
  left: 25px;
  display: block;
}

// Turn off debug msg via js 
.is-debug-mode:before {
  content: '';
}


.colophon {
  color: $color1;
  font-size: 13px;
  text-align: center;
  margin: 40px auto;
  position: relative;
  z-index: 1;
  
  a {
    color: $color1;
  }
}
View Compiled
'use strict';

let calculator            = document.getElementById('calculator');
let calcDisplayEl         = document.getElementById('calc-display');
let calcDisplayValue      = calcDisplayEl.value;
let currentCalcMode       = calculator.dataset.calcMode;
let calcBtn               = document.getElementById('calc-btn');  
let clearBtn              = document.getElementById('clear-btn');
let decimalBtn            = document.getElementById('decimal-btn');  
let percentageBtn         = document.getElementById('percentage-btn');
let memory                = [];
let debug                 = false;

// If in debug mode, we output console logs and show debug info 
if(!debug) {
  // Turn off all console logs conveniently
  console.log = function() {}
  
  // Turn off debug data displaying calc mode 
  calculator.classList.add('is-debug-mode');
}

// Make calculator draggable 
$('.calculator-wrap').draggable({
  addClasses: true,
});

// Array of number button elements
let numbers = [
  document.getElementById('btn-1'),
  document.getElementById('btn-2'),
  document.getElementById('btn-3'),
  document.getElementById('btn-4'),
  document.getElementById('btn-5'),
  document.getElementById('btn-6'),
  document.getElementById('btn-7'),
  document.getElementById('btn-8'),
  document.getElementById('btn-9'),
  document.getElementById('btn-0')
];

// Array of operator button elements
let operators = [
  document.getElementById('add-btn'),
  document.getElementById('subtract-btn'),
  document.getElementById('divide-btn'),
  document.getElementById('multiply-btn'),
];

numbers.forEach(function(element) {
  // console.log(element);
  element.addEventListener('click', function(event) {
    event.preventDefault();
    
    // Use 'data-calc-mode' attr on form to set mode
    // Mode can be 'number' if number last pressed,
    // or 'operator' if operator last pressed'.
    currentCalcMode =  calculator.dataset.calcMode;
    
    //////////////////////////////////////////////////////// 
    // CALC MODE: INITIAL
    ////////////////////////////////////////////////////////
    if(currentCalcMode === 'initial') {

      // Calc is reset to initial. Update display with button value pressed
      calcDisplayEl.value = this.value;
      
      // Place this value into memory
      memory.push(calcDisplayEl.value);
      
    } 
    
    //////////////////////////////////////////////////////// 
    // CALC MODE: NUMBER
    ////////////////////////////////////////////////////////
    if(currentCalcMode === 'number') {
    
      // append the last number pressed to the value
      calcDisplayEl.value = calcDisplayEl.value + this.value;
      
       // We remove the last item (a number) from the array, and then update the array with the currect value
      memory.pop();
      
      // Update memory
      memory.push(calcDisplayEl.value);
    }
    
    //////////////////////////////////////////////////////// 
    // CALC MODE: OPERATOR
    ////////////////////////////////////////////////////////
    if(currentCalcMode === 'operator') {

      calcDisplayEl.value = this.value;
      
      memory.push(calcDisplayEl.value);
      
      console.log(memory);

    }
    
    // Since number has been presed, set data-calc-mode attr to 'number'
    // Get updated value of calc-display
    let currentDisplayEl  = document.getElementById('calc-display');
    
    // Set calc mode to number
    calculator.dataset.calcMode = 'number';

    // Update calc mode var
    currentCalcMode =  calculator.dataset.calcMode;
    
    let currentDisplayVal = parseInt(currentDisplayEl.value);
    
    // Place current display value into memory
    // memory.push(currentDisplayVal);
    console.log(memory);    

  }, false);  
});

// Bind click event to each operator button
operators.forEach(function(element) {
  element.addEventListener('click', function(event) {
    event.preventDefault();
    
    // Gets value from buttons data-operator attr.
    let buttonOperator = this.getAttribute('data-operator');
    
    memory.push({
      'operator': buttonOperator
    });
    
    // Set calc mode to operator
    calculator.dataset.calcMode = 'operator';
    
    console.log(memory);
    
  })
});

////////////////////////////////////////////////////////
// CLEAR BUTTON CLICK
////////////////////////////////////////////////////////
clearBtn.addEventListener('click', (event) => {
  event.preventDefault();
  
  // Reset some stuff
  calcDisplayEl.value = "0";
  memory = [];
  
  // Set calc mode to initial
  calculator.dataset.calcMode = 'initial';
  
  // console.log(memory);
  console.clear();
  
}, false);

////////////////////////////////////////////////////////
// DECIMAL BUTTON CLICK
////////////////////////////////////////////////////////
decimalBtn.addEventListener('click', (event) => {
  event.preventDefault();
  
  // If displayValue !== 0, append decimal point
  if(calcDisplayEl.value !== '0') {
    // append the last number pressed to the value
    calcDisplayEl.value = calcDisplayEl.value + '.';       
  }
    
}, false);

////////////////////////////////////////////////////////
// PERCENTAGE BUTTON CLICK
////////////////////////////////////////////////////////
percentageBtn.addEventListener('click', (event) => {
  event.preventDefault();
  
  // If displayValue !== 0, append decimal point
  if(calcDisplayEl.value !== '0') {
    // append the last number pressed to the value
    calcDisplayEl.value = parseInt(calcDisplayEl.value) / 100;       
  }
  
  memory = [calcDisplayEl.value];
  console.log(memory);
  
}, false);

////////////////////////////////////////////////////////
// CALC BUTTON CLICK
////////////////////////////////////////////////////////
calcBtn.addEventListener('click', (event) => {
  event.preventDefault();
  
  console.log(memory);
  
  // Lets calculate a result.
  let previousVal  = memory[0];
  let operator     = memory[1];
  let currentVal   = memory[2];
            
  // Operator returns a function name,
  // either 'add', 'subtract', 'multiple' or 'divide'
  // We us this funtion to calculate a result

  let calcMethodToUse = operator.operator;
  let result = '';            

  switch(calcMethodToUse) {
    case 'add':
      result = add(previousVal, currentVal);
      break;
    case 'subtract':
      result = subtract(previousVal, currentVal);
      break;
    case 'multiply':
      result = multiply(previousVal, currentVal);
      break;
    case 'divide':
      result = divide(previousVal, currentVal);
      break;
  }
    
  calcDisplayEl.value = result;
      
  memory = [result];

  console.log(memory);
    
}, false);


/////////////////////////////////////////////////////////
// OPERATOR FUNCTIONS
/////////////////////////////////////////////////////////

// Addition
const add = (a,b) => {
  return(+a + +b)
}

// Subtraction
const subtract = (a,b) => {
  return(a - b)
}

// Multiply
const multiply = (a,b) => {
  return(a * b)
}

// Divide
const divide = (a,b) => {
  return(a / b)
}

/////////////////////////////////////////////////////////
// KEY BINDINGS
/////////////////////////////////////////////////////////

window.addEventListener("keyup", checkKeyPressed, false);

function checkKeyPressed(e) {
  console.log('click');
  // If displayfield is in focus, we can type numbers in directly instead of triggering a click
  if(calcDisplayEl.is(':focus')) {
    return;
  }

  // Numbers 0-9
  for(let i = 48; i < 58; i++) {
    console.log(i);
    
    if (e.keyCode == [i]) {
      $('[data-btn-val="' + ([i] - 48) + '"]').trigger('click');
    }
  }

  // Plus key
  if (e.which == 107) {
    $('[data-operator="add"]').trigger('click');
  }

  // Minus key
  if (e.which == 109) {
    $('[data-operator="subtract"]').trigger('click');
  }

  // Enter (or equals) key
  if (e.which == 13 || e.keyCode == 187) {
    $('[data-operator="equals"]').trigger('click');
  }

  // Clear key (cmd + c)
  if (e.keyCode == 67) {
    console.log('cmd + c');
    $('[data-operator="clear"]').trigger('click');
  }
}
View Compiled

External CSS

  1. https://fonts.googleapis.com/css?family=Orbitron
  2. https://fonts.googleapis.com/css?family=Source+Code+Pro

External JavaScript

  1. https://cdnjs.cloudflare.com/ajax/libs/jquery/3.1.1/jquery.min.js
  2. https://code.jquery.com/ui/1.12.1/jquery-ui.min.js