Problems with setInterval/clearInterval - javascript

I have some code which I am trying to use for a gallery, it takes URLs from an array then changes an image on the page. Starting the gallery works fine
var move = window.setInterval(function(){gallery_switch_script()},2000);
But when I try to clear it within a function it doesn't clear the interval but the rest of the function does work but it only works once
function bwd(){
clearInterval(move);
var move = setInterval(function(){gallery_switch_script()},2000);
var b = i-1;
var valueBwd = array[b];
$(".galleryImg").fadeOut(1500,function(){$(".galleryImg").attr("src",valueBwd);});
$(".galleryImg").fadeIn(1500);
}
This spits out no errors at all. This seems to be the only part of the code which doesn't want to work, apart from the fast-forward button which contains a clearInterval() also.
var array = new Array();
array[0] = "";
array[1] = "img/gallery_1.png";
array[2] = "img/gallery_2.png";
array[3] = "";
array[4] = "";
array[5] = "";
array[6] = "";
array[7] = "";
array[8] = "";
array[9] = "";
array[10] = "";
array[11] = "";
array[12] = "";
array[13] = "";
array[14] = "";
array[15] = "";
array[16] = "";
array[17] = "";
array[18] = "";
array[19] = "";
window.onload=function(){var move = window.setInterval(function() {gallery_switch_script()},2000);};
var i = 0;
function gallery_switch_script(){
var value = array[i]
i+=1;
$(".galleryImg").fadeOut(1500,function(){$(".galleryImg").attr("src",value);});
$(".galleryImg").fadeIn(1500);
}
function fwd(){
window.clearInterval(move);
var move = setInterval(function(){gallery_switch_script()},10000);
gallery_switch_script();
}
function bwd();
clearInterval(move);
var move = setInterval(function(){gallery_switch_script()},2000);
var b = i-1;
var valueBwd = array[b];
$(".galleryImg").fadeOut(1500,function(){$(".galleryImg").attr("src",valueBwd);});
$(".galleryImg").fadeIn(1500);
}
This is all of my code.

because move is a local variable and not global.
window.onload=function(){var move = window.setInterval(function() {gallery_switch_script()},2000);};
It is defined inside the window.onload "scope" and is not accessible outside of it.
So define move outside of the function and it will work
var move;
window.onload=function(){move = window.setInterval(function() {gallery_switch_script()},2000);};
and
function bwd();
clearInterval(move);
move = setInterval(function(){gallery_switch_script()},2000);
var b = i-1;
var valueBwd = array[b];
$(".galleryImg").fadeOut(1500,function(){$(".galleryImg").attr("src",valueBwd);});
$(".galleryImg").fadeIn(1500);
}

Related

Javascript a TD click and get row cell data

