当前位置:网站首页>QT drawing network topology diagram (connecting database, recursive function, infinite drawing, dragging nodes)
QT drawing network topology diagram (connecting database, recursive function, infinite drawing, dragging nodes)
2022-07-04 23:07:00 【GreenHandBruce】
Hardware :ThinkPadT590
System :Win10
database :sqlserver2014
Qt:5.14.1
QtCreator:4.11.1
Source connection :
qt To achieve the drawing of network topology diagram , Connect first sqlserver The database obtains all node data , Then the relationship between each node is resolved by recursive function , And calculate the position of each node to be drawn on the graph , Then by rewriting
QGraphicsPixmapItem Class to draw a node graph , By rewriting
QGraphicsItem Class to draw the line between nodes .
As long as the relationship data between nodes is correct , You can draw infinitely .
The interface is as follows :
The dragging effect is as follows :
sqlserver The data in the database table is as follows :
The key codes are as follows :
#include <QtWidgets>
#include "nodeframe.h"
#include <iostream>
using namespace std;
NodeFrame::NodeFrame(QWidget *parent) :
QGraphicsView(parent)
{
setGeometry(0,0,1920,2000);
m_scene = new QGraphicsScene(0, 0, this->width(), this->height());
this->setScene(m_scene);
QScrollBar *horBar = this->horizontalScrollBar();
QScrollBar *verBar = this->verticalScrollBar();
horBar->setValue(horBar->maximum());
verBar->setValue(verBar->maximum());
// connectSqlServer();// Connect to the database and read the data , Disable here first , If you have a good database , You can drive
manulInitNoteList();// If you do not connect to the database, you can manually initialize the node queue , When connecting to the database , This line should be disabled !
initNodeList();
}
void NodeFrame::manulInitNoteList()
{
NodeInSql node;
node.nNodeID =1; node.nParentID =1; node.strNodeName =" The root node "; m_lstNodeInSql.append(node);
node.nNodeID =2; node.nParentID =1; node.strNodeName =" Child node 2"; m_lstNodeInSql.append(node);
node.nNodeID =3; node.nParentID =1; node.strNodeName =" Child node 3"; m_lstNodeInSql.append(node);
node.nNodeID =4; node.nParentID =1; node.strNodeName =" Child node 4"; m_lstNodeInSql.append(node);
node.nNodeID =5; node.nParentID =1; node.strNodeName =" Child node 5"; m_lstNodeInSql.append(node);
node.nNodeID =6; node.nParentID =2; node.strNodeName =" Child node 6"; m_lstNodeInSql.append(node);
node.nNodeID =7; node.nParentID =2; node.strNodeName =" Child node 7"; m_lstNodeInSql.append(node);
node.nNodeID =8; node.nParentID =3; node.strNodeName =" Child node 8"; m_lstNodeInSql.append(node);
node.nNodeID =9; node.nParentID =3; node.strNodeName =" Child node 9"; m_lstNodeInSql.append(node);
node.nNodeID =10; node.nParentID =4; node.strNodeName =" Child node 10"; m_lstNodeInSql.append(node);
node.nNodeID =11; node.nParentID =10; node.strNodeName =" Child node 11"; m_lstNodeInSql.append(node);
node.nNodeID =12; node.nParentID =11; node.strNodeName =" Child node 12"; m_lstNodeInSql.append(node);
node.nNodeID =13; node.nParentID =12; node.strNodeName =" Child node 13"; m_lstNodeInSql.append(node);
node.nNodeID =14; node.nParentID =13; node.strNodeName =" Child node 14"; m_lstNodeInSql.append(node);
node.nNodeID =15; node.nParentID =13; node.strNodeName =" Child node 15"; m_lstNodeInSql.append(node);
node.nNodeID =16; node.nParentID =13; node.strNodeName =" Child node 16"; m_lstNodeInSql.append(node);
node.nNodeID =17; node.nParentID =13; node.strNodeName =" Child node 17"; m_lstNodeInSql.append(node);
node.nNodeID =18; node.nParentID =13; node.strNodeName =" Child node 18"; m_lstNodeInSql.append(node);
}
NodeFrame::~NodeFrame()
{
delete m_scene;
}
void NodeFrame::refresh()
{
this->destroyed(m_scene);
m_scene = new QGraphicsScene(0, 0, this->width(), this->height());
this->setScene(m_scene);
initNodeList();
}
void NodeFrame::connectSqlServer()
{
QSqlDatabase db= QSqlDatabase::addDatabase("QODBC", "dbTemp");
db.setDatabaseName(QString("DRIVER={SQL SERVER};"
"SERVER=%1;" // Server name
"DATABASE=%2;"// Database name
"UID=%3;" // Login name
"PWD=%4;" // password
).arg("127.0.0.1,49674")// The port number on my computer is 49674
.arg("myTestSql")
.arg("Bruce")
.arg("Qwerty*963.-+")
);
// Database connection
bool ok = db.open();
if(ok)
{
qDebug()<<"database open success";
}
else
{
qDebug()<<db.lastError();
return;
}
// Database query
QSqlQuery query(db);
query.exec("SELECT * FROM Node;");
while(query.next())
{
NodeInSql node;
if(query.value(1).isValid())
node.nNodeID = query.value(1).toInt();
if(query.value(2).isValid())
node.nParentID = query.value(2).toInt();
if(query.value(3).isValid())
node.strNodeName = query.value(3).toString();
m_lstNodeInSql.append(node);
}
db.close();
}
void NodeFrame::initNodeList()
{
// Find the root node
NodeInSql nRootID;
foreach(NodeInSql node,m_lstNodeInSql)
{
if(node.nNodeID==node.nParentID)
{
nRootID = node;
}
}
NodeInfoToShow rootNodeInfoToShow;
rootNodeInfoToShow.nLevel = 0;
rootNodeInfoToShow.nNodeID = nRootID.nNodeID;
rootNodeInfoToShow.nParentID = nRootID.nParentID;
rootNodeInfoToShow.ptPos = QPoint(0,100);
rootNodeInfoToShow.strNodeName = nRootID.strNodeName;
m_lstNodeInfoToShow.append(rootNodeInfoToShow);
NetNode *rootNetNode = new NetNode(rootNodeInfoToShow,m_scene);
parseNodesInSql(rootNodeInfoToShow,rootNetNode);// Analyze all node relationships and locations
}
void NodeFrame::parseNodesInSql(NodeInfoToShow node,NetNode *netNode)
{
int nChildNum = 0;// At present node A node has several child nodes
int nWidth = node.nLevel%2==0?250:150;// Horizontal spacing between nodes
int nHeight = 200;// Longitudinal spacing between nodes
QList<NodeInfoToShow> lstNodeInCrtLevel;// At present node All nodes under
for(int i = 0;i<m_lstNodeInSql.count();i++)
{
if(m_lstNodeInSql[i].nParentID==node.nNodeID && m_lstNodeInSql[i].nParentID!=m_lstNodeInSql[i].nNodeID)
{
nChildNum++;
NodeInfoToShow rootNodeInfoToShow;
rootNodeInfoToShow.nLevel = node.nLevel+1;
rootNodeInfoToShow.nNodeID = m_lstNodeInSql[i].nNodeID;
rootNodeInfoToShow.nParentID = node.nNodeID;
rootNodeInfoToShow.ptPos = QPoint(0,0);// Here first 0,0 Point as initial value , Next, determine the location of each child node
rootNodeInfoToShow.strNodeName = m_lstNodeInSql[i].strNodeName;
lstNodeInCrtLevel.append(rootNodeInfoToShow);
}
}
// Determine the location of each child node
for(int i = 0;i<lstNodeInCrtLevel.count();i++)
{
if(nChildNum%2==1)// There are odd child nodes
{
int nHalf = (nChildNum-1)/2;
int nX =node.ptPos.x()+(i-nHalf)*nWidth;// Of the above node x Based on coordinates plus offset
int nY = node.ptPos.y()+nHeight;// Of the above node y Based on coordinates plus offset
lstNodeInCrtLevel[i].ptPos = QPoint(nX,nY);
}
else// There are even child nodes
{
int nHalf = nChildNum/2;
int nX =node.ptPos.x()+(i-nHalf)*nWidth+nWidth/2;// Of the above node x Based on coordinates plus offset
int nY = node.ptPos.y()+nHeight;// Of the above node y Based on coordinates plus offset
lstNodeInCrtLevel[i].ptPos = QPoint(nX,nY);
}
m_lstNodeInfoToShow.append(lstNodeInCrtLevel[i]);
NetNode *subNetNode = new NetNode(lstNodeInCrtLevel[i],m_scene);
NodeLink *link = new NodeLink(netNode, subNetNode);
if (link) {
m_scene->addItem(link);
}
parseNodesInSql(lstNodeInCrtLevel[i],subNetNode);
}
}
Source download connection :
边栏推荐
- [sword finger offer] questions 1-5
- Redis:Redis的事务
- Wechat official account solves the cache problem of entering from the customized menu
- 【ODX Studio编辑PDX】-0.3-如何删除/修改Variant变体中继承的(Inherited)元素
- Editplus-- usage -- shortcut key / configuration / background color / font size
- 攻防世界 MISC 进阶区 can_has_stdio?
- Talk about Middleware
- 攻防世界 MISC 进阶区 3-11
- Redis:Redis消息的发布与订阅(了解)
- debug和release的区别
猜你喜欢
Redis getting started complete tutorial: publish and subscribe
Redis getting started complete tutorial: Geo
Redis introduction complete tutorial: slow query analysis
Redis入门完整教程:慢查询分析
One of the commonly used technical indicators, reading boll Bollinger line indicators
The small program vant tab component solves the problem of too much text and incomplete display
JS 3D explosive fragment image switching JS special effect
Redis入门完整教程:初识Redis
Qt个人学习总结
Analysis of the self increasing and self decreasing of C language function parameters
随机推荐
[sword finger offer] questions 1-5
Qt个人学习总结
Redis getting started complete tutorial: publish and subscribe
Redis getting started complete tutorial: hash description
Redis入门完整教程:列表讲解
Unity vscode emmylua configuration error resolution
Redis getting started complete tutorial: Geo
Is Huatai Securities a nationally recognized securities firm? Is it safe to open an account?
MP进阶操作: 时间操作, sql,querywapper,lambdaQueryWapper(条件构造器)快速筛选 枚举类
Servlet服务器端和客户端中文输出乱码问题
SPH中的粒子初始排列问题(两张图解决)
The small program vant tab component solves the problem of too much text and incomplete display
【机器学习】手写数字识别
Redis入门完整教程:API的理解和使用
A complete tutorial for getting started with redis: transactions and Lua
HMS core unified scanning service
VIM editor knowledge summary
Three stage operations in the attack and defense drill of the blue team
Redis入门完整教程:哈希说明
JS card style countdown days