Javascript [object HTMLCollection] [closed] - javascript

Closed. This question needs debugging details. It is not currently accepting answers.
Edit the question to include desired behavior, a specific problem or error, and the shortest code necessary to reproduce the problem. This will help others answer the question.
Closed 3 years ago.
Improve this question
Using Javascript I am creating a list website (as a side-project).
I use the code:
var myNodelist = document.getElementsByTagName("LI");
and that works, but
localStorage.setItem("myNodelist", document.getElementsByTagName("LI"));
doesn't. it just returns [object HTMLCollection]. Does anyone know why?
// Create a "close" button and append it to each list item
var myNodelist = document.getElementsByTagName("LI");
var i;
for (i = 0; i < myNodelist.length; i++) {
var span = document.createElement("SPAN");
var txt = document.createTextNode("\u00D7");
span.className = "close";
span.appendChild(txt);
myNodelist[i].appendChild(span);
}
// Click on a close button to hide the current list item
var close = document.getElementsByClassName("close");
var i;
for (i = 0; i < close.length; i++) {
close[i].onclick = function() {
var div = this.parentElement;
div.style.display = "none";
}
}
// Add a "checked" symbol when clicking on a list item
var list = document.querySelector('ul');
list.addEventListener('click', function(ev) {
if (ev.target.tagName === 'LI') {
ev.target.classList.toggle('checked');
}
}, false);
// Create a new list item when clicking on the "Add" button
function newElement() {
var li = document.createElement("li");
var inputValue = document.getElementById("myInput").value;
var t = document.createTextNode(inputValue);
li.appendChild(t);
if (inputValue === '') {
alert("You must write something!");
} else {
document.getElementById("myUL").appendChild(li);
}
document.getElementById("myInput").value = "";
var span = document.createElement("SPAN");
var txt = document.createTextNode("\u00D7");
span.className = "close";
span.appendChild(txt);
li.appendChild(span);
for (i = 0; i < close.length; i++) {
close[i].onclick = function() {
var div = this.parentElement;
div.style.display = "none";
}
}
}
<!DOCTYPE html>
<html>
<head>
<meta name="viewport" content="width=device-width, initial-scale=1">
<style>
body {
margin: 0;
min-width: 250px;
}
/* Include the padding and border in an element's total width and height */
* {
box-sizing: border-box;
}
/* Remove margins and padding from the list */
ul {
margin: 0;
padding: 0;
}
/* Style the list items */
ul li {
cursor: pointer;
position: relative;
padding: 12px 8px 12px 40px;
list-style-type: none;
background: #eee;
font-size: 18px;
transition: 0.2s;
/* make the list items unselectable */
-webkit-user-select: none;
-moz-user-select: none;
-ms-user-select: none;
user-select: none;
}
/* Set all odd list items to a different color (zebra-stripes) */
ul li:nth-child(odd) {
background: #f9f9f9;
}
/* Darker background-color on hover */
ul li:hover {
background: #ddd;
}
/* When clicked on, add a background color and strike out text */
ul li.checked {
background: #888;
color: #fff;
text-decoration: line-through;
}
/* Add a "checked" mark when clicked on */
ul li.checked::before {
content: '';
position: absolute;
border-color: #fff;
border-style: solid;
border-width: 0 2px 2px 0;
top: 10px;
left: 16px;
transform: rotate(45deg);
height: 15px;
width: 7px;
}
/* Style the close button */
.close {
position: absolute;
right: 0;
top: 0;
padding: 12px 16px 12px 16px;
}
.close:hover {
background-color: #168e00;
color: white;
}
/* Style the header */
.header {
background-color: #168e00;
padding: 30px 40px;
color: white;
text-align: center;
}
/* Clear floats after the header */
.header:after {
content: "";
display: table;
clear: both;
}
/* Style the input */
input {
margin: 0;
border: none;
border-radius: 0;
width: 75%;
padding: 10px;
float: left;
font-size: 16px;
}
/* Style the "Add" button */
.addBtn {
padding: 10px;
width: 25%;
background: #d9d9d9;
color: #555;
float: left;
text-align: center;
font-size: 16px;
cursor: pointer;
transition: 0.3s;
border-radius: 0;
}
.addBtn:hover {
background-color: #bbb;
}
</style>
</head>
<body>
<div id="myDIV" class="header">
<h2 style="margin:5px">Groceries:</h2>
<input type="text" id="myInput" placeholder="Title...">
<span onclick="newElement()" class="addBtn">Add</span>
</div>
<ul id="myUL">
</ul>
</body>
</html>

If you write var Lists = document.getElementsByTagName("List"); in your console.log(list) you will see the list of elements that you need right ?
The console.log also shows array the same way ,each element of an array is print to the log without you having to write a for() loop.
However if you want to use the array you have to write the for loop
[object HTMLCollection]
means that there is an array of HTML objects, To work with the data you have to use a for loop or array methods so before storing it in local storage
Try Make an array with the object collection with
var arr = Array.from(htmlCollection);
Then save as is or convert to json string with
var myJsonString = JSON.stringify(arr);
I trust this helps

