Altering one element's position with the hover state of another - css

I have a css triangle positioned under one of two buttons that indicates the text below it is associated with that button. When I hover over the button next to it, I would like to move that triangle to under the second button.
My triangle is a an empty div with the following styling:
.nubbin {
width: 0;
height: 0;
border-left: 2em solid transparent;
border-right: 2em solid transparent;
border-bottom: 2em solid #435C6E;
margin-left: calc(50% - 10em);
}
My buttons have classes of, "report and class". What I've tried is:
.chat:hover~.nubbing {
margin-left: calc(50% + 10em);
}
and
.chat:hover+.nubbing {
margin-left: calc(50% + 10em);
}
What am I doing wrong?

Like ralph.m mentions, you're better off the using ::after pseudo element.
Check out this example:
http://jsfiddle.net/scottmey/PhZ7x/2/
Hopefully this points you in the right direction.
.comment {
position: relative;
display: inline-block;
width: 620px;
vertical-align: top;
padding: 3px 10px;
background: #435C6E;
margin-bottom: 15px;
margin-left: 10px;
}
.comment:hover:after {
content: "";
position: absolute;
top: 5px;
left: -15px;
border-style: solid;
border-width: 10px 15px 10px 0;
border-color: transparent #435C6E;
display: block;
width: 0;
z-index: 1;
}

Related

How to add "arrow-down" triangle with CSS to responsive tabs

I'm using Responsive tabs by petelove666 and I have a small detail I'd like to add but it seems I can not get it to work.
I would like a arrow-down formed by triangle at the middle of active tab.
I tried to change CSS to
.responsive-tabs__list__item--active{
background: white;
color: #3E4649;
/*border-bottom: 2px solid #F39114;*/
position: absolute;
margin-left: -50px;
width: 0;
height: 0;
border-top: solid 20px #F39114;
border-left: solid 5px transparent;
border-right: solid 5px transparent;
}
But it doesn't work at all.
Here is my fiddle https://jsfiddle.net/dvx8nw15/. And the goal is to have a down arrow at the middle of active tab as seen from the attached picture with blue color:
All you need to do is to add an absolutely centered triangle to list__item:
.responsive-tabs__list__item { position: relative }
.responsive-tabs__list__item--active:after {
content: '';
height: 0;
width: 0;
border-left: 10px solid transparent;
border-right: 10px solid transparent;
border-top: 10px solid black;
left: 0;
right: 0;
top: 100%;
margin: auto;
position: absolute;
display: block;
}
And the updated fiddle
Remove the list-style-type from the list items and add a div that will be your arrow. The triangle trick is to set an element with size 0 but to set a border, the top border in that case is actually a triangle, so when you give it a color and set the other side to be transparent you'll get a triangle.
li{
list-style-type:none;
display: flex;
align-items: center;
}
.arrow{
width: 0px;
height: 0px;
border: 5px solid transparent;
border-top-color: #F39114;
margin-top: 0.2em;
margin-right: 0.2em;
}
<ul>
<li><div class="arrow"></div>One</li>
<li><div class="arrow"></div>Two</li>
<li><div class="arrow"></div>Three</li>
</ul>
UPDATE
Adding a fiddle without adding a div and using :before pseudo element instead
Example with your code
You need to add class arrow to each li you want to style or otherwise add it to the container once and then set .arrow li instead of li.arrow
Second example - better since you don't need to style each li
Just add position: relative to your li.responsive-tabs__list__item. And then use a pseudoclass to print the arrow in your active item with this code:
.responsive-tabs__list__item--active:after {
content: '';
position: absolute;
bottom: -10px;
left: 50%;
width: 20px;
height: 20px;
background: black;
margin-left: -10px;
transform: rotate(45deg);
z-index: -1;
}
You can find an example in this fiddle

CSS for Line Arrow

