I have a ReactJS project and I've been advised not to use jQuery for various reasons, so I'm attempting to convert the following jQuery to JavaScript -- it smoothly changes background color while scrolling the page:
$( window ).ready(function() {
var wHeight = $(window).height();
$('.slide')
.height(wHeight)
.scrollie({
scrollOffset : -50,
scrollingInView : function(elem) {
var bgColor = elem.data('background');
$('body').css('background-color', bgColor);
}
});
});
CSS:
* { box-sizing: border-box }
body {
font-family: 'Coming Soon', cursive;
transition: background 1s ease;
background: #3498db;
}
p {
color: #ecf0f1;
font-size: 2em;
text-align: center;
}
a {
text-decoration: none;
}
HTML:
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<script src="https://s3-us-west-2.amazonaws.com/s.cdpn.io/2542/jquery.scrollie.min_1.js"></script>
<div class="main-wrapper">
<div class="slide slide-one" data-background="#3498db">
<p>Title</p>
<center>Go To Green.</center>
</div>
<div class="slide slide-two" data-background="#27ae60">
<a name="green">
<p>Green area</p>
<center>Go To Red.</center>
</a>
</div>
<div class="slide slide-three" data-background="#e74c3c">
<a name="red">
<p>Red area</p>
<center>Page over. Hope that was helpful :)</center>
</a>
</div>
But how can I do the conversion to JavaScript to fit the ReactJS project?
Thank you in advance and will be sure to accept/upvote answer
Changing from JQuery to JavaScript is always possible. Because JQuery builds on JavaScript. Most of the time ( like in your case ) it's not even that much work.
I've not changed your CSS or HTML. So this is just some new JavaScript. However you should put this script at the end of your website.
(function() { // create an own scope and run when everything is loaded
// collect all the slides in this array and apply the correct height
var slides = document.getElementsByClassName('slide')
for (slide of slides) slide.style.height = window.innerHeight + 'px'
// use the native scroll event
document.addEventListener("scroll", function() {
// how much have we scrolled already
var currentOffset = document.documentElement.scrollTop || document.body.scrollTop
// now check for all slides if they are in view (only one will be)
for (slide of slides) {
// 200 is how much before the top the color should change
var top = slide.getBoundingClientRect().top + currentOffset - 200
var bottom = top + slide.offsetHeight
// check if the current slide is in view
if (currentOffset >= top && currentOffset <= bottom) {
// set the new color, the smooth transition comes from the CSS tag
// CSS: transition: background 1s ease;
document.body.style.background = slide.dataset.background
break
}
}
})
}())
Additionally you might want to listen on resize event, because as of now when you resize the window will look a bit off ( this replaces the 5 line of the code above)
function setSize() {
for (slide of slides) slide.style.height = window.innerHeight + 'px'
}
window.addEventListener("resize", setSize)
setSize()
Solution
(function() {
var slides = document.getElementsByClassName('slide')
function setSize() {
for (slide of slides) slide.style.height = window.innerHeight + 'px'
}
window.addEventListener("resize", setSize)
setSize()
document.addEventListener("scroll", function() {
var currentOffset = document.documentElement.scrollTop || document.body.scrollTop
for (slide of slides) {
// 100 is how much before the top the color should change
var top = slide.getBoundingClientRect().top + currentOffset - 100
var bottom = top + slide.offsetHeight
if (currentOffset >= top && currentOffset <= bottom) {
document.body.style.background = slide.dataset.background
break
}
}
})
}())
body {
font-family: 'Coming Soon', cursive;
transition: background 1s ease;
background: #3498db;
}
p {
color: #ecf0f1;
font-size: 2em;
text-align: center;
}
a { text-decoration: none;
}
<div class="main-wrapper">
<div class="slide slide-one" data-background="#3498db">
<p>Title</p>
<center>Go To Green.</center>
</div>
<div class="slide slide-two" data-background="#27ae60">
<a name="green">
<p>Green area</p>
<center>Go To Red.</center>
</a>
</div>
<div class="slide slide-three" data-background="#e74c3c">
<a name="red">
<p>Red area</p>
<center>Page over. Hope that was helpful :)</center>
</a>
</div>
The plugin you are referring to links an example from their README that includes a link to a newer version that makes use of this other plugin that does not use jQuery and in fact does what you want it to do, I think. It is called in-view and it looks very good to me (both the functionality and the code).
Its usage is very similar to what you are doing currently. From the newer example linked above:
var $target = $('.wrapper');
inView('.section').on('enter', function(el){
var color = $(el).attr('data-background-color');
$target.css('background-color', color );
});
I do realize that I am in a way not answering the question, because this is not a jQuery-to-vanilla-JS guide, but I do think that it helps to know that somebody already did it for you.
Should give you some idea.
var wHeight = window.innerHeight;
To select elements in javascript:
on browser open inspect element, console tab and type:
document.get
and it gives you hint what to get
To get style of element:
var elem1 = document.getElementById("elemId");
var style = window.getComputedStyle(elem1, null);
To set Property:
document.body.style.setProperty(height`, wHeight +"px");
Below is some modifications that you can make, As people commented I am not trying to teach you how to's but want to give you some start:
// $( window ).ready(function() { //remove this
var wHeight = $(window).height(); // USe this instead: var wHeight = window.innerHeight;
$('.slide') //instead of selecting with jquery "$('.slide')" select with: Javascript var x = document.getElementsByClassName("example") ;
.height(wHeight) // Here you are chaining methods, read this article https://schier.co/blog/2013/11/14/method-chaining-in-javascript.html
.scrollie({
scrollOffset : -50,
scrollingInView : function(elem) {
var bgColor = elem.data('background'); //var bgColor = window.getComputedStyle(elem, null);
$('body').css('background-color', bgColor); //document.body.style.background = bgColor;
}
});
// }); //remove this
For .... in
var t = document.getElementsByClassName('slide')
console.log(typeof t) //object
for (var prop in t) {
console.log('t.' + prop, '=', t[prop]);
// output is index.html:33 t.0 = <div class="slide slide-one" data- background="#3498db">…</div>
// output is index.html:33 t.1 = <div class="slide slide-two" data- background="#27ae60">…</div>
// output is index.html:33 t.2 = <div class="slide slide-three" data-background="#e74c3c">…</div><a name="red">…</a></div>
// output is index.html:33 t.length = 3
// output is index.html:33 t.item = function item() { [native code] }
// output is index.html:33 t.namedItem = function namedItem() { [native code] }
}
Related
I have some text elements that should move in their x-axis based on the scroll position.
Please see this pen for reference:
https://codepen.io/magglomag/pen/GRZwRNB
HTML
<h1 class="moving-text-wrapper">
<div class="moving-text moving-text-1" data-scroll-speed="-4">Lorem</div>
<div class="moving-text moving-text-2" data-scroll-speed="2">ipsum</div>
<div class="moving-text moving-text-3" data-scroll-speed="9">sonsetetur</div>
<div class="moving-text moving-text-4" data-scroll-speed="-6">sit</div>
<div class="moving-text moving-text-5" data-scroll-speed="3">amet</div>
</h1>
CSS
html {
height: 300vh;
}
.moving-text-wrapper {
margin-top: 100vh;
text-align: center;
}
jQuery
$.fn.moveIt = function(){
var $window = $(window);
var instances = [];
$(this).each(function(){
instances.push(new moveItItem($(this)));
});
window.addEventListener('scroll', function(){
var scrollTop = $window.scrollTop();
var elemOffsetTop = $( '.moving-text-wrapper' ).offset().top;
var translateX = elemOffsetTop - scrollTop - $( window ).height()/2;
instances.forEach(function(inst){
inst.update(translateX);
});
}, {passive: true});
}
var moveItItem = function(el){
this.el = $(el);
this.speed = parseInt(this.el.attr('data-scroll-speed'));
};
moveItItem.prototype.update = function(translateX){
this.el.css('transform', 'translateX(' + -(translateX / this.speed) + 'px)');
};
$(function(){
$('[data-scroll-speed]').moveIt();
});
What I’d like to add is a little easing to the variable translateX, so when the scrolling stops the text will move a little bit longer and does not stop directly like in the current pen.
Any hints how to solve that?
Many thanks!
Actually this was quite easy to solve with CSS transitions:
I just added a transition to the elements like this:
.moving-text {
transition-property: transform;
transition-duration: 1s;
transition-timing-function: ease-out;
}
See updated Codepen for reference:
https://codepen.io/magglomag/pen/YzqRPoX
I know how to fix the animation that goes down only when the image is showing up in the window with jQuery, but now I want to do that with JavaScript. Struggling with that. The image must be fluently go down (+50px for 1.6 seconds). Have googling around, but most of them are done with jQuery I suggest and that is not what I want. Furtermore the animation should start when the scrollTop is between 600px and 800px.
function scrollFunction() {
var animate = document.getElementById("picture");
var position = 0;
var top = 0;
var scrollTop = window.pageYOffset || document.documentElement.scrollTop;
if(scrollTop > 600 && scrollTop < 800){
position++;
animate.style.top = position + "50px";
} else {
stop();
}
}
function stop() {
clearTimeout(animate);
}
#picture {
width: 100%;
height: auto;
top: -5px;
position: relative;
display: block;
margin-left: auto;
margin-right: auto;
margin-bottom: 20px;
}
<div class="col-sm-12 col-xs-12">
<h1 class="responsive-h1">Mi<span class="logo-orange"> Pad2</span></h1>
<p class="edition-title above-text-black">Black Edition</p>
<img src="Img/picture.jpg" id="picture"/>
</div>
jsFiddle : https://jsfiddle.net/n1q3fy8w/
Javascript
var imgSlide = document.getElementById('slidedown-image');
var slideDown = setInterval(function() {
var topVal = parseInt(window.getComputedStyle(imgSlide).top, 10);
imgSlide.style.top = (topVal + 1) + "px";
}, 15);
setTimeout(function( ) { clearInterval( slideDown ); }, 1600);
You get the element first, after that you setup a setInterval which will basically move our img downwards, we then also set a setTimeout which after 1600ms remvoes the slideDown interval and the image stops. Your image however may need position: absolute.
The above answer will only work in Chrome, this however should work in all browswers
jsFiddle : https://jsfiddle.net/n1q3fy8w/1/
javascript
var imgSlide = document.getElementById('slidedown-image');
var slideDown = setInterval(function() {
var topVal = parseInt(imgSlide.style.top, 10);
imgSlide.style.top = (topVal + 1) + "px";
}, 15);
setTimeout(function( ) { clearInterval( slideDown ); }, 1600);
Ok so getComputedStyle only works in chrome, so to get this to work on all other browsers, you have to specifically set the css property on the element and not via CSS.
When you use javascript to access an element and change its style like so element.style.bottom = '150px' the .style gets you all of the css values for your inline styles on that element, so any css changes on an element that is done via a .css/.less file you can't access via javascript.
So all the above code does is we set a top: 0 on the element itself and in our code we use imageSlide.style.top instead of chrome's window.getComputedStyle
Have you considered using a CSS transition? if you are changing the value of top you should be able to add transition: top 1.6s in your css (to picture). (Then the vendor prefixed versions when you get it working)
The problem I'm having is filling a div with text using letter-spacing. The main issue is, I don't know the width of the div.
First I was thinking using, text-align= justify, but since that I've been running in the dark and got no clue to how to solve this. I'm guessing some scripting magic might do the trick.
An imgur link giving you an idea what I mean:
<div id="container">
<h1>Sample</h1>
<p>Another even longer sample text</p>
</div>
Here is a link showcasing an example; JSfiddle.
Based the comment of the poster it seems JavaScript is no problem. Here's a possible approach to solve the problem with jQuery:
JSFiddle 1
function dynamicSpacing(full_query, parent_element) {
$(full_query).css('letter-spacing', 0);
var content = $(full_query).html();
var original = content;
content = content.replace(/(\w|\s)/g, '<span>$1</span>');
$(full_query).html(content);
var letter_width = 0;
var letters_count = 0;
$(full_query + ' span').each(function() {
letter_width += $(this).width();
letters_count++;
});
var h1_width = $(parent_element).width();
var spacing = (h1_width - letter_width) / (letters_count - 1);
$(full_query).html(original);
$(full_query).css('letter-spacing', spacing);
}
$(document).ready(function() {
// Initial
dynamicSpacing('#container h1', '#container');
// Refresh
$(window).resize(function() {
dynamicSpacing('#container h1', '#container');
});
});
Update
Small tweak for when the wrapper gets too small: JSFiddle 2
Another solution if you don't have to be semantic (because you will get many spans), I mean if you need only the visual result, is to use flexbox.
So you have your <div id="#myText">TEXT 1</div>
We need to get this:
<div id="#myText">
<span>T</span>
<span>E</span>
<span>X</span>
<span>T</span>
<span> </span>
<span>1</span>
</div>
So then you can apply CSS:
#myText {
display: flex;
flex-direction: row;
justify-content: space-between;
}
In order to transform the text to span you can use jQuery or whatever. Here with jQuery:
var words = $('#myText').text().split("");
$('#myText').empty();
$.each(words, function(i, v) {
if(v===' '){
$('#myText').append('<span> </span>');
} else {
$('#myText').append($("<span>").text(v));
}
});
For better results remove put letter-spacing: 0 into #myText so any extra spacing will be applied.
This is obviously evil, but since there is no straight forward way to do it with just css, you could do: demo
HTML:
<div>text</div>
CSS:
div, table {
background: yellow;
}
table {
width: 100%;
}
td {
text-align: center;
}
JS:
var text = jQuery("div").text();
var table = jQuery("<table><tr></tr></table>").get(0);
var row = table.rows[0];
for (var i = 0; i < text.length; i++) {
var cell = row.insertCell(-1);
jQuery(cell).text(text[i]);
}
jQuery("div").replaceWith(table);
This may help:
function fill(target) {
var elems = target.children();
$.each(elems, function(i,e) {
var x = 1;
var s = parseInt($(e).css('letter-spacing').replace('px',''));
while(x == 1) {
if($(e).width() <= target.width() - 10) {
s++;
$(e).css('letter-spacing', s+'px');
} else {
x = 0;
}
}
});
}
fill($('#test'));
Note: If letter spacing is : 0 then you don't have to use replace method. Or you can add letter-spacing:1px; to your css file.
For avoiding overflow, always give minus number to parent element's height for correct work.
An other approach I wrote for this question Stretch text to fit width of div. It calculates and aplies letter-spacing so the text uses the whole available space in it's container on page load and on window resize :
DEMO
HTML :
<div id="container">
<h1 class="stretch">Sample</h1>
<p class="stretch">Another even longer sample text</p>
</div>
jQuery :
$.fn.strech_text = function(){
var elmt = $(this),
cont_width = elmt.width(),
txt = elmt.text(),
one_line = $('<span class="stretch_it">' + txt + '</span>'),
nb_char = elmt.text().length,
spacing = cont_width/nb_char,
txt_width;
elmt.html(one_line);
txt_width = one_line.width();
if (txt_width < cont_width){
var char_width = txt_width/nb_char,
ltr_spacing = spacing - char_width + (spacing - char_width)/nb_char ;
one_line.css({'letter-spacing': ltr_spacing});
} else {
one_line.contents().unwrap();
elmt.addClass('justify');
}
};
$(document).ready(function () {
$('.stretch').each(function(){
$(this).strech_text();
});
$(window).resize(function () {
$('.stretch').each(function(){
$(this).strech_text();
});
});
});
CSS :
body {
padding: 130px;
}
#container {
width: 100%;
background: yellow;
}
.stretch_it{
white-space: nowrap;
}
.justify{
text-align:justify;
}
I have an h1 that is far down a page..
<h1 id="scroll-to">TRIGGER EVENT WHEN SCROLLED TO.</h1>
and I want to trigger an alert when the user scrolls to the h1, or has it in it's browser's view.
$('#scroll-to').scroll(function() {
alert('you have scrolled to the h1!');
});
how do I do this?
You can calculate the offset of the element and then compare that with the scroll value like:
$(window).scroll(function() {
var hT = $('#scroll-to').offset().top,
hH = $('#scroll-to').outerHeight(),
wH = $(window).height(),
wS = $(this).scrollTop();
if (wS > (hT+hH-wH)){
console.log('H1 on the view!');
}
});
Check this Demo Fiddle
Updated Demo Fiddle no alert -- instead FadeIn() the element
Updated code to check if the element is inside the viewport or not. Thus this works whether you are scrolling up or down adding some rules to the if statement:
if (wS > (hT+hH-wH) && (hT > wS) && (wS+wH > hT+hH)){
//Do something
}
Demo Fiddle
Combining this question with the best answer from jQuery trigger action when a user scrolls past a certain part of the page
var element_position = $('#scroll-to').offset().top;
$(window).on('scroll', function() {
var y_scroll_pos = window.pageYOffset;
var scroll_pos_test = element_position;
if(y_scroll_pos > scroll_pos_test) {
//do stuff
}
});
UPDATE
I've improved the code so that it will trigger when the element is half way up the screen rather than at the very top. It will also trigger the code if the user hits the bottom of the screen and the function hasn't fired yet.
var element_position = $('#scroll-to').offset().top;
var screen_height = $(window).height();
var activation_offset = 0.5;//determines how far up the the page the element needs to be before triggering the function
var activation_point = element_position - (screen_height * activation_offset);
var max_scroll_height = $('body').height() - screen_height - 5;//-5 for a little bit of buffer
//Does something when user scrolls to it OR
//Does it when user has reached the bottom of the page and hasn't triggered the function yet
$(window).on('scroll', function() {
var y_scroll_pos = window.pageYOffset;
var element_in_view = y_scroll_pos > activation_point;
var has_reached_bottom_of_page = max_scroll_height <= y_scroll_pos && !element_in_view;
if(element_in_view || has_reached_bottom_of_page) {
//Do something
}
});
I think your best bet would be to leverage an existing library that does that very thing:
http://imakewebthings.com/waypoints/
You can add listeners to your elements that will fire off when your element hits the top of the viewport:
$('#scroll-to').waypoint(function() {
alert('you have scrolled to the h1!');
});
For an amazing demo of it in use:
http://tympanus.net/codrops/2013/07/16/on-scroll-header-effects/
Inview library triggered event and works well with jquery 1.8 and higher!
https://github.com/protonet/jquery.inview
$('div').on('inview', function (event, visible) {
if (visible == true) {
// element is now visible in the viewport
} else {
// element has gone out of viewport
}
});
Read this https://remysharp.com/2009/01/26/element-in-view-event-plugin
Fire scroll only once after a successful scroll
Note: By successful scroll I mean when the user has scrolled to the desired
element or in other words when the desired element is in view
The accepted answer worked 90% for me so I had to tweak it a little to actually fire only once.
$(window).on('scroll',function() {
var hT = $('#comment-box-section').offset().top,
hH = $('#comment-box-section').outerHeight(),
wH = $(window).height(),
wS = $(this).scrollTop();
if (wS > ((hT+hH-wH)-500)){
console.log('comment box section arrived! eh');
// This detaches the scroll so doStuff() won't run more than once
$(window).off('scroll');
doStuff();
}
});
You could use this for all devices,
$(document).on('scroll', function() {
if( $(this).scrollTop() >= $('#target_element').position().top ){
do_something();
}
});
Intersection Observer can be the best thing IMO, without any external library it does a really good job.
const options = {
root: null,
threshold: 0.25, // 0 - 1 this work as a trigger.
rootMargin: '150px'
};
const target = document.querySelector('h1#scroll-to');
const observer = new IntersectionObserver(
entries => { // each entry checks if the element is the view or not and if yes trigger the function accordingly
entries.forEach(() => {
alert('you have scrolled to the h1!')
});
}, options);
observer.observe(target);
You can use jQuery plugin with the inview event like this :
jQuery('.your-class-here').one('inview', function (event, visible) {
if (visible == true) {
//Enjoy !
}
});
Link : https://remysharp.com/2009/01/26/element-in-view-event-plugin
This should be what you need.
Javascript:
$(window).scroll(function() {
var hT = $('#circle').offset().top,
hH = $('#circle').outerHeight(),
wH = $(window).height(),
wS = $(this).scrollTop();
console.log((hT - wH), wS);
if (wS > (hT + hH - wH)) {
$('.count').each(function() {
$(this).prop('Counter', 0).animate({
Counter: $(this).text()
}, {
duration: 900,
easing: 'swing',
step: function(now) {
$(this).text(Math.ceil(now));
}
});
}); {
$('.count').removeClass('count').addClass('counted');
};
}
});
CSS:
#circle
{
width: 100px;
height: 100px;
background: blue;
-moz-border-radius: 50px;
-webkit-border-radius: 50px;
border-radius: 50px;
float:left;
margin:5px;
}
.count, .counted
{
line-height: 100px;
color:white;
margin-left:30px;
font-size:25px;
}
#talkbubble {
width: 120px;
height: 80px;
background: green;
position: relative;
-moz-border-radius: 10px;
-webkit-border-radius: 10px;
border-radius: 10px;
float:left;
margin:20px;
}
#talkbubble:before {
content:"";
position: absolute;
right: 100%;
top: 15px;
width: 0;
height: 0;
border-top: 13px solid transparent;
border-right: 20px solid green;
border-bottom: 13px solid transparent;
}
HTML:
<div id="talkbubble"><span class="count">145</span></div>
<div style="clear:both"></div>
<div id="talkbubble"><span class="count">145</span></div>
<div style="clear:both"></div>
<div id="circle"><span class="count">1234</span></div>
Check this bootply:
http://www.bootply.com/atin_agarwal2/cJBywxX5Qp
If you are looking for a javascript version. You can call this method on scroll event listener.
showScrollTop = () =>{
const currentScrollPosition = window.pageYOffset;
let elementID = 'service-selector'
const elementOffsetTop = document.getElementById(elementID).offsetTop
if ( currentScrollPosition > elementOffsetTop){
// place your logic here
} else {
// place your logic here
}
}
window.addEventListener('scroll', showScrollTop)
If you are doing a lot of functionality based on scroll position, Scroll magic (http://scrollmagic.io/) is built entirely for this purpose.
It makes it easy to trigger JS based on when the user reaches certain elements when scrolling. It also integrates with the GSAP animation engine (https://greensock.com/) which is great for parallax scrolling websites
Just a quick modification to DaniP's answer, for anyone dealing with elements that can sometimes extend beyond the bounds of the device's viewport.
Added just a slight conditional - In the case of elements that are bigger than the viewport, the element will be revealed once it's top half has completely filled the viewport.
function elementInView(el) {
// The vertical distance between the top of the page and the top of the element.
var elementOffset = $(el).offset().top;
// The height of the element, including padding and borders.
var elementOuterHeight = $(el).outerHeight();
// Height of the window without margins, padding, borders.
var windowHeight = $(window).height();
// The vertical distance between the top of the page and the top of the viewport.
var scrollOffset = $(this).scrollTop();
if (elementOuterHeight < windowHeight) {
// Element is smaller than viewport.
if (scrollOffset > (elementOffset + elementOuterHeight - windowHeight)) {
// Element is completely inside viewport, reveal the element!
return true;
}
} else {
// Element is larger than the viewport, handle visibility differently.
// Consider it visible as soon as it's top half has filled the viewport.
if (scrollOffset > elementOffset) {
// The top of the viewport has touched the top of the element, reveal the element!
return true;
}
}
return false;
}
I use the same code doing that all the time, so added a simple jquery plugin doing it.
480 bytes long, and fast. Only bound elements analyzed in runtime.
https://www.npmjs.com/package/jquery-on-scrolled-to
It will be
$('#scroll-to').onScrolledTo(0, function() {
alert('you have scrolled to the h1!');
});
or use 0.5 instead of 0 if need to alert when half of the h1 shown.
Quick and fast implementation,
let triggered = false;
$(window).on('scroll',function() {
if (window.scrollY > ($('#scrollTo').offset().top+$('#scrollTo').outerHeight()-window.innerHeight) & !triggered){
console.log('triggered here on scroll..');
triggered = true;
}
});
using global variable triggered = false makes it just to happen once, otherwise, every time crossing past the element, this action is triggered.
Hello, I want a certain text to appear when I scroll past it or when I scroll until the point where the text is. The effect when appearing should be somewhat like the first effect on the top of the website http://namanyayg.com/.
I want the effect in minimal code with pure CSS and JS i.e no jQuery.
I was thinking that maybe I would use something like a display:none property for a span and then when you scroll past it the display becomes block but I dont know how to trigger the effect using javascript.
Any help would be appreciated.
First wrap whatever your text or content that you want to show on scroll, in one div so that you can show hide the div depending upon the scroll. Write two classes for your target div.
Your CSS:
/*Use this class when you want your content to be hidden*/
.BeforeScroll
{
height: 100px; /*Whatever you want*/
width: 100%; /*Whatever you want*/
.
.
display: none;
}
/*Use this class when you want your content to be shown after some scroll*/
.AfterScroll
{
height: 100px; /*Whatever you want*/
width: 100%; /*Whatever you want*/
.
.
display: block;
}
Your HTML:
<!--Set class BeforeScoll to your target div-->
<div id = "divToShowHide" class = "BeforeScroll">Content you want to show hide on scroll</div>
Your Script:
<!--include these script in head section or wherever you want-->
<script src="http://ajax.googleapis.com/ajax/libs/jqueryui/1.10.1/jquery-ui.min.js" type="text/javascript"></script>
<script type = "text/javascript">
$(document).ready(function(){
//Take your div into one js variable
var div = $("#divToShowHide");
//Take the current position (vertical position from top) of your div in the variable
var pos = div.position();
//Now when scroll event trigger do following
$(window).scroll(function () {
var windowpos = $(window).scrollTop();
//Now if you scroll more than 100 pixels vertically change the class to AfterScroll
// I am taking 100px scroll, you can take whatever you need
if (windowpos >= (pos.top - 100)) {
div.addClass("AfterScroll");
}
//If scroll is less than 100px, remove the class AfterScroll so that your content will be hidden again
else {
s.removeClass("AfterScroll");
}
//Note: If you want the content should be shown always once you scroll and do not want to hide it again when go to top agian, no need to write the else part
});
});
</script>
Hope it will solve your problem.
I would recommend this plugin
http://johnpolacek.github.io/superscrollorama/
Edit:
I don't know how no one noticed that the solution had to be made without using external libraries like jQuery. However, the solution is extremely easy with basic functionality. Find it here
HTML:
<div id="parent-div">
<div id="child-div">
Psst .. I am here!!
</div>
</div>
CSS:
#parent-div
{
position:relative;
height:3000px;
width:300px;
background-color:red;
}
#child-div
{
color:white;
position:relative;
top:1000px;
width:300px;
display:none;
text-align:center;
}
JS:
var body=document.getElementsByTagName("body")[0];
var parent=document.getElementById("parent-div");
var child=document.getElementById("child-div");
body.onscroll = function(){
//console.log(documenhttps://fiddle.jshell.net/3urv0tp0/#tidyt.getElementById("child-div").style.top)
if(document.documentElement.scrollTop>=child.offsetTop)//Adjust Tolerance as you want
{
child.style.display="block"
}
};
I was looking for this either. Here i was trying to make "show text after scrolling to (number)px with fade effect". I wish it will work as it works for me :) The animation will be playing again if u scroll back to it, idk how to make it just one like in web u showed xd (i will edit if I find out)
window.addEventListener("scroll", function() {showFunction()});
function showFunction() {
if (document.body.scrollTop > 900 || document.documentElement.scrollTop > 900) {
document.getElementById("toptexts2").style.display = "block";
} else {
document.getElementById("toptexts2").style.display = "none";
}
}
.toptexts2 {
animation: fadeEffect 3s; /* fading effect takes 3s */
}
#keyframes fadeEffect { /* from 0 to full opacity */
from {opacity: 0;}
to {opacity: 1;}
}
<div class="toptexts2" id="toptexts2">
<div>Hi!</div>
<div>↓ go down ↓</div>
</div>
I like this:
var doc = document, dE = doc.documentElement, bod = doc.body;
function E(e){
return doc.getElementById(e);
}
function xy(e, d){
if(!d)d = 'Top';
d = 'offset'+d;
var r = e[d];
while(e.offsetParent){
e = e.offsetParent; r += e[d];
}
return r;
}
function x(e){
return xy(e, 'Left');
}
function y(e){
return xy(e);
}
var txt = E('theId'), txtS = txt.style;
onscroll = function(){
var left = dE.scrollLeft || bod.scrollLeft || 0;
var top = dE.scrollTop || bod.scrollTop || 0;
var w = innerWidth || dE.clientWidth || bod.clientWidth;
var h = innerHeight || dE.clientHeight || bod.clientHeight;
if(top > y(txt)-h){
txtS.display = 'none';
}
else{
txtS.display = 'block';
}
}
I left the left stuff in there, just in case, but you can probably remove it.
var div=$("#divtochange");
$(window).scroll(function () {
var windowpos = $(window).scrollTop();
//---check the console to acurately see what the positions you need---
console.log(windowpos);
//---------------------
//Enter the band you want the div to be displayed
if ((windowpos >= 0) && (windowpos <= 114)){
div.addClass("AfterScroll");
}
else{
div.removeClass("AfterScroll");
}