DEV Community

Rodrigo Grau
Rodrigo Grau

Posted on

CSS EN REACT

  • [ESTILIZANDO CON CSS:]
  • [Plain CSS:]
  • [MÓDULOS DE CSS:]
  • [CSS IN JS:]
  • [Styled Components:]
  • [Emotion:]
  • [Stitches:]
  • [TailwindCSS:]

ESTILIZANDO CON CSS:

Dentro de React, cuando nosotros utilizamos alguna herramienta para estilizar, se tienen ciertas condiciones las cuales limitan en utilizar alguna u otra herramienta, ca la finalidad de que la experiencia de desarrollo sea más agradable.

Algunas de éstas herramientas son:

  • Plain CSS: Estilos dentro en un archivo directo “.css”.
  • CSS Modules: Permite aislar los estilos para no tenerlos todos juntos en un solo archivo css, así evitando hacer más compleja la cantidad de estilos para cada uno de los componentes o elementos que se están colocando dentro de la aplicación.
  • Prepocessors:
    • SASS
    • PostCSS
    • LESS
    • Stylus
  • CSS in JS: Es lo mas utilizado dentro de React, es el CSS escrito dentro de un componente o elementos de JSX, y a partir de eso se generan las clases y estilos asignados a dicho elemento.
  • Las maneras más sencillas de aplicar estilos de css en React son las siguientes:

    <button **className='btn btn__primary'** /> //Etiqueta de botón, la cual posee un selector de clase, con valor asignado de, una clase "btn" y será un variación con la clase "btn__primary"
    
    <button **style="background-color: red"** /> //Etiqueta de botón, la cual posee el atributo de "estilo" para colocar estilos en línea, con valor asignado de, las propiedades de estilos con sus valores correspondientes, dichos estilos serán colocados dentro del mismo atributo separados por punto y coma(;)
    
    <button **style={{ backgroundColor: 'red' }}** /> //Etiqueta de botón, la cual posee el atributo de "estilo" para colocar estilos, con valor asignado de, dentro de llaves por ser código de JS, un objeto dentro de un elemento JSX utilizando la sintaxis de camelCase para las propiedades de estilos y su valor  
    

Plain CSS:

Para implementarlo:

  • Se debe importar el archivo CSS desde su ruta, al archivo JSX donde se aplicarán los estilos. Así todas las clases que estén dentro de éste archivo se van a extender a toda la aplicación.
  • Mediante los selectores, ya sean de clase o identificadores, se pueden aplicar los estilos, agregado dichos selectores a los elementos dentro del componente JSX, siendo aplicados dichos estilos al importar el archivo CSS.
  • Entre más aisladas se tengan las funcionalidades de los componentes será mejor su uso e implementación.
  • En caso de que el componente esté aislado en una carpeta, dicha carpeta será nombrada con el nombre del componente y el archivo JSX será llamado “index.jsx”, así al importar dicho componente mediante su ruta, solo se necesitará colocar la ruta hasta la carpeta nombrada con el nombre del componente.

    /* style.css */
    
    **.card {** /*Selector de clase para el elemento que lo posea*/
        background-color: blue; /*Propiedad de color de fondo, con valor "azul"*/
        padding: 20px; /*Propiedad de margen interno, con valor de 20 pixeles a todos los lados*/
        border-radius: 12px; /*Propiedad de redondeo de esquinas, con valor de 12 pixeles a todas las esquinas*/
    **}**
    
```jsx
// index.jsx

**import './style.css'**; //Se importa el archivo CSS desde su ruta, el cual está ubicado en la misma carpeta de éste componente

export default function **Card()** { //Se exporta como valor por defecto, la decalración de función que será un componente, el cual ejecuta el siguiente bloque
    return ( //Se retorna una estructura de JSX, el cual será el componente a ser renderizado, siendo colocado entre paréntesis
        <div **className="card"** /> //Etiqueta contenedora de bloque, la cual posee un selector de clase, con valor asignado de, la clase dentro del archivo CSS importado, así aplicando los estilos al importar dicho archivo CSS
    );
}
```
Enter fullscreen mode Exit fullscreen mode
```jsx
// App.jsx

**import Card from './components/Card'**; //Se importa como valor por defecto, dicho componente, desde, su ruta la cual es colocada hasta el nombre de la carpeta nombrada con el nombre del componente("Card") y que contiene el archivo "index.jsx" el cual es importado en automático sin la necesidad de declararlo, y que también contiene el archivo "style.css" el cual aplica los estilos al componente "index.jsx"

export default function App() { //Se exporta como valor por defecto, la decalración de función que será un componente, el cual ejecuta el siguiente bloque
    return ( //Se retorna una estructura de JSX, el cual será el componente a ser renderizado, siendo colocado entre paréntesis
        <> //Fragmento de React para contener el componente sin ser renderizado dentro de otro elemento
            **<Card />** //Se llama a ejecutar dicho componente importado, como etiqueta HTML para poder ser renderizado
        </> 
    );
}
```
Enter fullscreen mode Exit fullscreen mode

MÓDULOS DE CSS:

