Scriptaculous - setStyle not working in Firefox - javascript

I'm attempting to adjust some elements on a page dynamically when it gets resized (or opened on smaller displays). There is a piece of code that looks roughly like this:
$('some_id').setStyle({'margin-left':'200px'});
And it works as intended in Chrome but is failing in Firefox with no JavaScript warning or errors. And to be clear I have inspected the element in Firefox. It's straight up just not getting the style set. If I manually add in this rule with the inspector it works as intended.
More code has been requested:
function reset_ad_size() {
topAlign($('leftColumn'), $('adContentLeftFloat'));
leftSide = leftAlign($('mainBodyFrame'), $('adContentLeftFloat'));
leftSide -= 190;
if(leftSide < 0) {
$('site_wrap_neo').setStyle({'margin-left':'200px'});
leftSide = 5;
}
$('adContentLeftFloat').setStyle({left:leftSide+'px'});
}
document.observe("dom:loaded", function() {
reset_ad_size();
window.onresize = function() {
reset_ad_size();
}
});

I found the problem and wound up fixing it with this:
$('site_wrap_neo').style.marginLeft='200px';
For whatever reason Firefox didn't like the setStyle from Scriptaculous on that.

Related

Why is page spinner JavaScript not working in IE11, but works in Chrome and FireFox?

I put together a Vanilla JavaScript function that checks to see if elements on the page are loaded within X seconds (var timerDelay), and after X seconds if DOM elements are still loading, a loader spinner is shown (<div class="psspinner"></div>). Once all DOM elements have finished loading, remove the spinner from the DOM. What I've put together seems to work fine in Chrome and FireFox, but not in Internet Explorer 11.
I've remade the script using jQuery since it doesn't work in IE11 with Vanilla JS. Since this script is responsible for checking if all DOM elements are loaded on the page or not, using jQuery is counterproductive because it relies on the jQuery library to load before the script will fire. Using Vanilla JS does not rely on a library, and would load much faster.
I'm not sure why the below function doesn't work in IE11. I've tried a combination of things, such as swapping out querySelectorAll with getElementsByClassName, but nothing I've tried works. Any suggestions?
Here is a JS Fiddle for providing the code in a dev environment: https://jsfiddle.net/7f1hhezs/
Plain JS Version:
/**
* Page Load Spinner
* - Add Spinner to DOM
* - Vanilla JS
*/
function pSpinner() {
var timerDelay = 0;
var spinnerHtml = '<div class="pspinner"></div>';
// Append HTML to body
var appendSpinner = document.body.innerHTML += spinnerHtml;
// Initiating setTimeout before showing spinner
setTimeout(function () {
if (document.querySelectorAll('.pspinner').length > 0) {
console.log('loaded');
document.querySelector('.pspinner').setAttribute('style', 'display: block; opacity: 1.00;');
} else {
console.log('false');
return false;
}
}, timerDelay);
// Remove spinner once DOM load completes
window.addEventListener('load', function () {
var removeElem = document.querySelectorAll('.pspinner')[0];
removeElem.parentNode.removeChild(removeElem);
});
}
document.addEventListener('DOMContentLoaded', function () {
pSpinner();
});
jQuery Version:
/**
* Page Load Spinner
* - Add Spinner to DOM
* - jQuery
*/
function pSpinner() {
var timerDelay = 2500;
var spinnerHtml = '<div class="pspinner"></div>';
var spinnerSel = $('.pspinner');
// Append HTML to body
var appendSpinner = $('body').append(spinnerHtml);
// Initiating setTimeout before showing spinner
setTimeout(function () {
$('.pspinner').css({ display: 'block' });
$('.pspinner').animate({ opacity: 1.00 }, 150);
}, timerDelay);
// Remove spinner once DOM load completes
//window.addEventListener('DOMContentLoaded', function () {
window.addEventListener('load', function () {
$('.pspinner').remove();
});
}
$(document).ready(function(){ pSpinner(); });
There Is No Issue With Your Script, Your CSS Is The Problem
Your script is absolutely fine You can try it by commenting out that event listener for load. You can't see why page loader is not being showed because IE is little different(by little, I refer to your case, in my opinion IE is just another from another Kingdom (kingdom of living things, "yeah I am talking Biology"). DOMContentLoaded is fired either after the load event (I am talking few MS) or few ms before either ways, Your CSS does not work in IE-11, But that is not related, you might want to change tag to CSS. and yeah I changed your code A little bit, umm cleaned it a little bit if you may;
var spinnerHtml = '<div class="pspinner"></div>';
document.body.innerHTML += spinnerHtml;
var spinner = document.querySelector('.pspinner');
document.addEventListener('DOMContentLoaded',function pSpinner() {
var timerDelay = 0;
setTimeout(function () {
if (spinner) {
console.log('loaded');
spinner.setAttribute('style', 'display: block; opacity: 1.00;');
} else {
console.log('false');
return false;
}
}, timerDelay);
});
//try commenting out code below you'll know function is running
window.addEventListener('load', function () {
spinner.parentNode.removeChild(spinner);
});
Here You go! I'm not an expert it can be optimized much by leaps and bound and different approach can be applied to solve this problem, and to do same task much efficiently, but topic isn't about optimization it is "Why your script isn't working". Your script is working your CSS animations are not!

