利用widget重构parkinglot

This commit is contained in:
wmj committed 2017-12-14 16:34:27 +08:00
1 parent 22bcf38c3f
commit 998cffecaf
6 files changed
+298

No files matched your search

+111
View File
@@ -0,0 +1,111 @@
#include "ParkingLotWidget.h"
#include <QFile>
#include <QMessageBox>
#include <QDomDocument>
#include <QDebug>
#include "Road.h"
#include "ParkingSpaceInfo.h"
#include <QPainter>
ParkingLotWidget::ParkingLotWidget(QWidget *parent, const QString& xml) : QWidget(parent)
{
resize(1000, 1000);
parse_xml(xml);
if (rootLayoutDirection == horizontal)
setLayout(hBoxLayout);
else
setLayout(vBoxLayout);
}
void ParkingLotWidget::paintEvent(QPaintEvent * event)
{
}
ParkingLotWidget::~ParkingLotWidget()
{
}
void ParkingLotWidget::parse_xml(const QString & xml)
{
QFile file(xml);
if (!file.open(QFile::ReadOnly | QFile::Text)) {
QMessageBox::critical(this, QObject::tr("Error"),
QObject::tr("Cannot read file %1").arg(xml));
}
QString errorStr;
int errorLine;
int errorColumn;
QDomDocument doc;
if (!doc.setContent(&file, false, &errorStr, &errorLine, &errorColumn)) {
QMessageBox::critical(this, QObject::tr("Error"),
QObject::tr("Parse error at line %1, column %2: %3")
.arg(errorLine).arg(errorColumn).arg(errorStr));
}
QDomElement element = doc.documentElement().firstChild().toElement();
QString name = element.tagName();
if (element.tagName() == "vLayout")
{
rootLayoutDirection = vertical;
vBoxLayout = parseVbox(element);
} else if (element.tagName() == "hLayout")
{
rootLayoutDirection = horizontal;
hBoxLayout = parseHbox(element);
} else
{
qDebug() << this -> objectName() << "布局文件错误";
}
}
inline QHBoxLayout * ParkingLotWidget::parseHbox(const QDomElement & element)
{
return static_cast<QHBoxLayout*>(parseLayout(element));
}
inline QVBoxLayout * ParkingLotWidget::parseVbox(const QDomElement & element)
{
return static_cast<QVBoxLayout*>(parseLayout(element));;
}
QBoxLayout * ParkingLotWidget::parseLayout(const QDomElement & element)
{
QBoxLayout* layout;
if (element.tagName() == "hLayout")
layout = new QHBoxLayout;
else
layout = new QVBoxLayout;
QDomElement child = element.firstChild().toElement();
while (!child.isNull())
{
QString name = child.tagName();
if (name == "road")
{
const int l = child.attribute("length").toInt();
if (child.attribute("direction") == "vertical")
layout->addWidget(new Road(this, l, Road::vertical));
else
layout->addWidget(new Road(this, l, Road::horizontal));
}
else if (name == "room")
{
const auto n = child.attribute("number", "1").toInt();
layout->addLayout(ParkingSpaceInfo::makeParkingSapceGroup(
this, child.attribute("direction"), n, child.attribute("expendDirection")));
}
else if ((name.at(0) == 'v' || name.at(0) == 'h' )&& name.contains("Layout"))
layout->addLayout(parseHbox(child));
else
qDebug() << this->objectName() << "错误的xml标签";
child = child.nextSiblingElement();
}
layout->setMargin(0);
layout->setSpacing(0);
layout->setContentsMargins(0, 0, 0, 0);
return layout;
}
+23
View File
@@ -0,0 +1,23 @@
#pragma once
#include <QWidget>
#include <QString>
#include <QHBoxLayout>
#include <QVBoxLayout>
#include <QDomDocument>
class ParkingLotWidget: public QWidget
{
Q_OBJECT
public:
explicit ParkingLotWidget(QWidget* parent, const QString& xml);
void paintEvent(QPaintEvent* event) override;
~ParkingLotWidget();
private:
void parse_xml(const QString& xml);
inline QHBoxLayout* parseHbox(const QDomElement& element);
inline QVBoxLayout* parseVbox(const QDomElement& element);
enum {horizontal, vertical} rootLayoutDirection;
QBoxLayout *parseLayout(const QDomElement& element);
QHBoxLayout *hBoxLayout = nullptr;
QVBoxLayout *vBoxLayout = nullptr;
};
+88
View File
@@ -0,0 +1,88 @@
#include "ParkingSpaceInfo.h"
#include <QPainter>
#include <QDebug>
ParkingSpaceInfo::ParkingSpaceInfo(QWidget* parent, const direction dir) : QWidget(parent)
{
this->dir = dir;
switch (dir)
{
case N:
case S:
resize(40, 60);
setMinimumSize(40, 60);
setMaximumSize(40, 60);
break;
case E:
case W:
resize(60, 40);
setMinimumSize(60, 40);
setMaximumSize(60, 40);
break;
}
}
ParkingSpaceInfo::ParkingSpaceInfo(QWidget* parent, const QString &dir)
{
direction d = {};
const char c = dir.at(0).unicode();
switch (c)
{
case 'N':d = N; break;
case 'E':d = E; break;
case 'W':d = W; break;
case 'S':d = S; break;
default: qDebug() << this->objectName() << "´íÎóµÄ·½Ïò";
}
this->ParkingSpaceInfo::ParkingSpaceInfo(parent, d);
}
QBoxLayout *ParkingSpaceInfo::makeParkingSapceGroup(QWidget* parent, const QString& dir, int n, const QString & expend)
{
QBoxLayout *layout;
if (expend == "down")
layout = new QVBoxLayout();
else
layout = new QHBoxLayout();
for (int i = 0; i < n; i++)
{
ParkingSpaceInfo *pk = new ParkingSpaceInfo(parent, dir);
layout->addWidget(pk);
}
layout->setMargin(0);
layout->setSpacing(0);
layout->setContentsMargins(0, 0, 0, 0);
return layout;
}
void ParkingSpaceInfo::paintEvent(QPaintEvent * event)
{
QPainter painter(this);
painter.setPen(Qt::blue);
// painter.drawRect(0, 0, this->width(), this->height());
painter.setPen(Qt::red);
painter.setBrush(Qt::white);
painter.translate(30, 20);
switch (dir) {
case E:
break;
case S:
painter.rotate(270);
break;
case W:
painter.rotate(180);
break;
case N:
painter.rotate(90);
break;
}
painter.translate(-30, -20);
painter.drawRect(0, 0, 60, 5);
painter.drawRect(0, 5, 10, 35);
painter.drawRect(10, 35, 50, 5);
painter.end();
}
ParkingSpaceInfo::~ParkingSpaceInfo()
{
}
+17
View File
@@ -0,0 +1,17 @@
#pragma once
#include <QWidget>
#include <QLayout>
class ParkingSpaceInfo: public QWidget
{
Q_OBJECT
public:
enum direction{N, S, E, W};
ParkingSpaceInfo(QWidget* parent, direction dir);
ParkingSpaceInfo(QWidget* parent, const QString &dir);
static QBoxLayout* makeParkingSapceGroup(QWidget* parent, const QString& dir, int n, const QString &expend);
void paintEvent(QPaintEvent* event) override;
~ParkingSpaceInfo();
private:
direction dir;
};
+44
View File
@@ -0,0 +1,44 @@
#include "Road.h"
#include <QPainter>
Road::Road(QWidget* parent, const int length, const direction dir)
:QWidget(parent), length(length), dir(dir)
{
switch(dir)
{
case horizontal:
resize(length, 50);
setMinimumSize(length, 50);
setMaximumSize(length, 50);
break;
case vertical:
resize(50, length);
setMinimumSize(50, length);
setMaximumSize(50, length);
break;
}
}
void Road::paintEvent(QPaintEvent * event)
{
QPainter painter(this);
painter.setBrush(Qt::white);
painter.setPen(Qt::white);
auto x = 0, y = 0;
if (dir == horizontal) {
while (x < length) {
painter.drawRect(x + 5, 20, 40, 10);
x += 50;
}
}
else {
while (y < length) {
painter.drawRect(20, y + 5, 10, 40);
y += 50;
}
}
}
Road::~Road()
{
}
+15
View File
@@ -0,0 +1,15 @@
#pragma once
#include <QWidget>
class Road: public QWidget
{
Q_OBJECT
public:
enum direction{ horizontal, vertical};
Road(QWidget* parent, const int length, direction dir);
void paintEvent(QPaintEvent* event) override;
~Road();
private:
const int length;
direction dir;
};