ui: styled code view
* updated spacings and colors in QtCodeView and QtCodeFile * using Source Code Pro Regular (had to remove light cut from the Fonts folder because it got always used) * updated syntax highlighted colors to fit design * changed colors of highlights * indent all QtCodeSnippets by maximum line number in QtCodeFile * fixed syntax highlighting to work with sole multiline comment end fortune cookie message = Your present plans are going to succeed.
This commit is contained in:
@@ -4,7 +4,7 @@
|
||||
<TabWidth>4</TabWidth>
|
||||
<FontName>Courier</FontName>
|
||||
<FontSize>12</FontSize>
|
||||
<LinkColor>255 255 0 100</LinkColor>
|
||||
<ActiveLinkColor>0 255 0 100</ActiveLinkColor>
|
||||
<LinkColor>222 222 222 100</LinkColor>
|
||||
<ActiveLinkColor>210 240 70 50</ActiveLinkColor>
|
||||
</code>
|
||||
</config>
|
||||
|
||||
Binary file not shown.
@@ -0,0 +1,19 @@
|
||||
#code_view #code_file QLabel#title_label {
|
||||
background-color: rgb(220,220,220);
|
||||
border-top-right-radius: 10px;
|
||||
font-family: "Source Code Pro";
|
||||
font-size: 14px;
|
||||
padding: 4px 12px;
|
||||
}
|
||||
|
||||
#code_view #code_file #code_snippet {
|
||||
font-family: "Source Code Pro";
|
||||
font-size: 14px;
|
||||
margin-bottom: 2px;
|
||||
}
|
||||
|
||||
#code_view #code_file #code_snippet #line_number_area {
|
||||
background-color: white;
|
||||
font-family: "Source Code Pro";
|
||||
font-size: 14px;
|
||||
}
|
||||
@@ -1,37 +0,0 @@
|
||||
QLineEdit#search_box {
|
||||
background: rgb(204, 204, 204);
|
||||
border: 0px;
|
||||
height: 26px;
|
||||
padding: 0 4px;
|
||||
selection-background-color: rgb(51, 51, 51);
|
||||
font-family: "Source Code Pro";
|
||||
font-size: 16px;
|
||||
font-weight: bold;
|
||||
}
|
||||
|
||||
QAbstractItemView#search_box_popup {
|
||||
selection-background-color: rgb(51, 51, 51);
|
||||
font-family: "Source Code Pro";
|
||||
font-size: 14px;
|
||||
font-weight: bold;
|
||||
}
|
||||
|
||||
QPushButton#search_button {
|
||||
border: 0px;
|
||||
border-image: url(data/gui/search_view/images/button_search.png);
|
||||
height: 26px;
|
||||
height: 26px;
|
||||
}
|
||||
|
||||
QPushButton#case_sensitive_button {
|
||||
border-image: url(data/gui/search_view/images/button_case_sensitive_inactive.png);
|
||||
border: 0px;
|
||||
height: 26px;
|
||||
height: 26px;
|
||||
margin-left: 4px;
|
||||
margin-right: 4px;
|
||||
}
|
||||
|
||||
QPushButton#case_sensitive_button:checked {
|
||||
border-image: url(data/gui/search_view/images/button_case_sensitive_active.png);
|
||||
}
|
||||
@@ -10,17 +10,18 @@ QtCodeFile::QtCodeFile(QtCodeView* parentView, const std::string& fileName, QWid
|
||||
, m_parentView(parentView)
|
||||
, m_fileName(fileName)
|
||||
{
|
||||
setObjectName("code_file");
|
||||
|
||||
QVBoxLayout* layout = new QVBoxLayout(this);
|
||||
layout->setMargin(0);
|
||||
layout->setSpacing(2);
|
||||
layout->setSpacing(0);
|
||||
layout->setAlignment(Qt::AlignTop);
|
||||
setLayout(layout);
|
||||
|
||||
QLabel* label = new QLabel(fileName.c_str(), this);
|
||||
QFontMetrics metrics(label->font());
|
||||
|
||||
label->setStyleSheet("background-color: #E1E1E1; padding: 3px;");
|
||||
label->setFixedWidth(metrics.boundingRect(fileName.c_str()).width() + 12);
|
||||
label->setObjectName("title_label");
|
||||
label->minimumSizeHint(); // force font loading
|
||||
label->setFixedWidth(label->fontMetrics().width(fileName.c_str()) + 32);
|
||||
label->setSizePolicy(sizePolicy().horizontalPolicy(), QSizePolicy::Fixed);
|
||||
layout->addWidget(label);
|
||||
}
|
||||
@@ -42,4 +43,15 @@ void QtCodeFile::addCodeSnippet(
|
||||
);
|
||||
layout()->addWidget(snippet.get());
|
||||
m_snippets.push_back(snippet);
|
||||
|
||||
int maxDigits = 1;
|
||||
for (std::shared_ptr<QtCodeSnippet> snippet : m_snippets)
|
||||
{
|
||||
maxDigits = qMax(maxDigits, snippet->lineNumberDigits());
|
||||
}
|
||||
|
||||
for (std::shared_ptr<QtCodeSnippet> snippet : m_snippets)
|
||||
{
|
||||
snippet->updateLineNumberAreaWidthForDigits(maxDigits);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -14,6 +14,7 @@ QtCodeSnippet::LineNumberArea::LineNumberArea(QtCodeSnippet *codeSnippet)
|
||||
: QWidget(codeSnippet)
|
||||
, m_codeSnippet(codeSnippet)
|
||||
{
|
||||
setObjectName("line_number_area");
|
||||
}
|
||||
|
||||
QtCodeSnippet::LineNumberArea::~LineNumberArea()
|
||||
@@ -43,7 +44,10 @@ QtCodeSnippet::QtCodeSnippet(
|
||||
, m_parentView(parentView)
|
||||
, m_startLineNumber(startLineNumber)
|
||||
, m_activeTokenId(activeTokenId)
|
||||
, m_digits(0)
|
||||
{
|
||||
minimumSizeHint(); // force font loading
|
||||
setObjectName("code_snippet");
|
||||
m_lineNumberArea = new LineNumberArea(this);
|
||||
|
||||
setReadOnly(true);
|
||||
@@ -52,15 +56,8 @@ QtCodeSnippet::QtCodeSnippet(
|
||||
setVerticalScrollBarPolicy(Qt::ScrollBarAlwaysOff);
|
||||
setLineWrapMode(QPlainTextEdit::NoWrap);
|
||||
|
||||
QFont font;
|
||||
font.setFamily(ApplicationSettings::getInstance()->getCodeFontName().c_str());
|
||||
font.setPointSize(ApplicationSettings::getInstance()->getCodeFontSize());
|
||||
font.setFixedPitch(true);
|
||||
setFont(font);
|
||||
|
||||
int tabWidth = ApplicationSettings::getInstance()->getCodeTabWidth();
|
||||
QFontMetrics metrics(font);
|
||||
setTabStopWidth(tabWidth * metrics.width(' '));
|
||||
setTabStopWidth(tabWidth * fontMetrics().width('9'));
|
||||
|
||||
m_highlighter = new QtHighlighter(document());
|
||||
|
||||
@@ -80,6 +77,7 @@ QtCodeSnippet::QtCodeSnippet(
|
||||
|
||||
setMaximumHeight(sizeHint().height());
|
||||
|
||||
m_digits = lineNumberDigits();
|
||||
updateLineNumberAreaWidth(0);
|
||||
}
|
||||
|
||||
@@ -90,14 +88,13 @@ QtCodeSnippet::~QtCodeSnippet()
|
||||
QSize QtCodeSnippet::sizeHint() const
|
||||
{
|
||||
int width = lineNumberAreaWidth() + document()->size().width();
|
||||
int height = (document()->size().height() + 1) * QFontMetrics(font()).lineSpacing();
|
||||
int height = (document()->size().height() + 1) * fontMetrics().lineSpacing() * 1.1f;
|
||||
return QSize(width, height);
|
||||
}
|
||||
|
||||
void QtCodeSnippet::lineNumberAreaPaintEvent(QPaintEvent *event)
|
||||
{
|
||||
QPainter painter(m_lineNumberArea);
|
||||
painter.fillRect(event->rect(), QColor(225,225,225));
|
||||
|
||||
QTextBlock block = firstVisibleBlock();
|
||||
int blockNumber = block.blockNumber();
|
||||
@@ -110,7 +107,7 @@ void QtCodeSnippet::lineNumberAreaPaintEvent(QPaintEvent *event)
|
||||
{
|
||||
QString number = QString::number(blockNumber + m_startLineNumber);
|
||||
painter.setPen(Qt::black);
|
||||
painter.drawText(0, top, m_lineNumberArea->width() - 3, fontMetrics().height(), Qt::AlignRight, number);
|
||||
painter.drawText(0, top, m_lineNumberArea->width() - 13, fontMetrics().height(), Qt::AlignRight, number);
|
||||
}
|
||||
|
||||
block = block.next();
|
||||
@@ -120,7 +117,7 @@ void QtCodeSnippet::lineNumberAreaPaintEvent(QPaintEvent *event)
|
||||
}
|
||||
}
|
||||
|
||||
int QtCodeSnippet::lineNumberAreaWidth() const
|
||||
int QtCodeSnippet::lineNumberDigits() const
|
||||
{
|
||||
int digits = 1;
|
||||
int max = qMax(1, m_startLineNumber + blockCount());
|
||||
@@ -130,9 +127,18 @@ int QtCodeSnippet::lineNumberAreaWidth() const
|
||||
max /= 10;
|
||||
digits++;
|
||||
}
|
||||
return digits;
|
||||
}
|
||||
|
||||
int width = fontMetrics().width(QLatin1Char('9')) * digits + 6;
|
||||
return width;
|
||||
int QtCodeSnippet::lineNumberAreaWidth() const
|
||||
{
|
||||
return fontMetrics().width(QLatin1Char('9')) * m_digits + 30;
|
||||
}
|
||||
|
||||
void QtCodeSnippet::updateLineNumberAreaWidthForDigits(int digits)
|
||||
{
|
||||
m_digits = digits;
|
||||
updateLineNumberAreaWidth(0);
|
||||
}
|
||||
|
||||
void QtCodeSnippet::annotateText(const TokenLocationFile& locationFile)
|
||||
|
||||
@@ -48,7 +48,9 @@ public:
|
||||
QSize sizeHint() const;
|
||||
|
||||
void lineNumberAreaPaintEvent(QPaintEvent *event);
|
||||
int lineNumberDigits() const;
|
||||
int lineNumberAreaWidth() const;
|
||||
void updateLineNumberAreaWidthForDigits(int digits);
|
||||
|
||||
void annotateText(const TokenLocationFile& locationFile);
|
||||
|
||||
@@ -79,6 +81,7 @@ private:
|
||||
QWidget *m_lineNumberArea;
|
||||
const int m_startLineNumber;
|
||||
const Id m_activeTokenId;
|
||||
int m_digits;
|
||||
|
||||
std::vector<Annotation> m_annotations;
|
||||
};
|
||||
|
||||
@@ -1,59 +1,58 @@
|
||||
#include "qt/utility/QtHighlighter.h"
|
||||
|
||||
#include <QTextCursor>
|
||||
#include <QTextDocument>
|
||||
|
||||
QtHighlighter::QtHighlighter(QTextDocument *parent)
|
||||
: QSyntaxHighlighter(parent)
|
||||
{
|
||||
HighlightingRule rule;
|
||||
|
||||
keywordFormat.setForeground(Qt::darkBlue);
|
||||
keywordFormat.setFontWeight(QFont::Bold);
|
||||
|
||||
QStringList keywordPatterns;
|
||||
keywordPatterns
|
||||
<< "\\bchar\\b" << "\\bclass\\b" << "\\bconst\\b"
|
||||
<< "\\bdouble\\b" << "\\benum\\b" << "\\bexplicit\\b"
|
||||
<< "\\bfriend\\b" << "\\binline\\b" << "\\bint\\b"
|
||||
<< "\\blong\\b" << "\\bnamespace\\b" << "\\boperator\\b"
|
||||
<< "\\bprivate\\b" << "\\bprotected\\b" << "\\bpublic\\b"
|
||||
<< "\\bshort\\b" << "\\bsignals\\b" << "\\bsigned\\b"
|
||||
<< "\\bslots\\b" << "\\bstatic\\b" << "\\bstruct\\b"
|
||||
<< "\\btemplate\\b" << "\\btypedef\\b" << "\\btypename\\b"
|
||||
<< "\\bunion\\b" << "\\bunsigned\\b" << "\\bvirtual\\b"
|
||||
<< "\\bvoid\\b" << "\\bvolatile\\b";
|
||||
<< "break" << "case" << "const" << "continue" << "default"
|
||||
<< "delete" << "do" << "else" << "explicit" << "false" << "for"
|
||||
<< "friend" << "if" << "inline" << "new" << "NULL" << "nullptr" << "operator"
|
||||
<< "private" << "protected" << "public" << "return" << "signals"
|
||||
<< "slots" << "static" << "switch" << "template" << "true" << "typedef"
|
||||
<< "typename" << "virtual" << "volatile" << "while";
|
||||
|
||||
QStringList typePatterns;
|
||||
typePatterns
|
||||
<< "bool" << "char" << "class" << "double"
|
||||
<< "enum" << "float" << "int" << "long"
|
||||
<< "namespace" << "short" << "signed" << "size_t"
|
||||
<< "struct" << "union" << "unsigned" << "void";
|
||||
|
||||
QRegExp directiveRegExp = QRegExp("#[a-z]+\\b");
|
||||
QRegExp commentRegExp = QRegExp("//[^\n]*");
|
||||
QRegExp quotationRegExp = QRegExp("\".*\"");
|
||||
QRegExp quotation2RegExp = QRegExp("<.*>");
|
||||
QRegExp numberRegExp = QRegExp("\\b[0-9]+\\b");
|
||||
QRegExp functionRegExp = QRegExp("\\b[A-Za-z0-9_]+(?=\\()");
|
||||
|
||||
QColor directiveColor = QColor(27,136,86);
|
||||
QColor keywordColor = QColor(27,136,86);
|
||||
QColor typeColor = QColor(208,93,24);
|
||||
QColor commentColor = Qt::gray;
|
||||
QColor numberColor = QColor(153,22,165);
|
||||
QColor quotationColor = QColor(63,169,245);
|
||||
QColor functionColor = QColor(172,150,0);
|
||||
|
||||
foreach (const QString &pattern, keywordPatterns)
|
||||
{
|
||||
rule.pattern = QRegExp(pattern);
|
||||
rule.format = keywordFormat;
|
||||
highlightingRules.append(rule);
|
||||
addHighlightingRule(keywordColor, QRegExp("\\b" + pattern + "\\b"));
|
||||
}
|
||||
|
||||
classFormat.setFontWeight(QFont::Bold);
|
||||
classFormat.setForeground(Qt::darkMagenta);
|
||||
rule.pattern = QRegExp("\\bQ[A-Za-z]+\\b");
|
||||
rule.format = classFormat;
|
||||
highlightingRules.append(rule);
|
||||
foreach (const QString &pattern, typePatterns)
|
||||
{
|
||||
addHighlightingRule(typeColor, QRegExp("\\b" + pattern + "\\b"));
|
||||
}
|
||||
|
||||
singleLineCommentFormat.setForeground(Qt::red);
|
||||
rule.pattern = QRegExp("//[^\n]*");
|
||||
rule.format = singleLineCommentFormat;
|
||||
highlightingRules.append(rule);
|
||||
|
||||
multiLineCommentFormat.setForeground(Qt::red);
|
||||
|
||||
quotationFormat.setForeground(Qt::darkGreen);
|
||||
rule.pattern = QRegExp("\".*\"");
|
||||
rule.format = quotationFormat;
|
||||
highlightingRules.append(rule);
|
||||
|
||||
functionFormat.setFontItalic(true);
|
||||
functionFormat.setForeground(Qt::blue);
|
||||
rule.pattern = QRegExp("\\b[A-Za-z0-9_]+(?=\\()");
|
||||
rule.format = functionFormat;
|
||||
highlightingRules.append(rule);
|
||||
|
||||
commentStartExpression = QRegExp("/\\*");
|
||||
commentEndExpression = QRegExp("\\*/");
|
||||
addHighlightingRule(directiveColor, directiveRegExp);
|
||||
addHighlightingRule(commentColor, commentRegExp);
|
||||
addHighlightingRule(quotationColor, quotationRegExp);
|
||||
addHighlightingRule(quotationColor, quotation2RegExp);
|
||||
addHighlightingRule(numberColor, numberRegExp);
|
||||
addHighlightingRule(functionColor, functionRegExp);
|
||||
}
|
||||
|
||||
void QtHighlighter::highlightBlock(const QString &text)
|
||||
@@ -71,12 +70,26 @@ void QtHighlighter::highlightBlock(const QString &text)
|
||||
}
|
||||
setCurrentBlockState(0);
|
||||
|
||||
QRegExp commentStartExpression = QRegExp("/\\*");
|
||||
QRegExp commentEndExpression = QRegExp("\\*/");
|
||||
|
||||
QTextCursor cursorStart = document()->find(commentStartExpression);
|
||||
QTextCursor cursorEnd = document()->find(commentEndExpression);
|
||||
|
||||
int startIndex = 0;
|
||||
if (previousBlockState() != 1)
|
||||
if (!cursorEnd.isNull() && (cursorStart.isNull() || cursorEnd < cursorStart)
|
||||
&& currentBlock().blockNumber() <= cursorEnd.blockNumber())
|
||||
{
|
||||
startIndex = 0;
|
||||
}
|
||||
else if (previousBlockState() != 1)
|
||||
{
|
||||
startIndex = commentStartExpression.indexIn(text);
|
||||
}
|
||||
|
||||
QTextCharFormat multiLineCommentFormat;
|
||||
multiLineCommentFormat.setForeground(Qt::gray);
|
||||
|
||||
while (startIndex >= 0)
|
||||
{
|
||||
int endIndex = commentEndExpression.indexIn(text, startIndex);
|
||||
@@ -96,3 +109,11 @@ void QtHighlighter::highlightBlock(const QString &text)
|
||||
startIndex = commentStartExpression.indexIn(text, startIndex + commentLength);
|
||||
}
|
||||
}
|
||||
|
||||
void QtHighlighter::addHighlightingRule(const QColor& color, const QRegExp& regExp)
|
||||
{
|
||||
HighlightingRule rule;
|
||||
rule.format.setForeground(color);
|
||||
rule.pattern = regExp;
|
||||
highlightingRules.append(rule);
|
||||
}
|
||||
|
||||
@@ -8,31 +8,24 @@ class QTextDocument;
|
||||
|
||||
class QtHighlighter : public QSyntaxHighlighter
|
||||
{
|
||||
Q_OBJECT
|
||||
Q_OBJECT
|
||||
|
||||
public:
|
||||
QtHighlighter(QTextDocument *parent = 0);
|
||||
QtHighlighter(QTextDocument *parent = 0);
|
||||
|
||||
protected:
|
||||
void highlightBlock(const QString &text);
|
||||
void highlightBlock(const QString &text);
|
||||
|
||||
private:
|
||||
struct HighlightingRule
|
||||
{
|
||||
QRegExp pattern;
|
||||
QTextCharFormat format;
|
||||
};
|
||||
QVector<HighlightingRule> highlightingRules;
|
||||
struct HighlightingRule
|
||||
{
|
||||
QRegExp pattern;
|
||||
QTextCharFormat format;
|
||||
};
|
||||
|
||||
QRegExp commentStartExpression;
|
||||
QRegExp commentEndExpression;
|
||||
void addHighlightingRule(const QColor& color, const QRegExp& regExp);
|
||||
|
||||
QTextCharFormat keywordFormat;
|
||||
QTextCharFormat classFormat;
|
||||
QTextCharFormat singleLineCommentFormat;
|
||||
QTextCharFormat multiLineCommentFormat;
|
||||
QTextCharFormat quotationFormat;
|
||||
QTextCharFormat functionFormat;
|
||||
QVector<HighlightingRule> highlightingRules;
|
||||
};
|
||||
|
||||
#endif // QT_HIGHLIGHTER_H
|
||||
|
||||
@@ -10,6 +10,7 @@
|
||||
#include "qt/utility/utilityQt.h"
|
||||
#include "utility/FileSystem.h"
|
||||
#include "utility/messaging/type/MessageActivateToken.h"
|
||||
#include "utility/text/TextAccess.h"
|
||||
|
||||
QtCodeView::QtCodeView(ViewLayout* viewLayout)
|
||||
: CodeView(viewLayout)
|
||||
@@ -30,14 +31,15 @@ void QtCodeView::createWidgetWrapper()
|
||||
void QtCodeView::initGui()
|
||||
{
|
||||
QWidget* widget = QtWidgetWrapper::getWidgetOfView(this);
|
||||
utility::setWidgetBackgroundColor(widget, Colori(255, 125, 0, 255));
|
||||
widget->setStyleSheet(TextAccess::createFromFile("data/gui/code_view/code_view.css")->getText().c_str());
|
||||
widget->setObjectName("code_view");
|
||||
|
||||
QScrollArea* scroll = dynamic_cast<QScrollArea*>(widget);
|
||||
m_frame = std::make_shared<QFrame>(scroll);
|
||||
|
||||
QVBoxLayout* layout = new QVBoxLayout(m_frame.get());
|
||||
layout->setSpacing(10);
|
||||
layout->setContentsMargins(3, 3, 3, 3);
|
||||
layout->setContentsMargins(15, 15, 15, 15);
|
||||
layout->setAlignment(Qt::AlignTop);
|
||||
m_frame->setLayout(layout);
|
||||
|
||||
|
||||
Reference in New Issue
Block a user