Skip to content

Commit b2dbd21

Browse files
Do not use pedantic hinting.
1 parent 5ff7825 commit b2dbd21

File tree

9 files changed

+90
-17
lines changed

9 files changed

+90
-17
lines changed

src/SixLabors.Fonts/Tables/TrueType/Hinting/TrueTypeInterpreter.cs

Lines changed: 12 additions & 17 deletions
Original file line numberDiff line numberDiff line change
@@ -66,7 +66,7 @@ internal class TrueTypeInterpreter
6666
private const int MaxCallStack = 128;
6767
private const float Epsilon = 0.000001F;
6868

69-
private readonly List<OpCode> debugList = new();
69+
private readonly List<OpCode> debugList = [];
7070

7171
public TrueTypeInterpreter(int maxStack, int maxStorage, int maxFunctions, int maxInstructionDefs, int maxTwilightPoints)
7272
{
@@ -77,7 +77,7 @@ public TrueTypeInterpreter(int maxStack, int maxStorage, int maxFunctions, int m
7777
this.state = default;
7878
this.cvtState = default;
7979
this.twilight = new Zone(maxTwilightPoints, isTwilight: true);
80-
this.controlValueTable = Array.Empty<float>();
80+
this.controlValueTable = [];
8181
this.contours = Array.Empty<ushort>();
8282
}
8383

@@ -97,7 +97,6 @@ public void SetControlValueTable(short[]? cvt, float scale, float ppem, byte[]?
9797
this.controlValueTable = new float[cvt.Length];
9898
}
9999

100-
// TODO: How about SIMD here? Will the JIT vectorize this?
101100
for (int i = 0; i < cvt.Length; i++)
102101
{
103102
this.controlValueTable[i] = cvt[i] * scale;
@@ -227,15 +226,15 @@ private void Execute(StackInstructionStream stream, bool inFunction, bool allowF
227226
// ==== STORAGE MANAGEMENT ====
228227
case OpCode.RS:
229228
{
230-
int loc = CheckIndex(this.stack.Pop(), this.storage.Length);
229+
int loc = IndexOrZero(this.stack.Pop(), this.storage.Length);
231230
this.stack.Push(this.storage[loc]);
232231
}
233232

234233
break;
235234
case OpCode.WS:
236235
{
237236
int value = this.stack.Pop();
238-
int loc = CheckIndex(this.stack.Pop(), this.storage.Length);
237+
int loc = IndexOrZero(this.stack.Pop(), this.storage.Length);
239238
this.storage[loc] = value;
240239
}
241240

@@ -245,15 +244,15 @@ private void Execute(StackInstructionStream stream, bool inFunction, bool allowF
245244
case OpCode.WCVTP:
246245
{
247246
float value = this.stack.PopFloat();
248-
int loc = CheckIndex(this.stack.Pop(), this.controlValueTable.Length);
247+
int loc = IndexOrZero(this.stack.Pop(), this.controlValueTable.Length);
249248
this.controlValueTable[loc] = value;
250249
}
251250

252251
break;
253252
case OpCode.WCVTF:
254253
{
255254
int value = this.stack.Pop();
256-
int loc = CheckIndex(this.stack.Pop(), this.controlValueTable.Length);
255+
int loc = IndexOrZero(this.stack.Pop(), this.controlValueTable.Length);
257256
this.controlValueTable[loc] = value * this.scale;
258257
}
259258

@@ -316,7 +315,7 @@ private void Execute(StackInstructionStream stream, bool inFunction, bool allowF
316315
{
317316
int y = this.stack.Pop();
318317
int x = this.stack.Pop();
319-
var vec = Vector2.Normalize(new Vector2(F2Dot14ToFloat(x), F2Dot14ToFloat(y)));
318+
Vector2 vec = Vector2.Normalize(new Vector2(F2Dot14ToFloat(x), F2Dot14ToFloat(y)));
320319
if (opcode == OpCode.SFVFS)
321320
{
322321
this.state.Freedom = vec;
@@ -1379,8 +1378,8 @@ private void Execute(StackInstructionStream stream, bool inFunction, bool allowF
13791378
amount *= 1 << (6 - this.state.DeltaShift);
13801379

13811380
// update the CVT
1382-
CheckIndex(cvtIndex, this.controlValueTable.Length);
1383-
this.controlValueTable[cvtIndex] += F26Dot6ToFloat(amount);
1381+
int loc = IndexOrZero(cvtIndex, this.controlValueTable.Length);
1382+
this.controlValueTable[loc] += F26Dot6ToFloat(amount);
13841383
}
13851384
}
13861385
}
@@ -1504,13 +1503,9 @@ private void Execute(StackInstructionStream stream, bool inFunction, bool allowF
15041503
}
15051504
}
15061505

1507-
private static int CheckIndex(int index, int length)
1508-
{
1509-
Guard.MustBeBetweenOrEqualTo(index, 0, length - 1, nameof(index));
1510-
return index;
1511-
}
1506+
private static int IndexOrZero(int index, int length) => (uint)index < (uint)length ? index : 0;
15121507

1513-
private float ReadCvt() => this.controlValueTable[CheckIndex(this.stack.Pop(), this.controlValueTable.Length)];
1508+
private float ReadCvt() => this.controlValueTable[IndexOrZero(this.stack.Pop(), this.controlValueTable.Length)];
15141509

15151510
private void OnVectorsUpdated()
15161511
{
@@ -2474,7 +2469,7 @@ public Zone(ControlPoint[] controlPoints, bool isTwilight)
24742469
this.IsTwilight = isTwilight;
24752470
this.Current = controlPoints;
24762471

2477-
var original = new ControlPoint[controlPoints.Length];
2472+
ControlPoint[] original = new ControlPoint[controlPoints.Length];
24782473
controlPoints.AsSpan().CopyTo(original);
24792474
this.Original = original;
24802475
this.TouchState = new TouchState[controlPoints.Length];
Lines changed: 3 additions & 0 deletions
Loading
Lines changed: 3 additions & 0 deletions
Loading
Lines changed: 3 additions & 0 deletions
Loading
46.2 KB
Binary file not shown.
54.2 KB
Binary file not shown.
275 KB
Binary file not shown.
Lines changed: 63 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,63 @@
1+
// Copyright (c) Six Labors.
2+
// Licensed under the Six Labors Split License.
3+
4+
namespace SixLabors.Fonts.Tests.Issues;
5+
6+
public class Issues_493
7+
{
8+
[Fact]
9+
public void Test_Issue_493_Ogham()
10+
{
11+
const string text =
12+
"""
13+
Ogham
14+
᚛ᚐᚅᚋᚐᚇᚐᚅᚈᚐ᚜
15+
""";
16+
17+
FontCollection fontCollection = new();
18+
string name = fontCollection.Add(TestFonts.NotoSansOghamRegular).Name;
19+
20+
FontFamily mainFontFamily = fontCollection.Get(name);
21+
Font mainFont = mainFontFamily.CreateFont(30, FontStyle.Regular);
22+
23+
TextOptions options = new(mainFont) { HintingMode = HintingMode.Standard };
24+
25+
TextLayoutTestUtilities.TestLayout(text, options);
26+
}
27+
28+
[Fact]
29+
public void Test_Issue_493_Runic()
30+
{
31+
const string text =
32+
"""
33+
Runic
34+
ᚦᛖᚱᛅᛈᛁᛑᛒᚱᚢᚾᚠᛅᚢᛋ
35+
""";
36+
37+
FontCollection fontCollection = new();
38+
string name = fontCollection.Add(TestFonts.NotoSansRunicRegular).Name;
39+
40+
FontFamily mainFontFamily = fontCollection.Get(name);
41+
Font mainFont = mainFontFamily.CreateFont(30, FontStyle.Regular);
42+
43+
TextOptions options = new(mainFont) { HintingMode = HintingMode.Standard };
44+
45+
TextLayoutTestUtilities.TestLayout(text, options);
46+
}
47+
48+
[Fact]
49+
public void Test_Issue_493_MgOpenCanonic()
50+
{
51+
const string text = "the quick brown fox jumps over the lazy dog";
52+
53+
FontCollection fontCollection = new();
54+
string name = fontCollection.Add(TestFonts.NotoSansRunicRegular).Name;
55+
56+
FontFamily mainFontFamily = fontCollection.Get(name);
57+
Font mainFont = mainFontFamily.CreateFont(30, FontStyle.Regular);
58+
59+
TextOptions options = new(mainFont) { HintingMode = HintingMode.Standard };
60+
61+
TextLayoutTestUtilities.TestLayout(text, options);
62+
}
63+
}

tests/SixLabors.Fonts.Tests/TestFonts.cs

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -305,6 +305,12 @@ public static class TestFonts
305305

306306
public static string MyanmarSansRegular => GetFullPath("NotoSansMyanmar-Regular.ttf");
307307

308+
public static string NotoSansOghamRegular => GetFullPath("NotoSansOgham-Regular.ttf");
309+
310+
public static string NotoSansRunicRegular => GetFullPath("NotoSansRunic-Regular.ttf");
311+
312+
public static string MgOpenCanonicRegular => GetFullPath("mgopencanonicaregular.ttf");
313+
308314
public static Stream TwemojiMozillaData() => OpenStream(TwemojiMozillaFile);
309315

310316
public static Stream SegoeuiEmojiData() => OpenStream(SegoeuiEmojiFile);

0 commit comments

Comments
 (0)