localStorage不保存/显示项目

时间:2019-07-03 14:34:30

标签: javascript html local-storage

我做我的待办事项清单。 (我学习香草JS)。我在将某些项目保存到localStorage时遇到了一些问题。当我使用Google chrome(F12)时,看到undefiend。也许,我没有正确保存到localStorage。我试图将var task更改为数组,但这无济于事。请告诉我我的错误。我知道,我的代码必须重写,这是我在JS上的第一个代码。 P.s.在控制台中(在stackOverflow中),我遇到了这个错误

{
  "message": "Uncaught SyntaxError: Unexpected identifier",
  "filename": "https://stacksnippets.net/js",
  "lineno": 348,
  "colno": 6
}

但在我的浏览器中没有。

var task = document.querySelector("ul");
var forTask;
function toLocal(){
    forTask = task.innerHTML;
    localStorage.setItem("forLocal",forTask);
}
function newElement(newChild) {
    let btnDel= document.createElement("button");
    btnDel.className = "fa fa-trash-o";
    let myEd = document.getElementById("myEdit");
    let spanClose1 = document.getElementsByClassName("close1")[0];
    let spanRedact = document.getElementsByClassName("redact")[0];
    let myDel = document.getElementById("myDelete");
    let spanClose = document.getElementsByClassName("close")[0];
    let spanYes = document.getElementsByClassName("yes")[0];
    //create button
    let divWithBut = document.createElement("div");
    divWithBut.className = "forButt";
    let btnRedact = document.createElement("button");
    btnRedact.className = "fa fa-pencil";
    //redact but
    btnRedact.onclick = function(){
        myEd.style.display = "block";
        let editText = document.getElementById("editText");
        let divWithText = divWithBut.parentElement.getElementsByClassName("todoPost")[0];
        editText.value = divWithText.innerHTML;
        editText.currentTarget;
        spanRedact.onclick = function(){
            divWithText.textContent = editText.value;
            divWithText.className = "todoPost";
            myEd.style.display = "none";
        };
        spanClose1.onclick = function() {
            myEd.style.display = "none";
        };
    }
    /*************************** */
    /*done but*/
    let doneBut = document.createElement("button");
    doneBut.className = "fa fa-check-circle-o";
    doneBut.onclick = function(){
        let divWithText = divWithBut.parentElement.getElementsByClassName("todoPost")[0];
        divWithText.classList.toggle("checked");
    }
    /******************* */
    divWithBut.appendChild(btnRedact);
    divWithBut.appendChild(doneBut);
    divWithBut.appendChild(btnDel);
    /******************/
//for index
    let indexDiv = document.createElement("div");
    indexDiv.className = "indexDiv";
    let numbInd = 1;
    indexDiv.innerHTML = numbInd;
    /*********************************** */
        //create arrow
    let divWithArrow = document.createElement("div");
    divWithArrow.className = "myArrow";
    let arrowUP = document.createElement("i");
    arrowUP.className = "fa fa-chevron-up";
    let arrowDown = document.createElement("i");
    arrowDown.className = "fa fa-chevron-down";
    divWithArrow.appendChild(arrowUP);
    divWithArrow.appendChild(arrowDown);
    //for date
    let date = new Date();
    let curr_date = date.getDate();
    let curr_month = date.getMonth()+1;
    let curr_year = date.getFullYear();
    let curr_hour = date.getHours();
    let curr_minutes = date.getMinutes();
    let d = (curr_date + "." + curr_month + "." + curr_year+"<br>"+curr_hour+":"+curr_minutes);
    let divTime = document.createElement("div");
    divTime.style.textAlign = "center";;
    divTime.innerHTML = d;
    //***************************/
    let div1 = document.createElement("div");
    div1.className = "timeComent";
    let myli = document.createElement("li");
    myli.className = "todoPost";
    let addField = document.getElementById("addField").value;
    task = document.createTextNode(addField);
    myli.appendChild(task);
    div1.appendChild(divTime);
    div1.appendChild(indexDiv);
    div1.appendChild(divWithArrow);
    div1.appendChild(myli);
    divWithBut.style.display = "flex";
    div1.appendChild(divWithBut);
    if (addField === '') {
        alert("You must write something!");
    } else {
        document.getElementById("forToDo").appendChild(div1);
        toLocal();
    }
    document.getElementById("addField").value = "";
    //delete but
    btnDel.onclick = function(){
        myDel.style.display = "block";
        spanClose.onclick = function() {
            myDel.style.display = "none";
        };
        spanYes.onclick = function() {
            myDel.style.display = "none";
            div1.remove();
        };
    }
toLocal();
}
if(localStorage.getItem("forLocal")){
    task.innerHTML = localStorage.getItem("forLocal");
}
*{
    margin: 0;
    padding: 0;
}
header{

    width: 100%;
    display: flex;
    align-items: center;
    align-content: center;
    justify-content: center;
    overflow: auto;
}
.firstBar{
    width: 100%;
    display: flex;
    align-items: center;
    align-content: center;
    justify-content: center;
    overflow: auto;
}
.indexDiv{
    font-style: normal;
    text-align: center;
    color: #fff;
    width: 15px;
    height: 20px;
    margin: 10px;
    background-color: #888;
}
.fafaArrow{
    font-size: 24px;
    color: #000;
}
.timeComent{
    margin-top: 15px;
    margin-bottom: 15px;
    display: flex;
    justify-content:center;
    align-items: center;
}
.numberpost{
    padding: 5px;
    color: rgb(255, 255, 255);
    background: rgb(141, 112, 112);
}
.todoPost{
    background-color: #eee;
    width: 50%;
    margin: 5px;
    overflow: auto;
    text-align: justify;
}
.shadow {
    background: rgba(102, 102, 102, 0.5);
    width: 100%;
    height: 100%;
    position: absolute;
    top: 0;
    left: 0;
    display: none;
}
.window {
    width: 300px;
    height: 50px;
    text-align: center;
    padding: 15px;
    border: 3px solid #0000cc;
    border-radius: 10px;
    color: #0000cc;
    position: absolute;
    top: 0;
    right: 0;
    bottom: 0;
    left: 0;
    margin: auto;
    background: #fff;
}
.shadow:target {display: block;}


