1 #include "lib9.h" 2 #include "draw.h" 3 4 enum 5 { 6 Max = 100 7 }; 8 9 Point 10 string(Image *dst, Point pt, Image *src, Point sp, Font *f, char *s) 11 { 12 return _string(dst, pt, src, sp, f, s, nil, 1<<24, dst->clipr, nil, ZP, SoverD); 13 } 14 15 Point 16 stringop(Image *dst, Point pt, Image *src, Point sp, Font *f, char *s, Drawop op) 17 { 18 return _string(dst, pt, src, sp, f, s, nil, 1<<24, dst->clipr, nil, ZP, op); 19 } 20 21 Point 22 stringn(Image *dst, Point pt, Image *src, Point sp, Font *f, char *s, int len) 23 { 24 return _string(dst, pt, src, sp, f, s, nil, len, dst->clipr, nil, ZP, SoverD); 25 } 26 27 Point 28 stringnop(Image *dst, Point pt, Image *src, Point sp, Font *f, char *s, int len, Drawop op) 29 { 30 return _string(dst, pt, src, sp, f, s, nil, len, dst->clipr, nil, ZP, op); 31 } 32 33 Point 34 runestring(Image *dst, Point pt, Image *src, Point sp, Font *f, Rune *r) 35 { 36 return _string(dst, pt, src, sp, f, nil, r, 1<<24, dst->clipr, nil, ZP, SoverD); 37 } 38 39 Point 40 runestringop(Image *dst, Point pt, Image *src, Point sp, Font *f, Rune *r, Drawop op) 41 { 42 return _string(dst, pt, src, sp, f, nil, r, 1<<24, dst->clipr, nil, ZP, op); 43 } 44 45 Point 46 runestringn(Image *dst, Point pt, Image *src, Point sp, Font *f, Rune *r, int len) 47 { 48 return _string(dst, pt, src, sp, f, nil, r, len, dst->clipr, nil, ZP, SoverD); 49 } 50 51 Point 52 runestringnop(Image *dst, Point pt, Image *src, Point sp, Font *f, Rune *r, int len, Drawop op) 53 { 54 return _string(dst, pt, src, sp, f, nil, r, len, dst->clipr, nil, ZP, op); 55 } 56 57 Point 58 _string(Image *dst, Point pt, Image *src, Point sp, Font *f, char *s, Rune *r, int len, Rectangle clipr, Image *bg, Point bgp, Drawop op) 59 { 60 int m, n, wid, max; 61 ushort cbuf[Max], *c, *ec; 62 uchar *b; 63 char *subfontname; 64 char **sptr; 65 Rune **rptr; 66 Font *def; 67 68 if(s == nil){ 69 s = ""; 70 sptr = nil; 71 }else 72 sptr = &s; 73 if(r == nil){ 74 r = (Rune*) L""; 75 rptr = nil; 76 }else 77 rptr = &r; 78 while((*s || *r) && len){ 79 max = Max; 80 if(len < max) 81 max = len; 82 n = cachechars(f, sptr, rptr, cbuf, max, &wid, &subfontname); 83 if(n > 0){ 84 _setdrawop(dst->display, op); 85 86 m = 47+2*n; 87 if(bg) 88 m += 4+2*4; 89 b = bufimage(dst->display, m); 90 if(b == 0){ 91 _drawprint(2, "string: %r\n"); 92 break; 93 } 94 if(bg) 95 b[0] = 'x'; 96 else 97 b[0] = 's'; 98 BPLONG(b+1, dst->id); 99 BPLONG(b+5, src->id); 100 BPLONG(b+9, f->cacheimage->id); 101 BPLONG(b+13, pt.x); 102 BPLONG(b+17, pt.y+f->ascent); 103 BPLONG(b+21, clipr.min.x); 104 BPLONG(b+25, clipr.min.y); 105 BPLONG(b+29, clipr.max.x); 106 BPLONG(b+33, clipr.max.y); 107 BPLONG(b+37, sp.x); 108 BPLONG(b+41, sp.y); 109 BPSHORT(b+45, n); 110 b += 47; 111 if(bg){ 112 BPLONG(b, bg->id); 113 BPLONG(b+4, bgp.x); 114 BPLONG(b+8, bgp.y); 115 b += 12; 116 } 117 ec = &cbuf[n]; 118 for(c=cbuf; c<ec; c++, b+=2) 119 BPSHORT(b, *c); 120 pt.x += wid; 121 bgp.x += wid; 122 agefont(f); 123 len -= n; 124 } 125 if(subfontname){ 126 if(_getsubfont(f->display, subfontname) == 0){ 127 def = f->display->defaultfont; 128 if(def && f!=def) 129 f = def; 130 else 131 break; 132 } 133 } 134 } 135 return pt; 136 } 137