• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 // Copyright 2018 The PDFium Authors
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
4 
5 // Original code copyright 2014 Foxit Software Inc. http://www.foxitsoftware.com
6 
7 #include "core/fxcrt/css/cfx_cssdata.h"
8 
9 #include <algorithm>
10 #include <utility>
11 
12 #include "core/fxcrt/check_op.h"
13 #include "core/fxcrt/compiler_specific.h"
14 #include "core/fxcrt/css/cfx_cssstyleselector.h"
15 #include "core/fxcrt/css/cfx_cssvaluelistparser.h"
16 #include "core/fxcrt/fx_codepage.h"
17 #include "core/fxcrt/fx_extension.h"
18 
19 namespace {
20 
21 #undef CSS_PROP____
22 #define CSS_PROP____(a, b, c, d) {CFX_CSSProperty::a, c, d},
23 const CFX_CSSData::Property kPropertyTable[] = {
24 #include "core/fxcrt/css/properties.inc"
25 };
26 #undef CSS_PROP____
27 
28 #undef CSS_PROP_VALUE____
29 #define CSS_PROP_VALUE____(a, b, c) {CFX_CSSPropertyValue::a, c},
30 const CFX_CSSData::PropertyValue kPropertyValueTable[] = {
31 #include "core/fxcrt/css/property_values.inc"
32 };
33 #undef CSS_PROP_VALUE____
34 
35 const CFX_CSSData::LengthUnit kLengthUnitTable[] = {
36     {"cm", CFX_CSSNumber::Unit::kCentiMeters},
37     {"em", CFX_CSSNumber::Unit::kEMS},
38     {"ex", CFX_CSSNumber::Unit::kEXS},
39     {"in", CFX_CSSNumber::Unit::kInches},
40     {"mm", CFX_CSSNumber::Unit::kMilliMeters},
41     {"pc", CFX_CSSNumber::Unit::kPicas},
42     {"pt", CFX_CSSNumber::Unit::kPoints},
43     {"px", CFX_CSSNumber::Unit::kPixels},
44 };
45 
46 // 16 colours from CSS 2.0 + alternate spelling of grey/gray.
47 const CFX_CSSData::Color kColorTable[] = {
48     {"aqua", 0xff00ffff},    {"black", 0xff000000}, {"blue", 0xff0000ff},
49     {"fuchsia", 0xffff00ff}, {"gray", 0xff808080},  {"green", 0xff008000},
50     {"grey", 0xff808080},    {"lime", 0xff00ff00},  {"maroon", 0xff800000},
51     {"navy", 0xff000080},    {"olive", 0xff808000}, {"orange", 0xffffa500},
52     {"purple", 0xff800080},  {"red", 0xffff0000},   {"silver", 0xffc0c0c0},
53     {"teal", 0xff008080},    {"white", 0xffffffff}, {"yellow", 0xffffff00},
54 };
55 
56 }  // namespace
57 
GetPropertyByName(WideStringView name)58 const CFX_CSSData::Property* CFX_CSSData::GetPropertyByName(
59     WideStringView name) {
60   if (name.IsEmpty())
61     return nullptr;
62 
63   uint32_t hash = FX_HashCode_GetLoweredW(name);
64   auto* result = std::lower_bound(
65       std::begin(kPropertyTable), std::end(kPropertyTable), hash,
66       [](const CFX_CSSData::Property& iter, const uint32_t& hash) {
67         return iter.dwHash < hash;
68       });
69 
70   if (result != std::end(kPropertyTable) && result->dwHash == hash) {
71     return result;
72   }
73   return nullptr;
74 }
75 
GetPropertyByEnum(CFX_CSSProperty property)76 const CFX_CSSData::Property* CFX_CSSData::GetPropertyByEnum(
77     CFX_CSSProperty property) {
78   auto index = static_cast<size_t>(property);
79   CHECK_LT(index, std::size(kPropertyTable));
80   // SAFETY: CHECK() on previous line ensures index is in bounds.
81   return UNSAFE_BUFFERS(&kPropertyTable[index]);
82 }
83 
GetPropertyValueByName(WideStringView wsName)84 const CFX_CSSData::PropertyValue* CFX_CSSData::GetPropertyValueByName(
85     WideStringView wsName) {
86   if (wsName.IsEmpty())
87     return nullptr;
88 
89   uint32_t hash = FX_HashCode_GetLoweredW(wsName);
90   auto* result = std::lower_bound(
91       std::begin(kPropertyValueTable), std::end(kPropertyValueTable), hash,
92       [](const PropertyValue& iter, const uint32_t& hash) {
93         return iter.dwHash < hash;
94       });
95 
96   if (result != std::end(kPropertyValueTable) && result->dwHash == hash) {
97     return result;
98   }
99   return nullptr;
100 }
101 
GetLengthUnitByName(WideStringView wsName)102 const CFX_CSSData::LengthUnit* CFX_CSSData::GetLengthUnitByName(
103     WideStringView wsName) {
104   if (wsName.IsEmpty() || wsName.GetLength() != 2) {
105     return nullptr;
106   }
107   auto* iter =
108       std::find_if(std::begin(kLengthUnitTable), std::end(kLengthUnitTable),
109                    [wsName](const CFX_CSSData::LengthUnit& unit) {
110                      return wsName.EqualsASCIINoCase(unit.value);
111                    });
112   return iter != std::end(kLengthUnitTable) ? iter : nullptr;
113 }
114 
GetColorByName(WideStringView wsName)115 const CFX_CSSData::Color* CFX_CSSData::GetColorByName(WideStringView wsName) {
116   if (wsName.IsEmpty()) {
117     return nullptr;
118   }
119   auto* iter = std::find_if(std::begin(kColorTable), std::end(kColorTable),
120                             [wsName](const CFX_CSSData::Color& color) {
121                               return wsName.EqualsASCIINoCase(color.name);
122                             });
123   return iter != std::end(kColorTable) ? iter : nullptr;
124 }
125