Xamarin Scroll lagging in WebView - xamarin

So i injected some java script in my webview and on scroll event i call the nativ function on cs.
The problem is that the scroll function is lagging for some reasion even though i have it inside setTimeout event.
Any idee on how to solve it?
Obbs the scroll work just fine when i remove the code below.
Here is the js function
script.Append(#"var timer; window.addEventListener('scroll', function(e) {
if (timer)
clearTimeout(timer);
timer = setTimeout(function(){
if (window.toBottom === true){
window.toBottom = false;
Native('onScroll', window.scrollY);
return;
}
if ((window.innerHeight + window.scrollY) >= (document.body.offsetHeight -30)) {
Native('onScrolledBottomReached', window.scrollY);
}else if (window.scrollY<=5) {
Native('OnScrolledTopReached', window.scrollY);
}else {
Native('onScroll', window.scrollY);
}
},1000);
});");

Related

Canvas keydown events

I'm fairly new to canvas and experimenting with random functions. I've gotten mouseClick events and now I'm trying to implement a keydown event to do something simple like change the background color.
I'm looking at a lot of keyDown event examples and am a little confused about the structured.
Is it as simple as
if (e.keyCode == 40) { *change background color code }
I'm seeing a lot of people having some false, true statements in there as well, which throws me off.
Yes, it's that simple. Check if the key was pressed inside of a listener for the keydown event:
window.addEventListener('keydown', function (event) {
if (event.keyCode === 40) {
*change background*
}
});
Alternative:
var keys = [];
window.addEventListener('keydown', function (event) {
keys[event.keyCode] = true;
if (keys[40] === true) {
*change background color*
}
});
window.addEventListener('keyup', function (event) {
keys[event.keyCode] = false;
});
(might be aforementioned true/false statements OP mentioned)
JSFiddle: #1, #2.

tap event fired after taphold jQuery Mobile 1.1.1

I am developing an app for iOS using Phonegap bundled with jQuery Mobile 1.1.1. I have a div on my page that is listening for both tap and taphold events.
The problem I am facing is that the tap event is fired after the taphold event once I lift my finger. How do I prevent this?
A solution is provided here but is this the only way to do this? Kinda nullifies the whole point of having two different events for tap & taphold if you need to use a boolean flag to differentiate the two.
Following is my code:
$('#pageOne').live('pageshow', function(event) {
$('#divOne').bind('taphold', function (event) {
console.log("TAP HOLD!!");
});
$('#divOne').bind('tap', function () {
console.log("TAPPED!!");
});
});
Would greatly appreciate the help. Thanks!
Simply set this at the top of your document or anywhere before you define your even:
$.event.special.tap.emitTapOnTaphold = false;
Then you can use it like this:
$('#button').on('tap',function(){
console.log('tap!');
}).on('taphold',function(){
console.log('taphold!');
});
[Tried and Tested]
I checked jQuery Mobile's implementation. They are firing the 'tap' event after 'taphold' every time on 'vmouseup'.
Workaround would be not to fire the 'tap' event if the 'taphold' has been fired. Create a custom event or modify the source as per you need as follows:
$.event.special.tap = {
tapholdThreshold: 750,
setup: function() {
var thisObject = this,
$this = $( thisObject );
$this.bind( "vmousedown", function( event ) {
if ( event.which && event.which !== 1 ) {
return false;
}
var origTarget = event.target,
origEvent = event.originalEvent,
/****************Modified Here**************************/
tapfired = false,
timer;
function clearTapTimer() {
clearTimeout( timer );
}
function clearTapHandlers() {
clearTapTimer();
$this.unbind( "vclick", clickHandler )
.unbind( "vmouseup", clearTapTimer );
$( document ).unbind( "vmousecancel", clearTapHandlers );
}
function clickHandler( event ) {
clearTapHandlers();
// ONLY trigger a 'tap' event if the start target is
// the same as the stop target.
/****************Modified Here**************************/
//if ( origTarget === event.target) {
if ( origTarget === event.target && !tapfired) {
triggerCustomEvent( thisObject, "tap", event );
}
}
$this.bind( "vmouseup", clearTapTimer )
.bind( "vclick", clickHandler );
$( document ).bind( "vmousecancel", clearTapHandlers );
timer = setTimeout( function() {
tapfired = true;/****************Modified Here**************************/
triggerCustomEvent( thisObject, "taphold", $.Event( "taphold", { target: origTarget } ) );
}, $.event.special.tap.tapholdThreshold );
});
}
};
You can use stopImmediatePropagation() method of jquery to solve this issue. According to the explanation in jquery api, stopImmediatePropagation() method
"Keeps the rest of the handlers from being executed and prevents the
event from bubbling up the DOM tree."
put this in your taphold event handler... this suggestion assumes o is a jQuery object that fired the taphold
jQuery(o).one('tap click', function(){ return false; });
the binding to the one method will fire the event only once. returning false will stop the execution of that event if it was an < a > tag.
Since swipe, triggers taphold then I was able to keep it simple with:
$(c).bind("taphold",function(e){
if(e.target.wait){
e.target.wait = false;
}else{
alert("fire the taphold");
}//eo if not waiting
});
$(c).bind("swipe",function(e){
e.target.wait = true;//taphold will come next if I don't wave it off
alert(e.target.text+"("+e.target.attributes.dataId.value+") got swiped");
return false;
});
To support tap too then I'd defer the wait clear until the tap event which will also always fire.
I still have problems, with jquery-mobile's taphold, I solved the problem of the click called after taphold, putting a timeout on the element.
JQM 1.4 with emitTapOnTaphold = false;
Example:
$(".element").on("taphold", function () {
        // function her
         setTimeout (function () {
             $(this).blur();
         400);
});
$.event.special.tap = {
tapholdThreshold: 750,
setup: function() {
var thisObject = this,
$this = $( thisObject );
$this.bind( "vmousedown", function( event ) {
if ( event.which && event.which !== 1 ) {
return false;
}
var origTarget = event.target,
origEvent = event.originalEvent,
/****************Modified Here**************************/
tapfired = false,
timer;
function clearTapTimer() {
clearTimeout( timer );
}
function clearTapHandlers() {
clearTapTimer();
$this.unbind( "vclick", clickHandler )
.unbind( "vmouseup", clearTapTimer );
$( document ).unbind( "vmousecancel", clearTapHandlers );
}
function clickHandler( event ) {
clearTapHandlers();
// ONLY trigger a 'tap' event if the start target is
// the same as the stop target.
/****************Modified Here**************************/
//if ( origTarget === event.target) {
if ( origTarget === event.target && !tapfired) {
triggerCustomEvent( thisObject, "tap", event );
}
}
$this.bind( "vmouseup", clearTapTimer )
.bind( "vclick", clickHandler );
$( document ).bind( "vmousecancel", clearTapHandlers );
timer = setTimeout( function() {
tapfired = true;/****************Modified Here**************************/
triggerCustomEvent( thisObject, "taphold", $.Event( "taphold", { target: origTarget } ) );
}, $.event.special.tap.tapholdThreshold );
});
}
};
#Akash Budhia: Thanks for your solutions.
It's great, sounds it work for me!

hidding elements in a layout page mvc3

ok so im having a hard time hiding some layout sections (divs in my layout page and im using mvc3).
I have this js fragment which is basically the main logic:
$('.contentExpand').bind('click', function () {
$.cookie('right_container_visible', "false");
});
//Cookies Functions========================================================
//Cookie for showing the right container
if ($.cookie('right_container_visible') === 'false') {
if ($('#RightContainer:visible')) {
$('#RightContainer').hide();
}
$.cookie('right_container_visible', null);
} else {
if ($('#RightContainer:hidden')) {
$('#RightContainer').show();
}
}
as you can see, im hidding the container whenever i click into some links that have a specific css. This seems to work fine for simple tests. But when i start testing it like
.contentExpand click --> detail button click --> .contentExpand click --> [here unexpected issue: the line $.cookie('right_container_visible', null); is read but it doesnt set the vaule to null as if its ignoring it]
Im trying to understand whats the right logic to implement this. Anyone knows how i can solve this?
The simpliest solution is to create variable outside delegate of bind.
For example:
var rightContVisibility = $.cookie('right_container_visible');
$('.contentExpand').bind('click', function () {
$.cookie('right_container_visible', "false");
rightContVisibility = "false";
});
if (rightContVisibility === 'false') {
...
}
The best thing that worked for me was to create an event that can catch the resize of an element. I got this from another post but I dont remember which one. Anyway here is the code for the event:
//Event to catch rezising============================================================================
(function () {
var interval;
jQuery.event.special.contentchange = {
setup: function () {
var self = this,
$this = $(this),
$originalContent = $this.text();
interval = setInterval(function () {
if ($originalContent != $this.text()) {
$originalContent = $this.text();
jQuery.event.handle.call(self, { type: 'contentchange' });
}
}, 100);
},
teardown: function () {
clearInterval(interval);
}
};
})();
//=========================================================================================
//Function to resize the right container============================================================
(function ($) {
$.fn.fixRightContainer = function () {
this.each(function () {
var width = $(this).width();
var parentWidth = $(this).offsetParent().width();
var percent = Math.round(100 * width / parentWidth);
if (percent > 62) {
$('#RightContainer').remove();
}
});
};
})(jQuery);
//===================================================================================================

.bind() statement not working in jQuery Easy Confirmation plugin

Did anyone who used jQuery Easy Confirmation plugin run into this issue - the button upon which the confirm box is bound loses its original click event after the first click? I had to change the plugin code to this to make it work. The difference here is between .bind and .click. Can anyone explain why? Pls. let me know if my question is not clear. Thx!
Original plugin code:
// Re-bind old events
var rebindHandlers = function () {
if (target._handlers != undefined) {
jQuery.each(target._handlers, function () {
//this is the difference
$target.bind(type, this);
});
}
}
Changed (working) code:
// Re-bind old events
var rebindHandlers = function () {
if (target._handlers != undefined) {
jQuery.each(target._handlers, function () {
//this is the difference
if(type == 'click')
$target.click(this);
else {
$target.bind(type, this);
}
});
}
}
Try using some alerts to see what's happening...
// Re-bind old events
var rebindHandlers = function () {
if (target._handlers != undefined) {
jQuery.each(target._handlers, function () {
if(type == 'click')
alert('$target.click(' + this + ');');
//$target.click(this);
else {
alert('$target.bind(' + type + ', ' + this + ');');
//$target.bind(type, this);
}
});
}
}

How can I cancel scrollTo if it's been triggered?

I'd like to do something like:
var scrollable;
scrollable = $(window).scrollTo(99999, 99999);
$(window).scroll(function() {
// cancel the scrollTo
scrollable = null;
});
Based on jonobr1's code this works for me:
if(window.addEventListener) document.addEventListener('DOMMouseScroll', stopScroll, false);
document.onmousewheel = stopScroll;
function stopScroll() {
$(window)._scrollable().stop(true, false); // Stops and dequeue's animations
}
I added a call to stopScroll before my scrollTo calls in my event handlers too.
After some fiddling I found this to work well.
$(window).scrollTo(99999, 99999);
$(window).click(function() {
stopScroll();
});
if(window.addEventListener) document.addEventListener('DOMMouseScroll', stopScroll, false);
document.onmousewheel = stopScroll;
function stopScroll() {
$(window).stop(true, false); // Stops and dequeue's animations
}
No need to modify plugin or source!

Resources