Centering div margin top and margin bottom - javascript

I'm trying to get margin-top and margin-bottom to center my <div>. This JavaScript, which I wrote, works. However, if the site is cached once, CTRL+F5 refresh causes the script to receive a wrong clientHeight. Refreshing second time, retrieves the correct clientHeight.
I've tried using window.load and this works. However, it is so slow that the <div> loads and after 2 seconds, it shifts to the middle.
<script type="text/javascript">
var height = $(window).height();
var clientHeight = document.getElementById('account-wall').clientHeight;
var calc_height = (height - clientHeight) / 2;
document.getElementById("account-wall").style.marginTop = calc_height + 'px';
document.getElementById("account-wall").style.marginBottom = calc_height + 'px';
</script>
<script type="text/javascript">
$(window).load(function() {
var height = $(window).height();
console.log(height);
var clientHeight = $('.account-wall').height();
console.log(clientHeight);
var calc_height = (height - clientHeight) / 2;
document.getElementById("account-wall").style.marginTop = calc_height + 'px';
document.getElementById("account-wall").style.marginBottom = calc_height + 'px';
});
</script>

Use a resize event since you need it to be centered even if the window.height changes. To make sure it is centered from the beggining use .resize() to trigger the event.
$(window).on('resize', function(event){
var height = $(window).height();
console.log(height);
var clientHeight = $('.account-wall').height();
console.log(clientHeight);
var calc_height = (height - clientHeight)/2;
document.getElementById("account-wall").style.marginTop = calc_height+'px';
document.getElementById("account-wall").style.marginBottom = calc_height+'px';
}).resize();

Related

Javascript: target specific div or element?

I want to rewrite the following code so that it doesn't get the height of the <body>, but rather the height of the element I put the object in to carry out the function:
var img = document.getElementById("logo");
window.onscroll = function() {
var bodyHeight = parseInt(getComputedStyle(document.body).height, 10);
var scrollLimit = bodyHeight - window.innerHeight;
var scrollTop = document.body.scrollTop;
var scrollPCT = (scrollTop / (scrollLimit / 100)) / 100;
logo.style.top = bodyHeight * scrollPCT - logo.offsetHeight + "px";
};
How can I target, say an ID, instead of document.body? I tried the following but it didn't work at all:
var img = document.getElementById("logo");
window.onscroll = function() {
var body = document.getElementById("container");
var bodyHeight = parseInt(getComputedStyle(document.getElementById("container")).height, 10);
var scrollLimit = bodyHeight - window.innerHeight;
var scrollTop = document.getElementById("container").scrollTop;
var scrollPCT = (scrollTop / (scrollLimit / 100)) / 100;
logo.style.top = bodyHeight * scrollPCT - logo.offsetHeight + "px";
};
The desired effect involves a reverse scroll in which an image will move down as the user scrolls down, instead of up, like it normally does.
I guess the computed height does not work? Use the clientHeight property:
var bodyHeight = document.getElementById("container").clientHeight;
(or one of the other height properties)

calculate and set the height for some div (initial settings). When the height of the browser window is changed --> change the height for div

I need calculate and set the height for some div (initial settings). When the height of the browser window is changed --> change the height for div.
How will be better to rewrite this code (I want do initial settings once and change it when window resize):
$(document).ready(function () {
var height = document.documentElement.clientHeight - 500;
if (height < 135) {
height = 135;
}
document.getElementById('left_space').style.height = height + 'px';
$(window).resize(function () {
var height = document.documentElement.clientHeight - 500;
if (height < 135)
{
height = 135;
}
document.getElementById('left_space').style.height = height + 'px';
});
});
If you are purely looking to tidy up the code, it could look something like this:
$(document).ready(function () {
var resizeIt = function() {
var height = Math.max(document.documentElement.clientHeight - 500, 135);
$('#left_space').css('height', height + 'px');
};
resizeIt();
$(window).resize(function () {
resizeIt();
});
});
Here I have pulled out the lines of code that set the height into their own function, so the code is not duplicated. Then I took advantage of some of the shorter syntax you can use in jQuery for finding and changing styles of elements.
is that what you are looking for?
api.jquery.com
jQuery(document).ready(function () {
$(window).resize(function() {
var height = document.documentElement.clientHeight - 500;
if (height < 135) {
height = 135;
}
document.getElementById('left_space').style.height = height + 'px';
jQuery(window).resize(function () {
var height = document.documentElement.clientHeight - 500;
if (height < 135)
{
height = 135;
}
document.getElementById('left_space').style.height = height + 'px';
});
});
});
I think jQuery(window).resize one would be good

document.ready vs document.onLoad

