array of divs not being parsed in onclick function in javascript - javascript

I am trying to make a program where when the user clicks on any of the divs in the div of id types, countries, languages, genres that clicked div should be switching color to either green or black, and also list all the neighbor divs of that clicked div in the console. But for some reason it is only printing the divs of the last div of id genres in the console on any div clicked. Please Help
My code's snippet:
var filter_options_div = document.getElementById("filter_options").children;
for (var y = 0; y < filter_options_div.length; y++) {
if (filter_options_div[y].tagName == "DIV") {
var option = filter_options_div[y].querySelectorAll("div");
for (var x = 0; x < option.length; x++) {
option[x].style.backgroundColor = "green";
var inserting = option;
option[x].onclick = function() {
for (var z = 0; z < inserting.length; z++) {
console.log(inserting[z]);
}
if (this.style.backgroundColor == "rgb(51, 51, 51)") {
this.style.backgroundColor = "green";
} else {
this.style.backgroundColor = "rgb(51, 51, 51)";
}
};
}
}
}
#filter_options {
width: 50%;
height: 100%;
position: fixed;
top: 0;
z-index: 2;
background-color: orange;
float: left;
}
#filter_options p {
margin-top: 50px;
}
#filter_options div {
background-color: rgb(51, 51, 51);
text-align: center;
overflow: auto;
white-space: nowrap;
}
#filter_options div div {
font-size: 18px;
display: inline-block;
color: white;
padding: 14px;
background-color: rgb(51, 51, 51);
user-select: none;
}
<html lang="en">
<head>
<meta charset="UTF-8">
<title>TEST</title>
</head>
<body>
<div id="filter_options">
<p></p>
<div id="types">
<div>Film</div><div>Tv-Show</div><div>Music</div>
</div>
<p></p>
<div id="countries">
<div>Australia</div><div>China</div><div>France</div><div>Hong-Kong</div><div>India</div><div>Japan</div><div>Canada</div><div>Germany</div><div>Italy</div><div>Spain</div><div>U.K.</div><div>United States</div>
</div>
<p></p>
<div id="languages">
<div>English</div><div>Hindi</div><div>Punjabi</div>
</div>
<p></p>
<div id="genres">
<div>Action</div><div>Adventure</div><div>Animation</div><div>Biography</div><div>Comedy</div><div>Crime</div><div>Documentary</div><div>Drama</div><div>Fantasy</div><div>Family</div><div>Foreign</div><div>History</div><div>Horror</div><div>Kids</div><div>Music</div><div>Magical realism</div><div>Mystery</div><div>News</div><div>Philosophical</div><div>Political</div><div>Reality</div><div>Romance</div><div>Saga</div><div>Satire</div><div>Sci-Fi</div><div>Social</div><div>Speculative</div><div>Sport</div><div>Talk</div><div>Thriller</div><div>Urban</div><div>Western</div><div>War</div>
</div>
</div>
</body>
</html>

'onclick' event handler function needs to be updated.
Also, given the 'inserting' variable scope with respect to 'onlick' function, it will have the same value for all handlers which is the last variable in the loop.
One way of solving this is updating the code as follows:
function getSiblings(el, filter) {
var siblings = [];
el = el.parentNode.firstChild;
do { if (!filter || filter(el)) siblings.push(el); } while (el = el.nextSibling);
return siblings;
}
var filter_options_div = document.getElementById("filter_options").children;
for (var y = 0; y < filter_options_div.length; y++) {
if (filter_options_div[y].tagName == "DIV") {
var option = filter_options_div[y].querySelectorAll("div");
for (var x = 0; x < option.length; x++) {
option[x].style.backgroundColor = "green";
var inserting = option;
option[x].onclick = function(event) {
var neighbors = getSiblings(event.currentTarget);
for (var z = 0; z < neighbors.length; z++) {
console.log(neighbors[z]);
}
if (this.style.backgroundColor == "rgb(51, 51, 51)") {
this.style.backgroundColor = "green";
} else {
this.style.backgroundColor = "rgb(51, 51, 51)";
}
};
}
}
}

Related

Runtime Error when using a for loop inside a while loop

