HAL
comment_dialog.cpp
Go to the documentation of this file.
4 #include <QDialogButtonBox>
5 #include <QTextEdit>
6 #include <QLineEdit>
7 #include <QPushButton>
8 #include <QLabel>
9 #include <QToolBar>
10 #include <QColorDialog>
11 
12 #include <QTextList>
13 #include <QMenuBar>
14 #include <QMenu>
15 #include <QTextBlockFormat>
16 #include <QTextCharFormat>
17 
18 #include <QFontDatabase>
19 #include <QStyle>
20 
21 namespace hal
22 {
23 
24  CommentDialog::CommentDialog(const QString windowTitle, CommentEntry* entry, QWidget *parent) : QDialog(parent),
25  mCommentEntry(entry)
26  {
28  init();
29  // should be extracted from stylesheet, still doesnt work...
30  mDefaultFont = QFont("Iosevka");
31  mDefaultFont.setPixelSize(14);
32 
33  if(entry)
34  {
35  // fix parsing error and then comment this in!
36  mLastModifiedLabel->setText(mCommentEntry->getLastModifiedTime().toString(mCommentEntry->getDateFormatString()));
37  mLastModifiedLabel->show();
38  mHeaderEdit->setText(entry->getHeader());
39  mTextEdit->setHtml(entry->getText());
40  updateColorActionPixmap(mDefaultColor); //default text color
41  }
42  }
43 
45  {
46 
47  }
48 
50  {
51  return mHeaderEdit->text();
52  }
53 
55  {
56  return mTextEdit->toHtml();
57  }
58 
59  void CommentDialog::init()
60  {
61  setBaseSize(600, 400);
62 
63  QStyle* s = style();
64  s->unpolish(this);
65  s->polish(this);
66 
67  // header
68  // with black border
69 // mHeaderContainer = new QWidget;
70 // mHeaderContainerLayout = new QHBoxLayout(mHeaderContainer);
71 // mHeaderContainerLayout->setContentsMargins(9,20,6,9); // space of layout to surrounding edges (increases container-widget size)
72 // //mHeaderContainer->setStyleSheet("background-color: black");
73 // mHeaderContainer->setObjectName("header-container");
74 // mHeaderEdit = new QLineEdit;
75 // //mHeaderEdit->setStyleSheet("background-color: #171e22; color: #A9B7C6;");
76 // mLastModifiedLabel = new QLabel;
77 // // perhaps a spacer item with fixed size at the front instead of left spacing/margin
78 // mHeaderContainerLayout->addWidget(mHeaderEdit);
79 // mHeaderContainerLayout->addWidget(mLastModifiedLabel);
80 
81  //without black border
82  mHeaderContainerLayout = new QHBoxLayout;
83  mHeaderEdit = new QLineEdit;
84  mLastModifiedLabel = new QLabel;
85  mHeaderContainerLayout->addWidget(mHeaderEdit);
86  mHeaderContainerLayout->addWidget(mLastModifiedLabel);
87  mLastModifiedLabel->hide();
88 
89  // toolbar
90  mToolBar = new QToolBar;
91  mBoldAction = mToolBar->addAction("Bold", this, &CommentDialog::boldTriggered); //first arg can be an icon
92  mBoldAction->setCheckable(true);
93  mBoldAction->setShortcut(Qt::CTRL | Qt::Key_B);
94  mToolBar->addSeparator();
95  mItalicsAction = mToolBar->addAction("Italics", this, &CommentDialog::italicsTriggered);
96  mItalicsAction->setCheckable(true);
97  mItalicsAction->setShortcut(Qt::CTRL | Qt::Key_I);
98  mToolBar->addSeparator();
99  mUnderscoreAction = mToolBar->addAction("Underscore", this, &CommentDialog::underscoreTriggered);
100  mUnderscoreAction->setCheckable(true);
101  mUnderscoreAction->setShortcut(Qt::CTRL | Qt::Key_U);
102  mToolBar->addSeparator(); // returns action...?
103  QPixmap pix(16, 16);
104  pix.fill(QColor(mDefaultColor));
105  mColorAction = mToolBar->addAction(pix, "Colors", this, &CommentDialog::colorTriggered);
106  mToolBar->addSeparator();
107  mListAction = mToolBar->addAction("List", this, &CommentDialog::bulletListTriggered);
108  mListAction->setCheckable(true);
109  mToolBar->addSeparator();
110  mCodeAction = mToolBar->addAction("Code", this, &CommentDialog::codeTriggered);
111  mCodeAction->setCheckable(true);
112 
113  // textedit
114  mTextEdit = new QTextEdit;
115 // QTextCharFormat fmt;
116 // fmt.setForeground(QColor(mDefaultColor));//set text color to the default text color
117 // mTextEdit->mergeCurrentCharFormat(fmt);
118 
119  // buttons
121 
122  // add everything
123  mLayout = new QVBoxLayout(this);
124  //mLayout->addWidget(mHeaderContainer);
125  mLayout->addLayout(mHeaderContainerLayout);
126  mLayout->addWidget(mToolBar);
127  mLayout->addWidget(mTextEdit);
128  mLayout->addWidget(buttonBox);
129 
130  connect(buttonBox, &QDialogButtonBox::accepted, this, &CommentDialog::handleOkClicked);
131  connect(buttonBox, &QDialogButtonBox::rejected, this, &CommentDialog::handleCancelClicked);
132 
133  connect(mTextEdit, &QTextEdit::currentCharFormatChanged, this, &CommentDialog::handleCurrentCharFormatChanged);
134  connect(mTextEdit, &QTextEdit::cursorPositionChanged, this, &CommentDialog::handleCursorPositionChanged);
135 
136  s = style();
137  s->unpolish(this);
138  s->polish(this);
139  }
140 
141  void CommentDialog::mergeFormatOnWordOrSelection(const QTextCharFormat &format)
142  {
143  QTextCursor cursor = mTextEdit->textCursor();
144  if(!cursor.hasSelection())
145  cursor.select(QTextCursor::WordUnderCursor); // perhaps not necessary? could be quite annoying
146  cursor.mergeCharFormat(format);
147  mTextEdit->mergeCurrentCharFormat(format);
148  }
149 
150  void CommentDialog::updateColorActionPixmap(const QColor &c)
151  {
152  QPixmap pix(16, 16);
153  pix.fill(c);
154  mColorAction->setIcon(pix);
155  }
156 
157  void CommentDialog::handleColorSelected()
158  {
159  auto act = dynamic_cast<QAction*>(sender());
160  if(!act) return;
161 
162  auto color = act->data().value<QColor>();
163  if(!color.isValid()) return;
164 
165  QTextCharFormat fmt;
166  fmt.setForeground(color);
167  mergeFormatOnWordOrSelection(fmt);
168  updateColorActionPixmap(color);
169  }
170 
171  void CommentDialog::handleCurrentCharFormatChanged(const QTextCharFormat &format)
172  {
173  // ugly workaround since the original color is black, but the stylesheet transforms only the "visuals" (black color is still set as format)
174  QColor color = (format.foreground().color() == Qt::black) ? mDefaultColor : format.foreground().color();
175  mBoldAction->setChecked(format.font().bold());
176  mItalicsAction->setChecked(format.font().italic());
177  mUnderscoreAction->setChecked(format.font().underline());
178  mCodeAction->setChecked(format.background().color() == mTextEdit->palette().color(QPalette::AlternateBase)); // put these strings in vars...
179  updateColorActionPixmap(color);
180  }
181 
182  void CommentDialog::handleCursorPositionChanged()
183  {
184  //updateColorActionPixmap(mTextEdit->textCursor().charFormat().foreground().color());
185  mListAction->setChecked(mTextEdit->textCursor().currentList()); // yes this works, isnt c++ fun
186  }
187 
188  void CommentDialog::boldTriggered()
189  {
190  QTextCharFormat fmt;
191  fmt.setFontWeight(mBoldAction->isChecked() ? QFont::Bold : QFont::Normal);
192  mergeFormatOnWordOrSelection(fmt);
193  }
194 
195  void CommentDialog::italicsTriggered()
196  {
197  QTextCharFormat fmt;
198  fmt.setFontItalic(mItalicsAction->isChecked());
199  mergeFormatOnWordOrSelection(fmt);
200  }
201 
202  void CommentDialog::underscoreTriggered()
203  {
204  QTextCharFormat fmt;
205  fmt.setFontUnderline(mUnderscoreAction->isChecked());
206  mergeFormatOnWordOrSelection(fmt);
207  }
208 
209  void CommentDialog::colorTriggered()
210  {
211  //QColor color(Qt::red);
212  QColor color(mRedColor);
213  QMenu* men = new QMenu(this);
214  QPixmap map(16, 16);
215  map.fill(color);
216  auto act = men->addAction(map, "Red", this, &CommentDialog::handleColorSelected);
217  act->setData(color);
218 
219  color = QColor(mGreenColor);
220  map.fill(color);
221  act = men->addAction(map, "Green", this, &CommentDialog::handleColorSelected);
222  act->setData(color);
223 
224  color = QColor(mYellowColor);
225  map.fill(color);
226  act = men->addAction(map, "Yellow", this, &CommentDialog::handleColorSelected);
227  act->setData(color);
228 
229  color = QColor(mDefaultColor); // out of stylesheet
230  map.fill(color);
231  act = men->addAction(map, "Default", this, &CommentDialog::handleColorSelected);
232  act->setData(color);
233 
234  QRect geo = mToolBar->actionGeometry(mColorAction);
235  QPoint global = mToolBar->mapToGlobal(QPoint(geo.x(), geo.y()));
236  men->move(global.x(), global.y() + geo.height());
237  men->exec();
238  }
239 
240  void CommentDialog::bulletListTriggered()
241  {
242  QTextCursor cursor = mTextEdit->textCursor();
243  if(cursor.currentList())
244  {
245  QTextBlock block = cursor.block();
246  cursor.currentList()->remove(block);
247  QTextBlockFormat blockFmt = cursor.blockFormat();
248  blockFmt.setIndent(0);
249  cursor.setBlockFormat(blockFmt);
250  }
251  else
252  {
254  // MarkerType (as well as the function setMarker) exists since version 5.14,
255  // pipeline from ubuntu 20.04 might use 5.12....
256  //QTextBlockFormat::MarkerType marker = QTextBlockFormat::MarkerType::NoMarker;
257 
258  cursor.beginEditBlock();
259 
260  QTextBlockFormat blockFmt = cursor.blockFormat();
261  //blockFmt.setMarker(marker);
262  cursor.setBlockFormat(blockFmt);
263  QTextListFormat listFmt;
264  if(cursor.currentList())
265  listFmt = cursor.currentList()->format();
266  else
267  {
268  listFmt.setIndent(blockFmt.indent()+1);
269  blockFmt.setIndent(0);
270  cursor.setBlockFormat(blockFmt);
271  }
272  listFmt.setStyle(style);
273  cursor.createList(listFmt);
274  cursor.endEditBlock();
275  }
276  }
277 
278  void CommentDialog::codeTriggered()
279  {
280  QTextCharFormat fmt;
281  //mTextEdit->palette().color(QPalette::Background)
282  //fmt.setBackground(mCodeAction->isChecked() ? QColor("#334652") : mTextEdit->palette().color(QPalette::Background)); //dependent on background
283  fmt.setBackground(mCodeAction->isChecked() ? mTextEdit->palette().color(QPalette::AlternateBase) : mTextEdit->palette().color(QPalette::Background));
284  fmt.setFont(mCodeAction->isChecked() ? QFontDatabase::systemFont(QFontDatabase::FixedFont) : mDefaultFont);
285  mergeFormatOnWordOrSelection(fmt);
286  }
287 
288  void CommentDialog::handleOkClicked()
289  {
291  }
292 
293  void CommentDialog::handleCancelClicked()
294  {
296  }
297 
298 }
CommentDialog(const QString windowTitle, CommentEntry *entry=nullptr, QWidget *parent=nullptr)
The CommentEntry class encapsulated information related to a comment.
Definition: comment_entry.h:43
QDateTime getLastModifiedTime() const
QString getHeader() const
QString getText() const
QString getDateFormatString() const
void setCheckable(bool)
void setChecked(bool)
QVariant data() const const
void setIcon(const QIcon &icon)
void setData(const QVariant &userData)
void setShortcut(const QKeySequence &shortcut)
void addLayout(QLayout *layout, int stretch)
void addWidget(QWidget *widget, int stretch, Qt::Alignment alignment)
const QColor & color() const const
QString toString(Qt::DateFormat format) const const
virtual void done(int r)
bool bold() const const
bool italic() const const
void setPixelSize(int pixelSize)
bool underline() const const
QFont systemFont(QFontDatabase::SystemFont type)
void setText(const QString &)
void setText(const QString &)
QAction * addAction(const QString &text)
QAction * exec()
QMetaObject::Connection connect(const QObject *sender, const char *signal, const QObject *receiver, const char *method, Qt::ConnectionType type)
QObject * sender() const const
int x() const const
int y() const const
int height() const const
int x() const const
int y() const const
virtual void polish(QWidget *widget)
virtual void unpolish(QWidget *widget)
int indent() const const
void setIndent(int indentation)
QFont font() const const
void setFont(const QFont &font, QTextCharFormat::FontPropertiesInheritanceBehavior behavior)
void setFontItalic(bool italic)
void setFontUnderline(bool underline)
void setFontWeight(int weight)
QTextList * currentList() const const
void currentCharFormatChanged(const QTextCharFormat &f)
void cursorPositionChanged()
void setHtml(const QString &text)
void mergeCurrentCharFormat(const QTextCharFormat &modifier)
QTextCursor textCursor() const const
QBrush background() const const
QBrush foreground() const const
void setBackground(const QBrush &brush)
void setForeground(const QBrush &brush)
void setIndent(int indentation)
void setStyle(QTextListFormat::Style style)
QAction * addAction(const QString &text)
QAction * addSeparator()
T value() const const
void setBaseSize(const QSize &)
void hide()
QPoint mapToGlobal(const QPoint &pos) const const
void move(int x, int y)
void show()
QStyle * style() const const
void setWindowTitle(const QString &)