Замораживает интерфейс программы при пинге и не пингует IP

Столкнулся с проблемой, что либо интерфейс замораживается, либо не пингуются ip адреса в файле ip.txt.

1 кнопка (без нажатия на неё) чтобы пинговала только - 1 строчку в ip.txt.
2 кнопка (без нажатия на неё) чтобы пинговала только - 2 строчку.

Помогите пожалуйста исправить.

main.py

import sys
import os
from PyQt5 import QtCore, QtGui, QtWidgets

from ui import Ui_Form


class MainWindow(QtWidgets.QWidget, Ui_Form):
    def __init__(self):
        super().__init__()
        self.setupUi(self)

    def colorburron1(self):  # функция для 1 кнопки, чтобы считывалась только 1 строчка в ip.txt
        with open('ip.txt') as f:
            for index, line in enumerate(f):
                if index == 1:
                    ip1 = line
                    break
        for ips in ip1:
            response = os.system('ping -n 5 ' + ip1)
            if response == 0:
                self.pushButton.setStyleSheet(
                    'QPushButton {background-color: green}')
            else:
                self.pushButton.setStyleSheet(
                    'QPushButton {background-color: red}')

    def colorburron2(self):  # функция для 2 кнопки, чтобы считывалась только 2 строчка в ip.txt
        with open('ip.txt') as f:
            for index, line in enumerate(f):
                if index == 2:
                    ip1 = line
                    break
        for ips in ip1:
            response = os.system('ping -n 5 ' + ip1)
            if response == 0:
                self.pushButton_2.setStyleSheet(
                    'QPushButton {background-color: green}')
            else:
                self.pushButton_2.setStyleSheet(
                    'QPushButton {background-color: red}')


if __name__ == "__main__":
    app = QtWidgets.QApplication(sys.argv)
    w = MainWindow()
    w.show()
    sys.exit(app.exec_())

ui.py

from PyQt5 import QtCore, QtGui, QtWidgets


class Ui_Form(object):
    def setupUi(self, Form):
        Form.setObjectName("Form")
        Form.resize(384, 69)
        Form.setStyleSheet("QPushButton {\n"
"Background-color: green\n"
"}")
        self.pushButton = QtWidgets.QPushButton(Form)
        self.pushButton.setGeometry(QtCore.QRect(0, 0, 51, 41))
        self.pushButton.setObjectName("pushButton")
        self.pushButton_2 = QtWidgets.QPushButton(Form)
        self.pushButton_2.setGeometry(QtCore.QRect(50, 0, 51, 41))
        self.pushButton_2.setObjectName("pushButton_2")
        self.pushButton_3 = QtWidgets.QPushButton(Form)
        self.pushButton_3.setGeometry(QtCore.QRect(100, 0, 51, 41))
        self.pushButton_3.setObjectName("pushButton_3")
        self.pushButton_4 = QtWidgets.QPushButton(Form)
        self.pushButton_4.setGeometry(QtCore.QRect(150, 0, 51, 41))
        self.pushButton_4.setObjectName("pushButton_4")
        self.pushButton_5 = QtWidgets.QPushButton(Form)
        self.pushButton_5.setGeometry(QtCore.QRect(200, 0, 51, 41))
        self.pushButton_5.setObjectName("pushButton_5")
        self.pushButton_6 = QtWidgets.QPushButton(Form)
        self.pushButton_6.setGeometry(QtCore.QRect(250, 0, 51, 41))
        self.pushButton_6.setObjectName("pushButton_6")
        self.pushButton_7 = QtWidgets.QPushButton(Form)
        self.pushButton_7.setGeometry(QtCore.QRect(300, 0, 51, 41))
        self.pushButton_7.setObjectName("pushButton_8")

        self.retranslateUi(Form)
        QtCore.QMetaObject.connectSlotsByName(Form)

    def retranslateUi(self, Form):
        _translate = QtCore.QCoreApplication.translate
        Form.setWindowTitle(_translate("Form", "Form"))
        self.pushButton.setText(_translate("Form", "PushButton"))
        self.pushButton_2.setText(_translate("Form", "PushButton"))
        self.pushButton_3.setText(_translate("Form", "PushButton"))
        self.pushButton_4.setText(_translate("Form", "PushButton"))
        self.pushButton_5.setText(_translate("Form", "PushButton"))
        self.pushButton_6.setText(_translate("Form", "PushButton"))
        self.pushButton_7.setText(_translate("Form", "PushButton"))


if __name__ == "__main__":
    import sys
    app = QtWidgets.QApplication(sys.argv)
    Form = QtWidgets.QWidget()
    ui = Ui_Form()
    ui.setupUi(Form)
    Form.show()
    sys.exit(app.exec_())
    


Ответы (1 шт):

Автор решения: S. Nick

Sorry, мне показалась ваша форма не очень понятна.

Да, можно os.system() запускать в дополнительном потоке, но я вам предложу познакомиться с классом QProcess, который используется для запуска внешних программ и взаимодействия с ними.

import sys
from PyQt5.Qt import *


class MainWindow(QWidget):
    def __init__(self):
        super().__init__()

        self.lcdTime = QLCDNumber(self)
        self.lcdTime.setSegmentStyle(QLCDNumber.Filled)  
        self.lcdTime.setDigitCount(8)
        self.lcdTime.setMinimumSize(120, 40)
        
        self.runButton = QPushButton('Start')
        self.runButton.clicked.connect(self.callProgram)

        self.label = QLabel()

        self.lineEdit = QLineEdit(placeholderText="Введите IP")

        layout = QGridLayout(self)
        layout.addWidget(self.lcdTime, 0, 1, alignment=Qt.AlignRight | Qt.AlignTop)        
        layout.addWidget(self.label, 1, 0, 1, 2, alignment=Qt.AlignCenter)
        layout.addWidget(self.lineEdit, 2, 0)
        layout.addWidget(self.runButton, 2, 1)
        
        layout.setRowStretch(0, 0)
        layout.setRowStretch(1, 1)
        layout.setRowStretch(2, 0)

        self.process = QProcess(self)
        # https://doc.qt.io/qt-5/qprocess.html#finished
        self.process.finished.connect(self.on_finished) 

        self.ipAddress = '' 
        
        self.timer = QTimer(self, interval=1000)  
        self.timer.timeout.connect(self.on_timeout)

    @pyqtSlot(int, QProcess.ExitStatus) 
    def on_finished(self, exitCode, exitStatus):
        if self.runButton.text()  == 'Start':
            return

        if exitCode == 0:
            text = '<span style="color: green; font-size: 20px;">Подключен</span>'
        else:
            text = '<span style="color: red; font-size: 20px;">НЕ подключен</span>' 
        self.label.setText(f'Ping для {self.ipAddress}: {text}')
        self.label.adjustSize()
        
    def on_timeout(self): 
        time = QTime.currentTime()
        text = time.toString("hh:mm:ss")           
        if ((time.second() % 2) == 0):
            text = text[0:2] + ' ' + text[3:5] + ' ' + text[6:]
        self.lcdTime.display(text)

        if ((time.second() % 5) == 0):           # установите нужный вам интервал для ping
            self.process.start('ping', [self.ipAddress, '-n', '2', '-w', '100'])  

    def callProgram(self):
        self.ipAddress = self.lineEdit.text()
        if not self.ipAddress:
            msg = QMessageBox.information(self, 'Внимание', 'Введите ipAddress.')
            return
    
        if self.runButton.text()  == 'Start':
            self.runButton.setText('Stop')
            self.timer.start()
        else:
            self.timer.stop()
            self.runButton.setText('Start')
            
            text = '<span style="color: #AE4CCF; font-size: 20px;">НЕ пингунтся, нажмите Start.</span>' 
            self.label.setText(f'Ping для {self.ipAddress}: {text}')           


if __name__ == '__main__':
    app = QApplication(sys.argv)
    w = MainWindow()
    w.resize(600, 300)
    w.show()
    sys.exit(app.exec_())

введите сюда описание изображения

введите сюда описание изображения

введите сюда описание изображения

введите сюда описание изображения

→ Ссылка