How can I revert the width of a div after animation? - javascript

Here's what I'm trying to do:
A position:sticky div has a rectangle in it (id=mysquare). After scrolling a bit, the width of mysquare should shrink using jquery's animate. Then, when scrolling back up, mysquare should instantly grow back to its original width.
The problem:
The animation bit works fine. What doesn't work is reverting back to mysquare's original width. When you scroll back up after mysquare shrinks to 100px, it stays the same (when it should theoretically go back to 150px).
var headheight = $(".myheading").height();
$(function() {
$(window).scroll(function() {
if ($(this).scrollTop() > headheight) {
//if scrolled past myheading
//Gradually change the width of the square to 100px, from 150px
$("#mysquare").animate({
width: "100px",
}, 1500);
}
if ($(this).scrollTop() < headheight) {
//If not scrolled past myheading
//Keep the square big
$("#mysquare").width("150px");
}
})
});
div.sticky {
position: -webkit-sticky;
position: sticky;
top: 0;
background-color: yellow;
padding: 10px;
font-size: 20px;
}
#mysquare {
height: 50px;
background-color: #555;
}
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.2.1/jquery.min.js"></script>
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
</head>
<body>
<div class="myheading" style="height: 50px;"></div>
<div class="sticky">Hello
<div id="mysquare" style="width 150px;">
</div>
</div>
<main style="height:500px;"></main>
</body>
</html>
A JSFiddle: https://jsfiddle.net/82n16x07/7/
On a side note, mysquare seems to take up the entire width of the screen when first loaded in. Any help with that would also be appreciated.

after animation you need to remove the element and replace it to have other css applied
var headheight = $(".myheading").height();
$(function() {
$(window).scroll(function() {
if ($(this).scrollTop() > headheight) {
//if scrolled past myheading
//Gradually change the width of the square to 100px, from 150px
$("#mysquare").animate({
width: "100px",
}, 1500);
}
if ($(this).scrollTop() < headheight) {
var elm = document.getElementById('mysquare');
var newone = elm.cloneNode(true);
elm.parentNode.replaceChild(newone, elm);
//If not scrolled past myheading
//Keep the square big
$("#mysquare").width("500px");
}
})
});
div.sticky {
position: -webkit-sticky;
position: sticky;
top: 0;
background-color: yellow;
padding: 10px;
font-size: 20px;
}
#mysquare {
height: 50px;
background-color: #555;
}
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.2.1/jquery.min.js"></script>
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
</head>
<body>
<div class="myheading" style="height: 50px;"></div>
<div class="sticky">Hello
<div id="mysquare" style="width 150px;">
</div>
</div>
<main style="height:500px;"></main>
</body>
</html>

Your initial width problem is caused by an incorrect style directive, with a missing colon:
<div id="mysquare" style="width 150px;">
should be:
<div id="mysquare" style="width: 150px;">
The main problem is caused by the fact that the animate() function is repeatedly called when the scroll condition is true, and these function calls stack up. If you wait long enough, they clear, and the box is returned to it's normal size.
To fix this, you can add a shrunk flag to determine if the box is shrunk or not, and check this flag to determine whether or not to issue a new animate() call.
var headheight = $(".myheading").height();
var shrunk=false;
$(function() {
$(window).scroll(function() {
if ($(this).scrollTop() > headheight && !shrunk) {
//if scrolled past myheading
//Gradually change the width of the square back to the size of the new image
shrunk=true;
$("#mysquare").animate({
width: "100px",
}, 1500);
}
if ($(this).scrollTop() < headheight) {
//If not scrolled past myheading
//Keep the square big
shrunk=false;
$("#mysquare").width("150px");
}
})
});
div.sticky {
position: -webkit-sticky;
position: sticky;
top: 0;
background-color: yellow;
padding: 10px;
font-size: 20px;
}
#mysquare {
height: 50px;
width:150px;
background-color: #555;
}
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.2.1/jquery.min.js"></script>
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
</head>
<body>
<div class="myheading" style="height: 50px;"></div>
<div class="sticky">Hello
<div id="mysquare" style="width: 150px;">
</div>
</div>
<main style="height:500px;"></main>
</body>
</html>

Just try with this. hope this works for you.
var lastScrollTop = 0;
$(window).scroll(function(event){
var thisScrolltop = $(this).scrollTop();
if (thisScrolltop > lastScrollTop){
// write code here, when down scroll
} else {
// write code here, when up scroll
}
lastScrollTop = thisScrolltop;
});

