Помогите исправить алгоритм поиска пикселя в TImage
Доброго времени суток. Скажу сразу - уже мало что соображаю, ибо долго сидел с этим кодом . Вроде и пустяк, но никак не могу развязать этот узел.
Мне надо найти определенный пиксель в компоненте TImage. Для этого я написал 2 функции.
Эта функция собственно ищет любой пиксель с заданным цветом и возвращает его координаты:
Код:
{тип на координаты курсора, будет использоваться в функции по поиску пикселя}
type
CursorXY = record
X : Integer;
Y : Integer;
Res : Boolean;
end;
{функция поиска пикселя
FindColor - цвет который будем искать
X, Y - координаты с которых будем начинать поиск
StopX, StopY - по каким координатам будем прекращать поиск}
function FindPixel(FindColor, X, Y, StopX, StopY: Integer): CursorXY;
var
X1 : Integer;
Flag : Boolean;
begin
Result.Res:= False;
Flag := False;
while Y <= StopY-1 do
begin
for X1:= X to StopX-1 do
begin
SetCursorPos(X1, Y);
if Form1.Image1.Picture.Bitmap.Canvas.Pixels[X1, Y] = FindColor then
begin
Result.X := X1; {возвращаем координаты найденного пикселя}
Result.Y := Y;
Result.Res := True; {а также информацию о том что пиксель найден}
Flag := True; {мы нашли наш пиксель}
Break; {значит выходим из цикла}
end;
end;
if Flag then {если завершили внутренний цикл - завершаем и внешний}
Break;
Inc(Y);
end;
end;
Эта функция сверяет относительно найденного пикселя последующий пиксели (типа по маске), чтобы найти именно тот пиксель который мне нужен, ибо с одинаковыми цветами таких пикселей много.
Код:
const
{массив цветов пикселей на начало фона картинки, на данной картинке это координаты 369, 226}
ArrayAreaPhoto : array[0..30] of Integer = (13224393, 13027014, 13290186,
12698049, 13224393, 12500670, 13158600, 12829635, 12895428, 12566463,
12961221, 13158600, 13487565, 12829635, 13224393, 12961221, 13224393,
13224393, 13355979, 13158600, 13290186, 13224393, 13290186, 12763842,
13487565, 13027014, 13619151, 12895428, 13224393, 13092807, 13290186);
{функция проверки по маске}
function FindAreaPhotoEX(X, Y: integer): Boolean;
var
i: Integer;
begin
for i:= 0 to 30 do
begin
if Form1.Image1.Picture.Bitmap.Canvas.Pixels[X, Y] <> ArrayAreaPhoto[i] then
begin
Result:= False;
Exit;
end;
Inc(X);
end;
Result:= True;
end;
Эти 2 функции по отдельности работают как надо. Может там конечно еще какие то нюансы алгоритма всплывут и можно будет улучшить - то дело такое. Проблема в том что не получается найти искомый пиксель, который я пытаюсь найти следующим образом:
Код:
{функция поиска начала фона под картинкой
X, Y - координаты начала поиска, обычно 0, 0
StopX, StopY - по каким координатам будем прекращать поиск}
function FindAreaPhoto(X, Y, StopX, StopY: Integer): CursorXY;
var
CursorPosition : CursorXY;
begin
Result.Res := False;
CursorPosition.X:= X;
CursorPosition.Y:= Y;
while True do {крутим пока что вечный цикл, пока не найдем маску}
begin
{я думаю что ошибка в этой строке, но ума не приложу что еще не так}
CursorPosition:= FindPixel(ArrayAreaPhoto[0], CursorPosition.X, CursorPosition.Y, StopX, StopY);
{если первый пиксель найден - проверяем маску}
if CursorPosition.Res and (CursorPosition.X < StopX-30) then
begin
{Если нашли маску - завершаем работу функции}
if FindAreaPhotoEX(CursorPosition.X, CursorPosition.Y) then
begin {но сюда мы почему то никогда не попадаем!}
Result.X := CursorPosition.X;
Result.Y := CursorPosition.Y;
Result.Res := True;
Exit;
end;
Inc(CursorPosition.X); {нам же в другой раз нужен следующий пиксель по координате X}
end;
end;
end;
Одним словом - я запутался. Прилагаю готовый проект, который можно скачать ниже. Перед тем как запускать, закоментируйте строку 70 SetCursorPos(X1, Y);, ибо будет по экрану самопроизвольно бегать мышка. Сделал для наглядности. Либо тогда останавливать проект горячими клавишами.
|