Chromium Code Reviews| OLD | NEW |
|---|---|
| 1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 2012 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 /** | 5 /** |
| 6 * Global (placed in the window object) variable name to hold internal | 6 * Global (placed in the window object) variable name to hold internal |
| 7 * file dragging information. Needed to show visual feedback while dragging | 7 * file dragging information. Needed to show visual feedback while dragging |
| 8 * since DataTransfer object is in protected state. Reachable from other | 8 * since DataTransfer object is in protected state. Reachable from other |
| 9 * file manager instances. | 9 * file manager instances. |
| 10 */ | 10 */ |
| (...skipping 28 matching lines...) Expand all Loading... | |
| 39 * @type {Array.<File>} | 39 * @type {Array.<File>} |
| 40 * @private | 40 * @private |
| 41 */ | 41 */ |
| 42 this.selectedFileObjects_ = []; | 42 this.selectedFileObjects_ = []; |
| 43 } | 43 } |
| 44 | 44 |
| 45 FileTransferController.prototype = { | 45 FileTransferController.prototype = { |
| 46 __proto__: cr.EventTarget.prototype, | 46 __proto__: cr.EventTarget.prototype, |
| 47 | 47 |
| 48 /** | 48 /** |
| 49 * @this {FileTransferController} | |
|
mtomasz
2013/02/14 04:38:56
Shall we convert it to FileTransferController.prot
yoshiki
2013/02/14 06:17:36
Yes, you're right and I'll convert them to FileTra
| |
| 49 * @param {cr.ui.List} list Items in the list will be draggable. | 50 * @param {cr.ui.List} list Items in the list will be draggable. |
| 50 */ | 51 */ |
| 51 attachDragSource: function(list) { | 52 attachDragSource: function(list) { |
| 52 list.style.webkitUserDrag = 'element'; | 53 list.style.webkitUserDrag = 'element'; |
| 53 list.addEventListener('dragstart', this.onDragStart_.bind(this, list)); | 54 list.addEventListener('dragstart', this.onDragStart_.bind(this, list)); |
| 54 list.addEventListener('dragend', this.onDragEnd_.bind(this, list)); | 55 list.addEventListener('dragend', this.onDragEnd_.bind(this, list)); |
| 55 }, | 56 }, |
| 56 | 57 |
| 57 /** | 58 /** |
| 59 * @this {FileTransferController} | |
| 58 * @param {cr.ui.List} list List itself and its directory items will could | 60 * @param {cr.ui.List} list List itself and its directory items will could |
| 59 * be drop target. | 61 * be drop target. |
| 60 * @param {boolean=} opt_onlyIntoDirectories If true only directory list | 62 * @param {boolean=} opt_onlyIntoDirectories If true only directory list |
| 61 * items could be drop targets. Otherwise any other place of the list | 63 * items could be drop targets. Otherwise any other place of the list |
| 62 * accetps files (putting it into the current directory). | 64 * accetps files (putting it into the current directory). |
| 63 */ | 65 */ |
| 64 attachDropTarget: function(list, opt_onlyIntoDirectories) { | 66 attachDropTarget: function(list, opt_onlyIntoDirectories) { |
| 65 list.addEventListener('dragover', this.onDragOver_.bind(this, | 67 list.addEventListener('dragover', this.onDragOver_.bind(this, |
| 66 !!opt_onlyIntoDirectories, list)); | 68 !!opt_onlyIntoDirectories, list)); |
| 67 list.addEventListener('dragenter', this.onDragEnterList_.bind(this, list)); | 69 list.addEventListener('dragenter', this.onDragEnterList_.bind(this, list)); |
| 68 list.addEventListener('dragleave', this.onDragLeave_.bind(this, list)); | 70 list.addEventListener('dragleave', this.onDragLeave_.bind(this, list)); |
| 69 list.addEventListener('drop', this.onDrop_.bind(this, | 71 list.addEventListener('drop', this.onDrop_.bind(this, |
| 70 !!opt_onlyIntoDirectories)); | 72 !!opt_onlyIntoDirectories)); |
| 71 }, | 73 }, |
| 72 | 74 |
| 75 /** | |
|
mtomasz
2013/02/14 04:38:56
Description missing in several methods, but this m
yoshiki
2013/02/14 06:17:36
There are a lot of missing description of method a
mtomasz
2013/02/14 07:40:09
Sgtm!
| |
| 76 * @this {FileTransferController} | |
| 77 */ | |
| 73 attachBreadcrumbsDropTarget: function(breadcrumbsController) { | 78 attachBreadcrumbsDropTarget: function(breadcrumbsController) { |
| 74 var container = breadcrumbsController.getContainer(); | 79 var container = breadcrumbsController.getContainer(); |
| 75 container.addEventListener('dragover', | 80 container.addEventListener('dragover', |
| 76 this.onDragOver_.bind(this, true, null)); | 81 this.onDragOver_.bind(this, true, null)); |
| 77 container.addEventListener('dragenter', | 82 container.addEventListener('dragenter', |
| 78 this.onDragEnterBreadcrumbs_.bind(this, breadcrumbsController)); | 83 this.onDragEnterBreadcrumbs_.bind(this, breadcrumbsController)); |
| 79 container.addEventListener('dragleave', | 84 container.addEventListener('dragleave', |
| 80 this.onDragLeave_.bind(this, null)); | 85 this.onDragLeave_.bind(this, null)); |
| 81 container.addEventListener('drop', this.onDrop_.bind(this, true)); | 86 container.addEventListener('drop', this.onDrop_.bind(this, true)); |
| 82 }, | 87 }, |
| 83 | 88 |
| 84 /** | 89 /** |
| 85 * Attach handlers of copy, cut and paste operations to the document. | 90 * Attach handlers of copy, cut and paste operations to the document. |
| 91 * @this {FileTransferController} | |
| 86 */ | 92 */ |
| 87 attachCopyPasteHandlers: function() { | 93 attachCopyPasteHandlers: function() { |
| 88 this.document_.addEventListener('beforecopy', | 94 this.document_.addEventListener('beforecopy', |
| 89 this.onBeforeCopy_.bind(this)); | 95 this.onBeforeCopy_.bind(this)); |
| 90 this.document_.addEventListener('copy', | 96 this.document_.addEventListener('copy', |
| 91 this.onCopy_.bind(this)); | 97 this.onCopy_.bind(this)); |
| 92 this.document_.addEventListener('beforecut', | 98 this.document_.addEventListener('beforecut', |
| 93 this.onBeforeCut_.bind(this)); | 99 this.onBeforeCut_.bind(this)); |
| 94 this.document_.addEventListener('cut', | 100 this.document_.addEventListener('cut', |
| 95 this.onCut_.bind(this)); | 101 this.onCut_.bind(this)); |
| 96 this.document_.addEventListener('beforepaste', | 102 this.document_.addEventListener('beforepaste', |
| 97 this.onBeforePaste_.bind(this)); | 103 this.onBeforePaste_.bind(this)); |
| 98 this.document_.addEventListener('paste', | 104 this.document_.addEventListener('paste', |
| 99 this.onPaste_.bind(this)); | 105 this.onPaste_.bind(this)); |
| 100 this.copyCommand_ = this.document_.querySelector('command#copy'); | 106 this.copyCommand_ = this.document_.querySelector('command#copy'); |
| 101 }, | 107 }, |
| 102 | 108 |
| 103 /** | 109 /** |
| 104 * Write the current selection to system clipboard. | 110 * Write the current selection to system clipboard. |
| 105 * | 111 * |
| 112 * @this {FileTransferController} | |
| 106 * @param {DataTransfer} dataTransfer DataTransfer from the event. | 113 * @param {DataTransfer} dataTransfer DataTransfer from the event. |
| 107 * @param {string} effectAllowed Value must be valid for the | 114 * @param {string} effectAllowed Value must be valid for the |
| 108 * |dataTransfer.effectAllowed| property ('move', 'copy', 'copyMove'). | 115 * |dataTransfer.effectAllowed| property ('move', 'copy', 'copyMove'). |
| 109 */ | 116 */ |
| 110 cutOrCopy_: function(dataTransfer, effectAllowed) { | 117 cutOrCopy_: function(dataTransfer, effectAllowed) { |
| 111 var directories = []; | 118 var directories = []; |
| 112 var files = []; | 119 var files = []; |
| 113 var entries = this.selectedEntries_; | 120 var entries = this.selectedEntries_; |
| 114 for (var i = 0; i < entries.length; i++) { | 121 for (var i = 0; i < entries.length; i++) { |
| 115 (entries[i].isDirectory ? directories : files).push(entries[i].fullPath); | 122 (entries[i].isDirectory ? directories : files).push(entries[i].fullPath); |
| 116 } | 123 } |
| 117 | 124 |
| 118 // Tag to check it's filemanager data. | 125 // Tag to check it's filemanager data. |
| 119 dataTransfer.setData('fs/tag', 'filemanager-data'); | 126 dataTransfer.setData('fs/tag', 'filemanager-data'); |
| 120 | 127 |
| 121 dataTransfer.setData('fs/isOnDrive', this.isOnDrive); | 128 dataTransfer.setData('fs/isOnDrive', this.isOnDrive); |
| 122 if (this.currentDirectory) | 129 if (this.currentDirectory) |
| 123 dataTransfer.setData('fs/sourceDir', this.currentDirectory.fullPath); | 130 dataTransfer.setData('fs/sourceDir', this.currentDirectory.fullPath); |
| 124 dataTransfer.setData('fs/directories', directories.join('\n')); | 131 dataTransfer.setData('fs/directories', directories.join('\n')); |
| 125 dataTransfer.setData('fs/files', files.join('\n')); | 132 dataTransfer.setData('fs/files', files.join('\n')); |
| 126 dataTransfer.effectAllowed = effectAllowed; | 133 dataTransfer.effectAllowed = effectAllowed; |
| 127 dataTransfer.setData('fs/effectallowed', effectAllowed); | 134 dataTransfer.setData('fs/effectallowed', effectAllowed); |
| 128 | 135 |
| 129 for (var i = 0; i < this.selectedFileObjects_.length; i++) { | 136 for (var i = 0; i < this.selectedFileObjects_.length; i++) { |
| 130 dataTransfer.items.add(this.selectedFileObjects_[i]); | 137 dataTransfer.items.add(this.selectedFileObjects_[i]); |
| 131 } | 138 } |
| 132 }, | 139 }, |
| 133 | 140 |
| 134 /** | 141 /** |
| 135 * Extracts source root from the |dataTransfer| object. | 142 * Extracts source root from the |dataTransfer| object. |
|
mtomasz
2013/02/14 04:38:56
Shall we add an empty line between description and
yoshiki
2013/02/14 06:17:36
I think we don't always need a blank line. But it
| |
| 143 * @this {FileTransferController} | |
| 136 * @param {DataTransfer} dataTransfer DataTransfer object from the event. | 144 * @param {DataTransfer} dataTransfer DataTransfer object from the event. |
| 137 * @return {string} Path or empty string (if unknown). | 145 * @return {string} Path or empty string (if unknown). |
| 138 */ | 146 */ |
| 139 getSourceRoot_: function(dataTransfer) { | 147 getSourceRoot_: function(dataTransfer) { |
| 140 var sourceDir = dataTransfer.getData('fs/sourceDir'); | 148 var sourceDir = dataTransfer.getData('fs/sourceDir'); |
| 141 if (sourceDir) | 149 if (sourceDir) |
| 142 return PathUtil.getRootPath(sourceDir); | 150 return PathUtil.getRootPath(sourceDir); |
| 143 | 151 |
| 144 // For drive search, sourceDir will be set to null, so we should double | 152 // For drive search, sourceDir will be set to null, so we should double |
| 145 // check that we are not on drive. | 153 // check that we are not on drive. |
| (...skipping 10 matching lines...) Expand all Loading... | |
| 156 if (views[i][DRAG_AND_DROP_GLOBAL_DATA]) | 164 if (views[i][DRAG_AND_DROP_GLOBAL_DATA]) |
| 157 return views[i][DRAG_AND_DROP_GLOBAL_DATA].sourceRoot; | 165 return views[i][DRAG_AND_DROP_GLOBAL_DATA].sourceRoot; |
| 158 } | 166 } |
| 159 | 167 |
| 160 // Unknown source. | 168 // Unknown source. |
| 161 return ''; | 169 return ''; |
| 162 }, | 170 }, |
| 163 | 171 |
| 164 /** | 172 /** |
| 165 * Queue up a file copy operation based on the current system clipboard. | 173 * Queue up a file copy operation based on the current system clipboard. |
| 174 * @this {FileTransferController} | |
| 166 * @param {DataTransfer} dataTransfer System data transfer object. | 175 * @param {DataTransfer} dataTransfer System data transfer object. |
| 167 * @param {string=} opt_destinationPath Paste destination. | 176 * @param {string=} opt_destinationPath Paste destination. |
| 168 * @param {string=} opt_effect Desired drop/paste effect. Could be | 177 * @param {string=} opt_effect Desired drop/paste effect. Could be |
| 169 * 'move'|'copy' (default is copy). Ignored if conflicts with | 178 * 'move'|'copy' (default is copy). Ignored if conflicts with |
| 170 * |dataTransfer.effectAllowed|. | 179 * |dataTransfer.effectAllowed|. |
| 171 * @return {string} Either "copy" or "move". | 180 * @return {string} Either "copy" or "move". |
| 172 */ | 181 */ |
| 173 paste: function(dataTransfer, opt_destinationPath, opt_effect) { | 182 paste: function(dataTransfer, opt_destinationPath, opt_effect) { |
| 174 var destinationPath = opt_destinationPath || | 183 var destinationPath = opt_destinationPath || |
| 175 this.directoryModel_.getCurrentDirPath(); | 184 this.directoryModel_.getCurrentDirPath(); |
| (...skipping 21 matching lines...) Expand all Loading... | |
| 197 targetOnDrive); | 206 targetOnDrive); |
| 198 } else { | 207 } else { |
| 199 console.log('Ignore move into the same folder'); | 208 console.log('Ignore move into the same folder'); |
| 200 } | 209 } |
| 201 | 210 |
| 202 return toMove ? 'move' : 'copy'; | 211 return toMove ? 'move' : 'copy'; |
| 203 }, | 212 }, |
| 204 | 213 |
| 205 /** | 214 /** |
| 206 * Preloads an image thumbnail for the specified file entry. | 215 * Preloads an image thumbnail for the specified file entry. |
| 216 * @this {FileTransferController} | |
| 207 * @param {Entry} entry Entry to preload a thumbnail for. | 217 * @param {Entry} entry Entry to preload a thumbnail for. |
| 208 */ | 218 */ |
| 209 preloadThumbnailImage_: function(entry) { | 219 preloadThumbnailImage_: function(entry) { |
| 210 var imageUrl = entry.toURL(); | 220 var imageUrl = entry.toURL(); |
| 211 var metadataTypes = 'thumbnail|filesystem'; | 221 var metadataTypes = 'thumbnail|filesystem'; |
| 212 this.preloadedThumbnailImageNode_ = this.document_.createElement('div'); | 222 this.preloadedThumbnailImageNode_ = this.document_.createElement('div'); |
| 213 this.preloadedThumbnailImageNode_.className = 'img-container'; | 223 this.preloadedThumbnailImageNode_.className = 'img-container'; |
| 214 this.directoryModel_.getMetadataCache().get( | 224 this.directoryModel_.getMetadataCache().get( |
| 215 imageUrl, | 225 imageUrl, |
| 216 metadataTypes, | 226 metadataTypes, |
| 217 function(metadata) { | 227 function(metadata) { |
| 218 new ThumbnailLoader(imageUrl, | 228 new ThumbnailLoader(imageUrl, |
| 219 ThumbnailLoader.LoaderType.IMAGE, | 229 ThumbnailLoader.LoaderType.IMAGE, |
| 220 metadata). | 230 metadata). |
| 221 load(this.preloadedThumbnailImageNode_, | 231 load(this.preloadedThumbnailImageNode_, |
| 222 ThumbnailLoader.FillMode.FILL); | 232 ThumbnailLoader.FillMode.FILL); |
| 223 }.bind(this)); | 233 }.bind(this)); |
| 224 }, | 234 }, |
| 225 | 235 |
| 226 /** | 236 /** |
| 227 * Renders a drag-and-drop thumbnail. | 237 * Renders a drag-and-drop thumbnail. |
| 238 * @this {FileTransferController} | |
| 228 * @return {HTMLElement} Element containing the thumbnail. | 239 * @return {HTMLElement} Element containing the thumbnail. |
| 229 */ | 240 */ |
| 230 renderThumbnail_: function() { | 241 renderThumbnail_: function() { |
| 231 var length = this.selectedEntries_.length; | 242 var length = this.selectedEntries_.length; |
| 232 | 243 |
| 233 var container = this.document_.querySelector('#drag-container'); | 244 var container = this.document_.querySelector('#drag-container'); |
| 234 var contents = this.document_.createElement('div'); | 245 var contents = this.document_.createElement('div'); |
| 235 contents.className = 'drag-contents'; | 246 contents.className = 'drag-contents'; |
| 236 container.appendChild(contents); | 247 container.appendChild(contents); |
| 237 | 248 |
| (...skipping 24 matching lines...) Expand all Loading... | |
| 262 icon.className = 'detail-icon'; | 273 icon.className = 'detail-icon'; |
| 263 icon.setAttribute('file-type-icon', FileType.getIcon(entry)); | 274 icon.setAttribute('file-type-icon', FileType.getIcon(entry)); |
| 264 contents.appendChild(icon); | 275 contents.appendChild(icon); |
| 265 var label = this.document_.createElement('div'); | 276 var label = this.document_.createElement('div'); |
| 266 label.className = 'label'; | 277 label.className = 'label'; |
| 267 label.textContent = entry.name; | 278 label.textContent = entry.name; |
| 268 contents.appendChild(label); | 279 contents.appendChild(label); |
| 269 return container; | 280 return container; |
| 270 }, | 281 }, |
| 271 | 282 |
| 283 /** | |
| 284 * @this {FileTransferController} | |
| 285 */ | |
| 272 onDragStart_: function(list, event) { | 286 onDragStart_: function(list, event) { |
| 273 // Nothing selected. | 287 // Nothing selected. |
| 274 if (!this.selectedEntries_.length) { | 288 if (!this.selectedEntries_.length) { |
| 275 event.preventDefault(); | 289 event.preventDefault(); |
| 276 return; | 290 return; |
| 277 } | 291 } |
| 278 | 292 |
| 279 var dt = event.dataTransfer; | 293 var dt = event.dataTransfer; |
| 280 var dragThumbnail = this.renderThumbnail_(); | 294 var dragThumbnail = this.renderThumbnail_(); |
| 281 dt.setDragImage(dragThumbnail, 1000, 1000); | 295 dt.setDragImage(dragThumbnail, 1000, 1000); |
| 282 | 296 |
| 283 if (this.canCopyOrDrag_(dt)) { | 297 if (this.canCopyOrDrag_(dt)) { |
| 284 if (this.canCutOrDrag_(dt)) | 298 if (this.canCutOrDrag_(dt)) |
| 285 this.cutOrCopy_(dt, 'copyMove'); | 299 this.cutOrCopy_(dt, 'copyMove'); |
| 286 else | 300 else |
| 287 this.cutOrCopy_(dt, 'copy'); | 301 this.cutOrCopy_(dt, 'copy'); |
| 288 } else { | 302 } else { |
| 289 event.preventDefault(); | 303 event.preventDefault(); |
| 290 } | 304 } |
| 291 | 305 |
| 292 window[DRAG_AND_DROP_GLOBAL_DATA] = { | 306 window[DRAG_AND_DROP_GLOBAL_DATA] = { |
| 293 sourceRoot: this.directoryModel_.getCurrentRootPath() | 307 sourceRoot: this.directoryModel_.getCurrentRootPath() |
| 294 }; | 308 }; |
| 295 }, | 309 }, |
| 296 | 310 |
| 311 /** | |
| 312 * @this {FileTransferController} | |
| 313 */ | |
| 297 onDragEnd_: function(list, event) { | 314 onDragEnd_: function(list, event) { |
| 298 var container = this.document_.querySelector('#drag-container'); | 315 var container = this.document_.querySelector('#drag-container'); |
| 299 container.textContent = ''; | 316 container.textContent = ''; |
| 300 this.setDropTarget_(null); | 317 this.setDropTarget_(null); |
| 301 this.setScrollSpeed_(null, 0); | 318 this.setScrollSpeed_(null, 0); |
| 302 delete window[DRAG_AND_DROP_GLOBAL_DATA]; | 319 delete window[DRAG_AND_DROP_GLOBAL_DATA]; |
| 303 }, | 320 }, |
| 304 | 321 |
| 322 /** | |
| 323 * @this {FileTransferController} | |
| 324 */ | |
| 305 onDragOver_: function(onlyIntoDirectories, list, event) { | 325 onDragOver_: function(onlyIntoDirectories, list, event) { |
| 306 if (list) { | 326 if (list) { |
| 307 // Scroll the list if mouse close to the top or the bottom. | 327 // Scroll the list if mouse close to the top or the bottom. |
| 308 var rect = list.getBoundingClientRect(); | 328 var rect = list.getBoundingClientRect(); |
| 309 if (event.clientY - rect.top < rect.bottom - event.clientY) { | 329 if (event.clientY - rect.top < rect.bottom - event.clientY) { |
| 310 this.setScrollSpeed_(list, | 330 this.setScrollSpeed_(list, |
| 311 -this.calculateScrollSpeed_(event.clientY - rect.top)); | 331 -this.calculateScrollSpeed_(event.clientY - rect.top)); |
| 312 } else { | 332 } else { |
| 313 this.setScrollSpeed_(list, | 333 this.setScrollSpeed_(list, |
| 314 this.calculateScrollSpeed_(rect.bottom - event.clientY)); | 334 this.calculateScrollSpeed_(rect.bottom - event.clientY)); |
| 315 } | 335 } |
| 316 } | 336 } |
| 317 event.preventDefault(); | 337 event.preventDefault(); |
| 318 var path = this.destinationPath_ || | 338 var path = this.destinationPath_ || |
| 319 (!onlyIntoDirectories && this.directoryModel_.getCurrentDirPath()); | 339 (!onlyIntoDirectories && this.directoryModel_.getCurrentDirPath()); |
| 320 event.dataTransfer.dropEffect = this.selectDropEffect_(event, path); | 340 event.dataTransfer.dropEffect = this.selectDropEffect_(event, path); |
| 321 event.preventDefault(); | 341 event.preventDefault(); |
| 322 }, | 342 }, |
| 323 | 343 |
| 344 /** | |
| 345 * @this {FileTransferController} | |
| 346 */ | |
| 324 onDragEnterList_: function(list, event) { | 347 onDragEnterList_: function(list, event) { |
| 325 event.preventDefault(); // Required to prevent the cursor flicker. | 348 event.preventDefault(); // Required to prevent the cursor flicker. |
| 326 this.lastEnteredTarget_ = event.target; | 349 this.lastEnteredTarget_ = event.target; |
| 327 var item = list.getListItemAncestor(event.target); | 350 var item = list.getListItemAncestor(event.target); |
| 328 item = item && list.isItem(item) ? item : null; | 351 item = item && list.isItem(item) ? item : null; |
| 329 if (item == this.dropTarget_) | 352 if (item == this.dropTarget_) |
| 330 return; | 353 return; |
| 331 | 354 |
| 332 var entry = item && list.dataModel.item(item.listIndex); | 355 var entry = item && list.dataModel.item(item.listIndex); |
| 333 if (entry) { | 356 if (entry) { |
| 334 this.setDropTarget_(item, entry.isDirectory, event.dataTransfer, | 357 this.setDropTarget_(item, entry.isDirectory, event.dataTransfer, |
| 335 entry.fullPath); | 358 entry.fullPath); |
| 336 } else { | 359 } else { |
| 337 this.setDropTarget_(null); | 360 this.setDropTarget_(null); |
| 338 } | 361 } |
| 339 }, | 362 }, |
| 340 | 363 |
| 364 /** | |
| 365 * @this {FileTransferController} | |
| 366 */ | |
| 341 onDragEnterBreadcrumbs_: function(breadcrumbsContainer, event) { | 367 onDragEnterBreadcrumbs_: function(breadcrumbsContainer, event) { |
| 342 event.preventDefault(); // Required to prevent the cursor flicker. | 368 event.preventDefault(); // Required to prevent the cursor flicker. |
| 343 this.lastEnteredTarget_ = event.target; | 369 this.lastEnteredTarget_ = event.target; |
| 344 var path = breadcrumbsContainer.getTargetPath(event); | 370 var path = breadcrumbsContainer.getTargetPath(event); |
| 345 if (!path) | 371 if (!path) |
| 346 return; | 372 return; |
| 347 | 373 |
| 348 this.setDropTarget_(event.target, true, event.dataTransfer, path); | 374 this.setDropTarget_(event.target, true, event.dataTransfer, path); |
| 349 }, | 375 }, |
| 350 | 376 |
| 377 /** | |
| 378 * @this {FileTransferController} | |
| 379 */ | |
| 351 onDragLeave_: function(list, event) { | 380 onDragLeave_: function(list, event) { |
| 352 // If mouse moves from one element to another the 'dragenter' | 381 // If mouse moves from one element to another the 'dragenter' |
| 353 // event for the new element comes before the 'dragleave' event for | 382 // event for the new element comes before the 'dragleave' event for |
| 354 // the old one. In this case event.target != this.lastEnteredTarget_ | 383 // the old one. In this case event.target != this.lastEnteredTarget_ |
| 355 // and handler of the 'dragenter' event has already caried of | 384 // and handler of the 'dragenter' event has already caried of |
| 356 // drop target. So event.target == this.lastEnteredTarget_ | 385 // drop target. So event.target == this.lastEnteredTarget_ |
| 357 // could only be if mouse goes out of listened element. | 386 // could only be if mouse goes out of listened element. |
| 358 if (event.target == this.lastEnteredTarget_) { | 387 if (event.target == this.lastEnteredTarget_) { |
| 359 this.setDropTarget_(null); | 388 this.setDropTarget_(null); |
| 360 this.lastEnteredTarget_ = null; | 389 this.lastEnteredTarget_ = null; |
| 361 } | 390 } |
| 362 if (event.target == list) | 391 if (event.target == list) |
| 363 this.setScrollSpeed_(list, 0); | 392 this.setScrollSpeed_(list, 0); |
| 364 }, | 393 }, |
| 365 | 394 |
| 395 /** | |
| 396 * @this {FileTransferController} | |
| 397 */ | |
| 366 onDrop_: function(onlyIntoDirectories, event) { | 398 onDrop_: function(onlyIntoDirectories, event) { |
| 367 if (onlyIntoDirectories && !this.dropTarget_) | 399 if (onlyIntoDirectories && !this.dropTarget_) |
| 368 return; | 400 return; |
| 369 var destinationPath = this.destinationPath_ || | 401 var destinationPath = this.destinationPath_ || |
| 370 this.directoryModel_.getCurrentDirPath(); | 402 this.directoryModel_.getCurrentDirPath(); |
| 371 if (!this.canPasteOrDrop_(event.dataTransfer, destinationPath)) | 403 if (!this.canPasteOrDrop_(event.dataTransfer, destinationPath)) |
| 372 return; | 404 return; |
| 373 event.preventDefault(); | 405 event.preventDefault(); |
| 374 this.paste(event.dataTransfer, destinationPath, | 406 this.paste(event.dataTransfer, destinationPath, |
| 375 this.selectDropEffect_(event, destinationPath)); | 407 this.selectDropEffect_(event, destinationPath)); |
| 376 this.setDropTarget_(null); | 408 this.setDropTarget_(null); |
| 377 this.setScrollSpeed_(null, 0); | 409 this.setScrollSpeed_(null, 0); |
| 378 }, | 410 }, |
| 379 | 411 |
| 412 /** | |
| 413 * @this {FileTransferController} | |
| 414 */ | |
| 380 setDropTarget_: function(domElement, isDirectory, opt_dataTransfer, | 415 setDropTarget_: function(domElement, isDirectory, opt_dataTransfer, |
| 381 opt_destinationPath) { | 416 opt_destinationPath) { |
| 382 if (this.dropTarget_ == domElement) | 417 if (this.dropTarget_ == domElement) |
| 383 return; | 418 return; |
| 384 | 419 |
| 385 /** @type {string?} */ | 420 /** @type {string?} */ |
| 386 this.destinationPath_ = null; | 421 this.destinationPath_ = null; |
| 387 if (domElement) { | 422 if (domElement) { |
| 388 if (isDirectory && | 423 if (isDirectory && |
| 389 this.canPasteOrDrop_(opt_dataTransfer, opt_destinationPath)) { | 424 this.canPasteOrDrop_(opt_dataTransfer, opt_destinationPath)) { |
| (...skipping 14 matching lines...) Expand all Loading... | |
| 404 clearTimeout(this.navigateTimer_); | 439 clearTimeout(this.navigateTimer_); |
| 405 this.navigateTimer_ = undefined; | 440 this.navigateTimer_ = undefined; |
| 406 } | 441 } |
| 407 if (domElement && isDirectory && opt_destinationPath) { | 442 if (domElement && isDirectory && opt_destinationPath) { |
| 408 this.navigateTimer_ = setTimeout(function() { | 443 this.navigateTimer_ = setTimeout(function() { |
| 409 this.directoryModel_.changeDirectory(opt_destinationPath); | 444 this.directoryModel_.changeDirectory(opt_destinationPath); |
| 410 }.bind(this), 2000); | 445 }.bind(this), 2000); |
| 411 } | 446 } |
| 412 }, | 447 }, |
| 413 | 448 |
| 414 isDocumentWideEvent_: function(event) { | 449 /** |
| 450 * @this {FileTransferController} | |
| 451 * @return {boolean} Returns false if {@code <input type="text">} element is | |
| 452 * currently active. Otherwise, returns true. | |
| 453 */ | |
| 454 isDocumentWideEvent_: function() { | |
| 415 return this.document_.activeElement.nodeName.toLowerCase() != 'input' || | 455 return this.document_.activeElement.nodeName.toLowerCase() != 'input' || |
| 416 this.document_.activeElement.type.toLowerCase() != 'text'; | 456 this.document_.activeElement.type.toLowerCase() != 'text'; |
| 417 }, | 457 }, |
| 418 | 458 |
| 459 /** | |
| 460 * @this {FileTransferController} | |
| 461 */ | |
| 419 onCopy_: function(event) { | 462 onCopy_: function(event) { |
| 420 if (!this.isDocumentWideEvent_(event) || | 463 if (!this.isDocumentWideEvent_() || |
| 421 !this.canCopyOrDrag_()) { | 464 !this.canCopyOrDrag_()) { |
| 422 return; | 465 return; |
| 423 } | 466 } |
| 424 event.preventDefault(); | 467 event.preventDefault(); |
| 425 this.cutOrCopy_(event.clipboardData, 'copy'); | 468 this.cutOrCopy_(event.clipboardData, 'copy'); |
| 426 this.notify_('selection-copied'); | 469 this.notify_('selection-copied'); |
| 427 }, | 470 }, |
| 428 | 471 |
| 472 /** | |
| 473 * @this {FileTransferController} | |
| 474 */ | |
| 429 onBeforeCopy_: function(event) { | 475 onBeforeCopy_: function(event) { |
| 430 if (!this.isDocumentWideEvent_(event)) | 476 if (!this.isDocumentWideEvent_()) |
| 431 return; | 477 return; |
| 432 | 478 |
| 433 // queryCommandEnabled returns true if event.returnValue is false. | 479 // queryCommandEnabled returns true if event.returnValue is false. |
| 434 event.returnValue = !this.canCopyOrDrag_(); | 480 event.returnValue = !this.canCopyOrDrag_(); |
| 435 }, | 481 }, |
| 436 | 482 |
| 483 /** | |
| 484 * @this {FileTransferController} | |
| 485 * @return {boolean} Returns true if some files are selected and all the file | |
| 486 * on drive is available to be copied. Otherwise, returns false. | |
| 487 */ | |
| 437 canCopyOrDrag_: function() { | 488 canCopyOrDrag_: function() { |
| 438 if (this.isOnDrive && | 489 if (this.isOnDrive && |
| 439 this.directoryModel_.isDriveOffline() && | 490 this.directoryModel_.isDriveOffline() && |
| 440 !this.allDriveFilesAvailable) | 491 !this.allDriveFilesAvailable) |
| 441 return false; | 492 return false; |
| 442 return this.selectedEntries_.length > 0; | 493 return this.selectedEntries_.length > 0; |
| 443 }, | 494 }, |
| 444 | 495 |
| 496 /** | |
| 497 * @this {FileTransferController} | |
| 498 */ | |
| 445 onCut_: function(event) { | 499 onCut_: function(event) { |
| 446 if (!this.isDocumentWideEvent_(event) || | 500 if (!this.isDocumentWideEvent_() || |
| 447 !this.canCutOrDrag_()) { | 501 !this.canCutOrDrag_()) { |
| 448 return; | 502 return; |
| 449 } | 503 } |
| 450 event.preventDefault(); | 504 event.preventDefault(); |
| 451 this.cutOrCopy_(event.clipboardData, 'move'); | 505 this.cutOrCopy_(event.clipboardData, 'move'); |
| 452 this.notify_('selection-cut'); | 506 this.notify_('selection-cut'); |
| 453 }, | 507 }, |
| 454 | 508 |
| 509 /** | |
| 510 * @this {FileTransferController} | |
| 511 */ | |
| 455 onBeforeCut_: function(event) { | 512 onBeforeCut_: function(event) { |
| 456 if (!this.isDocumentWideEvent_(event)) | 513 if (!this.isDocumentWideEvent_()) |
| 457 return; | 514 return; |
| 458 // queryCommandEnabled returns true if event.returnValue is false. | 515 // queryCommandEnabled returns true if event.returnValue is false. |
| 459 event.returnValue = !this.canCutOrDrag_(); | 516 event.returnValue = !this.canCutOrDrag_(); |
| 460 }, | 517 }, |
| 461 | 518 |
| 519 /** | |
| 520 * @this {FileTransferController} | |
| 521 * @return {boolean} Returns true if some files are selected and all the file | |
| 522 * on drive is available to be cut. Otherwise, returns false. | |
| 523 */ | |
| 462 canCutOrDrag_: function() { | 524 canCutOrDrag_: function() { |
| 463 return !this.readonly && this.canCopyOrDrag_(); | 525 return !this.readonly && this.canCopyOrDrag_(); |
| 464 }, | 526 }, |
| 465 | 527 |
| 528 /** | |
| 529 * @this {FileTransferController} | |
| 530 */ | |
| 466 onPaste_: function(event) { | 531 onPaste_: function(event) { |
| 467 // Need to update here since 'beforepaste' doesn't fire. | 532 // Need to update here since 'beforepaste' doesn't fire. |
| 468 if (!this.isDocumentWideEvent_(event) || | 533 if (!this.isDocumentWideEvent_() || |
| 469 !this.canPasteOrDrop_(event.clipboardData)) { | 534 !this.canPasteOrDrop_(event.clipboardData)) { |
| 470 return; | 535 return; |
| 471 } | 536 } |
| 472 event.preventDefault(); | 537 event.preventDefault(); |
| 473 var effect = this.paste(event.clipboardData); | 538 var effect = this.paste(event.clipboardData); |
| 474 | 539 |
| 475 // On cut, we clear the clipboard after the file is pasted/moved so we don't | 540 // On cut, we clear the clipboard after the file is pasted/moved so we don't |
| 476 // try to move/delete the original file again. | 541 // try to move/delete the original file again. |
| 477 if (effect == 'move') { | 542 if (effect == 'move') { |
| 478 this.simulateCommand_('cut', function(event) { | 543 this.simulateCommand_('cut', function(event) { |
| 479 event.preventDefault(); | 544 event.preventDefault(); |
| 480 event.clipboardData.setData('fs/clear', ''); | 545 event.clipboardData.setData('fs/clear', ''); |
| 481 }); | 546 }); |
| 482 } | 547 } |
| 483 }, | 548 }, |
| 484 | 549 |
| 550 /** | |
| 551 * @this {FileTransferController} | |
| 552 */ | |
| 485 onBeforePaste_: function(event) { | 553 onBeforePaste_: function(event) { |
| 486 if (!this.isDocumentWideEvent_(event)) | 554 if (!this.isDocumentWideEvent_()) |
| 487 return; | 555 return; |
| 488 // queryCommandEnabled returns true if event.returnValue is false. | 556 // queryCommandEnabled returns true if event.returnValue is false. |
| 489 event.returnValue = !this.canPasteOrDrop_(event.clipboardData); | 557 event.returnValue = !this.canPasteOrDrop_(event.clipboardData); |
| 490 }, | 558 }, |
| 491 | 559 |
| 560 /** | |
| 561 * @this {FileTransferController} | |
| 562 * @return {boolean} Returns true if {@code opt_destinationPath} is | |
| 563 * available to be pasted to. Otherwise, returns false. | |
| 564 */ | |
| 492 canPasteOrDrop_: function(dataTransfer, opt_destinationPath) { | 565 canPasteOrDrop_: function(dataTransfer, opt_destinationPath) { |
| 493 var destinationPath = opt_destinationPath || | 566 var destinationPath = opt_destinationPath || |
| 494 this.directoryModel_.getCurrentDirPath(); | 567 this.directoryModel_.getCurrentDirPath(); |
| 495 if (this.directoryModel_.isPathReadOnly(destinationPath)) { | 568 if (this.directoryModel_.isPathReadOnly(destinationPath)) { |
| 496 return false; | 569 return false; |
| 497 } | 570 } |
| 498 if (this.directoryModel_.isSearching()) | 571 if (this.directoryModel_.isSearching()) |
| 499 return false; | 572 return false; |
| 500 | 573 |
| 501 if (!dataTransfer.types || dataTransfer.types.indexOf('fs/tag') == -1) | 574 if (!dataTransfer.types || dataTransfer.types.indexOf('fs/tag') == -1) |
| 502 return false; // Unsupported type of content. | 575 return false; // Unsupported type of content. |
| 503 if (dataTransfer.getData('fs/tag') == '') { | 576 if (dataTransfer.getData('fs/tag') == '') { |
| 504 // Data protected. Other checks are not possible but it makes sense to | 577 // Data protected. Other checks are not possible but it makes sense to |
| 505 // let the user try. | 578 // let the user try. |
| 506 return true; | 579 return true; |
| 507 } | 580 } |
| 508 | 581 |
| 509 var directories = dataTransfer.getData('fs/directories').split('\n'). | 582 var directories = dataTransfer.getData('fs/directories').split('\n'). |
| 510 filter(function(d) { return d != ''; }); | 583 filter(function(d) { return d != ''; }); |
| 511 | 584 |
| 512 for (var i = 0; i < directories.length; i++) { | 585 for (var i = 0; i < directories.length; i++) { |
| 513 if (destinationPath.substr(0, directories[i].length) == directories[i]) | 586 if (destinationPath.substr(0, directories[i].length) == directories[i]) |
| 514 return false; // recursive paste. | 587 return false; // recursive paste. |
| 515 } | 588 } |
| 516 | 589 |
| 517 return true; | 590 return true; |
| 518 }, | 591 }, |
| 519 | 592 |
| 593 /** | |
| 594 * Execute paste command. | |
| 595 * | |
| 596 * @this {FileTransferController} | |
| 597 * @return {boolean} Returns true, the paste is success. Otherwise, returns | |
| 598 * false. | |
| 599 */ | |
| 520 queryPasteCommandEnabled: function() { | 600 queryPasteCommandEnabled: function() { |
| 521 if (!this.isDocumentWideEvent_()) { | 601 if (!this.isDocumentWideEvent_()) { |
| 522 return false; | 602 return false; |
| 523 } | 603 } |
| 524 | 604 |
| 525 // HACK(serya): return this.document_.queryCommandEnabled('paste') | 605 // HACK(serya): return this.document_.queryCommandEnabled('paste') |
| 526 // should be used. | 606 // should be used. |
| 527 var result; | 607 var result; |
| 528 this.simulateCommand_('paste', function(event) { | 608 this.simulateCommand_('paste', function(event) { |
| 529 result = this.canPasteOrDrop_(event.clipboardData); | 609 result = this.canPasteOrDrop_(event.clipboardData); |
| 530 }.bind(this)); | 610 }.bind(this)); |
| 531 return result; | 611 return result; |
| 532 }, | 612 }, |
| 533 | 613 |
| 534 /** | 614 /** |
| 535 * Allows to simulate commands to get access to clipboard. | 615 * Allows to simulate commands to get access to clipboard. |
| 616 * @this {FileTransferController} | |
| 536 * @param {string} command 'copy', 'cut' or 'paste'. | 617 * @param {string} command 'copy', 'cut' or 'paste'. |
| 537 * @param {Function} handler Event handler. | 618 * @param {Function} handler Event handler. |
| 538 */ | 619 */ |
| 539 simulateCommand_: function(command, handler) { | 620 simulateCommand_: function(command, handler) { |
| 540 var iframe = this.document_.querySelector('#command-dispatcher'); | 621 var iframe = this.document_.querySelector('#command-dispatcher'); |
| 541 var doc = iframe.contentDocument; | 622 var doc = iframe.contentDocument; |
| 542 doc.addEventListener(command, handler); | 623 doc.addEventListener(command, handler); |
| 543 doc.execCommand(command); | 624 doc.execCommand(command); |
| 544 doc.removeEventListener(command, handler); | 625 doc.removeEventListener(command, handler); |
| 545 }, | 626 }, |
| 546 | 627 |
| 628 /** | |
| 629 * @this {FileTransferController} | |
| 630 */ | |
| 547 onSelectionChanged_: function(event) { | 631 onSelectionChanged_: function(event) { |
| 548 var entries = this.selectedEntries_; | 632 var entries = this.selectedEntries_; |
| 549 var files = this.selectedFileObjects_ = []; | 633 var files = this.selectedFileObjects_ = []; |
| 550 this.preloadedThumbnailImageNode_ = null; | 634 this.preloadedThumbnailImageNode_ = null; |
| 551 | 635 |
| 552 var fileEntries = []; | 636 var fileEntries = []; |
| 553 for (var i = 0; i < entries.length; i++) { | 637 for (var i = 0; i < entries.length; i++) { |
| 554 if (entries[i].isFile) | 638 if (entries[i].isFile) |
| 555 fileEntries.push(entries[i]); | 639 fileEntries.push(entries[i]); |
| 556 } | 640 } |
| (...skipping 30 matching lines...) Expand all Loading... | |
| 587 this.copyCommand_.disabled = !this.canCopyOrDrag_(); | 671 this.copyCommand_.disabled = !this.canCopyOrDrag_(); |
| 588 | 672 |
| 589 if (this.allDriveFilesAvailable) | 673 if (this.allDriveFilesAvailable) |
| 590 prepareFileObjects(); | 674 prepareFileObjects(); |
| 591 }.bind(this)); | 675 }.bind(this)); |
| 592 } else { | 676 } else { |
| 593 prepareFileObjects(); | 677 prepareFileObjects(); |
| 594 } | 678 } |
| 595 }, | 679 }, |
| 596 | 680 |
| 681 /** | |
| 682 * @this {FileTransferController} | |
| 683 */ | |
| 597 get currentDirectory() { | 684 get currentDirectory() { |
| 598 if (this.directoryModel_.isSearching() && this.isOnDrive) | 685 if (this.directoryModel_.isSearching() && this.isOnDrive) |
| 599 return null; | 686 return null; |
| 600 return this.directoryModel_.getCurrentDirEntry(); | 687 return this.directoryModel_.getCurrentDirEntry(); |
| 601 }, | 688 }, |
| 602 | 689 |
| 690 /** | |
| 691 * @this {FileTransferController} | |
| 692 */ | |
| 603 get readonly() { | 693 get readonly() { |
| 604 return this.directoryModel_.isReadOnly(); | 694 return this.directoryModel_.isReadOnly(); |
| 605 }, | 695 }, |
| 606 | 696 |
| 697 /** | |
| 698 * @this {FileTransferController} | |
| 699 */ | |
| 607 get isOnDrive() { | 700 get isOnDrive() { |
| 608 return this.directoryModel_.getCurrentRootType() === RootType.DRIVE; | 701 return this.directoryModel_.getCurrentRootType() === RootType.DRIVE; |
| 609 }, | 702 }, |
| 610 | 703 |
| 704 /** | |
| 705 * @this {FileTransferController} | |
| 706 */ | |
| 611 notify_: function(eventName) { | 707 notify_: function(eventName) { |
| 612 var self = this; | 708 var self = this; |
| 613 // Set timeout to avoid recursive events. | 709 // Set timeout to avoid recursive events. |
| 614 setTimeout(function() { | 710 setTimeout(function() { |
| 615 cr.dispatchSimpleEvent(self, eventName); | 711 cr.dispatchSimpleEvent(self, eventName); |
| 616 }, 0); | 712 }, 0); |
| 617 }, | 713 }, |
| 618 | 714 |
| 619 /** | 715 /** |
| 716 * @this {FileTransferController} | |
| 620 * @type {Array.<Entry>} | 717 * @type {Array.<Entry>} |
| 621 */ | 718 */ |
| 622 get selectedEntries_() { | 719 get selectedEntries_() { |
| 623 var list = this.directoryModel_.getFileList(); | 720 var list = this.directoryModel_.getFileList(); |
| 624 var selectedIndexes = this.directoryModel_.getFileListSelection(). | 721 var selectedIndexes = this.directoryModel_.getFileListSelection(). |
| 625 selectedIndexes; | 722 selectedIndexes; |
| 626 var entries = selectedIndexes.map(function(index) { | 723 var entries = selectedIndexes.map(function(index) { |
| 627 return list.item(index); | 724 return list.item(index); |
| 628 }); | 725 }); |
| 629 | 726 |
| 630 // TODO(serya): Diagnostics for http://crbug/129642 | 727 // TODO(serya): Diagnostics for http://crbug/129642 |
| 631 if (entries.indexOf(undefined) != -1) { | 728 if (entries.indexOf(undefined) != -1) { |
| 632 var index = entries.indexOf(undefined); | 729 var index = entries.indexOf(undefined); |
| 633 entries = entries.filter(function(e) { return !!e; }); | 730 entries = entries.filter(function(e) { return !!e; }); |
| 634 console.error('Invalid selection found: list items: ', list.length, | 731 console.error('Invalid selection found: list items: ', list.length, |
| 635 'wrong indexe value: ', selectedIndexes[index], | 732 'wrong indexe value: ', selectedIndexes[index], |
| 636 'Stack trace: ', new Error().stack); | 733 'Stack trace: ', new Error().stack); |
| 637 } | 734 } |
| 638 return entries; | 735 return entries; |
| 639 }, | 736 }, |
| 640 | 737 |
| 738 /** | |
| 739 * @this {FileTransferController} | |
| 740 * @return {string} Returns the appropriate drop query type ('none', 'move' | |
| 741 * or copy') to the current modifiers status and the destination. | |
| 742 */ | |
| 641 selectDropEffect_: function(event, destinationPath) { | 743 selectDropEffect_: function(event, destinationPath) { |
| 642 if (!destinationPath || | 744 if (!destinationPath || |
| 643 this.directoryModel_.isPathReadOnly(destinationPath)) | 745 this.directoryModel_.isPathReadOnly(destinationPath)) |
| 644 return 'none'; | 746 return 'none'; |
| 645 if (event.dataTransfer.effectAllowed == 'copyMove' && | 747 if (event.dataTransfer.effectAllowed == 'copyMove' && |
| 646 this.getSourceRoot_(event.dataTransfer) == | 748 this.getSourceRoot_(event.dataTransfer) == |
| 647 PathUtil.getRootPath(destinationPath) && | 749 PathUtil.getRootPath(destinationPath) && |
| 648 !event.ctrlKey) { | 750 !event.ctrlKey) { |
| 649 return 'move'; | 751 return 'move'; |
| 650 } | 752 } |
| 651 if (event.dataTransfer.effectAllowed == 'copyMove' && | 753 if (event.dataTransfer.effectAllowed == 'copyMove' && |
| 652 event.shiftKey) { | 754 event.shiftKey) { |
| 653 return 'move'; | 755 return 'move'; |
| 654 } | 756 } |
| 655 return 'copy'; | 757 return 'copy'; |
| 656 }, | 758 }, |
| 657 | 759 |
| 760 /** | |
| 761 * @this {FileTransferController} | |
| 762 * @return {number} Returns an appropriate scroll speed to the distance. | |
| 763 */ | |
| 658 calculateScrollSpeed_: function(distance) { | 764 calculateScrollSpeed_: function(distance) { |
| 659 var SCROLL_AREA = 25; // Pixels. | 765 var SCROLL_AREA = 25; // Pixels. |
| 660 var MIN_SCROLL_SPEED = 50; // Pixels/sec. | 766 var MIN_SCROLL_SPEED = 50; // Pixels/sec. |
| 661 var MAX_SCROLL_SPEED = 300; // Pixels/sec. | 767 var MAX_SCROLL_SPEED = 300; // Pixels/sec. |
| 662 if (distance < 0 || distance > SCROLL_AREA) | 768 if (distance < 0 || distance > SCROLL_AREA) |
| 663 return 0; | 769 return 0; |
| 664 return MAX_SCROLL_SPEED - (MAX_SCROLL_SPEED - MIN_SCROLL_SPEED) * | 770 return MAX_SCROLL_SPEED - (MAX_SCROLL_SPEED - MIN_SCROLL_SPEED) * |
| 665 (distance / SCROLL_AREA); | 771 (distance / SCROLL_AREA); |
| 666 }, | 772 }, |
| 667 | 773 |
| 774 /** | |
| 775 * @this {FileTransferController} | |
| 776 */ | |
| 668 setScrollSpeed_: function(list, speed) { | 777 setScrollSpeed_: function(list, speed) { |
| 669 var SCROLL_INTERVAL = 200; // Milliseconds. | 778 var SCROLL_INTERVAL = 200; // Milliseconds. |
| 670 if (speed == 0 && this.scrollInterval_) { | 779 if (speed == 0 && this.scrollInterval_) { |
| 671 clearInterval(this.scrollInterval_); | 780 clearInterval(this.scrollInterval_); |
| 672 this.scrollInterval_ = null; | 781 this.scrollInterval_ = null; |
| 673 } else if (speed != 0 && !this.scrollInterval_) { | 782 } else if (speed != 0 && !this.scrollInterval_) { |
| 674 this.scrollInterval_ = setInterval(this.scroll_.bind(this), | 783 this.scrollInterval_ = setInterval(this.scroll_.bind(this), |
| 675 SCROLL_INTERVAL); | 784 SCROLL_INTERVAL); |
| 676 } | 785 } |
| 677 this.scrollStep_ = speed * SCROLL_INTERVAL / 1000; | 786 this.scrollStep_ = speed * SCROLL_INTERVAL / 1000; |
| 678 this.scrollList_ = list; | 787 this.scrollList_ = list; |
| 679 }, | 788 }, |
| 680 | 789 |
| 790 /** | |
| 791 * @this {FileTransferController} | |
| 792 */ | |
| 681 scroll_: function() { | 793 scroll_: function() { |
| 682 if (this.scrollList_) | 794 if (this.scrollList_) |
| 683 this.scrollList_.scrollTop += this.scrollStep_; | 795 this.scrollList_.scrollTop += this.scrollStep_; |
| 684 } | 796 } |
| 685 }; | 797 }; |
| OLD | NEW |