I have a list of items that on hover show a few options below each item in a div. I would like to show these options only when the user hovers on the list item and when they move away reclaim the space that the div occupies. Hence I've used display: none; on the div and on hover set it to display: block;.
A demo of this is here
This works as intended but the transition is way too fast and gives a sort of jarring effect. Is there a nicer way to fade in and out this div (preferably with CSS only)? Or do I need to resort to using JavaScript for this? (I've developed the app without jQuery so far and would prefer not having to include it only for this).
Also the height of the list items vary so using an opacity transition from 0 to some height is not a viable option.
One can not transition on display property and property with auto value.
This can be achieved by using max-height property.
Instead of display: none, use max-height: 0 and instead of display: block, use max-height: <some value which you expect to be maximum>.
Please note the caveat, the transition speed depends on the value of the max-height.
For example, if the computed height of container1 is 200px and of container2 is 400px; setting the max-height to 500px from 0 will exhibit different transition speed for both the container for the same timer function.
Hope this helps, Working code here
HTML:
<div class="item">
Item 1.....more text here
<div class="actions">
Opt 1 Opt 2
</div>
</div>
<div class="item">
Item 2
<div class="actions">
Opt 1 Opt 2
</div>
</div>
CSS:
.actions{display:none;}
.item{margin:30px;}
jQuery:
$(document).on({
mouseenter: function () {
$(this).children('.actions').stop().fadeIn('fast');
},
mouseleave: function () {
$(this).children('.actions').stop().fadeOut('fast');
}
}, '.item');
Related
guys, I wrote a code that whenever I click on a button (that plus sign) my input should slide but as you see my running code whenever I click that button first it start sliding the input until it reaches the placeholder then it starts sliding placeholder as a separate element they don't slide together so I wanted to know is there any way to fix this?that only input slides and placeholder slide with it.
HTML:
<div id="container">
<h1>LIST<i class="fa fa-plus" aria-hidden="true"></i></h1>
<input type="text" placeholder="Add New Todo"></div>
jQuery
var plusSign = $("h1 i")
plusSign.on("click",function(event){
$('input:text').slideToggle(3000);
})
https://jsfiddle.net/Ghost007D/aduLw0u3/1/
The simplest way is to modify your input to:
border: 0; /* change */
display: block; /* add this */
and to prevent animation buildups in jQuery - use .stop() like:
$('input:text').stop().slideToggle(3000);
and additionally to toggle your icon you could do:
plusSign.toggleClass("fa-plus fa-minus"); // if needed
jsFiddle DEMO
the proper way would be to create a wrapper around the input and animate that element instead; but if you're happy with the results and it's tested across browsers - you can keep it like this.
To explain the issue you had:
.slideToggle() does pretty much:
animate height:
if element has no height set it to display: none;
but if your element has borders - those are not animated, and will disappear as soon the element is set to display: none; creating the undesired jump.
Another issue is when animating inline elements - where line-height can interfere - therefore setting to inline-block or block helps - a lot.
I would like to make the transition of the menu to be smooth. The problem is when you click the arrows, the 2nd div will show on the bottom of the 1st div, making it not smooth to look at. pls see below for my code:
Pls see my code here:
http://www.codeply.com/go/mdMPOkmFVH
in your code you need to do some basic change in CSS, your CSS should be as follows
.btn-arrow {
display: inline-block;
text-align: center;
}
.effects-list {
text-align: center;
}
.col-xs-4 {
min-height:20px;
}
Here you need to set minimum height 20px for class .col-xs-4, The reason behind this is the jquery function needs to set sliding element to have position absolute, and you were setting it to relative by force. and if all child elements in divs are absolute elements, then absolute elements won't acquire it's space in parent div and that is why it will make parent div's acquired content will be empty. so it will treat it as empty div and set it's height as 0px, and won't show anything in the div... so here we are specifying it's minimum height to solve our issue.
Another thing that we could have done is adding white space to the parent div
e.g.
<div class="col-xs-4" id="effects_menu"> </div>
Assuming I have 2 elements on a responsive design like this:
<div id="container">
<div class="first"></div>
<div class="second"></div>
</div>
both of them with style contains:
width: auto;
display: inline-block;
float: left;
And because I'm expecting different screen sizes to view page, so, according to screen size, sometimes they will be rendered/displayed on the same row, and sometimes they will not!, the second DIV will be moved to a separate row.
So, I'm wondering, how can I check if they are on the same line with JavaScript?
Thank you
"on the same line" would require inline elements or floating block elements of the exact same height. DIVs are block elements by default. So either use <span> tags instead of <div>, or add display: inline-block;to the CSS rule of those DIVs
ADDITION after EDIT OF QUESTION:
width: auto for a <div> means 100% of the parent element (in this case full width). As I wrote: If you have blocks, use display: inline-block; in their CSS. If you want them to have the same height, put them into a common container DIV (which you already have) and apply the following CSS:
#container {
display: table;
}
.first, .second {
display: table-cell;
width: 50%;
}
Aha (edited question), Javascript: Well, read out the DIV widths, add them and compare the result to the (read-out) container width.
You can use the element bounding boxes and check for overlap:
var rect1 = $('.first')[0].getBoundingClientRect();
var rect2 = $('.second')[0].getBoundingClientRect();
var overlaps = rect1.top <= rect2.bottom && rect2.top <= rect1.bottom;
This checks for any overlap which will probably be sufficient for your use. I used jQuery to get the elements but you can use pure js in the same way, it would just be a bit more verbose.
There is no concept of line on a page. You can check the x and y position of any element in the window and then decide if that meets whatever criteria you have for "on the same line".
By default, a div is the full width of a window so the two divs inside your container in this HTML:
<div id="container">
<div class="first"></div>
<div class="second"></div>
</div>
will be one above the other unless there is some other CSS you have not disclosed that controls the layout to allow them to be in the same row. If they are indeed width: auto and don't have any other layout rules affecting this, then they will each be full width and thus first will be above second in the layout stream. They would never be "on the same line" by any typical definition of that phrase.
Feel free to try it out here: https://jsfiddle.net/jfriend00/y0k7hLr8/ by resizing the right pane to any width you want. In all cases, the first will stay on top of the second.
If, on the other hand, you allow the div elements to have a different type of layout such as let them be display: inline-block and define a width for them, then the layout engine will fit as many on a given row as possible like here: https://jsfiddle.net/jfriend00/229rs97p/
Something tells me display: flex might help you in this. Read https://css-tricks.com/snippets/css/a-guide-to-flexbox/ for more info.
I know that transitions for the display property don't work, but I was wondering if there is a work around for this. I tried the visibility property but it doesn't seem to suit the task I am trying to achieve, or maybe I did it wrong. As you can see, I am displaying different text when you hover over the anchor tag by setting the span to display: none;. Animating the opacity won't be a good solution because the element being animated will still occupy the space it held. Is there maybe a workaround in Javascript or jQuery? Here is the code. I left out the transition property and its prefixes for brevity. The animation I want is for it to switch slowly between the two, i.e. One fades out, the other fades in. There doesn't have to be an overlap, but it doesn't matter if there is.
HTML
<div class="navbar">
<ul>
<li><a id="menu1" href="index.html"><i class="fa fa-home"></i><span> Home</span><span class="show"> Welcome Home</span></a></li>
</ul>
</div>
CSS
.show, a:hover span {
display: none;
}
a:hover .show {
display: inline;
}
You could try using jquery slide transitions when you hover over the anchor element. Check out http://api.jquery.com/slideToggle/
An example is
$("#menu1").hover(function () { $("#menu1 span").slideToggle("slow"); }, function(){ $("#menu1 span").slideToggle("slow"); });
You can try that on hover the object floats and animate the opacity. Making it float wont make him occupy the space.
Cheers J
I have some content displayed as a list within a div. By default, the div is hidden, but becomes visible once it's parent has the class ".open":
<li class="dropdown">
<a>Options</a>
<div class="dropdown-menu">
<div class="menu-scroll">
<ul>
<li>...</li>
<li>...</li>
<li>...</li>
</ul>
</div>
</div>
</li>
What happens is when I click the anchor within the list item, the list item receives the ".open" class, which enables displaying the ".dropdown-menu" . Now my problem is that I want that menu to have a max-height of say 200px, after which it should initialize the scroll. Considering that each of it's list items are 50px tall, we would have these scennarios:
2 list items, height of 100px, no scroll
3 list items, height of 150px, no scroll
4 list items, height of 200px, no scroll
5+ list items, height of over 200px and SCROLL
This means I can't set a fixed height for .menu-scroll, since I want it to scale until reaching that height. What I do is set:
max-height: 200px;
height: auto;
It works perfect the first time I trigger the dropdowns but afterwards it renders everything wrong, like this:
What I've tried:
Initializing jScrollpane when clicking the anchor that toggles the .open class.
Initializing jScrollpane on document ready and only reinitializing the object when clicking the same anchor.
The results are the same everytime, as shown in the illustration above. I've searched the documentation, FAQ, StackOverflow, Google Groups but to no avail. Does anyone have any clues on this?
EDIT: This is the code I use to trigger the dropdown and initialize the scroll:
$('.dropdown-toggle').on("click", function() {
$(this).parent('.dropdown').toggleClass('open').find('.dropdown-menu').jScrollPane();
});
What the .open class does is add
.dropdown.open .dropdown-menu {
display: block;
}
to the otherwise hidden .dropdown-menu:
.dropdown.dropdown-menu {
display: none;
}
if you get it right on first trigger and then it fails after that implies you have to check your script. Can you post your script here?