I need help Building a python app for windows - python

Windows10/Python3
So i have the beep.pyw file located in startup:shell, it beeps every 30 minutes automatically when you open the pc.
And i'm using Tkinter to make a GUI widget "widget.py" which contains 4 advices to do in the breaks like (breathing stretching, hydrating etc...) = Done
Problem is :
How to open the widget every time the pc beeps.
Should i put both files in one file or how can i add the statement to open the "widget.py" in the "beep.pyw" ?
This is the beep.pyw :
import time
import winsound
beep_time = 30*60
def beep_every60():
while True :
winsound.Beep(2000, 1000)
winsound.Beep(2000, 1000)
time.sleep(beep_time)
beep_every60()

import time
import winsound
from tkinter import *
class WindowsBeep(Tk):
def __init__(self):
super().__init__()
self.title_ = "Windows Beep"
self.title(self.title_)
self.bg = "#222222"
self.fg = "#cccccc"
self["bg"] = self.bg
self.__largura_tela__ = self.winfo_screenwidth()
self.__altura_tela__ = self.winfo_screenheight()
self.porcentagem_largura = 0.50
self.porcentagem_altura = 0.75
self.__largura_app__ = int(self.__largura_tela__ * self.porcentagem_largura)
self.__altura_app__ = int(self.__altura_tela__ * self.porcentagem_altura)
self.centro_l_janela = int((self.__largura_tela__ // 2) - (self.__largura_app__ // 2) + 2)
self.centro_a_janela = int((self.__altura_tela__ * (1 - self.porcentagem_altura)) // 2)
self.__center__ = f"{self.__largura_app__}x{self.__altura_app__}+{self.centro_l_janela}+{self.centro_a_janela}"
self.geometry(self.__center__)
beep_time = 30*60
def beep_every60():
while True :
winsound.Beep(2000, 1000)
winsound.Beep(2000, 1000)
WindowsBeep().mainloop()
time.sleep(beep_time)
beep_every60()

Related

Need to get mean and max values with this script

I'm having a few problems.
First, given wind speeds seem to be low, especially compared to other weather stations reporting close by (apparently there are lots of enthusiasts in my area). Just watching the trees, flag, bushes, small animals flying across my yard, I can tell 1.6mph is a wee bit low. Everything tested fine inside, and when I run the test script outside its picking up the signal as it spins.
the 2nd problem is it always reports the "mean" and "max" speeds as exactly the same. I've tried to adjust the intervals, but no matter what length of time I put in, they always report as the same numbers.
from gpiozero import Button
import requests
import time
import math
import statistics
import database
wind_count = 0
radius_cm = 9.0
wind_interval = 5
ADJUSTMENT = 1.18
interval = 60
gust = 0
def spin():
global wind_count
wind_count = wind_count + 1
def calculate_speed(time_sec):
global wind_count
global gust
circumference_cm = (2 * math.pi) * radius_cm
rotations = wind_count / 2.0
dist_cm = circumference_cm * rotations
dist_km = (circumference_cm * rotations) / 100000
dist_mi = dist_km * 0.621371
mi_per_sec = dist_mi / time_sec
mi_per_hour = mi_per_sec * 3600
return mi_per_hour * ADJUSTMENT
def reset_wind():
global wind_count
wind_count = 0
def reset_gust():
global gust
gust = 0
wind_speed_sensor = Button(16)
wind_speed_sensor.when_activated = spin
while True:
print("Starting Weather Sensor Read Loop...")
start_time = time.time()
while time.time() - start_time <= interval:
print("Start timed loop...")
wind_start_time = time.time()
reset_wind()
reset_gust()
store_speeds = []
time.sleep(wind_interval)
final_speed = calculate_speed(wind_interval)
store_speeds.append(final_speed)
wind_gust_speed = (max(store_speeds))
wind_speed = (statistics.mean(store_speeds))
print(wind_average, wind_speed)
When I comment out "store_speeds = [ ]" the first loop the speeds are reported the same, every loop after I get a "max" reading thats "different" than the mean. This still troubles me, because why on the first loop are they the same? Am I wrong for thinking with the wind_interval set at 5, and the interval set to 60, that its taking 5 second samples over a 60 second period, giving me 12 sample to get the mean and max from?
My goal is every time it reports, I get a mean and max for that "loop" if possible, and not a mean/max over the time the script stays running before its interrupted/stopped.
Here is the working and corrected code:
from gpiozero import Button
import time
import math
import statistics
wind_count = 0
radius_cm = 9.0
wind_interval = 5
interval = 30
CM_IN_A_KM = 100000.0
SECS_IN_AN_HOUR = 3600
ADJUSTMENT = 1.18
store_speeds = []
def reset_wind():
global wind_count
wind_count = 0
def spin():
global wind_count
wind_count = wind_count + 1
def calculate_speed(time_sec):
global wind_count
circumference_cm = (2 * math.pi) * radius_cm
rotations = wind_count / 2.0
dist_km = (circumference_cm * rotations) / CM_IN_A_KM
km_per_sec = dist_km / time_sec
km_per_hour = km_per_sec * SECS_IN_AN_HOUR
mi_per_hour = km_per_hour * 0.6214
return mi_per_hour * ADJUSTMENT
wind_speed_sensor = Button(16)
wind_speed_sensor.when_pressed = spin
while True:
store_speeds = []
for _ in range (interval//wind_interval):
reset_wind()
#reset_gust()
time.sleep(wind_interval) # counter is spinning in background
final_speed = calculate_speed(wind_interval)
store_speeds.append(final_speed)
wind_gust = max(store_speeds)
wind_speed = statistics.mean(store_speeds)
print(wind_speed, wind_gust)

Update displayed value everytime ipywidgets are updated

In my notebook i have 7 FloatSlider widgets. I want to have the product of these 7 widgets displayed at all times in a way that, as the user moves the sliders, the value displayed is updated. Currently i am trying to display the product of the SliderWidgets in a Widgets.Text (n), but i am not sure if it is the best solution.
import ipywidgets as widgets
caption = widgets.Label(value='Play around with the variables to see how N changes!')
r = widgets.FloatSlider(value=1,
min=1.0,
max=3.0,
step=0.1,
description="R*")
fp = widgets.FloatSlider(value=1,
min=0.35,
max=1.0,
step=0.05,
description="fp")
ne = widgets.FloatSlider(value=1
min=0.2,
max=3.0,
step=0.1,
description="ne")
fl = widgets.FloatSlider(value=1,
min=1.0,
max=1.3,
step=0.05,
description="fl")
fi = widgets.FloatSlider(value=1,
min=0.5,
max=1.5,
step=0.05,
description="fi")
fc = widgets.FloatSlider(value=0.20,
min=0.10,
max=0.30,
step=0.05,
description="fi",)
l = widgets.FloatSlider(value=60000000.0,
min=5000000.0,
max=1000000000.0,
step=5000000,
description="fi")
n = widgets.Text(
value= str(int(r.value * fp.value * ne.value * fl.value * fi.value * fc.value * l.value)) + " civilizations" ,
description='Estimated N:',
disabled=True)
left_box = VBox([r, fp, ne,fl])
right_box = VBox([ fi,fc,l,n])
HBox([left_box, right_box])
This code that i used displays the widgets, but does not update the widget n automatically. What is the best way for me to do it, that does not involve printing a new value everytime?
You can use an observe and a callback function on value change for each slider
def on_value_change(change):
n.value = str(int(r.value * fp.value * ne.value * fl.value * fi.value * fc.value * l.value)) + " civilizations"
r.observe(on_value_change)
fp.observe(on_value_change)
# ...

Implement multithreading in Python Zelle graphics

I am creating a program which opens a world map in a window using Zelle's graphics.py. It has one function which draws dots on the map, and another function which undraws those dots after they are on the screen for 1 second (which are stored in a list after being drawn). I want these functions to work concurrently, but when the addDots() function is called in a thread it won't draw the dot in the window, it just stalls. Here is the module which I run:
import thread
import threading
import time
import random
import sys
sys.path.append('..')
from Display import map
import tester
import datetime
dots = list(())
def deleteDots():
while 1==1:
tF = datetime.datetime.now()
a = 0
for i in range(len(dots)):
tD = tF - dots[i-a][2]
tD = int(str(tD)[5:7])
if tD >= 1:
map.deletePoint(dots[i-a][0],dots[i-a][1])
dots.pop(i-a)
a = a+1
def addDots():
oldResponseCount = tester.getResponseCount()
oldResponseCount = int(str(oldResponseCount))
while 1==1:
print(oldResponseCount)
newResponseCount = tester.getResponseCount()
newResponseCount = int(str(newResponseCount))
print(newResponseCount)
if(newResponseCount != oldResponseCount):
difference = newResponseCount - oldResponseCount
for i in range(difference):
lat = random.randint(-90,90)
long = random.randint(-180,180)
map.drawPoint(lat,long)
tI = datetime.datetime.now()
dots.append([lat,long,tI])
oldResponseCount = newResponseCount
if __name__ == '__main__':
threading.Thread(target=addDots).start()
threading.Thread(target=deleteDots).start()
And here is the map module which draws the map on a graphics window and contains the functions to plot and delete a point:
from graphics import *
import math
import images
size = 0.6
Circles = list(())
win = GraphWin("My Window", 1920*size, 1080*size)
win.setBackground('blue')
images.test(size)
myImage = Image(Point(960*size,540*size), "../Display/temp.gif")
myImage.draw(win)
import time
def drawPoint(lat,long):
x = int(long*5.3+960)*size
y = int(lat*(-5.92)+540)*size
pt = Point(x,y)
cir = Circle(pt,5)
cir.setFill(color_rgb(255,0,0))
Circles.append([cir,x,y])
cir.draw(win)
def deletePoint(lat,long):
x = int(long*5.3+960)*size
y = int(lat*(-5.92)+540)*size
for c in Circles:
if c[1]==x and c[2]==y:
c[0].undraw()
How should I go about doing this?
There are a couple of issues that have to be addressed. First, any graphics.py commands that invoke tkinter (i.e. commands that cause something to be drawn/undrawn) must be issued by the primary (main) thread. So we need the secondary threads to communicate drawing requests to the primary thread.
Second, you have both your secondary threads modifying the Circles and dots lists -- you need to syncronize (lock) access to these lists so that only one thread at a time can modify or iterate them.
Below is my rework of your code as an example. I've eliminated map and tester routines as I'm just putting dots up on a window with one thread and deleting them after they are a second old from another thread:
from threading import Thread, Lock
from queue import Queue # use for thread-safe communications
from random import randint
import time
from graphics import *
def drawPoint(lat, long):
x = int(long * 5.3 + 960)
y = int(lat * -5.92 + 540)
point = Point(x, y)
circle = Circle(point, 5)
circle.setFill(color_rgb(255, 0, 0))
circles_lock.acquire()
circles.append(circle)
circles_lock.release()
actions.put((circle.draw, win))
def deletePoint(lat, long):
global circles
x = int(long * 5.3 + 960)
y = int(lat * -5.92 + 540)
keep_circles = []
circles_lock.acquire()
for circle in circles:
center = circle.getCenter()
if center.getX() == x and center.getY() == y:
actions.put((circle.undraw,))
else:
keep_circles.append(circle)
circles = keep_circles
circles_lock.release()
def deleteDots():
global dots
while True:
keep_dots = []
dots_lock.acquire()
now = time.time()
for dot in dots:
lat, long, then = dot
if now - then >= 1.0:
deletePoint(lat, long)
else:
keep_dots.append(dot)
dots = keep_dots
dots_lock.release()
time.sleep(0.5)
def addDots():
while True:
lat = randint(-90, 90)
long = randint(-180, 180)
drawPoint(lat, long)
dots_lock.acquire()
dots.append((lat, long, time.time()))
dots_lock.release()
time.sleep(0.25)
win = GraphWin("My Window", 1920, 1080)
circles = []
circles_lock = Lock()
dots = []
dots_lock = Lock()
actions = Queue()
Thread(target=addDots, daemon=True).start()
Thread(target=deleteDots, daemon=True).start()
while True:
if not actions.empty():
action, *arguments = actions.get()
action(*arguments)
time.sleep(0.125)

ModuleNotFoundError: No module named 'breezypythongui'

I have created GUI program in python which converts C2F and F2C when I run my program I get an error though I imported module correctly. Can anyone please help me to solve an error
Code:
from breezypythongui import EasyFrame
#from tkinter import PhotoImage
from tkinter import *
class ProgDemo(EasyFrame):
def __init__(self):
EasyFrame.__init__(self,width="600", title = "Program")
self.addLabel(text = "Temp",row = 1, column = 0)
self.getinput = self.addFloatField(value = 0.0,row = 1,column = 1)
self.addLabel(text = "Output",row = 2, column = 0)
self.op = self.addFloatField(value = 0.0,row = 2,column = 1)
self.grp1 = self.addRadiobuttonGroup(row = 3,column = 0)
C_to_F = self.grp1.addRadiobutton(text = "C to F")
F_to_C = self.grp1.addRadiobutton(text = "F to C")
self.conBtn = self.addButton(text = "convert",row = 5, column = 0,command = self.tempc)
self.resetBtn = self.addButton(text = "reset",row = 5, column = 1,command = self.reseti)
def tempc(self):
ipval = self.getinput.getNumber()
if self.grp1.getSelectedButton()["value"] == "C to F":
op = 9.0/5.0 * ipval + 32
else:
op = (ipval - 32) * 5.0/9.0
self.op.setValue(op)
def reseti(self):
self.getinput.setValue(0);
self.op.setValue(0);
def main():
ProgDemo().mainloop()
if __name__ == "__main__":
main()
Screenshot:
It seems like, the module is missing and you need it.
So download and install it: http://home.wlu.edu/~lambertk/breezypythongui/
You need to have the module breezepythongui.py and your python code in the same folder. Not only having the folder but both modules must be in the same folder.
For example; My python code "myfirstguiproject.py" and "breezypythongui.py" are in the same folder.
I know when you extract the downloaded zip file named breezypythongui.zip, it will create a folder and in that folder there is the "breezypythongui.py" module. You need to get rid of the folder and only keep the module (breezypythongui.py).

Python Cocos2d: tiles show up only once

I'm working on a custom tiled map loader. Seems to work fine, I don't get any errors, but the screen only shows up 1 tile of each type.
this is the file structure:
/main.py
/other/render2.py
/other/render.py
here's the render2.py file:
import pyglet, json
from pyglet.window import key
from pyglet.gl import *
from ConfigParser import SafeConfigParser
from cocos.layer import *
from cocos.batch import *
from cocos.sprite import Sprite
class renderer( Layer ):
#init function
def __init__(self):
super( renderer, self ).__init__()
#call function, returns the map as a list of sprites, and coordinates
def __call__(self, mapname):
#runs the map file parser
parser = SafeConfigParser()
#reads the map file
try:
world = parser.read('maps/'+mapname+'.txt')
print world
except IOError:
return
#These variables the config from the map file
tileSize = int(parser.get('config', 'tilesize'))
layers = int(parser.get('config', 'layers'))
mapList = []
#the super mega advanced operation to render the mapList
for i in range(0,layers):
layer = json.loads(parser.get('layer'+str(i), 'map'))
tileType = parser.get('layer'+str(i), 'tiletype')
nTiles = int(parser.get('layer'+str(i), 'tiles'))
tileSet = []
#this over here loads all 16 tiles of one type into tileSet
for n in range(0, nTiles):
tileSet.append(Sprite("image/tiles/"+tileType+"/"+str(n)+".png", scale = 1, anchor = (0,0)))
for x in range(0, len(layer)):
for y in range(0, len(layer[x])):
X = (x*tileSize)
Y = (y*tileSize)
total = [tileSet[layer[x][y]], i, X, Y]
print layer[x][y], tileSet[layer[x][y]]
mapList.append(total)
return mapList
This is an example of what this returns :
[<cocos.sprite.Sprite object at 0x060910B0>, 0, 0,0 ]
[<cocos.sprite.Sprite object at 0x060910B0> , 0, 64,64 ]
It returns a huge list with a lot of sublists like these in it.
when I call it from the main.py file, it only draws the last tile of each kind.
here's the main.py file:
import sys, os
sys.path.insert(0, os.path.join(os.path.dirname(__file__), '..'))
import pyglet
import threading,time
from pyglet import clock
from pyglet.gl import *
from cocos.director import *
from cocos.menu import *
from cocos.scene import *
from cocos.layer import *
from cocos.actions import *
from cocos.batch import *
from cocos.sprite import Sprite
from other.render2 import renderer
import random; rr = random.randrange
class Background(ScrollableLayer):
def __init__(self):
super(Background, self).__init__()
world = renderer()
bg = world('sampleidea')
batch = BatchNode()
for i in range(0, len(bg)):
l= bg[i][1]
x= bg[i][2]
y= bg[i][3]
spr = bg[i][0]
spr.position =(x,y)
batch.add(spr, z = l)
self.add(batch)
class Menu(Layer):
def __init__(self):
super(Menu, self).__init__()
title = Sprite('image/title.png' )
title.position = (400,520)
self.add( title )
def start():
director.set_depth_test()
background = Background()
menu = Menu()
scene = Scene(background, menu)
return scene
def init():
director.init( do_not_scale=True, resizable=True, width=1280, height=720)
def run(scene):
director.run( scene )
if __name__ == "__main__":
init()
s = start()
run(s)
What am I doing wrong? I have an older render.py, which does work, but I remade it since it loaded each sprite file for each tile. That took way to long to load on big maps.
This is the old render.py I've been using before.
It's quite different since it used different map files too.
import pyglet, json
from pyglet.window import key
from pyglet.gl import *
from ConfigParser import SafeConfigParser
from cocos.layer import *
from cocos.batch import *
from cocos.sprite import Sprite
class renderer( Layer ):
def __init__(self):
super( renderer, self ).__init__()
def __call__(self, mapname):
parser = SafeConfigParser()
try:
world = parser.read('maps/'+mapname+'.txt')
print world
except IOError:
print("No world file!")
return
tilesize = json.loads(parser.get('data', 'tilesize'))
world = json.loads(parser.get('data', 'world'))
maplist = []
for l in range(len(world)):
for x in range(len(world[l])):
for y in range(len(world[l][x])):
if world[l][x][y] != None:
foldername = str(world[l][x][y][0])
imagename = str(world[l][x][y][1])
spr = Sprite("image/tiles/"+foldername+"/"+imagename+".png", scale = 1, anchor = (0,0))
X = (x*tilesize)
Y = (y*tilesize)
total = [spr, l, X, Y]
maplist.append(total)
return maplist
Is it possible to make the new "render" to work?
The problem is that my new optimized "renderer" creates a bunch of
cocos.sprite.Sprite objects, instead of just loading Image files as i thought it would. The code in my question only repositioned the same sprite object over and over again this way. To solve this, the way to do it is by opening the image with pyglet.image.load(), and creating sprite objects with that.
example:
f = pyglet.image.load('sprite.png')
batch = CocosNode()
batch.position = 50, 100
add(batch)
for i in range(0, 200):
test = Sprite(f)
test.position = i*10,i*10
batch.add( test )

Categories