jquery increase/decrease image contrast on scroll - javascript

This site I am developing is using HTML5, CSS3, Bootstrap 4, and Jquery. I would like to have a scroll effect on a full-screen background-image that is at the very top of my page (100vh hero banner type thing). I am trying to gradually increase the contrast (css filter: contrast(some%)) of an image as the user scrolls down (its fine if the image is completely unrecognizable by the time it leaves viewport).
I have some Jquery that somewhat does the effect I am looking for, however I would like the effect to be more gradual.
The main issue I am having is that when the user scrolls back to the top of the page the contrast value gets set to 0% leaving a completely grayed out image. What I would like is for the contrast to gradually decrease back to normal (100%) as the user scrolls back up all the way to the top of the page.
I have set up a very simplified codepen. I couldn't get a css background-image url value to reference an external link from codepen, so I am targeting the effect on a full screen image ().
Thanks!
Link to the Pen: [codepen-link][1]
[1]: http://codepen.io/wdzajicek/pen/MVovZE
See code below in snippet
$(document).ready(function (){
$(window).scroll(function(){
var pixelstop = $(window).scrollTop();
$(".myimage ").css("filter", "contrast(" + pixelstop + "%)");
});
});
.header {
height: 100vh;
}
.myimage {
position:absolute;
top: 0;
left: 0;
min-width: 100%;
width; 100%;
z-index: -1;
}
.jumbotron {
position: relative;
background-color: unset;
margin-top: 150px;
z-index: 999;
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<header class="header text-center">
<img src="https://raw.githubusercontent.com/wdzajicek/portfolio/master/assets/img/header-bg.jpg" class="myimage" alt="">
</header>

There is the main problem in $(window).scrollTop(); it will return 0 value
that's why contrast value gets set to 0% leaving a completely grayed out image
var pixelstop = $(window).scrollTop();
replace the code with
var pixelstop = 100+100*$(window).scrollTop()/$(window).height();
don't just copy this code please understand thanks.

$(document).ready(function (){
$(window).scroll(function(){
var pixelstop = 100+100*$(window).scrollTop()/$(window).height();
console.log(pixelstop);
$(".myimage ").css("filter", "contrast(" + pixelstop + "%)");
});
});
.header {
height: 100vh;
}
.myimage {
position:absolute;
top: 0;
left: 0;
min-width: 100%;
width; 100%;
z-index: -1;
}
.jumbotron {
position: relative;
background-color: unset;
margin-top: 150px;
z-index: 999;
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/1.8.3/jquery.min.js"></script>
<header class="header text-center">
<img src="https://raw.githubusercontent.com/wdzajicek/portfolio/master/assets/img/header-bg.jpg" class="myimage" alt="">
</header>
100 is default value of filter contrast not 0. that's why the background is grey out because it reaches zero.

Related

How to overlay a new image onto a fixed container when scrolling?

I'm trying to replicate this overlay phone effect from this website:
https://www.beemit.com.au/
Basically, when you scroll down, the contents inside the fixed div (phone) also change.
I cannot grasp my head around the revealing effect created when you scroll down. I have only managed to create the fixed div and the various sections on the webpage.
Here's a simple version of the overlay-on-scroll.
There are 3 elements, the first image you want to be shown in the 'phone', the second image which gradually gets revealed and the footer element. They have different z-indexes so footer is behind both first and second and second is behind first.
The phone has a fixed position so it doesn't move on scrolling. The footer is placed relative to the body (or whatever container you have) just out of view at 100%.
We introduce a simple event listener on scrolling which tests whether there is an overlap between the footer and the phone. If there is then we set the height of the first image element to be its original height minus the overlap. This reveals the bottom part of the second element.
Without seeing your code I can't tell whether you need more sophistication (for example, you have to be aware of stacking contexts if your phone and footer are not in the same one).
const footer = document.querySelector('.footer');
const first = document.querySelector('.first');
const firstBottom = first.getBoundingClientRect().bottom;
const firstHeight = firstBottom - first.getBoundingClientRect().top;
function checkOverlay() {
const top = footer.getBoundingClientRect().top;
if ( top < firstBottom) {
first.style.height = firstHeight - firstBottom + top + 'px';
}
}
body {
width:100vw;
height: 100vh;
overflow-y: scroll;
overflow-x: hidden;
}
.first, .second {
position: fixed;
top: 50%;
left: 50%;
border: 1px solid black;
width: 20vmin;
height: 30vmin;
overflow:hidden;
}
.first {
background-image: linear-gradient(magenta, pink);
z-index: 0;
}
.second {
background-image: linear-gradient(cyan, lime);
z-index: -1;
}
.footer {
width: 100%;
height: 50%;
background-image: linear-gradient(red,blue);
position: relative;
top: 100%;
z-index: -2;
}
<body onscroll="checkOverlay();">
<div class="first"></div>
<div class="second"></div>
<div class="footer"></div>
</body>

Javascript Scrolling Parallax Positioning

I'm currently doing a javascript parallax page. I've managed to set the background image and 2 other pictures(#content,#content2).
When i scroll all the way down past my content and then to my content2, I want my webpage to end there. However I'm able to scroll down infinitely.
Can anyone please look at my code and tell me what i need to add or change so that my webpage ends and stops scrolling after content2.
Please note that my #image is my main background and the content and content2 are separate images that go over my background but i want my page and scrolling to stop at content2.
Code:
<style type="text/css">
* {
margin: 0px;
padding: 0px;
}
#image {
position: relative;
z-index: -1
}
#content {
height:690px;
width: 100%;
margin-top:-10px;
background:url(http:/chicago_bulls_wallpaper_backgrounds.jpg);
position: relative;
z-index: 1;
background-repeat: no-repeat;
background-position: center center;
}
#content2 {
top:710px;
height:570px;
width: 100%;
margin-top:-10px;
background:url(All.jpg);
position: relative;
z-index: 1;
background-repeat: no-repeat;
background-position: center center
}
</style>
<script type="text/javascript">
var ypos, image;
function parallex() {
ypos = window.pageYOffset;
image = document.getElementById('image');
image.style.top = ypos * 1 + 'px';
}
window.addEventListener('scroll', parallex);
</script>
<img id="image" src="black-glass.png" height="710px" width="100%" />
<div id="content"></div>
<div id="content2"></div>
It's because your parallax factor is 1, meaning that the background is moving exactly with the screen. Thus, the browser thinks that it always has room and can always afford to scroll down, which is actually a pretty hilarious bug.
If you were intending true parallax scrolling, set your factor to less than 1, like this:
image.style.top = ypos * 0.95 + 'px';
If you simply didn't want your background to move at all with the rest of the page, set the body's background to this image (as you already do with the divs), and set the background-attachment property to fixed - no JavaScript required.
Is something like this what you are wanting? I am not having a problem with infinite scrolling.
http://codepen.io/vinsongrant/pen/advzww
<img id="image" src="https://upload.wikimedia.org/wikipedia/commons/d/da/The_City_London.jpg" height="710px" width="100%" />
<div id="content">
<h1>Here is content 1</h1>
</div>
<div id="content2">
<h1>Here is content 2</h1>
</div>

