5

I need to create a fluid shape with a cut off corner and a border. The shape needs to be able to sit on an unknown background. This in itself isn't an issue but I also need the background of this element/s to be semi-opaque.

Here's what I have so far...

* {
  -webkit-box-sizing: border-box;
  -moz-box-sizing: border-box;
  box-sizing: border-box;
}

body {
    background: pink;
}

.sidebar-widget {
    border: 1px solid #44AAAB;
    border-right: none;
    border-bottom: none;
    position: relative;
    padding: 15px 0 0 15px;
    margin-bottom: 20px;
}

.sidebar-widget .inner {
    position: relative;
    padding: 15px 0 0 15px;
    left: -15px;
    top: -15px;
    background: #f2f2f2;
}

.sidebar-widget .inner:before {
    content: "";
    width: 100%;
    height: 15px;
    background: #f2f2f2;
    border: 1px solid #44AAAB;
    border-right: none;
    border-top: none;
    position: absolute;
    left: -1px;
    bottom: -16px;
}

.sidebar-widget .inner .content:after {
    content: "";
    width: 15px;
    height: 100%;
    background: #f2f2f2;
    border: 1px solid #44AAAB;
    border-left: none;
    border-bottom: none;
    position: absolute;
    right: -16px;
    top: -1px;
}

.corner {
    width: 22px;
    height: 22px;
    border-right: 1px solid #44AAAB;
    background: #f2f2f2;
    position: absolute;
    right: 4px;
    bottom: 4px;
    transform: rotate(45deg);
    z-index: 1;
}

.sidebar-widget.trans-bg .inner,
.sidebar-widget.trans-bg .inner:before,
.sidebar-widget.trans-bg .inner .content:after,
.trans-bg .corner {
    background: rgba(0,0,0,0.5);
}
<div class="sidebar-widget">
    <div class="corner"></div>
    <div class="inner">
        <div class="content">
            Lorem ipsum dolor sit amet, consectetur adipiscing elit. Nam tellus felis, faucibus id velit eget, auctor tristique ex. Pellentesque id dolor risus. Donec tincidunt, nisl id laoreet tristique, ligula magna placerat mi, id congue magna diam ut sem. Aenean ornare eros nec sapien porta, laoreet venenatis est lobortis.
        </div>
    </div>
</div>

<div class="sidebar-widget trans-bg">
    <div class="corner"></div>
    <div class="inner">
        <div class="content">
            Lorem ipsum dolor sit amet, consectetur adipiscing elit. Nam tellus felis, faucibus id velit eget, auctor tristique ex. Pellentesque id dolor risus. Donec tincidunt, nisl id laoreet tristique, ligula magna placerat mi, id congue magna diam ut sem. Aenean ornare eros nec sapien porta, laoreet venenatis est lobortis.
        </div>
    </div>
</div>

This approach works when the element has solid background but as you can see the square element used to create the cut-off corner is clearly visible when using a semi-opaque background. Can anyone think of a way to get around this?

JSFiddle version

web-tiki
  • 99,765
  • 32
  • 217
  • 249
