| // Copyright 2014 The Chromium Authors. All rights reserved. |
| // Use of this source code is governed by a BSD-style license that can be |
| // found in the LICENSE file. |
| |
| #include "components/nacl/renderer/progress_event.h" |
| |
| #include "base/bind.h" |
| #include "base/location.h" |
| #include "base/logging.h" |
| #include "base/message_loop/message_loop_proxy.h" |
| #include "components/nacl/renderer/ppb_nacl_private.h" |
| #include "content/public/renderer/pepper_plugin_instance.h" |
| #include "ppapi/shared_impl/ppapi_globals.h" |
| #include "third_party/WebKit/public/platform/WebString.h" |
| #include "third_party/WebKit/public/web/WebDOMResourceProgressEvent.h" |
| #include "third_party/WebKit/public/web/WebDocument.h" |
| #include "third_party/WebKit/public/web/WebElement.h" |
| #include "third_party/WebKit/public/web/WebLocalFrame.h" |
| #include "third_party/WebKit/public/web/WebPluginContainer.h" |
| #include "v8/include/v8.h" |
| |
| namespace nacl { |
| |
| namespace { |
| blink::WebString EventTypeToString(PP_NaClEventType event_type) { |
| switch (event_type) { |
| case PP_NACL_EVENT_LOADSTART: |
| return blink::WebString::fromUTF8("loadstart"); |
| case PP_NACL_EVENT_PROGRESS: |
| return blink::WebString::fromUTF8("progress"); |
| case PP_NACL_EVENT_ERROR: |
| return blink::WebString::fromUTF8("error"); |
| case PP_NACL_EVENT_ABORT: |
| return blink::WebString::fromUTF8("abort"); |
| case PP_NACL_EVENT_LOAD: |
| return blink::WebString::fromUTF8("load"); |
| case PP_NACL_EVENT_LOADEND: |
| return blink::WebString::fromUTF8("loadend"); |
| case PP_NACL_EVENT_CRASH: |
| return blink::WebString::fromUTF8("crash"); |
| } |
| NOTIMPLEMENTED(); |
| return blink::WebString(); |
| } |
| |
| void DispatchProgressEventOnMainThread(PP_Instance instance, |
| const ProgressEvent &event) { |
| content::PepperPluginInstance* plugin_instance = |
| content::PepperPluginInstance::Get(instance); |
| if (!plugin_instance) |
| return; |
| |
| blink::WebPluginContainer* container = plugin_instance->GetContainer(); |
| // It's possible that container() is NULL if the plugin has been removed from |
| // the DOM (but the PluginInstance is not destroyed yet). |
| if (!container) |
| return; |
| blink::WebLocalFrame* frame = container->element().document().frame(); |
| if (!frame) |
| return; |
| v8::HandleScope handle_scope(plugin_instance->GetIsolate()); |
| v8::Local<v8::Context> context( |
| plugin_instance->GetIsolate()->GetCurrentContext()); |
| if (context.IsEmpty()) { |
| // If there's no JavaScript on the stack, we have to make a new Context. |
| context = v8::Context::New(plugin_instance->GetIsolate()); |
| } |
| v8::Context::Scope context_scope(context); |
| |
| if (!event.resource_url.empty()) { |
| blink::WebString url_string = blink::WebString::fromUTF8( |
| event.resource_url.data(), event.resource_url.size()); |
| blink::WebDOMResourceProgressEvent blink_event( |
| EventTypeToString(event.event_type), |
| event.length_is_computable, |
| event.loaded_bytes, |
| event.total_bytes, |
| url_string); |
| container->element().dispatchEvent(blink_event); |
| } else { |
| blink::WebDOMProgressEvent blink_event(EventTypeToString(event.event_type), |
| event.length_is_computable, |
| event.loaded_bytes, |
| event.total_bytes); |
| container->element().dispatchEvent(blink_event); |
| } |
| } |
| |
| } // namespace |
| |
| void DispatchProgressEvent(PP_Instance instance, const ProgressEvent &event) { |
| ppapi::PpapiGlobals::Get()->GetMainThreadMessageLoop()->PostTask( |
| FROM_HERE, |
| base::Bind(&DispatchProgressEventOnMainThread, instance, event)); |
| } |
| |
| } // namespace nacl |