Вот мой подход
Демонстрация Codepen
Весь раздел представляет собой элемент flex
, вертикально центрированный (смаленький отрицательный margin-top
). Ipso facto , если содержимое изменяется, результатом является эффект, при котором новое содержимое, помещенное в раздел, выталкивает все элементы одного уровня в обоих направлениях.
button
просто переключаеткласс .open
, который запускает анимацию CSS, показывающую (и скрывающую) набор полей одного и того же брата (в разметке кнопки были определены до fieldset
, но они отображаются после благодаря свойству order
.
Разметка
<section class="login">
<h1>Wir suchen noch <br />Frontend-Helden</h1>
<form>
<button type="button" class="login__btt login__btt--zufalls"
data-collapsed-text="zufalls button"
data-expandend-text="abbrechen">zufalls button</button>
<button type="button" class="login__btt login__btt--anmelden">anmelden</button>
<fieldset class="login__credentials">
<ul>
<li>
<label for="username">User</label>
<input type="text" id="username" />
</li>
<li>
<label for="password">Password</label>
<input type="password" id="password" />
</li>
</fieldset>
</form>
</section>
CSS (актуально, см. Демонстрацию для полного стиля)
body {
margin: 0;
padding: 0;
height: 100vh;
min-height: 500px;
text-align: center;
display: flex;
flex-flow: column wrap;
justify-content: center;
font-size: 1.5rem;
background: linear-gradient(135deg, #9bc, yellowgreen) 0 0 no-repeat;
background-size: 100% 50vh; }
.login {
width: 500px;
margin: -20vh auto 0 auto; }
.login form {
box-shadow: 0 0 20px #9bc;
padding: 2em;
display: flex;
background: #fff;
flex-direction: column; }
.login ul {
list-style-type: none;
margin: 0; padding: 0;
width: 100% }
.login li {
margin-bottom: 20px;
display: flex;
flex-direction: row;
justify-content: space-between;
align-items: center;
width: 300px; }
.login__btt {
display: block;
cursor: pointer;
margin: 1em auto;
order: 1;
width: 300px;
padding: .8em 2em;
border: 1px #ccc solid;
border-radius: 5px;
font-size: .65em; }
.login__credentials {
order: 0;
border: 0;
overflow: hidden;
padding: 0;
width: 260px;
text-align: left;
margin: 0 auto;
opacity: 0;
height: 0;
transition: height 1s .1s, opacity .25s 0s; }
.open ~ .login__credentials {
transition: height 1s 0s, opacity .5s .5s;
height: 140px;
opacity: 1; }
JS
let btt_zufalls = document.querySelector('.login__btt--zufalls');
btt_zufalls.addEventListener('click', function(){
this.classList.toggle('open');
this.textContent = [this.dataset.collapsedText, this.dataset.expandedText][+this.matches('.open')]
});
Конечный результат
![enter image description here](https://i.stack.imgur.com/lawhz.gif)