扩展现有对象以添加额外的 JavaScript 原型方法
Extending existing Object to add additional JavaScript Prototype methods
假设我有一个类似于下面的函数,它创建了一个非常简单的微型图书馆:
var microLib = function(selector) {
var el;
var selectorEngine = function(selector)
{
var selector_value = selector.slice(1);
return document.getElementById(selector_value);
};
el = selectorEngine(selector);
Element.prototype.func_1 = function(){
return 'first';
};
Element.prototype.func_2 = function(){
return 'second';
};
return el;
};
window._$ = microLib;
此脚本将允许我编写如下代码:
var elem = _$("#div_with_id"); //some element on my web page
console.log(elem.func_2()); //outputs 'second' in the console
所以现在,我正在寻找一种方法来在补充代码中扩展 _$
以添加额外的 Element.prototype
方法,这样我就可以编写:
console.log(elem.func_3()); //to output 'third' in the console
我需要这样做的原因是因为这个 extension 需要在另一个 JavaScript 文件中进行,否则我会添加另一个方法并且是完成它。
我该怎么做?
这是我建议的方法示例:http://jsfiddle.net/rbxssmx8/。
JS:
var toArray = Function.prototype.call.bind(Array.prototype.slice);
var qAll = document.querySelectorAll.bind(document);
var _$ = (function() {
function dom(selector) {
if(!(this instanceof dom)) {
return new dom(selector);
}
this.elements = toArray(qAll(selector));
}
dom.prototype.iterate = function(func) {
this.elements.forEach(func);
return this;
};
dom.prototype.addClass = function() {
var klasses = arguments;
return this.iterate(function(element) {
element.classList.add.apply(element.classList, klasses);
});
};
dom.extend = function(name, func) {
this.prototype[name] = func;
};
dom.ready = function(func) {
document.addEventListener("DOMContentLoaded", func);
};
return dom;
})();
_$.extend("removeClass", function() {
var klasses = arguments;
return this.iterate(function(element) {
element.classList.remove.apply(element.classList, klasses);
});
});
_$("div").addClass("gray");
var $el = _$("div:last-of-type");
$el.removeClass("gray");
所以我在 What's wrong with extending the DOM and the alternative suggested by the author was to use Object Wrappers. A quick search on that led me to this post on SO: Using object wrappers to extend the JavaScripts DOM?
上阅读了这篇 post
结合@DRD 的回答,我更新了我的代码:
(function() {
var microLib = function (selector){
return new Dom(selector);
};
function Dom(selector)
{
var selector_value = selector.slice(1);
this.element = document.getElementById(selector_value);
}
Dom.prototype.func_1 = function(){
return 'first';
};
Dom.prototype.func_2 = function(){
return 'second';
};
microLib.extend = function(name, func){
Dom.prototype[name] = func;
};
window._$ = microLib;
})();
然后,每当您想扩展和添加另一个功能时,请在之后执行此操作:
_$.extend('func_3', function(){ //this is inline with my earlier question
return 'third';
});
很有魅力!与扩展 Element.prototype
.
相比,绝对 更安全 选项
假设我有一个类似于下面的函数,它创建了一个非常简单的微型图书馆:
var microLib = function(selector) {
var el;
var selectorEngine = function(selector)
{
var selector_value = selector.slice(1);
return document.getElementById(selector_value);
};
el = selectorEngine(selector);
Element.prototype.func_1 = function(){
return 'first';
};
Element.prototype.func_2 = function(){
return 'second';
};
return el;
};
window._$ = microLib;
此脚本将允许我编写如下代码:
var elem = _$("#div_with_id"); //some element on my web page
console.log(elem.func_2()); //outputs 'second' in the console
所以现在,我正在寻找一种方法来在补充代码中扩展 _$
以添加额外的 Element.prototype
方法,这样我就可以编写:
console.log(elem.func_3()); //to output 'third' in the console
我需要这样做的原因是因为这个 extension 需要在另一个 JavaScript 文件中进行,否则我会添加另一个方法并且是完成它。
我该怎么做?
这是我建议的方法示例:http://jsfiddle.net/rbxssmx8/。
JS:
var toArray = Function.prototype.call.bind(Array.prototype.slice);
var qAll = document.querySelectorAll.bind(document);
var _$ = (function() {
function dom(selector) {
if(!(this instanceof dom)) {
return new dom(selector);
}
this.elements = toArray(qAll(selector));
}
dom.prototype.iterate = function(func) {
this.elements.forEach(func);
return this;
};
dom.prototype.addClass = function() {
var klasses = arguments;
return this.iterate(function(element) {
element.classList.add.apply(element.classList, klasses);
});
};
dom.extend = function(name, func) {
this.prototype[name] = func;
};
dom.ready = function(func) {
document.addEventListener("DOMContentLoaded", func);
};
return dom;
})();
_$.extend("removeClass", function() {
var klasses = arguments;
return this.iterate(function(element) {
element.classList.remove.apply(element.classList, klasses);
});
});
_$("div").addClass("gray");
var $el = _$("div:last-of-type");
$el.removeClass("gray");
所以我在 What's wrong with extending the DOM and the alternative suggested by the author was to use Object Wrappers. A quick search on that led me to this post on SO: Using object wrappers to extend the JavaScripts DOM?
上阅读了这篇 post结合@DRD 的回答,我更新了我的代码:
(function() {
var microLib = function (selector){
return new Dom(selector);
};
function Dom(selector)
{
var selector_value = selector.slice(1);
this.element = document.getElementById(selector_value);
}
Dom.prototype.func_1 = function(){
return 'first';
};
Dom.prototype.func_2 = function(){
return 'second';
};
microLib.extend = function(name, func){
Dom.prototype[name] = func;
};
window._$ = microLib;
})();
然后,每当您想扩展和添加另一个功能时,请在之后执行此操作:
_$.extend('func_3', function(){ //this is inline with my earlier question
return 'third';
});
很有魅力!与扩展 Element.prototype
.