Se incorporó esta funcionalidad dentro del manejo de estilos en React, lo cual permite cargar los estilos desde un archivo aislado y único para cada componente que se puede importar, al cual para acceder a los estilos se hace igual que un objeto.

  • Se pueden tener tantas variaciones como se necesiten.
  • Se pueden tener distintos tipos de implementación para que se puedan aplicar de acuerdo a la funcionalidad que se espera.
  • A pesar de escribir estilo de CSS dentro del archivo, la forma en la que se utilizan dentro de un componente es:

    • Debe ser nombrado, antes de la extensión “*****.css**” con la palabra “******module*********”.
    • Importar el archivo de “módulo de CSS”(Name.module.css) para poder implementarlo, esto retorna los estilos asociados en una especie de “objeto”, todas las clases, todos los ID, y todo lo que esté referente en el elemento “root”.
    • Para pasar esa configuración de los estilos a un elemento dentro de un componente JSX es vía el ***************className*************** o el *id*, indicándole cual va ser la clase o id que se le va a pasar al elemento.
    • Para acceder a los estilos y aplicarlos, mediante el selector de clase o identificador en el elemento, dentro de llaves por ser código de JS, se hace al igual que un objeto, mediante el módulo de CSS importado, se accede a la clase o id correspondiente.
    • Al importar el módulo de CSS, se cargar todas las clases sin importar que no se utilicen, para evitarlo, se puede hacer destructuración:

      • import { className } from './Component.module.css';
      /* Button.module.css */
      
      **.btn {** /* Selector de clase para el elemento que lo posea */
          **background-color: 'red';** /* Propiedad de color de fondo, con valor "rojo" */
      **}**
      
    ```jsx
    // Button.jsx

    **import styles from './Button.module.css';** //Se exporta el módulo de estilos de css, desde, su ruta
    export default function Button() { //Se exporta como valor por defecto, la declaración de función que será un componente, el cual ejecuta el siguiente bloque
        return ( //Se retorna una estructura de JSX, el cual será el componente a ser renderizado, siendo colocado entre paréntesis
            <button **className={styles.btn}** /> //Etiqueta de botón, la cual posee un selector de clase, con valor asignado de, dentro de llaves por ser código de JS, desde el módulo de estilos de css, acceder al selector de clase "btn" para aplicar sus estilos correspondientes
        );
    }
    ```
Enter fullscreen mode Exit fullscreen mode

CSS IN JS:

Al utilizar el CSS dentro de JS, éste está implícitamente dentro del archivo del mismo componente, y a partir de ahí es como se va atribuyendo la funcionalidad, con la finalidad de tener los estilos y el JS dentro del mismo archivo, teniendo todos los estilos correspondientes solamente a un componente, así aislando la funcionalidad correspondiente a cada una de los componentes y elementos.

Para el manejo de CSS en JS se tienen muchas herramientas:

  • Styled Components:
  • Emotion:
  • JSS:
  • Stitches:

Styled Components:

Éstos son componentes estilizados.

  • Estilos condicionados a través de props.
  • CSS-in-JS.
  • Puedes extender estilos y reutilizarlos.
  • Puedes definir tus estilos con Template Literals o con objetos.

Para implementarlo:

  • Se debe instalar la dependencia *******************************styled-components****************************, mediante *npm****:
    • npm install --save styled-components
  • Se importa el objeto/función *********styled********* desde la librería *******************************styled-components*******************************:

    **import styled from 'styled-components';** //Se importa el objeto/función "styled", desde la librería 'styled-components'
    

    Al importar dicha librería se puede acceder al objeto *********styled******, el cual contiene todos los elementos de HTML para poderlos definir como un componente de tipo **************************styled Component*****************************.

  • Se debe declarar una variable o constante la cual será el elemento HTML a ser renderizado dentro de un componente, la cual debe tener asignado como valor, desde el objeto ******styled****** importado, obtener el elemento HTML requerido, siendo que dicho elemento posee todos sus atributos, siendo controlado igual que un elemento HTML, ya que es lo mismo.

Para aplicar los estilos, hay dos maneras de hacerlo:

  1. Seguido de obtener el elemento HTML requerido se utiliza *************************interpolación************************* utilizando comillas invertidas , donde dentro de ellas se colocan los estilos(atributos) de CSS:

    **const StyledCard = styled.div`** //Declaración de constante con valor asignado de, del obejto "styled" importado, se obtiene el elemento "contenedor de bloque", y dentro de comillas invertidas se hacer **interpolación** para colocar las siguientes propiedades CSS
        **background-color: blue;** //Propiedad de color de fondo, con valor "azul"
        **padding: 20px;** //Propiedad de margen interno, con valor de 20 pixeles a todos lados
        **border-radius: 15px;** //Propiedad de redondeo de las esquinas, con valor de 15 pixeles a todas las esquinas
    **`;**
    

    Éste elemento es un componente, es un *****componente estilizado*****, al cual ya se le asignaron su estilos.

    Para renderizarlo:

- Si solo se necesitan dicho ********componente estilizado********, no hay necesidad de renderizarlo dentro de otro componente que esté dentro del mismo archivo, ya que cada componente debe de estar lo más aislado posible, entonces solo se exporta para ser renderizado en el archivo correspondiente:
Enter fullscreen mode Exit fullscreen mode
    ```jsx
    import **styled** from 'styled-components'; //Se importa el objeto/función "styled", desde la librería 'styled-components'

    const **StyledCard** = **styled.div**` //Declaración de constante con valor asignado de, del obejto "styled" importado, se obtiene el elemento "contenedor de bloque", y dentro de comillas invertidas se hacer interpolación para colocar las siguientes propiedades CSS
        background-color: blue; //Propiedad de color de fondo, con valor "azul"
        padding: 20px; //Propiedad de margen interno, con valor de 20 pixeles a todos lados
        border-radius: 15px; //Propiedad de redondeo de las esquinas, con valor de 15 pixeles a todas las esquinas
    `;

    **export default StyledCard;** //Se exporta como valo por defecto, dicho componente estilizado, para ser renderizado en su lugar correspondiente
    ```
