Hepsinde undefined variable yazıyor kısacası
Pomodoro.py
çalıştırıldığında ne hata veriyor?
Pomodoro.py Çalıştığında herhangi bir hata vermiyor.
Üzerinde çalıştığımız py dosyası zaten. Yani benim yazdığım.
sizin yazdığınız şekilde düzenledim self.yazialani kısmını.
Bu çıkıyor ve sonrasında herhangi bir şey olmuyor.
Ben “Pomodoro için hangi işlemi uygulayacaksınız” kısmını değiştirmek istiyordum sadece.
Fakat 5dk’ya bastım mesela. 5 dakikaya bastığımda değil 5dk bitince yazı değişiyor
O zaman sorun yok.
Güzel.
‘Tamam’ dediğinizde pencere gelmiyor mu?
QMessageBox
, exec()
edildikten sonra text
’i değiştirilemez.
Neden yeni QMessageBox
lar oluşturmuyorsunuz? veya QMessageBox
şart mı?
Bence bir label
fazlasıyla işimizi görür.
Bu programda da mesela QLabel Kullandım. Ancak butonlar çalıştığında yazı değişiyor.
şimdi pomodoro.py’de ne var da bu sefer yazı değişmiyor ?
Bence de QMessageBox kısmına zaten boşuna girdik.
Fakat işte dediğim gibi bu programda nedense QLabel olmuyor
import sys
from PyQt5 import QtWidgets
from PyQt5 import QtGui
class window(QtWidgets.QWidget):
def __init__(self):
super().__init__()
self.init_ui()
def init_ui(self):
self.yazialani = QtWidgets.QLabel("0")
self.button1 = QtWidgets.QPushButton("+1 eklemek için bana bas")
self.button2 = QtWidgets.QPushButton("-1 eklemek için bana bas")
self.say = 0
v_box = QtWidgets.QVBoxLayout()
v_box.addWidget(self.button1)
v_box.addWidget(self.button2)
v_box.addWidget(self.yazialani)
v_box.addStretch()
h_box = QtWidgets.QHBoxLayout()
h_box.addStretch()
h_box.addLayout(v_box)
h_box.addStretch()
self.setLayout(h_box)
self.button1.clicked.connect(self.click)
self.button2.clicked.connect(self.click2)
self.show()
def click(self):
self.say += 1
self.yazialani.setText("{}".format(str(self.say)))
def click2(self):
self.say -= 1
self.yazialani.setText("{}".format(str(self.say)))
app = QtWidgets.QApplication(sys.argv)
pencere = window()
etiket = QtWidgets.QLabel(pencere)
etiket.setPixmap(QtGui.QPixmap("kartal.jpg"))
etiket.move(400,200)
sys.exit(app.exec_())
Yazı bu programda değişiyor.
Gayet temiz bir şekilde.
Bu kısmı şöyle değiştirdiğinizde çalışmıyor mu?
self.yazialani = QtWidgets.QLabel("Pomodoro Tekniği İçin Hangisini seçeceksin ")
Şuanda aynen bu şekilde
Blok-alıntı
self.yazialani = QtWidgets.QLabel(“Pomodoro İçin Hangi İşlemi Uygulayacaksınız ?”)
Fakat yazı dakika bitince değişiyor. Butona tıkladığımda değil.
Yani aslında çalışıyor fakat dakika bitince çalışıyor diyeyim.
Butona tıklayınca yazması lazımdı oysaki
Butonların tetikledikleri tüm fonksiyonların altında label
'ın text
'ini değiştirin.
Bkz. QLabel().setText()
Örneğin:
def period1(self):
self.timer.stop()
self.timer.singleShot(300000, lambda:self.audio.play())
QMessageBox.information(self, "Bilgilendirme", "5 dakikalık periyot başladı.")
self.yazialani.label.setText("5 Dakikalık uygulama seçildi")
QLabel
ekledim.
# pomodoro.py
import sys
from PyQt5.QtWidgets import (QApplication, QMainWindow, QMessageBox, QPushButton)
from PyQt5.QtCore import QTimer
import simpleaudio as sa
from tasarim import Ui_Form
class Pomodoro(QMainWindow):
def __init__(self):
super().__init__()
self.ui = Ui_Form()
self.ui.setupUi(self)
self.setWindowTitle("Pomodoro Tekniği ile Çalış")
self.ui.pushButton.clicked.connect(self.period1)
self.ui.pushButton_2.clicked.connect(self.period2)
self.ui.pushButton_3.clicked.connect(self.period3)
self.ui.pushButton_4.clicked.connect(self.period4)
self.timer = QTimer()
self.audio = sa.WaveObject.from_wave_file("audio.wav")
def period1(self):
self.timer.stop()
self.timer.singleShot(300000, lambda:self.audio.play())
QMessageBox.information(self, "Bilgilendirme", "5 dakikalık periyot başladı.")
self.ui.label.setText("5 Dakikalık uygulama seçildi")
def period2(self):
self.timer.stop()
self.timer.singleShot(900000, lambda:self.audio.play())
QMessageBox.information(self, "Bilgilendirme", "15 dakikalık periyot başladı.")
self.ui.label.setText("15 Dakikalık uygulama seçildi")
def period3(self):
self.timer.stop()
self.timer.singleShot(1500000, lambda:self.audio.play())
QMessageBox.information(self, "Bilgilendirme", "25 dakikalık periyot başladı.")
self.ui.label.setText("25 Dakikalık uygulama seçildi")
def period4(self):
self.timer.stop()
self.timer.singleShot(2100000, lambda:self.audio.play())
QMessageBox.information(self, "Bilgilendirme", "35 dakikalık periyot başladı.")
self.ui.label.setText("35 Dakikalık uygulama seçildi")
if __name__ == "__main__":
app = QApplication(sys.argv)
window = Pomodoro()
window.show()
sys.exit(app.exec_())
# tasarim.py
from PyQt5.QtCore import (QCoreApplication, QDate, QDateTime, QMetaObject,
QObject, QPoint, QRect, QSize, QTime, QUrl, Qt)
from PyQt5.QtGui import (QBrush, QColor, QConicalGradient, QCursor, QFont,
QFontDatabase, QIcon, QKeySequence, QLinearGradient, QPalette, QPainter,
QPixmap, QRadialGradient)
from PyQt5.QtWidgets import *
class Ui_Form(object):
def setupUi(self, Form):
if not Form.objectName():
Form.setObjectName(u"Form")
Form.resize(400, 400)
self.gridLayoutWidget = QWidget(Form)
self.gridLayoutWidget.setObjectName(u"gridLayoutWidget")
self.gridLayoutWidget.setGeometry(QRect(9, 149, 381, 241))
self.gridLayout = QGridLayout(self.gridLayoutWidget)
self.gridLayout.setObjectName(u"gridLayout")
self.gridLayout.setContentsMargins(0, 0, 0, 0)
self.pushButton_3 = QPushButton(self.gridLayoutWidget)
self.pushButton_3.setObjectName(u"pushButton_3")
font = QFont()
font.setPointSize(11)
self.pushButton_3.setFont(font)
self.gridLayout.addWidget(self.pushButton_3, 1, 0, 1, 1)
self.pushButton_2 = QPushButton(self.gridLayoutWidget)
self.pushButton_2.setObjectName(u"pushButton_2")
self.pushButton_2.setFont(font)
self.gridLayout.addWidget(self.pushButton_2, 0, 1, 1, 1)
self.pushButton_4 = QPushButton(self.gridLayoutWidget)
self.pushButton_4.setObjectName(u"pushButton_4")
self.pushButton_4.setFont(font)
self.gridLayout.addWidget(self.pushButton_4, 1, 1, 1, 1)
self.pushButton = QPushButton(self.gridLayoutWidget)
self.pushButton.setObjectName(u"pushButton")
self.pushButton.setFont(font)
self.gridLayout.addWidget(self.pushButton, 0, 0, 1, 1)
self.horizontalLayoutWidget = QWidget(Form)
self.horizontalLayoutWidget.setObjectName(u"horizontalLayoutWidget")
self.horizontalLayoutWidget.setGeometry(QRect(9, 9, 381, 101))
self.horizontalLayout = QHBoxLayout(self.horizontalLayoutWidget)
self.horizontalLayout.setObjectName(u"horizontalLayout")
self.horizontalLayout.setContentsMargins(0, 0, 0, 0)
self.label = QLabel(Form)
self.label.setObjectName(u"label")
self.label.setGeometry(QRect(16, 109, 371, 31))
font1 = QFont()
font1.setPointSize(15)
font1.setBold(False)
font1.setWeight(50)
self.label.setFont(font1)
self.retranslateUi(Form)
QMetaObject.connectSlotsByName(Form)
def retranslateUi(self, Form):
Form.setWindowTitle(QCoreApplication.translate("Form", u"Form", None))
self.pushButton_3.setText(QCoreApplication.translate("Form", u"25 Dakika", None))
self.pushButton_2.setText(QCoreApplication.translate("Form", u"15 Dakika", None))
self.pushButton_4.setText(QCoreApplication.translate("Form", u"35 Dakika", None))
self.pushButton.setText(QCoreApplication.translate("Form", u"5 Dakika", None))
self.label.setText(QCoreApplication.translate("Form", u"Hangi uygulamay\u0131 se\u00e7eceksiniz?", None))
Click2’yi bu şekilde değiştirdim.
labelin textine yazdım dediğiniz gibi. Ama bu sefer şöyle hata verdi
File “e:/Yeni klasör (4)/pythonProject5/PyQt5_____/Pomodoro.py”, line 63, in click2
self.yazialani.Label.setText("{} Dakika sonra alarm çalacaktır".format(str(self.minute)))
“”“AttributeError: ‘QLabel’ object has no attribute ‘Label’”"""""
PS E:\Yeni klasör (4)\pythonProject5>
def click2(self):
global wave_obj
global play_obj
self.minute += 0
self.yazialani.Label.setText("{} Dakika sonra alarm çalacaktır".format(str(self.minute)))
time.sleep(self.minute * 60)
wave_obj = sa.WaveObject.from_wave_file("C:/Users/taylan öztürk/Desktop/NCS/Alan Walker/Wav/Force.wav")
play_obj = wave_obj.play()
QLabel yazınca da aynı hata
Ben anahtar kelime olarak söylemiştim
Label
diye bir şey yok.
self.yazialani.setText("Mesaj")
self.yazialani
zaten bir QLabel
nesnesi. QLabel
, QLabel
’ın nesnesi olamaz.
Blok-alıntı
self.yazialani.setText(“{} Dakika sonra alarm çalacaktır”.format(str(self.minute)))
bu şekilde yazınca hata vermiyor ama işte yine dakika bittikten sonra 5 dakika sonra alarm çalacaktır yazısı çıkıyor
yine aynı yere geldik
Yeniden atayım son halini
import sys
from PyQt5 import QtWidgets
import simpleaudio as sa
import time
class pencere(QtWidgets.QWidget):
def __init__(self):
super().__init__()
self.init_ui()
def init_ui(self):
self.yazialani = QtWidgets.QLabel("Pomodoro İçin Hangi İşlemi Uygulayacaksınız ?")
self.minute = 0
self.button1 = QtWidgets.QPushButton("25 Dakika")
self.button2 = QtWidgets.QPushButton("5 Dakika")
self.button3 = QtWidgets.QPushButton("20 Dakika")
self.stopbutton = QtWidgets.QPushButton("Stop Music")
v_box = QtWidgets.QVBoxLayout()
v_box.addWidget(self.button1)
v_box.addWidget(self.button2)
v_box.addWidget(self.button3)
v_box.addWidget(self.yazialani)
v_box.addWidget(self.stopbutton)
v_box.addStretch()
h_box = QtWidgets.QHBoxLayout()
h_box.addStretch()
h_box.addLayout(v_box)
h_box.addStretch()
self.setLayout(h_box)
self.button1.clicked.connect(self.click1)
self.button2.clicked.connect(self.click2)
self.button3.clicked.connect(self.click3)
self.stopbutton.clicked.connect(self.click4)
def click1(self):
global wave_obj
global play_obj
self.minute += 25
self.yazialani.setText("{} Dakika sonra alarm çalacaktır".format(str(self.minute)))
time.sleep(self.minute * 60)
wave_obj = sa.WaveObject.from_wave_file("C:/Users/taylan öztürk/Desktop/NCS/Alan Walker/Wav/Force.wav")
play_obj = wave_obj.play()
def click2(self):
global wave_obj
global play_obj
self.minute += 0
self.yazialani.setText("{} Dakika sonra alarm çalacaktır".format(str(self.minute)))
time.sleep(self.minute * 60)
wave_obj = sa.WaveObject.from_wave_file("C:/Users/taylan öztürk/Desktop/NCS/Alan Walker/Wav/Force.wav")
play_obj = wave_obj.play()
def click3(self):
global wave_obj
global play_obj
self.minute += 20
self.yazialani.setText("{} Dakika sonra alarm çalacaktır".format(str(self.minute)))
time.sleep(self.minute * 60)
wave_obj = sa.WaveObject.from_wave_file("C:/Users/taylan öztürk/Desktop/NCS/Alan Walker/Wav/Force.wav")
play_obj = wave_obj.play()
def click4(self):
play_obj.stop()
app = QtWidgets.QApplication(sys.argv)
window = pencere()
window.show()
sys.exit(app.exec_())
Şu kodları kullanın. Kendi kodlarınız ile karşılaştırıp aradaki farkı inceleyin. Tasarım dosyasına bakmanıza gerek yok.
Hala time.sleep()
kullanıyorsunuz.
Sınıf içerisinde global
değişkenler kullanmayın. OOP
mantığına aykırı ve sürpriz hatalar çıkarma potansiyeline sahipler.
Kalıtım için sıkıntı olur diyorsanız bu programda herhangi bir sıkıntı olacağını düşünmüyorum.
time.sleep kullanmadan nasıl butonlara bastığımda gereken dakikaları işletebilirim ki ?
time.sleep() kullanmadan nasıl dakikaları yürütebilirim ki ?
Ve neden kullanmamda sakınca gördünüz ?
Çünkü sınıf içerisinde kullanıyorsunuz. Global değişken yerine örnek nitelikler
kullanmalısınız. Sınıfların dışında kullanılması yine tavsiye edilmiyor. Çünkü kod karmaşasını artırıyor ve zamanla programı test etmek, kaynak kodu tekrar kullanabilmek, hataları gidermek zorlaşıyor. Bug’lara da hazır olun.
Bkz. (Spagetti kod)
Zaten time.sleep
istediğiniz işi yapmıyor. Programın ‘uyuması’ ile zamanın ilerlemesi aynı şey değil.
Bu iş için QTimer
sınıfını kullanabilirsiniz.
Yukarıdaki kodları biraz anlatayım.
Her fonksiyonun ilk satırına self.timer.stop()
satırını ekledik. 5 dakika’ya tıkladınız, süre başladı. Henüz süre tamamlanmadan 15 dakika’ya tıkladınız. Her butona tıkladığınızda QTimer
sıfırlanıyor. Ardından self.singleShot()
metodunu kullandık. İlk parametresi ne kadar süre (milisaniye) geçtikten sonra işlem yapılacağını, ikinci parametresi ise bu süre tamamlandıktan sonra ne yapılacağını belirtiyor. İkinci parametre argüman olarak sadece fonksiyon alabiliyor.
QTimer
’a bir sınır belirlemezseniz sürekli ‘ateşler’. Biz singleShot
metodunu kullandık, böylelikle sadece ‘bir kere ateş’ edecek.
- Peki ‘ateşlemek’ ne demek? Örnek üzerinden anlatayım;
self.timer = QTimer()
self.timer.timeout.connect(lambda:print("Ateşlendi"))
self.timer.start(1000)
start(1000)
metodu her saniyede bir ‘ateşliyor’. Ateşleme = Timeout
Ateşleme işlemi gerçekleştiğinde QTimer’ın timeout
olduğu anlamına geliyor. Öyle olduğunda da terminale ‘Ateşlendi’ yazısı bastırılıyor.
Eğer self.timer.setSingleShot(True)
komutunu eklerseniz sadece bir kere ateşlenecek
.
Bkz. QTimer
Akşam bunu deneyeceğim.
Daha iyi anladım şimdi.
Son bir şey daha sormak istiyorum.
Globallar olmadan en alttaki “Music Stop” butonunu nasıl çalıştırabilirim?
Direkt playobj. stop yazarsam playobj bulunamadı diyecektir
Dediğim gibi, örnek niteliği (self) haline getirin.
Zaten şurada yapmıştım: PyQt5 projem İle alakalı bir sorun var - ggns7 tarafından #29