cssAudio - Activefile-genericCSS - ActiveGeneric - ActiveHTML - ActiveImage - ActiveJS - ActiveSVG - ActiveText - Activefile-genericVideo - ActiveLovehtmlicon-new-collectionicon-personicon-teamlog-outoctocatpop-outspinnerstartv

Pen Settings

CSS Base

Vendor Prefixing

Add External Stylesheets/Pens

Any URL's added here will be added as <link>s in order, and before the CSS in the editor. If you link to another Pen, it will include the CSS from that Pen. If the preprocessor matches, it will attempt to combine them before processing.

Quick-add: + add another resource

Add External Scripts/Pens

Any URL's added here will be added as <script>s in order, and run before the JavaScript in the editor. You can use the URL of any other Pen and it will include the JavaScript from that Pen.

Quick-add: + add another resource

Code Indentation

     

Save Automatically?

If active, Pens will autosave every 30 seconds after being saved once.

Auto-Updating Preview

If enabled, the preview panel updates automatically as you code. If disabled, use the "Run" button to update.

            
              <div class='maxWidthWrap'><canvas id='canvas' width='500px' height='500px'></canvas></div>
            
          
!
            
              .maxWidthWrap {
  width: 100%;
  max-width: 600px;
  margin: 0 auto;
}
            
          
!
            
              var BTNCURR, timeout, timeout2, sequence = [],
  COUNT = 0,
  POWER = 'off',
  prevent = true,
  stop = false,
  strict = false,
  ctrlBtnRadius = 9,
  canvasPadding = 10,
  btnPadding = canvasPadding / 3,
  redAudio = new Audio('https://s3.amazonaws.com/freecodecamp/simonSound1.mp3'),
  greenAudio = new Audio('https://s3.amazonaws.com/freecodecamp/simonSound2.mp3'),
  yellowAudio = new Audio('https://s3.amazonaws.com/freecodecamp/simonSound3.mp3'),
  blueAudio = new Audio('https://s3.amazonaws.com/freecodecamp/simonSound4.mp3'),
  canvasWidth,
  canvasHeight,
  canvasMidX,
  canvasMidY,
  outerBtnRadius,
  innerBtnRadius,
  middleRadius,
  displayText,
  btnText,
  displayWidth,
  displayHeight,
  displayX,
  displayY,
  ctrlBtnSpacing,
  ctrlBtnY,
  btnTextY;

var canvas = document.querySelector('#canvas'),
  ctx = canvas.getContext('2d');

// resize canvas if window is resized
function resizeCanvas() {
  ctx.clearRect(0, 0, canvas.width, canvas.height);
  // Set up temporary canvas
  var tempCanvas = document.createElement('canvas');
  tempCanvas.width = canvas.width;
  tempCanvas.height = canvas.height;
  var tempCtx = tempCanvas.getContext('2d');

  // Copy to temporary canvas
  tempCtx.drawImage(canvas, 0, 0);
  canvasWidth = document.querySelector('.maxWidthWrap').offsetWidth;
  canvasHeight = canvasWidth;

  // Resize original canvas
  canvas.width = canvasWidth;
  canvas.height = canvasWidth;
  // Copy back to resized canvas
  ctx = canvas.getContext('2d');
  ctx.drawImage(tempCanvas, 0, 0, tempCanvas.width, tempCanvas.height, 0, 0, canvas.width, canvas.height);

  drawInit();
}

function drawInit() {
  canvasMidX = canvasWidth / 2;
  canvasMidY = canvasHeight / 2;
  outerBtnRadius = canvasWidth / 2 - canvasPadding;
  innerBtnRadius = outerBtnRadius / 2;
  middleRadius = innerBtnRadius - btnPadding;
  displayText = middleRadius / 3;
  btnText = displayText / 2;
  displayWidth = displayText * 2;
  displayHeight = displayText * 1.3;
  displayX = canvasMidX - displayText;
  displayY = canvasMidY - middleRadius + displayText;
  ctrlBtnSpacing = btnText * 4;
  ctrlBtnY = canvasMidY;
  btnTextY = canvasMidY + displayText;

  background();
  midCircle();
  redBtn();
  greenBtn();
  yellowBtn();
  blueBtn();
  startBtn();
  onOffBtn();
  strictBtn();
  strictLight();
  update();
}

