Expanding linear-gradient background unaffected by div layout - html

I have the following code. When you click on it (excuse the on-the-fly, inline onclick - on my page it is more properly set up), the background expands to the right.
Unfortunately as I am using a :before with display: inline-block, it is affecting the layout of the text inside.
It also is being affected by the padding property I have on the box. I could solve this by setting a negative margin: -16px on the :before element however the height of the :before element goes off:
div {
border: 1px solid teal;
height: 64px;
border-radius: 10px;
overflow: hidden;
padding: 16px;
}
div:before {
display: inline-block;
height: 100%;
width: 5%;
content: '';
background: linear-gradient(130deg, lightblue 40%, white 0%);
transition: .3s;
}
div.active:before {
width: 200%;
/* or 300% if you want the entire background to be "taken over" */
}
<div onclick="this.classList.toggle('active')">
<span>Hi! I'm text! nice to meet you!</span>
</div>
This is how I want it to look like (it looks fine here because there is no text to get in the way and no padding property - both of which I will need for my webpage):
div {
border: 1px solid teal;
height: 64px;
border-radius: 10px;
overflow: hidden;
}
div:before {
display: inline-block;
height: 100%;
width: 5%;
content: '';
background: linear-gradient(130deg, lightblue 40%, white 0%);
transition: .3s;
}
div.active:before {
width: 200%;
/* or 300% if you want the entire background to be "taken over" */
}
<div onclick="this.classList.toggle('active')">
</div>
Does anyone know how to remove a :before from the layout of a box? Ideally without using position as on my page based on some parent items to the above box, position gets a bit "funky." But if it's the only solution then so be it.

Simply make the background on the main element and play with background-size
div {
border: 1px solid teal;
height: 64px;
border-radius: 10px;
overflow: hidden;
padding: 16px;
background-image: linear-gradient(130deg, lightblue 40%, white 0%);
background-size:10% 100%;
background-position:left;
background-repeat:no-repeat;
transition:background 0.5s;
}
div.active{
background-size:300% 100%;
}
<div onclick="this.classList.toggle('active')">
<span>Hi! I'm text! nice to meet you!</span>
</div>

Not sure if this is what you're looking for:
div {
border: 1px solid teal;
height: 64px;
border-radius: 10px;
overflow: hidden;
position:relative;
}
div:before {
display: inline-block;
height: 100%;
width: 5%;
content: '';
background: linear-gradient(130deg, lightblue 40%, white 0%);
transition: .3s;
position:absolute;
}
div.active:before {
width: 200%;
/* or 300% if you want the entire background to be "taken over" */
}
div span{
position:absolute;
padding: 16px;
}
<div onclick="this.classList.toggle('active')">
<span>Hi! I'm text! nice to meet you!</span>
</div>

The only way to fix this without either removing the :before or using position is by adding the text to the content property of the :before,
that would result in code like:
HTML:
<div onclick="this.classList.toggle('active')"></div>
CSS:
div {
border: 1px solid teal;
height: 64px;
border-radius: 10px;
overflow: hidden;
padding: 16px;
}
div:before {
display: inline-block;
height: 100%;
width: 100%;
content: "Hi! I'm text! nice to meet you!";
background: linear-gradient(130deg, lightblue 5%, white 0%); /*Or whatever width you like*/
transition: .3s;
text-align: center;
line-height: 4;
}
div.active:before {
width: 100%;
background: linear-gradient(130deg, lightblue 75%, white 0%); /*Or whatever width you like*/
/* or 100% lightblue if you want the entire background to be "taken over" */
}
But most accessibility hard- and software is incapable of handling a :before correctly.
So why not set the background on either the div or the span?
CSS:
span {
width: 100%;
background: linear-gradient(130deg, lightblue 5%, white 0%); /*Or whatever width you like*/
transition: .3s;
text-align: center;
line-height: 4;
}
span.active {
background: linear-gradient(130deg, lightblue 75%, white 0%); /*Or whatever width you like*/
}
which results in the same background effect, with the text centered.

Related

Animating CSS gradient works only if text doesn't wrap