I am wondering which one is the right one to run the js code which calculates the height of vertical menu depending on the window height and sets it on time, not late, not early.
I am using document.ready but it is not really helping me with the issue, it is not setting sometimes, I have to reload the page, then it is working, but not on the first load.
How to solve this problem?
Here is my code:
$(document).ready(function(){
var winh = document.body.clientHeight;
var footer = document.getElementById('footer').offsetHeight;
document.getElementById('sidebar').style.height = winh - 5/2*footer + 'px';
document.getElementById('sidebar').style.marginBottom = footer + 'px';
$(window).resize(function(){
var winh = document.body.clientHeight;
var footer = document.getElementById('footer').offsetHeight;
document.getElementById('sidebar').style.height = winh - 5/2*footer + 'px';
document.getElementById('sidebar').style.marginBottom = footer + 'px';
});
});
ready
When you run code when the document is ready, it means the DOM is loaded - but not things like images. If images will affect the height and width and the image tag has no width and height set, ready isn't the choice for you - otherwise it probably is.
onload
This includes images - so everything will be loaded. This means it fires a bit later.
both
var calculateSize = function () {
var winh = document.body.clientHeight;
var footer = document.getElementById('footer').offsetHeight;
document.getElementById('sidebar').style.height = winh - 5/2*footer + 'px';
document.getElementById('sidebar').style.marginBottom = footer + 'px';
}
$(document).ready(function(){
calculateSize();
$(window).resize(calculateSize);
});
window.onload = calculateSize ;

How can I resize and crop/letterbox image to completely fill div with image whatever resize

This is what I need:
The image must completely fill 100% the area the div covers - left to
right and top to bottom.
the image must not be squashed or streched - just be cropped or
must overflow.
The image must be kept as small as possible, so whatever the resize - you
can still see either the very sides OR the very top and bottom.
The div itself will be adjusting in height and width as both are a percentage of the main window.
I have found a little bit of JavaScript here that is manipulating the image just how I want when the window is resized, but is displaying it in the whole window.
<html>
<head>
<title>test</title>
<script type="text/javascript">
function resizeImage()
{
var window_height = document.body.clientHeight
var window_width = document.body.clientWidth
var image_width = document.images[0].width
var image_height = document.images[0].height
var height_ratio = image_height / window_height
var width_ratio = image_width / window_width
if (height_ratio > width_ratio)
{
document.images[0].style.width = "100%"
document.images[0].style.height = "auto"
}
else
{
document.images[0].style.width = "auto"
document.images[0].style.height = "100%"
}
}
</script>
</head>
<body onresize="resizeImage()">
<img onload="resizeImage()" src="f/a.jpg">
</body>
</html>
Here is a demo
Please don't just answer that all I need is:
<img style="width : 100%;">
This is so much more than that.
It's not too easy to explain but check the demo and drag the corner of the window around and that'll be worth 1000 words...!
Can it (or something like it) be made to work the same way within a % sized div?
I wrote a jQuery plugin that does exactly this. Check out my blog post here and the demo here
jQuery.fn.resizeToParent = function(options) {
var defaults = {
parent: 'div'
}
var options = jQuery.extend(defaults, options);
return this.each(function() {
var o = options;
var obj = jQuery(this);
// bind to load of image
obj.load(function() {
// dimensions of the parent
var parentWidth = obj.parents(o.parent).width();
var parentHeight = obj.parents(o.parent).height();
// dimensions of the image
var imageWidth = obj.width();
var imageHeight = obj.height();
// step 1 - calculate the percentage difference between image width and container width
var diff = imageWidth / parentWidth;
// step 2 - if height divided by difference is smaller than container height, resize by height. otherwise resize by width
if ((imageHeight / diff) < parentHeight) {
obj.css({'width': 'auto', 'height': parentHeight});
// set image variables to new dimensions
imageWidth = imageWidth / (imageHeight / parentHeight);
imageHeight = parentHeight;
}
else {
obj.css({'height': 'auto', 'width': parentWidth});
// set image variables to new dimensions
imageWidth = parentWidth;
imageHeight = imageHeight / diff;
}
// step 3 - center image in container
var leftOffset = (imageWidth - parentWidth) / -2;
var topOffset = (imageHeight - parentHeight) / -2;
obj.css({'left': leftOffset, 'top': topOffset});
});
// force ie to run the load function if the image is cached
if (this.complete) {
obj.trigger('load');
}
});
}
And if you want the image to resize when the window is resized, just bind a resize handler to the window:
$(window).resize(function() {
$('img').resizeToParent();
});
Ok I've been playing around with it:
<html>
<head>
<title>test</title>
<style>
#imgarea {
position:absolute;
right:0px;
height:75%;
width:70%;
top:25%;
}
</style>
<script type="text/javascript">
function resizeImage()
{
var window_height = document.body.clientHeight
var window_width = document.body.clientWidth
var image_width = document.images[0].width
var image_height = document.images[0].height
var area_width = window_width * 0.7
var area_height = window_height * 0.75
var height_ratio = image_height / area_height
var width_ratio = image_width / area_width
if (height_ratio > width_ratio)
{
document.images[0].style.width = "100%"
document.images[0].style.height = "auto"
}
else
{
document.images[0].style.width = "auto"
document.images[0].style.height = "100%"
}
}
</script>
</head>
<body onresize="resizeImage()">
<div id="imgarea">
<img onload="resizeImage()" src="f/a.jpg">
</div>
</body>
</html>
It keeps resizing as the div resizes - as mentioned the div is
resizing with the window - this one keeps working seemlesly.
It seems to be OK across IE9, Fire Fox, Oprea, Chrome, and safari
over xp and 7
so really it answers my question perfectly, its just - now i've seen Christian's centering version i wish i had the know-how to make this do it i've tried a few things but am now stuck. Any Ideas?
P.S. if you dont know the width and height % of the div when you right the script i think it could be got with GetElementById - somehow... beyond me though;)

