此功能中的功能不起作用,添加到收藏夹 E-commerce 项目

the function in this function doesnt work, add to favorites E-commerce project

我需要做的是当我点击 heartBtn 它变成红色并将该项目添加到本地存储 productsInFavArr 中的 object 数组中,当我点击它应该再次变成灰色并从 productsInFavArr 中删除 object。 添加功能在将项目添加到 arr 部分时工作正常,但 drawProductUI 函数应该检查产品是否存在于 productsInFacArr 中,btn 将为红色,如果不存在则为灰色,所以添加和删​​除项目后,我将 drawProductUI 功能放在添加和删除功能中,但直到我重新加载页面后它才起作用

并且删除功能在两次单击后从 arr 中删除了 object 并且仍然没有改变 btn

的颜色

所以我的主要问题是在添加或删除项目后更改 btn 的颜色,并且删除功能在单击两次后删除项目

代码如下:

// Draw Product UI
function drawProductUI(array){
var productsUI = array.map((item) => {        
    if (productsInFavArr) {
        for (const favProd of productsInFavArr){
                if (favProd.id === item.id) {
                    // console.log(favProd);
                return `
            <div class="product-item"> 
            <div class="product-img-container">
            <img src=${item.imgURL} alt="products" class="product-img" width="100%" height="150px">
            </div>
            <div class="product-text">
                <h2 class="product-title">${item.title}</h2>
                <span class="product-desc">${item.desc}</span>
                <p class="product-price">USD ${item.price}</p>
            </div>
            <div class="product-btns">
                <button class="add-to-cart">Add To Cart</button>
                <button class="heart-btn heart-icon-red" onclick="removeItemFromFav( ${item.id} )"><i class="far fa-heart"></i></button>
            </div>
            </div>
            `;
            }
    }}
    return`
    <div class="product-item"> 
        <div class="product-img-container">
            <img src=${item.imgURL} alt="products" class="product-img" width="100%" height="150px"> 
        </div>
        <div class="product-text">
            <h2 class="product-title">${item.title}</h2>
            <span class="product-desc">${item.desc}</span>
            <p class="product-price">USD ${item.price}</p>
        </div>
        <div class="product-btns">
            <button class="add-to-cart">Add To Cart</button>
            <button class="heart-btn heart-icon" ><i class="far fa-heart"></i></button>
        </div>
    </div>
    `
});
    productsContainer.innerHTML = productsUI.join("");    
}
drawProductUI(allProducts)


// add to favorites
for(let f=0; f < heartBtn.length; f++){
heartBtn[f].addEventListener("click" ,()=>{
    addToFavorites(allProducts[f]);
    function addToFavorites(product){
        if (localStorage.getItem("userValidate") && localStorage.getItem("passValidate")) {
            let productsInFavObj = localStorage.getItem("productsInFavObj");
            productsInFavObj = JSON.parse(productsInFavObj);
            if(productsInFavObj != null){
                    if(productsInFavObj[product.id] == undefined){
                        productsInFavObj = { 
                            ...productsInFavObj,
                            [product.id] : product
                            }
                        
                    }
            }else{
                productsInFavObj = {
                    [product.id] : product
                }
        }
        let productsInFavArr = Object.values(productsInFavObj)
    
        localStorage.setItem("productsInFavArr" , JSON.stringify(productsInFavArr) )
        localStorage.setItem("productsInFavObj" , JSON.stringify(productsInFavObj) )
    
        }else{
            window.location.href = "login.html";
        }
    
    }
    drawProductUI(allProducts)
}) 
}


// Remove From Favorite
function removeItemFromFav(id){

for(let f=0; f < heartBtn.length; f++){
    let productsInFavArr = localStorage.getItem("productsInFavArr")
    if(productsInFavArr){
        let items = JSON.parse(productsInFavArr);
        console.log("removed item:",allProducts[f]);
        let filteredItems = items.filter((item) => item.id !== id);
        localStorage.setItem("productsInFavArr" , JSON.stringify(filteredItems));        
        localStorage.setItem("productsInFavObj" , JSON.stringify(filteredItems) )
        drawProductUI(allProducts)
        console.log(filteredItems);
        if(filteredItems.length==0){
            localStorage.removeItem("productsInFavArr")
            localStorage.removeItem("productsInFavObj")
        }
    }
}
}

这是产品示例

