| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194 |
- using System;
- using System.Linq;
- using Avalonia.Media;
- using Avalonia.Media.TextFormatting;
- using Avalonia.Platform;
- using Avalonia.UnitTests;
- using Avalonia.Utilities;
- using Xunit;
- namespace Avalonia.Base.UnitTests.Media
- {
- public class GlyphRunTests : TestWithServicesBase
- {
- public GlyphRunTests()
- {
- AvaloniaLocator.CurrentMutable
- .Bind<IPlatformRenderInterface>().ToSingleton<MockPlatformRenderInterface>();
- }
- [InlineData(new double[] { 30, 0, 0 }, new int[] { 0, 0, 0 }, 0, 0, 0)]
- [InlineData(new double[] { 30, 0, 0 }, new int[] { 0, 0, 0 }, 0, 3, 30)]
- [InlineData(new double[] { 10, 10, 10 }, new int[] { 0, 1, 2 }, 1, 0, 10)]
- [InlineData(new double[] { 10, 10, 10 }, new int[] { 0, 1, 2 }, 2, 0, 20)]
- [InlineData(new double[] { 10, 10, 10 }, new int[] { 0, 1, 2 }, 2, 1, 30)]
- [Theory]
- public void Should_Get_Distance_From_CharacterHit(double[] advances, int[] clusters, int start, int trailingLength, double expectedDistance)
- {
- using(UnitTestApplication.Start(TestServices.StyledWindow))
- using (var glyphRun = CreateGlyphRun(advances, clusters))
- {
- var characterHit = new CharacterHit(start, trailingLength);
- var distance = glyphRun.GetDistanceFromCharacterHit(characterHit);
- Assert.Equal(expectedDistance, distance);
- }
- }
- [InlineData(new double[] { 30, 0, 0 }, new int[] { 0, 0, 0 }, 26.0, 0, 3, true)]
- [InlineData(new double[] { 10, 10, 10 }, new int[] { 0, 1, 2 }, 20.0, 1, 1, true)]
- [InlineData(new double[] { 10, 10, 10 }, new int[] { 0, 1, 2 }, 26.0, 2, 1, true)]
- [InlineData(new double[] { 10, 10, 10 }, new int[] { 0, 1, 2 }, 35.0, 2, 1, false)]
- [Theory]
- public void Should_Get_CharacterHit_FromDistance(double[] advances, int[] clusters, double distance, int start,
- int trailingLengthExpected, bool isInsideExpected)
- {
- using(UnitTestApplication.Start(TestServices.StyledWindow))
- using (var glyphRun = CreateGlyphRun(advances, clusters))
- {
- var textBounds = glyphRun.GetCharacterHitFromDistance(distance, out var isInside);
- Assert.Equal(start, textBounds.FirstCharacterIndex);
- Assert.Equal(trailingLengthExpected, textBounds.TrailingLength);
- Assert.Equal(isInsideExpected, isInside);
- }
- }
- [InlineData(new double[] { 10, 10, 10 }, new int[] { 10, 11, 12 }, 0, -1, 10, 1, 10)]
- [InlineData(new double[] { 10, 10, 10 }, new int[] { 10, 11, 12 }, 0, 15, 12, 1, 10)]
- [InlineData(new double[] { 30, 0, 0 }, new int[] { 0, 0, 0 }, 0, 0, 0, 3, 30.0)]
- [InlineData(new double[] { 10, 10, 10 }, new int[] { 0, 1, 2 }, 0, 1, 1, 1, 10.0)]
- [InlineData(new double[] { 10, 20, 0, 10 }, new int[] { 0, 1, 1, 3 }, 0, 2, 1, 2, 20.0)]
- [InlineData(new double[] { 10, 20, 0, 10 }, new int[] { 0, 1, 1, 3 }, 0, 1, 1, 2, 20.0)]
- [InlineData(new double[] { 10, 0, 20, 10 }, new int[] { 3, 1, 1, 0 }, 1, 1, 1, 2, 20.0)]
- [Theory]
- public void Should_Find_Nearest_CharacterHit(double[] advances, int[] clusters, int bidiLevel,
- int index, int expectedIndex, int expectedLength, double expectedWidth)
- {
- using(UnitTestApplication.Start(TestServices.MockPlatformRenderInterface))
- using (var glyphRun = CreateGlyphRun(advances, clusters, bidiLevel))
- {
- var textBounds = glyphRun.FindNearestCharacterHit(index, out var width);
- Assert.Equal(expectedIndex, textBounds.FirstCharacterIndex);
- Assert.Equal(expectedLength, textBounds.TrailingLength);
- Assert.Equal(expectedWidth, width, 2);
- }
- }
- [InlineData(new double[] { 30, 0, 0 }, new int[] { 0, 0, 0 }, 0, 0, 0, 3, 0)]
- [InlineData(new double[] { 0, 0, 30 }, new int[] { 0, 0, 0 }, 0, 0, 0, 3, 1)]
- [InlineData(new double[] { 30, 0, 0, 10 }, new int[] { 0, 0, 0, 3 }, 3, 0, 3, 1, 0)]
- [InlineData(new double[] { 10, 0, 0, 30 }, new int[] { 3, 0, 0, 0 }, 3, 0, 3, 1, 1)]
- [InlineData(new double[] { 10, 30, 0, 0, 10 }, new int[] { 0, 1, 1, 1, 4 }, 1, 0, 4, 0, 0)]
- [InlineData(new double[] { 10, 0, 0, 30, 10 }, new int[] { 4, 1, 1, 1, 0 }, 1, 0, 4, 0, 1)]
- [Theory]
- public void Should_Get_Next_CharacterHit(double[] advances,int[] clusters,
- int firstCharacterIndex, int trailingLength,
- int nextIndex, int nextLength,
- int bidiLevel)
- {
- using(UnitTestApplication.Start(TestServices.MockPlatformRenderInterface))
- using (var glyphRun = CreateGlyphRun(advances, clusters, bidiLevel))
- {
- var characterHit = glyphRun.GetNextCaretCharacterHit(new CharacterHit(firstCharacterIndex, trailingLength));
- Assert.Equal(nextIndex, characterHit.FirstCharacterIndex);
- Assert.Equal(nextLength, characterHit.TrailingLength);
- }
- }
- [InlineData(new double[] { 30, 0, 0 }, new int[] { 0, 0, 0 }, 0, 0, 0, 0, 0)]
- [InlineData(new double[] { 0, 0, 30 }, new int[] { 0, 0, 0 }, 0, 0, 0, 0, 1)]
- [InlineData(new double[] { 30, 0, 0, 10 }, new int[] { 0, 0, 0, 3 }, 3, 1, 3, 0, 0)]
- [InlineData(new double[] { 0, 0, 30, 10 }, new int[] { 3, 0, 0, 0 }, 3, 1, 3, 0, 1)]
- [InlineData(new double[] { 10, 30, 0, 0, 10 }, new int[] { 0, 1, 1, 1, 4 }, 4, 1, 4, 0, 0)]
- [InlineData(new double[] { 10, 0, 0, 30, 10 }, new int[] { 4, 1, 1, 1, 0 }, 4, 1, 4, 0, 1)]
- [Theory]
- public void Should_Get_Previous_CharacterHit(double[] advances, int[] clusters,
- int currentIndex, int currentLength,
- int previousIndex, int previousLength,
- int bidiLevel)
- {
- using(UnitTestApplication.Start(TestServices.MockPlatformRenderInterface))
- using (var glyphRun = CreateGlyphRun(advances, clusters, bidiLevel))
- {
- var characterHit = glyphRun.GetPreviousCaretCharacterHit(new CharacterHit(currentIndex, currentLength));
- Assert.Equal(previousIndex, characterHit.FirstCharacterIndex);
- Assert.Equal(previousLength, characterHit.TrailingLength);
- }
- }
- [InlineData(new double[] { 30, 0, 0 }, new int[] { 0, 0, 0 }, 0)]
- [InlineData(new double[] { 0, 0, 30 }, new int[] { 0, 0, 0 }, 1)]
- [InlineData(new double[] { 10, 10, 10, 10 }, new int[] { 0, 0, 0, 3 }, 0)]
- [InlineData(new double[] { 10, 10, 10, 10 }, new int[] { 3, 0, 0, 0 }, 1)]
- [InlineData(new double[] { 10, 10, 10, 10, 10 }, new int[] { 0, 1, 1, 1, 4 }, 0)]
- [InlineData(new double[] { 10, 10, 10, 10, 10 }, new int[] { 4, 1, 1, 1, 0 }, 1)]
- [Theory]
- public void Should_Find_Glyph_Index(double[] advances, int[] clusters, int bidiLevel)
- {
- using(UnitTestApplication.Start(TestServices.MockPlatformRenderInterface))
- using (var glyphRun = CreateGlyphRun(advances, clusters, bidiLevel))
- {
- if (glyphRun.IsLeftToRight)
- {
- for (var i = 0; i < clusters.Length; i++)
- {
- var cluster = clusters[i];
- var found = glyphRun.FindGlyphIndex(cluster);
- var expected = i;
- while (expected - 1 >= 0 && clusters[expected - 1] == cluster)
- {
- expected--;
- }
- Assert.Equal(expected, found);
- }
- }
- else
- {
- for (var i = clusters.Length - 1; i > 0; i--)
- {
- var cluster = clusters[i];
- var found = glyphRun.FindGlyphIndex(cluster);
- var expected = i;
- while (expected + 1 < clusters.Length && clusters[expected + 1] == cluster)
- {
- expected++;
- }
- Assert.Equal(expected, found);
- }
- }
- }
- }
- private static GlyphRun CreateGlyphRun(double[] glyphAdvances, int[] glyphClusters, int bidiLevel = 0)
- {
- var count = glyphAdvances.Length;
- var glyphInfos = new GlyphInfo[count];
- for (var i = 0; i < count; ++i)
- {
- glyphInfos[i] = new GlyphInfo(0, glyphClusters[i], glyphAdvances[i]);
- }
- return new GlyphRun(new MockGlyphTypeface(), 10, new string('a', count).AsMemory(), glyphInfos, biDiLevel: bidiLevel);
- }
- }
- }
|