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)#include <set> 65821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 7c5cede9ae108bb15f6b7a8aea21c7e1fefa2834cBen Murdoch#include <X11/Xlib.h> 8c5cede9ae108bb15f6b7a8aea21c7e1fefa2834cBen Murdoch 95821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "base/bind.h" 105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "base/bind_helpers.h" 115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "base/command_line.h" 125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "base/logging.h" 135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "base/nix/mime_util_xdg.h" 145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "base/nix/xdg_util.h" 15bbcdd45c55eb7c4641ab97aef9889b0fc828e7d3Ben Murdoch#include "base/process/launch.h" 162a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)#include "base/strings/string_number_conversions.h" 17868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)#include "base/strings/string_util.h" 18868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)#include "base/strings/utf_string_conversions.h" 195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "base/threading/thread_restrictions.h" 205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/browser/ui/libgtk2ui/select_file_dialog_impl.h" 211320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci#include "chrome/grit/generated_resources.h" 225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "content/public/browser/browser_thread.h" 2323730a6e56a168d1879203e4b3819bb36e3d8f1fTorne (Richard Coles)#include "ui/aura/window_tree_host.h" 245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "ui/base/l10n/l10n_util.h" 251320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci#include "ui/strings/grit/ui_strings.h" 265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// These conflict with base/tracked_objects.h, so need to come last. 285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include <gdk/gdkx.h> 295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include <gtk/gtk.h> 305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)using content::BrowserThread; 325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)namespace { 345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)std::string GetTitle(const std::string& title, int message_id) { 365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return title.empty() ? l10n_util::GetStringUTF8(message_id) : title; 375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)const char kKdialogBinary[] = "kdialog"; 405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} // namespace 425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)namespace libgtk2ui { 445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Implementation of SelectFileDialog that shows a KDE common dialog for 465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// choosing a file or folder. This acts as a modal dialog. 475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)class SelectFileDialogImplKDE : public SelectFileDialogImpl { 485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) public: 495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) SelectFileDialogImplKDE(Listener* listener, 505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) ui::SelectFilePolicy* policy, 515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) base::nix::DesktopEnvironment desktop); 525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) protected: 545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) virtual ~SelectFileDialogImplKDE(); 555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 56c5cede9ae108bb15f6b7a8aea21c7e1fefa2834cBen Murdoch // BaseShellDialog implementation: 57c5cede9ae108bb15f6b7a8aea21c7e1fefa2834cBen Murdoch virtual bool IsRunning(gfx::NativeWindow parent_window) const OVERRIDE; 58c5cede9ae108bb15f6b7a8aea21c7e1fefa2834cBen Murdoch 595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // SelectFileDialog implementation. 605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // |params| is user data we pass back via the Listener interface. 612a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) virtual void SelectFileImpl( 622a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) Type type, 63a3f6a49ab37290eeeb8db0f41ec0f1cb74a68be7Torne (Richard Coles) const base::string16& title, 642a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) const base::FilePath& default_path, 652a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) const FileTypeInfo* file_types, 662a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) int file_type_index, 672a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) const base::FilePath::StringType& default_extension, 682a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) gfx::NativeWindow owning_window, 692a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) void* params) OVERRIDE; 705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) private: 725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) virtual bool HasMultipleFileTypeChoicesImpl() OVERRIDE; 735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) struct KDialogParams { 755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) KDialogParams(const std::string& type, const std::string& title, 76c5cede9ae108bb15f6b7a8aea21c7e1fefa2834cBen Murdoch const base::FilePath& default_path, XID parent, 775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) bool file_operation, bool multiple_selection, 785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) void* kdialog_params, 79c5cede9ae108bb15f6b7a8aea21c7e1fefa2834cBen Murdoch void (SelectFileDialogImplKDE::*callback)(XID, 80c5cede9ae108bb15f6b7a8aea21c7e1fefa2834cBen Murdoch const std::string&, 815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) int, void*)) 825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) : type(type), title(title), default_path(default_path), parent(parent), 835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) file_operation(file_operation), 845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) multiple_selection(multiple_selection), 855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) kdialog_params(kdialog_params), callback(callback) { 865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) std::string type; 895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) std::string title; 902a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) base::FilePath default_path; 91c5cede9ae108bb15f6b7a8aea21c7e1fefa2834cBen Murdoch XID parent; 925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) bool file_operation; 935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) bool multiple_selection; 945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) void* kdialog_params; 95c5cede9ae108bb15f6b7a8aea21c7e1fefa2834cBen Murdoch void (SelectFileDialogImplKDE::*callback)(XID, const std::string&, 96c5cede9ae108bb15f6b7a8aea21c7e1fefa2834cBen Murdoch int, void*); 975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) }; 985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Get the filters from |file_types_| and concatenate them into 1005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // |filter_string|. 1015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) std::string GetMimeTypeFilterString(); 1025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Get KDialog command line representing the Argv array for KDialog. 1045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) void GetKDialogCommandLine(const std::string& type, const std::string& title, 105c5cede9ae108bb15f6b7a8aea21c7e1fefa2834cBen Murdoch const base::FilePath& default_path, XID parent, 1065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) bool file_operation, bool multiple_selection, CommandLine* command_line); 1075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Call KDialog on the FILE thread and post results back to the UI thread. 1095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) void CallKDialogOutput(const KDialogParams& params); 1105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Notifies the listener that a single file was chosen. 1122a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) void FileSelected(const base::FilePath& path, void* params); 1135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Notifies the listener that multiple files were chosen. 1152a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) void MultiFilesSelected(const std::vector<base::FilePath>& files, 1162a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) void* params); 1175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Notifies the listener that no file was chosen (the action was canceled). 1195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Dialog is passed so we can find that |params| pointer that was passed to 1205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // us when we were told to show the dialog. 1215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) void FileNotSelected(void *params); 1225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 123a36e5920737c6adbddd3e43b760e5de8431db6e0Torne (Richard Coles) void CreateSelectFolderDialog(Type type, 124a36e5920737c6adbddd3e43b760e5de8431db6e0Torne (Richard Coles) const std::string& title, 1252a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) const base::FilePath& default_path, 126c5cede9ae108bb15f6b7a8aea21c7e1fefa2834cBen Murdoch XID parent, void* params); 1275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) void CreateFileOpenDialog(const std::string& title, 1292a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) const base::FilePath& default_path, 130c5cede9ae108bb15f6b7a8aea21c7e1fefa2834cBen Murdoch XID parent, void* params); 1315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) void CreateMultiFileOpenDialog(const std::string& title, 1332a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) const base::FilePath& default_path, 134c5cede9ae108bb15f6b7a8aea21c7e1fefa2834cBen Murdoch XID parent, void* params); 1355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) void CreateSaveAsDialog(const std::string& title, 1372a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) const base::FilePath& default_path, 138c5cede9ae108bb15f6b7a8aea21c7e1fefa2834cBen Murdoch XID parent, void* params); 1395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Common function for OnSelectSingleFileDialogResponse and 1415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // OnSelectSingleFolderDialogResponse. 1425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) void SelectSingleFileHelper(const std::string& output, int exit_code, 1435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) void* params, bool allow_folder); 1445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 145c5cede9ae108bb15f6b7a8aea21c7e1fefa2834cBen Murdoch void OnSelectSingleFileDialogResponse(XID parent, 146c5cede9ae108bb15f6b7a8aea21c7e1fefa2834cBen Murdoch const std::string& output, 1475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) int exit_code, void* params); 148c5cede9ae108bb15f6b7a8aea21c7e1fefa2834cBen Murdoch void OnSelectMultiFileDialogResponse(XID parent, 149c5cede9ae108bb15f6b7a8aea21c7e1fefa2834cBen Murdoch const std::string& output, 1505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) int exit_code, void* params); 151c5cede9ae108bb15f6b7a8aea21c7e1fefa2834cBen Murdoch void OnSelectSingleFolderDialogResponse(XID parent, 152c5cede9ae108bb15f6b7a8aea21c7e1fefa2834cBen Murdoch const std::string& output, 1535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) int exit_code, void* params); 1545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Should be either DESKTOP_ENVIRONMENT_KDE3 or DESKTOP_ENVIRONMENT_KDE4. 1565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) base::nix::DesktopEnvironment desktop_; 1575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 158c5cede9ae108bb15f6b7a8aea21c7e1fefa2834cBen Murdoch // The set of all parent windows for which we are currently running 159c5cede9ae108bb15f6b7a8aea21c7e1fefa2834cBen Murdoch // dialogs. This should only be accessed on the UI thread. 160c5cede9ae108bb15f6b7a8aea21c7e1fefa2834cBen Murdoch std::set<XID> parents_; 161c5cede9ae108bb15f6b7a8aea21c7e1fefa2834cBen Murdoch 1625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) DISALLOW_COPY_AND_ASSIGN(SelectFileDialogImplKDE); 1635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}; 1645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// static 1665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)bool SelectFileDialogImpl::CheckKDEDialogWorksOnUIThread() { 1675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // No choice. UI thread can't continue without an answer here. Fortunately we 1685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // only do this once, the first time a file dialog is displayed. 1695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) base::ThreadRestrictions::ScopedAllowIO allow_io; 1705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) CommandLine::StringVector cmd_vector; 1725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) cmd_vector.push_back(kKdialogBinary); 1735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) cmd_vector.push_back("--version"); 1745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) CommandLine command_line(cmd_vector); 1755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) std::string dummy; 1765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return base::GetAppOutput(command_line, &dummy); 1775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 1785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// static 1805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)SelectFileDialogImpl* SelectFileDialogImpl::NewSelectFileDialogImplKDE( 1815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) Listener* listener, 1825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) ui::SelectFilePolicy* policy, 1835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) base::nix::DesktopEnvironment desktop) { 1845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return new SelectFileDialogImplKDE(listener, policy, desktop); 1855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 1865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)SelectFileDialogImplKDE::SelectFileDialogImplKDE( 1885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) Listener* listener, 1895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) ui::SelectFilePolicy* policy, 1905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) base::nix::DesktopEnvironment desktop) 1915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) : SelectFileDialogImpl(listener, policy), 1925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) desktop_(desktop) { 1935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) DCHECK(desktop_ == base::nix::DESKTOP_ENVIRONMENT_KDE3 || 1945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) desktop_ == base::nix::DESKTOP_ENVIRONMENT_KDE4); 1955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 1965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)SelectFileDialogImplKDE::~SelectFileDialogImplKDE() { 1985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 1995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 200c5cede9ae108bb15f6b7a8aea21c7e1fefa2834cBen Murdochbool SelectFileDialogImplKDE::IsRunning(gfx::NativeWindow parent_window) const { 201c5cede9ae108bb15f6b7a8aea21c7e1fefa2834cBen Murdoch DCHECK_CURRENTLY_ON(BrowserThread::UI); 202c5cede9ae108bb15f6b7a8aea21c7e1fefa2834cBen Murdoch if (parent_window && parent_window->GetHost()) { 203c5cede9ae108bb15f6b7a8aea21c7e1fefa2834cBen Murdoch XID xid = parent_window->GetHost()->GetAcceleratedWidget(); 204c5cede9ae108bb15f6b7a8aea21c7e1fefa2834cBen Murdoch return parents_.find(xid) != parents_.end(); 205c5cede9ae108bb15f6b7a8aea21c7e1fefa2834cBen Murdoch } 206c5cede9ae108bb15f6b7a8aea21c7e1fefa2834cBen Murdoch 207c5cede9ae108bb15f6b7a8aea21c7e1fefa2834cBen Murdoch return false; 208c5cede9ae108bb15f6b7a8aea21c7e1fefa2834cBen Murdoch} 209c5cede9ae108bb15f6b7a8aea21c7e1fefa2834cBen Murdoch 2105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// We ignore |default_extension|. 2115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void SelectFileDialogImplKDE::SelectFileImpl( 2125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) Type type, 213a3f6a49ab37290eeeb8db0f41ec0f1cb74a68be7Torne (Richard Coles) const base::string16& title, 2142a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) const base::FilePath& default_path, 2155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) const FileTypeInfo* file_types, 2165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) int file_type_index, 2172a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) const base::FilePath::StringType& default_extension, 2185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) gfx::NativeWindow owning_window, 2195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) void* params) { 220c5cede9ae108bb15f6b7a8aea21c7e1fefa2834cBen Murdoch DCHECK_CURRENTLY_ON(BrowserThread::UI); 2215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) type_ = type; 222c5cede9ae108bb15f6b7a8aea21c7e1fefa2834cBen Murdoch 223c5cede9ae108bb15f6b7a8aea21c7e1fefa2834cBen Murdoch XID window_xid = None; 224c5cede9ae108bb15f6b7a8aea21c7e1fefa2834cBen Murdoch if (owning_window && owning_window->GetHost()) { 225c5cede9ae108bb15f6b7a8aea21c7e1fefa2834cBen Murdoch // |owning_window| can be null when user right-clicks on a downloadable item 226c5cede9ae108bb15f6b7a8aea21c7e1fefa2834cBen Murdoch // and chooses 'Open Link in New Tab' when 'Ask where to save each file 227c5cede9ae108bb15f6b7a8aea21c7e1fefa2834cBen Murdoch // before downloading.' preference is turned on. (http://crbug.com/29213) 228c5cede9ae108bb15f6b7a8aea21c7e1fefa2834cBen Murdoch window_xid = owning_window->GetHost()->GetAcceleratedWidget(); 229c5cede9ae108bb15f6b7a8aea21c7e1fefa2834cBen Murdoch parents_.insert(window_xid); 230c5cede9ae108bb15f6b7a8aea21c7e1fefa2834cBen Murdoch } 2315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 2325d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) std::string title_string = base::UTF16ToUTF8(title); 2335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 2345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) file_type_index_ = file_type_index; 2355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if (file_types) 2365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) file_types_ = *file_types; 2375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) else 2385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) file_types_.include_all_files = true; 2395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 2405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) switch (type) { 2415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) case SELECT_FOLDER: 242a36e5920737c6adbddd3e43b760e5de8431db6e0Torne (Richard Coles) case SELECT_UPLOAD_FOLDER: 243a36e5920737c6adbddd3e43b760e5de8431db6e0Torne (Richard Coles) CreateSelectFolderDialog(type, title_string, default_path, 244c5cede9ae108bb15f6b7a8aea21c7e1fefa2834cBen Murdoch window_xid, params); 2455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return; 2465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) case SELECT_OPEN_FILE: 247c5cede9ae108bb15f6b7a8aea21c7e1fefa2834cBen Murdoch CreateFileOpenDialog(title_string, default_path, window_xid, params); 2485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return; 2495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) case SELECT_OPEN_MULTI_FILE: 250c5cede9ae108bb15f6b7a8aea21c7e1fefa2834cBen Murdoch CreateMultiFileOpenDialog(title_string, default_path, window_xid, params); 2515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return; 2525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) case SELECT_SAVEAS_FILE: 253c5cede9ae108bb15f6b7a8aea21c7e1fefa2834cBen Murdoch CreateSaveAsDialog(title_string, default_path, window_xid, params); 2545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return; 2555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) default: 2565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) NOTREACHED(); 2575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return; 2585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 2595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 2605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 2615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)bool SelectFileDialogImplKDE::HasMultipleFileTypeChoicesImpl() { 2625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return file_types_.extensions.size() > 1; 2635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 2645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 2655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)std::string SelectFileDialogImplKDE::GetMimeTypeFilterString() { 266e5d81f57cb97b3b6b7fccc9c5610d21eb81db09dBen Murdoch DCHECK_CURRENTLY_ON(BrowserThread::FILE); 2675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) std::string filter_string; 2685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // We need a filter set because the same mime type can appear multiple times. 2695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) std::set<std::string> filter_set; 2705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) for (size_t i = 0; i < file_types_.extensions.size(); ++i) { 2715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) for (size_t j = 0; j < file_types_.extensions[i].size(); ++j) { 2725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if (!file_types_.extensions[i][j].empty()) { 2732a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) std::string mime_type = base::nix::GetFileMimeType(base::FilePath( 2742a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) "name").ReplaceExtension(file_types_.extensions[i][j])); 2755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) filter_set.insert(mime_type); 2765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 2775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 2785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 2795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Add the *.* filter, but only if we have added other filters (otherwise it 2805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // is implied). 2815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if (file_types_.include_all_files && !file_types_.extensions.empty()) 2825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) filter_set.insert("application/octet-stream"); 2835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Create the final output string. 2845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) filter_string.clear(); 2855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) for (std::set<std::string>::iterator it = filter_set.begin(); 2865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) it != filter_set.end(); ++it) { 2875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) filter_string.append(*it + " "); 2885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 2895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return filter_string; 2905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 2915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 2925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void SelectFileDialogImplKDE::CallKDialogOutput(const KDialogParams& params) { 293e5d81f57cb97b3b6b7fccc9c5610d21eb81db09dBen Murdoch DCHECK_CURRENTLY_ON(BrowserThread::FILE); 2945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) CommandLine::StringVector cmd_vector; 2955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) cmd_vector.push_back(kKdialogBinary); 2965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) CommandLine command_line(cmd_vector); 2975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) GetKDialogCommandLine(params.type, params.title, params.default_path, 2985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) params.parent, params.file_operation, 2995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) params.multiple_selection, &command_line); 3005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) std::string output; 3015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) int exit_code; 3025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Get output from KDialog 3035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) base::GetAppOutputWithExitCode(command_line, &output, &exit_code); 3045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if (!output.empty()) 3055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) output.erase(output.size() - 1); 3065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 307c5cede9ae108bb15f6b7a8aea21c7e1fefa2834cBen Murdoch // Now the dialog is no longer showing, but we can't erase its parent from the 308c5cede9ae108bb15f6b7a8aea21c7e1fefa2834cBen Murdoch // parent set yet because we're on the FILE thread. 3095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) BrowserThread::PostTask( 3105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) BrowserThread::UI, FROM_HERE, 311c5cede9ae108bb15f6b7a8aea21c7e1fefa2834cBen Murdoch base::Bind(params.callback, this, params.parent, output, exit_code, 3125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) params.kdialog_params)); 3135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 3145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 3155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void SelectFileDialogImplKDE::GetKDialogCommandLine(const std::string& type, 3162a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) const std::string& title, const base::FilePath& path, 317c5cede9ae108bb15f6b7a8aea21c7e1fefa2834cBen Murdoch XID parent, bool file_operation, bool multiple_selection, 3185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) CommandLine* command_line) { 3195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) CHECK(command_line); 3205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 3215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Attach to the current Chrome window. 322c5cede9ae108bb15f6b7a8aea21c7e1fefa2834cBen Murdoch if (parent != None) { 323c5cede9ae108bb15f6b7a8aea21c7e1fefa2834cBen Murdoch command_line->AppendSwitchNative( 324c5cede9ae108bb15f6b7a8aea21c7e1fefa2834cBen Murdoch desktop_ == base::nix::DESKTOP_ENVIRONMENT_KDE3 ? 325c5cede9ae108bb15f6b7a8aea21c7e1fefa2834cBen Murdoch "--embed" : "--attach", 326c5cede9ae108bb15f6b7a8aea21c7e1fefa2834cBen Murdoch base::IntToString(parent)); 327c5cede9ae108bb15f6b7a8aea21c7e1fefa2834cBen Murdoch } 328c5cede9ae108bb15f6b7a8aea21c7e1fefa2834cBen Murdoch 3295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Set the correct title for the dialog. 3305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if (!title.empty()) 3315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) command_line->AppendSwitchNative("--title", title); 3325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Enable multiple file selection if we need to. 3335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if (multiple_selection) { 3345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) command_line->AppendSwitch("--multiple"); 3355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) command_line->AppendSwitch("--separate-output"); 3365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 3375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) command_line->AppendSwitch(type); 3385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // The path should never be empty. If it is, set it to PWD. 3395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if (path.empty()) 3402a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) command_line->AppendArgPath(base::FilePath(".")); 3415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) else 3425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) command_line->AppendArgPath(path); 3435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Depending on the type of the operation we need, get the path to the 3445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // file/folder and set up mime type filters. 3455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if (file_operation) 3465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) command_line->AppendArg(GetMimeTypeFilterString()); 3475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) VLOG(1) << "KDialog command line: " << command_line->GetCommandLineString(); 3485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 3495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 3502a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)void SelectFileDialogImplKDE::FileSelected(const base::FilePath& path, 3512a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) void* params) { 3525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if (type_ == SELECT_SAVEAS_FILE) 3535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *last_saved_path_ = path.DirName(); 3545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) else if (type_ == SELECT_OPEN_FILE) 3555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *last_opened_path_ = path.DirName(); 3565f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles) else if (type_ == SELECT_FOLDER || type_ == SELECT_UPLOAD_FOLDER) 3575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *last_opened_path_ = path; 3585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) else 3595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) NOTREACHED(); 3605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if (listener_) { // What does the filter index actually do? 3615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // TODO(dfilimon): Get a reasonable index value from somewhere. 3625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) listener_->FileSelected(path, 1, params); 3635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 3645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 3655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 3665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void SelectFileDialogImplKDE::MultiFilesSelected( 3672a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) const std::vector<base::FilePath>& files, void* params) { 3685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *last_opened_path_ = files[0].DirName(); 3695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if (listener_) 3705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) listener_->MultiFilesSelected(files, params); 3715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 3725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 3735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void SelectFileDialogImplKDE::FileNotSelected(void* params) { 3745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if (listener_) 3755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) listener_->FileSelectionCanceled(params); 3765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 3775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 3785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void SelectFileDialogImplKDE::CreateSelectFolderDialog( 379a36e5920737c6adbddd3e43b760e5de8431db6e0Torne (Richard Coles) Type type, const std::string& title, const base::FilePath& default_path, 380c5cede9ae108bb15f6b7a8aea21c7e1fefa2834cBen Murdoch XID parent, void *params) { 381a36e5920737c6adbddd3e43b760e5de8431db6e0Torne (Richard Coles) int title_message_id = (type == SELECT_UPLOAD_FOLDER) 382a36e5920737c6adbddd3e43b760e5de8431db6e0Torne (Richard Coles) ? IDS_SELECT_UPLOAD_FOLDER_DIALOG_TITLE 383a36e5920737c6adbddd3e43b760e5de8431db6e0Torne (Richard Coles) : IDS_SELECT_FOLDER_DIALOG_TITLE; 3845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) BrowserThread::PostTask( 3855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) BrowserThread::FILE, FROM_HERE, 3865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) base::Bind( 3875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) &SelectFileDialogImplKDE::CallKDialogOutput, 3885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) this, 3895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) KDialogParams( 3905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) "--getexistingdirectory", 391a36e5920737c6adbddd3e43b760e5de8431db6e0Torne (Richard Coles) GetTitle(title, title_message_id), 3925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) default_path.empty() ? *last_opened_path_ : default_path, 3935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) parent, false, false, params, 3945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) &SelectFileDialogImplKDE::OnSelectSingleFolderDialogResponse))); 3955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 3965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 3975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void SelectFileDialogImplKDE::CreateFileOpenDialog( 3982a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) const std::string& title, const base::FilePath& default_path, 399c5cede9ae108bb15f6b7a8aea21c7e1fefa2834cBen Murdoch XID parent, void* params) { 4005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) BrowserThread::PostTask( 4015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) BrowserThread::FILE, FROM_HERE, 4025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) base::Bind( 4035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) &SelectFileDialogImplKDE::CallKDialogOutput, 4045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) this, 4055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) KDialogParams( 4065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) "--getopenfilename", 4075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) GetTitle(title, IDS_OPEN_FILE_DIALOG_TITLE), 4085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) default_path.empty() ? *last_opened_path_ : default_path, 4095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) parent, true, false, params, 4105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) &SelectFileDialogImplKDE::OnSelectSingleFileDialogResponse))); 4115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 4125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 4135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void SelectFileDialogImplKDE::CreateMultiFileOpenDialog( 4142a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) const std::string& title, const base::FilePath& default_path, 415c5cede9ae108bb15f6b7a8aea21c7e1fefa2834cBen Murdoch XID parent, void* params) { 4165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) BrowserThread::PostTask( 4175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) BrowserThread::FILE, FROM_HERE, 4185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) base::Bind( 4195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) &SelectFileDialogImplKDE::CallKDialogOutput, 4205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) this, 4215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) KDialogParams( 4225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) "--getopenfilename", 4235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) GetTitle(title, IDS_OPEN_FILES_DIALOG_TITLE), 4245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) default_path.empty() ? *last_opened_path_ : default_path, 4255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) parent, true, true, params, 4265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) &SelectFileDialogImplKDE::OnSelectMultiFileDialogResponse))); 4275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 4285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 4295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void SelectFileDialogImplKDE::CreateSaveAsDialog( 4302a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) const std::string& title, const base::FilePath& default_path, 431c5cede9ae108bb15f6b7a8aea21c7e1fefa2834cBen Murdoch XID parent, void* params) { 4325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) BrowserThread::PostTask( 4335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) BrowserThread::FILE, FROM_HERE, 4345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) base::Bind( 4355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) &SelectFileDialogImplKDE::CallKDialogOutput, 4365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) this, 4375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) KDialogParams( 4385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) "--getsavefilename", 4395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) GetTitle(title, IDS_SAVE_AS_DIALOG_TITLE), 4405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) default_path.empty() ? *last_saved_path_ : default_path, 4415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) parent, true, false, params, 4425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) &SelectFileDialogImplKDE::OnSelectSingleFileDialogResponse))); 4435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 4445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 4455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void SelectFileDialogImplKDE::SelectSingleFileHelper(const std::string& output, 4465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) int exit_code, void* params, bool allow_folder) { 4475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) VLOG(1) << "[kdialog] SingleFileResponse: " << output; 4485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if (exit_code != 0 || output.empty()) { 4495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) FileNotSelected(params); 4505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return; 4515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 4525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 4532a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) base::FilePath path(output); 4545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if (allow_folder) { 4555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) FileSelected(path, params); 4565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return; 4575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 4585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 4595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if (CallDirectoryExistsOnUIThread(path)) 4605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) FileNotSelected(params); 4615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) else 4625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) FileSelected(path, params); 4635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 4645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 4655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void SelectFileDialogImplKDE::OnSelectSingleFileDialogResponse( 466c5cede9ae108bb15f6b7a8aea21c7e1fefa2834cBen Murdoch XID parent, const std::string& output, int exit_code, void* params) { 467e5d81f57cb97b3b6b7fccc9c5610d21eb81db09dBen Murdoch DCHECK_CURRENTLY_ON(BrowserThread::UI); 468c5cede9ae108bb15f6b7a8aea21c7e1fefa2834cBen Murdoch parents_.erase(parent); 4695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) SelectSingleFileHelper(output, exit_code, params, false); 4705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 4715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 4725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void SelectFileDialogImplKDE::OnSelectSingleFolderDialogResponse( 473c5cede9ae108bb15f6b7a8aea21c7e1fefa2834cBen Murdoch XID parent, const std::string& output, int exit_code, void* params) { 474e5d81f57cb97b3b6b7fccc9c5610d21eb81db09dBen Murdoch DCHECK_CURRENTLY_ON(BrowserThread::UI); 475c5cede9ae108bb15f6b7a8aea21c7e1fefa2834cBen Murdoch parents_.erase(parent); 4765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) SelectSingleFileHelper(output, exit_code, params, true); 4775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 4785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 4795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void SelectFileDialogImplKDE::OnSelectMultiFileDialogResponse( 480c5cede9ae108bb15f6b7a8aea21c7e1fefa2834cBen Murdoch XID parent, const std::string& output, int exit_code, void* params) { 481e5d81f57cb97b3b6b7fccc9c5610d21eb81db09dBen Murdoch DCHECK_CURRENTLY_ON(BrowserThread::UI); 4825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) VLOG(1) << "[kdialog] MultiFileResponse: " << output; 4835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 484c5cede9ae108bb15f6b7a8aea21c7e1fefa2834cBen Murdoch parents_.erase(parent); 485c5cede9ae108bb15f6b7a8aea21c7e1fefa2834cBen Murdoch 4865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if (exit_code != 0 || output.empty()) { 4875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) FileNotSelected(params); 4885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return; 4895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 4905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 4915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) std::vector<std::string> filenames; 4925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) Tokenize(output, "\n", &filenames); 4932a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) std::vector<base::FilePath> filenames_fp; 4945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) for (std::vector<std::string>::iterator iter = filenames.begin(); 4955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) iter != filenames.end(); ++iter) { 4962a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) base::FilePath path(*iter); 4975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if (CallDirectoryExistsOnUIThread(path)) 4985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) continue; 4995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) filenames_fp.push_back(path); 5005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 5015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 5025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if (filenames_fp.empty()) { 5035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) FileNotSelected(params); 5045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return; 5055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 5065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) MultiFilesSelected(filenames_fp, params); 5075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 5085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 5095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} // namespace libgtk2ui 510