Commit 2dc7a6a1 authored by Leandro Melo's avatar Leandro Melo
Browse files

More functionality for the generic highlighter options. Other small changes.

parent 68cec6a7
......@@ -57,7 +57,7 @@ public:
Highlighter(const QSharedPointer<Context> &defaultContext, QTextDocument *parent = 0);
virtual ~Highlighter();
void configureFormats(const FontSettings & fs);
void configureFormats(const FontSettings &fs);
protected:
virtual void highlightBlock(const QString &text);
......
......@@ -33,9 +33,10 @@
#include <QtCore/QSettings>
#include <QtCore/QString>
#include <QtCore/QStringList>
#include <QtCore/QLatin1String>
#ifdef Q_OS_LINUX
#ifdef Q_OS_UNIX
#include <QtCore/QDir>
#include <QtCore/QProcess>
#endif
......@@ -43,18 +44,28 @@
namespace TextEditor {
namespace Internal {
void applyDefaults(HighlighterSettings *settings)
QString findDefinitionsLocation()
{
settings->m_definitionFilesPath.clear();
QString definitionsLocation;
#ifdef Q_OS_LINUX
#ifdef Q_OS_UNIX
static const QLatin1String kateSyntax("/share/apps/katepart/syntax");
// Wild guess.
QDir dir(QLatin1String("/usr") + kateSyntax);
if (dir.exists()) {
settings->m_definitionFilesPath = dir.path();
} else {
// Some wild guesses.
QDir dir;
QStringList paths;
paths << QLatin1String("/usr") + kateSyntax
<< QLatin1String("/usr/local") + kateSyntax
<< QLatin1String("/opt") + kateSyntax;
foreach (const QString &path, paths) {
dir.setPath(path);
if (dir.exists()) {
definitionsLocation = path;
break;
}
}
if (definitionsLocation.isEmpty()) {
// Try kde-config.
QProcess process;
process.start(QLatin1String("kde-config"), QStringList(QLatin1String("--prefix")));
......@@ -64,14 +75,16 @@ void applyDefaults(HighlighterSettings *settings)
output.remove(QLatin1Char('\n'));
dir.setPath(output + kateSyntax);
if (dir.exists())
settings->m_definitionFilesPath = dir.path();
definitionsLocation = dir.path();
}
}
#endif
if (settings->m_definitionFilesPath.isEmpty())
settings->m_definitionFilesPath = Core::ICore::instance()->resourcePath() +
QLatin1String("/generic-highlighter");
if (definitionsLocation.isEmpty())
definitionsLocation = Core::ICore::instance()->resourcePath() +
QLatin1String("/generic-highlighter");
return definitionsLocation;
}
} // namespace Internal
......@@ -80,6 +93,7 @@ void applyDefaults(HighlighterSettings *settings)
namespace {
static const QLatin1String kDefinitionFilesPath("DefinitionFilesPath");
static const QLatin1String kAlertWhenDefinitionIsNotFound("AlertWhenDefinitionsIsNotFound");
static const QLatin1String kGroupPostfix("HighlighterSettings");
QString groupSpecifier(const QString &postFix, const QString &category)
......@@ -94,7 +108,7 @@ QString groupSpecifier(const QString &postFix, const QString &category)
using namespace TextEditor;
using namespace Internal;
HighlighterSettings::HighlighterSettings()
HighlighterSettings::HighlighterSettings() : m_alertWhenNoDefinition(true)
{}
void HighlighterSettings::toSettings(const QString &category, QSettings *s) const
......@@ -102,6 +116,7 @@ void HighlighterSettings::toSettings(const QString &category, QSettings *s) cons
const QString &group = groupSpecifier(kGroupPostfix, category);
s->beginGroup(group);
s->setValue(kDefinitionFilesPath, m_definitionFilesPath);
s->setValue(kAlertWhenDefinitionIsNotFound, m_alertWhenNoDefinition);
s->endGroup();
}
......@@ -109,16 +124,16 @@ void HighlighterSettings::fromSettings(const QString &category, QSettings *s)
{
const QString &group = groupSpecifier(kGroupPostfix, category);
s->beginGroup(group);
if (!s->contains(kDefinitionFilesPath))
applyDefaults(this);
m_definitionFilesPath = findDefinitionsLocation();
else
m_definitionFilesPath = s->value(kDefinitionFilesPath, QString()).toString();
m_alertWhenNoDefinition = s->value(kAlertWhenDefinitionIsNotFound, true).toBool();
s->endGroup();
}
bool HighlighterSettings::equals(const HighlighterSettings &highlighterSettings) const
{
return m_definitionFilesPath == highlighterSettings.m_definitionFilesPath;
return m_definitionFilesPath == highlighterSettings.m_definitionFilesPath &&
m_alertWhenNoDefinition == highlighterSettings.m_alertWhenNoDefinition;
}
......@@ -47,6 +47,7 @@ struct HighlighterSettings
bool equals(const HighlighterSettings &highlighterSettings) const;
bool m_alertWhenNoDefinition;
QString m_definitionFilesPath;
};
......@@ -57,7 +58,7 @@ inline bool operator!=(const HighlighterSettings &a, const HighlighterSettings &
{ return !a.equals(b); }
namespace Internal {
void applyDefaults(HighlighterSettings *settings);
QString findDefinitionsLocation();
}
} // namespace TextEditor
......
......@@ -33,6 +33,7 @@
#include "ui_highlightersettingspage.h"
#include <coreplugin/icore.h>
#include <coreplugin/coreconstants.h>
using namespace TextEditor;
using namespace Internal;
......@@ -89,15 +90,19 @@ QWidget *HighlighterSettingsPage::createPage(QWidget *parent)
{
QWidget *w = new QWidget(parent);
m_d->m_page.setupUi(w);
m_d->m_page.definitionFilesPath->setExpectedKind(Utils::PathChooser::Directory);
settingsToUI();
if (m_d->m_searchKeywords.isEmpty()) {
QTextStream(&m_d->m_searchKeywords) << m_d->m_page.definitionFilesGroupBox->title()
<< m_d->m_page.locationLabel->text();
<< m_d->m_page.locationLabel->text()
<< m_d->m_page.alertWhenNoDefinition->text();
}
connect(m_d->m_page.resetButton, SIGNAL(clicked()), this, SLOT(reset()));
connect(m_d->m_page.resetButton, SIGNAL(clicked()), this, SLOT(resetDefinitionsLocation()));
connect(m_d->m_page.downloadNoteLabel, SIGNAL(linkActivated(QString)),
Manager::instance(), SLOT(openDefinitionsUrl(QString)));
return w;
}
......@@ -125,6 +130,7 @@ void HighlighterSettingsPage::settingsFromUI()
locationChanged = true;
m_d->m_settings.m_definitionFilesPath = m_d->m_page.definitionFilesPath->path();
m_d->m_settings.m_alertWhenNoDefinition = m_d->m_page.alertWhenNoDefinition->isChecked();
if (QSettings *s = Core::ICore::instance()->settings())
m_d->m_settings.toSettings(m_d->m_settingsPrefix, s);
......@@ -132,25 +138,22 @@ void HighlighterSettingsPage::settingsFromUI()
emit definitionsLocationChanged();
}
void HighlighterSettingsPage::settingsToUI(const HighlighterSettings *settings)
void HighlighterSettingsPage::settingsToUI()
{
if (settings) {
m_d->m_page.definitionFilesPath->setPath(settings->m_definitionFilesPath);
} else {
m_d->m_page.definitionFilesPath->setPath(m_d->m_settings.m_definitionFilesPath);
}
m_d->m_page.definitionFilesPath->setPath(m_d->m_settings.m_definitionFilesPath);
m_d->m_page.alertWhenNoDefinition->setChecked(m_d->m_settings.m_alertWhenNoDefinition);
}
void HighlighterSettingsPage::reset()
void HighlighterSettingsPage::resetDefinitionsLocation()
{
HighlighterSettings defaultSettings;
applyDefaults(&defaultSettings);
settingsToUI(&defaultSettings);
m_d->m_page.definitionFilesPath->setPath(findDefinitionsLocation());
}
bool HighlighterSettingsPage::settingsChanged() const
{
if (m_d->m_settings.m_definitionFilesPath != m_d->m_page.definitionFilesPath->path())
return true;
if (m_d->m_settings.m_alertWhenNoDefinition != m_d->m_page.alertWhenNoDefinition->isChecked())
return true;
return false;
}
......@@ -57,11 +57,11 @@ signals:
void definitionsLocationChanged();
private slots:
void reset();
void resetDefinitionsLocation();
private:
void settingsFromUI();
void settingsToUI(const HighlighterSettings *settings = 0);
void settingsToUI();
bool settingsChanged() const;
......
......@@ -6,34 +6,56 @@
<rect>
<x>0</x>
<y>0</y>
<width>453</width>
<width>521</width>
<height>230</height>
</rect>
</property>
<property name="windowTitle">
<string>Form</string>
</property>
<layout class="QVBoxLayout" name="verticalLayout">
<layout class="QVBoxLayout" name="verticalLayout_2">
<item>
<widget class="QCheckBox" name="alertWhenNoDefinition">
<property name="text">
<string>Alert when a highlight definition is not found.</string>
</property>
</widget>
</item>
<item>
<widget class="QGroupBox" name="definitionFilesGroupBox">
<property name="title">
<string>Syntax Definition Files</string>
<string>Syntax Highlight Definition Files</string>
</property>
<layout class="QHBoxLayout" name="horizontalLayout_2">
<layout class="QVBoxLayout" name="verticalLayout">
<item>
<widget class="QLabel" name="locationLabel">
<widget class="QLabel" name="downloadNoteLabel">
<property name="text">
<string>Location:</string>
<string>&lt;!DOCTYPE HTML PUBLIC &quot;-//W3C//DTD HTML 4.0//EN&quot; &quot;http://www.w3.org/TR/REC-html40/strict.dtd&quot;&gt;
&lt;html&gt;&lt;head&gt;&lt;meta name=&quot;qrichtext&quot; content=&quot;1&quot; /&gt;&lt;style type=&quot;text/css&quot;&gt;
p, li { white-space: pre-wrap; }
&lt;/style&gt;&lt;/head&gt;&lt;body style=&quot; font-family:'MS Shell Dlg 2'; font-size:8.25pt; font-weight:400; font-style:normal;&quot;&gt;
&lt;p style=&quot; margin-top:0px; margin-bottom:0px; margin-left:0px; margin-right:0px; -qt-block-indent:0; text-indent:0px;&quot;&gt;&lt;span style=&quot; font-size:8pt;&quot;&gt;Files can be downloaded from the &lt;/span&gt;&lt;a href=&quot;http://kate-editor.org/downloads/syntax_highlighting&quot;&gt;&lt;span style=&quot; font-size:8pt; text-decoration: underline; color:#0000ff;&quot;&gt;Kate Text Editor&lt;/span&gt;&lt;/a&gt;&lt;span style=&quot; font-size:8pt;&quot;&gt; website and stored at the location below.&lt;/span&gt;&lt;/p&gt;&lt;/body&gt;&lt;/html&gt;</string>
</property>
<property name="textFormat">
<enum>Qt::RichText</enum>
</property>
<property name="textInteractionFlags">
<set>Qt::TextBrowserInteraction</set>
</property>
</widget>
</item>
<item>
<layout class="QHBoxLayout" name="horizontalLayout">
<item>
<widget class="Utils::PathChooser" name="definitionFilesPath" native="true">
<zorder>locationLabel</zorder>
<widget class="QLabel" name="locationLabel">
<property name="text">
<string>Location:</string>
</property>
</widget>
</item>
<item>
<widget class="Utils::PathChooser" name="definitionFilesPath" native="true"/>
</item>
<item>
<widget class="QToolButton" name="resetButton">
<property name="toolTip">
......@@ -51,11 +73,6 @@
</layout>
</item>
</layout>
<zorder>locationLabel</zorder>
<zorder>definitionFilesPath</zorder>
<zorder>resetButton</zorder>
<zorder>resetButton</zorder>
<zorder>resetButton</zorder>
</widget>
</item>
<item>
......
......@@ -35,6 +35,7 @@
#include "texteditorsettings.h"
#include "plaintexteditorfactory.h"
#include "highlightersettings.h"
#include "texteditorconstants.h"
#include <coreplugin/icore.h>
#include <utils/qtcassert.h>
......@@ -53,6 +54,8 @@
#include <QtCore/QRegExp>
#include <QtCore/QFuture>
#include <QtCore/QtConcurrentRun>
#include <QtCore/QUrl>
#include <QtGui/QDesktopServices>
#include <QtXml/QXmlSimpleReader>
#include <QtXml/QXmlInputSource>
#include <QtXml/QXmlStreamReader>
......@@ -65,8 +68,7 @@ Manager::Manager()
{}
Manager::~Manager()
{
}
{}
Manager *Manager::instance()
{
......@@ -79,9 +81,7 @@ QString Manager::definitionIdByName(const QString &name) const
QString Manager::definitionIdByMimeType(const QString &mimeType) const
{
if (m_idByMimeType.count(mimeType) <= 1) {
return m_idByMimeType.value(mimeType);
} else {
if (m_idByMimeType.count(mimeType) > 1) {
QStringList candidateIds;
QMultiHash<QString, QString>::const_iterator it = m_idByMimeType.find(mimeType);
QMultiHash<QString, QString>::const_iterator endIt = m_idByMimeType.end();
......@@ -91,6 +91,7 @@ QString Manager::definitionIdByMimeType(const QString &mimeType) const
qSort(candidateIds.begin(), candidateIds.end(), m_priorityComp);
return candidateIds.last();
}
return m_idByMimeType.value(mimeType);
}
QString Manager::definitionIdByAnyMimeType(const QStringList &mimeTypes) const
......@@ -192,9 +193,9 @@ void Manager::registerMimeType(int index) const
}
void Manager::parseDefinitionMetadata(const QFileInfo &fileInfo,
QString *comment,
QStringList *mimeTypes,
QStringList *patterns)
QString *comment,
QStringList *mimeTypes,
QStringList *patterns)
{
static const QLatin1Char kSemiColon(';');
static const QLatin1Char kSlash('/');
......@@ -257,3 +258,14 @@ void Manager::clear()
m_idByMimeType.clear();
m_definitions.clear();
}
void Manager::showGenericHighlighterOptions() const
{
Core::ICore::instance()->showOptionsDialog(Constants::TEXT_EDITOR_SETTINGS_CATEGORY,
Constants::TEXT_EDITOR_HIGHLIGHTER_SETTINGS);
}
void Manager::openDefinitionsUrl(const QString &location) const
{
QDesktopServices::openUrl(QUrl(location));
}
......@@ -66,6 +66,8 @@ public:
public slots:
void registerMimeTypes();
void showGenericHighlighterOptions() const;
void openDefinitionsUrl(const QString &location) const;
private slots:
void registerMimeType(int index) const;
......
......@@ -47,6 +47,8 @@
#include <QtCore/QSharedPointer>
#include <QtCore/QFileInfo>
#include <QDebug>
using namespace TextEditor;
using namespace TextEditor::Internal;
......@@ -59,7 +61,8 @@ PlainTextEditorEditable::PlainTextEditorEditable(PlainTextEditor *editor)
}
PlainTextEditor::PlainTextEditor(QWidget *parent)
: BaseTextEditor(parent)
: BaseTextEditor(parent),
m_isMissingSyntaxDefinition(true)
{
setRevisionsVisible(true);
setMarksVisible(true);
......@@ -71,7 +74,7 @@ PlainTextEditor::PlainTextEditor(QWidget *parent)
m_commentDefinition.clearCommentStyles();
connect(file(), SIGNAL(changed()), this, SLOT(configure()));
connect(file(), SIGNAL(changed()), this, SLOT(fileChanged()));
}
PlainTextEditor::~PlainTextEditor()
......@@ -112,13 +115,15 @@ void PlainTextEditor::setFontSettings(const FontSettings & fs)
}
}
void PlainTextEditor::configure()
void PlainTextEditor::fileChanged()
{
configure(Core::ICore::instance()->mimeDatabase()->findByFile(file()->fileName()));
}
void PlainTextEditor::configure(const Core::MimeType &mimeType)
{
m_isMissingSyntaxDefinition = true;
if (mimeType.isNull())
return;
......@@ -143,8 +148,12 @@ void PlainTextEditor::configure(const Core::MimeType &mimeType)
m_commentDefinition.setSingleLine(definition->singleLineComment());
m_commentDefinition.setMultiLineStart(definition->multiLineCommentStart());
m_commentDefinition.setMultiLineEnd(definition->multiLineCommentEnd());
m_isMissingSyntaxDefinition = false;
} catch (const HighlighterException &) {
}
} else if (file() && file()->fileName().endsWith(QLatin1String(".txt"))) {
m_isMissingSyntaxDefinition = false;
}
// @todo: Indentation specification through the definition files is not really being used
......@@ -153,6 +162,11 @@ void PlainTextEditor::configure(const Core::MimeType &mimeType)
m_indenter.reset(new NormalIndenter);
}
bool PlainTextEditor::isMissingSyntaxDefinition() const
{
return m_isMissingSyntaxDefinition;
}
QString PlainTextEditor::findDefinitionId(const Core::MimeType &mimeType,
bool considerParents) const
{
......@@ -162,7 +176,7 @@ QString PlainTextEditor::findDefinitionId(const Core::MimeType &mimeType,
if (definitionId.isEmpty()) {
foreach (const QString &parent, mimeType.subClassesOf()) {
const Core::MimeType &parentMimeType =
Core::ICore::instance()->mimeDatabase()->findByType(parent);
Core::ICore::instance()->mimeDatabase()->findByType(parent);
definitionId = findDefinitionId(parentMimeType, considerParents);
}
}
......
......@@ -48,6 +48,7 @@ class Indenter;
class TEXTEDITOR_EXPORT PlainTextEditorEditable : public BaseTextEditorEditable
{
Q_OBJECT
public:
PlainTextEditorEditable(PlainTextEditor *);
QList<int> context() const;
......@@ -70,13 +71,14 @@ public:
~PlainTextEditor();
void configure(const Core::MimeType &mimeType);
bool isMissingSyntaxDefinition() const;
public slots:
virtual void unCommentSelection();
virtual void setFontSettings(const FontSettings &fs);
private slots:
void configure();
void fileChanged();
protected:
virtual BaseTextEditorEditable *createEditableInterface() { return new PlainTextEditorEditable(this); }
......@@ -85,6 +87,7 @@ protected:
private:
QString findDefinitionId(const Core::MimeType &mimeType, bool considerParents) const;
bool m_isMissingSyntaxDefinition;
Utils::CommentDefinition m_commentDefinition;
QScopedPointer<Indenter> m_indenter;
};
......
......@@ -32,10 +32,15 @@
#include "texteditorconstants.h"
#include "texteditorplugin.h"
#include "texteditoractionhandler.h"
#include "texteditorsettings.h"
#include "manager.h"
#include "highlightersettings.h"
#include <coreplugin/coreconstants.h>
#include <coreplugin/editormanager/editormanager.h>
#include <QDebug>
using namespace TextEditor;
using namespace TextEditor::Internal;
......@@ -47,6 +52,9 @@ PlainTextEditorFactory::PlainTextEditorFactory(QObject *parent)
TextEditorActionHandler::Format |
TextEditorActionHandler::UnCommentSelection);
m_mimeTypes << QLatin1String(TextEditor::Constants::C_TEXTEDITOR_MIMETYPE_TEXT);
connect(Core::EditorManager::instance(), SIGNAL(currentEditorChanged(Core::IEditor*)),
this, SLOT(updateEditorInfoBar(Core::IEditor*)));
}
PlainTextEditorFactory::~PlainTextEditorFactory()
......@@ -77,6 +85,25 @@ Core::IEditor *PlainTextEditorFactory::createEditor(QWidget *parent)
return rc->editableInterface();
}
void PlainTextEditorFactory::updateEditorInfoBar(Core::IEditor *editor)
{
PlainTextEditorEditable *editorEditable = qobject_cast<PlainTextEditorEditable *>(editor);
if (editorEditable) {
PlainTextEditor *textEditor = static_cast<PlainTextEditor *>(editorEditable->editor());
if (textEditor->isMissingSyntaxDefinition() &&
TextEditorSettings::instance()->highlighterSettings().m_alertWhenNoDefinition) {
Core::EditorManager::instance()->showEditorInfoBar(
Constants::INFO_SYNTAX_DEFINITION,
tr("A highlight definition was not found for this file. Would you like to try to find one?"),
tr("Show highlighter options"),
Manager::instance(),
SLOT(showGenericHighlighterOptions()));
}
} else {
Core::EditorManager::instance()->hideEditorInfoBar(Constants::INFO_SYNTAX_DEFINITION);
}
}
void PlainTextEditorFactory::addMimeType(const QString &type)
{
m_mimeTypes.append(type);
......
......@@ -61,6 +61,9 @@ public:
TextEditor::TextEditorActionHandler *actionHandler() const { return m_actionHandler; }
private slots:
void updateEditorInfoBar(Core::IEditor *editor);
private:
QStringList m_mimeTypes;
TextEditor::TextEditorActionHandler *m_actionHandler;
......
......@@ -87,6 +87,7 @@ const char * const GOTO_NEXT_CHARACTER_WITH_SELECTION = "TextEditor.GotoNextChar
const char * const GOTO_PREVIOUS_WORD_WITH_SELECTION = "TextEditor.GotoPreviousWordWithSelection";
const char * const GOTO_NEXT_WORD_WITH_SELECTION = "TextEditor.GotoNextWordWithSelection";
const char * const C_TEXTEDITOR_MIMETYPE_TEXT = "text/plain";
const char * const INFO_SYNTAX_DEFINITION = "TextEditor.InfoSyntaxDefinition";
// Text color and style categories
......@@ -126,6 +127,10 @@ const char * const C_DIFF_LOCATION = "DiffLocation";
const char * const TEXT_EDITOR_SETTINGS_CATEGORY = "C.TextEditor";
const char * const TEXT_EDITOR_SETTINGS_CATEGORY_ICON = ":/core/images/category_texteditor.png";
const char * const TEXT_EDITOR_SETTINGS_TR_CATEGORY = QT_TRANSLATE_NOOP("TextEditor", "Text Editor");
const char * const TEXT_EDITOR_FONT_SETTINGS = "A.FontSettings";
const char * const TEXT_EDITOR_BEHAVIOR_SETTINGS = "B.BehaviourSettings";
const char * const TEXT_EDITOR_DISPLAY_SETTINGS = "D.DisplaySettings";
const char * const TEXT_EDITOR_HIGHLIGHTER_SETTINGS = "E.HighlighterSettings";
} // namespace Constants
} // namespace TextEditor
......
......@@ -143,27 +143,27 @@ TextEditorSettings::TextEditorSettings(QObject *parent)
formatDescriptions.append(FormatDescription(QLatin1String(C_DIFF_LOCATION), tr("Diff Location"), Qt::blue));
m_d->m_fontSettingsPage = new FontSettingsPage(formatDescriptions,
QLatin1String("A.FontSettings"),
QLatin1String(Constants::TEXT_EDITOR_FONT_SETTINGS),
this);
pm->addObject(m_d->m_fontSettingsPage);
// Add the GUI used to configure the tab, storage and interaction settings
TextEditor::BehaviorSettingsPageParameters behaviorSettingsPageParameters;
behaviorSettingsPageParameters.id = QLatin1String("B.BehaviourSettings");
behaviorSettingsPageParameters.id = QLatin1String(Constants::TEXT_EDITOR_BEHAVIOR_SETTINGS);
behaviorSettingsPageParameters.displayName = tr("Behavior");
behaviorSettingsPageParameters.settingsPrefix = QLatin1String("text");
m_d->m_behaviorSettingsPage = new BehaviorSettingsPage(behaviorSettingsPageParameters, this);
pm->addObject(m_d->m_behaviorSettingsPage);
TextEditor::DisplaySettingsPageParameters displaySettingsPageParameters;
displaySettingsPageParameters.id = QLatin1String("D.DisplaySettings"),
displaySettingsPageParameters.id = QLatin1String(Constants::TEXT_EDITOR_DISPLAY_SETTINGS),
displaySettingsPageParameters.displayName = tr("Display");
displaySettingsPageParameters.settingsPrefix = QLatin1String("text");