Jquery/Javascript not working on Firefox. Why?

I just found out that my script is working fine in Chrome, but not in FireFox - and I can't figure out why.
This is the site in development: www.fireflycovers.com
The script should execute when one of the round green buttons is clicked. (scrolls the window to the next container)
The script looks like this at the moment:
$('.scroll').css('display' , 'block');
$('.scroll').on('click', function(e) {
var container = $(this).parent();
// Scans if last container in group
while (document != container[0] &&
container.find('~.col, ~:has(.col)').length == 0) {
// If so, search siblings of parent instead
var container = container.parent(),
nextdiv = container.nextAll('.col, :has(.col)').first();
}
// Back to first .col (when no next .col)
if (nextdiv.length == 0) {
nextdiv = $(document).find('.col:first')
};
// Animates scrolling to new position
$('body').animate({scrollTop:nextdiv.offset().top}, 1000);
return false;
});
});
Did you try debugging at all? As in, putting console.log statements throughout your method to see what the values of things are at certain times and watching it execute? Anyway, does using this help at all?
$('body,html').animate({scrollTop:nextdiv.offset().top}, 1000);
Verified from Animate scrollTop not working in firefox
You need html because firefox behaves differently when it comes to overflow.

Appending div with image in Chrome

I am having problem with appending a div with an image to a page after clicking a link.
Here is my script, which on document.ready() adds the event.
var handler = function () {
$('#content').append("<div class=\"loading-graphic\" style=\"position:absolute;height:200px;width:200px;top:30%;left:40%;z-index:999;\"></div>");
//$("<div class=\"loading-graphic\" style=\"position:absolute;height:200px;width:200px;top:30%;left:40%;z-index:999;\"></div>").appendTo("div#content");
}
$(document).ready(function () {
for (var ls = document.links, numLinks = ls.length, i = 0; i < numLinks; i++) {
if (ls[i].parentElement.className != "t-window-actions t-header" && ls[i].parentElement.className != "t-widget t-numerictextbox") {
ls[i].onclick = handler;
}
}
})
The problem here that it doesn't work in Chrome while in Firefox and IE its working perfectly. After some digging i found out that it actually adds the div but doesn't show the image. (Tested it with adding the div on the beginning of the page, everything moves down and the div is empty)
I have tested it also adding it directly to page and then it works good but it's not what I'm looking for unfortunately.
Here is my css class:
.loading-graphic
{
background: url('~/Content/ico/loading_big.gif') no-repeat;
}
Got no idea what is causing the problem. Anyone got an idea? ;/
Honestly sometimes Chrome screws up. I have had issues with Chrome and background images, but it was only my computer. Try it on a different computer Chrome browser, it might not be the same.
The other thing I would suggest is, have your div coded already instead of appending it. So basically have it on the html code and position it out of sight, then when you need it, just move it to the right position.
It was the background position; also increased z-index, attached to body, and prevented other invisibility reasons.
var handler = function () {
$('body').append("<div class=\"loading-graphic\" style=\"position:absolute;height:200px;width:200px;top:50%;left:50%;margin:-100px 0 0 -100px;z-index:99999;background-position:center center;display:block !important;\"></div>");
}

jQuery: when using the on .scroll event and alert firefox seems to infinite loop

I have the following jQuery code in one of my master templates:
$(document).scroll(function() {
var scroll_top = $(document).scrollTop();
alert(scroll_top);
if (scroll_top <= 70) {
$('#fixedback').fadeOut(500);
} else {
$('#fixedback').fadeIn(500);
}
});
When the code executes Firefox 11 and 12 will blank the page and become unresponsive. I have to terminate the process in Task Manager. If I take out the alert(), the code executes perfectly. If I add an alert in any of the .scroll functions the same thing happens on any of my pages. The page will load and works until I scroll the page.
Using Jquery 1.7.1.min. and C# ASPX pages. I haven't tested on other browsers as it is only for development that I need the alerts to work.
It looks like a bug in Firefox.
The question: Firefox scrollTop problem has an answer that can be applied here. What it suggests is that you defer the alert() call using setTimeout() to give Firefox a chance to do whatever it needs to do to avoid blanking the page. Applying the workaround to your code, you would get something like this:
window.onscroll = catchScroll;
var timeOutId = 0;
var jitterBuffer = 200;
function catchScroll() {
if (timeOutId) clearTimeout(timeOutId);
timeOutId = setTimeout(function () { DoStuffOnScrollEvent() }, jitterBuffer);
}
function DoStuffOnScrollEvent() {
var scroll_top = $(document).scrollTop();
alert(scroll_top);
if (scroll_top <= 70) {
$('#fixedback').fadeOut(500);
} else {
$('#fixedback').fadeIn(500);
}
};
Or, instead of alert(), you could use console.log(), which will work natively in later versions of IE and Chrome, and Firefox via Firebug.

Forcing a DOM refresh in Internet explorer after javascript dom manipulation

Here is the situation. I have some javascript that looks like this:
function onSubmit() {
doSomeStuff();
someSpan.style.display="block";
otherSpan.style.display="none";
return doLongRunningOperation;
}
When I make this a form submit action, and run it from a non IE browser, it quickly swaps the two spans visibility and run the long javascript operation. If I do this in IE it does not do the swap until after onSubmit() completely returns.
I can force a dom redraw by sticking an alert box in like so:
function onSubmit() {
doSomeStuff();
someSpan.style.display="block";
otherSpan.style.display="none";
alert("refresh forced");
return doLongRunningOperation;
}
Also, the obvious jquery refactoring does not affect the IE behavior:
function onSubmit() {
doSomeStuff();
$("#someSpan").show();
$("#otherSpan").hide();
return doLongRunningOperation;
}
This behavior exists on IE8 and IE6. Is there anyway to force a redraw of the DOM in these browsers?
Mozilla (maybe IE as well) will cache/delay executing changes to the DOM which affect display, so that it can calculate all the changes at once instead of repeatedly after each and every statement.
To force an update (to force an immediate, synchronous reflow or relayout), your javascript should read a property that's affected by the change, e.g. the location of someSpan and otherSpan.
(This Mozilla implementation detail is mentioned in the video Faster HTML and CSS: Layout Engine Internals for Web Developers.)
To continue what ChrisW says:
here's flushing script to flash DOM, so you don't have to call alert(""); (found at http://amolnw.wordpress.com/category/programming/javascript/):
function flushThis(id){
var msie = 'Microsoft Internet Explorer';
var tmp = 0;
var elementOnShow = document.getElementById(id);
if (navigator.appName == msie){
tmp = elementOnShow.parentNode.offsetTop + 'px';
}else{
tmp = elementOnShow.offsetTop;
}
}
It works for me!!!
Thanks for the tip.
I had this problem in Chrome 21 dragging a word that had a letter with a descender ('g'). It was leaving a trail of moth dust behind on the screen, which would vanish the next time something made the screen refresh. ChrisW's solution (interrogating a layout-sensitive property) didn't work.
What did work was to add a 1-pixel blank div at the top of the page, then remove it a millisecond later, by calling the following the function at the end of the drag operation:
// Needed by Chrome, as of Release 21. Triggers a screen refresh, removing drag garbage.
function cleanDisplay() {
var c = document.createElement('div');
c.innerHTML = 'x';
c.style.visibility = 'hidden';
c.style.height = '1px';
document.body.insertBefore(c, document.body.firstChild);
window.setTimeout(function() {document.body.removeChild(c)}, 1);
}
Note: You need the delay. Simply adding and removing the div doesn't work. Also, the div needs to be added above the part of the page that needs to be redrawn.
You can also wrap you longterm function in a setTimeout(function(){longTerm();},1);
Can your longRunningOperation be called asynchronously?
element.focus() works for me in IE10
function displayOnOff(){
var elm = document.getElementById("myDiv");
elm.style.display="block";
elm.focus();
for(var i=0; i<1000000; i++){
console.log("waiting...............");
}
elm.style.display = "none";
}

Categories