aboutsummaryrefslogtreecommitdiffstats
path: root/tests/lib/unit++/gui.cc
diff options
context:
space:
mode:
Diffstat (limited to 'tests/lib/unit++/gui.cc')
-rw-r--r--tests/lib/unit++/gui.cc313
1 files changed, 313 insertions, 0 deletions
diff --git a/tests/lib/unit++/gui.cc b/tests/lib/unit++/gui.cc
new file mode 100644
index 00000000..6344b5e8
--- /dev/null
+++ b/tests/lib/unit++/gui.cc
@@ -0,0 +1,313 @@
+#include <algorithm>
+#include "gui.h"
+#include "unit++.h"
+#ifdef HAVE_SSTREAM
+#include <sstream>
+#endif
+using namespace unitpp;
+using namespace std;
+
+#ifdef GUI
+static const char* const img_error[] = {
+"14 14 2 1",
+". c #ff0000",
+"# c #ffffff",
+"...########...",
+"....######....",
+".....####.....",
+"#.....##.....#",
+"##..........##",
+"###........###",
+"####......####",
+"####......####",
+"###........###",
+"##..........##",
+"#.....##.....#",
+".....####.....",
+"....######....",
+"...########..."};
+
+static const char* const img_fail[] = {
+"14 14 2 1",
+"# c #ff0000",
+". c #ffffff",
+"..............",
+".##........##.",
+".###......###.",
+"..###....###..",
+"...###..###...",
+"....######....",
+".....####.....",
+".....####.....",
+"....######....",
+"...###..###...",
+"..###....###..",
+".###......###.",
+".##........##.",
+".............."};
+
+static const char* const img_ok[] = {
+"14 14 3 1",
+"# c #00ff00",
+"a c #00ff6a",
+". c #ffffff",
+"..........###.",
+".........###..",
+"........#a#...",
+"........aa#...",
+".......#aa....",
+".......#a.....",
+"......#aa.....",
+"#.....aa#.....",
+"###..#a#......",
+".##.##a.......",
+"..#aaa#.......",
+"...#aa#.......",
+"....##........",
+".....#........"};
+
+static const char* const img_empty[] = {
+"14 14 2 1",
+". c #f0f0f0",
+"# c #ffffff",
+"..............",
+".############.",
+".############.",
+".############.",
+".############.",
+".############.",
+".############.",
+".############.",
+".############.",
+".############.",
+".############.",
+".############.",
+".############.",
+".............."};
+
+
+cnt_item::cnt_item(QWidget* par, const QString& txt, const QColor& col,
+ const char* name)
+ : QHBox(par, name), v(0)
+{
+ setSpacing(3);
+ setMargin(5);
+ val = new QLabel("0", this);
+ val->setAlignment(QLabel::AlignVCenter | QLabel::AlignRight);
+ QPalette pal(val->palette());
+ QColorGroup cg(pal.active());
+ cg.setColor(QColorGroup::Foreground, col);
+ pal.setActive(cg);
+ val->setPalette(pal);
+ label = new QLabel(txt, this);
+}
+void cnt_item::value(int iv)
+{
+ v = iv;
+ val->setNum(v);
+}
+void cnt_item::inc()
+{
+ value(v+1);
+}
+
+cnt_line::cnt_line(const QString& txt, QWidget* par, const char* name)
+ : QHBox(par, name)
+{
+ label = new QLabel(txt, this);
+ QFont font(label->font());
+ font.setBold(true);
+ label->setFont(font);
+ cnts[0] = new cnt_item(this, "Total");
+ cnts[1] = new cnt_item(this, "OK", green);
+ cnts[2] = new cnt_item(this, "Fail", red);
+ cnts[3] = new cnt_item(this, "Error", red);
+ setSizePolicy(QSizePolicy(QSizePolicy::Preferred, QSizePolicy::Preferred));
+}
+
+void cnt_line::max(int m) { cnts[id_max]->value(m); }
+void cnt_line::inc_ok() { cnts[id_ok]->inc(); }
+void cnt_line::inc_fail() { cnts[id_fail]->inc(); }
+void cnt_line::inc_error() { cnts[id_error]->inc(); }
+void cnt_line::reset()
+{
+ for (int i = id_ok; i < n_id; ++i)
+ cnts[i]->value(0);
+}
+
+res_stack::res_stack(const QString& txt, QWidget* par, const char* name)
+ : QVBox(par, name)
+{
+ cnts = new cnt_line(txt, this, name);
+ bar = new QProgressBar(this);
+ setSizePolicy(QSizePolicy(QSizePolicy::Preferred, QSizePolicy::Preferred));
+}
+void res_stack::max(int v)
+{
+ cnts->max(v);
+ bar->setTotalSteps(v);
+}
+void res_stack::inc_progress(bool err)
+{
+ QPalette pal(bar->palette());
+ QColorGroup cg(pal.active());
+ QColor red(255,0,0);
+ QColor green(0,244,0);
+ cg.setColor(QColorGroup::Highlight, err ? red : green);
+ cg.setColor(QColorGroup::HighlightedText, black);
+ pal.setActive(cg);
+ pal.setInactive(cg);
+ pal.setDisabled(cg);
+ bar->setPalette(pal);
+ bar->setProgress(bar->progress()+1);
+}
+void res_stack::reset() {
+ cnts->reset();
+ bar->setProgress(0);
+}
+void res_stack::inc_ok() { cnts->inc_ok(); inc_progress(false); }
+void res_stack::inc_fail() { cnts->inc_fail(); inc_progress(true); }
+void res_stack::inc_error() { cnts->inc_error(); inc_progress(true); }
+
+QHBox* behave(QHBox* box, bool x_expand, bool y_expand)
+{
+ box->setSizePolicy(QSizePolicy(
+ x_expand ? QSizePolicy::Preferred : QSizePolicy::Maximum,
+ y_expand ? QSizePolicy::Preferred : QSizePolicy::Maximum));
+ box->setFrameShape(QFrame::StyledPanel);
+ box->setFrameShadow(QFrame::Raised);
+ box->setMargin(11);
+ box->setSpacing(6);
+ return box;
+}
+
+void node::setImg()
+{
+ static QPixmap i_emp((const char**)img_empty);
+ static QPixmap i_ok((const char**)img_ok);
+ static QPixmap i_fail((const char**)img_fail);
+ static QPixmap i_err((const char**)img_error);
+ static QPixmap* imgs[] = { &i_emp, &i_ok, &i_fail, &i_err };
+ item->setPixmap(0, *(imgs[st]));
+ if (st > is_ok)
+ for (QListViewItem* ip = item; ip != 0; ip = ip->parent())
+ ip->setOpen(true);
+};
+
+node::node(suite_node* par, test& t)
+ : item(new QListViewItem(par->lvi(), t.name().c_str())), t(t), st(none)
+{
+ par->add_child(this);
+ setImg();
+}
+node::node(gui* gp, test& t)
+ : item(new QListViewItem(gp->test_tree(), t.name().c_str())), t(t), st(none)
+{
+ setImg();
+ item->setOpen(true);
+}
+void node::run()
+{
+ for (QListViewItem* ip=item->firstChild(); ip != 0; ip=item->firstChild())
+ delete ip;
+ try {
+ t();
+ status(is_ok);
+ emit ok();
+ } catch (assertion_error& e) {
+ status(is_fail);
+ show_error(e);
+ emit fail();
+ } catch (exception& e) {
+ status(is_error);
+ show_error(e.what());
+ emit error();
+ } catch (...) {
+ status(is_error);
+ show_error("unknown ... exception");
+ emit error();
+ }
+}
+void node::show_error(assertion_error& e)
+{
+#ifdef HAVE_SSTREAM
+ ostringstream oss;
+ oss << e;
+ show_error(oss.str().c_str());
+#else
+ show_error(e.what()); // not well, but some sign
+#endif
+}
+void node::show_error(const char* msg)
+{
+ QListViewItem* elvi = new QListViewItem(item, msg);
+ elvi->setSelectable(false);
+}
+suite_node::suite_node(suite_node* par, suite& t) : node(par, t) { }
+suite_node::suite_node(gui* par, suite& t) : node(par, t) { }
+void suite_node::run()
+{
+ status(is_ok);
+ for (cctyp::iterator p = cc.begin(); p != cc.end(); ++p) {
+ (*p)->run();
+ status(max(status(), (*p)->status()));
+ }
+ switch (status()) {
+ case is_ok: emit ok(); break;
+ case is_fail: emit fail(); break;
+ case is_error: emit error(); break;
+ }
+}
+gui::gui(QApplication& app, QWidget* par, const char* name)
+ : QVBox(par, name), app(app)
+{
+ setMargin(6);
+ setSpacing(3);
+ tree = new QListView(behave(new QVBox(this), true, true), "tree");
+ tree->addColumn("Test");
+ tree->setFrameShadow(QListView::Sunken);
+ tree->setResizePolicy(QScrollView::Manual);
+ tree->setRootIsDecorated(true);
+ QVBox* f_cnts = new QVBox(this);
+ behave(f_cnts, true, false);
+ suites = new res_stack("Suites", f_cnts);
+ tests = new res_stack("Tests", f_cnts);
+ QHBox* hbox = behave(new QHBox(this), true, false);
+ b_run = new QPushButton("Run", hbox, "run");
+ b_stop = new QPushButton("Stop", hbox, "stop");
+ b_quit = new QPushButton("Quit", hbox, "quit");
+ connect(b_quit, SIGNAL(clicked()), &app, SLOT(quit()));
+ connect(b_run, SIGNAL(clicked()), this, SLOT(run_pressed()));
+ connect(b_stop, SIGNAL(clicked()), this, SLOT(stop_pressed()));
+}
+
+gui::~gui() { }
+
+void gui::processEvents(int t)
+{
+ app.processEvents(t);
+}
+void gui::reset()
+{
+ tests->reset();
+ suites->reset();
+}
+void gui::nconnect(node* n, res_stack* rs)
+{
+ connect(n, SIGNAL(ok()), rs, SLOT(inc_ok()));
+ connect(n, SIGNAL(fail()), rs, SLOT(inc_fail()));
+ connect(n, SIGNAL(error()), rs, SLOT(inc_error()));
+}
+void gui::add_test(node* n)
+{
+ nconnect(n, tests);
+}
+void gui::add_suite(node* n)
+{
+ nconnect(n, suites);
+}
+
+void gui::totSuites(int v) { suites->max(v); }
+void gui::totTests(int v) { tests->max(v); }
+
+#endif