HTML表单输入元素可视地定位在表单外部

问题描述 投票:1回答:2

我有高度设置为0的容器,其中包含表单。

<div class="container">
    <div role="button" data-define="show.element">show register form</div>
    <div class="box-wrapper">
      <div class="box">
        <form>
          <input class="form-element" type="text" name="login" placeholder="login"/>
          <input class="form-element" type="password" name="password" placeholder="password"/>
          <input class="form-element-submit" type="submit"/>
        </form>
      </div>
    </div>
  </div>

我想要实现的是,在使用“show register form”文本单击按钮后,从“box-wrapper”元素(最初将显示属性visibility设置为hidden)滑出的形式。点击我正在添加css类,它改变了box元素的高度,并将box-wrapper元素的属性可见性设置为“visible”。然而,表单输入元素不是像我想要的那样从盒子包装元素“滑出”,它们似乎最初被放置在“容器”元素的顶部。这是我的CSS代码:

body {
  background: #34495E;
}
.container {
  position: absolute;
  left: 50%;
  top: 50%;
  background: #191919;
  transform: translate(-50%, -50%);
  width: 400px;
  height: 400px;
  display: flex;
  flex-direction: column;
  align-items: center;
  justify-content: center;
}
div[data-define="show.element"] {
  width: 150px;
  text-align: center;
  background: none;
  border: 2px solid #3498db;
  border-radius: 15px;
  color: white;
  padding: 5px 10px;
  transition: 0.25s;
  outline: none;
}
div[data-define="show.element"]:hover {
  cursor: pointer;
  border-color: #2ECC71;
}
div[data-define="show.element"]:active {
  transform: translatey(2px);
}
.box {
  width: 300px;
  height: 0;
  border: none;
  transition: 1s;

  &-wrapper {
    position: relative;
    margin: 15px auto;
    width: 300px;
    height: 300px;
    visibility: hidden;

    &-visible {
      visibility: visible;
    }
  }
  &-active {
    height: 300px;
  }
}
form {
  height: 100%;
  display: flex;
  flex-direction: column;
  justify-content: center;
  align-items: center;
}
.form-element {
  margin: 10px auto;
  width: 150px;
  background: none;
  border: 2px solid #3498db;
  border-radius: 15px;
  color: white;
  padding: 5px 10px;
  transition: width 0.25s;
  text-align: center;
  outline: none;

  &-submit {
    margin: 10px auto;
    width: 150px;
    background: none;
    border: 2px solid #3498db;
    border-radius: 15px;
    color: white;
    padding: 5px 10px;
    transition: 0.25s;
    outline: none;
  }
}
.form-element:focus {
  width: 250px;
  border-color: #2ECC71;
}
.form-element-submit:hover {
  background: #2ECC71;
}

工作代码:https://codepen.io/Furmanus/pen/oVqKJG?editors=0100

我做错了什么?提前感谢您的帮助。

html css forms flexbox position
2个回答
1
投票

使身体相对。将z-index和background属性添加到show.element按钮。将框高度设置为20px,这样box-wrapper似乎来自show.element按钮。

body {
  background: #34495E;
  position: relative;
}
.container {
    position: absolute;
    left: 50%;
    top: 50%;
    margin-left: -12.5%;
    background: #191919;
    width: 400px;
    height: 400px;
    display: flex;
    flex-direction: column;
    align-items: center;
    justify-content: center;
}
div[data-define="show.element"] {
    width: 150px;
    z-index: 1;
    text-align: center;
    background: #191919;
    border: 2px solid #3498db;
    border-radius: 15px;
    color: white;
    padding: 5px 10px;
    transition: 0.1s;
    outline: none;
}
.box {
  width: 300px;
  height: 20px;
}

更新了codepen - https://codepen.io/anon/pen/QorQrj?editors=0100

编辑 - 啊像@kukkuz提到的那样,辩解内容是问题所在。当父级的高度为0但是对齐内容为中心时。它尝试垂直居中高度大于0的子元素,并最终向上移动到高度为0的父级的垂直居中。

删除justify-content将按照您的方式定位输入元素,但幻灯片动画存在问题,因为输入元素保留在它们应该的位置,并且转换没有区别,因为这些元素不受影响。

因此默认情况下,输入元素的设置,边距,边框,高度,填充为0。点击“显示注册表单”,将这些属性更新为它们应该是什么。

https://codepen.io/anon/pen/QorQrj?editors=0100


1
投票

你所要做的就是使用buttonbox-wrapper带到堆叠环境中的z-index上方。所以将z-index: 1添加到button - 因为z-index仅适用于定位元素(元素不应该具有静态位置),现在它将起作用。您可以阅读更多关于z-index and stacking context here的信息。

现在为button添加一个背景,以便我们可以直观地了解深度 - 请参阅下面的演示和updated codepen

const button = document.querySelector('div[role="button"]');
const submit = document.querySelector('input[type="submit"]');
const form = document.querySelector('form');
const box = document.querySelector('.box');
const boxWrapper = document.querySelector('.box-wrapper');
let isVisible = false;