This is a hangman project I'm working on. Inside the guessing function, a for loop is used to add onclick functions to the buttons and another for loop is used to check whether the button's text(a letter) is inside the word. Also a while loop is wrapping these for loops up to check whether the user is out of guesses or he guesses the word. But when I try to run it, browser crashes and I have no clue why it happens.
Also I wonder if I can put the while loop conditions inside the for loop as they works quite similar :/
Here is my code:
window.onload = function() {
var letters = "a b c d e f g h i j k l m n o p q r s t u v w x y z";
var category = ["Premier Leaque Football Teams", "Films", "Cities"];
var wordlist = [
["everton", "liverpool", "swansea", "chelsea", "hull", "manchester-city", "newcastle-united"],
["alien", "dirty-harry", "gladiator", "finding-nemo", "jaws"],
["manchester", "milan", "madrid", "amsterdam", "prague"]
];
var hints = [
["Based in Mersyside", "Based in Mersyside", "First Welsh team to reach the Premier Leauge", "Owned by A russian Billionaire", "Once managed by Phil Brown", "2013 FA Cup runners up", "Gazza's first club"],
["Science-Fiction horror film", "1971 American action film", "Historical drama", "Anamated Fish", "Giant great white shark"],
["Northern city in the UK", "Home of AC and Inter", "Spanish capital", "Netherlands capital", "Czech Republic capital"]
]
var buttons = document.getElementById("buttons");
var showCategory = document.getElementById("show_category");
var hyphens = document.getElementById("hyphens");
var showLives = document.getElementById("show_lives");
var showClue = document.getElementById("show_clue");
var showHint = document.getElementById("show_hint");
var playAgain = document.getElementById("play_again");
letters = letters.split(" ");
var letters_ul = document.createElement("ul");
for (var i = 0; i < letters.length; i++) {
var letters_li = document.createElement("li");
var letters_button = document.createElement("button");
letters_button.innerHTML = letters[i];
letters_li.appendChild(letters_button);
letters_ul.appendChild(letters_li);
}
buttons.appendChild(letters_ul);
initialize = function() {
var c = Math.floor(Math.random() * category.length);
var w = Math.floor(Math.random() * wordlist[c].length);
var word = wordlist[c][w];
var lives = 10;
showCategory.innerHTML = "The Chosen Category is " + category[c];
hyphens.innerHTML = "";
for (var i = 0; i < word.length; i++) {
hyphens.innerHTML += "-";
}
showLives.innerHTML = "You have " + lives + " lives"
showClue.innerHTML = "Clue : -";
showHint.addEventListener("click", function(){
showClue.innerHTML = "Clue : " + hints[c][w];
})
playAgain.addEventListener("click", function(){
initialize();
})
guessing(word, lives);
}
guessing = function(word, lives) {
var button_list = document.querySelectorAll("#buttons ul li button");
var isWord = false;
while (lives > 0 && !isWord) {
for (var i = 0; i < button_list.length; i++) {
button_list[i].addEventListener("click", function(e){
var h = "";
for (var j = 0; j < word.length; j++) {
if (word[j] === e.target.innerHTML) {
h += e.target.innerHTML;
} else if (hyphens.innerHTML[j] === word[j]) {
h += "";
} else {
h += "-";
}
if (hyphens.innerHTML === h && lives > 0) {
lives--;
showLives.innerHTML = "You have " + lives + " lives";
} else if (lives === 0 && !isWord) {
showLives.innerHTML = "Game Over!";
} else if (hyphens.innerHTML === word) {
showLives.innerHTML = "You Win!";
isWord = true;
}
hyphens.innerHTML = h;
}
}
)
}
}
}
initialize();
}
* {
box-sizing: border-box;
}
body {
margin: 0;
background-color: goldenrod;
font-family:'Courier New', Courier, monospace;
text-align: center;
color: white;
}
h1 {
font-size: 50px;
}
h2 {
font-size: 40px;
}
p {
font-size: 25px;
}
#buttons ul {
list-style-type: none;
margin: 0;
padding: 0;
}
#buttons ul li {
display: inline-block;
}
#buttons ul li button {
padding: 10px 15px;
border: 1px solid white;
border-radius: 5px;
background-color: white;
color: goldenrod;
margin: 5px;
}
#buttons ul li button:hover {
background-color: goldenrod;
color: white;
}
#buttons ul li button:active, #buttons ul li button:visited {
opacity: 0.5 !important;
background-color: goldenrod !important;
color: white !important;
}
#hyphens {
font-size: 50px;
}
#hangman {
border: 2px dashed white;
}
.container #show_hint, .container #play_again{
color: white;
background-color: goldenrod;
padding: 20px 40px;
margin: 15px;
border: 1px solid white;
}
.container #show_hint:hover, .container #play_again:hover {
background-color: white;
color: goldenrod;
}
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<meta name="description" content="hangman">
<meta name="keywords" content="hangman">
<meta name="author" content="Nick Hui">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>Hangman</title>
<link rel="stylesheet" href="hangman.css">
<script src="hangman.js"></script>
</head>
<body>
<h1>HANGMAN</h1>
<h2>VANILLA JAVASCRIPT HANGMAN GAME</h2>
<p>Use the alphabet below to guess the word, or click hint to get a clue.</p>
<div id="buttons"></div>
<p id="show_category"></p>
<div id="hyphens"></div>
<p id="show_lives">You have 10 lives</p>
<p id="show_clue">Clue: -</p>
<canvas id="hangman"></canvas>
<div class="container">
<button id="show_hint">HINT</button>
<button id="play_again">Play again</button>
</div>
</body>
</html>

