marion
marion

Reputation: 27

linking a command to a spinbox in Tkinter

I am creating a measurement converter to a Tkinter script and would like to add a spinbox that allows the user to select the original measurement type (currently only feet and Meters) and convert it to the other. The spinbox will be linked to an entry widget, but I can't seem to link the two widgets with a button to convert the measurments.

This is my spinbox code:

    self.SelectedLength = Tkinter.IntVar()
    measurements = ('Feet', 'Meters')
    sb = Spinbox(self, values=sorted(measurements), width=10, textvariable=self.SelectedLength)
    sb.grid(column=1, row=1)

And the code for the conversions:

def ConvertToMeters(self):
    value = float(self.entry.get())
    meters = ((0.3048 * value * 10000.0 + 0.5)/10000.0)
    self.labelVariable.set("The converted length in meters is: " + str(meters))


def ConvertToFeet(self):
    value = float(self.entry.get())
    feet = ((3.2808399 * value * 10000.0 + 0.5)/10000.0)
    self.labelVariable.set("The converted length in feet is: " + str(feet))

How do I link the conversions to the spinbox and a button to produce the desired output?

Upvotes: 0

Views: 3304

Answers (2)

slightlynybbled
slightlynybbled

Reputation: 2645

I know that this has some time on it, but I have a slightly better solution. I published a set of pip-installable widgets some time ago which I am still refining called tk_tools. Within that package is a SmartSpinBox widget which contains the variables internal to the class.

from tk_tools import SmartSpinBox

def callback(value):
    if value == 'feet':
        ConvertToFeet()
    else:
        ConvertToMeters()

ssb = SmartSpinBox(root, entry_type='str', values=('feet', 'meters'), callback=callback)
ssb.grid()

Check out the documentation for more useful elements!

Upvotes: 1

Terry Jan Reedy
Terry Jan Reedy

Reputation: 19144

The following works according to my understanding of your description.

import tkinter as tk


units = {'feet': (.3048, 'meters'), 'meters': (3.2808399, 'feet')}
def convert():
    orig = unit.get()
    mult, to = units[orig]
    output.set(str(mult * float(entry.get())) + ' ' + to)

root = tk.Tk()
output = tk.StringVar()
entry = tk.Entry(root)
unit = tk.Spinbox(root, values=tuple(units), width=10, wrap=True)
go = tk.Button(root, text='Convert', command=convert)
display = tk.Label(root, textvariable=output)
entry.grid(row=0, column=0)
unit.grid(row=0, column=1)
go.grid(row=0, column=2)
display.grid(row=1, column=0)
root.mainloop()

To generalize, you would need a spinbox for both input and output and two dicts of conversion factors, one to meters and one from meters.

Upvotes: 0

Related Questions