summaryrefslogtreecommitdiffstats
path: root/chrome/browser/file_select_helper.h
blob: 149962ddd397f2e211773ff33692ae3bb95b7372 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
// Copyright (c) 2011 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.

#ifndef CHROME_BROWSER_FILE_SELECT_HELPER_H_
#define CHROME_BROWSER_FILE_SELECT_HELPER_H_
#pragma once

#include <map>
#include <vector>

#include "base/compiler_specific.h"
#include "chrome/browser/ui/shell_dialogs.h"
#include "content/browser/tab_contents/tab_contents_observer.h"
#include "content/common/notification_observer.h"
#include "content/common/notification_registrar.h"
#include "net/base/directory_lister.h"

class Profile;
class RenderViewHost;
struct ViewHostMsg_RunFileChooser_Params;


// This class handles file-selection requests coming from WebUI elements
// (via the ExtensionHost class). It implements both the initialisation
// and listener functions for file-selection dialogs.
class FileSelectHelper
    : public SelectFileDialog::Listener,
      public NotificationObserver {
 public:
  explicit FileSelectHelper(Profile* profile);
  virtual ~FileSelectHelper();

  // Show the file chooser dialog.
  void RunFileChooser(RenderViewHost* render_view_host,
                      TabContents* tab_contents,
                      const ViewHostMsg_RunFileChooser_Params& params);

  // Enumerates all the files in directory.
  void EnumerateDirectory(int request_id,
                          RenderViewHost* render_view_host,
                          const FilePath& path);

 private:
  // Utility class which can listen for directory lister events and relay
  // them to the main object with the correct tracking id.
  class DirectoryListerDispatchDelegate
      : public net::DirectoryLister::DirectoryListerDelegate {
   public:
    DirectoryListerDispatchDelegate(FileSelectHelper* parent, int id)
        : parent_(parent),
          id_(id) {}
    virtual ~DirectoryListerDispatchDelegate() {}
    virtual void OnListFile(
        const net::DirectoryLister::DirectoryListerData& data) {
      parent_->OnListFile(id_, data);
    }
    virtual void OnListDone(int error) {
      parent_->OnListDone(id_, error);
    }
   private:
    // This FileSelectHelper owns this object.
    FileSelectHelper* parent_;
    int id_;

    DISALLOW_COPY_AND_ASSIGN(DirectoryListerDispatchDelegate);
  };

  // SelectFileDialog::Listener overrides.
  virtual void FileSelected(
      const FilePath& path, int index, void* params) OVERRIDE;
  virtual void MultiFilesSelected(const std::vector<FilePath>& files,
                                  void* params) OVERRIDE;
  virtual void FileSelectionCanceled(void* params) OVERRIDE;

  // NotificationObserver overrides.
  virtual void Observe(int type,
                       const NotificationSource& source,
                       const NotificationDetails& details) OVERRIDE;

  // Kicks off a new directory enumeration.
  void StartNewEnumeration(const FilePath& path,
                           int request_id,
                           RenderViewHost* render_view_host);

  // Callbacks from directory enumeration.
  virtual void OnListFile(
      int id,
      const net::DirectoryLister::DirectoryListerData& data);
  virtual void OnListDone(int id, int error);

  // Helper method to get allowed extensions for select file dialog from
  // the specified accept types as defined in the spec:
  //   http://whatwg.org/html/number-state.html#attr-input-accept
  SelectFileDialog::FileTypeInfo* GetFileTypesFromAcceptType(
      const string16& accept_types);

  // Profile used to set/retrieve the last used directory.
  Profile* profile_;

  // The RenderViewHost for the page showing a file dialog (may only be one
  // such dialog).
  RenderViewHost* render_view_host_;

  // Dialog box used for choosing files to upload from file form fields.
  scoped_refptr<SelectFileDialog> select_file_dialog_;

  // The type of file dialog last shown.
  SelectFileDialog::Type dialog_type_;

  // Maintain a list of active directory enumerations.  These could come from
  // the file select dialog or from drag-and-drop of directories, so there could
  // be more than one going on at a time.
  struct ActiveDirectoryEnumeration;
  std::map<int, ActiveDirectoryEnumeration*> directory_enumerations_;

  // Registrar for notifications regarding our RenderViewHost.
  NotificationRegistrar notification_registrar_;

  DISALLOW_COPY_AND_ASSIGN(FileSelectHelper);
};

#endif  // CHROME_BROWSER_FILE_SELECT_HELPER_H_