.redact {
    display: inline-block;
    border: 1px solid #0000cc;
    color: #0000cc;
    margin: 10px;
    text-decoration: none;
    background: #f2f2f2;
    font-size: 14pt;
    cursor:pointer;
    right: 0;
    top: 0;
    padding: 12px 16px 12px 16px;
}
.redact:hover {
    background-color: #68f462;
    color: white;}
.close{
    display: inline-block;
    border: 1px solid #0000cc;
    color: #0000cc;
    margin: 10px;
    text-decoration: none;
    background: #f2f2f2;
    font-size: 14pt;
    cursor:pointer;
    right: 0;
    top: 0;
    padding: 12px 16px 12px 16px;
}
.close:hover{
    background-color: #f44336;
    color: white;
}
/* Style the close button */
.close3 {
    position: absolute;
    right: 0;
    top: 0;
    padding: 12px 16px 12px 16px;
}

.yes {
    display: inline-block;
    border: 1px solid #0000cc;
    color: #0000cc;
    margin: 10px;
    text-decoration: none;
    background: #f2f2f2;
    font-size: 14pt;
    cursor:pointer;
    right: 0;
    top: 0;
    padding: 12px 16px 12px 16px;
}
.yes:hover{
    background-color: #68f462;
    color: white;
}

.close1{
    display: inline-block;
    border: 1px solid #0000cc;
    color: #0000cc;
    margin: 10px;
    text-decoration: none;
    background: #f2f2f2;
    font-size: 14pt;
    cursor:pointer;
    right: 0;
    top: 0;
    padding: 12px 16px 12px 16px;
}
.close1:hover{
    background-color: #f44336;
    color: white;
}

/* When clicked on, add a background color and strike out text */
div li.checked {
    background: #888;
    color: #fff;
    text-decoration: line-through;
}

/* Add a "checked" mark when clicked on */
div 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;
}
<!DOCTYPE html>
<html>
<head>
    <title>TO DO List</title>
    <link rel="stylesheet" type="text/css" href="styles/style.css" >
    <link rel="stylesheet" href="https://cdnjs.cloudflare.com/ajax/libs/font-awesome/4.7.0/css/font-awesome.min.css">
