Code Monkey home page Code Monkey logo

styled-media-query's Introduction

๐Ÿ’…๐Ÿ’ styled-media-query

npm npm David with-coffee with-love

Beautiful media queries better than CSS @media for styled-components with ability to specify custom breakpoints.

Don't forget to STAR ๐ŸŽŠ We are working so hard to add more features/customizations to styled-media-query!

Note: This documentation is for the latest version (v2). We still support v1 syntax but it'll be removed in v3.

Features:

  • Custom breakpoints
  • Custom size units (px, em, rem)
  • Awesome syntax for min-width and max-width for each breakpoint
  • Familiar syntax as it uses Tagged Template Literals just like styled-components
  • Ability to convert px to rem or em

Start

๐ŸŒฑ Installation

You can install it like every other library with awesome yarn:

yarn add styled-media-query

or with npm

npm install styled-media-query

Note: If you didn't install styled-components yet, install it as well yarn add styled-components

If you use UglifyJS and it fails or you need compiled module, update to latest version please!

๐Ÿƒ Usage

First let me mention how our default breakpoint look like:

{
  huge: '1440px',
  large: '1170px',
  medium: '768px',
  small: '450px',
}

The media has 3 main methods to generate media queries:

Basic Example

Probably this example will explain most of this library. You can use one of these methods to write different kinds of media queries like this:

import styled from "styled-components"; // You need this as well
import media from "styled-media-query";

const Box = styled.div`
  background: black;

  ${media.lessThan("medium")`
    /* screen width is less than 768px (medium) */
    background: red;
  `}

  ${media.between("medium", "large")`
    /* screen width is between 768px (medium) and 1170px (large) */
    background: green;
  `}

  ${media.greaterThan("large")`
    /* screen width is greater than 1170px (large) */
    background: blue;
  `}
`;

The code above is the same as below in pure CSS:

/* โ†“โ†“โ†“โ†“โ†“โ†“โ†“โ†“โ†“ */

div {
  background: black;

  @media (max-width: 768px) {
    /* screen width is less than 768px (medium) */
    background: red;
  }

  @media (min-width: 768px) and (max-width: 1170px) {
    /* screen width is between 768px (medium) and 1170px (large) */
    background: green;
  }

  @media (min-width: 1170px) {
    /* screen width is greater than 1170px (large) */
    background: blue;
  }
}

Note: You can use custom size instead of breakpoint names, too.

lessThan

You can use this type of media query to add styles for screen sizes less than given breakpoint or size.

Example with breakpoint:

media.lessThan('medium')`
  /* styles ... */
`

Example with custom size:

media.lessThan('768px')`
  /* styles ... */
`

Note: You can use rem and em too. (Even you can convert breakpoints to use em or rem with pxToRem and pxToEm functions)

greaterThan

You can use it to add styles for screen sizes greater than given breakpoint or size.

Example with breakpoint:

media.greaterThan('small')`
  /* styles ... */
`

Example with custom size:

media.greaterThan('450px')`
  /* styles ... */
`

between

We use between to add styles for screen sizes between the two given breakpoints or sizes.

Example with breakpoints:

media.between('small', 'medium')`
  /* styles ... */
`

Example with custom sizes:

media.between('450px', '768px')`
  /* styles ... */
`

Use with custom breakpoints:

Our breakpoints may not fit your app, so we export another function called generateMedia to generate a media object with your own custom breakpoints:

import styled from "styled-components"; // You need this as well
import { generateMedia } from "styled-media-query";

const customMedia = generateMedia({
  desktop: "78em",
  tablet: "60em",
  mobile: "46em"
});

// for example call it `Box`
const Box = styled.div`
  font-size: 20px;

  ${customMedia.lessThan("tablet")`
    /* for screen sizes less than 60em */
    font-size: 15px;
  `};
`;

In the case you needed the default breakpoints object, you can import it as follow:

import { defaultBreakpoints } from "styled-media-query";

๐Ÿฝ Concepts

There's a little to learn before you can read the API section.

Breakpoints Object

It's an object containing each break point name as keys and the screen width as values. styled-media-query exports the defaultBreakpoints object.

Media Generator Object

A media generator object is what is returned from generateMedia function or the default exported object from styled-media-query. Read API section for each method.

๐ŸŒผ API

We have a very minimal API, probably you are familiar with 90% of it so far.

Default media

A media generator object with default breakpoints object:

Example:

import media from "styled-media-query";

generateMedia

Generates custom media generator object with custom breakpoints:

generateMedia([breakpoints]);

Example:

import { generateMedia } from "styled-media-query";

const media = generateMedia({
  xs: "250px",
  sm: "450px",
  md: "768px",
  lg: "1200px"
});

pxToRem

Converts breakpoints object's units from px to rem based on the ratio of px to 1rem.

