Subversion Repositories Kolibri OS

Rev

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

Rev Author Line No. Line
396 Lrz 1
;  07.03.2007 Дописал управление с shift home + end усправил несколько багов
391 Lrz 2
;  06.03.2007 Переписал полностью алгоритм управления shift
348 Lrz 3
;  15.02.2007 улучшение снятия выделения и перерисовки очищаемой области, значительно приятнее работает компонент
4
;  13.02.2007 убрал по возможности мерцание, улучшена обработка перерисовки фона
5
; добавил фитчу внесения 0х0 по адресу ed_size иначе у Maxxx32 были несостыковки в коде. Причина в том, что оптимизация была сведена к тому, что я не чистил символы в буфере, когда удалял, я просто их не выводил, и потом, когда вносился новый символ, он попросту затирал уже имеющийся. Если бы, программа обрабатывала конец строки по ed_size, проблемы не возникло. Но сейчас этот недостаток исправлен.
306 Lrz 6
;  01.02.2007 доработка edit_box, исправил баги.
295 Lrz 7
;  26.01.2007 нормальная работа компанента исправил фукцию .check_offset
8
;  24.01.2007 пофиксел баги вызваные не правильным кодом )).
289 Lrz 9
;  22.01.2007 избавился от глюков при работе с выделением и удаление, корректная работа клавишей del & backspase
10
;  20.01.2007 реализовал выделение текста по shift
234 Lrz 11
;  12.12.2006 реализовал поддержку кнопки insert и сегодя компонент почти работает!!!!
12
;  07.12.2006 продолжается работа над переработкой компонента,изменениям подверглись многие функции, переработан вывод текста, а така же алгоритм внесения символов.
13
;  03.09.2006 по возможности отказался от 16 битной арифметики, добавил новые баги
14
;  09.08.2006 произведена оптимизация работы конпок DEL и Backspace, уменьшен размер выполняемого кода.
15
;  21.07.2006 добавлена функция кнопки Del, теперь можно удалять символы при помощи данной клавиши
16
; Автор: Евтихов Максим (Maxxxx32) email: maxxxxm@mail.ru
17
; Дата последних изменений: 13.06.06 10:40
18
;  Напишите в исходном коде своей программы use_edit_box,
19
; это вставит необходимые процедуры в код вашей программы.
20
;  Процедуры:
21
;   edit_box.draw - полная перерисовка;
22
;   edit_box.key - обработка клавиатуры;
23
;   edit_box.mouse - обработка мыши;
24
;   edit_box.focus - установка фокуса;
25
;   edit_box.blur - его размывание;
26
;   edit_box.get_n - получить количество прорисовываемых символов.
27
;  При вызове любых из этих процедур в регистре edi следует
28
; оставить указатель на структуру.
29
;  Пример структуры:
30
; some_edit edit_box 100,10,30,0x00ffffff,0,0x00aaaaaa,0,255,some_edit_text
31
; длина, высота, верх, цвет фона, цвет рамки, если выбран,
32
; цвет рамки, если не выбран, максимальное количество символов,
33
; указатель на буфер, где будут хранится символы. Буфер должен
34
; оканчиваться нулем, например если максимальное количество 255:
35
;  some_edit_text:
36
;       rb      256 ;255+1
37
 
38
;  Пример вызова процедуры:
39
;       mov     edi,some_edit
40
;       call    edit_box.draw
41
 
