Flexbox trong CSS

Flexbox trong CSS

Rate this post

Mô-đun Flexible Box, thường được gọi là flexbox, được thiết kế như một mô hình bố cục một chiều và là một phương pháp có thể cung cấp phân phối không gian giữa các Items trong một giao diện và khả năng căn chỉnh mạnh mẽ. Bài viết này đưa ra một phác thảo về các tính năng chính của flexbox, mà chúng ta sẽ khám phá chi tiết hơn trong phần còn lại của các hướng dẫn này.

Khi chúng ta mô tả flexbox là một chiều, chúng tôi đang mô tả thực tế là flexbox xử lý bố cục trong một dimensional tại một thời điểm – dưới dạng row hoặc cột. Điều này có thể tương phản với mô hình hai chiều của CSS Grid Layout, điều khiển các columns và row cùng nhau.

Các bài viết liên quan:

Hai trục của flexbox

Khi làm việc với flexbox, bạn cần suy nghĩ về hai trục – trục ngang và trục dọc. Trục ngang được xác định bởi thuộc flex-direction  và trục dọc chạy vuông góc với nó. Mọi thứ chúng tôi làm với flexbox đều đề cập đến các trục này, vì vậy cần hiểu cách chúng hoạt động ngay từ đầu.

Trục chính(main axis)

Trục chính được xác định flex-direction, có bốn giá trị có thể có:

  • row
  • row-reverse
  • column
  • column-reverse

Nếu bạn chọn row hoặc row-reverse, trục chính của bạn sẽ chạy dọc theo row theo inline direction.

Flexbox trong CSS

Chọn columns hoặc columns-reverse và trục chính của bạn sẽ chạy từ đầu trang đến cuối trang – theo chiều dọc.

Flexbox trong CSS

Trục ngang(Cross axis)

Cross axis chạy vuông góc với trục chính, do đó nếu flex-direction(trục chính) của bạn được đặt thành row hoặc row-reverse, cross axis sẽ chạy xuống các cột.

Flexbox trong CSS

Nếu trục chính của bạn là columns hoặc columns-reverse thì cross axis chạy dọc theo các hàng.

Flexbox trong CSS

Hiểu được trục nào là quan trọng khi chúng ta bắt đầu xem xét việc căn chỉnh và căn chỉnh; flexbox có các thuộc tính căn chỉnh và căn đều nội dung dọc theo trục này hoặc trục kia.

Sử dụng Flexbox

Một lĩnh vực quan trọng khác của sự hiểu biết là cách flexbox không đưa ra giả định về chế độ ghi của tài liệu. Trước đây, CSS được chú trọng nhiều vào các chế độ viết ngang và từ trái sang phải. Các phương pháp bố cục hiện đại bao gồm phạm vi chế độ viết và vì vậy chúng tôi không còn giả định rằng một dòng văn bản sẽ bắt đầu ở trên cùng bên trái của tài liệu và chạy về phía bên tay phải, với các dòng mới xuất hiện bên dưới dòng khác.

Bạn có thể đọc thêm về mối quan hệ giữa flexbox và đặc tả Chế độ Viết trong một bài viết sau; tuy nhiên, mô tả sau đây sẽ giúp giải thích lý do tại sao chúng ta không nói về trái và phải và trên cùng và dưới cùng khi chúng tôi mô tả hướng mà các flex items của chúng tôi chảy vào.

Nếu flex-direction là row và tôi đang làm việc bằng tiếng Anh, thì cạnh bắt đầu của trục chính sẽ ở bên trái, cạnh cuối ở bên phải.

Flexbox trong CSS

Nếu tôi làm việc bằng tiếng Ả Rập, thì cạnh bắt đầu của trục chính của tôi sẽ ở bên phải và cạnh cuối ở bên trái.

Flexbox trong CSS

Trong cả hai trường hợp, cạnh bắt đầu của trục chữ thập nằm ở trên cùng của flex container và cạnh kết thúc ở dưới cùng, vì cả hai ngôn ngữ đều có chế độ viết ngang.

Sau một thời gian, suy nghĩ về bắt đầu và kết thúc thay vì trái và phải trở nên tự nhiên và sẽ hữu ích cho bạn khi xử lý các phương pháp bố cục khác như CSS Grid Layout theo cùng một mẫu.

Flex container

Một vùng của tài liệu được bố trí bằng cách sử dụng flexbox được gọi là flex container. Để tạo flex container, chúng tôi đặt giá trị của thuộc tính display container của container thành flex  hoặc inline-flex. Ngay sau khi chúng tôi làm điều này, các phần tử con trực tiếp của container đó sẽ trở thành các flex items. Như với tất cả các thuộc tính trong CSS, một số giá trị initial được xác định, vì vậy khi tạo một flex container, tất cả các flex items được chứa sẽ hoạt động theo cách sau.

  • các Items hiển thị trong một row (mặc định của thuộc tính flex-direction là row).
  • các Items bắt đầu từ cạnh bắt đầu của trục chính.
  • các Items không kéo dài theo chiều chính, nhưng có thể co lại.
  • các Items sẽ kéo dài để lấp đầy kích thước của cross axis.
  • Thuộc tính flex-basis  được đặt thành tự động.
  • Thuộc tính flex-wrap được đặt thành nowrap.

Kết quả của việc này là tất cả các Items của bạn sẽ xếp thành một hàng, sử dụng kích thước của nội dung làm kích thước của chúng trong trục chính. Nếu có nhiều items hơn có thể chứa trong box, chúng sẽ không bọc mà thay vào đó sẽ tràn ra ngoài. Nếu một số items cao hơn những items khác, tất cả các Items sẽ kéo dài theo cross axis để lấp đầy kích thước đầy đủ của nó.

Bạn có thể xem trong ví dụ trực tiếp bên dưới cách này. Hãy thử chỉnh sửa các Items hoặc thêm các Items bổ sung để kiểm tra hoạt động initial của flexbox.

Flexbox trong CSS
<div class="box">
          <div>One</div>
          <div>Two</div>
          <div>Three
              <br>has
              <br>extra
              <br>text
          </div>
        </div>
      
 .box {
            display: flex;
          }

Thay đổi flex-direction

Thêm thuộc tính flex-direction vào tất cả flex container giúp chúng tôi để thay đổi hướng hiển thị các flex items của chúng tôi. Đặt flex-direction: row-reverse sẽ giữ cho các Items hiển thị dọc theo hàng, tuy nhiên dòng bắt đầu và dòng kết thúc được chuyển đổi.

Nếu chúng ta thay đổi flex-direction thành Columns, trục chính sẽ chuyển và các Items của chúng ta hiện hiển thị trong một cột. Đặt columns-reverse và dòng bắt đầu và dòng kết thúc lại được chuyển đổi.

Ví dụ trực tiếp bên dưới có flex-direction được đặt thành row-reverse. Hãy thử các giá trị khác – hàng, columns và column-reverse – để xem điều gì xảy ra với nội dung.

Flexbox trong CSS
     <div class="box">
          <div>One</div>
          <div>Two</div>
          <div>Three</div>
        </div>
 .box {
          display: flex;
          flex-direction: row-reverse;
        }

Multi-line flex containers với flex-wrap

Mặc dù flexbox là mô hình một chiều, có thể khiến các Items flex của chúng ta bị quấn thành nhiều dòng. Khi làm như vậy, bạn nên coi mỗi dòng là một flex container mới. Bất kỳ sự phân bố không gian nào sẽ xảy ra trên đường đó, không tham chiếu đến các đường ở hai bên.

Để gây ra, hãy thêm thuộc tính flex-wrap với giá trị là wrap. Bây giờ, nếu các Items của bạn quá lớn để tất cả hiển thị trên một dòng, chúng sẽ quấn vào một dòng khác. Mẫu trực tiếp bên dưới chứa các Items đã được cung cấp chiều rộng, tổng chiều rộng của các Items quá rộng đối với flex container. Khi flex-wrap được thiết lập để wrap, các Items sẽ wrap. Đặt nó thành nowrap, cũng là giá trị initial và thay vào đó, chúng sẽ thu nhỏ để vừa với container vì chúng đang sử dụng các giá trị flexbox initial cho phép các Items thu nhỏ. Sử dụng Nowrap sẽ gây ra tràn nếu các Items không thể co lại hoặc không thể co lại đủ nhỏ để vừa.

Flexbox trong CSS
<div class="box">
        <div>One</div>
        <div>Two</div>
        <div>Three</div>
      </div>
    
     .box {
        display: flex;
        flex-wrap: wrap;
    }