Making text scroll at different speed in a simple jquery parallax example

I am following this parallax tutorial that uses only jQuery. I slightly modified the HTML:
<section id="home" data-type="background" data-speed="10">
<article data-speed="1">One</article>
<article data-speed="20">Two</article>
</section>
<section id="about" data-type="background" data-speed="10">
</section>
css
#home {
background: url(home-bg.jpg) 50% 0 repeat fixed; min-height: 1000px;
height: 1000px;
margin: 0 auto;
width: 100%;
max-width: 1920px;
position: relative;
}
#home article {
height: 458px;
position: absolute;
text-align: center;
top: 150px;
width: 100%;
}
#about {
background: url(about-bg.jpg) 50% 0 repeat fixed; min-height: 1000px;
height: 1000px;
margin: 0 auto;
width: 100%;
max-width: 1920px;
position: relative;
-webkit-box-shadow: 0 0 50px rgba(0,0,0,0.8);
box-shadow: 0 0 50px rgba(0,0,0,0.8);
}
#about article {
height: 458px;
position: absolute;
text-align: center;
top: 150px;
width: 100%;
}
And the jQuery:
$(document).ready(function(){
// Cache the Window object
$window = $(window);
$('section[data-type="background"]').each(function(){
var $bgobj = $(this); // assigning the object
$(window).scroll(function() {
// Scroll the background at var speed
// the yPos is a negative value because we're scrolling it UP!
var yPos = -($window.scrollTop() / $bgobj.data('speed'));
// Put together our final background position
var coords = '50% '+ yPos + 'px';
// Move the background
$bgobj.css({ backgroundPosition: coords });
}); // window scroll Ends
});
});
This code moves everything in a section at the same speed, but I would like to have the <article> text move at a variable speed different (defined in the <article data-speed>) from the background image.
I wasn't sure how to move the text because background-position is for images, and I tried adjusting top but that didn't have any effect. I also tried setting transform: translateZ(); on the article css, but this also did not work.
How can I add different speeds to the <article> texts? I'd also like to stick to jQuery in the spirit of the example.
try modifying markup always wrapping the article with a section, for ex.:
<section id="about" data-speed="4" data-type="background">
<article>One</article>
</section>
<section id="home" data-speed="20" data-type="background" >
<article >Two</article>
</section>
edit--explanation
this is the source of your parallax jquery script:
$(document).ready(function(){
// Cache the Window object
$window = $(window);
$('section[data-type="background"]').each(function(){
var $bgobj = $(this); // assigning the object
$(window).scroll(function() {
// Scroll the background at var speed
// the yPos is a negative value because we're scrolling it UP!
var yPos = -($window.scrollTop() / $bgobj.data('speed'));
// Put together our final background position
var coords = '50% '+ yPos + 'px';
// Move the background
$bgobj.css({ backgroundPosition: coords });
}); // window scroll Ends
});
});
as you can tell what it's doing is slowing down the scroll of the section[data-type="background"] with a factor of data('speed');
This kind of script is built in a way to have one layer of parallax, if you want more parallax layers check wagersfield's parallax script