42
;  При вызове процедуры edit_box.key код клавиши должен
43
; находится в ah, то есть перед вызовом этой процедуры надо вызвать
44
; 2-ую сисемную функцию, например:
45
;       mov     eax,2
46
;       int     0x40
47
;       mov     edi,some_edit1
48
;       call    edit_box.key
49
;       mov     edi,some_edit2
50
;       call    edit_box.key
51
;  Перед вызовом обработчика мыши следует проверить, является ли окно
52
; активным.
53
;  Если щелчок мыши был пройзведен за пределами edit box
54
; фокус теряется.
55
macro use_edit_box
56
{
57
edit_box:
58
ed_width	equ [edi]		;ширина компонента
59
ed_left 	equ [edi+4]             ;положение по оси х
60
ed_top		equ [edi+8]             ;положение по оси у
61
ed_color	equ [edi+12]		;цвет фона компонента
62
ed_focus_border_color	equ [edi+16]	;цвет рамки компонента
63
ed_blur_border_color	equ [edi+20]    ;цвет не активного компонента
64
ed_text_color	equ [edi+24]            ;цвет текста
282 Lrz 65
ed_max		equ [edi+28]                    ;кол-во символов которые можно максимально ввести
66
ed_text 	equ [edi+32]                    ;указатель на буфер
67
ed_flags	equ [edi+36]            ;флаги
68
ed_size equ [edi+38]                    ;кол-во символов
69
ed_pos	equ [edi+42]                    ;позиция курсора
70
ed_offset	equ [edi+46]            ;смещение
71
cl_curs_x	equ [edi+50]		;предыдущее координата курсора по х
72
cl_curs_y	equ [edi+54]		;предыдущее координата курсора по у
396 Lrz 73
ed_shift_pos	equ [edi+58]            ;положение курсора
74
ed_shift_pos_old equ [edi+62]           ;старое положение курсора
234 Lrz 75
;==========================================================
76
;=== процедура прорисовки =================================
77
;==========================================================
78
.draw:
79
pusha
80
;--- рисуем рамку ---
81
	call	.draw_border		; Функция стабильна
82
.draw_bg_cursor_text:
83
;--- изменяем смещение, если надо ---
84
	call	.check_offset		;вычисление позиции курсора стабильна
85
;--- рисуем внутреннюю область ---
86
	call	.draw_bg                ;нарисовать прямоугольник рабочей области
402 Lrz 87
;---- рисуем выделение, по shift если есть
88
	call	.draw_shift
234 Lrz 89
.draw_cursor_text:
90
;--- рисуем курсор ---
91
	;--- может его не надо рисовать ----
282 Lrz 92
	test	word ed_flags,ed_focus
234 Lrz 93
	je	@f
94
	call	.draw_cursor
95
@@:
96
	call	.draw_text
97
popa
98
ret
99
;----------------------------------------------------------
402 Lrz 100
;--- процедура прорисовки выделеной части -----------------
101
;----------------------------------------------------------
102
.draw_shift:
103
	test	word ed_flags,ed_shift_bac ;установка флага, выделенной области
104
	jz	@f
105
        mov	ebp,shift_color
106
        mov	ebx,dword	ed_shift_pos
107
	call	.sh_cl_
108
@@:	ret
109
 
110
 
111
;----------------------------------------------------------
234 Lrz 112
;--- процедура прорисовки текста --------------------------
113
;----------------------------------------------------------
114
.draw_text:
115
;--- вычисляем, сколько помещается символов ---
116
;--- чтобы мусор не рисовать ---
117
	call 	.get_n
118
	mov	esi,ed_size
119
        mov	ebx,ed_offset
120
	sub	esi,ebx
121
	cmp	eax,esi
122
	jae	@F
123
	mov	esi,eax		;чтобы не выходить за пределы экрана
402 Lrz 124
;--- рисуем текст ---
234 Lrz 125
@@: 	mov	eax,4
126
	mov	ebx,ed_left
306 Lrz 127
	mov	edx,ed_offset
234 Lrz 128
	add	ebx,2
129
	shl	ebx,16
130
	mov	bx,ed_top
131
	add	ebx,4
132
	mov	ecx,ed_text_color
133
	add	edx,ed_text
134
	int	0x40
135
ret
136
;----------------------------------------------------------
137
;--- процедура прорисовки фона ----------------------------
138
;входные данные
139
;eax
292 Lrz 140
;edx - color
234 Lrz 141
;----------------------------------------------------------
343 Lrz 142
;вход только цвет edx
234 Lrz 143
.draw_bg:
144
	mov	ebx,ed_left
145
	add	ebx,1
146
	shl	ebx,16
147
	mov	bx,ed_width
148
	sub	ebx,1
391 Lrz 149
       	mov	edx,ed_color
150
.draw_bg_eax:
234 Lrz 151
	mov	ecx,ed_top
306 Lrz 152
	mov	eax,13
234 Lrz 153
	add	ecx,1
154
	shl	ecx,16
155
	mov	cx,ed_height
391 Lrz 156
	dec	ecx
306 Lrz 157
        int	0x40
234 Lrz 158
ret
159
 
160
;----------------------------------------------------------
161
;--- процедура получения количества символов в текущей щирине компонента --------------
162
;----------------------------------------------------------
163
.get_n:
306 Lrz 164
	mov	eax,ed_width	;получем ширину компонента
234 Lrz 165
	xor	edx,edx   ;результат распологается в паре edx:eax в eax - остаток
166
	sub	eax,4		;вычтим 4
167
	mov	ebx,6		;загрузми делитель
168
	div	ebx		;размделим на 6
169
ret
170
;----------------------------------------------------------
171
;--- процедура рисования курсора --------------------------
172
;----------------------------------------------------------
391 Lrz 173
;входные ebp- цвет
234 Lrz 174
.clear_cursor:
391 Lrz 175
	mov	edx,ebp
234 Lrz 176
	mov	ebx,cl_curs_x
177
	mov	ecx,cl_curs_y
178
	jmp	.draw_curs
179
.draw_cursor:
180
	mov	edx,ed_text_color
181
	mov	ebx,ed_pos
182
	mov	ecx,ed_offset
183
	sub	ebx,ecx
184
 
185
	lea     ebx,[ebx*2+ebx]
186
	shl     ebx,1
187
	;imul	ebx,6
188
	add	bx,ed_left
306 Lrz 189
	mov	ecx,ed_top
234 Lrz 190
	inc	ebx
306 Lrz 191
	add	ecx,2
234 Lrz 192
	mov	ebp,ebx
193
	shl	ebx,16
194
	mov	bx,bp
195
	mov	ebp,ecx
196
 
197
	shl	ecx,16
198
	mov	cx,bp
199
	add	cx,ed_height-4
200
 
201
	mov	cl_curs_x,ebx
202
	mov	cl_curs_y,ecx
203
.draw_curs:
204
	mov	eax,38
205
	int	0x40
206
ret
207
;----------------------------------------------------------
208
;--- процедура рисования рамки ----------------------------
209
;----------------------------------------------------------
210
.draw_border:
211
;--- цвет рамки ---
396 Lrz 212
	test	word ed_flags,ed_focus
234 Lrz 213
	mov	edx,ed_focus_border_color
214
	jne     @f
215
	mov	edx,ed_blur_border_color
216
@@:
217
;--- сверху ---
218
	mov	eax,38
219
	mov	ebx,ed_left
220
	mov 	ecx,ebx
221
	shl	ebx,16
222
	mov	bx,cx
223
	add	bx,ed_width
224
	mov	ecx, ed_top
225
	mov	esi,ecx
226
	shl	ecx,16
227
	mov	cx,si
228
	int	0x40
229
 
230
;--- снизу ---
231
	mov	esi,ecx
232
	add	ecx,ed_height
233
	mov	ebp,ecx
234
	shl	ecx,16
235
	mov	cx,bp
236
	int	0x40
237
 
238
;--- слева ---
239
	mov	cx,si
240
	mov	ebp,ebx
241
	sub	bx,ed_width
242
	int	0x40
243
 
244
;--- справа ---
245
	mov	ebx,ebp
246
	shl	ebx,16
247
	mov	bx,bp
248
	int	0x40
249
ret
250
;----------------------------------------------------------
251
;--- проверка, зашел ли курсор за границы и, если надо, ---
252
;--- изменяем смещение ------------------------------------
296 Lrz 253
;--- eax = -1, если не изменилось или eax = 0, если
234 Lrz 254
; изменилось
255
;----------------------------------------------------------
256
.check_offset:
350 Lrz 257
pusha
295 Lrz 258
	mov	ecx,ed_pos
259
	mov	ebx,ed_offset
260
	cmp	ebx,ecx
261
	ja	.sub_8
262
 
263
	push	ebx
234 Lrz 264
	call	.get_n			;получим кол-во символов в паре регистров edx:eax
265
	pop	ebx
295 Lrz 266
	mov	edx,ebx
267
	add	edx,eax		;ed_offset+width editbox
268
	cmp	edx,ecx
269
	ja	@f
270
 
271
	mov	edx,ed_size
296 Lrz 272
	cmp	edx,ecx
273
	je      .add_end
274
 
275
	sub	edx,ecx
295 Lrz 276
	cmp	edx,8
277
	jbe	.add_8
296 Lrz 278
	add	ebx,8
295 Lrz 279
	jmp	.chk_d
280
 
281
.sub_8: cmp	ecx,0
282
	je	.sub_min
283
	cmp	ebx,8
284
        jbe	.sub_min
285
	sub	ebx,8	;ebx=ed_offset
286
	jmp	.chk_d
287
.sub_min:
288
        xor	ebx,ebx
289
	jmp	.chk_d
290
 
296 Lrz 291
.add_end:sub	edx,eax
292
	mov	ebx,edx
293
	jmp	.chk_d
294
.add_8:	add	ebx,edx
295 Lrz 295
.chk_d:	mov	ed_offset,ebx
296
	call    .draw_bg
396 Lrz 297
	and	word ed_flags,ed_offset_cl
350 Lrz 298
popa
295 Lrz 299
	ret
300
@@:
396 Lrz 301
	or	word ed_flags,ed_offset_fl
350 Lrz 302
popa
295 Lrz 303
	ret
304
;==========================================================
305
;=== обработка клавиатуры =================================
306
;==========================================================
307
.key:
308
pusha
309
	test	word ed_flags,ed_focus ; если не в фокусе, выходим
350 Lrz 310
	je      @b
343 Lrz 311
;Проверка на нажаты shift
292 Lrz 312
	xor	ecx,ecx
282 Lrz 313
	push	eax
292 Lrz 314
	inc	ecx
282 Lrz 315
	mov	eax,66
316
	mov	ebx,3
317
	int	0x40
318
	test	al,0x03
319
	je	@f
343 Lrz 320
        or      word ed_flags,ed_shift   ;установим флаг
321
@@:     pop	eax   ;восстановим считаный символ с клавиатуры
234 Lrz 322
;----------------------------------------------------------
323
;--- проверяем, что нажато --------------------------------
324
;----------------------------------------------------------
325
	cmp	ah,8
326
	jz	.backspace
327
	cmp	ah,0xb6
328
	jz	.delete
329
	cmp	ah,176
330
	jz	.left
331
	cmp	ah,179
332
	jz	.right
333
	cmp	ah,180
334
	jz	.home
335
	cmp	ah,181
336
	jz	.end
337
	cmp	ah,185	;insert
338
	jz	.insert
339
;;;;;;;;;;;;;;;;;;;;;;;;;;;;
340
;Заглушка на обработку клавиш вверх и вниз
341
;;;;;;;;;;;;;;;;;;;;;;;;;;;;
342
	cmp	ah,177
343
        jz	.no_figure
344
	cmp	ah,178
345
	jz	.no_figure
346
	cmp	ah,27   ;ESC - клавиша ))
