Hiding and unhiding a particular element - javascript

I'm trying to hide a particular element on my browser game.
When it reaches the point of being visible it has to stay visible.
At the moment I've tried a few approaches but none of them seem to do the last part which is keeping it visible when the number of clicks goes back under the amount needed to make it visible.
CSS:
upgrade3 {
display: none;
}
js1(which completely doesn't work):
function showPerk() {
if (clicks >= price3reached || totalupgradeperk3 > 0) {
do{
document.getElementById("upgrade3").style.display =="block";
}
while(document.getElementById("upgrade3".style.display === 'none'));
}
update();
}
js2 (works but hides the element when going under the amount needed):
if (blnhideperk = true) {
if (clicks >= price3reached || totalupgradeperk3 > 0) {
document.getElementById("upgrade3").style.display = "block";
blnhideperk === false;
} // use === its something wierd about js = / == / === all do different comparisons
else {
document.getElementById("upgrade3").style.display = "none";
}
}
upgrade

Try
document.getElementById("upgrade3").style.display = "none";
Note the 1 equal sign, not 2 or 3, as those have other uses.

if (blnhideperk = true){
if (clicks >= price3reached || totalupgradeperk3 > 0){
document.getElementById("upgrade3").style.display = "block";
blnhideperk === false;}}
and moving
document.getElementById("upgrade3").style.display = "block";
out of the loop istead of in the else statement
seemed to do the trick

Related

How i make an element to be shown or not?

anchorArrows is an element that if I click the checkbox it must be shown and if it's not checked it must be hidden. The classList hidden and show are CSS classes with opacity 0 and 1
let q = document.getElementById("Q").value;
let q2 = document.getElementById("q2").value;
const anchorArrows = document.getElementById("anchor");
if((chkQ.checked == true) && (chkQ2.checked == false)){
anchorArrows.classList.add("show");
anchorArrows.classList.remove("hidden");
if(q > 0){
flechas(0,"x");
}else{
flechas(180,"x");
}
}else{
anchorArrows.classList.remove("show");
anchorArrows.classList.add("hidden");
}
if((chkQ2.checked == true) && (chkQ.checked == false)){
anchorArrows.classList.add("show");
anchorArrows.classList.remove("hidden");
if(q > 0){
flechas(0,"y");
}else{
flechas(180,"y");
}
}else{
anchorArrows.classList.remove("show");
anchorArrows.classList.add("hidden");
}
CSS:
.hidden{
opacity: 0;
}
.show{
opacity: 1;
}
You need to use else if and one else. The issue you have is the first if can be true, but the second else will wipe away the class.
if (chkQ.checked && !chkQ2.checked) {
anchorArrows.classList.add("show");
anchorArrows.classList.remove("hidden");
if (q > 0) {
flechas(0, "x");
} else {
flechas(180, "x");
}
} else if (chkQ2.checked && !chkQ.checked) {
anchorArrows.classList.add("show");
anchorArrows.classList.remove("hidden");
if (q > 0) {
flechas(0, "y");
} else {
flechas(180, "y");
}
} else {
anchorArrows.classList.remove("show");
anchorArrows.classList.add("hidden");
}
And to get rid of repeated code
let isValid = false;
if ((!chkQ.checked && chkQ2.checked) || (chkQ.checked && !chkQ2.checked)) {
isValid = true;
const num = +q > 0 ? 0 : 180;
const code = chkQ.checked ? "x" : "y";
flechas(num, code);
}
anchorArrows.classList.toggle("show", isValid);
anchorArrows.classList.toggle("hidden", !isValid);
Personally, I wouldn't use classes to change opacity, as multiple variables can affect the outcome of it. Instead, I would put opacity in the original Id/Class in the CSS, and use .style.opacity to change it.
For Example:
CSS:
#box {
opacity:1;
}
HTML:
<div id="box"></div>
Javascript:
document.getElementById('box').style.opacity = .5;
In your code, it would be anchorArrows.style.opacity = 1; for show, and anchorArrows.style.opacity = 0; for hidden.

classList and scroll event

