I wanted to start a new project with python, so i saw this so it looked cool so i wanted to give it a try, but i dont know how to make that scroller, all i found online was ways to make it scroll through text and documents, but not to control input, could someone help me make something like this?
and is there a way to make it display the number of characters above the scroller?
this is what i got online, i dont know if its the same thing as what i want
scrollbar1 = Scrollbar(master1, bg="green")
scrollbar1.pack( side = RIGHT, fill = Y )
You are looking for Scale widget . Please check this snippet and also please refer https://anzeljg.github.io/rin2/book2/2405/docs/tkinter/scale.html for more details.
from tkinter import *
root = Tk()
root.geometry("100x100")
v1 = DoubleVar()
s1 = Scale( root, variable = v1,from_ = 1, to = 100,orient = HORIZONTAL)
l3 = Label(root, text = "Horizontal Scaler")
l1 = Label(root)
s1.pack(anchor = CENTER)
l3.pack()
l1.pack()
root.mainloop()
Edit
If you want the scale value dynamically on moving the pointer of scale and without triggering any button then please check this snippet along with screenshot.
from tkinter import *
def get_value(val):
scale_val = "Scale value= " + str(val)
label.config(text = scale_val)
root = Tk()
root.geometry("100x150")
v1 = DoubleVar()
s1 = Scale( root, variable = v1,from_ = 1, to = 100,orient = HORIZONTAL, command=get_value)
l3 = Label(root, text = "Horizontal Scaler")
l1 = Label(root)
s1.pack(anchor = CENTER)
l3.pack()
l1.pack()
label = Label(root)
label.pack()
root.mainloop()
Related
I am trying to create the program that has an add button, When it is clicked, several different elements like entries and buttons should appear on the output window. Firstly I am not able to structure the display correctly and secondly I am not sure as to how to get the values entered by the user in entry widget of Tkinter.
Here is the Code:
from tkinter import *
from tkinter import messagebox
lb = Tk()
def addentry():
i = 3 // the 3 here should keep on incrementing so that the row goes on increasing as the user
keeps on adding different entries. This is for the display
ent1 = Entry(lb, bd=5).grid(row =i ,column= 0)
ent2 = Entry(lb, bd=5).grid(row = i, column=2)
ent3 = Entry(lb, bd=5).grid(row = i, column=4)
ent4 = Entry(lb, bd=5).grid(row = i , column=6)
addent = Button(lb, text = "Add Entry",command = addentry).grid(row = 0, column = 2)
It's all about keepin references. References are used to identify objects.
import tkinter as tk
root = tk.Tk()
my_entries = []
entry_row = 1
def addentry():
global entry_row
ent = tk.Entry(root, bd=5)
ent.grid(row =entry_row ,column= 0)
my_entries.append(ent)
entry_row = entry_row+1
def getter():
for entry in my_entries:
my_stuff = entry.get()
print(my_stuff)
addent = tk.Button(root, text = "Add Entry",command = addentry)
addent.grid(row = 0, column = 0)
getent = tk.Button(root,text='get input', command= getter)
getent.grid(row=0, column=1)
root.mainloop()
In this exampel we keepin the references of the tk.Entry and the variable entry_row while we would like to work with later on. There are a bunch of solution for this. Here we had used a global variable and a list in the global namespace to access them.
I am having trouble gaining the outputs from this form and i cant seem to identify where its going wrong.
from tkinter import *
def Button_to_text():
firstname_info = firstname.get()
lastname_info = lastname.get()
age_info = age.get()
print(firstname_info,lastname_info,age_info)
screen = Tk()
screen.geometry("500x500")
screen.title("python_form")
heading = Label(text = "Demo Form",bg = "orange", fg="black",width = "500")
heading.pack()
firstname_text = Label(text="firstname")
lastname_text = Label(text="lastname")
age_text = Label(text="age")
firstname_text.place(x=60, y= 40)
lastname_text.place(x=60,y=80)
age_text.place(x=60,y=120)
firstname = StringVar()
lastname = StringVar()
age = IntVar()
firstname_entry = Entry(textvariable = firstname)
lastname_entry = Entry(textvariable = lastname)
age_entry = Entry(textvariable = age)
firstname_entry.place(x=160, y=40)
lastname_entry.place(x=160,y=80)
age_entry.place(x=160,y=120)
register = Button(text = "register", width= "30",height ="2", command = Button_to_text())
register.place(x=50,y=290)
I followed a tutorial and my computing teacher cant help because he doesn't know python. plus my friends cant seem to identify the issue there are also no errors coming up so I know its a logic error and i also cant work out how to step so i can check variables
thanks to anyone who can help.
There are two problems with your code:
You have to use a mainloop to keep the window being displayed continuously.
You should not use the parentheses() while passing any function to a Button as an argument.
Note: And if the function has its own parameters then you will have to use lambda while passing it to a Button. But in your case, you can simply remove the parentheses().
Here's the fixed code:
from tkinter import *
def Button_to_text():
firstname_info = firstname.get()
lastname_info = lastname.get()
age_info = age.get()
print(firstname_info, lastname_info, age_info)
screen = Tk()
screen.geometry("500x500")
screen.title("python_form")
heading = Label(text="Demo Form", bg="orange", fg="black", width="500")
heading.pack()
firstname_text = Label(text="firstname")
lastname_text = Label(text="lastname")
age_text = Label(text="age")
firstname_text.place(x=60, y=40)
lastname_text.place(x=60, y=80)
age_text.place(x=60, y=120)
firstname = StringVar()
lastname = StringVar()
age = IntVar()
firstname_entry = Entry(textvariable=firstname)
lastname_entry = Entry(textvariable=lastname)
age_entry = Entry(textvariable=age)
firstname_entry.place(x=160, y=40)
lastname_entry.place(x=160, y=80)
age_entry.place(x=160, y=120)
register = Button(text="register", width="30", height="2", command=Button_to_text)
register.place(x=50, y=290)
screen.mainloop()
Note:
As a good practice, you should always use small letters in the names of functions like this: def button_to_text():.
And you should always import tkinter as tk instead of importing all * from tkinter. It is always a good practice. The only change you will need to do in the program is that you will need to use tk. before each item belonging to tkinter. Like this: screen = tk.Tk()
why does this code fail
im trying to summon a window when the settings button is pressed that allows users to change the forground and background colours
i get the radio buttons but recive an error every time i submit the colours even though their value is not 0
how do i fix this and why does it happen?
from tkinter import *
import os
from tkinter import messagebox as mgb
import tkinter.ttk as tk2
global colour_1, colour_2
colour_1 = "pink"
colour_2 = "purple" #background
def sayclick() :
btn.configure(text = "saying")
text = txt.get()
os.system("""PowerShell -Command "Add-Type –AssemblyName System.Speech; (New-Object System.Speech.Synthesis.SpeechSynthesizer).Speak('""" + text + """ ');" """)
btn.configure(text = "say")
def colourmenu():
window = Tk()
window.title("colour menu")
selected = IntVar()
selected2 = IntVar()
rad11 = tk2.Radiobutton(window,text='blue ', value=1, variable=selected)# set 1
rad21 = tk2.Radiobutton(window,text='green', value=2, variable=selected)#
rad31 = tk2.Radiobutton(window,text='red ', value=3, variable=selected)#
rad41 = tk2.Radiobutton(window,text='black', value=4, variable=selected)#
rad12 = tk2.Radiobutton(window,text='blue ', value=1, variable=selected2)
rad22 = tk2.Radiobutton(window,text='green', value=2, variable=selected2)
rad32 = tk2.Radiobutton(window,text='red ', value=3, variable=selected2)
rad42 = tk2.Radiobutton(window,text='black', value=4, variable=selected2)
def submitbut():
if selected.get() == 0 :
mgb.showinfo("error", "error: invalid colour choise")
elif selected2.get() == 0 :
mgb.showinfo("error", "error: invalid colour choise")
else :
for n in range(1,3):
if n == 1 :
val = selected.get()
rep = 1
else :
val = selected2.get()
rep = 2
if val == 1:
colour = "blue"
elif val == 2 :
colour = "green"
elif val == 3 :
colour = "red"
else :
colour = "black"
if rep == 1 :
bg = colour
else :
fg = colour
submit = Button(window, text="submit", command=submitbut)
txt1 = Label(window, text = "background")
txt1.grid(column = 0, row = 0)
txt2 = Label(window, text = "forground")
txt2.grid(column = 1, row = 0)
rad11.grid(column=0, row=1)#set 1
rad21.grid(column=0, row=2)#
rad31.grid(column=0, row=3)#
rad41.grid(column=0, row=4)#
rad12.grid(column=1, row=1)
rad22.grid(column=1, row=2)
rad32.grid(column=1, row=3)
rad42.grid(column=1, row=4)
submit.grid(column=0, row=5)
window.mainloop()
root = Tk()
root.geometry("170x120")
root.title("tts entry box")
root.configure(background = colour_2)
lab = Label(root, text = "enter text and than press\n\"say\" to say the text", font = ("Arial Bold", 10), fg = colour_2, bg = colour_1)
lab.grid(column = 0, row = 0)
btn = Button(root, text = " say. ", font = ("Arial", 8), bg = colour_1, fg = colour_2, command = sayclick)
btn.grid(column = 0, row = 3)
btn2 = Button(root, text = "settings", font = ("Arial", 8), bg = colour_1, fg = colour_2, command = colourmenu)
btn2.grid(column = 0, row = 4)
txt = Entry(root, width = 10, bg = colour_1, fg = colour_2)
txt.grid(column = 0, row = 2)
root.mainloop()
The problem is that you have two separate Tk objects in your program. This is almost always a bad idea, and the reason it's a bad idea is that it means that any code that relies on the "default Tk object" is likely to do the wrong thing.
In particular, when you do this:
selected = IntVar()
… you're creating an IntVar that's part of the first Tk that you created.1,2 But the Radiobutton widgets are attached to a different Tk. So, they can't read those variables (that's why you start off with all of the radio buttons in indeterminate state), and they can't write to them either.3
If you want to create a new top-level window, you don't need to create a whole new Tk environment, just use a Toplevel widget:
def colormenu():
window = Toplevel()
# the rest of your code can be the same
And then, the IntVars end up as part of the same Tk as the window.
While we're at it, do you really want to put a mainloop inside the other mainloop? This is legal, but I don't think it's what you want. It's almost certainly better to just return from colormenu after the submit.grid and let the main mainloop loop. (If you were trying to make colormenu a modal dialog, that blocks interaction with the main window, this isn't the way to do it.)
1. You can explicitly specify a parent when creating an IntVar, the same way you do for a widget. For example, selected = IntVar(window) would make this problem go away. But there are additional problems with having a separate Tk here, so it's better to solve them all at once by just not having one.
2. If you ever need to have multiple Tk instances, and need to know which one a variable, widget, etc. is attached to, you can look at its _root attribute. For example, selected._root is window._root will tell you whether they're part of the same Tk or not—in this case, it's False with your code as written, but True with the change in the next paragraph.
3. If you're curious why this isn't giving you a useful and easily-debuggable error, you have to understand how tkinter actually works. Tkinter is a wrapper around the Tk library, written in a completely separate scripting language called Tcl. Each Tk root instance has its own entirely independent Tcl interpreter, with its own independent global variables. So, your selected = IntVar() is creating a Tcl global variable named PY_VAR0 inside your first Tcl interpreter. Then, your variable=selected tells Tcl to store changes to the global variable PY_VAR0 in your second Tcl interpreter. So, whenever there's a change, Tcl writes to the global variable PY_VAR0 in the second interpreter, which is perfectly legal, but perfectly useless, because your selected looks up PY_VAR0 in the first interpreter.
I'm using a simple code that displays the square root of a number in a label, but for some reason the values get overlaped in a way that I couldn't avoid it, which means that, if I use it for a number that has a exact square root, then the answer goes messed up with the previous answer of many digits.
I've been use the next code so far:
from Tkinter import *
def square_calc():
x = x_val.get()
sqx = x ** 0.5
print x, "** 0.5 =", sqx
sqx_txt = Label(root, text = "x ** 0.5 =").grid(row=3, column=0)
sqx_lab = Label(root, text = sqx).grid(row=3, column=1)
root = Tk()
root.title("Calculating square root")
x_val = DoubleVar()
x_lab = Label(root, text = "x").grid(row=0, column=0)
nmb = Entry(root, textvariable = x_val).grid(row=0, column=1)
calc = Button(root, text = "Calculate", command=square_calc).grid(columnspan=2)
y_lab = Label(root, text = " ").grid(row=3, column=0)
root.mainloop()
The problem is that, every time you call square_calc(), you are simply creating and placing another Label. The right way to do this is to create a Label outside the function, then have the function update the Label's text with mylabel.config(text='new text').
The display is getting messed-up because every time your square_calc() function is called it creates new pair of Labels, but this may leave some parts of any previous ones visible. Since the one on the left is the same every time, so it's not noticeable with it, but the text in one on the right in column 1 is potentially different every time.
A simple way to fix that is to make the Label a global variable and create it outside the function, and then just change its contents in the function. As with all Tkinter widgets, this is can be done after it's created by calling the existing obj's config() method.
Here's a minimally-modified version of your code that illustrates doing that. Note, it also adds a sticky keyword arugment to the grid() method call for the label to left-justify it within the grid cell so it's closer to the text label immediately to its left (otherwise it would be center-justified within the cell).
from Tkinter import *
def square_calc():
x = x_val.get()
sqx = x ** 0.5
# print x, "** 0.5 =", sqx
sqx_txt = Label(root, text = "x ** 0.5 =").grid(row=3, column=0)
sqx_lab.config(text=sqx)
sqx_lab.grid(row=3, column=1, sticky=W)
root = Tk()
root.title("Calculating square root")
x_val = DoubleVar()
x_lab = Label(root, text = "x").grid(row=0, column=0)
nmb = Entry(root, textvariable = x_val).grid(row=0, column=1)
calc = Button(root, text = "Calculate", command=square_calc).grid(columnspan=2)
y_lab = Label(root, text = " ").grid(row=3, column=0)
sqx_lab = Label(root, text = " ")
root.mainloop()
There's another potentially serious flaw in your code. All those assignments of the form
variable = Widget(...).grid(...)
result in assigning the value None to the variable because that's what the grid() method returns. I didn't fix them because they do no harm in this cause since none of those variables are ever referenced again, but it would have been a problem if the new globally variable sqx_lab had been done that way since it is referenced elsewhere.
I am doing a bit of basic Tkinter code, and when I launch I get no errors, but my window is empty, even though I have added things to them. I saw this question here, but that does not help me, as I have what it says to do.
from tkinter import *
class App:
def __init__(self,master):
frame = Frame(master)
frame.pack
self.sg = Button(frame, text = "Study Guide", command = self.studyGuide)
self.sg.grid(row = 2, column = 1)
self.sg.pack()
self.quizlet = Button(frame, text = "Quizlet", command = self.quizlet)
self.quizlet.grid(row = 2, column = 2)
self.quizlet.pack()
self.flashcard = Button(frame, text = "Flash Cards", command = self.flashcard)
self.flashcard.grid(row = 2, column = 3)
self.flashcard.pack()
self.quitButton = Button(frame, text = "Quit", command = frame.quit)
self.quitButton.grid(row = 3, column = 2)
self.quitButton.pack()
self.text = Label(frame, text = "Social Studies Study Tool")
self.text.grid(row = 1, column = 2)
self.text.pack()
def studyGuide(self):
print("Study Guide")
def quizlet(self):
print("Quizlet")
def flashcard(self):
print("Flashcards")
root = Tk()
app = App(root)
root.mainloop()
First, for every element that you call grid for, don't call pack. You only need to use one or the other. Second:
frame = Frame(master)
frame.pack
You appear to be missing a parentheses here.
frame = Frame(master)
frame.pack()
Don't mix up layout managers! Use either pack() or grid(), but not both.
If you use pack, add the side where to pack the items:
frame.pack() # note the missing () in your code
...
self.sg.pack(side=TOP)
If you use grid(), add frame.grid() to the top of your code:
frame.grid()
...
self.sg.grid(row = 2, column = 1)