Skip to content

Commit

Permalink
feat: add radial gradients (#15)
Browse files Browse the repository at this point in the history
* feat: add radial gradient support
* fixed: linting errors
* chore: update README with radial gradient examples
* chore: remove Contributors section of README
  • Loading branch information
matthamil authored and AriTheElk committed Dec 8, 2016
1 parent 405efce commit 08092ed
Show file tree
Hide file tree
Showing 4 changed files with 182 additions and 12 deletions.
122 changes: 116 additions & 6 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -7,9 +7,9 @@
## Installation

npm install --save uigradients

## Examples
### Gradient Component
### Linear Gradient Component

``` jsx
// Import the component...
Expand All @@ -28,10 +28,28 @@ class App extends Component {
```
> ###### `cherry` is only one of the many presets provided by [_`uigradients`_](https://jsbros.github.io/uigradients/)
> A complete list of the gradient presets can be previewed [here](https://595f03bc-218b-4dc7-9045-df52791c557f.sbook.io/?selectedKind=Gradient%20Component&selectedStory=Color%20Previews&full=0&down=1&left=1&panelRight=0&downPanel=kadirahq%2Fstorybook-addon-actions%2Factions-panel).
> Test out these presets, or create your own! But be sure to
[**PR your creation**](https://github.com/JSBros/uigradients/compare) so the
rest of the community can benefit from your ascetic awesomeness!
> Test out these presets, or create your own! But be sure to
[**PR your creation**](https://github.com/JSBros/uigradients/compare) so the
rest of the community can benefit from your ascetic awesomeness!
### Radial Gradient Component
``` jsx
import { Gradient } from 'uigradients';
class App extends Component {
return (
// Add a "type" attribute on your component and
// set it to "radial" for a radial gradient!
// NOTE: If a "type" attribute is not on
// your component, the gradient type will
// default to linear
<Gradient gradient="aubergine" type="radial">
<h1>Wow, a radial gradient!</h1>
</Gradient>
);
}
```
### Gradient Generator
Expand All @@ -40,7 +58,7 @@ import { generator } from 'uigradients';
generator({gradient: 'intuitive_purple'});
/* The function above returns:
/* The function above returns:
background-color: ,#DA22FF,;
background-image: -webkit-linear-gradient(
left,
Expand All @@ -53,6 +71,59 @@ background-image: linear-gradient(
*/
```
uiGradients also supports [radial gradients](https://developer.mozilla.org/en-US/docs/Web/CSS/radial-gradient).
When using the `generator` function to create a radial gradient, two additional properties of `type` and `options` should be present on the object passed into `generator`.
The `type` and `options` properties are only required when generating a radial gradient. Passing an object with only a `gradient` property will generate a linear gradient.
``` jsx
import { generator } from 'uigradients';
generator({
gradient: 'intuitive_purple',
type: 'radial',
options: {
position: '45px 20px',
shape: 'ellipse', // 'circle' or 'ellipse'
colorStops: ['20%', '50%'], // Can be percentage or pixel values
extent: 'farthest-corner'
}
});
/* The function above returns:
background-image: -webkit-radial-gradient(
ellipse farthest-corner at 45px 20px,
#DA22FF 20%,
#9733EE 50%);
background-image: radial-gradient(
ellipse farthest-corner at 45px 20px,
#DA22FF 20%,
#9733EE 50%);
*/
```
#### Configuring the `options` for a Radial Gradient
If using the `generator` function to create a radial gradient, the following properties are valid configurations for a radial gradient:
```js
{
gradient: 'electric_violet',
type: 'radial'
options: {
position: '45px 20px', // defaults to center if omitted
shape: 'ellipse', // defaults to circle if omitted
colorStops: ['20%', '50%'], // the stop position for each color
extent: 'farthest-corner' // valid options are closest-side, closest-corner, farthest-side, and farthest-corner
}
}
```
Each property on the `options` object maps to the CSS values for [radial-gradient](https://developer.mozilla.org/en-US/docs/Web/CSS/radial-gradient).
NOTE: When using the `extent` property, the `position` property must also be set.
### <💅> Styled Components
#### Use the Generator in a styled-component
Expand Down Expand Up @@ -88,6 +159,45 @@ const Header = styled(Gradient)`
![Awesome!](http://imgur.com/7G9C4eN.png)
#### Or, you can generate a radial gradient
```js
import { generator } from 'uigradients';
import styled from 'styled-components';
const RadialComponent = styled.div`
${generator({gradient: 'electric_violet', type: 'radial'})}
`;
```
#### And render the component
![Radial gradient](https://i.imgur.com/PcyFqtx.jpg)
#### Customize a radial gradient
```js
import { generator } from 'uigradients';
import styled from 'styled-components';
const RadialComponent = styled.div`
${generator({
gradient: 'electric_violet',
type: 'radial',
options: {
position: '45px 20px',
shape: 'ellipse',
colorStops: ['20%', '50%'],
extent: 'farthest-corner'
}
}
)}`;
```
#### And render the component
![Custom radial gradient](http://i.imgur.com/ESjCRbI.jpg)
## Author
Built by [Garet McKinley](https://github.com/garetmckinley)
Expand Down
3 changes: 2 additions & 1 deletion src/components/gradient.js
Original file line number Diff line number Diff line change
Expand Up @@ -13,7 +13,8 @@ function GradientContainer(props) {
GradientContainer.propTypes = {
className: React.PropTypes.string,
gradient: React.PropTypes.string,
angle: React.PropTypes.number
angle: React.PropTypes.number,
type: React.PropTypes.string
};

GradientContainer.defaultProps = {
Expand Down
53 changes: 53 additions & 0 deletions src/generator.js
Original file line number Diff line number Diff line change
@@ -1,6 +1,54 @@
import { css } from 'styled-components';
import { gradients, randomGradientName } from './gradients';

function generateRadialGradientCss(options, gradientColors) {
const { shape, position, extent, colorStops } = options;
return css`background-image: -webkit-radial-gradient(
${shape} ${extent} at ${position},
${gradientColors[0]} ${colorStops[0]},
${gradientColors[1]} ${colorStops[1]});
background-image: -moz-radial-gradient(
${shape} ${extent} at ${position},
${gradientColors[0]} ${colorStops[0]},
${gradientColors[1]} ${colorStops[1]});
background-image: -o-radial-gradient(
${shape} ${extent} at ${position},
${gradientColors[0]} ${colorStops[0]},
${gradientColors[1]} ${colorStops[1]});
background-image: radial-gradient(
${shape} ${extent} at ${position},
${gradientColors[0]} ${colorStops[0]},
${gradientColors[1]} ${colorStops[1]});`;
}

function configRadialGradientOptions(options = {}) {
const { position, shape, colorStops, extent } = options;
const radialConfig = {};
if (position) {
radialConfig.position = position;
} else {
radialConfig.position = 'center';
}
if (shape && (shape === 'circle' || shape === 'ellipse')) {
radialConfig.shape = shape;
} else {
radialConfig.shape = 'circle';
}
if (Array.isArray(colorStops)) {
radialConfig.colorStops = colorStops;
} else {
radialConfig.colorStops = ['', ''];
}
if (extent === 'closest-side' ||
extent === 'closest-corner' ||
extent === 'farthest-side' ||
extent === 'farthest-corner') {
radialConfig.extent = extent;
} else {
radialConfig.extent = '';
}
return radialConfig;
}

function generator(props = {}) {
let gradient = '';
Expand All @@ -13,6 +61,11 @@ function generator(props = {}) {
if (props.angle !== undefined) {
angle = props.angle;
}
const { type, options } = props;
if (type === 'radial') {
const config = configRadialGradientOptions(options);
return generateRadialGradientCss(config, gradients[gradient]);
}
return css`background-color: ${gradients[gradient][0]};
background-image: -webkit-linear-gradient(
${angle}deg,
Expand Down
16 changes: 11 additions & 5 deletions stories/index.js
Original file line number Diff line number Diff line change
Expand Up @@ -24,11 +24,17 @@ map.forEach(function (value, key) {
});

storiesOf('Gradient Component', module)
.add('Color Previews', () => (
.add('Linear Gradient Previews', () => (
<div>
{GradientPreviews.map(function (value) {
return (<Preview gradient={value}>{value}</Preview>)
})}
{GradientPreviews.map(function (value, id) {
return (<Preview gradient={value} key={id}>{value}</Preview>)
})}
</div>
))
.add('Radial Gradient Previews', () => (
<div>
{GradientPreviews.map(function (value, id) {
return (<Preview gradient={value} key={id} type={'radial'}>{value}</Preview>)
})}
</div>
));

0 comments on commit 08092ed

Please sign in to comment.