File indexing completed on 2024-05-19 05:55:48
0001 /* 0002 * SPDX-FileCopyrightText: 2020-2021 Han Young <hanyoung@protonmail.com> 0003 * SPDX-FileCopyrightText: 2020 Devin Lin <espidev@gmail.com> 0004 * 0005 * SPDX-License-Identifier: GPL-2.0-or-later 0006 */ 0007 0008 #include "locationquerymodel.h" 0009 #include "weatherlocationlistmodel.h" 0010 0011 #include <KWeatherCore/LocationQueryReply> 0012 0013 #include <QDebug> 0014 #include <QTimer> 0015 0016 LocationQueryModel::LocationQueryModel() 0017 { 0018 inputTimer = new QTimer(this); 0019 inputTimer->setSingleShot(true); 0020 connect(inputTimer, &QTimer::timeout, this, &LocationQueryModel::setQuery); 0021 } 0022 0023 int LocationQueryModel::rowCount(const QModelIndex &parent) const 0024 { 0025 Q_UNUSED(parent); 0026 return m_results.size(); 0027 } 0028 0029 static QString buildResultName(const KWeatherCore::LocationQueryResult &result) 0030 { 0031 const auto &countryCode = result.countryCode(); 0032 if (result.subdivision() && countryCode == QLatin1String("US")) { 0033 return result.toponymName() + QLatin1String(", ") + *result.subdivision() + QLatin1String(" | ") + result.countryName(); 0034 } 0035 return result.toponymName() + QLatin1String(" | ") + result.countryName(); 0036 } 0037 0038 QVariant LocationQueryModel::data(const QModelIndex &index, int role) const 0039 { 0040 if (!index.isValid()) 0041 return QVariant(); 0042 0043 auto result = m_results.at(index.row()); 0044 0045 if (role == NameRole) { 0046 return buildResultName(result); 0047 } 0048 0049 return QVariant(); 0050 } 0051 0052 QHash<int, QByteArray> LocationQueryModel::roleNames() const 0053 { 0054 return {{NameRole, "name"}}; 0055 } 0056 0057 KWeatherCore::LocationQueryResult LocationQueryModel::get(int index) 0058 { 0059 if (index < 0 || index >= static_cast<int>(m_results.size())) 0060 return {}; 0061 return m_results.at(index); 0062 } 0063 0064 void LocationQueryModel::textChanged(QString query, int timeout) 0065 { 0066 m_text = std::move(query); 0067 0068 beginResetModel(); 0069 // clear results list 0070 m_results.clear(); 0071 0072 endResetModel(); 0073 if (!m_text.isEmpty()) { // do not query nothing 0074 m_loading = true; 0075 m_networkError = false; 0076 Q_EMIT propertyChanged(); 0077 0078 inputTimer->start(timeout); // make request once input stopped for 2 secs 0079 } 0080 } 0081 0082 void LocationQueryModel::setQuery() 0083 { 0084 qDebug() << "start query"; 0085 auto reply = m_querySource.query(m_text); 0086 connect(reply, &KWeatherCore::LocationQueryReply::finished, this, [this, reply]() { 0087 reply->error(); 0088 if (reply->error() == KWeatherCore::LocationQueryReply::NoError || reply->error() == KWeatherCore::LocationQueryReply::NotFound) { 0089 handleQueryResults(reply->result()); 0090 } 0091 }); 0092 } 0093 0094 void LocationQueryModel::addLocation(int index) 0095 { 0096 if (m_results.empty() || index < 0 || index >= static_cast<int>(m_results.size())) 0097 return; // don't add location 0098 WeatherLocationListModel::inst()->addLocation(m_results.at(index)); 0099 } 0100 0101 void LocationQueryModel::handleQueryResults(const std::vector<KWeatherCore::LocationQueryResult> &results) 0102 { 0103 qDebug() << "results arrived" << results.size(); 0104 beginResetModel(); 0105 // clear results list 0106 m_results.assign(results.begin(), results.end()); 0107 0108 endResetModel(); 0109 } 0110 0111 bool LocationQueryModel::loading() const 0112 { 0113 return m_loading; 0114 } 0115 bool LocationQueryModel::networkError() const 0116 { 0117 return m_networkError; 0118 } 0119 0120 void LocationQueryModel::clearResults() 0121 { 0122 beginResetModel(); 0123 m_results.clear(); 0124 endResetModel(); 0125 m_loading = false; 0126 m_networkError = false; 0127 Q_EMIT propertyChanged(); 0128 } 0129 0130 #include "moc_locationquerymodel.cpp"