1 // Copyright 2014 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 "chrome/utility/shell_handler_win.h" 6 7 #include <commdlg.h> 8 9 #include "base/files/file_path.h" 10 #include "base/memory/scoped_ptr.h" 11 #include "chrome/common/chrome_utility_messages.h" 12 #include "content/public/utility/utility_thread.h" 13 #include "ui/base/win/open_file_name_win.h" 14 #include "ui/base/win/shell.h" 15 16 ShellHandler::ShellHandler() {} 17 ShellHandler::~ShellHandler() {} 18 19 bool ShellHandler::OnMessageReceived(const IPC::Message& message) { 20 bool handled = true; 21 IPC_BEGIN_MESSAGE_MAP(ShellHandler, message) 22 IPC_MESSAGE_HANDLER(ChromeUtilityMsg_OpenItemViaShell, 23 OnOpenItemViaShell) 24 IPC_MESSAGE_HANDLER(ChromeUtilityMsg_GetOpenFileName, 25 OnGetOpenFileName) 26 IPC_MESSAGE_HANDLER(ChromeUtilityMsg_GetSaveFileName, 27 OnGetSaveFileName) 28 IPC_MESSAGE_UNHANDLED(handled = false) 29 IPC_END_MESSAGE_MAP() 30 return handled; 31 } 32 33 void ShellHandler::OnOpenItemViaShell(const base::FilePath& full_path) { 34 ui::win::OpenItemViaShell(full_path); 35 } 36 37 void ShellHandler::OnGetOpenFileName( 38 HWND owner, 39 DWORD flags, 40 const GetOpenFileNameFilter& filter, 41 const base::FilePath& initial_directory, 42 const base::FilePath& filename) { 43 ui::win::OpenFileName open_file_name(owner, flags); 44 open_file_name.SetInitialSelection(initial_directory, filename); 45 open_file_name.SetFilters(filter); 46 47 base::FilePath directory; 48 std::vector<base::FilePath> filenames; 49 50 if (::GetOpenFileName(open_file_name.GetOPENFILENAME())) 51 open_file_name.GetResult(&directory, &filenames); 52 53 if (filenames.size()) { 54 content::UtilityThread::Get()->Send( 55 new ChromeUtilityHostMsg_GetOpenFileName_Result(directory, filenames)); 56 } else { 57 content::UtilityThread::Get()->Send( 58 new ChromeUtilityHostMsg_GetOpenFileName_Failed()); 59 } 60 } 61 62 void ShellHandler::OnGetSaveFileName( 63 const ChromeUtilityMsg_GetSaveFileName_Params& params) { 64 ui::win::OpenFileName open_file_name(params.owner, params.flags); 65 open_file_name.SetInitialSelection(params.initial_directory, 66 params.suggested_filename); 67 open_file_name.SetFilters(params.filters); 68 open_file_name.GetOPENFILENAME()->nFilterIndex = 69 params.one_based_filter_index; 70 open_file_name.GetOPENFILENAME()->lpstrDefExt = 71 params.default_extension.c_str(); 72 73 open_file_name.MaybeInstallWindowPositionHookForSaveAsOnXP(); 74 75 if (::GetSaveFileName(open_file_name.GetOPENFILENAME())) { 76 content::UtilityThread::Get()->Send( 77 new ChromeUtilityHostMsg_GetSaveFileName_Result( 78 base::FilePath(open_file_name.GetOPENFILENAME()->lpstrFile), 79 open_file_name.GetOPENFILENAME()->nFilterIndex)); 80 return; 81 } 82 83 // Zero means the dialog was closed, otherwise we had an error. 84 DWORD error_code = ::CommDlgExtendedError(); 85 if (error_code != 0) 86 NOTREACHED() << "GetSaveFileName failed with code: " << error_code; 87 88 content::UtilityThread::Get()->Send( 89 new ChromeUtilityHostMsg_GetSaveFileName_Failed()); 90 } 91