summaryrefslogtreecommitdiff
path: root/src/gui
diff options
context:
space:
mode:
Diffstat (limited to 'src/gui')
-rw-r--r--src/gui/delimitedstringitemdelegate.cpp44
-rw-r--r--src/gui/delimitedstringitemdelegate.h42
-rw-r--r--src/gui/exportdialog.cpp194
-rw-r--r--src/gui/exportdialog.h61
-rw-r--r--src/gui/exportdialog.ui162
-rw-r--r--src/gui/latexprocess.cpp169
-rw-r--r--src/gui/latexprocess.h56
-rw-r--r--src/gui/mainmenu.cpp51
-rw-r--r--src/gui/mainmenu.h7
-rw-r--r--src/gui/mainmenu.ui36
-rw-r--r--src/gui/preferencedialog.cpp111
-rw-r--r--src/gui/preferencedialog.h31
-rw-r--r--src/gui/preferencedialog.ui272
-rw-r--r--src/gui/previewwindow.cpp208
-rw-r--r--src/gui/previewwindow.h72
-rw-r--r--src/gui/previewwindow.ui107
-rw-r--r--src/gui/styleeditor.cpp62
-rw-r--r--src/gui/styleeditor.h26
-rw-r--r--src/gui/tikzscene.cpp101
-rw-r--r--src/gui/tikzscene.h4
-rw-r--r--src/gui/tikzview.cpp8
-rw-r--r--src/gui/undocommands.cpp6
-rw-r--r--src/gui/undocommands.h36
23 files changed, 1752 insertions, 114 deletions
diff --git a/src/gui/delimitedstringitemdelegate.cpp b/src/gui/delimitedstringitemdelegate.cpp
new file mode 100644
index 0000000..7b6c58e
--- /dev/null
+++ b/src/gui/delimitedstringitemdelegate.cpp
@@ -0,0 +1,44 @@
+/*
+ TikZiT - a GUI diagram editor for TikZ
+ Copyright (C) 2018 Aleks Kissinger
+
+ This program is free software: you can redistribute it and/or modify
+ it under the terms of the GNU General Public License as published by
+ the Free Software Foundation, either version 3 of the License, or
+ (at your option) any later version.
+
+ This program 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 General Public License for more details.
+
+ You should have received a copy of the GNU General Public License
+ along with this program. If not, see <https://www.gnu.org/licenses/>.
+*/
+
+#include "delimitedstringitemdelegate.h"
+
+#include <QLineEdit>
+
+DelimitedStringItemDelegate::DelimitedStringItemDelegate(QObject *parent) : QItemDelegate (parent)
+{
+ _validator = new DelimitedStringValidator(this);
+}
+
+DelimitedStringItemDelegate::~DelimitedStringItemDelegate()
+{
+}
+
+QWidget *DelimitedStringItemDelegate::createEditor(
+ QWidget *parent,
+ const QStyleOptionViewItem &option,
+ const QModelIndex &index) const
+{
+ QWidget *editor = QItemDelegate::createEditor(parent, option, index);
+
+ if (QLineEdit *lineEdit = dynamic_cast<QLineEdit*>(editor)) {
+ lineEdit->setValidator(_validator);
+ }
+
+ return editor;
+}
diff --git a/src/gui/delimitedstringitemdelegate.h b/src/gui/delimitedstringitemdelegate.h
new file mode 100644
index 0000000..bd1a856
--- /dev/null
+++ b/src/gui/delimitedstringitemdelegate.h
@@ -0,0 +1,42 @@
+/*
+ TikZiT - a GUI diagram editor for TikZ
+ Copyright (C) 2018 Aleks Kissinger
+
+ This program is free software: you can redistribute it and/or modify
+ it under the terms of the GNU General Public License as published by
+ the Free Software Foundation, either version 3 of the License, or
+ (at your option) any later version.
+
+ This program 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 General Public License for more details.
+
+ You should have received a copy of the GNU General Public License
+ along with this program. If not, see <https://www.gnu.org/licenses/>.
+*/
+
+/*!
+ * A QItemDelete that attaches a DelimitedStringValidator to any QLineEdit
+ */
+
+#ifndef DELIMITEDSTRINGITEMDELEGATE_H
+#define DELIMITEDSTRINGITEMDELEGATE_H
+
+#include "delimitedstringvalidator.h"
+
+#include <QWidget>
+#include <QItemDelegate>
+
+class DelimitedStringItemDelegate : public QItemDelegate
+{
+ Q_OBJECT
+public:
+ DelimitedStringItemDelegate(QObject *parent=nullptr);
+ virtual ~DelimitedStringItemDelegate() override;
+ QWidget *createEditor(QWidget *parent, const QStyleOptionViewItem &option, const QModelIndex &index) const override;
+private:
+ DelimitedStringValidator *_validator;
+};
+
+#endif // DELIMITEDSTRINGITEMDELEGATE_H
diff --git a/src/gui/exportdialog.cpp b/src/gui/exportdialog.cpp
new file mode 100644
index 0000000..bd1ef53
--- /dev/null
+++ b/src/gui/exportdialog.cpp
@@ -0,0 +1,194 @@
+/*
+ TikZiT - a GUI diagram editor for TikZ
+ Copyright (C) 2018 Aleks Kissinger
+
+ This program is free software: you can redistribute it and/or modify
+ it under the terms of the GNU General Public License as published by
+ the Free Software Foundation, either version 3 of the License, or
+ (at your option) any later version.
+
+ This program 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 General Public License for more details.
+
+ You should have received a copy of the GNU General Public License
+ along with this program. If not, see <https://www.gnu.org/licenses/>.
+*/
+
+#include "exportdialog.h"
+#include "ui_exportdialog.h"
+
+#include "tikzit.h"
+
+#include <QFileDialog>
+#include <QSettings>
+#include <QStandardPaths>
+
+ExportDialog::ExportDialog(QWidget *parent) :
+ QDialog(parent),
+ ui(new Ui::ExportDialog)
+{
+ QSettings settings("tikzit", "tikzit");
+ ui->setupUi(this);
+
+ QIntValidator *v = new QIntValidator(this);
+ v->setBottom(1);
+ ui->width->setValidator(v);
+ ui->height->setValidator(v);
+ connect(ui->width, SIGNAL(editingFinished()),
+ this, SLOT(setHeightFromWidth()));
+ connect(ui->height, SIGNAL(editingFinished()),
+ this, SLOT(setWidthFromHeight()));
+
+ PdfDocument *doc = tikzit->previewWindow()->doc();
+ if (doc) {
+ QSize size = doc->size() * 4;
+ ui->width->blockSignals(true);
+ ui->height->blockSignals(true);
+ ui->width->setText(QString::number(size.width()));
+ ui->height->setText(QString::number(size.height()));
+ ui->width->blockSignals(false);
+ ui->height->blockSignals(false);
+ }
+
+ if (!settings.value("previous-export-file-format").isNull()) {
+ ui->fileFormat->setCurrentIndex(settings.value("previous-export-file-format").toInt());
+ }
+
+ // set a default export file
+ QString path = (!settings.value("previous-export-file-path").isNull()) ?
+ settings.value("previous-export-file-path").toString() :
+ QStandardPaths::writableLocation(QStandardPaths::DocumentsLocation);
+
+ QString suffix;
+ switch (ui->fileFormat->currentIndex()) {
+ case PNG: suffix = ".png"; break;
+ case JPG: suffix = ".jpg"; break;
+ case PDF: suffix = ".pdf"; break;
+ }
+
+ QString fileName;
+ int i = 0;
+ bool exists = true;
+ while (exists) {
+ fileName = path + "/tikzit_image" + QString::number(i) + suffix;
+ exists = QFileInfo::exists(fileName);
+ ++i;
+ }
+ ui->filePath->setText(QDir::toNativeSeparators(fileName));
+}
+
+ExportDialog::~ExportDialog()
+{
+ delete ui;
+}
+
+QString ExportDialog::filePath()
+{
+ return ui->filePath->text();
+}
+
+QSize ExportDialog::size()
+{
+ return QSize(ui->width->text().toInt(),
+ ui->height->text().toInt());
+}
+
+ExportDialog::Format ExportDialog::fileFormat()
+{
+ return static_cast<Format>(ui->fileFormat->currentIndex());
+}
+
+void ExportDialog::accept()
+{
+ QSettings settings("tikzit", "tikzit");
+ QFileInfo fi(filePath());
+ settings.setValue("previous-export-file-path", fi.absolutePath());
+ settings.setValue("previous-export-file-format", fileFormat());
+ QDialog::accept();
+}
+
+void ExportDialog::setHeightFromWidth()
+{
+ if (ui->keepAspect->isChecked()) {
+ PdfDocument *doc = tikzit->previewWindow()->doc();
+ if (doc == nullptr || doc->size().width() == 0 || doc->size().height() == 0) return;
+ int w = ui->width->text().toInt();
+ int h = (w * doc->size().height()) / doc->size().width();
+
+ ui->height->blockSignals(true);
+ ui->height->setText(QString::number(h));
+ ui->height->blockSignals(false);
+ }
+}
+
+void ExportDialog::setWidthFromHeight()
+{
+ if (ui->keepAspect->isChecked()) {
+ PdfDocument *doc = tikzit->previewWindow()->doc();
+ if (doc == nullptr || doc->size().width() == 0 || doc->size().height() == 0) return;
+ int h = ui->height->text().toInt();
+ int w = (h * doc->size().width()) / doc->size().height();
+
+ ui->width->blockSignals(true);
+ ui->width->setText(QString::number(w));
+ ui->width->blockSignals(false);
+ }
+}
+
+void ExportDialog::on_keepAspect_stateChanged(int state)
+{
+ if (state == Qt::Checked) setHeightFromWidth();
+}
+
+void ExportDialog::on_browseButton_clicked()
+{
+ QSettings settings("tikzit", "tikzit");
+
+ QString suffix;
+ switch (ui->fileFormat->currentIndex()) {
+ case PNG: suffix = "png"; break;
+ case JPG: suffix = "jpg"; break;
+ case PDF: suffix = "pdf"; break;
+ }
+
+ QFileDialog dialog;
+ dialog.setDefaultSuffix(suffix);
+ dialog.setWindowTitle(tr("Export File Path"));
+ dialog.setAcceptMode(QFileDialog::AcceptSave);
+ dialog.setNameFilter(ui->fileFormat->currentText());
+ dialog.setFileMode(QFileDialog::AnyFile);
+ dialog.setLabelText(QFileDialog::Accept, "Select");
+
+ QFileInfo fi(ui->filePath->text());
+ if (!fi.absolutePath().isEmpty()) {
+ dialog.setDirectory(fi.absolutePath());
+ dialog.selectFile(fi.baseName());
+ }
+
+ dialog.setOption(QFileDialog::DontUseNativeDialog);
+
+ if (dialog.exec()) {
+ ui->filePath->setText(QDir::toNativeSeparators(dialog.selectedFiles()[0]));
+ }
+}
+
+void ExportDialog::on_fileFormat_currentIndexChanged(int f)
+{
+ ui->width->setEnabled(f != PDF);
+ ui->height->setEnabled(f != PDF);
+ ui->keepAspect->setEnabled(f != PDF);
+
+ QString path = ui->filePath->text();
+ if (!path.isEmpty()) {
+ QRegularExpression re("\\.[^.]*$");
+ switch (f) {
+ case PNG: path.replace(re, ".png"); break;
+ case JPG: path.replace(re, ".jpg"); break;
+ case PDF: path.replace(re, ".pdf"); break;
+ }
+
+ ui->filePath->setText(path);
+ }
+}
diff --git a/src/gui/exportdialog.h b/src/gui/exportdialog.h
new file mode 100644
index 0000000..bcb6879
--- /dev/null
+++ b/src/gui/exportdialog.h
@@ -0,0 +1,61 @@
+/*
+ TikZiT - a GUI diagram editor for TikZ
+ Copyright (C) 2018 Aleks Kissinger
+
+ This program is free software: you can redistribute it and/or modify
+ it under the terms of the GNU General Public License as published by
+ the Free Software Foundation, either version 3 of the License, or
+ (at your option) any later version.
+
+ This program 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 General Public License for more details.
+
+ You should have received a copy of the GNU General Public License
+ along with this program. If not, see <https://www.gnu.org/licenses/>.
+*/
+
+/*!
+ * A dialog for exporting a LaTeX-generated preview to PNG, JPG, or PDF.
+ */
+
+#ifndef EXPORTDIALOG_H
+#define EXPORTDIALOG_H
+
+#include <QDialog>
+
+namespace Ui {
+class ExportDialog;
+}
+
+class ExportDialog : public QDialog
+{
+ Q_OBJECT
+
+public:
+ explicit ExportDialog(QWidget *parent = nullptr);
+ ~ExportDialog() override;
+ enum Format {
+ PNG = 0,
+ JPG = 1,
+ PDF = 2
+ };
+ QString filePath();
+ QSize size();
+ Format fileFormat();
+public slots:
+ void accept() override;
+
+protected slots:
+ void setHeightFromWidth();
+ void setWidthFromHeight();
+ void on_keepAspect_stateChanged(int state);
+ void on_browseButton_clicked();
+ void on_fileFormat_currentIndexChanged(int f);
+
+private:
+ Ui::ExportDialog *ui;
+};
+
+#endif // EXPORTDIALOG_H
diff --git a/src/gui/exportdialog.ui b/src/gui/exportdialog.ui
new file mode 100644
index 0000000..82cefdc
--- /dev/null
+++ b/src/gui/exportdialog.ui
@@ -0,0 +1,162 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<ui version="4.0">
+ <class>ExportDialog</class>
+ <widget class="QDialog" name="ExportDialog">
+ <property name="geometry">
+ <rect>
+ <x>0</x>
+ <y>0</y>
+ <width>394</width>
+ <height>119</height>
+ </rect>
+ </property>
+ <property name="sizePolicy">
+ <sizepolicy hsizetype="Fixed" vsizetype="Fixed">
+ <horstretch>0</horstretch>
+ <verstretch>0</verstretch>
+ </sizepolicy>
+ </property>
+ <property name="windowTitle">
+ <string>Export Image</string>
+ </property>
+ <layout class="QHBoxLayout" name="horizontalLayout">
+ <item>
+ <layout class="QFormLayout" name="formLayout">
+ <item row="0" column="0">
+ <widget class="QLabel" name="label">
+ <property name="text">
+ <string>File</string>
+ </property>
+ </widget>
+ </item>
+ <item row="1" column="0">
+ <widget class="QLabel" name="label_2">
+ <property name="text">
+ <string>Format</string>
+ </property>
+ </widget>
+ </item>
+ <item row="0" column="1">
+ <layout class="QHBoxLayout" name="horizontalLayout_2">
+ <item>
+ <widget class="QLineEdit" name="filePath"/>
+ </item>
+ <item>
+ <widget class="QToolButton" name="browseButton">
+ <property name="text">
+ <string>...</string>
+ </property>
+ </widget>
+ </item>
+ </layout>
+ </item>
+ <item row="1" column="1">
+ <widget class="QComboBox" name="fileFormat">
+ <item>
+ <property name="text">
+ <string>Portable Network Graphics (*.png)</string>
+ </property>
+ </item>
+ <item>
+ <property name="text">
+ <string>Jpeg Image (*.jpg)</string>
+ </property>
+ </item>
+ <item>
+ <property name="text">
+ <string>Original (*.pdf)</string>
+ </property>
+ </item>
+ </widget>
+ </item>
+ <item row="2" column="0">
+ <widget class="QLabel" name="label_3">
+ <property name="text">
+ <string>Dimensions</string>
+ </property>
+ </widget>
+ </item>
+ <item row="2" column="1">
+ <layout class="QHBoxLayout" name="horizontalLayout_3">
+ <item>
+ <widget class="QLineEdit" name="width"/>
+ </item>
+ <item>
+ <widget class="QLabel" name="label_4">
+ <property name="text">
+ <string> X </string>
+ </property>
+ </widget>
+ </item>
+ <item>
+ <widget class="QLineEdit" name="height"/>
+ </item>
+ </layout>
+ </item>
+ <item row="3" column="0">
+ <widget class="QLabel" name="label_5">
+ <property name="text">
+ <string/>
+ </property>
+ </widget>
+ </item>
+ <item row="3" column="1">
+ <widget class="QCheckBox" name="keepAspect">
+ <property name="text">
+ <string>Keep aspect ratio</string>
+ </property>
+ <property name="checked">
+ <bool>true</bool>
+ </property>
+ </widget>
+ </item>
+ </layout>
+ </item>
+ <item>
+ <widget class="QDialogButtonBox" name="buttonBox">
+ <property name="orientation">
+ <enum>Qt::Vertical</enum>
+ </property>
+ <property name="standardButtons">
+ <set>QDialogButtonBox::Cancel|QDialogButtonBox::Save</set>
+ </property>
+ </widget>
+ </item>
+ </layout>
+ </widget>
+ <resources/>
+ <connections>
+ <connection>
+ <sender>buttonBox</sender>
+ <signal>accepted()</signal>
+ <receiver>ExportDialog</receiver>
+ <slot>accept()</slot>
+ <hints>
+ <hint type="sourcelabel">
+ <x>248</x>
+ <y>254</y>
+ </hint>
+ <hint type="destinationlabel">
+ <x>157</x>
+ <y>274</y>
+ </hint>
+ </hints>
+ </connection>
+ <connection>
+ <sender>buttonBox</sender>
+ <signal>rejected()</signal>
+ <receiver>ExportDialog</receiver>
+ <slot>reject()</slot>
+ <hints>
+ <hint type="sourcelabel">
+ <x>316</x>
+ <y>260</y>
+ </hint>
+ <hint type="destinationlabel">
+ <x>286</x>
+ <y>274</y>
+ </hint>
+ </hints>
+ </connection>
+ </connections>
+</ui>
diff --git a/src/gui/latexprocess.cpp b/src/gui/latexprocess.cpp
new file mode 100644
index 0000000..59db9ea
--- /dev/null
+++ b/src/gui/latexprocess.cpp
@@ -0,0 +1,169 @@
+/*
+ TikZiT - a GUI diagram editor for TikZ
+ Copyright (C) 2018 Aleks Kissinger
+
+ This program is free software: you can redistribute it and/or modify
+ it under the terms of the GNU General Public License as published by
+ the Free Software Foundation, either version 3 of the License, or
+ (at your option) any later version.
+
+ This program 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 General Public License for more details.
+
+ You should have received a copy of the GNU General Public License
+ along with this program. If not, see <https://www.gnu.org/licenses/>.
+*/
+
+#include "latexprocess.h"
+#include "tikzit.h"
+
+#include <QDebug>
+#include <QStandardPaths>
+#include <QTemporaryDir>
+#include <QStringList>
+#include <QSettings>
+
+LatexProcess::LatexProcess(PreviewWindow *preview, QObject *parent) : QObject(parent)
+{
+ _preview = preview;
+ _output = preview->outputTextEdit();
+
+ _proc = new QProcess(this);
+ _proc->setProcessChannelMode(QProcess::MergedChannels);
+ _proc->setWorkingDirectory(_workingDir.path());
+
+ connect(_proc, SIGNAL(readyReadStandardOutput()), this, SLOT(readyReadStandardOutput()));
+ connect(_proc, SIGNAL(finished(int)), this, SLOT(finished(int)));
+
+ // for debug purposes
+ //_workingDir.setAutoRemove(false);
+}
+
+void LatexProcess::makePreview(QString tikz)
+{
+ QSettings settings("tikzit", "tikzit");
+ _preview->setStatus(PreviewWindow::Running);
+ _output->clear();
+
+ if (!_workingDir.isValid()) {
+ _output->appendPlainText("COULD NOT WRITE TO TEMP DIR: " + _workingDir.path() + "\n");
+ return;
+ }
+
+ _output->appendPlainText("USING TEMP DIR: " + _workingDir.path() + "\n");
+
+ QString pdflatex;
+
+ if (settings.value("auto-detect-pdflatex", true).toBool()) {
+ _output->appendPlainText("SEARCHING FOR pdflatex IN:");
+ _output->appendPlainText(qgetenv("PATH"));
+ _output->appendPlainText("\n");
+ pdflatex = QStandardPaths::findExecutable("pdflatex");
+ if (pdflatex.isEmpty()) {
+ // if pdflatex is not in PATH, we are probably on mac or windows, so try common
+ // install directories.
+ _output->appendPlainText("NOT FOUND IN PATH, TRYING:");
+
+ QStringList texDirs;
+ // common macOS tex directories:
+ texDirs << "/Library/TeX/texbin";
+ texDirs << "/usr/texbin";
+ texDirs << "/usr/local/bin";
+ texDirs << "/sw/bin";
+
+ // common windows tex directories
+ texDirs << "C:\\Program Files\\MiKTeX 2.9\\miktex\\bin";
+ texDirs << "C:\\Program Files\\MiKTeX 2.9\\miktex\\bin\\x64";
+ texDirs << "C:\\Program Files\\MiKTeX 2.8\\miktex\\bin";
+ texDirs << "C:\\Program Files\\MiKTeX 2.8\\miktex\\bin\\x64";
+ texDirs << "C:\\Program Files\\MiKTeX 2.7\\miktex\\bin";
+ texDirs << "C:\\Program Files\\MiKTeX 2.7\\miktex\\bin\\x64";
+
+ _output->appendPlainText(texDirs.join(":"));
+ pdflatex = QStandardPaths::findExecutable("pdflatex", texDirs);
+ }
+
+ if (pdflatex.isEmpty()) {
+ _output->appendPlainText("pdflatex NOT FOUND, ABORTING.\n");
+ _preview->setStatus(PreviewWindow::Failed);
+ return;
+ } else {
+ _output->appendPlainText("FOUND: " + pdflatex + "\n");
+ }
+ } else {
+ _output->appendPlainText("USING pdflatex:\n");
+ pdflatex = settings.value("pdflatex-path", "/usr/bin/pdflatex").toString();
+ _output->appendPlainText(pdflatex + "\n");
+ }
+
+ // copy tikzit.sty to preview dir
+ QFile::copy(":/tex/sample/tikzit.sty", _workingDir.path() + "/tikzit.sty");
+
+ // write out the file containing the tikz picture
+ QFile f(_workingDir.path() + "/preview.tex");
+ f.open(QIODevice::WriteOnly);
+ QTextStream tex(&f);
+ tex << "\\documentclass{article}\n";
+ tex << "\\usepackage{tikzit}\n";
+ tex << "\\tikzstyle{every picture}=[tikzfig]\n";
+ tex << "\\usepackage[graphics,active,tightpage]{preview}\n";
+ tex << "\\PreviewEnvironment{tikzpicture}\n";
+
+ // copy active *.tikzstyles file to preview dir
+ if (!tikzit->styleFile().isEmpty() && QFile::exists(tikzit->styleFilePath())) {
+ QFile::copy(tikzit->styleFilePath(), _workingDir.path() + "/" + tikzit->styleFile());
+ tex << "\\input{" + tikzit->styleFile() + "}\n";
+
+ // if there is a *.tikzdefs file with the same basename, copy and include it as well
+ QFileInfo fi(tikzit->styleFilePath());
+ QString defFile = fi.baseName() + ".tikzdefs";
+ QString defFilePath = fi.absolutePath() + "/" + defFile;
+ if (QFile::exists(defFilePath)) {
+ QFile::copy(defFilePath, _workingDir.path() + "/" + defFile);
+ tex << "\\input{" + defFile + "}\n";
+ }
+ }
+
+ tex << "\\begin{document}\n\n";
+ tex << tikz;
+ tex << "\n\n\\end{document}\n";
+
+ f.close();
+ _proc->start(pdflatex,
+ QStringList()
+ << "-interaction=nonstopmode"
+ << "-halt-on-error"
+ << "preview.tex");
+
+}
+
+void LatexProcess::kill()
+{
+ if (_proc->state() == QProcess::Running) _proc->kill();
+}
+
+void LatexProcess::readyReadStandardOutput()
+{
+ QByteArray s = _proc->readAllStandardOutput();
+ _output->appendPlainText(s);
+}
+
+void LatexProcess::finished(int exitCode)
+{
+ QByteArray s = _proc->readAllStandardOutput();
+ _output->appendPlainText(s);
+
+ if (exitCode == 0) {
+ QString pdf = _workingDir.path() + "/preview.pdf";
+ _output->appendPlainText("\n\nSUCCESSFULLY GENERATED: " + pdf + "\n");
+ _preview->setPdf(pdf);
+ _preview->setStatus(PreviewWindow::Success);
+ emit previewFinished();
+ } else {
+ _output->appendPlainText("\n\npdflatex RETURNED AN ERROR\n");
+ _preview->setStatus(PreviewWindow::Failed);
+ emit previewFinished();
+ }
+}
diff --git a/src/gui/latexprocess.h b/src/gui/latexprocess.h
new file mode 100644
index 0000000..9853883
--- /dev/null
+++ b/src/gui/latexprocess.h
@@ -0,0 +1,56 @@
+/*
+ TikZiT - a GUI diagram editor for TikZ
+ Copyright (C) 2018 Aleks Kissinger
+
+ This program is free software: you can redistribute it and/or modify
+ it under the terms of the GNU General Public License as published by
+ the Free Software Foundation, either version 3 of the License, or
+ (at your option) any later version.
+
+ This program 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 General Public License for more details.
+
+ You should have received a copy of the GNU General Public License
+ along with this program. If not, see <https://www.gnu.org/licenses/>.
+*/
+
+/*!
+ * Run pdflatex and dump its output to the appropriate tab of
+ * the PreviewWindow.
+ */
+
+#ifndef LATEXPROCESS_H
+#define LATEXPROCESS_H
+
+#include "previewwindow.h"
+
+#include <QObject>
+#include <QProcess>
+#include <QTemporaryDir>
+#include <QPlainTextEdit>
+
+class LatexProcess : public QObject
+{
+ Q_OBJECT
+public:
+ explicit LatexProcess(PreviewWindow *preview, QObject *parent = nullptr);
+ void makePreview(QString tikz);
+ void kill();
+
+private:
+ QTemporaryDir _workingDir;
+ PreviewWindow *_preview;
+ QPlainTextEdit *_output;
+ QProcess *_proc;
+
+public slots:
+ void readyReadStandardOutput();
+ void finished(int exitCode);
+
+signals:
+ void previewFinished();
+};
+
+#endif // LATEXPROCESS_H
diff --git a/src/gui/mainmenu.cpp b/src/gui/mainmenu.cpp
index 8166c59..6f4f8db 100644
--- a/src/gui/mainmenu.cpp
+++ b/src/gui/mainmenu.cpp
@@ -17,6 +17,7 @@
*/
#include "mainmenu.h"
+#include "preferencedialog.h"
#include "tikzit.h"
#include <QDebug>
@@ -33,6 +34,8 @@ MainMenu::MainMenu()
ui.actionCheck_for_updates_automatically->setChecked(settings.value("check-for-updates").toBool());
ui.actionCheck_for_updates_automatically->blockSignals(false);
}
+
+ updateRecentFiles();
}
void MainMenu::addDocks(QMenu *m)
@@ -48,6 +51,31 @@ QAction *MainMenu::updatesAction()
return ui.actionCheck_for_updates_automatically;
}
+void MainMenu::updateRecentFiles()
+{
+ QSettings settings("tikzit", "tikzit");
+ ui.menuOpen_Recent->clear();
+
+ QStringList recentFiles = settings.value("recent-files").toStringList();
+ //qDebug() << "update:" << recentFiles;
+
+ QAction *action;
+ foreach (QString f, recentFiles) {
+ QFileInfo fi(f);
+ action = new QAction(fi.fileName(), ui.menuOpen_Recent);
+ action->setData(f);
+ ui.menuOpen_Recent->addAction(action);
+ connect(action, SIGNAL(triggered()),
+ this, SLOT(openRecent()));
+ }
+
+ ui.menuOpen_Recent->addSeparator();
+ action = new QAction("Clear List", ui.menuOpen_Recent);
+ connect(action, SIGNAL(triggered()),
+ tikzit, SLOT(clearRecentFiles()));
+ ui.menuOpen_Recent->addAction(action);
+}
+
// File
void MainMenu::on_actionNew_triggered()
{
@@ -82,6 +110,15 @@ void MainMenu::on_actionExit_triggered()
tikzit->quit();
}
+void MainMenu::openRecent()
+{
+ if (sender() != nullptr) {
+ if (QAction *action = dynamic_cast<QAction*>(sender())) {
+ tikzit->open(action->data().toString());
+ }
+ }
+}
+
// Edit
void MainMenu::on_actionUndo_triggered()
@@ -228,6 +265,18 @@ void MainMenu::on_actionJump_to_Selection_triggered()
}
}
+void MainMenu::on_actionRun_LaTeX_triggered()
+{
+ tikzit->makePreview();
+}
+
+void MainMenu::on_actionPreferences_triggered()
+{
+ PreferenceDialog *d = new PreferenceDialog(this);
+ d->exec();
+ d->deleteLater();
+}
+
// View
void MainMenu::on_actionZoom_In_triggered()
@@ -260,5 +309,5 @@ void MainMenu::on_actionCheck_for_updates_automatically_triggered()
void MainMenu::on_actionCheck_now_triggered()
{
- tikzit->checkForUpdates();
+ tikzit->checkForUpdates(true);
}
diff --git a/src/gui/mainmenu.h b/src/gui/mainmenu.h
index c14a284..4d672cd 100644
--- a/src/gui/mainmenu.h
+++ b/src/gui/mainmenu.h
@@ -30,6 +30,7 @@ public:
MainMenu();
void addDocks(QMenu *m);
QAction *updatesAction();
+ void updateRecentFiles();
private:
Ui::MainMenu ui;
@@ -43,6 +44,8 @@ public slots:
void on_actionSave_As_triggered();
void on_actionExit_triggered();
+ void openRecent();
+
// Edit
void on_actionUndo_triggered();
void on_actionRedo_triggered();
@@ -63,10 +66,12 @@ public slots:
void on_actionExtendLeft_triggered();
void on_actionExtendRight_triggered();
- // Tikz
+ // Tools
void on_actionParse_triggered();
void on_actionRevert_triggered();
void on_actionJump_to_Selection_triggered();
+ void on_actionRun_LaTeX_triggered();
+ void on_actionPreferences_triggered();
// View
void on_actionZoom_In_triggered();
diff --git a/src/gui/mainmenu.ui b/src/gui/mainmenu.ui
index 0481c1d..08067aa 100644
--- a/src/gui/mainmenu.ui
+++ b/src/gui/mainmenu.ui
@@ -14,8 +14,14 @@
<property name="title">
<string>File</string>
</property>
+ <widget class="QMenu" name="menuOpen_Recent">
+ <property name="title">
+ <string>Open Recent</string>
+ </property>
+ </widget>
<addaction name="actionNew"/>
<addaction name="actionOpen"/>
+ <addaction name="menuOpen_Recent"/>
<addaction name="separator"/>
<addaction name="actionClose"/>
<addaction name="actionSave"/>
@@ -69,11 +75,14 @@
</widget>
<widget class="QMenu" name="menuTikz">
<property name="title">
- <string>Tikz</string>
+ <string>Tools</string>
</property>
<addaction name="actionParse"/>
<addaction name="actionRevert"/>
<addaction name="actionJump_to_Selection"/>
+ <addaction name="actionRun_LaTeX"/>
+ <addaction name="separator"/>
+ <addaction name="actionPreferences"/>
</widget>
<widget class="QMenu" name="menuView">
<property name="title">
@@ -197,7 +206,7 @@
</action>
<action name="actionParse">
<property name="text">
- <string>Parse Tikz</string>
+ <string>Parse TikZ</string>
</property>
<property name="shortcut">
<string>Ctrl+T</string>
@@ -226,7 +235,10 @@
</action>
<action name="actionRevert">
<property name="text">
- <string>Revert Tikz</string>
+ <string>Revert TikZ</string>
+ </property>
+ <property name="shortcut">
+ <string>Ctrl+Alt+T</string>
</property>
</action>
<action name="actionJump_to_Selection">
@@ -335,6 +347,24 @@
<string>About</string>
</property>
</action>
+ <action name="actionRun_LaTeX">
+ <property name="text">
+ <string>Make Preview</string>
+ </property>
+ <property name="shortcut">
+ <string>Ctrl+R</string>
+ </property>
+ </action>
+ <action name="actionClear_Menu">
+ <property name="text">
+ <string>Clear Menu</string>
+ </property>
+ </action>
+ <action name="actionPreferences">
+ <property name="text">
+ <string>Preferences...</string>
+ </property>
+ </action>
<addaction name="menuFile"/>
<addaction name="menuEdit"/>
<addaction name="menuView"/>
diff --git a/src/gui/preferencedialog.cpp b/src/gui/preferencedialog.cpp
new file mode 100644
index 0000000..06159af
--- /dev/null
+++ b/src/gui/preferencedialog.cpp
@@ -0,0 +1,111 @@
+#include "preferencedialog.h"
+#include "ui_preferencedialog.h"
+
+#include <QColorDialog>
+#include <QFileDialog>
+#include <QSettings>
+
+PreferenceDialog::PreferenceDialog(QWidget *parent) :
+ QDialog(parent),
+ ui(new Ui::PreferenceDialog)
+{
+ ui->setupUi(this);
+ QSettings settings("tikzit", "tikzit");
+ ui->autoPdflatex->setChecked(true);
+
+ if (!settings.value("auto-detect-pdflatex").isNull())
+ ui->autoPdflatex->setChecked(settings.value("auto-detect-pdflatex").toBool());
+ if (!settings.value("pdflatex-path").isNull())
+ ui->pdflatexPath->setText(settings.value("pdflatex-path").toString());
+
+
+ setColor(ui->axesColor, settings.value("grid-color-axes",
+ QColor(220,220,240)).value<QColor>());
+ setColor(ui->majorColor, settings.value("grid-color-major",
+ QColor(240,240,250)).value<QColor>());
+ setColor(ui->minorColor, settings.value("grid-color-minor",
+ QColor(250,250,255)).value<QColor>());
+
+
+ connect(ui->axesColor, SIGNAL(clicked()), this, SLOT(colorClick()));
+ connect(ui->majorColor, SIGNAL(clicked()), this, SLOT(colorClick()));
+ connect(ui->minorColor, SIGNAL(clicked()), this, SLOT(colorClick()));
+}
+
+PreferenceDialog::~PreferenceDialog()
+{
+ delete ui;
+}
+
+void PreferenceDialog::accept()
+{
+ QSettings settings("tikzit", "tikzit");
+ settings.setValue("auto-detect-pdflatex", ui->autoPdflatex->isChecked());
+ settings.setValue("pdflatex-path", ui->pdflatexPath->text());
+ settings.setValue("grid-color-axes", color(ui->axesColor));
+ settings.setValue("grid-color-major", color(ui->majorColor));
+ settings.setValue("grid-color-minor", color(ui->minorColor));
+ QDialog::accept();
+}
+
+void PreferenceDialog::on_resetColors_clicked()
+{
+ setColor(ui->axesColor, QColor(220,220,240));
+ setColor(ui->majorColor, QColor(240,240,250));
+ setColor(ui->minorColor, QColor(250,250,255));
+}
+
+void PreferenceDialog::colorClick()
+{
+ if (QPushButton *btn = dynamic_cast<QPushButton*>(sender())) {
+ QColor col = QColorDialog::getColor(
+ color(btn),
+ this,
+ "Set color",
+ QColorDialog::DontUseNativeDialog);
+ if (col.isValid()) setColor(btn, col);
+ }
+}
+
+void PreferenceDialog::on_autoPdflatex_stateChanged(int state)
+{
+ ui->pdflatexPath->setEnabled(state != Qt::Checked);
+ ui->browsePdflatex->setEnabled(state != Qt::Checked);
+}
+
+void PreferenceDialog::on_browsePdflatex_clicked()
+{
+ QSettings settings("tikzit", "tikzit");
+
+ QFileDialog dialog;
+ dialog.setWindowTitle(tr("pdflatex Path"));
+ dialog.setAcceptMode(QFileDialog::AcceptOpen);
+ dialog.setFileMode(QFileDialog::ExistingFile);
+ dialog.setLabelText(QFileDialog::Accept, "Select");
+
+ QFileInfo fi(ui->pdflatexPath->text());
+ if (!fi.absolutePath().isEmpty()) {
+ dialog.setDirectory(fi.absolutePath());
+ dialog.selectFile(fi.baseName());
+ }
+
+ dialog.setOption(QFileDialog::DontUseNativeDialog);
+
+ if (dialog.exec()) {
+ ui->pdflatexPath->setText(QDir::toNativeSeparators(dialog.selectedFiles()[0]));
+ }
+}
+
+void PreferenceDialog::setColor(QPushButton *btn, QColor col)
+{
+ QPalette pal = btn->palette();
+ pal.setColor(QPalette::Button, col);
+ btn->setPalette(pal);
+ btn->update();
+}
+
+QColor PreferenceDialog::color(QPushButton *btn)
+{
+ QPalette pal = btn->palette();
+ return pal.color(QPalette::Button);
+}
diff --git a/src/gui/preferencedialog.h b/src/gui/preferencedialog.h
new file mode 100644
index 0000000..9da8ae6
--- /dev/null
+++ b/src/gui/preferencedialog.h
@@ -0,0 +1,31 @@
+#ifndef PREFERENCEDIALOG_H
+#define PREFERENCEDIALOG_H
+
+#include <QDialog>
+
+namespace Ui {
+class PreferenceDialog;
+}
+
+class PreferenceDialog : public QDialog
+{
+ Q_OBJECT
+
+public:
+ explicit PreferenceDialog(QWidget *parent = nullptr);
+ ~PreferenceDialog() override;
+
+protected slots:
+ void accept() override;
+ void colorClick();
+ void on_resetColors_clicked();
+ void on_autoPdflatex_stateChanged(int state);
+ void on_browsePdflatex_clicked();
+
+private:
+ Ui::PreferenceDialog *ui;
+ QColor color(QPushButton *btn);
+ void setColor(QPushButton *btn, QColor col);
+};
+
+#endif // PREFERENCEDIALOG_H
diff --git a/src/gui/preferencedialog.ui b/src/gui/preferencedialog.ui
new file mode 100644
index 0000000..9a32e7d
--- /dev/null
+++ b/src/gui/preferencedialog.ui
@@ -0,0 +1,272 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<ui version="4.0">
+ <class>PreferenceDialog</class>
+ <widget class="QDialog" name="PreferenceDialog">
+ <property name="geometry">
+ <rect>
+ <x>0</x>
+ <y>0</y>
+ <width>345</width>
+ <height>176</height>
+ </rect>
+ </property>
+ <property name="windowTitle">
+ <string>Dialog</string>
+ </property>
+ <layout class="QVBoxLayout" name="verticalLayout">
+ <item>
+ <layout class="QFormLayout" name="formLayout">
+ <item row="0" column="0">
+ <widget class="QLabel" name="label">
+ <property name="text">
+ <string>pdflatex Location</string>
+ </property>
+ </widget>
+ </item>
+ <item row="0" column="1">
+ <layout class="QHBoxLayout" name="horizontalLayout">
+ <item>
+ <widget class="QLineEdit" name="pdflatexPath"/>
+ </item>
+ <item>
+ <widget class="QToolButton" name="browsePdflatex">
+ <property name="text">
+ <string>...</string>
+ </property>
+ </widget>
+ </item>
+ </layout>
+ </item>
+ <item row="1" column="1">
+ <widget class="QCheckBox" name="autoPdflatex">
+ <property name="text">
+ <string>Automatically detect pdflatex</string>
+ </property>
+ </widget>
+ </item>
+ <item row="2" column="0">
+ <widget class="QLabel" name="label_3">
+ <property name="text">
+ <string>Grid colors</string>
+ </property>
+ </widget>
+ </item>
+ <item row="2" column="1">
+ <layout class="QHBoxLayout" name="horizontalLayout_2">
+ <item>
+ <widget class="QFrame" name="frame">
+ <property name="frameShape">
+ <enum>QFrame::Box</enum>
+ </property>
+ <property name="frameShadow">
+ <enum>QFrame::Plain</enum>
+ </property>
+ <layout class="QHBoxLayout" name="horizontalLayout_3">
+ <property name="leftMargin">
+ <number>0</number>
+ </property>
+ <property name="topMargin">
+ <number>0</number>
+ </property>
+ <property name="rightMargin">
+ <number>0</number>
+ </property>
+ <property name="bottomMargin">
+ <number>0</number>
+ </property>
+ <item>
+ <widget class="QPushButton" name="axesColor">
+ <property name="autoFillBackground">
+ <bool>true</bool>
+ </property>
+ <property name="text">
+ <string/>
+ </property>
+ <property name="flat">
+ <bool>true</bool>
+ </property>
+ </widget>
+ </item>
+ </layout>
+ </widget>
+ </item>
+ <item>
+ <widget class="QLabel" name="label_4">
+ <property name="text">
+ <string>Axes</string>
+ </property>
+ </widget>
+ </item>
+ <item>
+ <spacer name="horizontalSpacer">
+ <property name="orientation">
+ <enum>Qt::Horizontal</enum>
+ </property>
+ <property name="sizeHint" stdset="0">
+ <size>
+ <width>40</width>
+ <height>20</height>
+ </size>
+ </property>
+ </spacer>
+ </item>
+ <item>
+ <widget class="QFrame" name="frame_2">
+ <property name="frameShape">
+ <enum>QFrame::Box</enum>
+ </property>
+ <property name="frameShadow">
+ <enum>QFrame::Plain</enum>
+ </property>
+ <layout class="QHBoxLayout" name="horizontalLayout_4">
+ <property name="leftMargin">
+ <number>0</number>
+ </property>
+ <property name="topMargin">
+ <number>0</number>
+ </property>
+ <property name="rightMargin">
+ <number>0</number>
+ </property>
+ <property name="bottomMargin">
+ <number>0</number>
+ </property>
+ <item>
+ <widget class="QPushButton" name="majorColor">
+ <property name="autoFillBackground">
+ <bool>true</bool>
+ </property>
+ <property name="text">
+ <string/>
+ </property>
+ <property name="flat">
+ <bool>true</bool>
+ </property>
+ </widget>
+ </item>
+ </layout>
+ </widget>
+ </item>
+ <item>
+ <widget class="QLabel" name="label_5">
+ <property name="text">
+ <string>Major</string>
+ </property>
+ </widget>
+ </item>
+ <item>
+ <spacer name="horizontalSpacer_2">
+ <property name="orientation">
+ <enum>Qt::Horizontal</enum>
+ </property>
+ <property name="sizeHint" stdset="0">
+ <size>
+ <width>40</width>
+ <height>20</height>
+ </size>
+ </property>
+ </spacer>
+ </item>
+ <item>
+ <widget class="QFrame" name="frame_3">
+ <property name="frameShape">
+ <enum>QFrame::Box</enum>
+ </property>
+ <property name="frameShadow">
+ <enum>QFrame::Plain</enum>
+ </property>
+ <layout class="QHBoxLayout" name="horizontalLayout_5">
+ <property name="leftMargin">
+ <number>0</number>
+ </property>
+ <property name="topMargin">
+ <number>0</number>
+ </property>
+ <property name="rightMargin">
+ <number>0</number>
+ </property>
+ <property name="bottomMargin">
+ <number>0</number>
+ </property>
+ <item>
+ <widget class="QPushButton" name="minorColor">
+ <property name="autoFillBackground">
+ <bool>true</bool>
+ </property>
+ <property name="text">
+ <string/>
+ </property>
+ <property name="flat">
+ <bool>true</bool>
+ </property>
+ </widget>
+ </item>
+ </layout>
+ </widget>
+ </item>
+ <item>
+ <widget class="QLabel" name="label_6">
+ <property name="text">
+ <string>Minor</string>
+ </property>
+ </widget>
+ </item>
+ </layout>
+ </item>
+ <item row="3" column="1">
+ <widget class="QPushButton" name="resetColors">
+ <property name="text">
+ <string>Reset colors</string>
+ </property>
+ </widget>
+ </item>
+ </layout>
+ </item>
+ <item>
+ <widget class="QDialogButtonBox" name="buttonBox">
+ <property name="orientation">
+ <enum>Qt::Horizontal</enum>
+ </property>
+ <property name="standardButtons">
+ <set>QDialogButtonBox::Cancel|QDialogButtonBox::Ok</set>
+ </property>
+ </widget>
+ </item>
+ </layout>
+ </widget>
+ <resources/>
+ <connections>
+ <connection>
+ <sender>buttonBox</sender>
+ <signal>accepted()</signal>
+ <receiver>PreferenceDialog</receiver>
+ <slot>accept()</slot>
+ <hints>
+ <hint type="sourcelabel">
+ <x>248</x>
+ <y>254</y>
+ </hint>
+ <hint type="destinationlabel">
+ <x>157</x>
+ <y>274</y>
+ </hint>
+ </hints>
+ </connection>
+ <connection>
+ <sender>buttonBox</sender>
+ <signal>rejected()</signal>
+ <receiver>PreferenceDialog</receiver>
+ <slot>reject()</slot>
+ <hints>
+ <hint type="sourcelabel">
+ <x>316</x>
+ <y>260</y>
+ </hint>
+ <hint type="destinationlabel">
+ <x>286</x>
+ <y>274</y>
+ </hint>
+ </hints>
+ </connection>
+ </connections>
+</ui>
diff --git a/src/gui/previewwindow.cpp b/src/gui/previewwindow.cpp
new file mode 100644
index 0000000..2f47efd
--- /dev/null
+++ b/src/gui/previewwindow.cpp
@@ -0,0 +1,208 @@
+/*
+ TikZiT - a GUI diagram editor for TikZ
+ Copyright (C) 2018 Aleks Kissinger
+
+ This program is free software: you can redistribute it and/or modify
+ it under the terms of the GNU General Public License as published by
+ the Free Software Foundation, either version 3 of the License, or
+ (at your option) any later version.
+
+ This program 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 General Public License for more details.
+
+ You should have received a copy of the GNU General Public License
+ along with this program. If not, see <https://www.gnu.org/licenses/>.
+*/
+
+#include "previewwindow.h"
+#include "ui_previewwindow.h"
+
+#include "tikzit.h"
+#include "latexprocess.h"
+#include "exportdialog.h"
+
+#include <QLabel>
+#include <QImage>
+#include <QPixmap>
+#include <QDebug>
+#include <QSettings>
+#include <QTemporaryDir>
+#include <QFile>
+#include <QTextStream>
+#include <QStandardPaths>
+#include <QMessageBox>
+#include <cmath>
+#include <QMovie>
+#include <QAction>
+
+PreviewWindow::PreviewWindow(QWidget *parent) :
+ QDialog(parent),
+ ui(new Ui::PreviewWindow)
+{
+ QSettings settings("tikzit", "tikzit");
+ ui->setupUi(this);
+
+ QVariant geom = settings.value("geometry-preview");
+
+ if (geom.isValid()) {
+ restoreGeometry(geom.toByteArray());
+ }
+
+ _doc = nullptr;
+
+ _loader = new QLabel(ui->tabWidget->tabBar());
+ _loader->setMinimumSize(QSize(16,16));
+ _loader->setMaximumSize(QSize(16,16));
+ _loader->setAutoFillBackground(false);
+ ui->tabWidget->tabBar()->setTabButton(1, QTabBar::RightSide, _loader);
+
+ connect(ui->tabWidget, SIGNAL(currentChanged(int)),
+ this, SLOT(render()));
+
+ render();
+}
+
+void PreviewWindow::contextMenuEvent(QContextMenuEvent *event)
+{
+ QMenu menu(this);
+ QAction *act;
+
+ act = new QAction("Export Image...");
+ connect(act, SIGNAL(triggered()), this, SLOT(exportImage()));
+ menu.addAction(act);
+
+ act = new QAction("Copy to Clipboard");
+ connect(act, SIGNAL(triggered()), this, SLOT(copyImageToClipboard()));
+ menu.addAction(act);
+
+ menu.exec(event->globalPos());
+}
+
+PdfDocument *PreviewWindow::doc() const
+{
+ return _doc;
+}
+
+PreviewWindow::~PreviewWindow()
+{
+ delete ui;
+}
+
+void PreviewWindow::setPdf(QString file)
+{
+ // use loadFromData to avoid holding a lock on the PDF file in windows
+ //QFile f(file);
+ //f.open(QFile::ReadOnly);
+ //QByteArray data = f.readAll();
+ //f.close();
+ PdfDocument *newDoc = new PdfDocument(file, this);
+
+ if (newDoc->isValid()) {
+ PdfDocument *oldDoc = _doc;
+ _doc = newDoc;
+ if (oldDoc != nullptr) delete oldDoc;
+ render();
+ } else {
+ QMessageBox::warning(nullptr,
+ "Could not read PDF",
+ "Could not read: '" + file + "'.");
+ delete newDoc;
+ }
+}
+
+QPlainTextEdit *PreviewWindow::outputTextEdit()
+{
+ return ui->output;
+}
+
+void PreviewWindow::setStatus(PreviewWindow::Status status)
+{
+ QMovie *oldMovie = _loader->movie();
+ if (status == PreviewWindow::Running) {
+ // loader.gif and loader@2x.gif derived from:
+ // https://commons.wikimedia.org/wiki/Throbbers#/media/File:Linux_Ubuntu_Loader.gif
+ // licensed GNU Free Documentation License v1.2
+ QMovie *movie = new QMovie(
+ (devicePixelRatioF() > 1.0) ? ":images/loader@2x.gif" : ":images/loader.gif",
+ QByteArray(), _loader);
+ _loader->setPixmap(QPixmap());
+ _loader->setMovie(movie);
+ movie->start();
+ } else if (status == PreviewWindow::Success) {
+ _loader->setMovie(nullptr);
+ QIcon accept(":images/dialog-accept.svg");
+ //accept.setDevicePixelRatio(devicePixelRatio());
+ _loader->setPixmap(accept.pixmap(QSize(16,16)));
+ } else if (status == PreviewWindow::Failed) {
+ _loader->setMovie(nullptr);
+ QIcon error(":images/dialog-error.svg");
+ //error.setDevicePixelRatio(devicePixelRatio());
+ _loader->setPixmap(error.pixmap(QSize(16,16)));
+ }
+
+ if (oldMovie != nullptr) oldMovie->deleteLater();
+
+
+ _loader->repaint();
+}
+
+void PreviewWindow::closeEvent(QCloseEvent *e) {
+ QSettings settings("tikzit", "tikzit");
+ settings.setValue("geometry-preview", saveGeometry());
+ QDialog::closeEvent(e);
+}
+
+void PreviewWindow::resizeEvent(QResizeEvent *e) {
+ render();
+ QDialog::resizeEvent(e);
+}
+
+void PreviewWindow::showEvent(QShowEvent *e) {
+ render();
+ QDialog::showEvent(e);
+}
+
+void PreviewWindow::render() {
+ if (_doc != nullptr) {
+ _doc->renderTo(ui->pdf,
+ ui->scrollArea->visibleRegion().boundingRect());
+ ui->pdf->repaint();
+ }
+}
+
+void PreviewWindow::exportImage()
+{
+ QSettings settings("tikzit", "tikzit");
+ if (_doc == nullptr) return;
+ ExportDialog *d = new ExportDialog(this);
+ int ret = d->exec();
+ if (ret == QDialog::Accepted) {
+ bool success;
+ if (d->fileFormat() == ExportDialog::PDF) {
+ success = _doc->exportPdf(d->filePath());
+ } else {
+ success = _doc->exportImage(
+ d->filePath(),
+ (d->fileFormat() == ExportDialog::PNG) ? "PNG" : "JPG",
+ d->size());
+ }
+
+ if (!success) {
+ QMessageBox::warning(this,
+ "Error",
+ "Could not write to: '" + d->filePath() +
+ "'. Check file permissions or choose a new location.");
+ }
+ }
+}
+
+void PreviewWindow::copyImageToClipboard()
+{
+ if (_doc != nullptr) {
+ _doc->copyImageToClipboard(_doc->size() * 4);
+ }
+}
+
+
diff --git a/src/gui/previewwindow.h b/src/gui/previewwindow.h
new file mode 100644
index 0000000..a14303b
--- /dev/null
+++ b/src/gui/previewwindow.h
@@ -0,0 +1,72 @@
+/*
+ TikZiT - a GUI diagram editor for TikZ
+ Copyright (C) 2018 Aleks Kissinger
+
+ This program is free software: you can redistribute it and/or modify
+ it under the terms of the GNU General Public License as published by
+ the Free Software Foundation, either version 3 of the License, or
+ (at your option) any later version.
+
+ This program 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 General Public License for more details.
+
+ You should have received a copy of the GNU General Public License
+ along with this program. If not, see <https://www.gnu.org/licenses/>.
+*/
+
+/*!
+ * Displays a LaTeX-generated PDF preview using Poppler. The right-click
+ * menu has options for exporting to file or clipboard.
+ */
+
+#ifndef PREVIEWWINDOW_H
+#define PREVIEWWINDOW_H
+
+#include "pdfdocument.h"
+
+#include <QDialog>
+#include <QLabel>
+#include <QPlainTextEdit>
+#include <QContextMenuEvent>
+#include <poppler/qt5/poppler-qt5.h>
+
+namespace Ui {
+class PreviewWindow;
+}
+
+class PreviewWindow : public QDialog
+{
+ Q_OBJECT
+
+public:
+ enum Status {
+ Running, Success, Failed
+ };
+ explicit PreviewWindow(QWidget *parent = nullptr);
+ ~PreviewWindow() override;
+ void setPdf(QString file);
+ QString preparePreview(QString tikz);
+ QPlainTextEdit *outputTextEdit();
+ void setStatus(Status status);
+
+ PdfDocument *doc() const;
+
+public slots:
+ void render();
+ void exportImage();
+ void copyImageToClipboard();
+
+protected:
+ void resizeEvent(QResizeEvent *e) override;
+ void showEvent(QShowEvent *e) override;
+ void closeEvent(QCloseEvent *e) override;
+ void contextMenuEvent(QContextMenuEvent *event) override;
+private:
+ Ui::PreviewWindow *ui;
+ PdfDocument *_doc;
+ QLabel *_loader;
+};
+
+#endif // PREVIEWWINDOW_H
diff --git a/src/gui/previewwindow.ui b/src/gui/previewwindow.ui
new file mode 100644
index 0000000..aa49980
--- /dev/null
+++ b/src/gui/previewwindow.ui
@@ -0,0 +1,107 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<ui version="4.0">
+ <class>PreviewWindow</class>
+ <widget class="QDialog" name="PreviewWindow">
+ <property name="geometry">
+ <rect>
+ <x>0</x>
+ <y>0</y>
+ <width>603</width>
+ <height>480</height>
+ </rect>
+ </property>
+ <property name="windowTitle">
+ <string>Preview</string>
+ </property>
+ <layout class="QVBoxLayout" name="verticalLayout">
+ <property name="leftMargin">
+ <number>3</number>
+ </property>
+ <property name="topMargin">
+ <number>3</number>
+ </property>
+ <property name="rightMargin">
+ <number>3</number>
+ </property>
+ <property name="bottomMargin">
+ <number>3</number>
+ </property>
+ <item>
+ <widget class="QTabWidget" name="tabWidget">
+ <property name="currentIndex">
+ <number>0</number>
+ </property>
+ <property name="documentMode">
+ <bool>true</bool>
+ </property>
+ <property name="tabsClosable">
+ <bool>false</bool>
+ </property>
+ <widget class="QWidget" name="pdfTab">
+ <attribute name="title">
+ <string>PDF</string>
+ </attribute>
+ <layout class="QVBoxLayout" name="verticalLayout_2">
+ <property name="leftMargin">
+ <number>0</number>
+ </property>
+ <property name="topMargin">
+ <number>0</number>
+ </property>
+ <property name="rightMargin">
+ <number>0</number>
+ </property>
+ <property name="bottomMargin">
+ <number>0</number>
+ </property>
+ <item>
+ <widget class="QScrollArea" name="scrollArea">
+ <property name="verticalScrollBarPolicy">
+ <enum>Qt::ScrollBarAlwaysOff</enum>
+ </property>
+ <property name="horizontalScrollBarPolicy">
+ <enum>Qt::ScrollBarAlwaysOff</enum>
+ </property>
+ <property name="widgetResizable">
+ <bool>true</bool>
+ </property>
+ <widget class="QWidget" name="scrollAreaWidgetContents">
+ <property name="geometry">
+ <rect>
+ <x>0</x>
+ <y>0</y>
+ <width>595</width>
+ <height>451</height>
+ </rect>
+ </property>
+ <layout class="QVBoxLayout" name="verticalLayout_4">
+ <item>
+ <widget class="QLabel" name="pdf">
+ <property name="text">
+ <string/>
+ </property>
+ </widget>
+ </item>
+ </layout>
+ </widget>
+ </widget>
+ </item>
+ </layout>
+ </widget>
+ <widget class="QWidget" name="outputTab">
+ <attribute name="title">
+ <string>Output</string>
+ </attribute>
+ <layout class="QVBoxLayout" name="verticalLayout_3">
+ <item>
+ <widget class="QPlainTextEdit" name="output"/>
+ </item>
+ </layout>
+ </widget>
+ </widget>
+ </item>
+ </layout>
+ </widget>
+ <resources/>
+ <connections/>
+</ui>
diff --git a/src/gui/styleeditor.cpp b/src/gui/styleeditor.cpp
index 29192d6..e2ade45 100644
--- a/src/gui/styleeditor.cpp
+++ b/src/gui/styleeditor.cpp
@@ -1,10 +1,30 @@
+/*
+ TikZiT - a GUI diagram editor for TikZ
+ Copyright (C) 2018 Aleks Kissinger
+
+ This program is free software: you can redistribute it and/or modify
+ it under the terms of the GNU General Public License as published by
+ the Free Software Foundation, either version 3 of the License, or
+ (at your option) any later version.
+
+ This program 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 General Public License for more details.
+
+ You should have received a copy of the GNU General Public License
+ along with this program. If not, see <https://www.gnu.org/licenses/>.
+*/
+
#include <QColorDialog>
#include <QDebug>
#include <QMessageBox>
#include "tikzit.h"
#include "styleeditor.h"
+#include "delimitedstringvalidator.h"
#include "ui_styleeditor.h"
+#include "delimitedstringitemdelegate.h"
StyleEditor::StyleEditor(QWidget *parent) :
QMainWindow(parent),
@@ -18,6 +38,14 @@ StyleEditor::StyleEditor(QWidget *parent) :
ui->leftArrow << ui->rightArrow <<
ui->properties;
+ DelimitedStringValidator *v = new DelimitedStringValidator(this);
+ ui->name->setValidator(v);
+ ui->category->lineEdit()->setValidator(v);
+ ui->shape->lineEdit()->setValidator(v);
+
+ DelimitedStringItemDelegate *delegate = new DelimitedStringItemDelegate(ui->properties);
+ ui->properties->setItemDelegate(delegate);
+
setWindowIcon(QIcon(":/images/tikzit.png"));
_styles = nullptr;
_activeStyle = nullptr;
@@ -44,40 +72,6 @@ StyleEditor::StyleEditor(QWidget *parent) :
SIGNAL(currentIndexChanged(int)),
this, SLOT(shapeChanged()));
- // setup the color dialog to display only the named colors that tikzit/xcolor knows
- // about as "standard colors".
- for (int i = 0; i < 48; ++i) {
- QColorDialog::setStandardColor(i, QColor(Qt::white));
- }
-
- // grayscale in column 1
- int pos = 0;
- for (int i=0; i < 5; ++i) {
- QColorDialog::setStandardColor(pos, tikzit->colorByIndex(i));
- pos += 1;
- }
-
- // rainbow in column 2
- pos = 6;
- for (int i=5; i < 11; ++i) {
- QColorDialog::setStandardColor(pos, tikzit->colorByIndex(i));
- pos += 1;
- }
-
- // brown/green/teal spectrum in column 3
- pos = 12;
- for (int i=11; i < 16; ++i) {
- QColorDialog::setStandardColor(pos, tikzit->colorByIndex(i));
- pos += 1;
- }
-
- // pinks in column 4
- pos = 18;
- for (int i=16; i < 19; ++i) {
- QColorDialog::setStandardColor(pos, tikzit->colorByIndex(i));
- pos += 1;
- }
-
refreshDisplay();
}
diff --git a/src/gui/styleeditor.h b/src/gui/styleeditor.h
index 4bae7db..2c35d56 100644
--- a/src/gui/styleeditor.h
+++ b/src/gui/styleeditor.h
@@ -1,3 +1,25 @@
+/*
+ TikZiT - a GUI diagram editor for TikZ
+ Copyright (C) 2018 Aleks Kissinger
+
+ This program is free software: you can redistribute it and/or modify
+ it under the terms of the GNU General Public License as published by
+ the Free Software Foundation, either version 3 of the License, or
+ (at your option) any later version.
+
+ This program 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 General Public License for more details.
+
+ You should have received a copy of the GNU General Public License
+ along with this program. If not, see <https://www.gnu.org/licenses/>.
+*/
+
+/*!
+ * A GUI editor for .tikzstyles files.
+ */
+
#ifndef STYLEEDITOR_H
#define STYLEEDITOR_H
@@ -17,8 +39,8 @@ class StyleEditor : public QMainWindow
Q_OBJECT
public:
- explicit StyleEditor(QWidget *parent = 0);
- ~StyleEditor();
+ explicit StyleEditor(QWidget *parent = nullptr);
+ ~StyleEditor() override;
void open();
void save();
diff --git a/src/gui/tikzscene.cpp b/src/gui/tikzscene.cpp
index c061221..31d5bf6 100644
--- a/src/gui/tikzscene.cpp
+++ b/src/gui/tikzscene.cpp
@@ -28,14 +28,15 @@
#include <QClipboard>
#include <QInputDialog>
#include <cmath>
+#include <delimitedstringvalidator.h>
TikzScene::TikzScene(TikzDocument *tikzDocument, ToolPalette *tools,
StylePalette *styles, QObject *parent) :
QGraphicsScene(parent), _tikzDocument(tikzDocument), _tools(tools), _styles(styles)
{
- _modifyEdgeItem = 0;
- _edgeStartNodeItem = 0;
+ _modifyEdgeItem = nullptr;
+ _edgeStartNodeItem = nullptr;
_drawEdgeItem = new QGraphicsLineItem();
_rubberBandItem = new QGraphicsRectItem();
_enabled = true;
@@ -43,7 +44,7 @@ TikzScene::TikzScene(TikzDocument *tikzDocument, ToolPalette *tools,
setSceneRect(-1000,-1000,2000,2000);
QPen pen;
- pen.setColor(QColor::fromRgbF(0.5f, 0.0f, 0.5f));
+ pen.setColor(QColor::fromRgbF(0.5, 0.0, 0.5));
//pen.setWidth(3.0f);
pen.setCosmetic(true);
_drawEdgeItem->setPen(pen);
@@ -51,7 +52,7 @@ TikzScene::TikzScene(TikzDocument *tikzDocument, ToolPalette *tools,
_drawEdgeItem->setVisible(false);
addItem(_drawEdgeItem);
- pen.setColor(QColor::fromRgbF(0.6f, 0.6f, 0.8f));
+ pen.setColor(QColor::fromRgbF(0.6, 0.6, 0.8));
//pen.setWidth(3.0f);
//QVector<qreal> dash;
//dash << 4.0 << 4.0;
@@ -110,7 +111,7 @@ void TikzScene::graphReplaced()
void TikzScene::extendSelectionUp()
{
bool found = false;
- float m = 0.0f;
+ qreal m = 0.0;
foreach (Node *n, getSelectedNodes()) {
if (!found) {
m = n->point().y();
@@ -128,7 +129,7 @@ void TikzScene::extendSelectionUp()
void TikzScene::extendSelectionDown()
{
bool found = false;
- float m = 0.0f;
+ qreal m = 0.0;
foreach (Node *n, getSelectedNodes()) {
if (!found) {
m = n->point().y();
@@ -146,7 +147,7 @@ void TikzScene::extendSelectionDown()
void TikzScene::extendSelectionLeft()
{
bool found = false;
- float m = 0.0f;
+ qreal m = 0.0;
foreach (Node *n, getSelectedNodes()) {
if (!found) {
m = n->point().x();
@@ -164,7 +165,7 @@ void TikzScene::extendSelectionLeft()
void TikzScene::extendSelectionRight()
{
bool found = false;
- float m = 0.0f;
+ qreal m = 0.0;
foreach (Node *n, getSelectedNodes()) {
if (!found) {
m = n->point().x();
@@ -266,7 +267,7 @@ void TikzScene::mousePressEvent(QGraphicsSceneMouseEvent *event)
}
}
- if (_modifyEdgeItem != 0) {
+ if (_modifyEdgeItem != nullptr) {
// store for undo purposes
Edge *e = _modifyEdgeItem->edge();
_oldBend = e->bend();
@@ -337,15 +338,15 @@ void TikzScene::mouseMoveEvent(QGraphicsSceneMouseEvent *event)
switch (_tools->currentTool()) {
case ToolPalette::SELECT:
- if (_modifyEdgeItem != 0) {
+ if (_modifyEdgeItem != nullptr) {
Edge *e = _modifyEdgeItem->edge();
// dragging a control point
QPointF src = toScreen(e->source()->point());
QPointF targ = toScreen(e->target()->point());
- float dx1 = targ.x() - src.x();
- float dy1 = targ.y() - src.y();
- float dx2, dy2;
+ qreal dx1 = targ.x() - src.x();
+ qreal dy1 = targ.y() - src.y();
+ qreal dx2, dy2;
if (_firstControlPoint) {
dx2 = mousePos.x() - src.x();
dy2 = mousePos.y() - src.y();
@@ -354,25 +355,26 @@ void TikzScene::mouseMoveEvent(QGraphicsSceneMouseEvent *event)
dy2 = mousePos.y() - targ.y();
}
- float baseDist = sqrt(dx1*dx1 + dy1*dy1);
- float handleDist = sqrt(dx2*dx2 + dy2*dy2);
- float wcoarseness = 0.1f;
+ qreal baseDist = sqrt(dx1*dx1 + dy1*dy1);
+ qreal handleDist = sqrt(dx2*dx2 + dy2*dy2);
+ qreal wcoarseness = 0.1;
if (!e->isSelfLoop()) {
- if (baseDist != 0) {
+ if (baseDist != 0.0) {
e->setWeight(roundToNearest(wcoarseness, handleDist/baseDist));
} else {
e->setWeight(roundToNearest(wcoarseness, handleDist/GLOBAL_SCALEF));
}
}
- float control_angle = atan2(-dy2, dx2);
+ qreal control_angle = atan2(-dy2, dx2);
int bcoarseness = 15;
+ qreal bcoarsenessi = 1.0/15.0;
if(e->basicBendMode()) {
- float bnd;
- float base_angle = atan2(-dy1, dx1);
+ qreal bnd;
+ qreal base_angle = atan2(-dy1, dx1);
if (_firstControlPoint) {
bnd = base_angle - control_angle;
} else {
@@ -380,12 +382,10 @@ void TikzScene::mouseMoveEvent(QGraphicsSceneMouseEvent *event)
if (bnd > M_PI) bnd -= 2*M_PI;
}
- e->setBend(round(bnd * (180.0f / M_PI) * (1.0f / (float)bcoarseness)) * bcoarseness);
+ e->setBend(static_cast<int>(round(bnd * (180.0 / M_PI) * bcoarsenessi)) * bcoarseness);
} else {
- int bnd = round(control_angle * (180.0f / M_PI) *
- (1.0f / (float)bcoarseness)) *
- bcoarseness;
+ int bnd = static_cast<int>(round(control_angle * (180.0 / M_PI) * bcoarsenessi)) * bcoarseness;
if (_firstControlPoint) {
// TODO: enable moving both control points
// if ([theEvent modifierFlags] & NSAlternateKeyMask) {
@@ -428,7 +428,7 @@ void TikzScene::mouseMoveEvent(QGraphicsSceneMouseEvent *event)
NodeItem *ni = _nodeItems[n];
// in (rare) cases, the graph can change while we are dragging
- if (ni != 0) {
+ if (ni != nullptr) {
ni->setPos(toScreen(_oldNodePositions[n]) + shift);
ni->writePos();
}
@@ -454,7 +454,7 @@ void TikzScene::mouseMoveEvent(QGraphicsSceneMouseEvent *event)
break;
case ToolPalette::EDGE:
if (_drawEdgeItem->isVisible()) {
- _edgeEndNodeItem = 0;
+ _edgeEndNodeItem = nullptr;
foreach (QGraphicsItem *gi, items(mousePos)) {
if (NodeItem *ni = dynamic_cast<NodeItem*>(gi)){
_edgeEndNodeItem = ni;
@@ -462,7 +462,7 @@ void TikzScene::mouseMoveEvent(QGraphicsSceneMouseEvent *event)
}
}
QPointF p1 = _drawEdgeItem->line().p1();
- QPointF p2 = (_edgeEndNodeItem != 0) ? toScreen(_edgeEndNodeItem->node()->point()) : mousePos;
+ QPointF p2 = (_edgeEndNodeItem != nullptr) ? toScreen(_edgeEndNodeItem->node()->point()) : mousePos;
QLineF line(p1, p2);
_drawEdgeItem->setLine(line);
@@ -482,11 +482,11 @@ void TikzScene::mouseReleaseEvent(QGraphicsSceneMouseEvent *event)
switch (_tools->currentTool()) {
case ToolPalette::SELECT:
- if (_modifyEdgeItem != 0) {
+ if (_modifyEdgeItem != nullptr) {
// finished dragging a control point
Edge *e = _modifyEdgeItem->edge();
- if (_oldWeight != e->weight() ||
+ if (!almostEqual(_oldWeight, e->weight()) ||
_oldBend != e->bend() ||
_oldInAngle != e->inAngle() ||
_oldOutAngle != e->outAngle())
@@ -495,7 +495,7 @@ void TikzScene::mouseReleaseEvent(QGraphicsSceneMouseEvent *event)
_tikzDocument->undoStack()->push(cmd);
}
- _modifyEdgeItem = 0;
+ _modifyEdgeItem = nullptr;
} else {
// otherwise, process mouse move normally
QGraphicsScene::mouseReleaseEvent(event);
@@ -517,7 +517,7 @@ void TikzScene::mouseReleaseEvent(QGraphicsSceneMouseEvent *event)
QPointF shift = mousePos - _mouseDownPos;
shift = QPointF(round(shift.x()/GRID_SEP)*GRID_SEP, round(shift.y()/GRID_SEP)*GRID_SEP);
- if (shift.x() != 0 || shift.y() != 0) {
+ if (shift.x() != 0.0 || shift.y() != 0.0) {
QMap<Node*,QPointF> newNodePositions;
foreach (QGraphicsItem *gi, selectedItems()) {
@@ -557,14 +557,14 @@ void TikzScene::mouseReleaseEvent(QGraphicsSceneMouseEvent *event)
break;
case ToolPalette::EDGE:
// add an edge
- if (_edgeStartNodeItem != 0 && _edgeEndNodeItem != 0) {
+ if (_edgeStartNodeItem != nullptr && _edgeEndNodeItem != nullptr) {
Edge *e = new Edge(_edgeStartNodeItem->node(), _edgeEndNodeItem->node(), _tikzDocument);
e->setStyleName(_styles->activeEdgeStyleName());
AddEdgeCommand *cmd = new AddEdgeCommand(this, e);
_tikzDocument->undoStack()->push(cmd);
}
- _edgeStartNodeItem = 0;
- _edgeEndNodeItem = 0;
+ _edgeStartNodeItem = nullptr;
+ _edgeEndNodeItem = nullptr;
_drawEdgeItem->setVisible(false);
break;
case ToolPalette::CROP:
@@ -613,19 +613,19 @@ void TikzScene::keyPressEvent(QKeyEvent *event)
if (event->modifiers() & Qt::ControlModifier) {
QPointF delta(0,0);
- float shift = (event->modifiers() & Qt::ShiftModifier) ? 1.0f : 10.0f;
+ qreal shift = (event->modifiers() & Qt::ShiftModifier) ? 1.0 : 10.0;
switch(event->key()) {
case Qt::Key_Left:
- delta.setX(-0.025f * shift);
+ delta.setX(-0.025 * shift);
break;
case Qt::Key_Right:
- delta.setX(0.025f * shift);
+ delta.setX(0.025 * shift);
break;
case Qt::Key_Up:
- delta.setY(0.025f * shift);
+ delta.setY(0.025 * shift);
break;
case Qt::Key_Down:
- delta.setY(-0.025f * shift);
+ delta.setY(-0.025 * shift);
break;
}
@@ -665,16 +665,23 @@ void TikzScene::mouseDoubleClickEvent(QGraphicsSceneMouseEvent *event)
}
break;
} else if (NodeItem *ni = dynamic_cast<NodeItem*>(it)) {
- bool ok;
- QString newLabel = QInputDialog::getText(views()[0], tr("Node label"),
- tr("Label:"), QLineEdit::Normal,
- ni->node()->label(), &ok);
- if (ok) {
+ QInputDialog *d = new QInputDialog(views()[0]);
+ d->setLabelText(tr("Label:"));
+ d->setTextValue(ni->node()->label());
+ d->setWindowTitle(tr("Node label"));
+
+ if (QLineEdit *le = d->findChild<QLineEdit*>()) {
+ le->setValidator(new DelimitedStringValidator(le));
+ }
+
+ if (d->exec()) {
QMap<Node*,QString> oldLabels;
oldLabels.insert(ni->node(), ni->node()->label());
- ChangeLabelCommand *cmd = new ChangeLabelCommand(this, oldLabels, newLabel);
+ ChangeLabelCommand *cmd = new ChangeLabelCommand(this, oldLabels, d->textValue());
_tikzDocument->undoStack()->push(cmd);
}
+
+ d->deleteLater();
break;
}
}
@@ -767,7 +774,7 @@ void TikzScene::pasteFromClipboard()
QRectF srcRect = g->realBbox();
QRectF tgtRect = graph()->realBbox();
- QPointF shift(tgtRect.right() - srcRect.left(), 0.0f);
+ QPointF shift(tgtRect.right() - srcRect.left(), 0.0);
if (shift.x() > 0) {
foreach (Node *n, g->nodes()) {
@@ -890,7 +897,7 @@ void TikzScene::refreshAdjacentEdges(QList<Node*> nodes)
EdgeItem *ei = _edgeItems[e];
// the list "nodes" can be out of date, e.g. if the graph changes while dragging
- if (ei != 0) {
+ if (ei != nullptr) {
if (nodes.contains(ei->edge()->source()) || nodes.contains(ei->edge()->target())) {
ei->edge()->updateControls();
ei->readPos();
diff --git a/src/gui/tikzscene.h b/src/gui/tikzscene.h
index 2a3e988..e8ea2c6 100644
--- a/src/gui/tikzscene.h
+++ b/src/gui/tikzscene.h
@@ -44,7 +44,7 @@ class TikzScene : public QGraphicsScene
Q_OBJECT
public:
TikzScene(TikzDocument *tikzDocument, ToolPalette *tools, StylePalette *styles, QObject *parent);
- ~TikzScene();
+ ~TikzScene() override;
Graph *graph();
QMap<Node*,NodeItem*> &nodeItems();
QMap<Edge*,EdgeItem*> &edgeItems();
@@ -108,7 +108,7 @@ private:
bool _draggingNodes;
QMap<Node*,QPointF> _oldNodePositions;
- float _oldWeight;
+ qreal _oldWeight;
int _oldBend;
int _oldInAngle;
int _oldOutAngle;
diff --git a/src/gui/tikzview.cpp b/src/gui/tikzview.cpp
index 52a32cf..5b0f09c 100644
--- a/src/gui/tikzview.cpp
+++ b/src/gui/tikzview.cpp
@@ -21,6 +21,7 @@
#include <QDebug>
#include <QScrollBar>
+#include <QSettings>
TikzView::TikzView(QWidget *parent) : QGraphicsView(parent)
{
@@ -53,6 +54,7 @@ void TikzView::setScene(QGraphicsScene *scene)
void TikzView::drawBackground(QPainter *painter, const QRectF &rect)
{
+ QSettings settings("tikzit", "tikzit");
QGraphicsView::drawBackground(painter, rect);
// draw a gray background if disabled
TikzScene *sc = static_cast<TikzScene*>(scene());
@@ -63,13 +65,13 @@ void TikzView::drawBackground(QPainter *painter, const QRectF &rect)
QPen pen1;
//pen1.setWidthF(0.5);
pen1.setCosmetic(true);
- pen1.setColor(QColor(250,250,255));
+ pen1.setColor(settings.value("grid-color-minor", QColor(250,250,255)).value<QColor>());
QPen pen2 = pen1;
- pen2.setColor(QColor(240,240,250));
+ pen2.setColor(settings.value("grid-color-major", QColor(240,240,250)).value<QColor>());
QPen pen3 = pen1;
- pen3.setColor(QColor(220,220,240));
+ pen3.setColor(settings.value("grid-color-axes", QColor(220,220,240)).value<QColor>());
painter->setPen(pen1);
diff --git a/src/gui/undocommands.cpp b/src/gui/undocommands.cpp
index f713582..8a00536 100644
--- a/src/gui/undocommands.cpp
+++ b/src/gui/undocommands.cpp
@@ -80,7 +80,7 @@ void MoveCommand::redo()
}
EdgeBendCommand::EdgeBendCommand(TikzScene *scene, Edge *edge,
- float oldWeight, int oldBend,
+ qreal oldWeight, int oldBend,
int oldInAngle, int oldOutAngle, QUndoCommand *parent) :
GraphUpdateCommand(scene, parent),
_edge(edge),
@@ -405,7 +405,7 @@ void ChangeLabelCommand::undo()
foreach (Node *n, _oldLabels.keys()) {
n->setLabel(_oldLabels[n]);
NodeItem *ni = _scene->nodeItems()[n];
- if (ni != 0) ni->updateBounds();
+ if (ni != nullptr) ni->updateBounds();
}
GraphUpdateCommand::undo();
@@ -416,7 +416,7 @@ void ChangeLabelCommand::redo()
foreach (Node *n, _oldLabels.keys()) {
n->setLabel(_newLabel);
NodeItem *ni = _scene->nodeItems()[n];
- if (ni != 0) ni->updateBounds();
+ if (ni != nullptr) ni->updateBounds();
}
GraphUpdateCommand::redo();
diff --git a/src/gui/undocommands.h b/src/gui/undocommands.h
index dc60549..ff51c90 100644
--- a/src/gui/undocommands.h
+++ b/src/gui/undocommands.h
@@ -36,7 +36,7 @@
class GraphUpdateCommand : public QUndoCommand {
public:
explicit GraphUpdateCommand(TikzScene *scene,
- QUndoCommand *parent = 0);
+ QUndoCommand *parent = nullptr);
void undo() override;
void redo() override;
protected:
@@ -49,7 +49,7 @@ public:
explicit MoveCommand(TikzScene *scene,
QMap<Node*,QPointF> oldNodePositions,
QMap<Node*,QPointF> newNodePositions,
- QUndoCommand *parent = 0);
+ QUndoCommand *parent = nullptr);
void undo() override;
void redo() override;
private:
@@ -61,18 +61,18 @@ class EdgeBendCommand : public GraphUpdateCommand
{
public:
explicit EdgeBendCommand(TikzScene *scene, Edge *edge,
- float oldWeight, int oldBend,
+ qreal oldWeight, int oldBend,
int oldInAngle, int oldOutAngle,
- QUndoCommand *parent = 0);
+ QUndoCommand *parent = nullptr);
void undo() override;
void redo() override;
private:
Edge *_edge;
- float _oldWeight;
+ qreal _oldWeight;
int _oldBend;
int _oldInAngle;
int _oldOutAngle;
- float _newWeight;
+ qreal _newWeight;
int _newBend;
int _newInAngle;
int _newOutAngle;
@@ -85,7 +85,7 @@ public:
QMap<int,Node*> deleteNodes,
QMap<int,Edge*> deleteEdges,
QSet<Edge*> selEdges,
- QUndoCommand *parent = 0);
+ QUndoCommand *parent = nullptr);
void undo() override;
void redo() override;
private:
@@ -98,7 +98,7 @@ class AddNodeCommand : public GraphUpdateCommand
{
public:
explicit AddNodeCommand(TikzScene *scene, Node *node, QRectF newBounds,
- QUndoCommand *parent = 0);
+ QUndoCommand *parent = nullptr);
void undo() override;
void redo() override;
private:
@@ -110,7 +110,7 @@ private:
class AddEdgeCommand : public GraphUpdateCommand
{
public:
- explicit AddEdgeCommand(TikzScene *scene, Edge *edge, QUndoCommand *parent = 0);
+ explicit AddEdgeCommand(TikzScene *scene, Edge *edge, QUndoCommand *parent = nullptr);
void undo() override;
void redo() override;
private:
@@ -120,7 +120,7 @@ private:
class ChangeEdgeModeCommand : public GraphUpdateCommand
{
public:
- explicit ChangeEdgeModeCommand(TikzScene *scene, Edge *edge, QUndoCommand *parent = 0);
+ explicit ChangeEdgeModeCommand(TikzScene *scene, Edge *edge, QUndoCommand *parent = nullptr);
void undo() override;
void redo() override;
private:
@@ -130,7 +130,7 @@ private:
class ApplyStyleToNodesCommand : public GraphUpdateCommand
{
public:
- explicit ApplyStyleToNodesCommand(TikzScene *scene, QString style, QUndoCommand *parent = 0);
+ explicit ApplyStyleToNodesCommand(TikzScene *scene, QString style, QUndoCommand *parent = nullptr);
void undo() override;
void redo() override;
private:
@@ -141,7 +141,7 @@ private:
class ApplyStyleToEdgesCommand : public GraphUpdateCommand
{
public:
- explicit ApplyStyleToEdgesCommand(TikzScene *scene, QString style, QUndoCommand *parent = 0);
+ explicit ApplyStyleToEdgesCommand(TikzScene *scene, QString style, QUndoCommand *parent = nullptr);
void undo() override;
void redo() override;
private:
@@ -152,7 +152,7 @@ private:
class PasteCommand : public GraphUpdateCommand
{
public:
- explicit PasteCommand(TikzScene *scene, Graph *graph, QUndoCommand *parent = 0);
+ explicit PasteCommand(TikzScene *scene, Graph *graph, QUndoCommand *parent = nullptr);
void undo() override;
void redo() override;
private:
@@ -167,7 +167,7 @@ public:
explicit ChangeLabelCommand(TikzScene *scene,
QMap<Node*,QString> oldLabels,
QString newLabel,
- QUndoCommand *parent = 0);
+ QUndoCommand *parent = nullptr);
void undo() override;
void redo() override;
private:
@@ -181,7 +181,7 @@ public:
explicit ReplaceGraphCommand(TikzScene *scene,
Graph *oldGraph,
Graph *newGraph,
- QUndoCommand *parent = 0);
+ QUndoCommand *parent = nullptr);
void undo() override;
void redo() override;
private:
@@ -195,7 +195,7 @@ public:
explicit ReflectNodesCommand(TikzScene *scene,
QSet<Node*> nodes,
bool horizontal,
- QUndoCommand *parent = 0);
+ QUndoCommand *parent = nullptr);
void undo() override;
void redo() override;
private:
@@ -209,7 +209,7 @@ public:
explicit RotateNodesCommand(TikzScene *scene,
QSet<Node*> nodes,
bool clockwise,
- QUndoCommand *parent = 0);
+ QUndoCommand *parent = nullptr);
void undo() override;
void redo() override;
private:
@@ -225,7 +225,7 @@ public:
const QVector<Node*> &newNodeOrder,
const QVector<Edge*> &oldEdgeOrder,
const QVector<Edge*> &newEdgeOrder,
- QUndoCommand *parent = 0);
+ QUndoCommand *parent = nullptr);
void undo() override;
void redo() override;
private: