| OLD | NEW |
| 1 /* | 1 /* |
| 2 * Copyright 2011 Google Inc. All Rights Reserved. | 2 * Copyright 2011 Google Inc. All Rights Reserved. |
| 3 * | 3 * |
| 4 * Licensed under the Apache License, Version 2.0 (the "License"); | 4 * Licensed under the Apache License, Version 2.0 (the "License"); |
| 5 * you may not use this file except in compliance with the License. | 5 * you may not use this file except in compliance with the License. |
| 6 * You may obtain a copy of the License at | 6 * You may obtain a copy of the License at |
| 7 * | 7 * |
| 8 * http://www.apache.org/licenses/LICENSE-2.0 | 8 * http://www.apache.org/licenses/LICENSE-2.0 |
| 9 * | 9 * |
| 10 * Unless required by applicable law or agreed to in writing, software | 10 * Unless required by applicable law or agreed to in writing, software |
| 11 * distributed under the License is distributed on an "AS IS" BASIS, | 11 * distributed under the License is distributed on an "AS IS" BASIS, |
| 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. |
| 13 * See the License for the specific language governing permissions and | 13 * See the License for the specific language governing permissions and |
| 14 * limitations under the License. | 14 * limitations under the License. |
| 15 */ | 15 */ |
| 16 | 16 |
| 17 #include "third_party/sfntly/src/subsetter/subsetter_impl.h" | 17 #include "third_party/sfntly/src/subsetter/subsetter_impl.h" |
| 18 | 18 |
| 19 #include <string.h> | 19 #include <string.h> |
| 20 | 20 |
| 21 #include <map> | 21 #include <map> |
| 22 #include <set> | 22 #include <set> |
| 23 | 23 |
| 24 #include "third_party/sfntly/src/sfntly/glyph_table.h" | 24 #include "third_party/sfntly/src/sfntly/table/core/name_table.h" |
| 25 #include "third_party/sfntly/src/sfntly/loca_table.h" | 25 #include "third_party/sfntly/src/sfntly/table/truetype/glyph_table.h" |
| 26 #include "third_party/sfntly/src/sfntly/name_table.h" | 26 #include "third_party/sfntly/src/sfntly/table/truetype/loca_table.h" |
| 27 #include "third_party/sfntly/src/sfntly/tag.h" | 27 #include "third_party/sfntly/src/sfntly/tag.h" |
| 28 #include "third_party/sfntly/src/sfntly/data/memory_byte_array.h" | 28 #include "third_party/sfntly/src/sfntly/data/memory_byte_array.h" |
| 29 #include "third_party/sfntly/src/sfntly/port/memory_input_stream.h" |
| 29 #include "third_party/sfntly/src/sfntly/port/memory_output_stream.h" | 30 #include "third_party/sfntly/src/sfntly/port/memory_output_stream.h" |
| 30 | 31 |
| 31 namespace sfntly { | 32 namespace sfntly { |
| 32 | 33 |
| 33 void ConstructName(UChar* name_part, UnicodeString* name, int32_t name_id) { | 34 void ConstructName(UChar* name_part, UnicodeString* name, int32_t name_id) { |
| 34 switch(name_id) { | 35 switch(name_id) { |
| 35 case NameId::kFullFontName: | 36 case NameId::kFullFontName: |
| 36 *name = name_part; | 37 *name = name_part; |
| 37 break; | 38 break; |
| 38 case NameId::kFontFamilyName: | 39 case NameId::kFontFamilyName: |
| (...skipping 33 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 72 | 73 |
| 73 SubsetterImpl::SubsetterImpl() { | 74 SubsetterImpl::SubsetterImpl() { |
| 74 } | 75 } |
| 75 | 76 |
| 76 SubsetterImpl::~SubsetterImpl() { | 77 SubsetterImpl::~SubsetterImpl() { |
| 77 } | 78 } |
| 78 | 79 |
| 79 bool SubsetterImpl::LoadFont(const char* font_name, | 80 bool SubsetterImpl::LoadFont(const char* font_name, |
| 80 const unsigned char* original_font, | 81 const unsigned char* original_font, |
| 81 size_t font_size) { | 82 size_t font_size) { |
| 82 ByteArrayPtr raw_font = | 83 MemoryInputStream mis; |
| 83 new MemoryByteArray((byte_t*)original_font, font_size); | 84 mis.Attach(original_font, font_size); |
| 84 if (factory_ == NULL) { | 85 if (factory_ == NULL) { |
| 85 factory_.Attach(FontFactory::GetInstance()); | 86 factory_.Attach(FontFactory::GetInstance()); |
| 86 } | 87 } |
| 87 | 88 |
| 88 FontArray font_array; | 89 FontArray font_array; |
| 89 factory_->LoadFonts(raw_font, &font_array); | 90 factory_->LoadFonts(&mis, &font_array); |
| 90 font_ = FindFont(font_name, font_array); | 91 font_ = FindFont(font_name, font_array); |
| 91 if (font_ == NULL) { | 92 if (font_ == NULL) { |
| 92 return false; | 93 return false; |
| 93 } | 94 } |
| 94 | 95 |
| 95 return true; | 96 return true; |
| 96 } | 97 } |
| 97 | 98 |
| 98 int SubsetterImpl::SubsetFont(const unsigned int* glyph_ids, | 99 int SubsetterImpl::SubsetFont(const unsigned int* glyph_ids, |
| 99 size_t glyph_count, | 100 size_t glyph_count, |
| (...skipping 114 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 214 for (size_t i = 0; i < glyph_count; ++i) { | 215 for (size_t i = 0; i < glyph_count; ++i) { |
| 215 glyph_id_remaining.insert(glyph_ids[i]); | 216 glyph_id_remaining.insert(glyph_ids[i]); |
| 216 } | 217 } |
| 217 | 218 |
| 218 // Identify if any given glyph id maps to a composite glyph. If so, include | 219 // Identify if any given glyph id maps to a composite glyph. If so, include |
| 219 // the glyphs referenced by that composite glyph. | 220 // the glyphs referenced by that composite glyph. |
| 220 while (!glyph_id_remaining.empty()) { | 221 while (!glyph_id_remaining.empty()) { |
| 221 IntegerSet comp_glyph_id; | 222 IntegerSet comp_glyph_id; |
| 222 for (IntegerSet::iterator i = glyph_id_remaining.begin(), | 223 for (IntegerSet::iterator i = glyph_id_remaining.begin(), |
| 223 e = glyph_id_remaining.end(); i != e; ++i) { | 224 e = glyph_id_remaining.end(); i != e; ++i) { |
| 224 if (*i < 0 || *i >= loca_table->NumGlyphs()) { | 225 if (*i < 0 || *i >= loca_table->num_glyphs()) { |
| 225 // Invalid glyph id, ignore. | 226 // Invalid glyph id, ignore. |
| 226 continue; | 227 continue; |
| 227 } | 228 } |
| 228 | 229 |
| 229 int32_t length = loca_table->GlyphLength(*i); | 230 int32_t length = loca_table->GlyphLength(*i); |
| 230 if (length == 0) { | 231 if (length == 0) { |
| 231 // Empty glyph, ignore. | 232 // Empty glyph, ignore. |
| 232 continue; | 233 continue; |
| 233 } | 234 } |
| 234 int32_t offset = loca_table->GlyphOffset(*i); | 235 int32_t offset = loca_table->GlyphOffset(*i); |
| (...skipping 30 matching lines...) Expand all Loading... |
| 265 CALLER_ATTACH Font* SubsetterImpl::Subset(const IntegerSet& glyph_ids) { | 266 CALLER_ATTACH Font* SubsetterImpl::Subset(const IntegerSet& glyph_ids) { |
| 266 // The tables are already checked in ResolveCompositeGlyphs(). | 267 // The tables are already checked in ResolveCompositeGlyphs(). |
| 267 GlyphTablePtr glyph_table = | 268 GlyphTablePtr glyph_table = |
| 268 down_cast<GlyphTable*>(font_->GetTable(Tag::glyf)); | 269 down_cast<GlyphTable*>(font_->GetTable(Tag::glyf)); |
| 269 LocaTablePtr loca_table = down_cast<LocaTable*>(font_->GetTable(Tag::loca)); | 270 LocaTablePtr loca_table = down_cast<LocaTable*>(font_->GetTable(Tag::loca)); |
| 270 | 271 |
| 271 // Setup font builders we need. | 272 // Setup font builders we need. |
| 272 FontBuilderPtr font_builder; | 273 FontBuilderPtr font_builder; |
| 273 font_builder.Attach(factory_->NewFontBuilder()); | 274 font_builder.Attach(factory_->NewFontBuilder()); |
| 274 | 275 |
| 275 GlyphTableBuilderPtr glyph_table_builder; | 276 GlyphTableBuilderPtr glyph_table_builder = |
| 276 glyph_table_builder.Attach(down_cast<GlyphTable::Builder*>( | 277 down_cast<GlyphTable::Builder*>(font_builder->NewTableBuilder(Tag::glyf)); |
| 277 font_builder->NewTableBuilder(Tag::glyf))); | 278 LocaTableBuilderPtr loca_table_builder = |
| 278 LocaTableBuilderPtr loca_table_builder; | 279 down_cast<LocaTable::Builder*>(font_builder->NewTableBuilder(Tag::loca)); |
| 279 loca_table_builder.Attach(down_cast<LocaTable::Builder*>( | |
| 280 font_builder->NewTableBuilder(Tag::loca))); | |
| 281 if (glyph_table_builder == NULL || loca_table_builder == NULL) { | 280 if (glyph_table_builder == NULL || loca_table_builder == NULL) { |
| 282 // Out of memory. | 281 // Out of memory. |
| 283 return NULL; | 282 return NULL; |
| 284 } | 283 } |
| 285 | 284 |
| 286 // Extract glyphs and setup loca list. | 285 // Extract glyphs and setup loca list. |
| 287 IntegerList loca_list; | 286 IntegerList loca_list; |
| 288 loca_list.resize(loca_table->NumGlyphs()); | 287 loca_list.resize(loca_table->num_glyphs()); |
| 289 loca_list.push_back(0); | 288 loca_list.push_back(0); |
| 290 int32_t last_glyph_id = 0; | 289 int32_t last_glyph_id = 0; |
| 291 int32_t last_offset = 0; | 290 int32_t last_offset = 0; |
| 292 GlyphTable::GlyphBuilderList* glyph_builders = | 291 GlyphTable::GlyphBuilderList* glyph_builders = |
| 293 glyph_table_builder->GlyphBuilders(); | 292 glyph_table_builder->GlyphBuilders(); |
| 294 for (IntegerSet::const_iterator i = glyph_ids.begin(), e = glyph_ids.end(); | 293 for (IntegerSet::const_iterator i = glyph_ids.begin(), e = glyph_ids.end(); |
| 295 i != e; ++i) { | 294 i != e; ++i) { |
| 296 int32_t length = loca_table->GlyphLength(*i); | 295 int32_t length = loca_table->GlyphLength(*i); |
| 297 int32_t offset = loca_table->GlyphOffset(*i); | 296 int32_t offset = loca_table->GlyphOffset(*i); |
| 298 | 297 |
| 299 GlyphPtr glyph; | 298 GlyphPtr glyph; |
| 300 glyph.Attach(glyph_table->GetGlyph(offset, length)); | 299 glyph.Attach(glyph_table->GetGlyph(offset, length)); |
| 301 | 300 |
| 302 // Add glyph to new glyf table. | 301 // Add glyph to new glyf table. |
| 303 ReadableFontDataPtr data = glyph->ReadFontData(); | 302 ReadableFontDataPtr data = glyph->ReadFontData(); |
| 304 WritableFontDataPtr copy_data; | 303 WritableFontDataPtr copy_data; |
| 305 copy_data.Attach(font_builder->GetNewData(data->Length())); | 304 copy_data.Attach(WritableFontData::CreateWritableFontData(data->Length())); |
| 306 data->CopyTo(copy_data); | 305 data->CopyTo(copy_data); |
| 307 GlyphBuilderPtr glyph_builder; | 306 GlyphBuilderPtr glyph_builder; |
| 308 glyph_builder.Attach(glyph_table_builder->GlyphBuilder(copy_data)); | 307 glyph_builder.Attach(glyph_table_builder->GlyphBuilder(copy_data)); |
| 309 glyph_builders->push_back(glyph_builder); | 308 glyph_builders->push_back(glyph_builder); |
| 310 | 309 |
| 311 // Configure loca list. | 310 // Configure loca list. |
| 312 for (int32_t j = last_glyph_id + 1; j <= *i; ++j) { | 311 for (int32_t j = last_glyph_id + 1; j <= *i; ++j) { |
| 313 loca_list[j] = last_offset; | 312 loca_list[j] = last_offset; |
| 314 } | 313 } |
| 315 last_offset += length; | 314 last_offset += length; |
| 316 loca_list[*i + 1] = last_offset; | 315 loca_list[*i + 1] = last_offset; |
| 317 last_glyph_id = *i; | 316 last_glyph_id = *i; |
| 318 } | 317 } |
| 319 for (int32_t j = last_glyph_id + 1; j <= loca_table->NumGlyphs(); ++j) { | 318 for (int32_t j = last_glyph_id + 1; j <= loca_table->num_glyphs(); ++j) { |
| 320 loca_list[j] = last_offset; | 319 loca_list[j] = last_offset; |
| 321 } | 320 } |
| 322 loca_table_builder->SetLocaList(&loca_list); | 321 loca_table_builder->SetLocaList(&loca_list); |
| 323 | 322 |
| 324 // Setup remaining builders. | 323 // Setup remaining builders. |
| 325 for (TableMap::iterator i = font_->Tables()->begin(), | 324 for (TableMap::const_iterator i = font_->GetTableMap()->begin(), |
| 326 e = font_->Tables()->end(); i != e; ++i) { | 325 e = font_->GetTableMap()->end(); i != e; ++i) { |
| 327 // We already build the builder for glyph and loca. | 326 // We already build the builder for glyph and loca. |
| 328 if (i->first != Tag::glyf && i->first != Tag::loca) { | 327 if (i->first != Tag::glyf && i->first != Tag::loca) { |
| 329 // The newTableBuilder() call will alter internal state of font_builder | 328 font_builder->NewTableBuilder(i->first, i->second->ReadFontData()); |
| 330 // AND the reference count of returned object. Therefore we need to | |
| 331 // dereference it. | |
| 332 TableBuilderPtr dereference; | |
| 333 dereference.Attach( | |
| 334 font_builder->NewTableBuilder(i->first, i->second->ReadFontData())); | |
| 335 } | 329 } |
| 336 } | 330 } |
| 337 | 331 |
| 338 return font_builder->Build(); | 332 return font_builder->Build(); |
| 339 } | 333 } |
| 340 | 334 |
| 341 } // namespace sfntly | 335 } // namespace sfntly |
| OLD | NEW |