From 09584cff27e11c6b040ac59874fc13c06490e0ae Mon Sep 17 00:00:00 2001 From: mg901 Date: Sat, 20 Jul 2019 15:25:14 +0300 Subject: [PATCH] feat(orientation): add orientation --- src/index.d.ts | 12 ++++++--- src/index.js.flow | 24 ++++++++++++----- src/utils/index.js | 60 ++++++++++++++++++++++++++++++----------- src/utils/index.spec.js | 55 ++++++++++++++++++++++++++++++++++--- 4 files changed, 120 insertions(+), 31 deletions(-) diff --git a/src/index.d.ts b/src/index.d.ts index cbaaf080..0ea6cdc4 100644 --- a/src/index.d.ts +++ b/src/index.d.ts @@ -16,10 +16,14 @@ export interface IBpProps { type RuleFnType = (props: IBpProps) => string; -export function up(breakName: string): RuleFnType; +export function up(breakName: string, orientation?: string): RuleFnType; -export function down(breakName: string): RuleFnType; +export function down(breakName: string, orientation?: string): RuleFnType; -export function between(minBreak: string, maxBreak: string): RuleFnType; +export function between( + minBreak: string, + maxBreak: string, + orientation?: string, +): RuleFnType; -export function only(breakName: string): RuleFnType; +export function only(breakName: string, orientation?: string): RuleFnType; diff --git a/src/index.js.flow b/src/index.js.flow index 210e052f..cf6e99a2 100644 --- a/src/index.js.flow +++ b/src/index.js.flow @@ -18,10 +18,20 @@ type BpProps = { type RuleFnType = (props: BpProps) => string; -declare export function up(breakName: string): RuleFnType; - -declare export function down(breakName: string): RuleFnType; - -declare export function between(minBreak: string, maxBreak: string): RuleFnType; - -declare export function only(breakName: string): RuleFnType; +declare export function up(breakName: string, orientation?: string): RuleFnType; + +declare export function down( + breakName: string, + orientation?: string, +): RuleFnType; + +declare export function between( + minBreak: string, + maxBreak: string, + orientation?: string, +): RuleFnType; + +declare export function only( + breakName: string, + orentation?: string, +): RuleFnType; diff --git a/src/utils/index.js b/src/utils/index.js index 432f86da..4a861226 100644 --- a/src/utils/index.js +++ b/src/utils/index.js @@ -17,6 +17,20 @@ export const DEFAULT_BREAKS: ThemeWithBreaks = { breakpoints: DEFAULT_BREAKS_MAP, }; +const withOrientationOrNot = (params: string, orientation?: string): string => { + const isValidOrientation = + orientation === 'portrait' || orientation === 'landscape'; + + if (!orientation) return params; + + invariant( + isValidOrientation, + `${orientation} is invalid orientation. Use 'landscape' or 'portrait'.`, + ); + + return `${params} and (orientation: ${orientation})`; +}; + export const withMinMedia = (minWidth: string): string => `@media (min-width: ${minWidth})`; @@ -124,24 +138,38 @@ export const calcMaxWidth = (breakName: string, theme: CustomTheme): string => { return toEm(getNextBreakpointValue(breakName, breakpoints)); }; -type Up = (string) => (BpProps) => string; -export const up: Up = (breakName) => ({ theme }) => - withMinMedia(calcMinWidth(breakName, theme)); +type Up = (string, orientation?: string) => (BpProps) => string; +export const up: Up = (breakName, orientation) => ({ theme }) => + withOrientationOrNot( + withMinMedia(calcMinWidth(breakName, theme)), + orientation, + ); -type Down = (string) => (BpProps) => string; -export const down: Down = (breakName) => ({ theme }) => - withMaxMedia(calcMaxWidth(breakName, theme)); +type Down = (string, orientation?: string) => (BpProps) => string; +export const down: Down = (breakName, orientation) => ({ theme }) => + withOrientationOrNot( + withMaxMedia(calcMaxWidth(breakName, theme)), + orientation, + ); -type Between = (string, string) => (BpProps) => string; -export const between: Between = (minBreak, maxBreak) => ({ theme }) => - withMinAndMaxMedia( - calcMinWidth(minBreak, theme), - calcMaxWidth(maxBreak, theme), +type Between = (string, string, orientation?: string) => (BpProps) => string; +export const between: Between = (minBreak, maxBreak, orientation) => ({ + theme, +}) => + withOrientationOrNot( + withMinAndMaxMedia( + calcMinWidth(minBreak, theme), + calcMaxWidth(maxBreak, theme), + ), + orientation, ); -type Only = (string) => (BpProps) => string; -export const only: Only = (breakName) => ({ theme }) => - withMinAndMaxMedia( - calcMinWidth(breakName, theme), - calcMaxWidth(breakName, theme), +type Only = (string, orientation?: string) => (BpProps) => string; +export const only: Only = (breakName, orientation) => ({ theme }) => + withOrientationOrNot( + withMinAndMaxMedia( + calcMinWidth(breakName, theme), + calcMaxWidth(breakName, theme), + ), + orientation, ); diff --git a/src/utils/index.spec.js b/src/utils/index.spec.js index 136bb7f4..11dd8226 100644 --- a/src/utils/index.spec.js +++ b/src/utils/index.spec.js @@ -33,25 +33,48 @@ const CUSTOM_THEME_IS_EMPTY = { }; describe('up', () => { - it('should return string with min breakpoint value and media query', () => { + it('should return min breakpoint value and media query', () => { expect(up('tablet')(CUSTOM_THEME)).toEqual('@media (min-width: 48em)'); }); - it('should return string with min breakpoint value and media query (from default theme)', () => { + it('should return min breakpoint value and media query (from default theme)', () => { expect(up('tablet')(CUSTOM_THEME_IS_EMPTY)).toEqual( '@media (min-width: 48em)', ); }); + it('should return min breakpoint value and media query with portrait orientation', () => { + expect(up('tablet', 'portrait')(CUSTOM_THEME)).toEqual( + '@media (min-width: 48em) and (orientation: portrait)', + ); + }); + + it('should return min breakpoint value and media query with landscape orientation', () => { + expect(up('tablet', 'landscape')(CUSTOM_THEME)).toEqual( + '@media (min-width: 48em) and (orientation: landscape)', + ); + }); }); describe('down', () => { - it('should return string with max breakpoint value and media query', () => { + it('should return max breakpoint value and media query', () => { expect(down('tablet')(CUSTOM_THEME)).toEqual( '@media (max-width: 61.99875em)', ); }); - it('should return string with max breakpoint value and media query (from default theme)', () => { + it('should return max breakpoint value and media query with portrait orientation', () => { + expect(down('tablet', 'portrait')(CUSTOM_THEME)).toEqual( + '@media (max-width: 61.99875em) and (orientation: portrait)', + ); + }); + + it('should return max breakpoint value and media query with landscape orientation', () => { + expect(down('tablet', 'landscape')(CUSTOM_THEME)).toEqual( + '@media (max-width: 61.99875em) and (orientation: landscape)', + ); + }); + + it('should return max breakpoint value and media query (from default theme)', () => { expect(down('tablet')(CUSTOM_THEME_IS_EMPTY)).toEqual( '@media (max-width: 61.99875em)', ); @@ -65,6 +88,18 @@ describe('between', () => { ); }); + it('should returns a string containing the value of the minimum and maximum breakpoints and media query and portrait orientation', () => { + expect(between('tablet', 'desktop', 'portrait')(CUSTOM_THEME)).toEqual( + '@media (min-width: 48em) and (max-width: 74.99875em) and (orientation: portrait)', + ); + }); + + it('should returns a string containing the value of the minimum and maximum breakpoints and media query and landscape orientation', () => { + expect(between('tablet', 'desktop', 'landscape')(CUSTOM_THEME)).toEqual( + '@media (min-width: 48em) and (max-width: 74.99875em) and (orientation: landscape)', + ); + }); + it('should returns a string containing the value of the minimum and maximum breakpoints and media query (from default theme)', () => { expect(between('tablet', 'desktop')(CUSTOM_THEME_IS_EMPTY)).toEqual( '@media (min-width: 48em) and (max-width: 74.99875em)', @@ -79,6 +114,18 @@ describe('only', () => { ); }); + it('should returns a string containing the minimum and maximum values of the current breakpoint and media query with portrait orientation', () => { + expect(only('tablet', 'portrait')(CUSTOM_THEME)).toEqual( + '@media (min-width: 48em) and (max-width: 61.99875em) and (orientation: portrait)', + ); + }); + + it('should returns a string containing the minimum and maximum values of the current breakpoint and media query with landscape orientation', () => { + expect(only('tablet', 'landscape')(CUSTOM_THEME)).toEqual( + '@media (min-width: 48em) and (max-width: 61.99875em) and (orientation: landscape)', + ); + }); + it('should returns a string containing the minimum and maximum values of the current breakpoint and media query (from default theme)', () => { expect(only('tablet')(CUSTOM_THEME_IS_EMPTY)).toEqual( '@media (min-width: 48em) and (max-width: 61.99875em)',