Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(1541)

Side by Side Diff: skia/ext/SkFontHost_fontconfig_direct.cpp

Issue 112074: Linux: Add support for chrooted renderers. (Closed)
Patch Set: Created 11 years, 6 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
OLDNEW
(Empty)
1 /* libs/graphics/ports/SkFontHost_fontconfig_direct.cpp
2 **
3 ** Copyright 2009, Google Inc.
4 **
5 ** Licensed under the Apache License, Version 2.0 (the "License");
6 ** you may not use this file except in compliance with the License.
7 ** You may obtain a copy of the License at
8 **
9 ** http://www.apache.org/licenses/LICENSE-2.0
10 **
11 ** Unless required by applicable law or agreed to in writing, software
12 ** distributed under the License is distributed on an "AS IS" BASIS,
13 ** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14 ** See the License for the specific language governing permissions and
15 ** limitations under the License.
16 */
17
18 #include "SkFontHost_fontconfig_direct.h"
19
20 #include <unistd.h>
21 #include <fcntl.h>
22
23 #include <fontconfig/fontconfig.h>
24
25 FontConfigDirect::FontConfigDirect()
26 : next_file_id_(0) {
27 FcInit();
28 }
29
30 bool FontConfigDirect::Match(std::string* result_family,
31 unsigned* result_fileid,
32 bool fileid_valid, unsigned fileid,
33 const std::string& family, int is_bold,
34 int is_italic) {
35 SkAutoMutexAcquire ac(mutex_);
36 FcPattern* pattern = FcPatternCreate();
37
38 FcValue fcvalue;
39 if (fileid_valid) {
40 const std::map<unsigned, std::string>::const_iterator
41 i = fileid_to_filename_.find(fileid);
42 if (i == fileid_to_filename_.end()) {
43 FcPatternDestroy(pattern);
44 return false;
45 }
46
47 fcvalue.type = FcTypeString;
48 fcvalue.u.s = (FcChar8*) i->second.c_str();
49 FcPatternAdd(pattern, FC_FILE, fcvalue, 0);
50 }
51 if (!family.empty()) {
52 fcvalue.type = FcTypeString;
53 fcvalue.u.s = (FcChar8*) family.c_str();
54 FcPatternAdd(pattern, FC_FAMILY, fcvalue, 0);
55 }
56 if (is_bold > 0) {
57 fcvalue.type = FcTypeInteger;
58 fcvalue.u.i = is_bold ? FC_WEIGHT_BOLD : FC_WEIGHT_NORMAL;
59 FcPatternAdd(pattern, FC_WEIGHT, fcvalue, 0);
60 }
61 if (is_italic > 0) {
62 fcvalue.type = FcTypeInteger;
63 fcvalue.u.i = is_bold ? FC_SLANT_ITALIC : FC_SLANT_ROMAN;
64 FcPatternAdd(pattern, FC_SLANT, fcvalue, 0);
65 }
66
67 FcConfigSubstitute(0, pattern, FcMatchPattern);
68 FcDefaultSubstitute(pattern);
69
70 // Font matching:
71 // CSS often specifies a fallback list of families:
72 // font-family: a, b, c, serif;
73 // However, fontconfig will always do its best to find *a* font when asked
74 // for something so we need a way to tell if the match which it has found is
75 // "good enough" for us. Otherwise, we can return NULL which gets piped up
76 // and lets WebKit know to try the next CSS family name. However, fontconfig
77 // configs allow substitutions (mapping "Arial -> Helvetica" etc) and we
78 // wish to support that.
79 //
80 // Thus, if a specific family is requested we set @family_requested. Then we
81 // record two strings: the family name after config processing and the
82 // family name after resolving. If the two are equal, it's a good match.
83 //
84 // So consider the case where a user has mapped Arial to Helvetica in their
85 // config.
86 // requested family: "Arial"
87 // post_config_family: "Helvetica"
88 // post_match_family: "Helvetica"
89 // -> good match
90 //
91 // and for a missing font:
92 // requested family: "Monaco"
93 // post_config_family: "Monaco"
94 // post_match_family: "Times New Roman"
95 // -> BAD match
96 FcChar8* post_config_family;
97 FcPatternGetString(pattern, FC_FAMILY, 0, &post_config_family);
98
99 FcResult result;
100 FcPattern* match = FcFontMatch(0, pattern, &result);
101 if (!match) {
102 FcPatternDestroy(pattern);
103 return false;
104 }
105
106 FcChar8* post_match_family;
107 FcPatternGetString(match, FC_FAMILY, 0, &post_match_family);
108 const bool family_names_match =
109 family.empty() ?
110 true :
111 strcasecmp((char *)post_config_family, (char *)post_match_family) == 0;
112
113 FcPatternDestroy(pattern);
114
115 if (!family_names_match) {
116 FcPatternDestroy(match);
117 return false;
118 }
119
120 FcChar8* c_filename;
121 if (FcPatternGetString(match, FC_FILE, 0, &c_filename) != FcResultMatch) {
122 FcPatternDestroy(match);
123 return NULL;
124 }
125 const std::string filename((char *) c_filename);
126
127 unsigned out_fileid;
128 if (fileid_valid) {
129 out_fileid = fileid;
130 } else {
131 const std::map<std::string, unsigned>::const_iterator
132 i = filename_to_fileid_.find(filename);
133 if (i == filename_to_fileid_.end()) {
134 out_fileid = next_file_id_++;
135 filename_to_fileid_[filename] = out_fileid;
136 fileid_to_filename_[out_fileid] = filename;
137 } else {
138 out_fileid = i->second;
139 }
140 }
141
142 if (*result_fileid)
143 *result_fileid = out_fileid;
144
145 FcChar8* c_family;
146 if (FcPatternGetString(match, FC_FAMILY, 0, &c_family)) {
147 FcPatternDestroy(match);
148 return NULL;
149 }
150
151 if (result_family)
152 *result_family = (char *) c_family;
153
154 return true;
155 }
156
157 int FontConfigDirect::Open(unsigned fileid) {
158 SkAutoMutexAcquire ac(mutex_);
159 const std::map<unsigned, std::string>::const_iterator
160 i = fileid_to_filename_.find(fileid);
161 if (i == fileid_to_filename_.end())
162 return -1;
163
164 return open(i->second.c_str(), O_RDONLY);
165 }
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698