From aa766021662250339edf01f37b0d7a047babc2e3 Mon Sep 17 00:00:00 2001 From: Jacob Parker Date: Sat, 16 Nov 2019 18:05:39 +0000 Subject: [PATCH 1/3] Add support for directional border shorthands --- src/__tests__/border.js | 100 ++++++++++++++++++++++++++++------- src/__tests__/borderRight.js | 47 ++++++++++++++++ src/__tests__/colors.js | 10 +++- src/__tests__/units.js | 27 +++++++--- src/transforms/border.js | 49 ++++++++++++++++- src/transforms/index.js | 11 +++- 6 files changed, 211 insertions(+), 33 deletions(-) create mode 100644 src/__tests__/borderRight.js diff --git a/src/__tests__/border.js b/src/__tests__/border.js index 31c9a08..2d39f85 100644 --- a/src/__tests__/border.js +++ b/src/__tests__/border.js @@ -2,80 +2,140 @@ import transformCss from '..' it('transforms border none', () => { expect(transformCss([['border', 'none']])).toEqual({ - borderWidth: 0, - borderColor: 'black', + borderTopWidth: 0, + borderRightWidth: 0, + borderBottomWidth: 0, + borderLeftWidth: 0, + borderTopColor: 'black', + borderRightColor: 'black', + borderBottomColor: 'black', + borderLeftColor: 'black', borderStyle: 'solid', }) }) it('transforms border shorthand', () => { expect(transformCss([['border', '2px dashed #f00']])).toEqual({ - borderWidth: 2, - borderColor: '#f00', + borderTopWidth: 2, + borderRightWidth: 2, + borderBottomWidth: 2, + borderLeftWidth: 2, + borderTopColor: '#f00', + borderRightColor: '#f00', + borderBottomColor: '#f00', + borderLeftColor: '#f00', borderStyle: 'dashed', }) }) it('transforms border shorthand in other order', () => { expect(transformCss([['border', '#f00 2px dashed']])).toEqual({ - borderWidth: 2, - borderColor: '#f00', + borderTopWidth: 2, + borderRightWidth: 2, + borderBottomWidth: 2, + borderLeftWidth: 2, + borderTopColor: '#f00', + borderRightColor: '#f00', + borderBottomColor: '#f00', + borderLeftColor: '#f00', borderStyle: 'dashed', }) }) it('transforms border shorthand missing color', () => { expect(transformCss([['border', '2px dashed']])).toEqual({ - borderWidth: 2, - borderColor: 'black', + borderTopWidth: 2, + borderRightWidth: 2, + borderBottomWidth: 2, + borderLeftWidth: 2, + borderTopColor: 'black', + borderRightColor: 'black', + borderBottomColor: 'black', + borderLeftColor: 'black', borderStyle: 'dashed', }) }) it('transforms border shorthand missing style', () => { expect(transformCss([['border', '2px #f00']])).toEqual({ - borderWidth: 2, - borderColor: '#f00', + borderTopWidth: 2, + borderRightWidth: 2, + borderBottomWidth: 2, + borderLeftWidth: 2, + borderTopColor: '#f00', + borderRightColor: '#f00', + borderBottomColor: '#f00', + borderLeftColor: '#f00', borderStyle: 'solid', }) }) it('transforms border shorthand missing width', () => { expect(transformCss([['border', '#f00 dashed']])).toEqual({ - borderWidth: 1, - borderColor: '#f00', + borderTopWidth: 1, + borderRightWidth: 1, + borderBottomWidth: 1, + borderLeftWidth: 1, + borderTopColor: '#f00', + borderRightColor: '#f00', + borderBottomColor: '#f00', + borderLeftColor: '#f00', borderStyle: 'dashed', }) }) it('transforms border shorthand missing color & width', () => { expect(transformCss([['border', 'dashed']])).toEqual({ - borderWidth: 1, - borderColor: 'black', + borderTopWidth: 1, + borderRightWidth: 1, + borderBottomWidth: 1, + borderLeftWidth: 1, + borderTopColor: 'black', + borderRightColor: 'black', + borderBottomColor: 'black', + borderLeftColor: 'black', borderStyle: 'dashed', }) }) it('transforms border shorthand missing style & width', () => { expect(transformCss([['border', '#f00']])).toEqual({ - borderWidth: 1, - borderColor: '#f00', + borderTopWidth: 1, + borderRightWidth: 1, + borderBottomWidth: 1, + borderLeftWidth: 1, + borderTopColor: '#f00', + borderRightColor: '#f00', + borderBottomColor: '#f00', + borderLeftColor: '#f00', borderStyle: 'solid', }) }) it('transforms border shorthand missing color & style', () => { expect(transformCss([['border', '2px']])).toEqual({ - borderWidth: 2, - borderColor: 'black', + borderTopWidth: 2, + borderRightWidth: 2, + borderBottomWidth: 2, + borderLeftWidth: 2, + borderTopColor: 'black', + borderRightColor: 'black', + borderBottomColor: 'black', + borderLeftColor: 'black', borderStyle: 'solid', }) }) it('transforms border for unsupported units', () => { expect(transformCss([['border', '3em solid black']])).toEqual({ - borderWidth: '3em', - borderColor: 'black', + borderTopWidth: '3em', + borderRightWidth: '3em', + borderBottomWidth: '3em', + borderLeftWidth: '3em', + borderTopColor: 'black', + borderRightColor: 'black', + borderBottomColor: 'black', + borderLeftColor: 'black', borderStyle: 'solid', }) }) diff --git a/src/__tests__/borderRight.js b/src/__tests__/borderRight.js new file mode 100644 index 0000000..4aab147 --- /dev/null +++ b/src/__tests__/borderRight.js @@ -0,0 +1,47 @@ +import transformCss from '..' + +it('transforms border none', () => { + expect(transformCss([['border-right', 'none']])).toEqual({ + borderRightWidth: 0, + borderRightColor: 'black', + }) +}) + +it('transforms border shorthand in other order', () => { + expect(transformCss([['border-right', '#f00 2px']])).toEqual({ + borderRightWidth: 2, + borderRightColor: '#f00', + }) +}) + +it('transforms border shorthand missing width', () => { + expect(transformCss([['border-right', '#f00']])).toEqual({ + borderRightWidth: 1, + borderRightColor: '#f00', + }) +}) + +it('transforms border shorthand missing color', () => { + expect(transformCss([['border-right', '2px']])).toEqual({ + borderRightWidth: 2, + borderRightColor: 'black', + }) +}) + +it('transforms border for unsupported units', () => { + expect(transformCss([['border-right', '3em black']])).toEqual({ + borderRightWidth: '3em', + borderRightColor: 'black', + }) +}) + +it('does not transform border with percentage width', () => { + expect(() => transformCss([['border-right', '3% black']])).toThrow() +}) + +it('does not transform style', () => { + expect(() => transformCss([['border-right', '2px dashed #f00']])).toThrow() + expect(() => transformCss([['border-right', 'dashed #f00']])).toThrow() + expect(() => transformCss([['border-right', '2px dashed']])).toThrow() + expect(() => transformCss([['border-right', 'dashed']])).toThrow() +}) diff --git a/src/__tests__/colors.js b/src/__tests__/colors.js index 9a0fe62..f919ac3 100644 --- a/src/__tests__/colors.js +++ b/src/__tests__/colors.js @@ -18,9 +18,15 @@ it('transforms transparent color', () => { it('transforms border shorthand with transparent color', () => { expect(transformCss([['border', '2px dashed transparent']])).toEqual({ - borderColor: 'transparent', + borderTopWidth: 2, + borderRightWidth: 2, + borderBottomWidth: 2, + borderLeftWidth: 2, + borderTopColor: 'transparent', + borderRightColor: 'transparent', + borderBottomColor: 'transparent', + borderLeftColor: 'transparent', borderStyle: 'dashed', - borderWidth: 2, }) }) diff --git a/src/__tests__/units.js b/src/__tests__/units.js index d1a13f8..1ce1f60 100644 --- a/src/__tests__/units.js +++ b/src/__tests__/units.js @@ -2,7 +2,8 @@ import transformCss from '..' // List of units from: // https://developer.mozilla.org/en-US/docs/Web/CSS/length -const lengthUnits = [ + +describe.each([ 'ch', 'em', 'ex', @@ -16,9 +17,7 @@ const lengthUnits = [ 'in', 'pc', 'pt', -] - -lengthUnits.forEach(unit => { +])('Handles unit: %s', unit => { const value = `2${unit}` it('allows CSS length units in transformed values', () => { @@ -56,14 +55,26 @@ lengthUnits.forEach(unit => { it('allows units to be used with border shorthand property', () => { expect(transformCss([['border', `#f00 ${value} dashed`]])).toEqual({ - borderWidth: value, - borderColor: '#f00', + borderTopWidth: value, + borderRightWidth: value, + borderBottomWidth: value, + borderLeftWidth: value, + borderTopColor: '#f00', + borderRightColor: '#f00', + borderBottomColor: '#f00', + borderLeftColor: '#f00', borderStyle: 'dashed', }) expect(transformCss([['border', value]])).toEqual({ - borderWidth: value, - borderColor: 'black', + borderTopWidth: value, + borderRightWidth: value, + borderBottomWidth: value, + borderLeftWidth: value, + borderTopColor: 'black', + borderRightColor: 'black', + borderBottomColor: 'black', + borderLeftColor: 'black', borderStyle: 'solid', }) }) diff --git a/src/transforms/border.js b/src/transforms/border.js index d4c77b4..64956af 100644 --- a/src/transforms/border.js +++ b/src/transforms/border.js @@ -13,7 +13,7 @@ const defaultBorderWidth = 1 const defaultBorderColor = 'black' const defaultBorderStyle = 'solid' -export default tokenStream => { +const baseParse = (tokenStream, allowBorderStyle) => { let borderWidth let borderColor let borderStyle @@ -47,7 +47,52 @@ export default tokenStream => { if (borderWidth === undefined) borderWidth = defaultBorderWidth if (borderColor === undefined) borderColor = defaultBorderColor - if (borderStyle === undefined) borderStyle = defaultBorderStyle + if (borderStyle === undefined) { + borderStyle = defaultBorderStyle + } else if (!allowBorderStyle) { + throw new Error( + 'Setting a border style on a single border side is not supported' + ) + } return { borderWidth, borderColor, borderStyle } } + +export default tokenStream => { + // eslint-disable-next-line prefer-const + let { borderWidth, borderColor, borderStyle } = baseParse(tokenStream, true) + + if (borderStyle === undefined) borderStyle = defaultBorderStyle + + return { + borderTopWidth: borderWidth, + borderRightWidth: borderWidth, + borderBottomWidth: borderWidth, + borderLeftWidth: borderWidth, + borderTopColor: borderColor, + borderRightColor: borderColor, + borderBottomColor: borderColor, + borderLeftColor: borderColor, + borderStyle, + } +} + +export const borderTop = tokenStream => { + const { borderWidth, borderColor } = baseParse(tokenStream, false) + return { borderTopWidth: borderWidth, borderTopColor: borderColor } +} + +export const borderRight = tokenStream => { + const { borderWidth, borderColor } = baseParse(tokenStream, false) + return { borderRightWidth: borderWidth, borderRightColor: borderColor } +} + +export const borderBottom = tokenStream => { + const { borderWidth, borderColor } = baseParse(tokenStream, false) + return { borderBottomWidth: borderWidth, borderBottomColor: borderColor } +} + +export const borderLeft = tokenStream => { + const { borderWidth, borderColor } = baseParse(tokenStream, false) + return { borderLeftWidth: borderWidth, borderLeftColor: borderColor } +} diff --git a/src/transforms/index.js b/src/transforms/index.js index 66320ae..0a50d86 100644 --- a/src/transforms/index.js +++ b/src/transforms/index.js @@ -7,7 +7,12 @@ import { PERCENT, AUTO, } from '../tokenTypes' -import border from './border' +import border, { + borderTop, + borderRight, + borderBottom, + borderLeft, +} from './border' import boxShadow from './boxShadow' import flex from './flex' import flexFlow from './flexFlow' @@ -55,8 +60,12 @@ const textShadowOffset = tokenStream => ({ export default { background, border, + borderBottom, borderColor, + borderLeft, borderRadius, + borderRight, + borderTop, borderWidth, boxShadow, flex, From 4fe5f869ec05df2bee6b0211eb476b19ad130092 Mon Sep 17 00:00:00 2001 From: Jacob Parker Date: Sat, 16 Nov 2019 18:22:17 +0000 Subject: [PATCH 2/3] Improve border consistency --- src/__tests__/border.js | 54 ++++++++---------------------------- src/__tests__/borderRight.js | 47 ------------------------------- src/__tests__/units.js | 2 +- src/transforms/border.js | 48 +++++++++----------------------- 4 files changed, 26 insertions(+), 125 deletions(-) delete mode 100644 src/__tests__/borderRight.js diff --git a/src/__tests__/border.js b/src/__tests__/border.js index 2d39f85..3007b1c 100644 --- a/src/__tests__/border.js +++ b/src/__tests__/border.js @@ -56,20 +56,6 @@ it('transforms border shorthand missing color', () => { }) }) -it('transforms border shorthand missing style', () => { - expect(transformCss([['border', '2px #f00']])).toEqual({ - borderTopWidth: 2, - borderRightWidth: 2, - borderBottomWidth: 2, - borderLeftWidth: 2, - borderTopColor: '#f00', - borderRightColor: '#f00', - borderBottomColor: '#f00', - borderLeftColor: '#f00', - borderStyle: 'solid', - }) -}) - it('transforms border shorthand missing width', () => { expect(transformCss([['border', '#f00 dashed']])).toEqual({ borderTopWidth: 1, @@ -98,34 +84,6 @@ it('transforms border shorthand missing color & width', () => { }) }) -it('transforms border shorthand missing style & width', () => { - expect(transformCss([['border', '#f00']])).toEqual({ - borderTopWidth: 1, - borderRightWidth: 1, - borderBottomWidth: 1, - borderLeftWidth: 1, - borderTopColor: '#f00', - borderRightColor: '#f00', - borderBottomColor: '#f00', - borderLeftColor: '#f00', - borderStyle: 'solid', - }) -}) - -it('transforms border shorthand missing color & style', () => { - expect(transformCss([['border', '2px']])).toEqual({ - borderTopWidth: 2, - borderRightWidth: 2, - borderBottomWidth: 2, - borderLeftWidth: 2, - borderTopColor: 'black', - borderRightColor: 'black', - borderBottomColor: 'black', - borderLeftColor: 'black', - borderStyle: 'solid', - }) -}) - it('transforms border for unsupported units', () => { expect(transformCss([['border', '3em solid black']])).toEqual({ borderTopWidth: '3em', @@ -140,6 +98,18 @@ it('transforms border for unsupported units', () => { }) }) +it('does not transform border shorthand missing style', () => { + expect(() => transformCss([['border', '2px #f00']])).toThrow() +}) + +it('does not transform border shorthand missing style & width', () => { + expect(() => transformCss([['border', '#f00']])).toThrow() +}) + +it('does not transforms border shorthand missing color & style', () => { + expect(() => transformCss([['border', '2px']])).toThrow() +}) + it('does not transform border with percentage width', () => { expect(() => transformCss([['border', '3% solid black']])).toThrow() }) diff --git a/src/__tests__/borderRight.js b/src/__tests__/borderRight.js deleted file mode 100644 index 4aab147..0000000 --- a/src/__tests__/borderRight.js +++ /dev/null @@ -1,47 +0,0 @@ -import transformCss from '..' - -it('transforms border none', () => { - expect(transformCss([['border-right', 'none']])).toEqual({ - borderRightWidth: 0, - borderRightColor: 'black', - }) -}) - -it('transforms border shorthand in other order', () => { - expect(transformCss([['border-right', '#f00 2px']])).toEqual({ - borderRightWidth: 2, - borderRightColor: '#f00', - }) -}) - -it('transforms border shorthand missing width', () => { - expect(transformCss([['border-right', '#f00']])).toEqual({ - borderRightWidth: 1, - borderRightColor: '#f00', - }) -}) - -it('transforms border shorthand missing color', () => { - expect(transformCss([['border-right', '2px']])).toEqual({ - borderRightWidth: 2, - borderRightColor: 'black', - }) -}) - -it('transforms border for unsupported units', () => { - expect(transformCss([['border-right', '3em black']])).toEqual({ - borderRightWidth: '3em', - borderRightColor: 'black', - }) -}) - -it('does not transform border with percentage width', () => { - expect(() => transformCss([['border-right', '3% black']])).toThrow() -}) - -it('does not transform style', () => { - expect(() => transformCss([['border-right', '2px dashed #f00']])).toThrow() - expect(() => transformCss([['border-right', 'dashed #f00']])).toThrow() - expect(() => transformCss([['border-right', '2px dashed']])).toThrow() - expect(() => transformCss([['border-right', 'dashed']])).toThrow() -}) diff --git a/src/__tests__/units.js b/src/__tests__/units.js index 1ce1f60..2370c53 100644 --- a/src/__tests__/units.js +++ b/src/__tests__/units.js @@ -66,7 +66,7 @@ describe.each([ borderStyle: 'dashed', }) - expect(transformCss([['border', value]])).toEqual({ + expect(transformCss([['border', `${value} solid`]])).toEqual({ borderTopWidth: value, borderRightWidth: value, borderBottomWidth: value, diff --git a/src/transforms/border.js b/src/transforms/border.js index 64956af..b6a3168 100644 --- a/src/transforms/border.js +++ b/src/transforms/border.js @@ -11,16 +11,25 @@ const BORDER_STYLE = regExpToken(/^(solid|dashed|dotted)$/) const defaultBorderWidth = 1 const defaultBorderColor = 'black' -const defaultBorderStyle = 'solid' -const baseParse = (tokenStream, allowBorderStyle) => { +export default tokenStream => { let borderWidth let borderColor let borderStyle if (tokenStream.matches(NONE)) { tokenStream.expectEmpty() - return { borderWidth: 0, borderColor: 'black', borderStyle: 'solid' } + return { + borderTopWidth: 0, + borderRightWidth: 0, + borderBottomWidth: 0, + borderLeftWidth: 0, + borderTopColor: 'black', + borderRightColor: 'black', + borderBottomColor: 'black', + borderLeftColor: 'black', + borderStyle: 'solid', + } } let partsParsed = 0 @@ -48,22 +57,11 @@ const baseParse = (tokenStream, allowBorderStyle) => { if (borderWidth === undefined) borderWidth = defaultBorderWidth if (borderColor === undefined) borderColor = defaultBorderColor if (borderStyle === undefined) { - borderStyle = defaultBorderStyle - } else if (!allowBorderStyle) { throw new Error( - 'Setting a border style on a single border side is not supported' + 'You must define a border style in the border shorthand (e.g. solid)' ) } - return { borderWidth, borderColor, borderStyle } -} - -export default tokenStream => { - // eslint-disable-next-line prefer-const - let { borderWidth, borderColor, borderStyle } = baseParse(tokenStream, true) - - if (borderStyle === undefined) borderStyle = defaultBorderStyle - return { borderTopWidth: borderWidth, borderRightWidth: borderWidth, @@ -76,23 +74,3 @@ export default tokenStream => { borderStyle, } } - -export const borderTop = tokenStream => { - const { borderWidth, borderColor } = baseParse(tokenStream, false) - return { borderTopWidth: borderWidth, borderTopColor: borderColor } -} - -export const borderRight = tokenStream => { - const { borderWidth, borderColor } = baseParse(tokenStream, false) - return { borderRightWidth: borderWidth, borderRightColor: borderColor } -} - -export const borderBottom = tokenStream => { - const { borderWidth, borderColor } = baseParse(tokenStream, false) - return { borderBottomWidth: borderWidth, borderBottomColor: borderColor } -} - -export const borderLeft = tokenStream => { - const { borderWidth, borderColor } = baseParse(tokenStream, false) - return { borderLeftWidth: borderWidth, borderLeftColor: borderColor } -} From e5e0e168e3fefd12cc9de146cf6a6a2b61879a40 Mon Sep 17 00:00:00 2001 From: Jacob Parker Date: Sat, 16 Nov 2019 18:24:34 +0000 Subject: [PATCH 3/3] fix build --- src/transforms/index.js | 11 +---------- 1 file changed, 1 insertion(+), 10 deletions(-) diff --git a/src/transforms/index.js b/src/transforms/index.js index 0a50d86..66320ae 100644 --- a/src/transforms/index.js +++ b/src/transforms/index.js @@ -7,12 +7,7 @@ import { PERCENT, AUTO, } from '../tokenTypes' -import border, { - borderTop, - borderRight, - borderBottom, - borderLeft, -} from './border' +import border from './border' import boxShadow from './boxShadow' import flex from './flex' import flexFlow from './flexFlow' @@ -60,12 +55,8 @@ const textShadowOffset = tokenStream => ({ export default { background, border, - borderBottom, borderColor, - borderLeft, borderRadius, - borderRight, - borderTop, borderWidth, boxShadow, flex,