Subversion Repositories Kolibri OS

Rev

Rev 6265 | Go to most recent revision | Details | Compare with Previous | Last modification | View Log | RSS feed

Rev Author Line No. Line
5987 leency 1
#ifndef INCLUDE_LABEL_H
2
#define INCLUDE_LABEL_H
5730 pavelyakov 3
 
4
#ifndef INCLUDE_MATH_H
5
#include "../lib/math.h"
6
#endif
7
 
6784 leency 8
#ifndef INCLUDE_IO_H
9
#include "../lib/io.h"
5730 pavelyakov 10
#endif
11
 
6021 leency 12
#include "../lib/patterns/rgb.h"
13
 
14
 
5981 leency 15
#define DEFAULT_FONT "/sys/fonts/Tahoma.kf"
16
 
5753 leency 17
:struct __SIZE
18
{
5816 leency 19
	dword width,height;
5987 leency 20
	signed offset_x, offset_y;
5757 pavelyakov 21
	float offset_i,w_italic;
5988 leency 22
	byte pt;
5754 pavelyakov 23
	byte TMP_WEIGHT;
5753 leency 24
};
5987 leency 25
:struct LABEL
5730 pavelyakov 26
{
5753 leency 27
	__SIZE size;
5987 leency 28
	int width,height;
5981 leency 29
	byte bold,italic,smooth;
5997 leency 30
	dword color, background;
5987 leency 31
	dword font,font_begin;
5730 pavelyakov 32
	word block;
5987 leency 33
	byte init();
5985 leency 34
	byte changeSIZE();
5987 leency 35
	byte symbol();
36
	byte symbol_size();
37
	dword getsize();
38
 
39
	dword raw;
40
	dword raw_size;
5985 leency 41
	void apply_smooth();
5987 leency 42
	int write_center();
43
	int write();
44
	void write_buf();
5985 leency 45
	void show_buf();
5987 leency 46
} label;
5981 leency 47
 
