javascript - 单击选项卡时过滤数据
问题描述
我有两个输入(标题和状态)和一个提交按钮。当我单击提交按钮时,我将输入值添加到表中。但是,表格有 3 个按钮;全部,活动且已完成。我想要做的是当我单击“活动”或“已完成”按钮时,该按钮应该处于活动状态并根据列表中的“状态”值过滤数据。(默认情况下应选择所有按钮并显示所有数据,无论其状态如何)
例如,在下图中,如果我单击“已完成”选项卡,该选项卡应该处于活动状态并且只显示 Cook。
这是我几天前尝试解决的 DOM 挑战,但仍然无法解决。我不允许更改 HTML 中的任何内容。只有普通的 JavaScript。
HTML
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8" />
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
<link
href="https://cdn.jsdelivr.net/npm/@ionic/core/css/ionic.bundle.css"
rel="stylesheet"
/>
<script
type="module"
src="https://cdn.jsdelivr.net/npm/@ionic/core/dist/ionic/ionic.esm.js"
></script>
<script
nomodule
src="https://cdn.jsdelivr.net/npm/@ionic/core/dist/ionic/ionic.js"
></script>
<script src="https://cdn.jsdelivr.net/npm/h8k-components@latest/dist/h8k-components.js"></script>
<link
rel="stylesheet"
href="https://cdn.jsdelivr.net/npm/h8k-design@latest/dist/index.css"
/>
<link rel="stylesheet" href="./styles.css" />
<script type="module" src="./index.js"></script>
<title>Document</title>
</head>
<body>
<div id="root">
<h8k-navbar header="Notes"></h8k-navbar>
<div class="layout-column align-items-center justify-content-start">
<section
class="layout-row align-items-center justify-content-center mt-30"
>
<input
data-testid="input-note-name"
type="text"
class="large mx-8"
placeholder="Note Title"
/>
<input
data-testid="input-note-status"
type="text"
class="large mx-8"
placeholder="Note Status"
/>
<button class="" data-testid="submit-button">Add Note</button>
</section>
<div class="mt-50">
<ul class="tabs">
<li class="tab-item slude-up-fade-in" data-testid="allButton">
All
</li>
<li class="tab-item slude-up-fade-in" data-testid="activeButton">
Active
</li>
<li class="tab-item slude-up-fade-in" data-testid="completedButton">
Completed
</li>
</ul>
</div>
<div class="card w-40 pt-30 pb-8">
<table>
<thead>
<tr>
<th>Title</th>
<th>Status</th>
</tr>
</thead>
<tbody data-testid="noteList"></tbody>
</table>
</div>
</div>
</div>
</body>
</html>
CSS
.tabs {
list-style: none;
display: flex;
margin: 0;
padding: 0;
}
.tabs .tab-item {
min-width: 88px;
display: flex;
flex-direction: row;
align-items: center;
justify-content: center;
position: relative;
cursor: pointer;
padding: 20px 16px;
color: var(--heading-color);
}
.tabs .tab-item::before {
content: '';
position: absolute;
top: 0;
width: 100%;
height: 2px;
background: var(--primary-color);
opacity: 0;
transition: opacity 0.3s ease-in-out;
}
.tabs .tab-item:active {
background: #fff;
position: relative;
color: black;
}
.tabs .tab-item:active::before {
opacity: 1;
}
table tbody tr td {
font-weight: bold;
font-size: 16px;
height: 21px;
padding: 1.6rem;
}
JavaScript
const nameInput = document.querySelector('[data-testid="input-note-name"]');
const statusInput = document.querySelector('[data-testid="input-note-status"]');
const submitButton = document.querySelector('[data-testid="submit-button"]');
const allButton = document.querySelector('[data-testid="allButton"]');
const activeButton = document.querySelector('[data-testid="activeButton"]');
const completedButton = document.querySelector(
'[data-testid="completedButton"]'
);
const noteList = document.querySelector('[data-testid="noteList"]');
const tabs = document.querySelector('.tabs');
submitButton.addEventListener('click', () => {
console.log('Hey');
const titleNode = document.createTextNode(nameInput.value);
const statusNode = document.createTextNode(statusInput.value);
const trEl = document.createElement('tr');
const tdEl = document.createElement('td');
const tdEl2 = document.createElement('td');
trEl.appendChild(tdEl);
tdEl.appendChild(titleNode);
trEl.appendChild(tdEl2);
tdEl2.appendChild(statusNode);
noteList.appendChild(trEl);
});
解决方案
以防万一您不尝试创建尽可能多的代码行并且您不想用尽可能多的变量填充全局空间,那么也许以下内容也适用于您:
const tb=document.querySelector("[data-testid=noteList]");
document.querySelector("button").onclick=ev=> // add an entry
tb.innerHTML+="<tr><td>"
+[...ev.target.parentNode.children]
.filter(e=>e.tagName==="INPUT")
.map(e=>e.value)
.join("</td><td>")+"</td></tr>";
document.querySelector("ul.tabs").onclick=ev=>{ // filter buttons
if (ev.target.tagName==="LI"){
let sel=ev.target.textContent.trim().toLowerCase();
[...tb.children].forEach(tr=>tr.style.display=
sel=="all" || sel===tr.children[1].textContent.trim().toLowerCase()
? "" : "none" )
}}
.tabs {
list-style: none;
display: flex;
margin: 0;
padding: 0;
}
.tabs .tab-item {
min-width: 88px;
display: flex;
flex-direction: row;
align-items: center;
justify-content: center;
position: relative;
cursor: pointer;
padding: 20px 16px;
color: var(--heading-color);
}
.tabs .tab-item::before {
content: '';
position: absolute;
top: 0;
width: 100%;
height: 2px;
background: var(--primary-color);
opacity: 0;
transition: opacity 0.3s ease-in-out;
}
.tabs .tab-item:active {
background: #fff;
position: relative;
color: black;
}
.tabs .tab-item:active::before {
opacity: 1;
}
table tbody tr td {
font-weight: bold;
font-size: 16px;
height: 1px;
padding: 2px 20px;
}
<div id="root">
<h8k-navbar header="Notes"></h8k-navbar>
<div class="layout-column align-items-center justify-content-start">
<section class="layout-row align-items-center justify-content-center mt-30">
<input data-testid="input-note-name" type="text" class="large mx-8" placeholder="Note Title" />
<input data-testid="input-note-status" type="text" class="large mx-8" placeholder="Note Status" />
<button class="" data-testid="submit-button">Add Note</button>
</section>
<div class="mt-50">
<ul class="tabs">
<li class="tab-item slude-up-fade-in" data-testid="allButton">
All
</li>
<li class="tab-item slude-up-fade-in" data-testid="activeButton">
Active
</li>
<li class="tab-item slude-up-fade-in" data-testid="completedButton">
Completed
</li>
</ul>
</div>
<div class="card w-40 pt-30 pb-8">
<table>
<thead>
<tr>
<th>Title</th>
<th>Status</th>
</tr>
</thead>
<tbody data-testid="noteList"></tbody>
</table>
</div>
</div>
</div>
<td>
我还冒昧地删除了元素 ( )周围的一些随机空白,padding: 1.6rem
因为我宁愿看到内容而不是空白。
推荐阅读
- ios - React Native iOS Swift 错误:无法构建 Objective-C 模块“React”
- vue.js - Axios 发布请求导致 400 - 错误请求
- node.js - nvm 或 npm,安装包
- javascript - 如何将使用的单选按钮的回声值获取到 JavaScript
- c - 如何避免函数参数中具有不同结构类型的重复代码?
- gradle - 从 gradle 开始:目录结构
- android - 如何根据BottomAppBar kotlin andorid中的FAB提供适当的边距?
- elixir - Task.async/1 中没有匹配的函数子句
- bash - 在 curl 中传递变量以将消息发送到 slack
- apache - 使用 .htaccess 将所有 .php 请求重定向到 .html