Skip to content

Instantly share code, notes, and snippets.

@jul
Last active October 6, 2024 10:48
Show Gist options
  • Save jul/594b8c7926790e09e32045fdc12e8bee to your computer and use it in GitHub Desktop.
Save jul/594b8c7926790e09e32045fdc12e8bee to your computer and use it in GitHub Desktop.
howto to do bi directionnal python + tcl/tk without tkinter
#!/usr/bin/env python
from subprocess import Popen, PIPE
from time import sleep, time, localtime
import fcntl
import os
# let's talk to tk/tcl directly through p.stdin
p = Popen(['wish'], stdin=PIPE, stdout=PIPE)
fd = p.stdout.fileno()
flag = fcntl.fcntl(fd, fcntl.F_GETFL)
fcntl.fcntl(fd, fcntl.F_SETFL, flag | os.O_NONBLOCK)
def puts(s):
for l in s.split("\n"):
p.stdin.write((l + "\n").encode())
p.stdin.flush()
def gets():
ret=p.stdout.read()
p.stdout.flush()
return ret
WIDTH=HEIGHT=400
puts(f"""
canvas .c -width {WIDTH} -height {HEIGHT} -bg white
pack .c
. configure -background white
ttk::button .ba -command {{ puts ch-=1 }} -text <<
pack .ba -side left -anchor w
ttk::button .bb -command {{ puts cm-=1 }} -text <
pack .bb -side left -anchor w
ttk::button .bc -command {{ puts ch+=1 }} -text >>
pack .bc -side right -anchor e
ttk::button .bd -command {{ puts cm+=1 }} -text >
pack .bd -side right -anchor e
""")
# Constant are CAPitalized in python by convention
from cmath import pi as PI, e as E
ORIG=complex(WIDTH/2, HEIGHT/2)
# correcting python notations j => I
I = complex("j")
rad_per_sec = 2.0 * PI /60.0
rad_per_min = rad_per_sec / 60
rad_per_hour = rad_per_min / 12
origin_vector_hand = WIDTH/2 * I
size_of_sec_hand = .9
size_of_min_hand = .8
size_of_hour_hand = .65
rot_sec = lambda sec : -E ** (I * sec * rad_per_sec )
rot_min = lambda min : -E ** (I * min * rad_per_min )
rot_hour = lambda hour : -E ** (I * hour * rad_per_hour )
to_real = lambda c1,c2 : "%f %f %f %f" % (c1.real,c1.imag,c2.real, c2.imag)
for n in range(60):
direction= origin_vector_hand * rot_sec(n)
start=.9 if n%5 else .85
puts(f".c create line {to_real(ORIG+start*direction,ORIG+.95*direction)}")
sleep(.01)
diff_offset_in_sec = (time() % (24*3600)) - \
localtime()[3]*3600 -localtime()[4] * 60.0 \
- localtime()[5]
ch=cm=0
while True:
# eventually parsing tcl output
back = gets()
# trying is more concise than checking
try:
back = back.decode()
exec(back)
except Exception as e:
pass
t = time()
s= t%60
m = m_in_sec = t%(60 * 60) + cm * 60
h = h_in_sec = (t- diff_offset_in_sec)%(24*60*60) + ch * 3600 + cm * 60
puts(".c delete second")
puts(".c delete minute")
puts(".c delete hour")
c0=ORIG+ -.1 * origin_vector_hand * rot_sec(s)
c1=ORIG+ size_of_sec_hand * origin_vector_hand * rot_sec(s)
puts( f".c create line {to_real(c0,c1)} -tag second -fill blue -smooth true")
c1=ORIG+size_of_min_hand * origin_vector_hand * rot_min(m)
puts(f".c create line {to_real(ORIG, c1)} -tag minute -fill green -smooth true")
c1=ORIG+size_of_hour_hand * origin_vector_hand * rot_hour(h)
puts(f".c create line {to_real(ORIG,c1)} -tag hour -fill red -smooth true")
puts("flush stdout")
sleep(.1)
@jul
Copy link
Author

jul commented Oct 5, 2024

image

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment