简体   繁体   中英

Multiple JavaScript countdowns

<?php wpsc_start_category_query(array('category_group'=>get_option('wpsc_default_category'), 'show_thumbnails'=> 1)); ?>

<script>
window.onload = function() {
    countdown('countdown<?php wpsc_print_category_id(); ?>');
}
var interval;

var seconds = 5;
function countdown(element) {
    interval = setInterval(function() {
        var el = document.getElementById(element);
        if(seconds == 0) {
         el.innerHTML = "countdown's over!";                    
         clearInterval(interval);
         return;
        }
        el.innerHTML = seconds + ' seconds remaining';
        seconds--;
    }, 1000);
}
</script>

<div id='countdown<?php wpsc_print_category_id(); ?>'></div>
<?php wpsc_end_category_query(); ?>

my task it display such countdown for every wp query. the problem is that it only displays for the last queried object. My guess is that's becaus window.onload, but I cant think any alternative

Any Help?

I don't 100% understand what the WP stuff does so this might just be total rubbish!

My code has 2 parts, a part to use in-place of your current code, the template, and a portion of code to have in your page <head> , the countdown function.

There's also a function to convert seconds into days,hours,mins and seconds should your interval not be constant at 5 seconds in the future.

The countdown function will update all countdowns that are set-up by the template code.

Hope it helps :)

Update

My code does not edit or delete anything on your server, obviously named my variable a little too close to home for you :) As my comment says, the delete call only removes the counter from the list holding information about the counters, removing the delete statement will leave finished counters in the list (not a problem, just less efficient as they are iterated over when tick() gets called)

I will try to describe what my code does at the bottom so you can understand better what is going on.

WPSC Template

<?php   wpsc_start_category_query(array('category_group'=>get_option('wpsc_default_category'), 'show_thumbnails'=> 1)); ?>
<script type="text/javascript">
if (!wpsc_categories) { wpsc_categories = {}; }
wpsc_categories['countdown_<?php wpsc_print_category_id(); ?>'] = 5; // this value is the countdown in seconds
</script>
<div id="countdown_<?php wpsc_print_category_id(); ?>"></div>
<?php wpsc_end_category_query(); ?>

If you want a 1 week countdown and for the countdown to persist over page views (so it does not reset to 1 week when you refresh) you will need to store a counter start date on your server, calculate the difference between then and now (with php) and use that in-place of 5 ( I guess that is what you planned on doing anyway though! )

Countdown Function - This should be included in the header of your page

<script type="text/javascript">
var wpsc_categories = [];

// the following function will update all counters using one timer (hopefully)
function tick() {
    var element;
    for (category in wpsc_categories) {
        if (wpsc_categories.hasOwnProperty(category)) {
            element = document.getElementById(category);
            if (wpsc_categories[category] == 0) {
                element.innerHTML = "countdown over!";
                delete wpsc_categories[category];
            } else {
                // MODIFIED THIS LINE, SEE NOTE
                //element.innerHTML = formatTime(wpsc_categories[category]--);
                element.innerHTML = formatTime(wpsc_categories[category]);
                wpsc_categories[category] -= 1;
            }
        }
    }
    //return setInterval(tick, 1000); //this line is bad :D
}

var interval = setInterval(tick, 1000) // start it running

// return formatted time from seconds (if required)
function formatTime(seconds) {
    var numdays = Math.floor(seconds / 86400);
    var numhours = Math.floor((seconds % 86400) / 3600);
    var numminutes = Math.floor(((seconds % 86400) % 3600) / 60);
    var numseconds = ((seconds % 86400) % 3600) % 60;
    return (numdays>0?numdays+" days ":"")+(numhours>0?numhours+" hours ":"")+(numminutes>0?numminutes+" minutes ":"")+(numseconds>0?numseconds+" seconds":"")
}
</script>

Note

I changed the way the remaining time is updated to make it a little more clear. I used a decrement operator -- which can be a little annoying.

Description

Your original template copied a large block of code for every category, including the countdown code and the call that invokes it, which is why only the last categories timer was working. window.onload was being overwritten by each subsequent category.

Yes you could have used an anonymous function to start the function rolling and it should have worked, but its probably not the best solution.

Now for my code

you had a question about if (!wpsc_categories) { wpsc_categories = {}; } if (!wpsc_categories) { wpsc_categories = {}; } wpsc_categories is an object that stores information about counters. this checks to see if the object exists and creates it if it does not so that the next like can add information about a counter.

In the browser, your client would get the following for 3 example groups.

<script type="text/javascript">
if (!wpsc_categories) { wpsc_categories = {}; }
wpsc_categories['countdown_example1'] = 5;
</script>
<div id="countdown_example1"></div>
<script type="text/javascript">
if (!wpsc_categories) { wpsc_categories = {}; }
wpsc_categories['countdown_example2'] = 5;
</script>
<div id="countdown_example2"></div>
<script type="text/javascript">
if (!wpsc_categories) { wpsc_categories = {}; }
wpsc_categories['countdown_example3'] = 5;
</script>
<div id="countdown_example3"></div>

As soon as the code in this block is executed by javascript the wpsc_categories variable will be filled with information about the 3 required counters. This information is what tick() uses to update the timers.

Update 2 My example used setInterval inside the tick() function, which was bad! as setInterval is a repeating timer, so every call to tick created a new timer and so it would change the time exponentially :D

setTimeout() is one-shot, setInterval() keeps going till you stop it!

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM