Int 33h - Работа с мышью.
Наиболее распространенным устройством ввода графической информации в ПЭВМ является мышь. При перемещении мыши и/или нажатии/отпускании кнопок мышь передает информацию в компью-тер о своих параметрах (величине перемещения и статусе кнопок). Существует много различных типов устройства типа мышь, отличаю-щихся как по принципу работы (механическая, оптомеханическая и оптическая), так и по способу общения (протоколу) с ПЭВМ. Для достижения некоторой унификации каждая мышь поставляется обычно вместе со своим драйвером - специальной программой, по-нимающей данный конкретный тип мыши и предоставляющей неко-торый (почти универсальный) интерфейс прикладным программам. При этом вся работа с мышью происходит через драйвер, который от-слеживает перемещения мыши, нажатие и отпускание кнопок мыши и обеспечивает работу с курсором мыши - специальным маркером на экране (обычно в виде стрелки), дублирующим все передвижения мы-ши и позволяющим пользователю указывать мышью на те или иные объекты на экране.
Работа с мышью реализуется через механизм прерываний. При-кладная программа осуществляет прерывание 33h, передавая в регист-рах необходимые параметры, и в регистрах же получает значения, воз-вращенные драйвером мыши.
Приводим набор функций для работы с мышью в соответствии со стандартом фирмы Microsoft. Ниже приведены используе-мые файлы Mouse.h и Mouse.cpp.
// File Mouse.h
#ifndef __MOUSE__
#define __MOUSE__
#define MOUSE_MOVE_MASK 0x01
#define MOUSE_LBUTTON_PRESS 0x02
#define MOUSE_LBUTTON_RELEASE 0x04
#define MOUSE_RBUTTON_PRESS 0x08
#define MOUSE_RBUTTON_RELEASE 0x10
#define MOUSE_MBUTTON_PRESS 0x20
#define MOUSE_MBUTTON_RELEASE 0x40
#define MOUSE_ALL_EVENTS Ox7F
struct MouseState {
int x, y;
int Buttons;
};
struct CursorShape {
unsigned AndMask [16];
unsigned XorMask [16];
int HotX, HotY;
};
typedef void ( *MouseHandler )( int, int, int, int );
int ResetMouse ();
void ShowModseCursor ();
void HideMouseCursor ();
void ReadMouseState ( MouseState& );
void MoveMouseCursor ( int, int );
void SetMouseHorzRange ( int, int );
void SetraouseVertRange ( int, int );
void SetMouseShape ( CursorShapeA );
void SetHldeRange ( int, int, int, int );
void SetMouseHandler ( MouseHandler, int = MOUSE_ALL_EVENTS );
void RerooveMouseHandler ();
#define ClearHideRange () ShowMouseCursor () #endif
// File Mouse.cpp #include <alloc.h> #include "Mouse.h"
#pragma inline
static MouseHandler CurHandler = NULL;
int ResetMouse ()
{
asm {
xor ax, ax int 33h
}
return _AX == OxFFFF; }
void ShowMouseCursor () {
asm {
mov ax, 1 int 33h
}
}
void HideMouseCursor ()
{
asm {
mov ax, 2 int 33h
}
}
void ReadMouseState ( MouseState& s ) {
asm {
mov ax, 3 int 33h
}
#if defined(__COMPACT__) || defined(__LARGE__) || defined(__HUGE__)
asm {
push es push di
les di, dword ptr s mov es:[di ], cx
mov es:[di+2], dx mov es:[di+4], bx
pop di pop es }
#else asm { push di
mov di, word ptr s mov [di ], cx mov [di+2], dx raov [di+4], bx pop di }
#endif
}
void MoveMouseCursor ( int x, int y ) {
asm {
mov ax, 4 mov cx, x raov dx, y int 33h } }
void SetHorzMouseRange ( int xmin, int xmax )
{
asm {
mov ax, 7 mov cx, xmin mov dx, xmax int 33h
}
}
void SetVertMouseRange ( int yrain, int ymax)
{
asm{
mov ax, 8
mov cx, ymin
mov dx, ymax
int 33h
}
}
void SetMouseShape ( CursorShape& c )
{
#if defined(__COMPACT ) || defined(__LARGE__) || defined(__HUGE__) asm {
push es
push di
les di, dword ptr c
mov bx, es:[di+16]
mov cx, es:[di+18] mov dx, d'i
mov ax, 9
int 33h
pop di
pop es
}
#else
asm {
push di
mov di, word ptr c
mov bx, [di+16]
mov cx, [di+18]
mov dx, di
mov ax, 9
int 33h
pop di
}
#endif }
void SetHideRange ( int x1, int y1, int x2, int y2.)
{
asm {
push si
push di
mov ax, 10h
mov cx, x1
mov dx,y1
mov si, x2
mov di, y2
int 33h
pop di pop si
}
}
static void far MouseStub () {
asm {
push ds // preserve ds
push ax // preserve ax
mov ax, seg CurHandler
mov ds, ax
pop ax // restore ax
push dx // у
push cx // x
push bx // button state
push ax // event mask
call CurHandler
add sp, 8 // clear stack
pop ds
}
}
void SetMouseHandler ( MouseHandler h, int mask )
{
void far *p = MouseStub;
CurHandler = h; asm {
push es
mov ax, OCh
mov cx, mask
les dx, p
int 33h
pop es
}
}
void ReraoveMouseHandler () {
CurHandler = NULL;
asm {
mov ax, OCh
mov cx, 0 int 33h } }
Инициализация и проверка наличия мыши
Функция ResetMouse производит инициализацию мыши и воз-вращает ненулевое значение, если мышь обнаружена.
Высветить на экране курсор мыши
Функция ShowMouseCursor выводит на экран курсор мыши. При этом курсор перемещается синхронно с перемещениями самой мыши.
Функция Hide Mouse Cursor убирает курсор мыши с экрана. Одна-ко при этом драйвер мыши продолжает отслеживать ее перемещения, причем к этой функции возможны вложенные вызовы. Каждый вызов функции HideMouseCursor уменьшает значение внутреннего счетчика драйвера на единицу, каждый вызов функции ShowMouseCursor уве-личивает счетчик. Курсор мыши виден только, когда значение счетчи-ка равно 0 (изначально счетчик равен -1).
При работе с мышью следует иметь в виду, что выводить изобра-жение поверх курсора мыши нельзя. Поэтому, если нужно произвести вывод на экран в том месте, где может находиться курсор мыши, сле-дует убрать его с экрана, выполнить требуемый вывод и затем снова вывести курсор мыши на экран.
Прочесть состояние мыши (ее координаты и состояние кнопок)
Функция ReadMouse State возвращает состояние мыши в полях структуры MouseState. Поля х и у содержат текущие координаты курсора в пикселах, поле Buttons определяет, какие кнопки нажаты. Установленный бит 0 соответствует нажатой левой кнопке, бит 1 -правой, и бит 2 - средней.
Передвинуть курсор мыши в точку с заданными координатами
Функция MoveMouseCursor служит для установки курсора мыши в точку с заданными координатами.
Установка области перемещения курсора
При необходимости можно ограничить область перемещения мы-ши по экрану. Для задания области возможного перемещения курсора по горизонтали служит функция SetHorzMouseRange, для задания об-ласти перемещения по вертикали - функция SetVertMouseRange.
Задание формы курсора
В графических режимах высокого разрешения (640 на 350 пиксе-лов и выше) курсор задается двумя масками 16 на 16 бит и смещением координат курсора от верхнего левого угла масок. Каждую из масок можно трактовать как изображение, составленное из пикселов белого (соответствующий бит равен 1) и черного (соответствующий бит равен 0) цветов. При выводе курсора на экран сначала на содержимое экра-на накладывается (с использованием операции AND_PUT) первая маска, называемая иногда AND-маской, а затем на то же самое место накладывается вторая маска (с использованием операции XOR_PUT). Все необходимые параметры для задания курсора мыши содержатся в полях структуры CursorShape. .Устанавливается форма курсора при помощи функции SetMouseShape.
Установка области гашения
Иногда желательно задать на экране область, при попадании в которую курсор мыши автоматически гасится. Для этого использу-ется функция SetHideRange. Но при выходе курсора из области гаше-ния он не восстанавливается. Поэтому для восстановления нормаль-ной работы курсора необходимо вызвать функцию ShowMouseCursor, независимо от того, попал ли курсор в область гашения или нет.
Установка обработчика событий
Вместо того, чтобы все время опрашивать драйвер мыши, можно передать драйверу адрес функции, которую нужно вызывать при на-ступлении заданных событий. Для установки этой функции следует воспользоваться функцией Set Mouse Handler, где в качестве первого параметра выступает указатель на функцию, а второй параметр задает события, при наступлении которых следует вызвать переданную функцию. События задаются посредством битовой маски. Возможные события определяются при помощи символических констант MOUSE_MOVE_MASK, MOUSE_LBUTTON_PRESS и других. Тре-буемые условия соединяются побитовой операцией ИЛИ, Передавае-мая функция получает 4 параметра - маску события, повлекшего за собой вызов функции, маску состояния кнопок мыши и текущие ко-ординаты курсора. По окончании работы программы необходимо обя-зательно убрать обработчик событий (при помощи функции RemoveMouseHandler).
Ниже приводится пример простейшей программы, устанавливаю- щей обработчик событий мыши на нажатие правой кнопки мыши и задающей свою форму курсора.
// File Example1. срр
#include <bios.h>
#include <conio.h>
#include "Mouse.h"
CursorShape с = {
0x0FFF, 0x07FF, 0x01FF, 0x007F, 0x801F, 0xC007,
0xC001, 0xE000, 0xE0FF, 0xF0FF, 0xF0FF, 0xF5FF,
0xF8FF, 0xFCFF, 0xFCFF, 0xFEFF, 0x0000, 0x6000,
0x7800, 0x3E00, 0x3F80, 0x1FE0, 0x1FF8, 0x0FFE,
0x0F00, 0x0700, 0x0700, 0x0300, 0x0300, 0x0100,
0x0100, 0x0000, 1,1
};
int DoneFlag = 0;
void SetViOeoMode ( int mode )
asm {
mov ax, mode
int 1Oh
}
#pragma argsused void
WaitPress (int mask, int button, int x, int у) {
if (mask & MOUSE_R8UTTON_PRESS ) DoneFlag = 1;
}
main ()
{
SetVideoMode ( 0x12 );
ResetMouse ();
StiowMouseCursor ();
SetMouseShape ( с );
SetMouseHandler ( WaitPress );
MoveMouseCursor ( 0, 0 );
while ( !DoneFlag )
HideMouseCursor (); ReraoveMouseHandler (); SetVideoMode ( 3 );
}
Оставить комментарий
Комментарии


//мышь на ассемблере
_asm{
mov ax, 4
mov cx, x
raov dx, y
int 33h };
выдает
1>c:\users\root\documents\visual studio 2008\projects\streamcapture\streamcapture\stream.cpp(116) : error C2443: operand size conflict
1>c:\users\root\documents\visual studio 2008\projects\streamcapture\streamcapture\stream.cpp(117) : warning C4405: 'dx' : identifier is reserved word
1>c:\users\root\documents\visual studio 2008\projects\streamcapture\streamcapture\stream.cpp(117) : error C2400: inline assembler syntax error in 'opcode'; found 'dx'

