-
Notifications
You must be signed in to change notification settings - Fork 3
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Merge pull request #59 from andy840119/fix-masking-issue
Implement masking container.
- Loading branch information
Showing
3 changed files
with
173 additions
and
7 deletions.
There are no files selected for viewing
60 changes: 60 additions & 0 deletions
60
osu.Framework.Font.Tests/Visual/Containers/MaskingContainerTestScene.cs
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,60 @@ | ||
// Copyright (c) andy840119 <[email protected]>. Licensed under the MIT Licence. | ||
// See the LICENCE file in the repository root for full licence text. | ||
|
||
using NUnit.Framework; | ||
using osu.Framework.Graphics; | ||
using osu.Framework.Graphics.Containers; | ||
using osu.Framework.Graphics.Shapes; | ||
using osuTK; | ||
using osuTK.Graphics; | ||
|
||
namespace osu.Framework.Font.Tests.Visual.Containers | ||
{ | ||
public class MaskingContainerTestScene : BackgroundGridTestSample | ||
{ | ||
private readonly MaskingContainer<Drawable> maskingContainer; | ||
|
||
public MaskingContainerTestScene() | ||
{ | ||
Child = maskingContainer = new MaskingContainer<Drawable> | ||
{ | ||
Anchor = Anchor.Centre, | ||
Origin = Anchor.Centre, | ||
Size = new Vector2(200), | ||
Children = new Drawable[] | ||
{ | ||
new Box | ||
{ | ||
Anchor = Anchor.Centre, | ||
Origin = Anchor.Centre, | ||
Size = new Vector2(250), | ||
Colour = Colour4.Red | ||
}, | ||
new DraggableCircle | ||
{ | ||
Anchor = Anchor.Centre, | ||
Origin = Anchor.Centre, | ||
Colour = Color4.Blue, | ||
Size = new Vector2(100) | ||
} | ||
} | ||
}; | ||
} | ||
|
||
[TestCase(Edges.None)] | ||
[TestCase(Edges.Left)] | ||
[TestCase(Edges.Right)] | ||
[TestCase(Edges.Top)] | ||
[TestCase(Edges.Bottom)] | ||
[TestCase(Edges.Vertical)] | ||
[TestCase(Edges.Horizontal)] | ||
[TestCase(Edges.Left | Edges.Top)] | ||
public void TestMasking(Edges edges) | ||
{ | ||
AddStep("apply masking", () => | ||
{ | ||
maskingContainer.MaskingEdges = edges; | ||
}); | ||
} | ||
} | ||
} |
107 changes: 107 additions & 0 deletions
107
osu.Framework.Font/Graphics/Containers/MaskingContainer.cs
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,107 @@ | ||
// Copyright (c) andy840119 <[email protected]>. Licensed under the MIT Licence. | ||
// See the LICENCE file in the repository root for full licence text. | ||
|
||
using System; | ||
using osu.Framework.Graphics.OpenGL; | ||
using osu.Framework.Graphics.OpenGL.Vertices; | ||
using osu.Framework.Graphics.Primitives; | ||
|
||
namespace osu.Framework.Graphics.Containers | ||
{ | ||
/// <summary> | ||
/// It's a container that only masking target direction. | ||
/// </summary> | ||
/// <typeparam name="T"></typeparam> | ||
public class MaskingContainer<T> : Container<T> where T : Drawable | ||
{ | ||
/// <summary> | ||
/// If enabled, only the portion of children that falls within this <see cref="Container"/>'s | ||
/// shape is drawn to the screen. | ||
/// </summary> | ||
public new bool Masking | ||
{ | ||
get => throw new InvalidOperationException("Should not get masking in here."); | ||
set => throw new InvalidOperationException("Should not assign masking in here."); | ||
} | ||
|
||
private Edges maskingEdges = Edges.None; | ||
|
||
public Edges MaskingEdges | ||
{ | ||
get => maskingEdges; | ||
set | ||
{ | ||
if (maskingEdges == value) | ||
return; | ||
|
||
maskingEdges = value; | ||
Invalidate(Invalidation.DrawNode); | ||
} | ||
} | ||
|
||
protected override DrawNode CreateDrawNode() | ||
=> new MaskingCompositeDrawableDrawNode(this); | ||
|
||
protected class MaskingCompositeDrawableDrawNode : CompositeDrawableDrawNode | ||
{ | ||
protected new MaskingContainer<T> Source => (MaskingContainer<T>)base.Source; | ||
|
||
/// <summary> | ||
/// Information about how masking of children should be carried out. | ||
/// </summary> | ||
private MaskingInfo? maskingInfo; | ||
|
||
public MaskingCompositeDrawableDrawNode(CompositeDrawable source) | ||
: base(source) | ||
{ | ||
} | ||
|
||
public override void ApplyState() | ||
{ | ||
base.ApplyState(); | ||
|
||
maskingInfo = Source.MaskingEdges == Edges.None | ||
? (MaskingInfo?)null | ||
: new MaskingInfo | ||
{ | ||
ScreenSpaceAABB = generateMasking(Source.ScreenSpaceDrawQuad.AABB, Source.MaskingEdges), | ||
}; | ||
} | ||
|
||
private static RectangleI generateMasking(RectangleI source, Edges edges) | ||
{ | ||
return source.Inflate(getExtendSize(Edges.Left), getExtendSize(Edges.Right), getExtendSize(Edges.Top), getExtendSize(Edges.Bottom)); | ||
|
||
int getExtendSize(Edges flag) | ||
{ | ||
const int extend_size = 1000; | ||
return edges.HasFlag(flag) ? 0 : extend_size; | ||
} | ||
} | ||
|
||
public override void Draw(Action<TexturedVertex2D> vertexAction) | ||
{ | ||
// will not working if not adding masking info into here. | ||
if (maskingInfo != null) | ||
GLWrapper.PushMaskingInfo(maskingInfo.Value); | ||
|
||
base.Draw(vertexAction); | ||
|
||
if (maskingInfo != null) | ||
GLWrapper.PopMaskingInfo(); | ||
} | ||
|
||
protected override void DrawChildrenOpaqueInteriors(DepthValue depthValue, Action<TexturedVertex2D> vertexAction) | ||
{ | ||
// will have black border if not adding masking info into here. | ||
if (maskingInfo != null) | ||
GLWrapper.PushMaskingInfo(maskingInfo.Value); | ||
|
||
base.DrawChildrenOpaqueInteriors(depthValue, vertexAction); | ||
|
||
if (maskingInfo != null) | ||
GLWrapper.PopMaskingInfo(); | ||
} | ||
} | ||
} | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters