Python 双按钮菜单迭代

Python 双按钮菜单迭代,python,micropython,Python,Micropython,我有一个脚本,我正在2040上适应micropython,我想使用两个按钮来导航菜单结构。我不知道如何使多选菜单中的迭代循环正常工作。。。以下是到目前为止我得到的信息: """ fit: a productivity logger """ import time import sys import os import uhashlib import machine def final_print(sec,final_hash,fina

我有一个脚本,我正在2040上适应micropython,我想使用两个按钮来导航菜单结构。我不知道如何使多选菜单中的迭代循环正常工作。。。以下是到目前为止我得到的信息:

""" fit: a productivity logger """
import time
import sys
import os
import uhashlib
import machine

def final_print(sec,final_hash,final_survey):
    """ leaves the summary on the screen before shutting down """
    mins = sec // 60
    sec = sec % 60
    hours = mins // 60
    mins = mins % 60
    short_sec = int(sec)
    duration = (str(hours) + "/" + str(mins) + "/" + str(short_sec))
    print("> fit the",str(final_hash)," went ",str(final_survey)," lasted //",str(duration))

def timer_down(f_seconds,timer_focus):
    """ counts down for defined period """
    now = time.time()
    end = now + f_seconds
    while now < end:
        now = time.time()
        fit_progress(now,end,timer_focus,f_seconds)
        b1pressed = button1.value()
        time.sleep(0.01)
        if not b1pressed:
             print('Ended Manually!')
             break

def timer_up(timer_focus):
    """ counts up for indefinite period """
    now = time.time()
    while True:
         minutes = int((time.time() - now) / 60)
         print(str(timer_focus)," for ",str(minutes))
         b1pressed = button1.value()
         time.sleep(0.01)
         if not b1pressed:
             print('Ended Manually!')
             break

def fit_progress(now,end,timer_focus,f_seconds):
    """ tracks progress of a count-down fit and prints to screen """
    remain = end - now
    f_minutes = int((remain)/60)
    j = 1 - (remain / f_seconds)
    pct = int(100*j)
    print(str(timer_focus),str(f_minutes),str(pct))

def multi_choice(options):
    done = 0
    while done == 0:
        for i in options:
            b1pressed = button1.value()
            b2pressed = button2.value()
            time.sleep(.01)
            b1released = button1.value()
            b2released = button2.value()
            if b2pressed and not b1pressed:
                print(i," b2 pressed")
                continue
            if b1pressed and not b2pressed:
                print(i," b1 pressed")
                time.sleep(2)
                return i

button1 = machine.Pin(2, machine.Pin.IN, machine.Pin.PULL_UP)
button2 = machine.Pin(3, machine.Pin.IN, machine.Pin.PULL_UP)

print("format?")
fType = multi_choice(['30-minute fit','60-minute fit','indefinite fit'])
print(fType," selected")

print("focus?")
F_FOCUS = multi_choice(['personal fit','work fit','learn fit','admin fit'])
print(F_FOCUS," selected")

fStart = time.time()

if fType == "30-minute fit":
    timer_down(1800,F_FOCUS)
elif fType == "60-minute fit":
    timer_down(3600,F_FOCUS)
elif fType == "indefinite fit":
    timer_up(F_FOCUS)
else:
    sys.exit()

fEnd = time.time()

print("sentiment?")
F_SURVEY = multi_choice(['+','=','-'])
print(F_SURVEY," selected")

fDuration = fEnd - fStart

F_HASH = uhashlib.sha256(str(fEnd).encode('utf-8')).digest()
F_HASH_SHORT = F_HASH[0:3]

fitdb = open("data.csv","a")
fitdb.write(str(F_HASH)+","+str(fType)+","+str(F_FOCUS)+","+str(F_SURVEY)+","+str(fStart)+","+str(fEnd)+","+str(fDuration)+"\n")
fitdb.close()

final_print(fDuration,F_HASH_SHORT,F_SURVEY)
print(F_HASH_SHORT," ",F_HASH)
以下是我想做的:

对于集合中的每个项目

  • 显示项目,等待按钮按下
  • 如果按下按钮1,选择该项目,返回该项目
  • 如果按下按钮2,则显示下一项,等待按钮按下
  • (迭代直到按下按钮1以选择项目)

同样,这是micropython,所以我没有您认为可用的所有模块。。。最好在原始代码中执行此操作。

0.01秒太短了。关键是,检测到“按钮按下”后,需要等待“按钮按下”。你需要像这样的东西:

def wait_for_btn_up(btn):
    count = 2
    while count > 0:
        if btn.value();
            count = 2
        else:
            count -= 1
        time.sleep(0.01)

    
def multi_choice(options):
    for i in options:
        print( "trying", i )
        # Wait for any button press.
        while 1:
            b1pressed = button1.value()
            b2pressed = button2.value()
            if b1pressed or b2pressed: 
                break
        if b1pressed:
            print( i, "chosen" )
            wait_for_btn_up(button1)
            return i
        # We know B2 was pressed.
        wait_for_btn_up(button2)

这在逻辑上确实很有帮助,但对于这个应用程序来说并不太有效,因为2040上MicroPython中的GPIO按钮需要经常读取。。。这就是为什么我需要在最后一个0.01秒刷新的原因。当然,这会打乱选择循环,这就是我一直争论的问题。你的版本在逻辑上很适合两个按钮的部分,但是现在按钮状态真的是零星读取。我做了很多嵌入式编码,你关于“需要经常阅读”的评论对我来说没有意义。现在,也许你需要实现一些去盎司逻辑;许多小型系统都没有这种内置功能。这仅仅意味着调用一个函数来等待key up稳定。我可以调整答案来做到这一点。我不怀疑你的技能,当然,逻辑是合理的,比我的混乱要好得多,但我不认为这是一个去盎司的问题。我用来收集按键的方法似乎需要进一步改进。使用你的功能,我只能按任意一个按钮(1,2)一次,然后它停止响应,我必须按另一个。。。在这一点上停止响应,我必须按下另一个按钮,一个交替的按钮输入。这很奇怪。那么,也许我不理解你的规格。如果B1和B2是独立的,瞬时的,常开按钮,那么代码应该可以工作。它们是,它只是两个樱桃MX开关,简单,独立,常开。一个在GPIO pin2(“按钮1”)上,另一个在GPIO pin3(“按钮2”)上。有了上述功能,我只能交替按下按钮1和按钮2以产生任何效果。连续按两次任一按钮都不会影响第二次(这会使实际选择的时间减少一半,并使选项滚动超过一个深度)。当电路开路时,button1.value()=“1”,当电路闭合时,button1.value()=“0”,但这几乎就像逻辑在改变后没有重新检查值一样。
def wait_for_btn_up(btn):
    count = 2
    while count > 0:
        if btn.value();
            count = 2
        else:
            count -= 1
        time.sleep(0.01)

    
def multi_choice(options):
    for i in options:
        print( "trying", i )
        # Wait for any button press.
        while 1:
            b1pressed = button1.value()
            b2pressed = button2.value()
            if b1pressed or b2pressed: 
                break
        if b1pressed:
            print( i, "chosen" )
            wait_for_btn_up(button1)
            return i
        # We know B2 was pressed.
        wait_for_btn_up(button2)