Skip to content
GitLab
Menu
Projects
Groups
Snippets
Help
Help
Support
Community forum
Keyboard shortcuts
?
Submit feedback
Contribute to GitLab
Sign in / Register
Toggle navigation
Menu
Open sidebar
Stefan Haun
firmware
Commits
122d37e9
Commit
122d37e9
authored
Sep 05, 2019
by
Rahix
Browse files
Merge 'Add DigiClk to preload'
See merge request
card10/firmware!282
parents
b8803880
c78dd28b
Changes
4
Hide whitespace changes
Inline
Side-by-side
preload/apps/digiclk/__init__.py
0 → 100644
View file @
122d37e9
import
os
import
sys
import
leds
import
display
import
buttons
sys
.
path
.
append
(
"/apps/digiclk/"
)
import
monotime
as
utime
import
draw
DIGITS
=
[
(
True
,
True
,
True
,
True
,
True
,
True
,
False
),
(
False
,
True
,
True
,
False
,
False
,
False
,
False
),
(
True
,
True
,
False
,
True
,
True
,
False
,
True
),
(
True
,
True
,
True
,
True
,
False
,
False
,
True
),
(
False
,
True
,
True
,
False
,
False
,
True
,
True
),
(
True
,
False
,
True
,
True
,
False
,
True
,
True
),
(
True
,
False
,
True
,
True
,
True
,
True
,
True
),
(
True
,
True
,
True
,
False
,
False
,
False
,
False
),
(
True
,
True
,
True
,
True
,
True
,
True
,
True
),
(
True
,
True
,
True
,
True
,
False
,
True
,
True
),
]
def
renderNum
(
d
,
num
,
x
):
draw
.
Grid7Seg
(
d
,
x
,
0
,
7
,
DIGITS
[
num
//
10
],
(
255
,
255
,
255
))
draw
.
Grid7Seg
(
d
,
x
+
5
,
0
,
7
,
DIGITS
[
num
%
10
],
(
255
,
255
,
255
))
def
renderColon
(
d
):
draw
.
GridVSeg
(
d
,
11
,
2
,
7
,
2
,
(
255
,
255
,
255
))
draw
.
GridVSeg
(
d
,
11
,
4
,
7
,
2
,
(
255
,
255
,
255
))
def
renderText
(
d
,
text
,
blankidx
=
None
):
bs
=
bytearray
(
text
)
if
blankidx
!=
None
:
bs
[
blankidx
:
blankidx
+
1
]
=
b
"_"
d
.
print
(
MODES
[
MODE
]
+
" "
+
bs
.
decode
(),
fg
=
(
255
,
255
,
255
),
bg
=
None
,
posx
=
0
,
posy
=
7
*
8
)
def
renderBar
(
d
,
num
):
d
.
rect
(
20
,
78
,
20
+
num
*
2
,
80
,
col
=
(
255
,
255
,
255
))
def
render
(
d
):
ltime
=
utime
.
localtime
()
years
=
ltime
[
0
]
months
=
ltime
[
1
]
days
=
ltime
[
2
]
hours
=
ltime
[
3
]
mins
=
ltime
[
4
]
secs
=
ltime
[
5
]
d
.
clear
()
if
MODE
==
CHANGE_YEAR
:
renderNum
(
d
,
years
//
100
,
1
)
renderNum
(
d
,
years
%
100
,
13
)
elif
MODE
==
CHANGE_MONTH
:
renderNum
(
d
,
months
,
13
)
elif
MODE
==
CHANGE_DAY
:
renderNum
(
d
,
days
,
13
)
else
:
renderNum
(
d
,
hours
,
1
)
renderNum
(
d
,
mins
,
13
)
if
MODE
not
in
(
CHANGE_YEAR
,
CHANGE_MONTH
,
CHANGE_DAY
)
and
secs
%
2
==
0
:
renderColon
(
d
)
renderText
(
d
,
NAME
,
None
)
renderBar
(
d
,
secs
)
d
.
update
()
LONG_DELAY
=
400
BUTTON_UPDATE_TIME
=
100
BUTTON_SEL
=
1
<<
0
BUTTON_SEL_LONG
=
1
<<
1
BUTTON_UP
=
1
<<
2
BUTTON_UP_LONG
=
1
<<
3
BUTTON_DOWN
=
1
<<
4
BUTTON_DOWN_LONG
=
1
<<
5
pressed_prev
=
0
button_long_prev
=
{
BUTTON_SEL
:
False
,
BUTTON_UP
:
False
,
BUTTON_DOWN
:
False
}
button_times
=
{
BUTTON_SEL
:
0
,
BUTTON_UP
:
0
,
BUTTON_DOWN
:
0
}
def
checkButton
(
button
,
button_long
,
osbutton
,
pressed
,
t
):
cur_buttons
=
0
if
pressed
&
osbutton
and
not
pressed_prev
&
osbutton
:
button_times
[
button
]
=
t
button_long_prev
[
button
]
=
False
elif
pressed_prev
&
osbutton
:
if
button_times
[
button
]
+
LONG_DELAY
<
t
:
cur_buttons
|=
button_long
button_times
[
button
]
=
t
button_long_prev
[
button
]
=
True
elif
not
pressed
&
osbutton
and
not
button_long_prev
[
button
]:
cur_buttons
|=
button
return
cur_buttons
def
checkButtons
():
global
pressed_prev
t
=
utime
.
time_monotonic_ms
()
pressed
=
buttons
.
read
(
buttons
.
BOTTOM_LEFT
|
buttons
.
TOP_RIGHT
|
buttons
.
BOTTOM_RIGHT
)
cur_buttons
=
0
cur_buttons
|=
checkButton
(
BUTTON_SEL
,
BUTTON_SEL_LONG
,
buttons
.
BOTTOM_LEFT
,
pressed
,
t
)
cur_buttons
|=
checkButton
(
BUTTON_UP
,
BUTTON_UP_LONG
,
buttons
.
TOP_RIGHT
,
pressed
,
t
)
cur_buttons
|=
checkButton
(
BUTTON_DOWN
,
BUTTON_DOWN_LONG
,
buttons
.
BOTTOM_RIGHT
,
pressed
,
t
)
pressed_prev
=
pressed
return
cur_buttons
def
modTime
(
yrs
,
mth
,
day
,
hrs
,
mns
,
sec
):
ltime
=
utime
.
localtime
()
new
=
utime
.
mktime
(
(
ltime
[
0
]
+
yrs
,
ltime
[
1
]
+
mth
,
ltime
[
2
]
+
day
,
ltime
[
3
]
+
hrs
,
ltime
[
4
]
+
mns
,
ltime
[
5
]
+
sec
,
None
,
None
,
)
)
utime
.
set_time
(
new
)
def
ctrl_display
(
bs
):
global
MODE
,
updated
updated
=
True
if
bs
&
BUTTON_SEL_LONG
:
MODE
=
CHANGE_HOURS
else
:
updated
=
False
def
ctrl_chg_hrs
(
bs
):
global
MODE
,
updated
updated
=
True
if
bs
&
BUTTON_SEL_LONG
:
MODE
=
DISPLAY
elif
bs
&
BUTTON_SEL
:
MODE
=
CHANGE_MINUTES
elif
bs
&
BUTTON_UP_LONG
:
modTime
(
0
,
0
,
0
,
10
,
0
,
0
)
elif
bs
&
BUTTON_DOWN_LONG
:
modTime
(
0
,
0
,
0
,
-
10
,
0
,
0
)
elif
bs
&
BUTTON_UP
:
modTime
(
0
,
0
,
0
,
1
,
0
,
0
)
elif
bs
&
BUTTON_DOWN
:
modTime
(
0
,
0
,
0
,
-
1
,
0
,
0
)
else
:
updated
=
False
def
ctrl_chg_mns
(
bs
):
global
MODE
,
updated
updated
=
True
if
bs
&
BUTTON_SEL_LONG
:
MODE
=
DISPLAY
elif
bs
&
BUTTON_SEL
:
MODE
=
CHANGE_SECONDS
elif
bs
&
BUTTON_UP_LONG
:
modTime
(
0
,
0
,
0
,
0
,
10
,
0
)
elif
bs
&
BUTTON_DOWN_LONG
:
modTime
(
0
,
0
,
0
,
0
,
-
10
,
0
)
elif
bs
&
BUTTON_UP
:
modTime
(
0
,
0
,
0
,
0
,
1
,
0
)
elif
bs
&
BUTTON_DOWN
:
modTime
(
0
,
0
,
0
,
0
,
-
1
,
0
)
else
:
updated
=
False
def
ctrl_chg_sec
(
bs
):
global
MODE
,
updated
updated
=
True
if
bs
&
BUTTON_SEL_LONG
:
MODE
=
DISPLAY
elif
bs
&
BUTTON_SEL
:
MODE
=
CHANGE_YEAR
elif
bs
&
BUTTON_UP_LONG
:
modTime
(
0
,
0
,
0
,
0
,
0
,
10
)
elif
bs
&
BUTTON_DOWN_LONG
:
modTime
(
0
,
0
,
0
,
0
,
0
,
-
10
)
elif
bs
&
BUTTON_UP
:
modTime
(
0
,
0
,
0
,
0
,
0
,
1
)
elif
bs
&
BUTTON_DOWN
:
modTime
(
0
,
0
,
0
,
0
,
0
,
-
1
)
else
:
updated
=
False
def
ctrl_chg_yrs
(
bs
):
global
MODE
,
updated
updated
=
True
if
bs
&
BUTTON_SEL_LONG
:
MODE
=
DISPLAY
elif
bs
&
BUTTON_SEL
:
MODE
=
CHANGE_MONTH
elif
bs
&
BUTTON_UP_LONG
:
modTime
(
10
,
0
,
0
,
0
,
0
,
0
)
elif
bs
&
BUTTON_DOWN_LONG
:
modTime
(
-
10
,
0
,
0
,
0
,
0
,
0
)
elif
bs
&
BUTTON_UP
:
modTime
(
1
,
0
,
0
,
0
,
0
,
0
)
elif
bs
&
BUTTON_DOWN
:
modTime
(
-
1
,
0
,
0
,
0
,
0
,
0
)
else
:
updated
=
False
def
ctrl_chg_mth
(
bs
):
global
MODE
,
updated
updated
=
True
if
bs
&
BUTTON_SEL_LONG
:
MODE
=
DISPLAY
elif
bs
&
BUTTON_SEL
:
MODE
=
CHANGE_DAY
elif
bs
&
BUTTON_UP_LONG
:
modTime
(
0
,
6
,
0
,
0
,
0
,
0
)
elif
bs
&
BUTTON_DOWN_LONG
:
modTime
(
0
,
-
6
,
0
,
0
,
0
,
0
)
elif
bs
&
BUTTON_UP
:
modTime
(
0
,
1
,
0
,
0
,
0
,
0
)
elif
bs
&
BUTTON_DOWN
:
modTime
(
0
,
-
1
,
0
,
0
,
0
,
0
)
else
:
updated
=
False
def
ctrl_chg_day
(
bs
):
global
MODE
,
updated
updated
=
True
if
bs
&
BUTTON_SEL_LONG
:
MODE
=
DISPLAY
elif
bs
&
BUTTON_SEL
:
MODE
=
CHANGE_HOURS
elif
bs
&
BUTTON_UP_LONG
:
modTime
(
0
,
0
,
10
,
0
,
0
,
0
)
elif
bs
&
BUTTON_DOWN_LONG
:
modTime
(
0
,
0
,
-
10
,
0
,
0
,
0
)
elif
bs
&
BUTTON_UP
:
modTime
(
0
,
0
,
1
,
0
,
0
,
0
)
elif
bs
&
BUTTON_DOWN
:
modTime
(
0
,
0
,
-
1
,
0
,
0
,
0
)
else
:
updated
=
False
NAME
=
None
FILENAME
=
"nickname.txt"
def
load_nickname
():
global
NAME
if
FILENAME
in
os
.
listdir
(
"."
):
with
open
(
"nickname.txt"
,
"rb"
)
as
f
:
name
=
f
.
read
().
strip
()
else
:
name
=
b
"no nick"
if
len
(
name
)
>
7
:
name
=
name
[
0
:
7
]
else
:
name
=
b
" "
*
(
7
-
len
(
name
))
+
name
NAME
=
name
# MODE values
DISPLAY
=
0
CHANGE_HOURS
=
1
CHANGE_MINUTES
=
2
CHANGE_SECONDS
=
3
CHANGE_YEAR
=
4
CHANGE_MONTH
=
5
CHANGE_DAY
=
6
MODE
=
DISPLAY
MODES
=
{
DISPLAY
:
"---"
,
CHANGE_HOURS
:
"HRS"
,
CHANGE_MINUTES
:
"MNS"
,
CHANGE_SECONDS
:
"SEC"
,
CHANGE_YEAR
:
"YRS"
,
CHANGE_MONTH
:
"MTH"
,
CHANGE_DAY
:
"DAY"
,
}
updated
=
False
CTRL_FNS
=
{
DISPLAY
:
ctrl_display
,
CHANGE_HOURS
:
ctrl_chg_hrs
,
CHANGE_MINUTES
:
ctrl_chg_mns
,
CHANGE_SECONDS
:
ctrl_chg_sec
,
CHANGE_YEAR
:
ctrl_chg_yrs
,
CHANGE_MONTH
:
ctrl_chg_mth
,
CHANGE_DAY
:
ctrl_chg_day
,
}
def
main
():
global
updated
try
:
load_nickname
()
with
display
.
open
()
as
d
:
last_secs
,
secs
=
0
,
0
last_msecs
,
msecs
=
0
,
0
while
True
:
updated
=
False
bs
=
checkButtons
()
CTRL_FNS
[
MODE
](
bs
)
last_secs
,
secs
=
secs
,
utime
.
time_monotonic
()
if
updated
or
secs
>
last_secs
:
render
(
d
)
last_msecs
,
msecs
=
msecs
,
utime
.
time_monotonic_ms
()
if
msecs
-
last_msecs
<
BUTTON_UPDATE_TIME
:
utime
.
sleep_ms
(
BUTTON_UPDATE_TIME
-
(
msecs
-
last_msecs
))
except
KeyboardInterrupt
:
pass
main
()
preload/apps/digiclk/draw.py
0 → 100644
View file @
122d37e9
def
_ceilDiv
(
a
,
b
):
return
(
a
+
(
b
-
1
))
//
b
def
TipHeight
(
w
):
return
_ceilDiv
(
w
,
2
)
-
1
def
Tip
(
d
,
x
,
y
,
w
,
c
,
invert
=
False
,
swapAxes
=
False
):
h
=
TipHeight
(
w
)
for
dy
in
range
(
h
):
for
dx
in
range
(
dy
+
1
,
w
-
1
-
dy
):
px
=
x
+
dx
py
=
y
+
dy
if
not
invert
else
y
+
h
-
1
-
dy
if
swapAxes
:
px
,
py
=
py
,
px
d
.
pixel
(
px
,
py
,
col
=
c
)
def
Seg
(
d
,
x
,
y
,
w
,
h
,
c
,
swapAxes
=
False
):
tip_h
=
TipHeight
(
w
)
body_h
=
h
-
2
*
tip_h
Tip
(
d
,
x
,
y
,
w
,
c
,
invert
=
True
,
swapAxes
=
swapAxes
)
px1
,
px2
=
x
,
x
+
w
py1
,
py2
=
y
+
tip_h
,
y
+
tip_h
+
body_h
if
swapAxes
:
px1
,
px2
,
py1
,
py2
=
py1
,
py2
,
px1
,
px2
d
.
rect
(
px1
,
py1
,
px2
-
1
,
py2
-
1
,
col
=
c
)
Tip
(
d
,
x
,
y
+
tip_h
+
body_h
,
w
,
c
,
invert
=
False
,
swapAxes
=
swapAxes
)
def
VSeg
(
d
,
x
,
y
,
w
,
l
,
c
):
Seg
(
d
,
x
,
y
,
w
,
l
,
c
)
def
HSeg
(
d
,
x
,
y
,
w
,
l
,
c
):
Seg
(
d
,
y
,
x
,
w
,
l
,
c
,
swapAxes
=
True
)
def
GridSeg
(
d
,
x
,
y
,
w
,
l
,
c
,
swapAxes
=
False
):
sw
=
w
-
2
tip_h
=
TipHeight
(
sw
)
x
=
x
*
w
y
=
y
*
w
l
=
(
l
-
1
)
*
w
Seg
(
d
,
x
+
1
,
y
+
tip_h
+
3
,
sw
,
l
-
3
,
c
,
swapAxes
=
swapAxes
)
def
GridVSeg
(
d
,
x
,
y
,
w
,
l
,
c
):
GridSeg
(
d
,
x
,
y
,
w
,
l
,
c
)
def
GridHSeg
(
d
,
x
,
y
,
w
,
l
,
c
):
GridSeg
(
d
,
y
,
x
,
w
,
l
,
c
,
swapAxes
=
True
)
def
Grid
(
d
,
x1
,
y1
,
x2
,
y2
,
w
,
c
):
for
x
in
range
(
x1
*
w
,
x2
*
w
):
for
y
in
range
(
y1
*
w
,
y2
*
w
):
if
x
%
w
==
0
or
x
%
w
==
w
-
1
or
y
%
w
==
0
or
y
%
w
==
w
-
1
:
d
.
pixel
(
x
,
y
,
col
=
c
)
def
Grid7Seg
(
d
,
x
,
y
,
w
,
segs
,
c
):
if
segs
[
0
]:
GridHSeg
(
d
,
x
,
y
,
w
,
4
,
c
)
if
segs
[
1
]:
GridVSeg
(
d
,
x
+
3
,
y
,
w
,
4
,
c
)
if
segs
[
2
]:
GridVSeg
(
d
,
x
+
3
,
y
+
3
,
w
,
4
,
c
)
if
segs
[
3
]:
GridHSeg
(
d
,
x
,
y
+
6
,
w
,
4
,
c
)
if
segs
[
4
]:
GridVSeg
(
d
,
x
,
y
+
3
,
w
,
4
,
c
)
if
segs
[
5
]:
GridVSeg
(
d
,
x
,
y
,
w
,
4
,
c
)
if
segs
[
6
]:
GridHSeg
(
d
,
x
,
y
+
3
,
w
,
4
,
c
)
preload/apps/digiclk/metadata.json
0 → 100644
View file @
122d37e9
{
"name"
:
"DigiClk"
,
"description"
:
"A Digital Clock, configurable via buttons"
,
"category"
:
"wearable"
,
"author"
:
"yrlf"
,
"revision"
:
1
}
preload/apps/digiclk/monotime.py
0 → 100644
View file @
122d37e9
import
utime
as
_utime
_offset_ms
=
0
def
time_monotonic
():
return
_utime
.
time
()
+
_offset_ms
//
1000
def
time_monotonic_ms
():
return
_utime
.
time_ms
()
+
_offset_ms
def
sleep
(
s
):
return
_utime
.
sleep
(
s
)
def
sleep_ms
(
ms
):
return
_utime
.
sleep_ms
(
ms
)
def
sleep_us
(
us
):
return
_utime
.
sleep_us
(
us
)
def
time
():
return
_utime
.
time
()
def
time_ms
():
return
_utime
.
time_ms
()
def
set_time
(
t
):
global
_offset_ms
cur_t
=
_utime
.
time_ms
()
_utime
.
set_time
(
t
)
new_t
=
_utime
.
time_ms
()
diff
=
cur_t
-
new_t
_offset_ms
+=
diff
def
set_unix_time
(
t
):
global
_offset_ms
cur_t
=
_utime
.
time_ms
()
_utime
.
set_unix_time
(
t
)
new_t
=
_utime
.
time_ms
()
diff
=
cur_t
-
new_t
_offset_ms
+=
diff
def
localtime
(
s
=
None
):
if
s
!=
None
:
return
_utime
.
localtime
(
s
)
else
:
return
_utime
.
localtime
()
def
mktime
(
t
):
return
_utime
.
mktime
(
t
)
def
alarm
(
s
,
cb
=
None
):
if
cb
!=
None
:
return
_utime
.
alarm
(
s
,
cb
)
else
:
return
_utime
.
alarm
(
s
)
Write
Preview
Supports
Markdown
0%
Try again
or
attach a new file
.
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment