HammerJS - Limit function call rate inside drag event - javascript

I'm using the drag event with HammerJS for changing the value of a input range.
If I change the value of the input range on each drag event the HammerJS keeps firing it so fast that some mobile devices crash.
How can I limit the function call rate inside drag event?

I don't think you can change the rate of events called, because the events trigger, when something on the screen changes (e.g. a finger slides from a position to another). But you could perhaps try to limit the handling of the event.
Something like this could do the job:
var lastDeltaX, lastDeltaY = 0;
hammer.on("pan", function(event) {
if((lastDetaX - event.deltaX) < 5 ||
(lastDetaY - event.deltaY) < 5)
{
//Do something
lastDeltaX = event.deltaX;
lastDeltaY = event.deltaY;
}
});

Related

Scroll using Scroll-Bar Only

I am using three.js to allow users to create and edit a 3D model that involves using the scroll-wheel/two finger function, to zoom in and out. I want a second section of the page that is off the screen by default but the user can scroll down to see it. Preferably, this will be done only using the scroll bar, while the scroll-wheel can still be used.
For performance reasons, I'd prefer not to have to use something such as vue.js. Users provide data that remains on their computer that I'm using in both sections. This prevents me from just placing the data on another screen.
Overflow:hidden is out of the question because then I can not scroll to the bottom portion.
I tried using PreventDefault with several different EventListeners but none of them worked properly.
Below is the function that determines the size of the window and should include a function or the code to prevent scrolling.There aren't particular elements that shouldn't scroll, all of them shouldn't.
function onWindowResize() {
var viewWidth;
var viewHeight;
viewHeight=window.innerHeight-315;
//For Mobile
if(!UIactive && innerWidth < 640){
viewWidth= window.innerWidth;
//For Computer & Tablet
} else {
viewWidth= window.innerWidth -317;
if(window.innerHeight < 700){
viewHeight=window.innerHeight-52.67;
//Disable Scrollwheel
window.addEventListener('wheel',function(event){
//mouseController.wheel(event);
event.preventDefault();
}, false);
}
}
camera.aspect = (viewWidth) / (viewHeight);
camera.updateProjectionMatrix();
renderer.setSize(viewWidth, viewHeight);
UI.style.height= (viewHeight+'px');
}
Edit: I tried using the answer to a similar question. This did not achieve the desired result. I changed the code to be both window... and document... and a console.log statement included works but I can still scroll.
this.canvas.addEventListener('wheel',function(event){
mouseController.wheel(event);
return false;
}, false);
I then proceeded to try using preventDefault again and recieved the following error
Unable to preventDefault inside passive event listener due to target being treated as passive
Google Chrome docs say that,
With this intervention wheel/touchpad scrolling won't be blocked on document level wheel event listeners that do not need to call preventDefault() on wheel events.
Thus, you should apply the onmousewheel event on a specific div like so:
<div id="ScrollableDiv" style="height : 900px;background-color : red">
</div>
function stop(){
return false;
}
var div = document.getElementById('ScrollableDiv');
div.onmousewheel= stop;
Please refer this working fiddle.

Keep menu from closing when using touch events

I have hooked up a simple long touch function that after 500ms uses the "open" API command to open the context menu. The menu opens. However, on "touchend" the menu disappears. It only stays if I touchmove over the context menu before "touchend". Is there a way to prevent this sort of behaviour? From the source code, only a "touchstart" in a different part of the dom should trigger a close event.
Code is below, in case useful. Not that a delegate of tr is required by my context menu - to explain the targetTr variable use below.
var mobDevice_onLongTouch,
mobDevice_touchTimer,
mobDevice_longPressDuration = 500; //length of time we want the user to touch before we do something
//handle long press on the datatable
var touchArea = document.querySelector("#table");
touchArea.addEventListener("touchstart", touchAreaTouchStart, false);
touchArea.addEventListener("touchend", touchAreaTouchEnd, false);
function touchAreaTouchStart(e) {
var targetTr = $(e.target).closest('tr');
mobDevice_touchTimer = setTimeout(function () { touchArea_onLongTouch(targetTr) }, mobDevice_longPressDuration)
};
function touchAreaTouchEnd(e) {
if (mobDevice_touchTimer) {
clearTimeout(mobDevice_touchTimer) //reset the clock
}
};
function touchArea_onLongTouch(target) {
$('#table').contextmenu('open', target);
};
I solved this. ContextMenu was working fine, but the DOM control I was touching on registered a change event (to highlight a table row) on touchend. So the context menu popped up during touch and hold, then got cleared by a DOM change at touchend.
The solution was to manually add the highlight table row event to touchstart and preventDefault on touchend (when the touch target was inside the table)

