diff options
author | Andreas Stöckel <astoecke@techfak.uni-bielefeld.de> | 2014-03-04 12:59:32 +0000 |
---|---|---|
committer | andreas <andreas@daaaf23c-2e50-4459-9457-1e69db5a47bf> | 2014-03-04 12:59:32 +0000 |
commit | c543117ff43c63a053ea786ed606398ac4687494 (patch) | |
tree | bf13926dff41782831fbf5fc37c274f09f7a0360 /src/gui/components |
added source code
git-svn-id: file:///var/local/svn/basicwriter@12 daaaf23c-2e50-4459-9457-1e69db5a47bf
Diffstat (limited to 'src/gui/components')
-rw-r--r-- | src/gui/components/GridTree.cpp | 95 | ||||
-rw-r--r-- | src/gui/components/GridTree.hpp | 232 | ||||
-rw-r--r-- | src/gui/components/UIGrid.cpp | 81 | ||||
-rw-r--r-- | src/gui/components/UIGrid.hpp | 49 | ||||
-rw-r--r-- | src/gui/components/UIPaneFrame.cpp | 113 | ||||
-rw-r--r-- | src/gui/components/UIPaneFrame.hpp | 50 |
6 files changed, 620 insertions, 0 deletions
diff --git a/src/gui/components/GridTree.cpp b/src/gui/components/GridTree.cpp new file mode 100644 index 0000000..000b859 --- /dev/null +++ b/src/gui/components/GridTree.cpp @@ -0,0 +1,95 @@ +/* + BasicWriter + Copyright (C) 2014 Benjamin Paaßen, Andreas Stöckel + + 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 <http://www.gnu.org/licenses/>. +*/ + +#include "GridTree.hpp" + +#include <iostream> + +namespace uigrid { + +Splitter getSplitter(Orientation orientation, const Rect &r) +{ + switch (orientation) { + case Orientation::vert: + return Splitter(this, Rect(r.x1, r.y2 - ss, r.x2, r.y2), + orientation); + case Orientation::horz: + return Splitter(this, Rect(r.x1, r.y1, r.x2 - ss, r.y2 - ss), + orientation); + default: + return Rect(0, 0, 0, 0); + } +} + +void GridTreeNode::gatherBoundingBoxes(std::vector<FrameArea> *areas, + std::vector<Splitter> *splitters, const Rect &r, + int splitterSize) +{ + const int ss = splitterSize; + const int h = r.h(); + const int w = r.w(); + + // If this node is a leaf, store the area of the frame and the splitter + // positions in the given lists and abort. + if (isLeaf()) { + if (areas) { + areas->push_back(FrameArea(this, r)); + } + if (splitters) { + splitters->push_back(getSplitter(Orientation::vert, r)); + splitters->push_back(getSplitter(Orientation::horz, r)); + } + return; + } + + // Recursively descend into the child nodes. Calculate the area the + // child nodes occupy. The last child should always occupy all remaining + // space in order to avoid gaps caused by rounding errors. + unsigned int i = 0; + switch (orientation) { + case Orientation::vert: { + int offsY = r.y1; + for (auto it = children.begin(); it != children.end(); + it++, i++) { + const int ch = (i == children.size() - 1) + ? r.y2 - offsY : h * (*it)->relativeSize; + (*it)->gatherBoundingBoxes(areas, splitters, + Rect::bounds(r.x1, offsY, w, ch), splitterSize); + offsY += ch; + } + } + break; + case Orientation::horz: { + int offsX = r.x1; + for (auto it = children.begin(); it != children.end(); + it++, i++) { + const int cw = (i == children.size() - 1) + ? r.x2 - offsX : w * (*it)->relativeSize; + (*it)->gatherBoundingBoxes(areas, splitters, + Rect::bounds(offsX, r.y1, cw, h), splitterSize); + offsX += cw; + } + } + break; + case Orientation::none: + break; + } +} + +} + diff --git a/src/gui/components/GridTree.hpp b/src/gui/components/GridTree.hpp new file mode 100644 index 0000000..1b0a52a --- /dev/null +++ b/src/gui/components/GridTree.hpp @@ -0,0 +1,232 @@ +/* + BasicWriter + Copyright (C) 2014 Benjamin Paaßen, Andreas Stöckel + + 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 <http://www.gnu.org/licenses/>. +*/ + +#ifndef _GRID_TREE_H_ +#define _GRID_TREE_H_ + +#include <vector> +#include <list> + +namespace uigrid { + +class GridTreeNode; + +enum class Orientation +{ + none, horz, vert +}; + +struct Rect +{ + int x1, y1, x2, y2; + + Rect(int x1, int y1, int x2, int y2) : + x1(x1), y1(y1), x2(x2), y2(y2) + { + // Do nothing here + } + + static Rect bounds(int x, int y, int w, int h) + { + return Rect(x, y, x + w, y + h); + } + + int w() const + { + return x2 - x1; + } + + int h() const + { + return y2 - y1; + } + +}; + +struct FrameArea +{ + GridTreeNode *node; + Rect r; + + FrameArea(GridTreeNode *node, const Rect &r) : + node(node), r(r) + { + // Do nothing here + } +}; + +struct Splitter +{ + GridTreeNode *node; + Rect r; + Orientation orientation; + + Splitter(GridTreeNode *node, const Rect &r, Orientation orientation) : + node(node), r(r), orientation(orientation) + { + // Do nothing here + } +}; + +class GridTreeNode +{ + +private: + Orientation orientation; + float relativeSize; + GridTreeNode *parent; + void *data; + + std::list<GridTreeNode*> children; + + void setParent(GridTreeNode *parent) + { + if (this->parent) { + this->parent->removeChild(this); + } + if (parent) { + parent->addChild(this); + } + this->parent = parent; + } + + void removeChild(GridTreeNode *node) + { + for (auto it = children.begin(); it != children.end();) { + if (*it == node) { + it = children.erase(it); + } else { + it++; + } + } + } + + void addChild(GridTreeNode *node) + { + children.push_back(node); + } + +public: + + /** + * Constructor of the GridTreeNode class. + * + * @param orientation describes the orientation of the children of + * this grid tree node. + * @param relativeSize contains the size of this node relative to the size + * of its parent node. The sum of the relativeSizes of all siblings has to + * be one. + * @param data is the data that should be attached to the node. + */ + GridTreeNode(Orientation orientation, float relativeSize = 1.0f, + GridTreeNode *parent = nullptr, void *data = nullptr) : + orientation(orientation), relativeSize(relativeSize), parent(nullptr), + data(data) + { + setParent(parent); + } + + ~GridTreeNode() + { + // Delete all children + for (auto c : children) { + delete c; + } + } + + /** + * Returns true if this element of the grid tree is a "leaf" (e.g. this + * element has no children). + * + * @return true if the grid element is a leaf node, false otherwise. + */ + bool isLeaf() const + { + return children.empty(); + } + + /** + * Returns true if this element is the root node (has no parent). + * + * @return true if this element is the root node, false otherwise. + */ + bool isRoot() const + { + return parent == nullptr; + } + + /** + * Sets the relative size of the node. + * + * @param relativeSize is the new relative size of the frame. Should be in + * an interval of [0, 1]. + */ + void setRelativeSize(float relativeSize) + { + this->relativeSize = relativeSize; + } + + /** + * Returns the current relative size of the node. + * + * @return the current relative size of the node. + */ + float getRelativeSize() + { + return relativeSize; + } + + /** + * Returns the data that was attached to this grid tree node. + * + * @return the data that was attached to this grid tree node. + */ + void* getData() + { + return data; + } + + /** + * Gathers the frame areas and the areas for which splitters should be + * drawn. + * + * @param areas is the list into which the frame area descriptors should be + * inserted. + * @param splitters is the list into which the splitter descriptors should + * be inserted. If nullptr is given, the list is not filled + * @param w is the width of the region for which the splitters should be + * gathered. + * @param h is the height of the region for which the splitters should be + * gathered. + */ + void gatherBoundingBoxes(std::vector<FrameArea> *areas, + std::vector<Splitter> *splitters, const Rect &r, + int splitterSize); + + /** + * Returns the position of the splitter with the given orientation for this + * element. + */ + Rect getSplitterPosition(Orientation orientation, const Rect &r); + +}; + +} + +#endif /* _GRID_TREE_H_ */ + diff --git a/src/gui/components/UIGrid.cpp b/src/gui/components/UIGrid.cpp new file mode 100644 index 0000000..4d6f0e8 --- /dev/null +++ b/src/gui/components/UIGrid.cpp @@ -0,0 +1,81 @@ +/* + BasicWriter + Copyright (C) 2014 Benjamin Paaßen, Andreas Stöckel + + 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 <http://www.gnu.org/licenses/>. +*/ + +#include <QApplication> +#include <QColor> +#include <QPainter> +#include <QPalette> + +#include "GridTree.hpp" + +#include "UIGrid.hpp" + +#include <iostream> + +namespace uigrid { + +UIGrid::UIGrid(QWidget *parent) : + QWidget(parent) +{ + // Enable automatic ereasing of the background + setAutoFillBackground(true); + + // Create the root grid node. + rootGridNode = new GridTreeNode(Orientation::horz, 1.0); + + // Insert two new nodes into the tree + GridTreeNode *nd1 = new GridTreeNode(Orientation::vert, 0.25, rootGridNode); + GridTreeNode *nd2 = new GridTreeNode(Orientation::horz, 0.75, rootGridNode); + + // Add three nodes as children of the first node + new GridTreeNode(Orientation::horz, 0.33, nd1); + new GridTreeNode(Orientation::horz, 0.33, nd1); + new GridTreeNode(Orientation::horz, 0.33, nd1); + + new GridTreeNode(Orientation::vert, 0.75, nd2); + new GridTreeNode(Orientation::horz, 0.25, nd2); +} + +UIGrid::~UIGrid() +{ + delete rootGridNode; +} + +void UIGrid::paintEvent(QPaintEvent *event) +{ + const QPalette &palette = QApplication::palette(); + // Gather all splitter and frame area regions + std::vector<Splitter> splitters; + std::vector<FrameArea> areas; + rootGridNode->gatherBoundingBoxes(&areas, &splitters, + Rect(0, 0, width(), height()), 5); + + QPainter painter(this); + + // Draw the splitters (first the background, then the dividing line) + painter.setPen(palette.mid().color()); + for (auto &c : splitters) { + QRect r(c.r.x1, c.r.y1, c.r.w(), c.r.h()); + painter.fillRect(r, palette.light()); + } + +} + + +} + diff --git a/src/gui/components/UIGrid.hpp b/src/gui/components/UIGrid.hpp new file mode 100644 index 0000000..14d161d --- /dev/null +++ b/src/gui/components/UIGrid.hpp @@ -0,0 +1,49 @@ +/* + BasicWriter + Copyright (C) 2014 Benjamin Paaßen, Andreas Stöckel + + 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 <http://www.gnu.org/licenses/>. +*/ + +#ifndef _UI_GRID_H_ +#define _UI_GRID_H_ + +#include <QWidget> + +namespace uigrid { + +class GridTreeNode; + +class UIGrid : public QWidget +{ + Q_OBJECT + +private: + GridTreeNode *rootGridNode; + +protected: + virtual void paintEvent(QPaintEvent *event); + +public: + + UIGrid(QWidget *parent); + + ~UIGrid(); + +}; + +} + +#endif /* _UI_GRID_H_ */ + diff --git a/src/gui/components/UIPaneFrame.cpp b/src/gui/components/UIPaneFrame.cpp new file mode 100644 index 0000000..1192bad --- /dev/null +++ b/src/gui/components/UIPaneFrame.cpp @@ -0,0 +1,113 @@ +/* + BasicWriter + Copyright (C) 2014 Benjamin Paaßen, Andreas Stöckel + + 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 <http://www.gnu.org/licenses/>. +*/ + +#include <QBoxLayout> +#include <QVBoxLayout> +#include <QHBoxLayout> +#include <QPushButton> +#include <QFrame> +#include <QColor> +#include <QToolButton> +#include <QSizePolicy> +#include <QLabel> +#include <QTreeView> +#include <QDir> +#include <QFileSystemModel> + +#include <gui/components/UIPaneFrame.hpp> + +static void setWidgetColor(QWidget *w, const QColor c) +{ + QPalette p(w->palette()); + p.setColor(QPalette::Background, c); + w->setAutoFillBackground(true); + w->setPalette(p); +} + +UIPaneFrame::UIPaneFrame(QWidget *parent) : + QWidget(parent) +{ + // Create the layout components + rootLayout = new QVBoxLayout; + topLayout = new QHBoxLayout; + centerLayout = new QVBoxLayout; + bottomLayout = new QHBoxLayout; + + // Assemble the top bar +// QToolButton *btn = new QToolButton; +// btn->setIcon(QIcon::fromTheme("user-home")); + + QLabel *lbl = new QLabel("Dies ist nur ein Test"); + lbl->setContentsMargins(10, 0, 10, 0); + + QToolButton *btn2 = new QToolButton; + btn2->setIcon(QIcon::fromTheme("edit-find")); + + QToolButton *btn3 = new QToolButton; + btn3->setIcon(QIcon::fromTheme("window-new")); + +// topLayout->addWidget(btn); + topLayout->addWidget(lbl); + topLayout->addWidget(btn2); + topLayout->addWidget(btn3); + + QTreeView *tree = new QTreeView; + QFileSystemModel *model = new QFileSystemModel; + model->setRootPath(QDir::currentPath()); + tree->setModel(model); + centerLayout->addWidget(tree); + + // Remove the spacing of the layout components + removeLayoutSpacing(rootLayout); + removeLayoutSpacing(topLayout); + removeLayoutSpacing(centerLayout); + removeLayoutSpacing(bottomLayout); + + // Create the widget containers + topContainer = new QWidget; + centerContainer = new QWidget; + bottomContainer = new QWidget; + + // Assign the layouts to the top and bottom part, add the components to the + // root layout + topContainer->setLayout(topLayout); + topContainer->setSizePolicy(QSizePolicy::Minimum, QSizePolicy::Preferred); + + centerContainer->setLayout(centerLayout); + + bottomContainer->setLayout(bottomLayout); + topContainer->setSizePolicy(QSizePolicy::Minimum, QSizePolicy::Preferred); + + rootLayout->addWidget(topContainer, 0); + rootLayout->addWidget(centerContainer, 1); + rootLayout->addWidget(bottomContainer, 0); + + this->setLayout(rootLayout); +} + +UIPaneFrame::~UIPaneFrame() +{ + +} + +void UIPaneFrame::removeLayoutSpacing(QBoxLayout *layout) +{ + layout->setContentsMargins(0, 0, 0, 0); + layout->setSpacing(0); +} + diff --git a/src/gui/components/UIPaneFrame.hpp b/src/gui/components/UIPaneFrame.hpp new file mode 100644 index 0000000..32bbca7 --- /dev/null +++ b/src/gui/components/UIPaneFrame.hpp @@ -0,0 +1,50 @@ +/* + BasicWriter + Copyright (C) 2014 Benjamin Paaßen, Andreas Stöckel + + 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 <http://www.gnu.org/licenses/>. +*/ + +#ifndef _UI_PANE_FRAME_HPP_ +#define _UI_PANE_FRAME_HPP_ + +#include <QWidget> + +class QBoxLayout; +class QVBoxLayout; +class QHBoxLayout; + +class UIPaneFrame : public QWidget +{ + Q_OBJECT + +private: + QVBoxLayout *rootLayout; + QHBoxLayout *topLayout; + QVBoxLayout *centerLayout; + QHBoxLayout *bottomLayout; + QWidget *topContainer; + QWidget *centerContainer; + QWidget *bottomContainer; + + void removeLayoutSpacing(QBoxLayout *layout); + +public: + explicit UIPaneFrame(QWidget *parent = 0); + ~UIPaneFrame(); + +}; + +#endif /* _UI_PANE_FRAME_HPP_ */ + |