parameters:

  • breakpoints: Object - a breakpoints object
  • ratio: number default: 16 - how many px is equal to 1rem? (It's your root font-size)

Example:

import { pxToRem } from "styled-media-query";

const breakpointsInRem = pxToRem(
  {
    small: "250px",
    medium: "768px",
    large: "1200px"
  },
  10
);

/* โ†“โ†“ returns โ†“โ†“
{
  small: '25rem',
  medium: '76.8rem',
  large: '120rem',
}
*/

pxToEm

Similar to pxToRem. Converts breakpoints object's units from px to em based on the ratio of px to 1em.

parameters:

  • breakpoints: Object - a breakpoints object
  • ratio: number default: 16 - how many px is equal to 1em? (Probably it's your root font-size)

Example: Similar to pxToRem.

โš™๏ธ Troubleshoot

If you use UglifyJS and it fails or you need compiled module you need to update your module to v2 right now to fix the issue:

npm install styled-media-query@latest

๐Ÿฟ Contributions

I'd love to contribute in open source projects, and love to see people contribute. So any kind of contributions (bug reports, suggestions, PRs, issues, etc) are super welcome.

๐Ÿฟ TODO

  • Add convertors for em and rem to px and vice-versa.
  • Add between() method
  • Add LICENSE
  • Write tests with Jest
  • Ability to specify custom media attributes
  • Add support for glamorous
  • ... You say?

License

Licensed under the MIT License, Copyright ยฉ 2017 Mohammad Rajabifard.

See LICENSE for more information.

styled-media-query's People

Contributors

apacheex avatar brajabi avatar franky47 avatar morajabi avatar raulfdm avatar timhagn avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

styled-media-query's Issues

Misleading API

So when I'm doing a media.lessThan('1024px')) I'd expect the media query to look like: @media (max-width: 1023px) { }, because that's what the API states: lessThan. The same issue applies to greaterThan.

What I'd suggest here is:

  1. Rename the functions to: lessThanOrEqual/greaterThanOrEqual
  2. Make lessThan always substract 1 from passed value, and greaterThan add 1 to the value

We could also leave the API as is and add the -OrEqual variations.

What do you think about it?

defining generateMedia breakpoints using type Number

Hi, I love this package and would like to ask to allow configuring the generateMedia object with numbers instead of strings with units, so internally you will check the type and if it's a number you'll convert it to string and add px.

I ask this because this is how I use your package:

import { generateMedia } from 'styled-media-query' 

export const viewports = {
  mobile: "460px",
  l     : "1200px",
  xl    : "1800px",
  huge  : "2200px"
}

const media = generateMedia(viewports)

media.below = media.lessThan
media.above = media.greaterThan

export default media

As you can see, I renamed the methods because I didn't like the long names, I keep forgetting them, so the shorter the better for me. anyway, I am exporting the viewports variable because I need to use it in javascript as well, and I would prefer your library to understand the numbers mean pixels so I won't have to do the transformation on my end:

export const viewports = {
  mobile: 460,
  l     : 1200,
  xl    : 1800,
  huge  : 2200
}

it would be useful for others as well, this is why I ask this, instead of countless devs making it work with numbers, it would be useful if supported out-of-the-box as my request is not something out of the ordinary and many times there should be coupling because css and js values. (working DRY, avoiding possible bugs)

Thanks :)

Package publish automation

Hi everyone.

Since I was add as collaborator, I'd propose some changes to improve this library quality.
In a couple days I'll create more proposals and pull requests but this one is about automating the deployment process.

Proposal

My idea here is to use semantic-release to do this process for us.

For those who doesn't know what's this about, semantic release takes care of our versioning using Angular commit message versioning:
image

It means each commit made needs to follow this structure because it'll be used to:

  1. decide what version would be next. If a commit with fix prefix is merged into master, then semantic release will automatically bump from 2.2.1 to 2.2.2 (minor version) for example;
  2. Auto generates Change log when it happens;
  3. Auto generates tag publish;

Needs

To set this flow only the only thing I need is a NPM_TOKEN environment variable to publish to npm and a GH_TOKEN to publish change logs and tags:

image

The rest is on me :)

Add overlap between screens

Hi, first I would like to thank you for this project ๐Ÿ˜Š

My issue is about overlap between screens, for now we have some problems about it, for example:

${media.lessThan("medium")`
  /* screen width is less than 768px (medium) */
  background: red;
`}

${media.greaterThan("medium")`
   /* screen width is greater than 768px (medium) */
  background: blue;
`}

The both examples will be happens if screen is exactly 768px.

Maybe a good ideia is use an approach like the Rupture.

Thanks!

[TypeScript] Wrong Type Definition

Hello everyone ๐Ÿ‘‹

Expected Behavior

Be able to pass size (e.g. 1024px) to all media query generators without any TypeScript complaint.

