[kde-doc-english] [kate] addons/project: project: auto detect git/svn/hg repositories

Michal Humpula michal.humpula at hudrydum.cz
Tue Sep 9 19:52:22 UTC 2014


Git commit 8ec7aea613ed45243b4c80ff11ccde64f73c2c36 by Michal Humpula.
Committed on 08/09/2014 at 16:18.
Pushed by michalhumpula into branch 'master'.

project: auto detect git/svn/hg repositories

Enable possibility to fallback to autogenarated in memory stub projects
for different repositories (git, mercurial, subversion), when
.kateproject file is not found, but repository folder is.

GUI: project plugin has now plugin config page
REVIEW: 120103

M  +1    -0    addons/project/CMakeLists.txt
M  +14   -4    addons/project/kateproject.cpp
M  +9    -4    addons/project/kateproject.h
A  +109  -0    addons/project/kateprojectconfigpage.cpp     [License: LGPL (v2+)]
A  +55   -0    addons/project/kateprojectconfigpage.h     [License: LGPL (v2+)]
M  +143  -2    addons/project/kateprojectplugin.cpp
M  +21   -0    addons/project/kateprojectplugin.h

http://commits.kde.org/kate/8ec7aea613ed45243b4c80ff11ccde64f73c2c36

diff --git a/addons/project/CMakeLists.txt b/addons/project/CMakeLists.txt
index 5a38c57..e9ee95a 100644
--- a/addons/project/CMakeLists.txt
+++ b/addons/project/CMakeLists.txt
@@ -19,6 +19,7 @@ set(kateprojectplugin_PART_SRCS
   kateprojectinfoviewterminal.cpp
   kateprojectinfoviewcodeanalysis.cpp
   kateprojectinfoviewnotes.cpp
+  kateprojectconfigpage.cpp
 )
 
 add_library (kateprojectplugin MODULE ${kateprojectplugin_PART_SRCS})
diff --git a/addons/project/kateproject.cpp b/addons/project/kateproject.cpp
index 20417e5..343d9d6 100644
--- a/addons/project/kateproject.cpp
+++ b/addons/project/kateproject.cpp
@@ -72,7 +72,7 @@ KateProject::~KateProject()
     saveNotesDocument();
 }
 
-bool KateProject::load(const QString &fileName)
+bool KateProject::loadFromFile(const QString &fileName)
 {
     /**
      * bail out if already fileName set!
@@ -109,15 +109,25 @@ bool KateProject::reload(bool force)
     const QByteArray jsonData = file.readAll();
     QJsonParseError parseError;
     QJsonDocument project(QJsonDocument::fromJson(jsonData, &parseError));
+
     if (parseError.error != QJsonParseError::NoError) {
         return false;
     }
 
-    /**
-     * now: get global group
-     */
     QVariantMap globalProject = project.toVariant().toMap();
 
+    return load(globalProject, force);
+}
+
+bool KateProject::loadFromData(const QVariantMap& globalProject, const QString& directory)
+{
+    m_baseDir = directory;
+    m_fileName = QDir(directory).filePath(QLatin1String(".kateproject"));
+    return load(globalProject);
+}
+
+bool KateProject::load(const QVariantMap &globalProject, bool force)
+{
     /**
      * no name, bad => bail out
      */
diff --git a/addons/project/kateproject.h b/addons/project/kateproject.h
index 4e59106..e400bd0 100644
--- a/addons/project/kateproject.h
+++ b/addons/project/kateproject.h
@@ -51,11 +51,13 @@ class KateProjectWorkerThread : public QThread
 public:
     KateProjectWorkerThread(QObject *worker)
         : QThread()
-        , m_worker(worker) {
+        , m_worker (worker)
+    {
     }
 
 protected:
-    virtual void run() {
+    virtual void run()
+    {
         exec();
         delete m_worker;
     }
@@ -84,12 +86,13 @@ public:
     ~KateProject();
 
     /**
-     * Load a project.
+     * Load a project from project file
      * Only works once, afterwards use reload().
      * @param fileName name of project file
      * @return success
      */
-    bool load(const QString &fileName);
+    bool loadFromFile(const QString &fileName);
+    bool loadFromData(const QVariantMap &globalProject, const QString &directory);
 
     /**
      * Try to reload a project.
@@ -200,6 +203,8 @@ public:
     void unregisterDocument(KTextEditor::Document *document);
 
 private Q_SLOTS:
+    bool load(const QVariantMap &globalProject, bool force = false);
+
     /**
      * Used for worker to send back the results of project loading
      * @param topLevel new toplevel element for model
diff --git a/addons/project/kateprojectconfigpage.cpp b/addons/project/kateprojectconfigpage.cpp
new file mode 100644
index 0000000..79962e3
--- /dev/null
+++ b/addons/project/kateprojectconfigpage.cpp
@@ -0,0 +1,109 @@
+/* This file is part of the KDE project
+
+   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 "kateprojectconfigpage.h"
+#include "kateprojectplugin.h"
+
+#include <QLabel>
+#include <QVBoxLayout>
+#include <QCheckBox>
+#include <QGroupBox>
+#include <KLocalizedString>
+
+KateProjectConfigPage::KateProjectConfigPage(QWidget *parent, KateProjectPlugin *plugin)
+    :  KTextEditor::ConfigPage(parent)
+    , m_plugin(plugin)
+    , m_changed(false)
+{
+    QVBoxLayout *layout = new QVBoxLayout(this);
+    layout->setMargin(0);
+
+    QVBoxLayout *vbox = new QVBoxLayout;
+    QGroupBox *group = new QGroupBox(i18n("Autoload repositories"), this);
+    group->setWhatsThis(i18n(
+        "Project plugin is able to autoload repository working copies in case"
+        "there is .kateproject file already defined"));
+
+    m_cbAutoGit = new QCheckBox(i18n("&Git"), this);
+    vbox->addWidget(m_cbAutoGit);
+
+    m_cbAutoSubversion = new QCheckBox(i18n("&Subversion"), this);
+    vbox->addWidget(m_cbAutoSubversion);
+    m_cbAutoMercurial = new QCheckBox(i18n("&Mercurial"), this);
+    vbox->addWidget(m_cbAutoMercurial);
+
+    vbox->addStretch(1);
+    group->setLayout(vbox);
+
+    layout->addWidget(group);
+    layout->insertStretch(-1, 10);
+
+    reset();
+
+    connect(m_cbAutoGit, SIGNAL(stateChanged(int)), this, SLOT(slotMyChanged()));
+    connect(m_cbAutoSubversion, SIGNAL(stateChanged(int)), this, SLOT(slotMyChanged()));
+    connect(m_cbAutoMercurial, SIGNAL(stateChanged(int)), this, SLOT(slotMyChanged()));
+}
+
+QString KateProjectConfigPage::name() const
+{
+    return QString(i18n("Projects"));
+}
+
+QString KateProjectConfigPage::fullName() const
+{
+    return QString(i18n("Projects properties"));
+}
+
+QIcon KateProjectConfigPage::icon() const
+{
+    return QIcon::fromTheme(QLatin1String("view-list-tree"));
+}
+
+void KateProjectConfigPage::apply()
+{
+    if (!m_changed) {
+        return;
+    }
+
+    m_changed = false;
+
+    m_plugin->setAutoRepository(
+        m_cbAutoGit->checkState() == Qt::Checked,
+        m_cbAutoSubversion->checkState() == Qt::Checked,
+        m_cbAutoMercurial->checkState() == Qt::Checked);
+}
+
+void KateProjectConfigPage::reset()
+{
+    m_cbAutoGit->setCheckState(m_plugin->autoGit() ? Qt::Checked : Qt::Unchecked);
+    m_cbAutoSubversion->setCheckState(m_plugin->autoSubversion() ? Qt::Checked : Qt::Unchecked);
+    m_cbAutoMercurial->setCheckState(m_plugin->autoMercurial() ? Qt::Checked : Qt::Unchecked);
+    m_changed = false;
+}
+
+void KateProjectConfigPage::defaults()
+{
+    reset();
+}
+
+void KateProjectConfigPage::slotMyChanged()
+{
+    m_changed = true;
+    emit changed();
+}
diff --git a/addons/project/kateprojectconfigpage.h b/addons/project/kateprojectconfigpage.h
new file mode 100644
index 0000000..9e97b60
--- /dev/null
+++ b/addons/project/kateprojectconfigpage.h
@@ -0,0 +1,55 @@
+/* This file is part of the KDE project
+
+   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 KATE_PROJECT_CONFIGPAGE_H
+#define KATE_PROJECT_CONFIGPAGE_H
+
+#include <ktexteditor/configpage.h>
+
+class KateProjectPlugin;
+class QWidget;
+class QCheckBox;
+
+class KateProjectConfigPage : public KTextEditor::ConfigPage
+{
+    Q_OBJECT
+public:
+    explicit KateProjectConfigPage(QWidget *parent = nullptr, KateProjectPlugin *plugin = nullptr);
+    ~KateProjectConfigPage() {};
+
+    virtual QString name() const;
+    virtual QString fullName() const;
+    virtual QIcon icon() const;
+
+public Q_SLOTS:
+    void apply();
+    void defaults();
+    void reset();
+
+private Q_SLOTS:
+    void slotMyChanged();
+
+private:
+    QCheckBox *m_cbAutoGit;
+    QCheckBox *m_cbAutoSubversion;
+    QCheckBox *m_cbAutoMercurial;
+    KateProjectPlugin *m_plugin;
+    bool m_changed;
+};
+
+#endif /* KATE_PROJECT_CONFIGPAGE_H */
diff --git a/addons/project/kateprojectplugin.cpp b/addons/project/kateprojectplugin.cpp
index a15489b..4832352 100644
--- a/addons/project/kateprojectplugin.cpp
+++ b/addons/project/kateprojectplugin.cpp
@@ -22,12 +22,16 @@
 #include "kateprojectplugin.moc"
 
 #include "kateproject.h"
+#include "kateprojectconfigpage.h"
 #include "kateprojectpluginview.h"
 
 #include <ktexteditor/editor.h>
 #include <ktexteditor/application.h>
 #include <ktexteditor/document.h>
 
+#include <KSharedConfig>
+#include <KConfigGroup>
+
 #include <QFileInfo>
 #include <QTime>
 
@@ -43,12 +47,22 @@
 
 namespace
 {
-const QString ProjectFileName = QLatin1String(".kateproject");
+const QString ProjectFileName = QStringLiteral(".kateproject");
+const QString GitFolderName = QStringLiteral(".git");
+const QString SubversionFolderName = QStringLiteral(".svn");
+const QString MercurialFolderName = QStringLiteral(".hg");
+
+const QString GitConfig = QStringLiteral("git");
+const QString SubversionConfig = QStringLiteral("subversion");
+const QString MercurialConfig = QStringLiteral("mercurial");
+
+const QStringList DefaultConfig = QStringList() << GitConfig << SubversionConfig << MercurialConfig;
 }
 
 KateProjectPlugin::KateProjectPlugin(QObject *parent, const QList<QVariant> &)
     : KTextEditor::Plugin(parent)
     , m_completion(this)
+    , m_autoGit(true)
 {
     qRegisterMetaType<KateProjectSharedQStandardItem>("KateProjectSharedQStandardItem");
     qRegisterMetaType<KateProjectSharedQMapStringItem>("KateProjectSharedQMapStringItem");
@@ -72,6 +86,8 @@ KateProjectPlugin::KateProjectPlugin(QObject *parent, const QList<QVariant> &)
     }
 #endif
 
+    readConfig();
+
     foreach(KTextEditor::Document * document, KTextEditor::Editor::instance()->application()->documents()) {
         slotDocumentCreated(document);
     }
@@ -91,11 +107,24 @@ QObject *KateProjectPlugin::createView(KTextEditor::MainWindow *mainWindow)
     return new KateProjectPluginView(this, mainWindow);
 }
 
+int KateProjectPlugin::configPages() const
+{
+    return 1;
+}
+
+KTextEditor::ConfigPage *KateProjectPlugin::configPage(int number, QWidget *parent)
+{
+    if (number != 0) {
+        return 0;
+    }
+    return new KateProjectConfigPage(parent, this);
+}
+
 KateProject *KateProjectPlugin::createProjectForFileName(const QString &fileName)
 {
     KateProject *project = new KateProject();
 
-    if (!project->load(fileName)) {
+    if (!project->loadFromFile(fileName)) {
         delete project;
         return 0;
     }
@@ -135,6 +164,11 @@ KateProject *KateProjectPlugin::projectForDir(QDir dir)
             return createProjectForFileName(canonicalFileName);
         }
 
+        KateProject *project;
+        if ((project = detectGit(dir)) || (project = detectSubversion(dir)) || (project = detectMercurial(dir))) {
+            return project;
+        }
+
         /**
          * else: cd up, if possible or abort
          */
@@ -201,3 +235,110 @@ void KateProjectPlugin::slotDirectoryChanged(const QString &path)
         }
     }
 }
+
+KateProject* KateProjectPlugin::detectGit(const QDir &dir)
+{
+
+    if (m_autoGit && dir.exists(GitFolderName) && QFileInfo(dir, GitFolderName).isDir()) {
+        return createProjectForRepository(QStringLiteral("git"), dir);
+    }
+
+    return nullptr;
+}
+
+KateProject* KateProjectPlugin::detectSubversion(const QDir &dir)
+{
+    if (m_autoSubversion && dir.exists(SubversionFolderName) && QFileInfo(dir, SubversionFolderName).isDir()) {
+        return createProjectForRepository(QStringLiteral("svn"), dir);
+    }
+
+    return nullptr;
+}
+
+KateProject* KateProjectPlugin::detectMercurial(const QDir &dir)
+{
+    if (m_autoMercurial && dir.exists(MercurialFolderName) && QFileInfo(dir, MercurialFolderName).isDir()) {
+        return createProjectForRepository(QStringLiteral("hg"), dir);
+    }
+
+    return nullptr;
+}
+
+KateProject *KateProjectPlugin::createProjectForRepository(const QString &type, const QDir &dir)
+{
+    QVariantMap cnf, files;
+    files[type] = 1;
+    cnf[QLatin1String("name")] = dir.dirName();
+    cnf[QLatin1String("files")] = (QVariantList() << files);
+
+    KateProject *project = new KateProject ();
+    project->loadFromData(cnf, dir.canonicalPath());
+
+    m_projects.append(project);
+
+    emit projectCreated(project);
+    return project;
+}
+
+void KateProjectPlugin::setAutoRepository(bool onGit, bool onSubversion, bool onMercurial)
+{
+    m_autoGit = onGit;
+    m_autoSubversion = onSubversion;
+    m_autoMercurial = onMercurial;
+    writeConfig();
+}
+
+bool KateProjectPlugin::autoGit() const
+{
+    return m_autoGit;
+}
+
+bool KateProjectPlugin::autoSubversion() const
+{
+    return m_autoSubversion;
+}
+
+bool KateProjectPlugin::autoMercurial() const
+{
+    return m_autoMercurial;
+}
+
+void KateProjectPlugin::readConfig()
+{
+    KConfigGroup config(KSharedConfig::openConfig(), "project");
+    QStringList autorepository = config.readEntry("autorepository", DefaultConfig);
+
+    m_autoGit = m_autoSubversion = m_autoMercurial = false;
+
+    if (autorepository.contains(GitConfig)) {
+        m_autoGit = true;
+    }
+
+    if (autorepository.contains(SubversionConfig)) {
+        m_autoSubversion = true;
+    }
+
+    if (autorepository.contains(MercurialConfig)) {
+        m_autoMercurial = true;
+    }
+}
+
+void KateProjectPlugin::writeConfig()
+{
+    KConfigGroup config(KSharedConfig::openConfig(), "project");
+    QStringList repos;
+
+    if (m_autoGit) {
+        repos << GitConfig;
+    }
+
+    if (m_autoSubversion) {
+        repos << SubversionConfig;
+    }
+
+    if (m_autoMercurial) {
+        repos << MercurialConfig;
+    }
+
+    config.writeEntry("autorepository", repos);
+}
diff --git a/addons/project/kateprojectplugin.h b/addons/project/kateprojectplugin.h
index 2317935..3af12b1 100644
--- a/addons/project/kateprojectplugin.h
+++ b/addons/project/kateprojectplugin.h
@@ -43,6 +43,9 @@ public:
 
     QObject *createView(KTextEditor::MainWindow *mainWindow);
 
+    virtual int configPages() const;
+    virtual KTextEditor::ConfigPage *configPage (int number = 0, QWidget *parent = 0);
+
     /**
      * Create new project for given project filename.
      * Null pointer if no project can be opened.
@@ -95,6 +98,11 @@ public:
         return m_document2Project.value(document);
     }
 
+    void setAutoRepository(bool onGit, bool onSubversion, bool onMercurial);
+    bool autoGit() const;
+    bool autoSubversion() const;
+    bool autoMercurial() const;
+
 Q_SIGNALS:
     /**
      * Signal that a new project got created.
@@ -127,6 +135,15 @@ public Q_SLOTS:
     void slotDirectoryChanged(const QString &path);
 
 private:
+    KateProject *createProjectForRepository(const QString &type, const QDir &dir);
+    KateProject *detectGit(const QDir &dir);
+    KateProject *detectSubversion(const QDir &dir);
+    KateProject *detectMercurial(const QDir &dir);
+
+    void readConfig();
+    void writeConfig();
+
+private:
     /**
      * open plugins, maps project base directory => project
      */
@@ -147,6 +164,10 @@ private:
      * Project completion
      */
     KateProjectCompletion m_completion;
+
+    bool m_autoGit : 1;
+    bool m_autoSubversion : 1;
+    bool m_autoMercurial : 1;
 };
 
 #endif


More information about the kde-doc-english mailing list