Home | History | Annotate | Download | only in gfx
      1 // Copyright (c) 2012 The Chromium Authors. All rights reserved.
      2 // Use of this source code is governed by a BSD-style license that can be
      3 // found in the LICENSE file.
      4 
      5 #include "ui/gfx/font_list.h"
      6 
      7 #include <algorithm>
      8 #include <string>
      9 #include <vector>
     10 
     11 #include "base/strings/string_number_conversions.h"
     12 #include "base/strings/string_util.h"
     13 #include "testing/gtest/include/gtest/gtest.h"
     14 
     15 namespace {
     16 
     17 // Helper function for comparing fonts for equality.
     18 std::string FontToString(const gfx::Font& font) {
     19   std::string font_string = font.GetFontName();
     20   font_string += "|";
     21   font_string += base::IntToString(font.GetFontSize());
     22   int style = font.GetStyle();
     23   if (style & gfx::Font::BOLD)
     24     font_string += "|bold";
     25   if (style & gfx::Font::ITALIC)
     26     font_string += "|italic";
     27   if (style & gfx::Font::UNDERLINE)
     28     font_string += "|underline";
     29   return font_string;
     30 }
     31 
     32 }  // namespace
     33 
     34 namespace gfx {
     35 
     36 TEST(FontListTest, FontDescString_FromDescString) {
     37   // Test init from font name style size string.
     38   FontList font_list = FontList("Droid Sans serif, Sans serif, 10px");
     39   EXPECT_EQ("Droid Sans serif, Sans serif, 10px",
     40             font_list.GetFontDescriptionString());
     41 }
     42 
     43 TEST(FontListTest, FontDescString_FromFontNamesStyleAndSize) {
     44   // Test init from font names, style and size.
     45   std::vector<std::string> font_names;
     46   font_names.push_back("Arial");
     47   font_names.push_back("Droid Sans serif");
     48   int font_style = Font::BOLD | Font::ITALIC | Font::UNDERLINE;
     49   int font_size = 11;
     50   FontList font_list = FontList(font_names, font_style, font_size);
     51   // "Underline" doesn't appear in the font description string.
     52   EXPECT_EQ("Arial,Droid Sans serif,Bold Italic 11px",
     53             font_list.GetFontDescriptionString());
     54 }
     55 
     56 TEST(FontListTest, FontDescString_FromFont) {
     57   // Test init from Font.
     58   Font font("Arial", 8);
     59   FontList font_list = FontList(font);
     60   EXPECT_EQ("Arial,8px", font_list.GetFontDescriptionString());
     61 }
     62 
     63 TEST(FontListTest, FontDescString_FromFontWithNonNormalStyle) {
     64   // Test init from Font with non-normal style.
     65   Font font("Arial", 8);
     66   FontList font_list = FontList(font.Derive(2, Font::BOLD));
     67   EXPECT_EQ("Arial,Bold 10px", font_list.GetFontDescriptionString());
     68 
     69   font_list = FontList(font.Derive(-2, Font::ITALIC));
     70   EXPECT_EQ("Arial,Italic 6px", font_list.GetFontDescriptionString());
     71 
     72   // "Underline" doesn't appear in the font description string.
     73   font_list = FontList(font.Derive(-4, Font::UNDERLINE));
     74   EXPECT_EQ("Arial,4px", font_list.GetFontDescriptionString());
     75 }
     76 
     77 TEST(FontListTest, FontDescString_FromFontVector) {
     78   // Test init from Font vector.
     79   Font font("Arial", 8);
     80   Font font_1("Sans serif", 10);
     81   std::vector<Font> fonts;
     82   fonts.push_back(font.Derive(0, Font::BOLD));
     83   fonts.push_back(font_1.Derive(-2, Font::BOLD));
     84   FontList font_list = FontList(fonts);
     85   EXPECT_EQ("Arial,Sans serif,Bold 8px", font_list.GetFontDescriptionString());
     86 }
     87 
     88 TEST(FontListTest, Fonts_FromDescString) {
     89   // Test init from font name size string.
     90   FontList font_list = FontList("serif,Sans serif, 13px");
     91   const std::vector<Font>& fonts = font_list.GetFonts();
     92   EXPECT_EQ(2U, fonts.size());
     93   EXPECT_EQ("serif|13", FontToString(fonts[0]));
     94   EXPECT_EQ("Sans serif|13", FontToString(fonts[1]));
     95 }
     96 
     97 TEST(FontListTest, Fonts_FromDescStringInFlexibleFormat) {
     98   // Test init from font name size string with flexible format.
     99   FontList font_list = FontList("  serif   ,   Sans serif ,   13px");
    100   const std::vector<Font>& fonts = font_list.GetFonts();
    101   EXPECT_EQ(2U, fonts.size());
    102   EXPECT_EQ("serif|13", FontToString(fonts[0]));
    103   EXPECT_EQ("Sans serif|13", FontToString(fonts[1]));
    104 }
    105 
    106 TEST(FontListTest, Fonts_FromDescStringWithStyleInFlexibleFormat) {
    107   // Test init from font name style size string with flexible format.
    108   FontList font_list = FontList("  serif  ,  Sans serif ,  Bold   "
    109                                 "  Italic   13px");
    110   const std::vector<Font>& fonts = font_list.GetFonts();
    111   EXPECT_EQ(2U, fonts.size());
    112   EXPECT_EQ("serif|13|bold|italic", FontToString(fonts[0]));
    113   EXPECT_EQ("Sans serif|13|bold|italic", FontToString(fonts[1]));
    114 }
    115 
    116 TEST(FontListTest, Fonts_FromFont) {
    117   // Test init from Font.
    118   Font font("Arial", 8);
    119   FontList font_list = FontList(font);
    120   const std::vector<Font>& fonts = font_list.GetFonts();
    121   EXPECT_EQ(1U, fonts.size());
    122   EXPECT_EQ("Arial|8", FontToString(fonts[0]));
    123 }
    124 
    125 TEST(FontListTest, Fonts_FromFontWithNonNormalStyle) {
    126   // Test init from Font with non-normal style.
    127   Font font("Arial", 8);
    128   FontList font_list = FontList(font.Derive(2, Font::BOLD));
    129   std::vector<Font> fonts = font_list.GetFonts();
    130   EXPECT_EQ(1U, fonts.size());
    131   EXPECT_EQ("Arial|10|bold", FontToString(fonts[0]));
    132 
    133   font_list = FontList(font.Derive(-2, Font::ITALIC));
    134   fonts = font_list.GetFonts();
    135   EXPECT_EQ(1U, fonts.size());
    136   EXPECT_EQ("Arial|6|italic", FontToString(fonts[0]));
    137 }
    138 
    139 TEST(FontListTest, Fonts_FromFontVector) {
    140   // Test init from Font vector.
    141   Font font("Arial", 8);
    142   Font font_1("Sans serif", 10);
    143   std::vector<Font> input_fonts;
    144   input_fonts.push_back(font.Derive(0, Font::BOLD));
    145   input_fonts.push_back(font_1.Derive(-2, Font::BOLD));
    146   FontList font_list = FontList(input_fonts);
    147   const std::vector<Font>& fonts = font_list.GetFonts();
    148   EXPECT_EQ(2U, fonts.size());
    149   EXPECT_EQ("Arial|8|bold", FontToString(fonts[0]));
    150   EXPECT_EQ("Sans serif|8|bold", FontToString(fonts[1]));
    151 }
    152 
    153 TEST(FontListTest, Fonts_DescStringWithStyleInFlexibleFormat_RoundTrip) {
    154   // Test round trip from font description string to font vector to
    155   // font description string.
    156   FontList font_list = FontList("  serif  ,  Sans serif ,  Bold   "
    157                                 "  Italic   13px");
    158 
    159   const std::vector<Font>& fonts = font_list.GetFonts();
    160   FontList font_list_1 = FontList(fonts);
    161   const std::string& desc_str = font_list_1.GetFontDescriptionString();
    162 
    163   EXPECT_EQ("serif,Sans serif,Bold Italic 13px", desc_str);
    164 }
    165 
    166 TEST(FontListTest, Fonts_FontVector_RoundTrip) {
    167   // Test round trip from font vector to font description string to font vector.
    168   Font font("Arial", 8);
    169   Font font_1("Sans serif", 10);
    170   std::vector<Font> input_fonts;
    171   input_fonts.push_back(font.Derive(0, Font::BOLD));
    172   input_fonts.push_back(font_1.Derive(-2, Font::BOLD));
    173   FontList font_list = FontList(input_fonts);
    174 
    175   const std::string& desc_string = font_list.GetFontDescriptionString();
    176   FontList font_list_1 = FontList(desc_string);
    177   const std::vector<Font>& round_trip_fonts = font_list_1.GetFonts();
    178 
    179   EXPECT_EQ(2U, round_trip_fonts.size());
    180   EXPECT_EQ("Arial|8|bold", FontToString(round_trip_fonts[0]));
    181   EXPECT_EQ("Sans serif|8|bold", FontToString(round_trip_fonts[1]));
    182 }
    183 
    184 TEST(FontListTest, FontDescString_GetStyle) {
    185   FontList font_list = FontList("Arial,Sans serif, 8px");
    186   EXPECT_EQ(Font::NORMAL, font_list.GetFontStyle());
    187 
    188   font_list = FontList("Arial,Sans serif,Bold 8px");
    189   EXPECT_EQ(Font::BOLD, font_list.GetFontStyle());
    190 
    191   font_list = FontList("Arial,Sans serif,Italic 8px");
    192   EXPECT_EQ(Font::ITALIC, font_list.GetFontStyle());
    193 
    194   font_list = FontList("Arial,Italic Bold 8px");
    195   EXPECT_EQ(Font::BOLD | Font::ITALIC, font_list.GetFontStyle());
    196 }
    197 
    198 TEST(FontListTest, Fonts_GetStyle) {
    199   std::vector<Font> fonts;
    200   fonts.push_back(gfx::Font("Arial", 8));
    201   fonts.push_back(gfx::Font("Sans serif", 8));
    202   FontList font_list = FontList(fonts);
    203   EXPECT_EQ(Font::NORMAL, font_list.GetFontStyle());
    204   fonts[0] = fonts[0].Derive(0, Font::ITALIC | Font::BOLD);
    205   fonts[1] = fonts[1].Derive(0, Font::ITALIC | Font::BOLD);
    206   font_list = FontList(fonts);
    207   EXPECT_EQ(Font::ITALIC | Font::BOLD, font_list.GetFontStyle());
    208 }
    209 
    210 TEST(FontListTest, FontDescString_Derive) {
    211   FontList font_list = FontList("Arial,Sans serif,Bold Italic 8px");
    212 
    213   FontList derived = font_list.Derive(10, Font::ITALIC | Font::UNDERLINE);
    214   EXPECT_EQ("Arial,Sans serif,Italic 18px", derived.GetFontDescriptionString());
    215   EXPECT_EQ(Font::ITALIC | Font::UNDERLINE, derived.GetFontStyle());
    216 
    217   // FontList has a special case for Font::UNDERLINE.  See if the handling of
    218   // Font::UNDERLINE in GetFonts() is okay or not.
    219   derived.GetFonts();
    220   EXPECT_EQ(Font::ITALIC | Font::UNDERLINE, derived.GetFontStyle());
    221 }
    222 
    223 TEST(FontListTest, Fonts_Derive) {
    224   std::vector<Font> fonts;
    225   fonts.push_back(gfx::Font("Arial", 8));
    226   fonts.push_back(gfx::Font("Sans serif", 8));
    227   FontList font_list = FontList(fonts);
    228 
    229   FontList derived = font_list.Derive(5, Font::BOLD | Font::UNDERLINE);
    230   const std::vector<Font>& derived_fonts = derived.GetFonts();
    231 
    232   EXPECT_EQ(2U, derived_fonts.size());
    233   EXPECT_EQ("Arial|13|bold|underline", FontToString(derived_fonts[0]));
    234   EXPECT_EQ("Sans serif|13|bold|underline", FontToString(derived_fonts[1]));
    235 }
    236 
    237 TEST(FontListTest, FontDescString_DeriveWithSizeDelta) {
    238   FontList font_list = FontList("Arial,Sans serif,Bold 18px");
    239 
    240   FontList derived = font_list.DeriveWithSizeDelta(-8);
    241   EXPECT_EQ("Arial,Sans serif,Bold 10px",
    242             derived.GetFontDescriptionString());
    243 }
    244 
    245 TEST(FontListTest, Fonts_DeriveWithSizeDelta) {
    246   std::vector<Font> fonts;
    247   fonts.push_back(gfx::Font("Arial", 18).Derive(0, Font::ITALIC));
    248   fonts.push_back(gfx::Font("Sans serif", 18).Derive(0, Font::ITALIC));
    249   FontList font_list = FontList(fonts);
    250 
    251   FontList derived = font_list.DeriveWithSizeDelta(-5);
    252   const std::vector<Font>& derived_fonts = derived.GetFonts();
    253 
    254   EXPECT_EQ(2U, derived_fonts.size());
    255   EXPECT_EQ("Arial|13|italic", FontToString(derived_fonts[0]));
    256   EXPECT_EQ("Sans serif|13|italic", FontToString(derived_fonts[1]));
    257 }
    258 
    259 TEST(FontListTest, Fonts_GetHeight_GetBaseline) {
    260   // If a font list has only one font, the height and baseline must be the same.
    261   Font font1("Arial", 16);
    262   ASSERT_EQ("arial",
    263             base::StringToLowerASCII(font1.GetActualFontNameForTesting()));
    264   FontList font_list1("Arial, 16px");
    265   EXPECT_EQ(font1.GetHeight(), font_list1.GetHeight());
    266   EXPECT_EQ(font1.GetBaseline(), font_list1.GetBaseline());
    267 
    268   // If there are two different fonts, the font list returns the max value
    269   // for ascent and descent.
    270   Font font2("Symbol", 16);
    271   ASSERT_EQ("symbol",
    272             base::StringToLowerASCII(font2.GetActualFontNameForTesting()));
    273   EXPECT_NE(font1.GetBaseline(), font2.GetBaseline());
    274   EXPECT_NE(font1.GetHeight() - font1.GetBaseline(),
    275             font2.GetHeight() - font2.GetBaseline());
    276   std::vector<Font> fonts;
    277   fonts.push_back(font1);
    278   fonts.push_back(font2);
    279   FontList font_list_mix(fonts);
    280   // ascent of FontList == max(ascent of Fonts)
    281   EXPECT_EQ(std::max(font1.GetHeight() - font1.GetBaseline(),
    282                      font2.GetHeight() - font2.GetBaseline()),
    283             font_list_mix.GetHeight() - font_list_mix.GetBaseline());
    284   // descent of FontList == max(descent of Fonts)
    285   EXPECT_EQ(std::max(font1.GetBaseline(), font2.GetBaseline()),
    286             font_list_mix.GetBaseline());
    287 }
    288 
    289 TEST(FontListTest, Fonts_DeriveWithHeightUpperBound) {
    290   std::vector<Font> fonts;
    291 
    292   fonts.push_back(gfx::Font("Arial", 18));
    293   fonts.push_back(gfx::Font("Sans serif", 18));
    294   fonts.push_back(gfx::Font("Symbol", 18));
    295   FontList font_list = FontList(fonts);
    296 
    297   // A smaller upper bound should derive a font list with a smaller height.
    298   const int height_1 = font_list.GetHeight() - 5;
    299   FontList derived_1 = font_list.DeriveWithHeightUpperBound(height_1);
    300   EXPECT_LE(derived_1.GetHeight(), height_1);
    301   EXPECT_LT(derived_1.GetHeight(), font_list.GetHeight());
    302   EXPECT_LT(derived_1.GetFontSize(), font_list.GetFontSize());
    303 
    304   // A larger upper bound should not change the height of the font list.
    305   const int height_2 = font_list.GetHeight() + 5;
    306   FontList derived_2 = font_list.DeriveWithHeightUpperBound(height_2);
    307   EXPECT_LE(derived_2.GetHeight(), height_2);
    308   EXPECT_EQ(font_list.GetHeight(), derived_2.GetHeight());
    309   EXPECT_EQ(font_list.GetFontSize(), derived_2.GetFontSize());
    310 }
    311 
    312 }  // namespace gfx
    313