JavaScript variable changing between two values on a regular basis [duplicate] - javascript

This question already has answers here:
Is there a better way of writing v = (v == 0 ? 1 : 0); [closed]
(31 answers)
Closed 5 years ago.
I want a variable's value regularly changing between 0 and 1. If I have a variable whose value is 0 (counter = 0), how can I increase it by 1 (counter = 1) after a few seconds, then decrease it back to 0 ( counter = 0) after another few seconds? An endless loop basically is what I want.
I'm assuming this will require setTimeout or setInterval, but I've absolutely no idea how I'd go about this. I'm very unfamiliar with the syntax; I'm very much a newbie. Does anyone have any pointers?
Thanks!

You can create an endless, timed loop by having a function that calls itself at the end via setTimeout. See below.
var count = 0;
function flip() {
count = Number(!count);
console.log(count);
setTimeout(flip, 1000);
}
flip();

A more generic approach:
// possible addition: allow user to stop the timer
const rotate = (time, vals) => {
// TODO: handle incorrect vals (non-empty array) or time (positive number)
let idx = 0;
setInterval(() => idx = (idx + 1) % vals.length, time);
return {
get val() {return vals[idx];}
}
}
const toggle = rotate(1000, [0, 1])
toggle.val //=> depends on when you call it, changes every 1000 ms
// but always either 0 or 1.
One advantage of this is that it doesn't keep the value in global scope where someone else can mess with it, but encapsulates it in a closure.
It's more generic because you can easily change the time between updates and you can choose whatever you want for values (for example, rotate(5000, ['foo', 'bar', 'baz').)

var counter = 0;
var changeCounter = function () {
counter = counter === 0 ? 1 : 0;
console.log('counter', counter);
setTimeout(changeCounter, 1000);
}
changeCounter();

This sounds like homework but try this:
var value = 0;
setInterval(
function() {
value = value===0 ? 1 : 0;
console.log('value =', value);
},
1000
);
setInterval will call the function over and over again without needing to call setTimeout over and over again.

setInterval is what you want, as documented in W3C, you should pass a function and a time interval in milliseconds on how often to execute the code.
var counter = 0;
setInterval(function(){
counter = 1 - counter;
//Do what you want with the result...
//alert(counter);
}, 1000);
https://codepen.io/paulodiogo/pen/xPPOKa?editors=1010
Not using global variable...
https://codepen.io/paulodiogo/pen/KyyMXZ

Related

Continuous progression of a variable (chrome extension)

I want to make a continous counter. I mean, I want to close the page and in the other day open it and continue the counter from where I left.
Like, my counter did count 14235 times in one day. In another day I want it to continue from where I left (14235).
Code I made :
var a = 0; //// a is the "counter"
function count() { ///// function to count
chrome.storage.local.get(['a'], function(value) { return a = value.a;});
a += 1;
chrome.storage.local.set({"a": a}, function(){})
console.log(a)
setTimeout(count, 5000)
}
count()
I get 2 values in console.log, one from 0 and one from 14235, while I want get only one. Help.
Your questions is not getting well seen so I decided help you.
You cannot make a equal the last value, at least I cannot do it.
But you can do a better thing. Call it.
function count() {
if(a === 0){ chrome.storage.local.get(['b'], function(value) { return a = value.b }); } else { chrome.storage.local.set({"b": a}, function(){}) }
/// here, if a = 0 it will get the previous value but if a != 0 it will save the value :D
console.log(a)
setTimeout(count, 100)
a += 1;
}
count()
Hope see you again !

Cycle through strings from an array, displaying one every second [duplicate]

This question already has answers here:
javascript interval
(3 answers)
Closed 4 years ago.
$(function() {
let testOne = 'test one.';
let testTwo = 'test two';
let messageBox = $('messagebox');
let a = ['test:', testOne,'test2:', testTwo];
let i = 1
setInterval(cool, 1000)
function cool() {
messageBox.text(a[1])
}
});
Hi there,
I am new to JS. I am looking to have testOne and testTwo (going to add a few more) display in timers across my screen. I was given help to get this far.
I am trying to, for example, have a word and its English definition appear on the screen in a time loop, rotating the words in a loop. (kind of like a live screen-saver)
What am I missing?
Thank you for your time, help, and effort.
You've got a good start.
As others have mentioned, unless you're using a custom HTML element (i.e. <messagebox>), use # at the beginning of your selector to indicate that "messagebox" is an ID. See jQuery's ID Selector.
$('#messagebox')
Alternatively, use a class and the class selector.
$('.messagebox')
The index of the array element to display is currently hard-coded to 1. We want to increment it upon each iteration so the text will change. But we only want to count up to the number of array elements and then go back to the first one and start over.
Below, I'm using JavaScript's increment and remainder operators to increment i while limiting it to the number of elements in a. Note that the "postfix" method "returns the value before incrementing", so i starts at zero.
a[i++ % a.length]
Working example:
$(function() {
let $messageBox = $('#messagebox');
let testOne = 'test one.';
let testTwo = 'test two.';
let a = ['test:', testOne, 'test2:', testTwo];
let i = 0;
function cool() {
$messageBox.text(a[i++ % a.length])
}
setInterval(cool, 1000);
});
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<div id="messagebox"></div>
EDIT
I don't like letting i count up indefinitely. The math might get wonky after about 9 quadrillion loop iterations, which is how high JavaScript can safely count.
Safe in this context refers to the ability to represent integers exactly and to correctly compare them. For example, Number.MAX_SAFE_INTEGER + 1 === Number.MAX_SAFE_INTEGER + 2 will evaluate to true, which is mathematically incorrect. -- developer.mozilla.org
console.log(Number.MAX_SAFE_INTEGER);
console.log(Number.MAX_SAFE_INTEGER + 1);
console.log(Number.MAX_SAFE_INTEGER + 2);
console.log(Number.MAX_SAFE_INTEGER + 1 === Number.MAX_SAFE_INTEGER + 2);
So, here's what happens after about three million centuries:
$(function() {
let $messageBox = $('#messagebox');
let testOne = 'test one.';
let testTwo = 'test two.';
let a = ['test:', testOne, 'test2:', testTwo];
let i = 9007199254740990;
function cool() {
console.log(i);
$messageBox.text(a[i++ % a.length])
}
setInterval(cool, 1000);
});
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<div id="messagebox"></div>
That's not good enough.
We need this thing running well past the end of time.
Let's keep it safe:
$(function() {
let $messageBox = $('#messagebox');
let testOne = 'test one.';
let testTwo = 'test two.';
let a = ['test:', testOne, 'test2:', testTwo];
let i = 0;
function cycleText() {
console.log(i);
$messageBox.text(a[i]);
i = ++i % a.length;
setTimeout(cycleText, 1000);
}
cycleText();
});
body {
font-size: 2em;
text-align: center;
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<div id="messagebox"></div>
You can easily swap out the messages in your array and update an html element using your code. Instead of passing a hardcoded index in, just increment a number until it reaches the length of the array (n < array.length) and reset it to 0.
I personally would recommend making your messagebox element a div or something out of the box just for readability sake (so nobody comes in and gets confused where messagebox is coming from). However, if you have a specific use case for a custom html element, make sure you're doing it correctly.
https://jsfiddle.net/mswilson4040/oxbn8t14/2/
<messagebox>Initial Value...</messagebox> // custom HTML element called messagebox
$(function() {
let testOne = 'test one.';
let testTwo = 'test two';
let interval = -1;
let messageBox = $('messagebox');
let a = ['test:', testOne,'test2:', testTwo];
// let i = 1 <-- this isn't doing anything
setInterval(cool, 1000)
function cool() {
interval = interval < a.length ? interval += 1 : 0;
messageBox.text(a[interval])
}
});

How to permanently change var?

So, I have a var set in a function and a array(called "card_idx) set up, and I want the var be set to 0 until a certain number is reached in the array but the number doesn't go up in order (1..2..3..4 extra). It jumps around depending on how the person plays ( so it can be like...1...2...2.1....5....3.2...). And I want the var to be set to 0 until a specific number is reached and then it is changed to 1.
I try having it set up like:
var x=0;
if(card_idx == 3.2){
x=1
}
but the moment there no longer on 3.2 it will change back to zero, how do i make it so it will stay 1?
While your example isn't complete enough to reproduce the problem, I imagine you may be running into trouble with variable scope.
JS variables are locally scoped to the function surrounding them, which works to your advantage here. If you declare x at the beginning of the function that goes through your data, the loop can modify it and the value will be retained after the loop completes:
function crunch(data) {
var x = 0;
data.forEach(function (item) {
if (item.index === 3.2) {
x = 1;
}
});
console.log(x);
}
If any item in data had an index of 3.2, x will be set to 1 and printed to the console at the end. The callback to forEach grabs x using closure, but this would work just the same with a for loop.
Using x within the loop, the value will not be reset until crunch returns. Every time crunch is called, x will be set to 0, may be set to 1 if an item has the right index, and will retain that value until the end of crunch.
Now, with forEach, if you were to declare x inside the loop callback rather than in crunch, it would reset every time:
function crunch(data) {
data.forEach(function (item) {
var x = 0;
if (item.index === 3.2) {
x = 1;
}
});
}
Because var operates at the function level, this will not keep its value and will be 0 for every item.
You could try this. Use an extra boolean to check if x has ever been set.
Be aware that your variables are outside the iteration.
var x = 0;
var hasSet = false;
// start looping
if (card_idx == 3.2 && hasSet = false) {
x = 1
hasSet = true;
}
Or maybe (if your question was more clear) this will work out too.
var x = 0;
// start looping
if (card_idx == 3.2 && x <= 0) {
x = 1
}

Is it Possiable to call to previous increments of a variable?

for example lets say i have a loop that is doing basic counting, while the variable is less than 16 the loop will run and at the end of the loop you add 2 to the variable and add one to a "count" variable
what i want to know is if its possible to callback to any of the previous variables for either variable for example can i count all the times count % 2 === 0?
im not quite sure if once a variable makes any kind of change if all previous versions of that variable are gone
http://codepen.io/anon/pen/Gojoxm
var two = 0;
var count = 0;
while ( two < 16) {
two += 2;
count++;
};
console.log(count);
If I understand you right, then no, you cannot. When you assign a new value to a variable, the previous value is lost.
You have to either run this loop again or store intermediate values in an array:
var values = [];
var two = 0;
while (two < 16) {
two += 2;
values.push(two);
}
console.log(values.length); // the same result
Then, you will always be able to do whatever you want with these values.
For example, you can check if there were any odd values:
var anyOddNumbers = values.some(function(x) { return x % 2 === 1; }); // false

storing the value of setInterval

if I had a code like this
count=0
count2=setInterval('count++',1000)
the count2 variable would always set as 2 not the actual value of count as it increases every second
my question is: can you even store the value of the seInterval() method
The return value of setInterval() is an ID number that can be passed to clearInterval() to stop the periodically executed function from running another time. Here's an example of that:
var id = setInterval(function() {
// Periodically check to see if the element is there
if(document.getElementById('foo')) {
clearInterval(id);
weAreReady();
}
}, 100);
In your example, if you want count2 to have the same value as count, you could use:
var count = 0, count2 = 0;
setInterval(function() {
// I wrote this on two lines for clarity.
++count;
count2 = count;
}, 1000);
setInterval returns an ID which you can later use to clearInterval(), that is to stop the scheduled action from being performed. It will not be related to the count values in any way.
var count=0;
function incrementCount(){
count++;
}
setTimeout("incrementCount()", 1000);

Categories