void addRecentApplication(KService::Ptr service, bool append) { // remove existing item if any if (removeExistingItem(service->entryPath())) { --recentApplicationCount; } QStandardItem *appItem = StandardItemFactory::createItemForService(service, displayOrder); appItem->setData(applicationTitle, Kickoff::GroupNameRole); itemsByPath.insert(service->entryPath(), appItem); if (append) { q->insertRow(recentApplicationCount, appItem); } else { q->insertRow(0, appItem); } ++recentApplicationCount; while (recentApplicationCount > maxRecentApps) { --recentApplicationCount; QList<QStandardItem*> row = q->takeRow(recentApplicationCount); //don't leave pending stuff in itemsByPath if (!row.isEmpty()) { itemsByPath.remove(row.first()->data(UrlRole).toString()); qDeleteAll(row.begin(), row.end()); } } }
void KMimeTypeTest::testPreferredService() { // The "NotShowIn=KDE" service should not be the preferred one! KService::Ptr serv = KMimeTypeTrader::self()->preferredService("text/plain"); QVERIFY(serv); qDebug() << serv->entryPath(); QVERIFY(serv->entryPath() != m_nonKdeApp); QCOMPARE(serv->entryPath(), m_textPlainApp); }
void addRecentApplication(KService::Ptr service,bool append) { // remove existing item if any removeExistingItem(service->entryPath()); QStandardItem *appItem = StandardItemFactory::createItemForService(service); itemsByPath.insert(service->entryPath(),appItem); if (append) { recentAppItem->appendRow(appItem); } else { recentAppItem->insertRow(0,appItem); } }
void KateFileTree::slotFixOpenWithMenu() { QMenu *menu = (QMenu*)sender(); menu->clear(); KTextEditor::Document *doc = model()->data(m_indexContextMenu, KateFileTreeModel::DocumentRole).value<KTextEditor::Document *>(); if (!doc) return; // get a list of appropriate services. KMimeType::Ptr mime = KMimeType::mimeType(doc->mimeType()); //kDebug(13001) << "mime type: " << mime->name(); QAction *a = 0; KService::List offers = KMimeTypeTrader::self()->query(mime->name(), "Application"); // for each one, insert a menu item... for(KService::List::Iterator it = offers.begin(); it != offers.end(); ++it) { KService::Ptr service = *it; if (service->name() == "Kate") continue; a = menu->addAction(KIcon(service->icon()), service->name()); a->setData(service->entryPath()); } // append "Other..." to call the KDE "open with" dialog. a = menu->addAction(i18n("&Other...")); a->setData(QString()); }
KPluginInfo::KPluginInfo( const KService::Ptr service ) : d( new KPluginInfoPrivate ) { if (!service) { d = 0; // isValid() == false return; } d->service = service; d->entryPath = service->entryPath(); if ( service->isDeleted() ) { d->hidden = true; return; } d->name = service->name(); d->comment = service->comment(); d->icon = service->icon(); d->author = service->property( QLatin1String("X-KDE-PluginInfo-Author") ).toString(); d->email = service->property( QLatin1String("X-KDE-PluginInfo-Email") ).toString(); d->pluginName = service->property( QLatin1String("X-KDE-PluginInfo-Name") ).toString(); d->version = service->property( QLatin1String("X-KDE-PluginInfo-Version") ).toString(); d->website = service->property( QLatin1String("X-KDE-PluginInfo-Website") ).toString(); d->category = service->property( QLatin1String("X-KDE-PluginInfo-Category") ).toString(); d->license = service->property( QLatin1String("X-KDE-PluginInfo-License") ).toString(); d->dependencies = service->property( QLatin1String("X-KDE-PluginInfo-Depends") ).toStringList(); QVariant tmp = service->property( QLatin1String("X-KDE-PluginInfo-EnabledByDefault") ); d->enabledbydefault = tmp.isValid() ? tmp.toBool() : false; }
bool KonqView::changePart(const QString &mimeType, const QString &serviceName, bool forceAutoEmbed) { // Caller should call stop first. assert( !m_bLoading ); //kDebug() << "mimeType=" << mimeType // << "requested serviceName=" << serviceName // << "current service name=" << m_service->desktopEntryName(); if (serviceName == m_service->desktopEntryName()) { m_serviceType = mimeType; return true; } if (isLockedViewMode()) { //kDebug() << "This view's mode is locked - can't change"; return false; // we can't do that if our view mode is locked } KService::List partServiceOffers, appServiceOffers; KService::Ptr service; KonqFactory konqFactory; KonqViewFactory viewFactory = konqFactory.createView( mimeType, serviceName, &service, &partServiceOffers, &appServiceOffers, forceAutoEmbed ); if ( viewFactory.isNull() ) { // Revert location bar's URL to the working one if(currentHistoryEntry()) setLocationBarURL( currentHistoryEntry()->locationBarURL ); return false; } m_serviceType = mimeType; m_partServiceOffers = partServiceOffers; m_appServiceOffers = appServiceOffers; // Check if that's already the kind of part we have -> no need to recreate it // Note: we should have an operator== for KService... if ( m_service && m_service->entryPath() == service->entryPath() ) { kDebug() << "Reusing service. Service type set to" << m_serviceType; if ( m_pMainWindow->currentView() == this ) m_pMainWindow->updateViewModeActions(); } else { m_service = service; switchView( viewFactory ); } return true; }
void ApplicationsProtocol::get( const KUrl & url ) { KService::Ptr service = KService::serviceByDesktopName(url.fileName()); if (service && service->isValid()) { KUrl redirUrl(KStandardDirs::locate("apps", service->entryPath())); redirection(redirUrl); finished(); } else { error( KIO::ERR_IS_DIRECTORY, url.prettyUrl() ); } }
QMimeData * KRunnerModel::mimeData(const QModelIndexList &indexes) const { KUrl::List urls; foreach (const QModelIndex & index, indexes) { KUrl url = data(index, CommonModel::Url).toString(); KService::Ptr service = serviceForUrl(url); if (service) { urls << KUrl(service->entryPath()); } }
static void createFileEntry(KIO::UDSEntry& entry, const KService::Ptr& service, const KUrl& parentUrl) { entry.clear(); entry.insert(KIO::UDSEntry::UDS_NAME, KIO::encodeFileName(service->name())); entry.insert(KIO::UDSEntry::UDS_FILE_TYPE, S_IFREG); const QString fileUrl = parentUrl.url(KUrl::AddTrailingSlash) + service->desktopEntryName(); entry.insert(KIO::UDSEntry::UDS_URL, fileUrl); entry.insert(KIO::UDSEntry::UDS_ACCESS, 0500); entry.insert(KIO::UDSEntry::UDS_MIME_TYPE, "application/x-desktop"); entry.insert(KIO::UDSEntry::UDS_SIZE, 0); entry.insert(KIO::UDSEntry::UDS_LOCAL_PATH, KStandardDirs::locate("apps", service->entryPath())); entry.insert(KIO::UDSEntry::UDS_MODIFICATION_TIME, time(0)); entry.insert(KIO::UDSEntry::UDS_ICON_NAME, service->icon()); }
void RecordItNowPluginManager::loadInfos(const QString &type) { KConfig cfg("recorditnowrc"); KConfigGroup pCfg(&cfg, "Plugins"); KService::List offers = KServiceTypeTrader::self()->query(type); KService::List::const_iterator iter; for (iter = offers.begin(); iter < offers.end(); ++iter) { KService::Ptr service = *iter; KPluginInfo info(service); if (!info.isValid()) { kWarning() << "invalid plugin info:" << service->entryPath(); continue; } else { info.setConfig(pCfg); info.load(pCfg); m_plugins[info] = 0; } } }
/* * 接受isoftappdaemon finished 信号 * 1.更新所有包列表中对应包的状态 * 2.给每个页面发送taskfinished信号 * 3.更新taskqueue队列: * a、删除当前任务 * b、开始新任务 */ void JadedBus::getFinished(const QString &pkgName,qlonglong status) { if (status != STATUS_REMOVED && status != STATUS_UPDATED && status != STATUS_INSTALLED && status != STATUS_INSTALL && status != STATUS_UPGRADED && status != STATUS_INSTALL_ERROR) { return; } if(pkgName.isEmpty()) { return; } int i =0; for (i = 0; i < AllPkgList.size(); ++i) { if (AllPkgList.at(i).pkgName == pkgName) { if (status == STATUS_INSTALLED) { if (AllPkgList[i].status != 1) { AllPkgList[i].status = 1; QDateTime local(QDateTime::currentDateTime()); AllPkgList[i].datetime = local.toString("yyyy-MM-dd hh:mm:ss"); QString desktopName = m_isoftapp->GetDesktopName(pkgName).value(); if (!desktopName.isEmpty()) desktopName = desktopName.left(desktopName.size() - 8); KService::Ptr service = KService::serviceByDesktopName(desktopName); if (!service) { service = KService::serviceByDesktopName(pkgName); } if (service) { if (!service->exec().isEmpty() && !service->noDisplay()) { QFile::link(service->entryPath(), QStandardPaths::writableLocation(QStandardPaths::DesktopLocation) + "/" + service->name() + ".desktop"); } } } } else if (status == STATUS_REMOVED) { if (AllPkgList[i].status != 2) { AllPkgList[i].status = 2; QDateTime local(QDateTime::currentDateTime()); AllPkgList[i].datetime = local.toString("yyyy-MM-dd hh:mm:ss"); } } else if ( status == STATUS_INSTALL_ERROR) { if (AllPkgList[i].status != 2) { AllPkgList[i].status = 2; } QString details ="insatallfailed"; m_errored(pkgName,details); } getMyPkgNumber(); break; } } taskFinished(pkgName); for (i = 0; i < m_taskQueue.size(); i++) { if (m_taskQueue[i].status == "doing" && pkgName == m_taskQueue[i].name) { if (m_taskQueue[i].action == "update") { int t = (int)time(NULL); m_updateInfo.replace(pkgName,QString::number(t, 10)); //getUpdate() ; } printf("trace:%s,%d,name[%s],index[%d][%s] task is finished.\n",__FUNCTION__,__LINE__, qPrintable(m_taskQueue[i].name),i,qPrintable(m_taskQueue[i].action)); m_taskQueue[i].status = "done"; g_doingPkgName = ""; m_taskQueue.removeFirst(); m_runTask(); return; } } return; }
QVariant AppsModel::data(const QModelIndex &index, int role) const { if (!index.isValid() || index.row() >= m_entryList.count()) { return QVariant(); } const AbstractEntry *entry = m_entryList.at(index.row()); if (role == Qt::DisplayRole) { return entry->name(); } else if (role == Qt::DecorationRole) { return entry->icon(); } else if (role == Kicker::IsParentRole) { return (entry->type() == AbstractEntry::GroupType); } else if (role == Kicker::HasChildrenRole) { if (entry->type() == AbstractEntry::GroupType) { const AbstractGroupEntry *groupEntry = static_cast<const AbstractGroupEntry *>(entry); if (groupEntry->model() && groupEntry->model()->count()) { return true; } } } else if (role == Kicker::FavoriteIdRole) { if (entry->type() == AbstractEntry::RunnableType) { return QVariant("app:" + static_cast<AppEntry *>(m_entryList.at(index.row()))->service()->storageId()); } } else if (role == Kicker::HasActionListRole) { if (entry->type() == AbstractEntry::RunnableType || !m_hiddenEntries.isEmpty()) { return true; } else if (entry->type() == AbstractEntry::GroupType) { const AbstractGroupEntry *groupEntry = static_cast<const AbstractGroupEntry *>(entry); if (groupEntry->model()) { const AppsModel *appsModel = qobject_cast<const AppsModel *>(groupEntry->model()); if (appsModel && !appsModel->hiddenEntries().isEmpty()) { return true; } } } } else if (role == Kicker::ActionListRole) { QVariantList actionList; if (entry->type() == AbstractEntry::RunnableType) { const KService::Ptr service = static_cast<const AppEntry *>(entry)->service(); if (ContainmentInterface::mayAddLauncher(m_appletInterface, ContainmentInterface::Desktop)) { actionList << Kicker::createActionItem(i18n("Add to Desktop"), "addToDesktop"); } if (ContainmentInterface::mayAddLauncher(m_appletInterface, ContainmentInterface::Panel)) { actionList << Kicker::createActionItem(i18n("Add to Panel"), "addToPanel"); } if (ContainmentInterface::mayAddLauncher(m_appletInterface, ContainmentInterface::TaskManager, service->entryPath())) { actionList << Kicker::createActionItem(i18n("Add as Launcher"), "addToTaskManager"); } if (m_menuEntryEditor->canEdit(service->entryPath())) { actionList << Kicker::createSeparatorActionItem(); QVariantMap editAction = Kicker::createActionItem(i18n("Edit Application..."), "editApplication"); editAction["icon"] = "kmenuedit"; // TODO: Using the KMenuEdit icon might be misleading. actionList << editAction; } #ifdef PackageKitQt5_FOUND QStringList files(service->entryPath()); if (service->isApplication()) { files += QStandardPaths::findExecutable(KShell::splitArgs(service->exec()).first()); } FindPackageJob* job = new FindPackageJob(files); // TODO: Would be great to make this async. if (job->exec() && !job->packageNames().isEmpty()) { QString packageName = job->packageNames().first(); QVariantMap removeAction = Kicker::createActionItem(i18n("Remove '%1'...", packageName), "removeApplication", packageName); removeAction["icon"] = "applications-other"; actionList << removeAction; } #endif if (appletConfig() && appletConfig()->contains("hiddenApplications")) { const QStringList &hiddenApps = appletConfig()->value("hiddenApplications").toStringList(); if (!hiddenApps.contains(service->menuId())) { actionList << Kicker::createActionItem(i18n("Hide Application"), "hideApplication"); } } } if (!m_hiddenEntries.isEmpty()) { actionList << Kicker::createSeparatorActionItem(); actionList << Kicker::createActionItem(i18n("Unhide Applications in this Submenu"), "unhideSiblingApplications"); } if (entry->type() == AbstractEntry::GroupType) { const AbstractGroupEntry *groupEntry = static_cast<const AbstractGroupEntry *>(entry); if (groupEntry->model()) { const AppsModel *appsModel = qobject_cast<const AppsModel *>(groupEntry->model()); if (appsModel && !appsModel->hiddenEntries().isEmpty()) { actionList << Kicker::createActionItem(i18n("Unhide Applications in '%1'", entry->name()), "unhideChildApplications"); } } } return actionList; } else if (role == Kicker::UrlRole) { if (entry->type() == AbstractEntry::RunnableType) { return QUrl::fromLocalFile(static_cast<AppEntry *>(m_entryList.at(index.row()))->service()->entryPath()); } } return QVariant(); }
void KateProjectTreeViewContextMenu::exec(const QString &filename, const QPoint &pos, QWidget *parent) { /** * create context menu */ QMenu menu; QAction *copyAction = menu.addAction(QIcon::fromTheme(QStringLiteral("edit-copy")), i18n("Copy Filename")); /** * handle "open with" * find correct mimetype to query for possible applications */ QMenu *openWithMenu = menu.addMenu(i18n("Open With")); QMimeType mimeType = QMimeDatabase().mimeTypeForFile(filename); KService::List offers = KMimeTypeTrader::self()->query(mimeType.name(), QStringLiteral("Application")); /** * for each one, insert a menu item... */ for (KService::List::Iterator it = offers.begin(); it != offers.end(); ++it) { KService::Ptr service = *it; if (service->name() == QStringLiteral("Kate")) { continue; // omit Kate } QAction *action = openWithMenu->addAction(QIcon::fromTheme(service->icon()), service->name()); action->setData(service->entryPath()); } /** * perhaps disable menu, if no entries! */ openWithMenu->setEnabled(!openWithMenu->isEmpty()); KMoreToolsMenuFactory menuFactory(QLatin1String("kate/addons/project/git-tools")); QMenu gitMenu; // must live as long as the maybe filled menu items should live if (isGit(filename)) { menuFactory.fillMenuFromGroupingNames(&gitMenu, { QLatin1String("git-clients-and-actions") }, QUrl::fromLocalFile(filename)); menu.addSection(i18n("Git:")); Q_FOREACH(auto action, gitMenu.actions()) { menu.addAction(action); } } /** * run menu and handle the triggered action */ if (QAction *action = menu.exec(pos)) { // handle apps if (copyAction == action) { QApplication::clipboard()->setText(filename); } else { // handle "open with" const QString openWith = action->data().toString(); if (KService::Ptr app = KService::serviceByDesktopPath(openWith)) { QList<QUrl> list; list << QUrl::fromLocalFile(filename); KRun::runService(*app, list, parent); } } } }
void KSycocaDict::save(QDataStream &str) { if (count() == 0) { d->hashTableSize = 0; d->hashList.clear(); str << d->hashTableSize; str << d->hashList; return; } d->offset = str.device()->pos(); //qDebug() << "KSycocaDict:" << count() << "entries."; //qDebug() << "Calculating hash keys.."; int maxLength = 0; //qDebug() << "Finding maximum string length"; for(KSycocaDictStringList::const_iterator it = d->stringlist->constBegin(); it != d->stringlist->constEnd(); ++it) { string_entry* entry = *it; entry->hash = 0; if (entry->length > maxLength) maxLength = entry->length; } //qDebug() << "Max string length=" << maxLength << "existing hashList=" << d->hashList; // use "almost prime" number for sz (to calculate diversity) and later // for the table size of big tables // int sz = d->stringlist->count()*5-1; register unsigned int sz = count()*4 + 1; while(!(((sz % 3) && (sz % 5) && (sz % 7) && (sz % 11) && (sz % 13)))) sz+=2; d->hashList.clear(); // Times (with warm caches, i.e. after multiple runs) // kbuildsycoca5 --noincremental 2.83s user 0.20s system 95% cpu 3.187 total // kbuildsycoca5 --noincremental 2.74s user 0.25s system 93% cpu 3.205 total // unittest: 0.50-60 msec per iteration / 0.40-50 msec per iteration // Now that MimeTypes are not parsed anymore: // kbuildsycoca5 --noincremental 2.18s user 0.30s system 91% cpu 2.719 total // kbuildsycoca5 --noincremental 2.07s user 0.34s system 89% cpu 2.681 total // If I enabled s_maxItems = 50, it goes down to // but I don't know if that's a good idea. // kbuildsycoca5 --noincremental 1.73s user 0.31s system 85% cpu 2.397 total // kbuildsycoca5 --noincremental 1.84s user 0.29s system 95% cpu 2.230 total // try to limit diversity scan by "predicting" positions // with high diversity QVector<int> oldvec(maxLength*2+1); oldvec.fill(0); int mindiv=0; int lastDiv = 0; while(true) { int divsum=0,divnum=0; int maxDiv = 0; int maxPos = 0; for (int pos = -maxLength; pos <= maxLength; ++pos) { // cut off if (oldvec[pos+maxLength] < mindiv) { oldvec[pos+maxLength]=0; continue; } const int diversity = calcDiversity(d->stringlist, pos, sz); if (diversity > maxDiv) { maxDiv = diversity; maxPos = pos; } oldvec[pos + maxLength] = diversity; divsum += diversity; ++divnum; } // arbitrary cut-off value 3/4 of average seems to work if (divnum) mindiv=(3*divsum)/(4*divnum); if (maxDiv <= lastDiv) break; //qDebug() << "Max Div=" << maxDiv << "at pos" << maxPos; lastDiv = maxDiv; addDiversity(d->stringlist, maxPos); d->hashList.append(maxPos); } for(KSycocaDictStringList::Iterator it = d->stringlist->begin(); it != d->stringlist->end(); ++it) { (*it)->hash = d->hashKey((*it)->keyStr); } // fprintf(stderr, "Calculating minimum table size..\n"); d->hashTableSize = sz; //qDebug() << "hashTableSize=" << sz << "hashList=" << d->hashList << "oldvec=" << oldvec; struct hashtable_entry { string_entry *entry; QList<string_entry*>* duplicates; qint64 duplicate_offset; }; hashtable_entry *hashTable = new hashtable_entry[ sz ]; //qDebug() << "Clearing hashtable..."; for (unsigned int i=0; i < sz; i++) { hashTable[i].entry = 0; hashTable[i].duplicates = 0; } //qDebug() << "Filling hashtable..."; for(KSycocaDictStringList::const_iterator it = d->stringlist->constBegin(); it != d->stringlist->constEnd(); ++it) { string_entry* entry = *it; //qDebug() << "entry keyStr=" << entry->keyStr << entry->payload.data() << entry->payload->entryPath(); int hash = entry->hash % sz; if (!hashTable[hash].entry) { // First entry hashTable[hash].entry = entry; } else { if (!hashTable[hash].duplicates) { // Second entry, build duplicate list. hashTable[hash].duplicates = new QList<string_entry*>; hashTable[hash].duplicates->append(hashTable[hash].entry); hashTable[hash].duplicate_offset = 0; } hashTable[hash].duplicates->append(entry); } } str << d->hashTableSize; str << d->hashList; d->offset = str.device()->pos(); // d->offset points to start of hashTable //qDebug() << QString("Start of Hash Table, offset = %1").arg(d->offset,8,16); // Write the hashtable + the duplicates twice. // The duplicates are after the normal hashtable, but the offset of each // duplicate entry is written into the normal hashtable. for(int pass = 1; pass <= 2; pass++) { str.device()->seek(d->offset); //qDebug() << QString("Writing hash table (pass #%1)").arg(pass); for(uint i=0; i < d->hashTableSize; i++) { qint32 tmpid; if (!hashTable[i].entry) tmpid = (qint32) 0; else if (!hashTable[i].duplicates) tmpid = (qint32) hashTable[i].entry->payload->offset(); // Positive ID else tmpid = (qint32) -hashTable[i].duplicate_offset; // Negative ID str << tmpid; //qDebug() << QString("Hash table : %1").arg(tmpid,8,16); } //qDebug() << QString("End of Hash Table, offset = %1").arg(str.device()->at(),8,16); //qDebug() << QString("Writing duplicate lists (pass #%1)").arg(pass); for(uint i=0; i < d->hashTableSize; i++) { const QList<string_entry*> *dups = hashTable[i].duplicates; if (dups) { hashTable[i].duplicate_offset = str.device()->pos(); /*qDebug() << QString("Duplicate lists: Offset = %1 list_size = %2") .arg(hashTable[i].duplicate_offset,8,16).arg(dups->count()); */ for(QList<string_entry*>::ConstIterator dup = dups->begin(); dup != dups->end(); ++dup) { const qint32 offset = (*dup)->payload->offset(); if (!offset) { const QString storageId = (*dup)->payload->storageId(); qDebug() << "about to assert! dict=" << this << "storageId=" << storageId << (*dup)->payload.data(); if ((*dup)->payload->isType(KST_KService)) { KService::Ptr service = KService::Ptr::staticCast((*dup)->payload); qDebug() << service->storageId() << service->entryPath(); } // save() must have been called on the entry Q_ASSERT_X( offset, "KSycocaDict::save", QByteArray("entry offset is 0, save() was not called on " + (*dup)->payload->storageId().toLatin1() + " entryPath=" + (*dup)->payload->entryPath().toLatin1()) ); } str << offset ; // Positive ID str << (*dup)->keyStr; // Key (QString) } str << (qint32) 0; // End of list marker (0) } } //qDebug() << QString("End of Dict, offset = %1").arg(str.device()->at(),8,16); } //qDebug() << "Cleaning up hash table."; for(uint i=0; i < d->hashTableSize; i++) { delete hashTable[i].duplicates; } delete [] hashTable; }