12

I'm having trouble trying to get Arduino digital ports values and set these values into a Python Tkinter Widget Scale.

I'm using Python and Arduino with Firmata. I'm able to access my arduino board with python code. For example in a label widget I'm getting and setting Arduino analog port value in real-time to a label as in following code without any problems:

import Tkinter
import pyfirmata
def onStartButtonPress():
 while True:
 if flag.get():
 analogReadLabel.config(text=str(a0.read()))
 analogReadLabel.update_idletasks()
 top.update()
 else:
 break
 board.exit()
 top.destroy()
def onExitButtonPress():
 flag.set(False)
port = 'COM7'
board = pyfirmata.Arduino(port)
it = pyfirmata.util.Iterator(board)
it.start()
a0 = board.get_pin('a:0:i')
top = Tkinter.Tk()
top.title("Reading Analog pins")
descriptionLabel = Tkinter.Label(top, text="Potentiometer input:- ")
descriptionLabel.grid(column=1, row=1)
analogReadLabel = Tkinter.Label(top, text="Press Start..")
analogReadLabel.grid(column=2, row=1)
flag = Tkinter.BooleanVar(top)
flag.set(True)
startButton = Tkinter.Button(top, text="Start", command=onStartButtonPress)
startButton.grid(column=1, row=2)
exitButton = Tkinter.Button(top, text="Exit", command=onExitButtonPress)
exitButton.grid(column=2, row=2)
top.mainloop()

Up to this point it's okay and the GUI shows me something like:

Python Gui interface reading real-time value from analog 0

But what I'm trying to do and not getting is:

What I'm trying to update Scale with digital pins

Here is the code:

import Tkinter
import pyfirmata
import serial; 
def onStartButtonPress():
 while True:
 if flag.get():
 analogReadLabel.config(text=str(d8.read()))
 analogReadLabel1.config(text=str(d9.read()))
 analogReadLabel2.config(text=str(d10.read()))
 analogReadLabel.update_idletasks()
 pos1 = d8.read()
 if pos1 == True:
 pos1 = int(pos1)
 pos1 = 0
 brightnessScale.set(pos1)
 pos2 = d9.read()
 if pos2 == True:
 pos2 = int(pos2)
 pos2 = 100
 brightnessScale.set(pos2)
 ''' and so on '''
 brightnessScale.update_idletasks()
 top.update()
 else:
 break
board.exit()
top.destroy()
def onExitButtonPress():
 flag.set(False)
port = 'COM7'
board = pyfirmata.Arduino(port)
it = pyfirmata.util.Iterator(board)
it.start()
a0 = board.get_pin('a:0:i')
d4 = board.get_pin('d:4:i')
d5 = board.get_pin('d:5:i')
d6 = board.get_pin('d:6:i')
d7 = board.get_pin('d:7:i')
d8 = board.get_pin('d:8:i')
d9 = board.get_pin('d:9:i')
d10 = board.get_pin('d:10:i')
top = Tkinter.Tk()
top.geometry("800x600")
top.title("Reading Analog pins")
descriptionLabel = Tkinter.Label(top, text="Potentiometer input:- ")
descriptionLabel.grid(column=1, row=1)
analogReadLabel = Tkinter.Label(top, text="Level 1")
analogReadLabel.grid(column=2, row=1)
analogReadLabel1 = Tkinter.Label(top, text="Level 2")
analogReadLabel1.grid(column=3, row=1)
analogReadLabel2 = Tkinter.Label(top, text="Level 3")
analogReadLabel2.grid(column=4, row=1)
brightnessScale = Tkinter.Scale(top, from_ = 500, 
 to = 0, 
 length = 500, 
 width = "30",
 tickinterval = 50, 
 bg = "lightskyblue",
 highlightcolor = "darkblue",
 highlightbackground = "royalblue",
 troughcolor = "darkblue",
 state = Tkinter.DISABLED,
 sliderlength = 50,
 relief = "sunken",
 label = "Volume do Reservatorio em %",
 orient = Tkinter.VERTICAL)
brightnessScale.grid(column=1, row=5)
Tkinter.Label(top,text="Volume da Caixa em (%)").grid(column=1, row=6)
flag = Tkinter.BooleanVar(top)
flag.set(True)
startButton = Tkinter.Button(top, text="Start", command=onStartButtonPress)
startButton.grid(column=1, row=2)
exitButton = Tkinter.Button(top, text="Exit", command=onExitButtonPress)
exitButton.grid(column=2, row=2)
top.mainloop()

To summarize: I have reed switches in each digital port declared in the code. These reed switches are normally open state, when I put a magnetic field near them it turn to close and I get a change in that value like from False to True. What I'm trying to do is update the Tkinter Scale Widget in real time as the labels but I'm not getting it.

Is there any trick in python code that can solve my problem ? Because I did a lot of research on the internet and I could not get done, as you can see in image 2 when the state of the second digital pin changes, a label changes to True, and in the scale code this corresponds to the value 100, but it's still on the 0 mark.

I'm not comfortable also with the usage of command, and variable parameters of scale widget.

In short, I want to update in real time python Tkinter scale widget according to values from digital ports from arduino using firmata.

I'm using Python 2.7

PS: for completeness:

This is my arduino code (Sketch) without firmata, which is working as expected.

int level; 
int position; 
void setup() {
pinMode(8, INPUT); 
pinMode(9, INPUT);
pinMode(10, INPUT);
pinMode(11, INPUT);
pinMode(12, INPUT);
Serial.begin(9600); // ativa a porta serial
void loop() {
digitalWrite(8, LOW); 
digitalWrite(9, LOW);
digitalWrite(10, LOW);
digitalWrite(11, LOW);
digitalWrite(12, LOW);
position = digitalRead(8); 
if ( position == HIGH) {level=0;}
position = digitalRead(9); 
if ( position == HIGH) {Level=100;}
position = digitalRead(10); 
if ( position == HIGH) {level=200;}
position = digitalRead(11); 
if ( position == HIGH) {level=300;}
position = digitalRead(12); 
if ( position == HIGH) {level=400;}
Serial.println(level); 
delay(500);
}

What I could do also here is get these values via serial in python and use them to update the scale in this way but I don't know if in this method it's gonna work also!

And what I thought in Python: But I still have much to learn in algorithms and Data Structures. Just the Pseudo Code:

def setScaleValue():
while True:
 if flag.get():
 pos1 = d4.read()
 if pos1 == True: #or 1 
 #Here is the problem i don't know for sure what comes in my digital port
 #If is a True bool or a 1 as HIGH value from arduino
 #And probably i don't know if it's possible to change the values of a scale in this way !!!
 #or if i'm mistaken the Cast stuff in Python
 pos1 = int(pos1)
 pos1 = 0
 brightnessScale.set(pos1)
 pos2 = d8.read()
 if pos2 == True:
 pos2 = int(pos2)
 pos2 = 100
 brightnessScale.set(pos2)
 brightnessScale.update_idletasks()
 top.update()
 else:
 break
board.exit()
top.destroy()
return
d4 = board.get_pin('d:4:i')
d5 = board.get_pin('d:5:i')
d6 = board.get_pin('d:6:i')
d7 = board.get_pin('d:7:i')
d8 = board.get_pin('d:8:i')
brightnessScale = Tkinter.Scale(top, from_ = 500, 
 to = 0, 
 length = 500, 
 width = "30",
 tickinterval = 50, 
 bg = "lightskyblue",
 highlightcolor = "darkblue",
 highlightbackground = "royalblue",
 troughcolor = "darkblue",
 state = Tkinter.DISABLED,
 sliderlength = 50,
 relief = "sunken",
 label = "Volume do Reservatorio em %",
 orient = Tkinter.VERTICAL)
brightnessScale.grid(column=1, row=5)
Tkinter.Label(top,text="Volume da Caixa em (%)").grid(column=1, row=6)
James Waldby - jwpat7
8,9203 gold badges20 silver badges33 bronze badges
asked Nov 22, 2015 at 15:16
2
  • your third file is malformed, def setScaleValue(): isn't defined properly, you need an indent level change after a function definition. Commented Jun 21, 2018 at 1:04
  • When your code runs, can you be able to click on stop button? Commented Sep 25, 2018 at 5:07

1 Answer 1

1

in your code:

pos2 = d8.read()
print("pos2 is {} type {}".format(pos2, type(pos2))) # This way, you'll know the var type you're getting on the console
 if posX == True:
 posX = int(posX) # You then cast to an integer
 posX = 100 # You discard pos2 value by setting it to 100
 brightnessScale.set(posX) # You set the scale always to value 100

By adding the print line, you can ensure the variable value and type.
Then, you may have to adapt your if statement accordingly.
Beware what you're doing then with those 2 lines reaffecting posX, this is probably not what you want to do before updating the scale.

answered Mar 16, 2017 at 6:19

Your Answer

Draft saved
Draft discarded

Sign up or log in

Sign up using Google
Sign up using Email and Password

Post as a guest

Required, but never shown

Post as a guest

Required, but never shown

By clicking "Post Your Answer", you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.