Related

Setting an element position according to another element (seems JS/CSS bug)

I have a div that will be set according to the hovered element position in window. At first I thought this was a JQuery bug, but after more investigating and changing to vanilla, it's still the same.
I have created a code snippet to demonstrate my problem. If you mouse enter white div from top, the position is correct and orange box cover entire white box, but if you enter it from other sides, it's incorrect by few pixel:
var inspector_rect2= document.getElementById('inspector_rect');
$(window).mouseover(function(event) {
inspector_rect2.style.left= event.target.getBoundingClientRect().x+'px';
inspector_rect2.style.top= event.target.getBoundingClientRect().y+'px';
inspector_rect2.style.width= event.target.getBoundingClientRect().width+'px';
inspector_rect2.style.height= event.target.getBoundingClientRect().height+'px';
});
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
<!DOCTYPE html>
<html lang="en">
<head>
<title></title>
<meta charset="UTF-8">
</head>
<style>
html, body {
height : 100%;
margin : 0;
width : 100%;
}
.MyCSS {
background-color : silver;
}
.Container {
height : 100%;
margin : auto;
width : 50%;
}
.Header {
height : 5%;
padding : 2% 0;
width : 100%;
}
.MainContent {
background-color : white;
height : 70%;
width: 100%;
}
.inspector{
position: absolute;
pointer-events: none;
z-index: 999;
background: rgba(255, 166, 0, 0.5);
}
</style>
<body class="MyCSS">
<div class="Container" >
<div class="Header" ></div>
<div class="MainContent" ></div>
</div>
</body>
<div id=inspector_rect class=inspector></div>
It seems to be caused by an interaction between requesting .getBoundingClientRect() and setting width and height.
Generally, you should just make one request, store it, then re-use as needed.
$(window).mouseover(function(event) {
const rect = event.target.getBoundingClientRect();
inspector_rect2.style.left= rect.x+'px';
inspector_rect2.style.top= rect.y+'px';
inspector_rect2.style.width= rect.width+'px';
inspector_rect2.style.height= rect.height+'px';
});

Scroll div depending on parent position

I have a parent div with two child divs. The first child should be fixed when the parent is in viewport. The second child should scroll into position and overlap the first. Both child divs should be removed and follow the parent as soon as they reach the bottom of the parent.
Right now, I'm adding a class on scroll position but I'm not sure how to detect when the child is at bottom of parent and then remove the class.
var sticky = $('.sticky'),
scroll = $(window).scrollTop();
if (scroll >= 70) {
sticky.addClass('fixed');
} else {
sticky.removeClass('fixed');
}
How can I make the child divs follow the parent in the best way? I've tried to search for something similar what I want but couldn't find any good explanation.
This fiddle is what I've got so far.
If I am understanding this correctly, what you could do is measure bottom of parent div and child sticky div relative to the document.body, and if child element's bottom crossing parent's bottom you can remove .fixed class.
Something like this.
$(window).scroll(function(){
var sticky = $('.sticky'),
scroll = $(window).scrollTop();
if (scroll >= 70) {
sticky.addClass('fixed')
}else {
sticky.removeClass('fixed');
}
if(getBottom('.sticky') >= getBottom('.holder')){
sticky.removeClass('fixed');
}
});
function getBottom(element){
var $elm = $(element);
var offset = $elm.offset();
var top = offset.top;
return top + $elm.outerHeight();
}
body { margin: 0; }
section {
height: 2000px;
padding-top: 100px;
}
div {
width: 300px;
height: 100px;
}
.holder {
border: 1px solid black;
width: 500px;
height: 200px;
position: relative;
}
.sticky {
top:30px;
left:10px;
background: orange;
z-index: 9999;
position: relative;
}
.other-div {
background: gold;
top: 20px;
z-index: 0;
}
.fixed {
position: fixed;
}
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<meta name="viewport" content="width=device-width">
<title>Divs</title>
</head>
<body>
<section>
<div class="holder">
<div class="other-div fixed">This div should stay fixed for a while</div>
<div class="sticky">This div will become fixed on scroll</div>
</div>
</section>
<script src="https://code.jquery.com/jquery-3.1.0.js"></script>
</body>
</html>
Jsfiddle of the above snippet https://jsfiddle.net/azs06/3ubshm4t/7/
Note, I made some css changes, which you can adjust as you need.

How to use the scroll event in Javascript (NO Jquery)

