added exit function
[public/library.git] / librarian.py
1 #!/usr/bin/env python
2
3 import curses
4
5 stdscr=0
6
7 def menutest(s, l):
8     global stdscr
9     stdscr=s
10     curses.curs_set(0)
11     (rows,cols)=stdscr.getmaxyx()
12     w = curses.newwin(10,40,(rows-10)/2, (cols-40)/2)
13
14     menu(w, l)
15     
16     curses.curs_set(1)
17
18 # item is a list of (string, callable) tuples
19 def menu(w, items):
20     w.keypad(1)
21     highlight=0
22     redrawMenu(w,items,highlight)
23
24     w.refresh()
25     ch=w.getch()
26     while (ch!=113): # leave on q
27         if ch==curses.KEY_UP:
28             if highlight!=0:
29                 w.chgat(highlight,0, 0)
30                 highlight -= 1
31                 w.chgat(highlight,0, curses.A_REVERSE)
32         if ch==curses.KEY_DOWN:
33             if highlight!=len(items)-1:
34                 w.chgat(highlight,0, 0)
35                 highlight += 1
36                 w.chgat(highlight,0, curses.A_REVERSE)
37         if ch==114 or ch==10:
38             (s,f)=items[highlight]
39             f()
40             redrawMenu(w,items,highlight)
41         w.refresh()
42         ch = w.getch()
43
44 def redrawMenu(w,items,highlight):
45     i=0
46     for (mitem,fun) in items:
47         w.addstr(i,0, mitem)
48         i +=1
49     w.chgat(highlight, 0, curses.A_REVERSE)
50     w.refresh()
51
52 # items is a list of (label, value) pairs
53 def redrawForm(w, caption, items, buttonlabel, m):
54     (y,x)=w.getmaxyx()
55     w.border()
56     curses.curs_set(1)
57     w.addstr(1,1,caption)
58     r=3
59     for l,v in items:
60         c = m-len(l)-2
61         w.addstr(r,c,l+":")
62         w.addstr(r,m,v)
63         r+=2
64     w.addstr(r,x-len(buttonlabel)-len("<cancel>")-6, "<cancel>  <"+buttonlabel+">")
65     w.refresh()
66
67
68 #the final form for book data entry - takes caption and book info.
69 def bookForm(caption, book, buttonlabel):
70     labels = ["ISBN", "LCCN", "Title", "Subtitle", "Authors", "Edition",
71               "Publisher", "Publish Date", "Publish Year", "Publish Month", "Publish location",
72               "Pages", "Pagination", "weight"]
73     entries = []
74     m = 0
75     for l in labels:
76         m = max(len(l),m)
77         if l.lower() in book:
78             entries.append(book[l.lower()])
79         else:
80             entries.append("")
81     m+=4
82
83     w=curses.newwin(34,50,1,10)
84     (y,x)=w.getmaxyx()
85     w.keypad(1)
86     redrawForm(w,caption,zip(labels,entries),buttonlabel,m)
87     bcol = [x-len(buttonlabel)-len("<cancel>")-6, x-len(buttonlabel)-4]
88     bwidth = [8,len(buttonlabel)+2]
89     
90     highlight=0
91     b = -1
92     r=3
93     w.chgat(r,m,x-m-2,curses.A_UNDERLINE)
94     w.move(r,m+len(entries[highlight]))
95     ch = w.getch()
96     while (ch!=113):
97         if ch==curses.KEY_UP:
98             if highlight == len(labels):
99                 w.chgat(r,bcol[b],bwidth[b],curses.A_NORMAL)
100                 highlight = len(labels)-1
101                 b = -1
102                 r=3+2*highlight
103                 w.chgat(r,m,x-m-2,curses.A_UNDERLINE)
104                 w.move(r,m+len(entries[highlight]))
105                 curses.curs_set(1)
106             elif highlight!=0:
107                 w.chgat(r,m,x-m-2,curses.A_NORMAL)
108                 highlight -= 1
109                 r=3+2*highlight
110                 w.chgat(r,m,x-m-2,curses.A_UNDERLINE)
111                 w.move(r,m+len(entries[highlight]))
112         if ch==curses.KEY_DOWN:
113             if highlight >= len(labels) -1:
114                 highlight = len(labels)
115                 b += 1
116                 b = min(b,1)
117                 curses.curs_set(0)
118                 w.chgat(r,m,x-m-2,curses.A_NORMAL)
119                 r = y-3
120                 w.chgat(r,bcol[b],bwidth[b],curses.A_REVERSE)
121             else:
122                 w.chgat(r,m,x-m-2,curses.A_NORMAL)
123                 highlight += 1
124                 r=3+2*highlight
125                 w.chgat(r,m,x-m-2,curses.A_UNDERLINE)
126                 w.move(r,m+len(entries[highlight]))
127         if ch==10:
128             if b != -1:
129                 if b == 0:
130                     w.clear()
131                     w.refresh()
132                     return {}
133                 elif b == 1:
134                     w.clear()
135                     w.refresh()
136                     return {"title": "I was 'added'"}
137             elif highlight == len(labels)-1:
138                 highlight = len(labels)
139                 b=0
140                 curses.curs_set(0)
141                 w.chgat(r,m,x-m-2,curses.A_NORMAL)
142                 r = y-3
143                 w.chgat(r,bcol[b],bwidth[b],curses.A_REVERSE)
144             else:
145                 w.chgat(r,m,x-m-2,curses.A_NORMAL)
146                 highlight += 1
147                 r=3+2*highlight
148                 w.chgat(r,m,x-m-2,curses.A_UNDERLINE)
149                 w.move(r,m+len(entries[highlight]))
150
151
152         w.refresh()
153         ch = w.getch()
154
155     curses.curs_set(0)
156     w.clear()
157     w.refresh()
158     return {"title":"this is what I returned"}
159
160
161 def addForm():
162     book = {"title":"A Book of Tests", "pages":"123"}
163     book = bookForm("Add a book", book, "add")
164     stdscr.getch()
165     bookForm("View the book", book, "done")
166
167
168 def updateMenu():
169     w=curses.newwin(1,50,10,10)
170     w.addstr("I will be used to update or modify book records")
171     w.refresh()
172
173 def deleteMenu():
174     w=curses.newwin(1,50,10,10)
175     w.addstr("I will be used to delete book records")
176     w.refresh()
177
178 def browseMenu():
179     w=curses.newwin(1,50,10,10)
180     w.addstr("I will be used to browse book records")
181     w.refresh()
182
183 m = [("Browse Library", browseMenu),
184      ("Add Book or other item", addForm),
185      ("Modify/Update record", updateMenu),
186      ("Remove book from catalogue", deleteMenu),
187      ("Exit", exit)]
188 curses.wrapper(menutest, m)