Why is the mousedown event being fired after click instead of during? - javascript

I have a div class "guessed" and have a timer to detect whether a short press and long press. When testing, the console logs "MOUSEDOWN" after the press instead of on the press.
The console also logs "SHORT PRESS" even if it's held for longer than 2 seconds.
I've tested the code on JSFiddle and it's working fine. However within my website, the code doesn't work. Can anyone spot the error? Many thanks
var timer = 0;
var timerInterval;
$(document).on('mousedown', '.guessed', function() {
console.log("MOUSEDOWN");
timerInterval = setInterval(function() {
timer += 1;
}, 300);
});
$(document).on('mouseup', '.guessed', function() {
if (timer < 1) {
console.log("SHORT PRESS");
clearInterval(timerInterval);
timer = 0;
return;
}
console.log("LONG PRESS");
clearInterval(timerInterval);
timer = 0;
});
.guessed { border:1px solid red; width:100px; height:100px; }
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
<div class='guessed'>mouse me</div>

You can simply use html attributes for mouseup and mousedown events and call custom defined JavaScript functions just like in the following example :
var timer = 0,timerInterval;
function mousedownfunction() {
console.log("MOUSE DOWN");
timerInterval = setInterval(function() {
timer += 1;
}, 300);
}
function mouseupfunction() {
console.log("MOUSE UP");
if (timer < 1) {
console.log("SHORT PRESS");
clearInterval(timerInterval);
timer = 0;
return;
} else {
console.log("LONG PRESS");
clearInterval(timerInterval);
timer = 0;
return;
}
}
<div class="guessed" onmousedown="mousedownfunction()" onmouseup="mouseupfunction()">
<p>Mouse</p>
</div>

Related

how to make it have a wait until it executes a new code

So how do I make it wait 1000 milliseconds until it executes a different code(btw, What is the JavaScript version of sleep()? IS NOT helping me, so PLEASE don't close this question(and I'm not very good with JavaScript)).
Here is my code:
<!DOCTYPE html>
<html>
<head>
<title>Start</title>
</head>
<body>
<div id="changeText" style="font-family:verdana;"><br><br>
Press ENTER to continue</div>
<script>
document.addEventListener('keydown',function(e){
if(e.keyCode==13){
newPageTitle = 'Executing...';
document.title = newPageTitle;
//wait goes here
newPageTitle = 'Loading...';
document.title = newPageTitle;
//wait goes here
newPageTitle = 'Fetching Data...';
document.title = newPageTitle;
//wait goes here
newPageTitle = 'Done!';
document.title = newPageTitle;
//wait goes here
window.location.href=('https://example.com');
}
});
</script>
<script>
var text = ["<br><br>Press ENTER to continue_", "<br><br>Press ENTER to continue"];
var counter = 0;
var elem = document.getElementById("changeText");
var inst = setInterval(change, 700);
function change() {
elem.innerHTML = text[counter];
counter++;
if (counter >= text.length) {
counter = 0;
}
}
</script>
</body>
</html>
what I want it to do is whenever you press enter it changes the title, then it waits 1000 milliseconds to change the tile again, and then it waits 680 milliseconds to redirect you to another webpage (also for some reason when it's in the code snippet you have to click the snippet area and the you can press enter).
To do your animation on the document title, that would be a serie of nested setTimeout() function looking like this:
setTimeout(function () {
document.title = "Executing...";
setTimeout(function () {
document.title = "Loading...";
setTimeout(function () {
document.title = "Fetching Data...";
setTimeout(function () {
document.title = "Done!";
setTimeout(function () {
window.location.href = "https://example.com";
}, 1000);
}, 4000);
}, 3000);
}, 2000);
}, 1000);
I agree that is ugly. And you would have to calculate the added delays from outer to inner... So you could have a function to set the timeouts and make your code readable and maintainable.
Notice that nice looking script:
wait(1000, 'Executing...')
wait(2000, 'Loading...')
wait(3000, 'Fetching Data...')
wait(4000, 'Done!')
wait(1000)
Here is a demo where I console logged the title texts... Because we won't see the effect otherwize, since the snippet is an iframe.
document.addEventListener('keydown', function(e) {
if (e.keyCode == 13) {
wait(1000, 'Executing...')
wait(2000, 'Loading...')
wait(3000, 'Fetching Data...')
wait(4000, 'Done!')
wait(1000)
}
});
var text = ["<br><br>Press ENTER to continue_", "<br><br>Press ENTER to continue"];
var counter = 0;
var elem = document.getElementById("changeText");
var inst = setInterval(change, 700);
function change() {
elem.innerHTML = text[counter];
counter++;
if (counter >= text.length) {
counter = 0;
}
}
// A global variable to sum up the delays
let wait_time = 0;
function wait(delay, message) {
// Each "wait" call is adding its delay to the global wait_time
wait_time += delay
// This is the delay to use in this timeout
// "let" making it scoped to this function call
let timeoutDelay = wait_time;
console.log(timeoutDelay)
// Set a timeout
setTimeout(function() {
// If there is a message, use it on the title.
// else, redirect
if (message) {
console.log(message)
document.title = message;
} else {
window.location.href = ('https://example.com');
}
}, timeoutDelay)
}
<div id="changeText" style="font-family:verdana;"><br><br> Press ENTER to continue</div>

Cannot understand why event is undefined

I'm sorry, I feel this is a really classic issue but since I'm learning I don't know why it's not working in my case.
I'm trying to have a script that detect your idle time and if so, execute a function that get your mouse position.
In order to do that, I have the function TimerIncrement() that can check 2 seconds of inactivity, if so I would like to execute another function called GetMousePos in order to get the mouse position and to have a console.log of it.
I've tried looking online and on the forums but nothing I have been doing is helping.
Thanks for the precious help.
var idleTime = 0;
$(document).ready(function () {
//Increment the idle time counter every minute.
var idleInterval = setInterval(timerIncrement, 1000); // 1s
//Zero the idle timer on mouse movement.
$(this).mousemove(function (e) {
idleTime = 0;
});
$(this).keypress(function (e) {
idleTime = 0;
});
});
function timerIncrement() {
idleTime = idleTime + 1;
if (idleTime > 2) { // 2sec
getMousePos();
idleTime = 0; // reset timer
}
}
function getMousePos(event) {
x = event.pageX;
y = event.pageY;
console.log(x);
}
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
So you're calling getMousePos which takes a parameter of event and you are not passing anything to it hence the Cannot read property 'pageX' as event.pageX (event not defined). You can only get to the event object ON a event callback so I am assuming you want to get the last event you have seen if any.
The below should work for you, storing the lastEvent seen you should then be able to get the info you want. Hopefully, this code example makes you understand what you were missing.
var idleTime = 0;
var lastEvent = undefined;
$(document).ready(function () {
//Increment the idle time counter every minute.
var idleInterval = setInterval(timerIncrement, 1000); // 1s
//Zero the idle timer on mouse movement.
$(this).mousemove(function (e) {
idleTime = 0;
lastEvent = e;
});
$(this).keypress(function (e) {
idleTime = 0;
lastEvent = e;
});
});
function timerIncrement() {
idleTime = idleTime + 1;
if (idleTime > 2) { // 2sec
getMousePos(lastEvent);
idleTime = 0; // reset timer
}
}
function getMousePos(event) {
if (!event) {
console.log("No mouse or keypress has been executed yet");
return;
}
x = event.pageX;
y = event.pageY;
console.log(x);
}
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
You can't get the mouse position without an event, so we need to track the mousemove and save the latest position.
$(function() {
let idleTime = 0
let pos = []
let timer = window.setInterval(incTime, 1000)
function incTime() {
idleTime++
checkTime()
$('.time span')[0].innerText = idleTime
}
function checkTime() {
if (idleTime > 2) {
resetTime()
$('.x span')[0].innerText = pos[0]
$('.y span')[0].innerText = pos[1]
}
}
$(document).on('mousemove', e => {
window.clearInterval(timer)
resetTime()
pos[0] = e.pageX
pos[1] = e.pageY
timer = window.setInterval(incTime, 1000)
})
function resetTime() {
idleTime = 0
$('.time span')[0].innerText = idleTime
}
})
<div class="time">Idle time: <span>0</span></div>
<div class="x">X: <span></span></div>
<div class="y">Y: <span></span></div>
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>

change content based on timer

The click functions I made change the content. But, whenever I use setinterval or settimeout, the functions run 1 time and then run again immediately without using the delay.
What am I doing wrong?
$(document).ready(function() {
$('.seashellcontainertwo').hide();
var settimer = 1;
$('.seashellcontainer').click(function() {
settimer = 0;
$('.seashellcontainer').hide();
$('.seashellcontainertwo').show();
});
$('.seashellcontainertwo').click(function() {
settimer = 0;
$('.seashellcontainertwo').hide();
$('.seashellcontainer').show();
});
if (settimer == 1) {
setInterval(function() {
$('.seashellcontainertwo').hide();
$('.seashellcontainer').show();
}, 3000);
setInterval(function() {
$('.seashellcontainertwo').show();
$('.seashellcontainer').hide();
}, 3000);
}
});
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<div class="seashellcontainer">seashellcontainer</div>
<div class="seashellcontainertwo">seashellcontainertwo</div>
I suppose,this is what you were trying to achieve in intervals, Not sure about click events though. Further clarification will help.
$(document).ready(function() {
var seaShellContainerTwo = $('.seashellcontainertwo');
var seaShellContainer = $('.seashellcontainer');
seaShellContainerTwo.hide();
var settimer = 0;
setInterval(function() {
if (settimer === 1) {
seaShellContainerTwo.hide();
seaShellContainer.show();
settimer = 0;
} else {
seaShellContainerTwo.show();
seaShellContainer.hide();
settimer = 1;
}
}, 3000);
});
<script src="https://ajax.googleapis.com/ajax/libs/jquery/1.11.1/jquery.min.js"></script>
<div class="seashellcontainer">seashellcontainer</div>
<div class="seashellcontainertwo">seashellcontainertwo</div>

Check when element is double-clicked with middle mouse button

<div style="width: 250px;
height: 100px;
background-color: Green;
border-style: solid;
border-color: Black;"></div>
With the code above, I create a green box with a black outline. Fiddle.
Below, I have a Javascript function myFunction().
function myFunction() {
window.alert("Hello world!");
}
How do I get this function to run when the user uses his middle mouse button twice in a row with his mouse in the green box (as quickly as how someone double-clicks with his left mouse button)?
Plain JavaScript 1:
Cross browser support
var div = document.getElementsByTagName("div")[0];
var count = 0;
var timeout;
div.onmouseup = function(e){ // thanks RobG, it should be `mouseup`
if(e.which == 2){
count++;
if(!timeout){
timeout = setTimeout(function(){
timeout = undefined;
check();
}, 250);
}
}else{
count = 0;
}
};
function check(){
if(count >= 2){
alert('y');
}
count = 0;
}
DEMO
With jQuery:
Not working in Firefox 27.0 - use "Plain JS 1"
$("div").dblclick(function(e){
if(e.which == 2)
alert('y');
})
DEMO
Plain JavaScript 2:
Doesn't work in Safari 7/FireFox 27.0 - use "Plain JS 1"
var div = document.getElementsByTagName("div")[0];
div.ondblclick = function (e) {
if(e.button == 1) alert('y');
};
DEMO
Start simple. Add a click handler to you div like this:
<div style="width: 250px;
height: 100px;
background-color: Green;
border-style: solid;
border-color: Black;" onclick="myFunction();"></div>
Get that working, then search for how to modify the click event to use other buttons
Here is a function version of Gaurang's answer, however I can't get it to work reliably on Mac OS (nor is Gaurang's answer reliable). Anyway, it might be useful.
// Listener to add
function foo(e) {
console.log(this.id + ':' + e.button);
}
// Main function
var addNonPrimaryDblclick = (function() {
var timeout = null,
count = 0,
delay = 250;
// If timeout expires, reset everything
function checkTimeout() {
if (timeout) {
clearTimeout(timeout);
timeout = null;
count = 0;
}
}
return function(element, listener, newDelay) {
if (typeof newDelay != 'undefined') delay = newDelay;
// Add isDoubleClick as listener
element.addEventListener('mouseup', isDoubleClick, false);
function isDoubleClick(e) {
// A bit of debug
console.log('button: ' + e.button + ' which: ' + e.which);
e.preventDefault();
// 2 is the secondary button, equivalent to 3 in "which" scheme
if (e.button == 2) {
count++;
if (timeout) {
// If this is second click within delay, reset everything
// and call listener
if (count == 2) {
clearTimeout(timeout);
timeout = null;
count = 0;
// Set element to "this" in the listener and pass event
listener.call(element, e);
return;
}
// If no timeout setup, doso
} else {
timeout = setTimeout(checkTimeout, delay);
}
}
}
}
}());
// Example use - set long delay for testing
addNonPrimaryDblclick(document.getElementById('d0'), foo, 1000);

How to trigger a setInterval function on a user click?

I'm trying to write a JS timer that will be triggered by a user click on the button with id="start".
I've got the timer itself working correctly, but when I try to add code to initiate the timer on the button click (id="start") I break it and am not sure why.
Any help would be greatly appreciated!
Here is the JS code:
$(document).ready(function(){
var count = 0;
$('#start').click(function(){
setInterval(function(){
count++;
$('#timer').html(count + ' tacos seconds');
},1000);
});
});
$(document).ready(function() {
$('#start').click((function(container) {
var interval;
return function() {
if(interval) clearInterval(interval);
var count = 0;
interval = setInterval(function() {
count++;
$(container).html(count + ' tacos seconds');
}, 1000);
};
})("#timer"));
});
$(document).ready(function() {
var count = 0;
var myInterval = null;
$('#start').click(function(){
myInterval = setInterval(function(){
count++;
$('#timer').html(count + ' tacos seconds');
},1000);
});
});
When setting your setInterval in the scope of the click handler, try assigning it to a variable to hold the interval declared up a level. This has typically always worked for me.
Not sure exactily what your objective is, but maybe you'd want to try something like this:
var startInterveal;
var timerStarted = false;
var count =0;
$(document).ready(function () {
$('#start').click(function () {
if (!timerStarted) {
timerStarted = true;
count =0;
$(this).attr('disabled', 'disabled');
startInterveal = setInterval('tick();', 1000);
}
});
});
function tick() {
count++;
$('#timer').html(count + ' tacos seconds');
}
Here is a 2nd answer if you really want to go nuts and have something resuable:
$(document).ready(function() {
$('#start').click(overboard("#timer"));
$('#start2').click(overboard("#timer2"));
});
function overboard(container) {
var interval;
return function() {
if (interval) clearInterval(interval);
var count = 0;
interval = setInterval(function() {
count++;
$(container).html(count + ' tacos seconds');
}, 1000);
};
}

Categories

Resources