Javascript onmouseUp without hold

I have set event listener onmouseUp.
I want to make difference between onmouseUp in short time (just click) and onmouseUp after holding lets say more than one second OR onmouseDown with mouseMove together.
Reason:
I'm listening button number 2 (which == 2), and i want to have function onclick to center something and zoom something with holding button2 and moving mouse up/down. But not to do it both in one time.
Is it possible in JS or jQuery with any integrated method?
Get NOW on Mouse Down
Get NOW on Mouse Up
var start = 0;
$('#button').mousedown(function () {
start = $.now();
});
$('#button').mouseup(function () {
end = $.now();
$('#output').html(end - start);
if (end - start > 1000) {
alert('you just held the mouse for 1 second');
}
});
DEMO
You can measure the time that was spent for the action before mouse is up:
E.g.:
$(<your_element>).on(<your_event_type>, function(e) {
start = new Date().getTime();
});
Then do a similar thing for the other event type and calculate a stop value.
Compute the difference stop - start and make a decision.
This will also cover the case when the mouse is moved while the click is pressed ( because it is bigger than a specified threshold ). But if you want to check that mouse was moved, you can use its coordinates (e.pageX and e.pageY).

JQuery Distinction between quick Click event and a prolonged MouseDown

I'm trying to create a scrolling button that reacts differently to a quick click event than it does to a prolonged MouseDown (click and hold). The quick click event will scroll a specific number of pixels while click and hold will slowly scroll the pane until mouse up where it will stop.
This is what I have currently:
var mdown;
$('.next').bind('mousedown', function(event) {
mdown = event.timeStamp;
moving = setInterval(function(){
$('#main').scrollLeft($('#main').scrollLeft() + 5);
}, 1);
});
$('.next').bind('mouseup', function(event) {
clearInterval(moving);
if ((event.timeStamp - mdown) < 100)
$('#main').animate({ scrollLeft : '+=800'}, 500);
});
Is there another way of doing this without comparing event timestamps? Is a click event treated any differently than mousedown/mouseup? Thanks!
Check this plugin(It defines an event to handle long clicks):
https://github.com/pisi/Longclick

Jquery Listbox Change event does not fire on Keyboard scrolling

I've got a simple Listbox on a HTML form and this very basic jQuery code
//Toggle visibility of selected item
$("#selCategory").change(function() {
$(".prashQs").addClass("hide");
var cat = $("#selCategory :selected").attr("id");
cat = cat.substr(1);
$("#d" + cat).removeClass("hide");
});
The change event fires fine when the current item is selected using the Mouse, but when I scroll through the items using the keyboard the event is not fired and my code never executes.
Is there a reason for this behavior? And what's the workaround?
The onchange event isn't generally fired until the element loses focus. You'll also want to use onkeypress. Maybe something like:
var changeHandler = function() {
$(".prashQs").addClass("hide");
var cat = $("#selCategory :selected").attr("id");
cat = cat.substr(1);
$("#d" + cat).removeClass("hide");
}
$("#selCategory").change(changeHandler).keypress(changeHandler);
You'll want both onchange and onkeypress to account for both mouse and keyboard interaction respectively.
Sometimes the change behavior can differ per browser, as a workaround you could do something like this:
//Toggle visibility of selected item
$("#selCategory").change(function() {
$(".prashQs").addClass("hide");
var cat = $("#selCategory :selected").attr("id");
cat = cat.substr(1);
$("#d" + cat).removeClass("hide");
}).keypress(function() { $(this).change(); });
You can chain whatever events you want and manually fire the change event.
IE:
var changeMethod = function() { $(this).change(); };
....keypress(changeMethod).click(changeMethod).xxx(changeMethod);
The behavior you describe, the change event triggering by keyboard scrolling in a select element, is actually an Internet Explorer bug. The DOM Level 2 Event specification defines the change event as this:
The change event occurs when a control
loses the input focus and its value
has been modified since gaining focus.
This event is valid for INPUT, SELECT,
and TEXTAREA. element.
If you really want this behavior, I think you should look at keyboard events.
$("#selCategory").keypress(function (e) {
var keyCode = e.keyCode || e.which;
if (keyCode == 38 || keyCode == 40) { // if up or down key is pressed
$(this).change(); // trigger the change event
}
});
Check a example here...
I had this problem with IE under JQuery 1.4.1 - change events on combo boxes were not firing if the keyboard was used to make the change.
Seems to have been fixed in JQuery 1.4.2.
$('#item').live('change keypress', function() { /* code */ });

Categories

Resources