diff --git a/plugins/execute/nativeappconfig.cpp b/plugins/execute/nativeappconfig.cpp index 6f2dd8c6ce..bdc6eca8f0 100644 --- a/plugins/execute/nativeappconfig.cpp +++ b/plugins/execute/nativeappconfig.cpp @@ -1,522 +1,519 @@ /* This file is part of KDevelop Copyright 2009 Andreas Pakulat Copyright 2010 Aleix Pol Gonzalez This library is free software; you can redistribute it and/or modify it under the terms of the GNU Library General Public License as published by the Free Software Foundation; either version 2 of the License, or (at your option) any later version. This library is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Library General Public License for more details. You should have received a copy of the GNU Library General Public License along with this library; see the file COPYING.LIB. If not, write to the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "nativeappconfig.h" #include #include #include #include #include #include #include #include "nativeappjob.h" #include #include #include #include #include #include #include #include #include #include #include "executeplugin.h" #include #include #include #include "projecttargetscombobox.h" #include #include #include #include #include KIcon NativeAppConfigPage::icon() const { return KIcon("system-run"); } static KDevelop::ProjectBaseItem* itemForPath(const QStringList& path, KDevelop::ProjectModel* model) { return model->itemFromIndex(model->pathToIndex(path)); } //TODO: Make sure to auto-add the executable target to the dependencies when its used. void NativeAppConfigPage::loadFromConfiguration(const KConfigGroup& cfg, KDevelop::IProject* project ) { bool b = blockSignals( true ); projectTarget->setBaseItem( project ? project->projectItem() : 0, true); projectTarget->setCurrentItemPath( cfg.readEntry( ExecutePlugin::projectTargetEntry, QStringList() ) ); KUrl exe = cfg.readEntry( ExecutePlugin::executableEntry, KUrl()); if( !exe.isEmpty() || project ){ executablePath->setUrl( !exe.isEmpty() ? exe : project->folder() ); }else{ KDevelop::IProjectController* pc = KDevelop::ICore::self()->projectController(); if( pc ){ executablePath->setUrl( pc->projects().count() ? pc->projects().first()->folder() : KUrl() ); } } //executablePath->setFilter("application/x-executable"); executableRadio->setChecked( true ); if ( !cfg.readEntry( ExecutePlugin::isExecutableEntry, false ) && projectTarget->count() ){ projectTargetRadio->setChecked( true ); } arguments->setClearButtonShown( true ); arguments->setText( cfg.readEntry( ExecutePlugin::argumentsEntry, "" ) ); workingDirectory->setUrl( cfg.readEntry( ExecutePlugin::workingDirEntry, KUrl() ) ); - environment->setCurrentProfile( cfg.readEntry( ExecutePlugin::environmentGroupEntry, "default" ) ); + environment->setCurrentProfile( cfg.readEntry( ExecutePlugin::environmentGroupEntry, QString() ) ); runInTerminal->setChecked( cfg.readEntry( ExecutePlugin::useTerminalEntry, false ) ); terminal->setEditText( cfg.readEntry( ExecutePlugin::terminalEntry, terminal->itemText(0) ) ); QVariantList deps = KDevelop::stringToQVariant( cfg.readEntry( ExecutePlugin::dependencyEntry, QString() ) ).toList(); QStringList strDeps; foreach( const QVariant& dep, deps ) { QStringList deplist = dep.toStringList(); KDevelop::ProjectModel* model = KDevelop::ICore::self()->projectController()->projectModel(); KDevelop::ProjectBaseItem* pitem=itemForPath(deplist, model); KIcon icon; if(pitem) icon=KIcon(pitem->iconName()); QListWidgetItem* item = new QListWidgetItem(icon, KDevelop::joinWithEscaping( deplist, '/', '\\' ), dependencies ); item->setData( Qt::UserRole, dep ); } dependencyAction->setCurrentIndex( dependencyAction->findData( cfg.readEntry( ExecutePlugin::dependencyActionEntry, "Nothing" ) ) ); blockSignals( b ); } NativeAppConfigPage::NativeAppConfigPage( QWidget* parent ) : LaunchConfigurationPage( parent ) { setupUi(this); //Setup data info for combobox dependencyAction->setItemData(0, "Nothing" ); dependencyAction->setItemData(1, "Build" ); dependencyAction->setItemData(2, "Install" ); dependencyAction->setItemData(3, "SudoInstall" ); addDependency->setIcon( KIcon("list-add") ); removeDependency->setIcon( KIcon("list-remove") ); moveDepUp->setIcon( KIcon("go-up") ); moveDepDown->setIcon( KIcon("go-down") ); browseProject->setIcon(KIcon("folder-document")); //Set workingdirectory widget to ask for directories rather than files workingDirectory->setMode(KFile::Directory | KFile::ExistingOnly | KFile::LocalOnly); - KDevelop::EnvironmentGroupList env( KGlobal::config() ); - environment->addItems( env.groups() ); - configureEnvironment->setSelectionWidget(environment); //connect signals to changed signal connect( projectTarget, SIGNAL(currentIndexChanged(QString)), SIGNAL(changed()) ); connect( projectTargetRadio, SIGNAL(toggled(bool)), SIGNAL(changed()) ); connect( executableRadio, SIGNAL(toggled(bool)), SIGNAL(changed()) ); connect( executablePath->lineEdit(), SIGNAL(textEdited(QString)), SIGNAL(changed()) ); connect( executablePath, SIGNAL(urlSelected(KUrl)), SIGNAL(changed()) ); connect( arguments, SIGNAL(textEdited(QString)), SIGNAL(changed()) ); connect( workingDirectory, SIGNAL(urlSelected(KUrl)), SIGNAL(changed()) ); connect( workingDirectory->lineEdit(), SIGNAL(textEdited(QString)), SIGNAL(changed()) ); connect( environment, SIGNAL(currentIndexChanged(int)), SIGNAL(changed()) ); connect( addDependency, SIGNAL(clicked(bool)), SLOT(addDep()) ); connect( addDependency, SIGNAL(clicked(bool)), SIGNAL(changed()) ); connect( removeDependency, SIGNAL(clicked(bool)), SIGNAL(changed()) ); connect( removeDependency, SIGNAL(clicked(bool)), SLOT(removeDep()) ); connect( moveDepDown, SIGNAL(clicked(bool)), SIGNAL(changed()) ); connect( moveDepUp, SIGNAL(clicked(bool)), SIGNAL(changed()) ); connect( moveDepDown, SIGNAL(clicked(bool)), SLOT(moveDependencyDown()) ); connect( moveDepUp, SIGNAL(clicked(bool)), SLOT(moveDependencyUp()) ); connect( dependencies->selectionModel(), SIGNAL(selectionChanged(QItemSelection,QItemSelection)), SLOT(checkActions(QItemSelection,QItemSelection)) ); connect( dependencyAction, SIGNAL(currentIndexChanged(int)), SIGNAL(changed()) ); connect( runInTerminal, SIGNAL(toggled(bool)), SIGNAL(changed()) ); connect( terminal, SIGNAL(editTextChanged(QString)), SIGNAL(changed()) ); connect( terminal, SIGNAL(currentIndexChanged(int)), SIGNAL(changed()) ); connect( dependencyAction, SIGNAL(currentIndexChanged(int)), SLOT(activateDeps(int)) ); connect( targetDependency, SIGNAL(textChanged(QString)), SLOT(depEdited(QString))); connect( browseProject, SIGNAL(clicked(bool)), SLOT(selectItemDialog())); } void NativeAppConfigPage::depEdited( const QString& str ) { int pos; QString tmp = str; addDependency->setEnabled( !str.isEmpty() && ( !targetDependency->validator() || targetDependency->validator()->validate( tmp, pos ) == QValidator::Acceptable ) ); } void NativeAppConfigPage::activateDeps( int idx ) { browseProject->setEnabled( dependencyAction->itemData( idx ).toString() != "Nothing" ); dependencies->setEnabled( dependencyAction->itemData( idx ).toString() != "Nothing" ); targetDependency->setEnabled( dependencyAction->itemData( idx ).toString() != "Nothing" ); } void NativeAppConfigPage::checkActions( const QItemSelection& selected, const QItemSelection& unselected ) { Q_UNUSED( unselected ); kDebug() << "checkActions"; if( !selected.indexes().isEmpty() ) { kDebug() << "have selection"; Q_ASSERT( selected.indexes().count() == 1 ); QModelIndex idx = selected.indexes().at( 0 ); kDebug() << "index" << idx; moveDepUp->setEnabled( idx.row() > 0 ); moveDepDown->setEnabled( idx.row() < dependencies->count() - 1 ); removeDependency->setEnabled( true ); } else { removeDependency->setEnabled( false ); moveDepUp->setEnabled( false ); moveDepDown->setEnabled( false ); } } void NativeAppConfigPage::moveDependencyDown() { QList list = dependencies->selectedItems(); if( !list.isEmpty() ) { Q_ASSERT( list.count() == 1 ); QListWidgetItem* item = list.at( 0 ); int row = dependencies->row( item ); dependencies->takeItem( row ); dependencies->insertItem( row+1, item ); dependencies->selectionModel()->select( dependencies->model()->index( row+1, 0, QModelIndex() ), QItemSelectionModel::ClearAndSelect | QItemSelectionModel::SelectCurrent ); } } void NativeAppConfigPage::moveDependencyUp() { QList list = dependencies->selectedItems(); if( !list.isEmpty() ) { Q_ASSERT( list.count() == 1 ); QListWidgetItem* item = list.at( 0 ); int row = dependencies->row( item ); dependencies->takeItem( row ); dependencies->insertItem( row-1, item ); dependencies->selectionModel()->select( dependencies->model()->index( row-1, 0, QModelIndex() ), QItemSelectionModel::ClearAndSelect | QItemSelectionModel::SelectCurrent ); } } void NativeAppConfigPage::addDep() { KIcon icon; KDevelop::ProjectBaseItem* pitem = targetDependency->currentItem(); if(pitem) icon= KIcon(pitem->iconName()); QListWidgetItem* item = new QListWidgetItem(icon, targetDependency->text(), dependencies); item->setData( Qt::UserRole, targetDependency->itemPath() ); targetDependency->setText(""); addDependency->setEnabled( false ); dependencies->selectionModel()->clearSelection(); item->setSelected(true); // dependencies->selectionModel()->select( dependencies->model()->index( dependencies->model()->rowCount() - 1, 0, QModelIndex() ), QItemSelectionModel::ClearAndSelect | QItemSelectionModel::SelectCurrent ); } void NativeAppConfigPage::selectItemDialog() { if(targetDependency->selectItemDialog()) { addDep(); } } void NativeAppConfigPage::removeDep() { QList list = dependencies->selectedItems(); if( !list.isEmpty() ) { Q_ASSERT( list.count() == 1 ); int row = dependencies->row( list.at(0) ); delete dependencies->takeItem( row ); dependencies->selectionModel()->select( dependencies->model()->index( row - 1, 0, QModelIndex() ), QItemSelectionModel::ClearAndSelect | QItemSelectionModel::SelectCurrent ); } } void NativeAppConfigPage::saveToConfiguration( KConfigGroup cfg, KDevelop::IProject* project ) const { Q_UNUSED( project ); cfg.writeEntry( ExecutePlugin::isExecutableEntry, executableRadio->isChecked() ); cfg.writeEntry( ExecutePlugin::executableEntry, executablePath->url() ); cfg.writeEntry( ExecutePlugin::projectTargetEntry, projectTarget->currentItemPath() ); cfg.writeEntry( ExecutePlugin::argumentsEntry, arguments->text() ); cfg.writeEntry( ExecutePlugin::workingDirEntry, workingDirectory->url() ); cfg.writeEntry( ExecutePlugin::environmentGroupEntry, environment->currentProfile() ); cfg.writeEntry( ExecutePlugin::useTerminalEntry, runInTerminal->isChecked() ); cfg.writeEntry( ExecutePlugin::terminalEntry, terminal->currentText() ); cfg.writeEntry( ExecutePlugin::dependencyActionEntry, dependencyAction->itemData( dependencyAction->currentIndex() ).toString() ); QVariantList deps; for( int i = 0; i < dependencies->count(); i++ ) { deps << dependencies->item( i )->data( Qt::UserRole ); } cfg.writeEntry( ExecutePlugin::dependencyEntry, KDevelop::qvariantToString( QVariant( deps ) ) ); } QString NativeAppConfigPage::title() const { return i18n("Configure Native Application"); } QList< KDevelop::LaunchConfigurationPageFactory* > NativeAppLauncher::configPages() const { return QList(); } QString NativeAppLauncher::description() const { return "Executes Native Applications"; } QString NativeAppLauncher::id() { return "nativeAppLauncher"; } QString NativeAppLauncher::name() const { return i18n("Native Application"); } NativeAppLauncher::NativeAppLauncher() { } KJob* NativeAppLauncher::start(const QString& launchMode, KDevelop::ILaunchConfiguration* cfg) { Q_ASSERT(cfg); if( !cfg ) { return 0; } if( launchMode == "execute" ) { IExecutePlugin* iface = KDevelop::ICore::self()->pluginController()->pluginForExtension("org.kdevelop.IExecutePlugin", "kdevexecute")->extension(); Q_ASSERT(iface); KJob* depjob = iface->dependecyJob( cfg ); QList l; if( depjob ) { l << depjob; } l << new NativeAppJob( KDevelop::ICore::self()->runController(), cfg ); return new KDevelop::ExecuteCompositeJob( KDevelop::ICore::self()->runController(), l ); } kWarning() << "Unknown launch mode " << launchMode << "for config:" << cfg->name(); return 0; } QStringList NativeAppLauncher::supportedModes() const { return QStringList() << "execute"; } KDevelop::LaunchConfigurationPage* NativeAppPageFactory::createWidget(QWidget* parent) { return new NativeAppConfigPage( parent ); } NativeAppPageFactory::NativeAppPageFactory() { } NativeAppConfigType::NativeAppConfigType() { factoryList.append( new NativeAppPageFactory() ); } NativeAppConfigType::~NativeAppConfigType() { qDeleteAll(factoryList); factoryList.clear(); } QString NativeAppConfigType::name() const { return i18n("Compiled Binary"); } QList NativeAppConfigType::configPages() const { return factoryList; } QString NativeAppConfigType::id() const { return ExecutePlugin::_nativeAppConfigTypeId; } KIcon NativeAppConfigType::icon() const { return KIcon("application-x-executable"); } bool NativeAppConfigType::canLaunch ( KDevelop::ProjectBaseItem* item ) const { if( item->target() && item->target()->executable() ) { return canLaunch( item->target()->executable()->builtUrl() ); } return false; } bool NativeAppConfigType::canLaunch ( const KUrl& file ) const { return ( file.isLocalFile() && QFileInfo( file.toLocalFile() ).isExecutable() ); } void NativeAppConfigType::configureLaunchFromItem ( KConfigGroup cfg, KDevelop::ProjectBaseItem* item ) const { cfg.writeEntry( ExecutePlugin::isExecutableEntry, false ); KDevelop::ProjectModel* model = KDevelop::ICore::self()->projectController()->projectModel(); cfg.writeEntry( ExecutePlugin::projectTargetEntry, model->pathFromIndex( model->indexFromItem( item ) ) ); cfg.writeEntry( ExecutePlugin::workingDirEntry, item->executable()->builtUrl().upUrl() ); cfg.sync(); } void NativeAppConfigType::configureLaunchFromCmdLineArguments ( KConfigGroup cfg, const QStringList& args ) const { cfg.writeEntry( ExecutePlugin::isExecutableEntry, true ); cfg.writeEntry( ExecutePlugin::executableEntry, args.first() ); QStringList a(args); a.removeFirst(); cfg.writeEntry( ExecutePlugin::argumentsEntry, KShell::joinArgs(a) ); cfg.sync(); } QList targetsInFolder(KDevelop::ProjectFolderItem* folder) { QList ret; foreach(KDevelop::ProjectFolderItem* f, folder->folderList()) ret += targetsInFolder(f); ret += folder->targetList(); return ret; } bool actionLess(QAction* a, QAction* b) { return a->text() < b->text(); } bool menuLess(QMenu* a, QMenu* b) { return a->title() < b->title(); } QMenu* NativeAppConfigType::launcherSuggestions() { QMenu* ret = new QMenu(i18n("Project Executables")); KDevelop::ProjectModel* model = KDevelop::ICore::self()->projectController()->projectModel(); QList projects = KDevelop::ICore::self()->projectController()->projects(); foreach(KDevelop::IProject* project, projects) { if(project->projectFileManager()->features() & KDevelop::IProjectFileManager::Targets) { QList targets=targetsInFolder(project->projectItem()); QHash > targetsContainer; QMenu* projectMenu = ret->addMenu(KIcon("project-development"), project->name()); foreach(KDevelop::ProjectTargetItem* target, targets) { if(target->executable()) { QStringList path = model->pathFromIndex(target->index()); if(!path.isEmpty()){ QAction* act = new QAction(projectMenu); act->setData(KDevelop::joinWithEscaping(path, '/','\\')); act->setProperty("name", target->text()); path.removeFirst(); act->setText(path.join("/")); act->setIcon(KIcon("system-run")); connect(act, SIGNAL(triggered(bool)), SLOT(suggestionTriggered())); targetsContainer[target->parent()].append(act); } } } QList separateActions; QList submenus; foreach(KDevelop::ProjectBaseItem* folder, targetsContainer.keys()) { QList actions = targetsContainer.value(folder); if(actions.size()==1 || !folder->parent()) { separateActions += actions.first(); } else { foreach(QAction* a, actions) { a->setText(a->property("name").toString()); } QStringList path = model->pathFromIndex(folder->index()); path.removeFirst(); QMenu* submenu = new QMenu(path.join("/")); submenu->addActions(actions); submenus += submenu; } } qSort(separateActions.begin(), separateActions.end(), actionLess); qSort(submenus.begin(), submenus.end(), menuLess); foreach(QMenu* m, submenus) projectMenu->addMenu(m); projectMenu->addActions(separateActions); projectMenu->setEnabled(!projectMenu->isEmpty()); } } return ret; } void NativeAppConfigType::suggestionTriggered() { QAction* action = qobject_cast(sender()); KDevelop::ProjectModel* model = KDevelop::ICore::self()->projectController()->projectModel(); KDevelop::ProjectTargetItem* pitem = dynamic_cast(itemForPath(KDevelop::splitWithEscaping(action->data().toString(),'/', '\\'), model)); if(pitem) { QPair launcher = qMakePair( launchers().at( 0 )->supportedModes().at(0), launchers().at( 0 )->id() ); KDevelop::IProject* p = pitem->project(); KDevelop::ILaunchConfiguration* config = KDevelop::ICore::self()->runController()->createLaunchConfiguration(this, launcher, p, pitem->text()); KConfigGroup cfg = config->config(); QStringList splitPath = model->pathFromIndex(pitem->index()); // QString path = KDevelop::joinWithEscaping(splitPath,'/','\\'); cfg.writeEntry( ExecutePlugin::projectTargetEntry, splitPath ); cfg.writeEntry( ExecutePlugin::dependencyEntry, KDevelop::qvariantToString( QVariantList() << splitPath ) ); cfg.writeEntry( ExecutePlugin::dependencyActionEntry, "Build" ); cfg.sync(); emit signalAddLaunchConfiguration(config); } } #include "nativeappconfig.moc" diff --git a/plugins/executescript/scriptappconfig.cpp b/plugins/executescript/scriptappconfig.cpp index 370231a587..a688dbe512 100644 --- a/plugins/executescript/scriptappconfig.cpp +++ b/plugins/executescript/scriptappconfig.cpp @@ -1,234 +1,230 @@ /* This file is part of KDevelop Copyright 2009 Andreas Pakulat Copyright 2009 Niko Sams This library is free software; you can redistribute it and/or modify it under the terms of the GNU Library General Public License as published by the Free Software Foundation; either version 2 of the License, or (at your option) any later version. This library is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Library General Public License for more details. You should have received a copy of the GNU Library General Public License along with this library; see the file COPYING.LIB. If not, write to the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "scriptappconfig.h" #include #include #include #include #include #include #include #include "scriptappjob.h" #include #include #include #include #include #include #include #include #include #include #include #include "executescriptplugin.h" #include #include #include KIcon ScriptAppConfigPage::icon() const { return KIcon("system-run"); } void ScriptAppConfigPage::loadFromConfiguration(const KConfigGroup& cfg, KDevelop::IProject* project ) { bool b = blockSignals( true ); if( project ) { executablePath->setStartDir( project->folder() ); } interpreter->lineEdit()->setText( cfg.readEntry( ExecuteScriptPlugin::interpreterEntry, "" ) ); executablePath->setUrl( cfg.readEntry( ExecuteScriptPlugin::executableEntry, "" ) ); remoteHostCheckbox->setChecked( cfg.readEntry( ExecuteScriptPlugin::executeOnRemoteHostEntry, false ) ); remoteHost->setText( cfg.readEntry( ExecuteScriptPlugin::remoteHostEntry, "" ) ); bool runCurrent = cfg.readEntry( ExecuteScriptPlugin::runCurrentFileEntry, true ); if ( runCurrent ) { runCurrentFile->setChecked( true ); } else { runFixedFile->setChecked( true ); } arguments->setText( cfg.readEntry( ExecuteScriptPlugin::argumentsEntry, "" ) ); workingDirectory->setUrl( cfg.readEntry( ExecuteScriptPlugin::workingDirEntry, KUrl() ) ); - environment->setCurrentProfile( cfg.readEntry( ExecuteScriptPlugin::environmentGroupEntry, "default" ) ); + environment->setCurrentProfile( cfg.readEntry( ExecuteScriptPlugin::environmentGroupEntry, QString() ) ); outputFilteringMode->setCurrentIndex( cfg.readEntry( ExecuteScriptPlugin::outputFilteringEntry, 0u )); //runInTerminal->setChecked( cfg.readEntry( ExecuteScriptPlugin::useTerminalEntry, false ) ); blockSignals( b ); } ScriptAppConfigPage::ScriptAppConfigPage( QWidget* parent ) : LaunchConfigurationPage( parent ) { setupUi(this); interpreter->lineEdit()->setPlaceholderText(i18n("Type or select an interpreter")); //Set workingdirectory widget to ask for directories rather than files workingDirectory->setMode(KFile::Directory | KFile::ExistingOnly | KFile::LocalOnly); - KDevelop::EnvironmentGroupList env( KGlobal::config() ); - environment->addItems( env.groups() ); - - //connect signals to changed signal connect( interpreter->lineEdit(), SIGNAL(textEdited(QString)), SIGNAL(changed()) ); connect( executablePath->lineEdit(), SIGNAL(textEdited(QString)), SIGNAL(changed()) ); connect( executablePath, SIGNAL(urlSelected(KUrl)), SIGNAL(changed()) ); connect( arguments, SIGNAL(textEdited(QString)), SIGNAL(changed()) ); connect( workingDirectory, SIGNAL(urlSelected(KUrl)), SIGNAL(changed()) ); connect( workingDirectory->lineEdit(), SIGNAL(textEdited(QString)), SIGNAL(changed()) ); connect( environment, SIGNAL(currentIndexChanged(int)), SIGNAL(changed()) ); //connect( runInTerminal, SIGNAL(toggled(bool)), SIGNAL(changed()) ); } void ScriptAppConfigPage::saveToConfiguration( KConfigGroup cfg, KDevelop::IProject* project ) const { Q_UNUSED( project ); cfg.writeEntry( ExecuteScriptPlugin::interpreterEntry, interpreter->lineEdit()->text() ); cfg.writeEntry( ExecuteScriptPlugin::executableEntry, executablePath->url() ); cfg.writeEntry( ExecuteScriptPlugin::executeOnRemoteHostEntry, remoteHostCheckbox->isChecked() ); cfg.writeEntry( ExecuteScriptPlugin::remoteHostEntry, remoteHost->text() ); cfg.writeEntry( ExecuteScriptPlugin::runCurrentFileEntry, runCurrentFile->isChecked() ); cfg.writeEntry( ExecuteScriptPlugin::argumentsEntry, arguments->text() ); cfg.writeEntry( ExecuteScriptPlugin::workingDirEntry, workingDirectory->url() ); cfg.writeEntry( ExecuteScriptPlugin::environmentGroupEntry, environment->currentProfile() ); cfg.writeEntry( ExecuteScriptPlugin::outputFilteringEntry, outputFilteringMode->currentIndex() ); //cfg.writeEntry( ExecuteScriptPlugin::useTerminalEntry, runInTerminal->isChecked() ); } QString ScriptAppConfigPage::title() const { return i18n("Configure Script Application"); } QList< KDevelop::LaunchConfigurationPageFactory* > ScriptAppLauncher::configPages() const { return QList(); } QString ScriptAppLauncher::description() const { return i18n("Executes Script Applications"); } QString ScriptAppLauncher::id() { return "scriptAppLauncher"; } QString ScriptAppLauncher::name() const { return i18n("Script Application"); } ScriptAppLauncher::ScriptAppLauncher(ExecuteScriptPlugin* plugin) : m_plugin( plugin ) { } KJob* ScriptAppLauncher::start(const QString& launchMode, KDevelop::ILaunchConfiguration* cfg) { Q_ASSERT(cfg); if( !cfg ) { return 0; } if( launchMode == "execute" ) { return new ScriptAppJob( m_plugin, cfg); } kWarning() << "Unknown launch mode " << launchMode << "for config:" << cfg->name(); return 0; } QStringList ScriptAppLauncher::supportedModes() const { return QStringList() << "execute"; } KDevelop::LaunchConfigurationPage* ScriptAppPageFactory::createWidget(QWidget* parent) { return new ScriptAppConfigPage( parent ); } ScriptAppPageFactory::ScriptAppPageFactory() { } ScriptAppConfigType::ScriptAppConfigType() { factoryList.append( new ScriptAppPageFactory() ); } ScriptAppConfigType::~ScriptAppConfigType() { qDeleteAll(factoryList); factoryList.clear(); } QString ScriptAppConfigType::name() const { return i18n("Script Application"); } QList ScriptAppConfigType::configPages() const { return factoryList; } QString ScriptAppConfigType::id() const { return ExecuteScriptPlugin::_scriptAppConfigTypeId; } KIcon ScriptAppConfigType::icon() const { return KIcon("preferences-plugin-script"); } bool ScriptAppConfigType::canLaunch(const KUrl& /*file*/) const { return false; } bool ScriptAppConfigType::canLaunch(KDevelop::ProjectBaseItem* /*item*/) const { return false; } void ScriptAppConfigType::configureLaunchFromItem(KConfigGroup /*config*/, KDevelop::ProjectBaseItem* /*item*/) const { } void ScriptAppConfigType::configureLaunchFromCmdLineArguments(KConfigGroup cfg, const QStringList &args) const { QStringList a(args); cfg.writeEntry( ExecuteScriptPlugin::interpreterEntry, a.takeFirst() ); cfg.writeEntry( ExecuteScriptPlugin::executableEntry, a.takeFirst() ); cfg.writeEntry( ExecuteScriptPlugin::argumentsEntry, KShell::joinArgs(a) ); cfg.sync(); } #include "scriptappconfig.moc" diff --git a/util/CMakeLists.txt b/util/CMakeLists.txt index 5bf1255882..ea2d6afcbc 100644 --- a/util/CMakeLists.txt +++ b/util/CMakeLists.txt @@ -1,82 +1,83 @@ add_definitions( -DKDE_DEFAULT_DEBUG_AREA=9508 ) ########### next target ############### set(kdevplatformutil_LIB_SRCS formattinghelpers.cpp richtextpushbutton.cpp richtexttoolbutton.cpp kdevstringhandler.cpp focusedtreeview.cpp processlinemaker.cpp commandexecutor.cpp environmentconfigurebutton.cpp environmentselectionwidget.cpp + environmentselectionmodel.cpp environmentgrouplist.cpp activetooltip.cpp executecompositejob.cpp fileutils.cpp shellutils.cpp sequentiallyrunjobs.cpp multilevellistview.cpp placeholderitemproxymodel.cpp projecttestjob.cpp ) set (kdevplatformutil_LIB_UI runoptions.ui ) if(NOT WIN32) add_subdirectory(dbus_socket_transformer) endif(NOT WIN32) add_subdirectory(duchainify) add_subdirectory(tests) kde4_add_ui_files(kdevplatformutil_LIB_SRCS ${kdevplatformutil_LIB_US}) kde4_add_library(kdevplatformutil SHARED ${kdevplatformutil_LIB_SRCS}) target_link_libraries(kdevplatformutil ${KDE4_KDEUI_LIBS} ${KDE4_KCMUTILS_LIBRARY} kdevplatforminterfaces ) # Might want to add kdevplatform* when they're exported targets target_link_libraries(kdevplatformutil LINK_INTERFACE_LIBRARIES ${KDE4_KDEUI_LIBS}) set_target_properties(kdevplatformutil PROPERTIES VERSION ${KDEVPLATFORM_LIB_VERSION} SOVERSION ${KDEVPLATFORM_LIB_SOVERSION}) install(TARGETS kdevplatformutil EXPORT KDevPlatformTargets ${INSTALL_TARGETS_DEFAULT_ARGS} ) install( FILES kdevplatform_shell_environment.sh DESTINATION bin PERMISSIONS OWNER_EXECUTE OWNER_WRITE OWNER_READ GROUP_EXECUTE GROUP_READ WORLD_EXECUTE WORLD_READ) install( FILES kdev_format_source DESTINATION bin PERMISSIONS OWNER_EXECUTE OWNER_WRITE OWNER_READ GROUP_EXECUTE GROUP_READ WORLD_EXECUTE WORLD_READ) ########### install files ############### install( FILES formattinghelpers.h richtextpushbutton.h richtexttoolbutton.h kdevstringhandler.h ksharedobject.h focusedtreeview.h activetooltip.h processlinemaker.h commandexecutor.h utilexport.h environmentconfigurebutton.h environmentselectionwidget.h environmentgrouplist.h pushvalue.h kdevvarlengtharray.h embeddedfreetree.h executecompositejob.h convenientfreelist.h spinlock.h fileutils.h sequentiallyrunjobs.h multilevellistview.h placeholderitemproxymodel.h projecttestjob.h DESTINATION ${INCLUDE_INSTALL_DIR}/kdevplatform/util COMPONENT Devel) diff --git a/util/environmentconfigurebutton.cpp b/util/environmentconfigurebutton.cpp index b95e5365b2..c61364b161 100644 --- a/util/environmentconfigurebutton.cpp +++ b/util/environmentconfigurebutton.cpp @@ -1,104 +1,95 @@ /* This file is part of KDevelop Copyright 2010 Milian Wolff This library is free software; you can redistribute it and/or modify it under the terms of the GNU Library General Public License as published by the Free Software Foundation; either version 2 of the License, or (at your option) any later version. This library is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Library General Public License for more details. You should have received a copy of the GNU Library General Public License along with this library; see the file COPYING.LIB. If not, write to the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "environmentconfigurebutton.h" #include "environmentselectionwidget.h" #include "environmentgrouplist.h" #include #include #include #include #include #include namespace KDevelop { class EnvironmentConfigureButtonPrivate { public: EnvironmentConfigureButtonPrivate(EnvironmentConfigureButton* _q) : q(_q), selectionWidget(0) { } void showDialog() { KDialog dlg(qApp->activeWindow()); QStringList selected; if (selectionWidget) { - selected << selectionWidget->currentProfile(); + selected << selectionWidget->effectiveProfileName(); } KCModuleProxy proxy("kcm_kdev_envsettings", 0, selected); dlg.setMainWidget(&proxy); dlg.setWindowTitle(proxy.moduleInfo().moduleName()); dlg.setWindowIcon(KIcon(proxy.moduleInfo().icon())); dlg.resize(480, 320); if (dlg.exec() == KDialog::Accepted) { proxy.save(); - if (selectionWidget) { - const QString wasSelected = selectionWidget->currentProfile(); - KDevelop::EnvironmentGroupList env( KGlobal::config() ); - selectionWidget->clear(); - selectionWidget->addItems(env.groups()); - if (env.groups().contains(wasSelected)) { - selectionWidget->setCurrentProfile(wasSelected); - } else { - selectionWidget->setCurrentProfile(env.defaultGroup()); - } - } emit q->environmentConfigured(); } } EnvironmentConfigureButton *q; EnvironmentSelectionWidget *selectionWidget; }; EnvironmentConfigureButton::EnvironmentConfigureButton(QWidget* parent) : QPushButton(parent), d(new EnvironmentConfigureButtonPrivate(this)) { setText(QString()); setSizePolicy(QSizePolicy::Minimum, QSizePolicy::Minimum); setIcon(KIcon("configure")); setToolTip(i18n("Configure environment variables")); connect(this, SIGNAL(clicked(bool)), this, SLOT(showDialog())); } EnvironmentConfigureButton::~EnvironmentConfigureButton() { delete d; } void EnvironmentConfigureButton::setSelectionWidget(EnvironmentSelectionWidget* widget) { + connect(this, SIGNAL(environmentConfigured()), + widget, SLOT(reconfigure())); d->selectionWidget = widget; } } #include "environmentconfigurebutton.moc" diff --git a/util/environmentgrouplist.cpp b/util/environmentgrouplist.cpp index cec71bde7e..17a5357818 100644 --- a/util/environmentgrouplist.cpp +++ b/util/environmentgrouplist.cpp @@ -1,190 +1,200 @@ /* This file is part of KDevelop Copyright 2007 Andreas Pakulat This library is free software; you can redistribute it and/or modify it under the terms of the GNU Library General Public License as published by the Free Software Foundation; either version 2 of the License, or (at your option) any later version. This library is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Library General Public License for more details. You should have received a copy of the GNU Library General Public License along with this library; see the file COPYING.LIB. If not, write to the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "environmentgrouplist.h" #include #include #include #include #include #include namespace KDevelop { class EnvironmentGroupListPrivate { public: QMap > m_groups; QString m_defaultGroup; }; static const QString defaultEnvGroupKey = "Default Environment Group"; static const QString envGroup = "Environment Settings"; static const QString groupListKey = "Group List"; void decode( KConfigGroup cfg, EnvironmentGroupListPrivate* d ) { d->m_defaultGroup = cfg.readEntry( defaultEnvGroupKey, QString( "default" ) ); QStringList grouplist = cfg.readEntry( groupListKey, QStringList() << "default" ); foreach( const QString &envgrpname, grouplist ) { KConfigGroup envgrp( &cfg, envgrpname ); QMap variables; foreach( const QString &varname, envgrp.keyList() ) { variables[varname] = envgrp.readEntry( varname, QString("") ); } d->m_groups.insert( envgrpname, variables ); } } void encode( KConfigGroup cfg, EnvironmentGroupListPrivate* d ) { cfg.writeEntry( defaultEnvGroupKey, d->m_defaultGroup ); cfg.writeEntry( groupListKey, d->m_groups.keys() ); foreach( const QString &group, cfg.groupList() ) { if( !d->m_groups.keys().contains( group ) ) { cfg.deleteGroup( group ); } } foreach( const QString &group, d->m_groups.keys() ) { KConfigGroup envgrp( &cfg, group ); envgrp.deleteGroup(); foreach( const QString &var, d->m_groups[group].keys() ) { envgrp.writeEntry( var, d->m_groups[group][var] ); } } cfg.sync(); } +EnvironmentGroupList::EnvironmentGroupList( const EnvironmentGroupList& rhs ) + : d( new EnvironmentGroupListPrivate( *rhs.d ) ) +{ +} + +EnvironmentGroupList& EnvironmentGroupList::operator=( const EnvironmentGroupList& rhs ) +{ + *d = *rhs.d; + return *this; +} + EnvironmentGroupList::EnvironmentGroupList( KSharedConfigPtr config ) - : d(new EnvironmentGroupListPrivate) + : d( new EnvironmentGroupListPrivate ) { KConfigGroup cfg( config, envGroup ); decode( cfg, d ); } EnvironmentGroupList::EnvironmentGroupList( KConfig* config ) - : d(new EnvironmentGroupListPrivate) + : d( new EnvironmentGroupListPrivate ) { KConfigGroup cfg( config, envGroup ); decode( cfg, d ); } - EnvironmentGroupList::~EnvironmentGroupList() { delete d; } const QMap EnvironmentGroupList::variables( const QString& group ) const { return d->m_groups[group.isEmpty() ? d->m_defaultGroup : group]; } QMap& EnvironmentGroupList::variables( const QString& group ) { return d->m_groups[group.isEmpty() ? d->m_defaultGroup : group]; } QString EnvironmentGroupList::defaultGroup() const { return d->m_defaultGroup; } void EnvironmentGroupList::setDefaultGroup( const QString& group ) { if( group.isEmpty() ) { return; } if( d->m_groups.contains( group ) ) { d->m_defaultGroup = group; } } void EnvironmentGroupList::saveSettings( KConfig* config ) const { KConfigGroup cfg(config, envGroup ); encode( cfg, d ); config->sync(); } void EnvironmentGroupList::loadSettings( KConfig* config ) { d->m_groups.clear(); KConfigGroup cfg(config, envGroup ); decode( cfg, d ); } QStringList EnvironmentGroupList::groups() const { return d->m_groups.keys(); } void EnvironmentGroupList::removeGroup( const QString& group ) { d->m_groups.remove( group ); } EnvironmentGroupList::EnvironmentGroupList() - : d( new EnvironmentGroupListPrivate) + : d( new EnvironmentGroupListPrivate ) { } QStringList EnvironmentGroupList::createEnvironment( const QString & group, const QStringList & defaultEnvironment ) const { QMap retMap; foreach( const QString &line, defaultEnvironment ) { QString varName = line.section( '=', 0, 0 ); QString varValue = line.section( '=', 1 ); retMap.insert( varName, varValue ); } if( !group.isEmpty() ) { QMap userMap = variables(group); for( QMap::const_iterator it = userMap.constBegin(); it != userMap.constEnd(); ++it ) { retMap.insert( it.key(), it.value() ); } } QStringList env; for( QMap::const_iterator it = retMap.constBegin(); it != retMap.constEnd(); ++it ) { env << it.key() + '=' + it.value(); } return env; } } diff --git a/util/environmentgrouplist.h b/util/environmentgrouplist.h index 4981b73577..5dd564b847 100644 --- a/util/environmentgrouplist.h +++ b/util/environmentgrouplist.h @@ -1,141 +1,144 @@ /* This file is part of KDevelop Copyright 2007 Andreas Pakulat This library is free software; you can redistribute it and/or modify it under the terms of the GNU Library General Public License as published by the Free Software Foundation; either version 2 of the License, or (at your option) any later version. This library is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Library General Public License for more details. You should have received a copy of the GNU Library General Public License along with this library; see the file COPYING.LIB. If not, write to the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef KDEVPLATFORM_ENVIRONMENTGROUPLIST_H #define KDEVPLATFORM_ENVIRONMENTGROUPLIST_H #include "utilexport.h" #include class KConfig; template class QMap; class QString; class QStringList; namespace KDevelop { /** * This class manages a list of environment groups, each group containing a number * of environment variables and their values. * * The class is constructed from a KConfig object for easy usage in the plugins. * * The methods to change the environments is protected to disallow access to those methods * from plugins, only the environment widget is allowed to change them. * * Example Usage * \code * KSharedConfigPtr config = KGlobal::config(); * EnvironmentGroupList env(config); * KConfigGroup cfg(config, "QMake Builder"); * QMap myenvVars = env.variables( cfg.readEntry("QMake Environment") ); * \endcode * * Two entries are used by this class: * "Default Environment Group" and "Environment Variables". * * "Default Environment Variables" stores the default group that should be used if the * user didn't select a group via a plugins configuration dialog. * * "Environment Variables" entry stores the actual list of * . The groupname can't contain '%' or '='. * For example, suppose that two configuration, say "release" and "debug" exist. * Then the actual contents of .kdev4 project file will be * * \code * [Environment Settings] * Default Environment Group=debug * Environment Variables=debug_PATH=/home/kde-devel/usr/bin,release_PATH=/usr/bin * \endcode * */ class KDEVPLATFORMUTIL_EXPORT EnvironmentGroupList { public: + EnvironmentGroupList( const EnvironmentGroupList& rhs ); + EnvironmentGroupList& operator=( const EnvironmentGroupList& rhs ); + /** * Creates an a list of EnvironmentGroups from a KConfig object * @param config the KConfig object to read the environment groups from */ EnvironmentGroupList( KSharedConfigPtr config ); EnvironmentGroupList( KConfig* config ); ~EnvironmentGroupList(); /** * Creates a merged environment between the defaults specified by * \a defaultEnvironment and those saved in \a group */ QStringList createEnvironment(const QString& group, const QStringList& defaultEnvironment ) const; /** * returns the variables that are set for a given group. * This function provides read-only access to the environment * @param group the name of the group for which the environment should be returned * @return a map containing the environment variables for this group, or an empty map if the group doesn't exist in this list */ const QMap variables( const QString& group ) const; /** * returns the default group * The default group should be used by plugins unless the user chooses a different group * @return the name of the default group, defaults to "default" */ QString defaultGroup() const; /** * Fetch the list of known groups from the list * @return the list of groups */ QStringList groups() const; protected: EnvironmentGroupList(); /** * returns the variables that are set for a given group. * This function provides write access to the environment, so new variables can be inserted, existing ones changed or deleted * * If a non-existing group is specified this returns a new empty map and that way this function can be used to add a new group * to the list of environment groups * @param group the name of the group for which the environment should be returned * @return a map containing the environment variables for this group, or an empty map if the group doesn't exist in this list */ QMap& variables( const QString& group ); /** * Changes the default group. * @param group a new groupname, if a group of this name doesn't exist the default group is not changed */ void setDefaultGroup( const QString& group ); /** * Stores the environment groups in this list to the given KConfig object * @param config a KConfig object to which the environment settings should be stored */ void saveSettings( KConfig* config ) const; void loadSettings( KConfig* config ); void removeGroup( const QString& group ); private: class EnvironmentGroupListPrivate* const d; }; } #endif diff --git a/util/environmentselectionmodel.cpp b/util/environmentselectionmodel.cpp new file mode 100644 index 0000000000..5885624950 --- /dev/null +++ b/util/environmentselectionmodel.cpp @@ -0,0 +1,113 @@ +/* This file is part of KDevelop +Copyright 2013 Ivan Shapovalov + +This library is free software; you can redistribute it and/or +modify it under the terms of the GNU Library General Public +License as published by the Free Software Foundation; either +version 2 of the License, or (at your option) any later version. + +This library is distributed in the hope that it will be useful, +but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU +Library General Public License for more details. + +You should have received a copy of the GNU Library General Public License +along with this library; see the file COPYING.LIB. If not, write to +the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, +Boston, MA 02110-1301, USA. +*/ + +#include "environmentselectionmodel.h" + +namespace +{ + +QStringList entriesFromEnv( const KDevelop::EnvironmentGroupList& env ) +{ + // We add an empty (i. e. default profile) entry to the front of the model's list. + return QStringList( QString() ) + env.groups(); +} + +} + +namespace KDevelop +{ + +EnvironmentSelectionModel::EnvironmentSelectionModel( QObject* parent ) : + QStringListModel( parent ), + m_env( KGlobal::config() ) +{ + setStringList( entriesFromEnv( m_env ) ); + m_groupsLookupTable = stringList().toSet(); +} + +QVariant EnvironmentSelectionModel::headerData( int section, Qt::Orientation orientation, int role ) const +{ + if( section != 0 || + orientation != Qt::Horizontal || + role != Qt::DisplayRole ) { + return QVariant(); + } + + return i18nc("@title:column", "Profile"); +} + +QVariant EnvironmentSelectionModel::data( const QModelIndex& index, int role ) const +{ + QVariant nativeData = QStringListModel::data( index, Qt::DisplayRole ); + QString profileName = nativeData.toString(); + + switch( role ) { + case Qt::DisplayRole: + if( profileName.isEmpty() ) { + return i18nc( "@item:inlistbox", "Use default profile (currently: %1)", m_env.defaultGroup() ); + } + + if( !m_groupsLookupTable.contains( profileName ) ) { + return i18nc( "@item:inlistbox", "%1 (does not exist)", profileName ); + } + + return nativeData; + + case EffectiveNameRole: + if( profileName.isEmpty() ) { + return m_env.defaultGroup(); + } + + return nativeData; + + default: + return QStringListModel::data( index, role ); + } +} + +bool EnvironmentSelectionModel::setData( const QModelIndex& index, const QVariant& value, int role ) +{ + return false; +} + +EnvironmentGroupList EnvironmentSelectionModel::environment() const +{ + return m_env; +} + +void EnvironmentSelectionModel::reload() +{ + m_env = EnvironmentGroupList( KGlobal::config() ); + + setStringList( entriesFromEnv( m_env ) ); + m_groupsLookupTable = stringList().toSet(); +} + +QString EnvironmentSelectionModel::reloadSelectedItem( const QString& currentProfile ) +{ + if( m_groupsLookupTable.contains( currentProfile ) ) { + return currentProfile; + } else { + return QString(); + } +} + +} // namespace KDevelop + +#include "environmentselectionmodel.moc" diff --git a/util/environmentselectionmodel.h b/util/environmentselectionmodel.h new file mode 100644 index 0000000000..aff563789e --- /dev/null +++ b/util/environmentselectionmodel.h @@ -0,0 +1,76 @@ +/* This file is part of KDevelop +Copyright 2013 Ivan Shapovalov + +This library is free software; you can redistribute it and/or +modify it under the terms of the GNU Library General Public +License as published by the Free Software Foundation; either +version 2 of the License, or (at your option) any later version. + +This library is distributed in the hope that it will be useful, +but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU +Library General Public License for more details. + +You should have received a copy of the GNU Library General Public License +along with this library; see the file COPYING.LIB. If not, write to +the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, +Boston, MA 02110-1301, USA. +*/ + +#ifndef ENVIRONMENTSELECTIONMODEL_H +#define ENVIRONMENTSELECTIONMODEL_H + +#include "environmentgrouplist.h" + +#include + +#include +#include + +namespace KDevelop +{ + +class EnvironmentSelectionModel : public QStringListModel +{ + Q_OBJECT + +public: + enum SpecialRoles + { + EffectiveNameRole = Qt::UserRole + 1 + }; + + explicit EnvironmentSelectionModel( QObject* parent = 0 ); + + virtual QVariant headerData( int section, Qt::Orientation orientation, int role = Qt::DisplayRole ) const; + + virtual QVariant data( const QModelIndex& index, int role ) const; + virtual bool setData( const QModelIndex& index, const QVariant& value, int role = Qt::EditRole ); + + /** + * @returns The @ref EnvironmentGroupList which has bee used to populate this + * model. + */ + EnvironmentGroupList environment() const; + + /** + * Reloads the model from the global config. + */ + void reload(); + + /** + * Shall be used by views to update selection (current item) after the model has been reloaded. + * + * @param currentProfile Previous selected item. + * @returns The item which shall become selected. + */ + QString reloadSelectedItem( const QString& currentProfile ); + +private: + EnvironmentGroupList m_env; + QSet m_groupsLookupTable; +}; + +} // namespace KDevelop + +#endif // ENVIRONMENTSELECTIONMODEL_H diff --git a/util/environmentselectionwidget.cpp b/util/environmentselectionwidget.cpp index a198f32284..5f62db58a5 100644 --- a/util/environmentselectionwidget.cpp +++ b/util/environmentselectionwidget.cpp @@ -1,65 +1,104 @@ /* This file is part of KDevelop Copyright 2007 Dukju Ahn This library is free software; you can redistribute it and/or modify it under the terms of the GNU Library General Public License as published by the Free Software Foundation; either version 2 of the License, or (at your option) any later version. This library is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Library General Public License for more details. You should have received a copy of the GNU Library General Public License along with this library; see the file COPYING.LIB. If not, write to the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include "environmentselectionwidget.h" #include "environmentgrouplist.h" +#include "environmentselectionmodel.h" #include #include #include #include +#include +#include +#include +#include namespace KDevelop { -class EnvironmentSelectionWidgetPrivate +struct EnvironmentSelectionWidgetPrivate { + KComboBox* comboBox; + EnvironmentSelectionModel* model; + EnvironmentSelectionWidget* owner; + + EnvironmentSelectionWidgetPrivate( EnvironmentSelectionWidget* _owner ) + : comboBox( new KComboBox( _owner ) ) + , model( new EnvironmentSelectionModel( _owner ) ) + , owner( _owner ) + { + comboBox->setModel( model ); + comboBox->setEditable( false ); + } }; EnvironmentSelectionWidget::EnvironmentSelectionWidget( QWidget *parent ) - : KComboBox( parent ), d( new EnvironmentSelectionWidgetPrivate ) + : QWidget( parent ), d( new EnvironmentSelectionWidgetPrivate( this ) ) { // Taken from kdelibs/kdeui/dialogs/kconfigdialogmanager.cpp (no idea whether this is documented) // Commits d44186bce4670d2985fb6aba8dba59bbd2c4c77a and 8edc1932ecc62370d9a31836dfa9b2bd0175a293 // introduced a regression in kdelibs to fix problems running some apps against Qt4.8. Unfortunately // this fix breaks exactly our use-case, which is to store the text-value in kconfig instead of // the index even though the combobox is editable. Since that change the special combobox-code in // kconfigdialogmanager.cpp is run before check a user-property and hence our user-property is // ignored. Setting this special kcfg_property to the name of our user-property again overrides // the hardcoded combobox-behaviour - until the next one breaks things in kdelibs :| setProperty("kcfg_property", QByteArray("currentProfile")); + + setLayout( new QHBoxLayout( this ) ); + layout()->addWidget( d->comboBox ); + layout()->setMargin( 0 ); + + setCurrentProfile( QString() ); // select the default profile } EnvironmentSelectionWidget::~EnvironmentSelectionWidget() { delete d; } QString EnvironmentSelectionWidget::currentProfile() const { - return currentText(); + return d->model->index( d->comboBox->currentIndex(), 0 ).data( Qt::EditRole ).toString(); } void EnvironmentSelectionWidget::setCurrentProfile( const QString& profile ) { - setCurrentItem( profile ); + d->comboBox->setCurrentIndex( d->comboBox->findData( profile, Qt::EditRole ) ); +} + +void EnvironmentSelectionWidget::reconfigure() +{ + QString selectedProfile = currentProfile(); + d->model->reload(); + setCurrentProfile( d->model->reloadSelectedItem( selectedProfile ) ); } +QString EnvironmentSelectionWidget::effectiveProfileName() const +{ + return d->model->index( d->comboBox->currentIndex(), 0 ).data( EnvironmentSelectionModel::EffectiveNameRole ).toString(); +} + +EnvironmentGroupList EnvironmentSelectionWidget::environment() const +{ + return d->model->environment(); +} } #include "environmentselectionwidget.moc" diff --git a/util/environmentselectionwidget.h b/util/environmentselectionwidget.h index 0784ba1452..ede70012b7 100644 --- a/util/environmentselectionwidget.h +++ b/util/environmentselectionwidget.h @@ -1,82 +1,86 @@ /* This file is part of KDevelop Copyright 2007 Dukju Ahn This library is free software; you can redistribute it and/or modify it under the terms of the GNU Library General Public License as published by the Free Software Foundation; either version 2 of the License, or (at your option) any later version. This library is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Library General Public License for more details. You should have received a copy of the GNU Library General Public License along with this library; see the file COPYING.LIB. If not, write to the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #ifndef KDEVPLATFORM_ENVIRONMENTSELECTIONWIDGET_H #define KDEVPLATFORM_ENVIRONMENTSELECTIONWIDGET_H #include + #include "utilexport.h" +#include "environmentgrouplist.h" namespace KDevelop { /** - * Simple compobox which allows each plugin to decide which environment + * Simple combobox which allows each plugin to decide which environment * variable group to use. * * Can be used just like a KComboBox in Configuration dialogs including usage * with KConfigXT. * - * Example code to populate the list: - * \code - * EnvironmentGroupList envlist( PluginSettings::self()->config() ); - * ui->kcfg_environmentGroup->addItems( envlist.groups()) ); - * \endcode - * - * The .kcfg file for that would include an entry like this: - * \code - * - * default - * - * \endcode - * - * It is important to list "default" as the default value, because that is currently - * the only way to avoid an empty entry in the combo box. + * @note The widget is populated and defaulted automatically. * */ -class KDEVPLATFORMUTIL_EXPORT EnvironmentSelectionWidget : public KComboBox +class KDEVPLATFORMUTIL_EXPORT EnvironmentSelectionWidget : public QWidget { Q_OBJECT Q_PROPERTY( QString currentProfile READ currentProfile WRITE setCurrentProfile USER true ) public: explicit EnvironmentSelectionWidget( QWidget *parent = 0 ); ~EnvironmentSelectionWidget(); /** - * Return the currently selected text as special property so this widget - * works with KConfigXT - * @returns the currently selected items text + * @returns The currently selected environment profile name, as written to KConfigXT */ QString currentProfile() const; /** - * Setter for the KConfigXT property - * @param text the item text which should be set as current. + * Sets the environment profile to be written to KConfigXT and updates the combo-box. + * + * @param text The environment profile name to select */ void setCurrentProfile( const QString& text ); -private: - class EnvironmentSelectionWidgetPrivate* const d; - friend class EnvironmentSelectionWidgetPrivate; + /** + * @returns The currently effective environment profile name (like @ref currentProfile(), + * but with empty value resolved to the default profile). + */ + QString effectiveProfileName() const; + /** + * @returns The @ref EnvironmentGroupList which has been used to populate this + * widget. + */ + EnvironmentGroupList environment() const; + +public slots: + /** + * Makes the widget re-read its environment group list. + */ + void reconfigure(); + +private: + struct EnvironmentSelectionWidgetPrivate* const d; + friend struct EnvironmentSelectionWidgetPrivate; }; } #endif