File indexing completed on 2024-07-21 07:58:07

0001 /*
0002     SPDX-FileCopyrightText: 2013 Lukas Tinkl <ltinkl@redhat.com>
0003     SPDX-FileCopyrightText: 2013 Jan Grulich <jgrulich@redhat.com>
0004 
0005     SPDX-License-Identifier: LGPL-2.1-only OR LGPL-3.0-only OR LicenseRef-KDE-Accepted-LGPL
0006 */
0007 
0008 #include "bssidcombobox.h"
0009 
0010 #include <NetworkManagerQt/Manager>
0011 #include <NetworkManagerQt/Utils>
0012 #include <NetworkManagerQt/WirelessDevice>
0013 
0014 #include <KLocalizedString>
0015 
0016 bool signalCompare(const NetworkManager::AccessPoint::Ptr &one, const NetworkManager::AccessPoint::Ptr &two)
0017 {
0018     return one->signalStrength() > two->signalStrength();
0019 }
0020 
0021 BssidComboBox::BssidComboBox(QWidget *parent)
0022     : QComboBox(parent)
0023 {
0024     setEditable(true);
0025     setInsertPolicy(QComboBox::NoInsert);
0026 
0027     connect(this, &BssidComboBox::editTextChanged, this, &BssidComboBox::slotEditTextChanged);
0028     connect(this, QOverload<int>::of(&BssidComboBox::activated), this, &BssidComboBox::slotCurrentIndexChanged);
0029 }
0030 
0031 QString BssidComboBox::bssid() const
0032 {
0033     QString result;
0034     if (!m_dirty)
0035         result = itemData(currentIndex()).toString();
0036     else
0037         result = currentText();
0038 
0039     // qCDebug(PLASMA_NM_EDITOR_LOG) << "Result:" << currentIndex() << result;
0040 
0041     return result;
0042 }
0043 
0044 bool BssidComboBox::isValid() const
0045 {
0046     if (bssid().isEmpty()) {
0047         return true;
0048     }
0049 
0050     return NetworkManager::macAddressIsValid(bssid());
0051 }
0052 
0053 void BssidComboBox::slotEditTextChanged(const QString &)
0054 {
0055     m_dirty = true;
0056     Q_EMIT bssidChanged();
0057 }
0058 
0059 void BssidComboBox::slotCurrentIndexChanged(int)
0060 {
0061     m_dirty = false;
0062     setEditText(bssid());
0063     Q_EMIT bssidChanged();
0064 }
0065 
0066 void BssidComboBox::init(const QString &bssid, const QString &ssid)
0067 {
0068     m_initialBssid = bssid;
0069 
0070     // qCDebug(PLASMA_NM_EDITOR_LOG) << "Initial ssid:" << m_initialBssid;
0071 
0072     QList<NetworkManager::AccessPoint::Ptr> aps;
0073 
0074     for (const NetworkManager::Device::Ptr &device : NetworkManager::networkInterfaces()) {
0075         if (device->type() == NetworkManager::Device::Wifi) {
0076             NetworkManager::WirelessDevice::Ptr wifiDevice = device.objectCast<NetworkManager::WirelessDevice>();
0077             NetworkManager::WirelessNetwork::Ptr wifiNetwork = wifiDevice->findNetwork(ssid);
0078 
0079             if (!wifiNetwork) {
0080                 continue;
0081             }
0082 
0083             for (const NetworkManager::AccessPoint::Ptr &newAp : wifiNetwork->accessPoints()) {
0084                 bool found = false;
0085                 for (const NetworkManager::AccessPoint::Ptr &existingAp : aps) {
0086                     if (newAp->hardwareAddress() == existingAp->hardwareAddress()) {
0087                         if (newAp->signalStrength() > existingAp->signalStrength()) {
0088                             aps.removeOne(existingAp);
0089                             break;
0090                         } else {
0091                             found = true;
0092                             break;
0093                         }
0094                     }
0095                 }
0096 
0097                 if (!found) {
0098                     aps << newAp;
0099                 }
0100             }
0101         }
0102     }
0103 
0104     std::sort(aps.begin(), aps.end(), signalCompare);
0105     addBssidsToCombo(aps);
0106 
0107     const int index = findData(m_initialBssid);
0108     if (index == -1) {
0109         insertItem(0, m_initialBssid, m_initialBssid);
0110         setCurrentIndex(0);
0111     } else {
0112         setCurrentIndex(index);
0113     }
0114     setEditText(m_initialBssid);
0115 }
0116 
0117 void BssidComboBox::addBssidsToCombo(const QList<NetworkManager::AccessPoint::Ptr> &aps)
0118 {
0119     clear();
0120 
0121     if (aps.isEmpty()) {
0122         addItem(i18n("First select the SSID"));
0123         return;
0124     }
0125 
0126     for (const NetworkManager::AccessPoint::Ptr &ap : aps) {
0127         if (!ap) {
0128             continue;
0129         }
0130 
0131         const QString text = i18n("%1 (%2%)\nFrequency: %3 Mhz\nChannel: %4",
0132                                   ap->hardwareAddress(),
0133                                   ap->signalStrength(),
0134                                   ap->frequency(),
0135                                   QString::number(NetworkManager::findChannel(ap->frequency())));
0136         addItem(text, QVariant::fromValue(ap->hardwareAddress()));
0137     }
0138 }
0139 
0140 #include "moc_bssidcombobox.cpp"