function stopActions() {
  stop = true;
  prevent = true;
  window.clearTimeout(timeout);
  sequence = [];
}

// on off
function gamePower() {
  canvas.removeEventListener('mouseup', gamePower, false);
  POWER = (POWER === 'off') ? 'on' : 'off';
  onOffBtn();
  if (POWER === 'on') {
    update();
  } else {
    stopActions();
    ctx.clearRect(0, 0, canvasWidth, canvasHeight);
    strict = false;
    drawInit();
  }
}
// update display
function update() {
  ctx.clearRect(displayX, displayY, displayWidth, displayHeight);
  display();
}
// reset and start a new game
function resetStartGame() {
  startBtn();
  canvas.removeEventListener('mouseup', resetStartGame, false);
  if (POWER === 'off') {
    return;
  }
  stopActions();
  clearTimeout(timeout);
  ctx.clearRect(0, 0, canvasWidth, canvasHeight);
  drawInit();
  stop = false;
  timeout = setTimeout(nextLevel, 1000);
}

function nextLevel() {
  addToSequence();
  COUNT = 0;
  timeout = setTimeout(runSequence, 1000);
}

function compareSequence(btnPressed) {
  if (sequence[COUNT] === btnPressed) {
    COUNT++;
    if (COUNT >= sequence.length) {
      prevent = true;
      timeout = setTimeout(nextLevel, 1000);
    }
  } else {
    if (strict === true) {
      resetStartGame();
    } else {
      prevent = true;
      COUNT = 0;
      timeout = setTimeout(runSequence, 1000);
    }
  }
}

function addToSequence() {
  var btn = 0;
  var num = Math.floor(Math.random() * (5 - 1) + 1);
  switch (num) {
    case 1:
      btn = 'redBtn';
      break;
    case 2:
      btn = 'greenBtn';
      break;
    case 3:
      btn = 'yellowBtn';
      break;
    case 4:
      btn = 'blueBtn';
      break;
    default:
      console.log('switch statement error');
      btn = 'redBtn';
      break;
  }
  sequence.push(btn);
  update();
}

function audio(t) {
  if (t === 'redBtn') {
    redAudio.play();
  } else if (t === 'greenBtn') {
    greenAudio.play();
  } else if (t === 'yellowBtn') {
    yellowAudio.play();
  } else if (t === 'blueBtn') {
    blueAudio.play();
  } else {
    redAudio.play();
  }
} // end audio
function btnTimer() {
  window[BTNCURR]('clicked');
  setTimeout(btnTimerStop, 300);
}

function btnTimerStop() {
  window[BTNCURR]('nada');
}

function runSequence() {
  if (stop === true) {
    return;
  }
  BTNCURR = sequence[COUNT];
  audio(BTNCURR);
  btnTimer(BTNCURR);
  COUNT++;
  if (COUNT >= sequence.length) {
    COUNT = 0;
    prevent = false;
    return;
  }
  timeout = window.setTimeout(runSequence, 1500);
}
// draw background
function background() {
  ctx.beginPath();
  ctx.arc(canvasMidX, canvasMidY, canvasWidth / 2 - 1, 0, 2 * Math.PI, false);
  ctx.arc(canvasMidX, canvasMidY, canvasWidth / 2 - 1, 0, 2 * Math.PI);
  var gradient = ctx.createRadialGradient(canvasMidX, canvasMidY, 0, canvasMidX, canvasMidY, canvasWidth);
  gradient.addColorStop(0, "white");
  gradient.addColorStop(0.2, "#3B3B3B");
  gradient.addColorStop(1, "black");
  ctx.fillStyle = gradient;
  ctx.fill();
}
// draw middle circle
function midCircle() {
  ctx.beginPath();
  ctx.arc(canvasMidX, canvasMidY, middleRadius, 0, 2 * Math.PI);
  ctx.fillStyle = '#232323';
  ctx.fill();
  ctx.fillStyle = 'grey';
  ctx.textAlign = 'center';
  ctx.font = btnText + 'px serif';
  ctx.fillText('Power', canvasMidX, btnTextY);
  ctx.fillText('Start', canvasMidX - ctrlBtnSpacing, btnTextY);
  ctx.fillText('Strict', canvasMidX + ctrlBtnSpacing, btnTextY);
  ctx.lineWidth = '1';
}

// convert degree to radian
function radian(num) {
  return num * (Math.PI / 180);
}

function arcBtnCheck(x, y, deg1, deg2) {
  ctx.beginPath();
  ctx.arc(x, y, outerBtnRadius, deg1, deg2, false);
  ctx.arc(x, y, innerBtnRadius, deg2, deg1, true);
  // ctx.closePath();
}

function drawArcBtn(x, y, deg1, deg2, clr2) {
  ctx.beginPath();
  ctx.arc(x, y, outerBtnRadius, deg1, deg2, false);
  ctx.arc(x, y, innerBtnRadius, deg2, deg1, true);
  ctx.fillStyle = clr2;
  ctx.strokeStyle = 'black';
  ctx.closePath();
  ctx.fill();
  ctx.stroke();
}
// draw red btn
function redBtn(color) {
  var clr;
  if (color === 'clicked') {
    clr = 'lightpink';
  } else {
    clr = 'red';
    canvas.removeEventListener('mouseup', redBtn, false);
  }
  drawArcBtn(canvasMidX + btnPadding, canvasMidY - btnPadding, radian(270), radian(360), clr);

}

function greenBtn(color) {
  var clr;
  if (color === 'clicked') {
    clr = 'lightgreen';
  } else {
    clr = 'green';
    canvas.removeEventListener('mouseup', greenBtn, false);
  }
  drawArcBtn(canvasMidX - btnPadding, canvasMidY - btnPadding, radian(180), radian(270), clr);
}

// draw yellow btn
function yellowBtn(color) {
  var clr;
  if (color === 'clicked') {
    clr = 'white';
  } else {
    clr = 'yellow';
    canvas.removeEventListener('mouseup', yellowBtn, false);
  }
  drawArcBtn(canvasMidX - btnPadding, canvasMidY + btnPadding, radian(90), radian(180), clr);
}
// draw blue btn
function blueBtn(color) {
  var clr;
  if (color === 'clicked') {
    clr = 'skyblue';
  } else {
    clr = 'blue';
    canvas.removeEventListener('mouseup', blueBtn, false);
  }
  drawArcBtn(canvasMidX + btnPadding, canvasMidY + btnPadding, radian(0), radian(90), clr);
}

function ctrlBtnCheck(x, y) {
  ctx.beginPath();
  ctx.arc(x, y, ctrlBtnRadius, 0, 2 * Math.PI, false);
}

function drawCtrlBtn(x, y, clr) {
  ctx.beginPath();
  var gradient = ctx.createRadialGradient(x - 1, y - 1, ctrlBtnRadius / 2, x, y, ctrlBtnRadius);
  gradient.addColorStop(0, clr);
  gradient.addColorStop(0.7, '#24292D');
  gradient.addColorStop(1, clr);
  ctx.fillStyle = gradient;
  ctx.strokeStyle = 'grey';
  ctx.lineWidth = 1;
  ctx.arc(x, y, ctrlBtnRadius, 0, 2 * Math.PI, false);
  ctx.fill();
  //ctx.stroke();
}
// draw start button
function startBtn() {
  drawCtrlBtn(canvasMidX - ctrlBtnSpacing, ctrlBtnY, 'red');
}

// draw on off power button
function onOffBtn() {
  var clr = (POWER === 'on') ? 'grey' : '#6F6F6F';
  var strokeColor = (POWER === 'on') ? 'aqua' : 'grey';
  drawCtrlBtn(canvasMidX, ctrlBtnY, clr);
  ctx.strokeStyle = strokeColor;
  ctx.stroke();
}

// draw strict button
function strictBtn() {
  drawCtrlBtn(canvasMidX + ctrlBtnSpacing, ctrlBtnY, 'yellow');
}

// draw strict button light
function strictLight() {
  var clr = (strict === true) ? 'green' : 'black';
  ctx.fillStyle = clr;
  ctx.beginPath();
  ctx.arc(canvasMidX + ctrlBtnSpacing, ctrlBtnY - 20, 3, 0, 2 * Math.PI);
  ctx.fill();
}

function strictBtnUp() {
  strictBtn();
  if (POWER === 'on') {
    canvas.removeEventListener('mouseup', strictBtnUp, false);
    strict = (strict === false) ? true : false;
    strictLight();
  }
}