jquery pan a large image within small div container using buttons

Hi there I need to an interactive element using a large image. This image sized 1000x1000 pixel with simple imagery will contain several questions with yes or no. What I want to do is place this image within a small div (say 500x300) with hidden overflow and add hotspots on the image for the yes/no option. What I want is when the user clicks yes, then the hotspot link pans to specific x/y coordinates of the same large image. Viewer will only see within the 500x300 window. So on and so forth. Is this possible? It seems so simple yet only option I can find is the pan by mouse option or iframe option with complicated divs and anchors. I'm not an expert in java/jquery but would love to find a script that is adaptable. Please help!
This sounded fun so I made a custom solution real quick. Demo here: jsBin
It's heavily reliant on the proper CSS, so check that in the bin, but here's the JS part:
var choice = document.querySelectorAll('.choice'),
image = document.getElementById('image')
for ( var i=0; i<choice.length; i++) {
choice[i].addEventListener('click', function (event) {
var x = this.dataset['x'],
y = this.dataset['y'];
image.style.top = '-'+y+'px';
image.style.left = '-'+x+'px';
})
}
Use css transitions for animation. Set up the positions you want the buttons to move the image around to in the image using a series of javascript objects. Then, set up your anchors, text, etc using absolute positioning on top of the image inside of a div container. Finally, add a click action in jQuery to assign your different positions to the top and left css of that container.
The end result, then, will be that you click an anchor, the left and top positions are assigned to the container via css in jQuery, and the transitions will slide the image around with the anchors.
I set up a fiddle here.
Here's the html from the fiddle:
<div id="window">
<div id="container">
<img src="http://upload.wikimedia.org/wikipedia/en/1/1f/Kill_The_Lights_1000x1000.jpg" id="image">
<ul>
<li><a id="city" href="#">City</a></li>
<li><a id="bottom" href="#">Bottom</a></li>
</ul>
</div>
</div>
And the CSS:
#window {
width:500px;
height:300px;
overflow:hidden;
position:relative;
}
#window a {
position: absolute;
z-index: 2;
display: block;
padding: 10px;
background: rgba(255,255,255,.5);
}
#city {
top: 20px;
left: 20px;
}
#bottom {
top: 220px;
left: 220px;
}
#container {
-webkit-transition:left 2s, top 2s, -webkit-transform 2s;
transition:left 2s, top 2s, transform 2s;
position: absolute;
z-index: 1;
top: 0px;
left: 0px;
}
Here's some javascript to give an example of setting up the positions as objects.
var city = {
top: -200,
left: -200
};
var bottom = {
top: -700,
left: -100
}
$('a').click(function() {
var t = this.id;
var c = $('#container');
if (typeof eval(t) !== 'undefined') {
c.css({
'top': eval(t).top,
'left': eval(t).left
});
}
});
I've just made a Fiddle with a demo image from where you could proceed.
HTML:
<div class="imgHolder">
<div class="hotspot one">Click</div>
<img src="image.jpg" />
</div>
CSS:
.imgHolder {
overflow:hidden;
width:300px;
height:300px;
position:relative;
}
.hotspot.one {
position:absolute;
top:10px;
padding:2px;
background-color:#fff;
left:10px;
}
.hotspot:hover {
cursor:pointer;
}
img {
position:relative;
z-index:-1;
}
jQuery:
$(".hotspot").on("click", function () {
$("img").animate({
"right": "+=100px"
});
});
For reference: http://api.jquery.com/animate/
You could e.g. fade hotspots in and out on specific positions and use animate() to move to the next hotspot.

