Мы столкнулись с некоторой проблемой производительности с CSS Grid, и нам не удалось найти причину root. В одном минимальном случае использования, демонстрирующем эту проблему, когда пользователь вводит один символ в текстовое поле, это вызывает массивные вычисления макета, которые замедляют процесс ввода. Мы полагали, что проблема возникла из нашего JavaScript кода, но даже после удаления JavaScript из нашего примера проблема остается. Похоже, это связано в основном с CSS Grid.
Мы создали небольшой пример на Codepen, который показывает проблему: https://codepen.io/sbegaudeau/pen/abOLyJG
<html lang="en">
<body>
<div id="root">
<div class="app">
<div class="view">
<div class="container">
<div class="content">
<div class="outer">
<div class="inner">
<div class="section">
<div class="sectionContent">
<div class="innerContent">
<input class="textfield" type="text" value="XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX"/>
<button class="button action" type="button">
Action 1
</button>
<button class="button action" type="button">
Action 2
</button>
<button class="button action" type="button">
Action 3
</button>
<button class="button action" type="button">
Action 4
</button>
<button class="button action" type="button">
Action 5
</button>
<button class="button action" type="button">
Action 6
</button>
<button class="button action" type="button">
Action 7
</button>
</div>
</div>
</div>
<div class="section">
<div class="sectionContent">
<div class="radiogroup">
<label class="radio"><input type="radio" value="choice1" />Choice 1</label>
<label class="radio"><input type="radio" value="choice2" checked=""/>Choice 2</label>
</div>
</div>
<div class="sectionContent">
<div class="radiogroup">
<label class="radio"><input type="radio" value="choice1" />Choice 1</label>
<label class="radio"><input type="radio" value="choice2" checked=""/>Choice 2</label>
</div>
</div>
<div class="sectionContent">
<div class="radiogroup">
<label class="radio"><input type="radio" value="choice1" />Choice 1</label>
<label class="radio"><input type="radio" value="choice2" checked=""/>Choice 2</label>
</div>
</div>
<div class="sectionContent">
<div class="radiogroup">
<label class="radio"><input type="radio" value="choice1" />Choice 1</label>
<label class="radio"><input type="radio" value="choice2" checked=""/>Choice 2</label>
</div>
</div>
<div class="sectionContent">
<div class="radiogroup">
<label class="radio"><input type="radio" value="choice1" />Choice 1</label>
<label class="radio"><input type="radio" value="choice2" checked=""/>Choice 2</label>
</div>
</div>
<div class="sectionContent">
<div class="radiogroup">
<label class="radio"><input type="radio" value="choice1" />Choice 1</label>
<label class="radio"><input type="radio" value="choice2" checked=""/>Choice 2</label>
</div>
</div>
</div>
</div>
</div>
</div>
</div>
</div>
</div>
</div>
</body>
</html>
.button {
display: grid;
grid-template-columns: 1fr;
grid-template-rows: 1fr;
justify-items: center;
align-items: center;
min-width: 90px;
padding: 8px 32px;
}
.radiogroup {
display: flex;
flex-direction: row;
}
.radio {
display: grid;
grid-template-columns: min-content 1fr;
grid-template-rows: 1fr;
column-gap: 8px;
align-items: center;
}
.inner {
display: grid;
grid-template-columns: 1fr;
grid-template-rows: repeat(min-content);
}
.section {
display: grid;
grid-template-columns: 1fr;
grid-template-rows: min-content 1fr;
grid-gap: 32px;
gap: 32px;
}
.sectionContent {
display: grid;
grid-template-rows: min-content;
gap: 16px;
}
.innerContent {
display: grid;
grid-template-columns: 1fr max-content;
}
.app {
display: grid;
grid-template-columns: 1fr;
grid-template-rows: 1fr;
}
.view {
display: grid;
grid-template-columns: 1fr;
grid-template-rows: min-content 1fr min-content;
}
.container {
display: grid;
grid-template-columns: 1fr 960px 1fr;
grid-template-rows: 64px 1fr;
}
.content {
display: grid;
grid-template-columns: 1fr;
grid-template-rows: 1fr;
grid-column-start: 2;
grid-column-end: 3;
grid-row-start: 2;
grid-row-end: 3;
}
.outer {
display: grid;
grid-template-colums: 1fr;
grid-template-rows: 1fr;
}
Попробуйте ввести один символ в текстовое поле с помощью Chrome Мониторинга производительности Devtools, и вы увидите, что при вводе одного символа запускается раскладка 50 мс (см. Скриншот ниже). В нашем сложном примере может потребоваться более 100 мс для ввода одного символа, который действительно заметен.
Что мы делаем, чтобы сделать это настолько дорогим?
