Remove dynamically created elements in a form - javascript

I know this is a basic questions, but I am working on making a dynamic form and was having a bit of trouble figuring out how to delete elements that share the same class. I have looked around on the web and other posts for a means to accomplish this, but still was unable to figure it out.
I am new to this so I apologize for the basic question. Below, I have pasted the relevant code and my attempt at this. Would anyone be able to assist me?
var ingCounter = 1;
var dirCounter = 1;
var limit = 10;
function addIngredient(divName){
if (ingCounter == limit) {
alert("You have reached the add limit");
}
else {
var newdiv = document.createElement('div');
newdiv.innerHTML = "<div class='ingredientSet'><input class='ingredientInput' type='text' name='ingredients[]'><button class='deleteIngredientButton' type='button' onClick='removeElement('directionSet');'>X</button></div>";
document.getElementById(divName).appendChild(newdiv);
ingCounter++;
}
}
function addDirection(divName){
if (dirCounter == limit) {
alert("You have reached the add limit");
}
else {
var newdiv = document.createElement('div');
newdiv.innerHTML = "<div class='directionSet'><input class='directionInput' type='text' name='directions[]'><button class='deleteDirectionButton' type='button'>X</button></div>";
document.getElementById(divName).appendChild(newdiv);
dirCounter++;
}
}
function removeElement(elementId) {
// Removes an element from the document
var element = document.getElementById(elementId);
element.parentNode.removeChild(element);
}
<!DOCTYPE html>
<html lang="en">
<head>
<!-- Required meta tags -->
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>Homemade</title>
<!-- Required program scripts -->
<script src="https://cdn.jsdelivr.net/npm/vue/dist/vue.js"></script>
<script src="https://code.jquery.com/jquery-3.5.1.js" integrity="sha256-QWo7LDvxbWT2tbbQ97B53yJnYU3WhH/C8ycbRAkjPDc=" crossorigin="anonymous"></script>
<!-- Style Sheets-->
<link rel="stylesheet" href="/styles/navBarStyle.css">
<link rel="stylesheet" href="/styles/myRecipesStyle.css">
<link rel="stylesheet" href="/styles/createRecipeStyle.css">
<link rel="stylesheet" href="/styles/errorMessageStyle.css">
</head>
<body>
<!-- Background image -->
<img id="background" src="/images/foodBackground.jpg" alt="">
<div id="newRecipeContainer">
<div id="closeButtonContainer">
<div id="backButton"><a id="back" href="/recipes/myRecipes">← My Recipes</a></div>
</div>
<form id="createRecipeForm" action="/recipes/createRecipe" method="POST" enctype="multipart/form-data">
<label id="formSubHeading">Create Your Homemade Recipe</label>
<%- include('../_partial/_messages'); -%>
<div id="recipeNameContainer">
<label id="recipeNameLabel">Title</label>
<input id="recipeNameInput" type="text" name="recipeName">
</div>
<div id="recipeImage">
<label id="recipeImageLabel">Add An Image of Your Meal</label>
<input id="recipeImageInput" type="file" accept="image/*" name="recipeImage"/>
<label id="recipeImageInputLabel" for="recipeImageInput" name="recipeImage">Choose A File</label>
</div>
<div id="recipeDescription">
<label id="recipeDescriptionLabel">Description</label>
<textarea id="recipeDescriptionInput" name="recipeDescription" cols="30" rows="10" maxlength="2000"></textarea>
</div>
<div class="ingredientsContainer">
<label id="ingredientsLabel">Ingredients</label>
<button id="addIngredientButton" type="button" onClick="addIngredient('allIngredients');">Add Another Ingredient</button>
<div id="allIngredients">
<div class="ingredientSet">
<input class="ingredientInput" type="text" name="ingredients[]">
</div>
</div>
</div>
<div class="directionsContainer">
<label id="directionsLabel">Directions</label>
<button id="addDirectionButton" type="button" onClick="addDirection('allDirections');">Add Another Direction</button>
<div id="allDirections">
<div class="directionSet">
<input class="directionInput" type="text" name="directions[]">
</div>
</div>
</div>
<div id="createRecipeButtonContainer">
<button id="createRecipeButton" type="submit">Create Recipe</button>
</div>
</form>
</div>
</body>
<!-- Required scripts to run app -->
<script src="/controls/newRecipeControl.js"></script>
<script src="/controls/errorMessageControl.js"></script>
</html>
Thanks for any help.

