diff options
| author | jpbruyere <jp.bruyere@hotmail.com> | 2016-02-12 17:47:36 +0100 |
|---|---|---|
| committer | jpbruyere <jp.bruyere@hotmail.com> | 2016-02-12 17:47:36 +0100 |
| commit | 970a3f7239d5e57eb011295cda9eee015bbe97f4 (patch) | |
| tree | 7d09918825c72a7e0f58b5d8b174f27805cdfcc5 | |
| parent | 44caf51048bde7e9daf78acc779278642c798748 (diff) | |
| parent | d1e33e2f2212e2f9a60caebd3eb839b36357b2c6 (diff) | |
Merge branch 'NewClipping'
| -rw-r--r-- | Tests/GOLIBTest_4.cs | 2 | ||||
| -rw-r--r-- | Tests/GOLIBTests.cs | 7 | ||||
| -rwxr-xr-x | Tests/Interfaces/clip0.crow | 10 | ||||
| -rwxr-xr-x | Tests/Interfaces/clip1.crow | 25 | ||||
| -rwxr-xr-x | Tests/Interfaces/clip2.crow | 15 | ||||
| -rwxr-xr-x | Tests/Interfaces/clip3.crow | 34 | ||||
| -rwxr-xr-x | Tests/Interfaces/clip4.crow | 58 | ||||
| -rw-r--r-- | Tests/Tests.csproj | 15 | ||||
| -rw-r--r-- | src/GraphicObjects/Border.cs | 9 | ||||
| -rw-r--r-- | src/GraphicObjects/GraphicObject.cs | 112 | ||||
| -rw-r--r-- | src/GraphicObjects/Group.cs | 73 | ||||
| -rw-r--r-- | src/GraphicObjects/IGOLibHost.cs | 1 | ||||
| -rw-r--r-- | src/GraphicObjects/ILayoutable.cs | 1 | ||||
| -rw-r--r-- | src/GraphicObjects/Label.cs | 3 | ||||
| -rw-r--r-- | src/GraphicObjects/PrivateContainer.cs | 78 | ||||
| -rw-r--r-- | src/GraphicObjects/RadioButton.cs | 3 | ||||
| -rw-r--r-- | src/GraphicObjects/Scroller.cs | 53 | ||||
| -rw-r--r-- | src/GraphicObjects/TemplatedControl.cs | 5 | ||||
| -rw-r--r-- | src/GraphicObjects/Window.cs | 2 | ||||
| -rw-r--r-- | src/OpenTKGameWindow.cs | 128 | ||||
| -rw-r--r-- | src/Rectangles.cs | 2 |
21 files changed, 433 insertions, 203 deletions
diff --git a/Tests/GOLIBTest_4.cs b/Tests/GOLIBTest_4.cs index 8fbfe4ec..9c8fe385 100644 --- a/Tests/GOLIBTest_4.cs +++ b/Tests/GOLIBTest_4.cs @@ -171,7 +171,7 @@ namespace test { if (!e.Mouse.IsButtonDown (MouseButton.Left)||sender!=c) return; - redrawClip.AddRectangle (c.ScreenCoordinates(c.Slot)); + clipping.AddRectangle (c.ScreenCoordinates(c.Slot)); c.Left += e.XDelta; c.Top += e.YDelta; c.registerForGraphicUpdate (); diff --git a/Tests/GOLIBTests.cs b/Tests/GOLIBTests.cs index fbf76ea2..b87bfe75 100644 --- a/Tests/GOLIBTests.cs +++ b/Tests/GOLIBTests.cs @@ -37,6 +37,12 @@ namespace test int frameCpt = 0; int idx = 0; string[] testFiles = { + "testWindow.goml", + "clip4.crow", + "clip3.crow", + "clip2.crow", + "clip0.crow", + "clip1.crow", "0.crow", "5.crow", "testCombobox.goml", @@ -64,7 +70,6 @@ namespace test "testWindow2.goml", "testWindow3.goml", - "testWindow.goml", "testCheckbox.goml", "testLabel.goml", "testAll.goml", diff --git a/Tests/Interfaces/clip0.crow b/Tests/Interfaces/clip0.crow new file mode 100755 index 00000000..2ebea9ff --- /dev/null +++ b/Tests/Interfaces/clip0.crow @@ -0,0 +1,10 @@ +<?xml version="1.0"?> +<Container Fit="true" Margin="50" Background="LimeGreen" CacheEnabled="false" + HorizontalAlignment="Right" VerticalAlignment="Bottom" + MouseEnter="{Background=Gray}" + MouseLeave="{Background=LimeGreen}"> + <Label HorizontalAlignment="Center" VerticalAlignment="Center" CacheEnabled="false" + MouseEnter="{Background=DimGray}" Width="100" + MouseLeave="{Background=BlueCrayola}" + Margin="10" Text="{drawing}" Background="BlueCrayola"/> + </Container>
\ No newline at end of file diff --git a/Tests/Interfaces/clip1.crow b/Tests/Interfaces/clip1.crow new file mode 100755 index 00000000..4aeb7fde --- /dev/null +++ b/Tests/Interfaces/clip1.crow @@ -0,0 +1,25 @@ +<?xml version="1.0"?> +<Container Fit="true" Margin="20" Background="SkyBlue" CacheEnabled="false" + HorizontalAlignment="Right" VerticalAlignment="Bottom" + MouseEnter="{Background=LightGray}" + MouseLeave="{Background=SkyBlue}"> + <Container Fit="true" Margin="20" Background="Red" CacheEnabled="true" + HorizontalAlignment="Right" VerticalAlignment="Bottom" + MouseEnter="{Background=White}" + MouseLeave="{Background=Red}"> + <Container Fit="true" Margin="20" Background="Yellow" CacheEnabled="false" + HorizontalAlignment="Right" VerticalAlignment="Bottom" + MouseEnter="{Background=Blue}" + MouseLeave="{Background=Yellow}"> + <Container Margin="50" Background="LimeGreen" CacheEnabled="true" + HorizontalAlignment="Right" VerticalAlignment="Bottom" + MouseEnter="{Background=Gray}" + MouseLeave="{Background=LimeGreen}"> + <Label HorizontalAlignment="Center" VerticalAlignment="Center" CacheEnabled="true" + MouseEnter="{Background=DimGray}" + MouseLeave="{Background=BlueCrayola}" + Margin="1" Text="{drawing}" Background="BlueCrayola"/> + </Container> + </Container> + </Container> + </Container>
\ No newline at end of file diff --git a/Tests/Interfaces/clip2.crow b/Tests/Interfaces/clip2.crow new file mode 100755 index 00000000..4f95bf90 --- /dev/null +++ b/Tests/Interfaces/clip2.crow @@ -0,0 +1,15 @@ +<?xml version="1.0"?> +<Group Fit="true" Margin="50" Background="Yellow" CacheEnabled="true" + HorizontalAlignment="Right" VerticalAlignment="Bottom" + MouseEnter="{Background=DimGray}" + MouseLeave="{Background=Yellow}"> +<Group Width="300" Height="200" Margin="50" Background="LimeGreen" CacheEnabled="false" + HorizontalAlignment="Right" VerticalAlignment="Bottom" + MouseEnter="{Background=Gray}" + MouseLeave="{Background=LimeGreen}"> + <Label Left="10" HorizontalAlignment="Right" VerticalAlignment="Center" CacheEnabled="true" + MouseEnter="{Background=DimGray}" Width="100" + MouseLeave="{Background=BlueCrayola}" + Margin="10" Text="{drawing}" Background="BlueCrayola"/> + </Group> + </Group>
\ No newline at end of file diff --git a/Tests/Interfaces/clip3.crow b/Tests/Interfaces/clip3.crow new file mode 100755 index 00000000..b08216c0 --- /dev/null +++ b/Tests/Interfaces/clip3.crow @@ -0,0 +1,34 @@ +<?xml version="1.0"?> +<Group Fit="true" Margin="50" Background="Yellow" CacheEnabled="true" + HorizontalAlignment="Right" VerticalAlignment="Bottom" + MouseEnter="{Background=DimGray}" + MouseLeave="{Background=Yellow}"> + <HorizontalStack Fit="true"> + <VerticalStack Fit="true" Margin="50" Background="LimeGreen" CacheEnabled="false" + HorizontalAlignment="Right" VerticalAlignment="Bottom" + MouseEnter="{Background=Gray}" + MouseLeave="{Background=LimeGreen}"> + <Label HorizontalAlignment="Center" VerticalAlignment="Center" CacheEnabled="true" + MouseEnter="{Background=DimGray}" Width="100" + MouseLeave="{Background=BlueCrayola}" + Margin="10" Text="{fps}" Background="BlueCrayola"/> + <Label HorizontalAlignment="Center" VerticalAlignment="Center" CacheEnabled="true" + MouseEnter="{Background=DimGray}" Width="100" + MouseLeave="{Background=BlueCrayola}" + Margin="10" Text="{drawing}" Background="BlueCrayola"/> + </VerticalStack> + <VerticalStack Fit="true" Margin="50" Background="LimeGreen" CacheEnabled="false" + HorizontalAlignment="Right" VerticalAlignment="Bottom" + MouseEnter="{Background=Gray}" + MouseLeave="{Background=LimeGreen}"> + <Label HorizontalAlignment="Center" VerticalAlignment="Center" CacheEnabled="true" + MouseEnter="{Background=DimGray}" Width="100" + MouseLeave="{Background=BlueCrayola}" + Margin="10" Text="{fpsMax}" Background="BlueCrayola"/> + <Label HorizontalAlignment="Center" VerticalAlignment="Center" CacheEnabled="true" + MouseEnter="{Background=DimGray}" Width="100" + MouseLeave="{Background=BlueCrayola}" + Margin="10" Text="{fpsMin}" Background="BlueCrayola"/> + </VerticalStack> + </HorizontalStack> + </Group>
\ No newline at end of file diff --git a/Tests/Interfaces/clip4.crow b/Tests/Interfaces/clip4.crow new file mode 100755 index 00000000..69fc7f12 --- /dev/null +++ b/Tests/Interfaces/clip4.crow @@ -0,0 +1,58 @@ +<?xml version="1.0"?> +<Border Fit="true" BorderWidth="2" > +<Scroller CornerRadius="2" VerticalScrolling="true" Height="200" Width="300" Background="DimGray" Margin="2"> + <VerticalStack Margin="10" VerticalAlignment="Top" Fit="true" Background="vgradient|0:BlueCrayola|1:Black" > + <Label MouseEnter="{Background=Gray}" MouseLeave="{Background=hgradient|0:DarkRed|1:Transparent}" Margin="5" Background="hgradient|0:DarkRed|1:Transparent" Font="droid,20" Text="label 1"/> + <Label MouseEnter="{Background=Gray}" MouseLeave="{Background=hgradient|0:DarkRed|1:Transparent}" Margin="5" Background="hgradient|0:DarkRed|1:Transparent" Font="droid,20" Text="label 2"/> + <Label MouseEnter="{Background=Gray}" MouseLeave="{Background=hgradient|0:DarkRed|1:Transparent}" Margin="5" Background="hgradient|0:DarkRed|1:Transparent" Font="droid,20" Text="label 3"/> + <Label MouseEnter="{Background=Gray}" MouseLeave="{Background=hgradient|0:DarkRed|1:Transparent}" Margin="5" Background="hgradient|0:DarkRed|1:Transparent" Font="droid,20" Text="label 4"/> + <Label MouseEnter="{Background=Gray}" MouseLeave="{Background=hgradient|0:DarkRed|1:Transparent}" Margin="5" Background="hgradient|0:DarkRed|1:Transparent" Font="droid,20" Text="label 5"/> + <Label MouseEnter="{Background=Gray}" MouseLeave="{Background=hgradient|0:DarkRed|1:Transparent}" Margin="5" Background="hgradient|0:DarkRed|1:Transparent" Font="droid,20" Text="label 6"/> + <Label MouseEnter="{Background=Gray}" MouseLeave="{Background=hgradient|0:DarkRed|1:Transparent}" Margin="5" Background="hgradient|0:DarkRed|1:Transparent" Font="droid,20" Text="label 7"/> + <Label MouseEnter="{Background=Gray}" MouseLeave="{Background=hgradient|0:DarkRed|1:Transparent}" Margin="5" Background="hgradient|0:DarkRed|1:Transparent" Font="droid,20" Text="label 8"/> + <Label MouseEnter="{Background=Gray}" MouseLeave="{Background=hgradient|0:DarkRed|1:Transparent}" Margin="5" Background="hgradient|0:DarkRed|1:Transparent" Font="droid,20" Text="label 9"/> + <Label MouseEnter="{Background=Gray}" MouseLeave="{Background=hgradient|0:DarkRed|1:Transparent}" Margin="5" Background="hgradient|0:DarkRed|1:Transparent" Font="droid,20" Text="label 10"/> + <Label MouseEnter="{Background=Gray}" MouseLeave="{Background=hgradient|0:DarkRed|1:Transparent}" Margin="5" Background="hgradient|0:DarkRed|1:Transparent" Font="droid,20" Text="label 11"/> + <Label MouseEnter="{Background=Gray}" MouseLeave="{Background=hgradient|0:DarkRed|1:Transparent}" Margin="5" Background="hgradient|0:DarkRed|1:Transparent" Font="droid,20" Text="label 12"/> + <Label MouseEnter="{Background=Gray}" MouseLeave="{Background=hgradient|0:DarkRed|1:Transparent}" Margin="5" Background="hgradient|0:DarkRed|1:Transparent" Font="droid,20" Text="label 13"/> + <Label MouseEnter="{Background=Gray}" MouseLeave="{Background=hgradient|0:DarkRed|1:Transparent}" Margin="5" Background="hgradient|0:DarkRed|1:Transparent" Font="droid,20" Text="label 14"/> + <Label MouseEnter="{Background=Gray}" MouseLeave="{Background=hgradient|0:DarkRed|1:Transparent}" Margin="5" Background="hgradient|0:DarkRed|1:Transparent" Font="droid,20" Text="label 15"/> + <Label MouseEnter="{Background=Gray}" MouseLeave="{Background=hgradient|0:DarkRed|1:Transparent}" Margin="5" Background="hgradient|0:DarkRed|1:Transparent" Font="droid,20" Text="label 16"/> + <Label MouseEnter="{Background=Gray}" MouseLeave="{Background=hgradient|0:DarkRed|1:Transparent}" Margin="5" Background="hgradient|0:DarkRed|1:Transparent" Font="droid,20" Text="label 17"/> + <Label MouseEnter="{Background=Gray}" MouseLeave="{Background=hgradient|0:DarkRed|1:Transparent}" Margin="5" Background="hgradient|0:DarkRed|1:Transparent" Font="droid,20" Text="label 18"/> + <Label MouseEnter="{Background=Gray}" MouseLeave="{Background=hgradient|0:DarkRed|1:Transparent}" Margin="5" Background="hgradient|0:DarkRed|1:Transparent" Font="droid,20" Text="label 19"/> + <Label MouseEnter="{Background=Gray}" MouseLeave="{Background=hgradient|0:DarkRed|1:Transparent}" Margin="5" Background="hgradient|0:DarkRed|1:Transparent" Font="droid,20" Text="label 20"/> + <Label MouseEnter="{Background=Gray}" MouseLeave="{Background=hgradient|0:DarkRed|1:Transparent}" Margin="5" Background="hgradient|0:DarkRed|1:Transparent" Font="droid,20" Text="label 21"/> + <Label MouseEnter="{Background=Gray}" MouseLeave="{Background=hgradient|0:DarkRed|1:Transparent}" Margin="5" Background="hgradient|0:DarkRed|1:Transparent" Font="droid,20" Text="label 22"/> + <Label MouseEnter="{Background=Gray}" MouseLeave="{Background=hgradient|0:DarkRed|1:Transparent}" Margin="5" Background="hgradient|0:DarkRed|1:Transparent" Font="droid,20" Text="label 23"/> + <Label MouseEnter="{Background=Gray}" MouseLeave="{Background=hgradient|0:DarkRed|1:Transparent}" Margin="5" Background="hgradient|0:DarkRed|1:Transparent" Font="droid,20" Text="label 24"/> + <Label MouseEnter="{Background=Gray}" MouseLeave="{Background=hgradient|0:DarkRed|1:Transparent}" Margin="5" Background="hgradient|0:DarkRed|1:Transparent" Font="droid,20" Text="label 25"/> + </VerticalStack> +</Scroller> +</Border> +<!--<VerticalStack Fit="true" Margin="50" Background="LimeGreen" CacheEnabled="false" + HorizontalAlignment="Right" VerticalAlignment="Bottom" + MouseEnter="{Background=Gray}" + MouseLeave="{Background=LimeGreen}"> + + <CheckBox Margin="20" Background="BlueCrayola"/> + <CheckBox/> + <CheckBox/> + <CheckBox/> + <CheckBox/> + <RadioButton/> + <RadioButton/> + <RadioButton/> + <RadioButton/> + <RadioButton/> + <CheckBox/> + + <Label HorizontalAlignment="Center" VerticalAlignment="Center" CacheEnabled="true" + MouseEnter="{Background=DimGray}" Width="100" + MouseLeave="{Background=BlueCrayola}" + Margin="10" Text="{fps}" Background="BlueCrayola"/> + <Label HorizontalAlignment="Center" VerticalAlignment="Center" CacheEnabled="true" + MouseEnter="{Background=DimGray}" Width="100" + MouseLeave="{Background=BlueCrayola}" + Margin="10" Text="{drawing}" Background="BlueCrayola"/> + </VerticalStack>-->
\ No newline at end of file diff --git a/Tests/Tests.csproj b/Tests/Tests.csproj index cbb628a7..091b535c 100644 --- a/Tests/Tests.csproj +++ b/Tests/Tests.csproj @@ -224,6 +224,21 @@ <None Include="Interfaces\testStacks.crow"> <CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory> </None> + <None Include="Interfaces\clip0.crow"> + <CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory> + </None> + <None Include="Interfaces\clip1.crow"> + <CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory> + </None> + <None Include="Interfaces\clip2.crow"> + <CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory> + </None> + <None Include="Interfaces\clip3.crow"> + <CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory> + </None> + <None Include="Interfaces\clip4.crow"> + <CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory> + </None> </ItemGroup> <ItemGroup> <Folder Include="Interfaces\" /> diff --git a/src/GraphicObjects/Border.cs b/src/GraphicObjects/Border.cs index 58ccff33..7011690e 100644 --- a/src/GraphicObjects/Border.cs +++ b/src/GraphicObjects/Border.cs @@ -62,6 +62,15 @@ namespace Crow CairoHelpers.CairoRectangle(gr, rBack, CornerRadius); gr.Stroke (); } + + gr.Save (); + //clip to client zone + CairoHelpers.CairoRectangle (gr, ClientRectangle, CornerRadius); + gr.Clip (); + + if (child != null) + child.Paint (ref gr); + gr.Restore (); } #endregion } diff --git a/src/GraphicObjects/GraphicObject.cs b/src/GraphicObjects/GraphicObject.cs index 14516dba..24fd852a 100644 --- a/src/GraphicObjects/GraphicObject.cs +++ b/src/GraphicObjects/GraphicObject.cs @@ -31,6 +31,9 @@ namespace Crow internal List<Binding> Bindings = new List<Binding> (); internal int layoutingTries = 0; + Rectangles clipping = new Rectangles(); + public Rectangles Clipping { get { return clipping; }} + #region IValueChange implementation public event EventHandler<ValueChangeEventArgs> ValueChanged; public virtual void NotifyValueChanged(string MemberName, object _value) @@ -121,15 +124,7 @@ namespace Crow [XmlIgnore]public ILayoutable Parent { get { return _parent; } set { -// if (_parent == value) -// return; -// if (_parent != null) -// ClearBinding (); -// _parent = value; -// -// if (DataSource != null) -// ResolveBindings (); } } @@ -149,21 +144,19 @@ namespace Crow get { return Parent == null ? null : Parent.HostContainer; } } public virtual Rectangle ContextCoordinates(Rectangle r){ - return - Parent.ContextCoordinates (r);// + ClientRectangle.Position; + GraphicObject go = Parent as GraphicObject; + if (go == null) + return r + Parent.ClientRectangle.Position; + return go.CacheEnabled ? + r + Parent.ClientRectangle.Position : + Parent.ContextCoordinates (r); } public virtual Rectangle ScreenCoordinates (Rectangle r){ return Parent.ScreenCoordinates(r) + Parent.getSlot().Position + Parent.ClientRectangle.Position; } - public virtual Rectangle getSlot() - { - return Slot; - } - public virtual Rectangle getBounds() - { - return Bounds; - } + public virtual Rectangle getSlot() => Slot; + public virtual Rectangle getBounds() => Bounds; #endregion #region EVENT HANDLERS @@ -478,14 +471,21 @@ namespace Crow public virtual bool Contains(GraphicObject goToFind){ return false; } - - public virtual void registerClipRect() - { - HostContainer.redrawClip.AddRectangle (ScreenCoordinates(Slot)); + public virtual void RegisterClip(Rectangle clip){ + if (CacheEnabled && bmp != null) + Clipping.AddRectangle (clip + ClientRectangle.Position); + Parent.RegisterClip (clip + Slot.Position + ClientRectangle.Position); + } +// public virtual void registerClipRect(Rectangle clip) +// { +// Rectangle tmp = ContextCoordinates (clip); +// if (CacheEnabled) { +// } + //HostContainer.redrawClip.AddRectangle (ScreenCoordinates(Slot)); //this clipping should take only last painted slots on each level in ancestor tree which //is not the case for now. - HostContainer.redrawClip.AddRectangle (ScreenCoordinates(LastPaintedSlot)); - } + //HostContainer.redrawClip.AddRectangle (ScreenCoordinates(LastPaintedSlot)); + //} /// <summary> /// Clear chached object and add clipping region in redraw list of interface /// </summary> @@ -502,12 +502,6 @@ namespace Crow { if (IsQueuedForRedraw) return; - //test if this speed up a lot to cancel clipping for an uncached group - Group p = Parent as Group; - if (p != null) { - if (p.bmp == null) - return; - } if (HostContainer == null) return; HostContainer.gobjsToRedraw.Add (this); @@ -734,9 +728,9 @@ namespace Crow } /// <summary> - /// Interfal drawing context creation on a cached surface limited to slot size + /// Internal drawing context creation on a cached surface limited to slot size /// this trigger the effective drawing routine </summary> - protected virtual void UpdateGraphic () + protected virtual void RecreateCache () { int stride = 4 * Slot.Width; @@ -752,17 +746,34 @@ namespace Crow draw.Flush (); } } + protected virtual void UpdateCache(Context ctx){ + Rectangle rb = Slot + Parent.ClientRectangle.Position; + using (ImageSurface cache = new ImageSurface (bmp, Format.Argb32, Slot.Width, Slot.Height, 4 * Slot.Width)) { + // //TODO:improve equality test for basic color and Fill + // if (this.Background is SolidColor) { + // if ((this.Background as SolidColor).Equals (Color.Clear)) { + // ctx.Save (); + // ctx.Operator = Operator.Clear; + // ctx.Rectangle (rb); + // ctx.Fill (); + // ctx.Restore (); + // } + // } + ctx.SetSourceSurface (cache, rb.X, rb.Y); + ctx.Paint (); + } + //Clipping.clearAndClip (ctx); + Clipping.Reset(); + } /// <summary> Chained painting routine on the parent context of the actual cached version /// of the widget </summary> - public virtual void Paint (ref Context ctx, Rectangles clip = null) + public virtual void Paint (ref Context ctx) { if (!Visible) return; LastPaintedSlot = Slot; - Rectangle rb = Parent.ContextCoordinates (Slot); - if (cacheEnabled) { if (Slot.Width > Interface.MaxCacheSize || Slot.Height > Interface.MaxCacheSize) cacheEnabled = false; @@ -770,28 +781,19 @@ namespace Crow if (cacheEnabled) { if (bmp == null) - UpdateGraphic (); + RecreateCache (); - using (ImageSurface source = new ImageSurface (bmp, Format.Argb32, Slot.Width, Slot.Height, 4 * Slot.Width)) { - //TODO:improve equality test for basic color and Fill - if (this.Background is SolidColor) { - if ((this.Background as SolidColor).Equals (Color.Clear)) { - ctx.Save (); - ctx.Operator = Operator.Clear; - ctx.Rectangle (rb); - ctx.Fill (); - ctx.Restore (); - } - } - ctx.SetSourceSurface (source, rb.X, rb.Y); - ctx.Paint (); - } - return; + UpdateCache (ctx); + } else { + Rectangle rb = Slot + Parent.ClientRectangle.Position; + ctx.Save (); + + ctx.Translate (rb.X, rb.Y); + + onDraw (ctx); + + ctx.Restore (); } - ctx.Save (); - ctx.Translate (rb.X, rb.Y); - onDraw (ctx); - ctx.Restore (); } #endregion diff --git a/src/GraphicObjects/Group.cs b/src/GraphicObjects/Group.cs index 9d9abbc6..e1e95579 100644 --- a/src/GraphicObjects/Group.cs +++ b/src/GraphicObjects/Group.cs @@ -204,66 +204,53 @@ namespace Crow break; } } - public override Rectangle ContextCoordinates(Rectangle r){ - return r + ClientRectangle.Position; - } protected override void onDraw (Context gr) { base.onDraw (gr); + gr.Save (); + //clip to client zone + CairoHelpers.CairoRectangle (gr, ClientRectangle, CornerRadius); + gr.Clip (); + foreach (GraphicObject g in children) { g.Paint (ref gr); } + gr.Restore (); } - - public override void Paint(ref Context ctx, Rectangles clip = null) + protected override void UpdateCache (Context ctx) { - if ( !Visible ) - return; - - if (bmp == null) - UpdateGraphic (); - else { - if (clip != null) - clip.Rebase (this); - else { - clip = new Rectangles (); - //TODO:added lately slot to empty clip, - //should rework this precise case causing expandable not - //to show image changes - clip.AddRectangle (ContextCoordinates (Slot.Size)); - } + Rectangle rb = Slot + Parent.ClientRectangle.Position; - if (!DrawingIsValid || clip != null) {//false when 1 child has changed - //child having their content changed has to be repainted - //and those with slot intersecting clip rectangle have also to be repainted + using (ImageSurface cache = new ImageSurface (bmp, Format.Argb32, Slot.Width, Slot.Height, 4 * Slot.Width)) { + Context gr = new Context (cache); - using (ImageSurface cache = - new ImageSurface (bmp, Format.Argb32, Slot.Width, Slot.Height, Slot.Width * 4)) { - Context gr = new Context (cache); - clip.clearAndClip (gr); + if (Clipping.count > 0) { + Clipping.clearAndClip (gr); + base.onDraw (gr); - Rectangle rBack = Slot.Size; - Background.SetAsSource (gr, rBack); - CairoHelpers.CairoRectangle(gr, rBack, CornerRadius); - gr.Fill (); + //clip to client zone + CairoHelpers.CairoRectangle (gr, ClientRectangle, CornerRadius); + gr.Clip (); - #if DEBUG_CLIP_RECTANGLE - clip.stroke (gr, Color.Amaranth.AdjustAlpha (0.8)); - #endif - foreach (GraphicObject c in children.Where(ch=>ch.Visible)) { - Rectangles childClip = clip.intersectingRects (ContextCoordinates(c.Slot)); - if (!c.DrawingIsValid || childClip.count > 0) - c.Paint (ref gr, childClip);//, localClip); - } - - gr.Dispose (); + foreach (GraphicObject c in children) { + if (!c.Visible) + continue; + if (Clipping.intersect(c.Slot + ClientRectangle.Position)) + c.Paint (ref gr); } + + #if DEBUG_CLIP_RECTANGLE + Clipping.stroke (gr, Color.Amaranth.AdjustAlpha (0.8)); + #endif } + gr.Dispose (); + + ctx.SetSourceSurface (cache, rb.X, rb.Y); + ctx.Paint (); } - - base.Paint (ref ctx, clip); + Clipping.Reset(); } #endregion diff --git a/src/GraphicObjects/IGOLibHost.cs b/src/GraphicObjects/IGOLibHost.cs index 1c50d558..1cf6978c 100644 --- a/src/GraphicObjects/IGOLibHost.cs +++ b/src/GraphicObjects/IGOLibHost.cs @@ -5,7 +5,6 @@ namespace Crow { public interface IGOLibHost { - Rectangles redrawClip { get; set; } List<GraphicObject> gobjsToRedraw { get; } GraphicObject activeWidget { get; set; } GraphicObject hoverWidget { get; set; } diff --git a/src/GraphicObjects/ILayoutable.cs b/src/GraphicObjects/ILayoutable.cs index 54e54f03..bbf1b4a6 100644 --- a/src/GraphicObjects/ILayoutable.cs +++ b/src/GraphicObjects/ILayoutable.cs @@ -21,6 +21,7 @@ namespace Crow LayoutingType RegisteredLayoutings { get; set; } void RegisterForLayouting(LayoutingType layoutType); + void RegisterClip(Rectangle clip); bool UpdateLayout(LayoutingType layoutType); diff --git a/src/GraphicObjects/Label.cs b/src/GraphicObjects/Label.cs index 1ce9409b..4c7e7006 100644 --- a/src/GraphicObjects/Label.cs +++ b/src/GraphicObjects/Label.cs @@ -597,12 +597,11 @@ namespace Crow SelBegin = -1; SelRelease = -1; SelectionInProgress = true; + registerForGraphicUpdate();//TODO:should put it in properties } //done at the end to set 'hasFocus' value after testing it base.onMouseDown (sender, e); - - registerForGraphicUpdate(); } public override void onMouseUp (object sender, MouseButtonEventArgs e) { diff --git a/src/GraphicObjects/PrivateContainer.cs b/src/GraphicObjects/PrivateContainer.cs index 9f787eac..77bf655f 100644 --- a/src/GraphicObjects/PrivateContainer.cs +++ b/src/GraphicObjects/PrivateContainer.cs @@ -133,33 +133,77 @@ namespace Crow break; } } - - public override Rectangle ContextCoordinates (Rectangle r) + protected override void onDraw (Context gr) { - return - Parent.ContextCoordinates(r) + Slot.Position + ClientRectangle.Position; + base.onDraw (gr); + + gr.Save (); + //clip to client zone + CairoHelpers.CairoRectangle (gr, ClientRectangle, CornerRadius); + gr.Clip (); + + if (child != null) + child.Paint (ref gr); + gr.Restore (); } - public override void Paint(ref Cairo.Context ctx, Rectangles clip = null) + protected override void UpdateCache (Context ctx) { - if (!Visible)//check if necessary?? - return; + //ctx.Save (); - ctx.Save(); + Rectangle rb = Slot + Parent.ClientRectangle.Position; - if (clip != null) - clip.clip(ctx); + using (ImageSurface cache = new ImageSurface (bmp, Format.Argb32, Slot.Width, Slot.Height, 4 * Slot.Width)) { + Context gr = new Context (cache); - base.Paint(ref ctx, clip); + //clip to client zone + CairoHelpers.CairoRectangle (gr, ClientRectangle, CornerRadius); + gr.Clip (); - //clip to client zone - CairoHelpers.CairoRectangle (ctx, Parent.ContextCoordinates(ClientRectangle + Slot.Position), CornerRadius); - ctx.Clip(); + if (Clipping.count > 0) { + + Clipping.clearAndClip (gr); + + if (child != null) { + + base.onDraw (gr); - if (child != null) - child.Paint(ref ctx, clip); - ctx.Restore(); + child.Paint (ref gr); + } + } + + gr.Dispose (); + + ctx.SetSourceSurface (cache, rb.X, rb.Y); + ctx.Paint (); + } + Clipping.Reset(); + + //ctx.Restore (); } +// public override Rectangle ContextCoordinates (Rectangle r) +// { +// return +// Parent.ContextCoordinates(r) + Slot.Position + ClientRectangle.Position; +// } +// public override void Paint(ref Cairo.Context ctx) +// { +// if (!Visible)//check if necessary?? +// return; +// +// ctx.Save(); +// +// base.Paint(ref ctx); +// +// //clip to client zone +// CairoHelpers.CairoRectangle (ctx, Parent.ContextCoordinates(ClientRectangle + Slot.Position), CornerRadius); +// ctx.Clip(); +// +// if (child != null) +// child.Paint(ref ctx); +// +// ctx.Restore(); +// } #endregion diff --git a/src/GraphicObjects/RadioButton.cs b/src/GraphicObjects/RadioButton.cs index 141a9887..297b4c2b 100644 --- a/src/GraphicObjects/RadioButton.cs +++ b/src/GraphicObjects/RadioButton.cs @@ -71,6 +71,9 @@ namespace Crow get { return isChecked; } set { + if (isChecked == value) + return; + isChecked = value; NotifyValueChanged ("IsChecked", value); diff --git a/src/GraphicObjects/Scroller.cs b/src/GraphicObjects/Scroller.cs index 3ac8d66c..1924aac0 100644 --- a/src/GraphicObjects/Scroller.cs +++ b/src/GraphicObjects/Scroller.cs @@ -100,6 +100,11 @@ namespace Crow : base(){} #region GraphicObject Overrides + [XmlAttributeAttribute()][DefaultValue(false)] + public override bool CacheEnabled { + get { return base.CacheEnabled; } + set { base.CacheEnabled = value; } + } void OnChildLayoutChanges (object sender, LayoutingEventArgs arg) { int maxScroll = MaximumScroll; @@ -177,22 +182,56 @@ namespace Crow savedMousePos.Y += e.YDelta; base.onMouseMove (sender, new MouseMoveEventArgs(savedMousePos.X,savedMousePos.Y,e.XDelta,e.YDelta)); } - #endregion - - public override Rectangle ContextCoordinates (Rectangle r) + public override void RegisterClip (Rectangle clip) { - return base.ContextCoordinates (r) - new Point((int)ScrollX,(int)ScrollY); + base.RegisterClip (clip - new Point((int)ScrollX,(int)ScrollY)); } + #endregion + public override Rectangle ScreenCoordinates (Rectangle r) { return base.ScreenCoordinates (r) - new Point((int)ScrollX,(int)ScrollY); } - - public override void registerClipRect () +// protected override void onDraw (Context gr) +// { +// gr.Save (); +// //gr.ResetClip (); +// +// base.onDraw (gr); +// gr.Restore (); +// } + protected override void onDraw (Context gr) { - HostContainer.redrawClip.AddRectangle (base.ScreenCoordinates(Slot)); + Rectangle rBack = new Rectangle (Slot.Size); + + Background.SetAsSource (gr, rBack); + CairoHelpers.CairoRectangle(gr,rBack, CornerRadius); + gr.Fill (); + + gr.Save (); + //clip to scrolled client zone + CairoHelpers.CairoRectangle (gr, ClientRectangle, CornerRadius);//+ new Point((int)ScrollX,(int)ScrollY) + gr.Clip (); + + gr.Translate (-ScrollX, -ScrollY); + if (child != null) + child.Paint (ref gr); + gr.Restore (); } +// public override void Paint (ref Context ctx) +// { +// ctx.Save (); +// //ctx.ResetClip (); +// ctx.Translate (-ScrollX, -ScrollY); +// base.Paint (ref ctx); +// ctx.Restore (); +// } +// public override void registerClipRect () +// { +// HostContainer.redrawClip.AddRectangle (base.ScreenCoordinates(Slot)); +// } + } } diff --git a/src/GraphicObjects/TemplatedControl.cs b/src/GraphicObjects/TemplatedControl.cs index 9dacd466..50199f7a 100644 --- a/src/GraphicObjects/TemplatedControl.cs +++ b/src/GraphicObjects/TemplatedControl.cs @@ -93,11 +93,6 @@ namespace Crow NotifyValueChanged ("TemplatedHeight", 0); } } - - protected override void loadDefaultValues () - { - base.loadDefaultValues (); - } public override GraphicObject FindByName (string nameToFind) { //prevent name searching in template diff --git a/src/GraphicObjects/Window.cs b/src/GraphicObjects/Window.cs index d98d296c..726f858a 100644 --- a/src/GraphicObjects/Window.cs +++ b/src/GraphicObjects/Window.cs @@ -89,7 +89,7 @@ namespace Crow if (!HasFocus) return; - otkgw.redrawClip.AddRectangle (this.ScreenCoordinates(this.Slot)); + //otkgw.redrawClip.AddRectangle (this.ScreenCoordinates(this.Slot)); int currentLeft = this.Left; int currentTop = this.Top; diff --git a/src/OpenTKGameWindow.cs b/src/OpenTKGameWindow.cs index 16362c6c..00035390 100644 --- a/src/OpenTKGameWindow.cs +++ b/src/OpenTKGameWindow.cs @@ -54,7 +54,7 @@ namespace Crow List<GraphicObject> _gobjsToRedraw = new List<GraphicObject>(); #region IGOLibHost implementation - public Rectangles redrawClip { + public Rectangles clipping { get { return _redrawClip; } @@ -90,7 +90,7 @@ namespace Crow { GraphicObjects.Remove(g); GraphicObjects.Insert(0, g); - g.registerClipRect (); + //g.registerClipRect (); } } public void Quit () @@ -181,7 +181,7 @@ namespace Crow shader.ProjectionMatrix = Matrix4.CreateOrthographicOffCenter (0, ClientRectangle.Width, ClientRectangle.Height, 0, 0, 1); - redrawClip.AddRectangle (ClientRectangle); + clipping.AddRectangle (ClientRectangle); } void createOpenGLSurface() { @@ -253,71 +253,67 @@ namespace Crow updateTime.Restart (); #endif - using (surf = new ImageSurface (bmp, Format.Argb32, ClientRectangle.Width, ClientRectangle.Height, ClientRectangle.Width * 4)) { - using (ctx = new Context (surf)){ + GraphicObject[] invGOList = new GraphicObject[GraphicObjects.Count]; + GraphicObjects.CopyTo (invGOList, 0); + invGOList = invGOList.Reverse ().ToArray (); - GraphicObject[] invGOList = new GraphicObject[GraphicObjects.Count]; - GraphicObjects.CopyTo (invGOList, 0); - invGOList = invGOList.Reverse ().ToArray (); + #if MEASURE_TIME + layoutTime.Start (); + #endif + //Debug.WriteLine ("======= Layouting queue start ======="); - #if MEASURE_TIME - layoutTime.Start (); - #endif - //Debug.WriteLine ("======= Layouting queue start ======="); + while (Interface.LayoutingQueue.Count > 0) { + LayoutingQueueItem lqi = Interface.LayoutingQueue.Dequeue (); + lqi.ProcessLayouting (); + } - while (Interface.LayoutingQueue.Count > 0) { - LayoutingQueueItem lqi = Interface.LayoutingQueue.Dequeue (); - lqi.ProcessLayouting (); - } + #if MEASURE_TIME + layoutTime.Stop (); + #endif - #if MEASURE_TIME - layoutTime.Stop (); - #endif + //Debug.WriteLine ("otd:" + gobjsToRedraw.Count.ToString () + "-"); + //final redraw clips should be added only when layout is completed among parents, + //that's why it take place in a second pass + GraphicObject[] gotr = new GraphicObject[gobjsToRedraw.Count]; + gobjsToRedraw.CopyTo (gotr); + gobjsToRedraw.Clear (); + foreach (GraphicObject p in gotr) { + p.IsQueuedForRedraw = false; + p.Parent.RegisterClip (p.LastPaintedSlot); + p.Parent.RegisterClip (p.getSlot()); + } - //Debug.WriteLine ("otd:" + gobjsToRedraw.Count.ToString () + "-"); - //final redraw clips should be added only when layout is completed among parents, - //that's why it take place in a second pass - GraphicObject[] gotr = new GraphicObject[gobjsToRedraw.Count]; - gobjsToRedraw.CopyTo (gotr); - gobjsToRedraw.Clear (); - foreach (GraphicObject p in gotr) { - p.IsQueuedForRedraw = false; - p.registerClipRect (); - } + #if MEASURE_TIME + updateTime.Stop (); + drawingTime.Start (); + #endif - #if MEASURE_TIME - updateTime.Stop (); - drawingTime.Start (); - #endif + using (surf = new ImageSurface (bmp, Format.Argb32, ClientRectangle.Width, ClientRectangle.Height, ClientRectangle.Width * 4)) { + using (ctx = new Context (surf)){ - lock (redrawClip) { - if (redrawClip.count > 0) { - #if DEBUG_CLIP_RECTANGLE - redrawClip.stroke (ctx, new Color(1.0,0,0,0.3)); - #endif - redrawClip.clearAndClip (ctx); - //Link.draw (ctx); - foreach (GraphicObject p in invGOList) { - if (p.Visible) { + if (clipping.count > 0) { + //Link.draw (ctx); + clipping.clearAndClip(ctx); - ctx.Save (); - if (redrawClip.count > 0) { - Rectangles clip = redrawClip.intersectingRects (p.Slot); + foreach (GraphicObject p in invGOList) { + if (!p.Visible) + continue; - if (clip.count > 0) - p.Paint (ref ctx, clip); - } - ctx.Restore (); - } - } - ctx.ResetClip (); - #if DEBUG_CLIP_RECTANGLE - redrawClip.stroke (ctx, Color.Red.AdjustAlpha(0.1)); - #endif - redrawClip.Reset (); + ctx.Save (); + + p.Paint (ref ctx); + + ctx.Restore (); } + + #if DEBUG_CLIP_RECTANGLE + clipping.stroke (ctx, Color.Red.AdjustAlpha(0.5)); + #endif + + clipping.Reset (); } + #if MEASURE_TIME drawingTime.Stop (); #endif @@ -549,6 +545,9 @@ namespace Crow #endregion #region ILayoutable implementation + public void RegisterClip(Rectangle r){ + clipping.AddRectangle (r); + } public int LayoutingTries { get { throw new NotImplementedException (); } set { throw new NotImplementedException (); } @@ -559,17 +558,13 @@ namespace Crow } public void RegisterForLayouting (LayoutingType layoutType) { throw new NotImplementedException (); } public bool UpdateLayout (LayoutingType layoutType) { throw new NotImplementedException (); } - public Rectangle ContextCoordinates (Rectangle r) - { - return r; - } + public Rectangle ContextCoordinates (Rectangle r) => r; public Rectangle ScreenCoordinates (Rectangle r) => r; public ILayoutable Parent { get { return null; } set { throw new NotImplementedException (); } } - public ILayoutable LogicalParent { get { return null; } set { throw new NotImplementedException (); } @@ -581,15 +576,8 @@ namespace Crow public IGOLibHost HostContainer { get { return this; } } - - public Rectangle getSlot () - { - return ClientRectangle; - } - public Rectangle getBounds ()//redundant but fill ILayoutable implementation - { - return ClientRectangle; - } + public Rectangle getSlot () => ClientRectangle; + public Rectangle getBounds () => ClientRectangle; #endregion } }
\ No newline at end of file diff --git a/src/Rectangles.cs b/src/Rectangles.cs index dbb4118b..c507b2ba 100644 --- a/src/Rectangles.cs +++ b/src/Rectangles.cs @@ -147,6 +147,8 @@ namespace Crow } public void clearAndClip(Context ctx) { + if (list.Count == 0) + return; foreach (Rectangle r in list) ctx.Rectangle(r); |