I want to set information to localstorage - javascript

playlist = [];
//저장
function save() {
localStorage.setItem("playlist",JSON.stringify(playlist));
}
// 리스트 생성
$('td#btn-add-row').click(function() {
// id 구하기
var list_num = 1;
for(var i=1; i <= 100; i++ )
{
if ( $('#basic tr td:nth-child(1)').hasClass(String(i)) == false )
{
list_num = i; break;
}
}
// 추가
const tbody = document.getElementById('my-tbody');
const tr = document.createElement("tr");
tr.id = list_num;
const td1 = document.createElement("td");
td1.className = list_num;
td1.setAttribute("style", "cursor:pointer");
const td2 = document.createElement("td");
td2.innerText = "음악 "+list_num;
const td3 = document.createElement("td");
td3.innerHTML = "<input type='text' name='tb'>";
const td4 = document.createElement("td");
td4.innerHTML = "<input type='text'>";
tbody.appendChild(tr);
tr.appendChild(td1);
tr.appendChild(td2);
tr.appendChild(td3);
tr.appendChild(td4);
const data = {
url:$("#my-tbody > tr:nth-child(" + list_num + ")> td> input").val(),
name:$("#my-tbody > tr:nth-child(" + list_num + ")> td:nth-child(4)> input").val(),
id:list_num
}
playlist.push(data);
save();
// 동적 테이블
$("#basic").tableDnD();
});
I wish that URL, name, id are stored in a local storage according to the id value of tr. However, this code produces strange results in localstorage. The problem is that the URL and name are not saved. What should I do?

The reference of a value does not magically keep on updating. So you need to add event listeners to keep updating it. So easiest thing to do is add event listeners to the inputs and update the array of objects.
Below is the basic idea. (note: StackOverflow blocks local storage so I commented it out.)
// const playlist = localStorage.playlist ? JSON.parse(localStorage.playlist) : [];
const playlist = [];
const tableTbody = document.querySelector("#myTable tbody");
for (let i = 0; i < 10; i++) {
// either get the current value from localstorage or create new record
playlist[i] = playlist[i] || {
id: i,
url: '',
name: ''
};
const currentItem = playlist[i]
//create the table row
const tr = document.createElement("tr");
tr.dataset.id = currentItem.id;
// create the id cell
const tdId = document.createElement("td");
tdId.textContent = i + 1;
// create the url cell
const tdUrl = document.createElement("td");
const inputUrl = document.createElement("input");
inputUrl.type = "text";
inputUrl.name = 'url';
inputUrl.value = currentItem.url;
tdUrl.append(inputUrl);
// create the name cell
const tdName = document.createElement("td");
const inputName = document.createElement("input");
inputName.type = "text";
inputName.name = 'name';
inputName.value = currentItem.name;
tdName.append(inputName);
// add the cells to the row
tr.append(tdId);
tr.append(tdUrl);
tr.append(tdName);
// add the row to the table
tableTbody.append(tr);
}
tableTbody.addEventListener("input", function (event) {
// see what triggered the input event
const input = event.target;
// find the row so we know what record to update
const rowId = input.closest("tr").dataset("id");
// what field to update
const field = input.name;
// update the record
playlist[rowId][field] = input.value.trim();
// update local storage
// localStorage.playlist = JSON.stringify(playlist);
});
<table id="myTable">
<thead>
<tr>
<th>ID</th><th>url</th><th>name</th>
</tr>
</thead>
<tbody></tbody>
</table>

Related

Make an alterable/editable html table from javascript array