Does anyone have any pointers on how I can achieve the following 2 effects (red color) using pure CSS?
I am not asking for entire code but if anybody can guide me in proper direction, that would really be great.
Thanks in advance.
For second effect you should create for image's container two pseudo-elements :before and :after with border-radius set to desired value. Element :before you should position to left bottom side of container and the element :after you should position to right bottom side. You should also specify widths for each pseudo-element (for example: 50% and 50%, 60% and 40% etc.).
Code for the second effect:
.image {
position: relative;
width: 350px;
}
img {
display: block;
padding: 0;
margin: 0;
}
.image:before {
content: '';
display: inline-block;
background: rgba(255, 0, 0, .5);
width: 30%;
height: 120px;
position: absolute;
bottom: 0;
left: 0;
border-top-right-radius: 15px;
}
.image:after {
content: '';
display: inline-block;
background: rgba(255, 0, 0, .5);
width: 70%;
height: 120px;
position: absolute;
bottom: 0;
right: 0;
border-top-left-radius: 15px;
}
<div class="image">
<img src="http://placehold.it/350x350">
</div>
OK, here is a suggestion for the proper direction.
The lower red panel looks to me like two adjoining rectangles. You need to set the widths appropriately, and then for each rectangle round off one corner using border-radius: a b c d.
The effect looks to me like two of effect number 2. The red one, and then the same in white, possibly with a z-index to make sure that it (partly) covers the other one.
I trust you already know how to make the red translucent, either by using opacity or setting the colour using rgba.
I hope that helps.
You have to use the pseudo elements :after & :before to achieve the bulge in the otherwise straight div.
You may try something like this:
div {
height: 30px;
width: 200px;
background-color: red;
position: relative;
}
div:after {
content: '';
position: absolute;
left: 0;
right: 0;
width: 0px;
height: 0;
border-left: 10px solid transparent;
border-right: 10px solid transparent;
border-top: 10px solid #fff;
margin: auto;
}
div:before {
content: '';
position: absolute;
left: 0;
right: 0;
bottom: -8px;
width: 0px;
height: 0;
border-left: 12px solid transparent;
border-right: 12px solid transparent;
border-top: 10px solid red;
margin: auto;
}
<div></div>
Since you didn't provide a fiddle so use below solution as a guide. CSS will produces curved edges that you join together to produce desired results.
div.arrow-curved {
width: 120px;
height: 80px;
background: red;
position: relative;
-moz-border-radius: 10px;
-webkit-border-radius: 10px;
border-radius: 10px;
}
div.arrow-curved:before {
content:"";
position: absolute;
right: 100%;
top: 26px;
width: 0;
height: 0;
border-top: 13px solid transparent;
border-right: 26px solid red;
border-bottom: 13px solid transparent;
}
For more reference for CSS shapes: https://css-tricks.com/examples/ShapesOfCSS/

Overflow property causes part of code to disappear?

I'm trying to put a scrollbar inside my div tag yet when I do, the arrow on the side of it disappears. Is there are way to fix this?
Live preview here.
The bubble is supposed to look like this, but with a scrollbar in it of course.
.bubble {
background-color: #ffffff;
border: 1px solid #000000;
border-radius: 8px;
width: 240px;
height: 250px;
padding: 10px;
margin: 100px auto 100px auto;
position: relative;
overflow: scroll;
}
.bubble:before {
content: "";
position: absolute;
left: -25px;
top: 24px;
bottom: auto;
border-style: solid;
border-width: 12px 24px 12px 0px;
border-color: transparent #000000;
}
.bubble:after {
content: "";
position: absolute;
left: -23px;
top: 25px;
bottom: auto;
border-style: solid;
border-width: 11px 23px 11px 0px;
border-color: transparent #ffffff;
display: block;
width : 0px;
}
Put the below content div inside bubble div.
Put content of bubble div inside the below div and add the style..
<div class="content"></div>
Inside style :
.content{
height:70px;
overflow-y:scroll;}
HOPE IT HELPS
Try putting the content of the bubble inside a div, and put overflow: scroll on that child div, rather than on the entire bubble.

Offset border effect in pure css

I am trying to create an offset border effect. Can this be done with pure css.
These are buttons so will be different sizes and colours.
I use pseudo-element :after to create offset border effect.
body {
background: black;
padding: 30px;
}
div {
background: white;
height: 75px;
width: 175px;
position: relative;
}
div:after {
content: '';
background: transparent;
border: 1px solid white;
top: 7px;
right: 7px;
bottom: -7px;
left: -7px;
position: absolute;
z-index: -1;
}
<div></div>
Update
As web-tiki pointed out in comments on this answer, you can achieve the entire affect entirely with box-shadow. Take a look at their JSFiddle demo here: https://jsfiddle.net/5a0bvyup.
I'm going to leave my answer in the state I submitted it in because it does give some idea of how their implementation works (and if you look closely you'll see how their box-shadow differs from the one described below).
Note: In my answer I've made the foreground box red instead of white to demonstrate that this 'offset border' does not overlap the initial element. You'll need to change this back to white yourself.
The Left and Bottom Borders
You can achieve the left and bottom borders really easily with box-shadow. You simply need to create a solid shadow which matches the background colour, and then behind that add a second shadow which matches the foreground colour, offset by one pixel:
body {
background: black;
padding: 30px;
}
div {
background: red;
height: 72px;
width: 192px;
box-shadow: -2px 2px 0 5px black, -7px 7px 0 1px white;
}
<div></div>
The Top and Right Borders
You can then use pseudo-elements (::before and ::after) to fill in those extra borders:
body {
background: black;
padding: 30px;
}
div {
background: red;
height: 72px;
width: 192px;
box-shadow: -2px 2px 0 5px black, -7px 7px 0 1px white;
position: relative;
}
div::before {
background: white;
content: '';
position: absolute;
height: 1px;
width: 7px;
top: 6px;
right: 100%;
}
div::after {
background: white;
content: '';
position: absolute;
height: 7px;
width: 1px;
top: 100%;
right: 6px;
}
<div></div>