let products = [
{
    title: "Sunglasses",
    imgURL: "images/Products/sunglasses.jpg",
    desc: "Lorem ipsum dolor sit amet consectetur adipisicing elit. Aut nulla adipisci fugiat pariatur recusandae repudiandae fuga molestias doloremque itaque obcaecati.",
    price:80,
    id: 1
},
{
    title: "Laptop",
    imgURL: "images/Products/laptop.jpg",
    desc: "Lorem ipsum dolor sit amet consectetur adipisicing elit. Aut nulla adipisci fugiat pariatur recusandae repudiandae fuga molestias doloremque itaque obcaecati.",
    price:100,
    id: 2
},
{
    title: "Microphone",
    imgURL: "images/Products/mic.jpg",
    desc: "Lorem ipsum dolor sit amet consectetur adipisicing elit. Aut nulla adipisci fugiat pariatur recusandae repudiandae fuga molestias doloremque itaque obcaecati.",
    price:75,
    id: 3
},
{
    title: "Cat",
    imgURL: "images/Products/cat.jpg",
    desc: "Lorem ipsum dolor sit amet consectetur adipisicing elit. Aut nulla adipisci fugiat pariatur recusandae repudiandae fuga molestias doloremque itaque obcaecati.",
    price:200,
    id: 4
},
]

谢谢

drawProductUI 函数中,您没有读取本地存储值,但它取决于 productsInFavArr,它可能只读取一次本地存储值。我认为您需要在调用 drawProductUI 时获取新值,以便在不重新加载页面的情况下反映对本地存储所做的更改。

function drawProductUI(array){
    let productsInFavArr = JSON.parse(localStorage.getItem("productsInFavArr")) || []; // read the value here so it's fresh before redraw happens
    var productsUI = array.map((item) => {
    // rest of the function code

drawProductUI 函数中,您为所选项目定义处理程序:

<button class="heart-btn heart-icon-red" onclick="removeItemFromFav(${item.id})"> 
   <i class="far fa-heart"></i>
</button>

您应该对未选择的按钮版本执行相同的操作:

<button class="heart-btn heart-icon" onclick="addToFavorites(${item.id})">
    <i class="far fa-heart"></i>
</button>

这样,每次重绘 UI 时都会附加点击处理程序,而不仅仅是在读取 js 文件时附加一次,这是您当前定义处理程序时的情况。

有了这个,你需要在顶层定义 addToFavorites 函数,所以在循环之外,就像你定义 removeItemFromFav.

由于处理程序现在获取产品的 ID,因此您需要在处理之前找到合适的产品。

您还想在单击时重绘 UI,因此请将适当的方法添加到该函数的底部。

我已附上说明这些更改的评论:

function addToFavorites(id){ // this is now defined at the top level as removeItemFromFav
    if (localStorage.getItem("userValidate") && localStorage.getItem("passValidate")) {
        const product = allProducts.find(p => p.id == id); // this and next lines handle product lookup
        if (!product) { return; }
        let productsInFavObj = localStorage.getItem("productsInFavObj");
        productsInFavObj = JSON.parse(productsInFavObj);
        if(productsInFavObj != null){
            if(productsInFavObj[id] == undefined){
                productsInFavObj = { 
                    ...productsInFavObj,
                    [id] : product
                }            
            }
        }else{
            productsInFavObj = {
               [id] : product
            }
        }
        let productsInFavArr = Object.values(productsInFavObj)
        localStorage.setItem("productsInFavArr" , JSON.stringify(productsInFavArr) )
        localStorage.setItem("productsInFavObj" , JSON.stringify(productsInFavObj) )
        drawProductUI(allProducts); // this redraws the UI
    }else{
        window.location.href = "login.html";
    }
}
    

您最后要更正的是 removeItemFromFav 函数。 循环是不必要的

function removeItemFromFav(id){
    // loop is gone now, also console.logs are gone
    let productsInFavArr = localStorage.getItem("productsInFavArr")
    if(productsInFavArr){
        let items = JSON.parse(productsInFavArr);
        let filteredItems = items.filter((item) => item.id !== id);
        localStorage.setItem("productsInFavArr" , JSON.stringify(filteredItems));        
        localStorage.setItem("productsInFavObj" , JSON.stringify(filteredItems) )
        drawProductUI(allProducts)
        if(filteredItems.length==0){
            localStorage.removeItem("productsInFavArr")
            localStorage.removeItem("productsInFavObj")
        }
    }
}