diff options
author | Kris Maglione <kris@vimperator.org> | 2010-08-31 21:09:13 -0400 |
---|---|---|
committer | Kris Maglione <kris@vimperator.org> | 2010-08-31 21:09:13 -0400 |
commit | 8b0d9586b23eb166fafb064e75c4956021d73ca1 (patch) | |
tree | cc3a8bdda4e19dc18eadd5ed0edc4aa2131b43e2 /common/content/base.js | |
parent | 5632e14721897b9e7e23d493f95358bb7df73314 (diff) | |
download | pentadactyl-8b0d9586b23eb166fafb064e75c4956021d73ca1.tar.gz |
Merge testing.
--HG--
rename : common/content/base.js => common/modules/base.jsm
rename : common/content/services.js => common/modules/services.jsm
rename : common/content/style.js => common/modules/styles.jsm
rename : common/content/template.js => common/modules/template.jsm
rename : common/content/util.js => common/modules/util.jsm
Diffstat (limited to 'common/content/base.js')
-rw-r--r-- | common/content/base.js | 624 |
1 files changed, 0 insertions, 624 deletions
diff --git a/common/content/base.js b/common/content/base.js deleted file mode 100644 index e4a58bbb..00000000 --- a/common/content/base.js +++ /dev/null @@ -1,624 +0,0 @@ -// Copyright (c) 2009 by Kris Maglione <maglione.k@gmail.com> -// -// This work is licensed for reuse under an MIT license. Details are -// given in the LICENSE.txt file included with this file. -"use strict"; - -const Cc = Components.classes; -const Ci = Components.interfaces; -const Cr = Components.results; -const Cu = Components.utils; - -function allkeys(obj) { - let ret = {}; - try { - for (; obj; obj = obj.__proto__) { - services.get("debugger").wrapValue(obj).getProperties(ret, {}); - for (let prop in values(ret.value)) - yield prop.name.stringValue; - } - return; - } - catch (e) {} - - let __iterator__ = obj.__iterator__; - try { - if ("__iterator__" in obj) { - yield "__iterator__"; - delete obj.__iterator__; - } - for (let k in obj) - yield k; - } - finally { - if (__iterator__) - obj.__iterator__ = __iterator__; - } -} - -function debuggerProperties(obj) { - if (modules.services && services.get("debugger").isOn) { - let ret = {}; - services.get("debugger").wrapValue(obj).getProperties(ret, {}); - return ret.value; - } -} - -if (!Object.keys) - Object.keys = function keys(obj) [k for (k in obj) if (obj.hasOwnProperty(k))]; - -if (!Object.getOwnPropertyNames) - Object.getOwnPropertyNames = function getOwnPropertyNames(obj) { - let res = debuggerProperties(obj); - if (res) - return [prop.name.stringValue for (prop in values(res))]; - return Object.keys(obj); - } - -function properties(obj, prototypes) { - let orig = obj; - let seen = {}; - for (; obj; obj = prototypes && obj.__proto__) - for (let key in values(Object.getOwnPropertyNames(obj))) - if (!prototypes || !set.add(seen, key) && obj != orig) - yield key -} - -function values(obj) { - for (var k in obj) - if (obj.hasOwnProperty(k)) - yield obj[k]; -} -function foreach(iter, fn, self) { - for (let val in iter) - fn.call(self, val); -} - -function dict(ary) { - var obj = {}; - for (var i = 0; i < ary.length; i++) { - var val = ary[i]; - obj[val[0]] = val[1]; - } - return obj; -} - -function set(ary) { - let obj = {}; - if (ary) - for (var i = 0; i < ary.length; i++) - obj[ary[i]] = true; - return obj; -} -set.add = function (set, key) { - let res = this.has(set, key); - set[key] = true; - return res; -} -set.has = function (set, key) Object.prototype.hasOwnProperty.call(set, key); -set.remove = function (set, key) { delete set[key]; } - -function iter(obj) { - if (obj instanceof Ci.nsISimpleEnumerator) - return (function () { - while (obj.hasMoreElements()) - yield obj.getNext(); - })(); - if (isinstance(obj, [Ci.nsIStringEnumerator, Ci.nsIUTF8StringEnumerator])) - return (function () { - while (obj.hasMore()) - yield obj.getNext(); - })(); - if (isinstance(obj, Ci.nsIDOMNodeIterator)) - return (function () { - try { - while (true) - yield obj.nextNode(); - } - catch (e) {} - })(); - if (isinstance(obj, [Ci.nsIDOMHTMLCollection, Ci.nsIDOMNodeList])) - return array.iteritems(obj); - if (obj instanceof Ci.nsIDOMNamedNodeMap) - return (function () { - for (let i = 0; i < obj.length; i++) - yield [obj.name, obj]; - })(); - return Iterator(obj); -} - -function issubclass(targ, src) { - return src === targ || - targ && typeof targ === "function" && targ.prototype instanceof src; -} - -function isinstance(targ, src) { - const types = { - boolean: Boolean, - string: String, - function: Function, - number: Number - } - src = Array.concat(src); - for (var i = 0; i < src.length; i++) { - if (targ instanceof src[i]) - return true; - if (typeof src[i] == "string") - return Object.prototype.toString(targ) == "[object " + src[i] + "]"; - var type = types[typeof targ]; - if (type && issubclass(src[i], type)) - return true; - } - return false; -} - -function isobject(obj) { - return typeof obj === "object" && obj != null; -} - -/** - * Returns true if and only if its sole argument is an - * instance of the builtin Array type. The array may come from - * any window, frame, namespace, or execution context, which - * is not the case when using (obj instanceof Array). - */ -function isarray(val) { - return Object.prototype.toString.call(val) == "[object Array]"; -} - -/** - * Returns true if and only if its sole argument is an - * instance of the builtin Generator type. This includes - * functions containing the 'yield' statement and generator - * statements such as (x for (x in obj)). - */ -function isgenerator(val) { - return Object.prototype.toString.call(val) == "[object Generator]"; -} - -/** - * Returns true if and only if its sole argument is a String, - * as defined by the builtin type. May be constructed via - * String(foo) or new String(foo) from any window, frame, - * namespace, or execution context, which is not the case when - * using (obj instanceof String) or (typeof obj == "string"). - */ -function isstring(val) { - return Object.prototype.toString.call(val) == "[object String]"; -} - -/** - * Returns true if and only if its sole argument may be called - * as a function. This includes classes and function objects. - */ -function callable(val) { - return typeof val === "function"; -} - -function call(fn) { - fn.apply(arguments[1], Array.slice(arguments, 2)); - return fn; -} - -function memoize(obj, key, getter) { - obj.__defineGetter__(key, function () { - delete obj[key]; - return obj[key] = getter(obj, key); - }); -} - -/** - * Curries a function to the given number of arguments. Each - * call of the resulting function returns a new function. When - * a call does not contain enough arguments to satisfy the - * required number, the resulting function is another curried - * function with previous arguments accumulated. - * - * function foo(a, b, c) [a, b, c].join(" "); - * curry(foo)(1, 2, 3) -> "1 2 3"; - * curry(foo)(4)(5, 6) -> "4 5 6"; - * curry(foo)(4)(8)(9) -> "7 8 9"; - * - * @param {function} fn The function to curry. - * @param {integer} length The number of arguments expected. - * @default fn.length - * @optional - * @param {object} self The 'this' value for the returned function. When - * omitted, the value of 'this' from the first call to the function is - * preserved. - * @optional - */ -function curry(fn, length, self, acc) { - if (length == null) - length = fn.length; - if (length == 0) - return fn; - - // Close over function with 'this' - function close(self, fn) function () fn.apply(self, Array.slice(arguments)); - - if (acc == null) - acc = []; - - return function () { - let args = acc.concat(Array.slice(arguments)); - - // The curried result should preserve 'this' - if (arguments.length == 0) - return close(self || this, arguments.callee); - - if (args.length >= length) - return fn.apply(self || this, args); - - return curry(fn, length, self || this, args); - }; -} - -/** - * Updates an object with the properties of another object. Getters - * and setters are copied as expected. Moreover, any function - * properties receive new 'supercall' and 'superapply' properties, - * which will call the identically named function in target's - * prototype. - * - * let a = { foo: function (arg) "bar " + arg } - * let b = { __proto__: a } - * update(b, { foo: function () arguments.callee.supercall(this, "baz") }); - * - * a.foo("foo") -> "bar foo" - * b.foo() -> "bar baz" - * - * @param {Object} target The object to update. - * @param {Object} src The source object from which to update target. - * May be provided multiple times. - * @returns {Object} Returns its updated first argument. - */ -function update(target) { - for (let i = 1; i < arguments.length; i++) { - let src = arguments[i]; - Object.getOwnPropertyNames(src || {}).forEach(function (k) { - var get = src.__lookupGetter__(k), - set = src.__lookupSetter__(k); - if (!get && !set) { - var v = src[k]; - target[k] = v; - if (target.__proto__ && callable(v)) { - v.superapply = function (self, args) { - return target.__proto__[k].apply(self, args); - }; - v.supercall = function (self) { - return v.superapply(self, Array.slice(arguments, 1)); - }; - } - } - if (get) - target.__defineGetter__(k, get); - if (set) - target.__defineSetter__(k, set); - }); - } - return target; -} - -/** - * Extends a subclass with a superclass. The subclass's - * prototype is replaced with a new object, which inherits - * from the super class's prototype, {@see update}d with the - * members of 'overrides'. - * - * @param {function} subclass - * @param {function} superclass - * @param {Object} overrides @optional - */ -function extend(subclass, superclass, overrides) { - subclass.prototype = { __proto__: superclass.prototype }; - update(subclass.prototype, overrides); - - subclass.superclass = superclass.prototype; - subclass.prototype.constructor = subclass; - subclass.prototype.__class__ = subclass; - - if (superclass.prototype.constructor === Object.prototype.constructor) - superclass.prototype.constructor = superclass; -} - -/** - * @constructor Class - * - * Constructs a new Class. Arguments marked as optional must be - * either entirely elided, or they must have the exact type - * specified. - * - * @param {string} name The class's as it will appear when toString - * is called, as well as in stack traces. - * @optional - * @param {function} base The base class for this module. May be any - * callable object. - * @optional - * @default Class - * @param {Object} prototype The prototype for instances of this - * object. The object itself is copied and not used as a prototype - * directly. - * @param {Object} classProperties The class properties for the new - * module constructor. More than one may be provided. - * @optional - * - * @returns {function} The constructor for the resulting class. - */ -function Class() { - function constructor() { - let self = { - __proto__: Constructor.prototype, - constructor: Constructor, - get closure() { - delete this.closure; - function closure(fn) function () fn.apply(self, arguments); - for (let k in this) - if (!this.__lookupGetter__(k) && callable(this[k])) - closure[k] = closure(self[k]); - return this.closure = closure; - } - }; - var res = self.init.apply(self, arguments); - return res !== undefined ? res : self; - } - - var args = Array.slice(arguments); - if (isstring(args[0])) - var name = args.shift(); - var superclass = Class; - if (callable(args[0])) - superclass = args.shift(); - - var Constructor = eval("(function " + (name || superclass.name).replace(/\W/g, "_") + - String.substr(constructor, 20) + ")"); - Constructor.__proto__ = superclass; - Constructor.name = name || superclass.name; - - if (!("init" in superclass.prototype)) { - var superc = superclass; - superclass = function Shim() {}; - extend(superclass, superc, { - init: superc - }); - } - - extend(Constructor, superclass, args[0]); - update(Constructor, args[1]); - args = args.slice(2); - Array.forEach(args, function (obj) { - if (callable(obj)) - obj = obj.prototype; - update(Constructor.prototype, obj); - }); - return Constructor; -} -Class.toString = function () "[class " + this.constructor.name + "]", -Class.prototype = { - /** - * Initializes new instances of this class. Called automatically - * when new instances are created. - */ - init: function () {}, - - toString: function () "[instance " + this.constructor.name + "]", - - /** - * Exactly like {@see nsIDOMWindow#setTimeout}, except that it - * preserves the value of 'this' on invocation of 'callback'. - * - * @param {function} callback The function to call after 'timeout' - * @param {number} timeout The timeout, in seconds, to wait - * before calling 'callback'. - * @returns {integer} The ID of this timeout, to be passed to - * {@see nsIDOMWindow#clearTimeout}. - */ - setTimeout: function (callback, timeout) { - const self = this; - let notify = { notify: function notify(timer) { callback.call(self) } }; - let timer = services.create("timer"); - timer.initWithCallback(notify, timeout, timer.TYPE_ONE_SHOT); - return timer; - } -}; - -/** - * @class Struct - * - * Creates a new Struct constructor, used for creating objects with - * a fixed set of named members. Each argument should be the name of - * a member in the resulting objects. These names will correspond to - * the arguments passed to the resultant constructor. Instances of - * the new struct may be treated vary much like arrays, and provide - * many of the same methods. - * - * const Point = Struct("x", "y", "z"); - * let p1 = Point(x, y, z); - * - * @returns {function} The constructor for the new Struct. - */ -function Struct() { - let args = Array.slice(arguments); - const Struct = Class("Struct", StructBase, { - length: args.length, - members: args - }); - args.forEach(function (name, i) { - Struct.prototype.__defineGetter__(name, function () this[i]); - Struct.prototype.__defineSetter__(name, function (val) { this[i] = val; }); - }); - return Struct; -} -const StructBase = Class("StructBase", { - init: function () { - for (let i = 0; i < arguments.length; i++) - if (arguments[i] != undefined) - this[i] = arguments[i]; - }, - - clone: function clone() this.constructor.apply(null, this.slice()), - - // Iterator over our named members - __iterator__: function () { - let self = this; - return ([k, self[k]] for (k in values(self.members))) - } -}, { - /** - * Sets a lazily constructed default value for a member of - * the struct. The value is constructed once, the first time - * it is accessed and memoized thereafter. - * - * @param {string} key The name of the member for which to - * provide the default value. - * @param {function} val The function which is to generate - * the default value. - */ - defaultValue: function (key, val) { - let i = this.prototype.members.indexOf(key); - this.prototype.__defineGetter__(i, function () (this[i] = val.call(this), this[i])); // Kludge for FF 3.0 - this.prototype.__defineSetter__(i, function (value) { - this.__defineGetter__(i, function () value); - this.__defineSetter__(i, function (val) { value = val; }); - }); - } -}); -// Add no-sideeffect array methods. Can't set new Array() as the prototype or -// get length() won't work. -for (let k in values(["concat", "every", "filter", "forEach", "indexOf", "join", "lastIndexOf", - "map", "reduce", "reduceRight", "reverse", "slice", "some", "sort"])) - StructBase.prototype[k] = Array.prototype[k]; - -/** - * Array utility methods. - */ -const array = Class("util.Array", Array, { - init: function (ary) { - if (isgenerator(ary)) - ary = [k for (k in ary)]; - else if (ary.length) - ary = Array.slice(ary); - - return { - __proto__: ary, - __iterator__: function () this.iteritems(), - __noSuchMethod__: function (meth, args) { - var res = array[meth].apply(null, [this.__proto__].concat(args)); - - if (array.isinstance(res)) - return array(res); - return res; - }, - toString: function () this.__proto__.toString(), - concat: function () this.__proto__.concat.apply(this.__proto__, arguments), - map: function () this.__noSuchMethod__("map", Array.slice(arguments)) - }; - } -}, { - isinstance: function isinstance(obj) { - return Object.prototype.toString.call(obj) == "[object Array]"; - }, - - /** - * Converts an array to an object. As in lisp, an assoc is an - * array of key-value pairs, which maps directly to an object, - * as such: - * [["a", "b"], ["c", "d"]] -> { a: "b", c: "d" } - * - * @param {Array[]} assoc - * @... {string} 0 - Key - * @... 1 - Value - */ - toObject: function toObject(assoc) { - let obj = {}; - assoc.forEach(function ([k, v]) { obj[k] = v; }); - return obj; - }, - - /** - * Compacts an array, removing all elements that are null or undefined: - * ["foo", null, "bar", undefined] -> ["foo", "bar"] - * - * @param {Array} ary - * @returns {Array} - */ - compact: function compact(ary) ary.filter(function (item) item != null), - - /** - * Flattens an array, such that all elements of the array are - * joined into a single array: - * [["foo", ["bar"]], ["baz"], "quux"] -> ["foo", ["bar"], "baz", "quux"] - * - * @param {Array} ary - * @returns {Array} - */ - flatten: function flatten(ary) ary.length ? Array.concat.apply([], ary) : [], - - /** - * Returns an Iterator for an array's values. - * - * @param {Array} ary - * @returns {Iterator(Object)} - */ - itervalues: function itervalues(ary) { - let length = ary.length; - for (let i = 0; i < length; i++) - yield ary[i]; - }, - - /** - * Returns an Iterator for an array's indices and values. - * - * @param {Array} ary - * @returns {Iterator([{number}, {Object}])} - */ - iteritems: function iteritems(ary) { - let length = ary.length; - for (let i = 0; i < length; i++) - yield [i, ary[i]]; - }, - - /** - * Filters out all duplicates from an array. If - * <b>unsorted</b> is false, the array is sorted before - * duplicates are removed. - * - * @param {Array} ary - * @param {boolean} unsorted - * @returns {Array} - */ - uniq: function uniq(ary, unsorted) { - let ret = []; - if (unsorted) { - for (let [, item] in Iterator(ary)) - if (ret.indexOf(item) == -1) - ret.push(item); - } - else { - for (let [, item] in Iterator(ary.sort())) { - if (item != last || !ret.length) - ret.push(item); - var last = item; - } - } - return ret; - }, - - /** - * Zips the contents of two arrays. The resulting array is twice the - * length of ary1, with any shortcomings of ary2 replaced with null - * strings. - * - * @param {Array} ary1 - * @param {Array} ary2 - * @returns {Array} - */ - zip: function zip(ary1, ary2) { - let res = [] - for(let [i, item] in Iterator(ary1)) - res.push(item, i in ary2 ? ary2[i] : ""); - return res; - } -}); - -// vim: set fdm=marker sw=4 ts=4 et: |