Turnip
  • 35,836
  • 15
  • 89
  • 111
  • I’d say, probably easiest to use `border-image` for this kind of effect. – CBroe Mar 16 '15 at 13:01
  • There are several ways to achieve your layout described here : [Div with cut out edges, border and transparent background](http://stackoverflow.com/questions/12030835/div-with-cut-out-edges-border-and-transparent-background) – web-tiki Mar 16 '15 at 13:09
  • Hi @web-tiki not sure how i managed to miss that question. I tried your solution but unfortunately it relies on a fixed height which I don't have. There are also some issues with the rendering of border widths which I can't live with – Turnip Mar 16 '15 at 14:25
  • @uʍopǝpısdn I would suggest using [this approach](http://stackoverflow.com/a/28741674/1811992) in the linked question. – web-tiki Mar 16 '15 at 14:29
  • that solution also doesn't work with fluid height elements – Turnip Mar 16 '15 at 14:31

2 Answers2

3

For anyone who is interested here is how I ended up doing it.

Wrap the .corner in another element with overflow: hidden;

* {
  -webkit-box-sizing: border-box;
  -moz-box-sizing: border-box;
  box-sizing: border-box;
}

body {
    background: pink;
}

.sidebar-widget {
    border: 1px solid #44AAAB;
    border-right: none;
    border-bottom: none;
    position: relative;
    padding: 15px 0 0 15px;
    margin-bottom: 20px;
}

.sidebar-widget .inner {
    position: relative;
    padding: 15px 0 0 15px;
    left: -15px;
    top: -15px;
    background: #f2f2f2;
}

.sidebar-widget .inner:before {
    content: "";
    width: 100%;
    height: 15px;
    background: #f2f2f2;
    border: 1px solid #44AAAB;
    border-right: none;
    border-top: none;
    position: absolute;
    left: -1px;
    bottom: -16px;
}

.sidebar-widget .inner .content:after {
    content: "";
    width: 15px;
    height: 100%;
    background: #f2f2f2;
    border: 1px solid #44AAAB;
    border-left: none;
    border-bottom: none;
    position: absolute;
    right: -16px;
    top: -1px;
}

.corner-mask {
    width: 15px;
    height: 15px;
    position: absolute;
    right: 0;
    bottom: 0;
    overflow: hidden;
}

.corner {
    width: 22px;
    height: 22px;
    border-right: 1px solid #44AAAB;
    background: #f2f2f2;
    position: absolute;
    right: 4px;
    bottom: 4px;
    -webkit-transform: rotate(45deg);
    -moz-transform: rotate(45deg);
    transform: rotate(45deg);
    z-index: 1;
}

.sidebar-widget.trans-bg .inner,
.sidebar-widget.trans-bg .inner:before,
.sidebar-widget.trans-bg .inner .content:after,
.trans-bg .corner {
    background: rgba(0,0,0,0.5);
}
<div class="sidebar-widget">
    <div class="corner-mask">
        <div class="corner"></div>
    </div>
    <div class="inner">
        <div class="content">
            Lorem ipsum dolor sit amet, consectetur adipiscing elit. Nam tellus felis, faucibus id velit eget, auctor tristique ex. Pellentesque id dolor risus. Donec tincidunt, nisl id laoreet tristique, ligula magna placerat mi, id congue magna diam ut sem. Aenean ornare eros nec sapien porta, laoreet venenatis est lobortis.
        </div>
    </div>
</div>

<div class="sidebar-widget trans-bg">
    <div class="corner-mask">
        <div class="corner"></div>
    </div>
    <div class="inner">
        <div class="content">
            Lorem ipsum dolor sit amet, consectetur adipiscing elit. Nam tellus felis, faucibus id velit eget, auctor tristique ex. Pellentesque id dolor risus. Donec tincidunt, nisl id laoreet tristique, ligula magna placerat mi, id congue magna diam ut sem. Aenean ornare eros nec sapien porta, laoreet venenatis est lobortis.
        </div>
    </div>
</div>

JSFiddle version

Turnip
  • 35,836
  • 15
  • 89
  • 111
0

You can use another element inside .corner, see the example below:

<style>
    .corner, .corner_inner { /* added .corner_inner to your styles */
        width: 22px; 
        height: 22px; 
        border-right: 1px solid #44AAAB; 
        background: #f2f2f2; 
        position: absolute; 
        right: 4px; 
        bottom: 4px; 
        transform: rotate(45deg); 
        z-index: 1;
    }

    .trans-bg .corner {background: transparent} /* overwrite the background above */

    .trans-bg .corner_inner { /* set background and position for inner element */
        width: 11px; 
        height: 11px; 
        right: -1px; 
        bottom: 0; 
        background: rgba(0,0,0,0.5);
    }
</style>

<div class="sidebar-widget trans-bg">
    <div class="corner">
        <div class="corner_inner"></div>
    </div>
    ...
</div>

http://jsfiddle.net/6Lyph6zj/3/

I've edited your styles, some properties are overwritten and can be removed. I mean you can understand better what changes I've made.

pavel
  • 26,538
  • 10
  • 45
  • 61
  • 2
    Hi @panther. Your fiddle displays like this ... http://s12.postimg.org/iu2le8nrh/cut_corner_copy.png – Turnip Mar 16 '15 at 13:09
  • @uʍopǝpısdn: hm, strange. In safari it seems exactly the same as your code. I can't test it more, but the way with the inner elements (with background) and setting transparent background to `.corner` should be right. – pavel Mar 16 '15 at 13:11