https://github.com/akkartik/mu/blob/main/apps/browse/paginated-screen.mu
1
2
3
4
5
6
7
8
9
10
11
12 type paginated-screen {
13 screen: (handle screen)
14 nrows: int
15 ncols: int
16 page-width: int
17 top-margin: int
18 left-margin: int
19
20 toprow: int
21 botrow: int
22 leftcol: int
23 rightcol: int
24
25 row: int
26 col: int
27 }
28
29 fn initialize-paginated-screen _self: (addr paginated-screen), page-width: int, top-margin: int, left-margin: int {
30 var self/esi: (addr paginated-screen) <- copy _self
31 var screen-ah/eax: (addr handle screen) <- get self, screen
32 var _screen-addr/eax: (addr screen) <- lookup *screen-ah
33 var screen-addr/edi: (addr screen) <- copy _screen-addr
34 var nrows/eax: int <- copy 0
35 var ncols/ecx: int <- copy 0
36 nrows, ncols <- screen-size screen-addr
37 var dest/edx: (addr int) <- copy 0
38
39 dest <- get self, nrows
40 copy-to *dest, nrows
41
42 dest <- get self, ncols
43 copy-to *dest, ncols
44
45 {
46 var tmp/eax: int <- copy page-width
47 dest <- get self, page-width
48 copy-to *dest, tmp
49 }
50
51 {
52 var tmp/eax: int <- copy top-margin
53 dest <- get self, top-margin
54 copy-to *dest, tmp
55 }
56
57 {
58 var tmp/eax: int <- copy left-margin
59 dest <- get self, left-margin
60 copy-to *dest, tmp
61 }
62
63 {
64 var tmp/eax: int <- copy top-margin
65 dest <- get self, toprow
66 copy-to *dest, 1
67 add-to *dest, tmp
68 }
69
70 {
71 dest <- get self, botrow
72 copy-to *dest, nrows
73 }
74
75 start-drawing self
76 }
77
78 fn start-drawing _self: (addr paginated-screen) {
79 var self/esi: (addr paginated-screen) <- copy _self
80 clear-paginated-screen self
81 var tmp/eax: (addr int) <- copy 0
82 var tmp2/ecx: int <- copy 0
83
84 tmp <- get self, left-margin
85 tmp2 <- copy *tmp
86 tmp <- get self, leftcol
87 copy-to *tmp, 1
88 add-to *tmp, tmp2
89
90
91
92
93 tmp <- get self, page-width
94 tmp2 <- copy *tmp
95 tmp <- get self, leftcol
96 tmp2 <- add *tmp
97
98 {
99 tmp <- get self, ncols
100 compare tmp2, *tmp
101 break-if-<=
102 tmp2 <- copy *tmp
103 tmp2 <- increment
104 }
105
106 tmp <- get self, rightcol
107 copy-to *tmp, tmp2
108
109
110
111
112 tmp <- get self, toprow
113 tmp2 <- copy *tmp
114 tmp <- get self, row
115 copy-to *tmp, tmp2
116
117 tmp <- get self, leftcol
118 tmp2 <- copy *tmp
119 tmp <- get self, col
120 copy-to *tmp, tmp2
121
122 reposition-cursor self
123 }
124
125 fn done-drawing? _self: (addr paginated-screen) -> _/eax: boolean {
126
127 var self/esi: (addr paginated-screen) <- copy _self
128 var tmp/eax: (addr int) <- get self, left-margin
129 var first-col/ecx: int <- copy *tmp
130 first-col <- increment
131 tmp <- get self, leftcol
132 $done-drawing:first-page?: {
133 compare first-col, *tmp
134 break-if-!=
135 return 0
136 }
137
138 tmp <- get self, ncols
139 var max/ecx: int <- copy *tmp
140 max <- increment
141 tmp <- get self, rightcol
142
143
144
145
146
147 compare *tmp, max
148 {
149 break-if->
150 return 0
151 }
152 return 1
153 }
154
155 fn add-grapheme _self: (addr paginated-screen), c: grapheme {
156
157
158
159 $add-grapheme:body: {
160 var self/esi: (addr paginated-screen) <- copy _self
161 {
162 compare c, 0xa
163 break-if-!=
164 next-line self
165 reposition-cursor self
166 break $add-grapheme:body
167 }
168
169 var screen-ah/eax: (addr handle screen) <- get self, screen
170 var screen-addr/eax: (addr screen) <- lookup *screen-ah
171 print-grapheme screen-addr, c
172
173 var tmp/eax: (addr int) <- get self, col
174 increment *tmp
175
176 var tmp2/ecx: int <- copy *tmp
177 tmp <- get self, rightcol
178 compare tmp2, *tmp
179 {
180 break-if-<
181 next-line self
182 reposition-cursor self
183 }
184 }
185 }
186
187
188
189 fn test-print-grapheme-on-paginated-screen {
190 var pg-on-stack: paginated-screen
191 var pg/eax: (addr paginated-screen) <- address pg-on-stack
192 initialize-fake-paginated-screen pg, 3, 0xa, 0xa, 0, 0
193 start-drawing pg
194 {
195 var c/ecx: grapheme <- copy 0x61
196 add-grapheme pg, c
197 var done?/eax: boolean <- done-drawing? pg
198 var done/eax: int <- copy done?
199 check-ints-equal done, 0, "F - test-print-grapheme-on-paginated-screen/done"
200 }
201 var screen-ah/eax: (addr handle screen) <- get pg, screen
202 var screen-addr/eax: (addr screen) <- lookup *screen-ah
203 check-screen-row screen-addr, 1, "a", "F - test-print-grapheme-on-paginated-screen"
204 }
205
206 fn test-print-single-page {
207 var pg-on-stack: paginated-screen
208 var pg/eax: (addr paginated-screen) <- address pg-on-stack
209 initialize-fake-paginated-screen pg, 2, 4, 2, 0, 0
210 start-drawing pg
211
212 {
213 var c/ecx: grapheme <- copy 0x61
214 add-grapheme pg, c
215 var done?/eax: boolean <- done-drawing? pg
216 var done/eax: int <- copy done?
217 check-ints-equal done, 0, "F - test-print-single-page/done-1"
218 }
219 {
220 var c/ecx: grapheme <- copy 0x62
221 add-grapheme pg, c
222 var done?/eax: boolean <- done-drawing? pg
223 var done/eax: int <- copy done?
224 check-ints-equal done, 0, "F - test-print-single-page/done-2"
225 }
226 {
227 var c/ecx: grapheme <- copy 0x63
228 add-grapheme pg, c
229 var done?/eax: boolean <- done-drawing? pg
230 var done/eax: int <- copy done?
231 check-ints-equal done, 0, "F - test-print-single-page/done-3"
232 }
233 {
234 var c/ecx: grapheme <- copy 0x64
235 add-grapheme pg, c
236 var done?/eax: boolean <- done-drawing? pg
237 var done/eax: int <- copy done?
238 check-ints-equal done, 0, "F - test-print-single-page/done-4"
239 }
240 var screen-ah/eax: (addr handle screen) <- get pg, screen
241 var screen-addr/eax: (addr screen) <- lookup *screen-ah
242 check-screen-row screen-addr, 1, "ab ", "F - test-print-single-page/row1"
243 check-screen-row screen-addr, 2, "cd ", "F - test-print-single-page/row2"
244
245 }
246
247 fn test-print-single-page-narrower-than-page-width {
248 var pg-on-stack: paginated-screen
249 var pg/eax: (addr paginated-screen) <- address pg-on-stack
250 initialize-fake-paginated-screen pg, 2, 4, 5, 0, 0
251 start-drawing pg
252 {
253 var c/ecx: grapheme <- copy 0x61
254 add-grapheme pg, c
255 var done?/eax: boolean <- done-drawing? pg
256 var done/eax: int <- copy done?
257 check-ints-equal done, 0, "F - test-print-single-page-narrower-than-page-width/done-1"
258 }
259 {
260 var c/ecx: grapheme <- copy 0x62
261 add-grapheme pg, c
262 var done?/eax: boolean <- done-drawing? pg
263 var done/eax: int <- copy done?
264 check-ints-equal done, 0, "F - test-print-single-page-narrower-than-page-width/done-2"
265 }
266 {
267 var c/ecx: grapheme <- copy 0x63
268 add-grapheme pg, c
269 var done?/eax: boolean <- done-drawing? pg
270 var done/eax: int <- copy done?
271 check-ints-equal done, 0, "F - test-print-single-page-narrower-than-page-width/done-3"
272 }
273 {
274 var c/ecx: grapheme <- copy 0x64
275 add-grapheme pg, c
276 var done?/eax: boolean <- done-drawing? pg
277 var done/eax: int <- copy done?
278 check-ints-equal done, 0, "F - test-print-single-page-narrower-than-page-width/done-4"
279 }
280 {
281 var c/ecx: grapheme <- copy 0x65
282 add-grapheme pg, c
283 var done?/eax: boolean <- done-drawing? pg
284 var done/eax: int <- copy done?
285 check-ints-equal done, 0, "F - test-print-single-page-narrower-than-page-width/done-5"
286 }
287 var screen-ah/eax: (addr handle screen) <- get pg, screen
288 var screen-addr/eax: (addr screen) <- lookup *screen-ah
289 check-screen-row screen-addr, 1, "abcd", "F - test-print-single-page-narrower-than-page-width/row1"
290 check-screen-row screen-addr, 2, "e ", "F - test-print-single-page-narrower-than-page-width/row2"
291
292 }
293
294 fn test-print-single-page-narrower-than-page-width-with-margin {
295 var pg-on-stack: paginated-screen
296 var pg/eax: (addr paginated-screen) <- address pg-on-stack
297 initialize-fake-paginated-screen pg, 2, 4, 5, 0, 1
298 start-drawing pg
299 {
300 var c/ecx: grapheme <- copy 0x61
301 add-grapheme pg, c
302 var done?/eax: boolean <- done-drawing? pg
303 var done/eax: int <- copy done?
304 check-ints-equal done, 0, "F - test-print-single-page-narrower-than-page-width-with-margin/done-1"
305 }
306 {
307 var c/ecx: grapheme <- copy 0x62
308 add-grapheme pg, c
309 var done?/eax: boolean <- done-drawing? pg
310 var done/eax: int <- copy done?
311 check-ints-equal done, 0, "F - test-print-single-page-narrower-than-page-width-with-margin/done-2"
312 }
313 {
314 var c/ecx: grapheme <- copy 0x63
315 add-grapheme pg, c
316 var done?/eax: boolean <- done-drawing? pg
317 var done/eax: int <- copy done?
318 check-ints-equal done, 0, "F - test-print-single-page-narrower-than-page-width-with-margin/done-3"
319 }
320 {
321 var c/ecx: grapheme <- copy 0x64
322 add-grapheme pg, c
323 var done?/eax: boolean <- done-drawing? pg
324 var done/eax: int <- copy done?
325 check-ints-equal done, 0, "F - test-print-single-page-narrower-than-page-width-with-margin/done-4"
326 }
327 {
328 var c/ecx: grapheme <- copy 0x65
329 add-grapheme pg, c
330 var done?/eax: boolean <- done-drawing? pg
331 var done/eax: int <- copy done?
332 check-ints-equal done, 0, "F - test-print-single-page-narrower-than-page-width-with-margin/done-5"
333 }
334 var screen-ah/eax: (addr handle screen) <- get pg, screen
335 var screen-addr/eax: (addr screen) <- lookup *screen-ah
336 check-screen-row screen-addr, 1, " abc", "F - test-print-single-page-narrower-than-page-width-with-margin/row1"
337 check-screen-row screen-addr, 2, " de ", "F - test-print-single-page-narrower-than-page-width-with-margin/row2"
338
339 }
340
341 fn test-print-multiple-pages {
342 var pg-on-stack: paginated-screen
343 var pg/eax: (addr paginated-screen) <- address pg-on-stack
344 initialize-fake-paginated-screen pg, 2, 2, 1, 0, 0
345 start-drawing pg
346 {
347 var c/ecx: grapheme <- copy 0x61
348 add-grapheme pg, c
349 var done?/eax: boolean <- done-drawing? pg
350 var done/eax: int <- copy done?
351 check-ints-equal done, 0, "F - test-print-multiple-pages/done-1"
352 }
353 {
354 var c/ecx: grapheme <- copy 0x62
355 add-grapheme pg, c
356 var done?/eax: boolean <- done-drawing? pg
357 var done/eax: int <- copy done?
358 check-ints-equal done, 0, "F - test-print-multiple-pages/done-2"
359 }
360 {
361 var c/ecx: grapheme <- copy 0x63
362 add-grapheme pg, c
363 var done?/eax: boolean <- done-drawing? pg
364 var done/eax: int <- copy done?
365 check-ints-equal done, 0, "F - test-print-multiple-pages/done-3"
366 }
367 {
368 var c/ecx: grapheme <- copy 0x64
369 add-grapheme pg, c
370 var done?/eax: boolean <- done-drawing? pg
371 var done/eax: int <- copy done?
372 check-ints-equal done, 1, "F - test-print-multiple-pages/done-4"
373 }
374 var screen-ah/eax: (addr handle screen) <- get pg, screen
375 var screen-addr/eax: (addr screen) <- lookup *screen-ah
376 check-screen-row screen-addr, 1, "ac", "F - test-print-multiple-pages/row1"
377 check-screen-row screen-addr, 2, "bd", "F - test-print-multiple-pages/row2"
378
379 }
380
381 fn test-print-multiple-pages-2 {
382 var pg-on-stack: paginated-screen
383 var pg/eax: (addr paginated-screen) <- address pg-on-stack
384 initialize-fake-paginated-screen pg, 2, 4, 2, 0, 0
385 start-drawing pg
386 {
387 var c/ecx: grapheme <- copy 0x61
388 add-grapheme pg, c
389 var done?/eax: boolean <- done-drawing? pg
390 var done/eax: int <- copy done?
391 check-ints-equal done, 0, "F - test-print-multiple-pages-2/done-1"
392 }
393 {
394 var c/ecx: grapheme <- copy 0x62
395 add-grapheme pg, c
396 var done?/eax: boolean <- done-drawing? pg
397 var done/eax: int <- copy done?
398 check-ints-equal done, 0, "F - test-print-multiple-pages-2/done-2"
399 }
400 {
401 var c/ecx: grapheme <- copy 0x63
402 add-grapheme pg, c
403 var done?/eax: boolean <- done-drawing? pg
404 var done/eax: int <- copy done?
405 check-ints-equal done, 0, "F - test-print-multiple-pages-2/done-3"
406 }
407 {
408 var c/ecx: grapheme <- copy 0x64
409 add-grapheme pg, c
410 var done?/eax: boolean <- done-drawing? pg
411 var done/eax: int <- copy done?
412 check-ints-equal done, 0, "F - test-print-multiple-pages-2/done-4"
413 }
414 {
415 var c/ecx: grapheme <- copy 0x65
416 add-grapheme pg, c
417 var done?/eax: boolean <- done-drawing? pg
418 var done/eax: int <- copy done?
419 check-ints-equal done, 0, "F - test-print-multiple-pages-2/done-5"
420 }
421 {
422 var c/ecx: grapheme <- copy 0x66
423 add-grapheme pg, c
424 var done?/eax: boolean <- done-drawing? pg
425 var done/eax: int <- copy done?
426 check-ints-equal done, 0, "F - test-print-multiple-pages-2/done-6"
427 }
428 {
429 var c/ecx: grapheme <- copy 0x67
430 add-grapheme pg, c
431 var done?/eax: boolean <- done-drawing? pg
432 var done/eax: int <- copy done?
433 check-ints-equal done, 0, "F - test-print-multiple-pages-2/done-7"
434 }
435 {
436 var c/ecx: grapheme <- copy 0x68
437 add-grapheme pg, c
438 var done?/eax: boolean <- done-drawing? pg
439 var done/eax: int <- copy done?
440 check-ints-equal done, 1, "F - test-print-multiple-pages-2/done-8"
441 }
442 var screen-ah/eax: (addr handle screen) <- get pg, screen
443 var screen-addr/eax: (addr screen) <- lookup *screen-ah
444 check-screen-row screen-addr, 1, "abef", "F - test-print-multiple-pages-2/row1"
445 check-screen-row screen-addr, 2, "cdgh", "F - test-print-multiple-pages-2/row2"
446
447 }
448
449 fn test-print-multiple-pages-with-margins {
450 var pg-on-stack: paginated-screen
451 var pg/eax: (addr paginated-screen) <- address pg-on-stack
452 initialize-fake-paginated-screen pg, 3, 6, 2, 1, 1
453 start-drawing pg
454 {
455 var c/ecx: grapheme <- copy 0x61
456 add-grapheme pg, c
457 var done?/eax: boolean <- done-drawing? pg
458 var done/eax: int <- copy done?
459 check-ints-equal done, 0, "F - test-print-multiple-pages-with-margins/grapheme-1"
460 }
461 {
462 var c/ecx: grapheme <- copy 0x62
463 add-grapheme pg, c
464 var done?/eax: boolean <- done-drawing? pg
465 var done/eax: int <- copy done?
466 check-ints-equal done, 0, "F - test-print-multiple-pages-with-margins/grapheme-2"
467 }
468 {
469 var c/ecx: grapheme <- copy 0x63
470 add-grapheme pg, c
471 var done?/eax: boolean <- done-drawing? pg
472 var done/eax: int <- copy done?
473 check-ints-equal done, 0, "F - test-print-multiple-pages-with-margins/grapheme-3"
474 }
475 {
476 var c/ecx: grapheme <- copy 0x64
477 add-grapheme pg, c
478 var done?/eax: boolean <- done-drawing? pg
479 var done/eax: int <- copy done?
480 check-ints-equal done, 0, "F - test-print-multiple-pages-with-margins/grapheme-4"
481 }
482 {
483 var c/ecx: grapheme <- copy 0x65
484 add-grapheme pg, c
485 var done?/eax: boolean <- done-drawing? pg
486 var done/eax: int <- copy done?
487 check-ints-equal done, 0, "F - test-print-multiple-pages-with-margins/grapheme-5"
488 }
489 {
490 var c/ecx: grapheme <- copy 0x66
491 add-grapheme pg, c
492 var done?/eax: boolean <- done-drawing? pg
493 var done/eax: int <- copy done?
494 check-ints-equal done, 0, "F - test-print-multiple-pages-with-margins/grapheme-6"
495 }
496 {
497 var c/ecx: grapheme <- copy 0x67
498 add-grapheme pg, c
499 var done?/eax: boolean <- done-drawing? pg
500 var done/eax: int <- copy done?
501 check-ints-equal done, 0, "F - test-print-multiple-pages-with-margins/grapheme-7"
502 }
503 {
504 var c/ecx: grapheme <- copy 0x68
505 add-grapheme pg, c
506 var done?/eax: boolean <- done-drawing? pg
507 var done/eax: int <- copy done?
508 check-ints-equal done, 1, "F - test-print-multiple-pages-with-margins/grapheme-8"
509 }
510 var screen-ah/eax: (addr handle screen) <- get pg, screen
511 var screen-addr/eax: (addr screen) <- lookup *screen-ah
512 check-screen-row screen-addr, 1, " ", "F - test-print-multiple-pages-with-margins/row1"
513 check-screen-row screen-addr, 2, " ab ef", "F - test-print-multiple-pages-with-margins/row2"
514 check-screen-row screen-addr, 3, " cd gh", "F - test-print-multiple-pages-with-margins/row3"
515
516 }
517
518 fn initialize-fake-paginated-screen _self: (addr paginated-screen), nrows: int, ncols: int, page-width: int, top-margin: int, left-margin: int {
519 var self/esi: (addr paginated-screen) <- copy _self
520 var screen-ah/eax: (addr handle screen) <- get self, screen
521 allocate screen-ah
522 var screen-addr/eax: (addr screen) <- lookup *screen-ah
523 initialize-screen screen-addr, nrows, ncols
524 initialize-paginated-screen self, page-width, top-margin, left-margin
525 }
526
527
528
529 fn reposition-cursor _self: (addr paginated-screen) {
530 var self/esi: (addr paginated-screen) <- copy _self
531 var r/ecx: (addr int) <- get self, row
532 var c/edx: (addr int) <- get self, col
533
534
535
536
537
538 var screen-ah/eax: (addr handle screen) <- get self, screen
539 var screen-addr/eax: (addr screen) <- lookup *screen-ah
540 move-cursor screen-addr, *r *c
541 }
542
543 fn clear-paginated-screen _self: (addr paginated-screen) {
544 var self/esi: (addr paginated-screen) <- copy _self
545 var screen-ah/eax: (addr handle screen) <- get self, screen
546 var screen-addr/eax: (addr screen) <- lookup *screen-ah
547 clear-screen screen-addr
548 }
549
550 fn start-color-on-paginated-screen _self: (addr paginated-screen), fg: int, bg: int {
551 var self/esi: (addr paginated-screen) <- copy _self
552 var screen-ah/eax: (addr handle screen) <- get self, screen
553 var screen-addr/eax: (addr screen) <- lookup *screen-ah
554 start-color screen-addr, fg, bg
555 }
556
557 fn start-bold-on-paginated-screen _self: (addr paginated-screen) {
558 var self/esi: (addr paginated-screen) <- copy _self
559 var screen-ah/eax: (addr handle screen) <- get self, screen
560 var screen-addr/eax: (addr screen) <- lookup *screen-ah
561 start-bold screen-addr
562 }
563
564 fn start-underline-on-paginated-screen _self: (addr paginated-screen) {
565 var self/esi: (addr paginated-screen) <- copy _self
566 var screen-ah/eax: (addr handle screen) <- get self, screen
567 var screen-addr/eax: (addr screen) <- lookup *screen-ah
568 start-underline screen-addr
569 }
570
571 fn start-reverse-video-on-paginated-screen _self: (addr paginated-screen) {
572 var self/esi: (addr paginated-screen) <- copy _self
573 var screen-ah/eax: (addr handle screen) <- get self, screen
574 var screen-addr/eax: (addr screen) <- lookup *screen-ah
575 start-reverse-video screen-addr
576 }
577
578 fn start-blinking-on-paginated-screen _self: (addr paginated-screen) {
579 var self/esi: (addr paginated-screen) <- copy _self
580 var screen-ah/eax: (addr handle screen) <- get self, screen
581 var screen-addr/eax: (addr screen) <- lookup *screen-ah
582 start-blinking screen-addr
583 }
584
585 fn reset-formatting-on-paginated-screen _self: (addr paginated-screen) {
586 var self/esi: (addr paginated-screen) <- copy _self
587 var screen-ah/eax: (addr handle screen) <- get self, screen
588 var screen-addr/eax: (addr screen) <- lookup *screen-ah
589 reset-formatting screen-addr
590 }
591
592
593
594 fn next-line _self: (addr paginated-screen) {
595
596 var self/esi: (addr paginated-screen) <- copy _self
597 var tmp/eax: (addr int) <- copy 0
598 var tmp2/ecx: int <- copy 0
599
600 tmp <- get self, leftcol
601 tmp2 <- copy *tmp
602 tmp <- get self, col
603 copy-to *tmp, tmp2
604
605 tmp <- get self, row
606 increment *tmp
607
608
609
610
611 tmp2 <- copy *tmp
612 tmp <- get self, botrow
613 compare tmp2, *tmp
614 {
615 break-if-<=
616 next-page self
617 }
618 }
619
620 fn next-page _self: (addr paginated-screen) {
621
622 var self/esi: (addr paginated-screen) <- copy _self
623 var tmp/eax: (addr int) <- copy 0
624 var tmp2/ecx: int <- copy 0
625
626
627
628
629
630
631
632 tmp <- get self, rightcol
633 tmp2 <- copy *tmp
634 tmp <- get self, left-margin
635 tmp2 <- add *tmp
636 tmp <- get self, leftcol
637 copy-to *tmp, tmp2
638
639
640
641
642 tmp <- get self, page-width
643 tmp2 <- copy *tmp
644 tmp <- get self, leftcol
645 tmp2 <- add *tmp
646 tmp <- get self, rightcol
647 copy-to *tmp, tmp2
648
649
650
651
652 tmp <- get self, toprow
653 tmp2 <- copy *tmp
654 tmp <- get self, row
655 copy-to *tmp, tmp2
656
657 tmp <- get self, leftcol
658 tmp2 <- copy *tmp
659 tmp <- get self, col
660 copy-to *tmp, tmp2
661 }