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 3// found in the LICENSE file. 4 5#ifndef CONTENT_BROWSER_WEB_CONTENTS_WEB_DRAG_DEST_GTK_H_ 6#define CONTENT_BROWSER_WEB_CONTENTS_WEB_DRAG_DEST_GTK_H_ 7 8#include <gtk/gtk.h> 9 10#include "base/gtest_prod_util.h" 11#include "base/memory/scoped_ptr.h" 12#include "base/memory/weak_ptr.h" 13#include "content/common/content_export.h" 14#include "content/public/common/drop_data.h" 15#include "third_party/WebKit/public/web/WebDragOperation.h" 16#include "ui/base/gtk/gtk_signal.h" 17 18namespace content { 19 20class RenderViewHostImpl; 21class WebContents; 22class WebDragDestDelegate; 23 24// A helper class that handles DnD for drops in the renderer. In GTK parlance, 25// this handles destination-side DnD, but not source-side DnD. 26class CONTENT_EXPORT WebDragDestGtk { 27 public: 28 WebDragDestGtk(WebContents* web_contents, GtkWidget* widget); 29 ~WebDragDestGtk(); 30 31 DropData* current_drop_data() const { return drop_data_.get(); } 32 33 // This is called when the renderer responds to a drag motion event. We must 34 // update the system drag cursor. 35 void UpdateDragStatus(blink::WebDragOperation operation); 36 37 // Informs the renderer when a system drag has left the render view. 38 // See OnDragLeave(). 39 void DragLeave(); 40 41 WebDragDestDelegate* delegate() const { return delegate_; } 42 void set_delegate(WebDragDestDelegate* delegate) { delegate_ = delegate; } 43 44 GtkWidget* widget() const { return widget_; } 45 46 private: 47 RenderViewHostImpl* GetRenderViewHost() const; 48 49 // Called when a system drag crosses over the render view. As there is no drag 50 // enter event, we treat it as an enter event (and not a regular motion event) 51 // when |context_| is NULL. 52 CHROMEGTK_CALLBACK_4(WebDragDestGtk, gboolean, OnDragMotion, GdkDragContext*, 53 gint, gint, guint); 54 55 // We make a series of requests for the drag data when the drag first enters 56 // the render view. This is the callback that is used to give us the data 57 // for each individual target. When |data_requests_| reaches 0, we know we 58 // have attained all the data, and we can finally tell the renderer about the 59 // drag. 60 CHROMEGTK_CALLBACK_6(WebDragDestGtk, void, OnDragDataReceived, 61 GdkDragContext*, gint, gint, GtkSelectionData*, 62 guint, guint); 63 64 // The drag has left our widget; forward this information to the renderer. 65 CHROMEGTK_CALLBACK_2(WebDragDestGtk, void, OnDragLeave, GdkDragContext*, 66 guint); 67 68 // Called by GTK when the user releases the mouse, executing a drop. 69 CHROMEGTK_CALLBACK_4(WebDragDestGtk, gboolean, OnDragDrop, GdkDragContext*, 70 gint, gint, guint); 71 72 WebContents* web_contents_; 73 74 // The render view. 75 GtkWidget* widget_; 76 77 // The current drag context for system drags over our render view, or NULL if 78 // there is no system drag or the system drag is not over our render view. 79 GdkDragContext* context_; 80 81 // The data for the current drag, or NULL if |context_| is NULL. 82 scoped_ptr<DropData> drop_data_; 83 84 // The number of outstanding drag data requests we have sent to the drag 85 // source. 86 int data_requests_; 87 88 // The last time we sent a message to the renderer related to a drag motion. 89 gint drag_over_time_; 90 91 // Whether the cursor is over a drop target, according to the last message we 92 // got from the renderer. 93 bool is_drop_target_; 94 95 // Stores Handler IDs for the gtk signal handlers. We have to cancel the 96 // signal handlers when this WebDragDestGtk is deleted so that if, later on, 97 // we re-create the drag dest with the same widget, we don't get callbacks to 98 // deleted functions. 99 scoped_ptr<int[]> handlers_; 100 101 // A delegate that can receive drag information about drag events. 102 WebDragDestDelegate* delegate_; 103 104 // True if the drag has been canceled. 105 bool canceled_; 106 107 base::WeakPtrFactory<WebDragDestGtk> method_factory_; 108 109 DISALLOW_COPY_AND_ASSIGN(WebDragDestGtk); 110}; 111 112} // namespace content 113 114#endif // CONTENT_BROWSER_WEB_CONTENTS_WEB_DRAG_DEST_GTK_H_ 115