Charlie Jiang pushed to branch gsoc-2022-chariri-3 at FreeType / FreeType Demo Programs
Commits:
-
3f7c5c85
by Charlie Jiang at 2022-09-01T23:05:01+08:00
6 changed files:
- src/ftinspect/engine/engine.cpp
- src/ftinspect/engine/engine.hpp
- src/ftinspect/maingui.cpp
- src/ftinspect/models/fontinfomodels.cpp
- src/ftinspect/models/fontinfomodels.hpp
- src/ftinspect/panels/info.cpp
Changes:
... | ... | @@ -282,6 +282,7 @@ Engine::loadFont(int fontIndex, |
282 | 282 | {
|
283 | 283 | int numGlyphs = -1;
|
284 | 284 | fontType_ = FontType_Other;
|
285 | + palette_ = NULL;
|
|
285 | 286 | |
286 | 287 | update();
|
287 | 288 | curSFNTTablesValid_ = false;
|
... | ... | @@ -378,6 +379,7 @@ void |
378 | 379 | Engine::reloadFont()
|
379 | 380 | {
|
380 | 381 | update();
|
382 | + palette_ = NULL;
|
|
381 | 383 | if (!scaler_.face_id)
|
382 | 384 | return;
|
383 | 385 | imageType_.face_id = scaler_.face_id;
|
... | ... | @@ -865,6 +867,40 @@ Engine::resetCache() |
865 | 867 | FTC_Manager_Reset(cacheManager_);
|
866 | 868 | ftFallbackFace_ = NULL;
|
867 | 869 | ftSize_ = NULL;
|
870 | + palette_ = NULL;
|
|
871 | +}
|
|
872 | + |
|
873 | + |
|
874 | +void
|
|
875 | +Engine::loadDefaults()
|
|
876 | +{
|
|
877 | + if (fontType_ == FontType_CFF)
|
|
878 | + setCFFHintingMode(engineDefaults_.cffHintingEngineDefault);
|
|
879 | + else if (fontType_ == FontType_TrueType)
|
|
880 | + {
|
|
881 | + if (currentFontTricky())
|
|
882 | + setTTInterpreterVersion(TT_INTERPRETER_VERSION_35);
|
|
883 | + else
|
|
884 | + setTTInterpreterVersion(engineDefaults_.ttInterpreterVersionDefault);
|
|
885 | + }
|
|
886 | + setStemDarkening(false);
|
|
887 | + applyMMGXDesignCoords(NULL, 0);
|
|
888 | + |
|
889 | + setAntiAliasingEnabled(true);
|
|
890 | + setAntiAliasingTarget(FT_LOAD_TARGET_NORMAL);
|
|
891 | + setHinting(true);
|
|
892 | + setAutoHinting(false);
|
|
893 | + setGamma(1.8);
|
|
894 | + setEmbeddedBitmap(true);
|
|
895 | + setPaletteIndex(0);
|
|
896 | + setUseColorLayer(true);
|
|
897 | + |
|
898 | + renderingEngine()->setBackground(qRgba(255, 255, 255, 255));
|
|
899 | + renderingEngine()->setForeground(qRgba(0, 0, 0, 255));
|
|
900 | + |
|
901 | + resetCache();
|
|
902 | + reloadFont();
|
|
903 | + loadPalette();
|
|
868 | 904 | }
|
869 | 905 | |
870 | 906 |
... | ... | @@ -102,6 +102,7 @@ public: |
102 | 102 |
|
103 | 103 | void update();
|
104 | 104 | void resetCache();
|
105 | + void loadDefaults();
|
|
105 | 106 | |
106 | 107 | //////// Getters
|
107 | 108 |
... | ... | @@ -235,7 +235,10 @@ void |
235 | 235 | MainGUI::syncSettings()
|
236 | 236 | {
|
237 | 237 | if (tabWidget_->currentWidget() != comparatorTab_)
|
238 | + {
|
|
238 | 239 | settingPanel_->syncSettings();
|
240 | + settingPanel_->applyDelayedSettings();
|
|
241 | + }
|
|
239 | 242 | }
|
240 | 243 | |
241 | 244 |
... | ... | @@ -494,7 +494,7 @@ CompositeGlyphsInfoModel::index(int row, |
494 | 494 | int column,
|
495 | 495 | const QModelIndex& parent) const
|
496 | 496 | {
|
497 | - long long parentIdx = -1;
|
|
497 | + long long parentIdx = -1; // node index.
|
|
498 | 498 | if (parent.isValid()) // Not top-level
|
499 | 499 | parentIdx = static_cast<long long>(parent.internalId());
|
500 | 500 | if (parentIdx < 0)
|
... | ... | @@ -510,25 +510,33 @@ CompositeGlyphsInfoModel::index(int row, |
510 | 510 | return createIndex(row, column, iter->second);
|
511 | 511 | }
|
512 | 512 | |
513 | - int id = -1;
|
|
513 | + int glyphIndex = -1;
|
|
514 | 514 | CompositeGlyphInfo::SubGlyph const* sgInfo = nullptr;
|
515 | 515 | if (!parent.isValid()) // top-level nodes
|
516 | - id = glyphs_[row].index;
|
|
517 | - else if (parent.internalId() < glyphs_.size())
|
|
516 | + glyphIndex = glyphs_[row].index;
|
|
517 | + else if (parent.internalId() < nodes_.size())
|
|
518 | 518 | {
|
519 | - auto& sg = glyphs_[parent.internalId()].subglyphs;
|
|
520 | - if (row < 0 || static_cast<size_t>(row) >= sg.size())
|
|
519 | + auto& parentInfoIndex = nodes_[parent.internalId()].glyphInfoIndex;
|
|
520 | + if (parentInfoIndex < 0
|
|
521 | + || static_cast<size_t>(parentInfoIndex) > glyphs_.size())
|
|
521 | 522 | return {};
|
522 | - id = sg[row].index;
|
|
523 | + |
|
524 | + auto& sg = glyphs_[parentInfoIndex].subglyphs;
|
|
525 | + glyphIndex = sg[row].index;
|
|
523 | 526 | sgInfo = &sg[row];
|
524 | 527 | }
|
525 | 528 | |
526 | - if (id < 0)
|
|
529 | + if (glyphIndex < 0)
|
|
527 | 530 | return {};
|
531 | + |
|
532 | + ptrdiff_t glyphInfoIndex = -1;
|
|
533 | + auto iterGlyphInfoIter = glyphMapper_.find(glyphIndex);
|
|
534 | + if (iterGlyphInfoIter != glyphMapper_.end())
|
|
535 | + glyphInfoIndex = static_cast<ptrdiff_t>(iterGlyphInfoIter->second);
|
|
528 | 536 |
|
529 | 537 | InfoNode node = {
|
530 | 538 | parentIdx,
|
531 | - row, id,
|
|
539 | + row, glyphIndex, glyphInfoIndex,
|
|
532 | 540 | sgInfo
|
533 | 541 | };
|
534 | 542 | nodes_.push_back(node);
|
... | ... | @@ -590,6 +598,19 @@ CompositeGlyphsInfoModel::data(const QModelIndex& index, |
590 | 598 | return {};
|
591 | 599 | }
|
592 | 600 | |
601 | + if (role == Qt::DecorationRole && index.column() == CGIM_Glyph)
|
|
602 | + {
|
|
603 | + auto glyphIndex = n.glyphIndex;
|
|
604 | + auto iter = glyphIcons_.find(glyphIndex);
|
|
605 | + if (iter == glyphIcons_.end())
|
|
606 | + iter = glyphIcons_.emplace(glyphIndex, renderIcon(glyphIndex)).first;
|
|
607 | + |
|
608 | + auto& pixmap = iter->second;
|
|
609 | + if (pixmap.isNull())
|
|
610 | + return {};
|
|
611 | + return pixmap;
|
|
612 | + }
|
|
613 | + |
|
593 | 614 | if (role != Qt::DisplayRole)
|
594 | 615 | return {};
|
595 | 616 | |
... | ... | @@ -675,8 +696,36 @@ CompositeGlyphsInfoModel::endModelUpdate() |
675 | 696 | glyphMapper_.clear();
|
676 | 697 | for (size_t i = 0; i < glyphs_.size(); i++)
|
677 | 698 | glyphMapper_.emplace(glyphs_[i].index, i);
|
699 | + |
|
700 | + glyphIcons_.clear();
|
|
678 | 701 | endResetModel();
|
679 | 702 | }
|
680 | 703 | |
681 | 704 | |
705 | +QPixmap
|
|
706 | +CompositeGlyphsInfoModel::renderIcon(int glyphIndex) const
|
|
707 | +{
|
|
708 | + engine_->setSizeByPixel(20); // This size is arbitrary
|
|
709 | + if (!engine_->currentPalette())
|
|
710 | + engine_->loadPalette();
|
|
711 | + auto image = engine_->renderingEngine()
|
|
712 | + ->tryDirectRenderColorLayers(glyphIndex, NULL, false);
|
|
713 | + if (!image)
|
|
714 | + {
|
|
715 | + auto glyph = engine_->loadGlyph(glyphIndex);
|
|
716 | + if (!glyph)
|
|
717 | + return {};
|
|
718 | + image = engine_->renderingEngine()
|
|
719 | + ->convertGlyphToQImage(glyph, NULL, false);
|
|
720 | + }
|
|
721 | + |
|
722 | + if (!image)
|
|
723 | + return {};
|
|
724 | + |
|
725 | + auto result = QPixmap::fromImage(*image);
|
|
726 | + delete image;
|
|
727 | + return result;
|
|
728 | +}
|
|
729 | + |
|
730 | + |
|
682 | 731 | // end of fontinfomodels.cpp |
... | ... | @@ -11,6 +11,7 @@ |
11 | 11 | #include <vector>
|
12 | 12 | #include <unordered_map>
|
13 | 13 | #include <QAbstractTableModel>
|
14 | +#include <QPixmap>
|
|
14 | 15 | |
15 | 16 | class FixedSizeInfoModel
|
16 | 17 | : public QAbstractTableModel
|
... | ... | @@ -231,6 +232,7 @@ public: |
231 | 232 | long long parentNodeIndex;
|
232 | 233 | int indexInParent;
|
233 | 234 | int glyphIndex;
|
235 | + ptrdiff_t glyphInfoIndex;
|
|
234 | 236 | CompositeGlyphInfo::SubGlyph const* subGlyphInfo;
|
235 | 237 | };
|
236 | 238 | |
... | ... | @@ -272,6 +274,8 @@ private: |
272 | 274 | * 3. Node Index
|
273 | 275 | */
|
274 | 276 | std::vector<CompositeGlyphInfo> glyphs_;
|
277 | + |
|
278 | + // glyph index -> glyph info index
|
|
275 | 279 | std::unordered_map<int, size_t> glyphMapper_;
|
276 | 280 | // map <row, parentId> to node
|
277 | 281 | // the internal id of `QModelIndex` is the node's index
|
... | ... | @@ -279,6 +283,11 @@ private: |
279 | 283 | long long, LookupPairHash>
|
280 | 284 | nodeLookup_;
|
281 | 285 | mutable std::vector<InfoNode> nodes_;
|
286 | + |
|
287 | + mutable std::unordered_map<int, QPixmap> glyphIcons_;
|
|
288 | + |
|
289 | + // has to be const
|
|
290 | + QPixmap renderIcon(int glyphIndex) const;
|
|
282 | 291 | };
|
283 | 292 | |
284 | 293 |
... | ... | @@ -991,7 +991,7 @@ CompositeGlyphsTab::createConnections() |
991 | 991 | void
|
992 | 992 | CompositeGlyphsTab::forceReloadFont()
|
993 | 993 | {
|
994 | - engine_->reloadFont();
|
|
994 | + engine_->loadDefaults(); // this would reload the font
|
|
995 | 995 | auto face = engine_->currentFallbackFtFace();
|
996 | 996 | if (!face || !FT_IS_SFNT(face))
|
997 | 997 | {
|