JavaScript itareate over divs and create a new one if doesn't fits

Hello guys I hope you can help me with JavaScript, I'm trying to itarate over some divs, the issue is that when I iterate sometimes a div never change to the other divs, it suppose to be infinite, I will recive thousands of different divs with different height and it should create an other div container in the case it does not fits but I can not achieve it work's, I'm using Vanilla JavaScript because I'm lerning JavaScript Regards.
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Document</title>
<style>
.big_container{
height: 600px;
width: 150px;
background-color: #f1f1f1;
float: left;
}
.items{
background-color: gray;
height: 50px;
}
.new_container{
margin-bottom: 10px;
height: 300px;
width: 150px;
background-color: red;
float: left;
margin-left: 5px;
}
</style>
</head>
<body>
<div class="big_container">
<div class="items">1</div>
<div class="items">2</div>
<div class="items">3</div>
<div class="items">4</div>
<div class="items">5</div>
<div class="items">6</div>
<div class="items">7</div>
<div class="items">8</div>
<div class="items">9</div>
<div class="items">10</div>
<div class="items">11</div>
<div class="items">12</div>
<div class="items">13</div>
</div>
<div class="new_container">
</div>
</body>
<script>
number = 0
sum = 0
new_container = document.getElementsByClassName('new_container')[number].offsetHeight
divs = document.getElementsByClassName('items')
for ( var i = 0; i < divs.length; i++ ){
sum += this.document.getElementsByClassName( 'items' )[0].offsetHeight
if ( sum <= new_container ){
console.log(sum, "yes")
document.getElementsByClassName("new_container")[number].appendChild( this.document.getElementsByClassName( 'items' )[0] )
} else {
sum = 0
console.log(sum, "NO entra")
nuevo_contenedor = document.createElement('div'); // Creo un contenedor
nuevo_contenedor.className = "new_container";
nuevo_contenedor.setAttribute("style", "background-color: red;");
document.body.appendChild(nuevo_contenedor)
number += + 1
}
}
</script>
</html>
I really apreciate a hand.
I know that I'm late, but there is my approach how this can be done.
// generate items with different height
function generateItems(count) {
const arr = [];
for (let i = 0; i < count; i++) {
const div = document.createElement("DIV");
const height = Math.floor((Math.random() * 100) + 10);
div.setAttribute("style", `height: ${height}px`);
div.setAttribute("class", "items");
const t = document.createTextNode(i + 1);
div.appendChild(t);
arr.push(div);
}
return arr;
}
function createNewContainer(height) {
const new_container = document.createElement("DIV")
new_container.setAttribute("class", "new_container");
new_container.setAttribute("style", `height: ${height}px`)
document.body.appendChild(new_container);
return new_container;
}
function breakFrom(sourceContainerId, newContainerHeight) {
const srcContainer = document.getElementById(sourceContainerId);
const items = srcContainer.childNodes;
let new_container = createNewContainer(newContainerHeight);
let sumHeight = 0;
for (let i = 0; i < items.length; i++) {
let item = items[i];
if (item.offsetHeight > newContainerHeight) {
// stop!!! this item too big to fill into new container
throw new Error("Item too big.");
}
if (sumHeight + item.offsetHeight < newContainerHeight) {
// add item to new container
sumHeight += item.offsetHeight;
new_container.appendChild(item.cloneNode(true));
} else {
// create new container
new_container = createNewContainer(newContainerHeight);
new_container.appendChild(item.cloneNode(true));
// don't forget to set sumHeight)
sumHeight = item.offsetHeight;
}
}
// if you want to remove items from big_container
// for (let i = items.length - 1; i >= 0; i--) {
// srcContainer.removeChild(items[i]);
// }
}
// create big container with divs
const big_container = document.getElementById("big_container");
const items = generateItems(13);
items.forEach((div, index) => {
big_container.appendChild(div);
});
breakFrom("big_container", 300);
#big_container {
width: 150px;
background-color: #f1f1f1;
float: left;
}
.items {
background-color: gray;
border: 1px solid #000000;
text-align: center;
}
.new_container {
margin-bottom: 10px;
height: 300px;
width: 150px;
background-color: red;
border: 1px solid red;
float: left;
margin-left: 5px;
}
<div id="big_container"></div>
This example gives you the ability to play with divs of random height. Hope, this will help you.