347
	jz	.no_figure
348
;--- нажата другая клавиша ---
349
	test	word ed_flags,ed_figure_only  ; только цифры ?
350
	jz	@f
351
	cmp	ah,'0'
352
	jb	.no_figure
353
	cmp	ah,'9'
354
	ja	.no_figure
292 Lrz 355
;проверка на shift
306 Lrz 356
@@:	test	word ed_flags,ed_shift_on
292 Lrz 357
	je	@f
358
	;Входные данные edx=ed_size;ecx=ed_pos
359
	push	eax
360
	mov	edx,ed_size
361
	mov	ecx,ed_pos
350 Lrz 362
	pusha
343 Lrz 363
;clear
391 Lrz 364
	mov	ebp,edx ;ed_size
365
        call	.clear_bg
366
       	mov	ebp,ed_color
396 Lrz 367
	mov	ebx,dword	ed_shift_pos
348 Lrz 368
        call	.sh_cl_
350 Lrz 369
 
391 Lrz 370
.sh_nxt:popa
350 Lrz 371
	call	.del_char
292 Lrz 372
;;;;
391 Lrz 373
        mov	eax,dword ed_shift_pos
292 Lrz 374
        mov	ebx,ed_size
375
	sub	ebx,eax
376
	mov	ed_size,ebx
377
	pop	eax
378
        ; проверяем, находится ли курсор в конце
379
@@:	mov	ecx,ed_size
234 Lrz 380
	mov	edx, ed_max
343 Lrz 381
	test	word ed_flags,ed_insert
382
	jne	@f
289 Lrz 383
	cmp	ecx,edx
384
	jae	.no_figure
343 Lrz 385
@@:	mov	ebx, ed_pos
234 Lrz 386
	cmp	ebx,edx
387
	jl	@f ; если меньше или равно
388
.no_figure:
389
	popa
390
	ret
292 Lrz 391
.insert: test	word ed_flags,ed_insert	;not 	word ed_insert
392
         je     .insert_1
393
         and	word ed_flags,ed_insert_cl
394
	jmp	.no_figure
