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

Side by Side Diff: ppapi/proxy/ppb_font_proxy.cc

Issue 6981001: Make the Pepper proxy support in-process font rendering. (Closed) Base URL: svn://chrome-svn/chrome/trunk/src/
Patch Set: '' Created 9 years, 7 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 | Annotate | Revision Log
« no previous file with comments | « ppapi/proxy/ppb_font_proxy.h ('k') | ppapi/proxy/ppb_image_data_proxy.h » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 // Copyright (c) 2011 The Chromium Authors. All rights reserved. 1 // Copyright (c) 2011 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 "ppapi/proxy/ppb_font_proxy.h" 5 #include "ppapi/proxy/ppb_font_proxy.h"
6 6
7 #include "base/bind.h"
7 #include "ppapi/c/dev/ppb_font_dev.h" 8 #include "ppapi/c/dev/ppb_font_dev.h"
8 #include "ppapi/proxy/plugin_dispatcher.h" 9 #include "ppapi/proxy/plugin_dispatcher.h"
9 #include "ppapi/proxy/plugin_resource.h"
10 #include "ppapi/proxy/ppapi_messages.h" 10 #include "ppapi/proxy/ppapi_messages.h"
11 #include "ppapi/proxy/ppb_image_data_proxy.h"
12 #include "ppapi/shared_impl/resource_object_base.h"
13 #include "ppapi/thunk/ppb_image_data_api.h"
14 #include "ppapi/thunk/thunk.h"
15
16 using ppapi::thunk::PPB_ImageData_API;
17 using pp::shared_impl::WebKitForwarding;
11 18
12 namespace pp { 19 namespace pp {
13 namespace proxy { 20 namespace proxy {
14 21
15 class Font : public PluginResource {
16 public:
17 Font(const HostResource& resource);
18 virtual ~Font();
19
20 // PluginResource overrides.
21 virtual Font* AsFont() { return this; }
22
23 PP_FontDescription_Dev& desc() { return desc_; }
24 PP_FontDescription_Dev* desc_ptr() { return &desc_; }
25 PP_FontMetrics_Dev& metrics() { return metrics_; }
26
27 private:
28 PP_FontDescription_Dev desc_;
29 PP_FontMetrics_Dev metrics_;
30
31 DISALLOW_COPY_AND_ASSIGN(Font);
32 };
33
34 Font::Font(const HostResource& resource) : PluginResource(resource) {
35 memset(&desc_, 0, sizeof(PP_FontDescription_Dev));
36 desc_.face.type = PP_VARTYPE_UNDEFINED;
37 memset(&metrics_, 0, sizeof(PP_FontMetrics_Dev));
38 }
39
40 Font::~Font() {
41 PluginVarTracker::GetInstance()->Release(desc_.face);
42 }
43
44 namespace { 22 namespace {
45 23
46 PP_Resource Create(PP_Instance instance, 24 bool PPTextRunToTextRun(const PP_TextRun_Dev* run,
47 const PP_FontDescription_Dev* description) { 25 WebKitForwarding::Font::TextRun* output) {
48 PluginDispatcher* dispatcher = PluginDispatcher::GetForInstance(instance); 26 const std::string* str = PluginVarTracker::GetInstance()->GetExistingString(
49 if (!dispatcher) 27 run->text);
50 return 0; 28 if (!str)
29 return false;
51 30
52 SerializedFontDescription in_description; 31 output->text = *str;
53 in_description.SetFromPPFontDescription(dispatcher, *description, true); 32 output->rtl = PPBoolToBool(run->rtl);
54 33 output->override_direction = PPBoolToBool(run->override_direction);
55 HostResource result; 34 return true;
56 SerializedFontDescription out_description;
57 std::string out_metrics;
58 dispatcher->Send(new PpapiHostMsg_PPBFont_Create(
59 INTERFACE_ID_PPB_FONT,
60 instance, in_description, &result, &out_description, &out_metrics));
61
62 if (result.is_null())
63 return 0; // Failure creating font.
64
65 linked_ptr<Font> object(new Font(result));
66 out_description.SetToPPFontDescription(dispatcher, object->desc_ptr(), true);
67
68 // Convert the metrics, this is just serialized as a string of bytes.
69 if (out_metrics.size() != sizeof(PP_FontMetrics_Dev))
70 return 0;
71 memcpy(&object->metrics(), out_metrics.data(), sizeof(PP_FontMetrics_Dev));
72
73 return PluginResourceTracker::GetInstance()->AddResource(object);
74 } 35 }
75 36
76 PP_Bool IsFont(PP_Resource resource) {
77 Font* object = PluginResource::GetAs<Font>(resource);
78 return BoolToPPBool(!!object);
79 }
80
81 PP_Bool Describe(PP_Resource font_id,
82 PP_FontDescription_Dev* description,
83 PP_FontMetrics_Dev* metrics) {
84 Font* object = PluginResource::GetAs<Font>(font_id);
85 if (!object)
86 return PP_FALSE;
87
88 // Copy the description, the caller expects its face PP_Var to have a ref
89 // added to it on its behalf.
90 memcpy(description, &object->desc(), sizeof(PP_FontDescription_Dev));
91 PluginVarTracker::GetInstance()->AddRef(description->face);
92
93 memcpy(metrics, &object->metrics(), sizeof(PP_FontMetrics_Dev));
94 return PP_TRUE;
95 }
96
97 PP_Bool DrawTextAt(PP_Resource font_id,
98 PP_Resource image_data,
99 const PP_TextRun_Dev* text,
100 const PP_Point* position,
101 uint32_t color,
102 const PP_Rect* clip,
103 PP_Bool image_data_is_opaque) {
104 Font* font_object = PluginResource::GetAs<Font>(font_id);
105 if (!font_object)
106 return PP_FALSE;
107 PluginResource* image_object = PluginResourceTracker::GetInstance()->
108 GetResourceObject(image_data);
109 if (!image_object)
110 return PP_FALSE;
111 if (font_object->instance() != image_object->instance())
112 return PP_FALSE;
113
114 PPBFont_DrawTextAt_Params params;
115 params.font = font_object->host_resource();
116 params.image_data = image_object->host_resource();
117 params.text_is_rtl = text->rtl;
118 params.override_direction = text->override_direction;
119 params.position = *position;
120 params.color = color;
121 if (clip) {
122 params.clip = *clip;
123 params.clip_is_null = false;
124 } else {
125 params.clip = PP_MakeRectFromXYWH(0, 0, 0, 0);
126 params.clip_is_null = true;
127 }
128 params.image_data_is_opaque = image_data_is_opaque;
129
130 Dispatcher* dispatcher = PluginDispatcher::GetForInstance(
131 image_object->instance());
132 PP_Bool result = PP_FALSE;
133 if (dispatcher) {
134 dispatcher->Send(new PpapiHostMsg_PPBFont_DrawTextAt(
135 INTERFACE_ID_PPB_FONT,
136 SerializedVarSendInput(dispatcher, text->text),
137 params, &result));
138 }
139 return result;
140 }
141
142 int32_t MeasureText(PP_Resource font_id, const PP_TextRun_Dev* text) {
143 Font* object = PluginResource::GetAs<Font>(font_id);
144 if (!object)
145 return -1;
146
147 Dispatcher* dispatcher = PluginDispatcher::GetForInstance(object->instance());
148 int32_t result = 0;
149 if (dispatcher) {
150 dispatcher->Send(new PpapiHostMsg_PPBFont_MeasureText(
151 INTERFACE_ID_PPB_FONT, object->host_resource(),
152 SerializedVarSendInput(dispatcher, text->text),
153 text->rtl, text->override_direction, &result));
154 }
155 return result;
156 }
157
158 uint32_t CharacterOffsetForPixel(PP_Resource font_id,
159 const PP_TextRun_Dev* text,
160 int32_t pixel_position) {
161 Font* object = PluginResource::GetAs<Font>(font_id);
162 if (!object)
163 return -1;
164
165 Dispatcher* dispatcher = PluginDispatcher::GetForInstance(object->instance());
166 uint32_t result = 0;
167 if (dispatcher) {
168 dispatcher->Send(new PpapiHostMsg_PPBFont_CharacterOffsetForPixel(
169 INTERFACE_ID_PPB_FONT, object->host_resource(),
170 SerializedVarSendInput(dispatcher, text->text),
171 text->rtl, text->override_direction, pixel_position, &result));
172 }
173 return result;
174 }
175
176 int32_t PixelOffsetForCharacter(PP_Resource font_id,
177 const PP_TextRun_Dev* text,
178 uint32_t char_offset) {
179 Font* object = PluginResource::GetAs<Font>(font_id);
180 if (!object)
181 return -1;
182
183 Dispatcher* dispatcher = PluginDispatcher::GetForInstance(object->instance());
184 int32_t result = 0;
185 if (dispatcher) {
186 dispatcher->Send(new PpapiHostMsg_PPBFont_PixelOffsetForCharacter(
187 INTERFACE_ID_PPB_FONT, object->host_resource(),
188 SerializedVarSendInput(dispatcher, text->text),
189 text->rtl, text->override_direction, char_offset, &result));
190 }
191 return result;
192 }
193
194 const PPB_Font_Dev font_interface = {
195 &Create,
196 &IsFont,
197 &Describe,
198 &DrawTextAt,
199 &MeasureText,
200 &CharacterOffsetForPixel,
201 &PixelOffsetForCharacter
202 };
203
204 InterfaceProxy* CreateFontProxy(Dispatcher* dispatcher, 37 InterfaceProxy* CreateFontProxy(Dispatcher* dispatcher,
205 const void* target_interface) { 38 const void* target_interface) {
206 return new PPB_Font_Proxy(dispatcher, target_interface); 39 return new PPB_Font_Proxy(dispatcher, target_interface);
207 } 40 }
208 41
209 } // namespace 42 } // namespace
210 43
211 PPB_Font_Proxy::PPB_Font_Proxy(Dispatcher* dispatcher, 44 PPB_Font_Proxy::PPB_Font_Proxy(Dispatcher* dispatcher,
212 const void* target_interface) 45 const void* target_interface)
213 : InterfaceProxy(dispatcher, target_interface) { 46 : InterfaceProxy(dispatcher, target_interface) {
214 } 47 }
215 48
216 PPB_Font_Proxy::~PPB_Font_Proxy() { 49 PPB_Font_Proxy::~PPB_Font_Proxy() {
217 } 50 }
218 51
219 // static 52 // static
220 const InterfaceProxy::Info* PPB_Font_Proxy::GetInfo() { 53 const InterfaceProxy::Info* PPB_Font_Proxy::GetInfo() {
221 static const Info info = { 54 static const Info info = {
222 &font_interface, 55 ::ppapi::thunk::GetPPB_Font_Thunk(),
223 PPB_FONT_DEV_INTERFACE, 56 PPB_FONT_DEV_INTERFACE,
224 INTERFACE_ID_PPB_FONT, 57 INTERFACE_ID_PPB_FONT,
225 false, 58 false,
226 &CreateFontProxy, 59 &CreateFontProxy,
227 }; 60 };
228 return &info; 61 return &info;
229 } 62 }
230 63
231 bool PPB_Font_Proxy::OnMessageReceived(const IPC::Message& msg) { 64 bool PPB_Font_Proxy::OnMessageReceived(const IPC::Message& msg) {
232 bool handled = true; 65 // There aren't any font messages.
233 IPC_BEGIN_MESSAGE_MAP(PPB_Font_Proxy, msg) 66 NOTREACHED();
234 IPC_MESSAGE_HANDLER(PpapiHostMsg_PPBFont_Create, 67 return false;
235 OnMsgCreate)
236 IPC_MESSAGE_HANDLER(PpapiHostMsg_PPBFont_DrawTextAt,
237 OnMsgDrawTextAt)
238 IPC_MESSAGE_HANDLER(PpapiHostMsg_PPBFont_MeasureText,
239 OnMsgMeasureText)
240 IPC_MESSAGE_HANDLER(PpapiHostMsg_PPBFont_CharacterOffsetForPixel,
241 OnMsgCharacterOffsetForPixel)
242 IPC_MESSAGE_HANDLER(PpapiHostMsg_PPBFont_PixelOffsetForCharacter,
243 OnMsgPixelOffsetForCharacter)
244 IPC_MESSAGE_UNHANDLED(handled = false)
245 IPC_END_MESSAGE_MAP()
246 return handled;
247 } 68 }
248 69
249 void PPB_Font_Proxy::OnMsgCreate( 70 Font::Font(const HostResource& resource,
250 PP_Instance instance, 71 const PP_FontDescription_Dev& desc)
251 const SerializedFontDescription& in_description, 72 : PluginResource(resource),
252 HostResource* result, 73 webkit_event_(false, false) {
253 SerializedFontDescription* out_description, 74 const std::string* face = PluginVarTracker::GetInstance()->GetExistingString(
254 std::string* out_metrics) { 75 desc.face);
255 // Convert the face name in the input description.
256 PP_FontDescription_Dev in_pp_desc;
257 in_description.SetToPPFontDescription(dispatcher(), &in_pp_desc, false);
258 76
259 // Make sure the output is always defined so we can still serialize it back 77 WebKitForwarding* forwarding = GetDispatcher()->GetWebKitForwarding();
260 // to the plugin below.
261 PP_FontDescription_Dev out_pp_desc;
262 memset(&out_pp_desc, 0, sizeof(PP_FontDescription_Dev));
263 out_pp_desc.face = PP_MakeUndefined();
264 78
265 result->SetHostResource(instance, 79 WebKitForwarding::Font* result = NULL;
266 ppb_font_target()->Create(instance, &in_pp_desc)); 80 RunOnWebKitThread(base::Bind(&WebKitForwarding::CreateFontForwarding,
267 if (!result->is_null()) { 81 base::Unretained(forwarding),
268 // Get the metrics and resulting description to return to the browser. 82 &webkit_event_, desc,
269 PP_FontMetrics_Dev metrics; 83 face ? *face : std::string(), &result));
270 if (ppb_font_target()->Describe(result->host_resource(), &out_pp_desc, 84 font_forwarding_.reset(result);
271 &metrics)) { 85 }
272 out_metrics->assign(reinterpret_cast<const char*>(&metrics), 86
273 sizeof(PP_FontMetrics_Dev)); 87 Font::~Font() {
274 } 88 }
89
90 ppapi::thunk::PPB_Font_API* Font::AsFont_API() {
91 return this;
92 }
93
94 Font* Font::AsFont() {
95 return this;
96 }
97
98 PP_Bool Font::Describe(PP_FontDescription_Dev* description,
99 PP_FontMetrics_Dev* metrics) {
100 std::string face;
101 PP_Bool result = PP_FALSE;
102 RunOnWebKitThread(base::Bind(&WebKitForwarding::Font::Describe,
103 base::Unretained(font_forwarding_.get()),
104 &webkit_event_, description, &face, metrics,
105 &result));
106
107 if (result == PP_TRUE) {
108 description->face.type = PP_VARTYPE_STRING;
109 description->face.value.as_id =
110 PluginVarTracker::GetInstance()->MakeString(face);
111 } else {
112 description->face.type = PP_VARTYPE_UNDEFINED;
113 }
114 return result;
115 }
116
117 PP_Bool Font::DrawTextAt(PP_Resource pp_image_data,
118 const PP_TextRun_Dev* text,
119 const PP_Point* position,
120 uint32_t color,
121 const PP_Rect* clip,
122 PP_Bool image_data_is_opaque) {
123 // Convert to an ImageData object.
124 ppapi::shared_impl::ResourceObjectBase* image_base =
125 ppapi::shared_impl::TrackerBase::Get()->GetResourceAPI(pp_image_data);
126 if (!image_base)
127 return PP_FALSE;
128 PPB_ImageData_API* image_api = image_base->GetAs<PPB_ImageData_API>();
129 if (!image_api)
130 return PP_FALSE;
131 ImageData* image_data = static_cast<ImageData*>(image_api);
132
133 skia::PlatformCanvas* canvas = image_data->mapped_canvas();
134 bool needs_unmapping = false;
135 if (!canvas) {
136 needs_unmapping = true;
137 image_data->Map();
138 canvas = image_data->mapped_canvas();
139 if (!canvas)
140 return PP_FALSE; // Failure mapping.
275 } 141 }
276 142
277 // This must always get called or it will assert when trying to serialize 143 WebKitForwarding::Font::TextRun run;
278 // the un-filled-in SerializedFontDescription as the return value. 144 if (!PPTextRunToTextRun(text, &run)) {
279 out_description->SetFromPPFontDescription(dispatcher(), out_pp_desc, false); 145 if (needs_unmapping)
146 image_data->Unmap();
147 return PP_FALSE;
148 }
149 RunOnWebKitThread(base::Bind(
150 &WebKitForwarding::Font::DrawTextAt,
151 base::Unretained(font_forwarding_.get()),
152 &webkit_event_,
153 WebKitForwarding::Font::DrawTextParams(canvas, run, position, color,
154 clip, image_data_is_opaque)));
155
156 if (needs_unmapping)
157 image_data->Unmap();
158 return PP_TRUE;
280 } 159 }
281 160
282 void PPB_Font_Proxy::OnMsgDrawTextAt(SerializedVarReceiveInput text, 161 int32_t Font::MeasureText(const PP_TextRun_Dev* text) {
283 const PPBFont_DrawTextAt_Params& params, 162 WebKitForwarding::Font::TextRun run;
284 PP_Bool* result) { 163 if (!PPTextRunToTextRun(text, &run))
285 PP_TextRun_Dev run; 164 return -1;
286 run.text = text.Get(dispatcher()); 165 int32_t result = -1;
287 run.rtl = params.text_is_rtl; 166 RunOnWebKitThread(base::Bind(&WebKitForwarding::Font::MeasureText,
288 run.override_direction = params.override_direction; 167 base::Unretained(font_forwarding_.get()),
289 168 &webkit_event_, run, &result));
290 *result = ppb_font_target()->DrawTextAt(params.font.host_resource(), 169 return result;
291 params.image_data.host_resource(), &run, &params.position, params.color,
292 params.clip_is_null ? NULL : &params.clip, params.image_data_is_opaque);
293 } 170 }
294 171
295 void PPB_Font_Proxy::OnMsgMeasureText(HostResource font, 172 uint32_t Font::CharacterOffsetForPixel(const PP_TextRun_Dev* text,
296 SerializedVarReceiveInput text, 173 int32_t pixel_position) {
297 PP_Bool text_is_rtl, 174 WebKitForwarding::Font::TextRun run;
298 PP_Bool override_direction, 175 if (!PPTextRunToTextRun(text, &run))
299 int32_t* result) { 176 return -1;
300 PP_TextRun_Dev run; 177 uint32_t result = -1;
301 run.text = text.Get(dispatcher()); 178 RunOnWebKitThread(base::Bind(&WebKitForwarding::Font::CharacterOffsetForPixel,
302 run.rtl = text_is_rtl; 179 base::Unretained(font_forwarding_.get()),
303 run.override_direction = override_direction; 180 &webkit_event_, run, pixel_position, &result));
304 181 return result;
305 *result = ppb_font_target()->MeasureText(font.host_resource(), &run);
306 } 182 }
307 183
308 void PPB_Font_Proxy::OnMsgCharacterOffsetForPixel( 184 int32_t Font::PixelOffsetForCharacter(const PP_TextRun_Dev* text,
309 HostResource font, 185 uint32_t char_offset) {
310 SerializedVarReceiveInput text, 186 WebKitForwarding::Font::TextRun run;
311 PP_Bool text_is_rtl, 187 if (!PPTextRunToTextRun(text, &run))
312 PP_Bool override_direction, 188 return -1;
313 int32_t pixel_pos, 189 int32_t result = -1;
314 uint32_t* result) { 190 RunOnWebKitThread(base::Bind(&WebKitForwarding::Font::PixelOffsetForCharacter,
315 PP_TextRun_Dev run; 191 base::Unretained(font_forwarding_.get()),
316 run.text = text.Get(dispatcher()); 192 &webkit_event_, run, char_offset, &result));
317 run.rtl = text_is_rtl; 193 return result;
318 run.override_direction = override_direction;
319
320 *result = ppb_font_target()->CharacterOffsetForPixel(font.host_resource(),
321 &run, pixel_pos);
322 } 194 }
323 195
324 void PPB_Font_Proxy::OnMsgPixelOffsetForCharacter( 196 void Font::RunOnWebKitThread(const base::Closure& task) {
325 HostResource font, 197 GetDispatcher()->PostToWebKitThread(FROM_HERE, task);
326 SerializedVarReceiveInput text, 198 webkit_event_.Wait();
327 PP_Bool text_is_rtl,
328 PP_Bool override_direction,
329 uint32_t char_offset,
330 int32_t* result) {
331 PP_TextRun_Dev run;
332 run.text = text.Get(dispatcher());
333 run.rtl = text_is_rtl;
334 run.override_direction = override_direction;
335
336 *result = ppb_font_target()->PixelOffsetForCharacter(font.host_resource(),
337 &run, char_offset);
338 } 199 }
339 200
340 } // namespace proxy 201 } // namespace proxy
341 } // namespace pp 202 } // namespace pp
OLDNEW
« no previous file with comments | « ppapi/proxy/ppb_font_proxy.h ('k') | ppapi/proxy/ppb_image_data_proxy.h » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698