Enter fullscreen mode Exit fullscreen mode
- **Si se necesitan variaciones del mismo componente**, se debe de tener un componente base, del cual se van a crear sus variaciones, las cuales, al igual que el componente base, deben ser declarados como variables/constantes, a las que se les asigna como valor, acceder al objeto/función **styled**, el cual dentro de paréntesis recibe como argumento el componente base, y se utiliza ****************************interpolación**************************** utilizando comillas invertidas **` `**, donde dentro de ellas se colocan los estilos(atributos) de CSS que harán las variaciones:
Enter fullscreen mode Exit fullscreen mode
    ```jsx
    // index.jsx

    import **styled** from 'styled-components'; //Se importa el objeto/función "styled", desde la librería 'styled-components'

    const **Default** = **styled**.div` //Declaración de constante con valor asignado de, del objeto/función "styled" importado, se obtiene el elemento "contenedor de bloque", y dentro de comillas invertidas se hacer interpolación para colocar las siguientes propiedades CSS
        background-color: gray; //Propiedad de color de fondo, con valor "gris"
        border-radius: 15px; //Propiedad de redondeo de las esquinas, con valor de 15 pixeles a todas las esquinas
        padding: 20px; //Propiedad de margen interno, con valor de 20 pixeles a todos lados
    `;

    const **Primary** = styled(**Default**)` //Declaración de constante con valor asignado de, al objeto/función "styled" importado, se le envía como argumento, el componente "**Default**", adquiriendo sus propiedades CSS y con la posibilidad de modificarlas y agregar nuevas, y dentro de comillas invertidas se hacer interpolación para colocar las siguientes propiedades CSS
        background-color: red; //Propiedad de color de fondo, con valor "rojo"
        border-radius: 15px; //Propiedad de redondeo de las esquinas, con valor de 15 pixeles a todas las esquinas
        padding: 20px; //Propiedad de margen interno, con valor de 20 pixeles a todos lados

    `;

    const **Secondary** = styled(**Default**)` //Declaración de constante con valor asignado de, al objeto/función "styled" importado, se le envía como argumento, el componente "**Default**", adquiriendo sus propiedades CSS y con la posibilidad de modificarlas y agregar nuevas, y dentro de comillas invertidas se hacer interpolación para colocar las siguientes propiedades CSS
        background-color: white; //Propiedad de color de fondo, con valor "blanco"
        border-radius: 15px; //Propiedad de redondeo de las esquinas, con valor de 15 pixeles a todas las esquinas
        border: 2px solid black; //Propiedad de borde, con valor para ser de 2 pixeles de grosor, solido y de color ngro
        padding: 20px; //Propiedad de margen interno, con valor de 20 pixeles a todos lados

    `;

    export { //Se exportan
        **Default**, //Dicho componente estilizado
        **Primary**, //Dicho componente estilizado
        **Secondary**, //Dicho componente estilizado
    }
    ```
Enter fullscreen mode Exit fullscreen mode
    ```jsx
    //App.jsx

    import { **Default**, **Primary**, **Secondary**,} from './components/Card'; //Se importan, los tres componentes estilizados, para poder acceder a ellos individualmente, desde, su ruta la cual es colocada hasta el nombre de la carpeta nombrada con el nombre del componente("Card") y que contiene el archivo "index.jsx" el cual es importado en automático sin la necesidad de declararlo

    export default function App() { //Se exporta como valor por defecto, la declaración de función que será un componente y que ejecuta el sigueinte bloque
        return ( //Se retorna una estructura de JSX, el cual será el componente a ser renderizado, siendo colocado entre paréntesis
            <> //Fragmento de React para contener el componente sin ser renderizado dentro de otro elemento
                **<Default />** //Se llama a ejecutar dicho componente estilizado importado, como etiqueta HTML para poder ser renderizado
                **<Primary />** //Se llama a ejecutar dicho componente estilizado importado, como etiqueta HTML para poder ser renderizado
                **<Secondary />** //Se llama a ejecutar dicho componente estilizado importado, como etiqueta HTML para poder ser renderizado
            </> 
        );
    }
    ```
Enter fullscreen mode Exit fullscreen mode
  1. Seguido de obtener el elemento HTML requerido, al mismo dentro de paréntesis se le envía como argumento un objeto, donde dentro de ellas se colocan los estilos(atributos) de CSS utilizando la sintaxis de camelCase y el valor dentro de comillas ‘ ’:

    **const DefaultButton = styled.button({** //Declaración de constante con valo asignado de, del objeto/función "styled" importado, se obtiene el elemento "botón" el cual recibe como argumento un objeto con las siguientes propiedades CSS
        **backgroundColor: 'gray',** //Propiedad de color de fondo, con valor "gris"
        **color: 'white'** //Propiedad de color del texto, con valor "blanco"
    **});**
    

    Para renderizarlo:

- Si dicho componente estilizado necesita contener algo, se hace uso de la propiedad “**{children}**”, a demás de tener que ser renderizado dentro de otro componente para enviarle dicha propiedad:
Enter fullscreen mode Exit fullscreen mode
    ```jsx
    // index.jsx

    import PropTypes from "prop-types"; //Se importa la librería PropTypes, desde, "prop-types" que se utiliza para declarar y validar los tipos de las propiedades que se pasan a los componentes
    import styled from 'styled-components'; //Se importa el objeto/función "styled", desde la librería 'styled-components'

    const **DefaultButton** = styled.button({ //Declaración de constante con valo asignado de, del objeto/función "styled" importado, se obtiene el elemento "botón" el cual recibe como argumento un objeto con las siguientes propiedades CSS
        backgroundColor: 'gray', //Propiedad de color de fondo, con valor "gris"
        color: 'white' //Propiedad de color del texto, con valor "blanco"
        border: '1px solid black', //Propiedad de borde, con valores para ser de 1 pixel de grosor, solido, y de color "negro"
        borderRadius: '3px' //Propiedad de redondeo de las esquinas, con vlaor de 3 pixeles a todas las esquinas
    });

    const PrimarytButton = styled(DefaultButton)` //Declaración de constante con valor asignado de, al objeto/función "styled" importado, se le envía como argumento, el componente "**DefaultButton**", adquiriendo sus propiedades CSS y con la posibilidad de modificarlas y agregar nuevas, y dentro de comillas invertidas se hacer interpolación para colocar las siguientes propiedades CSS
        background-color: white; //Propiedad de color de fondo, con valor "blanco"
        color: black; //Propiedad de color del texto, con valor "negro"
        border: 1px solid gray; //Propiedad de borde, con valores para ser de 1 pixel de grosor, solido, y de color "gris"
        border-radius: 3px; //Propiedad de redondeo de las esquinas, con vlaor de 3 pixeles a todas las esquinas
    `;

    export default function **Button**(**{children, ...props}**) { //Se exporta como valor por defecto, la declaración de función que será un componente, el cual posee un parámetro para recibir la prop children, mediante la sintaxis de destructuración para obtener la prop children la cual representa un elemento hijo que se contendrá dentro de un componente, y que recibe todas las propiedades que se le envíen, la cual ejecuta el siguiente bloque
        return ( //Se retorna una estructura de JSX, el cual será el componente a ser renderizado, siendo colocado entre paréntesis
            **<DefaultButton {...props}>{children}</DefaultButton>** //Llamar a renderizar dicho componente estilizado, el cual recibe todas las propiedades que se le manden, y la propiedad children
            **<PrimaryButton {...props}>{children}</PrimaryButton>** //Llamar a renderizar dicho componente estilizado, el cual recibe todas las propiedades que se le manden, y la propiedad children
        );
    }

    **Button**.propTypes = { //A dicho componente, se accede a su propiedad "propTypes" para especificar los tipos de datos esperados para las props, a la cual se le asigna como valor, un objeto con las siguientes propiedades
        **children**: PropTypes.string //Se establece que, la propiedad "children" debe, desde la librería "PropTypes", ser un valor de cadena de texto
    }
    ```
Enter fullscreen mode Exit fullscreen mode
    ```jsx
    // App.jsx

    import **Button** from './components/Button'; //Se importa como valor por defecto, dicho componente, desde, su ruta la cual es colocada hasta el nombre de la carpeta nombrada con el nombre del componente("Button") y que contiene el archivo "index.jsx" el cual es importado en automático sin la necesidad de declararlo

    export default function App() { //Se exporta como valor por defecto, la declaración de función que será un componente, la cual ejecuta el siguiente bloque
        return ( //Se retorna una estructura de JSX, el cual será el componente a ser renderizado, siendo colocado entre paréntesis
            <> //Fragmento de React para contener el componente sin ser renderizado dentro de otro elemento
                **<Button onClick={() => alert("button")}>Click me</Button>** //Se llama a renderizar como etiqueta HTML, dicho componente importado, recibe la prop manejadora de eventos del evento de click sobre éste elemento con valor asignado dentro de llaves por ser código de JS, una función de flecha callback la cual ejecuta la función de ventana emergente la cual cual muestra dicha cadena de texo enviada como argumento, y contiene texto el cual es la propiedad children que necesita el componente estilizado que retorna éste componente
            </> 
        );
    }
    ```
