Frames and keys

A tutorial step: a menu too long for one screen, and the keys a reader turns its frames with.

List the days to come

Add a page listing the next twenty-eight days, each with how far off it is in words. It is an ordinary menu_page; the new part is that its entries do not fit on one screen. Add this, and app.menu_item("ahead") to the index menu:

DAYS_AHEAD = 28


def _in_words(gap: timedelta) -> str:
    days = gap.days
    if days == 0:
        return "today"
    if days == 1:
        return "tomorrow"
    return f"in {days} days"


@router.page(
    "4", name="ahead", title="The days to come",
    detail=f"the next {DAYS_AHEAD}", keywords=("AHEAD",),
)
async def ahead(request: PageRequest) -> Page:
    app = request.app
    today = _today(request)
    days = [today + timedelta(days=offset) for offset in range(DAYS_AHEAD)]
    return menu_page(
        request,
        items=[
            MenuItem(_long_date(day), _in_words(day - today), app.address_for("day", day=day))
            for day in days
        ],
    )
frame a
 THE DAYS TO COME                     4a
  
 1  Saturday 01 August 2026             
   today                                
 2  Sunday 02 August 2026               
   tomorrow                             
 3  Monday 03 August 2026               
   in 2 days                            
 4  Tuesday 04 August 2026              
   in 3 days                            
 5  Wednesday 05 August 2026            
   in 4 days                            
 6  Thursday 06 August 2026             
   in 5 days                            
 7  Friday 07 August 2026               
   in 6 days                            
 8  Saturday 08 August 2026             
   in 7 days                            
 9  Sunday 09 August 2026               
   in 8 days                            
                                        
                                        
  
 1-9 select, S page down, 0 index       
frame b
 THE DAYS TO COME                     4b
  
 1  Monday 10 August 2026               
   in 9 days                            
 2  Tuesday 11 August 2026              
   in 10 days                           
 3  Wednesday 12 August 2026            
   in 11 days                           
 4  Thursday 13 August 2026             
   in 12 days                           
 5  Friday 14 August 2026               
   in 13 days                           
 6  Saturday 15 August 2026             
   in 14 days                           
 7  Sunday 16 August 2026               
   in 15 days                           
 8  Monday 17 August 2026               
   in 16 days                           
 9  Tuesday 18 August 2026              
   in 17 days                           
                                        
                                        
  
 1-9 select, W up, S down, 0 index      

Turn the frames

Twenty-eight days will not fit nine to a screen, so menu_page spreads them over several frames. The footer names only the keys that do something on that frame: the first offers S to page down but no W, there being nowhere up to go; the second offers both. # turns to the next frame — the key a Viewdata reader tries without being told — and 0 always returns to the index. A and D do nothing here yet; the next step wires them.

Note

Choices and moves are different keys. A choice — a menu’s digit — leads somewhere new. A move — W, S, #, 0 — pages or steps within where the reader already is. The footer keeps them apart, and a page offers only the moves it can make.