summaryrefslogtreecommitdiff
path: root/firmware/drivers/lcd-2bit-vi.c
diff options
context:
space:
mode:
Diffstat (limited to 'firmware/drivers/lcd-2bit-vi.c')
-rw-r--r--firmware/drivers/lcd-2bit-vi.c167
1 files changed, 153 insertions, 14 deletions
diff --git a/firmware/drivers/lcd-2bit-vi.c b/firmware/drivers/lcd-2bit-vi.c
index 9ce952b9e0..5edb588ce0 100644
--- a/firmware/drivers/lcd-2bit-vi.c
+++ b/firmware/drivers/lcd-2bit-vi.c
@@ -82,6 +82,28 @@ void LCDFN(set_viewport)(struct viewport* vp)
82 82
83 fg_pattern = patterns[current_vp->fg_pattern & 3]; 83 fg_pattern = patterns[current_vp->fg_pattern & 3];
84 bg_pattern = patterns[current_vp->bg_pattern & 3]; 84 bg_pattern = patterns[current_vp->bg_pattern & 3];
85
86#if defined(SIMULATOR)
87 /* Force the viewport to be within bounds. If this happens it should
88 * be considered an error - the viewport will not draw as it might be
89 * expected.
90 */
91 if((unsigned) current_vp->x > (unsigned) LCDM(WIDTH)
92 || (unsigned) current_vp->y > (unsigned) LCDM(HEIGHT)
93 || current_vp->x + current_vp->width > LCDM(WIDTH)
94 || current_vp->y + current_vp->height > LCDM(HEIGHT))
95 {
96#if !defined(HAVE_VIEWPORT_CLIP)
97 DEBUGF("ERROR: "
98#else
99 DEBUGF("NOTE: "
100#endif
101 "set_viewport out of bounds: x: %d y: %d width: %d height:%d\n",
102 current_vp->x, current_vp->y,
103 current_vp->width, current_vp->height);
104 }
105
106#endif
85} 107}
86 108
87void LCDFN(update_viewport)(void) 109void LCDFN(update_viewport)(void)
@@ -443,8 +465,13 @@ void LCDFN(clear_viewport)(void)
443/* Set a single pixel */ 465/* Set a single pixel */
444void LCDFN(drawpixel)(int x, int y) 466void LCDFN(drawpixel)(int x, int y)
445{ 467{
446 if (((unsigned)x < (unsigned)current_vp->width) && 468 if ( ((unsigned)x < (unsigned)current_vp->width)
447 ((unsigned)y < (unsigned)current_vp->height)) 469 && ((unsigned)y < (unsigned)current_vp->height)
470#if defined(HAVE_VIEWPORT_CLIP)
471 && ((unsigned)x < (unsigned)LCDM(WIDTH))
472 && ((unsigned)y < (unsigned)LCDM(HEIGHT))
473#endif
474 )
448 LCDFN(pixelfuncs)[current_vp->drawmode](current_vp->x+x, current_vp->y+y); 475 LCDFN(pixelfuncs)[current_vp->drawmode](current_vp->x+x, current_vp->y+y);
449} 476}
450 477
@@ -513,8 +540,13 @@ void LCDFN(drawline)(int x1, int y1, int x2, int y2)
513 540
514 for (i = 0; i < numpixels; i++) 541 for (i = 0; i < numpixels; i++)
515 { 542 {
516 if (((unsigned)x < (unsigned)current_vp->width) && 543 if ( ((unsigned)x < (unsigned)current_vp->width)
517 ((unsigned)y < (unsigned)current_vp->height)) 544 && ((unsigned)y < (unsigned)current_vp->height)
545#if defined(HAVE_VIEWPORT_CLIP)
546 && ((unsigned)x < (unsigned)LCDM(WIDTH))
547 && ((unsigned)y < (unsigned)LCDM(HEIGHT))
548#endif
549 )
518 pfunc(current_vp->x + x, current_vp->y + y); 550 pfunc(current_vp->x + x, current_vp->y + y);
519 551
520 if (d < 0) 552 if (d < 0)
@@ -548,24 +580,40 @@ void LCDFN(hline)(int x1, int x2, int y)
548 x1 = x2; 580 x1 = x2;
549 x2 = x; 581 x2 = x;
550 } 582 }
551 583
584 /******************** In viewport clipping **********************/
552 /* nothing to draw? */ 585 /* nothing to draw? */
553 if (((unsigned)y >= (unsigned)current_vp->height) || (x1 >= current_vp->width) 586 if (((unsigned)y >= (unsigned)current_vp->height) || (x1 >= current_vp->width)
554 || (x2 < 0)) 587 || (x2 < 0))
555 return; 588 return;
556 589
557 /* clipping */
558 if (x1 < 0) 590 if (x1 < 0)
559 x1 = 0; 591 x1 = 0;
560 if (x2 >= current_vp->width) 592 if (x2 >= current_vp->width)
561 x2 = current_vp->width-1; 593 x2 = current_vp->width-1;
562 594
563 width = x2 - x1 + 1;
564
565 /* adjust x1 and y to viewport */ 595 /* adjust x1 and y to viewport */
566 x1 += current_vp->x; 596 x1 += current_vp->x;
567 y += current_vp->y; 597 y += current_vp->y;
568 598
599#if defined(HAVE_VIEWPORT_CLIP)
600 x2 += current_vp->x;
601
602 /********************* Viewport on screen clipping ********************/
603 /* nothing to draw? */
604 if (((unsigned)y >= (unsigned) LCDM(HEIGHT)) || (x1 >= LCDM(WIDTH))
605 || (x2 < 0))
606 return;
607
608 /* clipping */
609 if (x1 < 0)
610 x1 = 0;
611 if (x2 >= LCDM(WIDTH))
612 x2 = LCDM(WIDTH)-1;
613#endif
614
615 width = x2 - x1 + 1;
616
569 bfunc = LCDFN(blockfuncs)[current_vp->drawmode]; 617 bfunc = LCDFN(blockfuncs)[current_vp->drawmode];
570 dst = &LCDFN(framebuffer)[y>>3][x1]; 618 dst = &LCDFN(framebuffer)[y>>3][x1];
571 mask = 0x0101 << (y & 7); 619 mask = 0x0101 << (y & 7);
@@ -592,12 +640,12 @@ void LCDFN(vline)(int x, int y1, int y2)
592 y2 = ny; 640 y2 = ny;
593 } 641 }
594 642
643 /******************** In viewport clipping **********************/
595 /* nothing to draw? */ 644 /* nothing to draw? */
596 if (((unsigned)x >= (unsigned)current_vp->width) || (y1 >= current_vp->height) 645 if (((unsigned)x >= (unsigned)current_vp->width) || (y1 >= current_vp->height)
597 || (y2 < 0)) 646 || (y2 < 0))
598 return; 647 return;
599 648
600 /* clipping */
601 if (y1 < 0) 649 if (y1 < 0)
602 y1 = 0; 650 y1 = 0;
603 if (y2 >= current_vp->height) 651 if (y2 >= current_vp->height)
@@ -607,6 +655,20 @@ void LCDFN(vline)(int x, int y1, int y2)
607 y1 += current_vp->y; 655 y1 += current_vp->y;
608 y2 += current_vp->y; 656 y2 += current_vp->y;
609 x += current_vp->x; 657 x += current_vp->x;
658
659#if defined(HAVE_VIEWPORT_CLIP)
660 /********************* Viewport on screen clipping ********************/
661 /* nothing to draw? */
662 if (( (unsigned) x >= (unsigned)LCDM(WIDTH)) || (y1 >= LCDM(HEIGHT))
663 || (y2 < 0))
664 return;
665
666 /* clipping */
667 if (y1 < 0)
668 y1 = 0;
669 if (y2 >= LCDM(HEIGHT))
670 y2 = LCDM(HEIGHT)-1;
671#endif
610 672
611 bfunc = LCDFN(blockfuncs)[current_vp->drawmode]; 673 bfunc = LCDFN(blockfuncs)[current_vp->drawmode];
612 dst = &LCDFN(framebuffer)[y1>>3][x]; 674 dst = &LCDFN(framebuffer)[y1>>3][x];
@@ -651,12 +713,12 @@ void LCDFN(fillrect)(int x, int y, int width, int height)
651 LCDFN(blockfunc_type) *bfunc; 713 LCDFN(blockfunc_type) *bfunc;
652 bool fillopt = false; 714 bool fillopt = false;
653 715
716 /******************** In viewport clipping **********************/
654 /* nothing to draw? */ 717 /* nothing to draw? */
655 if ((width <= 0) || (height <= 0) || (x >= current_vp->width) 718 if ((width <= 0) || (height <= 0) || (x >= current_vp->width)
656 || (y >= current_vp->height) || (x + width <= 0) || (y + height <= 0)) 719 || (y >= current_vp->height) || (x + width <= 0) || (y + height <= 0))
657 return; 720 return;
658 721
659 /* clipping */
660 if (x < 0) 722 if (x < 0)
661 { 723 {
662 width += x; 724 width += x;
@@ -675,6 +737,31 @@ void LCDFN(fillrect)(int x, int y, int width, int height)
675 /* adjust for viewport */ 737 /* adjust for viewport */
676 x += current_vp->x; 738 x += current_vp->x;
677 y += current_vp->y; 739 y += current_vp->y;
740
741#if defined(HAVE_VIEWPORT_CLIP)
742 /********************* Viewport on screen clipping ********************/
743 /* nothing to draw? */
744 if ((x >= LCDM(WIDTH)) || (y >= LCDM(HEIGHT))
745 || (x + width <= 0) || (y + height <= 0))
746 return;
747
748 /* clip image in viewport in screen */
749 if (x < 0)
750 {
751 width += x;
752 x = 0;
753 }
754 if (y < 0)
755 {
756 height += y;
757 y = 0;
758 }
759 if (x + width > LCDM(WIDTH))
760 width = LCDM(WIDTH) - x;
761 if (y + height > LCDM(HEIGHT))
762 height = LCDM(HEIGHT) - y;
763#endif
764
678 765
679 if (current_vp->drawmode & DRMODE_INVERSEVID) 766 if (current_vp->drawmode & DRMODE_INVERSEVID)
680 { 767 {
@@ -751,12 +838,12 @@ void ICODE_ATTR LCDFN(mono_bitmap_part)(const unsigned char *src, int src_x,
751 unsigned data, mask, mask_bottom; 838 unsigned data, mask, mask_bottom;
752 LCDFN(blockfunc_type) *bfunc; 839 LCDFN(blockfunc_type) *bfunc;
753 840
841 /******************** Image in viewport clipping **********************/
754 /* nothing to draw? */ 842 /* nothing to draw? */
755 if ((width <= 0) || (height <= 0) || (x >= current_vp->width) || 843 if ((width <= 0) || (height <= 0) || (x >= current_vp->width) ||
756 (y >= current_vp->height) || (x + width <= 0) || (y + height <= 0)) 844 (y >= current_vp->height) || (x + width <= 0) || (y + height <= 0))
757 return; 845 return;
758 846
759 /* clipping */
760 if (x < 0) 847 if (x < 0)
761 { 848 {
762 width += x; 849 width += x;
@@ -777,6 +864,32 @@ void ICODE_ATTR LCDFN(mono_bitmap_part)(const unsigned char *src, int src_x,
777 /* adjust for viewport */ 864 /* adjust for viewport */
778 x += current_vp->x; 865 x += current_vp->x;
779 y += current_vp->y; 866 y += current_vp->y;
867
868#if defined(HAVE_VIEWPORT_CLIP)
869 /********************* Viewport on screen clipping ********************/
870 /* nothing to draw? */
871 if ((x >= LCDM(WIDTH)) || (y >= LCDM(HEIGHT))
872 || (x + width <= 0) || (y + height <= 0))
873 return;
874
875 /* clip image in viewport in screen */
876 if (x < 0)
877 {
878 width += x;
879 src_x -= x;
880 x = 0;
881 }
882 if (y < 0)
883 {
884 height += y;
885 src_y -= y;
886 y = 0;
887 }
888 if (x + width > LCDM(WIDTH))
889 width = LCDM(WIDTH) - x;
890 if (y + height > LCDM(HEIGHT))
891 height = LCDM(HEIGHT) - y;
892#endif
780 893
781 src += stride * (src_y >> 3) + src_x; /* move starting point */ 894 src += stride * (src_y >> 3) + src_x; /* move starting point */
782 src_y &= 7; 895 src_y &= 7;
@@ -893,12 +1006,12 @@ void ICODE_ATTR LCDFN(bitmap_part)(const FBFN(data) *src, int src_x,
893 FBFN(data) *dst, *dst_end; 1006 FBFN(data) *dst, *dst_end;
894 unsigned mask, mask_bottom; 1007 unsigned mask, mask_bottom;
895 1008
1009 /******************** Image in viewport clipping **********************/
896 /* nothing to draw? */ 1010 /* nothing to draw? */
897 if ((width <= 0) || (height <= 0) || (x >= current_vp->width) 1011 if ((width <= 0) || (height <= 0) || (x >= current_vp->width)
898 || (y >= current_vp->height) || (x + width <= 0) || (y + height <= 0)) 1012 || (y >= current_vp->height) || (x + width <= 0) || (y + height <= 0))
899 return; 1013 return;
900 1014
901 /* clipping */
902 if (x < 0) 1015 if (x < 0)
903 { 1016 {
904 width += x; 1017 width += x;
@@ -920,6 +1033,32 @@ void ICODE_ATTR LCDFN(bitmap_part)(const FBFN(data) *src, int src_x,
920 x += current_vp->x; 1033 x += current_vp->x;
921 y += current_vp->y; 1034 y += current_vp->y;
922 1035
1036#if defined(HAVE_VIEWPORT_CLIP)
1037 /********************* Viewport on screen clipping ********************/
1038 /* nothing to draw? */
1039 if ((x >= LCDM(WIDTH)) || (y >= LCDM(HEIGHT))
1040 || (x + width <= 0) || (y + height <= 0))
1041 return;
1042
1043 /* clip image in viewport in screen */
1044 if (x < 0)
1045 {
1046 width += x;
1047 src_x -= x;
1048 x = 0;
1049 }
1050 if (y < 0)
1051 {
1052 height += y;
1053 src_y -= y;
1054 y = 0;
1055 }
1056 if (x + width > LCDM(WIDTH))
1057 width = LCDM(WIDTH) - x;
1058 if (y + height > LCDM(HEIGHT))
1059 height = LCDM(HEIGHT) - y;
1060#endif
1061
923 src += stride * (src_y >> 3) + src_x; /* move starting point */ 1062 src += stride * (src_y >> 3) + src_x; /* move starting point */
924 src_y &= 7; 1063 src_y &= 7;
925 y -= src_y; 1064 y -= src_y;