In your code you are using getElementById but there is no id called directionSet its a class.
You can simply use parentElement and remove to remove the newly added dynamic inputs by calling an onClick function.
In the onClick function removeElement() - this refers to the elements we have clicked and it will remove from the form.
var ingCounter = 1;
var dirCounter = 1;
var limit = 10;
function addIngredient(divName) {
if (ingCounter == limit) {
alert("You have reached the add limit");
} else {
var newdiv = document.createElement('div');
newdiv.innerHTML = "<div class='ingredientSet'><input class='ingredientInput' type='text' name='ingredients[]'><button class='deleteIngredientButton' type='button' onClick='removeElement(this);'>X</button></div>";
document.getElementById(divName).appendChild(newdiv);
ingCounter++;
}
}
function addDirection(divName) {
if (dirCounter == limit) {
alert("You have reached the add limit");
} else {
var newdiv = document.createElement('div');
newdiv.innerHTML = "<div class='directionSet'><input class='directionInput' type='text' name='directions[]'><button class='deleteDirectionButton' onClick='removeElement(this);' type='button'>X</button></div>";
document.getElementById(divName).appendChild(newdiv);
dirCounter++;
}
}
function removeElement(elementId) {
// Removes an element from the document
elementId.parentElement.remove()
}
<!DOCTYPE html>
<html lang="en">
<head>
<!-- Required meta tags -->
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>Homemade</title>
</head>
<body>
<!-- Background image -->
<div id="newRecipeContainer">
<div id="closeButtonContainer">
<div id="backButton"><a id="back" href="/recipes/myRecipes">← My Recipes</a></div>
</div>
<form id="createRecipeForm" action="/recipes/createRecipe" method="POST" enctype="multipart/form-data">
<label id="formSubHeading">Create Your Homemade Recipe</label>
<div id="recipeNameContainer">
<label id="recipeNameLabel">Title</label>
<input id="recipeNameInput" type="text" name="recipeName">
</div>
<div id="recipeImage">
<label id="recipeImageLabel">Add An Image of Your Meal</label>
<input id="recipeImageInput" type="file" accept="image/*" name="recipeImage" />
<label id="recipeImageInputLabel" for="recipeImageInput" name="recipeImage">Choose A File</label>
</div>
<div id="recipeDescription">
<label id="recipeDescriptionLabel">Description</label>
<textarea id="recipeDescriptionInput" name="recipeDescription" cols="30" rows="10" maxlength="2000"></textarea>
</div>
<div class="ingredientsContainer">
<label id="ingredientsLabel">Ingredients</label>
<button id="addIngredientButton" type="button" onClick="addIngredient('allIngredients');">Add Another Ingredient</button>
<div id="allIngredients">
<div class="ingredientSet">
<input class="ingredientInput" type="text" name="ingredients[]">
</div>
</div>
</div>
<div class="directionsContainer">
<label id="directionsLabel">Directions</label>
<button id="addDirectionButton" type="button" onClick="addDirection('allDirections');">Add Another Direction</button>
<div id="allDirections">
<div class="directionSet">
<input class="directionInput" type="text" name="directions[]">
</div>
</div>
</div>
<div id="createRecipeButtonContainer">
<button id="createRecipeButton" type="submit">Create Recipe</button>
</div>
</form>
</div>
</body>
</html>

Related

Need the list to add new elements to the top of the list

