Hover direction according to container size - javascript

I would like to alter the hover direction based on the container size, if there's not enough space on the container to show the hover to the right, it should then show on the left.
See fiddle for details:
http://jsfiddle.net/jHgkp/3/
I use hoverIntent, but FULL details are on the Fiddle above:
$(document).ready(function(){
$(".discover").hoverIntent({
over: makeVisible,
out: makeInvisible,
timeout: 200
});
}); // close document.ready
function makeVisible() {
$(this).find('ul').fadeIn(100);}
function makeInvisible() {
$(this).find('ul').fadeOut(300);}

There are a few approches.
1) You can style the tooltip on the third element to show on the left side (not dynamic)
2) You can take the element offest().left + element.width + the tooltip width and compare it with the holder width. (dynamic)
3) Yo can the the tooltip offest + width and directly compare it to the holder width. (dynamic)
It depends what exactly you want...
This is the only JS added.
var holderWidth = $('.container').outerWidth();
and
//where 260 is left 150 + width 110
var pos = $(this).offset().left + 260
if(holderWidth < pos){
$(this).addClass('leftPos');
}else{
$(this).removeClass('leftPos');
}
and 1 line of css:
.leftPos ul { left: auto; right: 150px; }
Demo

Related

How to dynamically change the position of an absolute tooltip base on the target element