Viết tắt flex-flow

Bạn có thể kết hợp hai thuộc tính flex-direction và flex-wrap thành flex-flow. Giá trị đầu tiên được chỉ định là flex-direction và giá trị thứ hai là flex-wrap.

Trong ví dụ trực tiếp bên dưới, hãy thử thay đổi giá trị đầu tiên thành một trong các giá trị cho phép đối với hướng flex – hàng, row-reverse, columns hoặc columns-reverse và cũng thay đổi giá trị thứ hai thành wrap và bây giờ.

Flexbox trong CSS
  <div class="box">
        <div>One</div>
        <div>Two</div>
        <div>Three</div>
      </div>
    
.box {
        display: flex;
        flex-flow: row wrap;
      }

Thuộc tính flex items

Để có nhiều quyền kiểm soát hơn đối với các flex items, chúng tôi có thể nhắm items tiêu chúng trực tiếp. Chúng tôi thực hiện điều này bằng ba thuộc tính:

  • flex-grow
  • flex-shrink
  • flex-basis

Chúng tôi sẽ xem xét ngắn gọn các thuộc tính này trong phần tổng quan này và bạn có thể hiểu đầy đủ.

Trước khi có thể hiểu được những đặc tính này, chúng ta cần xem xét khái niệm về không gian khả dụng. Những gì chúng tôi đang làm khi chúng tôi thay đổi giá trị của các thuộc tính flex này là thay đổi cách phân phối không gian khả dụng giữa các Items của chúng tôi. Khái niệm về không gian có sẵn này cũng rất quan trọng khi chúng ta xem xét việc sắp xếp các mặt hàng.

Nếu chúng ta có ba items rộng 100 pixel trong một container rộng 500 pixel, thì không gian chúng tôi cần để bố trí các Items của mình là 300 pixel. Điều này để lại 200 pixel không gian khả dụng. Nếu chúng tôi không thay đổi các giá trị initial thì flexbox sẽ đặt khoảng trống đó sau items cuối cùng.

Flexbox trong CSS

Thay vào đó, nếu chúng ta muốn các Items lớn lên và lấp đầy không gian, thì chúng ta cần phải có một phương pháp phân phối không gian còn lại giữa các Items. Đây là những gì các thuộc tính flex mà chúng tôi áp dụng cho chính các Items sẽ thực hiện.

Thuộc tính cơ bản flex

flex-basis là thông số về kích thước items đó trong một vùng không gian có sẵn. Giá trị initial là giá trị mặc định mà trình duyệt có thể thấy. Trong ví dụ: các items có độ lớp 100px.

Nếu các Items không có kích thước thì kích thước của nội dung được sử dụng làm flex-basis. Đây là lý do tại sao khi chúng ta chỉ khai báo display: flex trên element cha để tạo các Items flex, các Items này đều di chuyển thành một row và chỉ chiếm nhiều không gian khi chúng cần để hiển thị nội dung của chúng.

Thuộc tính flex-grow

Với thuộc tính flex-grow được đặt thành số nguyên dương, các Items flex có thể phát triển dọc theo trục chính từ flex-basis của chúng. Điều này sẽ làm cho mặt row bị kéo dài và chiếm bất kỳ không gian có sẵn nào trên trục đó hoặc một tỷ lệ của không gian có sẵn nếu các mặt row khác cũng được phép phát triển.

Nếu chúng ta cho tất cả các mặt row của mình trong ví dụ trên giá trị flex-grow là 1 thì không gian có sẵn trong container flex sẽ được chia đều giữa các mặt row của chúng ta và chúng sẽ căng ra để lấp đầy container trên trục chính.

Thuộc tính flex-grow có thể được sử dụng để phân phối không gian theo tỷ lệ. Nếu chúng tôi đặt giá trị flex-grow của items đầu tiên là 2 và các Items khác có giá trị là 1, thì 2 phần sẽ được trao cho items đầu tiên (100px trong số 200px trong trường hợp của ví dụ trên), mỗi items 1 phần hai cái còn lại (50px mỗi cái trong tổng số 200px).

Thuộc tính flex-shrink