395
.insert_1:
396
	or	word ed_flags,ed_insert
234 Lrz 397
        jmp	.no_figure
292 Lrz 398
.ins_v:
306 Lrz 399
	dec	dword [ebp+38];ed_size    ;processing is insert
234 Lrz 400
	sub	esi,ecx
401
	add	esi,ebx
402
        mov	edi,esi
343 Lrz 403
;clear
404
pusha
405
	mov	edi,ebp
406
	mov	ebp,ed_pos
407
	call	.clear_bg
408
popa
234 Lrz 409
	jmp	.In_k
410
@@:     ; сдвигаем символы после курсора вправо
411
	mov	ecx,ed_size
412
	push	edi eax
292 Lrz 413
	mov	ebp,edi
234 Lrz 414
	mov	esi,ed_text     ; Указатель на буфер
415
				;Будем работать со строкой
416
	add	esi,ecx		;add ed_size добавим max size
417
	mov	edi,esi
418
 
419
       	cmp 	ecx,ebx         ;Если у нас позиция курсора = текущему размеру напечатанных символов т.е. курсор стоит в конце
420
	je	.In_k
421
 
292 Lrz 422
	test	word [ebp+36],ed_insert ;IF insert is enable  т.к. edi изменен адресуем через ebp
423
	jne	.ins_v
343 Lrz 424
;clear
425
pusha
426
	mov	edi,ebp
427
	mov	ebp,ed_size
428
	call	.clear_bg
429
popa
234 Lrz 430
	sub	ecx,ebx         ;Найдем кол-во символов для передвижения.
431
	inc	edi		;Сместим наши символы в право
432
	std
433
	inc 	ecx
434
   @@:
435
	;--------
436
	lodsb
437
	stosb
438
	;--------
439
	loop	@b
440
.In_k:	cld
441
	pop eax
442
	mov al,ah
443
	stosb
444
	pop edi
445
; вставляем код клавиши туда, где курсор
446
	; увеличиваем значение размера и позиции
447
	inc	 dword ed_size
295 Lrz 448
	inc	 dword ed_pos
234 Lrz 449
	call	.draw_all2
295 Lrz 450
	jmp	.shift;.draw_cursor_text
234 Lrz 451
.delete:
452
	mov	edx,ed_size
453
	mov	ecx,ed_pos
454
	cmp	edx,ecx
292 Lrz 455
	jg	.bac_del
289 Lrz 456
	test	word ed_flags,ed_shift_on
457
	jne	.del_bac
234 Lrz 458
	popa
459
	ret
289 Lrz 460
.bac_del:
292 Lrz 461
	call 	.del_char
234 Lrz 462
	jmp 	.draw_all
463
 
464
;--- нажата клавиша backspace ---
465
.backspace:
466
	; проверяем, курсор у левого края ?
467
	mov	edx,ed_size
468
	mov	ecx,ed_pos
469
	test	ecx,ecx
292 Lrz 470
	jnz	.del_bac
289 Lrz 471
        test	word ed_flags,ed_shift_on
472
        jne	.bac_del
234 Lrz 473
	popa
474
	ret
289 Lrz 475
.del_bac:
292 Lrz 476
	cmp	edx,ecx	;if ed_pos=ed_size
234 Lrz 477
	je	@f
478
	dec	ecx
479
	call 	.del_char
289 Lrz 480
@@:     test	word ed_flags,ed_shift_on
481
        jne	.bac_del
234 Lrz 482
	dec	 dword ed_pos
483
 
484
.draw_all:
343 Lrz 485
       	push	.shift;.draw_cursor_text;eax
289 Lrz 486
 
487
        test	word ed_flags,ed_shift_on
488
        je	@f
391 Lrz 489
        mov	eax,dword ed_shift_pos
289 Lrz 490
        mov	ebx,ed_size
491
	sub	ebx,eax
492
	mov	ed_size,ebx
493
 
391 Lrz 494
	mov	ebp,ed_color
343 Lrz 495
	call	.clear_cursor
496
	call	.check_offset
497
        call	.draw_bg
498
	ret
289 Lrz 499
@@:	dec	 dword ed_size
500
 
234 Lrz 501
.draw_all2:
290 Lrz 502
	and    word ed_flags,ed_shift_cl
391 Lrz 503
	mov	ebp,ed_color
234 Lrz 504
	call	.clear_cursor
505
	call	.check_offset
343 Lrz 506
	mov	ebp,ed_size
507
	call	.clear_bg
295 Lrz 508
	ret
234 Lrz 509
;--- нажата клавиша left ---
391 Lrz 510
.left:  mov	ebx,ed_pos
234 Lrz 511
	test	ebx,ebx
391 Lrz 512
	jz	.sh_st_of
513
	or	word ed_flags,ed_left_fl
514
	call	.sh_first_sh
234 Lrz 515
	dec	 dword ed_pos
391 Lrz 516
	call	.sh_enable
517
	jmp	.draw_cursor_text
234 Lrz 518
;--- нажата клавиша right ---
391 Lrz 519
.right:	mov	ebx,ed_pos
234 Lrz 520
	cmp	ebx,ed_size
391 Lrz 521
	je	.sh_st_of
522
	and	word ed_flags,ed_right_fl
523
	call	.sh_first_sh
234 Lrz 524
	inc	dword  ed_pos
391 Lrz 525
	call	.sh_enable
526
	jmp	.draw_cursor_text
527
.home:
289 Lrz 528
	mov	ebx,ed_pos
234 Lrz 529
	test	ebx,ebx
391 Lrz 530
	jz	.sh_st_of
531
	call	.sh_first_sh
234 Lrz 532
	xor	eax,eax
533
	mov	ed_pos,eax
391 Lrz 534
	call	.sh_home_end
535
 	jmp	.draw_cursor_text
536
.end:
289 Lrz 537
	mov	ebx,ed_pos
