Rectangle with curved sides and sharp corners - css

Is it possible to make something similar to this image with CSS? Each side of the rectangle has a curve on it. This is different to straight sides with only the border being rounded.

You can achieve the curved sides and pointed corners with the intersection of 2 oval shapes. You can use an oval div with hidden overflow and an oval pseudo element with the black background.
The pseudo element needs to be centered in it's parent. In the following example, I used absolute positioning to center it :
div{
position:relative;
width:600px; height:150px;
margin:0 -150px;
border-radius:50%;
overflow:hidden;
}
div:after{
content:'';
position:absolute;
top:-175px; left:150px;
height:500px; width:300px;
border-radius:inherit;
background:#000;
}
<div></div>

TV screen
https://css-tricks.com/examples/ShapesOfCSS/
#tv {
position: relative;
width: 200px;
height: 150px;
margin: 20px 0;
background: red;
border-radius: 50% / 10%;
color: white;
text-align: center;
text-indent: .1em;
}
#tv:before {
content: '';
position: absolute;
top: 10%;
bottom: 10%;
right: -5%;
left: -5%;
background: inherit;
border-radius: 5% / 50%;
}

You can achieve something similar using border-radius (shown below)
#rectangle {
border-radius: 25px;
padding: 20px;
width: 200px;
height: 150px;
}
This is a CSS3 feature. Have in mind that it only works on IE9 and up.

Related

Border radius 50% with concave border using pseudo elements

I want to create a div with border-radius 50% and having blue background such that right side part of curve should be filled with another color say light blue. How do we do that using css pseudo elements
#circle{
width: 50px;
height: 50px;
background: blue;
border-radius: 50%;
}
You can use the following solution:
#circle{
width: 50px;
height: 50px;
background: blue;
border-radius: 50%;
position:relative;
}
#circle:after {
content:"";
display:block;
position:absolute;
left:50%;
top:0;
height:100%;
width:50%;
background:lightblue;
z-index:-1;
}
<div id="circle"></div>

CSS: How to add slanted edge to right of div with complete browser cross-compatability?

I'm looking to achieve a slanted edge on my div. The problem I'm coming across is the simple code I found to accomplish this is not cross-browser compatible. In fact, it only shows in Chrome.
Can anyone advise on how to do the following so it works in ALL browsers:
clip-path:polygon(0 0, 70% 0, 100% 100%, 0 100%);
This effect would achieve:
Here's my entire CSS code:
.my-slanted-div {
position:absolute;
bottom:0;
left:0;
width:100px;
padding:10px 10px;
background-color:#eee;
font-size:20px;
clip-path:polygon(0 0, 70% 0, 100% 100%, 0 100%);
}
Can anyone help me out?
You can also skew pseudo-element, like this:
.my-slanted-div {
position:absolute;
bottom:40px;
left:0;
width:80px;
padding:10px 10px;
background-color:red;
font-size:20px;
}
.my-slanted-div:after {
width:50px;
background:red;
position:absolute;
height:100%;
content:' ';
right:-22px;
top:0;
transform: skew(45deg);
}
<div class="my-slanted-div">
TEXT
</div>
p.s. change angle, play with values...to get desired result...
Edit: Demo in context -> https://jsfiddle.net/Lbwj40mg/2/
This should do the trick using borders.
<div id="container">
<p id="text">Hello</p>
<div id="slanted"></div>
</div>
#container {
position: relative;
height: 200px;
width: 200px;
background:url(http://placehold.it/200x200);
}
#text {
position: absolute;
bottom: 15px;
left: 10px;
z-index: 1;
margin: 0;
}
#slanted {
position: absolute;
bottom: 0;
left: 0;
height: 0;
width: 0;
border-left: 75px solid #dedede;
border-right: 50px solid transparent;
border-bottom: 50px solid #dedede;
}
jsfiddle
I've made it work one way with :before and :after pseudos, you simply need to update the widths, heights and line-height to suit the size of tab you want; the rectangle must be the same height as the :before and :after bits for a clean look.
.box {
background: red;
width: 200px;
position: relative;
height: 100px;
line-height: 100px;
text-align: center;
margin-left: 50px;
color: white;
font-size: 21px;
font-family: arial, sans-serif;
}
.box:after {
position: absolute;
right: -50px;
content: '';
width: 0;
height: 0;
border-left: 50px solid transparent;
border-right: 50px solid transparent;
border-bottom: 100px solid red;
}
.box:before {
position: absolute;
left: -50px;
content: '';
width: 0;
height: 0;
border-left: 50px solid transparent;
border-right: 50px solid transparent;
border-bottom: 100px solid red;
}
<div class="box">
Text in the box
</div>
Here's a way with transform: rotate just to add to the list. Quite annoying as you will have to play with pixels for alignment and make some entries into #media rules for different screen sizes. But it should be fairly cross browser friendly (but maybe not opera mini)
body {
background-color: #333;
}
.container {
position: absolute; /* needs a position, relative is fine. abolsute just for this example */
top: 50%; left: 50%;
transform: translate(-50%, -50%);
width: 400px;
height: 200px;
background-color: #ccc;
overflow: hidden; /* required */
}
.salutations {
position: absolute;
bottom: 0;
left: 0;
padding: 0 10px 0 15px;
background-color: #fcfcfc;
height: 50px;
line-height: 50px; /* match height to vertically center text */
font-size: 30px;
}
.salutations::before {
content: '';
position: absolute;
top: 21px; /* play with this for alignment */
right: -36px; /* play with this for alignment */
height: 40px; width: 70px; /* may need to adjust these depending on container size */
background-color: #fcfcfc;
transform: rotate(60deg); /* to adjust angle */
z-index: -1; /* puts the pseudo element ::before below .salutations */
}
<div class="container">
<div class="salutations">Hello</div>
</div>
P.S. May have to adjust a pixel or two, my eyes suck.
Browser Compatability
transform: rotate
pseudo elements (::before)
Fiddle
https://jsfiddle.net/Hastig/wy5bjxg3/
It is most likely it is an SVG scaled to always fit its text which is simple and quick way of doing it; if you must use CSS then you could always:
Set a gradient to the div from color to transparent so that it takes up most of the div and the transition of color is abrupt and not smooth like how a normal gradient looks.
create another div and using borders create a triangle to touch the other main rectangular div such as doing:
.triangle {
width: 0;
height: 0;
border-style: solid;
border-width: 200px 200px 0 0;
border-color: #fff transparent transparent transparent;
}
Using css you can generate an element that takes the shape of a triangle.
Css tricks has a post on that.
By making the .slanted class position itself relative, we can position the generated content on the right side of the slanted div using absolute positioning.
It'll take some fiddling to get the perfect result you want, but here's an example.
.slanted{
background: #007bff;
color: #fff;
position: relative;
display:inline-block;
font-size: 20px;
height: 25px;
padding: 2px 4px;
}
.slanted::after {
content: " ";
display: block;
width: 0;
height: 0;
border-style: solid;
border-width: 29px 0 0 20px;
border-color: transparent transparent transparent #007bff;
position: absolute;
top: 0;
right: -20px;
}
<div class="slanted">Hello</div>

