Chromium Code Reviews| OLD | NEW |
|---|---|
| 1 // Copyright (c) 2011 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 2011 The Chromium Authors. All rights reserved. |
| 2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
| 3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
| 4 | 4 |
| 5 // Setting the src of an img to an empty string can crash the browser, so we | 5 // Setting the src of an img to an empty string can crash the browser, so we |
| 6 // use an empty 1x1 gif instead. | 6 // use an empty 1x1 gif instead. |
| 7 const EMPTY_IMAGE_URI = 'data:image/gif;base64,' | 7 const EMPTY_IMAGE_URI = 'data:image/gif;base64,' |
| 8 + 'R0lGODlhAQABAPABAP///wAAACH5BAEKAAAALAAAAAABAAEAAAICRAEAOw%3D%3D'; | 8 + 'R0lGODlhAQABAPABAP///wAAACH5BAEKAAAALAAAAAABAAEAAAICRAEAOw%3D%3D'; |
| 9 | 9 |
| 10 // If directory files changes too often, don't rescan directory more than once | 10 // If directory files changes too often, don't rescan directory more than once |
| (...skipping 181 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 192 'image': 'images/filetype_large_image.png', | 192 'image': 'images/filetype_large_image.png', |
| 193 'video': 'images/filetype_large_video.png' | 193 'video': 'images/filetype_large_video.png' |
| 194 }; | 194 }; |
| 195 | 195 |
| 196 /** | 196 /** |
| 197 * Regexp for archive files. Used to show mount-archive task. | 197 * Regexp for archive files. Used to show mount-archive task. |
| 198 */ | 198 */ |
| 199 const ARCHIVES_REGEXP = /.zip$/; | 199 const ARCHIVES_REGEXP = /.zip$/; |
| 200 | 200 |
| 201 /** | 201 /** |
| 202 * Item for the Grid View. | |
| 203 * @constructor | |
| 204 */ | |
| 205 function GridItem(fileManager, entry) { | |
| 206 var li = fileManager.document_.createElement('li'); | |
| 207 GridItem.decorate(li, fileManager, entry); | |
| 208 return li; | |
| 209 } | |
| 210 | |
| 211 GridItem.prototype = { | |
| 212 __proto__: cr.ui.ListItem.prototype, | |
| 213 | |
| 214 get label() { | |
| 215 return this.querySelector('filename-label').textContent; | |
| 216 }, | |
| 217 set label(value) { | |
| 218 // Grid sets it to entry. Ignore. | |
| 219 } | |
| 220 }; | |
| 221 | |
| 222 GridItem.decorate = function(li, fileManager, entry) { | |
| 223 li.__proto__ = GridItem.prototype; | |
| 224 fileManager.decorateThumbnail_(li, entry); | |
| 225 }; | |
| 226 | |
| 227 | |
| 228 /** | |
| 202 * Return a translated string. | 229 * Return a translated string. |
| 203 * | 230 * |
| 204 * Wrapper function to make dealing with translated strings more concise. | 231 * Wrapper function to make dealing with translated strings more concise. |
| 205 * Equivilant to localStrings.getString(id). | 232 * Equivilant to localStrings.getString(id). |
| 206 * | 233 * |
| 207 * @param {string} id The id of the string to return. | 234 * @param {string} id The id of the string to return. |
| 208 * @return {string} The translated string. | 235 * @return {string} The translated string. |
| 209 */ | 236 */ |
| 210 function str(id) { | 237 function str(id) { |
| 211 return localStrings.getString(id); | 238 return localStrings.getString(id); |
| (...skipping 888 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 1100 FileManager.prototype.setListType = function(type) { | 1127 FileManager.prototype.setListType = function(type) { |
| 1101 if (type && type == this.listType_) | 1128 if (type && type == this.listType_) |
| 1102 return; | 1129 return; |
| 1103 | 1130 |
| 1104 if (type == FileManager.ListType.DETAIL) { | 1131 if (type == FileManager.ListType.DETAIL) { |
| 1105 var selectedIndexes = this.grid_.selectionModel.selectedIndexes; | 1132 var selectedIndexes = this.grid_.selectionModel.selectedIndexes; |
| 1106 this.table_.dataModel = this.dataModel_; | 1133 this.table_.dataModel = this.dataModel_; |
| 1107 this.table_.style.display = ''; | 1134 this.table_.style.display = ''; |
| 1108 this.grid_.style.display = 'none'; | 1135 this.grid_.style.display = 'none'; |
| 1109 this.grid_.dataModel = this.emptyDataModel_; | 1136 this.grid_.dataModel = this.emptyDataModel_; |
| 1110 this.currentList_ = this.table_; | 1137 /** @type {cr.ui.List} */ |
| 1138 this.currentList_ = this.table_.list; | |
| 1111 this.dialogDom_.querySelector('button.detail-view').disabled = true; | 1139 this.dialogDom_.querySelector('button.detail-view').disabled = true; |
| 1112 this.dialogDom_.querySelector('button.thumbnail-view').disabled = false; | 1140 this.dialogDom_.querySelector('button.thumbnail-view').disabled = false; |
| 1113 this.table_.selectionModel.selectedIndexes = selectedIndexes; | 1141 this.table_.selectionModel.selectedIndexes = selectedIndexes; |
| 1114 } else if (type == FileManager.ListType.THUMBNAIL) { | 1142 } else if (type == FileManager.ListType.THUMBNAIL) { |
| 1115 var selectedIndexes = this.table_.selectionModel.selectedIndexes; | 1143 var selectedIndexes = this.table_.selectionModel.selectedIndexes; |
| 1116 this.grid_.dataModel = this.dataModel_; | 1144 this.grid_.dataModel = this.dataModel_; |
| 1117 this.grid_.style.display = ''; | 1145 this.grid_.style.display = ''; |
| 1118 this.table_.style.display = 'none'; | 1146 this.table_.style.display = 'none'; |
| 1119 this.table_.dataModel = this.emptyDataModel_; | 1147 this.table_.dataModel = this.emptyDataModel_; |
| 1148 /** @type {cr.ui.List} */ | |
| 1120 this.currentList_ = this.grid_; | 1149 this.currentList_ = this.grid_; |
| 1121 this.dialogDom_.querySelector('button.thumbnail-view').disabled = true; | 1150 this.dialogDom_.querySelector('button.thumbnail-view').disabled = true; |
| 1122 this.dialogDom_.querySelector('button.detail-view').disabled = false; | 1151 this.dialogDom_.querySelector('button.detail-view').disabled = false; |
| 1123 this.grid_.selectionModel.selectedIndexes = selectedIndexes; | 1152 this.grid_.selectionModel.selectedIndexes = selectedIndexes; |
| 1124 } else { | 1153 } else { |
| 1125 throw new Error('Unknown list type: ' + type); | 1154 throw new Error('Unknown list type: ' + type); |
| 1126 } | 1155 } |
| 1127 | 1156 |
| 1128 this.listType_ = type; | 1157 this.listType_ = type; |
| 1129 this.onResize_(); | 1158 this.onResize_(); |
| 1130 }; | 1159 }; |
| 1131 | 1160 |
| 1132 /** | 1161 /** |
| 1133 * Initialize the file thumbnail grid. | 1162 * Initialize the file thumbnail grid. |
| 1134 */ | 1163 */ |
| 1135 FileManager.prototype.initGrid_ = function() { | 1164 FileManager.prototype.initGrid_ = function() { |
| 1136 this.grid_ = this.dialogDom_.querySelector('.thumbnail-grid'); | 1165 this.grid_ = this.dialogDom_.querySelector('.thumbnail-grid'); |
| 1137 cr.ui.Grid.decorate(this.grid_); | 1166 cr.ui.Grid.decorate(this.grid_); |
| 1138 | 1167 |
| 1139 var self = this; | 1168 var self = this; |
| 1140 this.grid_.itemConstructor = function(entry) { | 1169 this.grid_.itemConstructor = GridItem.bind(null, this); |
| 1141 return self.renderThumbnail_(entry); | |
| 1142 }; | |
| 1143 | 1170 |
| 1144 this.grid_.selectionModel = new this.selectionModelClass_(); | 1171 this.grid_.selectionModel = new this.selectionModelClass_(); |
| 1145 | 1172 |
| 1146 this.grid_.addEventListener( | 1173 this.grid_.addEventListener( |
| 1147 'dblclick', this.onDetailDoubleClick_.bind(this)); | 1174 'dblclick', this.onDetailDoubleClick_.bind(this)); |
| 1148 this.grid_.selectionModel.addEventListener( | 1175 this.grid_.selectionModel.addEventListener( |
| 1149 'change', this.onSelectionChanged_.bind(this)); | 1176 'change', this.onSelectionChanged_.bind(this)); |
| 1150 cr.ui.contextMenuHandler.addContextMenuProperty(this.grid_); | 1177 cr.ui.contextMenuHandler.addContextMenuProperty(this.grid_); |
| 1151 this.grid_.contextMenu = this.fileContextMenu_; | 1178 this.grid_.contextMenu = this.fileContextMenu_; |
| 1152 this.grid_.addEventListener('mousedown', | 1179 this.grid_.addEventListener('mousedown', |
| (...skipping 119 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 1272 | 1299 |
| 1273 case 'copy': | 1300 case 'copy': |
| 1274 this.copySelectionToClipboard(); | 1301 this.copySelectionToClipboard(); |
| 1275 return; | 1302 return; |
| 1276 | 1303 |
| 1277 case 'paste': | 1304 case 'paste': |
| 1278 this.pasteFromClipboard(); | 1305 this.pasteFromClipboard(); |
| 1279 return; | 1306 return; |
| 1280 | 1307 |
| 1281 case 'rename': | 1308 case 'rename': |
| 1282 var leadIndex = this.currentList_.selectionModel.leadIndex; | 1309 var index = this.currentList_.selectionModel.selectedIndex; |
| 1283 var li = this.currentList_.getListItemByIndex(leadIndex); | 1310 var item = this.currentList_.getListItemByIndex(index); |
| 1284 var label = li.querySelector('.filename-label'); | 1311 if (item) |
| 1285 if (!label) { | 1312 this.initiateRename_(item); |
| 1286 console.warn('Unable to find label for rename of index: ' + | |
| 1287 leadIndex); | |
| 1288 return; | |
| 1289 } | |
| 1290 | |
| 1291 this.initiateRename_(label); | |
| 1292 return; | 1313 return; |
| 1293 | 1314 |
| 1294 case 'delete': | 1315 case 'delete': |
| 1295 this.deleteEntries(this.selection.entries); | 1316 this.deleteEntries(this.selection.entries); |
| 1296 return; | 1317 return; |
| 1297 } | 1318 } |
| 1298 }; | 1319 }; |
| 1299 | 1320 |
| 1300 /** | 1321 /** |
| 1301 * Respond to the back and forward buttons. | 1322 * Respond to the back and forward buttons. |
| (...skipping 354 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 1656 if (opt_imageLoadCallback) | 1677 if (opt_imageLoadCallback) |
| 1657 opt_imageLoadCallback(img, transform); | 1678 opt_imageLoadCallback(img, transform); |
| 1658 box.appendChild(img); | 1679 box.appendChild(img); |
| 1659 }; | 1680 }; |
| 1660 img.src = url; | 1681 img.src = url; |
| 1661 self.applyImageTransformation_(box, transform); | 1682 self.applyImageTransformation_(box, transform); |
| 1662 }); | 1683 }); |
| 1663 return box; | 1684 return box; |
| 1664 }; | 1685 }; |
| 1665 | 1686 |
| 1666 FileManager.prototype.renderThumbnail_ = function(entry) { | 1687 FileManager.prototype.decorateThumbnail_ = function(li, entry) { |
| 1667 var li = this.document_.createElement('li'); | |
| 1668 li.className = 'thumbnail-item'; | 1688 li.className = 'thumbnail-item'; |
| 1669 | 1689 |
| 1670 if (this.showCheckboxes_) | 1690 if (this.showCheckboxes_) |
| 1671 li.appendChild(this.renderCheckbox_(entry)); | 1691 li.appendChild(this.renderCheckbox_(entry)); |
| 1672 | 1692 |
| 1673 li.appendChild(this.renderThumbnailBox_(entry, false)); | 1693 li.appendChild(this.renderThumbnailBox_(entry, false)); |
| 1674 | 1694 li.appendChild(this.renderFileNameLabel_(entry)); |
| 1675 var div = this.document_.createElement('div'); | |
| 1676 div.className = 'filename-label'; | |
| 1677 var labelText = entry.name; | |
| 1678 if (this.currentDirEntry_.name == '') | |
| 1679 labelText = this.getLabelForRootPath_(labelText); | |
| 1680 | |
| 1681 div.textContent = labelText; | |
| 1682 div.entry = entry; | |
| 1683 | |
| 1684 li.appendChild(div); | |
| 1685 | |
| 1686 cr.defineProperty(li, 'lead', cr.PropertyKind.BOOL_ATTR); | |
| 1687 cr.defineProperty(li, 'selected', cr.PropertyKind.BOOL_ATTR); | |
| 1688 return li; | |
| 1689 }; | 1695 }; |
| 1690 | 1696 |
| 1691 /** | 1697 /** |
| 1692 * Render the type column of the detail table. | 1698 * Render the type column of the detail table. |
| 1693 * | 1699 * |
| 1694 * Invoked by cr.ui.Table when a file needs to be rendered. | 1700 * Invoked by cr.ui.Table when a file needs to be rendered. |
| 1695 * | 1701 * |
| 1696 * @param {Entry} entry The Entry object to render. | 1702 * @param {Entry} entry The Entry object to render. |
| 1697 * @param {string} columnId The id of the column to be rendered. | 1703 * @param {string} columnId The id of the column to be rendered. |
| 1698 * @param {cr.ui.Table} table The table doing the rendering. | 1704 * @param {cr.ui.Table} table The table doing the rendering. |
| (...skipping 29 matching lines...) Expand all Loading... | |
| 1728 * @param {string} columnId The id of the column to be rendered. | 1734 * @param {string} columnId The id of the column to be rendered. |
| 1729 * @param {cr.ui.Table} table The table doing the rendering. | 1735 * @param {cr.ui.Table} table The table doing the rendering. |
| 1730 */ | 1736 */ |
| 1731 FileManager.prototype.renderName_ = function(entry, columnId, table) { | 1737 FileManager.prototype.renderName_ = function(entry, columnId, table) { |
| 1732 var label = this.document_.createElement('div'); | 1738 var label = this.document_.createElement('div'); |
| 1733 if (this.showCheckboxes_) | 1739 if (this.showCheckboxes_) |
| 1734 label.appendChild(this.renderCheckbox_(entry)); | 1740 label.appendChild(this.renderCheckbox_(entry)); |
| 1735 label.appendChild(this.renderIconType_(entry, columnId, table)); | 1741 label.appendChild(this.renderIconType_(entry, columnId, table)); |
| 1736 label.entry = entry; | 1742 label.entry = entry; |
| 1737 label.className = 'detail-name'; | 1743 label.className = 'detail-name'; |
| 1738 if (this.currentDirEntry_.name == '') { | 1744 label.appendChild(this.renderFileNameLabel_(entry)); |
| 1739 label.appendChild(this.document_.createTextNode( | |
| 1740 this.getLabelForRootPath_(entry.name))); | |
| 1741 } else { | |
| 1742 label.appendChild(this.document_.createTextNode(entry.name)); | |
| 1743 } | |
| 1744 | 1745 |
| 1745 return label; | 1746 return label; |
| 1746 }; | 1747 }; |
| 1747 | 1748 |
| 1748 /** | 1749 /** |
| 1750 * Render filename label for grid and list view. | |
| 1751 * @param {Entry} entry The Entry object to render. | |
| 1752 * @return {HTMLDivElement} The label. | |
| 1753 */ | |
| 1754 FileManager.prototype.renderFileNameLabel_ = function(entry) { | |
| 1755 // Filename need to be in a '.filename-label' container for correct | |
| 1756 // work of inplace renaming. | |
| 1757 var fileName = this.document_.createElement('div'); | |
| 1758 fileName.className = 'filename-label'; | |
| 1759 fileName.textContent = this.currentDirEntry_.name == '' ? | |
| 1760 this.getLabelForRootPath_(entry.name) : entry.name; | |
| 1761 return fileName; | |
| 1762 }; | |
| 1763 | |
| 1764 /** | |
| 1749 * Render the Size column of the detail table. | 1765 * Render the Size column of the detail table. |
| 1750 * | 1766 * |
| 1751 * @param {Entry} entry The Entry object to render. | 1767 * @param {Entry} entry The Entry object to render. |
| 1752 * @param {string} columnId The id of the column to be rendered. | 1768 * @param {string} columnId The id of the column to be rendered. |
| 1753 * @param {cr.ui.Table} table The table doing the rendering. | 1769 * @param {cr.ui.Table} table The table doing the rendering. |
| 1754 */ | 1770 */ |
| 1755 FileManager.prototype.renderSize_ = function(entry, columnId, table) { | 1771 FileManager.prototype.renderSize_ = function(entry, columnId, table) { |
| 1756 var div = this.document_.createElement('div'); | 1772 var div = this.document_.createElement('div'); |
| 1757 | 1773 |
| 1758 div.textContent = '...'; | 1774 div.textContent = '...'; |
| (...skipping 745 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 2504 FileManager.prototype.selectEntry = function(name) { | 2520 FileManager.prototype.selectEntry = function(name) { |
| 2505 for (var i = 0; i < this.dataModel_.length; i++) { | 2521 for (var i = 0; i < this.dataModel_.length; i++) { |
| 2506 if (this.dataModel_.item(i).name == name) { | 2522 if (this.dataModel_.item(i).name == name) { |
| 2507 this.selectIndex(i); | 2523 this.selectIndex(i); |
| 2508 return; | 2524 return; |
| 2509 } | 2525 } |
| 2510 } | 2526 } |
| 2511 }; | 2527 }; |
| 2512 | 2528 |
| 2513 FileManager.prototype.selectIndex = function(index) { | 2529 FileManager.prototype.selectIndex = function(index) { |
| 2514 this.currentList_.focus(); | 2530 this.focusCurrentList_(); |
| 2515 if (index >= this.dataModel_.length) | 2531 if (index >= this.dataModel_.length) |
| 2516 return; | 2532 return; |
| 2517 this.currentList_.selectionModel.selectedIndex = index; | 2533 this.currentList_.selectionModel.selectedIndex = index; |
| 2518 this.currentList_.scrollIndexIntoView(index); | 2534 this.currentList_.scrollIndexIntoView(index); |
| 2519 }; | 2535 }; |
| 2520 | 2536 |
| 2521 /** | 2537 /** |
| 2522 * Add the file/directory with given name to the current selection. | 2538 * Add the file/directory with given name to the current selection. |
| 2523 * | 2539 * |
| 2524 * @param {string} name The name of the entry to select. | 2540 * @param {string} name The name of the entry to select. |
| 2525 * @return {boolean} Whether entry exists. | 2541 * @return {boolean} Whether entry exists. |
| 2526 */ | 2542 */ |
| 2527 FileManager.prototype.addItemToSelection = function(name) { | 2543 FileManager.prototype.addItemToSelection = function(name) { |
| 2528 var entryExists = false; | 2544 var entryExists = false; |
| 2529 for (var i = 0; i < this.dataModel_.length; i++) { | 2545 for (var i = 0; i < this.dataModel_.length; i++) { |
| 2530 if (this.dataModel_.item(i).name == name) { | 2546 if (this.dataModel_.item(i).name == name) { |
| 2531 this.currentList_.selectionModel.setIndexSelected(i, true); | 2547 this.currentList_.selectionModel.setIndexSelected(i, true); |
| 2532 this.currentList_.scrollIndexIntoView(i); | 2548 this.currentList_.scrollIndexIntoView(i); |
| 2533 this.currentList_.focus(); | 2549 this.focusCurrentList_(); |
| 2534 entryExists = true; | 2550 entryExists = true; |
| 2535 break; | 2551 break; |
| 2536 } | 2552 } |
| 2537 } | 2553 } |
| 2538 return entryExists; | 2554 return entryExists; |
| 2539 } | 2555 }; |
| 2556 | |
| 2557 FileManager.prototype.focusCurrentList_ = function() { | |
| 2558 if (this.listType_ == FileManager.ListType.DETAIL) | |
| 2559 this.table_.focus(); | |
| 2560 else // this.listType_ == FileManager.ListType.THUMBNAIL) | |
| 2561 this.grid_.focus(); | |
| 2562 }; | |
| 2540 | 2563 |
| 2541 /** | 2564 /** |
| 2542 * Return the name of the entries in the current directory | 2565 * Return the name of the entries in the current directory |
| 2543 * | 2566 * |
| 2544 * @return {object} Array of entry names. | 2567 * @return {object} Array of entry names. |
| 2545 */ | 2568 */ |
| 2546 FileManager.prototype.listDirectory = function() { | 2569 FileManager.prototype.listDirectory = function() { |
| 2547 var list = [] | 2570 var list = [] |
| 2548 for (var i = 0; i < this.dataModel_.length; i++) { | 2571 for (var i = 0; i < this.dataModel_.length; i++) { |
| 2549 list.push(this.dataModel_.item(i).name); | 2572 list.push(this.dataModel_.item(i).name); |
| (...skipping 693 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 3243 FileManager.prototype.prefetchCacheForSorting_ = function(entries, callback) { | 3266 FileManager.prototype.prefetchCacheForSorting_ = function(entries, callback) { |
| 3244 var field = this.dataModel_.sortStatus.field; | 3267 var field = this.dataModel_.sortStatus.field; |
| 3245 if (field) { | 3268 if (field) { |
| 3246 this.prepareSortEntries_(entries, field, callback); | 3269 this.prepareSortEntries_(entries, field, callback); |
| 3247 } else { | 3270 } else { |
| 3248 callback(); | 3271 callback(); |
| 3249 return; | 3272 return; |
| 3250 } | 3273 } |
| 3251 }; | 3274 }; |
| 3252 | 3275 |
| 3253 FileManager.prototype.findListItem_ = function(event) { | 3276 FileManager.prototype.findListItemForEvent_ = function(event) { |
| 3254 var node = event.srcElement; | 3277 var node = event.srcElement; |
| 3278 var list = this.currentList_; | |
| 3279 // Assume list items are direct children of the list. | |
| 3280 if (node == list) | |
| 3281 return null; | |
| 3255 while (node) { | 3282 while (node) { |
| 3256 if (node.tagName == 'LI') | 3283 var parent = node.parentNode; |
| 3257 break; | 3284 if (parent == list && node instanceof cr.ui.ListItem) |
| 3258 node = node.parentNode; | 3285 return node; |
| 3286 node = parent; | |
| 3259 } | 3287 } |
| 3260 | 3288 return null; |
| 3261 return node; | |
| 3262 }; | 3289 }; |
| 3263 | 3290 |
| 3264 FileManager.prototype.onGridMouseDown_ = function(event) { | 3291 FileManager.prototype.onGridMouseDown_ = function(event) { |
| 3265 this.updateCommands_(); | 3292 this.updateCommands_(); |
| 3266 | 3293 |
| 3267 if (this.allowRenameClick_(event, event.srcElement.parentNode)) { | 3294 var item = this.findListItemForEvent_(event); |
| 3295 if (!item) | |
| 3296 return; | |
| 3297 if (this.allowRenameClick_(event, item)) { | |
| 3268 event.preventDefault(); | 3298 event.preventDefault(); |
| 3269 this.initiateRename_(event.srcElement); | 3299 this.initiateRename_(item); |
| 3270 } | 3300 } |
| 3271 | |
| 3272 if (event.button != 1) | |
| 3273 return; | |
| 3274 | |
| 3275 var li = this.findListItem_(event); | |
| 3276 if (!li) | |
| 3277 return; | |
| 3278 }; | 3301 }; |
| 3279 | 3302 |
| 3280 FileManager.prototype.onTableMouseDown_ = function(event) { | 3303 FileManager.prototype.onTableMouseDown_ = function(event) { |
|
dgozman
2011/12/09 15:20:34
Same as onGridMouseDown_.
SeRya
2011/12/09 15:35:11
Fixed.
| |
| 3281 this.updateCommands_(); | 3304 this.updateCommands_(); |
| 3282 | 3305 |
| 3283 if (this.allowRenameClick_(event, | 3306 var list = this.table_.list; |
| 3284 event.srcElement.parentNode.parentNode)) { | 3307 var item = this.findListItemForEvent_(event); |
| 3308 if (!item) | |
| 3309 return; | |
| 3310 if (this.allowRenameClick_(event, item)) { | |
| 3285 event.preventDefault(); | 3311 event.preventDefault(); |
| 3286 this.initiateRename_(event.srcElement); | 3312 this.initiateRename_(item); |
| 3287 } | |
| 3288 | |
| 3289 if (event.button != 1) | |
| 3290 return; | |
| 3291 | |
| 3292 var li = this.findListItem_(event); | |
| 3293 if (!li) { | |
| 3294 console.log('li not found', event); | |
| 3295 return; | |
| 3296 } | 3313 } |
| 3297 }; | 3314 }; |
| 3298 | 3315 |
| 3299 /** | 3316 /** |
| 3300 * Unload handler for the page. May be called manually for the file picker | 3317 * Unload handler for the page. May be called manually for the file picker |
| 3301 * dialog, because it closes by calling extension API functions that do not | 3318 * dialog, because it closes by calling extension API functions that do not |
| 3302 * return. | 3319 * return. |
| 3303 */ | 3320 */ |
| 3304 FileManager.prototype.onUnload_ = function() { | 3321 FileManager.prototype.onUnload_ = function() { |
| 3305 if (this.subscribedOnDirectoryChanges_) { | 3322 if (this.subscribedOnDirectoryChanges_) { |
| (...skipping 11 matching lines...) Expand all Loading... | |
| 3317 // We receive a lot of events even in folders we are not interested in. | 3334 // We receive a lot of events even in folders we are not interested in. |
| 3318 if (event.fileUrl == this.currentDirEntry_.toURL()) | 3335 if (event.fileUrl == this.currentDirEntry_.toURL()) |
| 3319 this.rescanDirectoryLater_(); | 3336 this.rescanDirectoryLater_(); |
| 3320 }; | 3337 }; |
| 3321 | 3338 |
| 3322 /** | 3339 /** |
| 3323 * Determine whether or not a click should initiate a rename. | 3340 * Determine whether or not a click should initiate a rename. |
| 3324 * | 3341 * |
| 3325 * Renames can happen on mouse click if the user clicks on a label twice, | 3342 * Renames can happen on mouse click if the user clicks on a label twice, |
| 3326 * at least a half second apart. | 3343 * at least a half second apart. |
| 3344 * @param {MouseEvent} event Click on the item. | |
| 3345 * @param {cr.ui.ListItem} item Clicked item. | |
| 3327 */ | 3346 */ |
| 3328 FileManager.prototype.allowRenameClick_ = function(event, row) { | 3347 FileManager.prototype.allowRenameClick_ = function(event, item) { |
| 3329 if (this.dialogType_ != FileManager.DialogType.FULL_PAGE || | 3348 if (this.dialogType_ != FileManager.DialogType.FULL_PAGE || |
| 3330 this.currentDirEntry_ == null || this.currentDirEntry_.name == '' || | 3349 this.currentDirEntry_ == null || this.currentDirEntry_.name == '' || |
| 3331 isSystemDirEntry(this.currentDirEntry_)) { | 3350 isSystemDirEntry(this.currentDirEntry_)) { |
| 3332 // Renaming only enabled for full-page mode, outside of the root | 3351 // Renaming only enabled for full-page mode, outside of the root |
| 3333 // directory. | 3352 // directory. |
| 3334 return false; | 3353 return false; |
| 3335 } | 3354 } |
| 3336 | 3355 |
| 3337 // Didn't click on the label. | 3356 // Didn't click on the label. |
| 3338 if (!event.srcElement.classList.contains('filename-label')) | 3357 if (!event.srcElement.classList.contains('filename-label')) |
| 3339 return false; | 3358 return false; |
| 3340 | 3359 |
| 3341 // Wrong button or using a keyboard modifier. | 3360 // Wrong button or using a keyboard modifier. |
| 3342 if (event.button != 0 || event.shiftKey || event.metaKey || event.altKey) { | 3361 if (event.button != 0 || event.shiftKey || event.metaKey || event.altKey) { |
| 3343 this.lastLabelClick_ = null; | 3362 this.lastLabelClick_ = null; |
| 3344 return false; | 3363 return false; |
| 3345 } | 3364 } |
| 3346 | 3365 |
| 3347 var now = new Date(); | 3366 var now = new Date(); |
| 3348 var path = event.srcElement.entry.fullPath; | |
| 3349 var lastLabelClick = this.lastLabelClick_; | 3367 var lastLabelClick = this.lastLabelClick_; |
| 3350 this.lastLabelClick_ = {path: path, date: now}; | 3368 this.lastLabelClick_ = {index: item.listIndex, date: now}; |
| 3351 | 3369 |
| 3352 // Rename already in progress. | 3370 // Rename already in progress. |
| 3353 if (this.renameInput_.currentEntry) | 3371 if (this.renameInput_.currentEntry) |
| 3354 return false; | 3372 return false; |
| 3355 | 3373 |
| 3356 if (lastLabelClick && lastLabelClick.path == path) { | 3374 if (lastLabelClick && lastLabelClick.index == item.listIndex) { |
| 3357 var delay = now - lastLabelClick.date; | 3375 var delay = now - lastLabelClick.date; |
| 3358 if (delay > 500 && delay < 2000) { | 3376 if (delay > 500 && delay < 2000) { |
| 3359 this.lastLabelClick_ = null; | 3377 this.lastLabelClick_ = null; |
| 3360 return true; | 3378 return true; |
| 3361 } | 3379 } |
| 3362 } | 3380 } |
| 3363 | 3381 |
| 3364 return false; | 3382 return false; |
| 3365 }; | 3383 }; |
| 3366 | 3384 |
| 3367 FileManager.prototype.initiateRename_= function(label) { | 3385 FileManager.prototype.initiateRename_ = function(item) { |
| 3386 var label = item.querySelector('.filename-label'); | |
| 3368 var input = this.renameInput_; | 3387 var input = this.renameInput_; |
| 3369 | 3388 |
| 3370 input.value = label.textContent; | 3389 input.value = label.textContent; |
| 3371 input.style.top = label.offsetTop + 'px'; | 3390 input.style.top = label.offsetTop + 'px'; |
| 3372 input.style.left = label.offsetLeft + 'px'; | 3391 input.style.left = label.offsetLeft + 'px'; |
| 3373 input.style.width = label.clientWidth + 'px'; | 3392 input.style.width = label.clientWidth + 'px'; |
| 3374 label.parentNode.appendChild(input); | 3393 label.parentNode.appendChild(input); |
| 3375 input.focus(); | 3394 input.focus(); |
| 3376 var selectionEnd = input.value.lastIndexOf('.'); | 3395 var selectionEnd = input.value.lastIndexOf('.'); |
| 3377 if (selectionEnd == -1) { | 3396 if (selectionEnd == -1) { |
| 3378 input.select(); | 3397 input.select(); |
| 3379 } else { | 3398 } else { |
| 3380 input.selectionStart = 0; | 3399 input.selectionStart = 0; |
| 3381 input.selectionEnd = selectionEnd; | 3400 input.selectionEnd = selectionEnd; |
| 3382 } | 3401 } |
| 3383 | 3402 |
| 3384 // This has to be set late in the process so we don't handle spurious | 3403 // This has to be set late in the process so we don't handle spurious |
| 3385 // blur events. | 3404 // blur events. |
| 3386 input.currentEntry = label.entry; | 3405 input.currentEntry = this.currentList_.dataModel.item(item.listIndex); |
| 3387 }; | 3406 }; |
| 3388 | 3407 |
| 3389 FileManager.prototype.onRenameInputKeyDown_ = function(event) { | 3408 FileManager.prototype.onRenameInputKeyDown_ = function(event) { |
| 3390 if (!this.renameInput_.currentEntry) | 3409 if (!this.renameInput_.currentEntry) |
| 3391 return; | 3410 return; |
| 3392 | 3411 |
| 3393 switch (event.keyCode) { | 3412 switch (event.keyCode) { |
| 3394 case 27: // Escape | 3413 case 27: // Escape |
| 3395 this.cancelRename_(); | 3414 this.cancelRename_(); |
| 3396 event.preventDefault(); | 3415 event.preventDefault(); |
| (...skipping 571 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 3968 }); | 3987 }); |
| 3969 }, onError); | 3988 }, onError); |
| 3970 | 3989 |
| 3971 function onError(err) { | 3990 function onError(err) { |
| 3972 console.log('Error while checking free space: ' + err); | 3991 console.log('Error while checking free space: ' + err); |
| 3973 setTimeout(doCheck, 1000 * 60); | 3992 setTimeout(doCheck, 1000 * 60); |
| 3974 } | 3993 } |
| 3975 } | 3994 } |
| 3976 } | 3995 } |
| 3977 })(); | 3996 })(); |
| OLD | NEW |