【问题标题】:How do I count up in Firebase Firestore in front-end如何在前端的 Firebase Firestore 中进行计数
【发布时间】:2020-09-12 03:37:15
【问题描述】:

我正在创建一个允许用户跟踪新习惯的应用,并使用 Firestore 保存用户的数据。 数据库中存储的数据如下:

  • 标题(习惯名称)
  • 数(我做了多少次这个习惯)
  • 目标(我想每天/每周/每月检查多少次这个习惯)
  • Streak(我连续几天/几周/一个月/多少天检查过这个习惯)

我的目标基本上是单击一个对象(在本例中为 #container 中的火焰),并将 count 添加到数据库中。

这就是我现在得到的:

// Real-time listener
db.collection('habits').onSnapshot((snapshot) => {
    snapshot.docChanges().forEach(change => {
        if(change.type === 'added'){
            renderHabit(change.doc.data(), change.doc.id);
        }
    });
})

// Add new habit
const form = document.querySelector('form');
form.addEventListener('submit', evt => {
    evt.preventDefault();
    const habit = {
        title: form.habitTitle.value,
        count: 0,
        goal: form.habitGoal.value,
        streak: 0
    };

    db.collection('habits').add(habit)
        .catch(err => console.log(err));
    form.habitTitle.value = '';
    form.habitGoal.value = '';
})

// Update counter
const habitContainer = document.querySelector('.newHabit');
habitContainer.addEventListener('click', evt => {
    //console.log(evt);
    if(evt.target.tagName === 'I'){
        const id = evt.target.getAttribute('data-id');
        db.collection('habits').doc(id).update({
            count: 1
        });
    }
});

const habits = document.querySelector('.newHabit');

// Render habit data
const renderHabit = (data, id) => {
    const html = `
        <div id="wrapper" data-id="${id}">
            <div id="container">
                <span id="title">${data.title}</span>
                <div class="streakContainer">
                    <span id="streak">${data.streak}</span>
                    <i data-id="${id}">????</i>
                </div>

                <div class="countContainer">
                    <span id="count">${data.count}</span>
                    <span>/</span>
                    <span id="goal">${data.goal}</span>
                </div>

                <div id="progressbar">
                    <div id="timer"></div>
                    <div id="progressbaroverlay"></div> 
                </div>
            </div>
        </div>
    `;

    habits.innerHTML += html;
};

我试图声明var countNumber = 0; 最终在// Update counter 内的clickevent 上使用countNumber = countNumber++,这不起作用,因为countNumber 在刷新时再次设置为0(我相信)。

希望我足够清楚:)

谢谢!

【问题讨论】:

  • 您的代码中的countNumber 在哪里?您是否在前端使用任何类型的状态容器?
  • @jmargolisvt 我已经从我的代码中删除了countNumber,因为它不起作用,但我在我的 JS 文件的顶部声明了它。

标签: javascript firebase google-cloud-firestore


【解决方案1】:

在数据库中增加数字的最简单方法是使用 increment 运算符:

habitContainer.addEventListener('click', evt => {
    if(evt.target.tagName === 'I'){
        const id = evt.target.getAttribute('data-id');
        db.collection('habits').doc(id).update({
            count: firebase.firestore.FieldValue.increment(1)
        });
    }
});

每次调用此函数时,您的onSnapshot 侦听器都会被更新后的文档再次调用。您需要在其中处理 if(change.type === 'modified'){ 以在 UI 中显示更新的值/文档。

【讨论】:

  • 完美!谢谢。我不知道在 if(change.type === 'changed'){} 中添加什么来更新 UI。哦,顺便说一句,'changed' 不应该是 'modified' 吗?
  • 糟糕。很可能是这样。 :)
  • 嗨弗兰克,我一直在努力更新 UI 一段时间,但我似乎无法弄清楚。到目前为止,我已经做到了这一点:if(change.type === 'modified'){ const habitUpdate = document.querySelector('#wrapper[data-id="' + change.doc.id + '"]'); // li.childNodes[0].textContent = change.doc.data().count; habitUpdate.update(); } 关于如何改进这一点以便 UI 也得到更新的任何提示?
  • 乍一看还不错。您是否也在更新元素的innerHTML?如果您无法弄清楚,可能值得发布一个仅包含更新部分的新问题(所以看看您是否可以在不使用 Firestore 的情况下遇到同样的问题)。
  • 终于让它工作了。我所要做的就是将.querySelector 更改为首先更新值的id,然后删除.childNodes[]。无论如何感谢您的帮助!
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2020-11-05
  • 2021-01-19
  • 1970-01-01
  • 1970-01-01
  • 2019-02-27
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多