button.addEventListener('click', () => {
  if (isVisible) {
    box.classList.remove('box-active');
    boxWrapper.classList.remove('box-wrapper-visible');
    isVisible = false;
  } else {
    box.classList.add('box-active');
    boxWrapper.classList.add('box-wrapper-visible');
    isVisible = true;
  }
});
form.addEventListener('submit', e => {
  e.preventDefault();
});
body {
  background: #34495E;
}
.container {
  position: absolute;
  left: 50%;
  top: 50%;
  background: #191919;
  transform: translate(-50%, -50%);
  width: 400px;
  height: 400px;
  display: flex;
  flex-direction: column;
  align-items: center;
  justify-content: center;
}
div[data-define="show.element"] {
  width: 150px;
  text-align: center;
  background: #191919; /* background added */
  border: 2px solid #3498db;
  border-radius: 15px;
  color: white;
  padding: 5px 10px;
  transition: 0.1s;
  outline: none;
  position: relative; /* positioned the element */
  z-index: 1; /* added z-index */
}
div[data-define="show.element"]:hover {
  cursor: pointer;
  border-color: #2ECC71;
}
div[data-define="show.element"]:active {
  transform: translatey(2px);
}
.box {
  width: 300px;
  height: 0;
  border: none;
  transition: 1s;
}
.box-wrapper {
  position: relative;
  margin: 15px auto;
  width: 300px;
  height: 300px;
  visibility: hidden;
}
.box-wrapper-visible {
  visibility: visible;
}
.box-active {
  height: 300px;
}
form {
  height: 100%;
  display: flex;
  flex-direction: column;
  justify-content: center;
  align-items: center;
}
.form-element {
  margin: 10px auto;
  width: 150px;
  background: none;
  border: 2px solid #3498db;
  border-radius: 15px;
  color: white;
  padding: 5px 10px;
  transition: width 0.25s;
  text-align: center;
  outline: none;
}
.form-element-submit {
  margin: 10px auto;
  width: 150px;
  background: none;
  border: 2px solid #3498db;
  border-radius: 15px;
  color: white;
  padding: 5px 10px;
  transition: 0.25s;
  outline: none;
}
.form-element:focus {
  width: 250px;
  border-color: #2ECC71;
}
.form-element-submit:hover {
  background: #2ECC71;
}
<body>
  <div class="container">
    <div role="button" data-define="show.element">show register form</div>
    <div class="box-wrapper">
      <div class="box">
        <form>
          <input class="form-element" type="text" name="login" placeholder="login"/>
          <input class="form-element" type="password" name="password" placeholder="password"/>
          <input class="form-element-submit" type="submit"/>
        </form>
      </div>
    </div>
  </div>
</body>

为了解决放置在container顶部而不是从box-wrapper顶部的表单元素的问题 - 看看当我向min-height: 0元素添加input时会发生什么:

const button = document.querySelector('div[role="button"]');
const submit = document.querySelector('input[type="submit"]');
const form = document.querySelector('form');
const box = document.querySelector('.box');
const boxWrapper = document.querySelector('.box-wrapper');
let isVisible = false;

button.addEventListener('click', () => {
  if (isVisible) {
    box.classList.remove('box-active');
    boxWrapper.classList.remove('box-wrapper-visible');
    isVisible = false;
  } else {
    box.classList.add('box-active');
    boxWrapper.classList.add('box-wrapper-visible');
    isVisible = true;
  }
});
form.addEventListener('submit', e => {
  e.preventDefault();
});
body {
  background: #34495E;
}
.container {
  position: absolute;
  left: 50%;
  top: 50%;
  background: #191919;
  transform: translate(-50%, -50%);
  width: 400px;
  height: 400px;
  display: flex;
  flex-direction: column;
  align-items: center;
  justify-content: center;
}
div[data-define="show.element"] {
  width: 150px;
  text-align: center;
  background: #191919; /* background added */
  border: 2px solid #3498db;
  border-radius: 15px;
  color: white;
  padding: 5px 10px;
  transition: 0.1s;
  outline: none;
  position: relative; /* positioned the element */
  z-index: 1; /* added z-index */
}
div[data-define="show.element"]:hover {
  cursor: pointer;
  border-color: #2ECC71;
}
div[data-define="show.element"]:active {
  transform: translatey(2px);
}
.box {
  width: 300px;
  height: 0;
  border: none;
  transition: 1s;
}
.box-wrapper {
  position: relative;
  margin: 15px auto;
  width: 300px;
  height: 300px;
  visibility: hidden;
}
.box-wrapper-visible {
  visibility: visible;
}
.box-active {
  height: 300px;
}
form {
  height: 100%;
  display: flex;
  flex-direction: column;
  justify-content: center;
  align-items: center;
}
.form-element {
  margin: 10px auto;
  width: 150px;
  background: none;
  border: 2px solid #3498db;
  border-radius: 15px;
  color: white;
  padding: 5px 10px;
  transition: width 0.25s;
  text-align: center;
  outline: none;
  min-height: 0; /* added */
}
.form-element-submit {
  margin: 10px auto;
  width: 150px;
  background: none;
  border: 2px solid #3498db;
  border-radius: 15px;
  color: white;
  padding: 5px 10px;
  transition: 0.25s;
  outline: none;
}
.form-element:focus {
  width: 250px;
  border-color: #2ECC71;
}
.form-element-submit:hover {
  background: #2ECC71;
}
<body>
  <div class="container">
    <div role="button" data-define="show.element">show register form</div>
    <div class="box-wrapper">
      <div class="box">
        <form>
          <input class="form-element" type="text" name="login" placeholder="login"/>
          <input class="form-element" type="password" name="password" placeholder="password"/>
          <input class="form-element-submit" type="submit"/>
        </form>
      </div>
    </div>
  </div>
</body>

问题显然是由于列弹性框的默认min-height: auto - 弹性项目在弹性方向上的内容占用的空间最小。

轻微向顶部转移的另一个原因是因为你的justify-content: center元素有form

© www.soinside.com 2019 - 2024. All rights reserved.