Enter fullscreen mode Exit fullscreen mode
  • Para que un elemento/componente tenga un estilo CONDICIONADO dependiendo de una propiedad:

    • En la forma de objeto se tiene la forma de poder pasar los “***props***” y a partir de ellos, desde afuera se puede dar algún tipo de funcionalidad o comportamiento para como ser verá dicho elemento:

      • Se declara una constante/variable a la que se le asigna como valor, del objeto/función *********styled*********, obtener el elemento HTML que se requiera.
      • A dicho elemento obtenido, dentro de paréntesis, se le envía como argumento una función de flecha, que mediante dichas *******props*******, se ejecutará un bloque de código dentro de paréntesis para estilizar el componente/elemento.
      • El bloque de código que ejecuta la función que recibe el elemento obtenido, son las propiedades de CSS, las cuales al asignar su valor, se utiliza el operador ternario para condicionar mediante las *******props*******, el valor de dicha propiedad CSS.

        // index.jsx
        
        import PropTypes from "prop-types"; //Se importa la librería PropTypes, desde, "prop-types" que se utiliza para declarar y validar los tipos de las propiedades que se pasan a los componentes
        import styled from 'styled-components'; //Se importa el objeto/función "styled", desde la librería 'styled-components'
        
        const DefaultButton = styled.**button(props => ({** //Declaración de constante con valor asignado de, del objeto/función "styled", obtener el elemento "botón", el cual recibe como argumento una función flecha con el objeto "props", la cual ejecuta dentro de paréntesis, las siguientes propiedades de CSS dentro de llaves
            **backgroundColor: props.disabled ? "red" : "gray",** //Propiedad de color de fondo, con valor del operador ternario, el cual valida, del objeto de propiedades, si su propiedad "disabled" está activa(true), el valor será "rojo", de lo contrario será "gris"
            **color: props.disabled ? "black" : "white"** //Propiedad de color del texto, con valor del operador ternario, el cual valida, del objeto de propiedades, si su propiedad "disabled" está activa(true), el valor será "negro", de lo contrario será "blanco"
        **}))**;
        
        export default function Button({children, **...props}**) { //Se exporta como valor por defecto, la declaración de función que será un componente, el cual posee los parámetros para recibir como argumentos, la prop children, mediante la sintaxis de destructuración para obtener la prop children la cual representa un elemento hijo que se contendrá dentro de un componente, y que recibe todas las propiedades que se le envíen, la cual ejecuta el siguiente bloque
            return ( //Se retorna una estructura de JSX, el cual será el componente a ser renderizado, siendo colocado entre paréntesis
                <> //Fragmento de React para contener el componente sin ser renderizado dentro de otro elemento
                    <DefaultButton **{...props}**>{children}</DefaultButton> //Se llama a renderizar como etiqueta HTML, dicho componente "DefaultButton", recibe todas las props que se le envíen al componene "Button", y recibe la prop "children" que se le envía al componene "Button"
                </>
            );
        }
        
        Button.propTypes = { //A dicho componente, se accede a su propiedad "propTypes" para especificar los tipos de datos esperados para las props, a la cual se le asigna como valor, un objeto con las siguientes propiedades
            children: PropTypes.object //Se establece que, la propiedad "children" debe, desde la librería "PropTypes", ser un valor de cadena de texto
        }
        
        ```jsx
        // App.jsx

        import Button from './components/Button'; //Se importa como valor por defecto, dicho componente, desde, su ruta la cual es colocada hasta el nombre de la carpeta nombrada con el nombre del componente("Button") y que contiene el archivo "index.jsx" el cual es importado en automático sin la necesidad de declararlo

        export default function App() { //Se exporta como valor por defecto, la declaración de función que será un componente, la cual ejecuta el siguiente bloque
            return ( //Se retorna una estructura de JSX, el cual será el componente a ser renderizado, siendo colocado entre paréntesis
                <> //Fragmento de React para contener el componente sin ser renderizado dentro de otro elemento
                    <Button //Se llama a renderizar como etiqueta HTML, dicho componente importado, el cual recibe las siguientes props
                        **disabled** //Propiedad de "deshabilitado" activada
                        onClick={() => alert("button")}> //Propiedad manejadora de eventos del evento de click sobre éste elemento con valor asignado dentro de llaves por ser código de JS, una función de flecha callback la cual ejecuta la función de ventana emergente la cual cual muestra dicha cadena de texo enviada com argumento
                        Click me //Contiene texto el cual es la propiedad children que necesita el componente estilizado que retorna éste componente
                    </Button>
                </> 
            );
        }
        ```
Enter fullscreen mode Exit fullscreen mode
  • Para que un pueda hacer uso de psedoclases:

    • Al mismo nivel de las propiedades de CSS que recibe el componente, dentro de comillas ‘ ’, se coloca *&:, seguido de la pseudoclase: *‘&:hover’, seguido de dos puntos **: y dentro de llaves *{ }*, se colocan las propiedades y valores de CSS que tendrá dicho componente al utilizar la pseudoclase.

      const DefaultButton = styled.button({ //Declaración de constante con valo asignado de, del objeto/función "styled" importado, se obtiene el elemento "botón" el cual recibe como argumento un objeto con las siguientes propiedades CSS
          backgroundColor: "gray", //Propiedad de color de fondo, con valor "gris"
          color: "white", //Propiedad de color del texto, con valor "blanco"
          **'&:hover': {** //Pseudoclase de posicionamiento del puntero sobre éste componente, con valor de las siguientes propiedades
              **backgroundColor: "white",** //Propiedad de color de fondo, con valor "blanco"
              **color: "black"** //Propiedad de color del texto, con valor "negro"
          **}**
      });
      

Emotion:

  • Posee la mismas características que Styled components.
  • Tiene también una funcionalidad similar a los CSS Modules.
  • Composition.
  • Estilos condicionados out-the-box.

La diferencia con Styled Components y Emotion:

  • Styled Components: Se utilizan componentes estilizados, todo funciona como un componente, al cual se le colocan las propiedades de CSS directamente.
  • Emotion:

    • Dentro de los componentes se utiliza la propiedad *********css:{css }********* importada desde la librería @emotion/react, lo cual hace que los estilo sean en linea, similar a utilizar la propiedad *****style=""*****.

      import { **css** } from '@emotion/react';
      
      const DefaultButton = **props => {
          <button 
              css={css`
                  background-color: gray;
                  color: white;
              `}**
              {...props}
          **/>
      }**;
      
    • También se pueden crear los estilos por separado en el mismo archivo y asignarlos después al momento de renderizar el componente mediante el atributo css={ }:

      import { **css** } from '@emotion/react';
      
      **const DefaultButtonStyles = css`
          background-color: gray;
          color: white;
      `**
      const DefaultButton = **props** => {
          <button **{...props}** />
      };
      
      render(
          <div>
              <DefaultButton **css={DefaultButtonStyles}** />
          </div>
      )
      

Stitches:

Es una herramienta basada en tokens y variantes, en la cual no hay condicionales.

