Hold scroll bar always at the bottom - javascript

I have a div element and a simple style sheet for it :
CSS:
.container{
width:200px;
max-height:200px;
border:1px solid red;
overflow-y:scroll;
}
HTML:
<div class="container">
</div>
And i have a button for add contents to the div, as you know my div's height grows then has an scroll bar.
When i add new contents to the container, i want to show the last added item.
I try to use scrollTop() jQuery function with infinite value but it didn't work.
Any Idea?
The Fiddle
Edit : Because of using max-height, the maximum value of height property is 200.
So i can't use this approach :
$(".container").scrollTop($(".container").heigth());
Now, i can do it like this:
$(".container").scrollTop(10000);
And it's working, but i think it isn't good idea!
Update
Thanks to Nicole Van for the simple and great approach!
I change my fiddle with her solution : The Updated Fiddle

function ScrollToBottom(){
var d = document.getElementById("MyDiv");
d.scrollTop = d.scrollHeight;
}
Take a look at some other jQuery solutions here:
Scroll to bottom of div?

How are you adding? appending or preppending?
I mean you could get the new height of your container and scrollTo your new height if appending or scrollTo 0 if preppending
---EDIT this makes the trick:
$(".add").click(function(){
i++;
var s ="<p>added value "+i+" ! </p>";
$(".container").append(s);
var heightContainer = $(".container").height();
$(".container").scrollTop(heightContainer);
});
-----EDIT-------
This makes it, it overpass allways its innerheight so it works, even its not accurate:
var i=0;
$(".add").click(function(){
i++;
var s ="<p>added value "+i+" ! </p>", heightContainer;
$(".container").append(s);
heightContainer = $(".container").height() * i;
$(".container").scrollTop(heightContainer);
});
The ideal solution is that you know the height of the elemnts you are inserting so the heightContainer will be elemHeight * i

Related

How I can get an Image height and divide it by 2 using Jquery

Hi I need to set height of an image to half using j query, So that on click it expands to auto height, How is this possinble please guide.
Currently I used a class with property height: 202px and on click I change that class with another one containing height: auto property, But this does not work fine on responsive views.
So I need to divide the height:auto property by 2, How can i do this with j query, Please guide me with example
Here is my css
.how-we-do .expand-image {
height: auto
}
.how-we-do .expand-image2 {
height:202px ;
}
Here is my jquery code
$('.expand-image').each(function () {
$(this).removeClass('expand-image');
$(this).addClass('expand-image2');
});
You can use .height() to half the height of an on-screen image. .height() takes a function, the second parameter of which will be the current height of the element.
Return this value halved and you have what you need:
$('img').height(function(_,v){ return v/2; });
JSFiddle
Quickfix:
$('img').height() / 2
You can try this.
var cheight = $('.parendiv').innerHeight();
$('img').css({
'height' : cheight + 20
});

How to measure and set the width?