234 Lrz 538
	cmp	ebx,dword ed_size
391 Lrz 539
	je	.sh_st_of
396 Lrz 540
	call	.sh_first_sh
234 Lrz 541
	mov	eax,ed_size
542
	mov	ed_pos,eax
391 Lrz 543
	call	.sh_home_end
544
	jmp	.draw_cursor_text
545
;Обработка Shift для снятия выделения неизвестной области
348 Lrz 546
.shift: ;;;;;;;SHIFT
391 Lrz 547
	test    word ed_flags,ed_shift
348 Lrz 548
        je	.f_exit
343 Lrz 549
 
391 Lrz 550
@@:	mov	ebp,shift_color
551
	or	word ed_flags,ed_shift_bac ;установка флага, выделенной области
396 Lrz 552
	mov	ebx,dword	ed_shift_pos
348 Lrz 553
	call	.sh_cl_
554
        jmp	.draw_cursor_text
555
;;;;;;;;;;;;;;;;;;;;;
391 Lrz 556
.f_exit:call	.check_offset
396 Lrz 557
	and     word ed_flags,ed_shift_cl
348 Lrz 558
        call	.enable_null
559
	jmp	.draw_cursor_text
560
.sh_cl_:
282 Lrz 561
;;;;;;SHIFT end
391 Lrz 562
;обработка очистки, при левом - правом движении выделения
348 Lrz 563
;для обработки снятия выделения
396 Lrz 564
;входные параметры ebp=color ebx=ed_shift_pos
282 Lrz 565
	mov 	eax,dword	ed_pos
566
	cmp	eax,ebx
567
	jae	.sh_n
568
	push	eax  ;меньшее в eax
569
	push	ebx  ;большее
570
	jmp	.sh_n1
571
	             ;если иначе
572
.sh_n: 	push	ebx
573
	push	eax
574
.sh_n1:
575
	call	.check_offset
576
	call	.get_n
577
	mov	edx,eax	;size of ed_box
578
	mov	ecx,ed_offset
579
	add	eax,ecx	;eax = w_off= ed_offset+width
348 Lrz 580
	mov	edx,eax ;save
282 Lrz 581
	pop	ebx     ;большее
582
	pop	eax     ;меньшее
583
 
584
	cmp	eax,ecx         ;сравнение с меньшего с offset.
585
	jae	.f_f            ;если больше
586
	xor	eax,eax
348 Lrz 587
	cmp	edx,ebx		;cравним размер w_off с большим
282 Lrz 588
	jb	@f
589
	sub	ebx,ecx
590
	jmp     .nxt_f
348 Lrz 591
@@:	mov	ebx,edx
282 Lrz 592
	sub	ebx,ecx
593
	jmp     .nxt_f
594
.f_f:
595
	sub	eax,ecx
348 Lrz 596
	cmp	edx,ebx		;cравним размер w_off с большим
282 Lrz 597
	jle	@f
598
	sub	ebx,ecx
599
	sub	ebx,eax
600
	jmp     .nxt_f
234 Lrz 601
@@:
348 Lrz 602
	mov	ebx,edx
282 Lrz 603
	sub	ebx,ecx
604
	sub	ebx,eax
605
.nxt_f:
289 Lrz 606
	mov	edx,ebx
282 Lrz 607
	lea	ebx,[eax*2+eax]
608
	shl	ebx,1
609
	add	ebx,ed_left
610
	inc	ebx
611
	shl	ebx,16
612
	lea	ecx,[edx*2+edx]
613
	shl	ecx,1
614
	mov	bx,cx
391 Lrz 615
	inc	ebx
348 Lrz 616
	mov	edx,ebp;shift_color
617
 
282 Lrz 618
	call	.draw_bg_eax
396 Lrz 619
@@:	call	.enable_null
348 Lrz 620
	ret
391 Lrz 621
;;;;;;;;;;;;;;;;;;;;;
622
;Установка- снятие выделения в один символ
623
;;;;;;;;;;;;;;;;;;;;;
624
.drw_sim:
625
	mov	eax,dword	ed_pos
626
	call    .draw_rectangle   ;нарисовать прямоугольник с заданным цветом
627
        jmp     @b
628
;;;;;;;;;;;;;;;;;;;;;
629
;Фукция установки выделения при движения влево и вправо и нажатии shift
630
;Логика:
631
;;;;;;;;;;
632
.draw_wigwag:
633
;функция установки переменных
634
	mov	ebp,shift_color
635
	call	.clear_cursor
289 Lrz 636
 
391 Lrz 637
	or	word ed_flags,ed_shift_bac ;установка флага, выделенной области
638
	mov	ebp,shift_color
639
	mov 	eax,dword	ed_pos
640
	test	word ed_flags,ed_left_fl
641
	jz      .low
642
	jmp	@f
643
;;;;;;;;;;
644
;Фукция удаления выделения при движения влево и вправо и нажатии shift
645
;Логика:
646
;;;;;;;;;;
647
.draw_wigwag_cl:
648
;функция установки переменных
649
	mov	ebp,ed_color
650
	call	.clear_cursor
651
 
652
	mov	ebp,ed_color
653
	mov 	eax,dword	ed_pos
654
	test	word ed_flags,ed_left_fl
655
	jz      .low
656
@@:     call	.draw_rectangle  ;нарисовать прямоугольник закрашиваемой области
657
	ret
658
.low:   dec	eax
659
        jmp	@b
660
;входной параметр ebx - ed_pos
661
.sh_first_sh:
289 Lrz 662
	test    word ed_flags,ed_shift
663
	je	@f
391 Lrz 664
	mov	dword ed_shift_pos_old,ebx
289 Lrz 665
	test	word ed_flags,ed_shift_on
391 Lrz 666
	jne	@f
667
	mov	dword ed_shift_pos,ebx
