你可以使用 HTML、CSS 和 JavaScript 来创建时尚且动态的 Web 元素,比如构建的一个手风琴菜单。

当用户单击按钮时,手风琴菜单会展开和折叠。这是一种不必预先显示有关主题的所有信息的好方法,用户可以选择仅显示他们需要的信息。

在本教程中,我将向你展示如何构建一个简单的手风琴菜单,如下所示:

ezgif.com-gif-maker.gif

什么是手风琴菜单

在 UI 设计中,手风琴菜单是各种信息的垂直堆叠列表。对于每个列表,都有一个标记的标题指向相应的内容。默认情况下,每个列表的内容都是隐藏的。单击特定标签将展开其内容。

手风琴的一个非常常见的用例是保存一个常见问题列表,单击任何问题将切换/显示相应的答案。

如何使用 HTML、CSS 和 JS 构建手风琴菜单

我们将从定义 HTML 标记开始。如果你使用的是 VS Code 之类的 IDE 并且安装了 emmet,请创建一个新的 index.html 文件并键入 ! 然后按 enter 键。这应该为你的项目创建 HTML 样板代码。

或者,你可以将以下代码复制到 index.html 中,或从 Codepen 获取此项目的代码。

<!DOCTYPE html>
<html lang="en">
<head>
  <meta charset="UTF-8">
  <meta name="viewport" content="width=device-width, initial-scale=1.0">
  <meta http-equiv="X-UA-Compatible" content="ie=edge">
  <title>Document</title>
  <link rel="stylesheet" href="styles.css">
</head>
<body>

  <script src="app.js" type="text/javascript"></script>
</body>
</html>
HTML 页面结构

文件夹结构很简单。我们将创建一个名为 accordion 的文件夹。在文件夹内,我们将创建三个文件:index.htmlstyles.cssapp.js。如上所示,我们还将所有文件链接到我们的 HTML 标记中。

手风琴的 HTML 标记

对于菜单中的每个列表,我们将有两个 div——一个用于标签,另一个用于内容。

<body>
  <div class="accordion-body">
  <div class="accordion">
    <h1>Frequently Asked Questions</h1>
    <hr>
    <div class="container">
      <div class="label">What is HTML</div>
      <div class="content">Hypertext Markup Language (HTML) is a computer language that makes up most web pages and online applications. A hypertext is a text that is used to reference other pieces of text, while a markup language is a series of markings that tells web servers the style and structure of a document. HTML is very simple to learn and use.</div>
    </div>
    <hr>
    <div class="container">
      <div class="label">What is CSS?</div>
      <div class="content">CSS stands for Cascading Style Sheets. It is the language for describing the presentation of Web pages, including colours, layout, and fonts, thus making our web pages presentable to the users. CSS is designed to make style sheets for the web. It is independent of HTML and can be used with any XML-based markup language. CSS is popularly called the design language of the web.
</div>
    </div>
    <hr>
    <div class="container">
      <div class="label">What is JavaScript?</div>
      <div class="content">JavaScript is a scripting or programming language that allows you to implement complex features on web pages — every time a web page does more than just sit there and display static information for you to look at — displaying timely content updates, interactive maps, animated 2D/3D graphics, scrolling video jukeboxes, etc. — you can bet that JavaScript is probably involved. It is the third of the web trio.</div>
    </div>
    <hr>
    <div class="container">
      <div class="label">What is React?</div>
      <div class="content">React is a JavaScript library created for building fast and interactive user interfaces for web and mobile applications. It is an open-source, component-based, front-end library responsible only for the application’s view layer. In Model View Controller (MVC) architecture, the view layer is responsible for how the app looks and feels. React was created by Jordan Walke, a software engineer at Facebook. </div>
    </div>
    <hr>
    <div class="container">
      <div class="label">What is PHP?</div>
      <div class="content">PHP is a server-side and general-purpose scripting language that is especially suited for web development. PHP originally stood for Personal Home Page. However, now, it stands for Hypertext Preprocessor. It’s a recursive acronym because the first word itself is also an acronym.</div>
    </div>
    <hr>
    <div class="container">
      <div class="label">What is Node JS?</div>
      <div class="content">Node.js is an open-source, cross-platform, back-end JavaScript runtime environment that runs on the V8 engine and executes JavaScript code outside a web browser. Node.js lets developers use JavaScript to write command line tools and for server-side scripting—running scripts server-side to produce dynamic web page content before the page is sent to the user's web browser. Consequently, Node.js represents a "JavaScript everywhere" paradigm</div>
    </div>
    <hr>
  </div>
  </div>

  <script src="index.js" type="text/javascript"></script>
</body>
手风琴菜单标记

如果没有 CSS,我们的页面将看起来光秃秃的,就像这样:

htmlook.png

如何使用 CSS 设置手风琴菜单的样式

当然,我们希望我们的手风琴菜单看起来不错。是时候让一些 CSS 发挥作用了。我在代码中添加了一些注释来解释每个部分在做什么:

@import url('https://fonts.googleapis.com/css2?family=Rubik:wght@300&display=swap');

/* 将主体的背景颜色设置为蓝色,将字体设置为 Rubik */

body {
  background-color: #0A2344;
  font-family: 'rubik', sans-serif;
}

/* 将标题文本居中对齐 */
 
h1 {
  text-align: center;
}

/* 设置手风琴菜单的宽度,将顶部和底部的边距设置为 90px,左右边距设置为 auto */

.accordion {
  width: 800px;
  margin: 90px auto;
  color: black;
  background-color: white;
  padding: 45px 45px;
}

应用所有这些样式后,我们的手风琴菜单现在的样子如下:

withcss1.png
添加到手风琴菜单的样式

现在我们需要开始在内部做一些工作来设置它的功能。首先,我们将每个容器(包含标签和内容)的位置属性设置为 relative。

这意味着我们现在可以相对于它定位它的子级。

.accordion .container {
  position: relative;
  margin: 10px 10px;
}

/* 相对于 .container 定位标签,在顶部和底部添加填充并增加字体大小,也使 cursor 为 pointer */

.accordion .label {
  position: relative;
  padding: 10px 0;
  font-size: 30px;
  color: black;
  cursor: pointer;
}

你现在可以注意到下图中的差异:

withcss2.png

下一步是在每个列表的末尾附加一个小 “+” 号。这将让用户知道他们可以扩展该部分以了解/查看更多信息。

我们将使用 ::before 选择器来实现这一点。::before::after 选择器用于在指定元素之前或之后放置内容。

在这里,我们在标签前插入 “+”。但是我们将使用偏移属性 topright 将其放置在最右上角。


/* 将加号放置在距离右侧 5px 的位置,使用 transform 属性将其居中 */

.accordion .label::before {
  content: '+';
  color: black;
  position: absolute;
  top: 50%;
  right: -5px;
  font-size: 30px;
  transform: translateY(-50%);
}

/* 隐藏内容(高度:0),减小字体大小,对齐文本并添加过渡 */

.accordion .content {
  position: relative;
  background: white;
  height: 0;
  font-size: 20px;
  text-align: justify;
  width: 780px;
  overflow: hidden;
  transition: 0.5s;
}

/* 在内容之间添加一条水平线 */

.accordion hr {
  width: 100;
  margin-left: 0;
  border: 1px solid grey;
}

这将使一切变得更好。另外,请注意,每个列表的内容现在已被隐藏。

nowbig.png
手风琴菜单的内容现在被隐藏了

给手风琴菜单添加 JavaScript

现在,我们的手风琴菜单几乎是静态的。为了让容器在用户点击时显示内容,我们需要引入一些 JavaScript。

找到你的脚本 app.js,并输入以下代码:

const accordion = document.getElementsByClassName('container');

for (i=0; i<accordion.length; i++) {
  accordion[i].addEventListener('click', function () {
    this.classList.toggle('active')
  })
}

该脚本将通过 containerclassname 访问我们所有的列表。

然后我们将遍历列表。对于每个容器,我们只想为其注册一个事件侦听器。当它被点击时,我们希望在该元素上切换 “active” 类。

现在我们要测试这个效果。单击带有标签 What is HTML 的第一个容器,打开你的 DevTools(单击 F12),并在元素选项卡内检查它。

你应该找到在其上的 active 类:

active.png

再次单击该元素将从中删除 active 类。

如何完成应用程序

我们还需要做最后一件事,在样式表中创建一个活动类。我们将定义一旦 JavaScript 在容器上切换类,手风琴菜单的外观将是什么样的。


/* 活动时取消隐藏内容部分。设置高度 */

.accordion .container.active .content {
  height: 150px;
}

/* 激活后从加号变为负号 */

.accordion .container.active .label::before {
  content: '-';
  font-size: 30px;
}

这是我们的应用程序最终的外观和运行方式:

ezgif.com-gif-maker.gif
最终的样子

总结

在本教程中,我们使用 HTML、CSS 和 JavaScript 构建了一个手风琴菜单。

感谢你的关注。我希望你从本教程中学到了一些有用的东西。

如果你对此类内容感兴趣,请关注我的博客

祝你度过愉快的一周。

P/S:如果你正在学习 JavaScript,我创建了一本电子书,其中包含 50 个 JavaScript 主题的手绘数字笔记。在这里查看

原文:How to Build an Accordion Menu Using HTML, CSS and JavaScript,作者:Kingsley Ubah