I would like to make sub-navigation to measure its parents width and then set its own width accordingly. At the moment every sub-navigation (.primary-navigation ul ul) gets an individual class (customWidth-0 + i). Then using this class I measure its parent's width and set the width minus the padding. It's all working nice and fine, but I'm learning and I'd like to shorten the script. I was trying to loop this, use "this", but seem to get stuck at every point. It would be nice to learn to do this in a proper, robust way. Any help is very much appreciated. Thanks.
jQuery(document).ready(function( ) {
jQuery(".primary-navigation ul ul").each(function(i) {
i = i+1;
jQuery(this).addClass("customWidth-0" + i);
});
a = jQuery(".customWidth-01").prev().parent().width();
b = jQuery(".customWidth-02").prev().parent().width();
c = jQuery(".customWidth-03").prev().parent().width();
d = jQuery(".customWidth-04").prev().parent().width();
jQuery(".customWidth-01").css("width", a-31);
jQuery(".customWidth-02").css("width", b-31);
jQuery(".customWidth-03").css("width", c-31);
jQuery(".customWidth-04").css("width", d-31);
});
I took your look and added my code after commenting your sections out and got the same thing.
<script type="text/javascript">
jQuery(document).ready(function( ) {
jQuery(".primary-navigation ul ul").each(function(i) {
i = i+1;
var _this = jQuery(this), w = _this.parents('ul').width();
_this.css("width", (w-31)+"px");
//jQuery(this).addClass("customWidth-0" + i);
console.log(i);
});
/*
a = jQuery(".customWidth-01").prev().parent().width();
b = jQuery(".customWidth-02").prev().parent().width();
c = jQuery(".customWidth-03").prev().parent().width();
d = jQuery(".customWidth-04").prev().parent().width();
jQuery(".customWidth-01").css("width", a-31);
jQuery(".customWidth-02").css("width", b-31);
jQuery(".customWidth-03").css("width", c-31);
jQuery(".customWidth-04").css("width", d-31);
*/
});
</script>
It will find the div above given ul and take its width take off 31px and then apply it to given elements below. The LI elements inside of the UL will already have a 100% width and conform to that standard. If you wanted to you could just apply a position: relative; on the LIs of the .primary-navigation and then position: absolute; left: 0; top: ~20px; (top is a little skewed according to your em size.. This will do the same thing except it won't wrap your children and make it look weird.
If you gave me an exact image of what you wanted your menu to look like (not using javascript or anything maybe a designed version??) I could probably do a better job as this is still kinda hard to answer. Hopefully the code I provided helps you if not leave another comment and let me know if you have questions.
Below line is old answer.
Set a variable
var _this = jQuery(this), w = _this.parent().parent().width();
_this.css("width", (w-31)+"px");// just to be safe added px use w/e or leave blank it assumes it
This should work for you the same as you have it in the foreach.
you could also use .parents('ul')
w = _this.parents('ul').width();
function() {
$('.primary-navigation').children('li').each(
function(index) {
var parentWidth = $(this).width();
$(this).children('ul').width(parentWidth/2);
}
);
Is this what you are looking for? now all the sub menu is 1/2 of parent. you need to fix it to your specific need.
DEMO http://jsfiddle.net/La07pvf2/

How to get the real scroll height of div (say, inner text size)

I'm trying to make a auto-scrolling div that go to its top when it reaches the end. But it doesn't work...
function scrollPannel()
{
var pannel = document.getElementById('pannel');
if (typeof scrollPannel.count == 'undefined')
{
scrollPannel.count = 0;
}
else
{
scrollPannel.count += 2;
}
// trouble is here
if ((scrollPannel.count - pannel.scrollHeight) > pannel.clientHeight)
{
scrollPannel.count = 0;
}
pannel.scrollTop = scrollPannel.count;
setTimeout('scrollPannel()', 500);
}
HTML:
<div id='pannel' style="height:200px;overflow:auto" onmouseover="sleepScroll()">
<p>...</p><!-- long text -->
</div>
And after, I will need to find how to stop scrolling when "onmouseover" occures.
EDIT: I did not explained the problem clearly. In fact, I have tried something like:
if (scrollPannel.count > pannel.scrollHeight)
{
scrollPannel.count = 0;
}
The problem is that scrollHeight seems greater than div inner text. So it makes a lot of time to return to the top.
So I need an element property of which I could use the value to compare with my count variable. However I don't know Javascript a lot and I could not find anything. I hope it is as well simple as I think of it.
Try:
// calculate max scroll top position (go back to top once reached)
var maxScrollPosition = element.scrollHeight - element.clientHeight;
// example
element.scrollTop = maxScrollPosition;
That should do what you need.
You could try using the scrollHeight property.
https://developer.mozilla.org/en-US/docs/Web/API/element.scrollHeight
The solution I have involves jQuery, hope that's not a problem.
JavaScript:
var timeout;
function scrollPannel()
{
var divHeight = $("#pannel").height() / 2;
var scrollCount = $("#pannel").scrollTop();
var scrollHeight = $("#inside").height() - 20 - divHeight;
scrollCount += 2;
if ((scrollCount - scrollHeight) > 0)
{
scrollCount = 0;
}
$("#pannel").scrollTop(scrollCount);
timeout = window.setTimeout(scrollPannel(), 100);
}
function scrollStop() {
window.clearTimeout(timeout);
}
HTML:
<div id='pannel' onmouseover="scrollStop();" onmouseout="scrollPannel();">
<p id="inside"></p><!-- long text -->
</div>
Explanation:
jQuery's .height() of the inside element <p> gives us the actual height you're looking for, but it's not enough for reaching the bottom, since that happens before we reach the element's height. A little investigation shows that the "top" of scrollTop() is about half way inside the original div's height. You may need to play around with divHeight to get the exact results you're looking for.
Of course, I also included a method for stopping and continuing scrolling.
Good luck!
You should use scrollHeight property but to call it, you need to use an index like that:
$('#pannel')[0].scrollHeight;
If you set the scrollTop and scrollLeft to really high silly values they only ever get set as their maximum allowed values which I think is what you need? You can then use them to work out the scroll center if you wished.
See snippet example.
var mB = document.getElementById('myBox');
var mR = document.getElementById('myResult');
// Set the top and the left to silly values
mB.scrollTop = 99999999;
mB.scrollLeft = 99999999;
// They will only end up being set as their max
mR.innerHTML = "maxTop="+mB.scrollTop+"<br>maxLeft="+mB.scrollLeft;
// Now take the max values and divide by 2 to scroll back to middle.
mB.scrollTop = mB.scrollTop/2;
mB.scrollLeft = mB.scrollLeft/2;
#myBox{
overflow:auto;
}
#myContent{
border:1px solid black;
background-color:red;
}
<div id='myBox' style='width:300px;height:300px'>
<div id='myContent' style='width:500px;height:800px;line-height:800px;'><center>I am the center of the content</center></div>
</div>
<div id='myResult'></div>
I have got one solution....
function findMaxReach(){
let maxReach =0
document.querySelector('.YourElement').scrollLeft = 100000;
maxReach = document.querySelector('.YourElement').scrollLeft;
document.querySelector('.YourElement').scrollLeft = 0;
return maxReach
}