So HERE is the code. I simple want to change the color of the h1 heading when the scroll is 1000px from top. I would like to use purely javascript for this purpose.Please try and ignore how poorly the code has been written. Any suggestion would be more than welcome. Thank you for you time.
<html> <head> <title> scroll </title>
<!-- CSS !-->
<style> .redbox {
background-color: red;
position: absolute;
top: 10px;
height: 90px;
width: 100px;
} .reveal {
position: fixed;
top:450px;
transition: width 2s;
display: block;
} </style>
</head>
<!-- HTML !-->
<body>
<div class='redbox' id='red'> , </div>
<h1 class='reveal' id='demo'> The comes up on 1000 scroll! </h1>
<h1 style='position: absolute;top: 1900px;'> END </h1>
<!-- JS !-->
<script>
var top = window.pageYOffset || document.documentElement.scrollTop
if (top == 1000) {
document.getElementById('demo').style.color = 'red'}
</script> </body> </html>
You could check the current scroll offset using an event handler:
document.body.addEventListener('scroll', function() {
if(window.scrollY > 499) {
document.getElementById('myDiv').classList.add('appear'); // or whatever...
}
});

footer animate up when scrolling and touch bottom and animate down when scrolling up

This is a question that once asked in a different variation,
and i tried to use the code, but it doesn't work for me.
I want my footer to animate up when scrolling just a bit before reaching the bottom, and closing while scrolling up.
like in this site - you will see if you scroll all the way down.
http://www.pronto.co.il
this is my code:
css:
body, html { height: 1000px; }
html:
<button id="buttonTest">try me</button>
<div id="footer" style="display: none;"><img src="pics/try_me_1.png" ></div>
I'm trying to leave the jquery code but I don't understand exactly how it works here yet.
so this is the link to the answer - i took it and use animate() instead the alert.
Footer animates up when you reach bottom of screen, but fails to animate down when you scroll back up
will help me a lot. thank u so very much
you can add/remove a given class
var footer = document.querySelector("#footer");
window.onscroll = function(event) {
((window.innerHeight + window.scrollY) >= document.body.offsetHeight) ? footer.classList.add("visible") : footer.classList.remove("visible")
};
And here is your css
#footer{
position: fixed;
bottom: 0;
overflow: hidden;
height: 0;
transition: height .3s ease
}
#footer.visible{
height: 100px;/*what ever you want*/
}
As the comment suggest there is no animation on the link you provide, but based on the link question is just simple as this:
var isShowing = false;
$(window).scroll(function() {
if ($(window).scrollTop() + $(window).height() === $(document).height()) {
$('#footer').slideToggle();
isShowing = true;
} else if (isShowing === true && $(window).scrollTop() + $(window).height() <= $(document).height() * 0.9) {
$('#footer').slideToggle();
isShowing = false;
}
});
body,
html {
height: 1000px;
}
#footer {
height: 150px;
position: fixed;
bottom: 0;
width: 100%;
left: 0;
background:black;
display:none;
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/1.11.1/jquery.min.js"></script>
<button id="buttonTest">try me</button>
<div id="footer"></div>

Problems with the div not sticking to the top of the page when scrolled to

I'm trying to make the div "button_tray" stick to the top of the page when scrolled by. the whole page looks like this so you can get a better idea of what i'm trying to do: http://tinypic.com/r/n6cnte/8
It seems to be working when I pasted bits of code needed for this to work into jsfiddle: http://jsfiddle.net/5ADzD/641/
So I really have no idea what is it here making it not work.
Appreciate the help.
HTML:
<doctype html>
<html>
<head>
<meta charset="utf-8">
<link rel="stylesheet" href="<?php bloginfo(stylesheet_url)?>"/>
<script type="text/javascript" src="sticky.js"></script>
</head>
<body>
<div id="main_img"></div>
<div id="button_tray">
Sample 1
Sample 2
Sample 3
</div>
<div id="content">
part of CSS:
#button_tray {
width: 100%;
height: 100px;
background-color: #373737;
line-height: 100px;
color: orange;
font-size: 22px;
text-align: center;
}
#button_tray.sticky {
position: fixed;
top: 0px;
}
JS:
var $window = $(window);
$stickyEl = $('#button_tray');
var elTop = $stickyEl.offset().top;
$window.scroll(function() {
var windowTop = $window.scrollTop();
$stickyEl.toggleClass('sticky', windowTop > elTop);
});
Div tags are stacked on each other from top to bottom without CSS.
Probably, there is a syntax error. I believe instead of using #button_tray, try using .button_tray

Categories

Resources