Глюки при работе с функцией CopyRect
В ходе работы над программой RitmInMe я предусмотрел несколько форматов вывода результата, но на практике для небольших стихов самым удобным оказалось элементарное PrintScreen. Естественно, скриншот приходилось обрезать, да и перед этой операцией окошко программы лучше было бы свести к необходимому минимуму... В общем, в контекстное меню окна редактирования была добавлена опция Mini-PrintScreen, которая реализовала всю эту нуднятину, да ещё и затирала ставшие лишними изображения кнопок в правом верхнем углу скриншота программы. Но тут влезло несовершенство программного обеспечения: функция CopyRect, с помощью которой я вырезал из полной копии экрана нужное мне, в некоторых случаях работала с артефактами – повторялись строки и/или столбцы пикселей (см. пример):
Глюк небольшой, но противно...
Для начала я заменил обращение к CopyRect на обычный цикл попиксельной переписи участка изображения. Артефакты исчезли, но работало это раздражающе медленно. Коллективный разум программистов на Delphi устами Google присоветовал мне аналог CopyRect – APIшную функцию BitBlt.
Вот полученный код (с заремленными неудачными вариантами):
DC := GetDC(0);
BackgroundCanvas := TCanvas.Create;
BackgroundCanvas.Handle := DC;
w0 := Form1.Left+3;
h0 := Form1.Top+3;
{
BGBitmap.Canvas.CopyRect(Rect(0,
0, BGbitmap.Width-1, BGbitmap.Height-1)
,BackgroundCanvas
,Rect(w0, h0, Form1.Left+BGbitmap.Width-1,
Form1.Top+BGbitmap.Height-1));
}
{
for j := 0 to BGbitmap.Height-1 do
for i := 0 to BGbitmap.Width-1 do
BGBitmap.Canvas.Pixels[i,j]
:= BackgroundCanvas.Pixels[i+w0,j+h0];
}
try
BitBlt(BGBitmap.Canvas.Handle,0,0, BGbitmap.Width-1, BGbitmap.Height-1
,BackgroundCanvas.Handle,w0, h0,SrcCopy);
except
//
end;
Резюме: В CopyRect работало растягивание, и мне бы следовало аккуратнее посчитать координаты исходного и результирующего прямоугольников (в исходном – добавка для координаты нижнего правого угла не "-1", а "+2"). Но... Я предпочёл применить функцию BitBlt, у которой размер прямоугольника задаётся только результирующим и растягивания заведомо нет.