I have a quiz that after selecting the answer it will show result and move on to the next question after a set time.
Now how can i make it to show the result then pause and wait for mouse click before moving on?
self.rightAnswer = function(elm) {
startSound('rightsound', false);
//var bgcss = ($("#" + elm).toggleClass('correct'))
$(elm).toggleClass('correct');
background.pause();
setTimeout(function () {
self.money($(".active").data('amt'));
if(self.level() + 1 > 6) {
$("#game").fadeOut('slow', function() {
$("#game-over").html('Thanks you!');
$("#game-over").fadeIn('slow');
});
} else {
$("#question-answer-block").fadeOut('fast', function(){
$("#question-answer-block").fadeIn('slow');
self.level(self.level() + 1);
var bgcss = ($(elm).toggleClass('correct'))
self.showAllAnswers();
self.transitioning = false;
});
}
self.resetAnswersView();
startSound('background', true);
}, 5000);
}
I have a submit function on a textbox with JavaScript. When the script fires, it checks a Kendo grid for a certain article and adds +1 to its quantity as well as opening the corresponding cell in editing mode. What I want to achieve is that on every submit the timer that starts grid.editCell() will reset its timer.
Currently, the event fires properly. However, the timer doesn't get reset, although the clearTimeout() does work if I just simply start the timer and then clear it right afterwards.
JavaScript:
$('#txtBarcode').submit(function (e) {
var grid = $("#PickListDetailGrid").data("kendoGrid");
var dataSource = $("#PickListDetailGrid").data("kendoGrid").dataSource;
var allData = grid.dataSource.data();
var code = this.value;
var notification = $("#notification").data("kendoNotification");
var timer = null;
clearTimeout(timer);
$.each(allData, function (index, item) {
if (item.ArticleID == code) {
clearTimeout(timer);
timer = null;
if (item.Quantity > item.PickedQuantity && item.PickedQuantity.toString().length < 4) {
var edit = function () {
if (item.PickedQuantity != item.Quantity && timer != null) {
grid.select("tr:eq(" + (index) + ")");
grid.editCell("tr:eq(" + (index + 1) + ") td:eq(" + (5) + ")");
} else {
//do nothing
}
}
item.PickedQuantity++;
item.dirty = true;
dataSource.sync();
if (item.PickedQuantity != item.Quantity) {
console.log("tik tok");
if (timer) {
clearTimeout(timer); //cancel the previous timer.
timer = null;
}
timer = setTimeout(edit, 3000);
} else {
clearTimeout(timer);
timer = null;
}
document.getElementById("txtBarcode").value = "";
} else {
if (item.PickedQuantity.toString().length > 4) {
notification.hide();
notification.show({
message: "Added item"
}, "upload-success");
} else {
notification.hide();
notification.show({
title: "Quantity Error",
message: "You already picked this item to the maximum"
}, "error");
document.getElementById("txtBarcode").value = "";
grid.select("tr:eq(" + (index) + ")");
grid.editCell("tr:eq(" + (index + 1) + ") td:eq(" + (5) + ")");
$('.focus :input').focus();
}
}
}
})
})
You can try delay function like this. The delay function should be outside of the each function.
var delay = (function() {
var timer = 0;
return function(callback, ms) {
clearTimeout(timer);
timer = setTimeout(callback, ms);
};
})();
delay(function() {
//do something
}, 3000);
The problem was that var timer = null; had to be outside of the submit function to be properly cleared and set to null before assigning a new setTimeout() to it.
In this fiddle I made a script building a play button for audio files, that allows playing the file only twice and then disables it. But after reloading the page, the button is active again. How can I make sure, the button stays disabled for a defined duration of 30 seconds for example?
I was wrapping my head around localStorage and found a promising question/answer here, but couldn't transfer the knowhow to my usecase. Can someone help me out?
function buildLimitedPlay(selector) {
$(selector).each(function(i) {
var myaudio = $(this)[0];
var button = $(this).next("input.limited-play")[0];
var index = 2;
$(button).css('display', 'block');
$(button).val("Play Clip");
$(myaudio).on('ended', function() {
index--;
$(button).val('Play again');
if (index == 0) {
$(button).css('background', 'red');
$(button).css('cursor', 'not-allowed');
$(button).css('text-decoration', 'line-through');
$(button).disabled;
}
});
$(button).on("click", function() {
if (index > 0) {
myaudio.play();
}
});
});
}
buildLimitedPlay("audio.limited-play");
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.0.0/jquery.min.js"></script>
<audio class="limited-play" preload="none">
<source src="http://www.noiseaddicts.com/samples_1w72b820/3726.mp3" type="audio/mpeg">
</audio>
<input value="Play Clip" class="limited-play" type="button">
I'm assuming you want to automatically enable the play button after the predefined disabled time passes, also you will have multiple audios to play with multiple buttons. here is the code that will work after refresh and automatically enable the button after time out.
$(function () {
function now() { return +new Date }
var db = window.db = {
get: function (key) {
var entry = JSON.parse(localStorage.getItem(key) || "0");
if (!entry) return null;
if (entry.ttl && entry.ttl + entry.now < now()) {
localStorage.removeItem(key);
return null;
}
return entry.value;
},
set: function (key, value, ttl) {
localStorage.setItem(key, JSON.stringify({
ttl: ttl || 0,
now: now(),
value: value
}));
}
};
function buildLimitedPlay(selector) {
$(selector).each(function (i) {
var getRemainingTurn = function () {
var turn = db.get('remainingTurn' + i);
return null == turn ? 2 : turn;
};
var setRemainingTurn = function (turn, timeToLiveInMillisecond) {
db.set('remainingTurn' + i, turn, timeToLiveInMillisecond || 0);
};
var myaudio = this;
var $button = $(this).next("input.limited-play:first");
$button.css('display', 'block')
.on("click", function () {
if (getRemainingTurn() > 0) {
myaudio.play();
}
});
var setAudioState = function (turn) {
$button.val(2 == turn ? 'Play Clip' : 'Play again');
if (turn == 0) {
$button.css({ 'background': 'red', 'cursor': 'not-allowed', 'text-decoration': 'line-through' });
}
else {
$button.css({ 'background': '', 'cursor': '', 'text-decoration': 'none' });
}
};
var disabledPeriodInMillisecond = 30 * 1000;
var tryEnableAudio = function () {
turn = getRemainingTurn();
if (0 == turn) {
//because we don't know how much time passed since it was disabled in case of a page refresh for simplicity.
setTimeout(tryEnableAudio, 50);
return;
}
setAudioState(turn);
};
$(myaudio).on('ended', function () {
var turn = getRemainingTurn();
turn--;
setAudioState(turn);
if (0 == turn) {
setRemainingTurn(turn, disabledPeriodInMillisecond);
tryEnableAudio();
}
else {
setRemainingTurn(turn);
}
});
setAudioState(getRemainingTurn());
tryEnableAudio();
});
}
buildLimitedPlay("audio.limited-play");
});
I'm getting a console error (Uncaught TypeError: undefined is not a function) on line 156 on load and I can't figure it out for the life of me. I've provided the line in question and the full context its in below. Also, I added the site link in case it helps. I would appreciate any and all help/advice.
Site link
Here is the line in question (156): if (!$imgs.length) {return $.Deferred.resolve().promise();}
Here is the full code: http://pastebin.com/Ext4TwdP#
//*********************************************************
// Let's start, shall we?
//*********************************************************
jQuery(document).ready(function($) {
//*********************************************************
// Global variables
//*********************************************************
// Morphing icons
var myIcons = new SVGMorpheus('#iconset', {
duration: 250,
rotation: 'none'
});
//*********************************************************
// Turn off all Ajax caching (IE caches $.load)
//*********************************************************
$.ajaxSetup({
cache: false
});
//*********************************************************
// Preloader
//*********************************************************
window.addEventListener('DOMContentLoaded', function() {
$('#projects-list, footer p').hide();
new QueryLoader2(document.querySelector("body"), {
barColor: "#f30",
backgroundColor: "#000",
barHeight: 1,
minimumTime: 200,
fadeOutTime: 0,
onComplete: function() {
$('.site-overlay').remove();
$('#masthead').slideDown(100, function(){
$('#projects-list, footer p').show().addClass('fadeInUp');
});
// Set a timeout because 100ms is too quick
$(function() {
setTimeout(function() {
$('#projects-list, footer p').removeClass('fadeInUp');
}, 500);
});
}
});
});
//*********************************************************
// Small features
//*********************************************************
// Set top margin for #content to always match the height of the top header
function resize() {
var headerTop = $('#masthead').outerHeight();
(headerTop != parseInt($('#content').css('margin-top').slice(0, -2))) ? $('#content').stop().animate({'margin-top': headerTop}, 150) : console.log('');
}
resize();
window.onresize = resize;
// Hide header when scrolling down and show header when scrolling up
var lastScrollTop = 0;
$(window).scroll(function(event){
var st = $(this).scrollTop();
if (st < lastScrollTop || st === 0){
$('#masthead').removeClass('unpinned');
} else {
$('#masthead').addClass('unpinned');
}
lastScrollTop = st;
});
//*********************************************************
// Project hovers
//*********************************************************
$('#content').on('mouseenter', 'article.project', function(){
// If loading icon doesn't exist in the DOM...
if ( !$('.overlay').find('.loading-icon').length) {
// And if the project wrapper is activated...
if ( $(this).closest('#main').find('#project-wrapper').hasClass('activated') ) {
$(this).addClass('hover');
} else {
$(this).addClass('hover grayscale grayscale-fade');
}
// If loading icon exists in the DOM...
} else {
$(this).find('.post-link').hide();
}
// Dirty fix for 1px white flicker on hover (Chrome)
var overlayWidth = $('article.project').outerWidth();
$('.overlay').css({
marginLeft: -1,
width: overlayWidth + 2
});
}).on('mouseleave', 'article.project', function(){
// If #project-wrapper is activated...
if ( $(this).closest('#main').find('#project-wrapper').hasClass('activated') ) {
$(this).removeClass('hover');
$(this).find('.post-link').show();
// If #project-wrapper is not activated...
} else {
// If loading icon is present...
if ( $(this).find('.loading-icon').length ) {
// Only remove the 'hover' class
$(this).removeClass('hover');
// If loading icon is not present...
} else {
// Remove all classes
$(this).removeClass('hover grayscale grayscale-fade');
$(this).find('.post-link').show();
}
}
});
// Adjust the project titles so they always fit the container nicely
function adjustTitle() {
var thumbWidth = $('article.project > img').outerWidth();
if (thumbWidth <= 220) {
$('.overlay > h3').addClass('mobile');
} else {
$('.overlay > h3').removeClass('mobile');
}
}
$(window).on('resize', adjustTitle);
//*********************************************************
// Projects
//*********************************************************
(function($) {
// Function to allow an event to fire after all images are loaded
$.fn.imagesLoaded = function () {
$imgs = this.find('img[src!=""]');
// if there's no images, just return an already resolved promise
if (!$imgs.length) {return $.Deferred.resolve().promise();}
// for each image, add a deferred object to the array which resolves when the image is loaded
var dfds = [];
$imgs.each(function(){
var dfd = $.Deferred();
dfds.push(dfd);
var img = new Image();
img.onload = function(){dfd.resolve();}
img.src = this.src;
});
// return a master promise object which will resolve when all the deferred objects have resolved
// IE - when all the images are loaded
return $.when.apply($,dfds);
}
// Function for additional styling
function projectStyles() {
// Check the first slide input
$('#slider input:first').attr('checked', 'checked');
$('#project-wrapper').addClass('activated');
// Make the articles grey again after activation
$('article.project').addClass('grayscale grayscale-fade').css('opacity', '0.4');
// CSS effects
$('.post-container').addClass('fadeInUp');
$('.close-button').addClass('fadeInDown');
// Remove pesky, sticky 'hover' class
$('article.project').removeClass('hover');
}
// Open the project container
function openProject() {
var post_id = $(this).data('id'), // data-id attribute for .post-link
ajaxURL = site.custom_ajax; // Ajax URL localized from functions.php
// Add a loading icon
$('<span class="loading-icon"></span>').insertBefore(this);
// Add the 'active' class to make sure the div stays dark while loading
$(this).closest('article.project').addClass('active');
// Make all the articles grey when an article is clicked
$('article.project').addClass('grayscale grayscale-fade').css('opacity', '0.4');
// Remove the corner ribbon
$('article').removeClass('current');
$('.corner-ribbon').remove();
// Get the response from the Ajax function
$.ajax({
type: 'POST',
url: ajaxURL,
context: this,
data: {'action': 'load-content', post_id: post_id },
success: function(response) {
// Add a corner ribbon to note the current activated project
$(this).closest('article.project').removeClass('active').addClass('current');
$('<div class="corner-ribbon">Current</div>').prependTo('article.current');
// Wait until all images are loaded
$('#project-container').html(response).imagesLoaded().then(function() {
// Remove the loading icon
$('.loading-icon').remove();
// If the user has scrolled...
if ($(window).scrollTop() !== 0) {
// First scroll the page to the top
$('html, body').animate({
scrollTop : 0
},400, function() {
// Make the max-height of the container exact for a smoother transition
function matchContainerHeight() {
var containerHeight = $('#project-container').outerHeight();
$('#project-wrapper.activated').css('max-height', containerHeight);
}
setTimeout(matchContainerHeight, 100);
$(window).on('resize', matchContainerHeight);
projectStyles();
});
// If the user has not scrolled...
} else {
// Make the max-height of the container exact for a smoother transition
function matchContainerHeight() {
var containerHeight = $('#project-container').outerHeight();
$('#project-wrapper.activated').css('max-height', containerHeight);
}
setTimeout(matchContainerHeight, 100);
$(window).on('resize', matchContainerHeight);
projectStyles();
}
return false;
});
}
});
}
// User event
$('#content').on('click', '.post-link', function(e) {
e.preventDefault();
var projectTitle = $(this).data('title'), // data-title attribute for .post-link
projectSlug = $(this).data('slug') // data-slug attribute for .post-link
// Calls openProject() in context of 'this' (.post-link)
openProject.call(this);
$('head').find('title').text(projectTitle + ' | Keebs');
});
})(jQuery);
//*********************************************************
// Close button
//*********************************************************
(function($) {
// Close the project container
function closeProject() {
// Remove classes
$(this).removeClass('fadeInDown');
$('#project-wrapper').removeClass('activated').css('max-height', '');
$('article.project').removeClass('grayscale grayscale-fade').css('opacity', '1');
$('.post-container').removeClass('fadeInUp');
$('article').removeClass('current');
// Remove the corner ribbon since no projects are currently activated
$('.corner-ribbon').remove();
// Set the height of the project wrapper back to 0
$('body.single #project-wrapper').css('max-height', 0);
// Change the title of the document
$('head').find('title').text(site.title);
}
// User event
$('#content').on('click', '.close-button', function(e) {
e.preventDefault();
closeProject();
});
})(jQuery);
//*********************************************************
// Home button
//*********************************************************
(function($) {
// Load the Home page
function loadHome() {
var contactButton = $('#contact-button');
$('#content').fadeOut(50, function() {
$('<span class="loading-icon page-loading-icon"></span>').insertBefore('#content');
}).load(site.url + '/ #primary', function() {
$('.page-loading-icon').remove();
$(this).fadeIn(50);
$('body').removeClass('contact');
$('#contact-info, #clients').removeClass('fadeInUp');
$('#projects-list').addClass('fadeInUp');
$('body.single #project-wrapper').css('max-height', 0);
});
// Change the Projects button to 'Contact'
if ($('body').hasClass('contact')) {
$(contactButton).removeClass('project-button').addClass('contact-button').attr('data-title', 'Get in touch').css('width', '96px').text('Get in touch').shuffleLetters();
myIcons.to('mail');
}
// Change the title of the document
$('head').find('title').text(site.title);
}
// User event
$('.site-title a').on('click', function(e) {
e.preventDefault();
// Prevent accidental double clicks
if (!$(this).data('isClicked')) {
var link = $(this);
loadHome();
link.data('isClicked', true);
setTimeout(function() {
link.removeData('isClicked')
}, 1000);
}
});
})(jQuery);
//*********************************************************
// Contact button
//*********************************************************
(function($) {
var contactButton = $('#contact-button');
// Load the Contact page
function loadContact() {
$('#content').fadeOut(50, function() {
$('<span class="loading-icon page-loading-icon"></span>').insertBefore('#content');
}).load(site.url + '/contact/ #contact-keebs', function() {
$('.page-loading-icon').remove();
$(this).fadeIn(50);
$('body').addClass('contact');
$('#projects-list').removeClass('fadeInUp');
$('#contact-info, #clients').addClass('fadeInUp');
});
// Change the Contact button to 'Projects'
$(contactButton).removeClass('contact-button').addClass('project-button').attr('data-title', 'Projects').css('width', '71px').text('Projects').shuffleLetters();
myIcons.to('work');
// Change the title of the document
$('head').find('title').text('Contact | Keebs');
}
// Load the Projects page
function loadProjects() {
$('#content').fadeOut(50, function() {
$('<span class="loading-icon page-loading-icon"></span>').insertBefore('#content');
}).load(site.url + '/ #primary', function() {
$('.page-loading-icon').remove();
$(this).fadeIn(50);
$('body').removeClass('contact');
$('#contact-info, #clients').removeClass('fadeInUp');
$('#projects-list').addClass('fadeInUp');
$('body.single #project-wrapper').css('max-height', 0);
});
// Change the Projects button to 'Contact'
$(contactButton).removeClass('project-button').addClass('contact-button').attr('data-title', 'Get in touch').css('width', '96px').text('Get in touch').shuffleLetters();
myIcons.to('mail');
// Change the title of the document
$('head').find('title').text(site.title);
}
// User event
$('#mail-wrap').on('click', function(e) {
e.preventDefault();
// Prevent accidental double clicks
if (!$(this).data('isClicked')) {
var link = $(this);
if (!contactButton.hasClass('project-button')) {
loadContact();
} else {
loadProjects();
}
link.data('isClicked', true);
setTimeout(function() {
link.removeData('isClicked')
}, 500);
}
});
})(jQuery);
//*********************************************************
// Single template
//*********************************************************
// Check the first slide input
$('body.single #slider input:first').attr('checked', 'checked');
// Set the height of the project container
$('body.single #project-container').imagesLoaded().then(function() {
var containerHeight = $('#project-container').outerHeight();
$('body.single #project-wrapper').css('max-height', containerHeight);
});
// Make the projects list grayscale if the project wrapper is activated
if ( $('body.single #project-wrapper').hasClass('activated') ) {
$('article.project').addClass('grayscale grayscale-fade').css('opacity', '0.4');
}
//*********************************************************
// Shuffle Letters by Martin Angelov
//*********************************************************
(function($){
$.fn.shuffleLetters = function(prop){
var options = $.extend({
"step" : 8, // How many times should the letters be changed
"fps" : 60, // Frames Per Second
"text" : "", // Use this text instead of the contents
"callback" : function(){} // Run once the animation is complete
},prop)
return this.each(function(){
var el = $(this),
str = "";
// Preventing parallel animations using a flag;
if(el.data('animated')){
return true;
}
el.data('animated',true);
if(options.text) {
str = options.text.split('');
}
else {
str = el.text().split('');
}
// The types array holds the type for each character;
// Letters holds the positions of non-space characters;
var types = [],
letters = [];
// Looping through all the chars of the string
for(var i=0;i<str.length;i++){
var ch = str[i];
if(ch == " "){
types[i] = "space";
continue;
}
else if(/[a-z]/.test(ch)){
types[i] = "lowerLetter";
}
else if(/[A-Z]/.test(ch)){
types[i] = "upperLetter";
}
else {
types[i] = "symbol";
}
letters.push(i);
}
el.html("");
// Self executing named function expression:
(function shuffle(start){
// This code is run options.fps times per second
// and updates the contents of the page element
var i,
len = letters.length,
strCopy = str.slice(0); // Fresh copy of the string
if(start>len){
// The animation is complete. Updating the
// flag and triggering the callback;
el.data('animated',false);
options.callback(el);
return;
}
// All the work gets done here
for(i=Math.max(start,0); i < len; i++){
// The start argument and options.step limit
// the characters we will be working on at once
if( i < start+options.step){
// Generate a random character at thsi position
strCopy[letters[i]] = randomChar(types[letters[i]]);
}
else {
strCopy[letters[i]] = "";
}
}
el.text(strCopy.join(""));
setTimeout(function(){
shuffle(start+1);
},1000/options.fps);
})(-options.step);
});
};
function randomChar(type){
var pool = "";
if (type == "lowerLetter"){
pool = "abcdefghijklmnopqrstuvwxyz0123456789";
}
else if (type == "upperLetter"){
pool = "ABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789";
}
else if (type == "symbol"){
pool = ",.?/\\(^)![]{}*&^%$#'\"";
}
var arr = pool.split('');
return arr[Math.floor(Math.random()*arr.length)];
}
})(jQuery);
//*********************************************************
// iPad fix for slider
//*********************************************************
var iPadLabels = function () {
function fix() {
var labels = document.getElementsByTagName('label'),
target_id,
el;
for (var i = 0; labels[i]; i++) {
if (labels[i].getAttribute('for')) {
labels[i].onclick = labelClick;
}
}
}
function labelClick() {
el = document.getElementById(this.getAttribute('for'));
if (['radio', 'checkbox'].indexOf(el.getAttribute('type')) != -1) {
el.setAttribute('selected', !el.getAttribute('selected'));
} else {
el.focus();
}
}
return {
fix: fix
}
}();
window.onload = function () {
iPadLabels.fix();
}
//*********************************************************
// Annnd, we're done!
//*********************************************************
});
There were a couple problems with this.
1) I didn't declare the imgs variable.
2) I didn't include the () after $.Deferred.
So here's the updated code block:
// Function to allow an event to fire after all images are loaded
$.fn.imagesLoaded = function () {
var imgs = this.find('img[src!=""]');
// If there are no images, just return an already resolved promise
if (!imgs.length) {
return $.Deferred().resolve().promise();
}
// For each image, add a deferred object to the array which resolves when the image is loaded
var dfds = [];
imgs.each(function(){
var dfd = $.Deferred();
dfds.push(dfd);
var img = new Image();
img.onload = function(){dfd.resolve();};
img.src = this.src;
});
// Return a master promise object which will resolve when all the deferred objects have resolved
// IE - when all the images are loaded
return $.when.apply($, dfds);
};
Actually I have an update enquery into this point .
I have smth like that :
$(document).ready(function() {
setInterval(doSmth, 10000);
function doSmth() {
var result = document.getElementById("fooText").value;
if (result != "") {
doSmthElse(result);
}
});
}
}
});
I need to activate the interval ,that is fired each 10 seconds, in case only a text control has the focus else do nothing !!
Code for you is:
$(document).ready(function() {
setInterval(function(){
var result = $("#fooText").val();
if (result != "") {
// if
} else {
// else
}
}, 10000);
You can set the interval on focus of the field, and clear it on blur:
var interval;
$(field).focus(function() {
interval = setInterval(doMsth, 10000);
});
$(field).blur(function() {
clearInterval(interval);
});
(the interval var has to be global)
You can implement this in 2 ways,
Let the timer run and inside the function check if the activeElement == <text input>, then execute the rest of the function else return.
$(document).ready(function() {
setInterval(doSmth, 5000);
function doSmth() {
var resultEl = document.getElementById("fooText");
if (document.activeElement.id != resultEl.id) { return false; }
if (resultEl.value != "") {
doSmthElse(resultEl.value);
}
}
function doSmthElse(result) { alert(result);}
});
DEMO here
Set the timer on focus of the text box and remove the timer onblur of the input box.
$('#fooText').focus ( function () {
timer = setInterval(function() {
var textVal = $('#fooText').val();
if (textVal != '') {
doSmthElse(textVal );
}
}, 5000);
});
$('#fooText').blur (function () {
if (timer != '') clearInterval(timer);
});
DEMO here