// draw btn down position
function btnDown(btn) {
  if (btn === 'startBtn') {
    drawCtrlBtn(canvasMidX - ctrlBtnSpacing, ctrlBtnY, '#E50000');
  } else if (btn === 'onOffBtn') {
    drawCtrlBtn(canvasMidX, ctrlBtnY, '#616161');
  } else if (btn === 'strictBtn') {
    drawCtrlBtn(canvasMidX + ctrlBtnSpacing, ctrlBtnY, '#FFC300');
  }
}

/********************
Mouse Position and Events
********************/
function getMousePos(canvas, e) {
  var rect = canvas.getBoundingClientRect();
  return {
    x: e.clientX - rect.left,
    y: e.clientY - rect.top
  };
}

// mousedown event
canvas.addEventListener('mousedown', function(e) {
  var pos = getMousePos(canvas, e);
  var x = pos.x;
  var y = pos.y;

  // check if redBtn
  arcBtnCheck(canvasMidX + btnPadding, canvasMidY - btnPadding, radian(270), radian(360));

  if (ctx.isPointInPath(x, y)) {
    if (prevent === true) {
      return;
    }
    redAudio.pause();
    redAudio.currentTime = 0;
    audio('redBtn');
    redBtn('clicked');
    canvas.addEventListener('mouseup', redBtn, false);
    compareSequence('redBtn');
    return;
  }

  // check if greenBtn
  arcBtnCheck(canvasMidX - btnPadding, canvasMidY - btnPadding, radian(180), radian(270));

  if (ctx.isPointInPath(x, y)) {
    if (prevent === true) {
      return;
    }
    greenAudio.pause();
    greenAudio.currentTime = 0;
    audio('greenBtn');
    greenBtn('clicked');
    canvas.addEventListener('mouseup', greenBtn, false);
    compareSequence('greenBtn');
    return;
  }

  // check if yellowBtn
  arcBtnCheck(canvasMidX - btnPadding, canvasMidY + btnPadding, radian(90), radian(180));

  if (ctx.isPointInPath(x, y)) {
    if (prevent === true) {
      return;
    }
    yellowAudio.pause();
    yellowAudio.currentTime = 0;
    audio('yellowBtn');
    yellowBtn('clicked');
    canvas.addEventListener('mouseup', yellowBtn, false);
    compareSequence('yellowBtn');
    return;
  }
  // check if blueBtn
  arcBtnCheck(canvasMidX + btnPadding, canvasMidY + btnPadding, radian(0), radian(90));

  if (ctx.isPointInPath(x, y)) {
    if (prevent === true) {
      return;
    }
    blueAudio.pause();
    blueAudio.currentTime = 0;
    audio('blueBtn');
    blueBtn('clicked');
    canvas.addEventListener('mouseup', blueBtn, false);
    compareSequence('blueBtn');
    return;
  }
  // check if start button
  ctrlBtnCheck(canvasMidX - ctrlBtnSpacing, ctrlBtnY);
  if (ctx.isPointInPath(x, y)) {
    btnDown('startBtn');
    canvas.addEventListener('mouseup', resetStartGame, false);
  }
  // check if on off power button
  ctrlBtnCheck(canvasMidX, ctrlBtnY);
  if (ctx.isPointInPath(x, y)) {
    btnDown('onOffBtn');
    canvas.addEventListener('mouseup', gamePower, false);
  }

  // check if strict button
  ctx.beginPath();
  ctrlBtnCheck(canvasMidX + ctrlBtnSpacing, ctrlBtnY, 'yellow');
  if (ctx.isPointInPath(x, y)) {
    btnDown('strictBtn');
    canvas.addEventListener('mouseup', strictBtnUp, false);

  }

}, false);

// draw display, level
function display() {
  var level = sequence.length;
  level = (level < 10) ? '0' + level : level;
  ctx.beginPath();
  ctx.fillStyle = 'black';
  ctx.fillRect(displayX, displayY, displayWidth, displayHeight);
  if (POWER === 'on') {
    ctx.fillStyle = 'red';
    ctx.font = displayText + 'px serif';
    ctx.fillText(level, canvasMidX - btnPadding, displayY + displayText);
  }
}
window.addEventListener('resize', resizeCanvas, false);
window.addEventListener('orientationchange', resizeCanvas, false);
resizeCanvas();
            
          
!
999px
Loading ..................

Console