python-qt5
python-qt5 copied to clipboard
PyQt5 shows white border while displaying image in full screen
I'm using PyQt5 to build a UI for my computer vision app. The app has six pages, and on the fourth page, I receive video frames from a backend thread that runs when the app reaches this page. However, I'm having trouble getting the QLabel
on the fourth page to resize correctly and display the video frames in full screen.
Here is the code snippet that sends frames to the frontend:
qImg = QImage(combined_frame2.data, combined_frame2.shape[1], combined_frame2.shape[0], QImage.Format_RGB888)
self.update_video_frame.emit(qImg.rgbSwapped())
Here is the class for the fourth page:
class FourthPage(QWidget):
recording_finished = pyqtSignal()
switch_to_fifth_page = pyqtSignal()
def __init__(self, parent=None):
super().__init__(parent)
self.initUI()
def initUI(self):
self.setContentsMargins(0, 0, 0, 0)
# Set up the video label to take up the entire space
self.video_label = QLabel(self)
self.video_label.setAlignment(Qt.AlignCenter)
self.video_label.setStyleSheet("background-color: transparent;") # Optional: Set transparent background
# Set video_label to cover the entire widget
self.video_label.setGeometry(0, 0, self.width(), self.height())
self.click_player = QMediaPlayer()
# Install event filter to detect clicks on the video label
self.video_label.installEventFilter(self)
def resizeEvent(self, event):
# Ensure video_label resizes with the widget
self.video_label.setGeometry(0, 0, self.width(), self.height())
def stopRecording(self):
self.recording_finished.emit()
def playClickSound(self):
self.click_player.setMedia(QMediaContent(QUrl.fromLocalFile("/path/to/Click.mp3")))
self.click_player.setVolume(100)
self.click_player.play()
def handleMouseClick(self):
self.stopRecording()
self.playClickSound()
QTimer.singleShot(500, self.switch_to_fifth_page.emit)
def eventFilter(self, source, event):
if event.type() == QEvent.MouseButtonPress and source == self.video_label:
self.handleMouseClick()
return True
return super().eventFilter(source, event)
Here is the main class that controls the flow of the app:
class MainWindow(QWidget):
def __init__(self):
super().__init__()
self.stack = QStackedWidget(self)
self.setWindowFlags(Qt.WindowType.FramelessWindowHint)
self.setGeometry(0, 0, 800, 600)
self.showFullScreen()
self.initUI()
def initUI(self):
layout = QVBoxLayout(self)
self.introPage = IntroPage()
self.firstPage = FirstPage()
self.secondPage = SecondPage()
self.thirdPage = ThirdPage()
self.fourthPage = FourthPage()
self.startRecordingPage = StartRecordingPage()
self.fifthPage = FifthPage()
self.sixthPage = SixthPage()
self.stack.addWidget(self.introPage)
self.stack.addWidget(self.firstPage)
self.stack.addWidget(self.secondPage)
self.stack.addWidget(self.thirdPage)
self.stack.addWidget(self.startRecordingPage)
self.stack.addWidget(self.fourthPage)
self.stack.addWidget(self.fifthPage)
self.stack.addWidget(self.sixthPage)
layout.addWidget(self.stack)
self.setLayout(layout)
self.introPage.switch_to_first_page.connect(self.showFirstPage)
self.firstPage.switch_to_second_page.connect(self.showSecondPage)
self.secondPage.switch_to_third_page.connect(self.showThirdPage)
self.thirdPage.switch_to_recording_page.connect(self.showStartRecordingPage)
self.startRecordingPage.switch_to_fourth_page.connect(self.showFourthPage)
self.fourthPage.switch_to_fifth_page.connect(self.showFifthPage)
self.fourthPage.recording_finished.connect(self.stopRecording)
self.sixthPage.restart_requested.connect(self.restartApp)
self.sixthPage.exit_requested.connect(self.exitApp)
self.backend_thread = BackendThread()
self.backend_thread.update_video_frame.connect(self.update_video_frame)
self.backend_thread.finished.connect(self.showSixthPage)
self.showFullScreen()
def stopRecording(self):
self.backend_thread.stop_recording = True
def showFirstPage(self):
self.stack.setCurrentWidget(self.firstPage)
def showSecondPage(self):
self.stack.setCurrentWidget(self.secondPage)
def showThirdPage(self):
self.stack.setCurrentWidget(self.thirdPage)
def showStartRecordingPage(self):
self.stack.setCurrentWidget(self.startRecordingPage)
def showFourthPage(self):
self.stack.setCurrentWidget(self.fourthPage)
self.backend_thread.start()
def showFifthPage(self):
self.stack.setCurrentWidget(self.fifthPage)
QTimer.singleShot(100, self.run_processing) # Delay the processing to allow the UI to update
def showSixthPage(self):
self.stack.setCurrentWidget(self.sixthPage)
self.display_results()
def run_processing(self):
self.backend_thread.run_processing()
def update_video_frame(self, qImg):
self.fourthPage.video_label.setPixmap(QPixmap.fromImage(qImg))
def display_results(self):
font = self.sixthPage.results_label.font()
font.setPointSize(14)
self.sixthPage.results_label.setFont(font)
self.sixthPage.results_label.setWordWrap(True)
self.sixthPage.results_label.setFixedWidth(self.width() - 20)
self.sixthPage.results_label.setText(
f"Frame count: {self.backend_thread.frame_count}\n"
f"FPS: {self.backend_thread.fps}\n"
f"Transcript: {self.backend_thread.transcript}\n"
f"Objects List: {self.backend_thread.objects_list}\n"
f"Phrase Timestamps: {self.backend_thread.phrase_timestamps}\n"
)
def restartApp(self):
self.stack.setCurrentWidget(self.introPage)
def exitApp(self):
QApplication.instance().quit()
Problem: The QLabel
on the fourth page does not resize correctly to display the video frames in full screen. I've tried different spacing and margin options, but none of them work. It gives white borders on left, right and top
Question: How can I ensure that the QLabel
resizes correctly and displays the video frames in full screen on the fourth page?
Any help or suggestions would be greatly appreciated!