I am kind of stuck. I have thought of the idea to use the .insertBefore() but I am not sure where to place the syntax. I also need to add checkboxes instead of the bullets that automaticly apear when using , I have no clue have to do this.
My code is as follows.
HTML
const n = [];
function changeText() {
inputText = document.getElementById('inputText').value;
n.push(inputText);
document.querySelector('#list ul').innerHTML += "<li>" + inputText
}
<html lang="en">
<head>
<title>To-Do list</title>
<mmeta charset="UTF-8">
<link rel="stylesheet" href="todoStyle.css">
</head>
<body>
<div id="form">
<h1>New Task</h1>
<div id="button">
<button onclick="changeText()">Add to list</button>
</div>
<div id="input">
<input type="text" id="inputText" name="addNewList">
</div>
</div>
<div class="list1" id="list">
<h1>My to-do list</h1>
<ul>
</ul>
</div>
<script src="todo.js"></script>
</body>
</html>
I tried inserting the .insertBefore() in a new document.getElementById. But I was not sure where to insert this line of code.
To add an element to the beginning of an array, just array.unshift(element) instead of .push
And for putting a checkbox per array item:
<li><input type="checkbox"/></li>
One way to do it is to first save the current content. Then you will concatenate the new item with the current content, in the order you want it to be presented. I modified the code to work like that
const n = [];
function changeText() {
inputText = document.getElementById('inputText').value;
// add the item in the beginning of the list
n.unshift(inputText);
// save current listing
const currentContent = document.querySelector('#list ul').innerHTML;
// append new item in the beginning the the current listing
document.querySelector('#list ul').innerHTML = "<li>" + inputText + "</li>" + currentContent;
}
<html lang="en">
<head>
<title>To-Do list</title>
<mmeta charset="UTF-8">
<link rel="stylesheet" href="todoStyle.css">
</head>
<body>
<div id="form">
<h1>New Task</h1>
<div id="button">
<button onclick="changeText()">Add to list</button>
</div>
<div id="input">
<input type="text" id="inputText" name="addNewList">
</div>
</div>
<div class="list1" id="list">
<h1>My to-do list</h1>
<ul>
</ul>
</div>
<script src="todo.js"></script>
</body>
</html>
Try using afterbegin, I used css to remove the circle of the list styles and having a checkbox with the text, now you should have some events for the input to handle.
const n = [];
function changeText() {
inputText = document.getElementById('inputText').value;
n.push(inputText)
// get reference to the nav tag
const listUl = document.querySelector("#list ul");
listUl.insertAdjacentHTML("afterbegin", `
<li>
<input type="checkbox"/>
${inputText}
</li>
`);
}
#list ul li{
list-style:none;
}
<html lang="en">
<head>
<title>To-Do list</title>
<mmeta charset="UTF-8">
<link rel="stylesheet" href="todoStyle.css">
</head>
<body>
<div id="form">
<h1>New Task</h1>
<div id="button">
<button onclick="changeText()">Add to list</button>
</div>
<div id="input">
<input type="text" id="inputText" name="addNewList">
</div>
</div>
<div class="list1" id="list">
<h1>My to-do list</h1>
<ul>
</ul>
</div>
<script src="todo.js"></script>
</body>
</html>

Upload Files to Google Drive from HTML form and save url to google sheet

I am totally new to this stuff and get quite nothing of it.
I used some tutorials to write this, but I don't know how to get the link to the uploaded document in the google sheet.
This is the Apps Script code:
function doGet() {
var html = HtmlService.createHtmlOutputFromFile('index');
return html.setXFrameOptionsMode(HtmlService.XFrameOptionsMode.ALLOWALL);
}
// App Script function to save data to sheet
function saveData(data) {
var sheet = SpreadsheetApp.getActiveSheet();
sheet.appendRow(data);
}
function uploadFiles(data)
{
var file = data.myFile;
var folder = DriveApp.getFolderById('1NWq9CoBxzYumYQzTlCjLMS95Y6G2NY6X');
var createFile = folder.createFile(file);
return createFile.getUrl();
var uploadURL = file.getUrl();
}
And here the HTML code in: index.html
<!DOCTYPE html>
<html>
<head>
<base target="_top">
<meta charset="utf-8">
<meta name="viewport" content="width=device-width, initial-scale=1, shrink-to-fit=no">
<link rel="stylesheet" href="https://stackpath.bootstrapcdn.com/bootstrap/4.3.1/css/bootstrap.min.css" integrity="sha384-ggOyR0iXCbMQv3Xipma34MD+dH/1fQ784/j6cY/iJTQUOhcWr7x9JvoRxT2MZw1T" crossorigin="anonymous">
</head>
<body>
<div class="container">
<br>
<h1>Custom HTML Forms to Google Sheet</h1>
<br>
<div id="form">
<form>
<div class="form-group">
<label for="Name">Name</label>
<input type="text" class="form-control form-data" id="Name">
</div>
<div class="form-group">
<label for="Email">Email</label>
<input type="text" class="form-control form-data" id="Email">
</div>
<div class="form-group">
<label for="Age">Age</label>
<input type="text" class="form-control form-data" id="Age">
</div>
<div class="form-group">
<label for="Company">Company</label>
<input type="text" class="form-control form-data" id="Company">
</div>
<div class="form-group">
<label for="Mob">Mob</label>
<input type="text" class="form-control form-data" id="Mob">
</div>
<div>
<input type="file" name="myFile">
</div>
<button type="button" class="btn btn-primary" onclick="send_data()" id="submitBtn" value="Upload Files">Submit</button>
</form>
</div>
<!-- Optional if you want to give a completion feedback! -->
<div id="completion-msg" style="display: none;">
Thank you for completing this form!
<label id="resp"></label>
</div>
</div>
<script>
document.getElementById('submitBtn').addEventListener('click',
function send_data(){
google.script.run.withSuccessHandler(onSuccess).uploadFiles(this.parentNode)
var form_data = document.getElementsByClassName("form-data"); //retrieve filled form data
var i;
var data = [];
for(i=0; i<form_data.length; i++){
data.push(form_data[i].value);
}
google.script.run.saveData(data); // send to google app script
document.getElementById("form").style.display = "none"; // make form invisible
document.getElementById("completion-msg").style.display = "block"; // Optional if you want to give a completion feedback!
})
function onSuccess(data){
document.getElementById('resp').innerHTML = "File Uploaded to the path " +data;
}
</script>
</body>
</html>
It is totally ok, if you say that there is no way to change this code into something that works, but please say how I could solve it elsewise.
I would really appreciate it, if you help me. Thanks!

