Все, что вам нужно сделать, - это объединить третий регион с вашим объединенным регионом в режиме, который даст желаемый результат. Возможные режимы описаны в документации функции .
. Ниже приведен пример измененной версии обработчика событий OnMouseUp
. Предполагается, что больший прямоугольник рисуется первым. Модификации включают учет подписи и границ для нарисованных прямоугольников (поскольку обработчик перемещения мыши предоставляет клиентские координаты, но SetWindowRegion
требуется область с координатами окна) и удаление областей, когда они больше не требуются.
procedure TForm1.FormMouseUp(Sender: TObject; Button: TMouseButton; Shift: TShiftState; X, Y: Integer);
var
Pt: TPoint;
I: Integer;
begin
FSelecting := false;
FSelection.Right := X;
FSelection.Bottom := Y;
Invalidate;
FSelection.NormalizeRect;
if not FSelection.IsEmpty then
begin
FRectangles.Enqueue(FSelection);
if FRectangles.Count = MAXRECTANGLECOUNT then
begin
Region := CreateRectRgn(0, 0, Width, Height);
Region2 := CreateRectRgnIndirect(FRectangles.Dequeue);
// offset region to account for caption and borders
Pt := ClientOrigin;
OffsetRgn(Region2, Pt.X - Left, Pt.Y - Top);
CombineRgn(Region, Region, Region2, RGN_DIFF);
DeleteObject(Region2);
Region2 := CreateRectRgnIndirect(FRectangles.Dequeue);
// offset region to account for caption and borders
OffsetRgn(Region2, Pt.X - Left, Pt.Y - Top);
CombineRgn(Region, Region, Region2, RGN_OR);
DeleteObject(Region2);
SetWindowRgn(Handle, Region, True);
DeleteObject(Region);
end;
end;
end;
.. и избавление от неиспользуемых целочисленных переменных (pos1 .. pos4).
После того, как задана область окна, из списка прямоугольников исключаются два используемых прямоугольника. Так как их было два, теперь пусто.