I have some simple script to adding classes to my navbar relied on pageYOffset:
var navContainer = document.querySelector('.nav-container');
var firstTitle = document.querySelector('.first-title')
document.addEventListener('scroll',function(){
if(window.pageYOffset < 75){
navContainer.classList.remove('nav-action','yellow');
}else if(window.pageYOffset > 75){
navContainer.classList.add('nav-action')
}else if(window.pageYOffset<firstTitle.offsetTop){
navContainer.classList.remove('yellow');
}
else if(window.pageYOffset > firstTitle.offsetTop){
navContainer.classList.add('yellow');
};
});
my trouble is this that last condition is fulfilled when window.pageYOffset is bigger than firstTitle.offsetTop, writing this line between brackets in the console returns true, but nothing happens when I'm trying this all code.
Unless window.pageYOffset === 75, none of these lines will actually be executed. The previous conditions already catch all the cases.
I would suggest treating nav-action and yellow separately:
var navContainer = document.querySelector('.nav-container');
var firstTitle = document.querySelector('.first-title')
document.addEventListener('scroll', function() {
if (window.pageYOffset < 75) {
navContainer.classList.remove('nav-action');
} else {
navContainer.classList.add('nav-action')
}
if (window.pageYOffset < firstTitle.offsetTop) {
navContainer.classList.remove('yellow');
} else {
navContainer.classList.add('yellow');
}
});

filtered rows in navigable table

UPDATE:
I finally found a solution (with a while loop, in code below) but there is a problem: when I navigate search results (so elements which are not hidden), after navigating a bit in filtered results, the navigation stops working and I get a "TypeError: rows[selectedRow] is undefined"
if(selectedRow >= rows.length){
selectedRow = 0;
} else if(selectedRow < 0){
selectedRow = rows.length-1;
}
This part works for the full list but not in the filtered list. I think the while loop is causing this. How can I fix this please ?
Navigation:
var rows = document.getElementById("pokemons-list").children[1].children;
var selectedRow = 0;
document.body.onkeydown = function(e){
//Clear out old row's color
rows[selectedRow].style.backgroundColor = "#FFFFFF";
//Calculate new row
if(e.keyCode == 38){
if(rows[selectedRow].style.display == "none"){
while(rows[selectedRow].style.display == "none"){
selectedRow--;
}
}else {
selectedRow--;
}
} else if(e.keyCode == 40){
if(rows[selectedRow].style.display == "none"){
while(rows[selectedRow].style.display == "none"){
selectedRow++;
}
}else {
selectedRow++;
}
} else if(e.keyCode == 13){
Pokemon_ID = selectedRow + 1;
document.getElementById("id-input").value = Pokemon_ID;
document.getElementById("id-input").click();
}
if(selectedRow >= rows.length){
selectedRow = 0;
} else if(selectedRow < 0){
selectedRow = rows.length-1;
}
//Set new row's color
rows[selectedRow].style.backgroundColor = "dodgerblue";
};
It looks like your filter function hides rows that don't match the string that you've entered. The hiding is implemented by setting the display property to "none".
When you navigate, can't you ignore table rows that have their display property set to "none"?
Update: You can check the value of rows[selectedRow].style.display before performing rows[selectedRow].style.backgroundColor = "dodgerblue". If the value is "none", repeat the change that you made to selectedRow within the function (whether it was an increment or a decrement).
Update 2: Consider the block of code below:
while(rows[selectedRow].style.display == "none"){
selectedRow++;
}
If the value of selectedRow on entering the while loop is 0 and rows[0].style.display has the value "none" then the body of the loop changes the value of selectedRow to -1. The control will immediately go back to the loop guard and it'll try to check the value of
rows[-1].style.display. This is something you want to avoid, so why don't you try checking selectedRow after every line where you change it? A quick solution would involve changing the loop-bodies of your while loops:
while(rows[selectedRow].style.display == "none"){
selectedRow++;
if(selectedRow >= rows.length){
selectedRow = 0;
}
}
and
while(rows[selectedRow].style.display == "none"){
selectedRow--;
if(selectedRow < 0){
selectedRow = rows.length-1;
}
}

How do I smooth all the JavaScript transitions?

