summaryrefslogtreecommitdiffstats
path: root/ui/file_manager
diff options
context:
space:
mode:
authorhirono <hirono@chromium.org>2014-11-24 23:15:05 -0800
committerCommit bot <commit-bot@chromium.org>2014-11-25 07:15:29 +0000
commitd8e90211c6285c4fa95b37c1c7ca6f3f373daf04 (patch)
treea5f75903b755a293ce68eef4e93c79c29bc6ddeb /ui/file_manager
parentb6f9d6f0d6be795162553d4164ab20e70ef5b2a7 (diff)
downloadchromium_src-d8e90211c6285c4fa95b37c1c7ca6f3f373daf04.zip
chromium_src-d8e90211c6285c4fa95b37c1c7ca6f3f373daf04.tar.gz
chromium_src-d8e90211c6285c4fa95b37c1c7ca6f3f373daf04.tar.bz2
Files.app: Move gear menu related lines to new GearMenu and GearMenuController class.
BUG=267281 TEST=None Review URL: https://codereview.chromium.org/751463002 Cr-Commit-Position: refs/heads/master@{#305596}
Diffstat (limited to 'ui/file_manager')
-rw-r--r--ui/file_manager/file_manager/common/js/externs.js16
-rw-r--r--ui/file_manager/file_manager/foreground/js/compiled_resources.gyp2
-rw-r--r--ui/file_manager/file_manager/foreground/js/directory_model.js18
-rw-r--r--ui/file_manager/file_manager/foreground/js/file_manager.js173
-rw-r--r--ui/file_manager/file_manager/foreground/js/file_manager_commands.js5
-rw-r--r--ui/file_manager/file_manager/foreground/js/gear_menu_controller.js107
-rw-r--r--ui/file_manager/file_manager/foreground/js/main_scripts.js2
-rw-r--r--ui/file_manager/file_manager/foreground/js/scan_controller.js27
-rw-r--r--ui/file_manager/file_manager/foreground/js/ui/file_manager_ui.js9
-rw-r--r--ui/file_manager/file_manager/foreground/js/ui/gear_menu.js125
-rw-r--r--ui/file_manager/file_manager/main.html2
11 files changed, 324 insertions, 162 deletions
diff --git a/ui/file_manager/file_manager/common/js/externs.js b/ui/file_manager/file_manager/common/js/externs.js
index 2943193..4eaf8f3 100644
--- a/ui/file_manager/file_manager/common/js/externs.js
+++ b/ui/file_manager/file_manager/common/js/externs.js
@@ -53,6 +53,22 @@ EntriesChangedEvent.prototype.kind;
/** @type {Array.<!Entry>} */
EntriesChangedEvent.prototype.entries;
+/**
+ * @constructor
+ * @extends {Event}
+ * @struct
+ * @suppress {checkStructDictInheritance}
+ */
+var DirectoryChangeEvent = function() {};
+
+/** @type {DirectoryEntry} */
+DirectoryChangeEvent.prototype.previousDirEntry;
+
+/** @type {DirectoryEntry|Object} */
+DirectoryChangeEvent.prototype.newDirEntry;
+
+/** @type {boolean} */
+DirectoryChangeEvent.prototype.volumeChanged;
/**
* @param {string} url
diff --git a/ui/file_manager/file_manager/foreground/js/compiled_resources.gyp b/ui/file_manager/file_manager/foreground/js/compiled_resources.gyp
index 48d8b3a..81aef9b 100644
--- a/ui/file_manager/file_manager/foreground/js/compiled_resources.gyp
+++ b/ui/file_manager/file_manager/foreground/js/compiled_resources.gyp
@@ -73,6 +73,7 @@
'./file_transfer_controller.js',
'./file_watcher.js',
'./folder_shortcuts_data_model.js',
+ './gear_menu_controller.js',
'./launch_param.js',
'./metadata/metadata_cache.js',
'./naming_controller.js',
@@ -93,6 +94,7 @@
'./ui/file_grid.js',
'./ui/file_manager_ui.js',
'./ui/file_table.js',
+ './ui/gear_menu.js',
'./ui/list_container.js',
'./ui/location_line.js',
'./ui/multi_profile_share_dialog.js',
diff --git a/ui/file_manager/file_manager/foreground/js/directory_model.js b/ui/file_manager/file_manager/foreground/js/directory_model.js
index 390c8d4..82f42ba 100644
--- a/ui/file_manager/file_manager/foreground/js/directory_model.js
+++ b/ui/file_manager/file_manager/foreground/js/directory_model.js
@@ -84,6 +84,17 @@ DirectoryModel.prototype.getFileListSelection = function() {
};
/**
+ * Obtains current volume information.
+ * @return {VolumeInfo}
+ */
+DirectoryModel.prototype.getCurrentVolumeInfo = function() {
+ var entry = this.getCurrentDirEntry();
+ if (!entry)
+ return null;
+ return this.volumeManager_.getVolumeInfo(entry);
+};
+
+/**
* @return {?VolumeManagerCommon.RootType} Root type of current root, or null if
* not found.
*/
@@ -899,10 +910,15 @@ DirectoryModel.prototype.changeDirectoryEntry = function(
// For tests that open the dialog to empty directories, everything
// is loaded at this point.
util.testSendMessage('directory-change-complete');
-
+ var previousVolumeInfo =
+ previousDirEntry ?
+ this.volumeManager_.getVolumeInfo(previousDirEntry) : null;
+ // VolumeInfo for dirEntry.
+ var currentVolumeInfo = this.getCurrentVolumeInfo();
var event = new Event('directory-changed');
event.previousDirEntry = previousDirEntry;
event.newDirEntry = dirEntry;
+ event.volumeChanged = previousVolumeInfo !== currentVolumeInfo;
this.dispatchEvent(event);
}.bind(this));
}.bind(this, this.changeDirectorySequence_));
diff --git a/ui/file_manager/file_manager/foreground/js/file_manager.js b/ui/file_manager/file_manager/foreground/js/file_manager.js
index 9674489..8da91a9 100644
--- a/ui/file_manager/file_manager/foreground/js/file_manager.js
+++ b/ui/file_manager/file_manager/foreground/js/file_manager.js
@@ -174,6 +174,13 @@ function FileManager() {
*/
this.bannersController_ = null;
+ /**
+ * Gear menu controller.
+ * @type {GearMenuController}
+ * @private
+ */
+ this.gearMenuController_ = null;
+
// --------------------------------------------------------------------------
// DOM elements.
@@ -199,18 +206,6 @@ function FileManager() {
this.document_ = null;
/**
- * The menu item to toggle "Do not use mobile data for sync".
- * @type {HTMLMenuItemElement}
- */
- this.syncButton = null;
-
- /**
- * The menu item to toggle "Show Google Docs files".
- * @type {HTMLMenuItemElement}
- */
- this.hostedButton = null;
-
- /**
* The menu item for doing an action.
* @type {HTMLMenuItemElement}
* @private
@@ -261,28 +256,6 @@ function FileManager() {
this.pressingTab_ = false;
/**
- * True while a user is pressing <Ctrl>.
- *
- * TODO(fukino): This key is used only for controlling gear menu, so it
- * should be moved to GearMenu class. crbug.com/366032.
- *
- * @type {boolean}
- * @private
- */
- this.pressingCtrl_ = false;
-
- /**
- * True if shown gear menu is in secret mode.
- *
- * TODO(fukino): The state of gear menu should be moved to GearMenu class.
- * crbug.com/366032.
- *
- * @type {boolean}
- * @private
- */
- this.isSecretGearMenuShown_ = false;
-
- /**
* The last clicked item in the file list.
* @type {HTMLLIElement}
* @private
@@ -575,18 +548,24 @@ var BOTTOM_MARGIN_FOR_PREVIEW_PANEL_PX = 52;
listBeingUpdated = null;
});
- this.initGearMenu_();
this.initCommands_();
+
assert(this.directoryModel_);
assert(this.spinnerController_);
assert(this.commandHandler);
assert(this.selectionHandler_);
+
this.scanController_ = new ScanController(
this.directoryModel_,
this.ui_.listContainer,
this.spinnerController_,
this.commandHandler,
this.selectionHandler_);
+ this.gearMenuController_ = new GearMenuController(
+ this.ui_.gearButton,
+ this.ui_.gearMenu,
+ this.directoryModel_,
+ this.commandHandler);
chrome.fileManagerPrivate.onPreferencesChanged.addListener(
this.onPreferencesChanged_.bind(this));
@@ -661,42 +640,6 @@ var BOTTOM_MARGIN_FOR_PREVIEW_PANEL_PX = 52;
};
/**
- * One-time initialization for the gear menu.
- * @private
- */
- FileManager.prototype.initGearMenu_ = function() {
- this.ui_.gearButton.addEventListener(
- 'menushow', this.onShowGearMenu_.bind(this));
- this.dialogDom_.querySelector('#gear-menu').menuItemSelector =
- 'menuitem, hr';
-
- this.syncButton.checkable = true;
- this.hostedButton.checkable = true;
- };
-
- FileManager.prototype.onShowGearMenu_ = function() {
- this.refreshRemainingSpace_(false); /* Without loading caption. */
-
- // If the menu is opened while CTRL key pressed, secret menu itemscan be
- // shown.
- this.isSecretGearMenuShown_ = this.pressingCtrl_;
-
- // Update view of drive-related settings.
- this.commandHandler.updateAvailability();
- this.document_.getElementById('drive-separator').hidden =
- !this.shouldShowDriveSettings();
-
- // Force to update the gear menu position.
- // TODO(hirono): Remove the workaround for the crbug.com/374093 after fixing
- // it.
- var gearMenu = this.document_.querySelector('#gear-menu');
- gearMenu.style.left = '';
- gearMenu.style.right = '';
- gearMenu.style.top = '';
- gearMenu.style.bottom = '';
- };
-
- /**
* One-time initialization of commands.
* @private
*/
@@ -979,13 +922,6 @@ var BOTTOM_MARGIN_FOR_PREVIEW_PANEL_PX = 52;
this.dialogContainer_ = /** @type {!HTMLDivElement} */
(this.dialogDom_.querySelector('.dialog-container'));
- this.syncButton = /** @type {!HTMLMenuItemElement} */
- (queryRequiredElement(this.dialogDom_,
- '#gear-menu-drive-sync-settings'));
- this.hostedButton = /** @type {!HTMLMenuItemElement} */
- (queryRequiredElement(this.dialogDom_,
- '#gear-menu-drive-hosted-settings'));
-
this.ui_.taskMenuButton.addEventListener('select',
this.onTaskItemClicked_.bind(this));
@@ -1664,21 +1600,6 @@ var BOTTOM_MARGIN_FOR_PREVIEW_PANEL_PX = 52;
var use12hourClock = !prefs.use24hourClock;
self.ui_.listContainer.table.setDateTimeFormat(use12hourClock);
self.refreshCurrentDirectoryMetadata_();
-
- if (prefs.cellularDisabled)
- self.syncButton.setAttribute('checked', '');
- else
- self.syncButton.removeAttribute('checked');
-
- if (self.hostedButton.hasAttribute('checked') ===
- prefs.hostedFilesDisabled && self.isOnDrive()) {
- self.directoryModel_.rescan(false);
- }
-
- if (!prefs.hostedFilesDisabled)
- self.hostedButton.setAttribute('checked', '');
- else
- self.hostedButton.removeAttribute('checked');
});
};
@@ -1912,67 +1833,6 @@ var BOTTOM_MARGIN_FOR_PREVIEW_PANEL_PX = 52;
};
/**
- * Update the gear menu.
- * @private
- */
- FileManager.prototype.updateGearMenu_ = function() {
- this.refreshRemainingSpace_(true); // Show loading caption.
- };
-
- /**
- * Refreshes space info of the current volume.
- * @param {boolean} showLoadingCaption Whether show loading caption or not.
- * @private
- */
- FileManager.prototype.refreshRemainingSpace_ = function(showLoadingCaption) {
- if (!this.currentVolumeInfo_)
- return;
-
- var volumeSpaceInfo = /** @type {!HTMLElement} */
- (this.dialogDom_.querySelector('#volume-space-info'));
- var volumeSpaceInfoSeparator = /** @type {!HTMLElement} */
- (this.dialogDom_.querySelector('#volume-space-info-separator'));
- var volumeSpaceInfoLabel = /** @type {!HTMLElement} */
- (this.dialogDom_.querySelector('#volume-space-info-label'));
- var volumeSpaceInnerBar = /** @type {!HTMLElement} */
- (this.dialogDom_.querySelector('#volume-space-info-bar'));
- var volumeSpaceOuterBar = /** @type {!HTMLElement} */
- (this.dialogDom_.querySelector('#volume-space-info-bar').parentNode);
-
- var currentVolumeInfo = this.currentVolumeInfo_;
-
- // TODO(mtomasz): Add support for remaining space indication for provided
- // file systems.
- if (currentVolumeInfo.volumeType ==
- VolumeManagerCommon.VolumeType.PROVIDED) {
- volumeSpaceInfo.hidden = true;
- volumeSpaceInfoSeparator.hidden = true;
- return;
- }
-
- volumeSpaceInfo.hidden = false;
- volumeSpaceInfoSeparator.hidden = false;
- volumeSpaceInnerBar.setAttribute('pending', '');
-
- if (showLoadingCaption) {
- volumeSpaceInfoLabel.innerText = str('WAITING_FOR_SPACE_INFO');
- volumeSpaceInnerBar.style.width = '100%';
- }
-
- chrome.fileManagerPrivate.getSizeStats(
- currentVolumeInfo.volumeId, function(result) {
- var volumeInfo = this.volumeManager_.getVolumeInfo(
- this.directoryModel_.getCurrentDirEntry());
- if (currentVolumeInfo !== this.currentVolumeInfo_)
- return;
- updateSpaceInfo(result,
- volumeSpaceInnerBar,
- volumeSpaceInfoLabel,
- volumeSpaceOuterBar);
- }.bind(this));
- };
-
- /**
* Update the UI when the current directory changes.
*
* @param {Event} event The directory-changed event.
@@ -1987,7 +1847,6 @@ var BOTTOM_MARGIN_FOR_PREVIEW_PANEL_PX = 52;
// If volume has changed, then update the gear menu.
if (oldCurrentVolumeInfo !== this.currentVolumeInfo_) {
- this.updateGearMenu_();
// If the volume has changed, and it was previously set, then do not
// close on unmount anymore.
if (oldCurrentVolumeInfo)
@@ -2097,8 +1956,6 @@ var BOTTOM_MARGIN_FOR_PREVIEW_PANEL_PX = 52;
FileManager.prototype.onKeyDown_ = function(event) {
if (event.keyCode === 9) // Tab
this.pressingTab_ = true;
- if (event.keyCode === 17) // Ctrl
- this.pressingCtrl_ = true;
if (event.srcElement === this.ui_.listContainer.renameInput) {
// Ignore keydown handler in the rename input box.
@@ -2130,8 +1987,6 @@ var BOTTOM_MARGIN_FOR_PREVIEW_PANEL_PX = 52;
FileManager.prototype.onKeyUp_ = function(event) {
if (event.keyCode === 9) // Tab
this.pressingTab_ = false;
- if (event.keyCode == 17) // Ctrl
- this.pressingCtrl_ = false;
};
/**
diff --git a/ui/file_manager/file_manager/foreground/js/file_manager_commands.js b/ui/file_manager/file_manager/foreground/js/file_manager_commands.js
index 3b1bf35..ada7592 100644
--- a/ui/file_manager/file_manager/foreground/js/file_manager_commands.js
+++ b/ui/file_manager/file_manager/foreground/js/file_manager_commands.js
@@ -564,7 +564,8 @@ CommandHandler.COMMANDS_['drive-sync-settings'] = /** @type {Command} */ ({
*/
execute: function(event, fileManager) {
// If checked, the sync is disabled.
- var nowCellularDisabled = fileManager.syncButton.hasAttribute('checked');
+ var nowCellularDisabled =
+ fileManager.ui.gearMenu.syncButton.hasAttribute('checked');
var changeInfo = {cellularDisabled: !nowCellularDisabled};
chrome.fileManagerPrivate.setPreferences(changeInfo);
},
@@ -592,7 +593,7 @@ CommandHandler.COMMANDS_['drive-hosted-settings'] = /** @type {Command} */ ({
execute: function(event, fileManager) {
// If checked, showing drive hosted files is enabled.
var nowHostedFilesEnabled =
- fileManager.hostedButton.hasAttribute('checked');
+ fileManager.ui.gearMenu.hostedButton.hasAttribute('checked');
var nowHostedFilesDisabled = !nowHostedFilesEnabled;
/*
var changeInfo = {hostedFilesDisabled: !nowHostedFilesDisabled};
diff --git a/ui/file_manager/file_manager/foreground/js/gear_menu_controller.js b/ui/file_manager/file_manager/foreground/js/gear_menu_controller.js
new file mode 100644
index 0000000..6cd92a7
--- /dev/null
+++ b/ui/file_manager/file_manager/foreground/js/gear_menu_controller.js
@@ -0,0 +1,107 @@
+// Copyright 2014 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.
+
+/**
+ * @param {!cr.ui.MenuButton} gearButton
+ * @param {!GearMenu} gearMenu
+ * @param {!DirectoryModel} directoryModel
+ * @param {!CommandHandler} commandHandler
+ * @constructor
+ * @struct
+ */
+function GearMenuController(
+ gearButton, gearMenu, directoryModel, commandHandler) {
+ /**
+ * @type {!GearMenu}
+ * @const
+ * @private
+ */
+ this.gearMenu_ = gearMenu;
+
+ /**
+ * @type {!DirectoryModel}
+ * @const
+ * @private
+ */
+ this.directoryModel_ = directoryModel;
+
+ /**
+ * @type {!CommandHandler}
+ * @const
+ * @private
+ */
+ this.commandHandler_ = commandHandler;
+
+ gearButton.addEventListener('menushow', this.onShowGearMenu_.bind(this));
+ directoryModel.addEventListener(
+ 'directory-changed', this.onDirectoryChanged_.bind(this));
+ chrome.fileManagerPrivate.onPreferencesChanged.addListener(
+ this.onPreferencesChanged_.bind(this));
+ this.onPreferencesChanged_();
+}
+
+/**
+ * @private
+ */
+GearMenuController.prototype.onShowGearMenu_ = function() {
+ this.refreshRemainingSpace_(false); /* Without loading caption. */
+
+ // Update view of drive-related settings.
+ this.commandHandler_.updateAvailability();
+ this.gearMenu_.driveSeparator.hidden = !this.directoryModel_.isOnDrive();
+};
+
+/**
+ * @param {Event} event
+ * @private
+ */
+GearMenuController.prototype.onDirectoryChanged_ = function(event) {
+ event = /** @type {DirectoryChangeEvent} */ (event);
+ if (event.volumeChanged)
+ this.refreshRemainingSpace_(true); // Show loading caption.
+};
+
+/**
+ * Refreshes space info of the current volume.
+ * @param {boolean} showLoadingCaption Whether show loading caption or not.
+ * @private
+ */
+GearMenuController.prototype.refreshRemainingSpace_ =
+ function(showLoadingCaption) {
+ var currentVolumeInfo = this.directoryModel_.getCurrentVolumeInfo();
+ if (!currentVolumeInfo)
+ return;
+
+ // TODO(mtomasz): Add support for remaining space indication for provided
+ // file systems.
+ if (currentVolumeInfo.volumeType == VolumeManagerCommon.VolumeType.PROVIDED) {
+ this.gearMenu_.setSpaceInfo(null, false);
+ return;
+ }
+
+ this.gearMenu_.setSpaceInfo(new Promise(function(fulfill) {
+ chrome.fileManagerPrivate.getSizeStats(currentVolumeInfo.volumeId, fulfill);
+ }), true);
+};
+
+/**
+ * Handles preferences change and updates menu.
+ * @private
+ */
+GearMenuController.prototype.onPreferencesChanged_ = function() {
+ chrome.fileManagerPrivate.getPreferences(function(prefs) {
+ if (chrome.runtime.lastError)
+ return;
+
+ if (prefs.cellularDisabled)
+ this.gearMenu_.syncButton.setAttribute('checked', '');
+ else
+ this.gearMenu_.syncButton.removeAttribute('checked');
+
+ if (!prefs.hostedFilesDisabled)
+ this.gearMenu_.hostedButton.setAttribute('checked', '');
+ else
+ this.gearMenu_.hostedButton.removeAttribute('checked');
+ }.bind(this));
+};
diff --git a/ui/file_manager/file_manager/foreground/js/main_scripts.js b/ui/file_manager/file_manager/foreground/js/main_scripts.js
index a208df2..2409906 100644
--- a/ui/file_manager/file_manager/foreground/js/main_scripts.js
+++ b/ui/file_manager/file_manager/foreground/js/main_scripts.js
@@ -93,6 +93,7 @@
//<include src="file_transfer_controller.js">
//<include src="file_watcher.js">
//<include src="folder_shortcuts_data_model.js">
+//<include src="gear_menu_controller.js">
//<include src="launch_param.js">
//<include src="metadata/metadata_cache.js">
//<include src="naming_controller.js">
@@ -113,6 +114,7 @@
//<include src="ui/file_grid.js">
//<include src="ui/file_manager_ui.js">
//<include src="ui/file_table.js">
+//<include src="ui/gear_menu.js">
//<include src="ui/list_container.js">
//<include src="ui/location_line.js">
//<include src="ui/multi_profile_share_dialog.js">
diff --git a/ui/file_manager/file_manager/foreground/js/scan_controller.js b/ui/file_manager/file_manager/foreground/js/scan_controller.js
index 2fdd881..49f12dc 100644
--- a/ui/file_manager/file_manager/foreground/js/scan_controller.js
+++ b/ui/file_manager/file_manager/foreground/js/scan_controller.js
@@ -82,6 +82,13 @@ function ScanController(
*/
this.scanUpdatedTimer_ = 0;
+ /**
+ * Last value of hosted files disabled.
+ * @type {?boolean}
+ * @private
+ */
+ this.lastHostedFilesDisabled_ = null;
+
this.directoryModel_.addEventListener(
'scan-started', this.onScanStarted_.bind(this));
this.directoryModel_.addEventListener(
@@ -94,6 +101,9 @@ function ScanController(
'scan-updated', this.onScanUpdated_.bind(this));
this.directoryModel_.addEventListener(
'rescan-completed', this.onRescanCompleted_.bind(this));
+ chrome.fileManagerPrivate.onPreferencesChanged.addListener(
+ this.onPreferencesChanged_.bind(this));
+ this.onPreferencesChanged_();
}
/**
@@ -221,3 +231,20 @@ ScanController.prototype.onScanCancelled_ = function() {
ScanController.prototype.onRescanCompleted_ = function() {
this.selectionHandler_.onFileSelectionChanged();
};
+
+/**
+ * Handles preferences change and starts rescan if needed.
+ * @private
+ */
+ScanController.prototype.onPreferencesChanged_ = function() {
+ chrome.fileManagerPrivate.getPreferences(function(prefs) {
+ if (chrome.runtime.lastError)
+ return;
+ if (this.lastHostedFilesDisabled_ !== null &&
+ this.lastHostedFilesDisabled_ !== prefs.hostedFilesDisabled &&
+ this.directoryModel_.isOnDrive()) {
+ this.directoryModel_.rescan(false);
+ }
+ this.lastHostedFilesDisabled_ = prefs.hostedFilesDisabled;
+ }.bind(this));
+};
diff --git a/ui/file_manager/file_manager/foreground/js/ui/file_manager_ui.js b/ui/file_manager/file_manager/foreground/js/ui/file_manager_ui.js
index 34c01a8..2eae7f6 100644
--- a/ui/file_manager/file_manager/foreground/js/ui/file_manager_ui.js
+++ b/ui/file_manager/file_manager/foreground/js/ui/file_manager_ui.js
@@ -123,6 +123,7 @@ function FileManagerUI(element, launchParam) {
/**
* Search box.
* @type {!SearchBox}
+ * @const
*/
this.searchBox = new SearchBox(
this.element_.querySelector('#search-box'),
@@ -132,17 +133,25 @@ function FileManagerUI(element, launchParam) {
/**
* Toggle-view button.
* @type {!Element}
+ * @const
*/
this.toggleViewButton = queryRequiredElement(this.element_, '#view-button');
/**
* The button to open gear menu.
* @type {!cr.ui.MenuButton}
+ * @const
*/
this.gearButton = FileManagerUI.queryDecoratedElement_(
'#gear-button', cr.ui.MenuButton);
/**
+ * @type {!GearMenu}
+ * @const
+ */
+ this.gearMenu = new GearMenu(this.gearButton.menu);
+
+ /**
* Directory tree.
* @type {DirectoryTree}
*/
diff --git a/ui/file_manager/file_manager/foreground/js/ui/gear_menu.js b/ui/file_manager/file_manager/foreground/js/ui/gear_menu.js
new file mode 100644
index 0000000..abbbabf
--- /dev/null
+++ b/ui/file_manager/file_manager/foreground/js/ui/gear_menu.js
@@ -0,0 +1,125 @@
+// Copyright 2014 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.
+
+/**
+ * @param {!HTMLElement} element
+ * @constructor
+ * @struct
+ */
+function GearMenu(element) {
+ /**
+ * @type {!HTMLMenuItemElement}
+ * @const
+ */
+ this.syncButton = /** @type {!HTMLMenuItemElement} */
+ (queryRequiredElement(element, '#gear-menu-drive-sync-settings'));
+
+ /**
+ * @type {!HTMLMenuItemElement}
+ * @const
+ */
+ this.hostedButton = /** @type {!HTMLMenuItemElement} */
+ (queryRequiredElement(element, '#gear-menu-drive-hosted-settings'));
+
+ /**
+ * @type {!HTMLElement}
+ * @const
+ */
+ this.driveSeparator = queryRequiredElement(element, '#drive-separator');
+
+ /**
+ * @type {!HTMLElement}
+ * @const
+ * @private
+ */
+ this.volumeSpaceInfo_ = queryRequiredElement(element, '#volume-space-info');
+
+ /**
+ * @type {!HTMLElement}
+ * @const
+ * @private
+ */
+ this.volumeSpaceInfoSeparator_ =
+ queryRequiredElement(element, '#volume-space-info-separator');
+
+ /**
+ * @type {!HTMLElement}
+ * @const
+ * @private
+ */
+ this.volumeSpaceInfoLabel_ =
+ queryRequiredElement(element, '#volume-space-info-label');
+
+ /**
+ * @type {!HTMLElement}
+ * @const
+ * @private
+ */
+ this.volumeSpaceInnerBar_ =
+ queryRequiredElement(element, '#volume-space-info-bar');
+
+ /**
+ * @type {!HTMLElement}
+ * @const
+ * @private
+ */
+ this.volumeSpaceOuterBar_ = assertInstanceof(
+ this.volumeSpaceInnerBar_.parentElement,
+ HTMLElement);
+
+ /**
+ * Volume space info.
+ * @type {Promise.<MountPointSizeStats>}
+ * @private
+ */
+ this.spaceInfoPromise_ = null;
+
+ // Initialize attributes.
+ element.menuItemSelector = 'menuitem, hr';
+ this.syncButton.checkable = true;
+ this.hostedButton.checkable = true;
+}
+
+/**
+ * @param {Promise.<MountPointSizeStats>} spaceInfoPromise Promise to be
+ * fulfilled with space info.
+ * @param {boolean} showLoadingCaption Whether show loading caption or not.
+ */
+GearMenu.prototype.setSpaceInfo = function(
+ spaceInfoPromise, showLoadingCaption) {
+ this.spaceInfoPromise_ = spaceInfoPromise;
+
+ if (!spaceInfoPromise) {
+ this.volumeSpaceInfo_.hidden = true;
+ this.volumeSpaceInfoSeparator_.hidden = true;
+ return;
+ }
+
+ this.volumeSpaceInfo_.hidden = false;
+ this.volumeSpaceInfoSeparator_.hidden = false;
+ this.volumeSpaceInnerBar_.setAttribute('pending', '');
+ if (showLoadingCaption) {
+ this.volumeSpaceInfoLabel_.innerText = str('WAITING_FOR_SPACE_INFO');
+ this.volumeSpaceInnerBar_.style.width = '100%';
+ }
+
+ spaceInfoPromise.then(function(spaceInfo) {
+ if (this.spaceInfoPromise_ != spaceInfoPromise)
+ return;
+ this.volumeSpaceInnerBar_.removeAttribute('pending');
+ if (spaceInfo) {
+ var sizeStr = util.bytesToString(spaceInfo.remainingSize);
+ this.volumeSpaceInfoLabel_.textContent = strf('SPACE_AVAILABLE', sizeStr);
+
+ var usedSpace = spaceInfo.totalSize - spaceInfo.remainingSize;
+ this.volumeSpaceInnerBar_.style.width =
+ (100 * usedSpace / spaceInfo.totalSize) + '%';
+
+ this.volumeSpaceOuterBar_.hidden = false;
+ } else {
+ this.volumeSpaceOuterBar_.hidden = true;
+ this.volumeSpaceInfoLabel_.textContent = str('FAILED_SPACE_INFO');
+ }
+ }.bind(this));
+};
diff --git a/ui/file_manager/file_manager/main.html b/ui/file_manager/file_manager/main.html
index 5b479d8..930efad 100644
--- a/ui/file_manager/file_manager/main.html
+++ b/ui/file_manager/file_manager/main.html
@@ -106,6 +106,7 @@
<script src="foreground/js/file_transfer_controller.js"></script>
<script src="foreground/js/file_watcher.js"></script>
<script src="foreground/js/folder_shortcuts_data_model.js"></script>
+ <script src="foreground/js/gear_menu_controller.js"></script>
<script src="foreground/js/launch_param.js"></script>
<script src="foreground/js/metadata/metadata_cache.js"></script>
<script src="foreground/js/naming_controller.js"></script>
@@ -126,6 +127,7 @@
<script src="foreground/js/ui/file_grid.js"></script>
<script src="foreground/js/ui/file_manager_ui.js"></script>
<script src="foreground/js/ui/file_table.js"></script>
+ <script src="foreground/js/ui/gear_menu.js"></script>
<script src="foreground/js/ui/list_container.js"></script>
<script src="foreground/js/ui/location_line.js"></script>
<script src="foreground/js/ui/multi_profile_share_dialog.js"></script>