668
       	or	word ed_flags,ed_shift_on
669
@@:    	ret
670
;Обработка крайних положений в editbox при нажатом shift
671
;производит снятие выделение, если нет shift
672
;иначе вообще выходит
673
.sh_st_of:
674
	test    word ed_flags,ed_shift
675
	jne	@f
676
	test    word ed_flags,ed_shift_bac
348 Lrz 677
        je      @f
391 Lrz 678
       	mov	ebp,ed_color
396 Lrz 679
	mov	ebx,dword	ed_shift_pos
391 Lrz 680
	call	.sh_cl_  ;очистка выделеного фрагмента
681
	and	word ed_flags,ed_shift_cl ; очистка от того что убрали выделение
682
	jmp     .draw_cursor_text
683
@@:
684
        and	word ed_flags,ed_shift_off
685
	popa
686
	ret
687
 
688
;проверка состояния shift был ли он нажат раньше?
689
.sh_enable:
690
	test    word ed_flags,ed_shift
691
	jne	.sh_ext_en ;нарисовать закрашеный прямоугольник
692
 
693
	test    word ed_flags,ed_shift_bac
694
        je      @f
695
       	call	.check_offset
696
 
348 Lrz 697
	mov	ebp,ed_color
396 Lrz 698
	mov	ebx,dword	ed_shift_pos
348 Lrz 699
	call	.sh_cl_  ;очистка выделеного фрагмента
391 Lrz 700
	call	.draw_wigwag_cl
701
	and	word ed_flags,ed_shift_cl ; 1вар не нужно
702
	ret
703
 
704
@@:     mov	ebp,ed_color
705
	call	.clear_cursor
706
	call	.check_offset
707
	ret
348 Lrz 708
.sh_ext_en:
391 Lrz 709
       	call	.check_offset
396 Lrz 710
	test	word ed_flags,ed_offset_fl
402 Lrz 711
	je	@f
391 Lrz 712
;Рисование закрашеных прямоугольников и очистка их
713
        mov 	eax,dword	ed_shift_pos
714
	mov	ebx,dword	ed_pos
715
	mov	ecx,dword	ed_shift_pos_old
716
;проверка и рисование закрашеных областей
717
	cmp	eax,ecx
718
	je	.1_shem
719
	jb      .smaller
720
        cmp	ecx,ebx
721
        ja	.1_shem
722
        call	.draw_wigwag_cl ;clear
723
	jmp	.sh_e_end
724
.smaller:
725
        cmp	ecx,ebx
726
        jb	.1_shem
727
        call	.draw_wigwag_cl ;clear
728
	jmp	.sh_e_end
729
;alike  =
730
.1_shem: call	.draw_wigwag
731
.sh_e_end:	and	word ed_flags,ed_shift_off
732
	ret
733
@@:	mov	ebp,shift_color
396 Lrz 734
	mov	ebx,dword	ed_shift_pos
391 Lrz 735
	call	.sh_cl_
736
	jmp	.sh_e_end
737
;функция для обработки shift при нажатии home and end
738
.sh_home_end:
739
	mov	ebp,ed_color
740
	call	.clear_cursor
741
	test    word ed_flags,ed_shift_bac
742
        je      @f
743
	mov	ebp,ed_color
396 Lrz 744
	mov	ebx,dword	ed_shift_pos_old
391 Lrz 745
	call	.sh_cl_
746
 
747
@@:	test    word ed_flags,ed_shift
402 Lrz 748
	je	.sh_exit_ ;выйти
391 Lrz 749
        mov	ebp,shift_color
396 Lrz 750
        mov	ebx,dword	ed_shift_pos
391 Lrz 751
	call	.sh_cl_
752
	or	word ed_flags,ed_shift_bac ;установка флага, выделенной области
753
	jmp	.sh_e_end
396 Lrz 754
.sh_exit_: 	call	.check_offset
755
	ret
343 Lrz 756
;функция внесения 0 по адресу ed_size+1
757
.enable_null:
758
        pusha
759
        mov	eax,ed_size
760
	mov	ebx,ed_text
761
	add	eax,ebx
762
	inc	eax
763
	xor	ebx,ebx
764
	mov 	[eax],bl
765
	popa
766
	ret
396 Lrz 767
;- удаление символа
768
;Входные данные edx=ed_size;ecx=ed_pos
234 Lrz 769
.del_char:
770
	mov     esi,ed_text
289 Lrz 771
        test	word ed_flags,ed_shift_on
772
        je	@f
773
	mov	eax,dword ed_shift_pos
774
	mov	ebx,esi
775
        cmp	eax,ecx
776
	jae	.dh_n
777
 
778
	mov	ed_pos,eax	;что бы не было убегания курсора
779
	mov	ebp,ecx
780
	sub	ebp,eax
781
	add	ebx,eax  ;eax меньше
782
	sub	edx,ecx
234 Lrz 783
	add	esi,ecx
784
 
391 Lrz 785
	mov	dword ed_shift_pos,ebp
289 Lrz 786
        jmp	.del_ch_sh
787
	             ;если иначе
788
.dh_n:
789
	mov	ebp,eax
790
	sub	ebp,ecx
791
	add	ebx,ecx
792
	sub	edx,eax
793
	add	esi,eax
391 Lrz 794
	mov	dword ed_shift_pos,ebp
289 Lrz 795
	jmp	.del_ch_sh
796
 
797
@@:	add	esi,ecx ;указатель + смещение к реальному буфферу
234 Lrz 798
	mov	ebx,esi
799
	inc 	esi
800
	cld
801
 
802
	sub	edx,ecx
289 Lrz 803
.del_ch_sh:
804
 
234 Lrz 805
	push 	edi
806
	mov 	edi,ebx
807
@@:
808
	lodsb
809
	stosb
289 Lrz 810
	dec edx