First: its better if you use id to find the dom element from DOM API.
Second: you need to use .innerText to access the text content of list item.
<ul>
<li id="item">hello</li>
</ul>
localStorage.setItem("myNodelist",document.getElementById("item").innerText);

Related

javascript on a webpage displaying text wrongly

I have JS code on a webpage that loads questions in from mysql db and displays the text . What happens is that it cuts off words at the end of the line and continues the word on the next line at the start. So all text across the screen starts/ends at the same point.
This seems to be the code where it displays the text.
For example the text will look like at the end of a line 'cont' and then on next line at the start 'inue'.
How do i fix this?
var questions = <?=$questions;?>;
// Initialize variables
//------------------------------------------------------------------
var tags;
var tagsClass = '';
var liTagsid = [];
var correctAns = 0;
var isscorrect = 0;
var quizPage = 1;
var currentIndex = 0;
var currentQuestion = questions[currentIndex];
var prevousQuestion;
var previousIndex = 0;
var ulTag = document.getElementsByClassName('ulclass')[0];
var button = document.getElementById('submit');
var questionTitle = document.getElementById('question');
//save class name so it can be reused easily
//if I want to change it, I have to change it one place
var classHighlight = 'selected';
// Display Answers and hightlight selected item
//------------------------------------------------------------------
function showQuestions (){
document.body.scrollTop = 0; // For Safari
document.documentElement.scrollTop = 0; // For Chrome, Firefox, IE and Opera
if (currentIndex != 0) {
// create again submit button only for next pages
ulTag.innerHTML ='';
button.innerHTML = 'Submit';
button.className = 'submit';
button.id = 'submit';
if(quizPage<=questions.length){
//update the number of questions displayed
document.getElementById('quizNumber').innerHTML = quizPage;
}
}
//Display Results in the final page
if (currentIndex == (questions.length)) {
ulTag.innerHTML = '';
document.getElementById('question').innerHTML = '';
if(button.id == 'submit'){
button.className = 'buttonload';
button.innerHTML = '<i class="fa fa-spinner fa-spin"></i>Loading';
}
showResults();
return
}
questionTitle.innerHTML = "Question No:" + quizPage + " "+currentQuestion.question.category_name +"<br/>"+ currentQuestion.question.text;
if(currentQuestion.question.filename !== ''){
var br = document.createElement('br');
questionTitle .appendChild(br);
var img = document.createElement('img');
img.src = currentQuestion.question.filename;
img.className = 'imagecenter';
img.width = 750;
img.height = 350;
questionTitle .appendChild(img);
}
// create a for loop to generate the options and display them in the page
for (var i = 0; i < currentQuestion.options.length; i++) {
// creating options
var newAns = document.createElement('li');
newAns.id = 'ans'+ (i+1);
newAns.className = "notSelected listyle";
var textAns = document.createTextNode(currentQuestion.options[i].optiontext);
newAns.appendChild(textAns);
if(currentQuestion.options[i].file !== ''){
var br = document.createElement('br');
newAns .appendChild(br);
var img1 = document.createElement('img');
img1.src = currentQuestion.options[i].file;
img1.className = 'optionimg';
img1.width = 250;
img1.height = 250;
newAns .appendChild(img1);
newAns .appendChild(br);
}
var addNewAnsHere = document.getElementById('options');
addNewAnsHere.appendChild(newAns);
}
//.click() will return the result of $('.notSelected')
var $liTags = $('.notSelected').click(function(list) {
list.preventDefault();
//run removeClass on every element
//if the elements are not static, you might want to rerun $('.notSelected')
//instead of the saved $litTags
$liTags.removeClass(classHighlight);
//add the class to the currently clicked element (this)
$(this).addClass(classHighlight);
//get id name of clicked answer
for (var i = 0; i < currentQuestion.options.length ; i++) {
// console.log(liTagsid[i]);
if($liTags[i].className == "notSelected listyle selected"){
//store information to check answer
tags = $liTags[i].id;
// tagsClass = $LiTags.className;
tagsClassName = $liTags[i];
}
}
});
//check answer once it has been submitted
button.onclick = function (){
if(button.id == 'submit'){
button.className = 'buttonload';
button.innerHTML = '<i class="fa fa-spinner fa-spin"></i>Loading';
}
setTimeout(function() { checkAnswer(); }, 100);
};
}
//self calling function
showQuestions();
The website is on my local now but i can upload a screenimage if need be and the whole code of the webpage. Or is the issue in html?
edit: here is html/css code
<style>
/*========================================================
Quiz Section
========================================================*/
/*styling quiz area*/
.main {
background-color: white;
margin: 0 auto;
margin-top: 30px;
padding: 30px;
box-shadow: 0 0 20px 0 rgba(0, 0, 0, 0.2), 0 5px 5px 0 rgba(0, 0, 0, 0.24);
/*white-space: nowrap;*/
}
/*Editing the number of questions*/
.spanclass {
font-size: x-large;
}
#pages{
border: 3px solid;
display: inline-flex;
border-radius: 0.5em;
float: right;
}
#question{
word-break: break-all;
}
/*format text*/
p {
text-align: left;
font-size: x-large;
padding: 10px 10px 0;
}
.optionimg{
border: 2px solid black;
border-radius: 1.5em;
}
/*Form area width*/
/*formatting answers*/
.listyle {
list-style-type: none;
text-align: left;
background-color: transparent;
margin: 10px 5px;
padding: 5px 10px;
border: 1px solid lightgray;
border-radius: 0.5em;
font-weight: normal;
font-size: x-large;
display: inline-grid;
width: 48%;
height: 300px;
overflow: auto;
}
.listyle:hover {
background: #ECEEF0;
cursor: pointer;
}
/*Change effect of question when the questions is selected*/
.selected, .selected:hover {
background: #FFDEAD;
}
/*change correct answer background*/
.correct, .correct:hover {
background: #9ACD32;
color: white;
}
/*change wrong answer background*/
.wrong, .wrong:hover {
background: #db3c3c;
color: white;
}
/*========================================================
Submit Button
========================================================*/
.main button {
text-transform: uppercase;
width: 20%;
border: none;
padding: 15px;
color: #FFFFFF;
}
.submit:hover, .submit:active, .submit:focus {
background: #43A047;
}
.submit {
background: #4CAF50;
min-width: 120px;
}
/*next question button*/
.next {
background: #fa994a;
min-width: 120px;
}
.next:hover, .next:active, .next:focus {
background: #e38a42;
}
.restart {
background-color:
}
/*========================================================
Results
========================================================*/
.circle{
position: relative;
margin: 0 auto;
width: 200px;
height: 200px;
background: #bdc3c7;
-webkit-border-radius: 100px;
-moz-border-radius: 100px;
border-radius: 100px;
overflow: hidden;
}
.fill{
position: absolute;
bottom: 0;
width: 100%;
height: 80%;
background: #31a2ac;
}
.score {
position: absolute;
width: 100%;
top: 1.7em;
text-align: center;
font-family: Arial, sans-serif;
color: #fff;
font-size: 40pt;
line-height: 0;
font-weight: normal;
}
.circle p {
margin: 400px;
}
/*========================================================
Confeeti Effect
========================================================*/
canvas{
position:absolute;
left:0;
top:11em;
z-index:0;
border:0px solid #000;
}
.imagecenter{
display: block;
margin: 0 auto;
}
.buttonload {
background-color: #04AA6D; /* Green background */
border: none; /* Remove borders */
color: white; /* White text */
padding: 12px 24px; /* Some padding */
font-size: 16px; /* Set a font-size */
}
/* Add a right margin to each icon */
.fa {
margin-left: -12px;
margin-right: 8px;
}
#media only screen and (max-width: 900px){
.listyle {
width: 100% !important;
height: auto !important;
}
.imagecenter {
width: 100% !important;
}
.listyle img{
width: inherit !important;
height: unset !important;
}
.ulclass
{
padding:0px !important;
}
}
</style>
<!-- Main page -->
<div class="main">
<!-- Number of Question -->
<div class="wrapper" id="pages">
<span class="spanclass" id="quizNumber">1</span><span class="spanclass">/<?=$count?></span>
</div>
<!-- Quiz Question -->
<div class="quiz-questions" id="display-area">
<p id="question"></p>
<ul class="ulclass" id="options">
</ul>
<div id="quiz-results" class="text-center">
<button type="button" name="button" class="submit" id="submit">Submit</button>
</div>
</div>
</div>
<canvas id="canvas"></canvas>
<script src="https://code.jquery.com/jquery-3.2.1.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/2.1.3/jquery.min.js"></script>
<script>
I'm guessing that #question{ word-break: break-all; } is probably the culprit then? –
CB..yes that fixed it:)