How do you make a floating sidebar like envato?

I really like the floating panel on the left side of the following site:
http://envato.com/
I have no idea what its called, but I like how when you click on the search button, it expands to a search page, you click on another icon, and it expands with what appears like its own page.
How do I accomplish this? Is there some tutorial out there using html5, JavaScript or jQuery?
NOTE: All the answers so far only cover the floating bar, but not the clicking on a link on that floating bar to show a window expanded to the right.
<div id="float"></div>
#float{
position:fixed;
top:50px;
left:0;
}
Check working example at http://jsfiddle.net/TVwAv/
done using css,
HTML
<div id="floating_sidebar">
whatever you want to put here
</div>
CSS
#floating_sidebar {
position:fixed;
left: 0;
top: 100px; /* change to adjust height from the top of the page */
}
I am using this for a "floating (sticky) menu". What I have added is:
1. to avoid my 'footer' always being "scrolled" down in case the sidemenu is a little high, I only do the scrolling if necessary, i.e -
when the content is higher than the sidebar.
2. I found the animate effect a little "jumpy" to my taste, so I just changed the css through jquery. of-course you put a 0 in the animate time, but the animation still occurs, so it's cleaner and faster to use the css.
3. 100 is the height of my header. you can assume it to be the "threshold" of when to do the scrolling.
$(window).scroll(function(){
if ($('#sidebar').height() < $('#content').height())
{
if ($(this).scrollTop() > 90)
$('#sidebar').css({"margin-top": ($(this).scrollTop()) - 100 });
//$('#sidebar').animate({"marginTop": ($(this).scrollTop()) - 100 }, 0);
else
$('#sidebar').css({"margin-top": ($(this).scrollTop()) });
//$('#sidebar').animate({"marginTop": ($(this).scrollTop()) }, 0);
}
});`
you can use this ..
your html div is here
<div id="scrolling_div">Your text here</div>
And you javascript function is here
$(window).scroll(function(){
$('#scrolling_div').stop().animate({"marginTop": ($(this).scrollTop()) +10+ "px"}, "slow"});
});
You can also use the css for this
#scrolling_div {
position:absolute;
left: 0;
top: 100px;
}
I have not tested it but hopefully its worked.
I know this looks quite a big piece of code, however this function just works by specifying three simple options; your floater "top", your "target" (floater) and "reference" element to set the boundaries, it also takes care of the top and bottom position automatically, no css involved.
function scrollFloater(marginTop, reference, target, fixWhidth = false){
var processScroll = function(){
var from = reference.offset().top - marginTop;
var to = reference.offset().top + reference.outerHeight() + marginTop - target.outerHeight();
var scrollTop = $(this).scrollTop();
var bottom = to - reference.offset().top + marginTop;
if( fixWhidth )
target.css('width', target.width());
if( scrollTop > from && scrollTop < to )
target.css('position', 'fixed').css('top',marginTop);
else if( scrollTop >= to )
target.css('position', 'absolute').css('top', bottom);
else
target.css('position', '').css('top',marginTop);
}
$(window).scroll(function(){ processScroll(); });
processScroll();
}
And this is how you would use it:
$(function() {
scrollFloater(41, $('.box.auth.register'), $('.plans-floater'), true);
});
I hope this helps someone.

How can I Animate an Element to its natural height using jQuery [duplicate]

This question already has answers here:
Animate element to auto height with jQuery
(21 answers)
Closed 7 years ago.
I'm trying to get an element to animate to its "natural" height - i.e. the height it would be if it had height: auto;.
I've come up with this:
var currentHeight = $this.height();
$this.css('height', 'auto');
var height = $this.height();
$this.css('height', currentHeight + 'px');
$this.animate({'height': height});
Is there a better way to do this? It feels like a bit of a hack.
Edit:
Here's a complete script to play with for anyone that wants to test.
<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
<html lang="en">
<head>
<title>jQuery</title>
<style type="text/css">
p { overflow: hidden; background-color: red; border: 1px solid black; }
.closed { height: 1px; }
</style>
<script type="text/javascript" src="http://ajax.googleapis.com/ajax/libs/jquery/1.3.2/jquery.js"></script>
<script type="text/javascript">
$().ready(function()
{
$('div').click(function()
{
$('p').each(function()
{
var $this = $(this);
if ($this.hasClass('closed'))
{
var currentHeight = $this.height();
$this.css('height', 'auto');
var height = $this.height();
$this.css('height', currentHeight + 'px');
$this.animate({'height': height});
}
else
{
$this.animate({'height': 1});
}
$this.toggleClass('closed');
});
});
});
</script>
</head>
<body>
<div>Click Me</div>
<p>Hello - I started open</p>
<p class="closed">Hello - I started closed</p>
</body>
</html>
I permit myself to answer this thread, even if it's been answered a long time ago, cuz it just helped me.
In fact, i don't understand the first answer : why opening a half-closed element to get its height, and then closing it again ?
At the beginning, you hide the element so that just a part of it appears, right ? The best way (i believe) to do this is onready, with javascript. So, when you hide the element onready, just save the orig height in a var, so you don't have to hide(onready)-show-save height-hide to be able to toggle the elements visibility.
Look at what i did, it works perfectly :
$(document).ready(function(){
var origHeight = $("#foo").css('height');
$("#foo").css({"height" : "80px"});
$("#foo .toggle").bind("click", function(event){ toggleFoo(event, lastSearchesMidHeight); });
});
Here, when you call your toggle function, you know what is your original element height without wanking around.
I wrote it fast, hoping it could help someone in the future.
the easiest solution I found was to simply wrap the content element with a div that is limited in height and set to overflow:hidden. This truncates the inner content element to the height of the wrapping div. when the user clicks, hovers, etc. to show the full height of the content element - simply animate the wrapping div to the height of the inner content div.
I could suggest an equally-hackish solution...Clone the element, position it out of view, and get its height...then delete it and animate your original.
That aside, you could also use $.slideUp() and $.slideDown():
$this.hasClass('closed') ? $(this).slideDown() : $(this).slideUp() ;
If you need to keep a 1px line, you can apply that with a parent element:
<div style='border-top:1px solid #333333'>
<div class='toggleMe'>Hello World</div>
</div>
And apply the slidingUp/Down on the .toggleMe div.
I'd also like to chime in on this old thread, if I may, in case my solution helps anyone. My specific situation is this: I have some div's that are set with a max-height value that limits them to three lines tall, and when the user mouseovers them I want them to expand to their natural height; and when the mouse cursor leaves the div, I want them to shrink back down to the clipped, max-three-lines-tall height. I need to use the CSS max-height property, rather than height, because I have some div's that contain only one or two lines of text and I don't want them unnecessarily tall.
I tried many of the solutions in this thread, and the one that worked for me was the 'hackish suggestion' involving cloned elements suggested by Jonathan Sampson. I translated his idea into the following code. Please feel free to suggest improvements.
The functions are delegated to a parent element to handle div's created via an Ajax call. The div.overflow_expandable class has the following declaration: { max-height: 5em; overflow: hidden; }
$('#results').delegate('div.overflow_expandable', 'mouseenter', function() {
var $this = $(this);
// Close any other open divs
$('#results div.overflow_expandable').not($(this)).trigger('mouseleave');
// We need to convert the div's current natural height (which is less than
// or equal to its CSS max-height) to be a defined CSS 'height' property,
// which can then animate; and we unset max-height so that it doesn't
// prevent the div from growing taller.
if (!$this.data('originalHeight')) {
$this.data('originalHeight', $this.height());
$this.data('originalMaxHeight', parseInt($this.css('max-height')));
$this.css({ 'max-height':'none',
height: $this.data('originalHeight') });
}
// Now slide out if the div is at its original height
// (i.e. in 'closed' state) and if its original height was equal to
// its original 'max-height' (so when closed, it had overflow clipped)
if ($this.height() == $this.data('originalHeight') &&
$this.data('originalMaxHeight') == $this.data('originalHeight')) {
// To figure out the new height, clone the original element and set
// its height to auto, then measure the cloned element's new height;
// then animate our div to that height
var $clone = $this.clone().css({ height: 'auto', position: 'absolute',
zIndex: '-9999', left: '-9999px', width: $this.width() })
.appendTo($this);
$this.animate({ height: $clone.height() }, 'slow');
$clone.detach();
}
}).delegate('div.overflow_expandable', 'mouseleave', function() {
var $this = $(this);
// If the div has 'originalHeight' defined (it's been opened before) and
// if it's current height is greater than 'originalHeight' (it's open
// now), slide it back to its original height
if ($this.data('originalHeight') &&
$this.height() > $this.data('originalHeight'))
$this.animate({ height: $this.data('originalHeight') }, 'slow');
});
Found this post and end up using Greg's original 1px suggestion - works great!
Just added a callback to the animate function, to set the height of the element to 'auto' when the animation ends (in my case, the content of that specific element could change and be bigger).
$('div').click(function() {
if($('p').is(':hidden')) {
$('p').slideUp();
} else {
$('p').slideDown(function() { $('p').css('height','1px'); });
}
}
That should set the height of the p tags to be 1px once they've finished sliding.
This worked for me.
<div class="product-category">
<div class="category-name">
Cars
</div>
<div class="category-products" style="display: none; overflow: hidden;">
<div class="product">Red Car</div>
<div class="product">Green Car</div>
<div class="product">Yellow Car</div>
</div>
</div>
<script type="text/javascript">
$(document).ready(function() {
$('.product-category .category-name').click(function() {
if ($(this).parent().hasClass('active')) {
$(this).parent().removeClass('active');
var height = $(this).parent().find('.category-products').height();
$(this).parent().find('.category-products').animate({ height : '0px' }, 600, function() {
$(this).parent().find('.category-products').height(height).hide();
});
} else {
$(this).parent().addClass('active');
var height = $(this).parent().find('.category-products').height();
$(this).parent().find('.category-products').height(0).show().animate({ height : height + 'px' }, 600);
}
});
});
</script>
My solution is to store in the data attribute of the close button the original size of container (could have been stored also in the container itself, if you don't use the same button to also show again the container):
$(document).ready(function(){
$('.infoBox .closeBtn').toggle(hideBox, showBox);
});
function hideBox()
{
var parent = $(this).parent();
$(this).text('Show').data('originalHeight', parent.css('height'));
parent.animate({'height': 20});
return false;
}
function showBox()
{
var parent = $(this).parent();
$(this).text('Hide');
parent.animate({
'height': $(this).data('originalHeight')
});
return false;
}
I wanted to point to this answer, which suggest setting the height to "show" with the animate() function. I had to edit my "slideUp" style animate to use height:"hide" to work with it.

Categories

Resources