Hi I am having trouble figuring out how to make my rows editable
Html:
<body>
<div>
<button>Get</button>
<div id="table"></div>
</div>
</tbody>
</table>
</body>
I have a participant that i will want to also alter when i alter the html table
Javascript related to the participant:
function Participant(id, name) {
this.id = id;
this.name = name;
}
var participantArray = [];
//Used to get data from xml into the Participant and then add him to the array
var xpartic = xmlDoc.getElementsByTagName("participant");
for (i = 0; i < xpartic.length; i++) {
participanttxt += "Participant - " + "Id: " + xpartic.item(i).getAttribute("id") + " Name: " + xpartic.item(i).getAttribute("name") + "\n" ;
var novo = new Participant(xpartic.item(i).getAttribute("id"),xpartic.item(i).getAttribute("name"));
this.addtoArray = function(){
participantArray.push(novo)
}();
}
console.log(participantArray);
Javascript related to the table:
I dont know how to allow for the rows to be editable
let btnGet = document.querySelector('button');
let myTable = document.querySelector('#table');
// criação das tabelas
let headers = ['ID', 'NAME'];
btnGet.addEventListener('click', () => {
let table = document.createElement('table');
let headerRow = document.createElement('tr');
headers.forEach(headerText => {
let header = document.createElement('th');
let textNode = document.createTextNode(headerText);
header.appendChild(textNode);
headerRow.appendChild(header);
});
table.appendChild(headerRow);
participantArray.forEach(emp => {
let row = document.createElement('tr');
Object.values(emp).forEach(text => {
let cell = document.createElement("td");
let textNode = document.createTextNode(text);
cell.appendChild(textNode);
row.appendChild(cell);
})
table.appendChild(row);
});
myTable.appendChild(table);
});
This generates the following:
https://imgur.com/a/zyxQd32
I wanted to be able to alter these rows and then do something like this to the array
onTableAlter(){
for(...){
if(altered.id==participant.id){
participant.name=altered.name
}
}
}
When that table is altered.
I appreciate any help!

table won't allow me to append more than 2 cells

function createTable(data_array){
const billing_table_body = document.querySelector('#billing_progile_Table > tbody')
//we loop through object array and have access to each individual JSON
for(var i = 0; i<objarray.length;i++){
console.log("data : ",objarray[i].profileName)
//create row
const tr = document.createElement('tr'); //creating the row
console.log('creating new row');
//append individual tds
const td = document.createElement('td')
td.textContent = objarray[i].profileName//appends data from the json cell
td.className = 'text_td';
tr.appendChild(td);
const td_two = document.createElement('td')
td_two.textContent = objarray[i].cardemail
td.className = 'text_td';
tr.appendChild(td_two);
const td_three = document.createElement('td')
td_two.textContent = objarray[i].cardownername
td.className = 'text_td';
tr.appendChild(td_three);
const td_four = document.createElement('td')
td_two.textContent = objarray[i].cardnumber
td.className = 'text_td';
tr.appendChild(td_four);
//append whole row to tr
billing_table_body.appendChild(tr);
}
}
im trying to append the cells into the table with their data but the table won't allow me to do it and I need to write it like this because im trying to access specific objects of the json array. any help im new to JAVASCRIPT AND JSON
Please stop adding row and cells with createElement() method...!
const billing_table_body = document.querySelector('#billing_progile_Table > tbody')
function createRows(data_array)
{
data_array.forEach(el =>
{
let newRow = billing_table_body.insertRow()
newRow.insertCell().textContent = el.profileName
newRow.insertCell().textContent = el.cardemail
newRow.insertCell().textContent = el.cardownername
newRow.insertCell().textContent = el.cardnumber
newRow.querySelectorAll('td').forEach(td=>td.className='text_td')
})
}

Delete a row from a table (HTML/JS)

