I got an error message
"Uncaught TypeError: Cannot set property 'cssText' of undefined"
My Code:
var div = $('.postImg2')
var img = $('.postInner2');
var divAspect = 20 / 50;
var imgAspect = img.height / img.width;
if (postData.files != null) { // if attached images or videos exist
for (var i = 0; i < postData.files.length; i++) {
if(postData.files.length == 1){
postView = postView + "<div class='postImg1'><img class='postInner1' src='img_timeline/" + postData.files[i].url + "'></div>"
} else if(postData.files.length == 4){
if(imgAspect <= divAspect){
var imgWidthActual = div.offsetHeight / imgAspect;
var imgWidthToBe = div.offsetHeight / divAspect;
var marginLeft = -Math.round((imgWidthActual-imgWidthToBe)/2);
postView = postView + "<div class='postImg2'><img class='postInner2' src='img_timeline/" + postData.files[i].url + "'></div>"
img.style.cssText = 'margin-left:'+marginLeft+'px;'
} else {
img.style.cssText = 'margin-left:0;'
}
} else if (postData.files.length > 4){
postView = postView + "<div class='postImg3'><img class='postInner3' src='img_timeline/" + postData.files[i].url + "'></div>"
}
}
}
How do I use cssText in javascript?
The problem you have is you have a jQuery object and you act like it is DOM.
img.get(0).style.cssText = 'margin-left:0;'
//or
img[0].style.cssText = 'margin-left:0;'
but why use cssText? Seems better to do
img[0].style.marginLeft = "0px";
or since you are using jQuery
img.css("marginLeft", "0px")
And after that is complete it still will not work. The reason is the fact you are selecting the element before it is added to the page. The $('.postInner2'); is not going to pick up the image you added to the page in the loop since you select it before it is added. In reality you can not update the widths and select the elements until you append postView to the page.
Replace this
img.style.cssText = 'margin-left:'+marginLeft+'px;'
With this
img.css('margin-left',marginLeft+'px')
Here is a really basic example of how cssText works. I suspect your img variable is not set or is referencing a non-existant element.
Whatever the case, img.style is undefined.
Update To show how you could do this in jQuery (but why are you not using .css or .attr rather than mixing and matching pure JS with jQuery) ?
var img = $('.postInner2');
// Get the first element from the jQuery array and apply a style with cssText.
img[0].style.cssText = "width:100px;";
/**
* A better solution would be ".css" because it will apply to
* ALL elements with class .postInner2 without having to loop
*/
// $(".postInner2").css({width:"100px", marginLeft: "10px"});
/**
* Or if you have to override everything in the class:
*/
// $(".postInner2").attr("css","width:100px;margin-left:10px");
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<img class="postInner2" src="//placehold.it/400x200" alt="Placeholder" />
Edit2: actually, based on your updated code it looks like there is no way it can work. You are trying to fetch and manipulate your image before it even exists in the DOM, for example: div.offsetHeight / divAspect where the actual div is actually only described on the next line, and not ever added into the HTML anywhere.
I think you are going to have to re-think the flow of logic in your code.
Related
I need to check if a web page has Font Awesome in it. If not I'm going to load it with javascript. Kinda like how the facebook sdk checks to see if there is a script element containing the id "facebook-jssdk", if so it just returns (does nothing), if not it loads it. I need to do that for Font Awesome.
I think this is the best way to check for font-awesome, but I'm not sure if it's slower then just loading it again even if it is there.
function css(element, property) {
return window.getComputedStyle(element, null).getPropertyValue(property);
}
window.onload = function () {
var span = document.createElement('span');
span.className = 'fa';
span.style.display = 'none';
document.body.insertBefore(span, document.body.firstChild);
if ((css(span, 'font-family')) !== 'FontAwesome') {
// add a local fallback
}
document.body.removeChild(span);
};
One, not sure-fire way, would be to check for the existence of the Css file. The function below would find many variations, such as ones served from a cdn, or have a "-min" suffix in the file name. There are unlikely instances this will falsely return true (if for instance somebody created an additional css file called "font-awesome-extensions.css"). A more likely problem with this approach is if a font-awesome is bundled in another file then this wouldn't find the file and falsely return false.
function findCss(fileName) {
var finderRe = new RegExp(fileName + '.*?\.css', "i");
var linkElems = document.getElementsByTagName("link");
for (var i = 0, il = linkElems.length; i < il; i++) {
if (linkElems[i].href && finderRe.test(linkElems[i].href)) {
return true;
}
}
return false;
}
console.log(findCss("font-awesome"));
Here's a way, but ask yourself why you're doing this? source.
/**
* Checks if a font is available to be used on a web page.
*
* #param {String} fontName The name of the font to check
* #return {Boolean}
* #license MIT
* #copyright Sam Clarke 2013
* #author Sam Clarke <sam#samclarke.com>
*/
(function (document) {
var calculateWidth, monoWidth, serifWidth, sansWidth, width;
var body = document.body;
var container = document.createElement('div');
var containerCss = [
'position:absolute',
'width:auto',
'font-size:128px',
'left:-99999px'
];
// Create a span element to contain the test text.
// Use innerHTML instead of createElement as it's smaller
container.innerHTML = '<span style="' + containerCss.join(' !important;') + '">' +
Array(100).join('wi') +
'</span>';
container = container.firstChild;
calculateWidth = function (fontFamily) {
container.style.fontFamily = fontFamily;
body.appendChild(container);
width = container.clientWidth;
body.removeChild(container);
return width;
};
// Pre calculate the widths of monospace, serif & sans-serif
// to improve performance.
monoWidth = calculateWidth('monospace');
serifWidth = calculateWidth('serif');
sansWidth = calculateWidth('sans-serif');
window.isFontAvailable = function (fontName) {
return monoWidth !== calculateWidth(fontName + ',monospace') ||
sansWidth !== calculateWidth(fontName + ',sans-serif') ||
serifWidth !== calculateWidth(fontName + ',serif');
};
})(document);
You could do like this with jquery
var url = "https://maxcdn.bootstrapcdn.com/font-awesome/4.6.3/css/font-awesome.min.css";
check if the css is loaded
if (!$("link[href=url]").length)
//append the link to the head tag if not loaded
$('<link href=url rel="stylesheet">').appendTo("head")
I am trying to cycle through an array of pictures to make a photo-viewer on my webpage. The cycling method is working fine, but the transferring the message unto the css is not. I am wondering if there is any syntax issues within my javascript code or a concept that I am missing out on. I know that the cycling works because the alert I have is working.
var changeIt = ""
var backgroundPic = new Array(4);
backgroundPic[0] = '("images/displayPic1.jpg")';
backgroundPic[1] = '("images/displayPic2.jpg")';
backgroundPic[2] = '("images/displayPic3.jpg")';
backgroundPic[3] = '("images/displayPic4.jpg")';
backgroundPic[4] = '("images/displayPic5.jpg")';
var picCounter = 0;
var numberOfPics = 5;
var picTimer;
function setPic(){
alert("hi I want this pic: " + backgroundPic[picCounter]);
$('slider').css('background-image', url + "backgroundPic[picCounter]");
picCounter += 1;
if(picCounter >= numberOfPics){
picCounter = 0;
}
}
$(document).ready(function(){
$('.slider').css('background-image', backgroundPic[picCounter]);
picTimer = setInterval(setPic, 2000);
});
The issue is due to the incorrect syntax you're using when concatenating the CSS property value. Try this:
var backgroundPic = [ 'images/displayPic1.jpg', 'images/displayPic2.jpg', 'images/displayPic3.jpg', 'images/displayPic4.jpg', 'images/displayPic5.jpg' ];
var picCounter = 0;
var picTimer;
function setPic() {
// note the . in the jquery object below to indicate a class selector
$('.slider').css('background-image', 'url("' + backgroundPic[picCounter % backgroundPic.length] + '")');
picCounter++;
}
$(document).ready(function() {
picTimer = setInterval(setPic, 2000);
setPic();
});
You have to set background image like this:
$('.slider').css('background-image', "url('" + backgroundPic[picCounter] + "')");
You inverted the positioning of the quotemarks on the second line of setPic.
Try: $('slider').css('background-image', 'url' + backgroundPic[picCounter]);
On your setPic function, this line
$('slider').css('background-image', url + "backgroundPic[picCounter]");
isn't missing a dot on $('.slider')?
You'll need to include double quotes (") before and after the imageUrl like this:
$('slider').css('background-image', 'url("' + backgroundPic[picCounter] + '")');
This way, if the image has spaces it will still be set as a property.
I'am trying to identify with javascript if I need to force a page break in my document.
One element that is overflow hidden. I loop through each of the elements within this document. I remove all last childs until the height of the element within the overflow:hidden element is smaller. Now I know, when to page break and I push all removed childs in the new page.
Works fine in browser. But not in PDF...
I'am using http://wkhtmltopdf.org/
See problem here: Left: PDF, Right: Browser (Chrome)
Height of 3262px vs 358px...
Same if I use .clientHeight or jQuery .height().
Does anyone know a workaround to get heights the same?
Some code:
function isOverflowed(element){
// return element.scrollHeight > element.clientHeight;
// console.log(element.clientHeight);
// console.log(element.parent().height() +'>'+ element.height());
return element.parent().height() < element.height();
}
// var daysWrapper = document.getElementById('days');
// var days = daysWrapper.querySelectorAll(".section.day");
var days = $('#days .section.day');
// console.log(days);
days.each(function() {
var $this = $(this);
var area = $this.find('.day-info');
var content = area.children();
var lasts = $( '<div class="lasts">' );
var test = 0;
while(isOverflowed(content)) {
var last = content.children().last();
// lasts.append( $( last ) );
last.clone().prependTo(lasts);
last.remove();
test++;
if (test > 6) break;
}
content.find('h1').html(area.height() + ' - ' + content.height());
if (lasts.children().length ) {
var newPage = $this.clone();
newPage.insertAfter($this);
newPage.find('.day-image').remove();
newPage.find('.day-info').removeClass('overflow');
newPage.find('.day-info').children().html(lasts.html());
}
});
Thanks!
Lets say I have these images gallery, how do i randomly display the images everytime when i reload the page?
http://creativepreviews.com/fiddle/study/20131007/
Let's say the image will display in the background of the DIV, then the following should do it.
// JS
var imgArray = ["img1.jpg", "cat.jpg", "sky.jpg"]
function randomBg() {
x = Math.random()
y = Math.round(x * 10)
if (imgArray[y] != undefined) {
document.getElementById("blah").style.backgroundImage = "url('" + imgArray[y] + "')"
} else {
document.getElementById("blah").style.backgroundImage = "url('default.jpg')"
}
}
...and the HTML.
<script src="test.js"></script>
<body onload="randomBg()">
<div id="blah"></div>
...or you could replace the style.backgroundImage in the JS with innerHTML = <img src=" etc...
You could do something along these lines (not tested)
var grd = $('#grid');
var imgs = grd.children();
imgs.sort(function(){return (Math.round(Math.random()) - 0.5);});
grd.remove('li');
for(var i=0;i < imgs.length;i++) grd.append(imgs[i]);
In essence what we are doing is getting all the li elements in 'grid' into an array, randomizing them, removing them all from 'grid' and then putting them back in again.
If you had supplied a working fiddle rather than a link to the finished article it would be easier to modify it and provide a more complete solution.
What I'm trying to achieve:
Based on URL (ie., foo.com/item1), the div element "logoswap" receives a different class.
The following is the code I put together but it seems completely wrong. I'm not a JS pro by any means, XHTML/CSS is more my speed (some PHP)... I cannot use PHP, even if it is possible in PHP (and I know it is because I have a PHP version of what I need done already, but I can't call the PHP properly.
I'm really just trying to get a different logo to show up based on the directory/url... It doesn't have to be a background element called in by the CSS class necessarily, I just need a different image to load based on the aforementioned url variable...
$(function() {
var url = location.pathname;
if(url.indexOf('item1') > -1) {
document.getElementById("logoswap").className += " class1";
}
elseif(url.indexOf('item2') > -1) {
document.getElementById("logoswap").className += "class2";
}
elseif(url.indexOf('item3') > -1) {
document.getElementById("logoswap").className += "class3";
}
elseif(url.indexOf('item4') > -1) {
document.getElementById("logoswap").className += "class4";
}
elseif(url.indexOf('item5') > -1) {
document.getElementById("logoswap").className += "class5";
}
else {
document.getElementById("logoswap").className += "class1";
}
});
That's what I have... Ugly I'm sure.
That's why I'm here though, I definitely need some help.
Assigning CSS Class By URL Pathname
A jsfiddle has been setup for
this solution.
Here is a case for using numeric expressions if they are available. This does not apply to the above question.
$(function() {
var rgx = /item(\d+)$/,
url = location.pathname,
id = (rgx.test(url)) ? url.match(rgx)[1] : '1';
$("#logoswap").addClass("class" + id);
});
UPDATE:
In light of the new details you may need an array of values, these should be derived from or exactly equal to the class names you intend to use.
$(function(){
// my favorite way to make string arrays.
var matches = "brand1 brand2 brand3".split(" "),
url = location.pathname.match(/\w+$/)[0], // get the last item
id = matches.indexOf(url),
className = matches[(id > -1) ? id : 0];
$("#logoswap").addClass(className);
});
To make this work you will need a few things in place. I will assume that the paths will end in a number as we have outlined here. The default ends with 1. You will need the images to be accessible. You need to define the styles for each possibility.
CSS Setup
#logoswap {
height : 200px;
width : 200px;
}
.class1 {
background-image : url(/path/to/default.jpg);
}
.class2 {
background-image : url(/path/to/second.jpg);
}
.brand1 {
background-image : url(/path/to/brand/1/logo.jpg);
}
...
Without jQuery
if you do not have jQuery in your code you may need to use window.onload.
(function(){
var old = window.onload;
window.onload = function(){
old();
var r = /item(\d+)$/,
url = location.pathname,
id = (r.test(url)) ? url.match(r)[1] : '1';
document.getElementById('logoswap').className += "class" + id;
};
})()
I just want to take a moment here to
encourage anyone who is doing this
type of code to get used to Regular
Expressions and learn them. They are
far and away the most frequently used
cross language part of my development
arsenal.
There's nothing that wrong with what you have. You could tidy it up with something like below.
$(function() {
var url = location.pathname;
var logo = document.getElementById("logoswap");
var i = 6;
logo.className = "class1";
while(i--)
{
if(url.indexOf("item" + i) > -1) {
logo.className = "class" + i;
}
}
});
Hope this helps.
Using just HTML/CSS, you could add (or append via javascript) an id to the body of the page:
<body id="item1">
Then in your CSS, create a selector:
#item1 #logoswap {
// class1 CSS
}