Hướng dẫn react typescript css modules - phản ứng các mô-đun css TypeScript

A) Như bạn đang nói, có một tùy chọn đơn giản nhất (không tốt nhất) để sử dụng yêu cầu:require:

const css = require('./component.css')
  • Chúng ta cần có các kiểu đánh máy cho require vì nó không phải là tính năng tiêu chuẩn trong TypeScript.
  • Gõ đơn giản nhất cho yêu cầu cụ thể này có thể là:

    declare function require(name: string): string;
    
  • Webpack sau đó sẽ biên dịch TypeScript và sử dụng các mô -đun đúng cách - nhưng không có bất kỳ trợ giúp IDE nào và tên lớp kiểm tra để xây dựng.BUT without any IDE help and class names checks for build.

B) Có giải pháp tốt hơn để sử dụng nhập khẩu tiêu chuẩn:import:

import * as css from './component.css'
  • Cho phép tên lớp học đầy đủ IntelliSenseclass names IntelliSense
  • Yêu cầu định nghĩa loại cho mỗi tệp CSS, nếu không Trình biên dịch ____10 sẽ không thành công

Đối với Intellisense thích hợp, WebPack cần tạo định nghĩa loại cho từng tệp CSS:

  1. Sử dụng WebPack Typings-for-CSS-Modules-Loader

    webpackConfig.module.loaders: [
      { test: /\.css$/, loader: 'typings-for-css-modules?modules' }
      { test: /\.scss$/, loader: 'typings-for-css-modules?modules&sass' }
    ];
    
  2. Trình tải sẽ tạo các tệp

    declare function require(name: string): string;
    
    1 cho mỗi tệp CSS trong cơ sở mã của bạn

  3. Trình biên dịch TypeScript sẽ hiểu rằng nhập CSS sẽ là mô -đun với các thuộc tính (tên lớp) của chuỗi loại.

Đã đề cập

declare function require(name: string): string;
2 chứa một lỗi và do độ trễ tạo tệp loại, tốt nhất là khai báo loại
declare function require(name: string): string;
3 toàn cầu trong trường hợp tệp
declare function require(name: string): string;
1 của chúng tôi chưa được tạo.

Kịch bản lỗi nhỏ đó:

  1. Tạo tệp CSS
    declare function require(name: string): string;
    
    5
  2. Bao gồm nó trong thành phần
    declare function require(name: string): string;
    
    6
  3. Chạy
    declare function require(name: string): string;
    
    7
  4. Trình biên dịch TypeScript sẽ cố gắng biên dịch mã (lỗi)
  5. Trình tải sẽ tạo tệp đánh máy mô -đun CSS (
    declare function require(name: string): string;
    
    8), nhưng đã trễ trình biên dịch TypeScript để tìm tệp đánh máy mới
  6. Chạy lại
    declare function require(name: string): string;
    
    7 sẽ sửa lỗi xây dựng.

Easy Fix là tạo định nghĩa toàn cầu (ví dụ: Tệp được gọi là

import * as css from './component.css'
0 trong root nguồn của bạn) để nhập các mô -đun CSS:

declare module '*.css' {
  interface IClassNames {
    [className: string]: string
  }
  const classNames: IClassNames;
  export = classNames;
}

Định nghĩa này sẽ được sử dụng nếu không có tệp CSS được tạo (ví dụ: bạn đã thêm tệp CSS mới). Nếu không, sẽ được sử dụng cụ thể được tạo (cần phải có trong cùng một thư mục và được đặt tên giống như Tệp nguồn +

import * as css from './component.css'
1 mở rộng), ví dụ:
declare function require(name: string): string;
8 Định nghĩa và Intellisense sẽ hoạt động hoàn hảo.

Ví dụ về

declare function require(name: string): string;
8:

export const wrapper: string;
export const button: string;
export const link: string;

Và nếu bạn không muốn xem các bản đánh máy CSS được tạo, bạn có thể thiết lập bộ lọc trong IDE để ẩn tất cả các tệp với phần mở rộng .css.d.ts trong các nguồn của bạn.

Đã đăng vào thg 8 21, 2019 3:41 SA 2 phút đọc 2 phút đọc 2 phút đọc

Nếu bạn có kinh nghiệm làm việc với các stylesheets của các ứng dụng web lớn, source css cả trăm files, cả ngàn dòng, hàng chục ngàn tên class, thì vấn đề naming classes, các classes bị xung đột, overrides đôi khi trở nên cực kì quan trọng và có lúc bạn tốn tới hàng giờ để refactor lại component cũ chỉ để style component mới không bị ảnh hưởng tới các component đã style.naming classes, các classes bị xung đột, overrides đôi khi trở nên cực kì quan trọng và có lúc bạn tốn tới hàng giờ để refactor lại component cũ chỉ để style component mới không bị ảnh hưởng tới các component đã style.naming classes, các classes bị xung đột, overrides đôi khi trở nên cực kì quan trọng và có lúc bạn tốn tới hàng giờ để refactor lại component cũ chỉ để style component mới không bị ảnh hưởng tới các component đã style.

Từ đó, CSS Modules ra đời 🎉 . Nó giúp chúng ta có thể module hoá stylesheet thành các file CSS nhỏ và scoped locally to the component (*)CSS Modules ra đời 🎉 . Nó giúp chúng ta có thể module hoá stylesheet thành các file CSS nhỏ và scoped locally to the component (*)CSS Modules ra đời 🎉 . Nó giúp chúng ta có thể module hoá stylesheet thành các file CSS nhỏ và scoped locally to the component (*)

