jQuery - Increment number every second but onclick decrease - javascript

So I am trying to increase a number every second. So far this works fine but I have an additional condition that doesn't really works and I don't know why.
What I want is that after the value hits 10 or more you can click on a div and something happens with that div but also the value decreases by 10.
My Code:
var counter = 0;
var increment = 10;
var div = document.getElementById('number');
var st = setInterval(function(){
div.innerHTML = ++counter;
if (counter >= 10){
jQuery('#red-block').click(function(e) {
jQuery(this).css('border-radius','15px');
counter = counter -10;
});
}
},1000);
#red-block {
height: 40px;
width: 40px;
background-color: #ff0000;
display:block;
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<div id="number">1</div>
<div id="red-block"></div>
The problem is that after the counter hits 10 I click, the div changes but the value jumps for example to -17 and also I can click on the div as many times as I want and every times it decreases a big amount. This should only be possible each time the counter hits 10. Anybody has a solution for me what I am doing wrong? I believe it has something to do with setInterval

It happens because you are registering a new click event handler inside your setInterval functions. Move the click registration outside of the setInterval
function.
var counter = 0;
var increment = 10;
jQuery('#red-block').click(function (e) {
if (counter >= 10) {
jQuery(this).css('border-radius', '15px');
counter = counter - 10;
}
});
var div = document.getElementById('number');
var st = setInterval(function () {
div.innerHTML = ++counter;
}, 1000);

Separate this to your setInterval function and then put your if statement inside the click function
jQuery('#red-block').click(function(e) {
if (counter >= 10){
jQuery(this).css('border-radius','15px');
counter = counter -10;
}
});
var counter = 0;
var increment = 10;
var div = document.getElementById('number');
var st = setInterval(function(){
div.innerHTML = ++counter;
},1000);
jQuery('#red-block').click(function(e) {
if (counter >= 10){
jQuery(this).css('border-radius','15px');
counter = counter -10;
}
});
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<div id="number">1</div>
<div id="red-block">Click Me</div>

