FireBirdLib - Topfield TMS PVR TAP Programming Library
FM_PutStringAA.c
Go to the documentation of this file.
1#include <string.h>
2#include "FBLib_FontManager.h"
3
4void FM_PutStringAA(word rgn, dword x, dword y, dword maxX, char *str, dword fcolor, dword bcolor, tFontData *FontData, byte bDot, byte align, float AntiAliasFactor)
5{
7
8 int XEnd, YEnd;
9 dword *PixelData;
10 byte *FontBitmap;
11 dword i, X, Y;
12 dword CX, CY, CW, CH;
13 dword SaveBoxX;
14 dword dotWidth;
15 char newstr[256];
16 int width = 0, newstrlen;
17 int CharIndex;
18
19 dword LastBackgroundPixel = 0;
20 byte LastForegroundPixel = 0;
21 dword LastPixel = 0;
22 byte Grey = 0;
23 dword repcnt;
24 bool compressed_font;
25 dword StrLen;
26
27 if(!str || !str[0] || !FontData || !FontData->pFontData || (maxX <= x))
28 {
29 TRACEEXIT();
30 return;
31 }
32
33 if(GetOSDRegionWidth(rgn) && GetOSDRegionWidth(rgn) <= maxX) maxX = GetOSDRegionWidth(rgn) - 1;
34
35 strncpy(newstr, str, sizeof(newstr));
36 newstr[sizeof(newstr) - 1] = '\0';
37
38 XEnd = x + FM_GetStringWidth(newstr, FontData) - 1;
39 dotWidth = 0;
40
41 switch(bDot)
42 {
43 case 0:
44 {
45 char *p;
46
47 p = &newstr[strlen(newstr) - 1];
48 if(XEnd > (int)maxX)
49 {
50 newstrlen = strlen(newstr);
51 do
52 {
54 {
55 width = FontData->FontDef[FM_CharToIndex(*p)].Width;
56 XEnd -= width;
57 }
58 *p = '\0';
59 p--;
60 newstrlen--;
61 } while((XEnd > (int)maxX) && (width != 0) && (newstrlen > 0));
62 }
63 break;
64 }
65
66 case 1:
67 {
68 char *p;
69
70 p = &newstr[strlen(newstr) - 1];
71 if(XEnd > (int)maxX)
72 {
73 dotWidth = FM_GetStringWidth("...", FontData);
74 XEnd += dotWidth;
75 newstrlen = strlen(newstr);
76 do
77 {
79 {
80 width = FontData->FontDef[FM_CharToIndex(*p)].Width;
81 XEnd -= width;
82 }
83 *p = '\0';
84 p--;
85 newstrlen--;
86 } while((XEnd > (int)maxX) && (width != 0) && (newstrlen > 0));
87 strcat(newstr, "...");
88 }
89 break;
90 }
91
92 case 2:
93 {
94 char *p;
95
96 p = newstr;
97 if(XEnd > (int)maxX)
98 {
99 dotWidth = FM_GetStringWidth("...", FontData);
100 XEnd += dotWidth;
101 newstrlen = strlen(newstr);
102 do
103 {
104 if(FM_isValidCharacter(*p))
105 {
106 width = FontData->FontDef[FM_CharToIndex(*p)].Width;
107 XEnd -= width;
108 }
109 p++;
110 newstrlen--;
111 } while((XEnd > (int)maxX) && (width != 0) && (newstrlen > 0));
112 DeleteAt(newstr, 0, (int)(p - newstr));
113 InsertAt(newstr, 0, "...");
114 }
115
116 break;
117 }
118 }
119
120 if(XEnd > (int)maxX)
121 {
122 TRACEEXIT();
123 return;
124 }
125
126 YEnd = y + FM_GetStringHeight(newstr, FontData) - 1;
127
128 switch(align)
129 {
130 case ALIGN_LEFT:
131 {
132 SaveBoxX = x;
133 break;
134 }
135
136 case ALIGN_CENTER:
137 {
138 SaveBoxX = x + ((maxX - XEnd) >> 1);
139 break;
140 }
141
142 case ALIGN_RIGHT:
143 {
144 SaveBoxX = maxX - (XEnd - x);
145 break;
146 }
147
148 default:
149 SaveBoxX = x;
150 break;
151 }
152
153 if(bcolor & 0xff000000)
154 {
155 TAP_Osd_FillBox(rgn, x, y, maxX - x + 1, YEnd - y + 1, bcolor);
156 FM_InitAlphaLUT(fcolor, bcolor, AntiAliasFactor);
157 }
158
159 PixelData = (dword*) TAP_Osd_SaveBox(rgn, SaveBoxX, y, XEnd - x + 1, YEnd - y + 1);
160 if(PixelData)
161 {
162 CX = 0;
163 StrLen = strlen(newstr);
164 for(i = 0; i < StrLen; i++)
165 {
166 if(FM_isValidCharacter(newstr[i]))
167 {
168 CharIndex = FM_CharToIndex(newstr[i]);
169 FontBitmap = &FontData->pFontData[CharIndex == 0 ? 0 : FontData->FontDef[CharIndex].BitmapIndex];
170 CW = FontData->FontDef[CharIndex].Width;
171 CH = FontData->FontDef[CharIndex].Height;
172 compressed_font = FontData->FontDef[0].BitmapIndex != 0;
173
174 repcnt = 0;
175 for(Y = 0; Y < CH; Y++)
176 {
177 CY = (XEnd - x + 1) * Y;
178 for(X = 0; X < CW; X++)
179 {
180 if(repcnt == 0)
181 {
182 Grey = *FontBitmap++;
183
184 /* Compressed fonts have repeat counts after every 0x00
185 * and 0xff bytes */
186 if(compressed_font && (Grey == 0x00 || Grey == 0xff))
187 repcnt = *FontBitmap++ - 1;
188 }
189 else
190 --repcnt;
191
192 if(Grey != 0x00)
193 {
194 if(Grey == 0xff)
195 {
196 PixelData[CX + X + CY] = fcolor;
197 }
198 else
199 {
200 //Verhalten von bcolor.A
201 if(bcolor & 0xff000000)
202 {
203 PixelData[CX + X + CY] = (fcolor & 0xff000000) | (AlphaLUT[Grey].r << 16) | (AlphaLUT[Grey].g << 8) | AlphaLUT[Grey].b;
204 }
205 else
206 {
207 if((LastForegroundPixel != Grey) || (LastBackgroundPixel != PixelData[CX + X + CY]))
208 {
209 LastBackgroundPixel = PixelData[CX + X + CY];
210 LastForegroundPixel = Grey;
211 LastPixel = (fcolor & 0xff000000) | FM_AlphaBlendRGB(Grey, fcolor, LastBackgroundPixel, AntiAliasFactor);
212 }
213
214 PixelData[CX + X + CY] = LastPixel;
215 }
216 }
217 } // if grey else
218 } // for x
219 } // for y
220 CX += CW;
221 } // if FM_ValidChar
222 } // for i
223
224 TAP_Osd_RestoreBox(rgn, SaveBoxX, y, XEnd - x + 1, YEnd - y + 1, PixelData);
225 TAP_MemFree(PixelData);
226 } // if PixelData
227
228 TRACEEXIT();
229}
byte FM_CharToIndex(byte Char)
Definition: FM_CharToIndex.c:3
bool FM_isValidCharacter(byte Char)
tAlphaLUT AlphaLUT[256]
void FM_InitAlphaLUT(dword fgColor, dword bgColor, float AntiAliasFactor)
dword FM_AlphaBlendRGB(byte Alpha, dword FG, dword BG, float AntiAliasFactor)
dword FM_GetStringHeight(char *Text, tFontData *FontData)
dword FM_GetStringWidth(char *Text, tFontData *FontData)
void FM_PutStringAA(word rgn, dword x, dword y, dword maxX, char *str, dword fcolor, dword bcolor, tFontData *FontData, byte bDot, byte align, float AntiAliasFactor)
Definition: FM_PutStringAA.c:4
word GetOSDRegionWidth(word Region)
#define TRACEEXIT()
Definition: libFireBird.h:1244
@ Y
Definition: libFireBird.h:291
@ X
Definition: libFireBird.h:290
#define TRACEENTER()
Definition: libFireBird.h:1243
void InsertAt(const char *SourceString, int Pos, char *NewString)
Definition: InsertAt.c:4
void DeleteAt(char *SourceString, int Pos, int Len)
Definition: DeleteAt.c:4
tFontDef FontDef[191]
Definition: libFireBird.h:1821
byte * pFontData
Definition: libFireBird.h:1820
dword Width
Definition: libFireBird.h:1813
dword Height
Definition: libFireBird.h:1814
dword BitmapIndex
Definition: libFireBird.h:1815