Notice. New forum software under development. It's going to miss a few functions and look a bit ugly for a while, but I'm working on it full time now as the old forum was too unstable. Couple days, all good. If you notice any issues, please contact me.
|
Forum Index : Microcontroller and PC projects : Anyone know Python?
Page 1 of 3 | |||||
Author | Message | ||||
lew247 Guru Joined: 23/12/2015 Location: United KingdomPosts: 1676 |
I'm trying to get my Si7021 temp/humidity module working with Python I've got it working great BUT I cannot fathom or figure out how to get the min and max temperatures to check if the date has changed then use the current values date has changed means its a new day ie just gone midnight This is the code thats working perfectly from kivy.clock import Clock from functools import partial import smbus import time def read(Obs,dt): # SI7021 address, 0x40(64) # Read data, 2 bytes, Humidity MSB first bus = smbus.SMBus(1) rh = bus.read_i2c_block_data(0x40, 0xE5, 2) time.sleep(0.1) # Convert the data humid = ((rh[0] * 256 + rh[1]) * 125 / 65536.0) - 6 # SI7021 address, 0x40(64) # Read data , 2 bytes, Temperature MSB first temp = bus.read_i2c_block_data(0x40, 0xE3,2) time.sleep(0.1) # Convert the data cTemp = ((temp[0] * 256 + temp[1]) * 175.72 / 65536.0) - 46.85 fTemp = cTemp * 1.8 + 32 # Format the temperature for display and assign to indoor temperature # variable Temp = ['{:.1f}'.format(cTemp), u'\N{DEGREE CELSIUS}'] Obs['inTemp'] = Temp # Get new temperature in 60 seconds Clock.schedule_once(partial(read,Obs), 60) # Output data to screen *** this is what I need sent to the Display*** #print ("Humidity %%RH: %.2f%%" %humid) #print "Temperature : %.2f C" %cTemp This is what I'm trying but it keeps coming up with errors from kivy.clock import Clock from lib import derivedVariables as derive from functools import partial import smbus import pytz import datetime as dt from datetime import datetime import time def read(Obs,dt): # Define current time in station timezone Now = datetime.now() # current date and time Format = '%H:%M' # SI7021 address, 0x40(64) # Read data, 2 bytes, Humidity MSB first bus = smbus.SMBus(1) rh = bus.read_i2c_block_data(0x40, 0xE5, 2) time.sleep(0.01) # Convert the data humid = ((rh[0] * 256 + rh[1]) * 125 / 65536.0) - 6 # SI7021 address, 0x40(64) # Read data , 2 bytes, Temperature MSB first temp = bus.read_i2c_block_data(0x40, 0xE3,2) time.sleep(0.1) # Convert the data cTemp = ((temp[0] * 256 + temp[1]) * 175.72 / 65536.0) - 46.85 fTemp = cTemp * 1.8 + 32 # Format the temperature for display and assign to indoor temperature # variable Temp = ['{:.1f}'.format(cTemp), u'\N{DEGREE CELSIUS}'] Obs['inTemp'] = Temp # Define maximum and minimum temperature and time MaxTemp = Temp,'c',datetime.now() MinTemp = Temp,'c',datetime.now() #======================================== #This is what I am trying to modify to work MaxTemp = [max(Temp)[0],'c',datetime.fromtimestamp(Time[Temp.index(max(Temp))][0],Tz).strftime(Format),max(Temp)[0],Now] MinTemp = [min(Temp)[0],'c',datetime.fromtimestamp(Time[Temp.index(min(Temp))][0],Tz).strftime(Format),min(Temp)[0],Now] #============================================== # Else if midnight has passed, reset maximum and minimum temperature if datetime.now() > MaxTemp.date MaxTemp =Temp MinTemp = Temp # Else if current temperature is greater than maximum recorded temperature, # update maximum temperature elif Temp > MaxTemp: MaxTemp = Temp MinTemp = MinTemp # Else if current temperature is less than minimum recorded temperature, # update minimum temperature elif Temp < minTemp: MinTemp = Temp MaxTemp = MaxTemp # Else maximum and minimum temperature unchanged, return existing values else: MaxTemp = maxTemp MinTemp = MinTemp # Return required variables return MaxTemp,MinTemp # Get new temperature in 60 seconds Clock.schedule_once(partial(read,Obs), 60) # Output data to screen *** this is what I need sent to the Display*** #print ("Humidity %%RH: %.2f%%" %humid) #print "Temperature : %.2f C" %cTemp The error at the moment is Anyone know a simpler way to get the min and max temps and change them to zero at midnight? The two variables I need are MinTemp MaxTemp and update at midnight (new date) Edited 2020-10-28 21:07 by lew247 |
||||
hitsware2 Guru Joined: 03/08/2019 Location: United StatesPosts: 705 |
if datetime.now() > MaxTemp.date try : ( add colon ) if datetime.now() > MaxTemp.date: my site |
||||
lew247 Guru Joined: 23/12/2015 Location: United KingdomPosts: 1676 |
Thanks I tried that before it then comes up with different errors |
||||
lizby Guru Joined: 17/05/2016 Location: United StatesPosts: 3015 |
Don't make everybody guess. PicoMite, Armmite F4, SensorKits, MMBasic Hardware, Games, etc. on fruitoftheshed |
||||
lew247 Guru Joined: 23/12/2015 Location: United KingdomPosts: 1676 |
lol sorry I lost track of all the errors I'll try them all again now if datetime.now() > MaxTemp.date; ^ SyntaxError: invalid syntax Edited 2020-10-29 04:25 by lew247 |
||||
lew247 Guru Joined: 23/12/2015 Location: United KingdomPosts: 1676 |
I used a semicolon to get the above error When I use a colon I get 2020-10-28 18:26:07+0000 [-] if datetime.now() > MaxTemp.date: 2020-10-28 18:26:07+0000 [-] AttributeError: 'tuple' object has no attribute 'date' |
||||
hitsware2 Guru Joined: 03/08/2019 Location: United StatesPosts: 705 |
Look here ? Maybe try [] rather than () ? Python has lists, and tuples, and ?? like Basic has arrays ... Edited 2020-10-29 04:59 by hitsware2 my site |
||||
lew247 Guru Joined: 23/12/2015 Location: United KingdomPosts: 1676 |
I'm getting a bit further from kivy.clock import Clock from lib import derivedVariables as derive from functools import partial import smbus import pytz import datetime as dt from datetime import datetime import time def read(Obs,dt): # Define current time in station timezone Now = datetime.now() # current date and time Format = '%H:%M' M1 = datetime.now() # current day of Month Format = '%H:%M:%-d' # SI7021 address, 0x40(64) # Read data, 2 bytes, Humidity MSB first bus = smbus.SMBus(1) rh = bus.read_i2c_block_data(0x40, 0xE5, 2) time.sleep(0.01) # Convert the data humid = ((rh[0] * 256 + rh[1]) * 125 / 65536.0) - 6 # SI7021 address, 0x40(64) # Read data , 2 bytes, Temperature MSB first temp = bus.read_i2c_block_data(0x40, 0xE3,2) time.sleep(0.1) # Convert the data cTemp = ((temp[0] * 256 + temp[1]) * 175.72 / 65536.0) - 46.85 fTemp = cTemp * 1.8 + 32 # Format the temperature for display and assign to indoor temperature # variable Temp = ['{:.1f}'.format(cTemp), u'\N{DEGREE CELSIUS}'] Obs['inTemp'] = Temp # Define maximum and minimum temperature and time MaxTemp = Temp,'c',Now MinTemp = Temp,'c',Now # If midnight has passed, reset maximum and minimum temperature if Now > M1: MaxTemp = Temp MinTemp = Temp # Else if current temperature is greater than maximum recorded temperature, # update maximum temperature if Temp > MaxTemp: MaxTemp = Temp # Else if current temperature is less than minimum recorded temperature, # update minimum temperature if Temp < MinTemp: MinTemp = Temp MaxTemp = MaxTemp # Else maximum and minimum temperature unchanged, return existing values else: MaxTemp = maxTemp MinTemp = MinTemp I've got as far as line 58 now 2020-10-28 19:23:06+0000 [-] if Temp < MinTemp: 2020-10-28 19:23:06+0000 [-] TypeError: '<' not supported between instances of 'list' and 'tuple' Edited 2020-10-29 05:24 by lew247 |
||||
hitsware2 Guru Joined: 03/08/2019 Location: United StatesPosts: 705 |
if Temp > MaxTemp: MaxTemp = Temp MinTemp = MinTemp Maybe something to do with the ' immutability ' of some values ( in tuples or arrays or ? ) my site |
||||
lew247 Guru Joined: 23/12/2015 Location: United KingdomPosts: 1676 |
Just updated the previous post I've got it working as far as line 58 now from kivy.clock import Clock from lib import derivedVariables as derive from functools import partial import smbus import pytz import datetime as dt from datetime import datetime import time def read(Obs,dt): # Define current time in station timezone Now = datetime.now() # current date and time Format = '%H:%M' M1 = datetime.now() # current day of Month Format = '%H:%M:%-d' # SI7021 address, 0x40(64) # Read data, 2 bytes, Humidity MSB first bus = smbus.SMBus(1) rh = bus.read_i2c_block_data(0x40, 0xE5, 2) time.sleep(0.01) # Convert the data humid = ((rh[0] * 256 + rh[1]) * 125 / 65536.0) - 6 # SI7021 address, 0x40(64) # Read data , 2 bytes, Temperature MSB first temp = bus.read_i2c_block_data(0x40, 0xE3,2) time.sleep(0.1) # Convert the data cTemp = ((temp[0] * 256 + temp[1]) * 175.72 / 65536.0) - 46.85 fTemp = cTemp * 1.8 + 32 # Format the temperature for display and assign to indoor temperature # variable Temp = ['{:.1f}'.format(cTemp), u'\N{DEGREE CELSIUS}'] Obs['inTemp'] = Temp # Define maximum and minimum temperature and time MaxTemp = Temp,'c',Now MinTemp = Temp,'c',Now # If midnight has passed, reset maximum and minimum temperature if Now > M1: MaxTemp = Temp MinTemp = Temp # Else if current temperature is greater than maximum recorded temperature, # update maximum temperature if Temp > MaxTemp: MaxTemp = Temp # Else if current temperature is less than minimum recorded temperature, # update minimum temperature if Temp < MinTemp: MinTemp = Temp # Else maximum and minimum temperature unchanged, return existing values else: MaxTemp = maxTemp MinTemp = MinTemp # Return required variables return MaxTemp,MinTemp # Get new temperature in 60 seconds Clock.schedule_once(partial(read,Obs), 60) # Output data to screen *** this is what I need sent to the Display*** #print ("Humidity %%RH: %.2f%%" %humid) #print "Temperature : %.2f C" %cTemp If I delete the section in red it all works if I put it back in I get the error: 2020-10-28 19:50:49+0000 [-] if Temp < MinTemp: 2020-10-28 19:50:49+0000 [-] TypeError: '<' not supported between instances of 'list' and 'tuple' Python is hard, really hard Edited 2020-10-29 05:52 by lew247 |
||||
CircuitGizmos Guru Joined: 08/09/2011 Location: United StatesPosts: 1421 |
It is a whitespace/tabbing issue. You need to indent consistently. Micromites and Maximites! - Beginning Maximite |
||||
lew247 Guru Joined: 23/12/2015 Location: United KingdomPosts: 1676 |
OMG I went over it about tem times in case that was the issue and I could not find any problems with it I copy and pasted the section before it and changed the names and < > and it now works Python is something I don't intend to get into it's a real PITA |
||||
Tinine Guru Joined: 30/03/2016 Location: United KingdomPosts: 1646 |
And here endeth the lesson on why BASIC is and always will be the king of programming languages....you c? |
||||
hitsware2 Guru Joined: 03/08/2019 Location: United StatesPosts: 705 |
> Python is something I don't intend to get into it's a real PITA PITA for sure BUT Hard to evade . AFAIK no Basic for the current ' developement boards ' Most geared to Arduino ( even bigger PITA ) MicroPython and CircuitPython fairly common . my site |
||||
jcwippler Newbie Joined: 29/10/2020 Location: NetherlandsPosts: 3 |
Every tool takes time to dive in and get used to. Python has "min" and "max" functions built-in. Python 2.7.16 (default, Jun 5 2020, 22:59:21) [GCC 4.2.1 Compatible Apple LLVM 11.0.3 (clang-1103.0.29.20) (-macos10.15-objc- on darwin Type "help", "copyright", "credits" or "license" for more information. >>> max(123,234) 234 >>> min(123,234) 123 One way to make progress, is to enter lines at the "REPL" interactive prompt, until each piece works and makes sense. Maybe this is of use to you: >>> tmin = 123 >>> tmax = 234 >>> for t in [100,200,300]: ... print min(tmin,t), max(tmax,t) ... 100 234 123 234 123 300 >>> PS. Things to keep in mind: exact indentation matters, and exact upper/lower case in variable names matter. Edited 2020-10-29 10:46 by jcwippler |
||||
lew247 Guru Joined: 23/12/2015 Location: United KingdomPosts: 1676 |
To achieve what I need is beyond me I'm afraid I needed to accomplish this [ max/min temperature as a string, u'\N{DEGREE CELSIUS}', time of max/min formatted as a string, max/min temp as a float, time of max/min temp as a datetime ] I got lost at string float and datetime in Python Given up for now, I'll stick with the the temperature now showing on the display Edited 2020-10-29 20:39 by lew247 |
||||
greybeard Senior Member Joined: 04/01/2010 Location: AustraliaPosts: 157 |
Me and Monty are old mates. Can't help with the new version though. |
||||
lew247 Guru Joined: 23/12/2015 Location: United KingdomPosts: 1676 |
I'm trying to send this FROM a Pi to a Micromite via HC-12 serial communication from kivy.clock import Clock from functools import partial import smbus import time import time import serial ser = serial.Serial( port='/dev/ttyAMA0', baudrate = 9600, parity=serial.PARITY_NONE, stopbits=serial.STOPBITS_ONE, bytesize=serial.EIGHTBITS, timeout=1 ) def read(Obs,dt): # SI7021 address, 0x40(64) # Read data, 2 bytes, Humidity MSB first bus = smbus.SMBus(1) rh = bus.read_i2c_block_data(0x40, 0xE5, 2) time.sleep(0.1) # Convert the data humid = ((rh[0] * 256 + rh[1]) * 125 / 65536.0) - 6 # SI7021 address, 0x40(64) # Read data , 2 bytes, Temperature MSB first temp = bus.read_i2c_block_data(0x40, 0xE3,2) time.sleep(0.1) # Convert the data cTemp = ((temp[0] * 256 + temp[1]) * 175.72 / 65536.0) - 46.85 fTemp = cTemp * 1.8 + 32 # Format the temperature for display and assign to indoor temperature # variable Temp = ['{:.1f}'.format(cTemp), u'\N{DEGREE CELSIUS}'] Obs['inTemp'] = Temp ser.write(bytes(b'inTemp'),('i')(bytes(b'WindSpd')) # Get new temperature in 60 seconds Clock.schedule_once(partial(read,Obs), 60) # Output data to screen *** this is what I need sent to the Display*** #print ("Humidity %%RH: %.2f%%" %humid) #print "Temperature : %.2f C" %cTemp return True I get this error Clock.schedule_once(partial(read,Obs), 60) ^ SyntaxError: invalid syntax Everything worked perfectly until I added this line ser.write(bytes(b'inTemp'),bytes('i'),(bytes(b'WindSpd')) 'inTemp' and 'WindSpd' are strings The serial port and pyserial works fine, I've tested it by looping it back to itself and just sending ser.write(b'hello') via loopback and also via and HC-12 from Pi to Micromite which works as expected I've tried ser.write(bytes('inTemp'),bytes('i'),(bytes(b'WindSpd')) and ser.write(bytes(b'inTemp'),('i'),(bytes(b'WindSpd')) I'm TRYING to send the contents of inTemp followed by comma then the contents of WindSpd Ideally I'd like to end the transmit sequence with * so I can tell the Micromite the serial receive is ready to parse Does anyone know enough about Python to know how to do it? |
||||
GoodToGo! Senior Member Joined: 23/04/2017 Location: AustraliaPosts: 188 |
I don't know much about Python, but it looks like you are either missing a ")" or have one "(" too many..... ...... Don't worry mate, it'll be GoodToGo! |
||||
palcal Guru Joined: 12/10/2011 Location: AustraliaPosts: 1801 |
Try putting another closing bracket at the end of the line. "It is better to be ignorant and ask a stupid question than to be plain Stupid and not ask at all" |
||||
Page 1 of 3 |
Print this page |