How to change class and text of one tag by clicking on another tag?

I don't know how to describe this without making it more complicated.
So look at the result of the code and click on the first link with "Show", then the second one and third one.
When the second link is clicked, first one closes but text remains "Hide" and i want it to change to "Show".
So, when clicking a link, detect if any other link has text "Hide" and change it to "Show".
And please no jQuery...
document.getElementsByClassName("show")[0].onclick = function() {
var x = document.getElementsByClassName("hide")[0];
var y = document.getElementsByClassName("show")[0];
if (x.classList.contains("visible")) {
x.classList.remove("visible");
y.textContent = "Show";
} else {
closeOther();
x.classList.add("visible");
y.textContent = "Hide";
}
};
document.getElementsByClassName("show")[1].onclick = function() {
var x = document.getElementsByClassName("hide")[1];
var y = document.getElementsByClassName("show")[1];
if (x.classList.contains("visible")) {
x.classList.remove("visible");
y.textContent = "Show";
} else {
closeOther();
x.classList.add("visible");
y.textContent = "Hide";
}
};
document.getElementsByClassName("show")[2].onclick = function() {
var x = document.getElementsByClassName("hide")[2];
var y = document.getElementsByClassName("show")[2];
if (x.classList.contains("visible")) {
x.classList.remove("visible");
y.textContent = "Show";
} else {
closeOther();
x.classList.add("visible");
y.textContent = "Hide";
}
};
function closeOther() {
var visible = document.querySelectorAll(".visible"),
i, l = visible.length;
for (i = 0; i < l; ++i) {
visible[i].classList.remove("visible");
}
}
.style {
background-color: yellow;
width: 200px;
height: 200px;
display: inline-block;
}
.hide {
background-color: red;
width: 50px;
height: 50px;
display: none;
position: relative;
top: 50px;
left: 50px;
}
.hide.visible {
display: block;
}
<div class="style">
Show
<div class="hide">
</div>
</div>
<div class="style">
Show
<div class="hide">
</div>
</div>
<div class="style">
Show
<div class="hide">
</div>
</div>
I tried to write a solution which didn't use any javascript at all and worked using CSS alone. I couldn't get it to work though - CSS can identify focus but it can't identify blur (ie. when focus has just been removed).
So here is a solution which uses javascript and the classList API, instead:
var divs = document.getElementsByTagName('div');
function toggleFocus() {
for (var i = 0; i < divs.length; i++) {
if (divs[i] === this) continue;
divs[i].classList.add('show');
divs[i].classList.remove('hide');
}
this.classList.toggle('show');
this.classList.toggle('hide');
}
for (let i = 0; i < divs.length; i++) {
divs[i].addEventListener('click', toggleFocus, false);
}
div {
display: inline-block;
position: relative;
width: 140px;
height: 140px;
background-color: rgb(255,255,0);
}
.show::before {
content: 'show';
}
.hide::before {
content: 'hide';
}
div::before {
color: rgb(0,0,255);
text-decoration: underline;
cursor: pointer;
}
.hide::after {
content: '';
position: absolute;
top: 40px;
left: 40px;
width: 50px;
height: 50px;
background-color: rgb(255,0,0);
}
<div class="show"></div>
<div class="show"></div>
<div class="show"></div>
Like this?
Just added following to closeOther():
visible = document.querySelectorAll(".show"),
i, l = visible.length;
for (i = 0; i < l; ++i) {
visible[i].textContent="Show";
}

