Index: extensions/renderer/guest_view/guest_view_internal_custom_bindings.cc |
diff --git a/extensions/renderer/guest_view/guest_view_internal_custom_bindings.cc b/extensions/renderer/guest_view/guest_view_internal_custom_bindings.cc |
index 49dae796c2e27425c25b40e0a971df453ad28f85..6d97b3be88dc551a10fdea67908e1d397aa6af46 100644 |
--- a/extensions/renderer/guest_view/guest_view_internal_custom_bindings.cc |
+++ b/extensions/renderer/guest_view/guest_view_internal_custom_bindings.cc |
@@ -11,9 +11,17 @@ |
#include "content/public/renderer/render_view.h" |
#include "extensions/common/extension.h" |
#include "extensions/common/extension_messages.h" |
+#include "extensions/common/guest_view/guest_view_messages.h" |
#include "extensions/renderer/guest_view/extensions_guest_view_container.h" |
#include "extensions/renderer/script_context.h" |
#include "v8/include/v8.h" |
+#include "third_party/WebKit/public/web/WebBindings.h" |
+#include "third_party/WebKit/public/web/WebElement.h" |
+#include "third_party/WebKit/public/web/WebFrame.h" |
+#include "third_party/WebKit/public/web/WebLocalFrame.h" |
+#include "third_party/WebKit/public/web/WebRemoteFrame.h" |
+#include "third_party/WebKit/public/web/WebNode.h" |
+#include "content/public/renderer/render_frame.h" |
using content::V8ValueConverter; |
@@ -37,6 +45,10 @@ GuestViewInternalCustomBindings::GuestViewInternalCustomBindings( |
base::Bind( |
&GuestViewInternalCustomBindings::RegisterElementResizeCallback, |
base::Unretained(this))); |
+ |
+ RouteFunction("AttachIframeGuest", |
+ base::Bind(&GuestViewInternalCustomBindings::AttachIframeGuest, |
+ base::Unretained(this))); |
} |
void GuestViewInternalCustomBindings::AttachGuest( |
@@ -163,4 +175,80 @@ void GuestViewInternalCustomBindings::RegisterElementResizeCallback( |
args.GetReturnValue().Set(v8::Boolean::New(context()->isolate(), true)); |
} |
+bool GetWebNodeFromValue(v8::Handle<v8::Value> value, blink::WebNode* node) { |
Fady Samuel
2015/03/04 20:44:47
This can't use NPAPI. That code is deprecated. Is
|
+ NPVariant result; |
+ blink::WebBindings::toNPVariant(value, NULL, &result); |
+ if (result.type != NPVariantType_Object) { |
+ return false; |
+ } |
+ NPObject* obj = result.value.objectValue; |
+ return blink::WebBindings::getNode(obj, node); |
+} |
+ |
+void GuestViewInternalCustomBindings::AttachIframeGuest( |
+ const v8::FunctionCallbackInfo<v8::Value>& args) { |
+ // Allow for an optional callback parameter. |
+ CHECK(args.Length() >= 4 && args.Length() <= 5); |
+ // Element Instance ID. |
+ CHECK(args[0]->IsInt32()); |
+ // Guest Instance ID. |
+ CHECK(args[1]->IsInt32()); |
+ // Node. |
+ CHECK(args[2]->IsObject()); |
+ // Optional Callback Function. |
+ CHECK(args.Length() < 4 || args[3]->IsFunction()); |
+ LOG(INFO) << "has_callback: " << (args.Length() >= 4); |
+ |
+ int element_instance_id = args[0]->Int32Value(); |
+ int guest_instance_id = args[1]->Int32Value(); |
+ LOG(INFO) << "guest_instance_id: " << guest_instance_id << |
+ "element_instance_id: " << element_instance_id; |
+ |
+ blink::WebNode node; |
+ bool got_webnode = GetWebNodeFromValue(args[2], &node); |
+ CHECK(got_webnode); |
+ blink::WebElement element = node.to<blink::WebElement>(); |
+ blink::WebLocalFrame* frame = |
+ blink::WebLocalFrame::fromFrameOwnerElement(element); |
+ DCHECK(frame); |
+ content::RenderFrame* render_frame = |
+ content::RenderFrame::FromWebFrame(frame); |
+ |
+ // Parent must exist. |
+ blink::WebFrame* parent_frame = frame->parent(); |
+ DCHECK(parent_frame); |
+ DCHECK(parent_frame->isWebLocalFrame()); |
+ |
+ render_frame->Send( |
+ new GuestViewHostMsg_AttachLocalFrameToGuest( |
+ render_frame->GetRoutingID(), |
+ element_instance_id, |
+ guest_instance_id)); |
+ content::RenderFrame* embedder_parent_frame = |
+ content::RenderFrame::FromWebFrame(parent_frame); |
+ |
+ // Create a GuestViewContainer if it does not exist. |
+ ExtensionsGuestViewContainer* guest_view_container = |
+ ExtensionsGuestViewContainer::FromID(element_instance_id); |
+ // This is the first time we hear about the |element_instance_id|. |
+ DCHECK(!guest_view_container); |
+ // TODO(lazyboy): Leaked, make this render_frame observer and destruct. |
+ guest_view_container = new extensions::ExtensionsGuestViewContainer( |
Fady Samuel
2015/03/04 20:44:47
The container should self-destruct.
|
+ embedder_parent_frame); |
+ guest_view_container->SetElementInstanceID(element_instance_id); |
+ |
+ linked_ptr<ExtensionsGuestViewContainer::Request> request( |
+ new ExtensionsGuestViewContainer::AttachIframeRequest( |
+ guest_view_container, |
+ guest_instance_id, |
+ args.Length() == 4 ? args[3].As<v8::Function>() : |
+ v8::Handle<v8::Function>(), |
+ args.GetIsolate())); |
+ guest_view_container->IssueRequest(request); |
+ |
+ args.GetReturnValue().Set(v8::Boolean::New(context()->isolate(), true)); |
+ |
+ LOG(INFO) << "AttachLocalFrameToGuest complete"; |
+} |
+ |
} // namespace extensions |