Subversion Repositories Kolibri OS

Rev

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

Rev Author Line No. Line
1535 IgorA 1
format MS COFF
2
public EXPORTS
3
section '.flat' code readable align 16
4
 
5
include '../../../../macros.inc'
6
include '../../../../proc32.inc'
7
 
8
;-----------------------------------------------------------------------------
9
mem.alloc   dd ? ;функция для выделения памяти
10
mem.free    dd ? ;функция для освобождения памяти
11
mem.realloc dd ? ;функция для перераспределения памяти
12
dll.load    dd ?
13
 
14
BUF_STRUCT_SIZE equ 21
15
buf2d_data equ dword[edi] ;данные буфера изображения
16
buf2d_w equ dword[edi+8] ;ширина буфера
17
buf2d_h equ dword[edi+12] ;высота буфера
1538 IgorA 18
buf2d_l equ word[edi+4]
1535 IgorA 19
buf2d_t equ word[edi+6] ;отступ сверху
20
buf2d_size_lt equ dword[edi+4] ;отступ слева и справа для буфера
21
buf2d_color equ dword[edi+16] ;цвет фона буфера
22
buf2d_bits equ byte[edi+20] ;количество бит в 1-й точке изображения
23
 
24
struct buf_2d_header
25
	img_data dd ?
26
	left dw ? ;+4 left
27
	top dw ? ;+6 top
28
	size_x dd ? ;+8 w
29
	size_y dd ? ;+12 h
30
	color dd ? ;+16 color
31
	bit_pp db ? ;+21 bit in pixel
32
ends
33
 
34
macro swap v1, v2 {
35
  push v1
36
  push v2
37
  pop v1
38
  pop v2
39
}
40
 
41
;флаги, для функции обрезания буфера
42
BUF2D_OPT_CROP_TOP equ 1 ;обрезка сверху
43
BUF2D_OPT_CROP_LEFT equ 2 ;обрезка слева
44
BUF2D_OPT_CROP_BOTTOM equ 4 ;обрезка снизу
45
BUF2D_OPT_CROP_RIGHT equ 8 ;обрезка справа
46
BUF2D_BIT_OPT_CROP_TOP equ 0
47
BUF2D_BIT_OPT_CROP_LEFT equ 1
48
BUF2D_BIT_OPT_CROP_BOTTOM equ 2
49
BUF2D_BIT_OPT_CROP_RIGHT equ 3
50
 
51
;input:
52
; eax = указатель на функцию выделения памяти
53
; ebx = ... освобождения памяти
54
; ecx = ... перераспределения памяти
55
; edx = ... загрузки библиотеки (пока не используется)
56
align 16
57
lib_init:
58
	mov dword[mem.alloc], eax
59
	mov dword[mem.free], ebx
60
	mov dword[mem.realloc], ecx
61
	mov dword[dll.load], edx
62
	ret
63
 
64
;input:
65
; ebx = coord x
66
; ecx = coord y
67
; edx = pixel color
68
; edi = pointer to buffer struct
69
align 4
70
draw_pixel:
71
	;cmp buf2d_bits,24
72
	;jne @f
73
	bt ebx,31
74
	jc @f
75
	bt ecx,31
76
	jc @f
77
	cmp ebx,buf2d_w
78
	jge @f
79
	cmp ecx,buf2d_h
80
	jge @f
81
	push esi
82
		mov esi,buf2d_w ;size x
83
		imul esi,ecx ;size_x*y
84
		add esi,ebx	 ;size_x*y+x
85
		lea esi,[esi+esi*2] ;(size_x*y+x)*3
86
		add esi,buf2d_data  ;ptr+(size_x*y+x)*3
87
 
88
		mov word[esi],dx ;copy pixel color
89
		ror edx,16
90
		mov byte[esi+2],dl
91
		ror edx,16
92
	pop esi
93
	@@:
94
	ret
95
;endp
96
 
97
;создание буфера
98
align 4
99
proc buf_create, buf_struc:dword
100
	pushad
101
	mov edi,dword[buf_struc]
102
	mov ecx,buf2d_w
103
	mov ebx,buf2d_h
104
	imul ecx,ebx
105
	cmp buf2d_bits,24
106
	jne @f
107
		lea ecx,[ecx+ecx*2] ; 24 bit = 3
108
		;;;inc ecx ;запасной байт в конце буфера, что-бы не глючили некоторые функции на изображениях кратных 4К
109
	@@:
110
	cmp buf2d_bits,32
111
	jne @f
112
		shl ecx,2 ; 32 bit = 4
113
	@@:
114
	invoke mem.alloc,ecx
115
	mov buf2d_data,eax
116
 
117
	stdcall buf_clear,edi,buf2d_color ;очистка буфера фоновым цветом
118
	popad
119
	ret
120
endp
121
 
122
;создание буфера на основе изображения rgb
123
align 4
124
proc buf_create_f_img, buf_struc:dword, rgb_data:dword
125
	pushad
126
	mov edi,dword[buf_struc]
127
	mov ecx,buf2d_w
128
	mov ebx,buf2d_h
129
	imul ecx,ebx
130
	cmp buf2d_bits,24
131
	jne @f
132
		lea ecx,[ecx+ecx*2] ; 24 bit = 3
133
		;;;inc ecx ;запасной байт в конце буфера, что-бы не глючили некоторые функции на изображениях кратных 4К
134
	@@:
135
	cmp buf2d_bits,32
136
	jne @f
137
		shl ecx,2 ; 32 bit = 4
138
	@@:
139
	invoke mem.alloc,ecx
140
	mov buf2d_data,eax
141
 
142
	cmp buf2d_bits,24
143
	jne @f
144
		cld
145
		mov esi,[rgb_data]
146
		mov edi,eax ;eax=buf2d_data
147
		rep movsb ;копируем биты изображения в буфер
148
		jmp .end_create
149
	@@:
150
		stdcall buf_clear,edi,buf2d_color ;очистка буфера фоновым цветом
151
	.end_create:
152
	popad
153
	ret
154
endp
155
 
156
align 4
157
proc buf_clear, buf_struc:dword, color:dword ;очистка буфера заданым цветом
158
	pushad
159
	mov edi,dword[buf_struc]
160
 
161
	mov ecx,buf2d_w
162
	mov ebx,buf2d_h
163
	imul ecx,ebx
164
 
165
	cld
166
 
167
	cmp buf2d_bits,8
168
	jne .end_clear_8
169
		mov edi,buf2d_data
170
		mov al,byte[color]
171
		rep stosb
172
		jmp .end_clear_32
173
	.end_clear_8:
174
 
175
	cmp buf2d_bits,24
176
	jne .end_clear_24
177
		mov edi,buf2d_data
178
		mov eax,dword[color]
179
		mov ebx,eax
180
		shr ebx,16
181
		@@:
182
			stosw
183
			mov byte[edi],bl
184
			inc edi
185
			loop @b
186
		jmp .end_clear_32
187
	.end_clear_24:
188
 
189
	cmp buf2d_bits,32
190
	jne .end_clear_32
191
		mov edi,buf2d_data
192
		mov eax,dword[color]
193
		rep stosd
194
		;jmp .end_clear_32
195
	.end_clear_32:
196
	popad
197
	ret
198
endp
199
 
1538 IgorA 200
;функция для обрезания буферов 8 и 24 битных, по заданому цвету.
201
;параметр opt задается комбинацией констант:
202
; BUF2D_OPT_CROP_TOP - обрезка сверху
203
; BUF2D_OPT_CROP_LEFT - обрезка слева
204
; BUF2D_OPT_CROP_BOTTOM - обрезка снизу
205
; BUF2D_OPT_CROP_RIGHT - обрезка справа
1535 IgorA 206
align 4
1538 IgorA 207
proc buf_crop_color, buf_struc:dword, color:dword, opt:dword
1535 IgorA 208
locals
209
	crop_r dd ?
210
endl
211
	pushad
212
	mov edi,dword[buf_struc]
213
	cmp buf2d_bits,24
214
	jne .24end_f
215
 
216
	bt dword[opt],BUF2D_BIT_OPT_CROP_BOTTOM
217
	jae .24no_crop_bottom
218
		mov eax,dword[color]
219
		mov edx,eax ;ax = colors - r,g
220
		shr edx,16 ;dl = color - b
221
		mov ecx,buf2d_h
1555 IgorA 222
		cmp ecx,1
223
		jle .24no_crop_bottom ;проверяем на случай если высота буфера 1 пиксель
1535 IgorA 224
		mov ebx,buf2d_w
225
		imul ecx,ebx
226
		lea esi,[ecx+ecx*2] ;esi=3*ecx
227
		add esi,buf2d_data
228
		cld
229
		@@:
230
			sub esi,3
231
			cmp word[esi],ax
232
			jne @f
233
			cmp byte[esi+2],dl
234
			jne @f
235
			loop @b
236
		@@:
237
		lea ebx,[ebx+ebx*2]
238
		xor edx,edx
239
		mov eax,buf2d_h
240
		imul eax,ebx
241
		add eax,buf2d_data ;eax - указатель на конец буфера изображения
242
		@@:
243
			add esi,ebx
244
			cmp esi,eax
245
			jge @f
246
			inc edx ;вычисляем число полных строк для обрезания
247
			loop @b
248
		@@:
249
		cmp edx,0
250
		je .24no_crop_bottom
251
			cmp edx,buf2d_h
252
			jge .24no_crop_bottom ;что-бы не получить пустой буфер
253
			sub buf2d_h,edx ;уменьшаем высоту буфера
254
			mov ecx,buf2d_h
255
			imul ecx,ebx ;ecx = новый размер изображения
256
			invoke mem.realloc,buf2d_data,ecx
257
			mov buf2d_data,eax ;на случай если изменился указатель на данные
258
	.24no_crop_bottom:
259
 
260
	bt dword[opt],BUF2D_BIT_OPT_CROP_TOP
261
	jae .24no_crop_top
262
		mov eax,dword[color]
263
		mov edx,eax ;ax = colors - r,g
264
		shr edx,16 ;dl = color - b
265
		mov esi,buf2d_data
266
		mov ecx,buf2d_h
1555 IgorA 267
		cmp ecx,1
268
		jle .24no_crop_top ;проверяем на случай если высота буфера 1 пиксель
1535 IgorA 269
		dec ecx ;при обрезании должна остаться минимум 1-на строка пикселей
270
		mov ebx,buf2d_w
271
		imul ecx,ebx
272
		cld
273
		@@:
274
			cmp word[esi],ax
275
			jne @f
276
			cmp byte[esi+2],dl
277
			jne @f
278
			add esi,3
279
			loop @b
280
		@@:
281
		lea ebx,[ebx+ebx*2]
282
		xor edx,edx
283
		@@:
284
			sub esi,ebx
285
			cmp esi,buf2d_data
286
			jl @f
287
			inc edx ;вычисляем число полных строк для обрезания
288
			loop @b
289
		@@:
290
		cmp edx,0
291
		je .24no_crop_top
292
			xor eax,eax
293
			sub eax,edx
294
			mov ebx,buf2d_h
295
			sub ebx,edx
296
			stdcall buf_offset_h, edi, eax, edx, ebx ;сдвигаем изображение в буфере вверх (eax<0)
297
			sub buf2d_h,edx ;уменьшаем высоту буфера
298
			mov ecx,buf2d_h
299
			add buf2d_t,dx ;сдвигаем отступ вниз, на число обрезанных строк
300
			mov ebx,buf2d_w
301
			imul ecx,ebx
302
			lea ecx,[ecx+ecx*2]
303
			invoke mem.realloc,buf2d_data,ecx
304
			mov buf2d_data,eax ;на случай если изменился указатель на данные
305
	.24no_crop_top:
306
 
307
	bt dword[opt],BUF2D_BIT_OPT_CROP_RIGHT
308
	jae .24no_crop_right
309
		mov eax,dword[color]
310
		mov edx,eax ;ax = colors - r,g
311
		shr edx,16 ;dl = color - b
312
		mov ebx,buf2d_w
1555 IgorA 313
		cmp ebx,1
314
		jle .24no_crop_right ;на случай если ширина буфера 1 пиксель
1535 IgorA 315
		lea ebx,[ebx+ebx*2]
316
		mov esi,ebx
317
		imul esi,buf2d_h
318
		add esi,buf2d_data ;esi - указатель на конец буфера изображения
319
		mov dword[crop_r],0
320
		cld
1538 IgorA 321
		.24found_beg_right:
1535 IgorA 322
		sub esi,3 ;двигаемся на 1-ну колонку влево
323
		mov ecx,buf2d_h ;восстановление ecx для нового цикла
324
		@@:
325
			cmp word[esi],ax
1538 IgorA 326
			jne .24found_right
1535 IgorA 327
			cmp byte[esi+2],dl
1538 IgorA 328
			jne .24found_right
1535 IgorA 329
			sub esi,ebx ;прыгаем на верхнюю строку
330
			loop @b
331
		inc dword[crop_r]
332
 
333
		mov ecx,buf2d_w
334
		dec ecx ;1 колонка на запас
335
		cmp dword[crop_r],ecx
1538 IgorA 336
		jge .24found_right
1535 IgorA 337
 
338
		sub esi,3 ;двигаемся на 1-ну колонку влево
339
		mov ecx,buf2d_h ;восстановление ecx для нового цикла
340
		@@:
341
			add esi,ebx ;прыгаем на нижнюю строку
342
			cmp word[esi],ax
1538 IgorA 343
			jne .24found_right
1535 IgorA 344
			cmp byte[esi+2],dl
1538 IgorA 345
			jne .24found_right
1535 IgorA 346
			loop @b
347
		inc dword[crop_r]
348
 
349
		mov ecx,buf2d_w
350
		dec ecx ;1 колонка на запас
351
		cmp dword[crop_r],ecx
1538 IgorA 352
		jl .24found_beg_right
1535 IgorA 353
 
1538 IgorA 354
		.24found_right:
1535 IgorA 355
		cmp dword[crop_r],0
356
		je .24no_crop_right
357
			mov ecx,buf2d_w
358
			sub ecx,dword[crop_r]
1538 IgorA 359
			stdcall img_rgb_crop_r, buf2d_data, buf2d_w, ecx, buf2d_h ;обрезаем буфер, по новому размеру
1535 IgorA 360
			mov buf2d_w,ecx ;ставим новую ширину для буфера
361
			mov ebx,buf2d_h
362
			imul ecx,ebx
363
			lea ecx,[ecx+ecx*2]
364
			invoke mem.realloc,buf2d_data,ecx
365
			mov buf2d_data,eax ;на случай если изменился указатель на данные
366
	.24no_crop_right:
367
 
1538 IgorA 368
	bt dword[opt],BUF2D_BIT_OPT_CROP_LEFT
369
	jae .24no_crop_left
370
		mov eax,dword[color]
371
		mov edx,eax ;ax = colors - r,g
372
		shr edx,16 ;dl = color - b
373
		mov ebx,buf2d_w
1555 IgorA 374
		cmp ebx,1
375
		jle .24no_crop_left ;на случай если ширина буфера 1 пиксель
1538 IgorA 376
		lea ebx,[ebx+ebx*2]
377
		mov esi,buf2d_data ;esi - указатель на начоло буфера изображения
378
		mov dword[crop_r],0
379
		cld
380
		.24found_beg_left:
381
 
382
		mov ecx,buf2d_h ;восстановление ecx для нового цикла
383
		@@:
384
			cmp word[esi],ax
385
			jne .24found_left
386
			cmp byte[esi+2],dl
387
			jne .24found_left
388
			add esi,ebx ;прыгаем на нижнюю строку
389
			loop @b
390
		inc dword[crop_r]
391
		add esi,3 ;двигаемся на 1-ну колонку вправо
392
 
393
		mov ecx,buf2d_w
394
		dec ecx ;1 колонка на запас
395
		cmp dword[crop_r],ecx
396
		jge .24found_left
397
 
398
		mov ecx,buf2d_h ;восстановление ecx для нового цикла
399
		@@:
400
			sub esi,ebx ;прыгаем на верхнюю строку
401
			cmp word[esi],ax
402
			jne .24found_left
403
			cmp byte[esi+2],dl
404
			jne .24found_left
405
			loop @b
406
		inc dword[crop_r]
407
		add esi,3 ;двигаемся на 1-ну колонку вправо
408
 
409
		mov ecx,buf2d_w
410
		dec ecx ;1 колонка на запас
411
		cmp dword[crop_r],ecx
412
		jl .24found_beg_left
413
 
414
		.24found_left:
415
		cmp dword[crop_r],0
416
		je .24no_crop_left
417
			mov ecx,buf2d_w
418
			sub ecx,dword[crop_r]
419
			stdcall img_rgb_crop_l, buf2d_data, buf2d_w, ecx, buf2d_h ;обрезаем буфер, по новому размеру
420
			mov buf2d_w,ecx ;ставим новую ширину для буфера
421
			mov ebx,buf2d_h
422
			imul ecx,ebx
423
			lea ecx,[ecx+ecx*2]
424
			invoke mem.realloc,buf2d_data,ecx
425
			mov buf2d_data,eax ;на случай если изменился указатель на данные
426
			mov eax,dword[crop_r]
427
			add buf2d_l,ax
428
	.24no_crop_left:
429
 
1535 IgorA 430
	.24end_f:
431
 
432
 
433
	cmp buf2d_bits,8
434
	jne .8end_f
435
 
436
	bt dword[opt],BUF2D_BIT_OPT_CROP_BOTTOM
437
	jae .8no_crop_bottom
438
		mov eax,dword[color]
439
		mov esi,buf2d_data
440
		mov ecx,buf2d_h
1555 IgorA 441
		cmp ecx,1
442
		jle .8no_crop_bottom ;проверяем на случай если высота буфера 1 пиксель
1535 IgorA 443
		mov ebx,buf2d_w
444
		imul ecx,ebx
445
		mov esi,ecx
446
		add esi,buf2d_data
447
		cld
448
		@@:
449
			dec esi
450
			cmp byte[esi],al
451
			jne @f
452
			loop @b
453
		@@:
454
		xor edx,edx
455
		mov eax,buf2d_h
456
		imul eax,ebx
457
		add eax,buf2d_data ;eax - указатель на конец буфера изображения
458
		@@:
459
			add esi,ebx
460
			cmp esi,eax
461
			jge @f
462
			inc edx
463
			loop @b
464
		@@:
465
		cmp edx,0
466
		je .8no_crop_bottom
467
			cmp edx,buf2d_h
468
			jge .8no_crop_bottom ;что-бы не получить пустой буфер
469
			sub buf2d_h,edx ;уменьшаем высоту буфера
470
			mov ecx,buf2d_h
471
			imul ecx,ebx ;ecx = новый размер изображения
472
			invoke mem.realloc,buf2d_data,ecx
473
			mov buf2d_data,eax ;на случай если изменился указатель на данные
474
	.8no_crop_bottom:
475
 
476
	bt dword[opt],BUF2D_BIT_OPT_CROP_TOP
477
	jae .8no_crop_top
478
		mov eax,dword[color]
479
		mov esi,buf2d_data
480
		mov ecx,buf2d_h
1555 IgorA 481
		cmp ecx,1
482
		jle .8no_crop_top ;проверяем на случай если высота буфера 1 пиксель
1535 IgorA 483
		dec ecx ;при обрезании должна остаться минимум 1-на строка пикселей
484
		mov ebx,buf2d_w
485
		imul ecx,ebx
486
		cld
487
		@@:
488
			cmp byte[esi],al
489
			jne @f
490
			inc esi
491
			loop @b
492
		@@:
493
		xor edx,edx
494
		@@:
495
			sub esi,ebx
496
			cmp esi,buf2d_data
497
			jl @f
498
			inc edx
499
			loop @b
500
		@@:
501
		cmp edx,0
502
		je .8no_crop_top
503
			xor eax,eax
504
			sub eax,edx
505
			mov ebx,buf2d_h
506
			sub ebx,edx
507
			stdcall buf_offset_h, edi, eax, edx, ebx
508
			mov ecx,buf2d_h
509
			sub ecx,edx
510
			mov buf2d_h,ecx ;уменьшаем высоту буфера
511
			add buf2d_t,dx ;сдвигаем отступ вниз, на число обрезанных строк
512
			mov ebx,buf2d_w
513
			imul ecx,ebx
514
			invoke mem.realloc,buf2d_data,ecx
515
			mov buf2d_data,eax ;на случай если изменился указатель на данные
516
	.8no_crop_top:
517
 
518
	bt dword[opt],BUF2D_BIT_OPT_CROP_RIGHT
519
	jae .8no_crop_right
520
		mov eax,dword[color]
521
		mov ebx,buf2d_w
1555 IgorA 522
		cmp ebx,1
523
		jle .8no_crop_right ;на случай если ширина буфера 1 пиксель
1535 IgorA 524
		mov esi,ebx
525
		imul esi,buf2d_h
526
		add esi,buf2d_data ;esi - указатель на конец буфера изображения
527
		xor edx,edx
528
		cld
529
 
530
		.8found_beg:
531
		dec esi ;двигаемся на 1-ну колонку влево
532
		mov ecx,buf2d_h ;восстановление ecx для нового цикла
533
		@@:
534
			cmp byte[esi],al
535
			jne .8found
536
			sub esi,ebx ;прыгаем на верхнюю строку
