JS:从本地存储中删除/隐藏按钮文本

JS: Removing from local storage / hiding button text

各位晚上好。 试图结束我的待办事项列表,但我无法从 localStorage 中删除项目,除非使用错误的键删除所有内容,或者内容只是在页面刷新时重新出现。第二个较小的问题是按钮文本正在合并到 innerText 中,就像它应该的那样,但我找不到排除它的方法它目前被注释掉了,如果我不这样做,它就会破坏以前的入口。我在下面留下了我最近的一次相当糟糕的尝试,但除此之外,其余的似乎都在工作。

不确定是否可以附上整个代码,但在下面。

const todoForm = document.querySelector('#todoForm');
const todoList = document.querySelector('#todoList');
let todoItem = document.querySelector('#todoItem');
// const todo = JSON.parse(localStorage.getItem('todo'));

// Pull from storage
const savedList = JSON.parse(localStorage.getItem('todo')) || [];
for (let i = 0; i < savedList.length; i++) {
const newTodo = document.createElement('li');
newTodo.innerText = savedList[i].item;
const newButton = document.createElement('button');
let itemId = { id: new Date().getTime() };

// newButton.innerText = 'Remove';
newButton.setAttribute('id', itemId.id);
newTodo.isCompleted = savedList[i].isCompleted ? true : false;
if(newTodo.isCompleted) {
    newTodo.style.textDecoration = 'line-through';
}
todoList.appendChild(newTodo);
newTodo.appendChild(newButton);

}

// Add Item and Remove Button
todoForm.addEventListener('submit', function(e){
    e.preventDefault();
    const newTodo = document.createElement('li');
    const newItem = document.querySelector('#todoItem').value;
    const newButton = document.createElement('button');
    let itemId = { id: new Date().getTime() };
    // newButton.innerText = 'Remove';
    newButton.setAttribute('id', itemId.id);
    newTodo.innerText = newItem;
    newTodo.setAttribute('id', itemId.id);
    newTodo.isCompleted = false;
    todoList.appendChild(newTodo);
    newTodo.appendChild(newButton);
    todoForm.reset();

// Save to storage 
    savedList.push({ item: newTodo.innerText, isCompleted: false, id: new Date().getTime() });
    localStorage.setItem('todo', JSON.stringify(savedList));

});

// Strike Through Item
todoList.addEventListener('click', function(e){
    let clickListItem = e.target;

    if (!clickListItem.isCompleted){
        clickListItem.style.textDecoration = 'line-through';
        clickListItem.isCompleted = true;
    } else {
        clickListItem.style.textDecoration = 'none';
        clickListItem.isCompleted = false;
    }
    for (let i = 0; i < savedList.length; i++) {
        if (savedList[i].item === clickListItem.innerText) {
            savedList[i].isCompleted = !savedList[i].isCompleted;
            localStorage.setItem('todo', JSON.stringify(savedList));
        }
    }
});

// Remove from storage
todoList.addEventListener('click', function(e){
    let removeItem = e.target;
    const taskId = e.target.id;
    if (e.target.tagName === 'BUTTON'){
        e.target.parentNode.remove();
        removeFunc(taskId);
    }

});

function removeFunc(taskId){
    for (let i = 0; i < savedList.length; i++){
        const key = savedList[i].id;
        if(key === taskId.id){
            localStorage.removeItem(key);
            localStorage.setItem('todo', JSON.stringify(savedList));
        }
    }
}

感谢您的任何见解。

我的第一个猜测是,由于 ID 是由 Date.getTime() 在两个不同的时间调用定义的,所以这些 ID 是不一样的。我建议,当您在函数末尾按下 savedList 以添加项目时,您将 id 设置为 newItem.id,就像您设置项目名称一样,而不是调用getTime() 再次

我确实在您的代码中发现了一些问题。开始了。

  1. 删除文本重新出现 因为在添加项目时,如果您在它保存的本地存储中检查保存的值,则创建项目值设置为 newTodo.innerText 的待办事项对象额外的 Remove ,那是因为 innerText 获取 newTodo 下的元素文本(在我们的例子中,我们在那里有一个按钮)。作为修复,您只需要设置 textbox 的实际值而不是 innerText。您已经将其存储在名为 newItem
  2. 的变量中

是的,就像@cfinn16 指出的那样,当您将来自 remove 按钮属性的 ID 与来自 savedList 数组你会看到不匹配。作为解决方案,您可以转换 getTime().toString().

savedList.push({ item: newTodo.innerText, isCompleted: false, id: new Date().getTime() });
  1. 删除一个项目,实际上并没有从内存数组即savedList或本地存储中删除该项目。我们想要做的只是从 savedList 中获取 taskId,filter/remove 项,然后用相同的键将其替换到 localStorage 中。但是在页面刷新时加载每个 todoItems 时,您将新日期设置为每个 todoItems 的值,但这应该是本地存储本身的值。
let itemId = { id: new Date().getTime() };
  1. 删除项目,有类似的问题。在这里,您尝试使用文本从数组中查找被点击的项目,而不是我们可以使用 id 本身。
for (let i = 0; i < savedList.length; i++) {
        if (savedList[i].item === clickListItem.innerText) {
            savedList[i].isCompleted = !savedList[i].isCompleted;
            localStorage.setItem('todo', JSON.stringify(savedList));
        }
    }

解法: https://codepen.io/renishb10/project/editor/ANyqqo

如果您有任何问题,请告诉我。

在 Renish 的帮助下,我修改了以下内容并将其发布在此处,以便对其他人有所帮助。

// Save to storage 
    savedList.push({ item: newItem, isCompleted: false, id: new Date().getTime().toString() });
    localStorage.setItem('todo', JSON.stringify(savedList));

已将 new Date() 更改为字符串。正如 Renish 和 cfinn 指出的那样,我有不匹配 .id。将 newTodo 更改为 newItem 绕过我的 innerText 从被继承的按钮。

// Pull from Storage
newButton.innerText = 'Remove';
newButton.setAttribute('id', savedList[i].id);

修改了我从存储中提取代码以反映新按钮 .id

function removeFunc(taskId){
    splicedList = savedList.filter(l => l.id != taskId)
    localStorage.setItem('todo', JSON.stringify(splicedList));
    }

根据 .id,使用过滤器来查找要删除的项目。 Github 完整修改代码: https://github.com/BreadsticksN7/collections/blob/20b679fc704d05af5576faa3963f676c0bd2665e/todolist.js

感谢大家和他们的帮助。