Trong đó thuộc tính flex-grow đề cập đến việc thêm không gian trong trục chính, thuộc tính flex-shrink lại kiểm soát cách nó được lấy đi. Nếu chúng ta không có đủ không gian trong container để sắp xếp các Items của mình và flex-shrink được đặt thành một số nguyên dương, thì items có thể trở nên nhỏ hơn flex-basis. Như với flex-grow, các giá trị khác nhau có thể được chỉ định để làm cho một items co lại nhanh hơn các Items khác – một items có giá trị cao hơn được đặt cho flex-shrink sẽ co lại nhanh hơn so với các sản phẩm cùng loại có giá trị thấp hơn.

Kích thước tối thiểu của mặt row sẽ được tính đến trong khi tính toán lượng co rút thực tế sẽ xảy ra, điều đó có nghĩa là flex-shrink có khả năng xuất hiện ít nhất quán hơn so với co rút trong hoạt động. Do đó, chúng tôi sẽ xem xét chi tiết hơn cách thuật toán này hoạt động trong bài viết Kiểm soát tỷ lệ của các Items dọc theo trục chính.

Lưu ý: Các giá trị cho flex-shrink và thu nhỏ này là tỷ lệ. Thông thường, nếu tất cả các Items của mình được đặt thành flex: 1 1 200px và sau đó muốn một items phát triển với tốc độ gấp đôi, chúng tôi sẽ đặt items đó thành flex: 2 1 200px. Tuy nhiên, bạn cũng có thể sử dụng flex: 10 1 200px và flex: 20 1 200px nếu muốn.

Giá trị viết tắt cho các thuộc tính flex

Bạn sẽ rất hiếm khi thấy các thuộc tính flex-grow, flex-shrink và flex-base được sử dụng riêng lẻ; thay vào đó chúng được kết hợp thành viết tắt flex. Viết tắt flex cho phép bạn đặt ba giá trị theo thứ tự này – flex-grow, flex-shrink, flex-base.

Ví dụ trực tiếp bên dưới cho phép bạn kiểm tra các giá trị khác nhau của tốc ký flex; hãy nhớ rằng giá trị đầu tiên là flex-grow. Mang lại giá trị dương này có nghĩa là mặt row có thể phát triển. Thứ hai là flex-shrink – với giá trị dương, các Items có thể co lại, nhưng chỉ khi tổng giá trị của chúng tràn qua trục chính. Giá trị cuối cùng là flex-basis; đây là giá trị mà các mặt row đang sử dụng làm giá trị cơ bản để tăng trưởng và thu nhỏ từ đó.

Flexbox trong CSS
 <div class="box">
        <div class="one">One</div>
        <div class="two">Two</div>
        <div class="three">Three</div>
      </div>
    
.box {
        display: flex;
      }

      .one {
        flex: 1 1 auto;
      }

      .two {
        flex: 1 1 auto;
      }

      .three {
        flex: 1 1 auto;
      }

Ngoài ra còn có một số giá trị tốc ký được xác định trước bao gồm hầu hết các trường hợp sử dụng. Bạn sẽ thường thấy những thứ này được sử dụng trong các hướng dẫn, và trong nhiều trường hợp, đây là tất cả những gì bạn cần để sử dụng. Các giá trị được xác định trước như sau:

  • flex: initial
  • flex: auto
  • flex: none
  • flex: <positive-number>

Setting flex: initial đặt lại items về các giá trị initial của Flexbox. Điều này cũng giống như flex: 0 1 auto. Trong trường hợp này, giá trị của flex-grow là 0, vì vậy các Items sẽ không lớn hơn kích thước flex-basis của chúng. Giá trị của flex-shrink là 1, vì vậy các Items có thể co lại nếu chúng cần thay vì tràn. Giá trị của flex-basis là tự động. các Items sẽ sử dụng bất kỳ kích thước nào được đặt trên items trong kích thước chính hoặc chúng sẽ lấy kích thước của chúng từ kích thước nội dung.

Sử dụng flex: auto cũng giống như sử dụng flex: 1 1 auto; mọi thứ giống như với flex: initial nhưng trong trường hợp này, các Items có thể phát triển và lấp đầy container cũng như co lại nếu được yêu cầu.

Sử dụng flex: none có gì sẽ tạo ra các Items hoàn toàn không flex. Nó giống như thể bạn đã viết flex: 0 0 auto. các Items không thể phát triển hoặc thu nhỏ nhưng sẽ được sắp xếp bằng cách sử dụng flexbox với cơ sở tự động flex-shrink.

