animate = animate;
desanimate = undo animate;
Friends, I created a function that does an element animate or 'desanimate' depending on where the scroll of the body or a div is, it's working ok, how it works?
<li data-animation-time="[100, 800]" data-animation-position="right" class="list-item one"></li>
the first value of the data-animation-time array is the initial value, ie the animator function should be called when the scrollTop pass that value, the second value is the end, the 'desanimate' function should be called when the scrollTop pass that value.
Everything working as you can see here -> Codepen: http://codepen.io/celicoo/pen/ogKGEP (you need scroll to see the animation happens).
Now I want to determine which way the animation to happen and which way it should end, for that I changed this attr:
data-animation-position="right-to-left" instead of just right or left, and i add some ifs statements to the animation and 'desanimation' function:
Animate:
var animate = function(target, position) {
target.css('display', 'inline-block');
if (position === 'right-to-right') {
target.animate({
opacity: 1,
right: '0px'
}, 500);
}
else if (position === 'right-to-left') {
target.animate({
opacity: 1,
right: '0px'
}, 500);
}
else if (position === 'left-to-left') {
target.animate({
opacity: 1,
left: '0px'
}, 500);
}
else if (position === 'left-to-right') {
target.animate({
opacity: 1,
left: '0px'
}, 500);
}
};
'Desanimate':
var desanimate = function(target, position) {
if (position === 'right-to-right') {
target.animate({
opacity: 0,
right: '245px'
}, 500);
}
else if (position === 'right-to-left') {
target.animate({
opacity: 0,
left: '245px'
}, 500);
}
else if (position === 'left-to-left') {
target.animate({
opacity: 0,
left: '245px'
}, 500);
}
else if (position === 'left-to-right') {
target.animate({
opacity: 0,
right: '245px'
}, 500);
}
};
And is not working in the 'desanimate' way, something is not working good, and i really cant see what it is.
Could someone give me a hand here? What could be doing 'desanimate' not work when I inverted step values?
Example:
left-to-right
right-to-left
Codepen with old code working just with one side (ex: left or right);
Code pen with new code not working 100% with multiple sides (ex: left to left, left to right, right to right or right to left);
Updated the codepen link . Just have a look and let me know whether it matches the requirement.
+ function($) {
var animate = function(target, position) {
target.css('display', 'inline-block');
if (position === 'right-to-left' || position === 'right-to-right' ) {
target.css('right', '500px');
target.css('left','' );
target.animate({
opacity: 1,
right: '0px'
}, 500);
}
else if (position === 'left-to-right' || position=="left-to-left") {
target.css('left', '500px');
target.css('right', '');
target.animate({
opacity: 1,
left: '0px'
}, 500);
}
};
var disanimate = function(target, position) {
if (position === 'right-to-left' || position ==="left-to-left") {
target.css('left','' );
target.animate({
opacity: 0,
right: '245px'
}, 500);
}
else if (position === 'left-to-right' || position === "right-to-right") {
target.css('left','' );
target.animate({
opacity: 0,
left: '245px'
}, 500);
}
};
$(window).on('load', function() {
var target = $('[data-animation-time]');
var animationInitial = target.data('animation-time')[0];
var animationFinal = target.data('animation-time')[1];
var position = target.data('animation-position');
var shown = false;
$('.container').scroll(function() {
var scroll = $(this).scrollTop();
if (!shown && (animationInitial < scroll && animationFinal > scroll)) {
console.log("animate")
animate(target, position);
shown = true;
}
else if (shown && (animationFinal < scroll || animationInitial > scroll)) {
console.log("disanimate")
disanimate(target, position);
shown = false;
if (position.split("-")[0] == position.split("-")[2])
position = anti(position);
}
});
});
}(jQuery);
var anti = function (position){
if (position == "left-to-left")
return "right-to-right"
else
return "left-to-left"
}
Css :- it was right 500px. so intital position of card is fixed. i changed it to dynamic based on input and whenever you are adding right(css) you have to make sure left(css) is null because if you give both right and left it will get confused during animation
left-to-right & right-to-left both have their initial and final position same.. so no need of extra fittings.. so it will work even if you come from down
left-to-left & right-to-right don't have have their initial and final position same .. so left-to-left will become right-to-right in reverse loop. i did that using anti function
Related
I have a table on the right of my page( with id="efficacia"). I wrote this JS script in order to shift left/right clicking on it
JavaScript
$("#efficacia").click(function() {
var posizione = $("#efficacia").position();
if(posizione.right != 0) {
$(this).animate({
right: '0'
}, 1000);
} else {
$(this).animate({
right: '-202'
}, 1000);
}
});
CSS
#efficacia {
position: fixed;
right: -202px;
top: 200px;
cursor: pointer;
z-index: 100;
}
My script works well for the first "click", then when I click again it does not shitf on the right of 202px. It looks like that function does not enter in else statemet.
position().right does not exist. Only top and left.
http://api.jquery.com/position/
Base your condition on left attribute and it will work
position doesn't return a right property.
You can get the right css property so:
$("#efficacia").click(function() {
var right = parseInt($(this).css('right'));
if(right != 0) {
$(this).animate({
right: '0'
}, 1000);
} else {
$(this).animate({
right: '202'
}, 1000);
}
});
See the DEMO.
If you want get position of all corners then you can use getBoundingClientRect(). It will returns bottom, right, left, top, width and height of your div. But, of course, it will return values that starts from left corner.
var boundingBox = $(this).get(0).getBoundingClientRect();
console.log(boundingBox.right);
Read about getBoundingClientRect()
There's an error in your code at right: '-202'. You have to specify right: '-202px'.
Here's the updated code:
$("#efficacia").click(function() {
var right = $(this).css('right');
if(right != "0px") {
$(this).animate({
right: '0px'
}, 1000);
} else {
$(this).animate({
right: '-202px'
}, 1000);
}
});
That's it
jQuery.position() doesn't return value for style.right. It returns only
Object{top: somVal, left: somVal}
so if u want to get the value of right then get it from style attribute
Eg-
$("#efficacia").click(function() {
// var posizione = $("#efficacia").position();//here right is undefined
var right=this.style.right.replace("px", "") * 1;//fetch value of right from style
if(right != 0) {
$(this).animate({
right: '0'
}, 1000);
} else {
$(this).animate({
right: '202'
}, 1000);
}
});
This is my code:
http://jsfiddle.net/KCb5z/8/embedded/result/
http://jsfiddle.net/KCb5z/8/
$(function () {
var $select = $('#select');
var $window = $(window);
var isFixed = false;
var init = $select.length ? $select.offset().top : 0;
$window.scroll(function () {
var currentScrollTop = $window.scrollTop();
if (currentScrollTop > init && isFixed === false) {
isFixed = true;
$select.css({
top: 0,
position: 'fixed'
});
} else if (currentScrollTop <= init && isFixed === true) {
isFixed = false;
$select.css('position', 'relative');
}
});
$(".nav").click(function (e) {
e.preventDefault();
var divId = $(this).attr('href');
$('body').animate({
scrollTop: $(divId).offset().top - $select.height()
}, 500);
});
});
The issue is when I scroll past the yellow bar it changes its CSS from relative to fixed. This means the website is now less tall and it drags all the content up, causing a kind of glitching effect.
It's almost like I need a containing div for the yellow bar which remains to keep that height, or insert some sort of div to keep the website height the same if the bar is docked or not.
Can anyone show me please how this might be implemented?
When the position is set to fixed, add padding to the top of the body to accommodate it. Similarly, remove the padding when the element is un-fixed:
if (currentScrollTop > init && isFixed === false) {
isFixed = true;
$select.css({
top: 0,
position: 'fixed'
});
$('body').css('padding-top', $select.height());
}
else if (currentScrollTop <= init && isFixed === true) {
isFixed = false;
$select.css('position', 'relative');
$('body').css('padding-top', 0);
}
Example fiddle
Note, the padding-top can be set on any element above the one to be fixed if required. I just used body as it was the most convenient for an example.
Hey so i was trying to get my navigation to animate down after a certain div has passed but its not working properly. not sure why. it works when sliding down although a bit buggy(sometimes there seems to be a delay before it slides down and other times it slides down properly immediately). It also does not slide up it justs removes it self.
what am i doing wrong?
here is my code:
$(window).scroll(function () {
targetScroll = $('#scroll_verder').position().top,
currentScroll = $('html').scrollTop() || $('body').scrollTop();
if(currentScroll>=targetScroll){
$('.navbar').addClass('show-menu').animate({ top: '0px' });
}
else {
$('.navbar').stop();
$('.navbar').removeClass('show-menu');
$('.navbar').animate({ top: '-50px' });
}
});
Had a look at your code on the link you posted. This should do the trick:
var reachedTarget = false; // Prevent animation collisions with this
var targetScroll = $('#scroll_verder').position().top;
$(window).scroll(function () {
var currentScroll = $('html').scrollTop() || $('body').scrollTop();
if ( currentScroll >= targetScroll ) {
if ( !reachedTarget ) {
$('.navbar').stop();
$('.navbar').addClass('show-menu').animate({ top: '0px' });
}
reachedTarget = true;
} else{
if ( reachedTarget ) {
$('.navbar').stop();
$('.navbar').removeClass('show-menu').animate({ top: '-50px' });
}
reachedTarget = false;
}
});
EDIT: In CSS (to make sure initial position is correct):
.navbar.show-menu {
z-index: 999;
display: block;
top : -50px;
}
How can I change the following menu code to open/close when the mouse hovers, instead of when it is clicked on?
var w = 0;
$('.slide').children().each(function () {
w += $(this).outerWidth();
});
$('.outer').width(w + 5);
$('.wrap').width(w);
$('.slide').css('left', w);
$('.open').toggle(function () {
$('.slide').stop().animate({
left: 0
});
$(this).html('close');
}, function () {
$('.slide').stop().animate({
left: w
});
$(this).html('open');
});
Please check this Demo
In Fiddle, you can see the animation works on click. I need to make it work on hover. Can you help with this ?
Use .hover() api
Try this
$('.open').hover(function () {
instead of
$('.open').toggle(function () {
Just
$('.open').toggle(function() {
$('.slide').stop().animate({
left: 0
});
$(this).html('close');
}
in this part just replace toggle with hover
Try using $('.wrap').hover. If $('.open').hover, you will not able to click the nav items.
Also, you can create another wrapper to just wrap div.outer and a.open only
$('.wrap').hover(function() {
$('.slide').stop().animate({
left : 0
});
//this is the .wrap right now
$(this).find('a.open').html('close');
}, function() {
$('.slide').stop().animate({
left : w
});
//this is the .wrap right now
$(this).find('a.open').html('open');
});
http://jsfiddle.net/rooseve/42sWB/2/
$('.open').on('mouseenter mouseleave', function(e) {
if(e.type === 'mouseleave') {
$('.slide').stop().animate({
left: w
});
$(this).html('open');
} else {
$('.slide').stop().animate({
left: 0
});
$(this).html('close');
}
});
var w = 0;
var isVisible = false;
$('.slide').children().each(function() {
w += $(this).outerWidth();
});
$('.outer').width(w+5);
$('.wrap').width(w);
$('.slide').css('left', w);
$('.open').on("mouseover", function() {
if(isVisible == false) {
$('.slide').stop().animate({
left: 0
});
$(this).html('close');
isVisible = true;
}
else {
$('.slide').stop().animate({
left: w
});
$(this).html('open');
isVisible = false;
}
});
Firstly, when you hover the element - the div will be visible, until you hover the element for the second time.
Demo: http://jsfiddle.net/42sWB/3/
All the documentation talks about when the waypoint reaches the top of the viewport, but I would like the trigger to happen when any part of the waypoint is in the center of the viewport.
This code works fairly well if I'm scrolling down, but when I scroll up it doesn't work, obvoiusly.
$('.section').waypoint(function(direction) {
highlight('#' + this.id);
}, {
context: '#scroll',
offset: function (direction) {
return $(this).height();
}
});
I tried the code below and a couple variants and it never even hits either of the return statements.
$('.section').waypoint(function(direction) {
highlight('#' + this.id);
}, {
context: '#scroll',
offset: function (direction) {
if (direction == 'down') {
return -$(this).height();
} else {
return 0;
}
}
});
So now I'm trying this, based on waypoint examples, but $active.id doesn't work like this.id so my function "highlight" fails.
$('.section').waypoint(function (direction) {
var $active = $(this);
if (direction == 'down') {
$active = $active.prev();
}
if (!$active.length) {
$active = $(this);
}
highlight($active.id);
}, {
context: '#scroll',
offset: function (direction) {
return $(this).height();
}
});
The offset option does not take a direction parameter. I'd love to know if you got that from somewhere in the documentation because if there's a section using direction in an offset function, it's a mistake.
You can tell a waypoint to trigger when the top of the element hits the middle of the viewport by using a % offset:
offset: '50%'
If you need to have a different offset when scrolling up versus scrolling down, this is best accomplished by creating two different waypoints:
var $things = $('.thing');
$things.waypoint(function(direction) {
if (direction === 'down') {
// do stuff
}
}, { offset: '50%' });
$things.waypoint(function(direction) {
if (direction === 'up') {
// do stuff
}
}, {
offset: function() {
// This is the calculation that would give you
// "bottom of element hits middle of window"
return $.waypoints('viewportHeight') / 2 - $(this).outerHeight();
}
});