diff options
author | dgozman@chromium.org <dgozman@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98> | 2011-12-01 14:35:59 +0000 |
---|---|---|
committer | dgozman@chromium.org <dgozman@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98> | 2011-12-01 14:35:59 +0000 |
commit | 5f214a7915a163b2732d71371d45a5574c57e152 (patch) | |
tree | 343b4d11279b0d8c68ee2f7f55fa472260afc1f8 /chrome/browser | |
parent | 0c63f4630f3b38d9c8b4f620a23633ddac1026c6 (diff) | |
download | chromium_src-5f214a7915a163b2732d71371d45a5574c57e152.zip chromium_src-5f214a7915a163b2732d71371d45a5574c57e152.tar.gz chromium_src-5f214a7915a163b2732d71371d45a5574c57e152.tar.bz2 |
[filebrowser] Support renaming in Gallery.
BUG=chromium-os:23434,chromium-os:23435
TEST=See bug.
Review URL: http://codereview.chromium.org/8745013
git-svn-id: svn://svn.chromium.org/chrome/trunk/src@112462 0039d316-1c4b-4281-b951-d872f2087c98
Diffstat (limited to 'chrome/browser')
5 files changed, 178 insertions, 24 deletions
diff --git a/chrome/browser/extensions/extension_file_browser_private_api.cc b/chrome/browser/extensions/extension_file_browser_private_api.cc index 7c36dae..e844488 100644 --- a/chrome/browser/extensions/extension_file_browser_private_api.cc +++ b/chrome/browser/extensions/extension_file_browser_private_api.cc @@ -1571,6 +1571,7 @@ bool FileDialogStringsFunction::RunImpl() { SET_STRING(IDS_FILE_BROWSER, GALLERY_ROTATE_RIGHT); SET_STRING(IDS_FILE_BROWSER, GALLERY_UNDO); SET_STRING(IDS_FILE_BROWSER, GALLERY_REDO); + SET_STRING(IDS_FILE_BROWSER, GALLERY_FILE_EXISTS); SET_STRING(IDS_FILE_BROWSER, CONFIRM_OVERWRITE_FILE); SET_STRING(IDS_FILE_BROWSER, FILE_ALREADY_EXISTS); diff --git a/chrome/browser/resources/file_manager/js/image_editor/gallery.css b/chrome/browser/resources/file_manager/js/image_editor/gallery.css index 753bb78..6b2edb2 100644 --- a/chrome/browser/resources/file_manager/js/image_editor/gallery.css +++ b/chrome/browser/resources/file_manager/js/image_editor/gallery.css @@ -226,6 +226,29 @@ body { opacity: 0.2; } +/* Filename */ + +.gallery .filename-spacer { + padding: 0 10px; + display: -webkit-box; + -webkit-box-orient: horizontal; + -webkit-box-align: center; +} + +.gallery .filename-spacer > input { + background-color: transparent; + color: white; + width: 40em; + border: none; + outline: none; +} + +.gallery .filename-spacer > input:focus { + background-color: rgba(48, 48, 48, 0.75); + border-right: 1px solid white; + border-bottom: 1px solid white; +} + /* Thumbnails */ .gallery .ribbon-spacer { diff --git a/chrome/browser/resources/file_manager/js/image_editor/gallery.js b/chrome/browser/resources/file_manager/js/image_editor/gallery.js index 3caf971..8af4942 100644 --- a/chrome/browser/resources/file_manager/js/image_editor/gallery.js +++ b/chrome/browser/resources/file_manager/js/image_editor/gallery.js @@ -37,6 +37,7 @@ function Gallery(container, closeCallback, metadataProvider, shareActions, this.onFadeTimeoutBound_ = this.onFadeTimeout_.bind(this); this.fadeTimeoutId_ = null; this.mouseOverTool_ = false; + this.imageChanges_ = 0; this.initDom_(shareActions); } @@ -96,6 +97,18 @@ Gallery.prototype.initDom_ = function(shareActions) { this.toolbar_.className = 'toolbar tool dimmable'; this.container_.appendChild(this.toolbar_); + var filenameSpacer = doc.createElement('div'); + filenameSpacer.className = 'filename-spacer'; + this.toolbar_.appendChild(filenameSpacer); + + this.filenameEdit_ = doc.createElement('input'); + this.filenameEdit_.setAttribute('type', 'text'); + this.filenameEdit_.addEventListener('blur', + this.updateFilename_.bind(this)); + this.filenameEdit_.addEventListener('keydown', + this.onFilenameEditKeydown_.bind(this)); + filenameSpacer.appendChild(this.filenameEdit_); + this.ribbonSpacer_ = doc.createElement('div'); this.ribbonSpacer_.className = 'ribbon-spacer'; this.toolbar_.appendChild(this.ribbonSpacer_); @@ -153,6 +166,7 @@ Gallery.prototype.initDom_ = function(shareActions) { this.displayStringFunction_); this.imageView_ = this.editor_.getImageView(); + this.imageView_.addContentCallback(this.onImageContentChanged_.bind(this)); this.editor_.trackWindow(doc.defaultView); @@ -212,11 +226,21 @@ Gallery.prototype.load = function(parentDirEntry, items, selectedItem) { var selectedURL = urls[selectedIndex]; // Initialize the ribbon only after the selected image is fully loaded. this.metadataProvider_.fetch(selectedURL, function (metadata) { + // The first change is load, we should not count it. + self.imageChanges_ = -1; + self.filenameEdit_.value = ImageUtil.getFileNameFromUrl(selectedURL); self.editor_.openSession( selectedIndex, selectedURL, metadata, 0, initRibbon); }); }; +Gallery.prototype.onImageContentChanged_ = function() { + this.imageChanges_++; + if (this.imageChanges_ == 1) + this.ribbon_.getSelectedItem().setCopyName(); + this.updateFilename_(); +}; + Gallery.prototype.saveItem_ = function(item, callback, canvas, modified) { if (modified) { item.save( @@ -227,6 +251,7 @@ Gallery.prototype.saveItem_ = function(item, callback, canvas, modified) { }; Gallery.prototype.saveChanges_ = function(opt_callback) { + this.imageChanges_ = 0; this.editor_.requestImage( this.saveItem_.bind(this, this.ribbon_.getSelectedItem(), opt_callback)); }; @@ -237,6 +262,80 @@ Gallery.prototype.onActionExecute_ = function(action) { this.saveChanges_(action.execute.bind(action, [url])); }; +Gallery.prototype.updateFilename_ = function() { + var item = this.ribbon_.getSelectedItem(); + if (!item) + return; + + var fullName = item.getCopyName() || + ImageUtil.getFullNameFromUrl(item.getUrl()); + this.filenameEdit_.value = ImageUtil.getFileNameFromFullName(fullName); +}; + +Gallery.prototype.onFilenameEditKeydown_ = function() { + switch (event.keyCode) { + case 27: // Escape + this.filenameEdit_.blur(); + break; + + case 13: // Enter + if (this.filenameEdit_.value) { + this.renameItem_(this.ribbon_.getSelectedItem(), + this.filenameEdit_.value); + this.filenameEdit_.blur(); + } + break; + } + event.stopPropagation(); +}; + +Gallery.prototype.renameItem_ = function(item, name) { + var dir = this.parentDirEntry_; + var self = this; + var newName; + + if (this.imageChanges_ > 0) { + // We are editing the file. + newName = ImageUtil.replaceFileNameInFullName( + item.getCopyName(), name); + } else { + newName = ImageUtil.replaceFileNameInFullName( + ImageUtil.getFullNameFromUrl(item.getUrl()), name); + } + + function onError() { + console.log('Rename error: "' + + ImageUtil.getFullNameFromUrl(item.getUrl()) + '" to "' + name + '"'); + } + + function onSuccess(entry) { + item.setUrl(entry.toURL()); + self.updateFilename_(); + } + + function doRename() { + if (self.imageChanges_ > 0) { + // User this name in the next save operation. + item.setCopyName(newName); + self.updateFilename_(); + } else { + // Rename file in place. + dir.getFile( + ImageUtil.getFullNameFromUrl(item.getUrl()), + {create: false}, + function(entry) { entry.moveTo(dir, newName, onSuccess, onError); }, + onError); + } + } + + function onVictimFound(victim) { + self.editor_.getPrompt().show('file_exists', 3000); + } + + dir.getFile(newName, {create: false, exclusive: false}, + onVictimFound, doRename); +}; + Gallery.prototype.onClose_ = function() { // TODO: handle write errors gracefully (suggest retry or saving elsewhere). this.saveChanges_(this.closeCallback_); @@ -247,6 +346,9 @@ Gallery.prototype.prefetchImage = function(id, content, metadata) { }; Gallery.prototype.openImage = function(id, content, metadata, slide, callback) { + // The first change is load, we should not count it. + this.imageChanges_ = -1; + this.updateFilename_(); this.editor_.openSession(id, content, metadata, slide, callback); }; @@ -384,6 +486,9 @@ function Ribbon(container, client, metadataProvider, arrowLeft, arrowRight) { this.client_ = client; this.metadataProvider_ = metadataProvider; + this.items_ = []; + this.selectedIndex_ = -1; + this.arrowLeft_ = arrowLeft; this.arrowLeft_. addEventListener('click', this.selectNext.bind(this, -1, null)); @@ -678,6 +783,7 @@ Ribbon.Item = function(index, url, document, selectClosure) { } this.original_ = true; + this.copyName_ = null; }; Ribbon.Item.prototype.getIndex = function () { return this.index_ }; @@ -687,6 +793,9 @@ Ribbon.Item.prototype.getBox = function (index) { return this.boxes_[index] }; Ribbon.Item.prototype.isOriginal = function () { return this.original_ }; Ribbon.Item.prototype.getUrl = function () { return this.url_ }; +Ribbon.Item.prototype.setUrl = function (url) { this.url_ = url }; + +Ribbon.Item.prototype.getCopyName = function () { return this.copyName_ }; Ribbon.Item.prototype.isSelected = function() { return this.boxes_[0].hasAttribute('selected'); @@ -725,7 +834,9 @@ Ribbon.Item.prototype.save = function( } var newFile = this.isOriginal(); - var name = this.getCopyName(); + var name = this.copyName_; + this.original_ = false; + this.copyName_ = ''; function onSuccess(url) { console.log('Saved from gallery', name); @@ -761,9 +872,9 @@ Ribbon.Item.prototype.save = function( }; // TODO: Localize? -Ribbon.Item.COPY_SIGNATURE = '_Edited_'; +Ribbon.Item.COPY_SIGNATURE = 'Copy of '; -Ribbon.Item.prototype.getCopyName = function () { +Ribbon.Item.prototype.createCopyName_ = function () { // When saving a modified image we never overwrite the original file (the one // that existed prior to opening the Gallery. Instead we save to a file named // <original-name>_Edited_<date-stamp>.<original extension>. @@ -775,19 +886,16 @@ Ribbon.Item.prototype.getCopyName = function () { if (!this.original_) return name; - this.original_ = false; - var ext = ''; var index = name.lastIndexOf('.'); if (index != -1) { ext = name.substr(index); name = name.substr(0, index); } - var signaturePos = name.indexOf(Ribbon.Item.COPY_SIGNATURE); - if (signaturePos >= 0) { - // The file is likely to be a copy created during a previous session. - // Replace the signature instead of appending a new one. - name = name.substr(0, signaturePos); + + if (name.indexOf(Ribbon.Item.COPY_SIGNATURE) == 0) { + // TODO(dgozman): add a number to form 'Copy (X) of File.jpg'. + name = name.substr(Ribbon.Item.COPY_SIGNATURE.length); } var mimeType = this.metadata_.mimeType.toLowerCase(); @@ -806,21 +914,15 @@ Ribbon.Item.prototype.getCopyName = function () { } } - function twoDigits(n) { return (n < 10 ? '0' : '' ) + n } - - var now = new Date(); + return Ribbon.Item.COPY_SIGNATURE + name + ext; +}; - // Datestamp the copy with YYYYMMDD_HHMMSS (similar to what many cameras do) - return name + - Ribbon.Item.COPY_SIGNATURE + - now.getFullYear() + - twoDigits(now.getMonth() + 1) + - twoDigits(now.getDate()) + - '_' + - twoDigits(now.getHours()) + - twoDigits(now.getMinutes()) + - twoDigits(now.getSeconds()) + - ext; +Ribbon.Item.prototype.setCopyName = function(opt_name) { + if (opt_name) { + this.copyName_ = opt_name; + } else { + this.copyName_ = this.createCopyName_(); + } }; // The url and metadata stored in the item are not valid while the modified diff --git a/chrome/browser/resources/file_manager/js/image_editor/image_util.js b/chrome/browser/resources/file_manager/js/image_editor/image_util.js index 6e0d659..c8667e9 100644 --- a/chrome/browser/resources/file_manager/js/image_editor/image_util.js +++ b/chrome/browser/resources/file_manager/js/image_editor/image_util.js @@ -438,3 +438,30 @@ ImageUtil.ImageLoader.prototype.copyStrip_ = function( ImageUtil.removeChildren = function(element) { element.textContent = ''; }; + +ImageUtil.getFullNameFromUrl = function(url) { + if (url.indexOf('/') != -1) + return url.substr(url.lastIndexOf('/') + 1); + else + return url; +}; + +ImageUtil.getFileNameFromFullName = function(name) { + var index = name.lastIndexOf('.'); + if (index != -1) + return name.substr(0, index); + else + return name; +}; + +ImageUtil.getFileNameFromUrl = function(url) { + return ImageUtil.getFileNameFromFullName(ImageUtil.getFullNameFromUrl(url)); +}; + +ImageUtil.replaceFileNameInFullName = function(fullName, name) { + var index = fullName.lastIndexOf('.'); + if (index != -1) + return name + fullName.substr(index); + else + return name; +}; diff --git a/chrome/browser/resources/file_manager/js/mock_chrome.js b/chrome/browser/resources/file_manager/js/mock_chrome.js index a19cefb..17898e4 100644 --- a/chrome/browser/resources/file_manager/js/mock_chrome.js +++ b/chrome/browser/resources/file_manager/js/mock_chrome.js @@ -262,6 +262,7 @@ chrome.fileBrowserPrivate = { GALLERY_ENTER_WHEN_DONE: 'Press Enter when done', GALLERY_UNDO: 'Undo', GALLERY_REDO: 'Redo', + GALLERY_FILE_EXISTS: 'File already exists', CONFIRM_OVERWRITE_FILE: 'A file named "$1" already exists. Do you want to replace it?', FILE_ALREADY_EXISTS: 'The file named "$1" already exists. Please choose a different name.', |