Viết rút gọn bạn thường thấy trong các hướng dẫn là flex: 1 hoặc flex: 2, v.v. Điều này giống như thể bạn đã sử dụng flex: 1 1 0. các Items có thể phát triển và co lại từ flex-basis là 0.

Hãy thử các giá trị viết tắt này trong ví dụ trực tiếp bên dưới.

Flexbox trong CSS
 <div class="box">
        <div class="one">One</div>
        <div class="two">Two</div>
        <div class="three">Three</div>
      </div>
 .box {
        display: flex;
      }

      .one {
        flex: 1;
      }

      .two {
        flex: 1;
      }

      .three {
        flex: 1;
      }
  

Căn chỉnh, hợp lý và phân phối không gian trống giữa các Items

Một tính năng chính của flexbox là khả năng căn chỉnh và căn đều các Items trên trục chính và cross axis, đồng thời phân phối không gian giữa các Items flex. Lưu ý rằng các thuộc tính này sẽ được đặt trên flex container, không phải trên bản thân các Items.

Thuộc tính align-items sẽ căn chỉnh các Items trên cross axis.

Giá trị initial cho thuộc tính này là co giãn và đây là lý do tại sao các flex items kéo dài đến chiều cao của flex container theo mặc định. Điều này có thể được quy định bởi chiều cao của items cao nhất trong container hoặc bởi kích thước được đặt trên chính container flex.

Thay vào đó, bạn có thể đặt căn chỉnh các Items thành flex-start để làm cho các Items xếp row ở đầu container flex, flex-end để căn chỉnh chúng cho đến cuối hoặc căn giữa để căn giữa chúng. Hãy thử điều này trong ví dụ trực tiếp – chúng ta đã cung cấp cho thùng flex một chiều cao để bạn có thể thấy cách các Items có thể được di chuyển xung quanh bên trong container. Xem điều gì sẽ xảy ra nếu bạn đặt giá trị của các Items căn chỉnh thành:

  • stretch
  • flex-start
  • flex-end
  • center
Flexbox trong CSS
.box {
            display: flex;
            align-items: flex-start;
          }
<div class="box">
          <div>One</div>
          <div>Two</div>
          <div>Three
              <br>has
              <br>extra
              <br>text
          </div>
        </div>

justify-content

Thuộc tính justify-content được sử dụng để căn chỉnh các Items trên trục chính, hướng mà flex-direction đã thiết lập luồng. Giá trị initial là flex-start sẽ xếp các Items ở mép bắt đầu của container, nhưng bạn cũng có thể đặt giá trị thành flex-end để xếp chúng ở cuối hoặc căn giữa để xếp chúng ở giữa.

Bạn cũng có thể sử dụng giá trị khoảng cách giữa để lấy tất cả không gian trống sau khi các Items đã được sắp xếp và chia đều giữa các Items để có một lượng không gian bằng nhau giữa mỗi items. Để tạo ra một lượng không gian bằng nhau ở bên phải và bên trái của mỗi items, hãy sử dụng giá trị khoảng cách xung quanh. Với không gian xung quanh, các Items có một nửa kích thước không gian ở hai đầu. Hoặc, để làm cho các Items có không gian bằng nhau xung quanh chúng, hãy sử dụng không gian giá trị-đồng đều. Với không gian đồng đều, các Items có không gian kích thước đầy đủ ở hai đầu.

Hãy thử các giá trị sau của justify-content trong ví dụ trực tiếp:

  • flex-start
  • flex-end
  • center
  • space-around
  • space-between
  • space-evenly

Trong bài viết Căn chỉnh các Items trong một Flex Container, chúng ta sẽ tìm hiểu sâu hơn về các thuộc tính này, để hiểu rõ hơn về cách chúng hoạt động. Tuy nhiên, những ví dụ đơn giản này sẽ hữu ích trong phần lớn các trường hợp sử dụng.

Kết luận

Sau khi đọc bài viết này, bạn sẽ hiểu các tính năng cơ bản của Flexbox. Trong phần tiếp theo, chúng ta sẽ xem xét đặc tả này liên quan như thế nào đến các phần khác của CSS.

Leave a Reply