Chromium Code Reviews| Index: chrome/renderer/resources/extensions/downloads_custom_bindings.js |
| diff --git a/chrome/renderer/resources/extensions/downloads_custom_bindings.js b/chrome/renderer/resources/extensions/downloads_custom_bindings.js |
| new file mode 100644 |
| index 0000000000000000000000000000000000000000..428f7f14151c67ecd47c4381a06e7da3fb694b8c |
| --- /dev/null |
| +++ b/chrome/renderer/resources/extensions/downloads_custom_bindings.js |
| @@ -0,0 +1,138 @@ |
| +// Copyright (c) 2013 The Chromium Authors. All rights reserved. |
| +// Use of this source code is governed by a BSD-style license that can be |
| +// found in the LICENSE file. |
| + |
| +// Custom bindings for the downloads API. |
| + |
| +var downloadsNatives = requireNative('downloads'); |
| +var chromeHidden = requireNative('chrome_hidden').GetChromeHidden(); |
| +var sendRequest = require('sendRequest').sendRequest; |
| +var validate = require('schemaUtils').validate; |
| + |
| +function DownloadsEvent(eventName, opt_argSchemas, opt_extraArgSchemas, |
| + opt_eventOptions) { |
| + if (typeof eventName != 'string') |
| + throw new Error('chrome.DownloadsEvent requires an event name.'); |
| + |
| + this.eventName_ = eventName; |
| + this.determiningFilename_ = (eventName == 'downloads.onDeterminingFilename'); |
| + this.argSchemas_ = opt_argSchemas; |
| + this.extraArgSchemas_ = opt_extraArgSchemas; |
| + this.eventOptions_ = chromeHidden.parseEventOptions(opt_eventOptions); |
| + if (this.determiningFilename_) { |
| + this.subEvents_ = []; |
| + } else { |
| + this.actualEvent_ = |
| + new chrome.Event(eventName, opt_argSchemas, opt_eventOptions); |
| + } |
| +} |
| + |
| +// Test if the given callback is registered for this event. |
| +DownloadsEvent.prototype.hasListener = function(cb) { |
| + if (!this.eventOptions_.supportsListeners) |
| + throw new Error('This event does not support listeners.'); |
| + return this.findListener_(cb) > -1; |
| +}; |
| + |
| +// Test if any callbacks are registered fur thus event. |
|
vabr (Chromium)
2013/01/11 12:43:40
possibly a typo: "fur thus"
benjhayden
2013/01/11 21:21:27
Done.
|
| +DownloadsEvent.prototype.hasListeners = function() { |
| + if (!this.eventOptions_.supportsListeners) |
| + throw new Error('This event does not support listeners.'); |
| + return (this.determiningFilename_ ? (this.subEvents_.length > 0) : |
| + this.actualEvent_.hasListeners()); |
| +}; |
| + |
| +DownloadsEvent.prototype.addListener = function(cb) { |
| + if (!this.eventOptions_.supportsListeners) |
| + throw new Error('This event does not support listeners.'); |
| + if (!this.determiningFilename_) { |
| + this.actualEvent_.addListener(cb); |
| + return; |
| + } |
| + var entry = {callback: cb}; |
| + entry.determiner_id = downloadsNatives.GetFilenameDeterminerId(); |
| + entry.subEvent = new chrome.Event( |
| + this.eventName_ + '/' + entry.determiner_id, this.argSchemas_); |
| + chromeHidden.internalAPIs.downloadsInternal.addFilenameDeterminer( |
| + entry.determiner_id); |
| + entry.subEventCallback = function() { |
| + var download_id = arguments[0].id; |
| + try { |
| + var result = cb.apply(null, arguments); |
| + if (typeof(result) == 'object' && result.filename) { |
|
battre
2013/01/11 14:29:37
only if you pass a filename, you allow to set over
benjhayden
2013/01/11 21:21:27
Done.
|
| + chromeHidden.internalAPIs.downloadsInternal.determineFilename( |
| + entry.determiner_id, |
| + download_id, |
| + result.filename, |
| + result.overwrite || false); |
| + } else { |
| + chromeHidden.internalAPIs.downloadsInternal.determineFilename( |
| + entry.determiner_id, |
| + download_id); |
| + } |
| + } catch (e) { |
| + chromeHidden.internalAPIs.downloadsInternal.determineFilename( |
| + entry.determiner_id, |
| + download_id); |
| + throw e; |
| + } |
| + }; |
| + this.subEvents_.push(entry); |
| + entry.subEvent.addListener(entry.subEventCallback); |
| +}; |
| + |
| +DownloadsEvent.prototype.removeListener = function(cb) { |
| + if (!this.eventOptions_.supportsListeners) |
| + throw new Error('This event does not support listeners.'); |
| + if (!this.determiningFilename_) { |
| + this.actualEvent_.removeListener(cb); |
| + return; |
| + } |
| + var idx; |
| + while ((idx = this.findListener_(cb)) >= 0) { |
| + var e = this.subEvents_[idx]; |
| + e.subEvent.removeListener(e.subEventCallback); |
| + chromeHidden.internalAPIs.downloadsInternal.removeFilenameDeterminer( |
| + e.determiner_id); |
| + if (e.subEvent.hasListeners()) { |
| + console.error('Internal error: subEvent has orphaned listeners.'); |
| + } |
| + this.subEvents_.splice(idx, 1); |
| + } |
| +}; |
| + |
| +DownloadsEvent.prototype.findListener_ = function(cb) { |
| + if (!this.determiningFilename_) { |
| + return this.actualEvent_.findListener(cb); |
| + } |
| + for (var i in this.subEvents_) { |
| + var e = this.subEvents_[i]; |
| + if (e.callback === cb) { |
| + if (e.subEvent.findListener_(e.subEventCallback) > -1) |
| + return i; |
| + console.error('Internal error: subEvent has no callback.'); |
| + } |
| + } |
| + |
| + return -1; |
| +}; |
| + |
| +DownloadsEvent.prototype.addRules = function(rules, opt_cb) { |
| + if (!this.eventOptions_.supportsRules) |
| + throw new Error('This event does not support rules.'); |
| + this.eventForRules_.addRules(rules, opt_cb); |
| +} |
| + |
| +DownloadsEvent.prototype.removeRules = function(ruleIdentifiers, opt_cb) { |
| + if (!this.eventOptions_.supportsRules) |
| + throw new Error('This event does not support rules.'); |
| + this.eventForRules_.removeRules(ruleIdentifiers, opt_cb); |
| +} |
| + |
| +DownloadsEvent.prototype.getRules = function(ruleIdentifiers, cb) { |
| + if (!this.eventOptions_.supportsRules) |
| + throw new Error('This event does not support rules.'); |
| + this.eventForRules_.getRules(ruleIdentifiers, cb); |
| +} |
| + |
| +chromeHidden.registerCustomEvent('downloads', DownloadsEvent); |