OLD | NEW |
1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. | 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 | 2 // Use of this source code is governed by a BSD-style license that can be |
3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
4 | 4 |
5 #include "ui/gfx/render_text_mac.h" | 5 #include "ui/gfx/render_text_mac.h" |
6 | 6 |
7 #include <ApplicationServices/ApplicationServices.h> | 7 #include <ApplicationServices/ApplicationServices.h> |
8 | 8 |
9 #include <cmath> | 9 #include <cmath> |
10 #include <utility> | 10 #include <utility> |
(...skipping 137 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
148 return std::vector<Rect>(); | 148 return std::vector<Rect>(); |
149 } | 149 } |
150 | 150 |
151 bool RenderTextMac::IsCursorablePosition(size_t position) { | 151 bool RenderTextMac::IsCursorablePosition(size_t position) { |
152 // TODO(asvitkine): Implement this. http://crbug.com/131618 | 152 // TODO(asvitkine): Implement this. http://crbug.com/131618 |
153 return false; | 153 return false; |
154 } | 154 } |
155 | 155 |
156 void RenderTextMac::ResetLayout() { | 156 void RenderTextMac::ResetLayout() { |
157 line_.reset(); | 157 line_.reset(); |
| 158 attributes_.reset(); |
158 runs_.clear(); | 159 runs_.clear(); |
159 runs_valid_ = false; | 160 runs_valid_ = false; |
160 } | 161 } |
161 | 162 |
162 void RenderTextMac::EnsureLayout() { | 163 void RenderTextMac::EnsureLayout() { |
163 if (line_.get()) | 164 if (line_.get()) |
164 return; | 165 return; |
165 runs_.clear(); | 166 runs_.clear(); |
166 runs_valid_ = false; | 167 runs_valid_ = false; |
167 | 168 |
168 const Font& font = GetFont(); | 169 const Font& font = GetFont(); |
169 CTFontRef ct_font = | 170 CTFontRef ct_font = |
170 CreateCTFontWithPixelSize(font.GetFontName(), font.GetFontSize()); | 171 CreateCTFontWithPixelSize(font.GetFontName(), font.GetFontSize()); |
171 | 172 |
172 const void* keys[] = { kCTFontAttributeName }; | 173 const void* keys[] = { kCTFontAttributeName }; |
173 const void* values[] = { ct_font }; | 174 const void* values[] = { ct_font }; |
174 base::mac::ScopedCFTypeRef<CFDictionaryRef> attributes( | 175 base::mac::ScopedCFTypeRef<CFDictionaryRef> attributes( |
175 CFDictionaryCreate(NULL, keys, values, arraysize(keys), NULL, NULL)); | 176 CFDictionaryCreate(NULL, keys, values, arraysize(keys), NULL, |
| 177 &kCFTypeDictionaryValueCallBacks)); |
176 | 178 |
177 base::mac::ScopedCFTypeRef<CFStringRef> cf_text( | 179 base::mac::ScopedCFTypeRef<CFStringRef> cf_text( |
178 base::SysUTF16ToCFStringRef(text())); | 180 base::SysUTF16ToCFStringRef(text())); |
179 base::mac::ScopedCFTypeRef<CFAttributedStringRef> attr_text( | 181 base::mac::ScopedCFTypeRef<CFAttributedStringRef> attr_text( |
180 CFAttributedStringCreate(NULL, cf_text, attributes)); | 182 CFAttributedStringCreate(NULL, cf_text, attributes)); |
181 base::mac::ScopedCFTypeRef<CFMutableAttributedStringRef> attr_text_mutable( | 183 base::mac::ScopedCFTypeRef<CFMutableAttributedStringRef> attr_text_mutable( |
182 CFAttributedStringCreateMutableCopy(NULL, 0, attr_text)); | 184 CFAttributedStringCreateMutableCopy(NULL, 0, attr_text)); |
183 | 185 |
184 ApplyStyles(attr_text_mutable, ct_font); | 186 ApplyStyles(attr_text_mutable, ct_font); |
185 line_.reset(CTLineCreateWithAttributedString(attr_text_mutable)); | 187 line_.reset(CTLineCreateWithAttributedString(attr_text_mutable)); |
(...skipping 35 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
221 font_style(Font::NORMAL), | 223 font_style(Font::NORMAL), |
222 text_size(0), | 224 text_size(0), |
223 foreground(SK_ColorBLACK) { | 225 foreground(SK_ColorBLACK) { |
224 } | 226 } |
225 | 227 |
226 RenderTextMac::TextRun::~TextRun() { | 228 RenderTextMac::TextRun::~TextRun() { |
227 } | 229 } |
228 | 230 |
229 void RenderTextMac::ApplyStyles(CFMutableAttributedStringRef attr_string, | 231 void RenderTextMac::ApplyStyles(CFMutableAttributedStringRef attr_string, |
230 CTFontRef font) { | 232 CTFontRef font) { |
| 233 // Clear attributes and reserve space to hold the maximum number of entries, |
| 234 // which is at most three per style range per the code below. |
| 235 attributes_.reset(CFArrayCreateMutable(NULL, 3 * style_ranges().size(), |
| 236 &kCFTypeArrayCallBacks)); |
| 237 |
231 // https://developer.apple.com/library/mac/#documentation/Carbon/Reference/Cor
eText_StringAttributes_Ref/Reference/reference.html | 238 // https://developer.apple.com/library/mac/#documentation/Carbon/Reference/Cor
eText_StringAttributes_Ref/Reference/reference.html |
232 for (size_t i = 0; i < style_ranges().size(); ++i) { | 239 for (size_t i = 0; i < style_ranges().size(); ++i) { |
233 const StyleRange& style = style_ranges()[i]; | 240 const StyleRange& style = style_ranges()[i]; |
234 const CFRange range = CFRangeMake(style.range.start(), | 241 const CFRange range = CFRangeMake(style.range.start(), |
235 style.range.length()); | 242 style.range.length()); |
236 | 243 |
237 // Note: CFAttributedStringSetAttribute() does not appear to retain the | 244 // Note: CFAttributedStringSetAttribute() does not appear to retain the |
238 // values passed in, as can be verified via CFGetRetainCount(). | 245 // values passed in, as can be verified via CFGetRetainCount(). To ensure |
239 // | 246 // the attribute objects do not leak, they are saved to |attributes_|. |
240 // TODO(asvitkine): The attributed string appears to hold weak refs to these | |
241 // objects (it does not release them either), so we need to keep track of | |
242 // them ourselves and release them at an appropriate time. | |
243 | 247 |
244 CGColorRef foreground = gfx::SkColorToCGColorRef(style.foreground); | 248 base::mac::ScopedCFTypeRef<CGColorRef> foreground( |
| 249 gfx::CGColorCreateFromSkColor(style.foreground)); |
245 CFAttributedStringSetAttribute(attr_string, range, | 250 CFAttributedStringSetAttribute(attr_string, range, |
246 kCTForegroundColorAttributeName, | 251 kCTForegroundColorAttributeName, |
247 foreground); | 252 foreground); |
| 253 CFArrayAppendValue(attributes_, foreground); |
248 | 254 |
249 if (style.underline) { | 255 if (style.underline) { |
250 CTUnderlineStyle value = kCTUnderlineStyleSingle; | 256 CTUnderlineStyle value = kCTUnderlineStyleSingle; |
251 CFNumberRef underline = CFNumberCreate(NULL, kCFNumberSInt32Type, &value); | 257 base::mac::ScopedCFTypeRef<CFNumberRef> underline( |
| 258 CFNumberCreate(NULL, kCFNumberSInt32Type, &value)); |
252 CFAttributedStringSetAttribute(attr_string, range, | 259 CFAttributedStringSetAttribute(attr_string, range, |
253 kCTUnderlineStyleAttributeName, | 260 kCTUnderlineStyleAttributeName, |
254 underline); | 261 underline); |
| 262 CFArrayAppendValue(attributes_, underline); |
255 } | 263 } |
256 | 264 |
257 if (style.font_style & (Font::BOLD | Font::ITALIC)) { | 265 if (style.font_style & (Font::BOLD | Font::ITALIC)) { |
258 int traits = 0; | 266 int traits = 0; |
259 if (style.font_style & Font::BOLD) | 267 if (style.font_style & Font::BOLD) |
260 traits |= kCTFontBoldTrait; | 268 traits |= kCTFontBoldTrait; |
261 if (style.font_style & Font::ITALIC) | 269 if (style.font_style & Font::ITALIC) |
262 traits |= kCTFontItalicTrait; | 270 traits |= kCTFontItalicTrait; |
263 CTFontRef styled_font = | 271 base::mac::ScopedCFTypeRef<CTFontRef> styled_font( |
264 CTFontCreateCopyWithSymbolicTraits(font, 0.0, NULL, traits, traits); | 272 CTFontCreateCopyWithSymbolicTraits(font, 0.0, NULL, traits, traits)); |
265 // TODO(asvitkine): Handle |styled_font| == NULL case better. | 273 // TODO(asvitkine): Handle |styled_font| == NULL case better. |
266 if (styled_font) { | 274 if (styled_font) { |
267 CFAttributedStringSetAttribute(attr_string, range, kCTFontAttributeName, | 275 CFAttributedStringSetAttribute(attr_string, range, kCTFontAttributeName, |
268 styled_font); | 276 styled_font); |
| 277 CFArrayAppendValue(attributes_, styled_font); |
269 } | 278 } |
270 } | 279 } |
271 } | 280 } |
272 } | 281 } |
273 | 282 |
274 void RenderTextMac::ComputeRuns() { | 283 void RenderTextMac::ComputeRuns() { |
275 DCHECK(line_); | 284 DCHECK(line_); |
276 | 285 |
277 CFArrayRef ct_runs = CTLineGetGlyphRuns(line_); | 286 CFArrayRef ct_runs = CTLineGetGlyphRuns(line_); |
278 const CFIndex ct_runs_count = CFArrayGetCount(ct_runs); | 287 const CFIndex ct_runs_count = CFArrayGetCount(ct_runs); |
(...skipping 81 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
360 run_origin.offset(run_width, 0); | 369 run_origin.offset(run_width, 0); |
361 } | 370 } |
362 runs_valid_ = true; | 371 runs_valid_ = true; |
363 } | 372 } |
364 | 373 |
365 RenderText* RenderText::CreateInstance() { | 374 RenderText* RenderText::CreateInstance() { |
366 return new RenderTextMac; | 375 return new RenderTextMac; |
367 } | 376 } |
368 | 377 |
369 } // namespace gfx | 378 } // namespace gfx |
OLD | NEW |