Problems on the generated value of the qr code into a input field using JavaScript

JavaScript codes and HTML codes
I'm trying to put a generated value of the qr code a input text to be save in my SQLite database can't pust the darn value of the qr code
var resultDiv;
document.addEventListener("deviceready", init, false);
function init() {
document.querySelector("#startScan").
addEventListener("touchend", startScan, false);
resultDiv = document.querySelector("#results");//works in <p id="results"></p>
resultDiv = document.querySelector('#text4');//wont work at all <input id="text4" type="text" placeholder="Book Info"/>
}
function startScan() {
cordova.plugins.barcodeScanner.scan(
function (result) {
var s = result.text.split('|');
result.format;
result.cancelled;
resultDiv.innerHTML = s;
},
function (error) {
alert("Scanning failed: " + error);
}
);
}
JavaScript codes and HTML codes
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>qrBorrowers</title>
<link rel="stylesheet" href="css/style.css">
</head>
<body>
<script type="text/javascript" src="cordova.js"></script>
<nav>
<div class="topnav">
Add
Borrow
Return
QR code
</div>
</nav>
<Label>
<h1> Borrow a Book </h1>
</Label>
<div class="borrow">
<input id="text1" type="text" placeholder="Borrower Number" onfocus="this.value=''"/>
<input id="text2" type="text" placeholder="Borrower Last Name" onfocus="this.value=''" />
<input id="text3" type="text" placeholder="Borrower First Name" onfocus="this.value=''" />
<input id="text4" type="text" placeholder="Book Info"/>
<input id="text6" type="date" placeholder="Date Borrowed" />
<br>
</div>
<div class="borrow">
<p id="results"></p>
<button id="startScan">Start Scan</button>
<button id="savedb">Save </button>
</div>
<script type="text/javascript" src="js/scanQR.js"></script>
</body>
</html>
With inner HTML it will not going to save your generated QR code to input box. You need to change the innerHTML to value to save the value in input box such that you can use that when form submit as value to save in database.
var resultDiv;
document.addEventListener("deviceready", init, false);
function init() {
document.querySelector("#startScan").
addEventListener("touchend", startScan, false);
resultDiv = document.querySelector("#results");//works in <p id="results"></p>
resultDiv = document.querySelector('#text4');//wont work at all <input id="text4" type="text" placeholder="Book Info"/>
}
function startScan() {
cordova.plugins.barcodeScanner.scan(
function (result) {
var s = result.text.split('|');
result.format;
result.cancelled;
resultDiv.value = s;
},
function (error) {
alert("Scanning failed: " + error);
}
);
}
JavaScript codes and HTML codes
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>qrBorrowers</title>
<link rel="stylesheet" href="css/style.css">
</head>
<body>
<script type="text/javascript" src="cordova.js"></script>
<nav>
<div class="topnav">
Add
Borrow
Return
QR code
</div>
</nav>
<Label>
<h1> Borrow a Book </h1>
</Label>
<div class="borrow">
<input id="text1" type="text" placeholder="Borrower Number" onfocus="this.value=''"/>
<input id="text2" type="text" placeholder="Borrower Last Name" onfocus="this.value=''" />
<input id="text3" type="text" placeholder="Borrower First Name" onfocus="this.value=''" />
<input id="text4" type="text" placeholder="Book Info"/>
<input id="text6" type="date" placeholder="Date Borrowed" />
<br>
</div>
<div class="borrow">
<p id="results"></p>
<button id="startScan">Start Scan</button>
<button id="savedb">Save </button>
</div>
<script type="text/javascript" src="js/scanQR.js"></script>
</body>
</html>
To save the value in input box should not use "resultDiv.innerHTML = s;"
Rather you should use "resultDiv.value = s" which will save your code to input box which you can use to save in SQLite Database.

Adding HTML from JavaScript removes written texts from input