Está enfocada más en el ámbito de diseño, no utiliza un ***********run time***********, sino que se compila en tiempo de ejecución.

  • Basado en tokens y variantes.
  • Es muy similar a StyledComponents y Emotion pero con esteroides.
  • Framework Agnostic.
  • Puedes crear temas de forma muy simple.
  • Enfocado en temas de performance.
  • Genera un sólo componente con diferentes variantes de acuerdo a las necesidades que se tengan.

Variantes:

Variantes:

  • Define variantes múltiples de componentes.
  • Se define el elemento mediante una variable/constante, se le asigna la función *****style(’’, {})***** donde se define que elemento/componente se requiere, y se asignan las variantes del elemento por estilos.
  • Tiene mayor especificad.

Variantes compuestas:

  • Cuando múltiples variantes coincidan en algunas propiedades, se aplique un estilo específico.

Variantes por defecto:

  • Para definir, si no se pone ningún tipo de propiedad en el componente, cuales serían los estilos que aplicaría por defecto.

Tematización:

Tokens:

  • Definir todas las propiedades CSS con valores específicos y reutilizables, los cuales serán utilizadas mediante tokens: ***********************nombres clave***********************.
  • Permite definir múltiples temas.
  • Se definen todos los tokens, lo que permite generar los componentes con base en esos tokens.

Para implementarlo:

  • Se debe instalar la dependencia stitches, mediante ***npm***:
    • npm install @stitches/react
  • Se debe crear un archivo de configuración para definir los tokens, fuera del archivo proyecto y dentro de una carpeta correspondiente al proyecto.

    • Se debe nombrar: ***************************stitches.config.js***************************
    • Se importa la función *****************createStitches**************, desde la librería *‘@stitches/react’:

      // stitches.config.js
      
      **import { createStitches } from '@stitches/react';** //Se importa la función "**createStitches**", desde la librería '**@stitches/react**'
      
    • Se exporta una constante con la sintaxis de destructuración para acceder a las funcionalidades que contiene la función createStitches, con valor asignado de la función createStitches, la cual recibe como argumento, un objeto con las configuraciones necesarias para el proyecto.

      // stitches.config.js
      
      **import { createStitches } from '@stitches/react';** //Se importa la función "createStitches" para crear una nueva instancia de Stitches que se utiliza para definir estilos, desde la librería '@stitches/react'
      
      **export const {** //Se exporta la declración de constante con la sintaxis de destructuración para acceder a las funcionalidades dentro de la función createStitches
          styled,
          css,
          globalCss,
          keyframes,
          getCssText,
          theme,
          createTheme,
          config,
        **} = createStitches({** //Con valor asignado de ejecutar dicha función para crear una nueva instancia de Stitches que se utiliza para definir estilos, la cual recibe como argumento, un objeto con las siguientes propiedades, las cuales son las configuraciones para el proyecto
          **theme: {** //Propiedad de "tema" para definir los distintos tipos de temas que tendrá el componente
            **colors: {**  //Propiedad de colores para el tema, con las siguientes propiedades
              **black100: 'black',** //Declaración de TOKEN, que hará referencia a un valor de color, con valor asigado de, el color "negro"
              **gray500: 'lightgray',** //Declaración de TOKEN, que hará referencia a un valor de color, con valor asigado de, el color "lightgray"
              **primary500: 'blue',** //Declaración de TOKEN, que hará referencia a un valor de color, con valor asigado de, el color "azul"
              **secondary500: 'red'** //Declaración de TOKEN, que hará referncia a un valor de color, con valor asigado de, el color "rojo"
            **},
          },
          media: {** //Propiedad de pantallas de dispositvos, con las siguientes propiedades
            **bp1: '(min-width: 480px)',
          },
          utils: {**  //Propiedad de "utilidades" para estilos específicos mediante una función de flecha que recibe un valor y lo transforma para obtener un estilo CSS específico
            **paddingNormaliced: (value) => ({ padding: value * 4 })** //Declaración de propiedad personalizada, con valor asignado de, una función flecha que recibe un valor como argumento, y ejecuta, dentro de paréntesis el cual contiene un objeto, que a su vez posee como propiedad, el estilo CSS, que a su vez posee como valor, el valor recibido multiplicado por cuatro
          **},
      });**
      
    • Dentro del archivo del componente, se importa desde el archivo de configuración de stitches, la función styled desde su ruta, para poder aplicar los estilos que se definieron:

      **import { styled } from '../stitches.config.js';** //Se importa la función "styled" que se utiliza para definir un nuevo componente estilizado basado en un elemento HTML o en otro componente existente. Se utiliza "styled" para crear estilos y aplicarlos al componente que se está creando, todo dentro de JavaScript, desde, la ruta del archivo de configuración de stitches
      

Para aplicar los estilos:

  • Se declara una constante la cual será el componente, a la cual se le asigna como valor, ejecutar la función importada styled(’’, {}).
  • La función styled(’’, {}) recibe dos parámetros:
    1. El elemento que será el componente, el cual se coloca dentro de comillas.
    2. Los estilos que se le van a aplicar, mediante un objeto.
  • Dentro del objeto de la función styled(’’, {}), se colocan dentro del segundo parámetro, las propiedades CSS, las cuales serán aplicadas por defecto y a todas las variantes, hasta que se declare un estilo que lo cambie.
  • Dentro del segundo parámetro, se declara la propiedad “variants”, la cual dentro de un objeto, se declaran los distintos tipos de variantes como propiedad dentro de dicho objeto “variants”, las cuales pueden ser nombradas arbitrariamente, y deben ser separadas por comas.
  • Dentro del objeto que declara el tipo de variante, se declaran las distintas variantes, la cual dentro de un objeto se declaran las propiedades CSS que serán aplicados a dicha variante, siendo que a cada propiedad se le asigna como valor, un *********token:*********
    • Empezado con el símbolo $ seguido del nombre del *******token******* que hace referencia al valor del estilo que se requiere aplicar, las cuales será separadas por comas.
    • Cada token hace referencia a un valor de estilo declarado dentro del archivo de configuración “stitches.config.js