this.style.background is returning wrong value

I am trying to create an RGB color guessing game. The premise is that each time someone clicks on a div, the function should retrieve it's color value and match it with the random color value(pre-selected) out of a given number of color values.
Now, the game has two difficulty levels. Easy and hard. The code for the two levels is almost same, the number of color divs in easy are 3, while in the case of hard, the number of color divs is 6.
However, while in easy mode, the function is retrieving a color value which belongs to none of the three divs. In fact, it is returning the background color value.
Here is the code
var colors = randomColors(6);
var easyColor = [];
var squares = document.querySelectorAll(".square");
function color() {
var a = Math.floor(Math.random()*250);
var b = Math.floor(Math.random()*250);
var c = Math.floor(Math.random()*250);
return "rgb("+ [(a),(b),(c)].join(', ') + ")";
}
function randomColors(num) {
var arr = [];
for(var i =0; i < num; i++) {
arr.push(color());
}
return arr;
}
// Tried to generate different set of colors for easy mode. Still working on it.
for(var x = 0; x < 3; x++) {
easyColor[x] = color();
}
var easyRandomColor = easyColor[Math.floor(Math.random()*easyColor.length)];
// selecting hard difficulty works same as playing again, hence the reload()
document.getElementById("hard").addEventListener("click", function() {
window.location.reload();
});
document.getElementById("reset").addEventListener("click", function() {
window.location.reload();
});
var squareColor;
// setting up the easy level of the game
document.getElementById("easy").addEventListener("click", function() {
document.getElementById("header").style.background = "#232323";
for(var y = 0; y < 3; y++) {
squares[y].style.background = easyColor[y];
}
for(var z = 3; z < 6; z++) {
squares[z].style.background = "#232323";
}
easyRandomColor = easyColor[Math.floor(Math.random()*easyColor.length)];
document.getElementById("guess").textContent = easyRandomColor;
// setting up the background colors of easy level squares
for(var j = 0; j < easyColor.length; j++)
squares[j].addEventListener("click", function() {
squareColor = this.style.background;
console.log(squareColor, easyRandomColor);
if(squareColor === easyRandomColor) {
document.getElementById("header").style.background = name;
document.getElementById("display").textContent = "Correct!";
document.getElementById("reset").textContent = "Play again?";
for(var k = 0; k < easyColor.length; k++) {
squares[k].style.background = name;
}
} else{
this.style.background = "#232323";
document.getElementById("display").textContent = "Try again.";
}
});
document.getElementById("easy").classList.add("selected");
document.getElementById("hard").classList.remove("selected");
});
var randomColor = colors[Math.floor(Math.random()*colors.length)];
//changing the RGB in h1 to rgb of one the squares
document.getElementById("guess").textContent = randomColor;
//assigning colors to the squares and adding the click event
for(var j = 0; j < squares.length; j++) {
squares[j].style.background = colors[j];
squares[j].addEventListener("click", function() {
var name = this.style.background;
// console.log(name, randomColor);
if(name === randomColor) {
document.getElementById("header").style.background = name;
document.getElementById("display").textContent = "Correct!";
document.getElementById("reset").textContent = "Play again?";
for(var k = 0; k < squares.length; k++) {
squares[k].style.background = name;
}
} else{
this.style.background = "#232323";
document.getElementById("display").textContent = "Try again.";
}
});
}
body {
background-color: #232323;
margin: 0;
}
html {
margin: 0;
padding: 0;
}
.square {
width: 30%;
/*background: purple;*/
padding-bottom: 30%;
float: left;
margin: 1.66%;
transition: 0.2s ease-in;
border-radius: 6%;
}
#container {
margin: 0 auto;
max-width: 600px;
}
h1, h3 {
color: white;
padding-top: 1%;
padding-bottom: 0.5%;
margin-top: 0;
margin-bottom: 0;
text-align: center;
}
#header {
transition: 0.2s ease-in;
}
#nav {
margin-top: 0;
padding-top: 0;
background: white;
max-width: 100%;
clear: left;
}
#nav p {
margin: 0 auto;
position: relative;
max-width: 580px;
}
#reset {
position: relative;
}
#hard {
position: absolute;
right: 0;
}
#easy {
position: absolute;
right: 50px;
}
#display {
position: relative;
left: 27%;
}
<!DOCTYPE html>
<html>
<head>
<title>RGBA Guess</title>
<link rel="stylesheet" type="text/css" href="colorgame.css">
</head>
<body>
<div id="header">
<h3>
The Great
</h3>
<h1>
<span id="guess">number</span>
</h1>
<h3>
Guessing Game
</h3>
</div>
<div id="nav">
<p>
<button id="reset">New Colors</button>
<span id="display"></span>
<button id="easy">Easy</button>
<button id="hard" class="selected">Hard</button>
</p>
</div>
<div id="container">
<div class="square" id="sqaure1"></div>
<div class="square" id="sqaure2"></div>
<div class="square" id="sqaure3"></div>
<div class="square" id="sqaure4"></div>
<div class="square" id="sqaure5"></div>
<div class="square" id="sqaure6"></div>
</div>
<script type="text/javascript" src="colorgame.js"></script>
</body>
</html>
I know, there is a better way to do this. I can instead call the randomColors(3) in easy mode, but I want to know what is it that I am doing wrong so that I can avoid it in the future.
Than You
The reason the function is retrieving the wrong colour in easy mode is because you did not remove your hard mode click event listeners from the elements.
To explain the weird behaviour you are seeing where the colour
being logged is rgb(35, 35, 35). What is happening is the original
click event still attached is running first, and going to the
statement's else condition and setting it to that colour. Ie. when you make a
block disappear. To understand this just run through in your head what
would happen if both those click events executed one after another.
First hard than easy.
What you instead want to do is attach your click events once, and use a declared function at global scope. Which you can use for both the easy clicks and hard clicks. The reason you want to declare it is so you can remove it from the hidden squares with removeEventListener.
So in the future, just remember to clean up your click events when changing states. That is the lesson to learn here.
JSFiddle fixing your bug:
https://jsfiddle.net/jx6y0gt1/5/
Here is a fixed code snippet:
var colors = randomColors(6);
var easyColor = [];
var squares = document.querySelectorAll(".square");
function color() {
var a = Math.floor(Math.random() * 250);
var b = Math.floor(Math.random() * 250);
var c = Math.floor(Math.random() * 250);
return "rgb(" + [(a), (b), (c)].join(', ') + ")";
}
function randomColors(num) {
var arr = [];
for (var i = 0; i < num; i++) {
arr.push(color());
}
return arr;
}
// Tried to generate different set of colors for easy mode. Still working on it.
for (var x = 0; x < 3; x++) {
easyColor[x] = color();
}
var easyRandomColor = easyColor[Math.floor(Math.random() * easyColor.length)];
// selecting hard difficulty works same as playing again, hence the reload()
document.getElementById("hard").addEventListener("click", function() {
window.location.reload();
});
document.getElementById("reset").addEventListener("click", function() {
window.location.reload();
});
var squareColor;
// setting up the easy level of the game
document.getElementById("easy").addEventListener("click", function() {
document.getElementById("header").style.background = "#232323";
for (var y = 0; y < 3; y++) {
squares[y].style.background = easyColor[y];
}
for (var z = 3; z < 6; z++) {
squares[z].style.background = "#232323";
squares[z].removeEventListener("click", squareClicked);
}
randomColor = easyColor[Math.floor(Math.random() * easyColor.length)];
document.getElementById("guess").textContent = easyRandomColor;
document.getElementById("easy").classList.add("selected");
document.getElementById("hard").classList.remove("selected");
});
var randomColor = colors[Math.floor(Math.random() * colors.length)];
//changing the RGB in h1 to rgb of one the squares
document.getElementById("guess").textContent = randomColor;
//assigning colors to the squares and adding the click event
for (var j = 0; j < squares.length; j++) {
squares[j].style.background = colors[j];
squares[j].addEventListener("click", squareClicked);
}
function squareClicked() {
var name = this.style.background;
// console.log(name, randomColor);
if (name === randomColor) {
document.getElementById("header").style.background = name;
document.getElementById("display").textContent = "Correct!";
document.getElementById("reset").textContent = "Play again?";
for (var k = 0; k < squares.length; k++) {
squares[k].style.background = name;
}
} else {
this.style.background = "#232323";
document.getElementById("display").textContent = "Try again.";
}
}
body {
background-color: #232323;
margin: 0;
}
html {
margin: 0;
padding: 0;
}
.square {
width: 30%;
/*background: purple;*/
padding-bottom: 30%;
float: left;
margin: 1.66%;
transition: 0.2s ease-in;
border-radius: 6%;
}
#container {
margin: 0 auto;
max-width: 600px;
}
h1,
h3 {
color: white;
padding-top: 1%;
padding-bottom: 0.5%;
margin-top: 0;
margin-bottom: 0;
text-align: center;
}
#header {
transition: 0.2s ease-in;
}
#nav {
margin-top: 0;
padding-top: 0;
background: white;
max-width: 100%;
clear: left;
}
#nav p {
margin: 0 auto;
position: relative;
max-width: 580px;
}
#reset {
position: relative;
}
#hard {
position: absolute;
right: 0;
}
#easy {
position: absolute;
right: 50px;
}
#display {
position: relative;
left: 27%;
}
<body>
<div id="header">
<h3>
The Great
</h3>
<h1>
<span id="guess">number</span>
</h1>
<h3>
Guessing Game
</h3>
</div>
<div id="nav">
<p>
<button id="reset">New Colors</button>
<span id="display"></span>
<button id="easy">Easy</button>
<button id="hard" class="selected">Hard</button>
</p>
</div>
<div id="container">
<div class="square" id="sqaure1"></div>
<div class="square" id="sqaure2"></div>
<div class="square" id="sqaure3"></div>
<div class="square" id="sqaure4"></div>
<div class="square" id="sqaure5"></div>
<div class="square" id="sqaure6"></div>
</div>
</body>
Changes I have made
Add this to the bottom of your code:
function squareClicked() {
var name = this.style.background;
// console.log(name, randomColor);
if(name === randomColor) {
document.getElementById("header").style.background = name;
document.getElementById("display").textContent = "Correct!";
document.getElementById("reset").textContent = "Play again?";
for(var k = 0; k < squares.length; k++) {
squares[k].style.background = name;
}
} else{
this.style.background = "#232323";
document.getElementById("display").textContent = "Try again.";
}
}
Use it as a listener with your elements like this:
for(var j = 0; j < squares.length; j++) {
squares[j].style.background = colors[j];
squares[j].addEventListener("click", squareClicked);
}
In your switch to easy mode, set the value of randomColor from your easy colors, and delete your loop to reattach the click events, they are already there.
randomColor = easyColor[Math.floor(Math.random()*easyColor.length)];
Also a secondary bug when you switch to easy mode you can still click the hidden squares. Deactivate those squares in easy mode so they can not be clicked:
for(var j = 3; j < squares.length; j++) {
squares[j].removeEventListener("click", squareClicked);
}