234 Lrz 811
	jns @b
812
 
813
	pop edi
814
	ret
343 Lrz 815
;вычислить закрашиваемую область
816
;соглашение в ebp - передается ed_size
817
.clear_bg:
818
	call	.get_n  ;получить размер в символах ширины компонента
819
	push	eax
820
	mov	ebx,ed_offset
821
	add	eax,ebx	;eax = w_off= ed_offset+width
822
	mov	ebx,ebp ;ed_size
823
 
824
	cmp	eax,ebx
825
	jb	@f
826
	mov	eax,ed_pos
827
	sub	ebx,eax
828
	mov	ecx,ed_offset
829
	sub	eax,ecx
830
	jmp	.nxt
831
@@:	mov	ebx,ed_pos
832
	push	ebx
833
	sub	eax,ebx
834
	mov	ebx,eax	;It is don't optimal
835
 
836
	pop	eax	;ed_pos
837
       	mov	ecx,ed_offset
838
	sub	eax,ecx
839
.nxt:
840
	mov	ebp,eax  ;проверка на выход закрашиваемой области за пределы длины
841
	add	ebp,ebx
842
	pop	edx
843
	cmp	ebp,edx
844
	je	@f
845
	inc	ebx
846
 
847
@@:     mov	edx,ebx
848
	lea	ebx,[eax*2+eax]
849
	shl	ebx,1
850
	add	ebx,ed_left
851
	inc	ebx
852
	shl	ebx,16
853
	lea	ecx,[edx*2+edx]
854
	shl	ecx,1
855
	mov	bx,cx
856
	mov	edx,ed_color
857
	call	.draw_bg_eax
858
	ret
391 Lrz 859
;;;;;;;;;;;;;;;;;;;
860
;;; Обработка примитивов
861
;;;;;;;;;;;;;;;;;;;;
862
;Нарисовать прямоугольник, цвет передается в ebp
863
;входные параметры:
864
;eax=dword ed_pos
865
;ebp=-цвет ed_color or shift_color
866
.draw_rectangle:
867
	mov	ecx,dword ed_offset
868
	sub     eax,ecx
869
        lea	ebx,[eax*2+eax]
870
	shl	ebx,1
871
	inc	ebx
872
	add	ebx,ed_left
873
	shl	ebx,16
874
	mov	bx,6
875
	mov	edx,ebp
876
	call	.draw_bg_eax
877
	ret
234 Lrz 878
;==========================================================
879
;=== обработка мыши =======================================
880
;==========================================================
881
.mouse:
882
pusha
883
;----------------------------------------------------------
884
;--- получаем состояние кнопок мыши -----------------------
885
;----------------------------------------------------------
886
	mov	eax,37
887
	mov	ebx,2
888
	int	0x40
889
;----------------------------------------------------------
890
;--- проверяем состояние ----------------------------------
891
;----------------------------------------------------------
892
	test	eax,1
893
	jnz	.mouse_left_button
348 Lrz 894
	popa
234 Lrz 895
	ret
896
 
897
.mouse_left_button:
898
;----------------------------------------------------------
899
;--- получаем координаты мыши -----------------------------
900
;----------------------------------------------------------
901
	mov	eax,37
902
	xor	ebx,ebx
903
	inc	ebx
904
	int	0x40
905
;----------------------------------------------------------
906
;--- проверяем, попадает ли курсор в edit box -------------
907
;----------------------------------------------------------
908
	mov	ebx,ed_top
909
	cmp	ax,bx
910
	jl	._blur;.mouse_end_no_focus
911
 
912
	add	bx,ed_height
913
	cmp	ax,bx
914
	jg	._blur;.mouse_end_no_focus
915
 
916
	shr	eax,16
917
 
918
	mov	bx,ed_left
919
	cmp	ax,bx
920
	jl	._blur;.mouse_end_no_focus
921
 
922
	add	bx,ed_width
923
	cmp	ax,bx
924
	jg	._blur;.mouse_end_no_focus
925
;--- изменяем позицию курсора ---
926
	push	eax
391 Lrz 927
	mov	ebp,ed_color
234 Lrz 928
	call	.clear_cursor
929
	pop	eax
930
	xor	dx,dx
931
	sub	ax,ed_left
932
	add	ax,2
933
	mov	bx,6
934
	div	bx
935
	add	ax,ed_offset
936
	cmp	ax,ed_size
937
	jna	 @f
938
	mov	ax,ed_size
939
@@:
402 Lrz 940
	test    word ed_flags,ed_shift_bac
941
        je      @f
942
	mov	ebp,dword	ed_color
943
	mov	ebx,dword ed_shift_pos
944
	push	eax
945
	call	.sh_cl_
946
	and	word ed_flags,ed_shift_cl
947
	pop	eax
948
 
949
@@:
950
        test    word ed_flags,ed_shift
951
        je	@f
952
        mov	ebx,ed_pos
953
        mov	ed_shift_pos,ebx
954
 
955
        mov	ed_pos,eax
956
	mov	ebp,dword	shift_color
957
 
958
	call	.sh_cl_
959
	or      word ed_flags,ed_shift_bac	;установим бит что мы выделили
960
	and	word ed_flags,ed_shift_off
961
	jmp	.m_sh
962
@@:
963
 	mov	ed_pos,ax
964
.m_sh:  call	.draw_text
234 Lrz 965
	call	.draw_cursor
292 Lrz 966
;----------------------------------------------------------
967
;--- процедура установки фокуса ---------------------------
968
;----------------------------------------------------------
969
	bts	word ed_flags,1
348 Lrz 970
	jc	@f
292 Lrz 971
	call	.draw_cursor
348 Lrz 972
	jmp	.drc
234 Lrz 973
._blur:
306 Lrz 974
	test	word ed_flags,ed_always_focus
975
	jne	@f
