Subversion Repositories Kolibri OS

Rev

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

Rev Author Line No. Line
355 Lrz 1
;компонент OptionBox (Основан на Checkbox)
356 Lrz 2
;Огромная благодарность Maxxxx32, Diamond, Heavyiron, и другим программистам, и их программам, без
355 Lrz 3
;которых я не смог бы написать этот компонент.
4
;16.02.2007
5
;  - Теплов Алексей  www.lrz.land.ru
6
 
7
macro use_option_box
8
{
9
op_text_margin=4     ;расстояние от прямоугольника чек бокса до надписи
10
op_size=10           ;размер квадрата чек бокса
11
op_left equ [edi]    ;координата начала рисования по х
12
op_top equ [edi+2]   ;координата начала рисования по у
356 Lrz 13
op_border_color equ [edi+4] ;цвет рамки optionbox
14
op_text_color equ [edi+8]  ;цвет текста
15
op_text_ptr equ [edi+12]    ;указатель на начало текстовой строки
16
op_text_length equ [edi+16] ;длина надписи (2^64 такой длины может быть текст)
17
op_optibox_gr	equ [edi+18]
355 Lrz 18
option_box:
19
.draw:
20
pusha   ;сохраним все регистры
21
	mov	eax,38     	;рисование линии
22
	movzx	ebx,word op_left	;положение по х
23
	mov	ecx,ebx		;сохраним в регистре cx значение bx  1 микрооперация
24
	;push	bx  ;3 - микрооперации  используя стек можно выиграть в размере, используя регистры - в скорости
25
	shl	ebx,16		;сдвинем на 16 разрядов в лево (умножим на 65536)
26
	;pop	bx  ;2 - микрооперации  на данный момент сформирована [координата начала по оси x]*65536 + [координата начала по оси x]
27
	mov	bx,cx		;восстановим значение bx
28
	movzx	ecx,word op_top	;загрузим в cx значение y
29
	mov	esi,ecx		;сохраним значение регистра cx в регистр указатель si
30
	;push	cx
31
	shl	ecx,16		; сдвинем на 16 разрядов в лево (умножим на 65536)	mov	cx,si		;восстановим значение регистра cx
32
	mov 	cx,si		;восстановим значение регистра cx
33
	;pop	cx    	;[координата начала по оси y]*65536 + [координата начала по оси y]
34
	;push	cx
35
	add	ecx,op_size ;[координата начала по оси y]*65536 + [координата конца по оси y]
356 Lrz 36
	mov	edx,dword op_border_color ;Цвет линии
355 Lrz 37
	int	0x40   ;рисование вертикальной левой линии квадрата (прямоугольника)
38
;
39
	mov	ebp,ebx	;сохраним регистр bx в регистре указателя базы
40
	;push	bx   ;втолкнуть в bx [координата начала по оси х]*65536 + [координата начала по оси x]
41
	add	ebx,op_size      ;[координата начала + длина стороны по оси х]
42
	ror	ebx,16          ;[координата начала + дина стороны по оси х]*65536
43
	add	ebx,op_size      ;[координата начала+длина стороны по оси х]*65536 + [координата начала+длина стороны по оси x]
44
	int	0x40
45
 
46
	mov	bx,bp		;восстановим значение регистра bx
47
	;pop	bx
48
	mov	cx,si		;сохраним значение регистра cx в регистр указатель
49
	;pop	cx
50
	int	0x40
51
	add	ecx,op_size	;добавим размер стороны
52
	mov	esi,ecx		;сохраним значение регистра cx в регистр указатель si
53
	;push	cx
54
	shl	ecx,16
55
	mov	cx,si
56
	;pop	cx
57
	int	0x40            ;нарисовали прямоугольник
58
 
59
	mov	eax,13          ;закрашиваем его. Функция 13 - нарисовать полосу
60
	movzx	ebx,word op_left	;загрузить в bx, положение по х
61
	add	ebx,1		;сдвинем на 1 т.е. прибавим 1 иначе затрется рамка
62
	shl	ebx,16		;сдвинем на 16 разрядов в лево (умножим на 65536)
63
	mov	bx,op_size	;прибавим длину стороны прямоугольника
64
	sub	ebx,1		;вычтем 1 т.к. иначе затрется рамка
65
	mov	bp,bx		;сохраним регистр bx в регистре указателя базы
66
	;push	bx
67
	movzx	ecx,word op_top	;загрузим координаты по y
68
	add	ecx,1		;сдвинем на 1 т.е. прибавим 1 иначе затрется рамка
69
	shl	ecx,16		;сдвинем на 16 разрядов в лево (умножим на 65536)
70
	mov	cx,bp		;восстановим значение регистра cx
71
	;pop	cx
356 Lrz 72
	mov	edx,dword [sc.work]	;загрузим цвет полосы
355 Lrz 73
	int	0x40            ;закрасили
74
 
356 Lrz 75
        mov	eax,dword op_optibox_gr
355 Lrz 76
	mov	dword eax,[eax]
77
        cmp	eax,edi
78
	jne	@f
79
	call	.draw_op  ;нарисовать включенный чек бокс
80
;----------------------------
81
;расчет куда будет произведен вывод текста
82
;----------------------------
83
@@:	movzx	ebx,word op_left	;загрузить значение х для чек бокса
84
	add	ebx,(op_size+op_text_margin) ;добавить размер стороны и расстояние на котором начнется вывод текста
85
	shl	ebx,16		;сдвинем на 16 разрядов в лево (умножим на 65536)
86
	mov	bx,op_top	;загрузим значение по y
87
	add	ebx,(op_size-9+2)	;добавим значение длины стороны -9+2
88
	mov	ecx,op_text_color	;загрузим цвет надписи
89
 
90
	mov	edx,op_text_ptr		;укажем адрес от куда нужно выводить строку
91
	movzx 	esi,word op_text_length ;Загрузим длину надписи в esi
92
	;внесем в eax значение вывода надписи на канву
93
	mov	eax,4
94
	int	0x40          	;Вывод
95
popa				;восстановить значения регистров из стека
96
ret				;выйдем из процедуры
97
 
98
.clear_op:			;очистка чек бокса
356 Lrz 99
	mov	edx,dword [sc.work]	;цвет внутри чек бокса
355 Lrz 100
	jmp	@f		;безусловный прыжок на нижнюю метку @@
101
 
102
.draw_op:            ;нарисовать включенный чек бокс
103
	mov	edx,op_border_color	;загрузить цвет
104
@@:
105
	movzx	ebx,word op_left	;загрузить координату по х
106
	add	ebx,(op_size/3)	;добавить (сторона прямоугольника/3)
107
	shl	ebx,16		;сдвинем на 16 разрядов в лево (умножим на 65536)
108
	mov	bx,(op_size/2)	;загрузить (сторона прямоугольника/2)
109
	mov	bp,bx		;сохраним регистр bx в регистре указателя базы
110
	;push	bx
111
	movzx	ecx,word op_top	;загрузить координату по у
112
	mov	eax,13		;в eax - значения функции для вывода полосы т.е. по сути прямоугольника, который отображает включенный компонент чек бокс
113
	add	ecx,(op_size/3)	;добавить (сторона прямоугольника/3)
114
	shl	ecx,16		;сдвинем на 16 разрядов в лево (умножим на 65536)
115
	mov	cx,bp		;загрузим значения регистра указателя базы в cx
116
	;pop	cx
117
	int	0x40		;вывод
118
ret				;выйти из процедуры
119
 
120
.mouse:                 ;обработка мыши
121
pusha
122
	mov	eax,37   	;будем что то делать если у нас что - нить нажато
123
	mov	ebx,2		;внести в регистр значение 2
124
	int	0x40		;проверка не нажал ли пользователь кнопку мышки
125
	test	eax,eax    ;проверка если у нас в eax=0, то установим флаг и выйдем
126
	jnz	@f         ;перейти на нижнюю метку @@
127
	popa			;если ничего не произошло, то восстановим значения регистров из стека
128
	ret                     ;выход
129
@@:
130
	movzx	esi,word op_text_length ;загрузить кол-во символов в текстовой строке
131
	;Умножение на 6 Быстрое умножение можно воспользоваться любым мз методов, но на старых Процессорах (386,486,P1)быстрее будет с инструкцией Lea
132
	;lea	esi,[eax*2+eax]
133
	;shl	eax,1
134
	imul	esi,6               ; или можно и так умножить на 6
356 Lrz 135
	xor	ebx,ebx
355 Lrz 136
        add	esi,op_text_margin   ;добавить 3 - расстояние от чек бокса до надписи
137
 
138
	mov	eax,37		;получим координаты мышки
356 Lrz 139
	inc	ebx		;добавить 1
355 Lrz 140
	int	0x40                ;получить координаты курсора относительно окна
141
 
142
	movzx	ebx,word op_top           ;загрузить в bx значение координаты у
143
	cmp	ax,bx               ;сравнить с с координатой курсора
144
	jl	.mouse_end          ;SF <> OF если меньше
145
	add	ebx,op_size          ;добавить размер
146
	cmp	ax,bx               ;сравнить
147
	jg	.mouse_end          ;ZF = 0 и SF = OF если больше
148
 
149
	shr	eax,16              ;разделим на 65536 или просто сдвинем биты на 16 значений
150
	movzx	ebx,word op_left          ;произведем аналогичное сравнение
151
	cmp	ax,bx		     ;сравнить регистры
152
	jl	.mouse_end	     ;если меньше
153
	add	ebx,op_size	     ;добавить длину стороны прямоугольника
356 Lrz 154
	add	ebx,esi		     ;Учесть в значении по х еще и длину надписи к чекбоксу
355 Lrz 155
	cmp	ax,bx		     ;стравнить регистры
156
	jg	.mouse_end	     ;если больше
356 Lrz 157
	mov	eax,dword op_optibox_gr
355 Lrz 158
        mov	[eax],edi
159
 
160
.mouse_end:
161
popa				  ;восстановить регистры из стека
162
ret				  ;выйти
163
}
164
 
