diff options
Diffstat (limited to 'parts/documentation/interfaces')
5 files changed, 1204 insertions, 0 deletions
diff --git a/parts/documentation/interfaces/Mainpage.dox b/parts/documentation/interfaces/Mainpage.dox new file mode 100644 index 00000000..85126a6e --- /dev/null +++ b/parts/documentation/interfaces/Mainpage.dox @@ -0,0 +1,10 @@ +/** +@mainpage The KDevelop Documentation Part Interfaces Library + +This library contains interfaces to implement KDevelop documentation plugins. + +<b>Link with</b>: -ldocumentation_interfaces + +<b>Include path</b>: -I\$(kde_includes)/kdevelop/parts/documentation +*/ + diff --git a/parts/documentation/interfaces/Makefile.am b/parts/documentation/interfaces/Makefile.am new file mode 100644 index 00000000..206f62f9 --- /dev/null +++ b/parts/documentation/interfaces/Makefile.am @@ -0,0 +1,16 @@ +INCLUDES = -I$(top_srcdir)/lib/interfaces -I$(top_srcdir)/lib/util \ + $(all_includes) +METASOURCES = AUTO +partincludedirdir = $(includedir)/kdevelop/parts/documentation +lib_LTLIBRARIES = libdocumentation_interfaces.la +libdocumentation_interfaces_la_LDFLAGS = $(all_libraries) +libdocumentation_interfaces_la_LIBADD = $(LIB_QT) $(LIB_KDECORE) $(LIB_KDEUI) $(LIB_KIO) +libdocumentation_interfaces_la_SOURCES = kdevdocumentationplugin.cpp +partincludedir_HEADERS = kdevdocumentationplugin.h +servicetypedir = $(kde_servicetypesdir) +servicetype_DATA = kdevelopdocumentationplugins.desktop + +DOXYGEN_REFERENCES = dcop interfaces kdecore kdefx kdeui khtml kmdi kio kjs kparts kutils kdevutil kdevinterfaces +DOXYGEN_PROJECTNAME = KDevelop Documentation Part Interfaces Library +DOXYGEN_DOCDIRPREFIX = kdevdoc +include ../../../Doxyfile.am diff --git a/parts/documentation/interfaces/kdevdocumentationplugin.cpp b/parts/documentation/interfaces/kdevdocumentationplugin.cpp new file mode 100644 index 00000000..8e336c83 --- /dev/null +++ b/parts/documentation/interfaces/kdevdocumentationplugin.cpp @@ -0,0 +1,721 @@ +/* This file is part of the KDE project + Copyright (C) 2004 by Alexander Dymo <cloudtemple@mksat.net> + + 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., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ +#include "kdevdocumentationplugin.h" + +#include <qfile.h> +#include <qpainter.h> +#include <qstyle.h> +#include <qheader.h> +#include <qtextstream.h> + +#include <kstandarddirs.h> +#include <kiconloader.h> +#include <kconfig.h> +#include <kdebug.h> +#include <kdirwatch.h> +#include <klocale.h> + +//class DocumentationItem + +DocumentationItem::DocumentationItem(DocumentationItem::Type type, KListView *parent, + const QString &name) + :KListViewItem(parent, name), m_type(type) +{ + init(); +} + +DocumentationItem::DocumentationItem(DocumentationItem::Type type, KListViewItem *parent, + const QString &name) + :KListViewItem(parent, name), m_type(type) +{ + init(); +} + +DocumentationItem::DocumentationItem(DocumentationItem::Type type, KListView *parent, + KListViewItem *after, const QString &name) + :KListViewItem(parent, after, name), m_type(type) +{ + init(); +} + +DocumentationItem::DocumentationItem(DocumentationItem::Type type, KListViewItem * parent, + KListViewItem * after, const QString & name ) + :KListViewItem(parent, after, name), m_type(type) +{ + init(); +} + + +void DocumentationItem::init( ) +{ + QString icon; + + switch (m_type) + { + case Collection: + case Catalog: + icon = "folder"; + break; + case Book: + icon = "contents"; + break; + default: + icon = "document"; + } + + setPixmap(0, SmallIcon(icon)); +} + + + + + +//class DocumentationCatalogItem + + +DocumentationCatalogItem::DocumentationCatalogItem(DocumentationPlugin* plugin, + KListView *parent, const QString &name) + :DocumentationItem(DocumentationItem::Catalog, parent, name), m_plugin(plugin), + isLoaded(false), isActivated(false), m_isProjectDocumentationItem(false) +{ + setExpandable(true); + m_plugin->addCatalog(this); +} + +DocumentationCatalogItem::DocumentationCatalogItem(DocumentationPlugin* plugin, + DocumentationItem *parent, const QString &name) + :DocumentationItem(DocumentationItem::Catalog, parent, name), m_plugin(plugin), + isLoaded(false), isActivated(false), m_isProjectDocumentationItem(false) +{ + setExpandable(true); + m_plugin->addCatalog(this); +} + +DocumentationCatalogItem::~ DocumentationCatalogItem( ) +{ + m_plugin->clearCatalog(this); +} + +void DocumentationCatalogItem::setOpen(bool o) +{ + if (o) + { + load(); + } + DocumentationItem::setOpen(o); +} + +void DocumentationCatalogItem::load() +{ +if(isLoaded) +return; + + plugin()->createTOC(this); + isLoaded = true; +} + +void DocumentationCatalogItem::activate() +{ + if (!isActivated) + { + plugin()->setCatalogURL(this); + isActivated = true; + } + DocumentationItem::activate(); +} + + + + +//class IndexItemProto + +IndexItemProto::IndexItemProto(DocumentationPlugin *plugin, DocumentationCatalogItem *catalog, + IndexBox *listbox, const QString &text, const QString &description) + : m_listbox(listbox), m_text(text), m_description(description) +{ + plugin->indexes[catalog].append(this); + m_listbox->addIndexItem(this); +} + +IndexItemProto::~IndexItemProto() +{ + m_listbox->removeIndexItem(this); +} + + +//class IndexItem + +IndexItem::IndexItem(IndexBox *listbox, const QString &text) + :QListBoxText(listbox, text), m_listbox(listbox) +{ +} + +IndexItem::List IndexItem::urls() const +{ + List urlList; + QValueList<IndexItemProto*> itemProtos = m_listbox->items[text()]; + for (QValueList<IndexItemProto*>::const_iterator it = itemProtos.begin(); + it != itemProtos.end(); ++it) + urlList.append(qMakePair((*it)->description(), (*it)->url())); + return urlList; +} + + + + +//class ConfigurationItem + +ConfigurationItem::ConfigurationItem(QListView *parent, DocumentationPlugin * plugin, const QString &title, const QString &url, + bool indexPossible, bool fullTextSearchPossible) + :QCheckListItem(parent, "", QCheckListItem::CheckBox), m_title(title), m_url(url), + m_origTitle(title), m_contents(true), m_index(false), m_fullTextSearch(false), + m_indexPossible(indexPossible), m_fullTextSearchPossible(fullTextSearchPossible), + m_docPlugin( plugin ) +{ + setText(3, m_title); + setText(4, m_url); +} + +void ConfigurationItem::paintCell(QPainter *p, const QColorGroup &cg, int column, + int width, int align) +{ + if ( (column == 0) || (column == 1) || (column == 2) ) + { + if ( !p ) + return; + + QListView *lv = listView(); + if ( !lv ) + return; + + const BackgroundMode bgmode = lv->viewport()->backgroundMode(); + const QColorGroup::ColorRole crole = QPalette::backgroundRoleFromMode( bgmode ); + p->fillRect(0, 0, width, height(), cg.brush(crole)); + + QFontMetrics fm(lv->fontMetrics()); + int boxsize = lv->style().pixelMetric(QStyle::PM_CheckListButtonSize, lv); + int marg = lv->itemMargin(); + int styleflags = QStyle::Style_Default; + + if (((column == 0) && m_contents) || ((column == 1) && m_index) || ((column == 2) && m_fullTextSearch)) + styleflags |= QStyle::Style_On; + else + styleflags |= QStyle::Style_Off; + if ((column == 0) || ((column == 1) && m_indexPossible) || ((column == 2) && m_fullTextSearchPossible)) + styleflags |= QStyle::Style_Enabled; + + int x = 0; + int y = 0; + x += 3; + if (align & AlignVCenter) + y = ((height() - boxsize) / 2) + marg; + else + y = (fm.height() + 2 + marg - boxsize) / 2; + + QStyleOption opt(this); + lv->style().drawPrimitive(QStyle::PE_CheckListIndicator, p, + QRect(x, y, boxsize, fm.height() + 2 + marg), cg, styleflags, opt); + + return; + } + QListViewItem::paintCell(p, cg, column, width, align); +} + +int ConfigurationItem::width(const QFontMetrics &fm, const QListView *lv, int c) const +{ + if ((c == 0) || (c == 1) || (c == 2)) + return lv->style().pixelMetric(QStyle::PM_CheckListButtonSize, lv) + 4; + return QListViewItem::width(fm, lv, c); +} + + + + + + + + +//class DocumentationPlugin + +DocumentationPlugin::DocumentationPlugin(KConfig *pluginConfig, QObject *parent, const char *name) + :QObject(parent, name), config(pluginConfig), m_indexCreated(false) +{ +} + +DocumentationPlugin::~DocumentationPlugin() +{ +} + +void DocumentationPlugin::autoSetup() +{ + config->setGroup("General"); + if ( ! config->readBoolEntry("Autosetup", false) ) + { + autoSetupPlugin(); + config->setGroup("General"); + config->writeEntry("Autosetup", true); + config->sync(); + } +} + +void DocumentationPlugin::reload() +{ + clear(); + for (QValueList<DocumentationCatalogItem *>::iterator it = catalogs.begin(); + it != catalogs.end(); ++it) + { + createTOC(*it); + } +} + +void DocumentationPlugin::clear() +{ + for (QValueList<DocumentationCatalogItem *>::iterator it = catalogs.begin(); + it != catalogs.end(); ++it) + { + clearCatalog(*it); + } +} + +void DocumentationPlugin::clearCatalog(DocumentationCatalogItem *item) +{ + //clear named catalog map + for (QMap<QString, DocumentationCatalogItem*>::iterator it = namedCatalogs.begin(); + it != namedCatalogs.end(); ++it) + { + if (it.data() == item) + { + namedCatalogs.remove(it); + break; + } + } + //clear indexes for catalog + QValueList<IndexItemProto *> idx = indexes[item]; + for (QValueList<IndexItemProto *>::iterator it = idx.begin(); it != idx.end(); ++it) + { + delete *it; + } + indexes.remove(item); + + //remove catalog + catalogs.remove(item); +} + +void DocumentationPlugin::createIndex(IndexBox *index) +{ + if (m_indexCreated) + return; + + for (QValueList<DocumentationCatalogItem *>::iterator it = catalogs.begin(); + it != catalogs.end(); ++it) + { + loadIndex(index, *it); + } + m_indexCreated = true; +} + +void DocumentationPlugin::cacheIndex(DocumentationCatalogItem *item) +{ + kdDebug() << "Creating index cache for " << item->text(0) << endl; + + QString cacheName = locateLocal("data", QString("kdevdocumentation/index/cache_") + item->text(0)); + QFile cacheFile(cacheName); + if (!cacheFile.open(IO_WriteOnly)) + return; + + QTextStream str(&cacheFile); + str.setEncoding(QTextStream::Unicode); + str << CACHE_VERSION << endl; + + QValueList<IndexItemProto*> catalogIndexes = indexes[item]; + for (QValueList<IndexItemProto*>::const_iterator it = catalogIndexes.constBegin(); + it != catalogIndexes.constEnd(); ++it) + { + str << (*it)->text() << endl; + str << (*it)->description() << endl; + str << (*it)->url().url() << endl; + } + + cacheFile.close(); +} + +bool DocumentationPlugin::loadCachedIndex(IndexBox *index, DocumentationCatalogItem *item) +{ + QString cacheName = locateLocal("data", QString("kdevdocumentation/index/cache_") + item->cacheVersion() + item->text(0)); + QFile cacheFile(cacheName); + if (!cacheFile.open(IO_ReadOnly)) + return false; + + kdDebug() << "Using cached index for item: " << item->text(0) << endl; + + QTextStream str(&cacheFile); + str.setEncoding(QTextStream::Unicode); + QString cache = str.read(); + QStringList cacheList = QStringList::split("\n", cache, true); + QString ver = cacheList.first(); + if (ver != CACHE_VERSION) + { + kdDebug() << "Wrong cache version: " << ver << endl; + return false; + } + QStringList::const_iterator it = cacheList.begin(); + it++; + QString s[3]; int c = 0; + for (; it != cacheList.end(); ++it) + { + s[c] = *it; + if (c == 2) + { + IndexItemProto *ii = new IndexItemProto(this, item, index, s[0], s[1]); + ii->addURL(KURL(s[2])); + c = 0; + } + else c++; + } + cacheFile.close(); + + return true; +} + +void DocumentationPlugin::addCatalog(DocumentationCatalogItem *item) +{ + catalogs.append(item); + namedCatalogs[item->text(0)] = item; +// indexes[item] = QValueList<IndexItem*>(); +} + +void DocumentationPlugin::addCatalogConfiguration(KListView *configurationView, + const QString &title, const QString &url) +{ + new ConfigurationItem(configurationView, this, title, url, + hasCapability(Index), hasCapability(FullTextSearch)); +} + +void DocumentationPlugin::editCatalogConfiguration(ConfigurationItem *configurationItem, + const QString &title, const QString &url) +{ + configurationItem->setTitle(title); + configurationItem->setURL(url); +} + +void DocumentationPlugin::deleteCatalogConfiguration(const ConfigurationItem *const configurationItem) +{ + deletedConfigurationItems << configurationItem->title(); +} + +void DocumentationPlugin::clearCatalogIndex(DocumentationCatalogItem *item) +{ + //clear indexes for catalog + QValueList<IndexItemProto *> idx = indexes[item]; + for (QValueList<IndexItemProto *>::iterator it = idx.begin(); it != idx.end(); ++it) + { + delete *it; + } + indexes.remove(item); +} + +void DocumentationPlugin::loadIndex(IndexBox *index, DocumentationCatalogItem *item) +{ + if (!indexEnabled(item)) + return; + if (!needRefreshIndex(item) && loadCachedIndex(index, item)) + return; + createIndex(index, item); + cacheIndex(item); +} + +void DocumentationPlugin::init(KListView *contents) +{ + config->setGroup("Locations"); + QMap<QString, QString> entryMap = config->entryMap("Locations"); + + for (QMap<QString, QString>::const_iterator it = entryMap.begin(); + it != entryMap.end(); ++it) + { + if (catalogEnabled(it.key())) + createCatalog(contents, it.key(), config->readPathEntry(it.key())); + } +} + +void DocumentationPlugin::reinit(KListView *contents, IndexBox *index, QStringList restrictions) +{ + config->setGroup("Locations"); + QMap<QString, QString> entryMap = config->entryMap("Locations"); + + //remove deleted in configuration catalogs + for (QStringList::const_iterator it = deletedConfigurationItems.constBegin(); + it != deletedConfigurationItems.constEnd(); ++it) + { + if (namedCatalogs.contains(*it)) + delete namedCatalogs[*it]; + } + deletedConfigurationItems.clear(); + + //update configuration + for (QMap<QString, QString>::const_iterator it = entryMap.begin(); + it != entryMap.end(); ++it) + { + config->setGroup("Locations"); + if (restrictions.contains(it.key()) || (!catalogEnabled(it.key()))) + { + if (namedCatalogs.contains(it.key())) + delete namedCatalogs[it.key()]; + } + else + { + kdDebug() << "updating 1" << endl; + if (!namedCatalogs.contains(it.key())) //create catalog if it does not exist + { + DocumentationCatalogItem * item = createCatalog(contents, it.key(), config->readPathEntry(it.key())); + loadIndex(index, item); + index->setDirty(true); +// index->refill(indexes[item]); + } + else if (!indexEnabled(namedCatalogs[it.key()])) //clear index if it is disabled in configuration + { + kdDebug() << " updating: clearCatalogIndex" << endl; + clearCatalogIndex(namedCatalogs[it.key()]); + } + else if ( (indexEnabled(namedCatalogs[it.key()])) //index is requested in configuration but does not yet exist + && (!indexes.contains(namedCatalogs[it.key()])) ) + { + kdDebug() << " index requested " << endl; + loadIndex(index, namedCatalogs[it.key()]); + index->setDirty(true); + } + m_indexCreated = true; + } + } +} + +void DocumentationPlugin::loadCatalogConfiguration(KListView *configurationView) +{ + config->setGroup("Locations"); + QMap<QString, QString> entryMap = config->entryMap("Locations"); + + for (QMap<QString, QString>::const_iterator it = entryMap.begin(); + it != entryMap.end(); ++it) + { + if (namedCatalogs.contains(it.key()) + && namedCatalogs[it.key()]->isProjectDocumentationItem()) + continue; + + config->setGroup("Locations"); + ConfigurationItem *item = new ConfigurationItem(configurationView, this, it.key(), + config->readPathEntry(it.key()), + hasCapability(Index), hasCapability(FullTextSearch)); + config->setGroup("TOC Settings"); + item->setContents(config->readBoolEntry(item->title(), true)); + config->setGroup("Index Settings"); + item->setIndex(config->readBoolEntry(item->title(), false)); + config->setGroup("Search Settings"); + item->setFullTextSearch(config->readBoolEntry(item->title(), false)); + } +} + +void DocumentationPlugin::saveCatalogConfiguration(KListView *configurationView) +{ + config->setGroup("Locations"); + + for (QStringList::const_iterator it = deletedConfigurationItems.constBegin(); + it != deletedConfigurationItems.constEnd(); ++it) + { + config->deleteEntry(*it); + } + + QListViewItemIterator it(configurationView); + while (it.current()) + { + ConfigurationItem *confItem = dynamic_cast<ConfigurationItem*>(it.current()); + if ( confItem->docPlugin() != this ) + { + ++it; + continue; + } + + config->setGroup("Locations"); + if (confItem->isChanged()) + config->deleteEntry(confItem->origTitle()); + config->writePathEntry(confItem->title(), confItem->url()); + + config->setGroup("TOC Settings"); + if (confItem->isChanged()) + config->deleteEntry(confItem->origTitle()); + config->writeEntry(confItem->title(), confItem->contents()); + + config->setGroup("Index Settings"); + if (confItem->isChanged()) + config->deleteEntry(confItem->origTitle()); + config->writeEntry(confItem->title(), confItem->index()); + + config->setGroup("Search Settings"); + if (confItem->isChanged()) + config->deleteEntry(confItem->origTitle()); + config->writeEntry(confItem->title(), confItem->fullTextSearch()); + + ++it; + } + config->sync(); +} + +void DocumentationPlugin::setIndexEnabled( DocumentationCatalogItem * item, bool e ) +{ + QString group = config->group(); + config->setGroup("Index Settings"); + config->writeEntry(item->text(0), e); + config->setGroup(group); +} + +bool DocumentationPlugin::indexEnabled( DocumentationCatalogItem * item ) const +{ + QString group = config->group(); + config->setGroup("Index Settings"); + bool b = config->readBoolEntry(item->text(0), false); + config->setGroup(group); + return b; +} + +bool DocumentationPlugin::catalogEnabled(const QString &name) const +{ + QString group = config->group(); + config->setGroup("TOC Settings"); + bool b = config->readBoolEntry(name, true); + config->setGroup(group); + return b; +} + +void DocumentationPlugin::setCatalogEnabled(const QString &name, bool e) +{ + QString group = config->group(); + config->setGroup("TOC Settings"); + config->writeEntry(name, e); + config->setGroup(group); +} + + + + +//class IndexBox + +IndexBox::IndexBox(QWidget *parent, const char *name) + :KListBox(parent, name), m_dirty(false) +{ +} + +void IndexBox::addIndexItem(IndexItemProto *item) +{ + items[item->text()].append(item); +} + +void IndexBox::removeIndexItem(IndexItemProto *item) +{ + QString text = item->text(); + items[text].remove(item); + if (items[text].count() == 0) + { + items.remove(text); + QListBoxItem *item = findItem(text, Qt::CaseSensitive | Qt::ExactMatch); + if (item) + delete item; + } +} + +void IndexBox::fill() +{ + for (QMap<QString, QValueList<IndexItemProto*> >::const_iterator it = items.begin(); + it != items.end(); ++it) + { + new IndexItem(this, it.key()); + } +} + +void IndexBox::setDirty(bool dirty) +{ + m_dirty = dirty; +} + +void IndexBox::refill() +{ + if (m_dirty) + { + clear(); + fill(); + setDirty(false); + } +} + + +ProjectDocumentationPlugin::ProjectDocumentationPlugin(DocumentationPlugin *docPlugin, DocumentationPlugin::ProjectDocType type) + :QObject(0, 0), m_docPlugin(docPlugin), m_catalog(0), m_type(type), m_contents(0), m_index(0) +{ + kdDebug() << "ProjectDocumentationPlugin::ProjectDocumentationPlugin for type " << type << endl; + + m_watch = new KDirWatch(this); + connect(m_watch, SIGNAL(dirty(const QString&)), this, SLOT(reinit())); + m_watch->startScan(); +} + +ProjectDocumentationPlugin::~ProjectDocumentationPlugin() +{ + deinit(); +} + +void ProjectDocumentationPlugin::init(KListView *contents, IndexBox *index, const QString &url) +{ + m_contents = contents; + m_index = index; + m_url = url; + + if (m_catalog) + deinit(); + m_catalog = m_docPlugin->createCatalog(contents, + m_type == DocumentationPlugin::APIDocs ? i18n("Project API Documentation") + : i18n("Project User Manual"), url); + if (m_catalog) + { + m_catalog->setProjectDocumentationItem(true); + m_watch->addFile(url); + } +} + +void ProjectDocumentationPlugin::reinit() +{ + deinit(); + if (m_contents != 0 && m_index != 0 && m_url != 0) + init(m_contents, m_index, m_url); +} + +void ProjectDocumentationPlugin::deinit() +{ + m_watch->removeFile(m_url); + delete m_catalog; + m_catalog = 0; +} + +QString ProjectDocumentationPlugin::pluginName() const +{ + return m_docPlugin->pluginName(); +} + +QString ProjectDocumentationPlugin::catalogURL() const +{ + return m_url; +} + +#include "kdevdocumentationplugin.moc" diff --git a/parts/documentation/interfaces/kdevdocumentationplugin.h b/parts/documentation/interfaces/kdevdocumentationplugin.h new file mode 100644 index 00000000..5d100ab5 --- /dev/null +++ b/parts/documentation/interfaces/kdevdocumentationplugin.h @@ -0,0 +1,421 @@ +/* This file is part of the KDE project + Copyright (C) 2004 by Alexander Dymo <cloudtemple@mksat.net> + + 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., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ +#ifndef KDEV_DOC_PLUGIN_H +#define KDEV_DOC_PLUGIN_H + +#include <qmap.h> +#include <qvaluelist.h> +#include <qpair.h> + +#include <klistbox.h> +#include <klistview.h> +#include <kurl.h> +#include <kfile.h> + +#define CACHE_VERSION "3" + +/**Documentation list item. +Stores the type of a documentation it represents and an URL.*/ +class DocumentationItem: public KListViewItem +{ +public: + /**Type of documentation which is represented by this item.*/ + enum Type { + Collection /**<Collection - a collection of catalogs, folder with catalogs.*/, + Catalog /**<Catalog - a term which defines a document or a group of documents.*/, + Book /**<Book - a document with nested documents.*/, + Document /**<Document.*/ + }; + + DocumentationItem(Type type, KListView *parent, const QString &name); + DocumentationItem(Type type, KListView *parent, KListViewItem *after, const QString &name); + DocumentationItem(Type type, KListViewItem *parent, const QString &name); + DocumentationItem(Type type, KListViewItem *parent, KListViewItem *after, const QString &name); + + virtual void setURL(const KURL &url) { m_url = url; } + virtual KURL url() const { return m_url; } + + Type type() const { return m_type; } + + void setType(Type t) { + if(t != m_type) { + m_type = t; + init(); + } + } +private: + void init(); + + KURL m_url; + Type m_type; +}; + +class DocumentationPlugin; + +/**Documentation catalog list item.*/ +class DocumentationCatalogItem: public DocumentationItem +{ +public: + DocumentationCatalogItem(DocumentationPlugin* plugin, KListView *parent, const QString &name); + DocumentationCatalogItem(DocumentationPlugin* plugin, DocumentationItem *parent, const QString &name); + virtual ~DocumentationCatalogItem(); + + DocumentationPlugin* plugin() const { return m_plugin; } + + virtual void setOpen(bool o); + void load(); + + virtual bool isProjectDocumentationItem() const { return m_isProjectDocumentationItem; } + virtual void setProjectDocumentationItem(bool b) { m_isProjectDocumentationItem = b; } + + virtual QString cacheVersion() const { return ""; } /// should return a short string that identifies the version of the catalog + +protected: + virtual void activate(); + +private: + DocumentationPlugin* m_plugin; + bool isLoaded; + bool isActivated; + bool m_isProjectDocumentationItem; +}; + +class IndexBox; + +/**Prototype of index item. +Prototypes represent an index are used to build index items after index generation.*/ +class IndexItemProto +{ +public: + IndexItemProto(DocumentationPlugin *plugin, DocumentationCatalogItem *catalog, IndexBox *listbox, + const QString &text, const QString &description); + ~IndexItemProto(); + + void addURL(const KURL &url) { m_url = url; } + KURL url() const { return m_url; } + QString text() const { return m_text; } + QString description() const { return m_description; } + +private: + KURL m_url; + IndexBox *m_listbox; + QString m_text; + QString m_description; +}; + +/**Documentation index item.*/ +class IndexItem: public QListBoxText { +public: + typedef QPair<QString, KURL> URL; + typedef QValueList<URL> List; + + IndexItem(IndexBox *listbox, const QString &text); + + List urls() const; + +private: + IndexBox *m_listbox; +}; + +/**Documentation index view.*/ +class IndexBox: public KListBox{ +public: + IndexBox(QWidget *parent = 0, const char *name = 0); + + virtual void addIndexItem(IndexItemProto *item); + virtual void removeIndexItem(IndexItemProto *item); + virtual void fill(); + virtual void refill(); + virtual void setDirty(bool dirty); +// virtual void refill(QValueList<IndexItemProto*> &items); + +private: + QMap<QString, QValueList<IndexItemProto*> > items; + friend class IndexItem; + + bool m_dirty; +}; + +class QPainter; +class QColorGroup; +class QFontMetrics; +class DocumentationPlugin; + +/**Documentation configuration item.*/ +class ConfigurationItem: public QCheckListItem +{ +public: + ConfigurationItem(QListView *parent, DocumentationPlugin * plugin, const QString &title, const QString &url, + bool indexPossible, bool fullTextSearchPossible); + + virtual QString title() const { return m_title; } + virtual void setTitle(const QString title) { setText(3, m_title = title); } + virtual QString url() const { return m_url; } + virtual void setURL(const QString url) { setText(4, m_url = url); } + + virtual bool isChanged() const { return m_title == m_origTitle; } + virtual QString origTitle() const {return m_origTitle; } + + virtual void paintCell(QPainter *p, const QColorGroup &cg, int column, int width, int align); + virtual int width(const QFontMetrics &fm, const QListView *lv, int c) const; + + bool contents() const { return m_contents; } + void setContents(bool contents) { m_contents = contents; } + bool index() const { return m_index; } + void setIndex(bool index) { m_index = index; } + bool fullTextSearch() const { return m_fullTextSearch; } + void setFullTextSearch(bool fullTextSearch) { m_fullTextSearch = fullTextSearch; } + + bool indexPossible() const { return m_indexPossible; } + bool fullTextSearchPossible() const { return m_fullTextSearchPossible; } + + DocumentationPlugin * docPlugin() { return m_docPlugin; } + +private: + QString m_title; + QString m_url; + QString m_origTitle; + + bool m_contents; + bool m_index; + bool m_fullTextSearch; + + bool m_indexPossible; + bool m_fullTextSearchPossible; + + DocumentationPlugin * m_docPlugin; +}; + + +class ProjectDocumentationPlugin; + +/** +@short Documentation Plugin Interface + +All KDevelop documentation plugins must implement this interface. +Documentation plugin handles certain documentation type. It provides +methods to load documentation catalogs and indexes for a documentation +of that type. It also has methods to configure catalogs and provides +a list of URL's for the full text search tool. +*/ +class DocumentationPlugin: public QObject +{ + Q_OBJECT +public: + /**Capability of documentation plugin.*/ + enum Capability { Index=1 /**<index can be built for catalogs*/, + FullTextSearch=2 /**<full text search is possible in catalog locations*/, + CustomDocumentationTitles=4 /**<user can specify titles for documentation catalogs*/, + ProjectDocumentation=8 /**<plugin can handle project API documentation*/, + ProjectUserManual=16 /**<plugin can handle project user manual*/ }; + /**Possible project documentation types.*/ + enum ProjectDocType { APIDocs, UserManual }; + + /**Constructor. Should initialize capabilities of the plugin by using setCapabilities + protected method. For example, + @code + setCapabilities(Index | FullTextSearch); + @endcode + */ + DocumentationPlugin(KConfig *pluginConfig, QObject *parent =0, const char *name =0); + virtual ~DocumentationPlugin(); + + /**Returns the i18n name of the plugin.*/ + virtual QString pluginName() const = 0; + + /**Creates documentation catalog with given title and url.*/ + virtual DocumentationCatalogItem *createCatalog(KListView *contents, const QString &title, const QString &url) = 0; + + /**Initialize a list of catalogs. + @param contents the listview to fill with catalogs + */ + virtual void init(KListView *contents); + /**Reloads a list of catalogs. This method should add missing catalogs to the view, + update index for added catalogs and also delete restricted catalogs. + @param contents the listview to fill with catalogs + @param index the listbox with index to update + @param restrictions the list of catalogs names to remove + */ + virtual void reinit(KListView *contents, IndexBox *index, QStringList restrictions); + /**Initializes plugin configuration. Documentation plugins should be able to + initialize the default configuration on startup without any user interaction. + Call this in the constructor of your plugin.*/ + virtual void autoSetup(); + /**Plugin specific automatic setup code. This method is called by @ref autoSetup.*/ + virtual void autoSetupPlugin() = 0; + + /**Indicates if a catalog with specified name is enabled. Documentation plugin + should check this and do not load catalogs disabled in configuration. + All catalogs are enabled by default.*/ + virtual bool catalogEnabled(const QString &name) const; + /**Enables or disables documentation catalog.*/ + virtual void setCatalogEnabled(const QString &name, bool e); + + /**Indicates if an index of given catalog should be rebuilt. This method + is used by index caching algorythm to make a descision to rebuild index + or to load it from cache.*/ + virtual bool needRefreshIndex(DocumentationCatalogItem *item) = 0; + /**Indicates if an index is enabled for given catalog. If documentation plugin + has Index capability, indices for it's catalogs can be enabled/disabled + in configuration dialog.*/ + virtual bool indexEnabled(DocumentationCatalogItem *item) const; + /**Enables or disables index for documentation catalog.*/ + virtual void setIndexEnabled(DocumentationCatalogItem *item, bool e); + /**Builds index for given catalog. This method should fill index with + IndexItem objects. + @param index the listbox which contains index items + @param item the catalog item that holds an index being built + */ + virtual void createIndex(IndexBox *index, DocumentationCatalogItem *item) = 0; + + /**Creates a table of contents for given catalog. Documentation part uses + lazy loading of toc's to reduce startup time. This means that createTOC + will be called on expand event of catalog item.*/ + virtual void createTOC(DocumentationCatalogItem *item) = 0; + /**Sets the URL to the catalog. This method will be called each time user + clicks the documentation item. If it is too much overhead to determine the + documentation catalog url in @ref createCatalog method then you can set it here.*/ + virtual void setCatalogURL(DocumentationCatalogItem *item) = 0; + virtual QStringList fullTextSearchLocations() = 0; + + /**Loads catalog configuration and fills configurationView with ConfigurationItem objects.*/ + virtual void loadCatalogConfiguration(KListView *configurationView); + /**Saves catalog configuration basing on configurationView and + deletedConfigurationItems contents. If you use KConfig to store configuration, + it is important that you call KConfig::sync() method after saving.*/ + virtual void saveCatalogConfiguration(KListView *configurationView); + /**Adds new catalog to a configuration.*/ + virtual void addCatalogConfiguration(KListView *configurationView, + const QString &title, const QString &url); + /**Edits catalog configuration.*/ + virtual void editCatalogConfiguration(ConfigurationItem *configurationItem, + const QString &title, const QString &url); + /**Removes catalog from configuration. configurationItem should not be removed here.*/ + virtual void deleteCatalogConfiguration(const ConfigurationItem *const configurationItem); + + /**Returns a mode and a filter for catalog locator dialogs.*/ + virtual QPair<KFile::Mode, QString> catalogLocatorProps() = 0; + /**Returns a title of catalog defined by an url parameter.*/ + virtual QString catalogTitle(const QString &url) = 0; + + /**Reloads documentation catalogs and indices.*/ + virtual void reload(); + /**Clears documentation catalogs and indices.*/ + virtual void clear(); + + /**Checks if documentation plugin has given capability.*/ + bool hasCapability(Capability cap) const { return m_capabilities & cap; } + + /**Sets dirty flag for all indices. Index caching algorythm will update + the cache next time @ref createIndex is called.*/ + void setDirtyIndex(bool dirty) { m_indexCreated = dirty; } + + /**Caches index for documentation catalog. Reimplement this only if custom + caching algorythm is used (do not forget to reimplement also @ref loadCachedIndex + and @ref createIndex).*/ + virtual void cacheIndex(DocumentationCatalogItem *item); + /**Loads index from the cache. Reimplement this only if custom + caching algorythm is used (do not forget to reimplement also @ref cacheIndex + and @ref createIndex).*/ + virtual bool loadCachedIndex(IndexBox *index, DocumentationCatalogItem *item); + + /**Returns associated project documentation plugin. Default implementation returns zero. + Reimplement this if the documentation plugin can also handle project documentation.*/ + virtual ProjectDocumentationPlugin *projectDocumentationPlugin(ProjectDocType /* type */) { return 0; } + +public slots: + /**Creates index and fills index listbox. Reimplement this only if custom + caching algorythm is used (do not forget to reimplement also @ref cacheIndex + and @ref loadCachedIndex).*/ + virtual void createIndex(IndexBox *index); + +protected: + /**A list of loaded documentation catalogs.*/ + QValueList<DocumentationCatalogItem*> catalogs; + /**A map of names of loaded documentation catalogs.*/ + QMap<QString, DocumentationCatalogItem*> namedCatalogs; + /**A map of indices of loaded documentation catalogs.*/ + QMap<DocumentationCatalogItem*, QValueList<IndexItemProto*> > indexes; + + /**Sets capabilities of documentation plugin.*/ + void setCapabilities(int caps) { m_capabilities = caps; } + /**Clears index of given catalog.*/ + virtual void clearCatalogIndex(DocumentationCatalogItem *item); + /**Loads index from cache or creates and caches it if does not exist.*/ + void loadIndex(IndexBox *index, DocumentationCatalogItem *item); + + /**Stores items deleted from configuration. @ref saveCatalogConfiguration + uses this to remove entries from configuration file.*/ + QStringList deletedConfigurationItems; + + /**Configuration object used by a plugin.*/ + KConfig *config; + +private: + /**Adds catalog item to catalogs, namedCatalogs and indexes lists and maps.*/ + virtual void addCatalog(DocumentationCatalogItem *item); + /**Removes catalog item from catalogs, namedCatalogs and indexes lists and maps.*/ + virtual void clearCatalog(DocumentationCatalogItem *item); + + int m_capabilities; + bool m_indexCreated; + + +friend class IndexItemProto; +friend class DocumentationCatalogItem; +}; + + +/** +@short Project documentation plugin + +Represents functionality to display project documentation catalog and index in documentation browser. +*/ +class ProjectDocumentationPlugin: public QObject { + Q_OBJECT +public: + ProjectDocumentationPlugin(DocumentationPlugin *docPlugin, DocumentationPlugin::ProjectDocType type); + virtual ~ProjectDocumentationPlugin(); + + /**Initializes project documentation plugin - creates documentation catalog.*/ + virtual void init(KListView *contents, IndexBox *index, const QString &url); + /**Deinitializes project documentation plugin - removes documentation catalog.*/ + virtual void deinit(); + + QString pluginName() const; + QString catalogURL() const; + +public slots: + /**Performs reinitialization if project documentation has changed (after building api documentation).*/ + virtual void reinit(); + +protected: + DocumentationPlugin *m_docPlugin; + DocumentationCatalogItem *m_catalog; + +private: + DocumentationPlugin::ProjectDocType m_type; + + class KDirWatch *m_watch; + class KListView *m_contents; + class IndexBox *m_index; + QString m_url; +}; + +#endif diff --git a/parts/documentation/interfaces/kdevelopdocumentationplugins.desktop b/parts/documentation/interfaces/kdevelopdocumentationplugins.desktop new file mode 100644 index 00000000..08fed218 --- /dev/null +++ b/parts/documentation/interfaces/kdevelopdocumentationplugins.desktop @@ -0,0 +1,36 @@ +[Desktop Entry] +Type=ServiceType +X-KDE-ServiceType=KDevelop/DocumentationPlugins +X-KDE-Derived=KDevelop/Plugin +Name=KDevelop Documentation Plugin Interface +Name[ca]=Interfície de connectors de documentació de KDevelop +Name[da]=KDevelop grænseflade for dokumentations-plugin +Name[de]=Schnittstelle für Dokumentationsmodul (KDevelop) +Name[el]=Διασύνδεση πρόσθετου τεκμηρίωσης KDevelop +Name[es]=Interfaz de complemento de documentación de KDevelop +Name[et]=KDevelopi dokumentatsiooniplugina liides +Name[eu]=KDevelop-en dokumentazio plugin interfazea +Name[fa]=واسط وصلۀ مستندات KDevelop +Name[fr]=Interface du module externe de documentation de KDevelop +Name[gl]=Interface da extensión de documentación de KDevelop +Name[hu]=KDevelop dokumentációmodul-felület +Name[it]=Interfaccia a plugin della documentazione di KDevelop +Name[ja]=KDevelop ドキュメンテーションプラグイン インターフェース +Name[ms]=Antaramuka Plugin Dokumentasi KDevelop +Name[nds]=KDevelop-Koppelsteed för't Dokmentatschoon-Moduul +Name[ne]=केडीई विकास मिसिलीकरण प्लगइन इन्टरफेस +Name[nl]=KDevelop Documentatie Plugin Interface +Name[pl]=Interfejs do wtyczki dokumentacji dla KDevelop +Name[pt]=Interface de 'Plugin' de Documentação do KDevelop +Name[pt_BR]=Interface de Plug-in de Documentação do KDevelop +Name[ru]=Интерфейс для модулей документации KDevelop +Name[sk]=KDevelop rozhranie pre dokumentačný modul +Name[sl]=Vmesnik vstavka dokumentacije v KDevelopu +Name[sr]=Интерфејс KDevelop-овог прикључка за документацију +Name[sr@Latn]=Interfejs KDevelop-ovog priključka za dokumentaciju +Name[sv]=KDevelop insticksgränssnitt för dokumentation +Name[ta]=Kமுன்னேற்று தொகுப்பான் தேர்வுகள் உரை இடைமுகம் உள்ளீடு +Name[tg]=Интерфейс барои модулҳои ҳуҷҷатноки KDevelop +Name[tr]=KDevelop Belgelendirme Eklentisi Arayüzü +Name[zh_CN]=KDevelop 文档插件接口 +Name[zh_TW]=KDevelop 文件外掛程式介面 |