Javascript global variables not changing?!

I am working on the Odin project's javascript/jquery project to make an etcha sketch(of sorts). Initially the webpage loads fine, but when I attempt to change the size of the "gridval" with a prompt, only the box sizes change but not how many boxes fill the given space.
Thanks for your help in advance.
HTML
<!DCOTYPE html>
<html>
<head>
<title>Java Project</title>
<link rel="icon" href="https://www.codementor.io/assets/page_img/learn-javascript.png">
<link rel="stylesheet" type="text/css" href="css/style.css">
<script src="js/script.js"></script>
<script src="https://ajax.googleapis.com/ajax/libs/jquery/1.11.0/jquery.min.js"></script>
</head>
<body>
<button class="clear_button">Clear screen</button>
<div id="container"></div>
<script>creategrid();</script>
<script>hovereffect();</script>
</body>
</html>
CSS
#container{
width:400px;
height:400px;
background-color: #fc6;
}
.box{
width:52px;
height:52px;
display:inline-block;
margin: 1px;
background-color: #f86;
}
.clear_button{
background-color: #fc6;
color: #ffe;
border:none;
border-radius: 2px;
padding: 10px;
margin: 10px;
}
.clear_button:hover{
background-color: #426;
}
JavaScript
gridval = 16;
function creategrid(){
$(document).ready(function(){
//make grid code
for(var x = 0; x < gridval; x++){
for(var y = 0; y < gridval; y++){
var box = $("<div class='box'></div>");
box.appendTo('#container');
}
}
var width_height = 400/gridval - 2;
var box_class = document.querySelectorAll(".box");
for(var i = 0; i < box_class.length; i++){
box_class[i].style.width = width_height;
box_class[i].style.height = width_height;
}
//clear button code
$(".clear_button").click(function(){
$(".box").css("background-color", "#f86");
var val = gridval;
gridval = prompt("Please enter a value between 2 and 100 for the grid size!", val);
if(gridval != null) {
var width_height = 400/gridval - 2;
var box_class = document.querySelectorAll(".box");
for(var i = 0; i < box_class.length; i++){
box_class[i].style.width = width_height;
box_class[i].style.height = width_height;
}
}
});
});
}
//hover effect code
function hovereffect(){
$(document).ready(function(){
$(".box").hover(function(){
$(this).css("background-color", "#0ba");
}, function(){
$(this).css("background-color", "#9dd");
});
});
}
Your code needs a total reform, see the comments:
//The ready event will only be triggred once; on your page load.
$(function() {
//Default value
var gridval = 16;
/**
* Create the grid
*/
function createGrid(gridval) {
//make grid code
for (var x = 0; x < gridval; x++) {
for (var y = 0; y < gridval; y++) {
var box = $("<div class='box'></div>");
box.appendTo('#container');
}
}
var width_height = (400 / gridval) - 2;
var box_class = document.querySelectorAll(".box");
for (var i = 0; i < box_class.length; i++) {
box_class[i].style.width = width_height+'px'; //You needed +'px' here
box_class[i].style.height = width_height+'px'; //You needed +'px' here
}
}
//Execute the function on load
createGrid(gridval);
//Event delegation on since your elements will be created dynamically
$(document).on({mouseenter: function() {
$(this).css("backgroundColor", "#0ba");//backgroundColor instead of background-color
}, mouseleave: function() {
$(this).css("backgroundColor", "#9dd");
}}, ".box");
//clear button code
$(".clear_button").click(function() {
//$(".box").css("backgroundColor", "#f86"); // you don't need this all the elements will be removed!
var val = gridval;
gridval = prompt("Please enter a value between 2 and 100 for the grid size!", val);
if (gridval != null) {
//Empty the container
$("#container").empty();
createGrid(gridval);
}
});
});
#container {
width: 400px;
height: 400px;
background-color: #fc6;
}
.box {
width: 52px;
height: 52px;
/* Remove inline block */
display: block;
/* Add float*/
float:left;
margin: 1px;
background-color: #f86;
}
.clear_button {
background-color: #fc6;
color: #ffe;
border: none;
border-radius: 2px;
padding: 10px;
margin: 10px;
}
.clear_button:hover {
background-color: #426;
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<button class="clear_button">
Clear screen</button>
<div id="container"></div>

Categories

Resources