os_exchange_data_provider_win.h revision a93a17c8d99d686bd4a1511e5504e5e6cc9fcadf
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 UI_BASE_DRAGDROP_OS_EXCHANGE_DATA_PROVIDER_WIN_H_ 6#define UI_BASE_DRAGDROP_OS_EXCHANGE_DATA_PROVIDER_WIN_H_ 7 8#include <objidl.h> 9#include <shlobj.h> 10#include <string> 11#include <vector> 12 13// Win8 SDK compatibility, see http://goo.gl/fufvl for more information. 14// "Note: This interface has been renamed IDataObjectAsyncCapability." 15// If we're building on pre-8 we define it to its old name. It's documented as 16// being binary compatible. 17#ifndef __IDataObjectAsyncCapability_FWD_DEFINED__ 18#define IDataObjectAsyncCapability IAsyncOperation 19#endif 20 21#include "base/memory/scoped_vector.h" 22#include "base/win/scoped_comptr.h" 23#include "ui/base/dragdrop/os_exchange_data.h" 24#include "ui/base/ui_export.h" 25#include "ui/gfx/image/image_skia.h" 26#include "ui/gfx/vector2d.h" 27 28namespace ui { 29 30class DataObjectImpl : public DownloadFileObserver, 31 public IDataObject, 32 public IDataObjectAsyncCapability { 33 public: 34 class Observer { 35 public: 36 virtual void OnWaitForData() = 0; 37 virtual void OnDataObjectDisposed() = 0; 38 protected: 39 virtual ~Observer() { } 40 }; 41 42 DataObjectImpl(); 43 44 // Accessors. 45 void set_observer(Observer* observer) { observer_ = observer; } 46 void set_in_drag_loop(bool in_drag_loop) { in_drag_loop_ = in_drag_loop; } 47 48 // Number of known formats. 49 size_t size() const { return contents_.size(); } 50 51 // DownloadFileObserver implementation: 52 virtual void OnDownloadCompleted(const base::FilePath& file_path); 53 virtual void OnDownloadAborted(); 54 55 // IDataObject implementation: 56 HRESULT __stdcall GetData(FORMATETC* format_etc, STGMEDIUM* medium); 57 HRESULT __stdcall GetDataHere(FORMATETC* format_etc, STGMEDIUM* medium); 58 HRESULT __stdcall QueryGetData(FORMATETC* format_etc); 59 HRESULT __stdcall GetCanonicalFormatEtc( 60 FORMATETC* format_etc, FORMATETC* result); 61 HRESULT __stdcall SetData( 62 FORMATETC* format_etc, STGMEDIUM* medium, BOOL should_release); 63 HRESULT __stdcall EnumFormatEtc( 64 DWORD direction, IEnumFORMATETC** enumerator); 65 HRESULT __stdcall DAdvise(FORMATETC* format_etc, DWORD advf, 66 IAdviseSink* sink, DWORD* connection); 67 HRESULT __stdcall DUnadvise(DWORD connection); 68 HRESULT __stdcall EnumDAdvise(IEnumSTATDATA** enumerator); 69 70 // IDataObjectAsyncCapability implementation: 71 HRESULT __stdcall EndOperation( 72 HRESULT result, IBindCtx* reserved, DWORD effects); 73 HRESULT __stdcall GetAsyncMode(BOOL* is_op_async); 74 HRESULT __stdcall InOperation(BOOL* in_async_op); 75 HRESULT __stdcall SetAsyncMode(BOOL do_op_async); 76 HRESULT __stdcall StartOperation(IBindCtx* reserved); 77 78 // IUnknown implementation: 79 HRESULT __stdcall QueryInterface(const IID& iid, void** object); 80 ULONG __stdcall AddRef(); 81 ULONG __stdcall Release(); 82 83 private: 84 // FormatEtcEnumerator only likes us for our StoredDataMap typedef. 85 friend class FormatEtcEnumerator; 86 friend class OSExchangeDataProviderWin; 87 88 virtual ~DataObjectImpl(); 89 90 void StopDownloads(); 91 92 // Removes from contents_ the first data that matches |format|. 93 void RemoveData(const FORMATETC& format); 94 95 // Our internal representation of stored data & type info. 96 struct StoredDataInfo { 97 FORMATETC format_etc; 98 STGMEDIUM* medium; 99 bool owns_medium; 100 scoped_refptr<DownloadFileProvider> downloader; 101 102 StoredDataInfo(CLIPFORMAT cf, STGMEDIUM* medium) 103 : medium(medium), 104 owns_medium(true) { 105 format_etc.cfFormat = cf; 106 format_etc.dwAspect = DVASPECT_CONTENT; 107 format_etc.lindex = -1; 108 format_etc.ptd = NULL; 109 format_etc.tymed = medium ? medium->tymed : TYMED_HGLOBAL; 110 } 111 112 StoredDataInfo(FORMATETC* format_etc, STGMEDIUM* medium) 113 : format_etc(*format_etc), 114 medium(medium), 115 owns_medium(true) { 116 } 117 118 ~StoredDataInfo() { 119 if (owns_medium) { 120 ReleaseStgMedium(medium); 121 delete medium; 122 } 123 if (downloader.get()) 124 downloader->Stop(); 125 } 126 }; 127 128 typedef ScopedVector<StoredDataInfo> StoredData; 129 StoredData contents_; 130 131 base::win::ScopedComPtr<IDataObject> source_object_; 132 133 bool is_aborting_; 134 bool in_drag_loop_; 135 bool in_async_mode_; 136 bool async_operation_started_; 137 Observer* observer_; 138}; 139 140class UI_EXPORT OSExchangeDataProviderWin : public OSExchangeData::Provider { 141 public: 142 // Returns true if source has plain text that is a valid url. 143 static bool HasPlainTextURL(IDataObject* source); 144 145 // Returns true if source has plain text that is a valid URL and sets url to 146 // that url. 147 static bool GetPlainTextURL(IDataObject* source, GURL* url); 148 149 static DataObjectImpl* GetDataObjectImpl(const OSExchangeData& data); 150 static IDataObject* GetIDataObject(const OSExchangeData& data); 151 static IDataObjectAsyncCapability* GetIAsyncOperation( 152 const OSExchangeData& data); 153 154 explicit OSExchangeDataProviderWin(IDataObject* source); 155 OSExchangeDataProviderWin(); 156 157 virtual ~OSExchangeDataProviderWin(); 158 159 IDataObject* data_object() const { return data_.get(); } 160 IDataObjectAsyncCapability* async_operation() const { return data_.get(); } 161 162 // OSExchangeData::Provider methods. 163 virtual void SetString(const string16& data); 164 virtual void SetURL(const GURL& url, const string16& title); 165 virtual void SetFilename(const base::FilePath& path); 166 virtual void SetFilenames( 167 const std::vector<OSExchangeData::FileInfo>& filenames); 168 virtual void SetPickledData(OSExchangeData::CustomFormat format, 169 const Pickle& data); 170 virtual void SetFileContents(const base::FilePath& filename, 171 const std::string& file_contents); 172 virtual void SetHtml(const string16& html, const GURL& base_url); 173 174 virtual bool GetString(string16* data) const; 175 virtual bool GetURLAndTitle(GURL* url, string16* title) const; 176 virtual bool GetFilename(base::FilePath* path) const; 177 virtual bool GetFilenames( 178 std::vector<OSExchangeData::FileInfo>* filenames) const; 179 virtual bool GetPickledData(OSExchangeData::CustomFormat format, 180 Pickle* data) const; 181 virtual bool GetFileContents(base::FilePath* filename, 182 std::string* file_contents) const; 183 virtual bool GetHtml(string16* html, GURL* base_url) const; 184 virtual bool HasString() const; 185 virtual bool HasURL() const; 186 virtual bool HasFile() const; 187 virtual bool HasFileContents() const; 188 virtual bool HasHtml() const; 189 virtual bool HasCustomFormat(OSExchangeData::CustomFormat format) const; 190 virtual void SetDownloadFileInfo( 191 const OSExchangeData::DownloadFileInfo& download_info); 192 virtual void SetInDragLoop(bool in_drag_loop) OVERRIDE; 193#if defined(USE_AURA) 194 virtual void SetDragImage(const gfx::ImageSkia& image, 195 const gfx::Vector2d& cursor_offset) OVERRIDE; 196 virtual const gfx::ImageSkia& GetDragImage() const OVERRIDE; 197 virtual const gfx::Vector2d& GetDragImageOffset() const OVERRIDE; 198#endif 199 200 private: 201 scoped_refptr<DataObjectImpl> data_; 202 base::win::ScopedComPtr<IDataObject> source_object_; 203 204#if defined(USE_AURA) 205 // Drag image and offset data. Only used for Ash. 206 gfx::ImageSkia drag_image_; 207 gfx::Vector2d drag_image_offset_; 208#endif 209 210 DISALLOW_COPY_AND_ASSIGN(OSExchangeDataProviderWin); 211}; 212 213} // namespace ui 214 215#endif // UI_BASE_DRAGDROP_OS_EXCHANGE_DATA_PROVIDER_WIN_H_ 216