jQuery problem with change event and IE8 - asp.net

There is a bug in jQuery 1.4.2 that makes change event on select-element getting fired twice when using both DOM-event and a jQuery event, and this only on IE7/8.
Here is the test code:
<html>
<head>
<script src="http://code.jquery.com/jquery-1.4.2.js" type="text/javascript"></script>
<script type="text/javascript">
jQuery(document).ready(function() {
jQuery(".myDropDown").change(function() {
});
});
</script>
</head>
<body>
<select class="myDropDown" onchange="alert('hello');">
<option>1</option>
<option>2</option>
<option>3</option>
<option>4</option>
</select>
</body>
</html>
Update:
Another view of the problem, actually this is the real problem we have with our application. Binding a live change event on a selector that isn't even touching the select-element with DOM-event also causes double firing.
<html>
<head>
<script src="http://code.jquery.com/jquery-1.4.2.js" type="text/javascript"></script>
<script type="text/javascript">
jQuery(document).ready(function() {
jQuery(".someSelectThatDoesNotExist").live("change", function() {
});
});
</script>
</head>
<body>
<select class="myDropDown" onchange="alert('hello');">
<option>1</option>
<option>2</option>
<option>3</option>
<option>4</option>
</select>
</body>
</html>
Ticket to actual bug: http://dev.jquery.com/ticket/6593
This causes alot of trouble for us in our application cause we use both ASP.NET-events mixed with jQuery and once you hook up a change event on any element every select (dropdown) gets this double firing problem.
Is there anyone who knows a way around this in the meantime until this issue is fixed?

I hate to raise this question from the dead but jquery finally fixed this bug in version 1.7 which was recently released.

I had a play around with the bug and there doesn't appear to be any obvious workaround. In my testing I found that the second change event is triggered by jQuery, so I managed to knock together a quick solution that involves removing the DOM 0 event handler and applying it again on a timer that executes immediately when the thread completes:
jQuery(".myDropDown").change(function() {
if ($.browser.msie) {
var dd = $(this)[0],
oc = dd.onchange;
dd.onchange = null;
window.setTimeout(function () {
dd.onchange = oc;
}, 0);
}
});
This works fine for me in IE8, just one "hello" alert appears, although you might want to add an IE check in there. Or not, it probably won't make a difference It definitely needs that check and I've added it to the sample. Here's my fiddle.
The only other solution would be to remove the DOM 0 handler and use the jQuery handler only.

Clone the control and add the clone immediately after the intended one and assign the event, then remove the control:
if ($.browser.msie && (parseInt($.browser.version, 10) == 8 || parseInt($.browser.version, 10) == 7)) {
var btn2 = $(btn).clone();
$(btn).after(btn2);
$(btn).remove();
$(btn2).bind("click", function () {
//your function here
});
}

something like this?
jQuery(".myDropDown").removeAttr('onchange').change(function() {
alert(0);
});

We actually solve the problem another way, since this is specific to IE, ASP.NET and select element, we use the following code:
$(function () {
if ($.browser.msie) {
var prm = Sys.WebForms.PageRequestManager.getInstance();
prm.add_pageLoaded(function() {
$('select[onchange]:not(.iefixed)')
.addClass('iefixed')
.each(function () {
var self = $(this), dd = self[0], action = self.attr('onchange');
self.removeAttr('onchange').change(action);
dd.onpropertychange = function() { dd.blur(); };
});
});
}
});
This make sure that the fix is only applied to the select element that has autopostback set to true (onchange) once.
Basically we rely on jQuery to fire the change event for us, but in order for IE to do that, we need to trigger element blur event when onpropertychange happens.

Related

Disable Woocomerce register button after one click

Hello I would like to disable the woocommmerce register page button after one click to avoid multiple clicks.
I have searched the forums and found a bunch of solutions for custom forms and I've tried the following JS code but had no luck. I have a feeling I am setting the wrong selector because I cannot for the life of me figure out what the correct selector for the default register button is.
<script>
function disableButton() {
var btn = document.getElementById('woocommerce-register-nonce');
btn.disabled = true;
btn.innerText = 'Posting...'
}
</script>
I've also tried :
<script>
jQuery('woocommerce-Button.woocommerce-button.button.woocommerce-form-register__submit').live('click', function (e) {
var self = this;
$(this).attr("disabled", "disabled");
do_something();
setTimeout(function () {
$(self).removeAttr('disabled');
}, 10000);
});
</script>
Some guidance would be very much appreciated.
Update!
Based on Onboardmass's suggestion I have corrected the selector and got it partially working using jquery.
<script>
jQuery('.woocommerce-Button.woocommerce-button.button.woocommerce-form-register__submit').click(function(){
jQuery(this).attr("disabled", "disabled");
});
</script>
The button now gets disabled on click however the issue I'm facing now is that the form does not get submitted.
The issue you're facing is because the selector is incorrect. It should be .woocommerce-Button.woocommerce-button.button.woocommerce-form-register__submit.
For anyone else who may need this I was able to figure this one out by reading through the suggestions and other threads I found. Thank you Onboardmass & Martin for the guidance!
The time out function is required for the click to register.
<script>
$(document).ready(function () {
$(".woocommerce-Button.woocommerce-button.button.woocommerce-form-register__submit").click(function () {
setTimeout(function () { disableButton(); }, 0);
});
function disableButton() {
$(".woocommerce-Button.woocommerce-button.button.woocommerce-form-register__submit").prop('disabled', true);
}
});
</script>

Reload the "Sign In With Google" button if user changes locale