This example of animating a gradient in purely CSS works great when the text or thing doesn't wrap like text does at the end of a line. But when wrapping occurs, the gradient breaks and doesn't animate. Here is a slightly modified example to demonstrate. Shrink the screen so you can see the second block of text wrap around the edge, hover over it, and notice it won't animate.
.button {
background-size: 100%;
background-image: linear-gradient(#fff, #ccc);
border-radius: 0.45rem;
border: 1px solid #ddd;
cursor: pointer;
color: #333;
font-size: 1.25rem;
font-weight: 300;
position: relative;
}
.button:before {
border-radius: inherit;
background-image: linear-gradient(#ccc, #fff);
content: '';
display: block;
height: 100%;
position: absolute;
top: 0; left: 0;
opacity: 0;
width: 100%;
z-index: 100;
transition: opacity 0.45s;
}
.button:hover:before {
opacity: 1;
}
<span class='button'>hello</span> i am some text and then <span class='button'>i wrap around the edges</span> and go all the way around
Wondering if there is any way to get this working without using JS.
You can get a similar effect by using a gradient with larger than the display area height, and animating it's position:
.button {
background-size: 100% 150%;
background-position: 0 0;
background-image: linear-gradient(#fff 0, #ccc 50%, #fff 100%);
border-radius: 0.45rem;
border: 1px solid #ddd;
cursor: pointer;
color: #333;
font-size: 1.25rem;
font-weight: 300;
position: relative;
transition: background-position 0.45s;
}
.button:hover {
background-position: 0 100%;
}
<span class='button'>hello</span> i am some text and then <span class='button'>i wrap around the edges</span> and go all the way around

CSS Change color of border twice while giving it a left to right effect

I want to combine two animations in order to achieve a bottom border that turns to white and fills from left to right and then goes back to the initial color giving the effect that the white line dissapears.
I found this pen that shows how I want the white line to show up (it's the third button, curmudgeon). It should dissapear from left to right too.
https://codepen.io/lesbaa/pen/dojGVL
I created the border changing colors in steps in the code below.
body {
background: grey;
}
.box {
width: 150px;
height: 50px;
background: #161a1c;
border-bottom: 2px solid #1f262d;
}
.box:hover {
animation: line 1s;
}
#keyframes line {
50% {
border-bottom: 3px white solid;
}
}
<div class="box"></div>
Any ideas how I could achieve this?
Assuming it's even possible.
You can achieve this using a :pseudo-element and transition.
body {
background: #444;
}
.box {
display: block;
position: relative;
width: 150px;
height: 50px;
background: #161a1c;
border-bottom: 2px solid #1f262d;
overflow: hidden;
}
.box::after {
content: '';
position: absolute;
width: 145%;
height: 3px;
bottom: 0;
left: -145%;
background: linear-gradient(to right, #1f262d 0%, white 45%, white 100%);
z-index: 1;
transition: left 0s;
}
.box:hover::after {
left: 145%;
transition: left 1s ease-in;
}
<div class="box"></div>
You can use linear-gradient and adjust background-size/background-position on hover:
body {
background: grey;
}
.box {
width: 150px;
height: 50px;
background-image:linear-gradient(#fff,#fff);
background-position:bottom left;
background-size:0% 2px;
background-repeat:no-repeat;
background-color:#161a1c;
transition:
background-size 1s, /*animate the background-size*/
background-position 0s 1s; /*don't animate position and add a delay */
}
.box:hover {
background-position:bottom right;
background-size:100% 2px;
}
<div class="box"></div>
UPDATE
You can also do it like this:
body {
background: grey;
}
.box {
width: 150px;
height: 50px;
background-image:linear-gradient(#fff,#fff);
background-position:200% 100%;
background-size:200% 2px;
background-repeat:no-repeat;
background-color:#161a1c;
transition:0s;
}
.box:hover {
background-position:-100% 100%;
transition:all 1s;
}
<div class="box"></div>

is it possible to do a curved line with css gradient?

I have this design from a client with two layers of gradients in a button. The tricky thing is, one of the layers has a curved edge. I've mocked up the button so you have a sense of what I'm saying, hopefully.
What I managed to do is a straight edge (see code snippet, color difference is not important, just need the curve). Does anyone have done this before? Or does it have to be a background image? Thanks!
P.S. I also thought about using radial gradient on a pseudo element and absolute position it, but couldn't get the exact straight edge look like the linear gradient.
a {
background-image: linear-gradient(-155deg,rgba(74,148,214,.4) 45%,rgba(255,255,255,.08) 15%),linear-gradient(258deg,rgba(87,238,255,.1),rgba(77,108,211,.2));
background-color: rgba(74,148,214,.9);
color: #fff;
width: 200px;
height: 40px;
border-radius: 10px;
margin-top: 50px;
display: block;
text-align: center;
line-height: 40px;
}
<a>
Some button
</a>
You can get pretty close by using a radial-gradient instead of linear:
a {
background-image:
radial-gradient(ellipse farthest-corner at 0 140%, #3c84cc 0%, #316dc2 70%, #4e95d3 70%);
color: white;
width: 200px;
height: 50px;
border-radius: 10px;
margin-top: 50px;
display: block;
text-align: center;
line-height: 50px;
}
<a>
Some button
</a>
You can use a pseudo element to draw the curve using a circle, then just use whatever gradient you want as the background(s)
a {
background-color: lightblue;
color: #fff;
width: 200px;
height: 40px;
border-radius: 10px;
margin-top: 50px;
display: block;
text-align: center;
line-height: 40px;
position: relative;
z-index: 1;
overflow: hidden;
}
a:after {
content: '';
position: absolute;
background-color: blue;
width: 600px;
height: 200px;
border-radius: 50%;
top: 0;
left: 0;
transform: translate(-49%,0);
z-index: -1;
}
<a>
Some button
</a>
I just modified a bit #Blazemonger's post.
I fixed the position of the curved line.
a {
background-image: radial-gradient(ellipse farthest-corner at -10% 250%, #3c84cc 0%, #315dc2 80%, #4e95d3 80%);
color: white;
width: 200px;
height: 50px;
border-radius: 10px;
margin-top: 50px;
display: block;
text-align: center;
line-height: 50px;
}
<a>Some button</a>

Button with gradient outside border

How can I achieve the next thing in CSS to a < a > element ?
Image1
I managed to do something like this:
https://jsfiddle.net/25abxak1/
-- first of , I need the content to be wider and second , I want the first color to go above the border , just like in the picture.
I'm a begginer in CSS and I really need help.
Thank you
You can use display: inline-block on a, and for black part you can use :before pseudo-element. You should also set padding-left on a to width of :before + padding-right so that text is centered.
a {
color: #C46439;
background: none;
border-radius: 10px;
border: 1px solid #D2D1D1;
position: relative;
overflow: hidden;
padding: 10px 30px;
padding-left: 70px;
display: inline-block;
text-decoration: none;
}
a:before {
content: '';
position: absolute;
left: 0;
top: 0;
height: 100%;
width: 40px;
background: black;
}
Centered text
You can also use linear-gradient and set black part to 20% or something similar.
a {
color: #C46439;
background: linear-gradient(to right, black 0%, black 20%, white 20%, white 100%);
border-radius: 10px;
border: 1px solid #D2D1D1;
position: relative;
overflow: hidden;
padding: 10px 30px;
padding-left: 70px;
display: inline-block;
text-decoration: none;
}
Centered text

Make div with bottom triangle

I have been trying to do the white shape with a div:
http://sircat.net/joomla/sircat/mies/2.png
how do I get the diagonal shapes of the bottom of the div?
I have this for the div:
width: 620px;
height: 440px;
background-color: white;
thank you
Edit: just forget the bg behind the div, I want to make the div with the diagonal borders, not with the help of the bg because it is in the top layer
You can also use borders and the :after pseudo selector: http://jsfiddle.net/qQySU/
#pointed {
position: relative;
margin: 0 auto;
width: 200px;
height: 200px;
background-color: white;
}
#pointed:after,
#pointed::after {
position: absolute;
top: 100%;
left: 50%;
margin-left: -50%;
content: '';
width: 0;
height: 0;
border-top: solid 150px red;
border-left: solid 100px transparent;
border-right: solid 100px transparent;
}
I've colored the tip for easy identification of the borders. Play around the border widths on the last 3 lines to get the tip you want.
Edit.:
Reference for compability: http://caniuse.com/css-gencontent
Edit 2:
In exchange for semantics, you can get it more crossbrowser you can place the stle on a inner element instead of on the :after pseudo selector.
Simplest (least amount of code) method: just use a CSS linear-gradient http://dabblet.com/gist/3610406
HTML:
<div class='box'>Text goes here...</div>
CSS:
.box {
width: 26em;
min-height: 31em;
padding: 1em;
outline: solid 1px lightblue;
margin: 0 auto;
background: linear-gradient(45deg, dimgrey 47%, black 50%, transparent 50%)
no-repeat 0 100%,
linear-gradient(-45deg, dimgrey 47%, black 50%, transparent 50%)
no-repeat 100% 100%;;
background-size: 50% 14em;
}
Better compatibility & better looking: you could use a pseudo-element with a box-shadow: http://dabblet.com/gist/3610548
HTML:
<div class='box'>text goes here... hover me ;)</div>
CSS:
html { background: darkgrey; }
.box {
box-sizing: border-box;
position: relative;
width: 20em;
height: 20em;
padding: 1em;
margin: 3em auto 0;
background: white;
}
.box:before {
position: absolute;
right: 14.65%; /* 50% - 35.35% */ bottom: -35.35%; /* half of 70.71% */
width: 70.71%; /* 100%*sqrt(2)/2 */
height: 70.71%;
box-shadow: 2px 2px 1px dimgrey;
transform: rotate(45deg);
background: white;
content: '';
}
.box:hover, .box:hover:before {
background: plum;
}