본문 바로가기
Python

[PyQT5] 처음부터 따라하기 #4. ui component binding

by bryan.oh 2022. 3. 17.
반응형

PyQT5 따라하기 #4
UI Components Binding
Python 에서 UI Component 사용하기

 

이전 글에 이어서 소스에 추가를 하겠습니다.

self.window = loader.load(ui_file)

이렇게 window 를 load 했다면, 바인딩 하는 코드는

self.my_line_edit = self.window.findChild(QLineEdit, objectName)
# 여기서 objectName 은 designer.exe 에서 설정한 objectName 입니다.

designer.exe 의 objectName

 

바인딩

저는 편하게 쓰기 위해서 private 함수를 만들어봤습니다.

def __bindQLineEdit(self, objectName):
    return self.window.findChild(QLineEdit, objectName)
def __bindQDateEdit(self, objectName):
    return self.window.findChild(QDateEdit, objectName)
def __bindQLabel(self, objectName):
    return self.window.findChild(QLabel, objectName)
def __bindQPlainTextEdit(self, objectName):
    return self.window.findChild(QPlainTextEdit, objectName)
def __bindQComboBox(self, objectName):
    return self.window.findChild(QComboBox, objectName)
def __bindObject(self, qType, objectName):
    return self.window.findChild(qType, objectName)

그리고 호출해서 바인딩을 합니다.

self.lineEdit_file = self.__bindQLineEdit('fileLineEdit')
self.textEdit_log = self.__bindQPlainTextEdit('logPlainTextEdit')
fileLineEdit 와 logPlainTextEdit 는 designer.exe 에서 설정한 objectName 입니다.

 

바인딩 되었으면 python code 에서 해당 component 에 접근할 수 있습니다.

self.lineEdit_file.setText("PDF 파일을 선택해 주세요.")

 

 

 

버튼 바인딩 

버튼 클릭도 규칙을 만들었습니다.

def __bindQPushButton(self, objectName):
    btn = self.window.findChild(QPushButton, objectName)
    eval(f'btn.clicked.connect(self.click_{objectName})')
    return btn

objectName 의 버튼을 바인딩 하고, 클릭 이벤트까지 연결합니다.

이름은 click_{objectName} 입니다. 이 함수가 class 내에 def 되어있으면 그 함수를 호출합니다.

예를들어 objectName 이 selectPdfButton 이라면 class method 로 아래와 같이 존재해야 됩니다.

def click_selectPdfButton(self):
    self.textEdit_log.appendPlainText("click selectPdfButton!\n")

 

전체소스

test.py
import sys

from PySide2.QtWidgets import QApplication, QPushButton, QLineEdit, QPlainTextEdit
from PySide2.QtCore import QFile, QObject
from PySide2.QtUiTools import QUiLoader

UI_FILE_PATH = './PdfExtractorUI.ui'


class App(QObject):
    def __init__(self, ui_file_name, parent=None):
        super(App, self).__init__(parent)
        ui_file = QFile(ui_file_name)
        ui_file.open(QFile.ReadOnly)
        loader = QUiLoader()
        self.window = loader.load(ui_file)
        ui_file.close()
        # 여기 까지 고정

        self.bindComponents()   # [Custom] designer 에서 생성한 component들을 이 class 변수로 바인딩
        self.setDefaultComponents()  # [Custom] component의 기본값은 여기에서 설정

        # 화면에 띄움.
        self.window.show()

    def bindComponents(self):
        """
        bind with components
        """
        self.btn_select_pdf = self.__bindQPushButton('selectPdfButton')
        self.lineEdit_file = self.__bindQLineEdit('fileLineEdit')
        self.textEdit_log = self.__bindQPlainTextEdit('logPlainTextEdit')

    def setDefaultComponents(self):
        """
        초기값/상태 설정
        """
        self.lineEdit_file.setText("PDF 파일을 선택해 주세요.")

    def __bindQLineEdit(self, objectName):
        return self.window.findChild(QLineEdit, objectName)
    def __bindQDateEdit(self, objectName):
        return self.window.findChild(QDateEdit, objectName)
    def __bindQLabel(self, objectName):
        return self.window.findChild(QLabel, objectName)
    def __bindQPlainTextEdit(self, objectName):
        return self.window.findChild(QPlainTextEdit, objectName)
    def __bindQComboBox(self, objectName):
        return self.window.findChild(QComboBox, objectName)
    def __bindObject(self, qType, objectName):
        return self.window.findChild(qType, objectName)
    def __bindQPushButton(self, objectName):
        btn = self.window.findChild(QPushButton, objectName)
        # 버튼은 click_{버튼명} 으로 App 의 함수로 바인딩 시켜줌. click_{버튼명}의 함수가 존재해야함.
        eval(f'btn.clicked.connect(self.click_{objectName})')
        return btn

    def click_selectPdfButton(self):
        self.textEdit_log.appendPlainText("click selectPdfButton!\n")

if __name__ == '__main__':
    app = QApplication(sys.argv)
    form = App(UI_FILE_PATH)

    sys.exit(app.exec_())

 

 

실행 결과

 

 

 

728x90
반응형

댓글