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