- Селекторы
- Grid
- Базовые знания
- Описание Грид сетки
- Особенности Grid
- CSS свойства Grid для контейнера
- display:
- grid-template-columns/rows:
- grid-template-areas:
- grid-template:
- repeat()
- minmax()
- grid-row-gap/column-gap/gap
- align/justify/place-content
- align/justify/place-items
- grid-auto-rows/columns
- grid-auto-flow
- grid
- CSS свойства Grid для элементов
- grid-row/column
- grid-area
- align/justify/place-self
- Примеры
- Каркас HTML страницы
- Каркас для игрового приложения
- Простой блок на Grid
- Сравнение Flex и Grid
- Ссылки
- !important
- ::after
- ::backdrop
- ::before
- ::first-letter
- ::first-line
- ::-ms-browse
- ::-ms-check
- ::-ms-clear
- ::-ms-expand
- ::-ms-fill
- ::-ms-fill-lower
- ::-ms-fill-upper
- ::-ms-reveal
- ::-ms-thumb
- ::-ms-ticks-after
- ::-ms-ticks-before
- ::-ms-tooltip
- ::-ms-track
- ::-ms-value
- ::placeholder
- ::selection
- :active
- :checked
- :default
- :disabled
- :empty
- :enabled
- :first-child
- :first-of-type
- :focus
- :fullscreen
- :hover
- :indeterminate
- :in-range
- :invalid
- :lang
- :last-child
- :last-of-type
- :link
- :not
- :nth-child
- :nth-last-child
- :nth-last-of-type
- :nth-of-type
- :only-child
- :only-of-type
- :optional
- :out-of-range
- :read-only
- :read-write
- :required
- :root
- :target
- :valid
- :visited
- @charset
- @document
- @font-face
- @import
- @keyframes
- @media
- @page
- @supports
- @viewport
- align-content
- align-items
- align-self
- all
- animation
- animation-delay
- animation-direction
- animation-duration
- animation-fill-mode
- animation-iteration-count
- animation-name
- animation-play-state
- animation-timing-function
- backface-visibility
- background
- background-attachment
- background-clip
- background-color
- background-image
- background-origin
- background-position
- background-repeat
- background-size
- border
- border-bottom
- border-bottom-color
- border-bottom-left-radius
- border-bottom-right-radius
- border-bottom-style
- border-bottom-width
- border-collapse
- border-color
- border-image
- border-left
- border-left-color
- border-left-style
- border-left-width
- border-radius
- border-right
- border-right-color
- border-right-style
- border-right-width
- border-spacing
- border-style
- border-top
- border-top-color
- border-top-left-radius
- border-top-right-radius
- border-top-style
- border-top-width
- border-width
- bottom
- box-shadow
- box-sizing
- caption-side
- clear
- clip
- color
- column-count
- column-fill
- column-gap
- column-rule
- column-rule-color
- column-rule-style
- column-rule-width
- columns
- column-span
- column-width
- content
- counter-increment
- counter-reset
- cursor
- direction
- display
- empty-cells
- filter
- flex
- flex-basis
- flex-direction
- flex-flow
- flex-grow
- flex-shrink
- flex-wrap
- float
- font
- font-family
- font-kerning
- font-size
- font-stretch
- font-style
- font-variant
- font-weight
- height
- hyphens
- image-rendering
- justify-content
- left
- letter-spacing
- line-height
- list-style
- list-style-image
- list-style-position
- list-style-type
- margin
- margin-bottom
- margin-left
- margin-right
- margin-top
- marks
- max-height
- max-width
- min-height
- min-width
- -moz-orient
- object-fit
- opacity
- order
- orphans
- outline
- outline-color
- outline-offset
- outline-style
- outline-width
- overflow
- overflow-x
- overflow-y
- padding
- padding-bottom
- padding-left
- padding-right
- padding-top
- page-break-after
- page-break-before
- page-break-inside
- perspective
- perspective-origin
- pointer-events
- position
- quotes
- resize
- right
- table-layout
- tab-size
- text-align
- text-align-last
- text-decoration
- text-decoration-color
- text-decoration-line
- text-decoration-style
- text-indent
- text-overflow
- text-shadow
- text-transform
- top
- transform
- transform-origin
- transform-style
- transition
- transition-delay
- transition-duration
- transition-property
- transition-timing-function
- touch-action
- unicode-bidi
- user-select
- vertical-align
- visibility
- white-space
- widows
- width
- word-break
- word-spacing
- word-wrap
- writing-mode
- z-index
- zoom
Grid в CSS
Оглавление
Развернуть ▾Базовые знания
Grid — это сетка с элементами на ней. Расставлять элементы можно как угодно. Представьте себе шахматную доску и фигуры, Grid контейнер это доска, элементы это фигуры. А дальше ставь как нравится.
Grid — это набор горизонтальных и вертикальных «линий», которые пересекаются между собой и создают сетку из рядов и колонок. Элементы могут быть помещены в сетку, опираясь на номер линии или номер ряда/колонки.
Чтобы разобраться с Грид-сеткой нужно понять из чего конкретно состоит эта сетка:
<title>Схема Grid-сетки</title> <input type="checkbox" id="container" checked="checked" /> <label for="container">Grid контеинер</label> <input type="checkbox" style="opacity:0;" /> <label></label> <br> <input type="checkbox" id="cells" checked="checked" /> <label for="cells">Ячейки (cell)</label> <input type="checkbox" id="areas" /> <label for="areas">Области (поля, area)</label> <br> <input type="checkbox" id="rows" /> <label for="rows">Ряды, строки (row-track)</label> <input type="checkbox" id="columns" /> <label for="columns">Колонки (column-track)</label> <br> <input type="checkbox" id="lines" checked="checked" /> <label for="lines">Линии (line, -start, -end)</label> <input type="checkbox" id="gaps" /> <label for="gaps">Разрыв (gap)</label> <br> <div class="grid"> <div class="cell"></div> <div class="cell"></div> <div class="cell"></div> <div class="cell"></div> <div class="cell"></div> <div class="cell"></div> <div class="cell"></div> <div class="cell"></div> <div class="cell"></div> <div class="area area1"></div> <div class="area area2"></div> <main class="row"></main> <main class="row"></main> <main class="row"></main> <main class="column"></main> <main class="column"></main> <main class="column"></main> <nav class="gap-row"></nav> <nav class="gap-row"></nav> <nav class="gap-col"></nav> <nav class="gap-col"></nav> <section class="line-row"><i>1</i><i>-4</i></section> <section class="line-row"><i>2</i><i>-3</i></section> <section class="line-row"><i>3</i><i>-2</i></section> <section class="line-row"><i>4</i><i>-1</i></section> <section class="line-col"><i>1</i><i>-4</i></section> <section class="line-col"><i>2</i><i>-3</i></section> <section class="line-col"><i>3</i><i>-2</i></section> <section class="line-col"><i>4</i><i>-1</i></section> <article class="container"></article> </div>
body { font: 14px/1 sans-serif; color: #000; margin:0; text-align:center; } :root { --container-color: #777; --cell-color: #8488ab; --area-color: rgba(255, 128, 215, 0.4); --column-color: rgba(128, 210, 60, 0.4); --row-color: rgba(1, 183, 255, 0.4); --gap-color: #fbff9e; --line-color: #000; } input{ display: inline-block; } label{ display: inline-block; width:180px; vertical-align: top; cursor:pointer; padding:.3em; user-select:none; text-align:left; } #cells:not(:checked) ~ .grid .cell, #areas:not(:checked) ~ .grid .area, #rows:not(:checked) ~ .grid .row, #columns:not(:checked) ~ .grid .column, #lines:not(:checked) ~ .grid .line-row, #lines:not(:checked) ~ .grid .line-col, #gaps:not(:checked) ~ .grid .gap-row, #gaps:not(:checked) ~ .grid .gap-col, #container:not(:checked) ~ .grid .container { display: none; } #container:checked + label{ background: var(--container-color); color:#fff; } #rows:checked + label{ background: var(--row-color); } #columns:checked + label{ background: var(--column-color); } #cells:checked + label{ background: var(--cell-color); color:#fff; } #areas:checked + label{ background: var(--area-color); } #lines:checked + label{ background: var(--line-color); color:#fff; } #gaps:checked + label{ background: var(--gap-color); } .grid { display: grid; grid: 15px 65px 65px 65px 15px / 15px 150px 150px 150px 15px; grid-auto-rows: 15px; grid-auto-columns: 15px; grid-gap: 10px; margin:2em auto 0; width: 530px; } .container{ outline:5px solid var(--container-color); grid-row: 2 / 5; grid-column: 2 / 5; } .cell { background: var(--cell-color); z-index: 1; } .cell:nth-child(1) { grid-row: 2; grid-column: 2; } .cell:nth-child(2) { grid-row: 2; grid-column: 3; } .cell:nth-child(3) { grid-row: 2; grid-column: 4; } .cell:nth-child(4) { grid-row: 3; grid-column: 2; } .cell:nth-child(5) { grid-row: 3; grid-column: 3; } .cell:nth-child(6) { grid-row: 3; grid-column: 4; } .cell:nth-child(7) { grid-row: 4; grid-column: 2; } .cell:nth-child(8) { grid-row: 4; grid-column: 3; } .cell:nth-child(9) { grid-row: 4; grid-column: 4; } .area{ background: var(--area-color); z-index: 30; } .area1 { grid-column: 2 / span 2; grid-row: 2; } .area2 { grid-column: 3 / span 2; grid-row: 3 / span 2; } /* rows */ .row { background: var(--row-color); grid-column: 1 / 6; z-index: 3; } .column { background: var(--column-color); grid-row: 1 / 6; z-index: 3; } .row:nth-of-type(1) { grid-row: 2; } .row:nth-of-type(2) { grid-row: 3; } .row:nth-of-type(3) { grid-row: 4; } .column:nth-of-type(4) { grid-column: 2; } .column:nth-of-type(5) { grid-column: 3; } .column:nth-of-type(6) { grid-column: 4; } /* gap */ .gap-row, .gap-col{ z-index:20; background: var(--gap-color); } .gap-row { grid-column: 2 / 5; margin-top: -10px; height: 10px; } .gap-col { grid-row: 2 / 5; width: 10px; margin-left: -10px; } .gap-row:nth-of-type(1) { grid-row: 3; } .gap-row:nth-of-type(2) { grid-row: 4; } .gap-col:nth-of-type(3) { grid-column: 3; } .gap-col:nth-of-type(4) { grid-column: 4; } /* lines */ .line-row, .line-col{ z-index:40; } .line-row i{ margin-left:-1em; } .line-row i:last-child{ margin-right:-1em; } .line-col i{ margin-top:-1em; } .line-col i:last-child{ margin-bottom:-1em; } .line-row{ grid-column: 1 / 6; margin-top: -10px; height:8px; border:1px solid var(--line-color); border-left:0; border-right:0; display: flex; justify-content: space-between; align-items: center; } .line-col{ grid-row: 1 / 6; margin-left: -10px; width:8px; border:1px solid var(--line-color); border-top:0; border-bottom:0; display: flex; flex-flow: column; justify-content: space-between; align-items: center; } .line-row:nth-of-type(1) { grid-row: 2; border-top:0; margin-top: -9px; } .line-row:nth-of-type(2) { grid-row: 3; } .line-row:nth-of-type(3) { grid-row: 4; } .line-row:nth-of-type(4) { grid-row: 5; border-bottom:0; } .line-col:nth-of-type(5) { grid-column: 2; border-left:0; margin-left: -9px; } .line-col:nth-of-type(6) { grid-column: 3; } .line-col:nth-of-type(7) { grid-column: 4; } .line-col:nth-of-type(8) { grid-column: 5; border-right:0; }
Описание Грид сетки
-
Контейнер — содержит Grid сетку, в которой находятся элементы.
-
Элементы — HTML элементы внутри сетки. Ими станут HTML элементы первого уровня (прямые дети контейнера). Чтобы элемент появился в сетке, в нем (внутри) элемента должно быть хоть что-то (текст, другие HTML теги). Пустой элемент - это всего лишь ячейка для расположения в нем чего-либо.
-
Линии — это образные линии (на самом деле никаких линий нет), разделяющие сетку на колонки и ряды, они создают структуру сетки. Линии автоматически нумеруются. Также линиям можно указывать имена, чтобы потом прикреплять к ним элементы по номеру или по имени линии. По сути линия — это номер или имя колонки/ряда. Расстояние между линиями (колонками/рядами) можно указать через
grid-gap:
,grid-row-gap:
,grid-column-gap:
. -
Ряд/колонка (row/column, track) — все что находится между соседними линиями, т.е. линии разделяют сетку на ряды и колонки.
-
Ячейка (cell) — место куда будет расположен элемент. Ячейка это пересечение колонки и ряда.
-
Область (area, поле) — объединение одной или нескольких ячеек в общую ячейку (поле). Это такая большая ячейка также ограниченная линиями. Области можно задать имя, чтобы удобно было помещать туда элементы.
- Разрыв (gap) — расстояние между рядами и колонками.
Разрывает линию на две. Так между линиями, а как следствие и
колонками/рядами, ячейками появляется пустое место. Это своего рода
margin
,border-spacing
между ячейками. По умолчанию линия между ячейками всего одна (ячейки слеплены), но если указать разрыв, то мы разорвем линию, и появится расстояние между колонками/рядами, при этом номер или имя линии (колонки/ряда) остается одно.
Для включения Grid, любому HTML элементу достаточно присвоить css свойство display:grid;
или display:inline-grid;
.
После включения grid свойства, внутри контейнера создаются grid сетка, а все вложенные элементы (первого уровня) станут ячейками сетки.
body {font: 14px Verdana, sans-serif;} .grid, .inline-grid { border: 3px dashed #333; grid-gap: 3px 5px; margin: 15px 0; } .grid { display: grid; } .inline-grid { display: inline-grid; } .grid-item { border: 3px solid #aaccdd; border-radius: 5px; padding: 10px; background: rgba(242,226,5,.8); }
<title>display:grid</title> <div class="grid"> <div class="grid-item">display: grid</div> </div> Текст, в котором есть <div class="inline-grid"> <div class="grid-item">display: inline-grid</div> </div> продолжение текста <div class="grid"> <div class="grid-item">1</div> <div class="grid-item">2</div> </div>
Особенности Grid
Элементы Grid сетки можно расставлять сразу на несколько полей сетки. Можно менять направление или расположения элементов в сетке. Колонкам и рядам можно давать имена. Можно создавать шаблон сетки и расставлять элементы по шаблону.
-
Размеры колонок/рядов. Сетку можно создавать с точными или гибкими размерами колонок/рядов (шириной/высотой). Точные это
px
,em
,%
, а гибкие новая единица измерения в gridfr
(фракция - свободное место в сетке). -
Расположение элемента. Элементы можно размещать в указанном месте сетки, указав номер колонки/ряда или их имя (если оно есть). Или путем привязки элемента к области Grid (область нужно создать). Если не указать конкретное расположение элемента в сетке, то элемент размещается по умолчанию в первую свободную ячейку: как во flex: по горизонтали (→) или по вертикали (↓). Поведение по умолчанию можно изменить через свойство
grid-auto-flow:
. -
Выравнивание элементов. Элементы внутри ячейки можно выравнивать по горизонтали/вертикали. Выравнивается вложенный в ячейку элемент, а не сама ячейка. Например, в контейнере есть вложенный элемент первого уровня (это ячейка), внутри него есть «текст» или какой-то «div» (текст или div - это реальный элемент) выравнивание элемента выровняет вложенный в ячейку элемент внутри ячейки (размеры ячейки при этом не изменятся).
-
Несколько элементов в одной ячейке. В одной ячейке или области можно разместить несколько элементов. Чтобы указать кто «выше» (важнее) и кто «ниже» (неважный), нужно использовать css свойство
z-index:
. - Расширение сетки. Сколько колонок/рядов имеет сетка обычно указывается сразу, но если разместить элемент за пределами сетки (указать ему номер ряда/ячейки, который выходит за пределы сетки), тогда сетка автоматически расширяется и создаются дополнительные линии (колонки/ряды).
В веб-дизайне очень часто встречается компоновка, состоящая из верхнего, бокового, основного и нижнего колонтитулов. Для этого можно использовать grid-свойства:
<title>Example</title> <body> <header id="pageHeader">Header</header> <article id="mainArticle">Article</article> <nav id="mainNav">Nav</nav> <div id="siteAds">Ads</div> <footer id="pageFooter">Footer</footer> </body>
body { display: grid; grid-template-areas: "header header header" "nav article ads" "footer footer footer"; grid-template-rows: 80px 1fr 70px; grid-template-columns: 20% 1fr 15%; grid-row-gap: 10px; grid-column-gap: 10px; height: 100vh; margin: 0; } /* Stack the layout on small devices/viewports. */ @media all and (max-width: 575px) { body { grid-template-areas: "header" "article" "ads" "nav" "footer"; grid-template-rows: 80px 1fr 70px 1fr 70px; grid-template-columns: 1fr; } } header, footer, article, nav, div { padding: 1.2em; background: gold; } #pageHeader { grid-area: header; } #pageFooter { grid-area: footer; } #mainArticle { grid-area: article; } #mainNav { grid-area: nav; } #siteAds { grid-area: ads; }
CSS свойства Grid для контейнера
display:
Определяет элемент как контейнер grid и устанавливает новый контекст форматирования сетки для его содержимого.
Синтаксис
display: grid | inline-grid;
Значения
- grid
- генерирует блочную сетку
- inline-grid
- генерирует встроенную сетку
grid-template-columns:, grid-template-rows:
Указывают из скольки рядов (строк) и скольки колонок состоит сетка и какие у них размеры. Т.е. указывается сразу два понятия: сколько и какой размер.
В значении через пробелы указываются размеры: высота ряда (rows) или ширина колонки (columns). Сколько раз будет указан размер, столько будет рядов/колонок.
Синтаксис
grid-template-rows: размер размер ...; grid-template-columns: размер размер ...; grid-template-rows: [line-name] размер [line-name] размер ... [last-name]; grid-template-columns: [line-name] размер [line-name] размер ... [last-name];
Значения
- размер
- это высота ряда или ширина колонки, может быть:
-
auto — размер ряда/колонки подстраивается под размеры элементов, так, чтобы уместился самый большой из них. Не дает сжиматься меньше
min-width
илиmin-height
самого широкого или высокого элемента соответственно. Не дает растягиваться больше, чемmax-content
. Если в контейнере есть свободное место, то размер может растянуться до конца контейнера. -
px, em, %, vh, vw — размер абсолютный (px, pt), относительный (em, vw, vh) или в
%
от ширины/высоты контейнера. -
fr (фракция - свободное место в сетке) — специальная единица измерения в grid. Свободное место в контейнере делится на фракции, так если одной колонке указать
1fr
, а другой2fr
, то вторая будет больше первой в 2 раза и обе они заполнят все свободное пространство. Аналог flex-grow: у флексов. Тут можно также указывать дробные значения:0.5fr, 2.3fr
. -
min-content — наименьший размер контента. Для текста это ширина самого длинного слова или неразрывного фрагмента.
-
max-content — наибольший размер контента. Для текста это длина самой большой строки без переносов.
-
fit-content( max ) — функция которой передается макс. размер. Если контент меньше этого размера, ведет себя как
auto
, если больше, то ограничивает размер ряда/колонки до указанного в параметре max. - minmax( min, max ) — функция, позволяет разом указать минимальный и максимальный размер.
-
- line-name
- имя линии - перед размером можно указать (создать) имя для линии (ряда/колонки). Имя указывается в квадратных скобках
[имя] 100px
. Также можно указать сразу несколько имен через пробел внутри квадратных скобок:[имя еще_имя] 100px
. Символы в имени можно использовать любые, в том числе кириллицу. - last-name
- последнее имя — указанное имя станет
именем начальной линии ряда/колонки, но ряд/колонка состоит из двух
линий (они ведь имеют размер). Так имя линии является именем начала
одной колонки (ряда) и именем конца предыдущей колонки (ряда). И так вот
заполняется сетка, но в конце остается ряд/колонка и указанное для неё
имя это имя только начальной линии этого ряда/колонки, а у конечной
линии имени нет. Такое имя последней линии можно указать в конце. Т.е.
получается так:
[имя] 100px [имя2] 100px [последнее-имя]
.
У двух этих свойств есть сокращенные записи:
Пример
<title>grid-template-rows/columns</title> <b>grid-template-rows:</b> <input type="radio" name="r" id="rows1" checked /><label for="rows1">70px 70px</label> <input type="radio" name="r" id="rows2" /><label for="rows2">50px 50px 100px</label> <input type="radio" name="r" id="rows3" /><label for="rows3">1fr 1fr 1fr</label> <input type="radio" name="r" id="rows4" /><label for="rows4">repeat(4, 1fr)</label> <br> <b>grid-template-columns:</b> <input type="radio" name="c" id="columns1" checked /><label for="columns1">50px 100px 50%</label> <input type="radio" name="c" id="columns2" /><label for="columns2">1fr 2fr</label> <input type="radio" name="c" id="columns3" /><label for="columns3">1fr 1fr</label> <input type="radio" name="c" id="columns4" /><label for="columns4">repeat(4, 1fr)</label> <br> <div class="grid"> <div class="item">1</div> <div class="item">2</div> <div class="item">3</div> <div class="item">4</div> <div class="item">5</div> <div class="item">6</div> </div>
body { font: 14px/1 sans-serif; padding:1em; margin:0; } .grid { display: grid; grid-gap: .5em; /* grid-template: 1fr 1fr 1fr / 1fr 1fr 1fr; */ grid-auto-rows: 30px; grid-auto-columns: 30px; margin:1em 0 0; border: 1px dashed #aaa; min-height:200px; max-width:700px; } .item{ border-radius:3px; background:#a5b8d0; color:rgba(0,0,0,.5); font-size:150%; display:flex; justify-content:center; align-items:center; } input{ display: none; } label{ display: inline-block; cursor:pointer; padding:.3em 1em; user-select:none; text-align:left; } label:hover{ background:#ccc; } input:checked + label{ font-weight:bold; background:#ccc; } #rows1:checked ~ .grid{ grid-template-rows: 70px 70px; } #rows2:checked ~ .grid{ grid-template-rows: 50px 50px 100px; } #rows3:checked ~ .grid{ grid-template-rows: 1fr 1fr 1fr; } #rows4:checked ~ .grid{ grid-template-rows: repeat(4, 1fr); } #columns1:checked ~ .grid{ grid-template-columns: 50px 100px 50%; } #columns2:checked ~ .grid{ grid-template-columns: 1fr 2fr; } #columns3:checked ~ .grid{ grid-template-columns: 1fr 1fr; } #columns4:checked ~ .grid{ grid-template-columns: repeat(4, 1fr); }
grid-template-areas:
Позволяет создать визуальный шаблон сетки. В этом свойстве
задаются имена ячейкам, а затем элементы привязываются к этим именам
через свойство grid-area:
указываемое для отдельного элемента.
Синтаксис шикарен, потому что визуально показывает как выглядит сетка:
grid-template-areas: "имя имя2 имя3" "имя имя4 имя5" "имя none ."; /* или можно так */ grid-template-areas: "имя имя2 имя3" "имя имя4 имя5" "имя6 none ."; /* или одинарные кавычки */ grid-template-areas: 'имя имя2 имя3' 'имя имя4 имя5' 'имя6 none .';
Значения
- "имя имя2 имя3"
в значении внутри кавычек нужно через пробелы указывать имена. Каждые кавычки с именами будут представлять собой ряд сетки, а имена внутри кавычек задают имена ячейкам внутри этого ряда.- "имя имя имя2"
если указать одно и тоже имя несколько раз подряд, то имя объединит ячейки и мы получим область (большую ячейку). Объединять ячейки таким способом можно не только внутри ряда, но и между рядами.- .
- «точка» — указывается вместо имени и обозначает ячейку которую нужно пропустить (пустую ячейку). Можно использовать несколько точек подряд, пока между ними нет пробела они будут считаться за одну.
- none
- область не определена
Заметки:
- Символы в имени можно использовать любые, в том числе кириллицу.
-
Каждый ряд должен иметь одинаковое количество ячеек.
-
При использовании этого метода линии (включая последнюю линию) получают имена автоматически. Например, если область называется
bar
, то имя начальной линии ряда и колонки у этой области будетbar-start
, а имя последнейbar-end
. Это значит, что некоторые линии будут иметь много имен. Например крайняя левая линия из примера ниже (шаблон страницы) будет иметь сразу три имени:header-start
,main-start
иfooter-start
.Такая же логика работает и наоборот, если линиям указать имена
дом-start
идом-end
, то все что находится межу этими линиями превращается в область (ячейку) с именемдом
.
grid-template-areas:
также можно указывать в первом значении свойств:
Пример:
<title>grid-template-areas</title> <div class="grid"> <div class="header">header</div> <div class="main">main</div> <div class="menu">menu</div> </div>
html { height:100%; } body { font: 14px/1 sans-serif; margin:0; height:100%; } .grid{ min-height:100%; } .grid { display: grid; grid-template-rows: [header-top] minmax( 6em, auto) [header-bottom main-top] 1fr [main-bottom]; grid-template-columns: 1fr 30%; grid-template-areas: "header header" "main menu"; } .header { grid-area: header; } .main { grid-area: main; } .menu { grid-area: menu; /* пример прикрепления к именам линий ряда */ grid-row: main-top / main-bottom; /* или */ grid-row: menu-start / menu-end; /* или */ grid-row: 2 / 3; } /* красивости */ .header, .main, .menu{ display:flex; align-items:center; justify-content:center; color:rgba(0,0,0,.2); font-size:200%; text-transform:uppercase; } .header { background: #b0e6ff; } .main { background: #92d9e2; } .menu { background: #88c2f1; }
grid-template:
Позволяет разом указать три свойства: grid-template-rows
, grid-template-columns
и grid-template-areas
.
Синтаксис
grid-template: none; grid-template: grid-template-rows / grid-template-columns; grid-template: [ line-names? "строка" размер? line-names? ] ... grid-template: [ line-names? "строка" размер? line-names? ] ... / [ line-names? размер ] ... line-names? /* то что в [] или до ? — можно не указывать ... — можно повторять */
Это свойство можно заменить на сокращенное grid: grid-template-rows / grid-template-columns
grid-template:
не сбрасывает свойства для рядов/колонок по умолчанию: grid-auto-columns:, grid-auto-rows:, grid-auto-flow:. Чтобы это сделать, лучше вместо grid-template:
использовать свойство grid:.
repeat()
Функция позволяет повторять что-либо N раз. Используется при создании колонок/рядов в свойствах: grid-template-rows:
, grid-template-columns:
, grid-template:
.
repeat(<сколько раз повторять>, <что повторять>).
У нее два основных варианта:
- Повторение любой последовательности грид-полос указанное число раз.
- Повторение одной грид-полосы до заполнения грид-контейнера по соответствующей оси. Количество повторов задается ключевым словом
auto-fill
либоauto-fit
:auto-fill
повторяет грид-полосу столько раз, сколько вместится в размер грид-контейнера. Если у грид-контейнера задан максимальный размер, грид-полоса повторяется столько раз, сколько вместится без переполнения (если без переполнения никак не вмещается — то один раз). Если у грид-контейнера задан только минимальный размер, грид-полоса повторяется столько раз, сколько достаточно для превышения этого минимума. Хотя бы одно повторение будет в любом случае.auto-fit
— то же самое, но после размещения грид-элементов оставшиеся пустыми грид-полосы сжимаются до нуля, а интервалы между ними объединяются в один интервал. Т.е. пустые полосы как будто выбрасываются. Если полос вмещается пять, но элемента только три — в итоге и полос будет только три.
Есть несколько важных ограничений:
- Нельзя вкладывать
repeat
в другойrepeat
. - С
auto-fill
иauto-fit
можно повторять только конкретные размеры. Явно заданные (в единицах длины или процентах) или хотя бы явно ограниченные с одной стороны, но не*-content
, неfr
и неauto
.repeat(auto-fill, 100px)
— можноrepeat(auto-fit, minmax(100px, 1fr))
— можноrepeat(auto-fill, auto)
— нельзяrepeat(auto-fit, 1fr)
— нельзя
repeat
cauto-fill
илиauto-fit
может быть только один на одно свойство (grid-template-rows
илиgrid-template-columns
).grid-template-columns: repeat(3, 50px 5%) repeat(auto-fill, 100px) repeat(4, 80px)
— можноgrid-template-columns: repeat(auto-fill, 50px) repeat(2, 100px) repeat(auto-fit, 80px)
— нельзя (2repeat
с неизвестным количеством повторений)
- Если есть
repeat
cauto-fill
илиauto-fit
, то в остальныхrepeat
для этого же свойства тоже можно повторять только конкретные размеры (не*-content
, неfr
и неauto
).grid-template-columns: repeat(2, 2fr) repeat(4, 1fr)
— можно (нетauto-fill
/auto-fit
)grid-template-columns: repeat(4, 10%) repeat(auto-fill, 10em)
— можно (в первомrepeat
повторяется конкретная ширина в процентах)grid-template-columns: repeat(auto-fill, 100px) repeat(4, 1fr)
— нельзя (в одномrepeat
естьauto-fill
, а в другомrepeat
повторяется заранее неизвестная ширина).
Пример
<title>Пример 1</title> <b>grid-template:</b> <br> <input type="radio" name="a" id="al0" /> <label for="al0">repeat(3, 1fr) / repeat(3, 1fr)</label><br> <input type="radio" name="a" id="al1"/> <label for="al1">repeat(3, 70px) / repeat(3, 70px)</label><br> <input type="radio" name="a" id="al2" /> <label for="al2">repeat(auto-fill, 70px) / repeat(auto-fill, 70px)</label><br> <input type="radio" name="a" id="al3" /> <label for="al3">repeat(auto-fit, 70px) / repeat(auto-fit, 70px) </label><br> <input type="radio" name="a" id="al4" /> <label for="al4">repeat(auto-fill, minmax(70px,1fr)) / repeat(auto-fill, minmax(70px,1fr))</label><br> <input type="radio" name="a" id="al5" checked/> <label for="al5">repeat(auto-fit, minmax(70px,1fr)) / repeat(auto-fit, minmax(70px,1fr))</label><br> <input type="radio" name="a" id="al6" /><label for="al6"></label> <input type="radio" name="a" id="al7" /><label for="al7"></label> <br> <b>grid-auto-rows: </b> <input type="radio" name="au" id="au0" checked /><label for="au0">нет</label> <input type="radio" name="au" id="au1" /><label for="au1">50px</label> <div class="grid"> <div class="item">1</div> <div class="item">2</div> <div class="item">3</div> <div class="item">4</div> <div class="item">5</div> <div class="item">6</div> <div class="item">7</div> <div class="item">8</div> <div class="item">9</div> </div>
body { font: 14px/1 sans-serif; padding:1em; margin:0; max-width:700px; } input{ display: none; } label{ display: inline-block; cursor:pointer; padding:.3em .8em; user-select:none; text-align:left; font-family:monospace; } label:hover{ background:#ccc; } input:checked + label{ font-weight:bold; background:#ccc; } .grid { display: grid; grid-gap:.5em; margin:1em 0 0; border:1px dashed #666; animation: resize 6s linear infinite alternate; } .item { background:#a5b8d0; color:rgba(0,0,0,.5); font-size:200%; border-radius:3px; display:flex; justify-content:center; align-items:center; border:1px solid #8393a7; } #au1:checked ~ .grid{ grid-auto-rows: 50px; } #al0:checked ~ .grid{ grid-template: repeat(3, 1fr) / repeat(3, 1fr) } #al1:checked ~ .grid{ grid-template: repeat(3, 70px) / repeat(3, 70px) } #al2:checked ~ .grid{ grid-template: repeat(auto-fill, 70px) / repeat(auto-fill, 70px) } #al3:checked ~ .grid{ grid-template: repeat(auto-fit, 70px) / repeat(auto-fit, 70px) } #al4:checked ~ .grid{ grid-template: repeat(auto-fill, minmax(70px,1fr)) / repeat(auto-fill, minmax(70px,1fr)); } #al5:checked ~ .grid{ grid-template: repeat(auto-fit, minmax(70px,1fr)) / repeat(auto-fit, minmax(70px,1fr)); } #al6:checked ~ .grid{ } #al7:checked ~ .grid{ } @keyframes resize { 0%, 15% { width: 300px; height: 70px; } 85%, 100% { width: 100%; height: 280px; } }
minmax()
Функция позволяет задавать минимальное и максимальное значения для ряда/колонки. Используется в свойствах, где нужно задавать размер: grid-template-rows:
, grid-template-columns:
, grid-template:
.
Синтаксис
minmax(min, max)
Если указанное максимальное значение окажется меньше минимального, оно игнорируется, и функция воспринимается как представляющая только минимальное значение.
Значение может быть:
- px, em, rem, ... — единицы длины (100px)
- % — проценты (10%)
-
fr — гибкие размеры. Может использоваться только для макс. значения.
-
max-content — наименьший возможный размер ячейки, при котором содержимое свободно в ней умещается. Например, если в ячейке текст, идеальной шириной ячейки будет вся длина текста (в одну строку без переносов).
-
min-content — наименьший размер, при котором ячейка не переполняется. Например, если в ячейке текст то ширина будет равна самому длинному слову в тексте.
-
auto — зависит от того, используется оно как максимальное или минимальное значение в функции
minmax()
:- если в качестве максимума, то тоже самое что
max-content
. - если в качестве минимума, то значение будет минимальным возможным размером для ячейки. Такой размер отличается от
min-content
и задается свойствамиmin-width
илиmin-height
.
- если в качестве максимума, то тоже самое что
Примеры:
Варианты использования:
grid-template-columns: minmax( 100px, 200px ) 1fr 1fr; grid-template-columns: minmax( 200px, 50% ) 1fr 1fr; grid-template-columns: minmax( 200px, 1fr ) 1fr 1fr; grid-template-columns: minmax( min-content, max-content ) 1fr 1fr; grid-template-columns: minmax( auto, auto ) 1fr 1fr; grid-template-columns: repeat( auto-fit, minmax(200px, 1fr) );
Пример Grid: minmax()
<title>Пример Grid: minmax()</title> <b>grid-template-columns: </b><br> <input type="radio" name="col" id="col1" checked /> <label for="col1">minmax(100px, 300px) 1fr;</label><br> <input type="radio" name="col" id="col2" /> <label for="col2">minmax(200px, 80%) 1fr;</label><br> <input type="radio" name="col" id="col3" /> <label for="col3">minmax(200px, 1fr) 1fr;</label><br> <input type="radio" name="col" id="col4" /> <label for="col4">minmax(max-content, max-content) 1fr;</label><br> <input type="radio" name="col" id="col5" /> <label for="col5">minmax(min-content, min-content) 1fr;</label><br> <input type="radio" name="col" id="col6" /> <label for="col6">minmax(auto, auto) 1fr;</label><br> <input type="radio" name="col" id="col7" /> <label for="col7">repeat( auto-fit, minmax(200px, 1fr) );</label><br> <div class="grid"> <div class="item">С другой стороны постоянное информационно-пропагандистское обеспечение нашей деятельности </div> <div class="item"></div> </div>
body { font: 14px/1.25 sans-serif; padding:1em; margin:0; max-width:700px; } input{ display: none; } label{ display: inline-block; cursor:pointer; padding:0 .8em; user-select:none; text-align:left; font-family:monospace; } label:hover{ background:#ccc; } input:checked + label{ font-weight:bold; background:#ccc; } .grid { display: grid; grid-gap:.5em; margin:1em 0 0; border:1px dashed #666; animation: resize 6s linear infinite alternate; } .item { background:rgba(140, 160, 191, 0.7); color:rgba(0,0,0,.5); font-size:115%; border-radius:3px; padding:1em; } #col1:checked ~ .grid{ grid-template-columns: minmax(100px, 300px) 1fr; } #col2:checked ~ .grid{ grid-template-columns: minmax(200px, 80%) 1fr; } #col3:checked ~ .grid{ grid-template-columns: minmax(200px, 1fr) 1fr; } #col4:checked ~ .grid{ grid-template-columns: minmax(max-content, max-content) 1fr; } #col5:checked ~ .grid{ grid-template-columns: minmax(min-content, min-content) 1fr; } #col6:checked ~ .grid{ grid-template-columns: minmax(auto, auto) 1fr; } #col7:checked ~ .grid{ grid-template-columns: repeat( auto-fit, minmax(200px, 1fr) ); } @keyframes resize { 0%, 15% { width: 100px; height: 70px; } 85%, 100% { width: 100%; height: 280px; } }
grid-row-gap:, grid-column-gap:, grid-gap:
grid-row-gap:
задает разрыв между рядами.grid-column-gap:
задает разрыв между колонками.grid-gap:
задает разрыв для рядов и колонок разом. Это сокращение для двух предыдущих свойств. Если указать один параметр он будет выставлен для обоих значений.
синтаксис
grid-row-gap: размер; grid-column-gap: размер; grid-gap: размер размер; /* row column */ grid-gap: размер;
Размер может быть абсолютным (px, pt), относительным (%, em).
Префикс
grid-
будет удален и названия свойств станут: column-gap:
и row-gap:
. Chrome 68+, Safari 11.2 и Opera 54+ уже поддерживают свойства без этого префикса.Пример
<title>Grid-Gap</title> <b>grid-row-gap:</b> <input type="radio" name="r" id="rgap0" /><label for="rgap0">нет</label> <input type="radio" name="r" id="rgap1" checked /><label for="rgap1">20px</label> <input type="radio" name="r" id="rgap2" /><label for="rgap2">3em</label> <input type="radio" name="r" id="rgap3" /><label for="rgap3">5%</label> <br> <b>grid-column-gap:</b> <input type="radio" name="c" id="cgap0" /><label for="cgap0">нет</label> <input type="radio" name="c" id="cgap1" checked /><label for="cgap1">20px</label> <input type="radio" name="c" id="cgap2" /><label for="cgap2">3em</label> <input type="radio" name="c" id="cgap3" /><label for="cgap3">5%</label> <br> <b>grid-gap:</b> <input type="radio" name="d" id="gap0" checked /><label for="gap0">нет</label> <input type="radio" name="d" id="gap1" /><label for="gap1">10px</label> <input type="radio" name="d" id="gap2" /><label for="gap2">1em 3em</label> <input type="radio" name="d" id="gap3" /><label for="gap3">20% 5%</label> <br> <div class="grid"> <div class="item">1</div> <div class="item">2</div> <div class="item">3</div> <div class="item">4</div> <div class="item">5</div> <div class="item">6</div> </div>
body { font: 14px/1 sans-serif; padding:1em; margin:0; } .grid { display: grid; grid-template: 1fr 1fr / 1fr 1fr 1fr; margin:1em 0 0; border: 1px dashed #555; height:200px; max-width:500px; } .item{ background:#a5b8d0; color:rgba(0,0,0,.5); font-size:200%; display:flex; justify-content:center; align-items:center; } input{ display: none; } label{ display: inline-block; cursor:pointer; padding:.3em 1em; user-select:none; text-align:left; } label:hover{ background:#ccc; } input:checked + label{ font-weight:bold; background:#ccc; } /* #rgap0:checked ~ .grid{ grid-row-gap: unset; } */ #rgap1:checked ~ .grid{ grid-row-gap: 20px; } #rgap2:checked ~ .grid{ grid-row-gap: 3em; } #rgap3:checked ~ .grid{ grid-row-gap: 5%; } /* #cgap0:checked ~ .grid{ grid-column-gap: unset; } */ #cgap1:checked ~ .grid{ grid-column-gap: 20px; } #cgap2:checked ~ .grid{ grid-column-gap: 3em; } #cgap3:checked ~ .grid{ grid-column-gap: 5%; } /* #gap0:checked ~ .grid{ grid-gap: unset; } */ #gap1:checked ~ .grid{ grid-gap: 10px; } #gap2:checked ~ .grid{ grid-gap: 1em 3em; } #gap3:checked ~ .grid{ grid-gap: 20% 5%; }
align-content:, justify-content:, place-content:
Выравнивает ряды/колонки. Выравниваются ячейки сетки, не элементы внутри ячеек. Чтобы выровнять элементы, используйте: justify-items
, align-items
, place-items
.
Синтаксис
align-content: значение; /* выравнивает ряды по вертикали ↓↑ */ justify-content: значение; /* выравнивает колонки по горизонтали ←→ */ place-content: значение; /* сокращенная запись: установит оба значения */ place-content: align-content justify-content; /* сокращенная запись */
Значение может быть:
- stretch (default) — растягивает ряды/колонки (ячейки) полностью. Все пространство контейнера заполняется. Имеет смысл только если у рядов/колонок размер не задан жестко (они резиновые). Если они не резиновые, то работает как
start
. - start — ряды/колонки упакованы вплотную друг к другу к начальному краю контейнера.
- end — ряды/колонки упакованы вплотную друг к другу к конечному краю контейнера.
-
center — ряды/колонки упакованы вплотную друг к другу и находятся по середине контейнера.
- space-around — свободное пространство равномерно распределяется между рядами/колонками и добавляется по краям. Получается, что крайние ряд/колонка не прижимаются к краям контейнера, но расстояние до края в два раза меньше, чем между рядами/колонками.
- space-evenly — тоже что и
space-around
, только расстояние до краев контейнера такое же как и между рядами/колонками. - space-between — крайние ряд/колонка прижимаются к краям контейнера и свободное место равномерно распределяется между рядами/колонками.
Редкие значения:
-
safe значение — если ширина колонки или высота ряда превышает размер контейнера, то значение переключается на
start
. В значении тут может быть только:center
илиend
. -
unsafe значение — значение остается указанным, даже если ширина колонки или высота ряда превышает размер контейнера. В значении тут может быть только:
center
илиend
.
Пример
<title>Grid: align/justify-content:</title> <b>align-content:</b> <input type="radio" name="a" id="al0" /><label for="al0">нет</label> <input type="radio" name="a" id="al1" checked /><label for="al1">stretch</label> <input type="radio" name="a" id="al2" /><label for="al2">start</label> <input type="radio" name="a" id="al3" /><label for="al3">end</label> <input type="radio" name="a" id="al4" /><label for="al4">center</label> <input type="radio" name="a" id="al5" /><label for="al5">space-around</label> <input type="radio" name="a" id="al6" /><label for="al6">space-evenly</label> <input type="radio" name="a" id="al7" /><label for="al7">space-between</label> <br> <b>justify-content:</b> <input type="radio" name="b" id="js0" /><label for="js0">нет</label> <input type="radio" name="b" id="js1" checked /><label for="js1">stretch</label> <input type="radio" name="b" id="js2" /><label for="js2">start</label> <input type="radio" name="b" id="js3" /><label for="js3">end</label> <input type="radio" name="b" id="js4" /><label for="js4">center</label> <input type="radio" name="b" id="js5" /><label for="js5">space-around</label> <input type="radio" name="b" id="js6" /><label for="js6">space-evenly</label> <input type="radio" name="b" id="js7" /><label for="js7">space-between</label> <br> <b>place-content:</b> <input type="radio" name="c" id="pl0" checked/><label for="pl0">нет</label> <input type="radio" name="c" id="pl1" /><label for="pl1">center start</label> <input type="radio" name="c" id="pl2" /><label for="pl2">start center</label> <input type="radio" name="c" id="pl3" /><label for="pl3">end start</label> <input type="radio" name="c" id="pl4" /><label for="pl4">start end</label> <input type="radio" name="c" id="pl5" /><label for="pl5">space-between end</label> <input type="radio" name="c" id="pl6" /><label for="pl6">space-evenly space-evenly</label> <br> <div class="grid"> <div class="item">1</div> <div class="item">2</div> <div class="item">3</div> <div class="item">4</div> <div class="item">5</div> <div class="item">6</div> </div>
body { font: 14px/1 sans-serif; padding:1em; margin:0; } .grid { display: grid; grid-template: auto auto / auto auto auto; /* grid-gap: 1em; */ /* align-items:center; */ margin:1em 0 0; border: 1px dashed #555; height:200px; max-width:500px; } .item{ background:#a5b8d0; color:rgba(0,0,0,.5); font-size:200%; display:flex; justify-content:center; align-items:center; border:1px solid #8393a7; padding:.3em .7em; line-height:1; } input{ display: none; } label{ display: inline-block; cursor:pointer; padding:.3em .5em; user-select:none; text-align:left; } label:hover{ background:#ccc; } input:checked + label{ font-weight:bold; background:#ccc; } #al0:checked ~ .grid{ } #al1:checked ~ .grid{ align-content: stretch; } #al2:checked ~ .grid{ align-content: start; } #al3:checked ~ .grid{ align-content: end; } #al4:checked ~ .grid{ align-content: center; } #al5:checked ~ .grid{ align-content: space-around; } #al6:checked ~ .grid{ align-content: space-evenly; } #al7:checked ~ .grid{ align-content: space-between; } #js0:checked ~ .grid{ } #js1:checked ~ .grid{ justify-content: stretch; } #js2:checked ~ .grid{ justify-content: start; } #js3:checked ~ .grid{ justify-content: end; } #js4:checked ~ .grid{ justify-content: center; } #js5:checked ~ .grid{ justify-content: space-around; } #js6:checked ~ .grid{ justify-content: space-evenly; } #js7:checked ~ .grid{ justify-content: space-between; } #pl0:checked ~ .grid{ } #pl1:checked ~ .grid{ place-content: center start; } #pl2:checked ~ .grid{ place-content: start center; } #pl3:checked ~ .grid{ place-content: end start; } #pl4:checked ~ .grid{ place-content: start end; } #pl5:checked ~ .grid{ place-content: space-between end; } #pl6:checked ~ .grid{ place-content: space-evenly space-evenly; }
Полный синтаксис
Выше для упрощения был не полный синтаксис, однако он покрывает 99% нужного.
align-content: normal | <distribution> | <overflow>? <position> | <baseline> justify-content: normal | <distribution> | <overflow>? [ <position> | left | right ] /* <distribution> = space-between | space-around | space-evenly | stretch <overflow> = unsafe | safe <position> = center | start | end | flex-start | flex-end <baseline> = [ first | last ]? baseline то что в [] или до ? — можно не указывать */
- left — для
justify-content
, не работает дляalign-content
. Колонки упакованы вплотную друг к другу к левому краю контейнера. -
right — для
justify-content
, не работает дляalign-content
. Колонки упакованы вплотную друг к другу к правому краю контейнера. -
flex-start — тоже что
start
для грид-сетки. Т.е. если элементы не являются детьми flex контейнера ведет себя какstart
. -
flex-end — тоже что
end
для грид-сетки. Т.е. если элементы не являются детьми flex контейнера ведет себя какend
. - baseline, first baseline, last baseline — выравнивает по линии текста (первой или последней). Обратная совместимость: для
first baseline
этоstart
, дляlast baseline
этоend
.
align-items:, justify-items:, place-items:
Выравнивает элементы сетки - то что находится внутри ячеек сетки. Срабатывает для всех элементов grid. Чтобы выровнять сами ячейки (ряды колонки), используйте: justify-content
, align-content
, place-content
.
Синтаксис
align-items: значение; /* выравнивает элементы по вертикали ↓↑ */ justify-items: значение; /* выравнивает элементы по горизонтали ←→ */ place-items: значение; /* сокращенная запись: установит оба значения */ place-items: align-items justify-items; /* сокращенная запись */
Значение может быть:
-
auto (default) — указывает использовать значение
justify-items:
, которое задается для контейнера. Если элемент позиционирован черезabsolute
, то применяетсяnormal
. - stretch — растягивает все элементы на всю ширину/высоту ячеек.
- start — размещает все элементы в начале ячеек (слева или сверху).
- end — размещает все элементы в конце ячеек (справа или внизу).
- center — размещает все элементы по центру ячеек.
Редкие значения:
-
safe значение — если ширина или высота элемента превышает размер ячейки, то значение переключается на
start
. В значении тут может быть только:center
илиend
. -
unsafe значение — значение остается указанным, даже если ширина или высота элемента превышает размер ячейки. В значении тут может быть только:
center
илиend
.
Пример
<title>Grid: align/justify-items:</title> <b>align-items:</b> <input type="radio" name="a" id="al0" /><label for="al0">нет</label> <input type="radio" name="a" id="al1" /><label for="al1">stretch</label> <input type="radio" name="a" id="al2" /><label for="al2">start</label> <input type="radio" name="a" id="al3" /><label for="al3">end</label> <input type="radio" name="a" id="al4" checked /><label for="al4">center</label> <input type="radio" name="a" id="al5" /><label for="al5"></label> <input type="radio" name="a" id="al6" /><label for="al6"></label> <input type="radio" name="a" id="al7" /><label for="al7"></label> <br> <b>justify-items:</b> <input type="radio" name="b" id="js0" /><label for="js0">нет</label> <input type="radio" name="b" id="js1" /><label for="js1">stretch</label> <input type="radio" name="b" id="js2" /><label for="js2">start</label> <input type="radio" name="b" id="js3" /><label for="js3">end</label> <input type="radio" name="b" id="js4" checked /><label for="js4">center</label> <input type="radio" name="b" id="js5" /><label for="js5"></label> <input type="radio" name="b" id="js6" /><label for="js6"></label> <input type="radio" name="b" id="js7" /><label for="js7"></label> <br> <b>place-items:</b> <input type="radio" name="c" id="pl0" checked/><label for="pl0">нет</label> <input type="radio" name="c" id="pl1" /><label for="pl1">center start</label> <input type="radio" name="c" id="pl2" /><label for="pl2">start center</label> <input type="radio" name="c" id="pl3" /><label for="pl3">end start</label> <input type="radio" name="c" id="pl4" /><label for="pl4">start end</label> <input type="radio" name="c" id="pl5" /><label for="pl5">stretch start</label> <input type="radio" name="c" id="pl6" /><label for="pl6">start stretch</label> <br> <div class="grid"> <div class="item">1</div> <div class="item">2</div> <div class="item">3</div> <div class="item">4</div> <div class="item">5</div> <div class="item">6</div> <nav class="cell"></nav> <nav class="cell"></nav> <nav class="cell"></nav> <nav class="cell"></nav> <nav class="cell"></nav> <nav class="cell"></nav> </div>
body { font: 14px/1 sans-serif; padding:1em; margin:0; } input{ display: none; } label{ display: inline-block; cursor:pointer; padding:.3em .5em; user-select:none; text-align:left; } label:hover{ background:#ccc; } input:checked + label{ font-weight:bold; background:#ccc; } .grid { display: grid; grid-template: auto auto / auto auto auto; /* grid-gap: 1em; */ /* align-items:center; */ margin:1em 0 0; border: 1px dashed #555; border-bottom:0; border-right:0; height:200px; max-width:500px; } .item{ background:#a5b8d0; color:rgba(0,0,0,.5); font-size:200%; display:flex; justify-content:center; align-items:center; border:1px solid #8393a7; padding:.3em .7em; line-height:1; } .cell{ justify-self: stretch; align-self: stretch; border:1px dashed #555; border-top:0; border-left:0; width:100%; height:100%; } .cell:nth-of-type(1), .item:nth-of-type(1){ grid-row:1; grid-column:1; } .cell:nth-of-type(2), .item:nth-of-type(2){ grid-row:1; grid-column:2; } .cell:nth-of-type(3), .item:nth-of-type(3){ grid-row:1; grid-column:3; } .cell:nth-of-type(4), .item:nth-of-type(4){ grid-row:2; grid-column:1; } .cell:nth-of-type(5), .item:nth-of-type(5){ grid-row:2; grid-column:2; } .cell:nth-of-type(6), .item:nth-of-type(6){ grid-row:2; grid-column:3; } #al0:checked ~ .grid{ } #al1:checked ~ .grid{ align-items: stretch; } #al2:checked ~ .grid{ align-items: start; } #al3:checked ~ .grid{ align-items: end; } #al4:checked ~ .grid{ align-items: center; } #al5:checked ~ .grid{ align-items: ___; } #al6:checked ~ .grid{ align-items: ___; } #al7:checked ~ .grid{ align-items: ___; } #js0:checked ~ .grid{ } #js1:checked ~ .grid{ justify-items: stretch; } #js2:checked ~ .grid{ justify-items: start; } #js3:checked ~ .grid{ justify-items: end; } #js4:checked ~ .grid{ justify-items: center; } #js5:checked ~ .grid{ justify-items: ___; } #js6:checked ~ .grid{ justify-items: ___; } #js7:checked ~ .grid{ justify-items: ___; } #pl0:checked ~ .grid{ } #pl1:checked ~ .grid{ place-items: center start; } #pl2:checked ~ .grid{ place-items: start center; } #pl3:checked ~ .grid{ place-items: end start; } #pl4:checked ~ .grid{ place-items: start end; } #pl5:checked ~ .grid{ place-items: stretch start; } #pl6:checked ~ .grid{ place-items: start stretch; }
Полный синтаксис:
Выше для упрощения был не полный синтаксис, однако он покрывает 99% нужного.
align-items: normal | stretch | [ <overflow>? <position> ] | <baseline> justify-items: normal | stretch | <overflow>? [ <position> | left | right ] | <baseline> | legacy [ left | right | center ] /* <baseline> = [ first | last ]? baseline <overflow> = unsafe | safe <position> = center | start | end | self-start | self-end | flex-start | flex-end то что в [] или до ? — можно не указывать */
- left — для
justify-items
, не работает дляalign-items
. Все элементы прижимаются к левому краю ячеек. -
right — для
justify-items
, не работает дляalign-items
. Все элементы прижимаются к правому краю ячеек. -
flex-start — тоже что
start
для грид-сетки. Т.е. если элементы не являются детьми flex контейнера ведет себя какstart
. -
flex-end — тоже что
end
для грид-сетки. Т.е. если элементы не являются детьми flex контейнера ведет себя какend
. -
baseline, first baseline, last baseline — выравнивает по линии текста (первой или последней). Обратная совместимость: для
first baseline
этоstart
, дляlast baseline
этоend
. - legacy — позволяет управлять тем, как будет наследоваться значение детьми.
Еслиlegacy
указано безleft
,right
,center
, то значение просто наследуется у родителя или равноnormal
.
Когдаjustify-self:auto
ссылается на значениеjustify-items:
, берется значение без словаlegacy
, например уlegacy left
будет взятоleft
. Это нужно для правильного выравнивания тега<center>
или элемента с атрибутомalign
.
grid-auto-rows:, grid-auto-columns:
Устанавливает размер для авто-создаваемых (неявных) рядов/колонок.
Колонки/ряды создаются автоматически, когда в сетке элементов больше чем помещается в определенные ряды/колонки (ячейки) или когда элемент размещается за пределы указанной сетки.
grid-auto-columns: размер; grid-auto-rows: размер;
Возможные значения размеров смотрите в описании grid-template-rows:
и grid-template-columns:
— может быть px, em, %, fr и т.д.
Пример
<title>Grid: grid-auto-columns/rows:</title> Выглядит как баг: высота в repeat() указываются жестко, но когда блоки не лезут в контейнер, их высота сжимается меньше указанного в repeat() размера. Однако grid-auto-rows влияет на эту высоту. А grid-auto-column ни на что не влияет!<br><br> Так происходит, потому что repeat() не создает рядов/колонок больше чем лезет в блок, поэтому создаются неявные (auto) ряды. При этом неявные создаются только ряды и непоместившиеся блоки размещаются вниз.<br><br> Но если изменить "течение" <b>grid-auto-flow</b> на <b>column</b>, то будет все тоже самое, только теперь непоместившиеся блоки размещаются в колонки (вправо). <br> <br> <b>grid-template:</b> <code>repeat(auto-fit, 50px) / repeat(auto-fit, 50px);</code> <br> <b>grid-auto-flow: </b> <input type="radio" name="auf" id="auf0" checked /><label for="auf0">row</label> <input type="radio" name="auf" id="auf1" /><label for="auf1">column</label> <br> <b>grid-auto-rows: </b> <input type="radio" name="aur" id="aur0" checked /><label for="aur0">нет</label> <input type="radio" name="aur" id="aur1" /><label for="aur1">100px</label> <br> <b>grid-auto-column: </b> <input type="radio" name="auc" id="auc0" checked /><label for="auc0">нет</label> <input type="radio" name="auc" id="auc1" /><label for="auc1">100px</label> <div class="grid"> <div class="item">1</div> <div class="item">2</div> <div class="item">3</div> <div class="item">4</div> <div class="item">5</div> <div class="item">6</div> <div class="item">7</div> <div class="item">8</div> <div class="item">9</div> </div>
body { font: 14px/1.25 sans-serif; padding:1em; margin:0; max-width:700px; } input{ display: none; } label{ display: inline-block; cursor:pointer; padding:0 .8em; user-select:none; text-align:left; } label:hover{ background:#ccc; } input:checked + label{ font-weight:bold; background:#ccc; } .grid { display: grid; grid-gap:.5em; grid-template: repeat(auto-fit, 50px) / repeat(auto-fit, 50px); margin:1em 0 0; border:1px dashed #666; animation: resize 6s linear infinite alternate; } .item { background:#a5b8d0; color:rgba(0,0,0,.5); font-size:200%; border-radius:3px; display:flex; justify-content:center; align-items:center; border:1px solid #8393a7; } #auf1:checked ~ .grid{ grid-auto-flow: column; } #aur1:checked ~ .grid{ grid-auto-rows: 100px; } #auc1:checked ~ .grid{ grid-auto-columns: 100px; } @keyframes resize { 0%, 15% { width: 150px; height: 70px; } 85%, 100% { width: 100%; height: 280px; } }
grid-auto-flow:
Определяет логику добавления элементов в пустые ячейки.
Когда элементам конкретно не указано в какой ячейке (области) они должны быть расположены, то они размещаются в пустые ячейки. По умолчанию заполнение идет слева направо (→) до конца ряда, переход на следующий ряд и опять заполнение (похоже на то как мы читаем текст).
По умолчанию алгоритм row
т.е. такой → ↓ →, можно сделать так ↓ → ↓.
Синтаксис
grid-auto-flow: row | column | row dense | column dense
Значения
- row
- По умолчанию. Расставляет элементы в сетке по рядам → ↓ →. Добавляет ряды если в сетке нет места.
- column
- расставляет элементы в сетке по колонкам ↓ → ↓. Добавляет колонки если в сетке нет места.
- dense
- включает «dense» алгоритм заполнения, который пытается разместить элементы так, чтобы не оставалось пустых пространств (по умолчанию работает алгоритм «sparse»). При этом элементы могут располагаться не по-порядку. При вставке каждого следующего элемента, алгоритм проверяет нет ли пустой ячейки сзади куда может поместиться текущий элемент, если есть, помещает его туда а не в следующую ячейку. dense имеет смысл только при наличии областей в сетке - это когда элементу указано разместиться сразу в несколько ячеек (через span), тогда он как правило не помещается в одну ячейку и остается пустое место.
Пример
<title>Grid: grid-auto-flow</title> <b>grid-auto-flow:</b> <input type="radio" name="a" id="al1" checked /><label for="al1">row</label> <input type="radio" name="a" id="al2" /><label for="al2">row dense</label> <input type="radio" name="a" id="al3" /><label for="al3">column</label> <input type="radio" name="a" id="al4" /><label for="al4">column dense</label> <br> <b>размеры элементов:</b> <input type="radio" name="b" id="size1" /><label for="size1">разные</label> <input type="radio" name="b" id="size2" checked /><label for="size2">одинаковые</label> <br> <div class="grid"> <div class="item">1</div> <div class="item">2</div> <div class="item">3</div> <div class="item">4</div> <div class="item">5</div> <div class="item">6</div> <div class="item">7</div> <div class="item">8</div> <div class="item">9</div> </div>
body { font: 14px/1 sans-serif; padding:1em; margin:0; } input{ display: none; } label{ display: inline-block; cursor:pointer; padding:.3em .5em; user-select:none; text-align:left; } label:hover{ background:#ccc; } input:checked + label{ font-weight:bold; background:#ccc; } .grid { display: inline-grid; grid-template: 70px 70px 70px / 100px 100px 100px; grid-auto-rows: 70px; grid-auto-columns: 100px; grid-gap: 1em; padding:1em; margin:1em 0 0; background:#dae0e8; } .item{ background:#a5b8d0; color:rgba(0,0,0,.5); font-size:200%; display:flex; justify-content:center; align-items:center; } #size1:checked ~ .grid .item:nth-of-type(3){ grid-column: auto / span 2; } #size1:checked ~ .grid .item:nth-of-type(5){ grid-row: span 2 / auto; } #size1:checked ~ .grid .item:nth-of-type(7){ grid-row: span 2 / auto; } #al1:checked ~ .grid{ grid-auto-flow: row; } #al2:checked ~ .grid{ grid-auto-flow: row dense; } #al3:checked ~ .grid{ grid-auto-flow: column; } #al4:checked ~ .grid{ grid-auto-flow: column dense; }
grid:
Позволяет сокращенно записать свойства:
grid-template-rows:
grid-template-columns:
grid-template-areas:
grid-auto-rows:
grid-auto-columns:
grid-auto-flow:
Т.е. в этом свойстве можно описать почти все свойства грид-сетки. Однако, тут можно описать свойства только для «явных» или «неявных» рядов/колонок, сразу для тех и других не получиться. Если нужно указать свойства для тех и других, то нужно дописывать соответствующие свойства в дополнении к grid:
.
Синтаксис
grid: none grid: grid-template grid: grid-template-rows / grid-template-columns grid: grid-template-areas grid: grid-template-rows / [auto-flow dense?] grid-auto-columns? grid: [auto-flow dense?] grid-auto-rows? / grid-template-columns /* то что в [] или до ? — можно не указывать */
-
none — устанавливает все свойства в начальное состояние.
-
grid-template-rows / [auto-flow +dense?] grid-auto-columns? — ключевое слово
auto-flow
с правой стороны слэша устанавливает grid-auto-flow: column.dense
включает алгоритм упаковки «dense». Если не указанgrid-auto-columns
, то он будет равен auto. - [auto-flow +dense?] grid-auto-rows? / grid-template-columns — ключевое слово
auto-flow
с левой стороны слэша устанавливает grid-auto-flow: row.dense
включает алгоритм упаковки «dense». Если не указанgrid-auto-rows
, то он будет равен auto.
Примеры:
grid: 'header header header header' 'main main main right right' 'footer footer footer footer'; /* тоже что: */ grid-template-areas: 'header header header header' 'main main main right right' 'footer footer footer footer';
grid: 100px 300px / 3fr 1fr; /* тоже что: */ grid-auto-flow: row; grid-template-columns: 200px 1fr;
grid: auto-flow dense 100px / 1fr 2fr; /* тоже что: */ grid-auto-flow: row dense; grid-auto-rows: 100px; grid-template-columns: 1fr 2fr;
grid: 100px 300px / auto-flow 200px; /* тоже что: */ grid-template-rows: 100px 300px; grid-auto-flow: column; grid-auto-columns: 200px;
Также можно указать более сложный, но удобный для настройки все и сразу:
grid: [row1-start] "header header header" 1fr [row1-end] [row2-start] "footer footer footer" 25px [row2-end] / auto 50px auto; /* тоже что: */ grid-template-areas: "header header header" "footer footer footer"; grid-template-rows: [row1-start] 1fr [row1-end row2-start] 25px [row2-end]; grid-template-columns: auto 50px auto;
И еще варианты:
grid: repeat(auto-fill, 5em) / auto-flow 1fr; grid: auto-flow 1fr / repeat(auto-fill, 5em); grid: auto 1fr auto / repeat(5, 1fr); grid: repeat(3, auto) / repeat(4, auto);
CSS свойства Grid для элементов
CSS свойства: float
, display:inline-block
, display:table-cell
, vertical-align
и column-*
никак не влияют на элементы grid контейнера. У grid сетки свои правила...
grid-row-start:, grid-row-end:, grid-column-start:, grid-column-end:, grid-row:, grid-column
Указывает положение элемента в сетке. Т.е. размещает элемент в указанную ячейку. Указывать нужно имя или номер линии к которой относится ячейка и к которой нужно прикрепить элемент.
grid-column
и grid-row
— это сокращение для свойств: grid-column-start/grid-column-end
и grid-row-start / grid-row-end
. Можно указать только первое (одно) значение, оно будет относиться к начальной линии и элемент будет растягиваться на 1 ряд/колонку (т.е. будет помещен в одну ячейку начальная линия которой указана).
Синтаксис
grid-row-start: значение; /* где начинается линия ряда */ grid-row-end: значение; /* где кончается линия ряда */ grid-column-start: значение; /* где начинается линия колонки */ grid-column-end: значение; /* где кончается линия колонки */ grid-row: grid-row-start / grid-row-end; grid-column: grid-column-start / grid-column-end; /* можно указать одно значение, второе значение будет span 1 */ grid-row: grid-row-start; grid-column: grid-column-start;
Значения
- число/имя
- порядковый номер или имя линии к которой нужно прикрепить текущий элемент.
- span число
- слово span значит растянуть. Текущий элемент будет растягиваться на указанное число рядов/колонок. Если указано слово span, то относится всегда ко второму значению.
- span имя
- слово span значит растянуть. Текущий элемент будет растягиваться до указанного названия линии ряда/колонки. Если указано слово span, то относится всегда ко второму значению.
- auto
- элемент размещается по указанному алгоритму в свойстве контейнера grid-auto-flow:.
Пример
<title>Grid: grid-column/row:</title> <b>grid-row-start:</b> <input type="radio" name="rs" id="rs0" /><label for="rs0">нет</label> <input type="radio" name="rs" id="rs1" /><label for="rs1">1</label> <input type="radio" name="rs" id="rs2" checked /><label for="rs2">2</label> <input type="radio" name="rs" id="rs3" /><label for="rs3">3</label> <input type="radio" name="rs" id="rs4" /><label for="rs4">4</label> <br> <b>grid-row-end:</b> <input type="radio" name="re" id="re0" checked /><label for="re0">нет</label> <input type="radio" name="re" id="re1" /><label for="re1">1</label> <input type="radio" name="re" id="re2" /><label for="re2">2</label> <input type="radio" name="re" id="re3" /><label for="re3">3</label> <input type="radio" name="re" id="re4" /><label for="re4">4</label> <br> <b>grid-column-start:</b> <input type="radio" name="cs" id="cs0" /><label for="cs0">нет</label> <input type="radio" name="cs" id="cs1" /><label for="cs1">1</label> <input type="radio" name="cs" id="cs2" checked /><label for="cs2">2</label> <input type="radio" name="cs" id="cs3" /><label for="cs3">3</label> <input type="radio" name="cs" id="cs4" /><label for="cs4">4</label> <input type="radio" name="cs" id="cs5" /><label for="cs5">5</label> <input type="radio" name="cs" id="cs6" /><label for="cs6">6</label> <br> <b>grid-column-end:</b> <input type="radio" name="ce" id="ce0" checked /><label for="ce0">нет</label> <input type="radio" name="ce" id="ce1" /><label for="ce1">1</label> <input type="radio" name="ce" id="ce2" /><label for="ce2">2</label> <input type="radio" name="ce" id="ce3" /><label for="ce3">3</label> <input type="radio" name="ce" id="ce4" /><label for="ce4">4</label> <input type="radio" name="ce" id="ce5" /><label for="ce5">5</label> <input type="radio" name="ce" id="ce6" /><label for="ce6">6</label> <br> <b>grid-row:</b> <input type="radio" name="gr" id="gr0" checked /><label for="gr0">нет</label> <input type="radio" name="gr" id="gr1" /><label for="gr1">2</label> <input type="radio" name="gr" id="gr2" /><label for="gr2">1 / 3</label> <input type="radio" name="gr" id="gr3" /><label for="gr3">1 / span 3</label> <input type="radio" name="gr" id="gr4" /><label for="gr4">2 / span 2</label> <br> <b>grid-column:</b> <input type="radio" name="gc" id="gc0" checked /><label for="gc0">нет</label> <input type="radio" name="gc" id="gc1" /><label for="gc1">2</label> <input type="radio" name="gc" id="gc2" /><label for="gc2">1 / 3</label> <input type="radio" name="gc" id="gc3" /><label for="gc3">2 / span 3</label> <input type="radio" name="gc" id="gc4" /><label for="gc4">3 / span 2</label> <br> <div class="grid"> <div class="item"></div> <nav class="cell"></nav> <nav class="cell"></nav> <nav class="cell"></nav> <nav class="cell"></nav> <nav class="cell"></nav> <nav class="cell"></nav> <nav class="cell"></nav> <nav class="cell"></nav> <nav class="cell"></nav> <nav class="cell"></nav> <nav class="cell"></nav> <nav class="cell"></nav> <nav class="cell"></nav> <nav class="cell"></nav> <nav class="cell"></nav> </div>
body { font: 14px/1 sans-serif; padding:1em; margin:0; } input{ display: none; } label{ display: inline-block; cursor:pointer; padding:.3em .5em; user-select:none; text-align:left; } label:hover{ background:#ccc; } input:checked + label{ font-weight:bold; background:#ccc; } .grid { display: grid; grid: repeat(3, 1fr) / repeat(5, 1fr); margin:1em 0 0; border: 1px dashed #555; border-bottom:0; border-right:0; height:250px; width:450px; } .item{ background:rgba(46,85,113,0.32); color:rgba(0,0,0,.5); width:100%; height:100%; /* grid-column: 1 / span 2; grid-row: 2; */ /* grid-column-start: 2; grid-column-end: 2; grid-row-start: 2; grid-row-end: 2; */ } .cell{ justify-self: stretch; align-self: stretch; border:1px dashed #555; border-top:0; border-left:0; width:100%; height:100%; } .cell:nth-of-type(1){ grid-row:1; grid-column:1; } .cell:nth-of-type(2){ grid-row:1; grid-column:2; } .cell:nth-of-type(3){ grid-row:1; grid-column:3; } .cell:nth-of-type(4){ grid-row:1; grid-column:4; } .cell:nth-of-type(5){ grid-row:1; grid-column:5; } .cell:nth-of-type(6){ grid-row:2; grid-column:1; } .cell:nth-of-type(7){ grid-row:2; grid-column:2; } .cell:nth-of-type(8){ grid-row:2; grid-column:3; } .cell:nth-of-type(9){ grid-row:2; grid-column:4; } .cell:nth-of-type(10){ grid-row:2; grid-column:5; } .cell:nth-of-type(11){ grid-row:3; grid-column:1; } .cell:nth-of-type(12){ grid-row:3; grid-column:2; } .cell:nth-of-type(13){ grid-row:3; grid-column:3; } .cell:nth-of-type(14){ grid-row:3; grid-column:4; } .cell:nth-of-type(15){ grid-row:3; grid-column:5; } #cs0:checked ~ .grid .item{ } #cs1:checked ~ .grid .item{ grid-column-start: 1 } #cs2:checked ~ .grid .item{ grid-column-start: 2 } #cs3:checked ~ .grid .item{ grid-column-start: 3 } #cs4:checked ~ .grid .item{ grid-column-start: 4 } #cs5:checked ~ .grid .item{ grid-column-start: 5 } #cs6:checked ~ .grid .item{ grid-column-start: 6 } #ce0:checked ~ .grid .item{ } #ce1:checked ~ .grid .item{ grid-column-end: 1 } #ce2:checked ~ .grid .item{ grid-column-end: 2 } #ce3:checked ~ .grid .item{ grid-column-end: 3 } #ce4:checked ~ .grid .item{ grid-column-end: 4 } #ce5:checked ~ .grid .item{ grid-column-end: 5 } #ce6:checked ~ .grid .item{ grid-column-end: 6 } #rs0:checked ~ .grid .item{ } #rs1:checked ~ .grid .item{ grid-row-start: 1 } #rs2:checked ~ .grid .item{ grid-row-start: 2 } #rs3:checked ~ .grid .item{ grid-row-start: 3 } #rs4:checked ~ .grid .item{ grid-row-start: 4 } #rs5:checked ~ .grid .item{ grid-row-start: 5 } #rs6:checked ~ .grid .item{ grid-row-start: 6 } #re0:checked ~ .grid .item{ } #re1:checked ~ .grid .item{ grid-row-end: 1 } #re2:checked ~ .grid .item{ grid-row-end: 2 } #re3:checked ~ .grid .item{ grid-row-end: 3 } #re4:checked ~ .grid .item{ grid-row-end: 4 } #re5:checked ~ .grid .item{ grid-row-end: 5 } #re6:checked ~ .grid .item{ grid-row-end: 6 } #gc0:checked ~ .grid .item{ } #gc1:checked ~ .grid .item{ grid-column: 2; } #gc2:checked ~ .grid .item{ grid-column: 1 / 3; } #gc3:checked ~ .grid .item{ grid-column: 2 / span 3; } #gc4:checked ~ .grid .item{ grid-column: 3 / span 2; } #gr0:checked ~ .grid .item{ } #gr1:checked ~ .grid .item{ grid-row: 2; } #gr2:checked ~ .grid .item{ grid-row: 1 / 3; } #gr3:checked ~ .grid .item{ grid-row: 1 / span 3; } #gr4:checked ~ .grid .item{ grid-row: 2 / span 2; }
grid-area:
Дает элементу имя. По имени элемент будет относится к области указанной в свойстве grid-template-areas:. Или в значении можно указать номер/имя линий.
Синтаксис
grid-area: имя области; grid-area: row-start / column-start / row-end / column-end;
Значения
- имя области
- название области сетки.
- row-start / column-start / row-end / column-end
может быть числом или именем линии.
Пример
grid-area: header; /* или так: */ grid-area: 1 / col4-start / last-line / 6
align-self:, justify-self:, place-self:
Выравнивает текущий элемент внутри ячейки. Применяется к отдельному элементу контейнера.
Синтаксис
align-self: значение; /* выравнивает элемент внутри ячейки по вертикали ↓↑ */ justify-self: значение; /* выравнивает элемент внутри ячейки по горизонтали ←→ */ place-self: значение; /* сокращенная запись: установит оба значения */ place-self: align-self justify-self; /* сокращенная запись */
Значения
- stretch
- по умолчанию. Растягивает текущий элемент на всю ширину/высоту ячейки.
- start
- размещает текущий элемент в начале ячейки (слева или сверху).
- end
- размещает текущий элемент в конце ячейки (справа или внизу).
- center
- размещает текущий элемент по центру ячейки.
Редкие значения
- safe значение
если ширина или высота элемента превышает размер ячейки, то значение переключается на start. В значении тут может быть только: center или end.- unsafe значение
значение остается указанным, даже если ширина или высота элемента превышает размер ячейки. В значении тут может быть только: center или end.
Пример
<title>Grid: align/justify-self:</title> <b>align-self:</b> <input type="radio" name="a" id="al0" /><label for="al0">нет</label> <input type="radio" name="a" id="al1" checked /><label for="al1">stretch</label> <input type="radio" name="a" id="al2" /><label for="al2">start</label> <input type="radio" name="a" id="al3" /><label for="al3">end</label> <input type="radio" name="a" id="al4" /><label for="al4">center</label> <input type="radio" name="a" id="al5" /><label for="al5"></label> <input type="radio" name="a" id="al6" /><label for="al6"></label> <input type="radio" name="a" id="al7" /><label for="al7"></label> <br> <b>justify-self:</b> <input type="radio" name="b" id="js0" /><label for="js0">нет</label> <input type="radio" name="b" id="js1" checked /><label for="js1">stretch</label> <input type="radio" name="b" id="js2" /><label for="js2">start</label> <input type="radio" name="b" id="js3" /><label for="js3">end</label> <input type="radio" name="b" id="js4" /><label for="js4">center</label> <input type="radio" name="b" id="js5" /><label for="js5"></label> <input type="radio" name="b" id="js6" /><label for="js6"></label> <input type="radio" name="b" id="js7" /><label for="js7"></label> <br> <b>place-self:</b> <input type="radio" name="c" id="pl0" checked/><label for="pl0">нет</label> <input type="radio" name="c" id="pl1" /><label for="pl1">center start</label> <input type="radio" name="c" id="pl2" /><label for="pl2">start center</label> <input type="radio" name="c" id="pl3" /><label for="pl3">end start</label> <input type="radio" name="c" id="pl4" /><label for="pl4">start end</label> <input type="radio" name="c" id="pl5" /><label for="pl5">stretch start</label> <input type="radio" name="c" id="pl6" /><label for="pl6">start stretch</label> <br> <div class="grid"> <div class="item">1</div> <div class="item">2</div> <div class="item">3</div> <div class="item">4</div> <div class="item">5</div> <div class="item">6</div> </div>
body { font: 14px/1 sans-serif; padding:1em; margin:0; } input{ display: none; } label{ display: inline-block; cursor:pointer; padding:.3em .5em; user-select:none; text-align:left; } label:hover{ background:#ccc; } input:checked + label{ font-weight:bold; background:#ccc; } .grid { display: grid; grid-template: auto auto / auto auto auto; /* grid-gap: 1em; */ /* align-items:center; */ margin:1em 0 0; border: 1px dashed #555; border-bottom:0; border-right:0; height:200px; max-width:500px; } .item{ background:#a5b8d0; color:rgba(0,0,0,.5); font-size:200%; display:flex; justify-content:center; align-items:center; border:1px solid #8393a7; padding:.6em .9em; line-height:1; } .grid .item:nth-of-type(2){ background:#cae01b; border:1px solid #a0b116; } #al0:checked ~ .grid .item:nth-of-type(2){ } #al1:checked ~ .grid .item:nth-of-type(2){ align-self: stretch; } #al2:checked ~ .grid .item:nth-of-type(2){ align-self: start; } #al3:checked ~ .grid .item:nth-of-type(2){ align-self: end; } #al4:checked ~ .grid .item:nth-of-type(2){ align-self: center; } #al5:checked ~ .grid .item:nth-of-type(2){ align-self: ___; } #al6:checked ~ .grid .item:nth-of-type(2){ align-self: ___; } #al7:checked ~ .grid .item:nth-of-type(2){ align-self: ___; } #js0:checked ~ .grid .item:nth-of-type(2){ } #js1:checked ~ .grid .item:nth-of-type(2){ justify-self: stretch; } #js2:checked ~ .grid .item:nth-of-type(2){ justify-self: start; } #js3:checked ~ .grid .item:nth-of-type(2){ justify-self: end; } #js4:checked ~ .grid .item:nth-of-type(2){ justify-self: center; } #js5:checked ~ .grid .item:nth-of-type(2){ justify-self: ___; } #js6:checked ~ .grid .item:nth-of-type(2){ justify-self: ___; } #js7:checked ~ .grid .item:nth-of-type(2){ justify-self: ___; } #pl0:checked ~ .grid .item:nth-of-type(2){ } #pl1:checked ~ .grid .item:nth-of-type(2){ place-self: center start; } #pl2:checked ~ .grid .item:nth-of-type(2){ place-self: start center; } #pl3:checked ~ .grid .item:nth-of-type(2){ place-self: end start; } #pl4:checked ~ .grid .item:nth-of-type(2){ place-self: start end; } #pl5:checked ~ .grid .item:nth-of-type(2){ place-self: stretch start; } #pl6:checked ~ .grid .item:nth-of-type(2){ place-self: start stretch; }
Чтобы выровнять все элементы контейнера сразу, используйте: align-items:, justify-items:, place-items:. Там же вы найдете описание для редко-используемых значений.
Примеры
Каркас HTML страницы
<title>Пример 1</title> <body> <header>header</header> <nav>nav</nav> <section>section</section> <aside>aside</aside> <footer>footer</footer> </body>
body { display: grid; grid: "header header header" 80px "nav section aside" 1fr "footer footer footer" 50px / 15% 1fr 18%; min-height: 100vh; } header { grid-area: header; } nav { grid-area: nav; } section { grid-area: section; } aside { grid-area: aside; } footer { grid-area: footer; } /* стили для наглядности */ body{ margin:0; font-family: sans-serif; } body > *{ padding:1em; } header { background: #daebe8; } nav { background: #cfe0e8; } section { background: #b7d7e8; } aside { background: #bccad6; } footer { background: #b3d4ce; }
Каркас для игрового приложения
<title>Пример 2</title> <div id="grid"> <div id="title">Game Title</div> <div id="score">Score</div> <div id="stats">Stats</div> <div id="board">Board</div> <div id="controls">Controls</div> </div>
#grid { /** * Две колонки: * 1. подстраивается под контент, * 2. получает все оставшееся пространтсов * (но не может быть меньше минимального размера контента в ней или controls блока в этой же колонке) * * Три ряда: * 1. подстраивается под контент, * 2. получает все свободное пространство * (но не может быть меньше минимального размера любого из блоков в этмо ряду) * 3. подстраивается под контент. */ display: grid; grid-template-columns: /* 1 */ auto /* 2 */ 1fr; grid-template-rows: /* 1 */ auto /* 2 */ 1fr /* 3 */ auto; /* растянем на всю высоту */ height: 100vh; } /* указывает позиции блоков в сетке с помощью координат */ #title { grid-column: 1; grid-row: 1; } #score { grid-column: 1; grid-row: 3; } #stats { grid-column: 1; grid-row: 2; } #board { grid-column: 2; grid-row: 1 / span 2; } #controls { grid-column: 2; grid-row: 3; justify-self: center; } /* стили для наглядности */ body{ margin:0; font-family: sans-serif; } #grid > *{ padding: 1em; } #title { background: #daebe8; } #score { background: #cfe0e8; } #stats { background: #b7d7e8; } #board { background: #bccad6; } #controls { background: #b7d7e8; }
Усложним задачу.
Теперь нам нужно сделать так чтобы при повороте мобильного устройства, каркас менялся и получалось так:
В этом случае удобнее будет использовать области Grid сетки.
<title>Пример 3</title> <div id="grid"> <div id="title">Game Title</div> <div id="score">Score</div> <div id="stats">Stats</div> <div id="board">Board</div> <div id="controls">Controls</div> </div>
/* книжная ориентация */ @media (orientation: portrait) { #grid { display: grid; /* создадаим структуру сетки и укажем названия областей, * Такая структура будет работать по умолчанию и подоходиь для альбомной ориентации. */ grid-template-areas: "title stats" "score stats" "board board" "ctrls ctrls"; /* укажем размеры для рядов и колонок. */ grid-template-columns: auto 1fr; grid-template-rows: auto auto 1fr auto; height: 100vh; } } /* альбомная ориентация */ @media (orientation: landscape) { #grid { display: grid; /* создадаим структуру сетки и укажем названия областей, * Такая структура будет работать по умолчанию и подоходиь для альбомной ориентации. */ grid-template-areas: "title board" "stats board" "score ctrls"; /* укажем размеры для рядов и колонок. */ grid-template-columns: auto 1fr; grid-template-rows: auto 1fr auto; height: 100vh; } } /* расположим элементы в именованные областя сетки */ #title { grid-area: title; } #score { grid-area: score; } #stats { grid-area: stats; } #board { grid-area: board; } #controls { grid-area: ctrls; justify-self: center; } /* стили для наглядности */ body{ margin:0; font-family: sans-serif; } #grid > *{ padding:1em; } #title { background: #daebe8; } #score { background: #cfe0e8; } #stats { background: #b7d7e8; } #board { background: #bccad6; } #controls { background: #b7d7e8; }
Этот пример нужно просмотреть с телефона...
Простой блок на Grid
<title>Пример 4</title> <div class="support-grid"></div> <section class="grid-1"> <div class="panel panel-title"> <h1>Barry’s Cushion</h2> <p>Сказка о летаргии и мягкой мебели</p> </div> <div class="panel panel-1"></div> <div class="panel panel-2"></div> <div class="panel panel-3"> <p>“Наверное, мне пора вставать, есть дела.”</p> </div> <div class="panel panel-4"></div> <div class="panel panel-5"></div> <div class="panel panel-6"></div> <div class="panel panel-7"> <p>“Naaah.”</p> </div> <div class="panel panel-8"></div> <div class="panel panel-9"></div> <div class="panel panel-copyright"> <p>Sleepy Fat Cat by messenj4h<br> © Copyright happily ever after <a target="_blank" href="https://webdesign.tutsplus.com/tutorials/css-grid-layout-and-comics-as-explained-by-barry-the-cat--cms-27617">Envato Tuts+</a> </div> </section>
/* basics */ body { background: #f8f7f2; padding: 0 10%; font: 100%/1.5 'Kalam', cursive; } h1 { margin: 0; line-height: 1; padding: 10px; color: #251b19; } p { margin: 0; padding: 10px; color: #251b19; font-size: 1.2em; } a { color: #e56633; } a:hover { text-decoration: none; } /* the grid */ .grid-1 { display: grid; width: 100%; max-width: 770px; margin: 10% auto; grid-template-columns: 1fr; grid-template-rows: auto 200px 200px auto 200px 200px 200px auto 200px 200px auto; grid-gap: 25px; } /* panels */ .panel { color: white; background-repeat: no-repeat; background-position: center center; background-size: cover; box-shadow: 0 0px 0px 5px #251b19; } /* individual panels */ .panel-title { box-shadow: none; } .panel-1 { background-image: url(cat/cat-002.svg); box-shadow: none; } .panel-2 { background-image: url(cat/cat-001.svg); } .panel-3 { box-shadow: none; } .panel-4 { background-image: url(cat/cat-003.svg); } .panel-5 { background-image: url(cat/cat-004.svg); } .panel-6 { background-image: url(cat/cat-005.svg); } .panel-7 { box-shadow: none; } .panel-8 { background-image: url(cat/cat-007.svg); } .panel-9 { background-image: url(cat/cat-008.svg); box-shadow: none; } .panel-copyright { box-shadow: none; font-size: .75em; } /* media query 1 */ @media only screen and (min-width: 400px) { .grid-1 { grid-template-columns: repeat(2, 1fr); grid-template-rows: auto 200px auto 200px 200px auto 200px auto; } .panel-title, .panel-3, .panel-6, .panel-7, .panel-copyright { grid-column: span 2; } .panel-copyright { text-align: right; } .panel-7 { text-align: center; } h1 { font-size: 3em; } } /* media query 2 */ @media only screen and (min-width: 600px) { .grid-1 { grid-template-columns: repeat(3, 1fr); grid-template-rows: auto 200px 200px 200px auto; } .panel-title, .panel-copyright { grid-column: span 3; } .panel-3, .panel-6 { grid-column: auto; } .panel-8 { grid-column: span 2; } h1 { font-size: 3.5em; } p { font-size: 1.3em; } /* flexbox centering */ .panel-3 { display: flex; align-items: center; } /* layering */ .panel-7 { grid-column: 1; grid-row: 4; z-index: 1; margin: -5px 0 0 -10px; transform: rotate(-2deg); } .panel-7 p { background: #f8f7f2; box-shadow: 0 0px 0px 5px #251b19; text-align: left; } .panel-8 { grid-column: 1 / span 2; grid-row: 4; background-size: 70%; background-position: right; } }
Сравнение Flex и Grid
В отличие от Flex, которая ориентирована на одну ось, Grid оптимизирована для двумерных компоновок: когда требуется расположить (выровнять) содержимое в обоих измерениях (по вертикали и горизонтали).
Кроме того, благодаря возможности явного позиционирования элементов в сетке, Grid позволяет выполнять кардинальные преобразования в структуре, не требуя никаких изменений HTML разметки. Комбинируя медиа-запросы со свойствами CSS, управляющими компоновкой контейнера grid и его дочерних элементов, можно адаптировать верстку под любые форм-факторы устройств.
Grid и Flexbox, имеют свои особенности и нельзя сказать, что одно заменяет другое. Скорее Флекс является дополнением к Грид, или наоборот.
Flexbox фокусируется на распределении пространства внутри одной оси, использует более простой подход к компоновке, может использовать систему упаковки строк на основе размера содержимого для управления своей вторичной осью и полагается на иерархию разметки. Тогда как Grid больше подходит для создания каркасов, потому что имеет более мощный и комплексный подход и в целом не зависит от иерархии разметки. В отдельных случаях Grid позволяет создать адаптивный макет, который невозможно создать с помощью Flex или как-то еще.
<title> Grid: сравнение с Flex</title> <h5>Flex Box - ориентируется по одной оси (одномерный)</h5> <div class="flex container"> <div class="item">1</div> <div class="item">2</div> <div class="item">3</div> <div class="item">4</div> <div class="item">5</div> <div class="item">6</div> <div class="item">7</div> <div class="item">8</div> </div> <h5>CSS Grid - оринетируется по двум осям (двумерный)</h5> <div class="grid container"> <div class="item">1</div> <div class="item">2</div> <div class="item">3</div> <div class="item">4</div> <div class="item">5</div> <div class="item">6</div> </div>
html { box-sizing: border-box; font-family: sans-serif; } *, *::before, *::after { box-sizing: inherit; } .container{ /* border: 1px dashed #666; */ } .item{ background: #899db9; padding: 1em; border: 1px solid #fff; display: flex; justify-content:center; align-items:center; color:rgba(0,0,0,.5); } .flex { display: flex; flex-wrap: wrap; } .flex .item:nth-child(-n + 3) { flex-basis: 33.33%; } .flex .item:nth-child(n + 4) { flex-grow: 1; } .grid { display: grid; grid: "a b c d d" "f f g d d"; } .grid .item:nth-child(4) { grid-area: d; } .grid .item:nth-child(5) { grid-area: f; }
Ссылки
- Grid в CSS — источник.
- Grid — Учебник от hcdev.ru.
- Гриды на грядках — игра позволяет с интересом попрактиковаться с гридами.
- grid.layoutit.com — интерактивный генератор грид сетки.
- CSS Grid (developer.mozilla.org)
- Вёрстка на Grid в CSS. Полное руководство и справочник
- Большая статья про гриды (CSS Grid Layout)
- CSS Grid Layout. Быстрый старт
- Вёрстка на Grid в CSS. Полное руководство и справочник
- Полное руководство по CSS Grid
- Изучаем CSS Grid на примерах
- Как верстать на CSS Grid. Пошаговая инструкция с примерами