scoped locally to the component (*): nôm na là tất cả class name, selectors, animations trong css modules files sẽ chỉ hợp lệ ở component import nó và không ảnh hưởng tới thành phần các trong website.

Ở bài viết này, chúng ta sẽ sử dụng CSS Modules trong React. Nếu bạn sử dụng create-react-app (v2) để setup ứng dụng react của bạn thì CSS Modules đã được setup sẵn.create-react-app (v2) để setup ứng dụng react của bạn thì CSS Modules đã được setup sẵn.create-react-app (v2) để setup ứng dụng react của bạn thì CSS Modules đã được setup sẵn.

Vậy còn chờ gì nữa ? Give it a try.

Sử dụng CSS Modules trong React

Bắt đầu với 1 component Logo được style bằng SASS và convert nó sang kiểu CSS Modules.

/* -- Logo.js -- */

import React from "react";

const Logo = () => {
  return (
    <div className="logo">
      <div className="logo__text">
        <span className="logo__extra logo-extra--left" />
        <span className="logo__extra logo-extra--right" />
        <span className="logo__content">
          <span className="logo__name">{`thebao`}span>
          <span className="logo__key">{`dev`}span>
        span>
      div>
    div>
  );
};

export default Logo

Style Component với CSS Modules:

1.Tạo file CSS Modules

Chúng ta sẽ tạo 1 file scss với dạng là

import * as css from './component.css'
4 cùng folder với Logo.js và bắt dầu style component Logo.

Lưu ý ở ví dụ này mình sử dụng SCSS, các bạn hoàn toàn có thể sử dụng vanila CSS với

import * as css from './component.css'
5

/* -- Logo.module.scss -- */
        
.logo-wrapper {
  position: relative;
  z-index: 10;
  margin: 0 auto;


.logo-text {
  font-size: $font-size-large;
  padding: 0 .5rem;

  @include flexbox();

  @include align-items(center);

  @include position(relative);

  .content {
    font-family: $font-family-logo;
    background-color: $white;
    color: $primary;
    margin: auto 10px;
    padding: 5px 10px;
    border-radius: $border-radius-base;
    transform: skew(-15deg, 0deg);
  }

  .key {
    font-size: $font-size-super-large;
  }

  .name {
    font-size: $font-size-large;
  }

  .extra {
    background-color: $info;
    border-radius: $border-radius-base;
    opacity: .4;
    transform: skew(-15deg, 0deg);
    z-index: -1;

    @include size(30px, 25px);

    &-right {
      @include position(absolute, -6px, 2px, null, null);
    }

    &-left {
      @include position(absolute, null, null, -6px, 2px);
    }
  }

2.Import CSS Modules

Import styles ở trên vào Logo.js component. Biến logoStyles là 1 object chứa các CSS styles đã define ở trên. Từ đó chúng ta có thể get các classnames đã được create-react-app modular hoá (*) và sử dụng chúng trong JSX của Logo component.logoStyles là 1 object chứa các CSS styles đã define ở trên. Từ đó chúng ta có thể get các classnames đã được create-react-app modular hoá (*) và sử dụng chúng trong JSX của Logo component.logoStyles là 1 object chứa các CSS styles đã define ở trên. Từ đó chúng ta có thể get các classnames đã được create-react-app modular hoá (*) và sử dụng chúng trong JSX của Logo component.

 /* -- Logo.js -- */
        
import React from "react";

/* Import logoStyles */
import logoStyles from "./Logo.module.scss";

const Logo = () => {
  return (
    <div className={logoStyles["logo-wrapper"]}>
      <div className={logoStyles.["logo-text"]}>
        <span className={`${logoStyles.["extra"]} ${logoStyles.["extra-left"]}`} />
        <span className={`${logoStyles.["extra"]} ${logoStyles.["extra-right"]}`} />
        <span className={logoStyles.["content"]}>
          <span className={logoStyles.["name"]}>{`thebao`}span>
          <span className={logoStyles.["key"]}>{`dev`}span>
        span>
      div>
    div>
  );
};

export default Logo

*modular hoá: khi chúng ta inspect Logo component, các tên class còn được thêm vào 1 chuỗi kí tự đằng sau nó. Điều này giúp cho các classname được unique, scope chỉ trong component import nó. Lưu ý là import Logo.module.scss ở 2 component khác nhau thì nó cũng là 2 chuỗi kí tự khác nhau. Giải quyết được các vấn đề conflict, CSS specificity và cascade.modular hoá: khi chúng ta inspect Logo component, các tên class còn được thêm vào 1 chuỗi kí tự đằng sau nó. Điều này giúp cho các classname được unique, scope chỉ trong component import nó. Lưu ý là import Logo.module.scss ở 2 component khác nhau thì nó cũng là 2 chuỗi kí tự khác nhau. Giải quyết được các vấn đề conflict, CSS specificity và cascade.modular hoá: khi chúng ta inspect Logo component, các tên class còn được thêm vào 1 chuỗi kí tự đằng sau nó. Điều này giúp cho các classname được unique, scope chỉ trong component import nó. Lưu ý là import Logo.module.scss ở 2 component khác nhau thì nó cũng là 2 chuỗi kí tự khác nhau. Giải quyết được các vấn đề conflict, CSS specificity và cascade.

Tìm hiểu kĩ hơn về CSS Modules: https://viblo.asia/p/tim-hieu-ve-css-modules-phan-1-E7bGoxl4v5e2

That's it 😄. Cám ơn các bạn đã theo dõi.

Nguồn tham khảo: https://create-react-app.dev/docs/adding-a-css-modules-stylesheet

All rights reserved