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 #include "ppapi/cpp/private/flash.h" 6 7 #include <string.h> 8 9 #include "ppapi/c/pp_bool.h" 10 #include "ppapi/c/pp_errors.h" 11 #include "ppapi/cpp/dev/device_ref_dev.h" 12 #include "ppapi/cpp/dev/video_capture_dev.h" 13 #include "ppapi/cpp/image_data.h" 14 #include "ppapi/cpp/instance_handle.h" 15 #include "ppapi/cpp/module.h" 16 #include "ppapi/cpp/module_impl.h" 17 #include "ppapi/cpp/point.h" 18 #include "ppapi/cpp/rect.h" 19 #include "ppapi/cpp/trusted/browser_font_trusted.h" 20 #include "ppapi/cpp/url_request_info.h" 21 #include "ppapi/cpp/var.h" 22 #include "ppapi/c/private/ppb_flash.h" 23 #include "ppapi/c/private/ppb_flash_print.h" 24 25 namespace pp { 26 27 namespace { 28 29 template <> const char* interface_name<PPB_Flash_13_0>() { 30 return PPB_FLASH_INTERFACE_13_0; 31 } 32 33 template <> const char* interface_name<PPB_Flash_12_6>() { 34 return PPB_FLASH_INTERFACE_12_6; 35 } 36 37 template <> const char* interface_name<PPB_Flash_12_5>() { 38 return PPB_FLASH_INTERFACE_12_5; 39 } 40 41 template <> const char* interface_name<PPB_Flash_12_4>() { 42 return PPB_FLASH_INTERFACE_12_4; 43 } 44 45 template <> const char* interface_name<PPB_Flash_Print_1_0>() { 46 return PPB_FLASH_PRINT_INTERFACE_1_0; 47 } 48 49 // The combined Flash interface is all Flash v12.* interfaces. All v12 50 // interfaces just append one or more functions to the previous one, so we can 51 // have this meta one at the most recent version. Function pointers will be 52 // null if they're not supported on the current Chrome version. 53 bool initialized_combined_interface = false; 54 PPB_Flash_12_6 flash_12_combined_interface; 55 56 // Makes sure that the most recent version is loaded into the combined 57 // interface struct above. Any unsupported functions will be NULL. If there 58 // is no Flash interface supported, all functions will be NULL. 59 void InitializeCombinedInterface() { 60 if (initialized_combined_interface) 61 return; 62 if (has_interface<PPB_Flash_12_6>()) { 63 memcpy(&flash_12_combined_interface, get_interface<PPB_Flash_12_6>(), 64 sizeof(PPB_Flash_12_6)); 65 } else if (has_interface<PPB_Flash_12_5>()) { 66 memcpy(&flash_12_combined_interface, get_interface<PPB_Flash_12_5>(), 67 sizeof(PPB_Flash_12_5)); 68 } else if (has_interface<PPB_Flash_12_4>()) { 69 memcpy(&flash_12_combined_interface, get_interface<PPB_Flash_12_4>(), 70 sizeof(PPB_Flash_12_4)); 71 } 72 initialized_combined_interface = true; 73 } 74 75 } // namespace 76 77 namespace flash { 78 79 // static 80 bool Flash::IsAvailable() { 81 return has_interface<PPB_Flash_13_0>() || 82 has_interface<PPB_Flash_12_6>() || 83 has_interface<PPB_Flash_12_5>() || 84 has_interface<PPB_Flash_12_4>(); 85 } 86 87 // static 88 void Flash::SetInstanceAlwaysOnTop(const InstanceHandle& instance, 89 bool on_top) { 90 InitializeCombinedInterface(); 91 if (has_interface<PPB_Flash_13_0>()) { 92 get_interface<PPB_Flash_13_0>()->SetInstanceAlwaysOnTop( 93 instance.pp_instance(), PP_FromBool(on_top)); 94 } else if (flash_12_combined_interface.SetInstanceAlwaysOnTop) { 95 flash_12_combined_interface.SetInstanceAlwaysOnTop( 96 instance.pp_instance(), PP_FromBool(on_top)); 97 } 98 } 99 100 // static 101 bool Flash::DrawGlyphs(const InstanceHandle& instance, 102 ImageData* image, 103 const BrowserFontDescription& font_desc, 104 uint32_t color, 105 const Point& position, 106 const Rect& clip, 107 const float transformation[3][3], 108 bool allow_subpixel_aa, 109 uint32_t glyph_count, 110 const uint16_t glyph_indices[], 111 const PP_Point glyph_advances[]) { 112 InitializeCombinedInterface(); 113 if (has_interface<PPB_Flash_13_0>()) { 114 return PP_ToBool(get_interface<PPB_Flash_13_0>()->DrawGlyphs( 115 instance.pp_instance(), 116 image->pp_resource(), 117 &font_desc.pp_font_description(), 118 color, 119 &position.pp_point(), 120 &clip.pp_rect(), 121 transformation, 122 PP_FromBool(allow_subpixel_aa), 123 glyph_count, 124 glyph_indices, 125 glyph_advances)); 126 } 127 if (flash_12_combined_interface.DrawGlyphs) { 128 return PP_ToBool(flash_12_combined_interface.DrawGlyphs( 129 instance.pp_instance(), 130 image->pp_resource(), 131 &font_desc.pp_font_description(), 132 color, 133 &position.pp_point(), 134 &clip.pp_rect(), 135 transformation, 136 PP_FromBool(allow_subpixel_aa), 137 glyph_count, 138 glyph_indices, 139 glyph_advances)); 140 } 141 return false; 142 } 143 144 // static 145 Var Flash::GetProxyForURL(const InstanceHandle& instance, 146 const std::string& url) { 147 InitializeCombinedInterface(); 148 if (has_interface<PPB_Flash_13_0>()) { 149 return Var(PASS_REF, get_interface<PPB_Flash_13_0>()->GetProxyForURL( 150 instance.pp_instance(), url.c_str())); 151 } 152 if (flash_12_combined_interface.GetProxyForURL) { 153 return Var(PASS_REF, flash_12_combined_interface.GetProxyForURL( 154 instance.pp_instance(), url.c_str())); 155 } 156 return Var(); 157 } 158 159 // static 160 int32_t Flash::Navigate(const URLRequestInfo& request_info, 161 const std::string& target, 162 bool from_user_action) { 163 InitializeCombinedInterface(); 164 if (has_interface<PPB_Flash_13_0>()) { 165 return get_interface<PPB_Flash_13_0>()->Navigate( 166 request_info.pp_resource(), 167 target.c_str(), 168 PP_FromBool(from_user_action)); 169 } 170 if (flash_12_combined_interface.Navigate) { 171 return flash_12_combined_interface.Navigate( 172 request_info.pp_resource(), 173 target.c_str(), 174 PP_FromBool(from_user_action)); 175 } 176 return PP_ERROR_FAILED; 177 } 178 179 // static 180 double Flash::GetLocalTimeZoneOffset(const InstanceHandle& instance, 181 PP_Time t) { 182 InitializeCombinedInterface(); 183 if (has_interface<PPB_Flash_13_0>()) { 184 return get_interface<PPB_Flash_13_0>()->GetLocalTimeZoneOffset( 185 instance.pp_instance(), t); 186 } 187 if (flash_12_combined_interface.GetLocalTimeZoneOffset) { 188 return flash_12_combined_interface.GetLocalTimeZoneOffset( 189 instance.pp_instance(), t); 190 } 191 return 0.0; 192 } 193 194 // static 195 Var Flash::GetCommandLineArgs(Module* module) { 196 InitializeCombinedInterface(); 197 if (has_interface<PPB_Flash_13_0>()) { 198 return Var(PASS_REF, get_interface<PPB_Flash_13_0>()->GetCommandLineArgs( 199 module->pp_module())); 200 } 201 if (flash_12_combined_interface.GetCommandLineArgs) { 202 return Var( 203 PASS_REF, 204 flash_12_combined_interface.GetCommandLineArgs(module->pp_module())); 205 } 206 return Var(); 207 } 208 209 // static 210 void Flash::PreloadFontWin(const void* logfontw) { 211 InitializeCombinedInterface(); 212 if (has_interface<PPB_Flash_13_0>()) 213 return get_interface<PPB_Flash_13_0>()->PreloadFontWin(logfontw); 214 if (flash_12_combined_interface.PreloadFontWin) 215 return flash_12_combined_interface.PreloadFontWin(logfontw); 216 } 217 218 // static 219 bool Flash::IsRectTopmost(const InstanceHandle& instance, const Rect& rect) { 220 InitializeCombinedInterface(); 221 if (has_interface<PPB_Flash_13_0>()) { 222 return PP_ToBool(get_interface<PPB_Flash_13_0>()->IsRectTopmost( 223 instance.pp_instance(), &rect.pp_rect())); 224 } 225 if (flash_12_combined_interface.IsRectTopmost) { 226 return PP_ToBool(flash_12_combined_interface.IsRectTopmost( 227 instance.pp_instance(), &rect.pp_rect())); 228 } 229 return false; 230 } 231 232 // static 233 void Flash::UpdateActivity(const InstanceHandle& instance) { 234 InitializeCombinedInterface(); 235 if (has_interface<PPB_Flash_13_0>()) 236 get_interface<PPB_Flash_13_0>()->UpdateActivity(instance.pp_instance()); 237 else if (flash_12_combined_interface.UpdateActivity) 238 flash_12_combined_interface.UpdateActivity(instance.pp_instance()); 239 } 240 241 // static 242 Var Flash::GetSetting(const InstanceHandle& instance, PP_FlashSetting setting) { 243 InitializeCombinedInterface(); 244 if (has_interface<PPB_Flash_13_0>()) { 245 return Var(PASS_REF, get_interface<PPB_Flash_13_0>()->GetSetting( 246 instance.pp_instance(), setting)); 247 } 248 if (flash_12_combined_interface.GetSetting) { 249 return Var(PASS_REF, 250 flash_12_combined_interface.GetSetting(instance.pp_instance(), 251 setting)); 252 } 253 254 return Var(); 255 } 256 257 // static 258 bool Flash::SetCrashData(const InstanceHandle& instance, 259 PP_FlashCrashKey key, 260 const pp::Var& value) { 261 InitializeCombinedInterface(); 262 if (has_interface<PPB_Flash_13_0>()) { 263 return PP_ToBool(get_interface<PPB_Flash_13_0>()->SetCrashData( 264 instance.pp_instance(), key, value.pp_var())); 265 } 266 if (flash_12_combined_interface.SetCrashData) { 267 return PP_ToBool( 268 flash_12_combined_interface.SetCrashData(instance.pp_instance(), 269 key, value.pp_var())); 270 } 271 return false; 272 } 273 274 // static 275 int32_t Flash::EnumerateVideoCaptureDevices( 276 const InstanceHandle& instance, 277 const VideoCapture_Dev& video_capture, 278 std::vector<DeviceRef_Dev>* devices_out) { 279 InitializeCombinedInterface(); 280 if (has_interface<PPB_Flash_13_0>()) { 281 ResourceArrayOutputAdapter<DeviceRef_Dev> adapter(devices_out); 282 return get_interface<PPB_Flash_13_0>()->EnumerateVideoCaptureDevices( 283 instance.pp_instance(), 284 video_capture.pp_resource(), 285 adapter.pp_array_output()); 286 } 287 if (flash_12_combined_interface.EnumerateVideoCaptureDevices) { 288 ResourceArrayOutputAdapter<DeviceRef_Dev> adapter(devices_out); 289 return flash_12_combined_interface.EnumerateVideoCaptureDevices( 290 instance.pp_instance(), 291 video_capture.pp_resource(), 292 adapter.pp_array_output()); 293 } 294 return PP_ERROR_FAILED; 295 } 296 297 // static 298 bool Flash::InvokePrinting(const InstanceHandle& instance) { 299 if (has_interface<PPB_Flash_Print_1_0>()) { 300 get_interface<PPB_Flash_Print_1_0>()->InvokePrinting( 301 instance.pp_instance()); 302 return true; 303 } 304 return false; 305 } 306 307 } // namespace flash 308 } // namespace pp 309