How to make a box with arrow in CSS?

How to make a box with arrow in CSS?
Making round corner is easy. but any idea to make the arrow on left side without using image.
Is it possible to make possible with
only one elements <p>....</p>
body {
background: #ff004e;
padding: 40px
}
p {
background: white;
-webkit-border-radius: 10px;
-moz-border-radius: 10px;
border-radius: 10px;
width: 250px;
height: 150px
}
<p></p>
Like this :
.arrow {
border: solid 10px transparent;
border-right-color: #FFF;
}
Demo : http://jsfiddle.net/sparkup/edjdxjf2/
UPDATE :
It can also be achieved without empty elements with the css property :before
element:before {
content: "";
position: absolute;
top: 50%; // half way down (vertical center).
margin-top: -15px; // adjust position, arrow has a height of 30px.
left:-30px;
border: solid 15px transparent;
border-right-color: #FFF;
z-index: 1;
}
Demo : http://jsfiddle.net/sparkup/y89f1te0/
hope it helps
Chris Coyier has an excellent roundup of the possible shapes built in CSS using a single element (and before/afters):
http://css-tricks.com/examples/ShapesOfCSS/
Standard Tool-tip
If you want a simple arrow, then you can add a pseudo element with border-right.
body {
background:#ff004e;
padding:40px;
}
p {
background:white;
border-radius: 10px;
width:250px;
height:150px;
position: relative;
display: inline-block;
}
p:before {
content:"";
position: absolute;
height: 0px;
width: 0px;
top: 60px;
left: -29px; /* 1px buffer for zooming problems while rendering*/
border-width: 15px;
border-color: transparent white transparent transparent;
border-style: solid;
}
<p></p>
FIDDLE 1
Flat edge Tool-tip
If you want a flat edge for arrow, try this :
body {
background: #ff004e;
padding:40px;
}
p {
background:white;
border-radius: 10px;
width:250px;
height:150px;
position: relative;
display: inline-block;
}
p:before {
content:"";
position: absolute;
height: 45px;
width: 16px; /* 1px buffer for zooming problems while rendering*/
top: 50px;
left: -15px;
background: white;
}
p:after {
content:"";
position: absolute;
height: 40px;
width: 15px;
border-radius: 0 40px 40px 0;
top: 75px;
left: -15px;
background: #ff004e;
box-shadow: 0 -45px 0 0 #ff004e;
}
<p></p>
FIDDLE 2
Use this online tool and you can do it without typing lot of code
http://www.cssarrowplease.com
My answer (with no flat edge),
added some calculation formula:
.mainBox {
border: solid 1px #e0e0e0;
}
.mainBox:before {
content:"";
position: absolute;
/*The right value must be calculated with: (top value of after) - (top value of before) = (right value of before) */
/*example: (-4px) - (-7px) = 3px*/
right: 72px;
/*The `top` value must be identical to border-width*/
top: -7px;
width: 0;
height: 0;
border-style: solid;
/*The `border-width` value must be identical to top*/
border-width: 0 7px 7px 7px;
/*The border color 3rd (#e0e0e0) value must be identical to its parent border color*/
border-color: transparent transparent #e0e0e0 transparent;
/*The (z-index of before) must at least one below the (z-index of after)*/
/*Example: (z-index of before) < (z-index of after) or 9998 < 9999*/
z-index:9998;
}
.mainBox:after {
content:"";
position: absolute;
right: 75px;
top: -4px; /*suppose to be identical to border-width*/
width: 0;
height: 0;
border-style: solid;
border-width: 0 4px 4px 4px;
border-color: transparent transparent #fff transparent;
z-index:9999;
}
The basic rules are:
The before right value must be calculated with:
(after's top) - (before's top) = (before's right)
example: (-4px) - (-7px) = 3px
The before and after's top value must be identical to border-width.
The border color 3rd (#e0e0e0 in the example) value must be identical to its parent border color.
The before's z-index must at least one below the after's z-index.
example: (before's z-index) < (after's z-index) or 9998 < 9999.
The result:
a.right{ border-style: dashed;
border-color: transparent;
border-width: 0.53em;
display: -moz-inline-box;
display: inline-block;
font-size: 100px;
height: 0;
line-height: 0;
position: relative;
vertical-align: middle;
width: 0; border-left-width: 1em;
border-left-style: solid;
border-left-color: #666;
left: 0.25em; }
the above code can be used for right arrow.
You can make use of span if u don't want to use a div.
span#pointer{border:solid 10px transparent;border-right-color:#fff;position:absolute;margin:-85px 0 0 -20px;}
http://jsfiddle.net/SSKwn/

Resources