Switch div from fixed to absolute at bottom of browser

Im trying to add a footer at the bottom of this content that doesn't overlay the content but moves it up.
The only way I can see it working would be something like, when browser is at the bottom remove 'fixed' class on the left red '#work'.
js fiddle DEMO
Updated js fiddle DEMO
HTML
<div id="header-block">
Header-block, this sits here in the background
</div>
<div id="content">
<div id="work">
This content should be fixed when at the top
</div>
<div id="description">
This content should scroll -
</div>
</div><!-- end content -->
<div id="footer">
This should appear at the bottom
</div>
CSS
body {
margin: 0px;
padding: 0px;
}
#header-block {
background: green;
width: 100%;
position: fixed;
z-index: 1;
height: 300px;
top: 0;
}
#content {
margin-top: 300px;
width: 100%;
position: relative;
z-index: 2;
}
#work {
background: red;
width: 50%;
height: 100vh;
float: left;
position: absolute;
}
#description {
background: blue;
width: 50%;
height: 1200px;
float: right;
font-size: 30px;
}
#footer {
background: black;
width: 100%;
height: 100px;
position: absolute;
z-index: 3;
bottom: 0;
}
If I understand your question correct, this should do the trick (although it depends very much on JavaScript unfortunately).
// Fix work column on scroll
contentStart = $("#content").offset().top ;
contentSize = $("#content").height() ;
window.onscroll = function(){
if( window.XMLHttpRequest ) {
var position=window.pageYOffset;
// calculate the position of the footer and the actual seen window
var docViewTop = $(window).scrollTop();
var docViewBottom = docViewTop + $(window).height();
var elemTop = $("#footer").offset().top;
if ( position > 300 && !(docViewBottom >= elemTop)) {
$('#work').css({'position':'fixed', 'top':'0', 'height':'100vh'});
} else {
// if the footer is visible on the screen
if(docViewBottom >= elemTop) {
$('#work').css({ 'top': 0 - (docViewBottom - elemTop) }); // scroll the #main div relative to the footer
} else {
$('#work').css({'position':'relative', 'top': 'auto'}) ;
}
}
}
}
For further informations about the calculations, perhaps this question on stackoverflow is useful.
Edit: Andrew Haining posted his answer in between of my answer, perhaps give his link a try and maybe it's a better (more proper) solution. Unfortunately I haven't actualised this page when I was testing your code in JSFiddle and I didn't see his answer.
If you want to use my script, make sure you can test it with different resolutions. It works just fine for my resolution in JSFiddle, I didn't test any other.
I'm not 100% sure what you want, but if you remove the position: absolute and the bottom: 0 from the footer, and put a div with class='clearboth' above the footer, it seems to do what you need.
CSS
.clearboth {
clear: both;
}
This is a drawing of what I see on your fiddle;
Do you want the red and the blue to always be touching the black?
I don't see the red overlying the black
You should use jQuery to add a class containing the position:fixed value when the scroll position of the page is less than the inline position of the #work div. Once it scrolls past the position, remove the class and have the element fall back in line.
You can achieve this using the following jQuery methods.. .scrollTop() .offset().top() and $(window).height().
This tutorial will give you an understanding of what you need to do to achieve the necessary results, you will just have to change the calculation slightly using $(window).height(), $('#footer').height() and a few other changes to get what you desire.
Based on the question you asked i think this is what you mean. The red div should be fixed when it gets to the top but be absolute when it is below the top for scrolling and the black footer should be below the red while scrolling, check this code i have done for you. just add this jquery script and run it.
<script type="text/javascript" src="js/jquery.js"></script>
<script>
$(document).ready(function() {
$(window).scroll(function () {
console.log($(window).scrollTop());
if ($(window).scrollTop() >= 322) {
$('#footer').css("z-index","1");
$('#work').css(
{
"background": "red",
"width": '50%',
'height': '100vh',
'float': 'left',
'position': 'fixed',
'top': '0'
});
}
if ($(window).scrollTop() <= 322)
{
$('#work').css(
{
"background": "red",
"width": "50%",
"height": "100vh",
"float": "left",
"position": "absolute"
});
};
});
});
</script>
If not exactly a parallax, this is somewhat close to how parallax works, containers moving at different speeds, and some containers sitting fixed or scrolling when they attain a particular top/bottom offset in the viewport.
There's plugin that can do it. Skrollr
You can use Skrollr along with skrollrcss, and it'll make sure how the containers take position on screen based on scrolltop of the window and the container specifically.

Categories

Resources