在之前的教程中,我向您展示了如何使用 flexbox 构建响应式表单以及如何设置表单元素的样式。今天,我们将继续进入“表单”世界,学习从头开始创建响应式手工 svg 表单。
这是我们要构建的表单:
See the Pen A Responsive Handmade SVG Form by Envato Tuts+ (@tutsplus) on CodePen.
1. 从页面标记开始
我们将从一个 SVG 和一个form元素开始:
<svg style="display:none;">...</svg>
<form class="handmade-form">...</form>
SVG 精灵
对于我们的表格,我们将需要一堆手工插图。令人高兴的是,Tuts+ 的网页设计编辑Ian Yates为我们创作了一些精美的插图。谢谢你,伊恩:)
与我们在之前的教程中所做的类似,我们将创建一个 SVG 精灵并将所有绘图嵌入其中。然后,在表单内部,我们将在需要时通过调用 use 元素来呈现目标图标。
这是 SVG 精灵的标记:
<svg style="display:none;">
<symbol id="input1" viewBox="0 0 347.11 49.7" preserveAspectRatio="none">...</symbol>
<symbol id="input2" viewBox="0 0 345.27 56.51" preserveAspectRatio="none">...</symbol>
<symbol id="input3" viewBox="0 0 344.17 48.76" preserveAspectRatio="none">...</symbol>
<symbol id="input4" viewBox="0 0 347.13 54.94" preserveAspectRatio="none">...</symbol>
<symbol id="textarea" viewBox="0 0 704.84 271.56" preserveAspectRatio="none">...</symbol>
<symbol id="fieldset" viewBox="0 0 998.06 602.62" preserveAspectRatio="none">...</symbol>
<symbol id="checkbox_empty" viewBox="0 0 33.18 33.34">...</symbol>
<symbol id="checkmark" viewBox="0 0 37.92 33.3" preserveAspectRatio="none">...</symbol>
<symbol id="button" viewBox="0 0 256.6 60.02" preserveAspectRatio="none">...</symbol>
请注意 preserveAspectRatio="none" 我们附加到大多数插图的属性。我们这样做是因为,正如我们稍后会看到的,我们的图标会缩放并松开它们的初始尺寸。
形式
该表单将由一个标题和一个无序列表组成。另外,我们将使用 a .container 设置表单的最大宽度并将其内容水平居中:
<form class="handmade-form">
<div class="container">
<h1>Contact us</h1>
<ul>
<li class="grid grid-2">...</li>
<li class="grid grid-2">...</li>
<li class="form-wrapper">...</li>
<li class="form-wrapper">...</li>
<li class="grid grid-3">...</li>
</ul>
</div>
</form>
如您所见,上面的每个列表项都包含一个或多个类。或者,出于可读性的原因,我们可以创建一个额外的子元素并将这些类传递给它,如下所示:
<li> <div class="grid grid-2">...</div></li>
在列表中,我们将放置 SVG 和表单元素。
第一个列表项将包括两个必需的输入字段及其 SVG:
<div class="form-wrapper">
<input type="text" placeholder="Name*" required>
<svg>
<use xlink:href="#input1"></use>
</svg>
</div>
<div class="form-wrapper">
<input type="text" placeholder="Surname*" required>
<svg>
<use xlink:href="#input2"></use>
</svg>
</div>
同样,第二个列表项也将包含两个输入字段及其 SVG:
<div class="form-wrapper">
<input type="email" placeholder="Email*" required>
<svg>
<use xlink:href="#input3"></use>
</svg>
</div>
<div class="form-wrapper">
<input type="tel" placeholder="Phone">
<svg>
<use xlink:href="#input4"></use>
</svg>
</div>
在第三个列表项中,我们将放置一个 textarea 及其相关插图:
<textarea placeholder="Message"></textarea>
<svg>
<use xlink:href="#textarea"></use>
</svg>
第四个列表项将包含一个fieldset元素。在其中,我们将放置一个legend 元素,一个带有两个单选按钮的列表以及它们的 SVG 及其相关的 SVG:
<fieldset>
<legend>Select preferred method of contact</legend>
<ul class="checkbox-list">
<li>
<input type="radio" id="email" name="contact-method" checked>
<label for="email">
<svg>
<use xlink:href="#checkbox_empty"></use>
</svg>
<svg class="checkmark">
<use xlink:href="#checkmark"></use>
</svg>
By Email
</label>
</li>
<li>
<input type="radio" id="phone" name="contact-method">
<label for="phone">
<svg>
<use xlink:href="#checkbox_empty"></use>
</svg>
<svg class="checkmark">
<use xlink:href="#checkmark"></use>
</svg>
By Phone
</label>
</li>
</ul>
<svg>
<use xlink:href="#fieldset"></use>
</svg>
</fieldset>
最后,第五个列表项将包含提交和重置按钮以及它们的 SVG:
<div class="form-wrapper">
<button type="submit">SUBMIT</button>
<svg>
<use xlink:href="#button"></use>
</svg>
</div>
<div class="form-wrapper">
<button type="reset">RESET</button>
<svg>
<use xlink:href="#button"></use>
</svg>
</div>
2. 定义一些基本样式
在仔细查看各个表单元素之前,让我们先定义一些基本的 css 样式。这些将包括取自Envato Elements的自定义字体、一些自定义变量和一些重置规则:
@font-face {
font-family: "Summer";
src: url(SummerFont-Regular.woff);
}
@font-face {
font-family: "Summer Bold";
src: url(SummerFont-Bold.woff);
}
:root {
--white: #fff;
--red: #e31b23;
}
* {
padding: 0;
margin: 0;
border: none;
box-sizing: border-box;
}
input,
textarea,
button {
font-family: inherit;
font-size: 100%;
background: none;
outline: none;
}
[type="radio"] {
position: absolute;
left: -9999px;
}
button,
label {
cursor: pointer;
}
textarea {
resize: none;
}
ul {
list-style: none;
}
body {
font: 32px/1.2 "Summer";
margin: 1.5rem 0;
}
注意:为简单起见,我不会 在本教程中介绍所有CSS 规则。您可以通过单击 演示项目的CSS选项卡来检查其余部分。
3. 构建表单布局
在小屏幕上,我们所有的表单元素都将被堆叠:
但是,在宽度为 600 像素及以上的视口上,表单布局会发生变化。进一步来说:
我们将input前两行的 s 排列成两个等宽的列。
每个按钮将覆盖父行宽度的三分之一。
感谢 CSS Grid,我们可以轻松构建所需的多列布局。首先,我们将.handmade-form .grid容器设置为网格。然后,我们将使用grid-2和grid-3辅助类来定义网格列的数量:
@media screen and (min-width: 600px) {
.handmade-form .grid {
display: grid;
grid-gap: 1.5rem;
}
.handmade-form .grid-2 {
grid-template-columns: repeat(2, 1fr);
}
.handmade-form .grid-3 {
grid-template-columns: repeat(3, 1fr);
}
}
所有这些规则都放置在媒体查询中,因此它们只会在 600 像素及以上宽的视口上生效。
4. 样式化表单元素
整理好结构后,下一步是为所有表单元素指定一些初始的审美风格:
/*CUSTOM VARIABLES HERE*/
.handmade-form input:not([type="radio"]),
.handmade-form textarea,
.handmade-form button {
width: 100%;
}
.handmade-form input:not([type="radio"]),
.handmade-form textarea,
.handmade-form fieldset {
padding: 15px;
}
.handmade-form textarea {
height: 200px;
vertical-align: top;
}
.handmade-form legend {
padding-top: 15px;
margin: 0 auto;
}
.handmade-form ::placeholder {
color: inherit;
/*Fix opacity issue on Firefox*/
opacity: 1;
}
.handmade-form button {
font-family: "Summer Bold";
color: var(--white);
padding: 5px 10px;
}
放置插图
本练习的下一个也是最具挑战性的部分是相对于其关联的表单元素定位插图。为此,我们将使用该position属性。另一种实现方式可能是将绘图设置为背景图像。但是,我不是这个实现的忠实粉丝,因为它需要额外的操作来使图像适应各种屏幕。
让我们注意我们的计划:
SVG 将是绝对定位的元素。
它们将与表单控件位于相同的位置并具有相同的尺寸。这就是为什么我们之前将它们设置 preserveAspectRatio 为 none.
表单控件应该是可聚焦的,所以我们会给它们一个更高的z-index.
以下是此行为所需的样式:
.handmade-form .form-wrapper,
.handmade-form input:not([type="radio"]),
.handmade-form textarea,
.handmade-form button,
.handmade-form .checkbox-list label {
position: relative;
}
.handmade-form input:not([type="radio"]),
.handmade-form textarea,
.handmade-form button,
.handmade-form .checkbox-list label {
z-index: 1;
}
.handmade-form .form-wrapper svg {
position: absolute;
top: 0;
left: 0;
width: 100%;
height: 100%;
}
5.创建自定义单选按钮
为了创建我们的自定义单选按钮,我们将再次利用“CSS checkbox hack 技术”。
如果您再次查看标记部分,您会注意到该fieldset元素包含.checkbox-list列表。在每个标签内,有两个 SVG。第一个描述相关单选按钮的未选中状态,而另一个描述其选中状态。
单选按钮应该放在一行上,所以我们将把它.checkbox-list变成一个弹性容器。此外,我们绝对会相对于它们的标签定位它们并给它们一些固定尺寸(20px x 20px)。
当单选按钮更改其状态时,描述其选中状态的 SVG 将被动画化。为了达到这个效果,我们将使用我们在最近的教程中广泛介绍的stroke-dasharray和属性。stroke-dashoffset
以下是对应的样式:
.handmade-form .checkbox-list {
display: flex;
justify-content: center;
}
.handmade-form .checkbox-list li:not(:last-child) {
margin-right: 50px;
}
.handmade-form .checkbox-list label svg {
top: 50%;
left: -25px;
width: 20px;
height: 20px;
transform: translateY(-50%);
}
.handmade-form .checkbox-list label .checkmark {
stroke-dasharray: 233.69552612304688;
stroke-dashoffset: 233.69552612304688;
transition: stroke-dashoffset 0.5s linear;
}
.handmade-form [type="radio"]:checked + label .checkmark {
stroke-dashoffset: 0;
}
注意: 即使我将stroke-*属性附加到父 SVG 而不是它的path,效果仍然有效,因为这些属性是继承的。
结论
就是这样,伙计们!在本教程中,我们设法从头开始构建响应式手工 SVG 表单。我希望这个练习能帮助你学到一些新东西,并启发你在即将到来的项目中使用它。
以下是我们构建的内容的提醒:
See the Pen A Responsive Handmade SVG Form by Envato Tuts+ (@tutsplus) on CodePen.
在即将发布的教程中,我们将更进一步,讨论如何通过将其合并到流行的 wordpress 联系表单插件中来使此表单动态化。敬请关注!
一如既往,非常感谢您的阅读!
- SVG 精灵
- 形式
- 放置插图