So, I made some interaction that are triggered every click, I could've used switch too but I wanted to make it more readable.
All these transitions have something in common and that is they finish in an instant, so I tried to use css * { transition: all 0.5s; } and even body {
transition: all 0.5s; } but the transitions don't seem to smooth. Not even the background change is not smooth. And every time the innerHTML changes it happens instantly and I am trying not to mess myself fading in span after span. So the question is, how do I make all transitions smooth? Thanks in advance :D
var text = 0;
function changeText() {
text += 1;
if (text === 0) {
document.getElementById('secHeader').innerHTML = "Click anywhere to begin.";
}
else if (text === 1) {
document.getElementById('secHeader').innerHTML = "Are you ready?";
}
else if (text === 2) {
document.getElementById('secHeader').innerHTML = "Let's begin then...";
}
else if (text === 3) {
document.getElementById('secHeader').innerHTML = "You're about to experience a journey you'll never forget.";
}
else if (text === 4) {
document.getElementById('ImageBox').style.display = "none";
document.body.style.background = "black";
}
else if (text === 5) {
document.getElementById('thHeader').style.display = "block";
}
else if (text === 6) {
document.getElementById('thHeader').innerHTML = "You must be very curious then..."
}
else if (text === 7) {
document.getElementById('thHeader').style.visibility = "hidden";
document.getElementById('ftHeader').style.display = "block";
}
else if (text === 8) {
document.getElementById('ftHeader').innerHTML = "We can show you something..."
}
else if (text === 9) {
document.getElementById('ftHeader').style.visibility = "hidden";
document.getElementById('ffHeader').style.display = "block";
}
else if (text === 10) {
document.getElementById('ffHeader').innerHTML = "Let's see..."
}
else if (text === 11) {
document.getElementById('ffHeader').style.visibility = "hidden";
document.body.style.background = "linear-gradient(to right, #0f2027,
#203a43, #2c5364)";
}
}
If you use 'display: none' and then 'block' the transition property won't work. The element should be in the DOM, and 'display: none' deletes element from the DOM.
There are some CSS properties which can being affected by transition's effect.

Toggle Menus using buttons in JS - But it shows both menus

i want to toggle two menus offered by two buttons.the issue is when i click on button one, it shows the menu bound with button one but when i click the other, it shows both instead of hiding the first one and vice versa, on my login page. The menus are identified by the ids of; 'reqpwd' and 'signup' in html / JS. What is worng? also suggest improvement in code if possible. My JS code:
<script>
window.onload = function() {
document.getElementById('reqpwd').style.display = 'none';
document.getElementById('signup').style.display = 'none';
};
function chk(elm) {
var signup_ = signup.id;
var reqpwd_ = reqpwd.id;
elm_ = elm.id;
if (elm_ == reqpwd_){
hide(signup_);
show(reqpwd_);
}
if (elm_== signup_){
hide(reqpwd_);
show(signup_);
}
};
function show(abc) {
var menuBox = document.getElementById(abc);
if(menuBox.style.display == "none") { // if is menuBox displayed, hide it
menuBox.style.display = "block";
} };
function hide(abc){ // if is menuBox hidden, display it
var menuBox = document.getElementById(abc);
if(menuBox.style.display == "block"){
menuBox.style.display == "none";
}
};
</script>
Instead of menuBox.style.display == "none"; try using menuBox.style.visibility== "hidden";
Edit:
I have changed a few things in your code. Didn't make a whole lot of sense to me the way you're setting the styles on load (missing HTML), so I had to use IDs that made sense to me.
Edit:
Ok, my bad. I updated the code. I think the problem is on hide you're using double equals instead of single equals on menuBox.style.display == "none";. Thus the menu is never hiding.
https://codepen.io/juanferrer/pen/qmOmWa
Finally i have landed into something like this using the flag variable as a state indicator.. now the only requirement is to check toggle as well as disappear the relevant menu by the same button..i.e. if signup menu is already open, the signup or reset button should close it and vice versa.
window.onload = function() {
document.getElementById('regd').style.visibility = 'hidden'; //regisration msg
document.getElementById('rset').style.visibility = 'hidden'; //reset msg
document.getElementById('reqpwd').style.display = 'none';
document.getElementById('signup').style.display = 'none';
};
var flag = 0;
function chk(elm) {
var signup_ = signup.id;
var reqpwd_ = reqpwd.id;
elm_ = elm.id;
if (elm_ == reqpwd_ && flag === 0 || elm_ == reqpwd_ && flag == 2) {
flag = 1;
hide(signup_);
show(reqpwd_);
}
if (elm_ == signup_ && flag === 0 || elm_ == signup_ && flag == 1) {
flag = 2;
show(signup_);
hide(reqpwd_);
}
if (elm_ == reqpwd_ && flag == 1 || elm_ == signup_ && flag == 2) {
hide(elm_);
flag = 0;
}
};
function show(abc) {
var menuBox = document.getElementById(abc);
if (menuBox.style.display === "none") { // if is menuBox hidden, display it
menuBox.style.display = "block";
}
};
function hide(abc) { // if is menuBox
var menuBox = document.getElementById(abc);
if (menuBox.style.display === "block") { //if displayed, hide it
menuBox.style.display = "none";
}
};

Categories