292 Lrz 976
	btr	word ed_flags,1 ; если не в фокусе, выходим
977
	jnc     @f
402 Lrz 978
 
391 Lrz 979
	mov	ebp,ed_color
234 Lrz 980
	call	.clear_cursor
348 Lrz 981
.drc:	call	.draw_border
234 Lrz 982
@@:
983
popa
984
ret
985
 
986
;----------------------------------------------------------
987
;--- процедура размывания фокуса --------------------------
988
;----------------------------------------------------------
989
;.blur:
990
;pusha
991
;._blur:
992
	;btr     ed_flags,1
993
	;jnc     @f
994
	;call    .draw_border
995
	;call    .clear_cursor
996
;@@:
997
;popa
998
;ret
999
}
396 Lrz 1000
ed_figure_only= 1000000000000000b   ;одни символы
391 Lrz 1001
ed_always_focus= 100000000000000b
396 Lrz 1002
ed_focus=                     10b   ;фокус приложения
391 Lrz 1003
ed_shift_on=                1000b   ;если не установлен -значит впервые нажат shift,если был установлен, значит мы уже что - то делали удерживая shift
1004
ed_shift=                    100b   ;включается при нажатии на shift т.е. если нажимаю
1005
ed_shift_off=   1111111111111011b
1006
ed_shift_bac=              10000b   ;бит для очистки выделеного shift т.е. при установке говорит что есть выделение
1007
ed_shift_cl=    1111111111100011b
1008
ed_left_fl=               100000b
1009
ed_right_fl=    1111111111011111b
396 Lrz 1010
ed_offset_fl=            1000000b
1011
ed_offset_cl=   1111111110111111b
391 Lrz 1012
ed_insert=              10000000b
1013
ed_insert_cl=   1111111101111111b
1014
ed_height=14 ; высота
1015
shift_color=0x6a9480
234 Lrz 1016
macro draw_edit_boxes start,end
1017
{
1018
	mov	edi,start
1019
	mov	ecx,((end-start)/ed_struc_size)
1020
@@:
1021
	call	edit_box.draw
1022
	add	edi,ed_struc_size
1023
	loop	@b
1024
}
1025
 
1026
macro mouse_edit_boxes start,end
1027
{
1028
	mov	edi,start
1029
	mov	ecx,((end-start)/ed_struc_size)
1030
@@:
1031
	call	edit_box.mouse
1032
	add	edi,ed_struc_size
1033
	loop	@b
1034
}
1035
 
1036
macro key_edit_boxes start,end
1037
{
1038
	mov	edi,start
1039
	mov	ecx,((end-start)/ed_struc_size)
1040
@@:
396 Lrz 1041
;	push	eax
234 Lrz 1042
	call	edit_box.key
396 Lrz 1043
;	pop	eax
234 Lrz 1044
	add	edi,ed_struc_size
1045
	loop	@b
1046
}
391 Lrz 1047
ed_struc_size=66
234 Lrz 1048
struc  edit_box width,left,top,color,focus_border_color,\
396 Lrz 1049
       blur_border_color,text_color,max,text,flags
234 Lrz 1050
{
1051
.width dd width
1052
.left dd left
1053
.top dd top
1054
.color dd color
1055
.focus_border_color dd focus_border_color
1056
.blur_border_color dd blur_border_color
1057
.text_color dd text_color
1058
.max dd max
282 Lrz 1059
.text dd text
1060
.flags dw flags+0
396 Lrz 1061
.size dd 0
234 Lrz 1062
.pos dd 0
1063
.offset dd 0
1064
.cl_curs_x dd 0
1065
.cl_curs_y dd 0
391 Lrz 1066
.shift   dd 0
1067
.shift_old   dd 0
234 Lrz 1068
}
1069
 
402 Lrz 1070
struc  edit_box1 width,left,top,color,focus_border_color,\
1071
       blur_border_color,text_color,max,text,flags,ed_size
1072
{
1073
.width dd width
1074
.left dd left
1075
.top dd top
1076
.color dd color
1077
.focus_border_color dd focus_border_color
1078
.blur_border_color dd blur_border_color
1079
.text_color dd text_color
1080
.max dd max
1081
.text dd text
1082
.flags dw flags+0
1083
.size dd ed_size
1084
.pos dd 0
1085
.offset dd 0
1086
.cl_curs_x dd 0
1087
.cl_curs_y dd 0
1088
.shift   dd 0
1089
.shift_old   dd 0
1090
}
1091
 
234 Lrz 1092
macro edit_boxes_set_sys_color start,end,color_table
1093
{
1094
	mov	edi,start
1095
	mov	ecx,((end-start)/ed_struc_size)
1096
	mov	esi,color_table
1097
@@:
1098
	mov	eax,[esi+36]
1099
	mov	ebx,[esi+20]
1100
	mov	ed_focus_border_color,eax
1101
	shr	bh,1
1102
	shr	bl,1
1103
	shr	ah,1
1104
	shr	al,1
1105
	add	ah,bh
1106
	add	al,bl
1107
	ror	eax,16
1108
	ror	ebx,16
1109
	shr	bl,1
1110
	shr	al,1
1111
	add	al,bl
1112
	ror	eax,16
1113
	mov	ed_blur_border_color,eax
1114
	add	edi,ed_struc_size
1115
	loop	@b
306 Lrz 1116
}
1117
 
1118
macro draw_edit_box ed_ptr
1119
{
1120
        mov     edi,ed_ptr
1121
        call    edit_box.draw
1122
}
1123
 
1124
macro mouse_edit_box ed_ptr
1125
{
1126
        mov     edi,ed_ptr
1127
        call    edit_box.mouse
1128
}
1129
 
1130
macro key_edit_box ed_ptr
1131
{
1132
        mov     edi,ed_ptr
1133
        call    edit_box.key
234 Lrz 1134
}