I have this in Jquery all works:
$(document).ready(function() {
$("#checktable td:nth-child(1)").click(function(event){ // This line I need converted
event.preventDefault();
var $td = $(this).closest('tr').children('td'); //This line I need converted
var tid = $td.eq(0).text();
var tdate = $td.eq(1).text();
var tdescribe = $td.eq(2).text();
var wd = $td.eq(3).text();
var dep = $td.eq(4).text();
// ... more code
I need a similar thing in javascript, above only first td is clicked.
My javascript code so far:
function addRowHandlers() {
var table = document.getElementById("checktable2");
var rows = table.getElementsByTagName('tr');
var tid = '';
var tdate = '';
var tdescribe = '';
var wd = '';
var dep = '';
var tisclr = '';
for (var i = 1; i < rows.length; i++) {
rows[i].i = i;
rows[i].onclick = function() {
tid = table.rows[this.i].cells[0].innerText;
tdate = table.rows[this.i].cells[1].innerHTML;
tdescribe = table.rows[this.i].cells[2].innerHTML;
wd = table.rows[this.i].cells[3].innerHTML;
dep = table.rows[this.i].cells[4].innerHTML;
// ... etc more code
The javascript works but any td can be clicked, I am after only:
The first td clicked
Then get parent row
Then all child td's
I have been over dozens of StackOverflow posts and other sites as well... Thanks
And how do I add the event.preventDefault() to regular JS in such a case.
You'd bind the handler to the first .cell.
rows[i].cells[0].onclick = function () {
And then in the handler, access the .parentNode of this to get the row.
And since you're not closing over any variables except those in the function itself (and outside that function, of course), I'd just use a single handler instead of recreating it in the loop.
function addRowHandlers() {
var table = document.getElementById("checktable2");
var rows = table.getElementsByTagName('tr');
var tid = '';
var tdate = '';
var tdescribe = '';
var wd = '';
var dep = '';
var tisclr = '';
for (var i = 1; i < rows.length; i++) {
rows[i].i = i;
rows[i].cells[0].onclick = handler;
}
function handler() {
var row = this.parentNode;
tid = this.innerText;
tdate = row.cells[1].innerHTML;
tdescribe = row.cells[2].innerHTML;
wd = row.cells[3].innerHTML;
dep = row.cells[4].innerHTML;
// etc more code
}
}
I'd probably use a loop to get the desired content too. Maybe like this:
function handler() {
var row = this.parentNode;
var props = ["tid", "tdate", "tdescribe", "wd", "dep"];
var content = props.reduce(function(obj, key, i) {
obj[key] = row.cells[i][i ? "innerHTML" : "innerText"];
return obj;
}, {});
// etc more code
}
Now instead of variables, you have properties of the content object.

Array doesent update values

I want my array to be updated as soon as I run the replace function. What actually happens is that all the elements of my array get deleted here is the code:
var Person = [];
var editPersonId = 0;
var Details = [];
function AddPerson() {
this.Details[0] = document.getElementById("fname").value;
this.Details[1] = document.getElementById("lname").value;
this.Details[2] = document.getElementById("age").value;
this.Details[3] = document.getElementById("mobil").value;
this.Details[4] = document.getElementById("adress").value;
Person.push(this.Details);
}
function Clear(){
document.getElementById("fname").value = "";
document.getElementById("lname").value = "";
document.getElementById("age").value ="";
document.getElementById("mobil").value = "";
document.getElementById("adress").value = "";
}
function ShowContacts(){
var testIt= document.getElementById("search").value;
var i=0, k=0, indx=[], msg;
for ( i=0; i < Person.length; i++)
{
for ( k=0; k<=4; k++)
{
if (Person[i][k] === testIt)
{
document.getElementById("newFname").value = Person[i][0];
document.getElementById("newLname").value = Person[i][1];
document.getElementById("newAge").value = Person[i][2];
document.getElementById("newMobil").value = Person[i][3];
document.getElementById("newAdress").value = Person[i][4];
console.log(1);
editPersonId = i;
break;
}
}
}
}
function Replace(){
Person[editPersonId][0] = document.getElementById("newFname").value;
Person[editPersonId][1] = document.getElementById("newLname").value;
Person[editPersonId][2] = document.getElementById("newAge").value;
Person[editPersonId][3] = document.getElementById("newMobil").value;
Person[editPersonId][4] = document.getElementById("newAdress").value;
}
function Run(){
this.AddPerson();
this.Clear();
}
You override the contents of your Person insde of replace().
Person[editPersonId][0] = ...
While editPersonId is 0, means that the item you inserted in AddPerson will be overriden. And before replace(), you run clear(), which empties your inputs. So the elements don't get 'deleted', you replace them with an empty string.
You might wanna look into this article

JavaScript cannot find method a second time?

I'm attempting to build a poker game. The method in question is very simple, and it works when it runs the first time.
This part isn't perfect convention because I'm just using it to test my methods:
var $ = function (id) { return document.getElementById(id); };
var test = function() {
var deck = new POKER.Deck();
var hand = new POKER.Hand();
for (var i = 0; i < 7; i++){
hand.addCard(deck.dealCard());
}
hand.sortByRank();
for (var j = 0; j < 7; j++){
var img = document.createElement("img");
var card = hand.getCardAtIndex(j); //** <------- WORKS HERE**
img.src = card.getImage();
$("images").appendChild(img);
}
var testHand = new POKER.Hand();
testHand = hand.removePairs();
for (var k = 0; k < testHand.length; k++) {
var img2 = document.createElement("img");
var card2 = testHand.getCardAtIndex(k); // **<------FAILS HERE**
img2.src = card2.getImage();
$("handImg").appendChild(img2);
}
};
window.onload = function() {
test();
};
The first and second loop work, and the hand is displayed and everything. When it gets to the last loop, the debugger tells me "TypeError: testHand.getCardAtIndex is not a function"
I was attempting to test the removePairs method (to test for straights more easily), and when watching the variables in the debugger, testHand clearly gets populated correctly. The method seems to work just fine.
getCardAtIndex:
POKER.Hand.prototype.getCardAtIndex = function(index) {
return this.cards[index];
};
removePairs:
POKER.Hand.prototype.removePairs = function(){
var allCards = this.cards;
var tempCards = [];
var uniqueRanks = [];
var unique;
for(var i = 0; i < allCards.length; i++){
unique = true;
for(var j = 0; j < uniqueRanks.length; j++){
if(allCards[i].getRank() == uniqueRanks[j]){
unique = false;
break;
}
}
if(unique){
uniqueRanks.push(allCards[i].getRank());
tempCards.push(allCards[i]);
}
}
return tempCards;
};
I'm completely perplexed.
var testHand = new POKER.Hand();
testHand = hand.removePairs();
hand.removePairs() returns an Array, not a Hand object.
That's why you don't have access to the getCardAtIndex method.
If cards is a public property you could do:
testHand.cards = hand.removePairs();
Or you can have a setter method:
testHand.setCards(hand.removePairs);

Can't get form total cost

So I have a form with two dropdowns. The first dropdown is the options, and the other is more options. So it's like a mix and match, now I want to calculate the total from the two selected dropdowns. Here's what I got going
var repairCost = new Array();
repairCost["none_repair"] = 0;
repairCost["minor"] = 10;
repairCost["major"] = 20;
repairCost["extreme"] = 30;
var colorCost = new Array();
colorCost["none_color"] = 0;
colorCost["single_portrait"] = 10;
colorCost["group_scene"] = 20;
$("#repair_drop").change(function (event) {
getRepair();
function getRepair(){
var repair = 0;
var form = document.forms["myform"];
var selectedRepair = form.elements["repair_drop"];
repair = repairCost[selectedRepair.value];
return repair
}
});
$("#colorize_drop").change(function (event) {
getColor();
function getColor(){
var color = 0;
var form = document.forms["myform"];
var selectedColor = form.elements["colorize_drop"];
color = colorCost[selectedColor.value];
return color
}
});
var timer1 = null;
clearTimeout(timer1);
timer1 = setTimeout(total, 500)
function total(){
var cost = getRepair() + getColor();
console.log(cost);
}
total();
I end up getting
Uncaught ReferenceError: getRepair is not defined
So for example I'd choose repairCost["minor"] and colorCost["group_scene"], then my result would be $30. I have a timer in there so it automatically calculates the total. Any ideas?
You defined the getRepair function inside another function. Therefore you cannot access it from outside. You have to define it outside the function to be able to access it, like so :
var repairCost = new Array();
repairCost["none_repair"] = 0;
repairCost["minor"] = 10;
repairCost["major"] = 20;
repairCost["extreme"] = 30;
var colorCost = new Array();
colorCost["none_color"] = 0;
colorCost["single_portrait"] = 10;
colorCost["group_scene"] = 20;
function getRepair(){
var repair = 0;
var form = document.forms["myform"];
var selectedRepair = form.elements["repair_drop"];
repair = repairCost[selectedRepair.value];
return repair;
}
function getColor(){
var color = 0;
var form = document.forms["myform"];
var selectedColor = form.elements["colorize_drop"];
color = colorCost[selectedColor.value];
return color;
}
$("#repair_drop").change(function (event) {
getRepair();
});
$("#colorize_drop").change(function (event) {
getColor();
});
var timer1 = null;
clearTimeout(timer1);
timer1 = setTimeout(total, 500)
function total(){
var cost = getRepair() + getColor();
console.log(cost);
}
Why are you declaring functions within your events, and then calling them from there? Either declare them outside the events, or just inline the code - don't do both.

jQuery multiple parent() calls

I have this for loop that gets the id and text of parents elements:
for (var i = 1; i < parents_num; i++)
{
var prev_parent_text = jQuery(id).parent().parent().find('> .myclass').text();
var prev_parent_id = jQuery(id).parent('ul').parent('li').attr('id');
}
What I am trying to do is to increase the number of parent() by 2 in each loop:
For example,
for i = 1:
var prev_parent_text = jQuery(id).parent().parent().find('> .myclass').text();
var prev_parent_id = jQuery(id).parent('ul').parent('li').attr('id');
for i = 2:
var prev_parent_text = jQuery(id).parent().parent().parent().parent().find('> .myclass').text();
var prev_parent_id = jQuery(id).parent('ul').parent('li').parent('ul').parent('li').attr('id');
for i = 3:
var prev_parent_text = jQuery(id).parent().parent().parent().parent().parent().parent().find('> .myclass').text();
var prev_parent_id = jQuery(id).parent('ul').parent('li').parent('ul').parent('li').parent('ul').parent('li').attr('id');
and so on..
I have used the eq() function unsuccesfully:
var num = (i*2) - 2
var prev_parent_text = jQuery(id).parent().eq(num).find('> .myclass').text();
var prev_parent_id = jQuery(id).parent('ul').parent('li').eq(num).attr('id');
Thank you for any help
Keep a reference for each, and update the reference for each step:
var $id = jQuery(id);
var $li = jQuery(id);
for (var i = 1; i < parents_num; i++) {
$id = $id.parent().parent();
$li = $li.parent('ul').parent('li');
var prev_parent_text = $id.find('> .myclass').text();
var prev_parent_id = $li.attr('id');
}
You could add a custom jquery function for that, like this:
$.fn.nparent = function(n) {
var elem = $(this);
for (var i=0;i<n;i++) {
elem = elem.parent();
}
return elem;
}
And use it like:
var id = $('#element').nparents(4).attr('id');

Categories