I'm writing a graphic application that gives a word after I press a key in my electric piano using a database.
I'm using PyGame, Tkinter and Sqlite.
The application is pretty simple and is almost finished,
but I'm stuck with that error between my piano.py and the frontEnd.py.
The thing is that I want a Label that writes what was the last key I pressed and put it on a canvas.
I know the problem is related to the 'while True' and already changed it with 'while idKey < 176' but with this change I receive the "noneType" error.
This is the current code in my file piano.py
piano.py
import pygame
import pygame.midi
from pygame.locals import *
class backPiano():
def funcPiano(self):
self = backPiano
pygame.init()
pygame.fastevent.init()
event_get = pygame.fastevent.get
event_post = pygame.fastevent.post
pygame.midi.init()
input_id = pygame.midi.get_default_input_id()
i = pygame.midi.Input( input_id )
while True:
events = event_get()
if i.poll():
midi_events = i.read(10)
idKey = midi_events[0][0][0]
if idKey == 176:
return False
And the code in my frontEnd (only the function with the problem):
frontEnd.py
from tkinter import *
from tkinter import ttk, font
import multiprocessing
import time
import os
from database import dictionary, path
from piano import backPiano
class frontEnd(Frame):
def __init__(self, parent):
self.backPiano = backPiano()
def capturePiano(self):
backPiano.funcPiano(self)
superPiano = StringVar()
superPiano.set(backPiano.funcPiano(self).idKey)
labelPiano.configure(textvariable=superPiano)
self.parent.update()
canvasWidth = 500
canvasHeight = 500
w = Canvas(parent, width=canvasWidth, height=canvasHeight)
w.place(x=monitorWidth/2,y=monitorHeight/2, anchor=CENTER)
w.create_image(canvasWidth/2, canvasHeight/2, image=img, anchor=CENTER)
labelPiano = Label(parent)
labelPiano.place(x=monitorWidth/2,y=monitorHeight/2)
In the line 'superPiano.set(backPiano.funcPiano(self).idKey)' I tried:
"superPiano.set(backPiano.idKey)"
But because the variable is inside a function it can't be called with that.
The exact error I have is this:
Exception in Tkinter callback
Traceback (most recent call last):
File "C:\Users\admin\AppData\Local\Programs\Python\Python37\lib\tkinter\__init__.py", line 1705, in __call__
return self.func(*args)
File "C:\Users\admin\Desktop\python\frontEnd.py", line 202, in <lambda>
command=lambda : capturePiano(self)).place(x=monitorWidth/9,y=monitorHeight/2,anchor=CENTER)
File "C:\Users\admin\Desktop\python\frontEnd.py", line 187, in capturePiano
superPiano.set(backPiano.funcPiano(self).idKey)
AttributeError: 'bool' object has no attribute 'idKey'
I can't upload all the code, but the error is in the While True but removing it destroys all my code because I need the loop.
Thank you very much (and sorry if I made grammar mistakes).
As the error message says: funcPiano is returning a boolean (True) so when you try to take the idKey it fails, because booleans don't have that.
Related
I'm very new to Python and I'm trying to put my first application together that takes in trip information and inserts it into a text box for export out to a document. It's gone pretty good until today when I tried to implement multiple ways of inserting text from an entrybox into a text block with tkinter.
I have an entry widget that inserts text into a text widget when a button is pressed. That's simple enough but I wanted to make it to where you could simply hit the enter key to do the same thing.
When I implement this function I get the error:
"Exception in Tkinter callback
Traceback (most recent call last):
File "C:\Program Files\Spyder\pkgs\tkinter_init_.py", line 1892, in __ call __
return self.func(*args)
TypeError: insertstop() takes 0 positional arguments but 1 was given"
I've looked the error up and it seems like it would pop up if I put in arguments in my function call but I don't have any arguments in any of my function calls. Also it seems like maybe this error is related to a class or something? I haven't learned about classes yet and only have a basic idea of what they are. Do I need a class to do this?
Coincidentally I also added the argument(self) in my function and that made pressing enter work but it made my insert stop button quit working.
I'm sure I've missed something very basic but I just can't figure out what.
Thanks for any help!
import time
import os
import sys
from tkinter import *
# Creates the Tkinter form named "screen"
screen = Tk()
screen.geometry("550x645")
screen.title("Test")
# Initialize frames
menuframe = Frame(screen,
height=60,width=600,bg="gray",pady=5)
inputframe = Frame(screen,
height=300,width=600,pady=5)
outputframe = Frame(screen,
height=290,width=600,pady=5)
# Packs the frames so they will display
menuframe.pack()
inputframe.pack()
outputframe.pack()
#==STOPBOX==#
stopbox=Text(inputframe,yscrollcommand=1,height= 10,width=20,
padx=3,pady=3,relief=GROOVE,bg="gray79")
stopbox.place(x=345, y=90)
def insertstop():
global stop_vanconv
stop_vanconv=(stop_entry.get())
stopbox.insert(END, stop_vanconv + "\n")
stop_entry.delete("0","end")
stoplist_label = Label(inputframe,
text="Type stop locations and press" + '\n' +
"the Add Stop button to insert a new stop.")
stoplist_label.place(x=100, y=150)
stop_entry = Entry(inputframe,
textvariable = " ")
stop_entry.place(x=150, y=190)
addstopbutton = Button(inputframe,text="Add Stop",padx=20,pady=0,
activebackground="darkslategray4",command=insertstop)
addstopbutton.place(x=160, y=220)
stop_entry.bind('<Return>',insertstop)
screen.mainloop()
im getting the above error when i run this code snippet. Im trying to error proof user input by creating an error window when the user enters a value not in a dataframe. the code im running is below
import tkinter as tk
import tkinter.messagebox
import pandas as pd
root= tk.TK()
def customer_search():
try:
search = int(entry1.get())
except ValueError:
tk.messagebox("that customer doesnt exist, please enter a new number") #error proofing has to be added tomorrow
search = int(entry1.get())
k = df.loc[df['UniqueID'] == search]
k.to_excel("dashboard.xlsx")
df.to_excel("check.xlsx")
canvas1 = tk.Canvas(root, width=400, height=300)
canvas1.pack()
entry1 = tk.Entry(root)
canvas1.create_window(200, 140, window=entry1)
button1 = tk.Button(text='Enter a customer for analysis', command=customer_search)
button1.pack()
the error i get is as follows
Exception in Tkinter callback
Traceback (most recent call last):
File "C:/Users/....py", line 42, in customer_search
search = int(entry1.get())
ValueError: invalid literal for int() with base 10: 'a'
During handling of the above exception, another exception occurred:
Traceback (most recent call last):
File "C:\Users...\__init__.py", line 1705, in __call__
return self.func(*args)
File "C:/Users....py", line 44, in customer_search
tk.messagebox("that customer doesnt exist, please enter a new number") #error proofing has to be added tomorrow
TypeError: 'module' object is not callable
Process finished with exit code 0
tk.messagebox is a module containing multiple dialogs, you probably want to use tk.messagebox.showerror("Info Title", "Info content").
Other dialogs are showwarning and showinfo, depending on your use case.
tk.messagebox is a module not a function. A basic difference between modules and functions is that:
You can't call modules, i.e., you can't do module(). (This is precisely the mistake you are making.)
You can call functions, i.e., you can do function(). (This is what you should be doing instead.)
You need to do it this way (in customer_search):
tk.messagebox.showerror("Title here", "that customer doesnt exist, please enter a new number")
where tk.messagebox.showerror is a function in tk.messagebox module.
I am using kivy to make a small music player but i have some issues with it. I am using a screen manager which will direct the user to either his libraries, or the entire tracks list. When one of the two is selected i want to find and load all the titles as buttons, to be played when pressed. Here's the basic track class:
class Track(Button):
path = 'C:/Users/...../tracks/'
def __init__(self,title,**kwargs):
self.title = title
super(Track,self).__init__(text=self.title,**kwargs)
def playTrack(self):
self.sound = SoundLoader.load(self.path+self.title)
self.sound.play()
also here is a music class that finds all the tracks in the directory and adds them to a list:
class mymusic():
path = 'C:/Users/...../tracks'
def __init__(self,**kwargs):
self.tracks=os.listdir(self.path)
print self.tracks
def loadTracks(self):
trackslist = []
for i in self.tracks:
trackslist.append(Track(i))
return trackslist
Finally, here is the code i use, that is supposed to create the buttons (the sm below is the screen manager, and root,libraries and music are subclasses of screen):
f = lambda obj: obj.playTrack()
Music = music(name='Music')
layout = BoxLayout()
Music.add_widget(layout)
sm.add_widget(root(name='Root'))
sm.add_widget(libraries(name='My libaries'))
sm.add_widget(Music)
musicobj = mymusic()
tracklist = musicobj.loadTracks()
for i in tracklist:
print i
i.bind(on_press=f(i))
This does not work. By running it i get the following error:
Traceback (most recent call last):
File "C:\Users\Vlassis\Desktop\test.py", line 108, in <module>
i.bind(on_press=f(i))
File "kivy\_event.pyx", line 430, in kivy._event.EventDispatcher.bind (kivy\_event.c:5903)
AssertionError: None is not callable
also the last track in the directory plays in the background. I can't figure out why. Is the logic behind the code correct? How should i go about doing this? Thanks in advance.
Good evening,
I'm trying to learn some Python coding so I've written a short script that searches the screen for a button and then clicks the button a specified number of times. I have the code under 'RunScript' also saved as it's own file. When I run that script from terminal it works fine, but when I try to execute it by double clicking the icon, or from a button on a tkinter box using the below code it asks me for a number of loops and then does nothing. I'm working in a Lubuntu virtual machine.
Please can you tell me what I'm missing?
Thank you
#!/usr/bin/python3
from tkinter import *
import pyautogui
import easygui
PauseStatus = False
def RunScript():
LoopCount = easygui.enterbox('How Many Loops?')
for i in range (int(LoopCount)):
if PauseStatus:
easygui.msgbox(str(i) + ' loops completed\n' + str(int(LoopCount)-i) + 'loops remaining')
PauseStatus = False
while True:
ButtonPos = pyautogui.locateOnScreen('MyButton.png')
if ButtonPos is not None:
break
pyautogui.click(ButtonPos[0],ButtonPos[1],duration=0.25)
while True:
ButtonPos = pyautogui.locateOnScreen('MyButton.png')
if ButtonPos is not None:
break
easygui.msgbox(str(i+1) + ' loops completed')
root = Tk()
ControlPanel = Frame(root)
ControlPanel.pack()
startbutton = Button(ControlPanel, text="Start",command = RunScript)
startbutton.pack(side = LEFT)
stopbutton=Button(ControlPanel,text="Stop")
stopbutton.pack(side = LEFT)
root.mainloop()
You have error message similar to this
Exception in Tkinter callback
Traceback (most recent call last):
File "/usr/lib/python2.7/lib-tk/Tkinter.py", line 1539, in __call__
return self.func(*args)
File "<pyshell#3>", line 11, in RunScript
if PauseStatus:
UnboundLocalError: local variable 'PauseStatus' referenced before assignment
You have to use global in function RunScript
def RunScript():
global PauseStatus
or you have to declare variable inside function as local variable
def RunScript():
PauseStatus = False
I am trying to make a multiple "page" GUI using tkinter and couldn't really find a good method. I resorted to using grid_forget and seperating the "pages" in methods and it works like a charm. However I am trying to seperate the methods into a seperate file to make everything a little cleaner but I keep getting a global name error upon trying to run one of the methods with all of the widgets from my main file/class.
Traceback (most recent call last):
File "C:/Users/Derek/PycharmProjects/whites/Main.py", line 3, in <module>
from screens import *
File "C:\Users\Derek\PycharmProjects\whites\screens.py", line 4, in <module>
import Main
File "C:\Users\Derek\PycharmProjects\whites\Main.py", line 54, in <module>
app = Application(master=main, w=main.winfo_width(), h=main.winfo_height())
File "C:\Users\Derek\PycharmProjects\whites\Main.py", line 20, in __init__
home_screen(self,True)
NameError: global name 'home_screen' is not defined
I also tried importing it such as import screens and tried to run screens.home_screen(self,True) and that yeilds
AttributeError: 'module' object has no attribute 'home_screen'
Even though it does
Example Main.py
from screens import *
import globals
class Application(tk.Frame):
globals.init()
def __init__(self, w, h, master=None):
tk.Frame.__init__(self, master)
self.grid()
self.window_width = w
self.window_height = h
home_screen(self,True)
query_screen(False)
res_screen(False)
settings_screen(False)
screens.py
import tkinter as tk
import globals
import Main
def home_screen(self, state):
*define widgets for this "screen"
[EDIT]
Here is a copy of the full files.screens , Main , globals
[EDIT: 2]
So I changed the code around to try a different solution and it basically the same error. module object has no attribute if I attempt to convert the screens.py into a class and initialize it as an object but nothing. So I am guessing this means it is not python at all and more my project settings have somewhere gone askew
You define:
def home_screen(self, state):
but it's not in any class!
Remove the self from the function signature and call it using only state variable only
EDIT:
If you create main.py:
from screens import *
class Application():
def __init__(self):
home_screen(True)
# then later on
a = Application() # this will print 'True'
and in file screens.py:
def home_screen(state):
print state
it will work (assuming both are in the same directory).
The solutions was to run the screens.py and not the main.py. Why that is I have no idea but it still ultimately fits my goal. If anyone would like to weigh in go for it.
[EDIT]
Final solution, change the way the program starts.It now runs just fine.
if __name__ == "__main__":
main = tk.Tk()
main.wm_title("White's Canoe Livery")
main.state("zoomed")
main.update()
# print(main.winfo_width())
app = Application(master=main, w=main.winfo_width(), h=main.winfo_height())
app.mainloop()