// Button.jsx

import { styled } from '../stitches.config.js'; //Se importa la función "styled", desde, la ruta del archivo de configuración de stitches

**const Button = styled('button', {** //Declaración de constante, la cual será un componente, con valor asignado de, ejecutar la función "styled" que le declarará los distintos estilos del componente, la cual recibe como primer argumento "el elemento que será el componente", y como segundo argumento un objeto que contendrá sus distintos estilos, los cuales serán los siguientes y serán aplicados a todas las variantes hasta que dicho estilo sea cambiado al declarar el estilo de variante en el componente conrrespondiente
    **borderRadius: '5px',** //Propiedad de redondeo de las esquinas, con valor de 5 pixeles en cada esquina
    **border: '0',** //Propiedad de borde, con valor "0" para no tener borde
    **color: 'white',** //Propiedad de color del texto, con valor "blanco"
    **variants: {** //Propiedad de estilos, las cuales serán las distintas variantes del mismo componente, en un objeto contine los distos tipos de variantes
        **intent: {** //Variantes por "intención", dentro de un objeto contiene las dintintas variantes por "intención"
            **base: {** //Variante base, dentro de un objeto posee sus propiedades CSS para aplicar sus respectivos estilos
                **color: '$black100',** //Propiedad de color del texto, con valor del token que hace referencia a un color declarado dentro de la configuración del archivo "stitches.config.js"
                **backgroundColor: '$gray500'** //Propiedad de color de fondo, con valor del token que hace referencia a un color declarado dentro de la configuración del archivo "stitches.config.js"
            **},
            active: {** //Variante de "activo", dentro de un objeto posee sus propiedades CSS para aplicar sus respectivos estilos
                **backgroundColor: '$primary500'** //Propiedad de color de fondo, con valor del token que hace referencia a un color declarado dentro de la configuración del archivo "stitches.config.js"
            **},
            disabled: {** //Variante de "desactivado", dentro de un objeto posee sus propiedades CSS para aplicar sus respectivos estilos
                **backgroundColor: '$secondary500'** //Propiedad de color de fondo, con valor del token que hace referencia a un color declarado dentro de la configuración del archivo "stitches.config.js"
            **}
        },
        size: {** //Variantes por "tamaño", dentro de un objeto contiene las dintintas variantes por "tamaño"
            **base: {** //Variante "base", dentro de un objeto posee sus propiedades CSS para aplicar sus respectivos estilos
                **paddingNormaliced: 1,** //Propiedad personalizada en el archivo de configuraciones, con valor asignado de, el valor numérico 1, el cual será transformado a lo que fue declarado
                **fontSize: '1em'** //Propiedad de tamaño de fuente, con valor de 1 vez el tamaño de fuente declarado del elemento contenedor mas cercano
            **},
            small: {** //Variante "pequeña", dentro de un objeto posee sus propiedades CSS para aplicar sus respectivos estilos
                **padding: '2px 6px',** //Propiedad de margen interno, con valor de, 2 pixeles superior e inferior, y 6 pixeles a los lados
                **fontSize: '0.6em'** //Propiedad de tamaño de fuente, con valor de 0.6 veces el tamaño de fuente declarado del elemento contenedor mas cercano
            **},
            large: {** //Variante "grande", dentro de un objeto posee sus propiedades CSS para aplicar sus respectivos estilos
                **padding: '8px 10px',** //Propiedad de margen interno, con valor de, 8 pixeles superior e imferior, y 10 pixeles a los lados
                **fontSize: '1.2em'** //Propiedad de tamaño de fuente, con valor de 1.2 veces el tamaño de fuente declarado del elemento contenedor mas cercano
            **}
        }
    },
    defaultVariants: {** //Propiedad de estilos, los cuales serán los etilos por defecto del componente, en un objeto contine los estilos por defecto que serán aplicados al componente que no será una variante
        **intent: 'base',** //Propiedad de variante por "intención", con valor de, "base"
        **size: 'base'** //Propiedad de variante por "tamaño", con valor de, "base"
    **}
});**

export default **Button**; //Se exporta como valor por defecto, dicho componente "**Button**" con sus estilos aplicados, para poder ser renderizado
Enter fullscreen mode Exit fullscreen mode

RESPONSIVE:

  • Mobile First: Se utiliza ‘(min-width: …px)’
  • Desktop First: Se utiliza ‘(max-width: …px)’

