How do I unskew background image in skewed layer (CSS)?
I'd rather use a pseudo element that's holding the background-image. The key to the solution is using transform-origin
:
Example
.photo {
transform: skewX(35deg);
-ms-transform: skewX(35deg); /* IE 9 */
-webkit-transform: skewX(35deg); /* Safari and Chrome */
width: 100px;
height: 92px;
border-right: 1px solid black;
border-left: 1px solid black;
/* new styles */
position: relative;
overflow: hidden;
-webkit-transform-origin: top left;
-ms-transform-origin: top left;
transform-origin: top left;
}
.photo::before {
content: "";
transform: skewX(-35deg);
-ms-transform: skewX(-35deg); /* IE 9 */
-webkit-transform: skewX(-35deg); /* Safari and Chrome */
background-image: url('http://placekitten.com/200/200');
background-repeat: no-repeat;
background-position: top left;
/* new styles */
position: absolute;
-webkit-transform-origin: top left;
-ms-transform-origin: top left;
transform-origin: top left;
width: 1000%; /* something ridiculously big */
height: 1000%; /* something ridiculously big */
}
box with skew and background image
I was able to manage it using the method I spoke before in comment.
Basically, I used ::before
pseudo-elements to put the background image and then unskewed them.
Check it out:
/* +++++++++++++++ NEW INFORMATION ++++++++++++++ */
.accordion ul li::before {
content: "";
transform: skewX(20deg);
-ms-transform: skewX(20deg);
-webkit-transform: skewX(20deg);
background-image: url(http://michael-ferry.com/assets/accordion3.jpg);
background-repeat: no-repeat;
background-position: top left;
position: absolute;
transform: translateX(-50%) skewX(20deg);
-webkit-transform-origin: top left;
-ms-transform-origin: top left;
transform-origin: top left;
width: 200%;
height: 100%;
}
/* +++++++++++++++++++++++++++++++++++++++++++++ */
.accordion {
width: 100%;
height: 300px;
overflow: hidden;
max-width: 100%;
margin: 50px auto;
background-color: #FFAE00;
}
.accordion ul {
width: 90%;
display: table;
table-layout: fixed;
margin: 0;
padding: 0;
margin-left: 5%;
height: 100%;
}
.accordion ul li {
display: table-cell;
vertical-align: bottom;
position: relative;
margin-left: 0;
margin-right: 0;
width: 25%;
height: 250px;
background-repeat: no-repeat;
background-position: center center;
transition: all 500ms ease;
float: none;
transform: skewX(-20deg);
overflow: hidden;
}
.accordion ul li div {
display: block;
overflow: hidden;
width: 100%;
}
.accordion ul li div a {
display: block;
height: 300px;
width: 37vw;
position: relative;
z-index: 0;
vertical-align: bottom;
padding: 55px 45px;
box-sizing: border-box;
color: #fff;
margin-left: -53px;
text-decoration: none;
transform: skewX(20deg);
font-family: Open Sans, sans-serif;
transition: all 200ms ease;
}
.accordion ul li div a * {
opacity: 0;
margin: 0;
width: 100%;
text-overflow: ellipsis;
position: relative;
z-index: 0;
white-space: nowrap;
overflow: hidden;
-webkit-transform: translateX(-20px);
transform: translateX(-20px);
-webkit-transition: all 0.4s ease;
transition: all 0.4s ease;
}
.accordion ul li div a h2 {
font-family: Montserrat, sans-serif;
text-overflow: clip;
font-size: 24px;
text-transform: uppercase;
text-align: left;
border-bottom: unset;
margin-bottom: 2px;
top: 165px;
}
.accordion ul li div a p {
top: 165px;
font-size: 13.5px;
font-weight: 100;
margin-left: 0;
height: auto;
}
.accordion ul:hover li:hover {
width: 50%;
}
.accordion ul:hover li:hover a {
background: rgba(0, 0, 0, 0.4);
}
.accordion ul:hover li:hover a * {
opacity: 1;
transform: none;
}
<div class="accordion">
<ul>
<li>
<div>
<a href="#">
<h2>Lorem Ipsum</h2>
<p>Lorem ipsum dolor sit amet, consectetur adipiscing elit</p>
</a>
</div>
</li>
<li>
<div>
<a href="#">
<h2>Lorem Ipsum</h2>
<p>Lorem ipsum dolor sit amet, consectetur adipiscing elit</p>
</a>
</div>
</li>
<li>
<div>
<a href="#">
<h2>Lorem Ipsum</h2>
<p>Lorem ipsum dolor sit amet, consectetur adipiscing elit</p>
</a>
</div>
</li>
<li>
<div>
<a href="#">
<h2>Lorem Ipsum</h2>
<p>Lorem ipsum dolor sit amet, consectetur adipiscing elit</p>
</a>
</div>
</li>
</ul>
</div>
How to layer background image and skewed divs to create overlay using CSS
Following the answer posted here, I ended up using pseudo elements and an extra div to create the masking effect I wanted while still showing the background image.
.calloutbar-section {
background:#282a32;
position: relative;
padding: 80px 15px;
}
.calloutbar-section.footer .skewed-arrow.left,
.calloutbar-section.footer .skewed-arrow.none {
transform-origin: top right;
transform: skew(45deg, 0deg);
}
.calloutbar-section.footer .skewed-arrow.right {
transform-origin: bottom right;
transform: skew(-45deg, 0deg);
}
.calloutbar-section.footer .skewed-arrow {
position: absolute;
top: 0;
right: 0;
bottom: 0;
width: 35%;
background-color: transparent;
background-clip: padding-box;
border-left: 15px solid #FFFFFF;
z-index:1;
overflow-x: hidden;
}
.reversed {
color:#FFFFFF;
}
.calloutbar-section.footer .skewed-arrow.left::before {
content: "";
background-image:url(https://via.placeholder.com/1000);
transform: skewX(-45deg);
-ms-transform: skewX(-45deg); /* IE 9 */
-webkit-transform: skewX(-45deg); /* Safari and Chrome */
background-repeat: no-repeat;
background-position: top left;
background-size:cover;
position: absolute;
-webkit-transform-origin: top left;
-ms-transform-origin: top left;
transform-origin: top left;
width: 100%;
height: 100%;
}
.calloutbar-section.footer .skewed-arrow.right::before {
content: "";
background-image:url(https://via.placeholder.com/1000);
transform: skewX(45deg);
-ms-transform: skewX(45deg); /* IE 9 */
-webkit-transform: skewX(45deg); /* Safari and Chrome */
background-repeat: no-repeat;
background-position: top left;
background-size:cover;
position: absolute;
-webkit-transform-origin: bottom left;
-ms-transform-origin: bottom left;
transform-origin: bottom left;
width: 100%;
height: 100%;
}
<section class="calloutbar-section">
<div class="skewed-arrow left"></div>
<div class="skewed-arrow right"></div>
<div class="skewed-arrow none"></div>
<div class="calloutbar-body container">
<div class="row">
<div class="col-lg-7">
<div class="title reversed">Lorem Ipsum Amet</div>
<p class="reversed large">lorem ipsum amet</p>
</div>
</div>
</div>
</section>
how to set transform for div without effect on background image?
I had success by adding a pseudo-element ::before
, moving the background-image
to that pseudo-element, and applying a reversed skew to counteract your original skew.
This is based on a solution at sitepoint.com.
.q-item {
width: 180px;
height: 132px;
float: left;
margin-left: 58px;
padding-right: 1%;
border: 2px solid #1D2A3D;
-webkit-transform: skew(-20deg);
-moz-transform: skew(-20deg);
-ms-transform: skew(-20deg);
-o-transform: skew(-20deg);
transform: skew(-20deg);
}
.q-item::before {
content:"";
position: absolute;
width: 100%;
height: 100%;
background:url('http://jsfiddle.net/img/logo.png') no-repeat no-repeat 33px 1px;
-webkit-transform: skew(20deg);
-moz-transform: skew(20deg);
-ms-transform: skew(20deg);
-o-transform: skew(20deg);
transform: skew(20deg);
}
WORKING EXAMPLE
CSS Drop down menu with skewed first layer
Simply add a new <span>
element and specify the transform-origin
(example).
New HTML
Add a <span>
around the text of each of the .rhlink
anchors.
<ul id="nav">
<li class="rhombus"><a class="rhlink" href="#"><span>1 HTML</span></a>
<ul>
<li><a href="#">3.2 Mootools</a></li>
<li><a href="#">3.3 Prototype</a></li>
</ul>
</li>
<li class="rhombus"><a class="rhlink" href="#"><span>2 CSS</span></a></li>
<li class="rhombus"><a class="rhlink" href="#"><span>3 Javascript</span></a>
<ul>
<li><a href="#">3.1 jQuery</a>
<ul>
<li><a href="#">3.1.1 Download</a></li>
<li><a href="#">3.1.2 Tutorial</a></li>
</ul>
</li>
<li><a href="#">3.2 Mootools</a></li>
<li><a href="#">3.3 Prototype</a></li>
</ul>
</li>
</ul>
New CSS
Basically, you just have to skew()
the newly added <span>
and specify the transform-origin
to get the submenus to line up. The negative skew()
can't be used on the anchor itself because the anchor contains the visible content (border
and background
), so it would look like no skew was ever applied. Adding the child <span>
lets you keep the background
/border
and :hover
effect.
#nav,
#nav ul {
margin:0;
padding:0;
list-style-type:none;
list-style-position:outside;
position:relative;
line-height:1.5em;
}
#nav a:link,
#nav a:active,
#nav a:visited {
display:block;
padding:0px 5px;
border:1px solid #333;
color:#fff;
text-decoration:none;
background-color:#00ff21;
}
#nav a:hover {
background-color:#fff;
color:#333;
}
#nav > li {
float:left;
position:relative;
}
li.rhombus {
float:left;
position: relative;
-webkit-transform-origin:0 0;
-moz-transform-origin:0 0;
-ms-transform-origin:0 0;
-o-transform-origin:0 0;
transform-origin:0 0;
-webkit-transform:skew(35deg);
-moz-transform:skew(35deg);
-ms-transform:skew(35deg);
-o-transform:skew(35deg);
transform:skew(35deg);
}
li.rhombus > a span {
-webkit-transform:skew(-35deg);
-moz-transform:skew(-35deg);
-ms-transform:skew(-35deg);
-o-transform:skew(-35deg);
transform:skew(-35deg);
display:block;
}
li.rhombus > ul {
-webkit-transform-origin:0 0;
-moz-transform-origin:0 0;
-ms-transform-origin:0 0;
-o-transform-origin:0 0;
transform-origin:0 0;
-webkit-transform:skew(-35deg);
-moz-transform:translate(0,1px) skew(-35deg);
-ms-transform:skew(-35deg);
-o-transform:skew(-35deg);
transform:skew(-35deg);
}
#nav ul {
position:absolute;
top:1.5em;
left:0;
width:12em;
display:none;
}
#nav li ul a {
width:12em;
float:left;
}
#nav ul ul {
top:auto;
}
#nav li ul ul {
left:12em;
margin:0px 0 0 10px;
}
#nav li:hover ul ul,
#nav li:hover ul ul ul,
#nav li:hover ul ul ul ul {
display:none;
}
#nav li:hover ul,
#nav li li:hover ul,
#nav li li li:hover ul,
#nav li li li li:hover ul {
display:block;
}
Skew Input Border Without Skewing Text Inside
Solution
We need to add another layer. In this case, I'd typically use a label
element, wrapped around the input
. We can give that outer label
the border, and then skew it. Then we skew the inner input
the exact opposite amount.
Code
#search {
display:inline-block;
border:2px solid #323232;
border-radius: 0;
padding:3px 10px;
-moz-transform: skewX(-40deg);
-webkit-transform: skewX(-40deg);
-o-transform: skewX(-40deg);
-ms-transform: skewX(-40deg);
transform: skewX(-40deg);
}
#search input {
border:0;
box-shadow: none;
-moz-transform: skewX(40deg);
-webkit-transform: skewX(40deg);
-o-transform: skewX(40deg);
-ms-transform: skewX(40deg);
transform: skewX(40deg);
}
<form id="search-form" action="/idee" accept-charset="UTF-8" method="get"><input name="utf8" type="hidden" value="✓" />
<label id="search"><input type="text" placeholder="Search" /></label>
</form>
Related Topics
Concatenate Values in Less (Css) Without a Space
Column-Count Is Not Working in Chrome
How to Get Grid Items of Different Lengths to Wrap
CSS Nth-Child Apply Odd-Even Rule But Switch Every 4 Items
What's the Purpose of Using CSS Browser Reset Code
Scale HTML5 Video and Break Aspect Ratio to Fill Whole Site
How to Reset or Override Ie CSS Filters
How to Prevent CSS3 Animation Reset When Finished
Bootstrap 3 Changing Div Order on Small Screens Only
Align Right in a Table Cell with CSS
CSS Fixed Position with Auto Margin
What CSS3 Features Still Need Vendor Prefixes
Html5 Vertical Spacing Issue with <Img>
How to Use the Matrix Transform and Other Transform CSS Properties