Actual Behavior

The current type definition only allow us to pass the breakpoint keys (image below). If you pass a size, it'll work fine but the typescript compiler will complain about this unexpected value.

Screenshot 2020-01-24 at 11 57 34

Steps to Reproduce the Problem

  1. Access this sandbox https://codesandbox.io/s/silent-forest-rgzhj
  2. Wait until loads completely
  3. Check Box component media query warning

Specifications

  • Version: 2.1.2
  • Platform: any

Syntax highlight and Intellisense custom media

Hello, I tried to use custom sizes for the breakpoints but using the VS Code with the vs-styled-components plugin the syntax highlight and intellisense stop working. Any solution for that?

code

Is this project dead?

Hasn't been updated in two years and it seems like all recent issues are being ignored. So basically, is this project dead or will it be maintained again?

Syntax highlight for Webstorm?

Any ideas about how to "teach" Webstorm to highlight syntax correctly inside the media query?

Right now it looks like this:

image

I know about the hack with adding css, but maybe there is something better?

image

Discussion for v3 API for more flexibility and readability

Hi @morajabi, thank you for putting out this library. It has been super helpful so far. In my current project, I keep needing to write height based media queries, and in doing so, I have to opt traditional media query rather than use this library.

So, I was wondering if you are considering adding support for other aspects of media query in the library API?

What do you think about the new API for version 2.0.0

screen shot 2017-08-24 at 11 49 34 am

I'm working on a new API in version 2 and so far I came to this. What do you think about it? Is it readable? What can we add or change?

Note: The old API (media.to.large) is still there and you'll have no problems using it, but probably in version 3 it will be removed.

Dark color scheme support (via prefers-color-scheme media query)

Well, many operating systems now support a dark mode or dark theme.

I believe it would be interesting for this to be implemented here as well.

The media consultation of the preferred color scheme allows you to adjust the appearance of the website to match the user's preferred mode.

Syntax

no-preference Indicates that the user has made no preference known to the system. This keyword value evaluates to false in the boolean context.
light Indicates that user has notified the system that they prefer an interface that has a light theme.
dark Indicates that user has notified the system that they prefer an interface that has a dark theme.

Mozilla Firefox: https://developer.mozilla.org/en-US/docs/Web/CSS/@media/prefers-color-scheme
Google Chrome: https://www.chromestatus.com/feature/5109758977638400

Suggestion

  ${media.prefersColorScheme("dark")`
    body {
      background-color: black;
      color: white;
    }
  `}

What do you think about it?

[feature request] Specific Devices

Sometimes you need to do custom css that only applies for specific devices (i.e. iphone x). Would be cool if you had built in features for these.

Here's an example:

const Cool = styled.div`
  ${media.iphonex`
    /* styles to be applied to iphonex only */
  `}
`

Or something like

const Cool = styled.div`
  ${media.device('iphonex').orientation('portrait')`
    /* styles to be applied to iphonex only */
  `}
`

Here's some iphone device media queries

const media = {
  iphonex: (...args) => css`
    @media only screen 
    and (device-width : 375px) 
    and (device-height : 812px) 
    and (-webkit-device-pixel-ratio : 3) {
      ${css(...args)}
    }
  `
}

Issue with TypeScript and custom props

Been using this package for multiple projects and really like it. However, in my latest project I'm using TypeScript and because of this I found a bug in styled-media-query.

I got a styled components which expects a isVisible boolean prop:

interface OverlayProps {
    isVisible: boolean;
}

export const Overlay = styled.div<OverlayProps>`
    color: ${({ isVisible }): string => (isVisible ? 'red' : 'green')};
`;

This all works fine and TypeScript doesn't throw any errors. However, if I try to use the isVisible prop inside media I'm getting errors:

interface OverlayProps {
    isVisible: boolean;
}

export const Overlay = styled.div<OverlayProps>`
    opacity: ${({ isVisible }): string => (isVisible ? '0.3' : '0')};

    ${media.lessThan('large')`
        background-color: ${({ theme }): string => theme.shades.one};
        position: fixed;
        top: 52px;
        left: ${({ isVisible }): string => (isVisible ? '260px' : '0')};
        width: 100%;
        height: 100%;
        z-index: 2;
        opacity: ${({ isVisible }): string => (isVisible ? '0.3' : '0')};
        cursor: pointer;
        transition: all 300ms ease;
    `}
`;

The left and opacity declarations are throwing the following error: Property 'isVisible' does not exist on type 'ThemeProps<any>'.

Screenshot:

Screenshot 2019-12-17 at 09 46 31

Please let me know if you need any more information. Any help would be greatly appreciated!

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    ๐Ÿ–– Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. ๐Ÿ“Š๐Ÿ“ˆ๐ŸŽ‰

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google โค๏ธ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.