15821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Copyright (c) 2012 The Chromium Authors. All rights reserved. 25821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Use of this source code is governed by a BSD-style license that can be 35821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// found in the LICENSE file. 45821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 55821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#ifndef PPAPI_CPP_OUTPUT_TRAITS_H_ 65821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#define PPAPI_CPP_OUTPUT_TRAITS_H_ 75821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 82a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)#include <vector> 92a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) 105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "ppapi/c/pp_resource.h" 115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "ppapi/cpp/array_output.h" 122a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)#include "ppapi/cpp/resource.h" 135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)/// @file 155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)/// This file defines internal templates for defining how data is passed to the 165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)/// browser via output parameters and how to convert that data to the 175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)/// corresponding C++ object types. 185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)/// 195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)/// It is used by the callback system, it should not be necessary for end-users 205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)/// to use these templates directly. 215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)struct PP_Var; 235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)namespace pp { 255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)class Var; 275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)namespace internal { 295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// This goop is a trick used to implement a template that can be used to 315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// determine if a given class is the base class of another given class. It is 325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// used in the resource object partial specialization below. 335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)template<typename, typename> struct IsSame { 345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) static bool const value = false; 355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}; 365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)template<typename A> struct IsSame<A, A> { 375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) static bool const value = true; 385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}; 395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)template<typename Base, typename Derived> struct IsBaseOf { 405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) private: 415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // This class doesn't work correctly with forward declarations. 425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Because sizeof cannot be applied to incomplete types, this line prevents us 435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // from passing in forward declarations. 445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) typedef char (*EnsureTypesAreComplete)[sizeof(Base) + sizeof(Derived)]; 455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) static Derived* CreateDerived(); 475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) static char (&Check(Base*))[1]; 485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) static char (&Check(...))[2]; 495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) public: 515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) static bool const value = sizeof Check(CreateDerived()) == 1 && 525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) !IsSame<Base const, void const>::value; 535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}; 545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Template to optionally derive from a given base class T if the given 565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// predicate P is true. 575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)template <class T, bool P> struct InheritIf {}; 585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)template <class T> struct InheritIf<T, true> : public T {}; 595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Single output parameters ---------------------------------------------------- 615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Output traits for all "plain old data" (POD) types. It is implemented to 635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// pass a pointer to the browser as an output parameter. 645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// 655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// This is used as a base class for the general CallbackOutputTraits below in 665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// the case where T is not a resource. 675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)template<typename T> 685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)struct GenericCallbackOutputTraits { 695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // The type passed to the PPAPI C API for this parameter. For normal out 705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // params, we pass a pointer to the object so the browser can write into it. 715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) typedef T* APIArgType; 725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // The type used to store the value. This is used internally in asynchronous 745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // callbacks by the CompletionCallbackFactory to have the browser write into 755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // a temporary value associated with the callback, which is passed to the 765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // plugin code when the callback is issued. 775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) typedef T StorageType; 785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Converts a "storage type" to a value that can be passed to the browser as 805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // an output parameter. This just takes the address to convert the value to 815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // a pointer. 825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) static inline APIArgType StorageToAPIArg(StorageType& t) { return &t; } 835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Converts the "storage type" to the value we pass to the plugin for 855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // callbacks. This doesn't actually need to do anything in this case, 865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // it's needed for some of more complex template specializations below. 875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) static inline T& StorageToPluginArg(StorageType& t) { return t; } 887dbb3d5cf0c15f500944d211057644d6a2f37371Ben Murdoch 897dbb3d5cf0c15f500944d211057644d6a2f37371Ben Murdoch // Initializes the "storage type" to a default value, if necessary. Here, 907dbb3d5cf0c15f500944d211057644d6a2f37371Ben Murdoch // we do nothing, assuming that the default constructor for T suffices. 917dbb3d5cf0c15f500944d211057644d6a2f37371Ben Murdoch static inline void Initialize(StorageType* /* t */) {} 925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}; 935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Output traits for all resource types. It is implemented to pass a 955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// PP_Resource* as an output parameter to the browser, and convert to the 965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// given resource object type T when passing to the plugin. 975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// 985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Note that this class is parameterized by the resource object, for example 995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// ResourceCallbackOutputTraits<pp::FileRef>. This is used as a base class for 1005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// CallbackOutputTraits below for the case where T is a derived class of 1015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// pp::Resource. 1025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)template<typename T> 1035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)struct ResourceCallbackOutputTraits { 1045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // To call the browser, we just pass a PP_Resource pointer as the out param. 1055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) typedef PP_Resource* APIArgType; 1065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) typedef PP_Resource StorageType; 1075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) static inline APIArgType StorageToAPIArg(StorageType& t) { 1095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return &t; 1105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 1115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Converts the PP_Resource to a pp::* object, passing any reference counted 1135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // object along with it. This must only be called once since there will only 1145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // be one reference that the browser has assigned to us for the out param! 1155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // When calling into the plugin, convert the PP_Resource into the requested 1165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // resource object type. 1175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) static inline T StorageToPluginArg(StorageType& t) { 1185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return T(PASS_REF, t); 1195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 1207dbb3d5cf0c15f500944d211057644d6a2f37371Ben Murdoch 1217dbb3d5cf0c15f500944d211057644d6a2f37371Ben Murdoch static inline void Initialize(StorageType* t) { 1227dbb3d5cf0c15f500944d211057644d6a2f37371Ben Murdoch *t = 0; 1237dbb3d5cf0c15f500944d211057644d6a2f37371Ben Murdoch } 1245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}; 1255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// The general templatized base class for all CallbackOutputTraits. This class 127c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)// covers both resources and POD (ints, structs, etc.) by inheriting from the 128c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)// appropriate base class depending on whether the given type derives from 129c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)// pp::Resource. This trick allows us to do this once rather than writing 130c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)// specializations for every resource object type. 1315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)template<typename T> 1325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)struct CallbackOutputTraits 133c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) : public InheritIf<GenericCallbackOutputTraits<T>, 134c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) !IsBaseOf<Resource, T>::value>, 135c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) public InheritIf<ResourceCallbackOutputTraits<T>, 136c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) IsBaseOf<Resource, T>::value> { 1375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}; 1385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// A specialization of CallbackOutputTraits for pp::Var output parameters. 1405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// It passes a PP_Var* to the browser and converts to a pp::Var when passing 1415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// to the plugin. 1425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)template<> 1435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)struct CallbackOutputTraits<Var> { 1445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // To call the browser, we just pass a PP_Var* as an output param. 1455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) typedef PP_Var* APIArgType; 1465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) typedef PP_Var StorageType; 1475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) static inline APIArgType StorageToAPIArg(StorageType& t) { 1495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return &t; 1505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 1515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Converts the PP_Var to a pp::Var object, passing any reference counted 1535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // object along with it. This must only be called once since there will only 1545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // be one reference that the browser has assigned to us for the out param! 1555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) static inline pp::Var StorageToPluginArg(StorageType& t) { 1565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return Var(PASS_REF, t); 1575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 1587dbb3d5cf0c15f500944d211057644d6a2f37371Ben Murdoch 1597dbb3d5cf0c15f500944d211057644d6a2f37371Ben Murdoch static inline void Initialize(StorageType* t) { 1607dbb3d5cf0c15f500944d211057644d6a2f37371Ben Murdoch *t = PP_MakeUndefined(); 1617dbb3d5cf0c15f500944d211057644d6a2f37371Ben Murdoch } 1625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}; 1635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 164d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles)// A specialization of CallbackOutputTraits for bool output parameters. 165d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles)// It passes a PP_Bool* to the browser and converts to a bool when passing 166d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles)// to the plugin. 167d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles)template<> 168d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles)struct CallbackOutputTraits<bool> { 169d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles) // To call the browser, we just pass a PP_Bool* as an output param. 170d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles) typedef PP_Bool* APIArgType; 171d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles) typedef PP_Bool StorageType; 172d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles) 173d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles) static inline APIArgType StorageToAPIArg(StorageType& t) { 174d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles) return &t; 175d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles) } 176d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles) 177d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles) // Converts the PP_Bool to a bool object. 178d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles) static inline bool StorageToPluginArg(StorageType& t) { 179d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles) return PP_ToBool(t); 180d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles) } 181d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles) 182d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles) static inline void Initialize(StorageType* t) { 183d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles) *t = PP_FALSE; 184d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles) } 185d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles)}; 186d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles) 1875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Array output parameters ----------------------------------------------------- 1885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Output traits for vectors of all "plain old data" (POD) types. It is 1905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// implemented to pass a pointer to the browser as an output parameter. 1915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// 1925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// This is used as a base class for the general vector CallbackOutputTraits 1935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// below in the case where T is not a resource. 1945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)template<typename T> 1955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)struct GenericVectorCallbackOutputTraits { 1965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // All arrays are output via a PP_ArrayOutput type. 1975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) typedef PP_ArrayOutput APIArgType; 1985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // We store the array as this adapter which combines the PP_ArrayOutput 2005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // structure with the underlying std::vector that it will write into. 2015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) typedef ArrayOutputAdapterWithStorage<T> StorageType; 2025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 2035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Retrieves the PP_ArrayOutput interface for our vector object that the 2045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // browser will use to write into our code. 2055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) static inline APIArgType StorageToAPIArg(StorageType& t) { 2065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return t.pp_array_output(); 2075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 2085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 2095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Retrieves the underlying vector that can be passed to the plugin. 2105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) static inline std::vector<T>& StorageToPluginArg(StorageType& t) { 2115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return t.output(); 2125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 2137dbb3d5cf0c15f500944d211057644d6a2f37371Ben Murdoch 2147dbb3d5cf0c15f500944d211057644d6a2f37371Ben Murdoch static inline void Initialize(StorageType* /* t */) {} 2155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}; 2165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 2175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Output traits for all vectors of resource types. It is implemented to pass 2185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// a PP_ArrayOutput parameter to the browser, and convert the returned resources 2195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// to a vector of the given resource object type T when passing to the plugin. 2205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// 2215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Note that this class is parameterized by the resource object, for example 2225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// ResourceVectorCallbackOutputTraits<pp::FileRef>. This is used as a base 2235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// class for CallbackOutputTraits below for the case where T is a derived 2245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// class of pp::Resource. 2255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)template<typename T> 2265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)struct ResourceVectorCallbackOutputTraits { 2275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) typedef PP_ArrayOutput APIArgType; 2285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) typedef ResourceArrayOutputAdapterWithStorage<T> StorageType; 2295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 2305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) static inline APIArgType StorageToAPIArg(StorageType& t) { 2315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return t.pp_array_output(); 2325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 2335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) static inline std::vector<T>& StorageToPluginArg(StorageType& t) { 2345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return t.output(); 2355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 2367dbb3d5cf0c15f500944d211057644d6a2f37371Ben Murdoch 2377dbb3d5cf0c15f500944d211057644d6a2f37371Ben Murdoch static inline void Initialize(StorageType* /* t */) {} 2385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}; 2395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 240c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)// Specialization of CallbackOutputTraits for vectors. This struct covers both 241c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)// arrays of resources and arrays of POD (ints, structs, etc.) by inheriting 242c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)// from the appropriate base class depending on whether the given type derives 243c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)// from pp::Resource. This trick allows us to do this once rather than writing 244c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)// specializations for every resource object type. 2455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)template<typename T> 2465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)struct CallbackOutputTraits< std::vector<T> > 247c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) : public InheritIf<GenericVectorCallbackOutputTraits<T>, 248c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) !IsBaseOf<Resource, T>::value>, 249c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) public InheritIf<ResourceVectorCallbackOutputTraits<T>, 250c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) IsBaseOf<Resource, T>::value> { 2515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}; 2525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 2535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// A specialization of CallbackOutputTraits to provide the callback system 2545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// the information on how to handle vectors of pp::Var. Vectors of resources 2555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// and plain data are handled separately. See the above definition for more. 2565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)template<> 2575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)struct CallbackOutputTraits< std::vector<pp::Var> > { 2585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // All arrays are output via a PP_ArrayOutput type. 2595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) typedef PP_ArrayOutput APIArgType; 2605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 2615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // We store the array as this adapter which combines the PP_ArrayOutput 2625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // structure with the underlying std::vector that it will write into. 2635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) typedef VarArrayOutputAdapterWithStorage StorageType; 2645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 2655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Retrieves the PP_ArrayOutput interface for our vector object that the 2665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // browser will use to write into our code. 2675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) static inline APIArgType StorageToAPIArg(StorageType& t) { 2685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return t.pp_array_output(); 2695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 2705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 2715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Retrieves the underlying vector that can be passed to the plugin. 2725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) static inline std::vector<pp::Var>& StorageToPluginArg(StorageType& t) { 2735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return t.output(); 2745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 2757dbb3d5cf0c15f500944d211057644d6a2f37371Ben Murdoch 2767dbb3d5cf0c15f500944d211057644d6a2f37371Ben Murdoch static inline void Initialize(StorageType* /* t */) {} 2775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}; 2785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 2795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} // namespace internal 2805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} // namespace pp 2815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 2825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#endif // PPAPI_CPP_OUTPUT_TRAITS_H_ 283