/************************************************************************* ** GFReaderTest.cpp ** ** ** ** This file is part of dvisvgm -- a fast DVI to SVG converter ** ** Copyright (C) 2005-2024 Martin Gieseking ** ** ** ** This program is free software; you can redistribute it and/or ** ** modify it under the terms of the GNU General Public License as ** ** published by the Free Software Foundation; either version 3 of ** ** the License, or (at your option) any later version. ** ** ** ** This program is distributed in the hope that it will be useful, but ** ** WITHOUT ANY WARRANTY; without even the implied warranty of ** ** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the ** ** GNU General Public License for more details. ** ** ** ** You should have received a copy of the GNU General Public License ** ** along with this program; if not, see . ** *************************************************************************/ #include #include #include #include #include #include "GFReader.hpp" #ifndef SRCDIR #define SRCDIR "." #endif using namespace std; struct PixelActions : public Bitmap::Callback { void pixel (int x, int y, bool set, const Bitmap &bm) { if (charmap.size() == 0) { charmap.resize(bm.height()); for (int i=0; i < bm.height(); i++) charmap[i] = string(bm.width(), ' '); } EXPECT_GE(x, 0); EXPECT_LT(x, bm.width()); EXPECT_GE(y, 0); EXPECT_LT(y, bm.height()); charmap[y][x] = (set ? '*' : '-'); } vector charmap; }; const char *letter_a[] = { "-----------********--------------------", "--------**************-----------------", "------*****-------******---------------", "-----***------------*****--------------", "----*****------------******------------", "---*******------------******-----------", "---********-----------******-----------", "---********------------******----------", "---********------------******----------", "---********-------------******---------", "----******--------------******---------", "-----****---------------******---------", "------------------------******---------", "------------------------******---------", "------------------------******---------", "------------------------******---------", "-----------------*************---------", "-------------*****************---------", "----------*********-----******---------", "--------*******---------******---------", "------*******-----------******---------", "----********------------******---------", "---*******--------------******---------", "--********--------------******---------", "-********---------------******---------", "-*******----------------******---------", "-*******----------------******------**-", "*******-----------------******------**-", "*******-----------------******------**-", "*******-----------------******------**-", "*******----------------*******------**-", "*******----------------*******------**-", "********--------------********------**-", "-*******-------------***-*****------**-", "-********------------**---*****----**--", "--********---------****---*****----**--", "----*******------****------*********---", "------**************--------*******----", "---------********------------*****-----", }; const char *letter_g[] = { "------------------------------******---", "------------********--------*********--", "----------************----****----****-", "--------*****------*****-***-----*****-", "-------*****--------*******------*****-", "------*****----------*****-------*****-", "-----*****------------*****--------*---", "----******------------******-----------", "----******------------******-----------", "---******--------------******----------", "---******--------------******----------", "---******--------------******----------", "---******--------------******----------", "---******--------------******----------", "---******--------------******----------", "---******--------------******----------", "---******--------------******----------", "----******------------******-----------", "----******------------******-----------", "-----*****------------*****------------", "------*****----------*****-------------", "------******--------*****--------------", "------*******------*****---------------", "-----***--************-----------------", "-----**-----********-------------------", "----***--------------------------------", "----***--------------------------------", "----***--------------------------------", "----***--------------------------------", "----****-------------------------------", "----****-------------------------------", "----******-----------------------------", "-----*********************-------------", "-----************************----------", "------*************************--------", "-------**************************------", "------****************************-----", "----*****----------------**********----", "---*****--------------------********---", "--*****-----------------------******---", "-*****-------------------------*****---", "-*****-------------------------******--", "*****---------------------------*****--", "*****---------------------------*****--", "*****---------------------------*****--", "*****---------------------------*****--", "*****---------------------------*****--", "******-------------------------******--", "-*****-------------------------*****---", "--*****-----------------------*****----", "--******---------------------******----", "----*****-------------------*****------", "-----******---------------******-------", "-------*******---------*******---------", "---------*******************-----------", "-------------***********---------------", }; const char *letter_M[] = { "****************-------------------------------------****************-", "*****************-----------------------------------*****************-", "*****************-----------------------------------*****************-", "-------**********-----------------------------------**********--------", "--------**-*******---------------------------------**-*******---------", "--------**-*******---------------------------------**-*******---------", "--------**--*******-------------------------------**--*******---------", "--------**--*******-------------------------------**--*******---------", "--------**--*******-------------------------------**--*******---------", "--------**---*******-----------------------------**---*******---------", "--------**---*******-----------------------------**---*******---------", "--------**---*******-----------------------------**---*******---------", "--------**----*******---------------------------**----*******---------", "--------**----*******---------------------------**----*******---------", "--------**-----*******-------------------------**-----*******---------", "--------**-----*******-------------------------**-----*******---------", "--------**-----*******-------------------------**-----*******---------", "--------**------*******-----------------------**------*******---------", "--------**------*******-----------------------**------*******---------", "--------**-------*******---------------------**-------*******---------", "--------**-------*******---------------------**-------*******---------", "--------**-------*******---------------------**-------*******---------", "--------**--------*******-------------------**--------*******---------", "--------**--------*******-------------------**--------*******---------", "--------**--------*******-------------------**--------*******---------", "--------**---------*******-----------------**---------*******---------", "--------**---------*******-----------------**---------*******---------", "--------**----------*******---------------**----------*******---------", "--------**----------*******---------------**----------*******---------", "--------**----------*******---------------**----------*******---------", "--------**-----------*******-------------**-----------*******---------", "--------**-----------*******-------------**-----------*******---------", "--------**------------*******-----------**------------*******---------", "--------**------------*******-----------**------------*******---------", "--------**------------*******-----------**------------*******---------", "--------**-------------*******---------**-------------*******---------", "--------**-------------*******---------**-------------*******---------", "--------**-------------*******---------**-------------*******---------", "--------**--------------*******-------**--------------*******---------", "--------**--------------*******-------**--------------*******---------", "--------**---------------*******-----**---------------*******---------", "--------**---------------*******-----**---------------*******---------", "--------**---------------*******-----**---------------*******---------", "--------**----------------*******---**----------------*******---------", "--------**----------------*******---**----------------*******---------", "--------**-----------------*******-**-----------------*******---------", "--------**-----------------*******-**-----------------*******---------", "--------**-----------------*******-**-----------------*******---------", "--------**------------------********------------------*******---------", "--------**------------------********------------------*******---------", "--------**------------------********------------------*******---------", "-------****------------------******-------------------*******---------", "------******-----------------******-------------------*******---------", "----**********----------------****-------------------*********--------", "******************------------****------------***********************-", "******************------------****------------***********************-", "******************-------------**-------------***********************-", }; static void check_letter (const char **lettermap, const vector &charmap) { for (size_t i=0; i < charmap.size(); i++) ASSERT_EQ(lettermap[i], charmap[charmap.size()-i-1]); } class LoggingGFReader : public GFReader { public: LoggingGFReader (istream &is) : GFReader(is) {} void preamble (const string &str) override {_info = str;} string getInfo () const {return _info;} private: string _info; }; TEST(GFReaderTest, preamble) { string gf = string(SRCDIR)+"/data/cmr10.600gf"; ifstream ifs(gf, ios::binary); ASSERT_TRUE(bool(ifs)); LoggingGFReader gfReader(ifs); gfReader.executePreamble(); ASSERT_EQ(gfReader.getInfo(), " METAFONT output 2010.06.18:1911"); } TEST(GFReaderTest, postamble) { string gf = string(SRCDIR)+"/data/cmr10.600gf"; ifstream ifs(gf, ios::binary); ASSERT_TRUE(bool(ifs)); GFReader gfReader(ifs); gfReader.executePostamble(); const double bp2pt = 72.27/72.0; ASSERT_DOUBLE_EQ(gfReader.getDesignSize()*bp2pt, 10); ASSERT_NEAR(gfReader.getHPixelsPerPoint(), 8.333, 0.001); ASSERT_NEAR(gfReader.getVPixelsPerPoint(), 8.333, 0.001); } TEST(GFReaderTest, executeChar) { string gf = string(SRCDIR)+"/data/cmr10.600gf"; ifstream ifs(gf, ios::binary); ASSERT_TRUE(bool(ifs)); GFReader gfReader(ifs); PixelActions actions; { gfReader.executeChar('a'); ASSERT_EQ(gfReader.getBitmap().width(), 39); ASSERT_EQ(gfReader.getBitmap().height(), 39); SCOPED_TRACE("A"); gfReader.getBitmap().forAllPixels(actions); check_letter(letter_a, actions.charmap); }{ actions.charmap.clear(); gfReader.executeChar('g'); ASSERT_EQ(gfReader.getBitmap().width(), 39); ASSERT_EQ(gfReader.getBitmap().height(), 56); SCOPED_TRACE("B"); gfReader.getBitmap().forAllPixels(actions); check_letter(letter_g, actions.charmap); }{ actions.charmap.clear(); gfReader.executeChar('M'); ASSERT_EQ(gfReader.getBitmap().width(), 70); ASSERT_EQ(gfReader.getBitmap().height(), 57); SCOPED_TRACE("C"); gfReader.getBitmap().forAllPixels(actions); check_letter(letter_M, actions.charmap); } } TEST(GFReaderTest, executeAllChars) { string gf = string(SRCDIR)+"/data/cmr10.600gf"; ifstream ifs(gf, ios::binary); ASSERT_TRUE(bool(ifs)); GFReader gfReader(ifs); gfReader.executeAllChars(); const double bp2pt = 72.27/72.0; ASSERT_NEAR(gfReader.getCharWidth('M')*bp2pt, 0.573, 0.001); ASSERT_NEAR(gfReader.getCharWidth('g')*bp2pt, 0.313, 0.001); }