GUI: make it possible to save changes in library editor

This commit is contained in:
Daniel Marjamäki 2015-08-23 12:49:51 +02:00
parent 1b29a99e45
commit ea7209e669
3 changed files with 182 additions and 30 deletions

View File

@ -25,6 +25,7 @@
#include <QDomNodeList>
#include <QSettings>
#include <QFileDialog>
#include <QTextStream>
const unsigned int LibraryDialog::Function::Arg::ANY = ~0U;
@ -35,6 +36,7 @@ LibraryDialog::LibraryDialog(QWidget *parent) :
ui(new Ui::LibraryDialog)
{
ui->setupUi(this);
ui->buttonSave->setEnabled(false);
}
LibraryDialog::~LibraryDialog()
@ -42,14 +44,6 @@ LibraryDialog::~LibraryDialog()
delete ui;
}
void LibraryDialog::updateui()
{
ui->functions->clear();
for (const struct Function &function : functions) {
ui->functions->addItem(function.name);
}
}
static LibraryDialog::Function::Arg loadFunctionArg(const QDomElement &functionArgElement)
{
LibraryDialog::Function::Arg arg;
@ -141,10 +135,86 @@ void LibraryDialog::openCfg()
QFile file(selectedFile);
if (file.open(QIODevice::ReadOnly | QIODevice::Text)) {
loadFile(file);
updateui();
mFileName = selectedFile;
ui->buttonSave->setEnabled(false);
ui->functions->clear();
foreach (const struct Function &function, functions)
ui->functions->addItem(function.name);
}
}
}
static QDomElement FunctionElement(QDomDocument &doc, const LibraryDialog::Function &function)
{
QDomElement functionElement = doc.createElement("function");
functionElement.setAttribute("name", function.name);
if (!function.noreturn) {
QDomElement e = doc.createElement("noreturn");
e.appendChild(doc.createTextNode("false"));
functionElement.appendChild(e);
}
if (function.useretval)
functionElement.appendChild(doc.createElement("useretval"));
if (function.leakignore)
functionElement.appendChild(doc.createElement("leak-ignore"));
// Argument info..
foreach (const LibraryDialog::Function::Arg &arg, function.args) {
QDomElement argElement = doc.createElement("arg");
functionElement.appendChild(argElement);
if (arg.nr == LibraryDialog::Function::Arg::ANY)
argElement.setAttribute("nr", "any");
else
argElement.setAttribute("nr", arg.nr);
if (arg.notbool)
argElement.appendChild(doc.createElement("not-bool"));
if (arg.notnull)
argElement.appendChild(doc.createElement("not-null"));
if (arg.notuninit)
argElement.appendChild(doc.createElement("not-uninit"));
if (arg.strz)
argElement.appendChild(doc.createElement("strz"));
if (arg.formatstr)
argElement.appendChild(doc.createElement("formatstr"));
if (!arg.valid.isEmpty()) {
QDomElement e = doc.createElement("valid");
e.appendChild(doc.createTextNode(arg.valid));
argElement.appendChild(e);
}
if (!arg.minsize.type.isEmpty()) {
QDomElement e = doc.createElement("minsize");
e.setAttribute("type", arg.minsize.type);
e.setAttribute("arg", arg.minsize.arg);
if (!arg.minsize.arg2.isEmpty())
e.setAttribute("arg2", arg.minsize.arg2);
argElement.appendChild(e);
}
}
return functionElement;
}
void LibraryDialog::saveCfg()
{
QDomDocument doc;
QDomElement root = doc.createElement("def");
doc.appendChild(root);
root.setAttribute("format","2");
foreach (const Function &function, functions) {
root.appendChild(FunctionElement(doc, function));
}
QFile file(mFileName);
if (file.open(QIODevice::WriteOnly | QIODevice::Text)) {
QTextStream ts( &file );
ts << doc.toString();
ui->buttonSave->setEnabled(false);
}
}
void LibraryDialog::selectFunction(int row)
@ -154,16 +224,29 @@ void LibraryDialog::selectFunction(int row)
ui->useretval->setChecked(function.useretval);
ui->leakignore->setChecked(function.leakignore);
ui->arguments->clear();
for (const Function::Arg &arg : function.args) {
foreach (const Function::Arg &arg, function.args) {
QString s("arg");
if (arg.nr != Function::Arg::ANY)
s += QString::number(arg.nr);
if (arg.formatstr)
s += " formatstr";
else if (!arg.strz)
else if (arg.strz)
s += " strz";
else if (!arg.valid.isNull())
s += " " + arg.valid;
ui->arguments->addItem(s);
}
}
void LibraryDialog::changeFunction()
{
foreach (const QListWidgetItem *item, ui->functions->selectedItems())
{
Function &function = functions[ui->functions->row(item)];
function.noreturn = !ui->functionreturn->isChecked();
function.useretval = ui->useretval->isChecked();
function.leakignore = ui->leakignore->isChecked();
}
ui->buttonSave->setEnabled(true);
}

View File

@ -34,7 +34,7 @@ public:
~LibraryDialog();
struct Function {
Function() : noreturn(false), gccPure(false), gccConst(false),
Function() : noreturn(true), gccPure(false), gccConst(false),
leakignore(false), useretval(false) {
}
@ -73,7 +73,9 @@ public:
private slots:
void openCfg();
void saveCfg();
void selectFunction(int row);
void changeFunction();
private:
Ui::LibraryDialog *ui;
@ -81,6 +83,7 @@ private:
void updateui();
bool loadFile(QFile &file);
QList<struct Function> functions;
QString mFileName;
};
#endif // LIBRARYDIALOG_H

View File

@ -14,28 +14,22 @@
<string>Library Editor</string>
</property>
<layout class="QVBoxLayout" name="verticalLayout_3">
<item>
<widget class="QLabel" name="label">
<property name="autoFillBackground">
<bool>false</bool>
</property>
<property name="styleSheet">
<string notr="true">QLabel { background-color : red; color : blue; }</string>
</property>
<property name="text">
<string>EXPERIMENTAL</string>
</property>
</widget>
</item>
<item>
<layout class="QHBoxLayout" name="horizontalLayout_2">
<item>
<widget class="QPushButton" name="pushButton">
<widget class="QPushButton" name="buttonOpen">
<property name="text">
<string>Open</string>
</property>
</widget>
</item>
<item>
<widget class="QPushButton" name="buttonSave">
<property name="text">
<string>Save</string>
</property>
</widget>
</item>
<item>
<spacer name="horizontalSpacer">
<property name="orientation">
@ -64,8 +58,14 @@
</item>
<item>
<widget class="QListWidget" name="functions">
<property name="editTriggers">
<set>QAbstractItemView::NoEditTriggers</set>
</property>
<property name="selectionMode">
<enum>QAbstractItemView::SingleSelection</enum>
<enum>QAbstractItemView::ExtendedSelection</enum>
</property>
<property name="selectionBehavior">
<enum>QAbstractItemView::SelectRows</enum>
</property>
</widget>
</item>
@ -142,14 +142,14 @@
</hints>
</connection>
<connection>
<sender>pushButton</sender>
<sender>buttonOpen</sender>
<signal>clicked()</signal>
<receiver>LibraryDialog</receiver>
<slot>openCfg()</slot>
<hints>
<hint type="sourcelabel">
<x>56</x>
<y>36</y>
<x>61</x>
<y>27</y>
</hint>
<hint type="destinationlabel">
<x>72</x>
@ -157,9 +157,75 @@
</hint>
</hints>
</connection>
<connection>
<sender>functionreturn</sender>
<signal>clicked()</signal>
<receiver>LibraryDialog</receiver>
<slot>changeFunction()</slot>
<hints>
<hint type="sourcelabel">
<x>327</x>
<y>45</y>
</hint>
<hint type="destinationlabel">
<x>353</x>
<y>2</y>
</hint>
</hints>
</connection>
<connection>
<sender>useretval</sender>
<signal>clicked()</signal>
<receiver>LibraryDialog</receiver>
<slot>changeFunction()</slot>
<hints>
<hint type="sourcelabel">
<x>372</x>
<y>69</y>
</hint>
<hint type="destinationlabel">
<x>475</x>
<y>5</y>
</hint>
</hints>
</connection>
<connection>
<sender>leakignore</sender>
<signal>clicked()</signal>
<receiver>LibraryDialog</receiver>
<slot>changeFunction()</slot>
<hints>
<hint type="sourcelabel">
<x>419</x>
<y>99</y>
</hint>
<hint type="destinationlabel">
<x>319</x>
<y>3</y>
</hint>
</hints>
</connection>
<connection>
<sender>buttonSave</sender>
<signal>clicked()</signal>
<receiver>LibraryDialog</receiver>
<slot>saveCfg()</slot>
<hints>
<hint type="sourcelabel">
<x>102</x>
<y>9</y>
</hint>
<hint type="destinationlabel">
<x>115</x>
<y>1</y>
</hint>
</hints>
</connection>
</connections>
<slots>
<slot>selectFunction(int)</slot>
<slot>openCfg()</slot>
<slot>changeFunction()</slot>
<slot>saveCfg()</slot>
</slots>
</ui>