I can't find any documented way to reload the new "Sign in With Google" button in JavaScript.
I have to remove the script tag and the "button" div then re-add them both.
Does anyone know of a better way to do this?
Have you looked at the JS renderButton method ?
Assuming you have something like this to initialize the library and display the button in JS, you might be able to update locale in the second parameter to renderButton and call the method again to switch languages.
<html>
<body>
<script src="https://accounts.google.com/gsi/client" async defer></script>
<script>
function handleCredentialResponse(response) {
console.log("Encoded JWT ID token: " + response.credential);
}
window.onload = function () {
google.accounts.id.initialize({
client_id: "YOUR_GOOGLE_CLIENT_ID",
callback: handleCredentialResponse
});
google.accounts.id.renderButton(
document.getElementById("buttonDiv"),
{ theme: "outline", size: "large", locale: "the new locale" }
);
google.accounts.id.prompt(); // also display the One Tap dialog
}
</script>
<div id="buttonDiv"></div>
</div>
</body>
</html>
Obviously, you'd call renderButton a second time from outside of the window.onload example above, I didn't go as far as showing that in the code sample though.

UIkit 3 Event is not working

I've been trying to add a tooltip to a button that only shown when certain conditions are met. I'm using uikit#3.0.0-beta.35. According to the documentation, I should return false on beforeshow event.
UIkit.tooltip($element, { pos: 'top' });
$element.on('beforeshow', function(){
return false;
});
if(condition){
UIkit.tooltip($element).show();
}
The problem is that the beforeshow function never fires for some reason. I even tried this syntax mentioned in UIkit documentation:
UIkit.util.on($element, 'beforeshow', function () {
return false;
});
Unfortunately, none of these methods worked for me.
the docs has some mistake, switcher has the same problem. the event is triggered on document not the target. you can use this syntax like this:
UIkit.util.on(document, 'event', '#target-id', callback)
the docs confused me a long time :(
The problem with your code is, that you're trying to listen to an event directly on the element, while the event is triggered on the document - there is an error in the documentation, as they say it's triggered on the element, but it's not.
There is also a fresh false bug report regarding this
var $element = $('#hoverButton');
var $check = $('#tooltipToggle');
UIkit.tooltip($element);
$(document).on('beforeshow', $element, function() {
if (!$check.prop('checked')) return false;
});
<!-- UIkit CSS -->
<link rel="stylesheet" href="https://cdnjs.cloudflare.com/ajax/libs/uikit/3.0.0-beta.35/css/uikit.min.css" />
<!-- UIkit JS & jQuery (not required by UIKit anymore) -->
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/uikit/3.0.0-beta.35/js/uikit.min.js"></script>
<div class="uk-position-center">
<label>show tooltip <input id="tooltipToggle" class="uk-checkbox" type="checkbox"></label><br><br>
<button id="hoverButton" class="uk-button uk-button-default" title="Hello World">Hover</button>
</div>
For Switcher:
$(document).on('show', $('#switcherId'), function(){
console.log('fired');
});
I may need this answer in the future too...

How do I change the style of an input box in IE7 on focus?

I know IE7 has issues...
I've read posts here and on Google telling me I need to set the style by hand onfocus() and onblur(). However, everything I try isn't working!
Here is my jQuery
$(document).ready(function(){
if (jQuery.browser.msie === true) {
$("input.date-picker").each(function(i)
{
var $foo= $(this);
$foo.bind('onfocus onblur', function() {
$(this).toggleClass('smalltxt-active');
});
});
}//end if
});
The a corresponding box
<input name="ctl00$SelectionContent$Selections1$txtDestinationDate" type="text"
id="ctl00_SelectionContent_Selections1_txtDestinationDate" class="date-picker"
style="width:80px;" />
I have already confirmed that my code is detecting MSIE. That I am getting a count of 2 input.date-picker objects.
Any ideas?
Thanks in advance,
$foo.bind('onfocus onblur', function() {
should be
$foo.bind('focus blur', function() {
You don't need the each-loop really,
$("input.date-picker").bind('focusin focusout', function(){
$(this).toggleClass('smalltxt-active');
}
Is just fine. It will select all input elements with the class 'date-picker' and bind the events to it.
You may also want to read about the .focusin() and .focusout() events.
try this for many form element
$("input,select,button").bind('focusin focusout', function(){
$(this).toggleClass('focu');
});

Implementing modalpopups as default alert in entire project

right now I have a huge Solution in which we use javascript alerts via RegisterStartupScript for all messages and errors.. We were willing to modify all this to making something similar to the modalPopupExtender, or the extender itself in a way that doesn't require too much effort... I mean, to show a modalpopup on a single page I need to create it on the aspx file, setting the attributes etc... So i'm just asking for Ideas, want to know how you guys deal with this..
I'd probably use jQuery dialog and put the markup and initialization code in a MasterPage, set with autoOpen false and hidden by default. I'd inject code that interacts with the dialog into each page as needed.
<div id="modalDialog" title="Error">
<p id='modalDialogMsg'>An error has occurred.</p>
</div>
<script type="text/javascript">
$(function() {
$('#modalDialog').dialog({
autoOpen: false;
modal: true,
buttons: {
"OK" : function() {
$(this).dialog('close');
}
}
});
});
// You could "objectify" this, but I'll show as a global function
function showError( title, msg )
{
if (!title) {
title = 'Error';
}
if (!msg) {
msg = 'An error occurred.';
}
$('#modalDialogMessage').html(msg);
$('#modalDialog').attr('title',title)
.dialog('open');
}
</script>
Then, in your page you'd inject code that calls showError. Note this would need to be after the script above in order to make sure that the function has been defined. What would spit out would render like:
<script type="text/javascript">
$(function() {
showError('Database connection error', 'There was an error connecting to the database.' )'
});
</script>
Could you not place the modal popup/ modal popup extender into a user a control and embed the user control into each page?

Resources