Shared translucence across two elements (without overlap)?

I'm pretty sure this can't be done. But there are a lot of clever people out there, so here goes...
I'm creating an UI shape using two elements that overlap. Essentially a large square with a round protrusion.
I'd like these two elements to appear as one object (which is easy to do by giving them the same background color and overlap them) but I'd also like to have this element look like it has a single drop shadow.
The catch is that drop shadows are translucent and where the two elements overlap, you will get a darker spot due to both shadow elements combining.
Example:
http://jsbin.com/maboputexa/1/
Because these are two HTML elements, I'm pretty sure there's no way around this and this is just how it is. For now, I'm going to try not using translucent objects and go with a flat solid color for the shadow. But if anyone knows of any tricks to make this work in CSS3 with all the new options, please let me know!
(Note that I'm not referring to box-shadow properties as that wouldn't work with two objects as there always would have to be one object on top of the other).
More for the fun of it than with a real use:
2 divs, having shadows that do not overlap, and transparency that don't overlap
Notice the technique to avoid the shadows overlapping: z-index auto on the divs, and the shadow set on an pseudo element with z-index negative.
And the technique to avoid the transparency overlapping is a little disturbing, since it needs not only a mix-blend-mode, but also putting the divs behind the image ...
But, as I said, it's a funny result ...
Should work in Chrome, FF and Safari (this one untested)
body {
background-color: gray;
font-size: 30px;
}
.test1 {
width: 300px;
height: 200px;
position: absolute;
left: 150px;
top: 150px;
background-color: #555;
z-index: auto;
}
.test2 {
width: 300px;
height: 200px;
position: absolute;
left: 10px;
top: 0px;
border-radius: 50%;
background-color: #555;
z-index: auto;
-webkit-animation: move 5s infinite;
animation: move 5s infinite;
}
#-webkit-keyframes move {
0% {left: 0px; top: 0px;}
33% {left: 300px; top: 20px;}
66% {left: 300px; top: 220px;}
100% {left: 0px; top: 0px;}
}
#keyframes move {
0% {left: 0px; top: 0px;}
33% {left: 300px; top: 20px;}
66% {left: 300px; top: 220px;}
100% {left: 0px; top: 0px;}
}
.test1:after , .test2:after {
content: "";
position: absolute;
left: 0px;
toop: 0px;
width: 100%;
height: 100%;
box-shadow: 4px 4px 8px 2px black;
border-radius: inherit;
z-index: -1;
}
.overlay {
width: 600px;
height: 600px;
background-image: url(http://placekitten.com/1000/750);
background-size: cover;
position: absolute;
z-index: 4;
mix-blend-mode: overlay;
pointer-events: none;
}
<div class="test1">test1</div>
<div class="test2">test2</div>
<div class="overlay"></div>
if the goal is to draw a shape with shadow you may look at svg wich will be made for this.
CSS has limits and is not really meant for drawing:
For the CSS trick with html element, background and shadow , you can easily do the background in this case, but the shadow part will be average and a lost of precious time IMHO.
See: http://jsbin.com/paqayorewo/1/ or run snippet below.
.shape1 {
width: 200px;
height: 200px;
background: rgba(0,0,0,.5);
position: absolute;
top: 200px;
box-shadow:-3px 3px 2px 0px,
50px 50px 2px -48px,
-50px -50px 2px -48px}
.shape2 {
width: 200px;
height: 200px;
border-radius: 100px;
position: absolute;
top: 100px;
left: 100px;
overflow:hidden;
box-shadow:2px -3px 3px, -20px -20px 3px -24px, -40px -15px 2px -40px, 8px 3px 3px -3px}
.shape2:before,
.shape2:after {
content:'';
background: rgba(0,0,0,.5);
position:absolute;
}
.shape2:before {
height:50%;
width:100%;
}
.shape2:after {
width:50%;
height:50%;
top:50%;
right:0;
}
body {
position:relative;
}
<div class="shape1"></div>
<div class="shape2"></div>

How to style a rectangular div with elliptical rounded sides?

How to style a rectangular div with elliptical rounded sides?
You can get an ellipse by setting border-radius 50%.
You can get two elements, one inside the other, with different sizes, and so get the 2 ellipses needed
.test {
position: absolute;
left: 40px;
top: 40px;
width: 200px;
height: 200px;
border-radius: 50%;
overflow: hidden;
}
.test:after {
content: "";
position: absolute;
left: -30%;
top: 10%;
width: 160%;
height: 80%;
background-color: lightblue;
border-radius: 50%;
}
In this case, using an pseudo element , and so, only one div is needed
demo
Have you checked out this website? Try this:
div
{
border:2px solid;
border-radius:25px;
}

css start repeating background from defined position

#container{
background:url(images/bg-main.png) repeat-y;
width: 903px;
background-position: 0px 687px;
background-position: bottom;
height: 1200px;
margin-left: auto;
margin-right: auto;
}
#content{
background:url(images/bg-wood.png) repeat-y;
width: 903px;
height: 678px;
margin-left: auto;
margin-right: auto;
}
#content div is inside #container div. I want #container's background to start repeating at 687px from top. Is it possible?
EDIT: Is it possible that first x pixels of div (from top) have emtpy space and after x pixels backgrund starts?
As far as I know it's not possible how you're trying to do it, repeat-x and repeat-y, will repeat the image in both directions along the axis
if you repeat container background full length does the content div background image not cover up the first 678px anyway?
can you provide code in a JSFiddle so we can see what effect you're trying to achieve there will be a way ;)
You can achieve this with pseudo element (::before or ::after) and take advantage of calc() for the offset.
Pseudo element will give you more control and won't affect the content and does not require the need for an extra HTML tag.
Here is a basic example with 100px offset from top:
.background {
height: 300px;
border:1px solid;
position: relative;
}
.background::before {
content: '';
position: absolute;
bottom: 0;
left: 0;
height: calc(100% - 100px);
width: 100%;
display: block;
box-sizing: border-box;
background: url(//placehold.it/100x100);
}
<div class="background"></div>
You can also use the same techique to offset from left:
.background {
height: 300px;
border:1px solid;
position: relative;
}
.background::before {
content: '';
position: absolute;
bottom: 0;
right: 0;
height: 100%;
width: calc(100% - 100px);
display: block;
box-sizing: border-box;
background: url(//placehold.it/100x100);
}
<div class="background"></div>
Or even from both directions (reversed, too!):
.background {
height: 300px;
border:1px solid;
position: relative;
}
.background::before {
content: '';
position: absolute;
top: 0;
left: 0;
height: calc(100% - 100px);
width: calc(100% - 100px);
display: block;
box-sizing: border-box;
background: url(//placehold.it/100x100);
}
<div class="background"></div>
background : url('image path') 0px 287px repeat-y;
This will repeat vertically your background image from 287px from top.
but another way is to set this to your content div :
margin-top:287px;
you best solution is to do like this :
#container{
position:relative;
}
#background{
background:url('image url');
position:absolute;
top:287px;
left:0px;
z-index:100;
}
#content{
position:absolute;
top:0px;
left:0px;
z-index:99999;
}

Resources