537
			loop @b
538
		inc edx
539
		mov ecx,buf2d_w
540
		dec ecx ;1 колонка на запас
541
		cmp edx,ecx
542
		jge .8found
543
 
544
		dec esi ;двигаемся на 1-ну колонку влево
545
		mov ecx,buf2d_h ;восстановление ecx для нового цикла
546
		@@:
547
			add esi,ebx ;прыгаем на нижнюю строку
548
			cmp byte[esi],al
549
			jne .8found
550
			loop @b
551
		inc edx
552
 
553
		mov ecx,buf2d_w
554
		dec ecx ;1 колонка на запас
555
		cmp edx,ecx
556
		jl .8found_beg
557
 
558
		.8found:
559
		cmp edx,0
560
		je .8no_crop_right
561
			mov ecx,buf2d_w
562
			sub ecx,edx
1538 IgorA 563
			stdcall img_gray_crop_r, buf2d_data, buf2d_w, ecx, buf2d_h ;обрезаем буфер, по новому размеру
1535 IgorA 564
			mov buf2d_w,ecx ;ставим новую ширину для буфера
565
			mov ebx,buf2d_h
566
			imul ecx,ebx
567
			invoke mem.realloc,buf2d_data,ecx
568
			mov buf2d_data,eax ;на случай если изменился указатель на данные
569
	.8no_crop_right:
570
 
1538 IgorA 571
	bt dword[opt],BUF2D_BIT_OPT_CROP_LEFT
572
	jae .8no_crop_left
573
		mov eax,dword[color]
574
		mov ebx,buf2d_w
1555 IgorA 575
		cmp ebx,1
576
		jle .8no_crop_left ;на случай если ширина буфера 1 пиксель
1538 IgorA 577
		mov esi,buf2d_data ;esi - указатель на начоло буфера изображения
578
		mov edx,0
579
		cld
580
		.8found_beg_left:
581
 
582
		mov ecx,buf2d_h ;восстановление ecx для нового цикла
583
		@@:
584
			cmp word[esi],ax
585
			jne .8found_left
586
			add esi,ebx ;прыгаем на нижнюю строку
587
			loop @b
588
		inc edx
589
		inc esi ;двигаемся на 1-ну колонку вправо
590
 
591
		mov ecx,buf2d_w
592
		dec ecx ;1 колонка на запас
593
		cmp edx,ecx
594
		jge .8found_left
595
 
596
		mov ecx,buf2d_h ;восстановление ecx для нового цикла
597
		@@:
598
			sub esi,ebx ;прыгаем на верхнюю строку
599
			cmp word[esi],ax
600
			jne .8found_left
601
			loop @b
602
		inc edx
603
		inc esi ;двигаемся на 1-ну колонку вправо
604
 
605
		mov ecx,buf2d_w
606
		dec ecx ;1 колонка на запас
607
		cmp edx,ecx
608
		jl .8found_beg_left
609
 
610
		.8found_left:
611
		cmp edx,0
612
		je .8no_crop_left
613
			mov ecx,buf2d_w
614
			sub ecx,edx
615
			stdcall img_gray_crop_l, buf2d_data, buf2d_w, ecx, buf2d_h ;обрезаем буфер, по новому размеру
616
			mov buf2d_w,ecx ;ставим новую ширину для буфера
617
			mov ebx,buf2d_h
618
			imul ecx,ebx
619
			invoke mem.realloc,buf2d_data,ecx
620
			mov buf2d_data,eax ;на случай если изменился указатель на данные
621
			mov eax,edx
622
			add buf2d_l,ax
623
	.8no_crop_left:
624
 
1535 IgorA 625
	.8end_f:
626
 
627
	popad
628
	ret
629
endp
630
 
1538 IgorA 631
;обрезаем цветное изображение с правой стороны
1535 IgorA 632
;input:
633
;data_rgb - pointer to rgb data
634
;size_w_old - width img in pixels
635
;size_w_new - new width img in pixels
636
;size_h - height img in pixels
637
align 4
1538 IgorA 638
proc img_rgb_crop_r, data_rgb:dword, size_w_old:dword, size_w_new:dword, size_h:dword
1535 IgorA 639
	pushad
640
	mov eax, dword[size_w_old]
641
	lea eax, dword[eax+eax*2] ;eax = width(old) * 3(rgb)
642
	mov ebx, dword[size_w_new]
643
	lea ebx, dword[ebx+ebx*2] ;ebx = width(new) * 3(rgb)
644
	mov edx, dword[size_h]
645
	mov edi, dword[data_rgb] ;edi - получает данные
646
	mov esi, edi
647
	add edi, ebx
648
	add esi, eax
649
	cld
650
	@@:
651
		dec edx ;уменьшаем счетчик оставшихся строк на 1
652
		cmp edx,0
653
		jle @f
654
		mov ecx, ebx
655
		rep movsb ;перенос (копирование) строки пикселей
656
		add esi,eax ;переход на новую строчку изображения
657
		sub esi,ebx
658
		jmp @b
659
	@@:
660
	popad
661
	ret
662
endp
663
 
1538 IgorA 664
;обрезаем серое изображение с правой стороны
1535 IgorA 665
;input:
666
;data_gray - pointer to gray data
667
;size_w_old - width img in pixels
668
;size_w_new - new width img in pixels
669
;size_h - height img in pixels
670
align 4
1538 IgorA 671
proc img_gray_crop_r, data_gray:dword, size_w_old:dword, size_w_new:dword, size_h:dword
1535 IgorA 672
	pushad
673
	mov eax, dword[size_w_old]
674
	mov ebx, dword[size_w_new]
675
	mov edx, dword[size_h]
676
	mov edi, dword[data_gray] ;edi - получает данные
677
	mov esi, edi
678
	add edi, ebx
679
	add esi, eax
680
	cld
681
	@@:
682
		dec edx ;уменьшаем счетчик оставшихся строк на 1
683
		cmp edx,0
684
		jle @f
685
		mov ecx, ebx
686
		rep movsb ;перенос (копирование) строки пикселей
687
		add esi,eax ;переход на новую строчку изображения
688
		sub esi,ebx
689
		jmp @b
690
	@@:
691
	popad
692
	ret
693
endp
694
 
1538 IgorA 695
;обрезаем цветное изображение с левой стороны
696
;input:
697
;data_rgb - pointer to rgb data
698
;size_w_old - width img in pixels
699
;size_w_new - new width img in pixels
700
;size_h - height img in pixels
701
align 4
702
proc img_rgb_crop_l, data_rgb:dword, size_w_old:dword, size_w_new:dword, size_h:dword
703
	pushad
704
	mov edi,dword[data_rgb]
705
	mov esi,edi
706
	mov eax,dword[size_w_old]
707
	mov ebx,dword[size_w_new]
708
	cmp eax,ebx
709
	jle .end_f ;старый размер изображения не может быть меньше нового (при условии обрезания картинки)
710
		lea eax,[eax+eax*2]
711
		lea ebx,[ebx+ebx*2]
712
		sub eax,ebx
713
		mov edx,dword[size_h] ;высота изображения
714
		cld
715
		@@:
716
			add esi,eax
717
			mov ecx,ebx
718
			rep movsb
719
			dec edx
720
			cmp edx,0
721
			jg @b
722
	.end_f:
723
	popad
724
	ret
725
endp
726
 
727
;обрезаем серое изображение с левой стороны
728
;input:
729
;data_gray - pointer to gray data
730
;size_w_old - width img in pixels
731
;size_w_new - new width img in pixels
732
;size_h - height img in pixels
733
align 4
734
proc img_gray_crop_l, data_gray:dword, size_w_old:dword, size_w_new:dword, size_h:dword
735
	pushad
736
	mov edi,dword[data_gray]
737
	mov esi,edi
738
	mov eax,dword[size_w_old]
739
	mov ebx,dword[size_w_new]
740
	cmp eax,ebx
741
	jle .end_f ;старый размер изображения не может быть меньше нового (при условии обрезания картинки)
742
		sub eax,ebx
743
		mov edx,dword[size_h] ;высота изображения
744
		cld
745
		@@:
746
			add esi,eax
747
			mov ecx,ebx
748
			rep movsb
749
			dec edx
750
			cmp edx,0
751
			jg @b
752
	.end_f:
753
	popad
754
	ret
755
endp
756
 
1535 IgorA 757
;hoffs - колличество пикселей на котрые поднимается/опускается изображение
758
;img_t - высота, с которой начинается двигающаяся часть изображения
759
align 4
760
proc buf_offset_h, buf_struc:dword, hoffs:dword, img_t:dword, img_h:dword ;сдвигает изображение по высоте
761
	pushad
762
	mov edi,dword[buf_struc]
763
	cmp buf2d_bits,24
764
	jne .end_move_24
765
 
766
	mov eax,[hoffs]
767
	cmp eax,0
768
	je .end_move_24
769
		mov ebx,buf2d_w
770
		mov edx,dword[img_t]
771
			mov ecx,dword[img_h] ;ecx - высота сдвигаемых данных
772
			cmp ecx,buf2d_h
773
			jge .end_f ;ошибочное условие, высота изображения меньше чем высота сдвигаемого изображения
774
			imul ecx,ebx ;ecx - колличество пикселей в сдвигаемых данных
775
			lea ecx,[ecx+ecx*2]
776
		imul ebx,edx
777
		lea ebx,[ebx+ebx*2]
778
		mov esi,buf2d_data
779
		add esi,ebx
780
 
781
		add edx,eax ;edx = img_t+hoffs (hoffs<0)
782
		mov ebx,buf2d_w
783
		imul ebx,edx
784
		lea ebx,[ebx+ebx*2]
785
		mov edi,buf2d_data ;позиция, куда будет двигаться изображение
786
		add edi,ebx
787
 
788
		cmp eax,0
789
		jg .move_down_24
790
			;двигаем изображение вверх
791
			cld
792
			rep movsb
793
			jmp .end_f
794
		.move_down_24:
795
			;двигаем изображение вниз
796
			add esi,ecx
797
			dec esi
798
			add edi,ecx
799
			dec edi
800
			std
801
			rep movsb
802
			jmp .end_f
803
	.end_move_24:
804
 
805
;stdcall print_err,sz_buf2d_offset_h,txt_err_n24b
806
 
807
	cmp buf2d_bits,8
808
	jne .end_move_8
809
 
810
	mov eax,[hoffs]
811
	cmp eax,0
812
	je .end_move_8
813
		;двигаем изображение вверх
814
		mov ebx,buf2d_w
815
		mov edx,dword[img_t]
816
			mov ecx,dword[img_h] ;ecx - высота сдвигаемых данных
817
			cmp ecx,buf2d_h
818
			jge .end_f ;ошибочное условие, высота изображения меньше чем высота сдвигаемого изображения