I'm developing a web page by means of which user will add questions and answers. To add a new question the user clicks on the button and new div is added to container.
The problem is that when a new text-area is added, the text written in the other text-areas is removed.
View of filled text-area before clicking the button
View of text-area after clicking the button
Code:
<html lang="en" dir="ltr">
<head>
<meta charset="utf-8">
<title></title>
<script type="text/javascript">
const template = '<form class="eachtest">' +
'<textarea id="question" rows="4" cols="80" placeholder="Sual"></textarea>' +
'<br><strong> A </strong> ' +
'<textarea class="answer" rows="4" cols="80" placeholder="Cavab"></textarea><br>' +
'</form>';
function on_click() {
document.querySelector('.container').innerHTML += template;
}
</script>
</head>
<body>
<div class="container"></div>
<button id="add" type="button" name="button" onclick="on_click()">add</button>
</body>
</html>
innerHTML rebuild the whole content. Try the following:
<html lang="en" dir="ltr">
<head>
<meta charset="utf-8">
<title></title>
<script type="text/javascript">
const template = '<form class="eachtest"><textarea id="question" rows="4" cols="80" placeholder="Sual"></textarea><br><strong> A </strong> <textarea class="answer" rows="4" cols="80" placeholder="Cavab"></textarea><br></form>';
function on_click() {
document.querySelector('.container').insertAdjacentHTML('beforeend', template);
}
</script>
</head>
<body>
<div class="container">
</div>
<button id="add" type="button" name="button" onclick="on_click()">add</button>
</body>
</html>
For more info on innerHTML, click here
As you should avoid using inline JS and CSS, I propose you the following:
Create a hidden div id="template" in your HTML,
Use JS to append its content after your container when you click the "add" button.
I also changed your id="question" to class="question" as you can add multiple ones.
const template = document.querySelector('#template').innerHTML;
var container = document.querySelector('.container');
document.querySelector('#add').onclick = function() {
container.insertAdjacentHTML('beforeend', template);
}
#template {
display: none;
}
<html lang="en" dir="ltr">
<body>
<div class="container"></div>
<button id="add" type="button" name="button">Add</button>
<div id="template">
<form class="eachtest"><textarea class="question" rows="4" cols="80" placeholder="Sual"></textarea><br> <strong> A </strong><textarea class="answer" rows="4" cols="80" placeholder="Cavab"></textarea><br></form>
</div>
</body>
</html>
Hope it helps.
Use Jquery append() :D
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.0.3/jquery.min.js"></script>
<html lang="en" dir="ltr">
<head>
<meta charset="utf-8">
<title></title>
<script type="text/javascript">
const template = '<form class="eachtest"><textarea id="question" rows="4" cols="80" placeholder="Sual"></textarea><br><strong> A </strong> <textarea class="answer" rows="4" cols="80" placeholder="Cavab"></textarea><br></form>';
function on_click() {
$('.container').append(template)
}
</script>
</head>
<body>
<div class="container">
</div>
<button id="add" type="button" name="button" onclick="on_click()">add</button>
</body>
</html>

JQuery 2.0 closest with context

I thought that adding a DOM element as context to a JQuery method would restrict the method to looking ONLY at that element and its descendants instead of the entire document. If this is the case...
Why does this:
<!DOCTYPE html>
<html>
<head>
<title>Example</title>
<script src="jquery-2.0.2.js" type="text/javascript"></script>
<link rel="stylesheet" type="text/css" href="styles.css"/>
<script type="text/javascript">
$(document).ready(function() {
var contextElem = document.getElementById("row1");
$("img").closest(".drow", contextElem).each(function(index, elem) {
console.log("Context Element: " + elem.tagName + " " + elem.className
+ " " + elem.id);
});
});
</script>
</head>
<body>
<h1>JQuery Closest Example</h1>
<form method="post">
<div id="oblock">
<div class="dtable">
<div id="row1" class="drow">
<div class="dcell">
<img src="cell11.png"/><label for="cell11">Cell 1 1:</label>
<input name="cell11Value" value="0" required>
</div>
<div class="dcell">
<img src="cell12.png"/><label for="cell12">Cell 1 2:</label>
<input name="cell12Value" value="0" required >
</div>
</div>
<div id="row2"class="drow">
<div class="dcell">
<img src="cell21.png"/><label for="cell21">Cell 2 1:</label>
<input name="cell21Value" value="0" required>
</div>
<div class="dcell">
<img src="cell22.png"/><label for="cell22">Cell 2 2:</label>
<input name="cell22Value" value="0" required >
</div>
</div>
</div>
</div>
<div id="buttonDiv"><button type="submit">Save</button></div>
</form>
</body>
</html>
J
Result in this in the console:
Context Element: DIV drow row2
Instead of this:
Context Element: DIV drow row1
???
Passing in a context means jQuery will look for your selector as a descendent of context. In your case, your selector and context are the same element.

Categories

Resources