@@ -59,12 +59,10 @@ class IntegrationTest : public ::testing::Test {
59
59
iftb_patches_[i].set (blob.get ());
60
60
}
61
61
62
- /*
63
62
// Noto Sans JP VF
64
63
blob = make_hb_blob (
65
64
hb_blob_create_from_file (" ift/testdata/NotoSansJP[wght].subset.ttf" ));
66
- face = make_hb_face(hb_face_create(blob.get(), 0));
67
- noto_sans_vf_.set(face.get());
65
+ noto_sans_vf_.set (blob.get ());
68
66
69
67
vf_iftb_patches_.resize (5 );
70
68
for (int i = 1 ; i <= 4 ; i++) {
@@ -74,7 +72,6 @@ class IntegrationTest : public ::testing::Test {
74
72
assert (hb_blob_get_length (blob.get ()) > 0 );
75
73
vf_iftb_patches_[i].set (blob.get ());
76
74
}
77
- */
78
75
79
76
// Feature Test
80
77
blob = make_hb_blob (hb_blob_create_from_file (
@@ -113,18 +110,13 @@ class IntegrationTest : public ::testing::Test {
113
110
return absl::OkStatus ();
114
111
}
115
112
116
- /*
117
- Status InitEncoderForVfIftb(Encoder& encoder) {
118
- encoder.SetUrlTemplate("0x$2$1");
113
+ Status InitEncoderForVfMixedMode (Encoder& encoder) {
114
+ encoder.SetUrlTemplate (" {id}" );
119
115
{
120
116
hb_face_t * face = noto_sans_vf_.reference_face ();
121
117
encoder.SetFace (face);
122
118
hb_face_destroy (face);
123
119
}
124
- auto sc = encoder.SetId({0x479bb4b0, 0x20226239, 0xa7799c0f, 0x24275be0});
125
- if (!sc.ok()) {
126
- return sc;
127
- }
128
120
129
121
for (uint i = 1 ; i < vf_iftb_patches_.size (); i++) {
130
122
auto sc = encoder.AddExistingIftbPatch (i, vf_iftb_patches_[i]);
@@ -135,7 +127,6 @@ class IntegrationTest : public ::testing::Test {
135
127
136
128
return absl::OkStatus ();
137
129
}
138
- */
139
130
140
131
Status InitEncoderForMixedModeFeatureTest (Encoder& encoder) {
141
132
encoder.SetUrlTemplate (" {id}" );
@@ -172,24 +163,6 @@ class IntegrationTest : public ::testing::Test {
172
163
return absl::OkStatus ();
173
164
}
174
165
175
- /*
176
- Status AddPatches(IFTClient& client, Encoder& encoder) {
177
- auto patches = client.PatchesNeeded();
178
- for (const auto& id : patches) {
179
- FontData patch_data;
180
- auto it = encoder.Patches().find(id);
181
- if (it == encoder.Patches().end()) {
182
- return absl::InternalError(StrCat("Patch ", id, " was not found."));
183
- }
184
- patch_data.shallow_copy(it->second);
185
- client.AddPatch(id, patch_data);
186
- }
187
-
188
- return absl::OkStatus();
189
- }
190
- */
191
-
192
- /*
193
166
bool GvarHasLongOffsets (const FontData& font) {
194
167
auto face = font.face ();
195
168
auto gvar_data =
@@ -200,13 +173,12 @@ class IntegrationTest : public ::testing::Test {
200
173
uint8_t flags_1 = gvar_data.str ().at (15 );
201
174
return flags_1 == 0x01 ;
202
175
}
203
- */
204
176
205
177
FontData noto_sans_jp_;
206
178
std::vector<FontData> iftb_patches_;
207
179
208
- // FontData noto_sans_vf_;
209
- // std::vector<FontData> vf_iftb_patches_;
180
+ FontData noto_sans_vf_;
181
+ std::vector<FontData> vf_iftb_patches_;
210
182
211
183
FontData feature_test_;
212
184
std::vector<FontData> feature_test_patches_;
@@ -252,6 +224,31 @@ bool GlyphDataMatches(hb_face_t* a, hb_face_t* b, uint32_t codepoint) {
252
224
return *a_data == *b_data;
253
225
}
254
226
227
+ bool GvarDataMatches (hb_face_t * a, hb_face_t * b, uint32_t codepoint,
228
+ uint32_t ignore_count) {
229
+ uint32_t gid_a, gid_b;
230
+
231
+ hb_font_t * font_a = hb_font_create (a);
232
+ hb_font_t * font_b = hb_font_create (b);
233
+ bool a_present = hb_font_get_nominal_glyph (font_a, codepoint, &gid_a);
234
+ bool b_present = hb_font_get_nominal_glyph (font_b, codepoint, &gid_b);
235
+ hb_font_destroy (font_a);
236
+ hb_font_destroy (font_b);
237
+
238
+ if (!a_present && !b_present) {
239
+ return true ;
240
+ }
241
+
242
+ if (a_present != b_present) {
243
+ return false ;
244
+ }
245
+
246
+ auto a_data = FontHelper::GvarData (a, gid_a);
247
+ auto b_data = FontHelper::GvarData (b, gid_b);
248
+
249
+ return a_data->substr (ignore_count) == b_data->substr (ignore_count);
250
+ }
251
+
255
252
// TODO(garretrieger): full expansion test.
256
253
// TODO(garretrieger): test of a woff2 encoded IFT font.
257
254
// TODO(garretrieger): add IFTB only test case.
@@ -750,10 +747,9 @@ TEST_F(IntegrationTest, MixedMode_SequentialDependentPatches) {
750
747
ASSERT_TRUE (codepoints.contains (chunk4_cp));
751
748
}
752
749
753
- /*
754
750
TEST_F (IntegrationTest, MixedMode_DesignSpaceAugmentation) {
755
751
Encoder encoder;
756
- auto sc = InitEncoderForVfIftb (encoder);
752
+ auto sc = InitEncoderForVfMixedMode (encoder);
757
753
ASSERT_TRUE (sc.ok ()) << sc;
758
754
759
755
// target paritions: {{0, 1}, {2}, {3, 4}} + add wght axis
@@ -763,77 +759,39 @@ TEST_F(IntegrationTest, MixedMode_DesignSpaceAugmentation) {
763
759
sc.Update (encoder.AddExtensionSubsetOfIftbPatches ({3 , 4 }));
764
760
encoder.AddOptionalDesignSpace ({{kWght , *AxisRange::Range (100 , 900 )}});
765
761
encoder.AddIftbUrlTemplateOverride ({{kWght , *AxisRange::Range (100 , 900 )}},
766
- "vf-0x$2$1");
767
-
762
+ " vf-{id}" );
768
763
ASSERT_TRUE (sc.ok ()) << sc;
769
764
770
765
auto encoded = encoder.Encode ();
771
766
ASSERT_TRUE (encoded.ok ()) << encoded.status ();
772
-
773
- auto client = IFTClient::NewClient(std::move(*encoded));
774
- ASSERT_TRUE(client.ok()) << client.status();
767
+ auto encoded_face = encoded->face ();
775
768
776
769
// Phase 1: non VF augmentation.
777
- client->AddDesiredCodepoints({chunk3_cp, chunk4_cp});
778
- auto state = client->Process();
779
- ASSERT_TRUE(state.ok()) << state.status();
780
- ASSERT_EQ(*state, IFTClient::NEEDS_PATCHES);
781
-
782
- auto patches = client->PatchesNeeded();
783
- flat_hash_set<std::string> expected_patches = {"0x03", "0x04", "0x06"};
784
- ASSERT_EQ(patches, expected_patches);
785
- sc = AddPatches(*client, encoder);
786
- ASSERT_TRUE(sc.ok()) << sc;
787
-
788
- state = client->Process();
789
- ASSERT_TRUE(state.ok()) << state.status();
790
- ASSERT_EQ(*state, IFTClient::READY);
770
+ auto extended = Extend (encoder, *encoded, {chunk3_cp, chunk4_cp});
771
+ ASSERT_TRUE (extended.ok ()) << extended.status ();
772
+ auto extended_face = extended->face ();
791
773
792
774
// Phase 2: VF augmentation.
793
- sc = client->AddDesiredDesignSpace(kWght, 100, 900);
794
- ASSERT_TRUE(sc.ok()) << sc;
795
- state = client->Process();
796
- ASSERT_TRUE(state.ok()) << state.status();
797
- ASSERT_EQ(*state, IFTClient::NEEDS_PATCHES);
798
-
799
- patches = client->PatchesNeeded();
800
- expected_patches = {
801
- "0x0d",
802
- };
803
- ASSERT_EQ(patches, expected_patches);
804
- sc = AddPatches(*client, encoder);
805
- ASSERT_TRUE(sc.ok()) << sc;
806
-
807
- state = client->Process();
808
- ASSERT_TRUE(state.ok()) << state.status();
809
- ASSERT_EQ(*state, IFTClient::NEEDS_PATCHES);
810
-
811
- ASSERT_TRUE(GvarHasLongOffsets(client->GetFontData()));
812
- hb_face_unique_ptr face = client->GetFontData().face();
813
- ASSERT_GT(FontHelper::GvarData(face.get(), chunk0_gid)->size(), 0);
814
- ASSERT_GT(FontHelper::GvarData(face.get(), chunk1_gid)->size(), 0);
815
- ASSERT_EQ(FontHelper::GvarData(face.get(), chunk2_gid)->size(), 0);
816
- ASSERT_EQ(FontHelper::GvarData(face.get(), chunk3_gid)->size(), 0);
817
- ASSERT_EQ(FontHelper::GvarData(face.get(), chunk4_gid)->size(), 0);
818
-
819
- patches = client->PatchesNeeded();
820
- expected_patches = {"vf-0x03", "vf-0x04"};
821
- ASSERT_EQ(patches, expected_patches);
822
- sc = AddPatches(*client, encoder);
823
- ASSERT_TRUE(sc.ok()) << sc;
775
+ extended = ExtendWithDesignSpace (encoder, *encoded, {chunk3_cp, chunk4_cp},
776
+ {}, {{kWght , *AxisRange::Range (100 , 900 )}});
777
+ ASSERT_TRUE (extended.ok ()) << extended.status ();
778
+ extended_face = extended->face ();
824
779
825
- state = client->Process();
826
- ASSERT_TRUE(state.ok()) << state.status();
827
- ASSERT_EQ(*state, IFTClient::READY);
780
+ ASSERT_TRUE (GvarHasLongOffsets (*extended));
781
+ ASSERT_GT (FontHelper::GvarData (extended_face.get (), chunk0_gid)->size (), 0 );
782
+ ASSERT_GT (FontHelper::GvarData (extended_face.get (), chunk1_gid)->size (), 0 );
783
+ ASSERT_EQ (FontHelper::GvarData (extended_face.get (), chunk2_gid)->size (), 0 );
784
+ ASSERT_GT (FontHelper::GvarData (extended_face.get (), chunk3_gid)->size (), 0 );
785
+ ASSERT_GT (FontHelper::GvarData (extended_face.get (), chunk4_gid)->size (), 0 );
828
786
829
- face = client->GetFontData().face();
830
- ASSERT_GT(FontHelper::GvarData(face.get(), chunk0_gid)->size(), 0);
831
- ASSERT_GT(FontHelper::GvarData(face.get(), chunk1_gid)->size(), 0);
832
- ASSERT_EQ(FontHelper::GvarData(face.get(), chunk2_gid)->size(), 0);
833
- ASSERT_GT(FontHelper::GvarData(face.get(), chunk3_gid)->size(), 0);
834
- ASSERT_GT(FontHelper::GvarData(face.get(), chunk4_gid)->size(), 0);
787
+ auto orig_face = noto_sans_vf_.face ();
788
+ // The instancing processes changes some of the flags on the gvar data section
789
+ // so ignore diffs in the first 7 bytes
790
+ ASSERT_TRUE (
791
+ GvarDataMatches (orig_face.get (), extended_face.get (), chunk3_cp, 7 ));
835
792
}
836
793
794
+ /*
837
795
TEST_F(IntegrationTest, MixedMode_DesignSpaceAugmentation_DropsUnusedPatches) {
838
796
Encoder encoder;
839
797
auto sc = InitEncoderForVfIftb(encoder);
0 commit comments