819
			imul ecx,ebx ;ecx - колличество пикселей в сдвигаемых данных
820
		imul ebx,edx
821
		mov esi,buf2d_data
822
		add esi,ebx
823
 
824
		add edx,eax ;edx = img_t+hoffs (hoffs<0)
825
		mov ebx,buf2d_w
826
		imul ebx,edx
827
		mov edi,buf2d_data ;позиция, куда будет двигаться изображение
828
		add edi,ebx
829
 
830
		cmp eax,0
831
		jg .move_down_8
832
			cld
833
			rep movsb
834
			jmp .end_f
835
		.move_down_8:
836
			;двигаем изображение вниз
837
			add esi,ecx
838
			dec esi
839
			add edi,ecx
840
			dec edi
841
			std
842
			rep movsb
843
			jmp .end_f
844
	.end_move_8:
845
 
846
	.end_f:
847
	popad
848
	ret
849
endp
850
 
851
 
852
align 4
853
proc buf_draw_buf, buf_struc:dword
854
	pushad
855
	mov edi,dword[buf_struc]
856
	cmp buf2d_bits,24
857
	jne .error
858
		mov eax,7
859
		mov ebx,buf2d_data
860
 
861
		mov ecx,buf2d_w
862
		ror ecx,16
863
		mov edx,buf2d_h
864
		mov cx,dx
865
 
866
		mov edx,buf2d_size_lt
867
		ror edx,16
868
		int 0x40
869
		jmp .end_draw_24
870
	.error:
871
		stdcall print_err,sz_buf2d_draw,txt_err_n24b
872
	.end_draw_24:
873
	popad
874
	ret
875
endp
876
 
877
align 4
878
proc buf_delete, buf_struc:dword
879
	push edi
880
	mov edi,dword[buf_struc]
881
	invoke mem.free,buf2d_data
882
	pop edi
883
	ret
884
endp
885
 
886
align 4
887
proc buf_line_brs, buf_struc:dword, coord_x0:dword, coord_y0:dword, coord_x1:dword, coord_y1:dword, color:dword
888
locals
889
	loc_1 dd ?
890
	loc_2 dd ?
891
	napravl db ?
892
endl
893
	pushad
894
		mov edx,dword[color]
895
 
896
		mov eax,dword[coord_x1]
897
		sub eax,dword[coord_x0]
898
		bt eax,31
899
		jae @f
900
			neg eax
901
			inc eax
902
		@@:
903
		mov ebx,dword[coord_y1]
904
		sub ebx,dword[coord_y0]
905
		bt ebx,31
906
		jae @f
907
			neg ebx
908
			inc ebx
909
		@@:
910
 
911
		mov [napravl],byte 0 ;bool steep=false
912
		cmp eax,ebx
913
		jle @f
914
			mov [napravl],byte 1 ;bool steep=true
915
			swap dword[coord_x0],dword[coord_y0] ;swap(x0, y0);
916
			swap dword[coord_x1],dword[coord_y1] ;swap(x1, y1);
917
		@@:
918
		mov eax,dword[coord_y0] ;x0
919
		cmp eax,dword[coord_y1] ;if(x0>x1)
920
		jle @f
921
			swap dword[coord_y0],dword[coord_y1] ;swap(x0, x1);
922
			swap dword[coord_x0],dword[coord_x1] ;swap(y0, y1);
923
		@@:
924
 
925
; int deltax esi
926
; int deltay edi
927
; int error  ebp-6
928
; int ystep  ebp-8
929
 
930
		mov eax,dword[coord_y0]
931
		mov esi,dword[coord_y1]
932
		sub esi,eax ;deltax = y1-y0
933
		mov ebx,esi
934
		shr ebx,1
935
		mov [loc_1],ebx ;error = deltax/2
936
 
937
		mov eax,dword[coord_x0]
938
		mov edi,dword[coord_x1]
939
		mov [loc_2],dword -1 ;ystep = -1