How do I trigger the "Add" button after pressing enter in the textbox?

I created a to-do list so when you add something into the textbox and click the add button it adds it into the list which is shown below it. However, I want to quickly add a bunch of things and not tediously use my mouse to click the add button every time, that's why I have been trying to add in the function for when I press enter it will be added. But everything I've tried hasn't been working and yes I've read through and attempted to use code from other questions on stackoverflow which is why I've finally decided to ask this question.
Please help! [the end of the JavaScript part of the snippet is my most recent attempt]
// Create a "close" button and append it to each list item
var myNodelist = document.getElementsByTagName("LI");
var i;
for (i = 0; i < myNodelist.length; i++) {
var span = document.createElement("SPAN");
var txt = document.createTextNode("\u00D7");
span.className = "close";
span.appendChild(txt);
myNodelist[i].appendChild(span);
}
// Click on a close button to hide the current list item
var close = document.getElementsByClassName("close");
var i;
for (i = 0; i < close.length; i++) {
close[i].onclick = function() {
var div = this.parentElement;
div.style.display = "none";
}
}
// Add a "checked" symbol when clicking on a list item
var list = document.querySelector('ul');
list.addEventListener('click', function(ev) {
if (ev.target.tagName === 'LI') {
ev.target.classList.toggle('checked');
}
}, false);
// Create a new list item when clicking on the "Add" button
function newElement() {
var li = document.createElement("li");
var inputValue = document.getElementById("myInput").value;
var t = document.createTextNode(inputValue);
li.appendChild(t);
if (inputValue === '') {
alert("You must write something!");
} else {
document.getElementById("myUL").appendChild(li);
}
document.getElementById("myInput").value = "";
var span = document.createElement("SPAN");
var txt = document.createTextNode("\u00D7");
span.className = "close";
span.appendChild(txt);
li.appendChild(span);
for (i = 0; i < close.length; i++) {
close[i].onclick = function() {
var div = this.parentElement;
div.style.display = "none";
}
}
window.addEventListener('keyup', function (e) {
if (e.keyCode === 13) {
var button = document.getElementById("myInput");
button.click();
}
}, false);
}
body {
background-color: #81B9E3;
font-family: 'Handlee', cursive;
}
h1 {
color: #2F90DA;
font-size: xxx-large;
font-family: 'Concert One', cursive;
}
a {
text-decoration: none;
color: #2F90DA;
}
p{
color: black;
}
body {
margin: 0;
min-width: 250px;
}
/* Include the padding and border in an element's total width and height */
* {
box-sizing: border-box;
}
/* Remove margins and padding from the list */
ul {
margin: 0;
padding: 0;
}
/* Style the list items */
ul li {
cursor: pointer;
position: relative;
padding: 12px 8px 12px 40px;
list-style-type: none;
background: #7DB9FF;
font-size: 18px;
transition: 0.2s;
/* make the list items unselectable */
-webkit-user-select: none;
-moz-user-select: none;
-ms-user-select: none;
user-select: none;
}
/* Set all odd list items to a different color (zebra-stripes) */
ul li:nth-child(odd) {
background: #93C5FF;
}
/* Darker background-color on hover */
ul li:hover {
background: #51CA4C;
}
/* When clicked on, add a background color and strike out text */
ul li.checked {
background: #9DF599;
color: #51CA4C;
text-decoration: line-through;
}
/* Add a "checked" mark when clicked on */
ul li.checked::before {
content: '';
position: absolute;
border-color: #51CA4C;
border-style: solid;
border-width: 0 2px 2px 0;
top: 10px;
left: 16px;
transform: rotate(45deg);
height: 15px;
width: 7px;
}
/* Style the close button */
.close {
position: absolute;
right: 0;
top: 0;
padding: 12px 16px 12px 16px;
}
.close:hover {
background-color: #F44336;
color: white;
}
/* Style the header */
.header {
background-color: #2F90DA;
padding: 30px 40px;
color: white;
text-align: center;
}
/* Clear floats after the header */
.header:after {
content: "";
display: table;
clear: both;
}
/* Style the input */
input {
margin: 0;
border: none;
border-radius: 0;
width: 75%;
padding: 10px;
float: left;
font-size: 16px;
}
/* Style the "Add" button */
.addBtn {
padding: 8.5px;
width: 25%;
background: #81B9E3;
color: #fff;
float: left;
text-align: center;
font-size: 16px;
cursor: pointer;
transition: 0.3s;
border-radius: 0;
}
.addBtn:hover {
background-color: #51CA4C;
}
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="utf-8">
<meta name="viewport" content="width=device-width">
<title>To Do List</title>
<link rel="preconnect" href="https://fonts.gstatic.com">
<link href="https://fonts.googleapis.com/css2?family=Actor&family=Luckiest+Guy&display=swap" rel="stylesheet">
<link rel="preconnect" href="https://fonts.gstatic.com">
<link href="https://fonts.googleapis.com/css2?family=Concert+One&family=Handlee&family=Actor&display=swap" rel="stylesheet">
<link href="todo.css" rel="stylesheet" type="text/css" />
</head>
<body>
<div style="background-color: #DCEEF5; padding: 20px; text-align: center;">
<h1> 📖 To Do List 📖</h1>
<h2 style="margin-top: 0; margin-left: 20%; margin-right: 20%">Make your own to do list!</h2>
<h3>Type your task and click "Add". Once your task is completed, just click on the task to cross it off. Press the x button on the far right of a task to remove it.</h3>
<h4 style="margin-bottom: 3%;">Go back to Productify Home or Navigation</h4>
</div><br/>
</body>
<style>
</style>
</head>
<body>
<div id="myDIV" class="header">
<h2 style="margin:5px">📖 My To Do List 📖</h2>
<input type="text" id="myInput" placeholder="New Task...">
<span onclick="newElement()" class="addBtn">Add</span>
</div>
<ul id="myUL"></ul>
<script src="todo.js"></script>
</body>
</html>
You can probably get away with using the same handler for both the button and the input using a closure.
// Cache your elements
const input = document.querySelector('input');
const list = document.querySelector('div');
const button = document.querySelector('button');
// Pass in the input and list elements to the handler
// The handler returns a new function that will be used
// for both the button and input listeners
const handler = handleInput(input, list);
button.addEventListener('click', handler, false);
input.addEventListener('keyup', handler, false);
function handleInput(input, list) {
// Initialise the text in the input
let text = '';
// Add the text to the page, reset `text`,
// and reset the input value
function printLine(text) {
list.innerHTML += `<div>${text}</div>`;
text = '';
input.value = '';
}
// This is the listener
return function(e) {
const { code, target: { value, type } } = e;
// If the button is clicked call `printLine`
if (type === 'submit') printLine(text);
// If the input has changed
// If return has been pressed call printLine
// otherwise update the text value
if (type === 'text') {
if (code === 'Enter') {
printLine(text);
} else {
text = value;
}
}
}
}
<input />
<button>Add to list</button>
<div></div>

