Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Rgb #53

Merged
merged 9 commits into from Dec 17, 2016
Merged

Rgb #53

Show file tree
Hide file tree
Changes from 7 commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Jump to
Jump to file
Failed to load files.
Diff view
Diff view
46 changes: 46 additions & 0 deletions src/helpers/rgb.js
@@ -0,0 +1,46 @@
// @flow

import reduceHexValue from '../internalHelpers/_reduceHexValue'
import toHex from '../internalHelpers/_numberToHex'

/**
* Returns a string value for the color. The returned result is the smalles possible hex notation.
*
* @example
* // Styles as object usage
* const styles = {
* background: rgb(255, 205, 100),
* background: rgb({ red: 255, green: 205, blue: 100 }),
* }
*
* // styled-components usage
* const div = styled.div`
* background: ${rgb(255, 205, 100)};
* background: ${rgb({ red: 255, green: 205, blue: 100 })};
* `
*
* // CSS in JS Output
*
* element {
* background: "#ffcd64";
* background: "#ffcd64";
* }
*/

type RgbColor = {
red: number,
green: number,
blue: number,
}

function rgb(value: RgbColor | number, green?: number, blue?: number): string {
if (typeof value === 'number' && typeof green === 'number' && typeof blue === 'number') {
return reduceHexValue(`#${toHex(value)}${toHex(green)}${toHex(blue)}`)
} else if (typeof value === 'object' && green === undefined && blue === undefined) {
return reduceHexValue(`#${toHex(value.red)}${toHex(value.green)}${toHex(value.blue)}`)
}

throw new Error('Passed invalid arguments to rgb, please pass multiple numbers e.g. rgb(255, 205, 100) or an object e.g. rgb({ red: 255, green: 205, blue: 100 }).')
}

export default rgb
17 changes: 17 additions & 0 deletions src/helpers/test/__snapshots__/rgb.test.js.snap
@@ -0,0 +1,17 @@
exports[`rgb should convert a rgb object to a hex color 1`] = `
Object {
"background": "#ffcd64",
}
`;

exports[`rgb should convert multiple numbers to a hex color 1`] = `
Object {
"background": "#ffcd64",
}
`;

exports[`rgb should convert to a reduce hex value if possible 1`] = `
Object {
"background": "#fff",
}
`;
21 changes: 21 additions & 0 deletions src/helpers/test/rgb.test.js
@@ -0,0 +1,21 @@
// @flow
import rgb from '../rgb'

describe('rgb', () => {
it('should convert multiple numbers to a hex color', () => {
expect({ background: rgb(255, 205, 100) }).toMatchSnapshot()
})

it('should convert a rgb object to a hex color', () => {
expect({ background: rgb({ red: 255, green: 205, blue: 100 }) }).toMatchSnapshot()
})

it('should convert to a reduce hex value if possible', () => {
expect({ background: rgb({ red: 255, green: 255, blue: 255 }) }).toMatchSnapshot()
})

it('should throw an error if an object and multiple arguments are passed', () => {
expect(() => ({ background: rgb({ red: 255, green: 1, blue: 1 }, 250, 100) }))
.toThrow('Passed invalid arguments to rgb, please pass multiple numbers e.g. rgb(255, 205, 100) or an object e.g. rgb({ red: 255, green: 205, blue: 100 }).')
})
})
8 changes: 8 additions & 0 deletions src/internalHelpers/_numberToHex.js
@@ -0,0 +1,8 @@
// @flow

function numberToHex(value: number): string {
const hex = value.toString(16)
return hex.length === 1 ? `0${hex}` : hex
}

export default numberToHex
14 changes: 14 additions & 0 deletions src/internalHelpers/_reduceHexValue.js
@@ -0,0 +1,14 @@
// @flow

/**
* Reduces hex values if possible e.g. #ff8866 to #f86
* @private
*/
const reduceHexValue = (value: string): string => {
if (value.length === 7 && value[1] === value[2] && value[3] === value[4] && value[5] === value[6]) {
return `#${value[1]}${value[3]}${value[5]}`
}
return value
}

export default reduceHexValue
@@ -0,0 +1,7 @@
exports[`numberToHex should convert 0 to "00" 1`] = `"00"`;

exports[`numberToHex should convert 15 to "0f" 1`] = `"0f"`;

exports[`numberToHex should convert 16 to "10" 1`] = `"10"`;

exports[`numberToHex should convert 17 to "11" 1`] = `"11"`;
@@ -0,0 +1,9 @@
exports[`reduceHexValue should not reduce #112234 1`] = `"#112234"`;

exports[`reduceHexValue should not reduce #fff 1`] = `"#fff"`;

exports[`reduceHexValue should reduce #884422 to #842 1`] = `"#842"`;

exports[`reduceHexValue should reduce #ffffff to #fff 1`] = `"#fff"`;

exports[`reduceHexValue should return the value in case it can not be reduced 1`] = `"You rock!"`;
19 changes: 19 additions & 0 deletions src/internalHelpers/test/_numberToHex.test.js
@@ -0,0 +1,19 @@
import numberToHex from '../_numberToHex'

describe('numberToHex', () => {
it('should convert 0 to "00"', () => {
expect(numberToHex(0)).toMatchSnapshot()
})

it('should convert 15 to "0f"', () => {
expect(numberToHex(15)).toMatchSnapshot()
})

it('should convert 16 to "10"', () => {
expect(numberToHex(16)).toMatchSnapshot()
})

it('should convert 17 to "11"', () => {
expect(numberToHex(17)).toMatchSnapshot()
})
})
23 changes: 23 additions & 0 deletions src/internalHelpers/test/_reduceHexValue.test.js
@@ -0,0 +1,23 @@
import reduceHexValue from '../_reduceHexValue'

describe('reduceHexValue', () => {
it('should reduce #ffffff to #fff', () => {
expect(reduceHexValue('#ffffff')).toMatchSnapshot()
})

it('should reduce #884422 to #842', () => {
expect(reduceHexValue('#884422')).toMatchSnapshot()
})

it('should not reduce #112234', () => {
expect(reduceHexValue('#112234')).toMatchSnapshot()
})

it('should not reduce #fff', () => {
expect(reduceHexValue('#fff')).toMatchSnapshot()
})

it('should return the value in case it can not be reduced', () => {
expect(reduceHexValue('You rock!')).toMatchSnapshot()
})
})