I need to make a rectangle with the following things in mind:

I've tried using SVG and got it working except point 3.
My attempt now is to use 3 svgs (one for the left/right half circle and one for the middle part and position them absolutely but i can't get it to work just yet.

The middle part shouldn't scale to 100% height but im not familiar enough with svg scaling options.
Im using React and Glamor but that shouldnt matter for this. (snippet doesnt work because of dependencies, but you should get the issue)
import React from 'react';
import ReactDOM from 'react-dom';
import { css, style, after } from 'glamor';
const SectionTag = ({ className, name, url, height, borderWidth, fontSize, theme, fillColor }) => {
const styles = {
main: {
padding: 0,
display: 'block',
},
inline: style({
display: 'inline-block',
verticalAlign: 'top',
}),
textWrapper: style({
position: 'relative'
}),
background: style({
position: 'absolute',
top: 0,
left: 0,
right: 0,
bottom: 0,
width: '100%',
}),
text: css({
zIndex: 1,
position: 'relative',
color: theme.accentColor,
fontSize: fontSize,
lineHeight: 1,
textTransform: 'uppercase',
padding: '8px 1px',
height,
margin: 0,
}),
};
return (
<div className={css(className, styles.main)}>
<svg
xmlns="http://www.w3.org/2000/svg"
width={height / 2}
height={height}
viewBox={`0 0 ${height / 2} ${height}`}
className={styles.inline}
>
<rect rx={height / 2} ry={height / 2} x={borderWidth / 2} y={borderWidth / 2}
width={(height * 2) - (borderWidth)}
height={height - (borderWidth)}
style={{
fill: fillColor,
stroke: `url(#gradient-${name.replace(/ /g, '-').toLowerCase()})`,
strokeWidth: borderWidth
}} />
</svg>
<div className={css(styles.textWrapper, styles.inline)}>
<svg
xmlns="http://www.w3.org/2000/svg"
height={height}
viewBox={`0 0 ${height - 4} ${height}`}
className={css(styles.background)}
preserveAspectRatio="xMidYMin slice"
>
<linearGradient id={`gradient-${name.replace(/ /g, '-').toLowerCase()}`}>
<stop offset="0" style={{ stopColor: theme.leftColor }} />
<stop offset="1" style={{ stopColor: theme.rightColor }} />
</linearGradient>
<rect
x={-borderWidth}
y={0}
width={height - (borderWidth * 2)}
height={height - (borderWidth * 2)}
style={{
fill: fillColor,
stroke: `url(#gradient-${name.replace(/ /g, '-').toLowerCase()})`,
strokeWidth: borderWidth,
vectorEffect: 'non-scaling-stroke',
height: height,
top: 0,
padding: 0,
margin: 0,
}} />
</svg>
<p
height={height}
className={css(styles.text, styles.inline)}
>
{name}
</p>
</div>
<svg
xmlns="http://www.w3.org/2000/svg"
width={height / 2}
height={height}
viewBox={`0 0 ${height / 2} ${height}`}
className={styles.inline}
>
<rect rx={height / 2} ry={height / 2} x={-(height * 1.5)} y={borderWidth / 2}
width={(height * 2) - (borderWidth)}
height={height - (borderWidth)}
style={{
fill: fillColor,
stroke: `url(#gradient-${name.replace(/ /g, '-').toLowerCase()})`,
strokeWidth: borderWidth
}} />
</svg>
</div>
);
};
SectionTag.propTypes = {};
SectionTag.defaultProps = {
name: 'default',
height: 29,
borderWidth: 1,
fontSize: 10,
fillColor: 'rgba(255, 255, 255, .8)',
theme: {
leftColor: 'rgba(255, 188, 0, 0.31)',
rightColor: '#ff0000',
accentColor: '#f9811b'
}
};
const mountNode = document.querySelector('.el');
ReactDOM.render(<SectionTag name="Jane" />, mountNode);
<script src="https://cdnjs.cloudflare.com/ajax/libs/react/15.1.0/react.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/react/15.1.0/react-dom.min.js"></script>
<div id="el"></div>
Got it! The positioning of the middle part of the gradient was a bit tricky but here's my code:

import React from 'react';
import { css, style } from 'glamor';
const SectionTag = ({ className, name, url, height, borderWidth, fontSize, theme, fillColor }) => {
const styles = {
main: {
padding: 0,
display: 'block',
},
inline: style({
display: 'inline-block',
verticalAlign: 'top',
}),
textWrapper: style({
position: 'relative',
height,
}),
background: style({
position: 'absolute',
top: 0,
left: 0,
right: 0,
zIndex: 0,
}),
text: css({
zIndex: 2,
position: 'relative',
color: theme.accentColor,
fontSize: fontSize,
lineHeight: 1,
textTransform: 'uppercase',
padding: `${(height - fontSize)/2}px 1px`,
margin: 0,
}),
};
return (
<div className={css(className, styles.main)}>
<svg
xmlns="http://www.w3.org/2000/svg"
width={height / 2}
height={height}
viewBox={`0 0 ${height / 2} ${height}`}
className={styles.inline}
>
<rect rx={height / 2} ry={height / 2} x={borderWidth / 2} y={borderWidth / 2}
width={(height * 2) - (borderWidth)}
height={height - (borderWidth)}
style={{
fill: fillColor,
stroke: `url(#gradient-${name.replace(/ /g, '-').toLowerCase()})`,
strokeWidth: borderWidth,
vectorEffect: 'non-scaling-stroke',
}} />
</svg>
<div className={css(styles.textWrapper, styles.inline)}>
<p
height={height}
className={css(styles.text, styles.inline)}
>
{name}
</p>
<svg
xmlns="http://www.w3.org/2000/svg"
height={height}
width="100%"
className={css(styles.background)}
>
<linearGradient id={`gradient-${name.replace(/ /g, '-').toLowerCase()}`}>
<stop offset="0" style={{ stopColor: theme.leftColor }} />
<stop offset="1" style={{ stopColor: theme.rightColor }} />
</linearGradient>
<rect
x={-height}
y={borderWidth/2}
height={height- (borderWidth)}
style={{
width: `calc(100% + ${height * 2}px)`,
fill: fillColor,
stroke: `url(#gradient-${name.replace(/ /g, '-').toLowerCase()})`,
strokeWidth: borderWidth,
vectorEffect: 'non-scaling-stroke',
}} />
</svg>
</div>
<svg
xmlns="http://www.w3.org/2000/svg"
width={height / 2}
height={height}
viewBox={`0 0 ${height / 2} ${height}`}
className={styles.inline}
>
<rect rx={height / 2} ry={height / 2} x={-(height * 1.5)} y={borderWidth / 2}
width={(height * 2) - (borderWidth)}
height={height - (borderWidth)}
style={{
fill: fillColor,
stroke: `url(#gradient-${name.replace(/ /g, '-').toLowerCase()})`,
strokeWidth: borderWidth
}} />
</svg>
</div>
);
};
SectionTag.propTypes = {};
SectionTag.defaultProps = {
name: 'default',
height: 29,
borderWidth: 1,
fontSize: 10,
fillColor: 'rgba(255, 255, 255, .8)',
theme: {
leftColor: '#73abff',
rightColor: '#ff8c2b',
accentColor: '#0000FF'
}
};
export default SectionTag;
<script src="https://cdnjs.cloudflare.com/ajax/libs/react/15.1.0/react.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/react/15.1.0/react-dom.min.js"></script>
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With