File indexing completed on 2024-06-02 05:00:32
0001 // SPDX-FileCopyrightText: 2023 Joshua Goins <josh@redstrate.com> 0002 // SPDX-License-Identifier: GPL-3.0-or-later 0003 0004 #include "commentsmodel.h" 0005 0006 #include "plasmatube.h" 0007 0008 using namespace Qt::Literals::StringLiterals; 0009 0010 CommentsModel::CommentsModel(QObject *parent) 0011 : QAbstractListModel(parent) 0012 { 0013 } 0014 0015 QVariant CommentsModel::data(const QModelIndex &index, int role) const 0016 { 0017 Q_ASSERT(checkIndex(index, QAbstractItemModel::CheckIndexOption::IndexIsValid)); 0018 0019 const auto &comment = m_comments[index.row()]; 0020 0021 switch (role) { 0022 case AuthorRole: 0023 return comment.author(); 0024 case AuthorAvatarRole: 0025 return comment.authorAvatar(); 0026 case ContentRole: 0027 return comment.content(); 0028 default: 0029 return {}; 0030 } 0031 } 0032 0033 bool CommentsModel::loading() const 0034 { 0035 return m_loading; 0036 } 0037 0038 void CommentsModel::setLoading(bool loading) 0039 { 0040 if (m_loading == loading) { 0041 return; 0042 } 0043 m_loading = loading; 0044 Q_EMIT loadingChanged(); 0045 } 0046 0047 int CommentsModel::rowCount(const QModelIndex &parent) const 0048 { 0049 return parent.isValid() ? 0 : static_cast<int>(m_comments.size()); 0050 } 0051 0052 QHash<int, QByteArray> CommentsModel::roleNames() const 0053 { 0054 return { 0055 {AuthorRole, "author"}, 0056 {AuthorAvatarRole, "authorAvatar"}, 0057 {ContentRole, "content"}, 0058 }; 0059 } 0060 0061 void CommentsModel::fillComments(const QString &videoId) 0062 { 0063 if (!m_comments.isEmpty()) { 0064 beginResetModel(); 0065 m_comments.clear(); 0066 endResetModel(); 0067 } 0068 0069 m_continuation.clear(); 0070 m_videoId = videoId; 0071 fill(); 0072 } 0073 0074 void CommentsModel::loadMore() 0075 { 0076 if (!m_continuation.isEmpty()) { 0077 fill(); 0078 } 0079 } 0080 0081 void CommentsModel::fill() 0082 { 0083 if (m_loading) { 0084 return; 0085 } 0086 0087 setLoading(true); 0088 0089 auto future = PlasmaTube::instance().sourceManager()->selectedSource()->api()->requestComments(m_videoId, m_continuation); 0090 0091 m_futureWatcher = new QFutureWatcher<QInvidious::CommentsResult>(); 0092 m_futureWatcher->setFuture(future); 0093 0094 connect(m_futureWatcher, &QFutureWatcherBase::finished, this, [this] { 0095 if (m_futureWatcher->future().resultCount() != 0) { 0096 auto result = m_futureWatcher->result(); 0097 if (auto comments = std::get_if<QInvidious::Comments>(&result)) { 0098 const auto rows = rowCount({}); 0099 beginInsertRows({}, rows, rows + static_cast<int>(comments->comments.size()) - 1); 0100 m_comments << (*comments).comments; 0101 endInsertRows(); 0102 0103 m_continuation = comments->continuation; 0104 } else if (auto error = std::get_if<QInvidious::Error>(&result)) { 0105 // TODO: Log error 0106 } 0107 } 0108 0109 m_futureWatcher->deleteLater(); 0110 m_futureWatcher = nullptr; 0111 setLoading(false); 0112 }); 0113 } 0114 0115 #include "moc_commentsmodel.cpp"