940
		cmp eax,edi ;if (x0
941
		jge @f
942
			mov [loc_2],dword 1 ;ystep = 1
943
		@@:
944
		sub edi,eax ;x1-x0
945
 
946
		bts edi,31
947
		jae @f
948
			neg edi
949
			inc edi
950
		@@:
951
		and edi,0x7fffffff ;deltay = abs(x1-x0)
952
 
953
		mov eax,edi
954
		mov edi,[buf_struc]
955
		cmp buf2d_bits,24
956
		jne .coord_end
957
 
958
		cmp [napravl],0
959
		jne .coord_yx
960
			mov ebx,dword[coord_x0]
961
			mov ecx,dword[coord_y0]
962
 
963
			@@: ;for (x=x0 ; x
964
				cmp ecx,dword[coord_y1]
965
				jg @f ;jge ???
966
				call draw_pixel
967
 
968
				sub dword[loc_1],eax ;error -= deltay
969
				cmp dword[loc_1],0 ;if(error<0)
970
				jge .if0
971
					add ebx,[loc_2] ;y += ystep
972
					add [loc_1],esi ;error += deltax
973
				.if0:
974
				inc ecx
975
				jmp @b
976
			@@:
977
			jmp .coord_end
978
		.coord_yx:
979
			mov ebx,dword[coord_y0]
980
			mov ecx,dword[coord_x0]
981
 
982
			@@: ;for (x=x0 ; x
983
				cmp ebx,dword[coord_y1]
984
				jg @f ;jge ???
985
				call draw_pixel
986
 
987
				sub dword[loc_1],eax ;error -= deltay
988
				cmp dword[loc_1],0 ;if(error<0)
989
				jge .if1
990
					add ecx,[loc_2] ;y += ystep
991
					add [loc_1],esi ;error += deltax
992
				.if1:
993
				inc ebx
994
				jmp @b
995
			@@:
996
	.coord_end:
997
	popad
998
	ret
999
endp
1000
 
1653 IgorA 1001
;рисование горизонтальной линии, потому нет параметра coord_y1
1535 IgorA 1002
align 4
1634 IgorA 1003
proc buf_line_h, buf_struc:dword, coord_x0:dword, coord_y0:dword, coord_x1:dword, color:dword
1004
	pushad
1005
		mov edx,dword[color]
1006
 
1007
		mov eax,edi
1008
		mov edi,[buf_struc]
1009
		cmp buf2d_bits,24
1010
		jne @f
1011
 
1012
		mov ebx,dword[coord_x0]
1013
		mov ecx,dword[coord_y0]
1014
		mov esi,dword[coord_x1]
1015
 
1016
		@@: ;for (x=x0 ; x
1017
			call draw_pixel
1018
			inc ebx
1019
			cmp ebx,esi
1020
			jge @f
1021
			jmp @b
1022
		@@:
1023
	popad
1024
	ret
1025
endp
1026
 
1027
align 4
1028
proc buf_rect_by_size, buf_struc:dword, coord_x:dword,coord_y:dword,w:dword,h:dword, color:dword
1029
pushad
1030
	mov edi,[buf_struc]
1031
	cmp buf2d_bits,24
1032
	jne .coord_end
1033
 
1034
		mov eax,[coord_x]
1035
		mov ebx,[coord_y]
1036
		mov ecx,[w]
1642 IgorA 1037
		cmp ecx,1
1038
		jl .coord_end
1634 IgorA 1039
		add ecx,eax
1642 IgorA 1040
		dec ecx
1634 IgorA 1041
		mov edx,[h]
1642 IgorA 1042
		cmp edx,1
1043
		jl .coord_end
1044
 
1634 IgorA 1045
		add edx,ebx
1642 IgorA 1046
		dec edx
1634 IgorA 1047
		mov esi,dword[color]
1048
		stdcall buf_line_h, edi, eax, ebx, ecx, esi ;линия -
1049
		stdcall buf_line_brs, edi, eax, ebx, eax, edx, esi ;линия |
1050
		stdcall buf_line_h, edi, eax, edx, ecx, esi ;линия -
1051
		stdcall buf_line_brs, edi, ecx, ebx, ecx, edx, esi ;линия |
1052
	.coord_end:
1053
popad
1054
	ret
1055
endp
1056
 
1057
align 4
1642 IgorA 1058
proc buf_filled_rect_by_size, buf_struc:dword, coord_x:dword,coord_y:dword,w:dword,h:dword, color:dword
1059
pushad
1060
	mov edi,[buf_struc]
1061
	cmp buf2d_bits,24
1062
	jne .coord_end
1063
		mov eax,[coord_x]
1064
		mov ebx,[coord_y]
1065
		mov edx,[w]
1066
		add edx,eax
1067
		mov ecx,[h]
1068
		mov esi,dword[color]
1069
		cld
1070
		@@:
1071
			stdcall buf_line_h, edi, eax, ebx, edx, esi ;линия -
1072
			inc ebx
1073
			loop @b
1074
	.coord_end:
1075
popad
1076
	ret
1077
endp
1078
 
1079
align 4
1535 IgorA 1080
proc buf_circle, buf_struc:dword, coord_x:dword, coord_y:dword, r:dword, color:dword
1081
locals
1082
	po_x dd ?
1083
	po_y dd ?
1084
endl
1085
	pushad
1086
	mov edi,dword[buf_struc]
1087
	cmp buf2d_bits,24
1088
	jne .error
1089
		mov edx,dword[color]
1090
 
1091
		finit
1092
		fild dword[coord_x]
1093
		fild dword[coord_y]
1094
		fild dword[r]
1095
		fldz ;px=0
1096
		fld st1 ;py=r
1097
 
1098
		fldpi
1099
		fmul st0,st3
1100
		fistp dword[po_x]
1101
		mov esi,dword[po_x] ;esi=pi*r
1102
		shl esi,1 ;esi=2*pi*r
1103
 
1104
		;st0 = py
1105
		;st1 = px
1106
		;st2 = r
1107
		;st3 = y
1108
		;st4 = x
1109
 
1110
		@@:
1111
			;Point(px + x, y - py)
1112
			fld st1 ;st0=px
1113
			fadd st0,st5 ;st0=px+x
1114
			fistp dword[po_x]
1115
			mov ebx,dword[po_x]
1116
			fld st3 ;st0=y
1117
			fsub st0,st1 ;st0=y-py
1118
			fistp dword[po_y]
1119
			mov ecx,dword[po_y]
1120
			call draw_pixel
1121
			;px += py/r
1122
			fld st0 ;st0=py
1123
			fdiv st0,st3 ;st0=py/r
1124
			faddp st2,st0 ;st3+=st0
1125
			;py -= px/r
1126
			fld st1 ;st0=px
1127
			fdiv st0,st3 ;st0=px/r
1128
			fsubp st1,st0 ;st2-=st0
1129
 
1130
			dec esi
1131
			cmp esi,0
1132
			jge @b
1133
		jmp .exit_fun
1134
	.error:
1135
		stdcall print_err,sz_buf2d_circle,txt_err_n24b
1136
	.exit_fun:
1137
 
1138
	popad
1139
	ret
1140
endp
1141
 
1142
align 4
1143
proc buf_img_wdiv2, buf_struc:dword
1144
	pushad
1145
	mov edi,dword[buf_struc]
1146
	cmp buf2d_bits,24
1147
	jne .end_draw_24
1148
		mov eax,buf2d_w
1149
		mov ecx,buf2d_h
1150
		imul ecx,eax
1151
		stdcall img_rgb24_wdiv2, buf2d_data,ecx
1152
	.end_draw_24:
1153
	popad
1154
	ret
1155
endp
1156
 
1157
;input:
1158
;data_rgb - pointer to rgb data
1159
;size - count img pixels (size img data / 3(rgb) )
1160
align 4
1161
proc img_rgb24_wdiv2 data_rgb:dword, size:dword
1162
  ;push eax ebx ecx edx
1163
  mov eax,dword[data_rgb]
1164
  mov ecx,dword[size] ;ecx = size
1165
  lea ecx,[ecx+ecx*2]
1166
  cld
1167
  @@: ;затемнение цвета пикселей
1538 IgorA 1168
		shr byte[eax],1
1169
		inc eax
1170
		loop @b
1535 IgorA 1171
 
1172
  mov eax,dword[data_rgb]
1173
  mov ecx,dword[size] ;ecx = size
1174
  shr ecx,1
1175
  @@: ;сложение цветов пикселей
1538 IgorA 1176
		mov bx,word[eax+3] ;копируем цвет соседнего пикселя
1177
		add word[eax],bx
1178
		mov bl,byte[eax+5] ;копируем цвет соседнего пикселя
1179
		add byte[eax+2],bl
1180
		add eax,6 ;=2*3
1181
		loop @b
1535 IgorA 1182
 
1183
  mov eax,dword[data_rgb]
1184
  add eax,3
1185
  mov ebx,eax
1186
  add ebx,3
1187
  mov ecx,dword[size] ;ecx = size
1188
  shr ecx,1
1189
  dec ecx ;лишний пиксель
1190
  @@: ;поджатие пикселей
1538 IgorA 1191
		mov edx,dword[ebx]
1192
		mov word[eax],dx
1193
		shr edx,16
1194
		mov byte[eax+2],dl
1535 IgorA 1195
 
1538 IgorA 1196
		add eax,3
1197
		add ebx,6
1198
		loop @b
1535 IgorA 1199
  ;pop edx ecx ebx eax
1200
  ret
1201
endp
1202
 
1203
align 4
1204
proc buf_img_hdiv2, buf_struc:dword
1205
	pushad
1206
	mov edi,dword[buf_struc]
1207
	cmp buf2d_bits,24
1208
	jne .end_draw_24
1209
		mov eax,buf2d_w
1210
		mov ecx,buf2d_h
1211
		imul ecx,eax
1212
		stdcall img_rgb24_hdiv2, buf2d_data,ecx,eax
1213
	.end_draw_24:
1214
	popad
1215
	ret
1216
endp
1217
 
1218
;input:
1219
;data_rgb - pointer to rgb data
1220
;size - count img pixels (size img data / 3(rgb) )
1221
;size_w - width img in pixels
1222
align 4
1223
proc img_rgb24_hdiv2, data_rgb:dword, size:dword, size_w:dword
1224
  ;pushad
1225
 
1226
  mov eax,dword[data_rgb] ;eax =
1227
  mov ecx,dword[size]	  ;ecx = size
1228
  lea ecx,[ecx+ecx*2]
1229
  cld
1230
  @@: ;затемнение цвета пикселей
1231
    shr byte[eax],1
1232
    inc eax
1233
    loop @b
1234
 
1235
  mov eax,dword[data_rgb] ;eax =
1236
  mov edi,dword[size_w]
1237
  lea esi,[edi+edi*2] ;esi = width*3(rgb)
1238
  mov ebx,esi
1239
  add ebx,eax
1240
  mov ecx,dword[size]  ;ecx = size
1241
  shr ecx,1
1242
  xor edi,edi
1243
  @@: ;сложение цветов пикселей
1244
    mov dx,word[ebx] ;копируем цвет нижнего пикселя
1245
    add word[eax],dx
1246
    mov dl,byte[ebx+2] ;копируем цвет нижнего пикселя
1247
    add byte[eax+2],dl
1248
 
1249
    add eax,3
1250
    add ebx,3
1251
    inc edi
1252
    cmp edi,dword[size_w]
1253
    jl .old_line
1254
      add eax,esi
1255
      add ebx,esi
1256
      xor edi,edi
1257
    .old_line:
1258
    loop @b
1259
 
1260
 
1261
  mov eax,dword[data_rgb] ;eax =
1262
  add eax,esi ;esi = width*3(rgb)
1263
  mov ebx,esi
1264
  add ebx,eax
1265
  mov ecx,dword[size] ;ecx = size
1266
  shr ecx,1
1267
  sub ecx,dword[size_w] ;лишняя строка пикселей
1268
  xor edi,edi
1269
  @@: ;поджатие пикселей
1270
    mov edx,dword[ebx] ;копируем цвет нижнего пикселя
1271
    mov word[eax],dx
1272
    shr edx,16
1273
    mov byte[eax+2],dl
1274
 
1275
    add eax,3
1276
    add ebx,3
1277
    inc edi
1278
    cmp edi,dword[size_w]
1279
    jl .old_line_2
1280
      add ebx,esi
1281
      xor edi,edi
1282
    .old_line_2:
1283
    loop @b
1284
 
1285
  ;popad
1286
  ret
1287
endp
1288
 
1289
;преобразование буфера из 24-битного в 8-битный
1290
; spectr - определяет какой спектр брать при преобразовании 0-синий, 1-зеленый, 2-красный
1291
align 4
1292
proc buf_conv_24_to_8, buf_struc:dword, spectr:dword
1293
	pushad
1294
	mov edi,dword[buf_struc]
1295
	cmp buf2d_bits,24
1296
	jne .error
1297
		mov eax,buf2d_w
1298
		mov ecx,buf2d_h
1299
		imul ecx,eax
1300
		mov esi,ecx
1301
		;ebx - память из которой копируется
1302
		;edx - память куда копируется
1303
		mov edx,buf2d_data
1304
		mov ebx,edx
1305
		cmp [spectr],3
1306
		jge @f
1307
			add ebx,[spectr]
1308
		@@:
1309
			mov al,byte[ebx]
1310
			mov byte[edx],al
1311
			add ebx,3
1312
			inc edx
1313
			loop @b
1314
		mov buf2d_bits,8
1315
		invoke mem.realloc,buf2d_data,esi ;уменьшаем память занимаемую буфером
1316
		jmp .end_conv
1317
	.error:
1318
		stdcall print_err,sz_buf2d_conv_24_to_8,txt_err_n24b
1319
	.end_conv:
1320
	popad
1321
	ret
1322
endp
1323
 
1324
;преобразование буфера из 24-битного в 32-битный
1325
align 4
1326
proc buf_conv_24_to_32, buf_struc:dword, buf_str8:dword
1327
	pushad
1328
	mov edi,dword[buf_struc]
1329
	cmp buf2d_bits,24
1330
	jne .error1
1331
		mov ecx,buf2d_w
1332
		mov ebx,buf2d_h
1333
		imul ebx,ecx
1334
		mov ecx,ebx ;ecx = size  8 b
1335
		shl ebx,2   ;ebx = size 32 b
1336
		invoke mem.realloc,buf2d_data,ebx ;увеличиваем память занимаемую буфером
1337
		mov buf2d_data,eax ;на случай если изменился указатель на данные
1338
		mov buf2d_bits,32
1339
		mov edx,ebx ;edx = size 32 b
1340
		sub ebx,ecx ;ebx = size 24 b
1341
		mov eax,ecx
1342
		;eax - размер  8 битных данных
1343
		;ebx - размер 24 битных данных
1344
		;edx - размер 32 битных данных
1345
		add ebx,buf2d_data
1346
		add edx,buf2d_data
1347
		mov edi,dword[buf_str8]
1348
		cmp buf2d_bits,8
1349
		jne .error2
1350
		add eax,buf2d_data
1351
		mov edi,edx
1352
		;eax - указатель на конец  8 битных данных
1353
		;ebx - указатель на конец 24 битных данных
1354
		;edi - указатель на конец 32 битных данных
1355
		@@:
1356
			sub edi,4 ;отнимаем в начале цикла,
1357
			sub ebx,3 ; потому, что указатели стоят
1358
			dec eax   ; за пределами буферов
1359
			mov edx,dword[ebx]
1360
			mov dword[edi],edx
1361
			mov dl,byte[eax]
1362
			mov byte[edi+3],dl
1363
			loop @b
1364
 
1365
		jmp .end_conv
1366
	.error1:
1367
		stdcall print_err,sz_buf2d_conv_24_to_32,txt_err_n24b
1368
		jmp .end_conv
1369
	.error2:
1370
		stdcall print_err,sz_buf2d_conv_24_to_32,txt_err_n8b
1371
	.end_conv:
1372
	popad
1373
	ret
1374
endp
1375
 
1376
;функция копирует изображение из буфера buf_source (24b|32b) в buf_destination (24b)
1377
; указываются координаты вставки буфера buf_source относительно buf_destination
1378
; прозрачность при копировании не учитывается
1379
align 4
1380
proc buf_bit_blt, buf_destination:dword, coord_x:dword, coord_y:dword, buf_source:dword
1381
	locals
1382
		right_bytes dd ?
1383
	endl
1384
	pushad
1385
 
1386
	mov edi,[buf_source]
1387
	cmp buf2d_bits,24
1388
	je .sou24
1389
	cmp buf2d_bits,32
1390
	je .sou32
1391
		jmp .copy_end ;формат буфера не поодерживается
1392
 
1648 IgorA 1393
	.sou24: ;в источнике 24 битная картинка
1535 IgorA 1394
	mov eax,buf2d_w
1395
	mov edx,buf2d_h ;высота копируемой картинки
1396
	mov esi,buf2d_data ;данные копируемой картинки
1397
 
1398
	mov edi,[buf_destination]
1399
	cmp buf2d_bits,24
1400
	jne .copy_end ;формат буфера не поодерживается
1648 IgorA 1401
	mov ebx,[coord_x] ;в ebx временно ставим отступ изображения (для проверки)
1402
	cmp ebx,buf2d_w   ;проверяем влазит ли изображение по ширине
1403
	jge .copy_end     ;если изображение полностью вылазит за правую сторону
1535 IgorA 1404
		mov ebx,buf2d_h ;ebx - высота основного буфера
1405
		mov ecx,[coord_y]
1406
		cmp ecx,ebx
1407
		jge .copy_end ;если координата 'y' больше высоты буфера
1408
		add ecx,edx ;ecx - нижняя координата копируемой картинки
1409
		cmp ecx,ebx
1410
		jle @f
1411
			sub ecx,ebx
1412
			sub edx,ecx ;уменьшаем высоту копируемой картинки, в случе когда она вылазит за нижнюю границу
1413
		@@:
1414
		mov ebx,buf2d_w
1415
		mov ecx,ebx ;ecx используем для временных целей
1416
		imul ecx,[coord_y]
1417
		add ecx,[coord_x]
1418
		lea ecx,[ecx+ecx*2]
1419
		add ecx,buf2d_data
1420
		sub ebx,eax
1421
		mov edi,ecx ;edi указатель на данные буфера, куда будет производится копирование
1422
 
1423
	mov [right_bytes],0
1424
	mov ecx,[coord_x]
1425
	cmp ecx,ebx
1426
	jl @f
1427
		sub ecx,ebx
1428
		sub eax,ecx ;укорачиваем копируемую строку
1429
		add ebx,ecx ;удлинняем строку для сдвига главной картинки буфера
1430
		lea ecx,[ecx+ecx*2] ;ecx - число байт в 1-й строке картинки, которые вылазят за правую сторону
1431
		mov [right_bytes],ecx
1432
	@@:
1433
 
1434
	lea eax,[eax+eax*2] ;колличество байт в 1-й строке копируемой картинки
1435
	lea ebx,[ebx+ebx*2] ;колличество байт в 1-й строке буфера минус число байт в 1-й строке копируемой картинки
1436
 
1437
	cld
1438
	cmp [right_bytes],0
1439
	jg .copy_1
1440
	.copy_0: ;простое копирование
1441
		mov ecx,eax
1442
		rep movsb
1443
		add edi,ebx
1444
		dec edx
1445
		cmp edx,0
1446
		jg .copy_0
1447
	jmp .copy_end
1448
	.copy_1: ;не простое копирование (картинка вылазит за правую сторону)
1449
		mov ecx,eax
1450
		rep movsb
1451
		add edi,ebx
1452
		add esi,[right_bytes] ;добавляем байты, которые вылазят за правую границу
1453
		dec edx
1454
		cmp edx,0
1455
		jg .copy_1
1456
	jmp .copy_end
1457
 
1458
	.sou32: ;в источнике 32 битная картинка
1459
	mov eax,buf2d_w
1460
	mov edx,buf2d_h ;высота копируемой картинки
1461
	mov esi,buf2d_data ;данные копируемой картинки
1462
 
1463
	mov edi,[buf_destination]
1464
	cmp buf2d_bits,24
1465
	jne .copy_end ;формат буфера не поодерживается
1648 IgorA 1466
	mov ebx,[coord_x] ;в ebx временно ставим отступ изображения (для проверки)
1467
	cmp ebx,buf2d_w   ;проверяем влазит ли изображение по ширине
1468
	jge .copy_end     ;если изображение полностью вылазит за правую сторону
1535 IgorA 1469
		mov ebx,buf2d_h ;ebx - высота основного буфера
1470
		mov ecx,[coord_y]
1471
		cmp ecx,ebx
1472
		jge .copy_end ;если координата 'y' больше высоты буфера
1473
		add ecx,edx ;ecx - нижняя координата копируемой картинки
1474
		cmp ecx,ebx
1475
		jle @f
1476
			sub ecx,ebx
1477
			sub edx,ecx ;уменьшаем высоту копируемой картинки, в случе когда она вылазит за нижнюю границу
1478
		@@:
1479
		mov ebx,buf2d_w
1480
		mov ecx,ebx ;ecx используем для временных целей
1481
		imul ecx,[coord_y]
1482
		add ecx,[coord_x]
1483
		lea ecx,[ecx+ecx*2]
1484
		add ecx,buf2d_data
1485
		sub ebx,eax
1486
		mov edi,ecx ;edi указатель на данные буфера, куда будет производится копирование
1487
 
1488
	mov [right_bytes],0
1489
	mov ecx,[coord_x]
1490
	cmp ecx,ebx
1491
	jl @f
1492
		sub ecx,ebx
1493
		sub eax,ecx ;укорачиваем копируемую строку
1494
		add ebx,ecx ;удлинняем строку для сдвига главной картинки буфера
1495
		shl ecx,2 ;ecx - число байт в 1-й строке картинки, которые вылазят за правую сторону
1496
		mov [right_bytes],ecx
1497
	@@:
1498
 
1499
	;eax - колличество пикселей в 1-й строке копируемой картинки
1500
	lea ebx,[ebx+ebx*2] ;колличество байт в 1-й строке буфера минус число байт в 1-й строке копируемой картинки
1501
 
1502
	cld
1503
	cmp [right_bytes],0
1504
	jg .copy_3
1505
	.copy_2: ;простое копирование
1506
		mov ecx,eax
1507
		@@:
1508
			movsw
1509
			movsb
1510
			inc esi
1511
			loop @b
1512
		add edi,ebx
1513
		dec edx
1514
		cmp edx,0
1515
		jg .copy_2
1516
	jmp .copy_end
1517
	.copy_3: ;не простое копирование (картинка вылазит за правую сторону)
1518
		mov ecx,eax
1519
		@@:
1520
			movsw
1521
			movsb
1522
			inc esi
1523
			loop @b
1524
		add edi,ebx
1525
		add esi,[right_bytes] ;добавляем байты, которые вылазят за правую границу
1526
		dec edx
1527
		cmp edx,0
1528
		jg .copy_3
1529
 
1530
	.copy_end:
1531
	popad
1532
	ret
1533
endp
1534
 
1535
;input:
1536
; esi = pointer to color1 + transparent
1537
; edi = pointer to background color2
1538
;output:
1539
; [edi] = combine color
1540
align 4
1541
combine_colors:
1542
	push ax bx cx dx
1543
	mov bx,0x00ff ;---get transparent---
1544
	mov cl,byte[esi+3] ;pro
1545
	xor ch,ch
1546
	sub bx,cx ;256-pro
1653 IgorA 1547
	;---blye---
1535 IgorA 1548
	xor ah,ah
1653 IgorA 1549
	mov al,byte[esi]
1535 IgorA 1550
	imul ax,bx
1551
	xor dh,dh
1653 IgorA 1552
	mov dl,byte[edi]
1535 IgorA 1553
	imul dx,cx
1554
	add ax,dx
1653 IgorA 1555
	mov byte[edi],ah
1535 IgorA 1556
	;---green---
1557
	xor ah,ah
1558
	mov al,byte[esi+1]
1559
	imul ax,bx
1560
	xor dh,dh
1561
	mov dl,byte[edi+1]
1562
	imul dx,cx
1563
	add ax,dx
1564
	mov byte[edi+1],ah
1653 IgorA 1565
	;---red---
1535 IgorA 1566
	xor ah,ah
1653 IgorA 1567
	mov al,byte[esi+2]
1535 IgorA 1568
	imul ax,bx
1569
	xor dh,dh
1653 IgorA 1570
	mov dl,byte[edi+2]
1535 IgorA 1571
	imul dx,cx
1572
	add ax,dx
1653 IgorA 1573
	mov byte[edi+2],ah
1535 IgorA 1574
 
1575
	pop dx cx bx ax
1576
	ret
1577
 
1578
;функция копирует изображение из буфера buf_source (32b) в buf_destination (24b)
1579
; указываются координаты вставки буфера buf_source относительно buf_destination
1580
; при копировании учитывается прозрачность
1581
align 4
1582
proc buf_bit_blt_transp, buf_destination:dword, coord_x:dword, coord_y:dword, buf_source:dword
1583
	locals
1584
		right_bytes dd ?
1585
	endl
1586
	pushad
1587
 
1588
	mov edi,[buf_source]
1589
	cmp buf2d_bits,32
1590
	jne .copy_end ;формат буфера не поодерживается
1591
	mov eax,buf2d_w
1592
	mov edx,buf2d_h ;высота копируемой картинки
1593
	mov esi,buf2d_data ;данные копируемой картинки
1594
 
1595
	mov edi,[buf_destination]
1596
	cmp buf2d_bits,24
1597
	jne .copy_end ;формат буфера не поодерживается
1598
		mov ebx,buf2d_h ;ebx - высота основного буфера
1599
		mov ecx,[coord_y]
1600
		cmp ecx,ebx
1601
		jge .copy_end ;если координата 'y' больше высоты буфера
1602
		add ecx,edx ;ecx - нижняя координата копируемой картинки
1603
		cmp ecx,ebx
1604
		jle @f
1605
			sub ecx,ebx
1606
			sub edx,ecx ;уменьшаем высоту копируемой картинки, в случе когда она вылазит за нижнюю границу
1607
		@@:
1608
		mov ebx,buf2d_w
1609
		mov ecx,ebx ;ecx используем для временных целей
1610
		imul ecx,[coord_y]
1611
		add ecx,[coord_x]
1612
		lea ecx,[ecx+ecx*2]
1613
		add ecx,buf2d_data
1614
		sub ebx,eax
1615
		mov edi,ecx ;edi указатель на данные буфера, куда будет производится копирование
1616
 
1617
	mov [right_bytes],0
1618
	mov ecx,[coord_x]
1619
	cmp ecx,ebx
1620
	jl @f
1621
		sub ecx,ebx
1622
		sub eax,ecx ;укорачиваем копируемую строку
1623
		add ebx,ecx ;удлинняем строку для сдвига главной картинки буфера
1624
		shl ecx,2 ;ecx - число байт в 1-й строке картинки, которые вылазят за правую сторону
1625
		mov [right_bytes],ecx
1626
	@@:
1627
 
1628
	lea ebx,[ebx+ebx*2] ;колличество байт в 1-й строке буфера минус число байт в 1-й строке копируемой картинки
1629
 
1630
	cld
1631
	cmp [right_bytes],0
1632
	jg .copy_1
1633
	.copy_0: ;простое копирование
1634
		mov ecx,eax
1635
		@@:
1636
			call combine_colors
1637
			add edi,3
1638
			add esi,4
1639
			loop @b
1640
		add edi,ebx
1641
		dec edx
1642
		cmp edx,0
1643
		jg .copy_0
1644
	jmp .copy_end
1645
	.copy_1: ;не простое копирование (картинка вылазит за правую сторону)
1646
		mov ecx,eax
1647
		@@:
1648
			call combine_colors
1649
			add edi,3
1650
			add esi,4
1651
			loop @b
1652
		add edi,ebx
1653
		add esi,[right_bytes] ;добавляем байты, которые вылазят за правую границу
1654
		dec edx
1655
		cmp edx,0
1656
		jg .copy_1
1657
 
1658
	.copy_end:
1659
	popad
1660
	ret
1661
endp
1662
 
1663
;input:
1664
; ebx - color1
1665
; esi = pointer to transparent
1666
; edi = pointer to background color2
1667
;output:
1668
; [edi] = combine color
1669
align 4
1670
combine_colors_2:
1671
	push ax ebx cx dx si
1672
	mov cl,byte[esi] ;pro
1673
	xor ch,ch
1674
	mov si,0x00ff ;---get transparent---
1675
	sub si,cx ;256-pro
1676
 
1653 IgorA 1677
		;---blye---
1535 IgorA 1678
		mov al,bl
1679
		xor ah,ah
1680
		shr ebx,8
1681
		imul ax,si
1682
		xor dh,dh
1653 IgorA 1683
		mov dl,byte[edi]
1535 IgorA 1684
		imul dx,cx
1685
		add ax,dx
1653 IgorA 1686
		mov byte[edi],ah
1535 IgorA 1687
		;---green---
1688
		mov al,bl
1689
		xor ah,ah
1690
		shr ebx,8
1691
		imul ax,si
1692
		xor dh,dh
1693
		mov dl,byte[edi+1]
1694
		imul dx,cx
1695
		add ax,dx
1696
		mov byte[edi+1],ah
1697
		;---red---
1698
		mov al,bl
1699
		xor ah,ah
1700
		imul ax,si
1701
		xor dh,dh
1653 IgorA 1702
		mov dl,byte[edi+2]
1535 IgorA 1703
		imul dx,cx
1704
		add ax,dx
1653 IgorA 1705
		mov byte[edi+2],ah
1535 IgorA 1706
 
1707
	pop si dx cx ebx ax
1708
	ret
1709
 
1710
;функция копирует изображение из буфера buf_source (8b) в buf_destination (24b)
1711
; указываются координаты вставки буфера buf_source относительно buf_destination
1712
align 4
1713
proc buf_bit_blt_alpha, buf_destination:dword, coord_x:dword, coord_y:dword, buf_source:dword, color:dword
1714
	locals
1715
		right_bytes dd ?
1716
		dest_w_bytes dd ? ;колличество байт в буфере приемнике по ширине - ширина вставляемой картинки
1717
	endl
1718
	pushad
1719
 
1720
	mov edi,[buf_source]
1721
	cmp buf2d_bits,8
1722
	jne .error1 ;формат буфера не поодерживается
1723
	mov eax,buf2d_w
1724
	mov edx,buf2d_h ;высота копируемой картинки
1725
	mov esi,buf2d_data ;данные копируемой картинки
1726
 
1727
	mov edi,[buf_destination]
1728
	cmp buf2d_bits,24
1729
	jne .error2 ;формат буфера не поодерживается
1642 IgorA 1730
	mov ebx,[coord_x] ;в ebx временно ставим отступ изображения (для проверки)
1731
	cmp ebx,buf2d_w   ;проверяем влазит ли изображение по ширине
1732
	jge .copy_end     ;если изображение полностью вылазит за правую сторону
1535 IgorA 1733
		mov ebx,buf2d_h ;ebx - высота основного буфера
1734
		mov ecx,[coord_y]
1735
		cmp ecx,ebx
1736
		jge .copy_end ;если координата 'y' больше высоты буфера
1737
		add ecx,edx ;ecx - нижняя координата копируемой картинки
1738
		cmp ecx,ebx
1739
		jle @f
1740
			sub ecx,ebx
1741
			sub edx,ecx ;уменьшаем высоту копируемой картинки, в случе когда она вылазит за нижнюю границу
1742
		@@:
1743
		mov ebx,buf2d_w
1744
		mov ecx,ebx ;ecx используем для временных целей
1745
		imul ecx,[coord_y]
1746
		add ecx,[coord_x]
1747
		lea ecx,[ecx+ecx*2]
1748
		add ecx,buf2d_data
1749
		sub ebx,eax
1750
		mov edi,ecx ;edi указатель на данные буфера, куда будет производится копирование
1751
 
1752
	mov [right_bytes],0
1753
	mov ecx,[coord_x]
1754
	cmp ecx,ebx
1755
	jl @f
1756
		sub ecx,ebx
1757
		sub eax,ecx ;укорачиваем копируемую строку
1758
		add ebx,ecx ;удлинняем строку для сдвига главной картинки буфера
1759
		;ecx - число пикселей в 1-й строке картинки, которые вылазят за правую сторону
1760
		mov [right_bytes],ecx
1761
	@@:
1762
 
1763
	lea ebx,[ebx+ebx*2] ;колличество байт в 1-й строке буфера минус число байт в 1-й строке копируемой картинки
1764
	mov [dest_w_bytes],ebx
1765
	mov ebx,[color]
1766
 
1767
	cld
1768
	cmp [right_bytes],0
1769
	jg .copy_1
1770
	.copy_0: ;простое копирование
1771
		mov ecx,eax
1772
		@@:
1773
			call combine_colors_2
1774
			add edi,3
1775
			inc esi
1776
			loop @b
1777
		add edi,[dest_w_bytes]
1778
		dec edx
1779
		cmp edx,0
1780
		jg .copy_0
1781
	jmp .copy_end
1782
	.copy_1: ;не простое копирование (картинка вылазит за правую сторону)
1783
		mov ecx,eax
1784
		@@:
1785
			call combine_colors_2
1786
			add edi,3
1787
			inc esi
1788
			loop @b
1789
		add edi,[dest_w_bytes]
1790
		add esi,[right_bytes] ;добавляем байты, которые вылазят за правую границу
1791
		dec edx
1792
		cmp edx,0
1793
		jg .copy_1
1794
 
1795
	jmp .copy_end
1796
	.error1:
1797
		stdcall print_err,sz_buf2d_bit_blt_alpha,txt_err_n8b
1798
		jmp .copy_end
1799
	.error2:
1800
		stdcall print_err,sz_buf2d_bit_blt_alpha,txt_err_n24b
1801
	.copy_end:
1802
	popad
1803
	ret
1804
endp
1805
 
1806
;преобразование 8-битного буфера размером 16*16 в размер 1*256 символов
1807
align 4
1808
proc buf_convert_text_matrix, buf_struc:dword
1809
	locals
1810
		tmp_mem dd ?
1811
		c1 dw ?
1812
		c2 dd ?
1813
		c3 dw ?
1814
	endl
1815
	pushad
1816
	mov edi,dword[buf_struc]
1817
	cmp buf2d_bits,8
1818
	jne .error
1819
		mov ecx,buf2d_h
1820
		mov ebx,ecx
1821
		shr ebx,4 ;предполагаем что в буфере 16 строк с символами, потому делим на 2^4
1822
		mov edx,buf2d_w
1823
		imul ecx,edx ;ecx = size  8 b
1824
		invoke mem.alloc,ecx ;выделяем временную память
1825
		mov [tmp_mem],eax ;eax - new memory
1826
 
1827
		shr edx,4 ;предполагаем что в буфере 16 колонок с символами, потому делим на 2^4
1828
		mov eax,ebx
1829
		imul ebx,edx ;вычисляем кооличество пикселей на 1 символ
1830
		;eax = bhe - высота буквы
1831
		;ebx = bwi*bhe - колличество пикселей в 1-й букве
1832
		;edx = bwi - ширина буквы
1833
		;ecx,esi,edi - используются в цикле .c_0
1834
		shr buf2d_w,4
1835
		shl buf2d_h,4 ;преобразовываем размеры буфера
1836
 
1837
		cld
1838
		mov esi,buf2d_data
1839
		mov edi,[tmp_mem]
1840
		mov word[c3],16
1841
		.c_3:
1842
			mov dword[c2],eax
1843
			.c_2:
1844
				mov word[c1],16
1845
				.c_1:
1846
					mov ecx,edx ;.c_0:
1847
					rep movsb
1848
					add edi,ebx
1849
					sub edi,edx ;edi+=(bwi*bhe-bwi)
1850
					dec word[c1]
1851
					cmp word[c1],0
1852
					jg .c_1
1853
				add edi,edx
1854
				shl ebx,4
1855
				sub edi,ebx ;edi-=(16*bwi*bhe-bwi)
1856
				shr ebx,4
1857
				dec dword[c2]
1858
				cmp dword[c2],0
1859
				jg .c_2
1860
			sub edi,ebx
1861
			shl ebx,4
1862
			add edi,ebx ;edi+=(15*bwi*bhe)
1863
			shr ebx,4
1864
			dec word[c3]
1865
			cmp word[c3],0
1866
			jg .c_3
1867
 
1868
		mov edi,dword[buf_struc] ;копирование новой матрицы в основной буфер
1869
		mov edi,buf2d_data
1870
		mov esi,[tmp_mem]
1871
		mov ecx,ebx
1872
		shl ecx,8
1873
		rep movsb
1874
		invoke mem.free,[tmp_mem] ;чистим временную память
1875
		jmp .end_conv
1876
	.error:
1877
		stdcall print_err,sz_buf2d_convert_text_matrix,txt_err_n8b
1878
	.end_conv:
1879
	popad
1880
	ret
1881
endp
1882
 
1883
align 4
1884
buf_s_matr buf_2d_header ? ;локальная матрица символа
1885
 
1886
align 4
1887
proc buf_draw_text, buf_struc:dword, buf_t_matr:dword, text:dword, coord_x:dword, coord_y:dword, color:dword
1888
	locals
1889
		buf_t_matr_offs dd ?
1890
	endl
1891
	pushad
1892
	mov edi,dword[buf_struc]
1893
	cmp buf2d_bits,24
1894
	jne .error2
1895
	mov edi,dword[buf_t_matr]
1896
	cmp buf2d_bits,8
1897
	jne .error1
1898
		mov edx,buf2d_data
1899
		mov [buf_t_matr_offs],edx
1900
		mov ecx,BUF_STRUCT_SIZE ;копируем структуру текстовой матрицы
1901
		mov esi,edi
1902
		lea edi,[buf_s_matr]
1903
		cld
1904
		rep movsb
1905
		lea edi,[buf_s_matr]
1906
		shr buf2d_h,8 ;делим высоту символьного буфера на 256, для нахождения высоты 1-го символа
1907
		mov ebx,buf2d_h ;берем высоту символа
1908
		mov ecx,buf2d_w ;берем ширину символа
1909
 
1910
		mov eax,[coord_x]
1911
		mov esi,[text]
1912
		cmp byte[esi],0
1913
		je .end_draw ;если пустая строка
1914
		@@:
1915
			xor edx,edx
1916
			mov dl,byte[esi] ;берем код символа
1917
			imul edx,ebx ;умножаем его на высоту символа
1918
			imul edx,ecx ;умножаем на ширину символа
1919
			add edx,[buf_t_matr_offs] ;прибавляем смещение 0-го символа, т. е. получается смещение выводимого символа
1920
			mov buf2d_data,edx ;в локальный буфер символа, ставим указатель на нужный символ из буфера buf_t_matr
1921
			stdcall buf_bit_blt_alpha, [buf_struc], eax,[coord_y], edi,[color]
1922
			add eax,ecx
1923
			.new_s:
1924
				inc esi
1925
				cmp byte[esi],13
1926
				jne .no_13
1927
					mov eax,[coord_x]
1928
					add [coord_y],ebx
1929
					jmp .new_s
1930
				.no_13:
1931
			cmp byte[esi],0
1932
			jne @b
1933
		jmp .end_draw
1934
	.error1:
1935
		stdcall print_err,sz_buf2d_draw_text,txt_err_n8b
1936
		jmp .end_draw
1937
	.error2:
1938
		stdcall print_err,sz_buf2d_draw_text,txt_err_n24b
1939
	.end_draw:
1940
	popad
1941
	ret
1942
endp
1943
 
1944
align 4
1945
proc print_err, fun:dword, mes:dword ;выводим сообщение об шибке на доску отладки
1946
	pushad
1947
	mov eax,63
1948
	mov ebx,1
1949
 
1950
	mov esi,[fun]
1951
	@@:
1952
		mov cl,byte[esi]
1953
		int 0x40
1954
		inc esi
1955
		cmp byte[esi],0
1956
		jne @b
1957
	mov cl,':'
1958
	int 0x40
1959
	mov cl,' '
1960
	int 0x40
1961
	mov esi,[mes]
1962
	@@:
1963
		mov cl,byte[esi]
1964
		int 0x40
1965
		inc esi
1966
		cmp byte[esi],0
1967
		jne @b
1968
	popad
1969
	ret
1970
endp
1971
 
1972
;input:
1973
; ebp+8  = p0
1974
; ebp+12 = p1
1975
align 4
1976
line_len4i:
1977
	push ebp
1978
	mov ebp,esp
1979
		finit
1980
		fild word [ebp+8]
1981
		fisub word [ebp+12]
1982
		fmul st0,st0 ;st0=x^2
1983
		fild word [ebp+10]
1984
		fisub word [ebp+14]
1985
		fmul st0,st0 ;st0=y^2
1986
		fadd st0,st1
1987
		fsqrt
1988
		fstp dword [ebp+12]
1989
	pop ebp
1990
	ret 4 ;8
1991
 
1992
align 4
1993
proc buf_cruve_bezier, buffer:dword, coord_p0:dword,coord_p1:dword,coord_p2:dword, color:dword
1994
	locals
1995
		delt_t dd ?
1996
		opr_param dd ?
1997
		v_poi_0 dd ?
1998
	endl
1999
	pushad
2000
 
2001
;float t, xt,yt;
2002
;for(t=.0;t<1.;t+=.005){
2003
;  xt=pow(1.-t,2)*x0+2*t*(1.-t)*x1+pow(t,2)*x2;
2004
;  yt=pow(1.-t,2)*y0+2*t*(1.-t)*y1+pow(t,2)*y2;
2005
;  dc.SetPixel(xt,yt,255L);
2006
;}
2007
 
2008
	mov edx,[color] ;set cruve color
2009
	mov edi,[buffer]
2010
	xor ebx,ebx
2011
	xor ecx,ecx
2012
 
2013
	finit
2014
 
2015
	; calculate delta t
2016
	stdcall line_len4i, dword[coord_p1],dword[coord_p0]
2017
	fadd dword[esp]
2018
	add esp,4 ;pop ...
2019
 
2020
	stdcall line_len4i, dword[coord_p2],dword[coord_p1]
2021
	fadd dword[esp]
2022
	add esp,4 ;pop ...
2023
 
2024
	fadd st0,st0 ; len*=2
2025
	ftst
2026
	fstsw ax
2027
 
2028
	fld1
2029
	sahf
2030
	jle @f ;избегаем деления на 0
2031
		fdiv st0,st1
2032
	@@:
2033
	fstp dword[delt_t]
2034
 
2035
	finit
2036
 
2037
	;fild word[coord_p2+2] ;y2
2038
	fild word[coord_p1+2] ;y1
2039
	fild word[coord_p0+2] ;y0
2040
	fild word[coord_p2] ;x2
2041
	fild word[coord_p1] ;x1
2042
	fild word[coord_p0] ;x0
2043
	fld dword[delt_t]
2044
	fldz ;t=.0
2045
 
2046
	@@:
2047
		fld1
2048
		fsub st0,st1 ;1.-t
2049
		fmul st0,st0 ;pow(1.-t,2)
2050
		fmul st0,st3 ;...*x0
2051
		fstp dword[opr_param]
2052
 
2053
		fld1
2054
		fsub st0,st1 ;1.-t
2055
		fmul st0,st1 ;(1.-t)*t
2056
		fadd st0,st0
2057
		fmul st0,st4 ;...*x1
2058
		mov esi,dword[opr_param]
2059
		fstp dword[opr_param]
2060
 
2061
		fldz
2062
		fadd st0,st1 ;0+t
2063
		fmul st0,st0 ;t*t
2064
		fmul st0,st5 ;...*x2
2065
 
2066
		fadd dword[opr_param]
2067
		mov dword[opr_param],esi
2068
		fadd dword[opr_param]
2069
		fistp word[v_poi_0] ;x
2070
 
2071
		fld1
2072
		fsub st0,st1 ;1.-t
2073
		fmul st0,st0 ;pow(1.-t,2)
2074
		fmul st0,st6 ;...*y0
2075
		fstp dword[opr_param]
2076
 
2077
		fld1
2078
		fsub st0,st1 ;1.-t
2079
		fmul st0,st1 ;(1.-t)*t
2080
		fadd st0,st0
2081
		fmul st0,st7 ;...*y1
2082
		mov esi,dword[opr_param]
2083
		fstp dword[opr_param]
2084
 
2085
		fldz
2086
		fadd st0,st1 ;0+t
2087
		fmul st0,st0 ;t*t
2088
		fimul word[coord_p2+2] ;...*y2
2089
 
2090
		fadd dword[opr_param]
2091
		mov dword[opr_param],esi
2092
		fadd dword[opr_param]
2093
		fistp word[v_poi_0+2] ;y
2094
 
2095
		mov eax,1
2096
		mov bx,word[v_poi_0+2]
2097
		mov cx,word[v_poi_0]
2098
		call draw_pixel
2099
 
2100
		fadd st0,st1 ;t+dt
2101
 
2102
		fld1
2103
		fcomp
2104
		fstsw ax
2105
		sahf
2106
	jae @b
2107
 
2108
	popad
2109
	ret
2110
endp
2111
 
2112
txt_err_n8b db 'need buffer 8 bit',13,10,0
2113
txt_err_n24b db 'need buffer 24 bit',13,10,0
2114
 
2115
align 16
2116
EXPORTS:
2117
	dd sz_lib_init, lib_init
2118
	dd sz_buf2d_create, buf_create
2119
	dd sz_buf2d_create_f_img, buf_create_f_img
2120
	dd sz_buf2d_clear, buf_clear
2121
	dd sz_buf2d_draw, buf_draw_buf
2122
	dd sz_buf2d_delete, buf_delete
2123
	dd sz_buf2d_line, buf_line_brs
1634 IgorA 2124
	dd sz_buf2d_rect_by_size, buf_rect_by_size
1642 IgorA 2125
	dd sz_buf2d_filled_rect_by_size, buf_filled_rect_by_size
1535 IgorA 2126
	dd sz_buf2d_circle, buf_circle
2127
	dd sz_buf2d_img_hdiv2, buf_img_hdiv2
2128
	dd sz_buf2d_img_wdiv2, buf_img_wdiv2
2129
	dd sz_buf2d_conv_24_to_8, buf_conv_24_to_8
2130
	dd sz_buf2d_conv_24_to_32, buf_conv_24_to_32
2131
	dd sz_buf2d_bit_blt, buf_bit_blt
2132
	dd sz_buf2d_bit_blt_transp, buf_bit_blt_transp
2133
	dd sz_buf2d_bit_blt_alpha, buf_bit_blt_alpha
2134
	dd sz_buf2d_cruve_bezier, buf_cruve_bezier
2135
	dd sz_buf2d_convert_text_matrix, buf_convert_text_matrix
2136
	dd sz_buf2d_draw_text, buf_draw_text
2137
	dd sz_buf2d_crop_color, buf_crop_color
2138
	dd sz_buf2d_offset_h, buf_offset_h
2139
	dd 0,0
2140
	sz_lib_init db 'lib_init',0
2141
	sz_buf2d_create db 'buf2d_create',0
2142
	sz_buf2d_create_f_img db 'buf2d_create_f_img',0
2143
	sz_buf2d_clear db 'buf2d_clear',0 ;очистка буфера указанным цветом
2144
	sz_buf2d_draw db 'buf2d_draw',0
2145
	sz_buf2d_delete db 'buf2d_delete',0
2146
	sz_buf2d_line db 'buf2d_line',0 ;рисование линии
1642 IgorA 2147
	sz_buf2d_rect_by_size db 'buf2d_rect_by_size',0 ;рисование рамки прямоугольника, 2-я координата задана по размеру
2148
	sz_buf2d_filled_rect_by_size db 'buf2d_filled_rect_by_size',0 ;рисование залитого прямоугольника, 2-я координата задана по размеру
1535 IgorA 2149
	sz_buf2d_circle db 'buf2d_circle',0 ;рисование окружности
2150
	sz_buf2d_img_hdiv2 db 'buf2d_img_hdiv2',0 ;сжатие изображения по высоте в 2 раза (размер буфера не меняется)
2151
	sz_buf2d_img_wdiv2 db 'buf2d_img_wdiv2',0 ;сжатие изображения по ширине в 2 раза (размер буфера не меняется)
2152
	sz_buf2d_conv_24_to_8 db 'buf2d_conv_24_to_8',0
2153
	sz_buf2d_conv_24_to_32 db 'buf2d_conv_24_to_32',0
2154
	sz_buf2d_bit_blt db 'buf2d_bit_blt',0
2155
	sz_buf2d_bit_blt_transp db 'buf2d_bit_blt_transp',0
2156
	sz_buf2d_bit_blt_alpha db 'buf2d_bit_blt_alpha',0
2157
	sz_buf2d_cruve_bezier db 'buf2d_cruve_bezier',0
2158
	sz_buf2d_convert_text_matrix db 'buf2d_convert_text_matrix',0
2159
	sz_buf2d_draw_text db 'buf2d_draw_text',0
2160
	sz_buf2d_crop_color db 'buf2d_crop_color',0
2161
	sz_buf2d_offset_h db 'buf2d_offset_h',0