Can't open a new window with PyQt4 - python

I made this code .. A new window should open when i fill the requirements and press login but when i do that the window open then it disappears .. i saw a lot of codes using OOP but i don't understand them so i need any one to give me a simple solution
from PyQt4.QtCore import *
from PyQt4.QtGui import *
import sys
import os
import shutil
app = QApplication(sys.argv)
main_window = QWidget()
main_window.setWindowTitle("Keep It Safe V1.5")
main_window.setWindowIcon(QIcon('lock.png'))
main_window.resize(350, 180)
main_window.move(500, 200)
login_btn = QPushButton('Login', main_window)
login_btn.resize(150, 30)
login_btn.move(100, 120)
User = QLineEdit(main_window)
User.resize(250, 30)
User.move(50, 10)
User.setPlaceholderText('Enter your user name')
password = QLineEdit(main_window)
password.resize(250, 30)
password.move(50, 60)
password.setPlaceholderText('Enter your passsword')
password.setEchoMode(QLineEdit.Password)
check = QCheckBox(main_window, text="I accept the terms and policies")
check.move(50, 95)
def login_check():
user = User.text()
Pass = password.text()
if user == "Admin" and Pass == "admin" and check.isChecked():
print("Clicked")
sec_win =QWidget()
l = QLabel(sec_win , text = "second window opened")
sec_win.show()
else:
fai = QMessageBox.warning(main_window, "Error", "Incorrect user name or passwprd")
login_btn.clicked.connect(login_check)
main_window.show()
app.exec_()

A variable that is created within a function is local, so it will be deleted when it is finished executing, and sec_win is so it will be displayed but an instant later it will be removed, the solution is to create it before and only show it when necessary.
import sys
from PyQt4.QtCore import *
from PyQt4.QtGui import *
app = QApplication(sys.argv)
main_window = QWidget()
main_window.setWindowTitle("Keep It Safe V1.5")
main_window.setWindowIcon(QIcon('lock.png'))
main_window.resize(350, 180)
main_window.move(500, 200)
login_btn = QPushButton('Login', main_window)
login_btn.resize(150, 30)
login_btn.move(100, 120)
User = QLineEdit(main_window)
User.resize(250, 30)
User.move(50, 10)
User.setPlaceholderText('Enter your user name')
password = QLineEdit(main_window)
password.resize(250, 30)
password.move(50, 60)
password.setPlaceholderText('Enter your passsword')
password.setEchoMode(QLineEdit.Password)
check = QCheckBox(main_window, text="I accept the terms and policies")
check.move(50, 95)
sec_win =QWidget()
def login_check():
user = User.text()
Pass = password.text()
if user == "Admin" and Pass == "admin" and check.isChecked():
print("Clicked")
l = QLabel(sec_win , text = "second window opened")
sec_win.show()
else:
fai = QMessageBox.warning(main_window, "Error", "Incorrect user name or passwprd")
login_btn.clicked.connect(login_check)
main_window.show()
sys.exit(app.exec_())

Related

Program Doesn't Close After Quitting It In PyQt

So, Recently I was trying to make an audio player using PyQt5, pygame, and mutagen. The program works pretty fine. But when I'm playing a song and try to quit the program, the program stops responding and the song continues to play. But this doesn't happen when a song is not playing, it works fine then.
Here is the Code:
from PyQt5 import QtWidgets, QtGui
from PyQt5.QtWidgets import QApplication, QMainWindow, QSlider
from PyQt5.QtGui import QColor
from PyQt5.QtCore import Qt
import sys
import pygame as pg
from mutagen.mp3 import MP3
import os
import threading
pg.init()
#33206
class window(QMainWindow):
def __init__(self):
super(window, self).__init__()
self.setGeometry(425, 65, 400, 190)
self.setWindowIcon(QtGui.QIcon("icon"))
self.setWindowTitle("MultiMedia Player")
# MenuBar
file = QtWidgets.QAction("&Open Mp3", self)
file.setShortcut("Ctrl + O")
file.triggered.connect(self.open_mp3)
# Quit
quit = QtWidgets.QAction("&Quit", self)
quit.setShortcut("Q")
quit.triggered.connect(self.close_app)
# Add Items
items = QtWidgets.QAction("&Add Items", self)
items.setShortcut("Ctrl + P")
mainmenu = self.menuBar()
filemenu = mainmenu.addMenu("&Open")
filemenu.addAction(file)
add_items = mainmenu.addMenu("&Add Items")
add_items.addAction(items)
filemenu.addAction(quit)
self.flag = 0
self.home()
def home(self):
# colors
black = (13, 13, 13)
light_black = (36, 36, 36)
# Pause Button
self.pause_btn = QtWidgets.QPushButton(self)
self.pause_btn.setText("Pause")
self.pause_btn.setShortcut("p")
self.pause_btn.move(0, 120)
self.pause_btn.clicked.connect(self.pause)
# Play Button
self.play_btn = QtWidgets.QPushButton(self)
self.play_btn.setText("Play")
self.play_btn.setShortcut("Space")
self.play_btn.move(150, 120)
self.play_btn.clicked.connect(self.play)
# Stop Button
self.stop_btn = QtWidgets.QPushButton(self)
self.stop_btn.setText("Stop")
self.stop_btn.setShortcut("s")
self.stop_btn.move(300, 120)
self.stop_btn.clicked.connect(self.stop)
# color for the window
color = QColor(70, 70, 70)
# Volume_Up Button
self.vup_btn = QtWidgets.QPushButton(self)
self.vup_btn.setText("V(+)")
self.vup_btn.setShortcut("+")
self.vup_btn.move(300, 160)
self.vup_btn.clicked.connect(self.volume_up)
# Volume_Down Button
self.vdown_btn = QtWidgets.QPushButton(self)
self.vdown_btn.setText("V(-)")
self.vdown_btn.setShortcut("-")
self.vdown_btn.move(0, 160)
self.vdown_btn.clicked.connect(self.volume_down)
# Seek Slider
self.slider = QSlider(Qt.Horizontal, self)
self.slider.setGeometry(20, 75, 350, 20)
# Volume Slider
self.v_slider = QSlider(Qt.Horizontal, self)
self.v_slider.setGeometry(120, 165, 160, 20)
self.v_slider.setMinimum(0)
self.v_slider.setMaximum(100)
self.v_slider.setValue(70)
self.volume_value = self.v_slider.value()
self.v_slider.valueChanged.connect(self.slider_value_changed)
print(self.v_slider.value() / 100)
def msg(self, title, message):
msg1 = QtWidgets.QMessageBox()
msg1.setWindowIcon(QtGui.QIcon("icon"))
msg1.setWindowTitle(title)
msg1.setText(message)
msg1.setStandardButtons(QtWidgets.QMessageBox.Ok)
msg1.exec_()
def open_mp3(self):
name = QtWidgets.QFileDialog.getOpenFileName(self)
format = os.path.splitext(name[0])
if format[1] == ".mp3":
self.audio = MP3(name[0])
self.duration = self.audio.info.length//1
self.min = int(self.duration // 60)
self.sec = int(self.duration % 60)
self.total_time = str(self.min) + ":" + str(self.sec)
print(self.total_time)
self.slider.setMaximum(self.duration)
self.slider.setMinimum(0)
time = []
time.append(self.total_time)
self.label = QtWidgets.QLabel(self)
self.label.setText(self.total_time)
self.label.setFont(QtGui.QFont("Arial", 9))
self.label.adjustSize()
self.label.move(373, 77)
song = name[0]
pg.mixer.music.load(song)
pg.mixer.music.play(1)
pg.mixer.music.set_volume(self.v_slider.value()/100)
self.label = QtWidgets.QLabel(self)
self.label.setText(song)
self.label.setFont(QtGui.QFont("Arial", 15))
self.label.adjustSize()
self.label.move(0, 36)
self.label.show()
threading_1 = threading.Thread(target=self.cur_time).start()
else:
self.msg("Invalid Format", "Choose A .Mp3 File Only!")
volume_level = pg.mixer.music.get_volume()
print(volume_level)
def cur_time(self):
true = 1
while true == 1:
if self.flag == 0:
self.m_time = pg.mixer.music.get_pos()
self.mm_time = self.m_time * 0.001
self.s_time = self.mm_time // 1
self.slider.setValue(self.s_time)
print(self.s_time)
self.slider.sliderMoved.connect(self.seek_changed)
if self.s_time == -1:
self.slider.setValue(0)
true = 2
if self.flag == 1:
print(self.s_time)
def seek_changed(self):
print(self.slider.value())
pg.mixer.music.set_pos(self.slider.value())
def slider_value_changed(self):
self.volume_value = self.v_slider.value()
pg.mixer.music.set_volume(self.v_slider.value()/100)
def volume_up(self):
self.volume_value = self.volume_value + 10
self.v_slider.setValue(self.volume_value)
if self.volume_value >= 100:
self.volume_value = 100
pg.mixer.music.set_volume(self.v_slider.value() / 100)
print(self.v_slider.value() / 100)
def volume_down(self):
self.volume_value = self.volume_value - 10
self.v_slider.setValue(self.volume_value)
if self.volume_value <= 0:
self.volume_value = 0
pg.mixer.music.set_volume(self.v_slider.value() / 100)
print(self.v_slider.value() / 100)
def pause(self):
pg.mixer.music.pause()
self.flag = 1
def stop(self):
pg.mixer.music.stop()
self.flag = -1
def play(self):
pg.mixer.music.unpause()
self.flag = 0
def close_app(self):
choice = QtWidgets.QMessageBox.question(
self, "QUIT", "You Sure You Wanna Quit?", QtWidgets.QMessageBox.Yes | QtWidgets.QMessageBox.No)
if choice == QtWidgets.QMessageBox.Yes:
sys.exit()
else:
pass
def items(self):
layout = QtWidgets.QVBoxLayout(self)
song_name = QtWidgets.QFileDialog.getOpenFileName(self)
widget = QtWidgets.QListWidget()
widget.setAlternatingRowColors(True)
widget.setDragDropMode(
QtWidgets.QAbstractItemView.InternalMove)
widget.addItems([str(i) for i in range(1, 6)])
layout.addWidget(widget)
if __name__ == '__main__':
app = QApplication(sys.argv)
win = window()
win.show()
sys.exit(app.exec_())
Thanks In Advance.
The main problem is that you're still having the threading.Thread running, so while the QtApplication is "closed", the program is still alive.
You should really avoid using a while loop to check for the current position, as it will call request that value each time the loop cycles, consuming a lot of unnecessary CPU resources.
Also, you're connecting the sliderMoved signal to seek_changed each time the loops cycles, which is bad.
Use a QTimer instead, which will update the cursor position without overloading the process:
# create a timer in the window __init__
self.cursor_updater = QtCore.QTimer(interval=100, timeout=self.cur_time)
#...
def cur_time(self):
# ignore the update if the user is seeking
if self.slider.isSliderDown():
return
self.slider.setValue(pg.mixer.music.get_pos() * .001)
Then you just need to start the timer everytime the music starts (or unpauses) and stop whenever you stop or pause.
That said, there are other issues with your code.
pygame and Qt run their own event loops, so you can't easily and gracefully quit via sys.exit(), nor their own quit() functions, as it's possible that one or both of them would just hang in their own loop without being able to actually quit, keeping the process running (looping doing almost nothing) and consuming a lot of resources. I'm no expert in using pygame and PyQt but, as far as I know, you can call os._exit(0) instead.
the window closeEvent() should be taken care of, because if the user just closes the window without quitting, there won't be any confirmation dialog and the exit procedure described above won't be called.
pygame.mixer.music.get_pos() "only represents how long the music has been playing; it does not take into account any starting position offsets". So you'll need to keep track of the position whenever you use set_pos() and compute the actual value accordingly.
you should really consider using layouts, or ensure that the window size is fixed, otherwise the user will be able to resize it to a size smaller than the interface is.

Issues with the pyqt5 label visibility not hiding

I'm trying to hide an error label ("*") I have created when a line edit isn't filled in, and then have it disappear when it is filled in, but my program isn't consistent.
An example of it not working:
Leave the three slots empty then press the "Add Student" button - a red asterisk will appear next to each one.
enter anything into the first ("starting date") line edit then press the "Add Student" button - the red asterisk will disappear.
repeat 2 for the first name, but the red asterisk won't disappear.
repeat 2 for the last name, but the red asterisk won't disappear for that one either.
import sys
import datetime
from PyQt5 import QtWidgets as qt, QtGui, QtCore
class AddStudent(qt.QMainWindow):
def __init__(self):
# Set the window to the dimensions of the Screen
super().__init__()
screenSize = qt.QDesktopWidget().screenGeometry(-1)
self.height = screenSize.height()
self.width = screenSize.width()
self.setGeometry(0, 0, self.width, self.height)
self.setStyleSheet("QLabel {font: 16pt}")
# Add the buttons, line edits, and table
self.foundError = False
self.setup()
# Display the GUI
self.setWindowTitle("Add Student")
def setup(self):
self.startingDateLabel()
self.firstNameLabel()
self.lastNameLabel()
self.addStudentButton()
# Button Declarations
def startingDateLabel(self):
self.dateLabel = qt.QLabel(self)
self.dateLabel.setText("Starting Date:")
# (L/R, U/D, L/R, U/D)
self.dateLabel.setGeometry(158, 150, 262, 50)
self.dateLineEdit = qt.QLineEdit(self)
date = str(datetime.date.today()).split("-")
today = date[1] + "/" + date[2] + "/" + date[0]
self.dateLineEdit.setText(today)
self.dateLineEdit.setGeometry(435, 155, 250, 50)
def firstNameLabel(self):
self.firstName = qt.QLabel(self)
self.firstName.setText("First Name:")
self.firstName.setGeometry(205, 250, 215, 50)
self.firstNameLineEdit = qt.QLineEdit(self)
self.firstNameLineEdit.setGeometry(435, 255, 250, 50)
def lastNameLabel(self):
self.lastName = qt.QLabel(self)
self.lastName.setText("Last Name:")
self.lastName.setGeometry(208, 350, 212, 50)
self.lastNameLineEdit = qt.QLineEdit(self)
self.lastNameLineEdit.setGeometry(435, 355, 250, 50)
def addStudentButton(self):
self.addStudent = qt.QPushButton(self)
self.addStudent.setText("Add Student")
self.addStudent.setGeometry(800, 1500, 150, 50)
self.addStudent.clicked.connect(self.addStudentButtonPressed)
self.addStudent.show()
def addStudentButtonPressed(self):
# Check to make sure that everything that needs to be filled out is filled out
self.errorFound = False
# Check the starting date
if (self.dateLineEdit.text() == ""):
self.error1 = qt.QLabel(self)
self.error1.setText("*")
self.error1.setStyleSheet('color: red')
self.error1.setGeometry(715, 155, 30, 50)
self.error1.show()
self.errorFound = True
else:
try:
self.error1.hide()
self.errorFound = False
except:
self.errorFound = False
# Check the first name slot
if (self.firstNameLineEdit.text() == ""):
self.error2 = qt.QLabel(self)
self.error2.setText("*")
self.error2.setStyleSheet('color: red')
self.error2.setGeometry(715, 255, 30, 50)
self.error2.show()
self.errorFound = True
else:
try:
self.error2.hide()
self.errorFound = False
except:
self.errorFound = False
# Check the last name slot
if (self.lastNameLineEdit.text() == ""):
self.error3 = qt.QLabel(self)
self.error3.setText("*")
self.error3.setStyleSheet('color: red')
self.error3.setGeometry(715, 355, 30, 50)
self.error3.show()
self.errorFound = True
else:
try:
self.error3.hide()
self.errorFound = False
except:
self.errorFound = False
# Run the window
app = qt.QApplication(sys.argv)
window = AddStudent()
window.show()
sys.exit(app.exec())
I made the following changes to your code:
Just a code style thing: I used snake case for the variable and function names. This is the standard for python code, with PyQt being an odd exception (likely due to inheriting from a C++ code base).
I removed the use of self.errorFound. As I hinted in the comments, you never really check the value of this anywhere. While it might be useful to have a single self.errorFound if you just wanted to know if any of the user inputs were wrong, a single boolean couldn't tell you which input was wrong. I just simply check if the text for the user input is empty every time the submit function is called.
I used the QFormLayout class to position the widgets on the screen. This removes all of the guesswork and math of typing in absolute coordinates of where a widget should belong. It also prevents widgets from "disappearing" if the window is too small. This comes with the limitation that each row can only hold two widgets. For this reason, I ditched the asterisk in favor of just coloring the QLabel for the corresponding wrong input. This can be worked around with QGridLayout or, if you like the QFormLayout, with nested QHBoxLayout objects per each field. Let me know if the asterisk is needed.
With all that out of the way, here is updated code:
import sys
import datetime
from PyQt5 import QtWidgets as qt, QtGui, QtCore
class MyApp(qt.QMainWindow):
def __init__(self):
super().__init__()
screenSize = qt.QDesktopWidget().screenGeometry(-1)
self.setup()
self.setWindowTitle("My Awesome App!")
def setup(self):
self.form = qt.QGroupBox("Add Student")
self.form_layout = qt.QFormLayout()
self.create_date_input()
self.create_first_name_input()
self.create_last_name_input()
self.create_submit_button()
self.form.setLayout(self.form_layout)
self.setContentsMargins(5, 5, 5, 5)
self.setCentralWidget(self.form)
def create_date_input(self):
self.date_label = qt.QLabel("Starting Date:")
self.date_entry = qt.QLineEdit(self)
date = str(datetime.date.today()).split("-")
today = date[1] + "/" + date[2] + "/" + date[0]
self.date_entry.setText(today)
self.form_layout.addRow(
self.date_label,
self.date_entry,
)
def create_first_name_input(self):
self.first_name_label = qt.QLabel("First Name:")
self.first_name_entry = qt.QLineEdit(self)
self.form_layout.addRow(
self.first_name_label,
self.first_name_entry,
)
def create_last_name_input(self):
self.last_name_label = qt.QLabel("Last Name:")
self.last_name_entry = qt.QLineEdit(self)
self.form_layout.addRow(
self.last_name_label,
self.last_name_entry,
)
def create_submit_button(self):
self.submit_button = qt.QPushButton(self)
self.submit_button.setText("Add Student")
self.submit_button.clicked.connect(self.submit)
self.form_layout.addRow(self.submit_button)
def submit(self):
default_color = "color: black"
error_color = "color: red"
date_color = default_color
first_name_color = default_color
last_name_color = default_color
#really should validate if this is a date, not just if it is empty
if (self.date_entry.text() == ""):
date_color = error_color
if (self.first_name_entry.text() == ""):
first_name_color = error_color
if (self.last_name_entry.text() == ""):
last_name_color = error_color
self.date_label.setStyleSheet(date_color)
self.first_name_label.setStyleSheet(first_name_color)
self.last_name_label.setStyleSheet(last_name_color)
app = qt.QApplication(sys.argv)
window = MyApp()
window.show()
sys.exit(app.exec())
Here's another possible solution; while it might seem a bit more complicated than the other one proposed by CodeSurgeon, it is much more extensible to my opinion - and somehow a bit more elegant.
The catch here is the subclass of QLineEdit that embeds a child QLabel, which is made visible only if there's text in the field. The resizeEvent override has been added to ensure that the "*" label is always correctly placed whenever the window is resized.
There are many advantages to this approach, but the most important is that subclassing the "main" widget, instead of creating a new one that embeds other widgets, automatically exposes all of its methods and properties.
So, all of this allows you to add as many [text] fields as you want and enables/disables the submit button only if every one of them has some content in it.
import sys
from PyQt5 import QtCore, QtWidgets
class MyLineEdit(QtWidgets.QLineEdit):
def __init__(self, *args, **kwargs):
super().__init__(*args, **kwargs)
# the "invalid" label *has* to be a child of this QLineEdit
self.invalidLabel = QtWidgets.QLabel('*', self)
self.invalidLabel.setStyleSheet('color: red;')
spacing = 2
# get default margins and re-set them accordingly
self.leftMargin, self.topMargin, self.rightMargin, self.bottomMargin = self.getContentsMargins()
self.rightMargin += self.invalidLabel.minimumSizeHint().width() + spacing
self.setContentsMargins(self.leftMargin, self.topMargin, self.rightMargin + spacing, self.bottomMargin)
self.textChanged.connect(self.setValid)
self.setValid(self.text())
def setValid(self, text):
self.invalidLabel.setVisible(not bool(text))
def isValid(self):
return bool(self.text())
def resizeEvent(self, event):
self.invalidLabel.setGeometry(self.width() - self.rightMargin, self.topMargin,
self.invalidLabel.minimumSizeHint().width(), self.height() - self.topMargin - self.bottomMargin)
class MyApp(QtWidgets.QMainWindow):
def __init__(self):
super().__init__()
self.setup()
def setup(self):
self.form = QtWidgets.QGroupBox("Add Student")
self.setCentralWidget(self.form)
self.formLayout = QtWidgets.QFormLayout()
self.form.setLayout(self.formLayout)
self.fields = []
self.create_field('Starting Date:', defaultValue=QtCore.QDate.currentDate().toString('MM/dd/yyyy'))
self.create_field('First Name:')
self.create_field('Last Name:')
self.create_submit_button()
def create_field(self, label, defaultValue=''):
field = MyLineEdit(defaultValue)
self.fields.append(field)
field.defaultValue = field.text()
self.formLayout.addRow(label, field)
field.textChanged.connect(self.checkFields)
def create_submit_button(self):
self.submitButton = QtWidgets.QPushButton('Add Student')
self.formLayout.addRow(self.submitButton)
self.submitButton.clicked.connect(self.submit)
self.submitButton.setEnabled(False)
self.checkFields()
def checkFields(self):
self.submitButton.setEnabled(all(field.isValid() for field in self.fields))
def submit(self):
# doSomething([field.text() for field in self.fields)
for field in self.fields:
field.setText(field.defaultValue)
app = QtWidgets.QApplication(sys.argv)
w = MyApp()
w.show()
sys.exit(app.exec_())
As already pointed out, you should really think about validating the date contents (as one could enter anything there) since you are using a line edit.
The better solution is to use a QDateEdit, but you'll need to subclass it as I did with QLineEdit and create a separate create function, and obviously it will be "ignored" in the submit "validation" as QDateEdit fields automatically allows valid date inputs.
Otherwise you could use a QValidator, but it would be the proverbial pain in the a**, mainly because QDateTime already provides validation and a nice calendar view by using setCalendarPopup(True), and validating a date through regular expression is really annoying.

PyQt: How convert my script to GUI?

I'm following this tutorial for a PyQt5 GUI window:
Here's My code on pastebin.
import sys
from PyQt5 import QtWidgets, QtGui
def window1():
app = QtWidgets.QApplication(sys.argv)
w = QtWidgets.QWidget()
b = QtWidgets.QPushButton('Comparison Report', w)
l1 = QtWidgets.QLabel(w)
l2 = QtWidgets.QLabel(w)
l1.setText('Main Page')
b.setGeometry(200, 100, 300, 70)
w.setWindowTitle('Diff Util')
w.setGeometry(800, 200, 720, 800)
l1.move(310, 5)
w.show()
sys.exit(app.exec_())
#import file_report
#def on_click(self):
#file_report()
window1()
Here's a comparison file script also on pastebin... but i Need 10rep to link it >_>
import sys
import os
import difflib
first_file = input("Select original file: ")
second_file = input("Select second file for comparison: ")
first_file_lines = open(first_file).readlines()
second_file_lines = open(second_file).readlines()
difference = difflib.HtmlDiff(tabsize=8,
wrapcolumn=100).make_file(first_file_lines, second_file_lines, first_file, second_file, charset='utf-8')
difference_report = open('difference_report.html', 'w')
difference_report.write(difference)
difference_report.close()
os.startfile('difference_report.html')
My question is, how to connect my file_report.py to the pushbutton I've created with PyQt5?
As you can see I commented out "import file_report" because from my understanding I'm supposed to import my script... but the import causes it to run the script in terminal, and after execution will open my GUI. I would like to run this script, but contain it within the GUI window I've created instead of opening a terminal for execution.
So where in the PyQt5 script should I import, and include the .py file?
GUIs are not friendly with blocking tasks since for their existence they create a loop. Therefore the function input() should not be used, the solution to use elements provided by the library as QLineEdit, PyQt also provides dialog boxes for the selection of files.
import sys
from PyQt5 import QtWidgets, QtGui, QtCore
import difflib
class Widget(QtWidgets.QWidget):
def __init__(self, parent=None):
QtWidgets.QWidget.__init__(self, parent)
self.setLayout(QtWidgets.QGridLayout())
self.le1 = QtWidgets.QLineEdit("", self)
self.le2 = QtWidgets.QLineEdit("", self)
self.le3 = QtWidgets.QLineEdit("", self)
self.btn1 = QtWidgets.QPushButton("Select first file")
self.btn2 = QtWidgets.QPushButton("Select second file")
self.btn3 = QtWidgets.QPushButton("Select save File")
self.btnRun = QtWidgets.QPushButton("Run")
self.layout().addWidget(self.le1, 1, 1)
self.layout().addWidget(self.le2, 2, 1)
self.layout().addWidget(self.le3, 3, 1)
self.layout().addWidget(self.btn1, 1, 2)
self.layout().addWidget(self.btn2, 2, 2)
self.layout().addWidget(self.btn3, 3, 2)
self.layout().addWidget(self.btnRun, 4, 2)
self.btnRun.clicked.connect(self.onRun)
self.btn1.clicked.connect(self.selectFirstFile)
self.btn2.clicked.connect(self.selectSecondFile)
self.btn3.clicked.connect(self.selectSaveFile)
def selectFirstFile(self):
filename, _ = QtWidgets.QFileDialog.getOpenFileName(self, "Select Files", QtCore.QDir.currentPath(), "*.html")
if filename != "":
self.le1.setText(filename)
def selectSecondFile(self):
filename, _ = QtWidgets.QFileDialog.getOpenFileName(self, "Select Files", QtCore.QDir.currentPath(), "*.html")
if filename != "":
self.le2.setText(filename)
def selectSaveFile(self):
filename, _ = QtWidgets.QFileDialog.getSaveFileName(self, "Select Files", QtCore.QDir.currentPath(), "*.html")
if filename != "":
self.le3.setText(filename)
def onRun(self):
first_file = self.le1.text()
second_file = self.le2.text()
output_file = self.le3.text()
first_file_lines = open(first_file).readlines()
second_file_lines = open(second_file).readlines()
difference = difflib.HtmlDiff(tabsize=8, wrapcolumn=100).make_file(first_file_lines, second_file_lines, first_file, second_file, charset='utf-8')
difference_report = open(output_file, 'w')
difference_report.write(difference)
difference_report.close()
QtGui.QDesktopServices.openUrl(QtCore.QUrl.fromLocalFile(output_file))
if __name__ == '__main__':
app = QtWidgets.QApplication(sys.argv)
w = Widget()
w.show()
sys.exit(app.exec_())

python - pyqt5: error in show two form, name 'Window' is not defined

Welcome..
i have two form: Form1=>Window & form2 =>MainWindow
The problem occurs after pressing the exit button in the main window. Where it is supposed to return to the login window again.
form1 (Window for Login) code:
import sys
from PyQt5.QtWidgets import *
from form2 import *
class Window(QWidget):
right_uname = "admin"
right_pword = "password"
def __init__(self):
super().__init__()
self.init_ui()
def init_ui(self):
self.lbl_intro = QLabel('Welcome, please login')
self.lbl_enter_username = QLabel('Username:')
self.lbl_enter_password = QLabel('Password:')
self.txt_enter_username = QLineEdit()
self.txt_enter_password = QLineEdit()
self.cb_login = QCheckBox('Stay logged in?')
self.btn_login = QPushButton('Login')
self.grid = QGridLayout()
self.grid.setSpacing(5)
self.grid.addWidget(self.lbl_intro, 1, 1)
self.grid.addWidget(self.lbl_enter_username, 2, 0)
self.grid.addWidget(self.txt_enter_username, 2, 1)
self.grid.addWidget(self.lbl_enter_password, 3, 0)
self.grid.addWidget(self.txt_enter_password, 3, 1)
self.grid.addWidget(self.cb_login, 4, 1)
self.grid.addWidget(self.btn_login, 5, 1)
self.v_box = QVBoxLayout()
self.v_box.addStretch(0)
self.v_box.addLayout(self.grid)
self.v_box.addStretch(0)
self.h_box = QHBoxLayout()
self.h_box.addStretch(0)
self.h_box.addLayout(self.v_box)
self.h_box.addStretch(0)
self.setLayout(self.h_box)
self.btn_login.clicked.connect(lambda: self.btn_login_clk(self.txt_enter_username, self.txt_enter_password, self.cb_login.isChecked(), self.lbl_intro))
self.setWindowTitle('Login test')
self.show()
def btn_login_clk(self, username, password, cb, intro):
if username.text() == self.right_uname and password.text() == self.right_pword:
if cb:
intro.setText('Welcome,' + ' ' + self.right_uname + ' ' + 'cb ticked')
else:
self.mw = MainWindow()
self.hide()
self.mw.show()
else:
intro.setText('Wrong username or password')
self.clear_box()
def clear_box(self):
self.txt_enter_username.clear()
self.txt_enter_password.clear()
self.txt_enter_username.setFocus()
if __name__ == '__main__':
app = QApplication(sys.argv)
a_window = Window()
sys.exit(app.exec())
from2 (MainWindow) code:
from form1 import *
class MainWindow(Window):
def __init__(self):
super().__init__()
self.init_ui()
def init_ui(self):
self.lbl_intro = QLabel('Main Window')
self.lbl_user_logged = QLabel('Welcome,' + ' ' + self.right_uname)
self.lbl_append = QLabel('Write something')
self.txt_write_box = QLineEdit()
self.btn_append = QPushButton('Append')
self.btn_logout = QPushButton('Logout')
layout = QVBoxLayout()
layout.addWidget(self.lbl_intro)
layout.addWidget(self.lbl_user_logged)
layout.addWidget(self.lbl_append)
layout.addWidget(self.txt_write_box)
layout.addWidget(self.btn_append)
layout.addWidget(self.btn_logout)
self.setLayout(layout)
self.setWindowTitle('Main')
self.btn_append.clicked.connect(self.append_clk)
self.btn_logout.clicked.connect(self.logout_action)
self.show()
def append_clk(self):
self.appendee = open('text.txt', 'a')
self.appendee.write('hry')
self.appendee.close()
def logout_action(self):
self.close()
a_window = Window(self)
a_window.show()
a_window.clear_box()
When running:
name 'Window' is not defined
It looks like some sort of circular import problem to me, but I cannot replicate it though. Which version of Python are you using?
Anyway, firstly I would try changing form1 so that that import is local right before using MainWindow, to see if that solves the problem. I.e. removing the from form2 import * line at the top of form1 and changing your btn_login_clk method to this:
def btn_login_clk(self, username, password, cb, intro):
if username.text() == self.right_uname and password.text() == self.right_pword:
if cb:
intro.setText('Welcome,' + ' ' + self.right_uname + ' ' + 'cb ticked')
else:
from form2 import MainWindow # local import
self.mw = MainWindow()
self.hide()
self.mw.show()
else:
intro.setText('Wrong username or password')
self.clear_box()
On a slightly unrelated topic, I see that, when closing your MainWindow (i.e. logging out), you create a Window with the parent set to the MainWindow which you just closed. This will probably caluse the new window to be killed even before it appears (in my case, nothing appears and python exits with code 1), so the self argument should probably be removed:
def logout_action(self):
self.close()
a_window = Window() # no 'self' argument
a_window.show()
a_window.clear_box()

Using Pyqt with Twitters API

I am trying to build a GUI for my Twitter application that automatically follows people. I have it mostly working in the console, however I am trying to convert it into a GUI, and am running into a few issues. The main problem is that whenever I assign the script I want to run when a button is pushed, it either runs immediately when I run the app, which wont display the GUI; or the GUI displays, but the function on the button does nothing. I have been looking for days, but I do not know what the problem is.
#! /usr/bin/python
import time
import tweepy
from keys import keys
import requests_cache
from random import randint
from PyQt4 import QtGui
from PyQt4 import QtCore
from subprocess import call
import sys
from AddToDB import *
SCREEN_NAME = 'JonahHensley'
CONSUMER_KEY = keys['consumer_key']
CONSUMER_SECRET = keys['consumer_secret']
ACCESS_TOKEN = keys['access_token']
ACCESS_TOKEN_SECRET = keys['access_token_secret']
auth = tweepy.OAuthHandler(CONSUMER_KEY, CONSUMER_SECRET)
auth.set_access_token(ACCESS_TOKEN, ACCESS_TOKEN_SECRET)
api = tweepy.API(auth)
followers = api.followers_ids(SCREEN_NAME)
class Example(QtGui.QWidget):
def __init__(self):
super(Example, self).__init__()
self.initUI()
def initUI(self):
btn = QtGui.QPushButton('Yes', self)
btn.clicked.connect(follower.follow(self))
btn.resize(180, 40)
btn.move(20, 35)
qbtn = QtGui.QPushButton('No', self)
qbtn.clicked.connect(QtCore.QCoreApplication.instance().quit)
qbtn.resize(180, 40)
qbtn.move(20, 80)
self.setWindowTitle('Test')
self.show()
class follower(QtGui.QWidget):
def follow(self):
while True:
try:
for f in followers:
UserFollow = input("Follow users from: ")
print('Getting followers from ' + UserFollow)
api.wait_on_rate_limit = True
api.wait_on_rate_limit_notify = True
requests_cache.install_cache(cache_name='twitter_cache', backend='sqlite', expire_after=180)
print("followed {0}".format(api.get_user(f).screen_name))
api.create_friendship(f)
randnum = randint(10, 25)
randnumdisplay = print("Delaying next follow for " + str(randnum) + " seconds.")
print(str(randnumdisplay))
screen_names = [api.get_user(f).screen_name]
time.sleep(randnum)
except tweepy.TweepError:
print("Waiting till next interval...")
time.sleep(60 * 15)
continue
except StopIteration:
def main():
app = QtGui.QApplication(sys.argv)
gui = Example()
sys.exit(app.exec_())
if __name__ == '__main__':
main() break
def main():
app = QtGui.QApplication(sys.argv)
gui = Example()
sys.exit(app.exec_())
if __name__ == '__main__':
main()

Categories