I have some Javascript that is basically a countdown timer:
<script>
var clockRunning = false;
var clockPlaceholder = document.getElementById("clock-placeholder");
var targetDate;
var clock;
function updateClock() {
var cd = countdown(targetDate, null, countdown.DAYS | countdown.HOURS | countdown.MINUTES | countdown.SECONDS, 4);
clockPlaceholder.innerHTML = cd.toString();
if (targetDate.getTime() < (new Date()).getTime()) {
endCountdown();
}
}
function startCountdown() {
if (clockRunning == false) {
var h, m, s;
// setup target Date object
var now = new Date(); // console.debug(now.toString());
var laravelTime = '{{ $auction->endtime }}';
targetDate = new Date(laravelTime);
// start clock
clock = setInterval(updateClock, 1000);
clockRunning = true;
}
}
function endCountdown() {
clockPlaceholder.innerHTML = "Auction Ended"
clearInterval(clock);
clockRunning = false;
}
</script>
This line: var laravelTime = '{{ $auction->endtime }}'; just gets the endtime from the DB.
Anyway, it works perfectly on my computer but when I browse to the page on my mobile phone (iOS) it doesn't appear at all. Neither Safari nor Chrome shows it.
I'm quite new to js. Any help would be appreciated!
Related
I want to track the content consumption behavior on our SPA blog website. I refer to this blog post and modify its example to set a custom HTML tag in GTM like this, and the following tag will be triggered after a gtm_history event is triggered on blog article pages.
var contentContainer = "my article class";
var wordsPerMinute = 250;
var is_error = false;
var event_timer_reached = 'content_time_reached';
// Calculated Variables
var contentEl = document.querySelector(contentContainer);
if (contentEl == null) { is_error = true; }
/**
* Start content consumption plugin
*/
function initContentConsumption() {
var timeToRead = null;
var interval = null;
var contentEl = document.querySelectorAll(contentContainer);
var wordContentCount = wordCount(contentEl);
if (contentEl && wordContentCount) {
// Time to read by wordsPerMinute
timeToRead = (wordContentCount / wordsPerMinute).toFixed(2);
interval = timeToRead * 60 * 1000;
pageReadTimer(interval);
}
}
function pageReadTimer(interval) {
window.setTimeout(function() {
window.dataLayer = window.dataLayer || [];
window.dataLayer.push({ 'event': event_timer_reached });
}
, interval);
}
function wordCount(words) {
var count = 0;
for (var i = 0; i < words.length; i++) {
var cleanWords = words[i].innerText.replace(/\n\n/g, " ");
cleanWords = cleanWords.replace(/\n|\t/g, " ");
count += cleanWords.split(" ").length;
}
return count;
}
if(is_error==false){initContentConsumption()}
I expect the code to work as follows:
Calculate the characters of the blog post and suggest a minimal reading time
Push a "content-time-reached" event only when the reader stays on the page over the minimal reading time
So far, the code works fine if readers do spend more time reading a specific post. However, if it is not the case, the event might be pushed to the wrong page.
Say a reader selects post-A with the suggested reading time of 45 sec. If he only stays on the post for 30 seconds, goes to another Post B (say post-B has the suggested reading time of 60 seconds), and stays for 15 seconds, the event "content-time-reached" will still be fired. How it should work is that the event should not be pushed on either post-A or post-B since the reader doesn't stay longer on the blog post pages respectively than each post's suggested reading time.
I know the issue is that I use the "setTimeout" function to push the event, and it will push it whenever a reader stays on the site longer than any single blog's suggested reading time. I've changed my scripts based on the guidance of this post, added a new data layer variable named "custom.timer.running," and changed the "setTimeout" to "setInterval" and "clearInterval." However, it turned out that the tag was not fired at all.
var contentContainer = "my article class";
var wordsPerMinute = 250;
var is_error = false;
var event_timer_reached = 'content_time_reached';
var timerNumber = 1;
var limit = 1;
/**
* Start content consumption plugin
*/
function initContentConsumption() {
var timeToRead = null;
var interval = null;
var contentEl = document.querySelectorAll(contentContainer);
var wordContentCount = wordCount(contentEl);
if (contentEl && wordContentCount) {
// Time to read by wordsPerMinute
timeToRead = (wordContentCount / wordsPerMinute).toFixed(2);
interval = timeToRead * 60 * 1000;
pageReadTimer(interval);
}
}
function pageReadTimer(interval) {
var fireTimer = function() {
window.dataLayer = window.dataLayer || [];
window.dataLayer.push({ 'event': event_timer_reached,
'custom.timer.running' : 'false'});
timerNumber += 1;
if(limit < timerNumber){
window.clearInterval(timerId);}
}
if ({{custom.timer.running}} == 'false') {
window.dataLayer.push({ 'custom.timer.running' : 'true'});
var timerId = window.setInterval(fireTimer, interval); }
}
function wordCount(words) {
var count = 0;
for (var i = 0; i < words.length; i++) {
var cleanWords = words[i].innerText.replace(/\n\n/g, " ");
cleanWords = cleanWords.replace(/\n|\t/g, " ");
count += cleanWords.split(" ").length;
}
return count;
}
initContentConsumption()
I was implementing some audio files today in my Javascript and it works fine. But
I noticed that with each subsequent click the sound gets louder. I alreadio used the "Audio.volume" method but no luck.
My Code:
var AppController = (function () {
var correctItem, secondItem, thirdItem, selectedItems, selectedItemsShuffled;
var rotateImage = function() {
var i = 0;
var randomNumbers = createThreeRandomNumbers();
var interval = window.setInterval(function () {
i++;
document.getElementById("imageToRotate").src= "img/" + items.images[i].imageLink;
if (i === items.images.length -1) {
i = -1;
}
}, 125);
var clearData = function () {
correctItem = "";
secondItem = "";
thirdItem = "";
selectedItems = "";
selectedItemsShuffled = "";
removeNodeChildren("button-1");
removeNodeChildren("button-2");
removeNodeChildren("button-3");
};
var removeNodeChildren = function (obj) {
var myNode = document.getElementById(obj);
while (myNode.firstChild) {
myNode.removeChild(myNode.firstChild);
}
};
var resetGame = function () {
clearData();
document.getElementById("buttonWrapper").classList.remove("show");
rotateImage();
}
document.getElementById("imageToRotate").addEventListener("click", function (e) {
// select 3 items
correctItem = getSelectedItemDetails(e);
secondItem = getRandomItem(correctItem);
thirdItem = getSecondRandomItem(correctItem, secondItem);
selectedItems = [correctItem, secondItem, thirdItem];
selectedItemsShuffled = shuffleArray(selectedItems);
// create the numbers 1 to 3 randomly
var order = createThreeRandomNumbers();
// remove the rotating effect
clearInterval(interval);
// set the images to the buttons in a random order.
setItemsToButtons(order, selectedItemsShuffled);
//show the buttons
showButtons();
// Create an event which triggers when a button is clicked.
document.getElementById("buttonWrapper").addEventListener("click", function(e) {
var valueOfButtonPressed = e.srcElement.innerText.toLowerCase();
var clickedButton = e.srcElement.id;
if (valueOfButtonPressed === correctItem) {
document.getElementById(clickedButton).innerHTML = e.srcElement.innerText.toLowerCase() + '<span class="icon"><i class="fa fa-check green" aria-hidden="true"></i></span>';
if (!audio) {
var audio = new Audio("audio/correct.mp3");
}
audio.play();
audio.volume = 0.5;
setTimeout(resetGame, 5000);
} else {
document.getElementById(clickedButton).innerHTML = e.srcElement.innerText.toLowerCase() + '<span class="icon"><i class="fa fa-times red" aria-hidden="true"></i></span>';
if (!audio) {
var audio = new Audio("audio/wrong.mp3");
}
audio.play();
audio.volume = 0.5;
setTimeout(resetGame, 5000);
}
});
});
};
// 1: hide the buttons
hidebuttons();
// 2: Replace the title
replaceTitle("Animals");
// 3: set up image rotation until it's clicked.
rotateImage();
})();
Any help will be much appreciated. Cheers!
I'm fairly certain the reason is that you're making a new Audio object with every single click.
Instead of doing this with every click:
var audio = new Audio("audio/correct.mp3");
do a check to see if audio already exists. if it does, then simply do audio.play(). If it does not, THEN you make a new audio object.
I implemented a countdown timer via Moment.js library, and unfortunately it doesn't work on Firefox.
This is my code:
function createTimer(begin, timeUp) {
var timer = document.getElementById('timer');
var timerDays = document.getElementById('days').children[0];
var timerHours = document.getElementById('hours').children[0];
var timerMinutes = document.getElementById('minutes').children[0];
var timerSeconds = document.getElementById('seconds').children[0];
var intervalID = window.setInterval(function () {
// Difference between timeUp and now
var differenceToTimeUp = moment.duration(timeUp.diff(moment()));
// Difference between begin and now
var differenceToBegin = moment.duration(begin.diff(moment()));
if (differenceToTimeUp.asSeconds() > 0) {
timer.classList.remove('hidden');
} else {
timer.classList.add('hidden');
}
timerDays.innerText = ('0' + differenceToTimeUp.days()).slice(-2);
timerHours.innerText = ('0' + differenceToTimeUp.hours()).slice(-2);
timerMinutes.innerText = ('0' + differenceToTimeUp.minutes()).slice(-2);
timerSeconds.innerText = ('0' + differenceToTimeUp.seconds()).slice(-2);
}, 1000);
}
document.addEventListener('DOMContentLoaded', function () {
// // Comment out for production
// var test1 = moment('2016-02-02 11:00:00');
// var test2 = moment('2016-03-11 11:00:00');
// createTimer(test1, test2);
var now = moment(new Date(moment())).utc().format("YYYY-MM-DD HH:mm:ss");
var firstStart = moment('2016-02-11 11:00:00');
var firstEnd = moment('2016-02-15 17:00:00');
var secondStart = moment('2016-02-16 14:00:00');
var secondEnd = moment('2016-02-17 17:00:00');
if (now > firstStart._i && now < firstEnd._i) {
createTimer(firstStart, firstEnd);
}
});
In debugger I can see that moment is getting the date, so I think it has something to do with the setInterval function.
Any ideas?
UPDATE
Got it working. The mistake was actually not with momentJS. Changing the Text element with .innerText didn´t work on InternetExplorer. Using .textContent fixed it. I hade issues with my custom fonts as well on InternetExplorer when i used .tff. Using .woff worked fine.
I'm trying to create a small game that replicate neighbors cells in a grid. I use a web worker that draw replicate cells every seconds. I'm able to replicate the first second. If my initial cell is row3col3, the new replicated cells will be :
row3col2, row3col4
row2col3, row4col3
The problem is, after the first second (and the replication), the game freezes, and i'm not able to do something. Can't click on cells, etc.
EDIT : After few seconds, it go to '00:02' but Chrome crashed "Aw, Snap! Something went wrong...' [RELOAD]
EDIT 2 : After looking on the memory used, It appears I have an memory overflow, 16000 Mb ! My method is bad, so.
I know my code is not really optimised, and I think that is the problem. Unfortunatly, i'm not able to do more efficient code, so I ask some help to you guys, to give me some ways to explore.
Here the code :
var lastClicked;
var cellTab = Array();
var replicant = Array();
var newReplicant = Array();
var count = 5;
var rows = 20;
var cols = 20;
var randomRow = Math.floor((Math.random() * rows));
var randomCol = Math.floor((Math.random() * cols));
var grid = clickableGrid(rows, cols,randomRow,randomCol,cellTab, function(el,row,col,i){
console.log("You clicked on element:",el);
console.log("You clicked on row:",row);
console.log("You clicked on col:",col);
console.log("You clicked on item #:",i);
$(el).addClass('clicked');
lastClicked = el;
});
document.getElementById("game").appendChild(grid);
function clickableGrid( rows, cols, randomRow, randomCol, cellTab, callback ){
var i=0;
var grid = document.createElement('table');
grid.className = 'grid';
for (var r=0;r<rows;++r){
var tr = grid.appendChild(document.createElement('tr'));
for (var c=0;c<cols;++c){
var cell = tr.appendChild(document.createElement('td'));
$(cell).addClass('row'+r+'col'+c);
if(randomCol == c && randomRow == r)
{
storeCoordinate(r, c, replicant);
$(cell).css('background', '#000000');
}
storeCoordinate(r, c, cellTab);
cell.addEventListener('click',(function(el,r,c,i){
return function(){
callback(el,r,c,i);
}
})(cell,r,c,i),false);
}
}
return grid;
}
function storeCoordinate(xVal, yVal, array)
{
array.push({x: xVal, y: yVal});
}
function replicate(replicant)
{
for (var i = 0; i < replicant.length; i++) {
console.log(replicant);
var supRowX = replicant[i].x-1;
var supRowY = replicant[i].y;
storeCoordinate(supRowX, supRowY, newReplicant);
var subRowX = replicant[i].x+1;
var subRowY = replicant[i].y;
storeCoordinate(subRowX, subRowY, newReplicant);
var supColsX = replicant[i].x;
var supColsY = replicant[i].y-1;
storeCoordinate(supColsX, supColsY, newReplicant);
var subColsX = replicant[i].x;
var subColsY = replicant[i].y+1;
storeCoordinate(subColsX, subColsY, newReplicant);
}
}
function drawReplicant(replicant, cellTab)
{
for (var i = 0; i < replicant.length; i++) {
if($.inArray(replicant[i], cellTab))
{
$('.row'+replicant[i].x+'col'+replicant[i].y).css('background', '#000000');
}
}
}
var w = null; // initialize variable
// function to start the timer
function startTimer()
{
// First check whether Web Workers are supported
if (typeof(Worker)!=="undefined"){
// Check whether Web Worker has been created. If not, create a new Web Worker based on the Javascript file simple-timer.js
if (w==null){
w = new Worker("w.countdown.js");
}
// Update timer div with output from Web Worker
w.onmessage = function (event) {
document.getElementById("timer").innerHTML = event.data;
console.log(event.data);
replicate(replicant);
replicant = newReplicant;
drawReplicant(replicant, cellTab);
};
} else {
// Web workers are not supported by your browser
document.getElementById("timer").innerHTML = "Sorry, your browser does not support Web Workers ...";
}
}
// function to stop the timer
function stopTimer()
{
w.terminate();
timerStart = true;
w = null;
}
startTimer();
And here, the web worker :
var timerStart = true;
function myTimer(d0)
{
// get current time
var d=(new Date()).valueOf();
// calculate time difference between now and initial time
var diff = d-d0;
// calculate number of minutes
var minutes = Math.floor(diff/1000/60);
// calculate number of seconds
var seconds = Math.floor(diff/1000)-minutes*60;
var myVar = null;
// if number of minutes less than 10, add a leading "0"
minutes = minutes.toString();
if (minutes.length == 1){
minutes = "0"+minutes;
}
// if number of seconds less than 10, add a leading "0"
seconds = seconds.toString();
if (seconds.length == 1){
seconds = "0"+seconds;
}
// return output to Web Worker
postMessage(minutes+":"+seconds);
}
if (timerStart){
// get current time
var d0=(new Date()).valueOf();
// repeat myTimer(d0) every 100 ms
myVar=setInterval(function(){myTimer(d0)},1000);
// timer should not start anymore since it has been started
timerStart = false;
}
Maybe it's because I use jQuery ?
My code makes a number of divisions appear to orbit around an invisible horizontal axis on a plane. How it works: it fires a mouseevent listener onMouseDown, and captures the X of the user's cursor relative to the window. onMouseUp is simulated by a setTimeout function that is called 90 milliseconds later, it does the same and then subtracts the two values to determine the distance and direction to spin.
My question is: Why does it work correctly in FF, Chrome, and IE Quirks and IE 7 Standards, but not IE 8 Standards or IE 9 Standards?
IE8: the model breaks down and the divisons float away outside the containing boundary division. IE9: No response from the JS whatsoever.
The following contains the entire javascript on the page, which can be found # http://electrifiedpulse.com/360.html :
<script type=text/javascript>
var objectCount = 8; var pixel = new Array(); var size = new Array();
var command = "Stop"; var panel = new Array('0','Back','Front','Front','Back','Front','Back','Front','Back');
var quadrant = new Array(); var originalSize = 50;
var WindowWidth = 360; var WindowWidthHalf = WindowWidth/2; var sTime=0; var s1=0; var scrollSpeed;
var myX, myY;
function myMove(evt) {
if (window.event){myX = event.clientX;myY = event.clientY;}
else{myX = evt.clientX;myY = evt.clientY;}
}
document.onmousemove = myMove;
if (!window.event) {document.captureEvents(Event.MOUSEMOVE);}
function iScrollStop(){
sTime = sTime - 10;
document.getElementById('I_CONTROLS').innerHTML = sTime + ", " + scrollSpeed;
if(sTime<=0) command = "Stop";
else setTimeout(function(){iScrollStop()},10);
}
function iScrollPause(){
setTimeout(function(){this.checkPause()},100);
this.checkPause = function(){if(s1>sTime){command="Stop"; sTime=0; s1=0;}}
}
var iInitialX; //var d='Up';
function iScrollListen(d){
if(d=='Down'){ iInitialX = myX; setTimeout(function(){iScrollListen('Up')},90); iScrollPause();
}else if(d=='Up'){
var spinDirection = 'Right';
var iDifference = myX - iInitialX; if(iDifference < 0){ spinDirection = 'Left'; iDifference = Math.abs(iDifference);}
if (command!=spinDirection){sTime=0;s1=0;} var doScroll=0; if(command=='Stop') doScroll=1;
command = spinDirection; s1=sTime; sTime+=(iDifference*15); if(s1<=0)iScrollStop();
if(doScroll==1) iScroll();
}
}
function iScrollControl(c){command = c; if((c=='Left')||(c=='Right')) iScroll();}
function iScroll(){
scrollSpeed=(sTime<=1)? 1 : Math.ceil(sTime/1000);
if(scrollSpeed>=10)scrollSpeed=10;
scrollSpeed = 15 - scrollSpeed;
if(command=='Left') pixelDirection=2;
else if(command=='Right') pixelDirection=(0-2);
pixelDirectionNeg = (0-pixelDirection);
for(i=1;i<=objectCount;i++){
iObj = document.getElementById("iObject" + i);
pixel[i] = iObj.offsetLeft;
if((pixel[i]>=WindowWidthHalf)&&(pixel[i]<=WindowWidth)){
if(panel[i]=="Front") quadrant[i] = 4;
else quadrant[i] = 3;
}
if((pixel[i]>=0)&&(pixel[i]<=WindowWidthHalf)){
if(panel[i]=="Front") quadrant[i] = 1;
else quadrant[i] = 2;
}
if(quadrant[i]==1){
iObj.style.left = pixel[i]-pixelDirection;
size[i] = (pixel[i]-pixelDirection)*(1/(WindowWidthHalf/(originalSize/2))) + (originalSize/2);
Attribute(iObj,size[i]);
if(pixel[i]-pixelDirection<=0){quadrant[i]=2; panel[i]='Back';}
if(pixel[i]-pixelDirection>=WindowWidthHalf){quadrant[i]=4; panel[i]='Front';}
}
if(quadrant[i]==2){
iObj.style.left = pixel[i]-pixelDirectionNeg;
size[i] = (pixel[i]-pixelDirectionNeg)*(-1/(WindowWidthHalf/(originalSize/2))) + (originalSize/2);
Attribute(iObj,size[i]);
if(pixel[i]-pixelDirectionNeg<=0){quadrant[i]=1; panel[i]='Front';}
if(pixel[i]-pixelDirectionNeg>=WindowWidthHalf){quadrant[i]=3; panel[i]='Back';}
}
if(quadrant[i]==3){
iObj.style.left = pixel[i]-pixelDirectionNeg;
size[i] = (WindowWidth-(pixel[i]-pixelDirectionNeg))*(-1/(WindowWidthHalf/(originalSize/2))) + (originalSize/2);
Attribute(iObj,size[i]);
if(pixel[i]-pixelDirectionNeg<=WindowWidthHalf){quadrant[i]=2; panel[i]='Back';}
if(pixel[i]-pixelDirectionNeg>=WindowWidth){quadrant[i]=4; panel[i]='Front';}
}
if(quadrant[i]==4){
iObj.style.left = pixel[i]-pixelDirection;
size[i] = (WindowWidth-(pixel[i]-pixelDirection))*(1/(WindowWidthHalf/(originalSize/2))) + (originalSize/2);
Attribute(iObj,size[i]);
if(pixel[i]-pixelDirection<=WindowWidthHalf){quadrant[i]=1; panel[i]='Front';}
if(pixel[i]-pixelDirection>=WindowWidth){quadrant[i]=3; panel[i]='Back';}
}
}
if((command=='Left')||(command=='Right')) setTimeout(function(){iScroll()},scrollSpeed);
}
function Attribute(iObj,s){
iObj.style.width = s; iObj.style.height = s; iObj.style.top='50%'; iObj.style.marginTop = (0-(s/2))+"px"; iObj.style.zIndex = s;
}
</script>
I don't know what may or may not be relevant to you, so I included the entire script. If you want you could ignore the longest function,
iScroll()
#RyanStortz. Try to register events in this maner:
var isMouseCaptured=false;
function i_boundary_mousedown(ev) {
isMouseCaptured=true;
iScrollListen("Down");
}
function doc_mousemove(ev) {
if(isMouseCaptured) {
ev=ev||event;
myX=ev.clientX;
myY=ev.clientY;
}
}
function doc_mouseup(ev) {
if(isMouseCaptured) {
isMouseCaptured=false;
ev=ev||event;
myX=ev.clientX;
myY=ev.clientY;
}
}
var i_boundaryObj=document.getElementById('I_BOUNDARY');
if(window.addEventListener) {
i_boundaryObj.addEventListener('mousedown',i_boundary_mousedown,false);
document.addEventListener('mousemove',doc_mousemove,false);
document.addEventListener('mouseup',doc_mouseup,false)
}
else if(window.attachEvent) {
i_boundaryObj.attachEvent('onmousedown',i_boundary_mousedown)
document.attachEvent('onmousemove',doc_mousemove);
document.attachEvent('onmouseup',doc_mouseup)
}
else ;//
Add for DIV with class "I_BOUNDARY" id attribute "I_BOUNDARY" and remove onmousedown attribute.