Mouse on left of screen move image to left, same when mouse on right of screen

I'm trying to get an image that is around 1920x1200px to pan around on a 800x600px browser window.
So if my mouse is on the top-left of the browser window the image is alined so it's top-left margins are on the top-left of the browser window. The same goes for the bottum-right.
So if the mouse is in the centre of the screen the image should be centered too.
Im not sure what calculations are needed as my math is a bit rusty.
Currently I'm using a bit of javascript that just moves the image using CSS's top/left properties but without much success as it's just moving the picture around from it's top/left corner.
I'v also set the image's position to absolute in css.
function updateImgPosition( e )
{
var avatar = document.getElementById("avatar");
// Width
var windowWidth = window.innerWidth;
var mouseWidthLocation = e.x;
var percentOfWidth = (100 / windowWidth) * mouseWidthLocation;
// Height
var windowHeight = window.innerHeight;
var mouseHeightLocation = e.y;
var percentOfHeight = (100 / windowHeight) * mouseHeightLocation;
avatar.style.top = percentOfHeight + "%";
avatar.style.left = percentOfWidth + "%";
}
document.onmousemove = updateImgPosition;
This is a demo of what I have: http://jsfiddle.net/uQAmQ/1/
Fiddle: http://jsfiddle.net/uQAmQ/2/
You should not "pan" on an absolutely positioned element, because the window's width and height keep changing according to the image. A smoother solution involves using a background image. See the middle of my answer for the used logic.
Consider this JavaScript (read comments; HTML + CSS at fiddle):
(function(){ //Anonymous function wrapper for private variables
/* Static variables: Get the true width and height of the image*/
var avatar = document.getElementById("avatar");
var avatarWidth = avatar.width;
var avatarHeight = avatar.height;
var windowWidth = window.innerWidth;
var windowHeight = window.innerHeight;
/* Logic: Move */
var ratioY = (avatarHeight - windowHeight) / windowHeight;
var ratioX = (avatarWidth - windowWidth) / windowWidth;
function updateImgPosition( e ) {
var mouseY = e.pageX; //e.pageX, NOT e.x
var mouseX = e.pageY;
var imgTop = ratioY*(-mouseY);
var imgLeft = ratioX*(-mouseX);
document.body.style.backgroundPosition = imgLeft + "px " + imgTop + "px";
}
/* Add event to WINDOW, NOT "document"! */
window.onmousemove = updateImgPosition;
})();
The logic behind it:
Relative units cannot be used, because the image size is specified in absolute units.
The offsets should change according to a specific ratio, which is similar to: image size divided by window size.However, this ratio is not complete: The image would disappear at the bottom/left corner of the window. To fix this, substract the window's size from the image's size. The result can be found in the code at variable ratioX and ratioY.
The previous code had to be loaded at the window.onload event, because the image's size was dynamically calculated. For this reason, a HTML element was also included in the body.
The same code can be written much smaller and efficient, by specifying the size of the background in the code. See this improved code. Fiddle: http://jsfiddle.net/uQAmQ/3/
(function(){ //Anonymous function wrapper for private variables
/* Static variables: Get the true width and height of the image*/
var avatarWidth = 1690;
var avatarHeight = 1069;
var windowWidth = window.innerWidth;
var windowHeight = window.innerHeight;
/* Logic: Move */
var ratioY = (avatarHeight - windowHeight) / windowHeight;
var ratioX = (avatarWidth - windowWidth) / windowWidth;
function updateImgPosition( e ) {
var mouseX = e.pageX; //e.pageX, NOT e.x
var mouseY = e.pageY;
var imgTop = ratioY*(-mouseY);
var imgLeft = ratioX*(-mouseX);
document.body.style.backgroundPosition = imgLeft + "px " + imgTop + "px";
}
/* Add event to WINDOW, NOT "document"! */
window.onmousemove = updateImgPosition;
})();
If you don't mind a decreased code readability, the following code is the best solution, Fiddle: http://jsfiddle.net/uQAmQ/4/:
(function(){ //Anonymous function wrapper for private variables
/* Static variables: Get the true width and height of the image*/
var windowWidth = window.innerWidth;
var windowHeight = window.innerHeight;
var ratioY = (windowHeight - 1069) / windowHeight;
var ratioX = (windowWidth - 1690) / windowWidth;
window.onmousemove = function( e ) {
document.body.style.backgroundPosition = ratioX * e.pageX + "px " + ratioY * e.pageY + "px";
}
})();

Categories

Resources