summaryrefslogtreecommitdiffstats
path: root/chrome/browser/cocoa/download_item_mac.mm
blob: eca531689732ddf386d55037b2e6f37cd72e3eab (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
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
// Copyright (c) 2009 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.

#include "chrome/browser/cocoa/download_item_mac.h"

#include "base/basictypes.h"
#include "base/string_util.h"
#include "base/sys_string_conversions.h"
#import "chrome/browser/cocoa/download_shelf_controller.h"
#import "chrome/browser/cocoa/download_shelf_mac.h"
#import "chrome/browser/cocoa/download_shelf_view.h"
#include "chrome/browser/download/download_item_model.h"
#include "chrome/browser/download/download_manager.h"
#include "chrome/browser/download/download_shelf.h"

// A class for the chromium-side part of the download shelf context menu.

class DownloadShelfContextMenuMac : public DownloadShelfContextMenu {
 public:
  DownloadShelfContextMenuMac(BaseDownloadItemModel* model,
      DownloadShelfContextMenuBridge* bridge)
      : DownloadShelfContextMenu(model), bridge_(bridge) {
  }

  NSMenu* GetCocoaMenu();

  using DownloadShelfContextMenu::ExecuteItemCommand;

 private:
  DownloadShelfContextMenuBridge* bridge_;  // weak, owns us
};

NSMenu* DownloadShelfContextMenuMac::GetCocoaMenu() {
  // TODO(thakis): win/gtk show slightly different menus when the download is
  // in progress/done (mainly the first item)
  // TODO(thakis): this probably wants to be in a xib file or at least use
  // localized strings

  NSMenuItem* item;
  NSMenu* menu =
      [[[NSMenu alloc] initWithTitle:@"DownloadItemPopup"] autorelease];
  SEL action = @selector(performAction:);

  item = [menu addItemWithTitle:@"Open" action:action keyEquivalent:@""];
  //  [item addItemWithTitle:@"Open when complete" ...];  // In-progress text.
  [item setTag:OPEN_WHEN_COMPLETE];
  [item setTarget:bridge_];

  // TODO(thakis): Set correct checkbox state, make this a checkbox item
  item = [menu addItemWithTitle:@"Always open type"
                         action:action
                  keyEquivalent:@""];
  [item setTag:ALWAYS_OPEN_TYPE];
  [item setTarget:bridge_];

  [menu addItem:[NSMenuItem separatorItem]];

  item = [menu addItemWithTitle:@"Reveal in Finder"
                         action:action
                  keyEquivalent:@""];
  [item setTag:SHOW_IN_FOLDER];
  [item setTarget:bridge_];

  [menu addItem:[NSMenuItem separatorItem]];

  item = [menu addItemWithTitle:@"Cancel" action:action keyEquivalent:@""];
  [item setTag:CANCEL];
  [item setTarget:bridge_];

  return menu;
}


// A class for the cocoa side of the download shelf context menu.

@interface DownloadShelfContextMenuBridge : NSObject {
 @private
  scoped_ptr<DownloadShelfContextMenuMac> contextMenu_;
}

- (DownloadShelfContextMenuBridge*)initWithModel:(BaseDownloadItemModel*)model;
@end

@interface DownloadShelfContextMenuBridge(Private)
- (void)performAction:(id)sender;
- (NSMenu*)menu;
@end

@implementation DownloadShelfContextMenuBridge

- (DownloadShelfContextMenuBridge*)initWithModel:(BaseDownloadItemModel*)model {
  if ((self = [super init]) == nil) {
    return nil;
  }
  contextMenu_.reset(new DownloadShelfContextMenuMac(model, self));
  return self;
}

@end

@implementation DownloadShelfContextMenuBridge(Private)

- (void)performAction:(id)sender {
  contextMenu_->ExecuteItemCommand([sender tag]);
}

- (NSMenu*)menu {
  return contextMenu_->GetCocoaMenu();
}

@end


// DownloadItemMac -------------------------------------------------------------

DownloadItemMac::DownloadItemMac(BaseDownloadItemModel* download_model,
                                 NSRect frame,
                                 DownloadShelfController* parent)
    : download_model_(download_model), parent_(parent) {
  download_model_->download()->AddObserver(this);

  // TODO(thakis): The windows version of this does all kinds of things
  // (gratituous use of animation, special handling of dangerous downloads)
  // that we don't currently do.

  scoped_nsobject<NSPopUpButton> view(
      [[NSPopUpButton alloc] initWithFrame:frame pullsDown:YES]);
  [parent_ addDownloadItem:view.get()];

  // TODO(thakis): use filename eliding like gtk/windows versions
  std::wstring tmpname =
      download_model->download()->GetFileName().ToWStringHack();

  NSString* titleString = base::SysWideToNSString(tmpname);

  menu_.reset([[DownloadShelfContextMenuBridge alloc]
      initWithModel:download_model_.get()]);
  [view.get() setMenu:[menu_.get() menu]];

  [view.get() insertItemWithTitle:titleString atIndex:0];

  // TODO(thakis): Use file extension and iconForFileType. Currently, this
  // complains "<filename> is not a full path."
  [[view.get() itemAtIndex:0] setImage:
      [[NSWorkspace sharedWorkspace] iconForFile:titleString]];
}

DownloadItemMac::~DownloadItemMac() {
  download_model_->download()->RemoveObserver(this);
}

void DownloadItemMac::OnDownloadUpdated(DownloadItem* download) {
  DCHECK_EQ(download, download_model_->download());

  std::wstring status_text = download_model_->GetStatusText();
  // Remove the status text label.
  if (status_text.empty()) {
    // TODO(thakis): Once there is a status label, hide it here
    return;
  }

  // TODO(thakis): Set status_text as status label
}