The issues are:
You are registering your click event handler every time the
timer function runs, so a single click will trigger the callback
function many times. Just register it one time and within that
callback, check to see if the count should be adjusted.
Even when decreasing the counter by 10, it still increases by one.
Instead, just track the amount you are changing the count by (1 or
-10) and update the output based on the current "change by" value.
Also, since you are using jQuery, go ahead and use it (you've already taken the plunge).
Also (FYI), don't use .innnerHTML when you aren't setting any HTML, use .textContent for that. And, since you are using jQuery, you can use .text() instead of .textContent.
// Here's the jQuery way to get a reference to elements by their id's:
var $div = $('#number');
var $block = $('#red-block')
var counter = 1; // This will be the amount to change by
var count = 0; // This will be the current count at any given time
// Just set up the click event handler once, not every time the interval runs
$block.on("click", function(e) {
// But only do something if the count is right
if (count >= 10){
$(this).css('border-radius','15px');
counter = -10;
}
});
var st = setInterval(function(){
// Now, just adjust the count by the counter
count = count += counter;
$div.text(count); // <-- The jQuery way to set the text of an element
}, 1000);
#red-block {
height: 40px;
width: 40px;
background-color: #ff0000;
display:block;
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<div id="number">1</div>
<div id="red-block"></div>

Related

Change an image to a new image with Javascript each time the image is clicked

I have a folder of images and I want to replace the one currently being displayed with another image each time that it is clicked on.
I've managed to make this happen once - i.e. to make the if statement work, but I can't get to the elif statement. Why is the elif condition not being met. Everytime I click it just repeats the if statement, even though the console log shows that the backgroundImage is now budgies: url("http://localhost:3000/images_diamonds/budgies.jpg")
// For clicking on the image
document.querySelector('.diamond-pic').addEventListener('click', () => {
let elem = document.getElementById('pic1');
let ht = window.getComputedStyle(elem, null).getPropertyValue("background");
console.log(ht)
if (document.getElementById('pic1').style.backgroundImage="url(../../images_diamonds/ghecko.jpg)") {
document.getElementById("pic1").style.backgroundImage = "url('../../images_diamonds/budgies.jpg'";
console.log('if achieved')
} else if (document.getElementById('pic1').style.backgroundImage="url(../../images_diamonds/budgies.jpg)") {
document.getElementById("pic1").style.backgroundImage = "url('../../images_diamonds/Christmas_Beetle.jpg'";
console.log('else if achived')
} else {
console.log('else achieved')
}
});
The simplest way to do this is to keep the image names in an array and then just advance the image to the next one in the array when it's clicked.
let counter = 0;
let imgs = [
"https://static4.depositphotos.com/1026550/376/i/600/depositphotos_3763236-stock-photo-gold-star.jpg",
"https://previews.123rf.com/images/lineartestpilot/lineartestpilot1803/lineartestpilot180302423/96543894-cartoon-shooting-star.jpg",
"https://encrypted-tbn0.gstatic.com/images?q=tbn:ANd9GcTk5tGujYXbv4f9A0pvSuOWC6IhljTzmy4WBw&usqp=CAU",
"http://www.webweaver.nu/clipart/img/nature/planets/smiling-gold-star.png",
"https://upload.wikimedia.org/wikipedia/commons/thumb/3/34/Red_star.svg/2000px-Red_star.svg.png"
];
document.querySelector("img").addEventListener("click", function(event){
this.src = imgs[counter];
// As long as the counter is less than the last index in the array
// increase the counter. Otherwise, start over.
counter = counter < imgs.length-1 ? counter+1 : 0;
});
img { width: 200px;}
<img src="https://previews.123rf.com/images/lineartestpilot/lineartestpilot1802/lineartestpilot180274309/95545188-shooting-star-decorative-cartoon.jpg">
And here's an example when the images are used as backgrounds:
let counter = 0;
let imgs = [
"https://static4.depositphotos.com/1026550/376/i/600/depositphotos_3763236-stock-photo-gold-star.jpg",
"https://previews.123rf.com/images/lineartestpilot/lineartestpilot1803/lineartestpilot180302423/96543894-cartoon-shooting-star.jpg",
"https://encrypted-tbn0.gstatic.com/images?q=tbn:ANd9GcTk5tGujYXbv4f9A0pvSuOWC6IhljTzmy4WBw&usqp=CAU",
"http://www.webweaver.nu/clipart/img/nature/planets/smiling-gold-star.png",
"https://upload.wikimedia.org/wikipedia/commons/thumb/3/34/Red_star.svg/2000px-Red_star.svg.png"
];
document.querySelector("div").addEventListener("click", function(event){
this.style.background = "url(" + imgs[counter] + ")";
// As long as the counter is less than the last index in the array
// increase the counter. Otherwise, start over.
counter = counter < imgs.length-1 ? counter+1 : 0;
});
div { width: 300px;
height:300px; border:1px solid black; background:url("https://previews.123rf.com/images/lineartestpilot/lineartestpilot1802/lineartestpilot180274309/95545188-shooting-star-decorative-cartoon.jpg");
}
<div></div>

How to assign each variable a partner variable?

Sorry, if the title doesn't make too much sense, it's just that i don't even know what my problem is to begin trying to solve it. This code was meant to execute a function every second for 10 times that adds a div element, gives it a class, gives it a starting left position and starts moving it left. I've succeeded to create the div, give it a class and append it but where the problem comes in is making it move left.
I wanted to move it by having a variable that keeps track of the div left attribute, subtracting from that variable and always setting the divs left attribute to be equal to that variable, but it doesn't seem to be working correctly because all created divs follow one of that position tracking variable.
setInterval(function() {
var Count = 0;
var createddiv = document.createElement("div");
var divX = 1000;
if (Count < 1000) {
Count = Count + 100;
createddiv.classList.add("NewDiv");
createddiv.style.left = divX + "px";
document.body.appendChild(createddiv);
divX = divX - 100;
createddiv.style.left = divX + "px";
}
}, 1000)
From what I understand you want to move div from right to left in 10 seconds
JS
(function() {
var Count = 0;
var divX = 1000;
var createddiv;
var intervalRef = setInterval(function() {
if (Count < 1000) {
if(createddiv !== undefined) {
createddiv.parentNode.removeChild(createddiv);
}
createddiv = document.createElement("div");
Count = Count + 100;
createddiv.classList.add("NewDiv");
createddiv.style.left = divX + "px";
document.body.appendChild(createddiv);
divX = divX - 100;
createddiv.style.left = divX + "px";
} else {
clearInterval(intervalRef);
}
}, 1000);
})();
CSS
.NewDiv {
height: 100px;
width: 100px;
background-color: red;
position: relative;
}
Here is working demo in jsfiddle
Suggestion instead of creating new div every time, add one div and change it's left property.

Play Boostrap Popover on loop

DEMO: http://jsfiddle.net/0s730kxx/
I'm trying to open Bootstrap Popover to auto-open on loop but so far I've have manage only to auto-play once.
HTML:
<div class="container">
Hover Left |
Hover Right |
Click Me
</div>
JS:
$(document).ready(function(){
var time = 1000;
var len = $('.myclass').length;
var count = 0;
var fun = setInterval(function(){
count++;
if(count>len){
clearInterval(fun);
}
$('.p'+count).popover('show');
if(count>1){
var pre = count-1;
$('.p'+pre).popover('hide');
}
}, time);
});
Could anyone help? I want it on loop so it plays forever or atleast 10 or 20 times.
Modify javascript part of your fiddle like this:
$(document).ready(function(){
var time = 1000;
var len = $('.myclass').length;
var count = 0;
var fun = setInterval(function(){
count++;
if(count>len){
$('.p'+(count-1)).popover('hide');
count = 1;
//clearInterval(fun);
}
$('.p'+count).popover('show');
if(count>1){
var pre = count-1;
$('.p'+pre).popover('hide');
}
}, time);
});
Since you are not clearing the interval in this modified snippet, it will run forever as you expected.
Thats because you have added line
if(count>len){
clearInterval(fun);
}
After showing them 1 time count is 3 and clearInterval(fun) is called
which terminates further call to function fun().
Original comment: You can't clear the interval and expect the loop to continue! Instead of clearing set the count back to 0. But you'll also need to remember to hide the last popover.
var fun = setInterval(function(){
count++;
$('.p' + count).popover('show');
if(count > 1){
$('.p' + (count - 1)).popover('hide');
}
if(count > len){
count = 0;
}
}, time);
Here is a fiddle: http://jsfiddle.net/89gcqnfm/
Simplicity and modular arithmetic are your friends:
$(document).ready(function(){
var time = 1000;
var eles = $('.myclass');
var count = 0;
var fun = setInterval(function(){
if(eles.length < 1)
return (console.log("No elements found!")&&!1) || clearInterval(fun);
eles.eq(count%eles.length).popover('hide');
eles.eq(++count%eles.length).popover('show');
}, time);
});
https://jsfiddle.net/L2487dfy/

How to get around javascript timeout of 0

Here is a fiddle: http://jsfiddle.net/hB7gY/16/
I have the following code which controls a slideshow with four quadrants. The idea is to rotate through the slideshow and dynamically change the slides based upon a predefined time frame. For instance, many times a slide has a value of 0, which means instantly load the next slide in the series.
The problem is that when using fadeIn() or animate(), they take longer than the timeout of 0. I've tried incrementing my counters when this happens, but that doesn't work.
EDIT: I think I may not have been clear in my question, but the goal is to be able to load the next image instantly, but still maintain the animation effect on the previous image, so essentially it will appear as if both images are animating simultaneously.
var slide_array = <?php echo json_encode( $slides ); ?>;
jQuery(document).ready(function(){
var c =0;
var slide = 0;
var counter = 1000;
for (var i=0;i<slide_array.length;i++){
jQuery('#slide_'+i).attr('src', slide_array[i]["url"]);
}
var intFn = function(){
clearTimeout(interval);
c++;
slide++;
if (slide == slide_array.length) { slide = 0; }
if (c == 4){ c = 0; }
jQuery('#slide_'+c).attr('src',slide_array[slide]['url']).animate({
opacity: 0.5
}, 100, function() {
jQuery('#slide_'+c).attr('src',slide_array[slide]['url']).animate({
opacity: 1
}, 100);
});
counter = slide_array[slide]['duration'] * 1000;
//if (counter < 1000 ) { counter = 400; }
interval = setTimeout(intFn, counter);
}
var interval = setTimeout(intFn, 2500);
});

Overriding CSS onclick with while and setTimeOut

I am wanting to change/override the .left property of my css with javascript onclick. This I have managed to do, only I want the property to change in stages (every 1 sec) decrementing by 5em until it reaches 0em. Unfortunately, when I click on the ID to start the function, it just jumps from 30em to 0em. Instead of 30,25,20,15,10,5 etc every 1 sec. Any ideas? (No Jquery please!)
window.onload = function(){
document.getElementById("objection1").onclick = firstScroll;
}
function firstScroll(){
var content = document.getElementById("intB");
var thisNum = 30;
var em = "em";
function doScroll(){
content.style.left = thisNum+em;
}
while(thisNum > 0){
setTimeout(doScroll, 1000);
thisNum -= 5;
}
}
Your problem is when you call the while loop, the next interval is not fired yet, but your thisNum is already set to 0 after finishing the loop. So when the doScroll is fired, thisNum is 0 already.
Try:
window.onload = function(){
document.getElementById("objection1").onclick = firstScroll;
}
var thisNum = 30;
var em = "em";
function firstScroll(){
setTimeout(doScroll, 1000);
}
function doScroll(){
thisNum -= 5;
var content = document.getElementById("intB");
content.style.left = thisNum+em;
if (thisNum > 0){
setTimeout(doScroll, 1000);
}
}
Yes, you're repeatedly decrementing thisNum in a while loop. setTimeout is a function which is called in one second, but the while loop keeps going. doScroll should be decrementing the em value, not a while loop outside. This uses setInterval instead of setTimeout, but either will do..
var intTimer;
function doScroll(){
thisNum -= 5;
content.style.left = thisNum+"em";
if (thisNum <= 0){
window.clearInterval(intTimer);
}
}
intTimer = setInterval( doScroll, 1000);

Categories

Resources