diff options
author | brettw@chromium.org <brettw@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98> | 2012-03-26 22:21:59 +0000 |
---|---|---|
committer | brettw@chromium.org <brettw@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98> | 2012-03-26 22:21:59 +0000 |
commit | 11f515acdda3473200ff0cc4106a0020a7d4dc74 (patch) | |
tree | cdfd9713928d6f0fa73b5cd7bedbd965fc93e329 /ppapi/cpp/dev/file_chooser_dev.cc | |
parent | f60d96e82acd547ac834b93cd68865b66ab5b4da (diff) | |
download | chromium_src-11f515acdda3473200ff0cc4106a0020a7d4dc74.zip chromium_src-11f515acdda3473200ff0cc4106a0020a7d4dc74.tar.gz chromium_src-11f515acdda3473200ff0cc4106a0020a7d4dc74.tar.bz2 |
New file chooser interface that uses the new PP_ArrayOutput feature. This also changes PP_ArrayOutput to be pass-by-value.
This keeps backwards compat for the old interface. It fixes some bugs in the callback system that I found when working on the patch and adds some new machinery for doing array output in the proxy. It also re-enables the file chooser feature which was recently broken.
BUG=118857
Review URL: https://chromiumcodereview.appspot.com/9728001
git-svn-id: svn://svn.chromium.org/chrome/trunk/src@129022 0039d316-1c4b-4281-b951-d872f2087c98
Diffstat (limited to 'ppapi/cpp/dev/file_chooser_dev.cc')
-rw-r--r-- | ppapi/cpp/dev/file_chooser_dev.cc | 82 |
1 files changed, 66 insertions, 16 deletions
diff --git a/ppapi/cpp/dev/file_chooser_dev.cc b/ppapi/cpp/dev/file_chooser_dev.cc index 7987f48..a773def 100644 --- a/ppapi/cpp/dev/file_chooser_dev.cc +++ b/ppapi/cpp/dev/file_chooser_dev.cc @@ -4,6 +4,8 @@ #include "ppapi/cpp/dev/file_chooser_dev.h" +#include <string.h> + #include "ppapi/c/dev/ppb_file_chooser_dev.h" #include "ppapi/c/pp_errors.h" #include "ppapi/cpp/completion_callback.h" @@ -16,8 +18,12 @@ namespace pp { namespace { -template <> const char* interface_name<PPB_FileChooser_Dev>() { - return PPB_FILECHOOSER_DEV_INTERFACE; +template <> const char* interface_name<PPB_FileChooser_Dev_0_5>() { + return PPB_FILECHOOSER_DEV_INTERFACE_0_5; +} + +template <> const char* interface_name<PPB_FileChooser_Dev_0_6>() { + return PPB_FILECHOOSER_DEV_INTERFACE_0_6; } } // namespace @@ -25,28 +31,72 @@ template <> const char* interface_name<PPB_FileChooser_Dev>() { FileChooser_Dev::FileChooser_Dev(const InstanceHandle& instance, PP_FileChooserMode_Dev mode, const Var& accept_mime_types) { - if (!has_interface<PPB_FileChooser_Dev>()) - return; - PassRefFromConstructor(get_interface<PPB_FileChooser_Dev>()->Create( - instance.pp_instance(), mode, accept_mime_types.pp_var())); + if (has_interface<PPB_FileChooser_Dev_0_6>()) { + PassRefFromConstructor(get_interface<PPB_FileChooser_Dev_0_6>()->Create( + instance.pp_instance(), mode, accept_mime_types.pp_var())); + } else if (has_interface<PPB_FileChooser_Dev_0_5>()) { + PassRefFromConstructor(get_interface<PPB_FileChooser_Dev_0_5>()->Create( + instance.pp_instance(), mode, accept_mime_types.pp_var())); + } } FileChooser_Dev::FileChooser_Dev(const FileChooser_Dev& other) : Resource(other) { } -int32_t FileChooser_Dev::Show(const CompletionCallback& cc) { - if (!has_interface<PPB_FileChooser_Dev>()) - return cc.MayForce(PP_ERROR_NOINTERFACE); - return get_interface<PPB_FileChooser_Dev>()->Show( - pp_resource(), cc.pp_completion_callback()); +int32_t FileChooser_Dev::Show( + const CompletionCallbackWithOutput< std::vector<FileRef> >& callback) { + if (has_interface<PPB_FileChooser_Dev_0_6>()) { + return get_interface<PPB_FileChooser_Dev_0_6>()->Show( + pp_resource(), + callback.output(), + callback.pp_completion_callback()); + } + if (has_interface<PPB_FileChooser_Dev_0_5>()) { + // Data for our callback wrapper. The callback handler will delete it. + ChooseCallbackData0_5* data = new ChooseCallbackData0_5; + data->file_chooser = pp_resource(); + data->output = callback.output(); + data->original_callback = callback.pp_completion_callback(); + + return get_interface<PPB_FileChooser_Dev_0_5>()->Show( + pp_resource(), PP_MakeCompletionCallback(&CallbackConverter, data)); + } + return callback.MayForce(PP_ERROR_NOINTERFACE); } -FileRef FileChooser_Dev::GetNextChosenFile() const { - if (!has_interface<PPB_FileChooser_Dev>()) - return FileRef(); - return FileRef(PASS_REF, - get_interface<PPB_FileChooser_Dev>()->GetNextChosenFile(pp_resource())); +// static +void FileChooser_Dev::CallbackConverter(void* user_data, int32_t result) { + ChooseCallbackData0_5* data = static_cast<ChooseCallbackData0_5*>(user_data); + + // Get all of the selected file resources using the iterator API. + std::vector<PP_Resource> selected_files; + if (result == PP_OK) { + const PPB_FileChooser_Dev_0_5* chooser = + get_interface<PPB_FileChooser_Dev_0_5>(); + while (PP_Resource cur = chooser->GetNextChosenFile(data->file_chooser)) + selected_files.push_back(cur); + } + + // Need to issue the "GetDataBuffer" even for error cases & when the + // number of items is 0. + void* output_buf = data->output.GetDataBuffer( + data->output.user_data, + selected_files.size(), sizeof(PP_Resource)); + if (output_buf) { + if (!selected_files.empty()) { + memcpy(output_buf, &selected_files[0], + sizeof(PP_Resource) * selected_files.size()); + } + } else { + // Error allocating, need to free the resource IDs. + for (size_t i = 0; i < selected_files.size(); i++) + Module::Get()->core()->ReleaseResource(selected_files[i]); + } + + // Now execute the original callback. + PP_RunCompletionCallback(&data->original_callback, result); + delete data; } } // namespace pp |