Compare input value with li content in pure Javascript

I have to do some kind of ToDo list, where I have input and button to Add item to ul list. And now I done everything except compare every li item with input value. My question is how to compare every li content with value input to prevent duplicate items. Here is the code https://jsfiddle.net/qoLtxfaw/1/
// Variables
var ul = document.getElementById("taskList");
var task = document.getElementById("task");
var btn = document.querySelector('button');
var listItem = document.getElementsByTagName("LI");
// Append close btn to each list item
for (var i = 0; i < listItem.length; i++) {
var span = document.createElement("SPAN");
var txt = document.createTextNode("\u00D7");
span.className = "js-close";
span.appendChild(txt);
listItem[i].appendChild(span);
}
// Click on a close button to hide the current list item
var close = document.getElementsByClassName("js-close");
for (var i = 0; i < close.length; i++) {
close[i].onclick = function() {
var div = this.parentElement;
div.className = 'js-hide';
}
}
// proveravati ima li ul odnosno liste, ukoliko ne proverimo a nema ceo kod ce prestati da se izvrsava
if (ul) {
ul.onmouseover = function(event) {
var target = event.target;
target.style.background = '#efebeb';
};
ul.onmouseout = function(event) {
var target = event.target;
target.style.background = '';
};
}
// Add item to list on btn
btn.addEventListener('click', addItem);
// Add item to list on enter
task.onkeyup = function(e) {
if (e.keyCode == 13) {
addItem();
}
};
// // Add item to list
function addItem() {
var li = document.createElement("li");
var inputValue = document.getElementById('task').value;
li.setAttribute('id', task.value);
li.appendChild(document.createTextNode(task.value));
// ul.appendChild(li);
// compare every li item with inputValue
if (inputValue) { //if input value is true and has some value
//go trough all li items
for (var i = 0; i < listItem.length; i++) {
// compare every li item with inputValue
}
// Duplicate values don't allow in list
if (!inputValue) {
alert("No empty values are allowed!");
li.className = 'js-btn-disable';
} else {
ul.appendChild(li);
}
document.getElementById("task").value = "";
var span = document.createElement("SPAN");
var txt = document.createTextNode("\u00D7");
span.className = "js-close";
span.appendChild(txt);
li.appendChild(span);
for (var i = 0; i < close.length; i++) {
close[i].onclick = function() {
var div = this.parentElement;
div.className = 'js-hide';
}
}
}
}
#wrapper {
width: 500px;
margin: 0 auto;
background: #00bcd4;
border: 1px solid #f1f0f0;
padding-left: 10px;
font-size: 1.2em;
}
#wrapper #task {
background: transparent;
color: #ffffff;
font-size: 1.2em;
width: 80%;
height: 35px;
border: none;
border-bottom: 2px solid #ffffff;
outline: none;
margin: 15px 0 5px 0;
}
#wrapper #task ::-webkit-input-placeholder {
/* Chrome/Opera/Safari */
color: #ffffff;
}
#wrapper #task ::-moz-placeholder {
/* Firefox 19+ */
color: #ffffff;
}
#wrapper #task :-ms-input-placeholder {
/* IE 10+ */
color: #ffffff;
}
#wrapper #task :-moz-placeholder {
/* Firefox 18- */
color: #ffffff;
}
#wrapper button {
font-size: 1.2em;
border: 2px solid #ffffff;
background: transparent;
color: #ffffff;
padding: 5px 10px;
outline: none;
cursor: pointer;
}
#wrapper ul#taskList {
padding: 0;
background: #ffffff;
list-style-type: none;
text-align: left;
margin-bottom: 0;
margin-left: -10px;
}
#wrapper ul#taskList li {
padding: 10px;
position: relative;
cursor: pointer;
}
/* Style the close button */
.js-close {
position: absolute;
right: 0;
top: 0;
padding: 10px;
}
.js-close:hover {
color: #ffffff;
}
.js-hide {
display: none;
}
.js-background {
background: #efebeb;
}
.js-btn-disable {
opacity: 0.65;
cursor: not-allowed;
}
/*# sourceMappingURL=style.css.map */
<div id="wrapper">
<input type="text" id="task" />
<button>Add</button>
<ul id="taskList"></ul>
</div>
Have a look at this. I use firstChild and I moved the validation to the top of the function.
I use the inputValue after validating it but task everywhere else.
DRY - Don't Repeat Yourself
// Variables
var ul = document.getElementById("taskList");
var task = document.getElementById("task");
var btn = document.querySelector('button');
var listItem = document.getElementsByTagName("LI");
task.focus();
// Append close btn to each list item
for (var i = 0; i < listItem.length; i++) {
var span = document.createElement("SPAN");
var txt = document.createTextNode("\u00D7");
span.className = "js-close";
span.appendChild(txt);
listItem[i].appendChild(span);
}
// Click on a close button to hide the current list item
var close = document.getElementsByClassName("js-close");
for (var i = 0; i < close.length; i++) {
close[i].onclick = function() {
var div = this.parentElement;
div.className = 'js-hide';
}
}
// proveravati ima li ul odnosno liste, ukoliko ne proverimo a nema ceo kod ce prestati da se izvrsava
if (ul) {
ul.onmouseover = function(event) {
var target = event.target;
target.style.background = '#efebeb';
};
ul.onmouseout = function(event) {
var target = event.target;
target.style.background = '';
};
}
// Add item to list on btn
btn.addEventListener('click', addItem);
// Add item to list on enter
task.onkeyup = function(e) {
if (e.keyCode == 13) {
addItem();
}
};
// // Add item to list
function addItem() {
var inputValue = task.value.trim();
task.value = "";
task.focus();
// Empty or Duplicate values don't allow in list
if (!inputValue) {
alert("No empty values are allowed!");
return
}
var listItem = document.querySelectorAll("#taskList li");
for (var i = 0; i < listItem.length; i++) {
if (inputValue == listItem[i].firstChild.textContent) {
alert("No duplicate values are allowed!");
return
}
}
var li = document.createElement("li");
li.setAttribute('id', inputValue);
li.appendChild(document.createTextNode(inputValue));
ul.appendChild(li);
var span = document.createElement("SPAN");
var txt = document.createTextNode("\u00D7");
span.className = "js-close";
span.appendChild(txt);
li.appendChild(span);
for (var i = 0; i < close.length; i++) {
close[i].onclick = function() {
var div = this.parentElement;
div.className = 'js-hide';
}
}
}
#wrapper {
width: 500px;
margin: 0 auto;
background: #00bcd4;
border: 1px solid #f1f0f0;
padding-left: 10px;
font-size: 1.2em;
}
#wrapper #task {
background: transparent;
color: #ffffff;
font-size: 1.2em;
width: 80%;
height: 35px;
border: none;
border-bottom: 2px solid #ffffff;
outline: none;
margin: 15px 0 5px 0;
}
#wrapper #task ::-webkit-input-placeholder {
/* Chrome/Opera/Safari */
color: #ffffff;
}
#wrapper #task ::-moz-placeholder {
/* Firefox 19+ */
color: #ffffff;
}
#wrapper #task :-ms-input-placeholder {
/* IE 10+ */
color: #ffffff;
}
#wrapper #task :-moz-placeholder {
/* Firefox 18- */
color: #ffffff;
}
#wrapper button {
font-size: 1.2em;
border: 2px solid #ffffff;
background: transparent;
color: #ffffff;
padding: 5px 10px;
outline: none;
cursor: pointer;
}
#wrapper ul#taskList {
padding: 0;
background: #ffffff;
list-style-type: none;
text-align: left;
margin-bottom: 0;
margin-left: -10px;
}
#wrapper ul#taskList li {
padding: 10px;
position: relative;
cursor: pointer;
}
/* Style the close button */
.js-close {
position: absolute;
right: 0;
top: 0;
padding: 10px;
}
.js-close:hover {
color: #ffffff;
}
.js-hide {
display: none;
}
.js-background {
background: #efebeb;
}
.js-btn-disable {
opacity: 0.65;
cursor: not-allowed;
}
/*# sourceMappingURL=style.css.map */
<div id="wrapper">
<input type="text" id="task" />
<button>Add</button>
<ul id="taskList"></ul>
</div>

dropdown menu with only 10 visible links

So, I am wondering if it is possible to make the dropdown menu only have 10 visible links, and the rest would be invisible. If it ain't possible, is it possible to make it so you can only se 10 and scroll down. Any suggestions?
function myFunction() {
document.getElementById("myDropdown").classList.toggle("show");
}
function filterFunction() {
var input, filter, ul, li, a, i;
input = document.getElementById("myInput");
filter = input.value.toUpperCase();
div = document.getElementById("myDropdown");
a = div.getElementsByTagName("a");
for (i = 0; i < a.length; i++) {
if (a[i].innerHTML.toUpperCase().indexOf(filter) > -1) {
a[i].style.display = "";
} else {
a[i].style.display = "none";
}
}
}
.dropbtn {
background-color: #4CAF50;
color: white;
padding: 16px;
font-size: 16px;
border: none;
cursor: pointer;
}
.dropbtn:hover, .dropbtn:focus {
background-color: #3e8e41;
}
#myInput {
border-box: box-sizing;
background-image: url('searchicon.png');
background-position: 14px 12px;
background-repeat: no-repeat;
font-size: 16px;
padding: 14px 20px 12px 45px;
border: none;
}
.dropdown {
position: relative;
display: inline-block;
}
.dropdown-content {
display: none;
position: absolute;
background-color: #f6f6f6;
min-width: 230px;
overflow: auto;
box-shadow: 0px 8px 16px 0px rgba(0,0,0,0.2);
z-index: 1;
}
.dropdown-content a {
color: black;
padding: 12px 16px;
text-decoration: none;
display: block;
}
.dropdown a:hover {background-color: #ddd}
.show {display:block;}
<div class="dropdown">
<button onclick="myFunction()" class="dropbtn">Dropdown</button>
<div id="myDropdown" class="dropdown-content">
<input type="text" placeholder="Search.." id="myInput" onkeyup="filterFunction()">
About
Base
Blog
Contact
Custom
Support
Tools
About
Base
Blog
Contact
Custom
Support
Tools
About
Base
Blog
Contact
Custom
Support
Tools
</div>
</div>
EDIT: New answer:
I misinterpreted the question. You can slightly modify your filter function to keep track of shown items (10) and then just call it once whenever you open the menu. This way you're showing max 10 items when opening the menu and when filtering. fiddle: https://jsfiddle.net/d3kta5sw/
function myFunction() {
document.getElementById("myDropdown").classList.toggle("show");
filterFunction();
}
function filterFunction() {
var input, filter, ul, li, a, i,
elementsToShow = 10,
elementsShowing = 0;
input = document.getElementById("myInput");
filter = input.value.toUpperCase();
div = document.getElementById("myDropdown");
a = div.getElementsByTagName("a");
for (i = 0; i < a.length; i++) {
if (a[i].innerHTML.toUpperCase().indexOf(filter) > -1 &&
elementsShowing < elementsToShow) {
a[i].style.display = "";
elementsShowing++;
} else {
a[i].style.display = "none";
}
}
}
Old Answer (only works for first 10 visible items):
You can do this in pure css. Try adding the following, this will hide the 11th 'a' element and onwards:
.dropdown-content a:nth-of-type(n+11) {
display:none;
}
You could add the height values of the first 10 items and set that manually in CSS or you can use Javascript count the first 10 items and add their heights together. As it is now they all have the same height so you could do h*10 but if for some reason an item breaks to a second line your height would be off. I've updated your snipped.
I've updated the myFunction function. You'll notice I add the show class before calculating the height as offsetHeight will always return 0 if the parent is hidden.
Hiding When Clicking off Button
We can handle this with the blur event. Rather than using an attribute for the event like the onclick we're going to handle this solely with JS.
Returning to Top of Dropdown
In order to return to the top of the dropdown after you click out of the dropdown we need to use the scrollTop property. in myFunction() the last line we set scrollTop = 0 on the dropDown element which scrolls us to the top!
var btn = document.querySelector('.dropbtn');
btn.addEventListener('blur', function() {
var dd = document.querySelector('.dropdown-content');
if ( dd.classList.contains('show') ) {
dd.classList.remove('show');
}
});
function myFunction() {
var dropDown = document.getElementById('myDropdown'),
items = dropDown.children,
height = 0;
dropDown.classList.toggle('show');
for (var i = 1; i < 10; i++) {
height += items[i].offsetHeight;
}
dropDown.style.height = height + 'px';
dropDown.scrollTop = 0;
}
function filterFunction() {
var input, filter, ul, li, a, i;
input = document.getElementById("myInput");
filter = input.value.toUpperCase();
div = document.getElementById("myDropdown");
a = div.getElementsByTagName("a");
for (i = 0; i < a.length; i++) {
if (a[i].innerHTML.toUpperCase().indexOf(filter) > -1) {
a[i].style.display = "";
} else {
a[i].style.display = "none";
}
}
}
var btn = document.querySelector('.dropbtn');
btn.addEventListener('blur', function() {
var dd = document.querySelector('.dropdown-content');
if ( dd.classList.contains('show') ) {
dd.classList.remove('show');
}
});
.dropbtn {
background-color: #4CAF50;
color: white;
padding: 16px;
font-size: 16px;
border: none;
cursor: pointer;
}
.dropbtn:hover,
.dropbtn:focus {
background-color: #3e8e41;
}
#myInput {
border-box: box-sizing;
background-image: url('searchicon.png');
background-position: 14px 12px;
background-repeat: no-repeat;
font-size: 16px;
padding: 14px 20px 12px 45px;
border: none;
}
.dropdown {
position: relative;
display: inline-block;
}
.dropdown-content {
display: none;
position: absolute;
background-color: #f6f6f6;
min-width: 230px;
overflow: auto;
box-shadow: 0px 8px 16px 0px rgba(0, 0, 0, 0.2);
z-index: 1;
}
.dropdown-content a {
color: black;
padding: 12px 16px;
text-decoration: none;
display: block;
}
.dropdown a:hover {
background-color: #ddd
}
.show {
display: block;
}
<div class="dropdown">
<button onclick="myFunction()" class="dropbtn">Dropdown</button>
<div id="myDropdown" class="dropdown-content">
<input type="text" placeholder="Search.." id="myInput" onkeyup="filterFunction()">
About
Base
Blog
Contact
Custom
Support
Tools
About
Base
Blog
Contact
Custom
Support
Tools
About
Base
Blog
Contact
Custom
Support
Tools
</div>
</div>
CSS option:
.show{
overflow:overlay: //to hide to the other elements
height:200px; //to show desired number of elements
}
Better to use this element:
.dropdown-content