Las propiedades CSS de los estilos que se colocan primero, en el segundo argumento de la función styled, serán aplicados al break point que se esté trabajando, siendo recomendado empezar por Mobile First, e ir subiendo el tamaño de los break points.

  • Los break points se definen mediante un token en la propiedad *********media:{}*******, dentro de la función **createStitches({}) en el archivo stitches.config.js.
  • Se declara el token, y como valor, dentro de comillas y de paréntesis se coloca min-width: o max-width:, y se coloca el valor del break point.

    media: { //Propiedad de tamaños de pantalla, con valor de un objeto con las siguientes propiedades
          **bpMobile: '(min-width: 480px)',** //Declaración de token, para break point de mobile, con valor asignado de, ancho minimo, de, 480 pixeles
          **bpTablet: '(min-width: 720px)',** //Declaración de token, para break point de tablet, con valor asignado de, ancho minimo, de, 720 pixeles
          **bpDesktop: '(min-width: 1080px)',** //Declaración de token, para break point de desktop, con valor asignado de, ancho minimo, de, 1080 pixeles
    },
    
  • Una vez definidos los break points en el archivo stitches.config.js, al declarar los estilos utilizando la función *************styled(’’, {})**********, dentro de comillas *‘ ’*, se coloca, mediante el símbolo *@, el nombre del break point, y para asignar los estilos, se hace mediante un objeto al cual se le colocan las propiedades(estilo) CSS con su valor.

    intent: { //Variantes por "intención", dentro de un objeto contiene las dintintas variantes por "intención"
        base: { //Variante "base", dentro de un objeto posee sus propiedades CSS para aplicar sus respectivos estilos
            **'@bpMobile': {** //token el cual hace refetencia al break point de mobile, con valor de un objeto, el cual contine los siguiente estilos de CSS 
                **color: '$mobile',** //Propiedad de color del texto, con valor del token que hace referencia a un color declarado dentro de la configuración del archivo "stitches.config.js"
            **},
            '@bpTablet': {** //token el cual hace refetencia al break point de tablet, con valor de un objeto, el cual contine los siguiente estilos de CSS 
                **color: '$tablet',** //Propiedad de color del texto, con valor del token que hace referencia a un color declarado dentro de la configuración del archivo "stitches.config.js"
            **},
            '@bpDesktop': {** //token el cual hace refetencia al break point de desktop, con valor de un objeto, el cual contine los siguiente estilos de CSS 
                **color: '$desktop',** //Propiedad de color del texto, con valor del token que hace referencia a un color declarado dentro de la configuración del archivo "stitches.config.js"
            **},**
            backgroundColor: '$gray500' //Propiedad de color de fondo, con valor del token que hace referencia a un color declarado dentro de la configuración del archivo "stitches.config.js"
        },
    },
    

Para renderizar:

  • Se importa el componente desde la ruta del archivo que lo contiene.
  • Se coloca como etiqueta HTML para poder ser renderizado.
  • Se le colocan las propiedades que hacen referencia a las variables declaradas dentro de la propiedad “variants” al declarar los estilos del componente.
    • En caso de no necesitar ninguna variante, solo se renderiza el componente y así se le aplicarán los estilos por defecto.
import Button from './components/Button'; //Se importa como valor por defecto, el componente estilizado "Button", desde su ruta hasta el archivo del componente si colocar su extensión

export default function App() { //Se exporta como valor por defecto, la declaración de función que será un componente, el cual ejecuta el siguiente bloque
    return ( //Se retorna una estructura de JSX, el cual será el componente a ser renderizado, siendo colocado entre paréntesis
        <> //Fragmento de React para contener el componente sin ser renderizado dentro de otro elemento
            **<Button>Click me</Button>** //Se renderiza el componente "Button", el cual al no colocarle ningún atributo, se le aplican los estilos por defecto declarados en la propiedad "defaultVariants" y los estilos declarados al inicio del del objeto de estilos que son aplicados a todas las variantes, y contiene texto lo cual es lo que mostrará el componente
            **<Button** //Se renderiza el componente "Button", el cual recibe las siguientes "props"
                **intent={'active'}** //Propiedad de variante de "intención", con valor asignado dentro de llaves por ser código de JS, como cadena de texto, el valor de la variante que requiere, siendo el de "activo"
                **size={'large'}>** //Propiedad de variante de "tamaño", con valor asignado dentro de llaves por ser código de JS, como cadena de texto, el valor de la variante que requiere, siendo el de "grande"
                **Click me** //Contiene texto, lo cual es lo que mostrará el componente
            **</Button>
            <Button** //Se renderiza el componente "Button", el cual recibe las siguientes "props"
                **intent={'disabled'}** //Propiedad de variante de "intención", con valor asignado dentro de llaves por ser código de JS, como cadena de texto, el valor de la variante que requiere, siendo el de "desactivado"
                **size={'small'}>** //Propiedad de variante de "tamaño", con valor asignado dentro de llaves por ser código de JS, como cadena de texto, el valor de la variante que requiere, siendo el de "pequeño"
                **Click me** //Contiene texto, lo cual es lo que mostrará el componente
            **</Button>**
        </> 
    );
}
Enter fullscreen mode Exit fullscreen mode

TailwindCSS:

Es una herramienta que se considera una “*********************utility first*********************”, que en este caso provee todas las utilidades necesarias las cuales son la necesidades que se requieren para el comportamiento y visualización de los elementos sin la necesidad de escribir todo el código del CSS.

Las *****************utilities***************** son las necesidades que se tienen al momento de escribir en CSS, las cuales son el comportamiento y visualización.

Así ya no se piensa directamente en el CSS, sino en las utilidades/necesidades requeridas para un elemento, enfocándose en el “*********************utility first*********************”.

El performance, a nivel de purgado, solo utiliza las clases que realmente se están utilizando en los componentes de React, así solo se tiene un archivo con las clases que se están utilizando, incrementando el rendimiento.

  • Provee las utilidades, las cuales pueden ser modificadas.
  • Generación de clases en tiempo de construcción.
  • Purging.
  • Plugins para extender tus clases.
  • PostCSS.
  • Estilizado condicional con una dependencias.

Top comments (0)