QT 甚至在 waitForConnected 运行时处理
QT even processing while waitForConnected is running
我有一个循环,应该尝试连接到范围内的每个 IP:
for(...){
socket->connectToHost(addres,port);
do stuff....
if(socket->waitForConnected(2000))
{
do stuff...
if(socket->waitForReadyRead(1000))
{
do stuff...
}
else do stuff...
}
do stuff ......
}
在连接尝试期间 UI 冻结,因为在此期间没有任何事件处理。我试图添加 QCoreApplication::processEvents();在循环中,但是在 waitForConnected 期间它仍然冻结很长时间,我也尝试使用计时器,但这也不会起作用,因为 QT 首先需要事件处理才能使用计时器。有什么方法可以在连接期间提供事件处理(防止 UI 冻结),或者对 waitForConnection 使用一些非阻塞替代方法?
请写100遍'I must not wait in GUI event-handlers'。
使用异步信号或关闭通信。
最好的方法是通过将套接字的信号连接到相关插槽,以异步模式使用QTcpSocket
:
connect( socket, SIGNAL(connected()), this, SLOT(onConnected()) );
connect( socket, SIGNAL(readyRead()), this, SLOT(tcpReady()) );
connect( socket, SIGNAL(error(QAbstractSocket::SocketError)),
this, SLOT(tcpError(QAbstractSocket::SocketError)) );
并在插槽中处理您的应用程序逻辑:
void MyClass::onConnected()
{
...
}
void MyClass::tcpError(QAbstractSocket::SocketError error)
{
...
}
您还可以使用 QEventLoop
的本地事件循环,并将 connected
、error
、... 的信号连接到 QTcpSocket
的退出槽QEventLoop
。这样当套接字连接或发生错误时,本地事件循环退出并执行其余部分:
socket->connectToHost(addres,port);
QEventLoop loop;
loop.connect(socket, SIGNAL(connected()), SLOT(quit()));
loop.connect(socket, SIGNAL(error(QAbstractSocket::SocketError)), SLOT(quit()));
loop.exec();
//...
我不应该认为这是 "blocking wait without blocking the UI" 的标准模式。
我有一个循环,应该尝试连接到范围内的每个 IP:
for(...){
socket->connectToHost(addres,port);
do stuff....
if(socket->waitForConnected(2000))
{
do stuff...
if(socket->waitForReadyRead(1000))
{
do stuff...
}
else do stuff...
}
do stuff ......
}
在连接尝试期间 UI 冻结,因为在此期间没有任何事件处理。我试图添加 QCoreApplication::processEvents();在循环中,但是在 waitForConnected 期间它仍然冻结很长时间,我也尝试使用计时器,但这也不会起作用,因为 QT 首先需要事件处理才能使用计时器。有什么方法可以在连接期间提供事件处理(防止 UI 冻结),或者对 waitForConnection 使用一些非阻塞替代方法?
请写100遍'I must not wait in GUI event-handlers'。
使用异步信号或关闭通信。
最好的方法是通过将套接字的信号连接到相关插槽,以异步模式使用QTcpSocket
:
connect( socket, SIGNAL(connected()), this, SLOT(onConnected()) );
connect( socket, SIGNAL(readyRead()), this, SLOT(tcpReady()) );
connect( socket, SIGNAL(error(QAbstractSocket::SocketError)),
this, SLOT(tcpError(QAbstractSocket::SocketError)) );
并在插槽中处理您的应用程序逻辑:
void MyClass::onConnected()
{
...
}
void MyClass::tcpError(QAbstractSocket::SocketError error)
{
...
}
您还可以使用 QEventLoop
的本地事件循环,并将 connected
、error
、... 的信号连接到 QTcpSocket
的退出槽QEventLoop
。这样当套接字连接或发生错误时,本地事件循环退出并执行其余部分:
socket->connectToHost(addres,port);
QEventLoop loop;
loop.connect(socket, SIGNAL(connected()), SLOT(quit()));
loop.connect(socket, SIGNAL(error(QAbstractSocket::SocketError)), SLOT(quit()));
loop.exec();
//...
我不应该认为这是 "blocking wait without blocking the UI" 的标准模式。