mirror of
https://gitlab.com/freepascal.org/lazarus/lazarus.git
synced 2025-08-10 15:56:10 +02:00
GTK2 ScrollWindowEx
git-svn-id: trunk@34872 -
This commit is contained in:
parent
8d75d1d603
commit
b46ea85bc3
@ -7386,8 +7386,9 @@ var
|
||||
Window: PGdkWindow;
|
||||
{$ifdef GTK_2_8}
|
||||
Region: PGdkRegion;
|
||||
Rect1: TGdkRectangle;
|
||||
Rect2: TRect;
|
||||
Rect1: TGdkRectangle; // full source rect
|
||||
Rect1a: TGdkRectangle; // source rect for clip
|
||||
Rect2: TRect; // area to invalidate
|
||||
WidgetInfo: PWidgetInfo;
|
||||
{$ENDIF}
|
||||
begin
|
||||
@ -7410,50 +7411,84 @@ begin
|
||||
Rect1.Y := 0; //Widget^.Allocation.Y;
|
||||
Rect1.width := Widget^.Allocation.Width;
|
||||
Rect1.height := Widget^.Allocation.Height;
|
||||
|
||||
WidgetInfo := GetWidgetInfo(Widget, False);
|
||||
if WidgetInfo <> nil then begin
|
||||
if (dy < 0) then begin
|
||||
if (WidgetInfo^.UpdateRect.Bottom > 0) then
|
||||
Rect1.Height := Min(Rect1.height, WidgetInfo^.UpdateRect.Top);
|
||||
Rect2 := Rect(0, Rect1.height + dy, Rect1.width, Widget^.Allocation.Height);
|
||||
end;
|
||||
if dy > 0 then begin
|
||||
Rect1.y := Max(Rect1.y, WidgetInfo^.UpdateRect.Bottom);
|
||||
Rect2 := Rect(0, 0, Rect1.width, Rect1.y + dy);
|
||||
end;
|
||||
end;
|
||||
DebugLn(['ScrollWindowEx A ', dbgs(Rect1),' dy=',dy, ' scroll=',dbgs(prcScroll^), ' clip=',dbgs(prcClip^)]);
|
||||
|
||||
if PrcScroll <> nil then
|
||||
begin
|
||||
Rect1.x := PrcScroll^.Left;
|
||||
Rect1.y := PrcScroll^.Top;
|
||||
Rect1.width := PrcScroll^.Right - PrcScroll^.Left;
|
||||
Rect1.height := PrcScroll^.Bottom - PrcScroll^.Top;
|
||||
if (PrcClip <> nil) and EqualRect(PrcClip^, PrcScroll^) then
|
||||
// do nothing
|
||||
else
|
||||
begin
|
||||
Region := gdk_region_rectangle(@Rect1);
|
||||
gdk_window_move_region(Window, Region, dx, dy);
|
||||
Rect1.x := Max(Rect1.x, PrcScroll^.Left);
|
||||
Rect1.y := Max(Rect1.y, PrcScroll^.Top);
|
||||
Rect1.width := Min(Rect1.width - Rect1.x, PrcScroll^.Right - PrcScroll^.Left);
|
||||
//Rect1.width := Min(Rect1.width - (Rect1.x - Widget^.Allocation.X), PrcScroll^.Right - PrcScroll^.Left);
|
||||
Rect1.height := Min(Rect1.height - Rect1.y, PrcScroll^.Bottom - PrcScroll^.Top);
|
||||
end;
|
||||
if (PrcClip <> nil) then begin
|
||||
// Limit the source rect, so it will fit into PrcClip
|
||||
Rect1a.x := Max(PrcClip^.Left - dx, Rect1.x);
|
||||
Rect1a.y := Max(PrcClip^.Top - dy, Rect1.y);
|
||||
Rect1a.width := Min(PrcClip^.Right - dx - Rect1.x, Rect1.width);
|
||||
Rect1a.height := Min(PrcClip^.Bottom - dy - Rect1.y, Rect1.height);
|
||||
end
|
||||
else
|
||||
Rect1a := Rect1;
|
||||
DebugLn(['ScrollWindowEx B ', dbgs(Rect1), ' ', dbgs(Rect1a)]);
|
||||
|
||||
WidgetInfo := GetWidgetInfo(Widget, False);
|
||||
if WidgetInfo <> nil then begin
|
||||
DebugLn(['ScrollWindowEx C ', dbgs(WidgetInfo^.UpdateRect)]);
|
||||
// exclude allready invalidated area
|
||||
if (WidgetInfo^.UpdateRect.Right >= Rect1a.x + Rect1a.width) and
|
||||
(WidgetInfo^.UpdateRect.Left <= Rect1a.x)
|
||||
then begin
|
||||
if (dy < 0) and (WidgetInfo^.UpdateRect.Bottom > 0) then
|
||||
Rect1a.Height := Min(Rect1a.y + Rect1a.height,
|
||||
WidgetInfo^.UpdateRect.Top) - Rect1a.y;
|
||||
if (dy > 0) and (Rect1a.y < WidgetInfo^.UpdateRect.Bottom) then begin
|
||||
Rect1a.height := Rect1a.height - (WidgetInfo^.UpdateRect.Bottom - Rect1a.y);
|
||||
Rect1a.y := WidgetInfo^.UpdateRect.Bottom;
|
||||
end;
|
||||
end;
|
||||
end else
|
||||
begin
|
||||
Region := gdk_region_rectangle(@Rect1);
|
||||
// TODO: content moved into currently invalidated space, may reduce the inval rect
|
||||
|
||||
if (WidgetInfo^.UpdateRect.Bottom >= Rect1a.y + Rect1a.height) and
|
||||
(WidgetInfo^.UpdateRect.Top <= Rect1a.y)
|
||||
then begin
|
||||
if (dx < 0) and (WidgetInfo^.UpdateRect.Right > 0) then
|
||||
Rect1a.width := Min(Rect1a.x + Rect1a.width,
|
||||
WidgetInfo^.UpdateRect.Left) - Rect1a.x;
|
||||
if (dx > 0) and (Rect1a.x < WidgetInfo^.UpdateRect.Right) then begin
|
||||
Rect1a.width := Rect1a.width - (WidgetInfo^.UpdateRect.Right - Rect1a.x);
|
||||
Rect1a.x := WidgetInfo^.UpdateRect.Right;
|
||||
end;
|
||||
end;
|
||||
end;
|
||||
DebugLn(['ScrollWindowEx D ', dbgs(Rect1a)]);
|
||||
|
||||
|
||||
if (Rect1a.height > 0) and (Rect1a.width > 0) then begin
|
||||
// Calculate area to invalidate
|
||||
// Rect1a.y may either be equal or greater than Rect1.y
|
||||
// Rect1a.height may either be equal or less than Rect1.height
|
||||
if (dy < 0) then
|
||||
Rect2 := Rect(Rect1.x, Rect1a.y + Rect1a.height + dy,
|
||||
Rect1.width, Rect1.y + Rect1.height);
|
||||
if dy > 0 then
|
||||
Rect2 := Rect(Rect1.x, Rect1.y,
|
||||
Rect1.width, Rect1a.y + dy);
|
||||
// Todo dx
|
||||
DebugLn(['ScrollWindowEx E ', dbgs(Rect2)]);
|
||||
|
||||
Region := gdk_region_rectangle(@Rect1a);
|
||||
gdk_window_move_region(Window, Region, dx, dy);
|
||||
end
|
||||
else begin
|
||||
// invalidate, nothing to scroll
|
||||
Rect2 := Rect(Rect1.x, Rect1.y, Rect1.x + Rect1.width, Rect1.y + Rect1.height);
|
||||
DebugLn(['ScrollWindowEx F ', dbgs(Rect2)]);
|
||||
end;
|
||||
|
||||
// Rect2 includes the Area at the scroll-in side of Rect1
|
||||
// gdk_window_move_region is supposed to have invalidated it, but some
|
||||
// implementations seem not to do this. (bug 14297)
|
||||
if (prcScroll <> nil) then
|
||||
begin
|
||||
if prcClip <> nil then
|
||||
Rect1 := GdkRectFromRect(prcClip^)
|
||||
else
|
||||
Rect1 := GdkRectFromRect(prcScroll^);
|
||||
gtk_widget_draw(Widget, @Rect1);
|
||||
end else
|
||||
if (dy <> 0) then
|
||||
InvalidateRect(hWnd, @Rect2, false);
|
||||
{$ELSE}
|
||||
|
Loading…
Reference in New Issue
Block a user