summaryrefslogtreecommitdiffstats
path: root/chrome/browser/task_manager.cc
diff options
context:
space:
mode:
authorphajdan.jr@chromium.org <phajdan.jr@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98>2009-05-14 14:01:58 +0000
committerphajdan.jr@chromium.org <phajdan.jr@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98>2009-05-14 14:01:58 +0000
commit0da19221d7b32e3331ad50b2c9e642697e49ff05 (patch)
tree19e1cebe40b9e3a21ed67675769ba82284f42e99 /chrome/browser/task_manager.cc
parent81c78ac1f4407d0a9b1fa1dbb41916ababa225c7 (diff)
downloadchromium_src-0da19221d7b32e3331ad50b2c9e642697e49ff05.zip
chromium_src-0da19221d7b32e3331ad50b2c9e642697e49ff05.tar.gz
chromium_src-0da19221d7b32e3331ad50b2c9e642697e49ff05.tar.bz2
Extract Windows-specific parts of TaskManager.
- task_manager.cc compiles on POSIX - task_manager_unittest.cc passes on Linux - stub TaskManagerViewImpl for Linux (so that the unit test can pass) TEST=Task manager should not be obviously broken on Windows. http://crbug.com/11461 Review URL: http://codereview.chromium.org/115295 git-svn-id: svn://svn.chromium.org/chrome/trunk/src@16053 0039d316-1c4b-4281-b951-d872f2087c98
Diffstat (limited to 'chrome/browser/task_manager.cc')
-rw-r--r--chrome/browser/task_manager.cc515
1 files changed, 13 insertions, 502 deletions
diff --git a/chrome/browser/task_manager.cc b/chrome/browser/task_manager.cc
index b4c9bbe..43d328d 100644
--- a/chrome/browser/task_manager.cc
+++ b/chrome/browser/task_manager.cc
@@ -22,31 +22,10 @@
#include "grit/theme_resources.h"
#include "net/url_request/url_request.h"
#include "net/url_request/url_request_job.h"
-#include "views/accelerator.h"
-#include "views/background.h"
-#include "views/controls/button/native_button.h"
-#include "views/controls/link.h"
-#include "views/controls/menu/menu.h"
-#include "views/controls/table/group_table_view.h"
-#include "views/standard_layout.h"
-#include "views/widget/widget.h"
-#include "views/window/dialog_delegate.h"
-#include "views/window/window.h"
-
-// The task manager window default size.
-static const int kDefaultWidth = 460;
-static const int kDefaultHeight = 270;
// The delay between updates of the information (in ms).
static const int kUpdateTimeMs = 1000;
-// An id for the most important column, made sufficiently large so as not to
-// collide with anything else.
-static const int64 kNuthMagicNumber = 1737350766;
-static const int kBitMask = 0x7FFFFFFF;
-static const int kGoatsTeleportedColumn =
- (94024 * kNuthMagicNumber) & kBitMask;
-
template <class T>
static int ValueCompare(T value1, T value2) {
if (value1 < value2)
@@ -225,8 +204,8 @@ int TaskManagerModel::CompareValues(int row1, int row2, int col_id) const {
NOTREACHED();
}
}
- std::wstring title1 = GetResourceTitle(row1);
- std::wstring title2 = GetResourceTitle(row2);
+ string16 title1 = WideToUTF16(GetResourceTitle(row1));
+ string16 title2 = WideToUTF16(GetResourceTitle(row2));
UErrorCode compare_status = U_ZERO_ERROR;
UCollationResult compare_result = collator->compare(
static_cast<const UChar*>(title1.c_str()),
@@ -704,467 +683,6 @@ bool TaskManagerModel::GetProcessMetricsForRows(
}
////////////////////////////////////////////////////////////////////////////////
-// TaskManagerTableModel class
-////////////////////////////////////////////////////////////////////////////////
-
-class TaskManagerTableModel : public views::GroupTableModel,
- public TaskManagerModelObserver {
- public:
- explicit TaskManagerTableModel(TaskManagerModel* model)
- : model_(model),
- observer_(NULL) {
- model->SetObserver(this);
- }
- ~TaskManagerTableModel() {}
-
- // GroupTableModel.
- int RowCount();
- std::wstring GetText(int row, int column);
- SkBitmap GetIcon(int row);
- void GetGroupRangeForItem(int item, views::GroupRange* range);
- void SetObserver(views::TableModelObserver* observer);
- virtual int CompareValues(int row1, int row2, int column_id);
-
- // TaskManagerModelObserver.
- virtual void OnModelChanged();
- virtual void OnItemsChanged(int start, int length);
- virtual void OnItemsAdded(int start, int length);
- virtual void OnItemsRemoved(int start, int length);
-
- private:
- const TaskManagerModel* model_;
- views::TableModelObserver* observer_;
-};
-
-int TaskManagerTableModel::RowCount() {
- return model_->ResourceCount();
-}
-
-std::wstring TaskManagerTableModel::GetText(int row, int col_id) {
- switch (col_id) {
- case IDS_TASK_MANAGER_PAGE_COLUMN: // Process
- return model_->GetResourceTitle(row);
-
- case IDS_TASK_MANAGER_NET_COLUMN: // Net
- return model_->GetResourceNetworkUsage(row);
-
- case IDS_TASK_MANAGER_CPU_COLUMN: // CPU
- if (!model_->IsResourceFirstInGroup(row))
- return std::wstring();
- return model_->GetResourceCPUUsage(row);
-
- case IDS_TASK_MANAGER_PRIVATE_MEM_COLUMN: // Memory
- if (!model_->IsResourceFirstInGroup(row))
- return std::wstring();
- return model_->GetResourcePrivateMemory(row);
-
- case IDS_TASK_MANAGER_SHARED_MEM_COLUMN: // Memory
- if (!model_->IsResourceFirstInGroup(row))
- return std::wstring();
- return model_->GetResourceSharedMemory(row);
-
- case IDS_TASK_MANAGER_PHYSICAL_MEM_COLUMN: // Memory
- if (!model_->IsResourceFirstInGroup(row))
- return std::wstring();
- return model_->GetResourcePhysicalMemory(row);
-
- case IDS_TASK_MANAGER_PROCESS_ID_COLUMN:
- if (!model_->IsResourceFirstInGroup(row))
- return std::wstring();
- return model_->GetResourceProcessId(row);
-
- case kGoatsTeleportedColumn: // Goats Teleported!
- return model_->GetResourceGoatsTeleported(row);
-
- default:
- return model_->GetResourceStatsValue(row, col_id);
- }
-}
-
-SkBitmap TaskManagerTableModel::GetIcon(int row) {
- return model_->GetResourceIcon(row);
-}
-
-void TaskManagerTableModel::GetGroupRangeForItem(int item,
- views::GroupRange* range) {
- std::pair<int, int> range_pair = model_->GetGroupRangeForResource(item);
- range->start = range_pair.first;
- range->length = range_pair.second;
-}
-
-void TaskManagerTableModel::SetObserver(views::TableModelObserver* observer) {
- observer_ = observer;
-}
-
-int TaskManagerTableModel::CompareValues(int row1, int row2, int column_id) {
- return model_->CompareValues(row1, row2, column_id);
-}
-
-void TaskManagerTableModel::OnModelChanged() {
- if (observer_)
- observer_->OnModelChanged();
-}
-
-void TaskManagerTableModel::OnItemsChanged(int start, int length) {
- if (observer_)
- observer_->OnItemsChanged(start, length);
-}
-
-void TaskManagerTableModel::OnItemsAdded(int start, int length) {
- if (observer_)
- observer_->OnItemsAdded(start, length);
-}
-
-void TaskManagerTableModel::OnItemsRemoved(int start, int length) {
- if (observer_)
- observer_->OnItemsRemoved(start, length);
-}
-
-////////////////////////////////////////////////////////////////////////////////
-// TaskManagerContents class
-//
-// The view containing the different widgets.
-//
-////////////////////////////////////////////////////////////////////////////////
-
-class TaskManagerContents : public views::View,
- public views::ButtonListener,
- public views::DialogDelegate,
- public views::TableViewObserver,
- public views::LinkController,
- public views::ContextMenuController,
- public Menu::Delegate {
- public:
- TaskManagerContents(TaskManager* task_manager,
- TaskManagerModel* model);
- virtual ~TaskManagerContents();
-
- void Init(TaskManagerModel* model);
- virtual void Layout();
- virtual gfx::Size GetPreferredSize();
- virtual void ViewHierarchyChanged(bool is_add, views::View* parent,
- views::View* child);
- void GetSelection(std::vector<int>* selection);
- void GetFocused(std::vector<int>* focused);
-
- // ButtonListener implementation.
- virtual void ButtonPressed(views::Button* sender);
-
- // views::DialogDelegate
- virtual bool CanResize() const;
- virtual bool CanMaximize() const;
- virtual bool IsAlwaysOnTop() const;
- virtual bool HasAlwaysOnTopMenu() const;
- virtual std::wstring GetWindowTitle() const;
- virtual std::wstring GetWindowName() const;
- virtual int GetDialogButtons() const;
- virtual void WindowClosing();
- virtual void DeleteDelegate();
- virtual views::View* GetContentsView();
-
- // views::TableViewObserver implementation.
- virtual void OnSelectionChanged();
- virtual void OnDoubleClick();
- virtual void OnKeyDown(unsigned short virtual_keycode);
-
- // views::LinkController implementation.
- virtual void LinkActivated(views::Link* source, int event_flags);
-
- // Called by the column picker to pick up any new stat counters that
- // may have appeared since last time.
- void UpdateStatsCounters();
-
- // Menu::Delegate
- virtual void ShowContextMenu(views::View* source,
- int x,
- int y,
- bool is_mouse_gesture);
- virtual bool IsItemChecked(int id) const;
- virtual void ExecuteCommand(int id);
-
- private:
- scoped_ptr<views::NativeButton> kill_button_;
- scoped_ptr<views::Link> about_memory_link_;
- views::GroupTableView* tab_table_;
-
- TaskManager* task_manager_;
-
- // all possible columns, not necessarily visible
- std::vector<views::TableColumn> columns_;
-
- scoped_ptr<TaskManagerTableModel> table_model_;
-
- DISALLOW_EVIL_CONSTRUCTORS(TaskManagerContents);
-};
-
-TaskManagerContents::TaskManagerContents(TaskManager* task_manager,
- TaskManagerModel* model)
- : task_manager_(task_manager) {
- Init(model);
-}
-
-TaskManagerContents::~TaskManagerContents() {
-}
-
-void TaskManagerContents::Init(TaskManagerModel* model) {
- table_model_.reset(new TaskManagerTableModel(model));
-
- columns_.push_back(views::TableColumn(IDS_TASK_MANAGER_PAGE_COLUMN,
- views::TableColumn::LEFT, -1, 1));
- columns_.back().sortable = true;
- columns_.push_back(views::TableColumn(IDS_TASK_MANAGER_PHYSICAL_MEM_COLUMN,
- views::TableColumn::RIGHT, -1, 0));
- columns_.back().sortable = true;
- columns_.push_back(views::TableColumn(IDS_TASK_MANAGER_SHARED_MEM_COLUMN,
- views::TableColumn::RIGHT, -1, 0));
- columns_.back().sortable = true;
- columns_.push_back(views::TableColumn(IDS_TASK_MANAGER_PRIVATE_MEM_COLUMN,
- views::TableColumn::RIGHT, -1, 0));
- columns_.back().sortable = true;
- columns_.push_back(views::TableColumn(IDS_TASK_MANAGER_CPU_COLUMN,
- views::TableColumn::RIGHT, -1, 0));
- columns_.back().sortable = true;
- columns_.push_back(views::TableColumn(IDS_TASK_MANAGER_NET_COLUMN,
- views::TableColumn::RIGHT, -1, 0));
- columns_.back().sortable = true;
- columns_.push_back(views::TableColumn(IDS_TASK_MANAGER_PROCESS_ID_COLUMN,
- views::TableColumn::RIGHT, -1, 0));
- columns_.back().sortable = true;
-
- tab_table_ = new views::GroupTableView(table_model_.get(), columns_,
- views::ICON_AND_TEXT, false, true,
- true);
-
- // Hide some columns by default
- tab_table_->SetColumnVisibility(IDS_TASK_MANAGER_PROCESS_ID_COLUMN, false);
- tab_table_->SetColumnVisibility(IDS_TASK_MANAGER_SHARED_MEM_COLUMN, false);
- tab_table_->SetColumnVisibility(IDS_TASK_MANAGER_PRIVATE_MEM_COLUMN, false);
-
- UpdateStatsCounters();
- views::TableColumn col(kGoatsTeleportedColumn, L"Goats Teleported",
- views::TableColumn::RIGHT, -1, 0);
- col.sortable = true;
- columns_.push_back(col);
- tab_table_->AddColumn(col);
- tab_table_->SetObserver(this);
- SetContextMenuController(this);
- kill_button_.reset(new views::NativeButton(
- this, l10n_util::GetString(IDS_TASK_MANAGER_KILL)));
- kill_button_->AddAccelerator(views::Accelerator('E', false, false, false));
- kill_button_->SetAccessibleKeyboardShortcut(L"E");
- about_memory_link_.reset(new views::Link(
- l10n_util::GetString(IDS_TASK_MANAGER_ABOUT_MEMORY_LINK)));
- about_memory_link_->SetController(this);
-
- AddChildView(tab_table_);
-
- // Makes sure our state is consistent.
- OnSelectionChanged();
-}
-
-void TaskManagerContents::UpdateStatsCounters() {
- StatsTable* stats = StatsTable::current();
- if (stats != NULL) {
- int max = stats->GetMaxCounters();
- // skip the first row (it's header data)
- for (int i = 1; i < max; i++) {
- const char* row = stats->GetRowName(i);
- if (row != NULL && row[0] != '\0' && !tab_table_->HasColumn(i)) {
- // TODO(erikkay): Use l10n to get display names for stats. Right
- // now we're just displaying the internal counter name. Perhaps
- // stat names not in the string table would be filtered out.
- // TODO(erikkay): Width is hard-coded right now, so many column
- // names are clipped.
- views::TableColumn col(i, ASCIIToWide(row), views::TableColumn::RIGHT,
- 90, 0);
- col.sortable = true;
- columns_.push_back(col);
- tab_table_->AddColumn(col);
- }
- }
- }
-}
-
-void TaskManagerContents::ViewHierarchyChanged(bool is_add,
- views::View* parent,
- views::View* child) {
- // Since we want the Kill button and the Memory Details link to show up in
- // the same visual row as the close button, which is provided by the
- // framework, we must add the buttons to the non-client view, which is the
- // parent of this view. Similarly, when we're removed from the view
- // hierarchy, we must take care to clean up those items as well.
- if (child == this) {
- if (is_add) {
- parent->AddChildView(kill_button_.get());
- parent->AddChildView(about_memory_link_.get());
- } else {
- parent->RemoveChildView(kill_button_.get());
- parent->RemoveChildView(about_memory_link_.get());
- // Note that these items aren't deleted here, since this object is owned
- // by the TaskManager, whose lifetime surpasses the window, and the next
- // time we are inserted into a window these items will need to be valid.
- }
- }
-}
-
-void TaskManagerContents::Layout() {
- // kPanelHorizMargin is too big.
- const int kTableButtonSpacing = 12;
-
- gfx::Size size = kill_button_->GetPreferredSize();
- int prefered_width = size.width();
- int prefered_height = size.height();
-
- tab_table_->SetBounds(x() + kPanelHorizMargin,
- y() + kPanelVertMargin,
- width() - 2 * kPanelHorizMargin,
- height() - 2 * kPanelVertMargin - prefered_height);
-
- // y-coordinate of button top left.
- gfx::Rect parent_bounds = GetParent()->GetLocalBounds(false);
- int y_buttons = parent_bounds.bottom() - prefered_height - kButtonVEdgeMargin;
-
- kill_button_->SetBounds(x() + width() - prefered_width - kPanelHorizMargin,
- y_buttons,
- prefered_width,
- prefered_height);
-
- size = about_memory_link_->GetPreferredSize();
- int link_prefered_width = size.width();
- int link_prefered_height = size.height();
- // center between the two buttons horizontally, and line up with
- // bottom of buttons vertically.
- int link_y_offset = std::max(0, prefered_height - link_prefered_height) / 2;
- about_memory_link_->SetBounds(
- x() + kPanelHorizMargin,
- y_buttons + prefered_height - link_prefered_height - link_y_offset,
- link_prefered_width,
- link_prefered_height);
-}
-
-gfx::Size TaskManagerContents::GetPreferredSize() {
- return gfx::Size(kDefaultWidth, kDefaultHeight);
-}
-
-void TaskManagerContents::GetSelection(std::vector<int>* selection) {
- DCHECK(selection);
- for (views::TableSelectionIterator iter = tab_table_->SelectionBegin();
- iter != tab_table_->SelectionEnd(); ++iter) {
- // The TableView returns the selection starting from the end.
- selection->insert(selection->begin(), *iter);
- }
-}
-
-void TaskManagerContents::GetFocused(std::vector<int>* focused) {
- DCHECK(focused);
- int row_count = tab_table_->RowCount();
- for (int i = 0; i < row_count; ++i) {
- // The TableView returns the selection starting from the end.
- if (tab_table_->ItemHasTheFocus(i))
- focused->insert(focused->begin(), i);
- }
-}
-
-// ButtonListener implementation.
-void TaskManagerContents::ButtonPressed(views::Button* sender) {
- if (sender == kill_button_.get())
- task_manager_->KillSelectedProcesses();
-}
-
-// DialogDelegate implementation.
-bool TaskManagerContents::CanResize() const {
- return true;
-}
-
-bool TaskManagerContents::CanMaximize() const {
- return true;
-}
-
-bool TaskManagerContents::IsAlwaysOnTop() const {
- return true;
-}
-
-bool TaskManagerContents::HasAlwaysOnTopMenu() const {
- return true;
-};
-
-std::wstring TaskManagerContents::GetWindowTitle() const {
- return l10n_util::GetString(IDS_TASK_MANAGER_TITLE);
-}
-
-std::wstring TaskManagerContents::GetWindowName() const {
- return prefs::kTaskManagerWindowPlacement;
-}
-
-int TaskManagerContents::GetDialogButtons() const {
- return MessageBoxFlags::DIALOGBUTTON_NONE;
-}
-
-void TaskManagerContents::WindowClosing() {
- // Remove the view from its parent to trigger the contents'
- // ViewHierarchyChanged notification to unhook the extra buttons from the
- // non-client view.
- GetParent()->RemoveChildView(this);
- task_manager_->Close();
-}
-
-void TaskManagerContents::DeleteDelegate() {
- ReleaseWindow();
-}
-
-views::View* TaskManagerContents::GetContentsView() {
- return this;
-}
-
-// views::TableViewObserver implementation.
-void TaskManagerContents::OnSelectionChanged() {
- kill_button_->SetEnabled(!task_manager_->BrowserProcessIsSelected() &&
- tab_table_->SelectedRowCount() > 0);
-}
-
-void TaskManagerContents::OnDoubleClick() {
- task_manager_->ActivateFocusedTab();
-}
-
-void TaskManagerContents::OnKeyDown(unsigned short virtual_keycode) {
- if (virtual_keycode == VK_RETURN)
- task_manager_->ActivateFocusedTab();
-}
-
-// views::LinkController implementation
-void TaskManagerContents::LinkActivated(views::Link* source,
- int event_flags) {
- DCHECK(source == about_memory_link_);
- Browser* browser = BrowserList::GetLastActive();
- DCHECK(browser);
- browser->OpenURL(GURL("about:memory"), GURL(), NEW_FOREGROUND_TAB,
- PageTransition::LINK);
- // In case the browser window is minimzed, show it.
- browser->window()->Show();
-}
-
-void TaskManagerContents::ShowContextMenu(views::View* source,
- int x,
- int y,
- bool is_mouse_gesture) {
- UpdateStatsCounters();
- Menu menu(this, Menu::TOPLEFT, source->GetWidget()->GetNativeView());
- for (std::vector<views::TableColumn>::iterator i =
- columns_.begin(); i != columns_.end(); ++i) {
- menu.AppendMenuItem(i->id, i->title, Menu::CHECKBOX);
- }
- menu.RunMenuAt(x, y);
-}
-
-bool TaskManagerContents::IsItemChecked(int id) const {
- return tab_table_->IsColumnVisible(id);
-}
-
-void TaskManagerContents::ExecuteCommand(int id) {
- tab_table_->SetColumnVisibility(id, !tab_table_->IsColumnVisible(id));
-}
-
-////////////////////////////////////////////////////////////////////////////////
// TaskManager class
////////////////////////////////////////////////////////////////////////////////
@@ -1173,9 +691,8 @@ void TaskManager::RegisterPrefs(PrefService* prefs) {
prefs->RegisterDictionaryPref(prefs::kTaskManagerWindowPlacement);
}
-TaskManager::TaskManager() {
- model_ = new TaskManagerModel(this);
- contents_.reset(new TaskManagerContents(this, model_.get()));
+TaskManager::TaskManager() : model_(new TaskManagerModel(this)) {
+ Init();
}
TaskManager::~TaskManager() {
@@ -1184,14 +701,7 @@ TaskManager::~TaskManager() {
// static
void TaskManager::Open() {
TaskManager* task_manager = GetInstance();
- if (task_manager->contents_->window()) {
- task_manager->contents_->window()->Activate();
- } else {
- views::Window::CreateChromeWindow(NULL, gfx::Rect(),
- task_manager->contents_.get());
- task_manager->model_->StartUpdating();
- task_manager->contents_->window()->Show();
- }
+ task_manager->view_->OpenWindow();
}
void TaskManager::Close() {
@@ -1200,17 +710,18 @@ void TaskManager::Close() {
}
bool TaskManager::BrowserProcessIsSelected() {
- if (!contents_.get())
+ if (!view_.get())
return false;
std::vector<int> selection;
- contents_->GetSelection(&selection);
+ view_->GetSelection(&selection);
for (std::vector<int>::const_iterator iter = selection.begin();
iter != selection.end(); ++iter) {
// If some of the selection is out of bounds, ignore. This may happen when
// killing a process that manages several pages.
if (*iter >= model_->ResourceCount())
continue;
- if (model_->GetResourceProcessHandle(*iter) == GetCurrentProcess())
+ if (model_->GetResourceProcessHandle(*iter) ==
+ base::GetCurrentProcessHandle())
return true;
}
return false;
@@ -1218,20 +729,20 @@ bool TaskManager::BrowserProcessIsSelected() {
void TaskManager::KillSelectedProcesses() {
std::vector<int> selection;
- contents_->GetSelection(&selection);
+ view_->GetSelection(&selection);
for (std::vector<int>::const_iterator iter = selection.begin();
iter != selection.end(); ++iter) {
base::ProcessHandle process = model_->GetResourceProcessHandle(*iter);
DCHECK(process);
- if (process == GetCurrentProcess())
+ if (process == base::GetCurrentProcessHandle())
continue;
- TerminateProcess(process, 0);
+ base::KillProcess(process, base::PROCESS_END_KILLED_BY_USER, false);
}
}
void TaskManager::ActivateFocusedTab() {
std::vector<int> focused;
- contents_->GetFocused(&focused);
+ view_->GetFocused(&focused);
int focused_size = static_cast<int>(focused.size());
DCHECK(focused_size == 1);