I am trying to make a tooltip which basically shows a table (in my example below I used a large amount of text).
However I've wanted to change the position of the tooltip when you hover on the target element that is nearly at the corner of the screen.
Here is the Fiddle
$("strong").on("mouseover", function(){
var $this = $(this),
strongText = $this.text();
$tooltipContainer.show();
$tooltipContainer.append('<span>'+ strongText + '</span>');
}).on("mousemove", function(mousePos){...
You can change your mousemove code a little to update top position if overlap is there like below. Check demo - Fiddle
on("mousemove", function(mousePos){
var overlap = mousePos.pageY + posSrollY + $tooltipContainer.height() - $(window).height() - $(window).scrollTop();
$tooltipContainer.css({
left: mousePos.pageX,
top: mousePos.pageY + posSrollY - ( overlap > 0 && overlap )
});
})

How to use jQuery scroll to change the height of an element?

I have a HTML class navigation with the initial height of 100px and min-height is 40px. I want to change the height of the class, based on the scroll (if scroll down than size will decrease and if scroll up than size will increase). I use the following code and it's working perfectly.
$(window).scroll( function() {
if( $('.navigation').offset().top > 50 )
{
$('.navigation').css({
'height' : '40px',
'background' : 'rgba(37, 37, 37, 0.9)'
});
} else {
$('.navigation').css({
'height' : '100px',
'background' : '#b24926'
});
}
});
If I press the keyboard down arrow key two times than navigation class moved from original height to minimum height and if the up arrow key press two times than navigation class moved from minimum height to original height.
But I want to make the scroll more smooth (like 4-5 up or down key presses to reach from one height to another).
For example: initial height is: 100px and minimum height is 30px. Now:
if down arrow key is pressed/mouse wheel is move down one time than height will be 85px, if again down arrow is pressed height will be 70px and so on. That means for each down arrow key is pressed/mouse wheel is move down than height will decrease by 15-20px and for each up arrow key is pressed/mouse wheel is move up, height will increase by 15-20px.
Can anyone tell me how can I do that (without using third party api).
Thanks
You can use simple percent calculation to update height
var limitForMinimalHeight = 400; //after this distance navigation will be minimal height
var maxHeight = 100;
var minHeight = 40;
$(window).scroll( function() {
var screenTop = $(document).scrollTop();
var achievedDistancePercent = Math.min(screenTop*100/limitForMinimalHeight, 100);
var amounToAdd = ((maxHeight - minHeight) * (100 - achievedDistancePercent))/100;
var newHeight = minHeight + amounToAdd;
$('.navigation').height(newHeight);
});
You can test it on JSFiddle
$(document).scroll(function() {
if($(this).scrollTop()>100) {
$('.selector').addClass('scrolled');
}
if($(this).scrollTop()<40) {
$('.selector').removeClass('scrolled');
}
});

Responsive margin resizing

I want to have my elements resize their margins equally so that they fill the page. I tried turning the page width into a value using jquery but that didn't work.
var margen = $(window).width()
$(document).ready(function () {
$('#FixedMenu *').animate({
'margin-left': 'margen/6'
});
});
http://jsfiddle.net/clarinetking/2PGZS/40/
I make little update to your jsFiddle, you can see it here:
jsFiddle
What i change is this:
1.
You found width of screen:
var screenWidth = $(window).width();
2.
You found total width of child elements of your fixed menu
var widthOfChilds = 0;
$('#FixedMenu > *').each(function() {
widthOfChilds += $(this).outerWidth( true );
});
3.
You take off total width of child elements from screen size and you will get "free"width around child elements.
There are six of them, but you need space after last one from right, so you divide "free"width by number of childs + 1
var newmargin = (screenWidth - widthOfChilds)/7;
$('#FixedMenu *').animate({
'margin-left': newmargin
});
I hope it helped! :)

element.height returns visible height - I want total?

So apparently this is only happening to me - and I can't think why but if it works, I'm happy :)
I have a full screen slideshow and I have created a function that will vertically center any images that are too large.
function fixImages(){
maxheight = $('.index-slide-container').height();
$('.index-slide-container img').each( function(index, ele){
if (ele.height > maxheight){
offset = ( maxheight - ele.height ) / 2;
$(ele).css('top', offset + 'px');
}
});
}
fixImages();
However, ele.height returns the height of the visible part of the image (the height of it's container, as it has overflow:hidden, even though when I console.log(ele) and expand the element, 'height' is clearly the correct value.
I have also tried $(ele).height(), $(ele).css('height'), $(ele).outerHeight() and ele.clientHeight; all of which return the same.
Thanks
I made some tests, and $('img').height(); is giving me the right height of the picture.
If you wish to center the picture vertically why don't you use the absolute positioning with css like this for example :
.index-slide-container img {
position:absolute;
top:50%;
}
And than, you could set the negative margin programmatically with jQuery :
$('.index-slide-container img').each( function(i, e){
var height = $(e).height() / 2;
$(e).css({'margin-top':'-'+height});
});

Scrollpane on the bottom, css is hacky, javascript is hard

I want to put a bar on the bottom of my page containing a varying number of pictures, which (if wider than the page) can be scrolled left and right.
The page width is varying, and I want the pane to be 100% in width.
I was trying to do a trick by letting the middle div overflow and animate it's position with jquery.animate().
Like this:
Here is a fiddle without the js: http://jsfiddle.net/SoonDead/DdPtv/7/
The problems are:
without declaring a large width to the items holder it will not overflow horizontally but vertically. Is this a good hack? (see the width: 9000px in the fiddle)
I only want to scroll the middle pane if it makes sense. For this I need to calculate the width of the overflowing items box (which should be the sum of the items' width inside), and the container of it with the overflow: hidden attribute. (this should be the width of the browser window minus the left and right buttons).
Is there a way to calculate the length of something in js without counting all of it's childrens length manually and sum it up?
Is there a way to get the width of the browser window? Is there a way to get a callback when the window is resized? I need to correct the panes position if the window suddenly widens (and the items are in a position that should not be allowed)
Since the window's width can vary I need to calculate on the fly if I can scroll left or right.
Can you help me with the javascript?
UPDATE: I have a followup question for this one: Scroll a div vertically to a desired position using jQuery Please help me solve that one too.
Use white-space:nowrap on the item container and display:inline or display:inline-block to prevent the items from wrapping and to not need to calculate or set an explicit width.
Edit:: Here's a live working demo: http://jsfiddle.net/vhvzq/2/
HTML
<div class="hscroll">
<ol>
<li>...</li>
<li>...</li>
</ol>
<button class="left"><</button>
<button class="right">></button>
</div>
CSS
.hscroll { white-space:nowrap; position:relative }
.hscroll ol { overflow:hidden; margin:0; padding:0 }
.hscroll li { list-style-type:none; display:inline-block; vertical-align:middle }
.hscroll button { position:absolute; height:100%; top:0; width:2em }
.hscroll .left { left:0 }
.hscroll .right { right:0 }
JavaScript (using jQuery)
$('.hscroll').each(function(){
var $this = $(this);
var scroller = $this.find('ol')[0];
var timer,offset=15;
function scrollLeft(){ scroller.scrollLeft -= offset; }
function scrollRight(){ scroller.scrollLeft += offset; }
function clearTimer(){ clearInterval(timer); }
$this.find('.left').click(scrollLeft).mousedown(function(){
timer = setInterval(scrollLeft,20);
}).mouseup(clearTimer);
$this.find('.right').click(scrollRight).mousedown(function(){
timer = setInterval(scrollRight,20);
}).mouseup(clearTimer);
});
Thanks Phrogz for this part -- give the image container the white-space: nowrap; and display: inline-block;.
You can calculate the width without having to calculate the width of the children every time but you will need to calculate the width of the children once.
//global variables
var currentWidth = 0;
var slideDistance = 0;
var totalSize = 0;
var dispWidth = (winWidth / 2); //this should get you the middle of the page -- see below
var spacing = 6; //padding or margins around the image element
$(Document).Ready(function() {
$("#Gallery li").each(function () {
totalSize = totalSize + parseFloat($(this).children().attr("width"));// my images are wrapped in a list so I parse each li and get it's child
});
totalSpacing = (($("#Gallery li").siblings().length - 1) * spacing); //handles the margins between pictures
currentWidth = (parseFloat($("#Gallery li.pictureSelected").children().attr("width")) + spacing);
maxLeftScroll = (dispWidth - (totalSize + totalSpacing)); //determines how far left you can scroll
});
function NextImage() {
currentWidth = currentWidth + (parseFloat($("#Gallery li.pictureSelected").next().children().attr("width")) + spacing); //gets the current width plus the width of the next image plus spacing.
slideDistance = (dispWidth - currentWidth)
$("#Gallery").animate({ left: slideDistance }, 700);
}
There is a way to get the browser window with in javascript (jQuery example).
and there is a way to catch the resize event.
var winWidth = $(window).width()
if (winWidth == null) {
winWidth = 50;
}
$(window).resize(function () {
var winNewWidth = $(window).width();
if (winWidth != winNewWidth) {
window.clearTimeout(timerID);
timerID = window.setInterval(function () { resizeWindow(false); }, 100);
}
winWidth = winNewWidth;
});
On my gallery there's actually quite a bit more but this should get you pointed in the right direction.
You need to change your #items from
#items
{
float: left;
background: yellow;
width: 9000px;
}
to
#items {
background: yellow;
}
Then calculate the width very easily with jQuery
// #items width is calculated as the number of child .item elements multiplied by their outerWidth (width+padding+border)
$("#items").width(
$(".item").length * $(".item").outerWidth()
);
and simply declare click events for the #left and #right elements
$("#left").click(function() {
$("#middle").animate({
scrollLeft: "-=50px"
}, 'fast');
});
$("#right").click(function() {
$("#middle").animate({
scrollLeft: "+=50px"
}, 'fast');
});
jsFiddle link here
EDIT
I overlooked that detail about the varying image widths. Here is the correct way to calculate the total width
var totalWidth = 0;
$(".item").each(function(index, value) {
totalWidth += $(value).outerWidth();
});
$("#items").width(totalWidth);

Categories

Resources