2 * Copyright (C) 2013 Canonical, Ltd.
5 * Michael Terry <michael.terry@canonical.com>
6 * Michael Zanetti <michael.zanetti@canonical.com>
8 * This program is free software; you can redistribute it and/or modify
9 * it under the terms of the GNU General Public License as published by
10 * the Free Software Foundation; version 3.
12 * This program is distributed in the hope that it will be useful,
13 * but WITHOUT ANY WARRANTY; without even the implied warranty of
14 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 * GNU General Public License for more details.
17 * You should have received a copy of the GNU General Public License
18 * along with this program. If not, see <http://www.gnu.org/licenses/>.
21#include "AccountsService.h"
22#include "launcherbackend.h"
25#include <QDBusArgument>
28LauncherBackend::LauncherBackend(bool useStorage, QObject *parent):
33 m_accounts = new AccountsService(this);
35 setUser(qgetenv("USER"));
38LauncherBackend::~LauncherBackend()
43void LauncherBackend::clearItems()
45 for (LauncherBackendItem &app: m_storedApps) {
51QStringList LauncherBackend::storedApplications() const
53 auto files = QStringList();
54 for (const LauncherBackendItem &app: m_storedApps) {
55 files << app.settings->fileName();
60void LauncherBackend::setStoredApplications(const QStringList &appIds)
62 // Record all existing pinned apps, so we can notice them in new list
63 auto pinnedItems = QStringList();
64 for (LauncherBackendItem &app: m_storedApps) {
66 pinnedItems.append(app.settings->fileName());
72 for (const QString &appId: appIds) {
73 loadApp(makeAppDetails(appId, pinnedItems.contains(desktopFile(appId))));
79QString LauncherBackend::desktopFile(const QString &appId) const
81 QFileInfo fileInfo(QDir("/usr/share/applications"), appId);
82 return fileInfo.absoluteFilePath();
85QString LauncherBackend::displayName(const QString &appId) const
87 auto desktopFile = parseDesktopFile(appId);
88 auto displayName = desktopFile->value("Desktop Entry/Name").toString();
93QString LauncherBackend::icon(const QString &appId) const
95 auto desktopFile = parseDesktopFile(appId);
96 auto iconName = desktopFile->value("Desktop Entry/Icon").toString();
99 if (!iconName.isEmpty()) {
100 QFileInfo iconFileInfo(iconName);
101 if (iconFileInfo.isRelative()) {
102 iconName = "image://gicon/" + iconName;
109bool LauncherBackend::isPinned(const QString &appId) const
111 auto index = findItem(appId);
115 return m_storedApps[index].pinned;
119void LauncherBackend::setPinned(const QString &appId, bool pinned)
121 auto index = findItem(appId);
122 if (index >= 0 && !m_storedApps[index].pinned) {
123 m_storedApps[index].pinned = pinned;
128QList<QuickListEntry> LauncherBackend::quickList(const QString &appId) const
130 // TODO: Get static (from .desktop file) and dynamic (from the app itself)
131 // entries and return them here. Frontend related entries (like "Pin to launcher")
132 // don't matter here. This is just the backend part.
133 // TODO: emit quickListChanged() when the dynamic part changes
135 return QList<QuickListEntry>();
138int LauncherBackend::progress(const QString &appId) const
140 // TODO: Return value for progress emblem.
141 // TODO: emit progressChanged() when this value changes.
146int LauncherBackend::count(const QString &appId) const
148 // TODO: Return value for count emblem.
149 // TODO: emit countChanged() when this value changes.
154void LauncherBackend::setUser(const QString &username)
160void LauncherBackend::triggerQuickListAction(const QString &appId, const QString &quickListId)
162 // TODO: execute the given quicklist action
164 Q_UNUSED(quickListId)
167void LauncherBackend::syncFromAccounts()
169 QList<QVariantMap> apps;
170 bool defaults = true;
174 if (m_user != "" && m_accounts != nullptr) {
175 auto variant = m_accounts->getUserProperty(m_user, "launcher-items");
176 apps = qdbus_cast<QList<QVariantMap>>(variant.value<QDBusArgument>());
177 defaults = isDefaultsItem(apps);
180 // TODO: load default pinned ones from default config, instead of hardcoding here...
183 makeAppDetails("dialer-app.desktop", true) <<
184 makeAppDetails("messaging-app.desktop", true) <<
185 makeAppDetails("address-book-app.desktop", true) <<
186 makeAppDetails("camera-app.desktop", true) <<
187 makeAppDetails("gallery-app.desktop", true) <<
188 makeAppDetails("facebook-webapp.desktop", true) <<
189 makeAppDetails("webbrowser-app.desktop", true) <<
190 makeAppDetails("twitter-webapp.desktop", true) <<
191 makeAppDetails("gmail-webapp.desktop", true) <<
192 makeAppDetails("ubuntu-weather-app.desktop", true) <<
193 makeAppDetails("notes-app.desktop", true) <<
194 makeAppDetails("calendar-app.desktop", true);
197 for (const QVariant &app: apps) {
198 loadApp(app.toMap());
202void LauncherBackend::syncToAccounts()
204 if (m_user != "" && m_accounts != nullptr) {
205 QList<QVariantMap> items;
207 for (LauncherBackendItem &app: m_storedApps) {
208 items << makeAppDetails(app.settings->fileName(), app.pinned);
211 m_accounts->setUserProperty(m_user, "launcher-items", QVariant::fromValue(items));
215QSettings *LauncherBackend::parseDesktopFile(const QString &appId) const
217 auto fullAppId = desktopFile(appId);
218 return new QSettings(fullAppId, QSettings::IniFormat);
221void LauncherBackend::loadApp(const QVariantMap &details)
223 auto appId = details.value("id").toString();
224 auto isPinned = details.value("is-pinned").toBool();
226 if (appId.isEmpty()) {
230 LauncherBackendItem item;
231 item.settings = parseDesktopFile(appId);
232 item.pinned = isPinned;
233 m_storedApps.append(item);
236QVariantMap LauncherBackend::makeAppDetails(const QString &appId, bool pinned) const
239 details.insert("id", appId);
240 details.insert("is-pinned", pinned);
244bool LauncherBackend::isDefaultsItem(const QList<QVariantMap> &apps) const
246 // To differentiate between an empty list and a list that hasn't been set
247 // yet (and should thus be populated with the defaults), we use a special
248 // list of one item with the 'defaults' field set to true.
249 return (apps.size() == 1 && apps[0].value("defaults").toBool());
252int LauncherBackend::findItem(const QString &appId) const
254 auto fullAppId = desktopFile(appId);
255 for (int i = 0; i < m_storedApps.size(); ++i) {
256 if (m_storedApps[i].settings->fileName() == fullAppId) {
keysesc to close
- j k
- move down, up
- enter
- open
- esc
- back, or up a level
- 1 2 3 4
- readme, files, commits, refs
- /
- filter
- y
- copy the clone command
- c
- compare the chosen commit with another (or shift-click both)
- ?
- show or hide this list