Title is pretty self-explanatory; I'm trying to add a delete button to each row of a table, but right now it's deleting the table headers instead of the actual row. This is the Javascript; any tips?:
function addRow() {
var table = document.getElementById("todayTasks");
var row = document.createElement('tr');
row.id = "new_add";
var td0 = document.createElement("INPUT");
td0.type = "checkbox";
td0.id = "checkbox";
td0.onchange = updateItem;
var td1 = document.createElement('td');
var td2 = document.createElement('td');
var td3 = document.createElement("input");
td3.type = "button";
td3.value = "Delete";
td3.onclick = deleteFn;
if (document.getElementById('task').value === "") {
alert("Please provide a task.");
} else if (document.getElementById('duration').value === "") {
alert("Please provide a duration.");
} else {
td1.innerHTML = document.getElementById('task').value;
td2.innerHTML = document.getElementById('duration').value;
row.appendChild(td0);
row.appendChild(td1);
row.appendChild(td2);
row.appendChild(td3);
table.children[0].insertBefore(row, table.children[0].childNodes[1]);
}
function updateItem() //Cross out when checked
{
if (document.getElementById("checkbox").checked) {
document.getElementById("new_add").style.textDecoration = "line-through"
} else {
document.getElementById("new_add").style.textDecoration = "none"
}
}
function deleteFn(x) {
var i = x.rowIndex;
document.getElementById("todayTasks").deleteRow(i);
}
Your delete function take an event as an argument, that event hold a reference to the element via its property target. you can than get the tr which is the parent element of your input (if you wrap the input inside a td it would be the grand parent), then you can juste remove this element from the table
function deleteFn(event) {
var input = event.target;
var currentRow = input.parentNode;
document.getElementById("todayTasks").removeChild(currentRow);
}

Javascript generated table - How to update other cells in a row when a number input value in this row changes

I am facing a problem for this day I am creating a pop-up cart with a table, I create an array with
ID | NAME | QUANTITY | PRICE
then I generate the table from this array with javascript.My problem is I want to be able to update the price and the total when I change the quantity for a specific item line (= quantity in the table row). This should work for all generated table rows.
This is my javascript code:
var cartCount = 0;
var Total = 0;
var id = 1;
var labels = ['Name', 'Quantity', 'Price'];
var items;
var cartElement = document.getElementById('cartDisplay');
var counterElement = document.getElementById('counterDisplay');
function cartClick(name, quantity, price) {
const x = {
id: id,
name: name,
quantity: quantity,
price: price
};
if (Obj.some(e => e.name === x.name)) {
console.log('already there');
} else {
Obj.push(x);
cartCount = cartCount + 1;
Total = Total + x.price;
id = id +1;
buildTable(labels, Obj, document.getElementById('modalBODY'));
items = Obj;
console.log(items);
}
CheckCart(cartCount);
console.log(cartCount);
}
function CheckCart(counter) {
if (counter > 0) {
cartElement.style.display = "block";
counterElement.innerHTML = counter;
} else {
cartElement.style.display = "none";
}
}
function buildTable(labels, objects, container) {
container.innerHTML = '';
var table = document.createElement('table');
// class table
table.classList.add("cartTable");
var thead = document.createElement('thead');
var tbody = document.createElement('tbody');
var theadTr = document.createElement('tr');
for (var i = 0; i < labels.length; i++) {
var theadTh = document.createElement('th');
theadTh.classList.add("cartTh");
theadTh.setAttribute("colSpan", "2");
theadTh.style.padding = '12px';
theadTh.innerHTML = labels[i];
theadTr.appendChild(theadTh);
}
thead.appendChild(theadTr);
table.appendChild(thead);
for (j = 0; j < objects.length; j++) {
var tbodyTr = document.createElement('tr');
for (k = 0; k < labels.length; k++) {
var tbodyTd = document.createElement('td');
tbodyTd.classList.add("cartTd");
tbodyTd.setAttribute("colSpan", "2");
tbodyTd.style.padding = '12px';
if (labels[k] === "Quantity") {
var qinput = document.createElement('input');
qinput.setAttribute("type", "number");
qinput.setAttribute("min", "0");
qinput.setAttribute("max", "10");
qinput.setAttribute("id", "quantityInput");
qinput.setAttribute("value", objects[j][labels[k].toLowerCase()]);
tbodyTd.appendChild(qinput);
} else {
tbodyTd.innerHTML = objects[j][labels[k].toLowerCase()];
}
tbodyTr.appendChild(tbodyTd);
}
tbody.appendChild(tbodyTr);
}
table.appendChild(tbody);
var tfoot = document.createElement('tfoot');
var footTr = document.createElement('tr');
var footTh = document.createElement('th');
var footTd = document.createElement('td');
footTd.setAttribute("id", "totalElement")
tbodyTd.setAttribute("colSpan", "3");
footTh.setAttribute("colSpan", "4");
footTd.innerHTML = Total;
footTh.innerHTML = 'TOTAL';
footTd.classList.add("cartTd");
footTd.classList.add("footerTable");
footTh.classList.add("cartTh");
footTr.appendChild(footTh);
footTr.appendChild(footTd);
tfoot.appendChild(footTr);
table.appendChild(tfoot);
container.appendChild(table);
var beforeText = document.createElement("p");
beforeText.style.marginTop = '5px';
beforeText.innerHTML = "Requests";
container.appendChild(beforeText);
var input = document.createElement("INPUT");
input.setAttribute("type", "text");
input.style.width = '100%';
input.style.padding = '6px';
input.setAttribute("placeholder", "No onion, no tomato...");
container.appendChild(input);
}
I solved a similar problem by creating a rowid and when the user clicks into the row I check for changes. Here the main idea
tableRow.setAttribute("id", "row" + idTable + "_" + tableRow.rowIndex); // for easy handling and selecting rows
tableRow.addEventListener("click", function(){ ... here check for what ever change});
You could also go for a specific change in just one cell, so attach the eventlistener to each quantity cell and read the new value, validate and update other fields then
qinput.addEventListener("change", function(){ ... here check for what ever the change triggers });
EDIT fortheOP:
A generic example for adding an event listener to a tablerow this marks the selected table line red (class table-danger) and removes the colour from allother previous selected lines:
tableRow.addEventListener("click", function(){
tRowData = [];
if(this.classList.contains("table-danger")) {
this.classList.remove("table-danger");
return;
} else {
var nodeParent = this.parentNode;
var trows= nodeParent.getElementsByTagName("tr");
for(var i = 0; i < trows.length;i++) {
trows[i].classList.remove("table-danger");
}
this.classList.add("table-danger");
var cells = this.getElementsByTagName("td");
for ( i = 0; i < cells.length; i++) {
tRowData.push(cells[i].innerHTML); // e.g.: Here you could place your update routine
}
tRowData.push(this.getAttribute("id"));
tRowData.push(this.rowIndex);
return tRowData;
}
});

Why my selecting data only show the last data?

why i cannot select the first data and the second data when i tested using console.log
This is the table:
var ref = firebase.database().ref("recommendations");
ref.on("value", function(snapshot) {
// console.log(snapshot.val());
var recommendations = snapshot.val();
var keys = Object.keys(recommendations);
console.log(keys);
for (var i = 0; i < keys.length; i++) {
var k = keys[i];
var title = recommendations[k].title;
var link = recommendations[k].link;
var presenter = recommendations[k].presenter;
// document.getElementById('title').innerHTML = title;
// document.getElementById('presenter').innerHTML = presenter;
// document.getElementById('link').innerHTML = link;
var table = document.getElementById("data");
var tr = document.createElement('tr');
var td1 = tr.appendChild(document.createElement('td'));
var td2= tr.appendChild(document.createElement('td'));
var td3 = tr.appendChild(document.createElement('td'));
var tdEdit = tr.appendChild(document.createElement('td'));
td1.innerHTML = title;
td2.innerHTML = presenter;
td3.innerHTML = link;
tdEdit.innerHTML = "<button id='"+k+"' class='btn btn-default edit'>Edit</button>";
table.appendChild(tr);
}
$(document).ready(function() {
$(".edit").on("click", function(){
console.log(k);
})
});
});
The issue is that you log k which is a reference to inside the loop. So the loop go's key0 key1 key2 and stays key2 because thats the last value of k.
Use something like:
$(document).ready(function() {
$(".edit").on("click", function(){
// From the button perspective this references the Native element.
console.log(this.id); // or $(this).attr("id")
})
});

Categories

Resources