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_RENDERER_PEPPER_PEPPER_GRAPHICS_2D_HOST_H_ 6 #define CONTENT_RENDERER_PEPPER_PEPPER_GRAPHICS_2D_HOST_H_ 7 8 #include <vector> 9 10 #include "base/basictypes.h" 11 #include "base/compiler_specific.h" 12 #include "base/memory/weak_ptr.h" 13 #include "content/common/content_export.h" 14 #include "ppapi/c/ppb_graphics_2d.h" 15 #include "ppapi/host/host_message_context.h" 16 #include "ppapi/host/resource_host.h" 17 #include "third_party/WebKit/public/platform/WebCanvas.h" 18 #include "ui/events/latency_info.h" 19 #include "ui/gfx/point.h" 20 #include "ui/gfx/size.h" 21 22 namespace cc { 23 class SingleReleaseCallback; 24 class TextureMailbox; 25 } 26 27 namespace gfx { 28 class Rect; 29 } 30 31 namespace ppapi { 32 struct ViewData; 33 } 34 35 namespace content { 36 37 class PepperPluginInstanceImpl; 38 class PPB_ImageData_Impl; 39 class RendererPpapiHost; 40 41 class CONTENT_EXPORT PepperGraphics2DHost 42 : public ppapi::host::ResourceHost, 43 public base::SupportsWeakPtr<PepperGraphics2DHost> { 44 public: 45 static PepperGraphics2DHost* Create( 46 RendererPpapiHost* host, 47 PP_Instance instance, 48 PP_Resource resource, 49 const PP_Size& size, 50 PP_Bool is_always_opaque, 51 scoped_refptr<PPB_ImageData_Impl> backing_store); 52 53 virtual ~PepperGraphics2DHost(); 54 55 // ppapi::host::ResourceHost override. 56 virtual int32_t OnResourceMessageReceived( 57 const IPC::Message& msg, 58 ppapi::host::HostMessageContext* context) OVERRIDE; 59 virtual bool IsGraphics2DHost() OVERRIDE; 60 61 bool ReadImageData(PP_Resource image, const PP_Point* top_left); 62 // Assciates this device with the given plugin instance. You can pass NULL 63 // to clear the existing device. Returns true on success. In this case, a 64 // repaint of the page will also be scheduled. Failure means that the device 65 // is already bound to a different instance, and nothing will happen. 66 bool BindToInstance(PepperPluginInstanceImpl* new_instance); 67 // Paints the current backing store to the web page. 68 void Paint(blink::WebCanvas* canvas, 69 const gfx::Rect& plugin_rect, 70 const gfx::Rect& paint_rect); 71 72 bool PrepareTextureMailbox( 73 cc::TextureMailbox* mailbox, 74 scoped_ptr<cc::SingleReleaseCallback>* release_callback); 75 void AttachedToNewLayer(); 76 77 // Notifications about the view's progress painting. See PluginInstance. 78 // These messages are used to send Flush callbacks to the plugin. 79 void ViewInitiatedPaint(); 80 void ViewFlushedPaint(); 81 82 void SetScale(float scale); 83 float GetScale() const; 84 bool IsAlwaysOpaque() const; 85 PPB_ImageData_Impl* ImageData(); 86 gfx::Size Size() const; 87 88 private: 89 PepperGraphics2DHost(RendererPpapiHost* host, 90 PP_Instance instance, 91 PP_Resource resource); 92 93 bool Init(int width, 94 int height, 95 bool is_always_opaque, 96 scoped_refptr<PPB_ImageData_Impl> backing_store); 97 98 int32_t OnHostMsgPaintImageData(ppapi::host::HostMessageContext* context, 99 const ppapi::HostResource& image_data, 100 const PP_Point& top_left, 101 bool src_rect_specified, 102 const PP_Rect& src_rect); 103 int32_t OnHostMsgScroll(ppapi::host::HostMessageContext* context, 104 bool clip_specified, 105 const PP_Rect& clip, 106 const PP_Point& amount); 107 int32_t OnHostMsgReplaceContents(ppapi::host::HostMessageContext* context, 108 const ppapi::HostResource& image_data); 109 int32_t OnHostMsgFlush(ppapi::host::HostMessageContext* context, 110 const std::vector<ui::LatencyInfo>& latency_info); 111 int32_t OnHostMsgSetScale(ppapi::host::HostMessageContext* context, 112 float scale); 113 int32_t OnHostMsgReadImageData(ppapi::host::HostMessageContext* context, 114 PP_Resource image, 115 const PP_Point& top_left); 116 117 // If |old_image_data| is not NULL, a previous used ImageData object will be 118 // reused. This is used by ReplaceContents. 119 int32_t Flush(PP_Resource* old_image_data); 120 121 // Called internally to execute the different queued commands. The 122 // parameters to these functions will have already been validated. The last 123 // rect argument will be filled by each function with the area affected by 124 // the update that requires invalidation. If there were no pixels changed, 125 // this rect can be untouched. 126 void ExecutePaintImageData(PPB_ImageData_Impl* image, 127 int x, 128 int y, 129 const gfx::Rect& src_rect, 130 gfx::Rect* invalidated_rect); 131 void ExecuteScroll(const gfx::Rect& clip, 132 int dx, 133 int dy, 134 gfx::Rect* invalidated_rect); 135 void ExecuteReplaceContents(PPB_ImageData_Impl* image, 136 gfx::Rect* invalidated_rect, 137 PP_Resource* old_image_data); 138 139 void SendFlushAck(); 140 141 // Function scheduled to execute by ScheduleOffscreenFlushAck that actually 142 // issues the offscreen callbacks. 143 void SendOffscreenFlushAck(); 144 145 // Schedules the offscreen flush ACK at a future time. 146 void ScheduleOffscreenFlushAck(); 147 148 // Returns true if there is any type of flush callback pending. 149 bool HasPendingFlush() const; 150 151 // Scale |op_rect| to logical pixels, taking care to include partially- 152 // covered logical pixels (aka DIPs). Also scale optional |delta| to logical 153 // pixels as well for scrolling cases. Returns false for scrolling cases where 154 // scaling either |op_rect| or |delta| would require scrolling to fall back to 155 // invalidation due to rounding errors, true otherwise. 156 static bool ConvertToLogicalPixels(float scale, 157 gfx::Rect* op_rect, 158 gfx::Point* delta); 159 160 RendererPpapiHost* renderer_ppapi_host_; 161 162 scoped_refptr<PPB_ImageData_Impl> image_data_; 163 164 // Non-owning pointer to the plugin instance this context is currently bound 165 // to, if any. If the context is currently unbound, this will be NULL. 166 PepperPluginInstanceImpl* bound_instance_; 167 168 // Keeps track of all drawing commands queued before a Flush call. 169 struct QueuedOperation; 170 typedef std::vector<QueuedOperation> OperationQueue; 171 OperationQueue queued_operations_; 172 173 // True if we need to send an ACK to plugin. 174 bool need_flush_ack_; 175 176 // When doing offscreen flushes, we issue a task that issues the callback 177 // later. This is set when one of those tasks is pending so that we can 178 // enforce the "only one pending flush at a time" constraint in the API. 179 bool offscreen_flush_pending_; 180 181 // Set to true if the plugin declares that this device will always be opaque. 182 // This allows us to do more optimized painting in some cases. 183 bool is_always_opaque_; 184 185 // Set to the scale between what the plugin considers to be one pixel and one 186 // DIP 187 float scale_; 188 189 ppapi::host::ReplyMessageContext flush_reply_context_; 190 191 bool is_running_in_process_; 192 193 bool texture_mailbox_modified_; 194 bool is_using_texture_layer_; 195 196 friend class PepperGraphics2DHostTest; 197 DISALLOW_COPY_AND_ASSIGN(PepperGraphics2DHost); 198 }; 199 200 } // namespace content 201 202 #endif // CONTENT_RENDERER_PEPPER_PEPPER_GRAPHICS_2D_HOST_H_ 203