</head>
<body>
<header>
    <input id="addField" type="text" size="70%" placeholder="Task" name="Task">
    <button type="button" onclick="newElement()">Add</button>
</header>
<div>
    <div class="firstBar">
        <div class="fafaArrow">
            <i class="fa fa-caret-up" ></i>
            <i class="fa fa-caret-down"></i>
            <input class="inptxt" type="text" size="50%" name="Task">
            <i class="fa fa-filter"></i>
        </div>
    </div>
</div>
    <ul id="forToDo" >
    </ul>
<div id="myDelete" class="shadow">
    <div class="window">Delete item?<br>
        <span class="yes">Yes</span>
        <span class="close">No</span>
    </div>
</div>
<div id="myEdit" class="shadow">
    <div class="window">
        Edit text?<br>
        <label>
            <textarea id="editText"></textarea>
        </label>
        <span class="redact">Save</span>
        <span class="close1">Cancel</span>
    </div>
</div>
<script src="js/script2.js"></script>
</body>
</html>

2 个答案:

答案 0 :(得分:0)

需要以下更改。

1-为以下任务变量分别设置两个变量。

from django.shortcuts import render, redirect
from django.contrib import messages
from .forms import UserRegisterForm

# Create your views here.
def register(request):
    if request.method == 'POST':
        register_form = UserRegisterForm(request.POST)
        if register_form.is_valid():
            register_form.save()
            username = register_form.cleaned_data.get('username')
            email = register_form.cleaned_data.get('email')
            messages.success(request, f'Account created for {username}')
            return redirect('website-home')
    else:
        register_form = UserRegisterForm()
        return render(request, 'users/register.html', {'register_form':register_form})

例如,第一个是“ ulElement”,第二个是“ task”。
这是为了防止覆盖先前定义的值。

2-移动获取ul元素的时间并加载localStorage。

{% extends 'base.html' %}
{% load crispy_forms_tags %}

<!-- Extra Styling? -->
{% block extrahead %}
{% endblock extrahead %}

<!-- Include Navbar? -->
{% block navbar %}
{% include 'navbar.html' %}
{% endblock navbar %}

<!-- Main HTML Page Cotent -->
{% block content %}

<div class="container">
    <form>
        <fieldset>
            <div class="row justify-content-center">
                <div class="col-6">
                    {% csrf_token %}
                    <legend>
                        {{register_form|crispy}}
                    </legend>
                </div>
            </div>
        </fieldset>
        <div class='row justify-content-center'>
            <div class="col-6">
                <button type="submit" class="btn btn-success float-right">Register</button>
            </div>
        </div>
    </form>
</div>

{% endblock content %}

为确保元素存在,应在触发DOMContentLoaded事件之后调用document.querySelector()。
https://developer.mozilla.org/en-US/docs/Web/API/Window/DOMContentLoaded_event

3-删除toLocal();在newElement()函数的末尾。
就我的测试代码而言,不需要此语句。

答案 1 :(得分:0)

当您向页面添加元素时,您可以在特定时间点

task = document.createTextNode(addField);

由于task是全局变量(您在顶部声明了该变量),因此您正在使用创建的TextNode遮盖了它,因此当您调用toLocal时而你

forTask = task.innerHTML;

task没有innerHTML属性,因此它返回undefined

此外,由于某些原因,您在toLocal的末尾再次调用newElement。这不是 the 问题,而是您可能需要考虑的问题。我不确定这就是你想要的。

@TakayashiHarano提供了一些提示来解决此问题,但是我不确定您想要的只是在本地存储中具有最新元素。因此,我将重新编写toLocal,使其将字符串(项目的文本)作为输入,将其写入JSON数组的末尾(已经填充了以前本地存储中的内容),并且将阵列放回本地存储。

function toLocal(toAdd) {
    let storage = localStorage.getItem('forLocal');
    if (storage === null) {
        storage = [];
    } else {
        storage = JSON.parse(storage);
    }
    storage.push(toAdd);
    localStorage.setItem('forLocal', JSON.stringify(storage));
}

然后,您应该修改代码中读取本地存储的部分(末尾的部分),以基本模拟添加新项的方式,就像创建新任务时所做的一样,但对于已解析的JSON中的每个项,从本地存储。

为了公平起见,您的代码需要大量重写才能实现此目的,因此,我将作为练习留给您。