356 Lrz 165
struc option_box left,top,border_color,text_color,text,text_length,point_gr,flags
355 Lrz 166
{	;структура параметров для чек бокса
167
.left: dw left	;+0	;положение по х
168
.top: dw top	;+2	;положение по у
169
.border_color: dd border_color ;+8	цвет рамки
170
.text_color: dd text_color     ;+12	цвет текста надписи
171
.text: dd text	     ;+16		адрес в коде программы где расположен текстр
172
.text_length: dw text_length ; +20	длина текста
173
.option_group: dd point_gr	;указатель на размещение edi - идентификатора optibox
174
}
356 Lrz 175
op_struc_size=22			;общая структура 24 байт
355 Lrz 176
op_flag_en=10b
177
macro draw_option_boxes start,end	;рисовать чек боксы
178
{
179
	mov	edi,start			;Указатель на начало данных чек боксов т.е. на начало данных первого чекбокса
180
	mov	ecx,((end-start)/op_struc_size) ;Количество чек боксов
181
@@:
182
	call	option_box.draw                  ;Отобразить чек бокс
183
	add	edi,op_struc_size               ;Указатель на последующие чек боксы  т.е. +28
184
	loop	@b	;прыгнуть если в ecx/cx значение не 0 на верхнюю @@
185
}
186
macro mouse_option_boxes start,end	;установка чек боксов, в зависимости от события
187
{
188
	mov	edi,start		; Указатель на начало данных чек боксов т.е. на начало данных первого чекбокса
189
	mov	ecx,((end-start)/op_struc_size)	;Количество чек боксов
190
@@:
191
	call	option_box.mouse		;проверка мышки и обработка событий
192
	add	edi,op_struc_size	;Указатель на последующие чек боксы
193
	loop	@b	;прыгнуть если в ecx/cx значение не 0 на верхнюю @@
194
 
195
       	mov	edi,start		; Указатель на начало данных чек боксов т.е. на начало данных первого чекбокса
196
	mov	ecx,((end-start)/op_struc_size)	;Количество чек боксов
197
 
198
.home:
356 Lrz 199
	mov	eax,[edi+18]	;op_optibox_gr
355 Lrz 200
        mov	dword eax,[eax]
201
 
202
        pusha
203
 
204
	cmp	eax,edi
205
	jne	@f
206
 
207
	call	option_box.draw_op
208
	jmp	.nxtm
209
@@:     call	option_box.clear_op
210
 
211
.nxtm:  popa
212
	add	edi,op_struc_size               ;Указатель на последующие чек боксы  т.е. +28
213
        loop 	.home
214
 
215
}