5987 leency 48
:byte LABEL::changeSIZE()
5730 pavelyakov 49
{
5987 leency 50
	dword file_size;
5736 pavelyakov 51
	dword TMP_DATA;
52
	dword ofs;
5987 leency 53
	IF(size.pt<9) size.pt = 8;
54
	TMP_DATA = font = font_begin;
55
	TMP_DATA +=size.pt-8*4;
5754 pavelyakov 56
	ofs = DSDWORD[TMP_DATA];
57
	IF(ofs==-1)return false;
5987 leency 58
	font += ofs + 156;
59
	TMP_DATA = font;
5754 pavelyakov 60
	file_size = DSDWORD[TMP_DATA];
5987 leency 61
	TMP_DATA = font + file_size;
5783 leency 62
	height = DSBYTE[TMP_DATA - 1];
63
	width =  DSBYTE[TMP_DATA - 2];
5754 pavelyakov 64
	block = math.ceil(height*width/32);
65
	return true;
5736 pavelyakov 66
}
5987 leency 67
:dword LABEL::getsize(dword text1)
5736 pavelyakov 68
{
5753 leency 69
	size.height = size.width = 0;
5987 leency 70
	size.offset_x = size.offset_y = -1;
71
	IF(size.pt)IF(!changeSIZE())return 0;
5742 pavelyakov 72
	WHILE(DSBYTE[text1])
73
	{
5753 leency 74
		symbol_size(DSBYTE[text1]);
5742 pavelyakov 75
		text1++;
76
	}
5987 leency 77
	$neg size.offset_y
78
	$neg size.offset_x
5996 leency 79
	size.height += size.offset_y+1;
80
	size.width += size.offset_x+1;
5757 pavelyakov 81
	IF(italic)
82
	{
5758 pavelyakov 83
		size.w_italic = size.height/3;
84
		size.offset_i = size.w_italic/size.height;
85
		size.width += size.w_italic;
86
		size.w_italic = -size.w_italic;
5757 pavelyakov 87
	}
5753 leency 88
	return size.width;
5742 pavelyakov 89
}
5987 leency 90
:byte LABEL::symbol_size(byte s)
5742 pavelyakov 91
{
5981 leency 92
		dword xi,yi;
93
		dword tmp,_;
5985 leency 94
		dword iii = 0;
5981 leency 95
		byte rw=0;
5753 leency 96
		byte X;
5987 leency 97
		size.TMP_WEIGHT = math.ceil(size.pt/17);
5981 leency 98
		IF(s==32)
5753 leency 99
		{
100
			size.width += width/4;
5981 leency 101
			IF(bold) size.width+=size.TMP_WEIGHT;
5753 leency 102
			return;
103
		}
104
		IF(s==9)
105
		{
106
			size.width += width;
5981 leency 107
			IF(bold) size.width+=size.TMP_WEIGHT;
5753 leency 108
			return;
109
		}
5987 leency 110
		s = Cp866ToAnsi(s);
111
		tmp = 4*block*s + font;
5981 leency 112
		for(yi=0; yi
113
		{
114
			for(xi=0; xi
115
			{
116
				IF(iii%32) _ >>= 1;
5784 leency 117
				ELSE
118
				{
5981 leency 119
					tmp += 4;
120
					_ = DSDWORD[tmp];
121
				}
122
				IF(_&1)
5784 leency 123
				{
124
					IF(xi>rw)rw=xi;
125
					IF(size.height
5987 leency 126
					IF(size.offset_y<0)size.offset_y = yi;
127
					ELSE IF(yi
5784 leency 128
					IF(!X) X = xi;
129
					ELSE IF(X>xi)X = xi;
130
				}
5981 leency 131
				iii++;
132
			}
133
		}
5753 leency 134
		size.width += rw;
5981 leency 135
		IF(bold) size.width+=size.TMP_WEIGHT;
6264 leency 136
		//IF(s=='_') size.width--; //http://board.kolibrios.org/viewtopic.php?f=44&t=973&start=645
5987 leency 137
		IF(size.offset_x<0)size.offset_x = X;
5742 pavelyakov 138
}
5987 leency 139
:byte LABEL::symbol(signed x,y; byte s; dword image_raw)
5981 leency 140
{
141
		dword xi,yi;
5985 leency 142
		dword iii = 0;
143
		dword offs;
5981 leency 144
		float ital = -size.w_italic;
145
		dword ___x;
146
		byte rw=0;
147
		IF(s==32)return width/4;
148
		IF(s==9)return width;
5987 leency 149
		s = Cp866ToAnsi(s);
150
		EBX = block*s << 2 + font;
5981 leency 151
		for(yi=0; yi
152
		{
5987 leency 153
			EDI = size.offset_y + yi + y * size.width * 3 + image_raw;
5981 leency 154
			for(xi=0; xi
155
			{
156
				IF(iii%32) $shr ecx,1
157
				ELSE
158
				{
159
						EBX += 4;
160
						ECX = DSDWORD[EBX];
161
				}
162
				IF(ECX&true)
163
				{
164
						IF(xi>rw)rw=xi;
165
						___x = x+xi;
166
						IF(italic)___x+=math.ceil(ital);
5985 leency 167
						offs = ___x*3 + EDI;
168
						DSDWORD[offs] = DSDWORD[offs] & 0xFF000000 | color;
169
						IF(bold) DSDWORD[offs+3] = DSDWORD[offs+3] & 0xFF000000 | color;
5981 leency 170
				}
171
				iii++;
172
			}
173
			if (italic) ital-=size.offset_i;
174
		}
175
		return rw;
176
}
177
 
5987 leency 178
byte Cp866ToAnsi(byte s) {
5981 leency 179
	IF(s>=128)&&(s<=175)s+=64;
180
	ELSE IF(s>=224)&&(s<=239)s+=16;
6265 leency 181
	ELSE IF(s==241)s=184; //e rus with dots (yo)
182
	ELSE IF(s==240)s=168; //E rus with dots (yo)
6784 leency 183
	ELSE IF(s==242)s='E'; //E ukr (ye)
184
	ELSE IF(s==243)s=186; //e ukr (ye)
185
	ELSE IF(s==244)s='I'; //I ukr (yi)
186
	ELSE IF(s==245)s=191; //i ukr (yi)
5981 leency 187
	return s;
188
}
189
 
5987 leency 190
:byte LABEL::init(dword font_path)
191
{
6784 leency 192
	IO label_io;
5987 leency 193
	IF(font)free(font);
6784 leency 194
	label_io.read(font_path);
195
	IF(!EAX) {
196
		notify("'Error: KFONT is not loaded.' -E");
5987 leency 197
		return false;
198
	}
6784 leency 199
	font_begin = font = label_io.buffer_data;
200
	height = DSBYTE[calc(font_begin+label_io.FILES_SIZE)-1];
201
	width = DSBYTE[calc(font_begin+label_io.FILES_SIZE)-2];
5987 leency 202
	block = math.ceil(height*width/32);
203
	smooth = true;
204
	return true;
205
}
206
 
207
 
208
/*=====================================================================================
209
===========================                                 ===========================
210
===========================               RAW               ===========================
211
===========================                                 ===========================
212
=====================================================================================*/
213
 
214
 
6053 leency 215
inline fastcall dword b24(EAX) { return DSDWORD[EAX] & 0x00FFFFFF; }
5987 leency 216
:void LABEL::apply_smooth()
5981 leency 217
{
6053 leency 218
	dword i,line_w,to,dark_background;
5987 leency 219
	line_w = size.width * 3;
220
	to = size.height - 1 * line_w + raw - 3;
221
	for(i=raw; i < to; i+=3)
5985 leency 222
	{
5997 leency 223
		if(i-raw%line_w +3 == line_w) continue;
6021 leency 224
		// pixels position, where b - black, w - write
225
		// bw
226
		// wb
6053 leency 227
		if(b24(i)!=background) && (b24(i+3)==background) && (b24(i+line_w)==background) && (b24(i+3+line_w)!=background)
5997 leency 228
		{
6216 leency 229
			dark_background = MixColors(background,b24(i),210);
6053 leency 230
			DSDWORD[i+3] = DSDWORD[i+3] & 0xFF000000 | dark_background;
231
			DSDWORD[i+line_w] = DSDWORD[i+line_w] & 0xFF000000 | dark_background;
5981 leency 232
		}
6021 leency 233
		// wb
234
		// bw
6053 leency 235
		else if(b24(i)==background) && (b24(i+3)!=background) && (b24(i+line_w)!=background) && (b24(i+3+line_w)==background)
5981 leency 236
		{
6216 leency 237
			dark_background = MixColors(background,b24(i+3),210);
6053 leency 238
			DSDWORD[i] = DSDWORD[i] & 0xFF000000 | dark_background;
239
			DSDWORD[i+3+line_w] = DSDWORD[i+3+line_w] & 0xFF000000 | dark_background;
5981 leency 240
		}
241
	}
242
}
243
 
5997 leency 244
:int LABEL::write_center(dword x,y,w,h; dword _background, _color; byte fontSizePoints; dword txt)
5742 pavelyakov 245
{
5987 leency 246
	size.pt = fontSizePoints;
5985 leency 247
	getsize(txt);
5997 leency 248
	return write(w-size.width/2+x,y, _background, _color, fontSizePoints, txt);
5985 leency 249
}
250
 
5997 leency 251
:int LABEL::write(int x,y; dword _background, _color; byte fontSizePoints; dword text1)
5985 leency 252
{
5742 pavelyakov 253
	signed len=0;
5754 pavelyakov 254
	IF(!text1)return false;
5987 leency 255
	IF(size.pt)IF(!changeSIZE())return false;
256
	size.pt = fontSizePoints;
5753 leency 257
	getsize(text1);
5997 leency 258
	color = _color;
259
	background = _background;
5987 leency 260
	y -= size.offset_y;
5754 pavelyakov 261
	EDX = size.width*size.height*3;
5987 leency 262
	IF(!raw_size)
5745 leency 263
	{
5987 leency 264
		raw_size = EDX;
265
		raw = malloc(raw_size);
5745 leency 266
	}
5987 leency 267
	ELSE IF(raw_size
5745 leency 268
	{
5987 leency 269
		raw_size = EDX;
270
		raw = realloc(raw,raw_size);
5745 leency 271
	}
5985 leency 272
	// Fill background color {
5987 leency 273
	EBX = background;
274
	EAX = raw_size+raw;
275
	for (EDI=raw; EDI
5985 leency 276
	// }
5987 leency 277
	len = size.offset_x;
5730 pavelyakov 278
	WHILE(DSBYTE[text1])
279
	{
6264 leency 280
		//IF(DSBYTE[text1]=='_') len--; //http://board.kolibrios.org/viewtopic.php?f=44&t=973&start=645
5987 leency 281
		len+=symbol(len,0,DSBYTE[text1], raw);
282
		IF(bold)len+=math.ceil(size.pt/17);
5730 pavelyakov 283
		text1++;
284
	}
5985 leency 285
	IF (smooth) apply_smooth();
5987 leency 286
	show_buf(x,y);
5730 pavelyakov 287
	return len;
288
}
289
 
5997 leency 290
:void LABEL::write_buf(int x,y,w,h; dword _background, _color; byte fontSizePoints; dword text1)
5782 leency 291
{
5987 leency 292
	dword new_raw_size;
5782 leency 293
	IF(!text1)return;
5987 leency 294
	IF(size.pt)IF(!changeSIZE())return;
295
 
6021 leency 296
	if (size.pt != fontSizePoints) {
297
		size.pt = fontSizePoints;
298
		getsize(text1);
299
		y -= size.offset_y;
300
	}
5997 leency 301
	color = _color;
302
	background = _background;
5981 leency 303
 
5782 leency 304
	size.width = w;
5783 leency 305
	size.height = h;
5784 leency 306
 
5987 leency 307
	new_raw_size = w*h*3;
308
	IF(raw_size != new_raw_size)
5782 leency 309
	{
5987 leency 310
		raw_size = new_raw_size;
311
		free(raw);
312
		raw = malloc(raw_size);
5985 leency 313
		// Fill background color
5987 leency 314
		EBX = background;
315
		EAX = raw_size+raw;
316
		for (EDI=raw; EDI
5782 leency 317
	}
318
	WHILE(DSBYTE[text1])
319
	{
5987 leency 320
		x+=symbol(x,y,DSBYTE[text1], raw);
321
		IF(bold)x+=math.ceil(size.pt/17);
5782 leency 322
		text1++;
323
	}
324
	return;
325
}
326
 
5987 leency 327
:void LABEL::show_buf(dword x, y){
328
	_PutImage(x, y, size.width, size.height, raw);
5985 leency 329
}
330
 
331
 
332
 
5730 pavelyakov 333
#endif