menu.z80 4.7 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316
  1. menuMem = saveSScreen
  2. ;Now define where vars are located, 17 bytes required in all.
  3. textbox_top = menuMem
  4. textbox_left = textbox_top+1 ;needs to follow textbox_top
  5. textbox_bottom = menuMem+2
  6. textbox_width = textbox_bottom
  7. textbox_right = textbox_bottom+1 ;needs to follow textbox_bottom
  8. menucallptr = menuMem+4
  9. menutop = menuMem+6
  10. menucur = menuMem+8
  11. menuselection = menuMem+10
  12. menuheader_ptr = menuMem+12
  13. menuheader_coord= menuMem+14
  14. menuheader_cur = menuMem+16 ;1 byte
  15. menu_num_items = menuMem+17 ;2 bytes
  16. menu_get = menuMem+19
  17. menu_sel = menuMem+21
  18. menu_temp = menuMem+23
  19. menuopts = menuMem+25
  20. menudefault = TempWord1
  21. menutopinit = TempWord4
  22. #define MENU_MAX_ELEMENTS ((menuMem+768-menuopts)>>1)
  23. ;Menu:
  24. ;Get the y coordinate
  25. ld hl,(parsePtr)
  26. ld a,(hl)
  27. cp $AE
  28. jp z,fancymenu
  29. call p1_ParseFullArg
  30. push bc
  31. ;Get the x coordinate
  32. call p1_ParseNextFullArg
  33. pop hl
  34. ld h,c
  35. ;Save the coords
  36. ld (textbox_top),hl
  37. ; Get the width of the menu
  38. call p1_ParseNextFullArg
  39. ld (textbox_width),bc
  40. ;Get the header
  41. call p1_ParseNextFullArg
  42. ld (menuheader_ptr),bc
  43. ld hl,menuopts
  44. ld bc,0
  45. menu_param_loop:
  46. inc bc
  47. ld a,b
  48. cp MENU_MAX_ELEMENTS>>8
  49. jr nz,+_
  50. ld a,c
  51. cp MENU_MAX_ELEMENTS&255
  52. jp menu_err
  53. _:
  54. push bc
  55. push hl
  56. ld hl,(parsePtr)
  57. inc hl
  58. ld a,(hl)
  59. cp $AE
  60. jr z,menu_select_default
  61. call p1_ParseNextFullArg
  62. pop hl
  63. ld (hl),c
  64. inc hl
  65. ld (hl),b
  66. inc hl
  67. pop bc
  68. cp $2B
  69. jr z,menu_param_loop
  70. _:
  71. ld de,0
  72. jr +_
  73. menu_select_default:
  74. pop hl
  75. call p1_ParseNextFullArg
  76. ld h,b
  77. ld l,c
  78. dec hl
  79. pop bc
  80. dec bc
  81. ;If hl is negative, set DE to 0
  82. ld a,h
  83. add a,a
  84. jr c,-_
  85. ;set DE to min(HL,BC)
  86. ld d,b
  87. ld e,c
  88. dec de
  89. sbc hl,de
  90. jr nc,+_
  91. add hl,de
  92. ex de,hl
  93. _:
  94. ld (menudefault),de
  95. ;Save the number of elements
  96. ld (menu_num_items),bc
  97. ;Now we need to render the menu, but first we'll get the height of the menu in pixels
  98. ;4+font_height*min(9-int(y/font_height),BC+1
  99. ld a,(textbox_top)
  100. ld e,9
  101. add a,a
  102. jr c,cmp_menu_height
  103. .db $FE
  104. _:
  105. dec e
  106. sub FONT_HEIGHT*2
  107. jr nc,-_
  108. cmp_menu_height:
  109. ;E is the max height
  110. ;if BC+1 is smaller, use that
  111. inc bc
  112. inc b
  113. dec b
  114. jr nz,+_
  115. ld a,c
  116. cp e
  117. jr nc,+_
  118. ld e,c
  119. _:
  120. ;Now E is the number of items shown
  121. ;if menudefault>=E, then need to set menutopinit to menudefault-E+1
  122. ld hl,(menudefault)
  123. inc h
  124. dec h
  125. jr nz,$+6
  126. ld a,l
  127. sub e
  128. jr c,+_
  129. ld l,a
  130. jr nc,$+3
  131. inc h
  132. inc hl
  133. jr $+5
  134. _:
  135. ld hl,0
  136. ld (menutopinit),hl
  137. ;now do E*FONT_HEIGHT+4, given that it won't overflow 8 bits
  138. ld a,5
  139. ld b,FONT_HEIGHT
  140. _:
  141. add a,e
  142. djnz -_
  143. ;now set the width and height
  144. ld e,a
  145. ld a,(textbox_width)
  146. ld d,a
  147. ld ix,menu_command_lookup
  148. menu_entry:
  149. ;Set the default graphics buffer
  150. ld hl,(BufPtr)
  151. ld (gbuf_temp),hl
  152. ;save and set the the font method
  153. ld a,(textmode)
  154. push af
  155. ld a,2
  156. ld (textmode),a
  157. ld hl,(FontPointer)
  158. push hl
  159. ld hl,FontSet
  160. ld (FontPointer),hl
  161. xor a
  162. ld (font_ptr_page),a
  163. ld bc,(textbox_top)
  164. ld hl,(menuheader_ptr)
  165. call menuroutine
  166. pop hl
  167. ld (FontPointer),hl
  168. xor a
  169. ld (font_ptr_page),a
  170. pop af
  171. ld (textmode),a
  172. ret
  173. fancymenu:
  174. ;header,y,x,h,w,get,sel
  175. call p1_ParseNextFullArg
  176. ld (menuheader_ptr),bc
  177. call p1_ParseNextFullArg
  178. push bc
  179. call p1_ParseNextFullArg
  180. pop hl
  181. ld h,c
  182. ld (textbox_top),hl
  183. call p1_ParseNextFullArg
  184. push bc
  185. call p1_ParseNextFullArg
  186. pop hl
  187. ld h,c
  188. push hl ;w,h
  189. call p1_ParseNextFullArg
  190. ld (menu_get),bc
  191. call p1_ParseNextFullArg
  192. ld (menu_sel),bc
  193. ld hl,0
  194. ld (menutopinit),hl
  195. ld (menudefault),hl
  196. pop de
  197. ld ix,fancymenu_lookup
  198. jr menu_entry
  199. menu_err:
  200. ld hl,ErrStackOverflow_push
  201. ld (prev_page_call),hl
  202. jp prev_page_call
  203. fancymenu_lookup:
  204. ;save the current parsePtr
  205. ld hl,(parsePtr)
  206. push hl
  207. ;save Ans and replace with the current cursor
  208. ld hl,(Ans)
  209. push hl
  210. ;save thetaprime
  211. ld hl,(ThetaPrimeVar)
  212. push hl
  213. ;Save the text coordinates
  214. ld hl,(TextRow)
  215. push hl
  216. ;Set ThetaPrime
  217. ld l,a
  218. ld h,0
  219. ld (ThetaPrimeVar),hl
  220. ;now set the location to start parsing at
  221. ld hl,(menu_get)
  222. jr nc,+_
  223. ld hl,(menu_sel)
  224. ld bc,(menucur)
  225. _:
  226. ld (parsePtr),hl
  227. ;set Ans
  228. ld (Ans),bc
  229. ;Now parse
  230. call p1_ParserNext
  231. ;Restore text coordinates
  232. pop hl
  233. ld (TextRow),hl
  234. ;restore thetaprimevar
  235. pop hl
  236. ld (ThetaPrimeVar),hl
  237. ;restore Ans
  238. pop hl
  239. ld (Ans),hl
  240. ;restore parsePtr
  241. pop hl
  242. ld (parsePtr),hl
  243. ;return 0 if failed
  244. ld h,b
  245. ld l,c
  246. ld a,b
  247. or c
  248. ret nz
  249. scf
  250. ret
  251. menu_command_lookup:
  252. jr c,menu_command_select
  253. ;get element number BC
  254. ld hl,(menu_num_items)
  255. scf
  256. sbc hl,bc
  257. ret c
  258. ld hl,menuopts
  259. add hl,bc
  260. add hl,bc
  261. ld a,(hl)
  262. inc hl
  263. ld h,(hl)
  264. ld l,a
  265. ret
  266. menu_command_select:
  267. ld bc,(menucur)
  268. inc bc
  269. ret