Dotykamy czterdziestego artykułu z cyklu nauki o Pythonie, w którym poruszymy ciekawy temat jako "wisienka na torcie" 🍒. W nawiązaniu do poprzedniego artykułu, w którym wprowadziłem Cię w podstawy tworzenia graficznego interfejsu użytkownika z użyciem modułu "EasyGUI", tutaj pokażę Ci tym razem pakiet przeznaczony również do tworzenia aplikacji graficznych, tylko już o wiele bardziej zaawansowanych 🔥! Sięgniemy po "PyQt5", czyli możliwość programowania GUI w języku Python w oparciu o popularną bibliotekę "Qt" 💥!!! Wyjaśnię Ci czym dokładnie jest ten pakiet, jak się z niego korzysta i jak tutaj projektujemy graficzne aplikacje 💡. Zapraszam, temat będzie dosyć obszerny w czytaniu 😁!
PAKIET "PYQT5" POMOŻE CI W STWORZENIU ZAAWANSOWANEGO GUI!
Zanim zaczniemy przedstawienie samego pakietu i jego możliwości, uprzedzę że należy już posiadać wiedzę na temat klas i obiektów w Pythonie, aby dokładnie rozumieć kody źródłowe przedstawione w dalszej części materiału ⚠️.
Wyjaśnimy sobie w pierwszej kolejności pojęcie "graficznego interfejsu użytkownika", tak abyś miał(a) świadomość w jakim celu są tworzone i dlaczego jest to opłacalne 👍.
CZYM JEST GRAFICZNY INTERFEJS UŻYTKOWNIKA?
Graficzny interfejs użytkownika (ang. Graphical User Interface), to sposób korzystania z danej aplikacji z użyciem graficznych elementów, w której zamiast wprowadzania poleceń jedno po drugim, otrzymujemy widok ułożonych obok siebie różnych komponentów (takich jak przyciski, pola tekstowe czy listy rozwijane), z którymi możemy wejść w interakcję poprzez najeżdżanie myszą czy nawigowanie przy pomocy klawiatury ⭐.
GUI jest bardzo ważnym elementem ułatwiającym korzystanie z programu, ponieważ warstwa graficzna skutecznie "zakrywająca" instrukcje wymagające wiedzy informatycznej, sprawia że każdy może z niego skorzystać, bez względu na zawód jaki wykonuje na co dzień ❤️. Zamiast mogącego budzić zdziwienie hasła "mkdir", człowiek widzi przed sobą abstrakcyjny zapis "Dodaj nowy katalog" 😊. To sprawia, że nie jest potrzebna znajomość informatyki, aby móc poruszać się po programie i z niego korzystać ✅.
Ponadto automatyzujemy pewne czynności, sprowadzając mnóstwo poleceń i instrukcji w jedną wielką "wtyczkę", dzięki której komputer wykonuje całe zadanie od A do Z oczekując tylko jednego kliknięcia. Czyli nawet programiście może to pomóc, bo nie traci czasu na wprowadzanie w kółko tych samych poleceń, tylko wystarczy że kliknie przycisk, wprowadzi dane, a cała reszta robi się sama 🤩!
Graficzna warstwa aplikacji "stoi" pomiędzy użytkownikiem, a seriami instrukcji do wykonania, których rozumienie wymaga wiedzy technicznej z programowania. Dzięki niej, z programu może skorzystać każda osoba, nawet spoza grupy informatycznej 🤩!
Graficzny interfejs użytkownika jest powszechnie stosowany i składają się na to 2 bardzo ważne powody 👇:
- "ukrywają" trudne techniczne hasła pod bardzo przyjaznymi dla człowieka elementami, sprawiając że użytkownik nie musi mieć wiedzy z programowania, aby mógł skorzystać z aplikacji (polecenia są "ubierane" w język abstrakcyjny),
- pozwalają zautomatyzować wiele czynności i poleceń niezbędnych do zrealizowania jakiegoś zadania (np. sprowadzenie kilkunastu instrukcji do pojedynczego kliknięcia przycisku) i znacznie przyspieszyć naszą pracę.
Weźmy za przykład operację zapisu do pliku tekstowego 💾. Tradycyjnie musisz napisać kod, wstawić odpowiednie instrukcje i uruchomić program z konsoli ⏩. To może brzmieć prosto, lecz pamiętaj, że do tego trzeba mieć wiedzę jak to zrobić 🧠! A nie każda osoba jest informatykiem 🙂. Właśnie wtedy przydaje się warstwa graficzna 🎨!
Zamiast uruchamiania z wiersza poleceń, mamy plik wykonywalny na pulpicie 😊. Zamiast pisania kodu, mamy przed sobą okienko z polem tekstowym do wprowadzania nazwy pliku i przyciskami (jeden do wskazania w którym katalogu ma się on znaleźć, a drugi do wykonania operacji zapisu na dysku komputera) 😁. To oznacza, że z tej aplikacji będzie mógł skorzystać nie tylko informatyk, lecz każdy o jakiejkolwiek innej profesji i nie musi wcale wiedzieć co znajduje się "pod spodem" tego okienka 😉!
W tym momencie powinieneś/powinnaś już rozumieć dlaczego warto tworzyć graficzne interfejsy użytkownika (w skrócie GUI) dla własnych programów, więc przejdźmy zatem do poznania pakietu "PyQt5", o którym jest ten materiał 🔍!
CZYM JEST "PYQT5" W JĘZYKU PYTHON?
"PyQt5" to pakiet w języku Python stanowiący tzw. "binding" biblioteki zwanej "Qt", która jest powszechnie stosowana do programowania komercyjnych aplikacji graficznych z użyciem języka C++ ℹ️. Hasło "binding" w informatyce odnosi się do warstwy napisanego kodu źródłowego, za pomocą której komunikujemy się z wartościami i funkcjami kodu napisanego w języku A, używając języka B 🚀. W tym przypadku mamy "przejście" z C++'a do Pythona 🐍. Czyli jednym zdaniem, możemy pisać kod w Pythonie, aby korzystać z funkcjonalności napisanych w C++ 😊.
Korzystając z "PyQt5", jesteśmy w stanie tworzyć aplikacje graficzne funkcjonujące w sposób jaki prezentuje się najczęściej w wielu programach, z których korzystamy na co dzień. Czyli na jednym oknie możemy mieć wiele różnych pojedynczych elementów (tekstów, przycisków, pól tekstowych itp.), możemy wejść z nimi w interakcję kiedy chcemy, każdy z nich może reagować na swój sposób zależnie od jakiegoś zdarzenia i mało tego, mogą przynieść różne konsekwencje też dla innych elementów w tym oknie!
Z tego powodu, tutaj wymaga się od programisty nieco większej wprawy w projektowaniu, ponieważ wiele możliwości dawanych użytkownikowi w jednym czasie oznacza wiele rozwidleń i okoliczności jakie należy wziąć pod uwagę 💥. Na przykład zawartość pola tekstowego może wpływać na przycisk umieszczony tuż obok niego w taki sposób, że zostanie on zablokowany jeśli pole tekstowe jest puste, czyli tak jak jest w wielu grach, że trzeba podać imię bohatera, aby rozpocząć grę 😄. O takie zależności mi chodzi 🙂!
"PyQt5" umożliwia tworzenie zaawansowanych aplikacji z uwagi na możliwość konfigurowania pod wieloma względami, między innymi 👇:
- regulowanie tytułem, pozycją i rozmiarem okna,
- dodawanie wyskakujących okienek w postaci komunikatów,
- dodawanie elementów i definiowanie określonych reakcji na dane zdarzenia (np. co ma się stać po kliknięciu przycisku).
W dalszej części materiału opiszę dokładnie na czym to polega ℹ️.
Zwrócę jeszcze Twoją uwagę na fakt, iż oryginalna biblioteka "Qt", na bazie której powstał pakiet "PyQt5", jest produktem komercyjnym 💵. To oznacza, że możesz potrzebować odpowiedniej licencji na używanie pakietu do celów komercyjnych mimo tego, że sam pakiet jest w pełni darmowy ⚠️! Także gdy kiedykolwiek zainteresujesz się tworzeniem aplikacji graficznych z użyciem "PyQt5" na poważnie, upewnij się że twórcy biblioteki "Qt" zezwalają na taką ewentualność 🔥! Korzystanie z darmowego pakietu pochodzącego od komercyjnej biblioteki nie zwalnia Cię ze sprawdzenia braku konieczności posiadania ważnej licencji oryginału 🫵.
Wiemy już czym jest "PyQt5", a zatem przejdźmy do wytłumaczenia procesu instalacji (jako, że ten pakiet nie zawiera się w standardowej bibliotece Pythona 🙂) ⏏️!
JAK ZAINSTALOWAĆ PAKIET "PYQT5" W JĘZYKU PYTHON?
Musimy sobie włączyć wiersz poleceń (proponuję uruchomić jako administrator) i po upewnieniu się, że w zmiennej środowiskowej "Path" mamy dodaną ścieżkę prowadzącą do zainstalowanego Pythona, wpisujemy sobie poniższe polecenie i zatwierdzamy klawiszem Enter 👇:
pip install pyqt5To uruchomi instalator pakietów "pip", a on z kolei rozpocznie pobieranie pakietu "PyQt5" 🚀. Po pobraniu łącznie ponad 50 MB, na końcu powinieneś/powinnaś ujrzeć komunikat w takim stylu 👇:
Successfully installed PyQt5-Qt5-5.15.2 PyQt5-sip-12.19.0 pyqt5-5.15.11Wtedy możesz być pewny(-a), że pakiet został zainstalowany i od teraz jest do Twojej dyspozycji 😄!
To teraz dowiedzmy się jak z niego korzystać 🔍!
JAK SKORZYSTAĆ Z PAKIETU "PYQT5" W JĘZYKU PYTHON?
W Pythonie jest taki zwyczaj, że aby uzyskać dostęp do modułu czy pakietu podczas pisania kodu, należy go wpierw zaimportować ↩️. Natomiast w "PyQt5" piszemy troszkę inaczej, niż zazwyczaj. Mając otwarty dowolny skrypt, wprowadź na samej górze poniższą instrukcję 👇:
import PyQt5.QtWidgetsGotowe, od tej pory możesz korzystać ze wszystkich wartości i funkcji jakimi dysponuje ten pakiet ✅. Nie kończymy na samym "PyQt5", tylko dopisujemy "QtWidgets", gdyż to jest docelowe miejsce z definicjami komponentów, z jakich będziemy korzystać w tym materiale 💥!
Jeżeli nie chcesz importować całości, tylko jakiś jeden element (dana wartość i/lub funkcja), to możesz skorzystać z alternatywnej formy zapisu z użyciem słowa kluczowego "from" 👇:
from PyQt5.QtWidgets import [wartość/funkcja występująca w module/pakiecie]Tylko pamiętaj, że obie formy mają również wpływ na sposób odwoływania się do poszczególnych wartości i funkcji ⚠️! Więcej informacji na ten temat znajdziesz w załączonych artykułach ℹ️. Ja do ukazywanych kodów źródłowych będę posługiwał się pierwszym zapisem 1️⃣.
Instalację oraz dostęp do pakietu "PyQt5" mamy wyjaśnione, także teraz możemy przejść do części związanej z tworzeniem aplikacji graficznych 🎨! Abyśmy mogli postawić pierwsze kroki poprzez kod źródłowy, musimy rozumieć jak w ogóle powstaje taka aplikacja, czysto teoretycznie 🧩.
JAK POWSTAJE GRAFICZNY INTERFEJS UŻYTKOWNIKA POPRZEZ PAKIET "PYQT5" W JĘZYKU PYTHON?
Używając pakietu "PyQt5", aplikacja graficzna powstaje poprzez 2 kroki 2️⃣. Najpierw tworzymy samo okienko, czyli powierzchnię na której można "położyć" przeróżne komponenty, a potem budujemy same komponenty (przyciski, teksty, tabele itp.), nadajemy im właściwości i ustalamy w jakiej pozycji mają się znaleźć. Ponadto, mamy też możliwość programowania zachowania niektórych elementów, aby wykonywały pewne czynności w momencie jakiegoś zdarzenia 🚨. Może to być przeciągnięcie suwaka, zaznaczenie opcji w stylu wł./wył. (tzw. "ptaszek") lub też wprowadzenie dowolnego znaku do pola tekstowego 👍. To są przykładowe zdarzenia, do których możemy dodać funkcje wywołujące się w odpowiednim momencie (określamy to "wywołaniem zwrotnym", po angielsku "callback" ℹ️).
Pozycjonowanie komponentów w "PyQt5" odbywa się poprzez ustawianie współrzędnych znanych z matematyki w stylu "(X = 350, Y = 220)" 📐. Warto jednak abyś wiedział(a), że nie zawsze tak musi być i to zależy od samej biblioteki odpowiedzialnej za tworzenie graficznych interfejsów użytkownika ⚠️. Możesz się spotkać również z metodą rozmieszczania komponentów po określonych częściach okna nazywanych czasem "regionami", czyli np. określasz, że chcesz aby komponent zajął całą górną część okna, a rozmiar odpowiednio się skaluje zależnie od jego rozmiaru i może być dla przykładu 100% szerokości i 20% wysokości 💡. Takie podejście sprawia, że wymiary są zawsze proporcjonalne do wymiarów okna, a nie według sztywno przypisanych pikseli 🔥.
Wszystko co chciałem o tym napisać tytułem wstępu, a teraz czas wreszcie przejść do praktyki 🚀! Postąpimy według kroków opisanych wyżej, czyli najpierw utworzymy sobie samo okno, a potem pokażę parę dostępnych elementów (komponentów) i jak je "nałożyć" na okno 👍.
JAK UTWORZYĆ OKNO APLIKACJI GRAFICZNEJ Z UŻYCIEM PAKIETU "PYQT5" W JĘZYKU PYTHON?
Aby utworzyć okno w pakiecie "PyQt5", musimy wykonać 4 następujące kroki 👇:
- utworzyć obiekt dla całej aplikacji graficznej używając konstruktora klasy "QApplication",
- utworzyć obiekt używając konstruktora klasy "QWidget",
- wywołać metodę z obiektu okna "show", aby je wyświetlić,
- wywołać metodę z obiektu aplikacji "exec" celem jej uruchomienia.
Idźmy po kolei. Najpierw korzystamy z konstruktora klasy "QApplication" celem utworzenia samej aplikacji jako nadrzędnego obiektu dla całej reszty 👇:
my_application = PyQt5.QtWidgets.QApplication([])"QApplication" tworzy sam proces aplikacji przyjmując w parametrze listę argumentów, takich samych jakie się wprowadza w wierszu poleceń chcąc uruchomić jakiś program (często charakterystycznym symbolem jest poprzedzanie ich myślnikiem) ℹ️. Nie korzystamy z nich, więc wpisujemy pustą listę, natomiast ważne jest, aby nie zapomnieć jej wstawić! To jest obowiązkowy parametr ⚠️!
Następnie tworzymy sobie tzw. "widżet", czyli graficzny element aplikacji, którym w tym wypadku będzie całe okno (aplikacja jest jednym obiektem, a okno dla niej, osobnym ⚠️) 👇:
my_widget = PyQt5.QtWidgets.QWidget()W punkcie trzecim, wywołujemy metodę "show" na obiekcie naszego widżetu (okna), abyśmy mogli je zobaczyć na ekranie 👇:
my_widget.show()Jest to niezbędne, ponieważ bez tego wywołania uruchomi się tylko sam proces (czyli program wykonujący się w tle ℹ️), który będzie stale aktywny, natomiast nie ujrzymy żadnych zmian na ekranie 😐.
Na sam koniec wywołujemy metodę "exec", która oznacza dosłowne "uruchomienie" aplikacji 👇:
my_application.exec()To z kolei sprawi, że wyświetlone okno zostanie "podtrzymane" w takim stanie, gdyż jeżeli tego wywołania zabraknie, to podczas uruchamiania programu zobaczysz okno tylko na ułamek sekundy, które natychmiastowo zgaśnie 😁. To odpowiada za odbieranie sygnałów od użytkownika, takich jak na przykład zamknięcie okna po kliknięciu "krzyżyka" w prawym górnym rogu ❌.
To jest absolutne minimum do utworzenia okna w pakiecie "PyQt5". Uruchomienie takiego programu spowoduje wyświetlenie pustego okna bez zawartości 👇:
![]() |
Widok okna aplikacji graficznej pakietu "PyQt5".
Komponenty, takie jak przyciski czy pola tekstowe, umieszczane są osobno jako elementy "nakładane" na to okno (widżet) ℹ️. Zanim jednak przejdziemy do nich, chciałbym Ci jeszcze przedstawić jak możemy wpływać na samo okno, czyli jak zmienić tytuł i wymiary 🙂.
JAK ZMIENIĆ WŁAŚCIWOŚCI OKNA APLIKACJI GRAFICZNEJ W PAKIECIE "PYQT5" W JĘZYKU PYTHON?
Celem modyfikacji właściwości samego okna naszej aplikacji np. tytuł czy jego wymiary, trzeba sobie utworzyć klasę potomną od klasy "QWidget", która reprezentuje obiekt okna 💡. "Qt" zostało skonstruowane na kształt paradygmatu obiektowego, stąd moja przestroga na samej górze artykułu 🙂.
Klasa potomna w programowaniu obiektowym oznacza to, iż "pochodzi" od innej klasy (nazywanej wtedy "klasą bazową"). To sprawia, że ona przejmuje pewne jej właściwości i metody, dzięki czemu nie musimy ich pisać drugi raz ✅. Pomiędzy takimi klasami zachodzi wtedy relacja "JEST" i ma ona szczególne znaczenie dla polimorfizmu - jednej z najważniejszych zasad programowania obiektowego 😱! Nie będę tutaj rozpisywać szczegółów, tylko skieruję Cię do odpowiedniego artykułu, a my przechodzimy prosto do przedstawienia definicji takiej klasy dla okna ⏩!
Oto najbardziej podstawowa postać klasy potomnej klasy "QWidget", na razie bez żadnych modyfikacji 👇:
class MyWindow(PyQt5.QtWidgets.QWidget):
def __init__(self):
super().__init__()Usunąłem dodatkowe parametry jakie przyjmuje klasa "QWidget", aby nie zaciemniać istoty sprawy ℹ️. Teraz gdy mamy własną klasę dla okna, możemy swobodnie ją modyfikować 😄! Najlepiej wszelkie instrukcje umieszczać bezpośrednio po wywołaniu z hasłem "super" (wywołanie metody o tej samej nazwie o treści zawartej w klasie bazowej) 👍.
Tylko jeszcze zanim zaczniesz cokolwiek dodawać, nie zapomnij o zamianie konstruktora klasy dotyczącej okna na tę powyższą 👇:
my_widget = MyWindow()Tytuł okna możesz zmienić za pomocą wywołania metody "setWindowTitle" 👇:
self.setWindowTitle('Moje okno PyQt5')Podając dowolny łańcuch znaków, nadajesz oknu nowy tytuł umieszczony na listwie z przyciskami w prawym górnym rogu (minimalizacja, maksymalizacja, zamknięcie) ❤️.
Z kolei rozmiar okna zmieniamy poprzez użycie innej metody, "setFixedSize" 👇:
self.setFixedSize(PyQt5.QtCore.QSize(640, 320))Ona przyjmuje parametr niestandardowego typu danych "QSize", który oznacza jedynie współrzędne w osi X oraz Y - dokładnie, jak w matematyce 😄. Wstawiając do obu parametrów kolejno szerokość i wysokość, sprawisz że okno przyjmie dokładnie takie wymiary 😊.
Gdy wprowadzimy obie wyżej wymienione zmiany, to po uruchomieniu aplikacja graficzna będzie wyglądać tak 👇:
![]() |
Widok okna aplikacji graficznej pakietu "PyQt5" ze zmienionym tytułem i wymiarami.
Jest o wiele więcej innych metod jakimi możemy się posługiwać do edycji różnych szczegółów okna, więc zajrzyj do oficjalnej dokumentacji biblioteki "Qt", jeśli interesuje Cię ten temat 📖.
Okno dla aplikacji graficznej powstaje poprzez utworzenie dwóch osobnych obiektów: "QApplication" (proces) i "QWidget" (okno).
Teraz czas poznać kilka elementów jakie możemy dodać do samego okna i ujrzeć coś więcej niż pustą stronę 😅!
JAKIE ELEMENTY GRAFICZNEGO INTERFEJSU UŻYTKOWNIKA POSIADA PAKIET "PYQT5" W JĘZYKU PYTHON?
W pakiecie "PyQt5" znajduje się wiele elementów (komponentów), z których możemy budować aplikacje graficzne, wśród których występuje między innymi 👇:
- QLabel (tekst zwany "etykietą"),
- QPushButton (przycisk),
- QTableWidget (widżet tabeli takiej, jak w "Microsoft Excel"),
- QVBoxLayout (widżet układający komponenty w pionie),
- QMessageBox (okno komunikatu).
Naturalnie to nie są wszystkie elementy jakimi może się pochwalić ten pakiet 😉, więc sięgnij do oficjalnej dokumentacji "PyQt5", aby dowiedzieć się więcej 📖. W niniejszym materiale zaprezentuję tylko te wyżej wymienione, a więc zaczynamy ⏩!
QLABEL
"QLabel" oznacza "etykietę", czyli miejsce na tekst 🔤 albo grafikę 🎨. Tworzy obszar, na którym może się znaleźć jeden z tych dwóch elementów. Aby wyświetlić etykietę, wystarczy utworzyć sobie obiekt korzystając z konstruktora klasy "QLabel" 👇:
my_label = PyQt5.QtWidgets.QLabel(my_widget)Należy koniecznie wprowadzić parametr oznaczający jaki element ma "nosić" tę etykietę ⚠️. Wtedy taki obiekt jest nazywany "rodzicem", a ten znajdujący się "w środku" staje się "dzieckiem" bądź "obiektem potomnym" ℹ️.
Tuż po tej instrukcji, od razu dodaj sobie to wywołanie metody "setText" 👇:
my_label.setText('Moja etykieta')Bez tego nie będzie w ogóle widać czy stworzyła się jakakolwiek etykieta w oknie (zawartość będzie pusta), a konstruktor nie udostępnia możliwości przypisania jakiejkolwiek zawartości już w momencie tworzenia etykiety 😐. Ważne jest, aby obie te instrukcje umieścić PRZED wywołaniami metod "show" i "exec" ⚠️!
Gdy uruchomisz sobie program, Twoim oczom ukaże się niewielkich rozmiarów tekst jaki wpisałeś(-aś) w miejsce parametru metody "setText" 👇:
![]() |
Widok elementu "QLabel" pakietu "PyQt5".
I to tyle.
Element "QLabel" oznacza dosłownie "etykietę" - obszar na którym możesz wstawić tekst albo obrazek graficzny.
Przechodzimy do kolejnego elementu ➡️!
QPUSHBUTTON
"QPushButton" reprezentuje przycisk do kliknięcia ⏏️. Używając konstruktora klasy o tej samej nazwie, możesz w prosty sposób utworzyć obiekt przycisku o napisie, jaki tylko sobie życzysz umieścić 👇:
my_push_button = PyQt5.QtWidgets.QPushButton('Mój przycisk', my_widget)Dwa parametry jakie powinieneś/powinnaś wstawić, to 👇:
- łańcuch znaków oznaczający napis jaki znajdzie się na przycisku,
- wskazanie elementu graficzny jaki ma być "rodzicem" tego przycisku (obiektem, który będzie zawierał ten obiekt).
To wystarczy, aby ujrzeć przycisk na oknie , który wygląda tak 👇:
![]() |
Widok elementu "QPushButton" pakietu "PyQt5".
Możemy go sobie klikać do woli 😄. Natomiast na tym etapie klikanie przycisku nic nie da, ponieważ nie określiliśmy żadnej reakcji na to zdarzenie 🔥. Musimy dodać wywołanie następującej metody 👇:
my_push_button.clicked.connect(print_message)"clicked" oznacza rodzaj zdarzenia typu "naciśnięty" ⏏️. Pamiętaj, że jest wiele innych rodzajów zdarzeń np. "najechany kursorem myszy" i taki panuje zwyczaj tworzenia połączeń w bibliotekach do tworzenia graficznych interfejsów użytkownika pomiędzy akcjami, a reakcjami 🙂.
Metoda "connect" oczekuje podania parametru w postaci nazwy funkcji jaka ma zostać wywołana po kliknięciu przycisku 🚀. Taki zapis dodaje tzw. "wywołanie zwrotne" (ang. callback) 😮. To jest funkcja, która wywołuje się samoistnie w wyniku jakiegoś zdarzenia 💡. To oznacza, że z chwilą kliknięcia na przycisk powstanie reakcja na to zdarzenie w postaci wywołania funkcji, którą określamy w miejscu parametru 💥!
Dla tego przykładu dodajmy sobie najprostszą postać 👇:
def print_message():
print('Przycisk został kliknięty!')Gdy teraz uruchomisz program i klikniesz na przycisk, to ujrzysz w konsoli podany komunikat 😁! Może jednak powstać problem, gdybyśmy potrzebowali przekazać takiej funkcji parametr 😬.
Parametr metody "connect" jest "gniazdem" dla funkcji bezparametrowej. Wtedy mając funkcję z parametrem 👇:
def print_message(message):
print(message)wstawienie samej nazwy funkcji zakończy się fatalnie, ponieważ żadne parametry nie zostaną wprowadzone ❌! Co gorsza nie da się w sposób tradycyjny wprowadzić parametrów, gdyż w tamto miejsce należy wpisać samo odwołanie do funkcji 😳.
Wtedy musisz skorzystać z nietypowego obejścia w postaci użycia hasła "lambda" i cały parametr napisać w takiej formie 👇:
my_push_button.clicked.connect(lambda: print_message('Przycisk został kliknięty!'))Taka konstrukcja jest nazywana "wyrażeniem lambda" (ang. lambda expression), czyli zdefiniowanie funkcji anonimowej "wplecionej" bezpośrednio w miejsce parametru 🔥. Więcej informacji o samej konstrukcji znajdziesz w załączonym artykule ℹ️, a w powyższym przypadku tworzymy taką "otoczkę" wokół funkcji, która musi przyjąć jakiś parametr 💥. Innymi słowy, w miejsce parametru utworzyliśmy funkcję bezparametrową, w której znajduje się wywołanie funkcji z parametrem 😅. To jest jedyny sposób na wprowadzenie funkcji z określeniem parametrów jakie mają się znaleźć 👍.
Choć zapis może wyglądać na przerażający, to jest jak najbardziej "legitny" od strony składni i to uruchomi się bez żadnych problemów ✅. Teraz możesz umieszczać tyle parametrów ile potrzebuje funkcja, którą wywołujesz 😄!
To wszystko, co warto wiedzieć na temat przycisków w pakiecie "PyQt5" 👍. Jeżeli niczego nie widzisz w oknie upewnij się, że wszystkie te instrukcje są wstawione PRZED wywołaniami metod "show" i "exec" ⚠️! One muszą być jako ostatnie!
Za pomocą elementu "QPushButton" tworzymy przycisk, który można kliknąć i dodać określoną reakcję na to zdarzenie.
Teraz następny element ➡️!
QTABLEWIDGET
"QTableWidget" to element do tworzenia widoku tabeli. Takiej samej tabeli jaką widzimy we wszystkim znanym oprogramowaniu "Microsoft Excel" 😊. Wystarczy utworzyć obiekt typu "QTableWidget" korzystając z konstruktora klasy o tej samej nazwie 👇:
my_table_widget = PyQt5.QtWidgets.QTableWidget(3, 5, my_widget)Parametry jakie należy umieścić, to 👇:
- liczba rzędów (całkowitoliczbowy typ danych),
- liczba kolumn (całkowitoliczbowy typ danych),
- element graficzny jaki ma być "rodzicem" tejże tabeli.
Ta jedna instrukcja wystarczy w zupełności, aby po uruchomieniu programu zobaczyć wewnątrz okna obszar z tabelką w środku do przeciągania w poziomie i w pionie 👇:
![]() |
Widok elementu "QTableWidget" modułu "EasyGUI".
Warto wiedzieć, że możemy wpływać na komórki tabeli w trakcie wyświetlania aplikacji ❤️. Wystarczy podwójnie kliknąć na jedną z nich i komórka zamieni się w pole tekstowe, do którego możemy wprowadzać dowolny ciąg znaków 😄. Gdybyśmy chcieli, aby jakieś hasła występowały już od samego początku, musimy dopisać wywołanie metody "setItem" 👇:
my_table_widget.setItem(0, 0, PyQt5.QtWidgets.QTableWidgetItem('Moja komórka'))i podać w parametrach kolejno: indeks rzędu (według notacji indeksowej), indeks kolumny (również według notacji indeksowej) oraz obiekt typu "QTableWidgetItem", który oznacza pojedynczą komórkę tabeli przygotowaną pod ten element 💡. Współrzędne komórek opierają się na notacji indeksowej, tak jak w listach i krotkach, czyli elementy liczone są od zera ⚠️!
Jeżeli masz problemy z ustaleniem które wartości wprowadzić, aby dostać się do komórki, o którą Ci chodzi, może być pomocne spojrzenie na to, jak na listę dwuwymiarową ℹ️.
Wyjątkowo tutaj nie dochodzi do zgłoszenia jakiegokolwiek błędu, gdy przez przypadek wyjdziesz poza zakres liczby rzędów czy kolumn. Wtedy po prostu nic się nie stanie 🙂. Gdy teraz uruchomisz program, to ujrzysz podany łańcuch znaków we wskazanej komórce tabeli już od razu 👍!
Na sam koniec pokażę Ci jeszcze dwie metody, które poszerzają wymiary tabeli dostosowując szerokość i wysokość do wielkości rzędów i kolumn 👇:
my_table_widget.resizeRowsToContents()
my_table_widget.resizeColumnsToContents()"resizeRowsToContents" poszerza obszar przeznaczony dla tabeli według rzędów, a "resizeColumnsToContents", według kolumn 😉.
Używając elementu "QTableWidget", jesteś w stanie utworzyć tabelę znaną z arkuszów kalkulacyjnych o dowolnej liczbie rzędów i kolumn!
"QTableWidget" wyjaśnione ✔️. Idziemy dalej ➡️.
QVBOXLAYOUT
"QVBoxLayout" odnosi się do prostokątnego obszaru, w którym elementy znajdujące się wewnątrz niego układają się pionowo ↕️. Jest jednym z kilku dostępnych rodzajów układów umieszczających jeden obiekt pod drugim. Możemy chcieć mieć ładnie ułożone przyciski albo sekcje z nagłówkami, poniżej których znajdują się pola tekstowe. Do tego właśnie celu służą układy 💡.
Układ "QVBoxLayout" powstaje poprzez utworzenie obiektu z konstruktora klasy noszącej tę samą nazwę 👇:
my_vbox_layout = PyQt5.QtWidgets.QVBoxLayout(my_widget)Można dodać nieobowiązkowy parametr wskazując jaki element ma "posiadać" ten układ ℹ️.
Dodanie tego układu "w czystej postaci", spowoduje pojawienie się białej "ramki" wokół całej powierzchni okna bez niczego. Dlatego też warto od razu przedstawić metodę przeznaczoną do dodawania widżetów do środka tej "ramki", "addWidget" (przykład pokazuje dodawanie przycisku "QPushButton" do środka) 👇:
my_vbox_layout.addWidget(my_table_widget)Akurat ta metoda przyjmuje jedynie inne obiekty widżetowe, więc na przykład obiekt typu "QLabel" (etykieta) nie zostanie zaakceptowany (wtedy trzeba osadzić jeden element w drugim ℹ️) 🚫.
Wprowadzenie tej instrukcji do kodu, przyniesie taki skutek 👇:
![]() |
Widok elementu "QVBoxLayout" pakietu "PyQt5" po dodaniu przycisku.
Przycisk wewnątrz tej "ramki", a w rzeczywistości prostokątnego obszaru układającego elementy pionowo 😉. W tym przypadku jako jedyny obiekt znajdujący się w środku ma całą przestrzeń dla siebie, więc został umieszczony na środku 😲. Gdy dodasz ponowne wywołanie tego samego, lecz tym razem dasz na przykład poznaną tabelę "QTableWidget" 👇:
my_vbox_layout.addWidget(my_table_widget)to wtedy ujrzysz taki efekt 👇:
![]() |
Widok elementu "QVBoxLayout" pakietu "PyQt5" po dodaniu przycisku i tabeli.
Wówczas każdy z elementów ma dla siebie tyle miejsca, ile potrzebuje 😉. I jak widzisz, są rozmieszczone pionowo 👍.
Element "QVBoxLayout" przeznaczony jest do tworzenia odrębnego prostokątnego obszaru, wewnątrz którego elementy są układane pionowo.
No to na koniec ostatni element z listy ➡️!
QMESSAGEBOX
"QMessageBox", to najprościej ujmując wyskakujące okno określane jako "okno dialogowe" 💬. Obejmuje to kilka znanych rodzajów komunikatów 👇:
- about (okno informacyjne z nagłówkiem i tekstem),
- critical (okno z błędem),
- aboutQt (okno informacyjne dotyczące używanej wersji biblioteki "Qt"),
- warning (okno z ostrzeżeniem),
- question (okno z zapytaniem),
- information (okno informacyjne z pojedynczym tekstem).
Pokażę Ci jak to stosować używając typu "question" 🙂. To jest przykład wywołania metody o tej samej nazwie 👇:
my_answer = PyQt5.QtWidgets.QMessageBox.question(my_widget, 'Pytanie', 'Czy chcesz wyświetlić okno?')Zauważ, że najpierw odnosimy się do "QMessageBox", a potem do danego rodzaju komunikatu. Parametry jakie przyjmuje ta metoda, to 👇:
- element graficzny, który ma zostać "przykryty" oknem dialogowym (chodzi o to charakterystyczne blokowanie okna pod spodem przez system operacyjny i sygnał dźwiękowy, gdy klikniemy na nie, jak dane okno dialogowe jest widoczne i "zasłania" je 🚨),
- łańcuch znaków jako tytuł okna komunikatu,
- łańcuch znaków jako treść zapytania pod przyciskami do wyboru (tak/nie).
W tym przypadku, to w którym miejscu umieścimy sobie to wywołanie, ma ogromne znaczenie dla efektu wizualnego 👀! Jeżeli ona znajdzie się PRZED wywołaniem metody "show", to komunikat pojawi się ZANIM wyświetli się całe okno! Z kolei gdy wstawimy ją PO metodzie "show", to najpierw wyświetli się okno, a potem na nim pojawi się komunikat 💥! Także warto, abyś o tym pamiętał(a) 🫵!
Gdy uruchomimy sobie program z tą instrukcją, ujrzymy komunikat takiej postaci 👇:
![]() |
Widok elementu typu "question" pakietu "PyQt5".
Tu dodatkowa rzecz co do przypisania do zmiennej ⚠️! Gdy dany komunikat pojawia się na ekranie, to zaznaczamy przycisk i on znika, natomiast może zostać zapamiętana opcja jaką wybraliśmy 😱! Tak jest w tym przypadku!
Z chwilą wybrania jednej z opcji dostępnych w oknie dialogowym, zmienna przyjmuje jedną z charakterystycznych wartości typu "QMessageBox" 🔥. Dla typu "question", występują 2 rodzaje takiej wartości 👇:
- QMessageBox.No,
- QMessageBox.Yes.
Mając tę wiedzę, możemy skorzystać z tej informacji i wpłynąć na dalszy ciąg programu, podstawiając ją choćby pod instrukcję warunkową 💡! Oto przykład 👇:
if my_answer == PyQt5.QtWidgets.QMessageBox.Yes:
my_application.exec()Pamiętaj, że możesz skorzystać z poznanego wcześniej operatora relacyjnego w postaci alternatywy i tym samym sprawiać, aby coś się stało, gdy wartość przyjmuje jeden bądź drugi typ 👇:
if my_answer == PyQt5.QtWidgets.QMessageBox.Yes or my_answer == PyQt5.QtWidgets.QMessageBox.No:
my_application.exec()Ponieważ w typie "question" są tylko te dwie możliwości, to warunek zawsze będzie spełniony, niezależnie od tego co klikniemy 😁.
Za pomocą elementu "question" z klasy "QMessageBox", tworzysz okno dialogowe w formie zapytania. Zwracana wartość zapamiętuje kliknięty przycisk, której można później użyć do podstawiania do instrukcji warunkowych.
Koniec. Artykuł wyszedł naprawdę duży, nawet jak wprowadził Cię w same podstawy pakietu "PyQt5" 😊. Pamiętaj, że możesz skorzystać z dokumentacji zarówno samego "PyQt5", jak i oficjalnej dokumentacji biblioteki "Qt", która stanowi podstawę tego "bindingu" stworzonego do Pythona ❤️.
Wszystko na temat pakietu "PyQt5" ✅. Może na początku sprawiać trudność rozumienie całego procesu budowania okna, natomiast sam pakiet został naprawdę porządnie zrobiony na bazie biblioteki napisanej oryginalnie w języku C++ i doskonale spełnia swoje zadanie, aby umożliwić tworzenie własnych aplikacji graficznych z użyciem "Qt" w Pythonie 🏆.