Translating jQuery to Vanilla JS issue

I was watching a tutorial that used jQuery and wanted to turn it into JS, but my code is broken - was hoping someone could help me with this:
Tutorial JS:
$(function() {
var btn = $('button');
var progressBar = $('.progressbar');
btn.click(function() {
progressBar.find('li.active').next().addClass('active');
})
})
Taken from URL:http://www.kodhus.com/kodity/codify/kod/mGXAtb
Here is my failed attempt at rewriting the jQuery using JavaScript DOM:
var btn1 = document.getElementsByTagName('BUTTON');
var progBar = document.getElementsByClassName('progressbar');
function clickMe1() {
var elm = progBar.querySelectorAll("li");
var emlClass = elm.querySelector(".active");
return emlClass.nextElementSibling.addClass('active');
}
btn1.addEventListener("click", clickMe1, false);
where did I go wrong?
Working fiddle.
Your code will work after several changes check the notes below :
You've missed addClass() there it's a jQuery function, for vanilla JS use .classList.add() instead:
return emlClass.nextElementSibling.classList.add("active");
querySelectorAll(); will return a list of nodes you have to loop through them and add class, use :
var emlClass = progBar.querySelectorAll("li.active");
Instead of :
var elm = progBar.querySelectorAll("li");
var emlClass = elm.querySelector(".active");
Then loop and add active class:
for(var i=0;i<emlClass.length;i++){
emlClass[i].nextElementSibling.classList.add("active");
}
getElementsByTagName() and getElementsByClassName() will also returns a list of nodes with given name, you have to specify which one you want to pick (selecting the first in my example) :
var btn1 = document.getElementsByTagName('BUTTON')[0];
var progBar = document.getElementsByClassName('progressbar')[0];
Hope this helps.
var btn1 = document.getElementsByTagName('BUTTON')[0];
var progBar = document.getElementsByClassName('progressbar')[0];
function clickMe1() {
var emlClass = progBar.querySelectorAll("li.active");
for(var i=0;i<emlClass.length;i++){
emlClass[i].nextElementSibling.classList.add("active");
}
}
btn1.addEventListener("click", clickMe1, false);
.container {
width: 100%;
}
.progressbar {
counter-reset: step;
margin: 0;
margin-top: 50px;
padding: 0;
}
.progressbar li {
list-style-type: none;
float: left;
width: 33.33%;
position: relative;
text-align: center;
}
.progressbar li:before {
content: counter(step);
counter-increment: step;
width: 30px;
height: 30px;
line-height: 30px;
border: 2px solid #ddd;
display: block;
text-align: center;
margin: 0 auto 10px auto;
border-radius: 50%;
background-color: white;
}
.progressbar li:after {
content: '';
position: absolute;
width: 100%;
height: 2px;
background-color: #ddd;
top: 15px;
left: -50%;
z-index: -1;
}
.progressbar li:first-child:after {
content: none;
}
.progressbar li.active {
color: green;
}
.progressbar li.active:before {
border-color: green;
}
.progressbar li.active + li:after {
background-color: green;
}
button {
position: relative;
border: none;
padding: 10px 20px;
font-size: 16px;
border-radius: 2px;
left: 50%;
margin-top: 30px;
transform: translate(-50%);
cursor: pointer;
outline: none;
}
button:hover {
opacity: 0.8;
}
<div class="container">
<ul class="progressbar">
<li class="active">Step 1</li>
<li>Step 2</li>
<li>Step 3</li>
</ul>
</div>
<button>Next step</button>
.querySelectorAll("li") will return an array (or an array-like object) with one or more <li> tags. So you need to either:
loop through every <li> in that list and do the rest,
or just take the first item from that list if you don't want to worry about there being more than one li in the page,
or use .querySelector (not .querySelectorAll) to just take the first <li> for you.
MDN

Categories