Javascript 库开发范围和命名空间

标签 javascript namespaces

我们目前在大学的一门类(class)中学习了一些 Javascript 知识。 为此,我们为 show()、hide()、write 等常见任务实现了一个库。

目前我正在运行这样的实现:

var myLib_maker = function () {
/*
private scope
*/
var debuggingMode=true;
var currentElement=null;
/*
end private scope
*/
return {
    getElement: function (id) {
        var o;
        if (typeof id === 'string') { o = document.getElementById(id); }
        if (!!(o && o.nodeType !== 1)) { 
            throw {
                name: 'Type Error',
                message: 'Wrong node type at id: '+id
            } 
        }
      currentElement=o;
      return this;
    },
    getCurrentElement: function() {
        console.log(currentElement)
        return currentElement;
    },
    isVisible: function () {
        return this.getCurrentElement().style.display.toLowerCase() === "block"; 
    },
    show: function () {
        this.debug("show "+this.getCurrentElement())
        this.getCurrentElement().style.display = "block";
        return this;
    },
    hide: function () {
        this.debug("hide "+this.getCurrentElement())
        this.getCurrentElement().style.display = "none";
        return this;
    },
    toggle: function() {
        this.debug("toggle "+this.getCurrentElement())
        this.isVisible() ? this.hide(): this.show();
        return this;
    },
    write: function (content){
        this.debug("write to"+this.getCurrentElement().id);
        var tg = this.getCurrentElement().tagName.toLowerCase();
        if (tg === 'input' || tg === 'textarea') {
            currentElement.value = content; 
        } else { 
            currentElement.innerHTML = content;
        }
        return this
    },
    debug: function (what) {
        if (debuggingMode===true){
            console.log("[DEBUG] "+what);
        }
        return this;
    }

};
  }
  var myLib=myLib_maker();

我有一个外部函数(用于测试)来切换 2 个文本区域的内容。

 function switchEditors(id1, id2){
      c1=myLib.getElement(id1).getCurrentElement().value;
      c2=myLib.getElement(id2).getCurrentElement().value;
      myLib.getElement(id1).write(c2)
      myLib.getElement(id2).write(c1)
 }

我首先尝试使用以下代码,这显然不起作用,因为我覆盖了我的私有(private) currentElement,所以我总是写入 id2

function switchEditors(id1, id2){
      tmp=myLib.getElement(id1).getCurrentElement().value
      myLib.getElement(id1).write(myLib.getElement(id2).getCurrentElement().value)
      myLib.getElement(id2).write(tmp)
 } 

但我最初真正想要的不是使用私有(private) currentElement 变量。 write方法的第一个实现扩展了Element对象

Element.prototype.write= function (content){
    var tg = this.tagName.toLowerCase();
    if (tg === 'input' || tg === 'textarea') {
        this.value = content; 
    } else { 
         this.innerHTML = content;
    }
    return this;
}

这样返回的getElement函数

document.getElementById(id)

我想要级联(我希望这是正确的词 -> 我的意思是 myLib.getElement("myid").show().hide() 串联的东西)并直接访问 所有元素属性,但我们不能为我们的库使用全局范围,因此我必须以任何方式封装我的库。

那么有没有一种优雅的方式来使用级联,并且能够直接访问元素对象上的所有属性,而无需在全局元素范围内实现每个方法?

或者我的库设计完全错误,必须完全不同。 如果是这样,请告诉我,我很感激任何帮助。 (我试图弄清楚 jQuery 实际上是如何实现这些东西的,但并没有真正了解它是如何完成的......代码太多......:))

我希望我描述了我的愿望和要求。如果没有,请询​​问更具体的细节。

最佳答案

如您所知,currentElementgetElement 调用之间共享。相反,您可以使用 Object.create 创建 myLib 对象的新实例并将 currentElement 绑定(bind)到它。

getElement: function (id) {
    var o, self = Object.create(this);
    /* ... */
    self.currentElement = o;
    return self;
}

并在整个过程中使用 this.currentElement 以便每次调用都使用自己的当前元素。

关于Javascript 库开发范围和命名空间,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/5602229/

相关文章:

javascript - 向 'arguments' 类数组对象添加参数,性能测试

javascript - 如何获得 gulpfile 的绝对路径?

JavaScript 图形计数器。我该怎么办?

svg - %tagElement% 上的 href 的命名空间前缀 NS1 未定义,setAttributeNS

c++ - 在命名空间中使用正确的语法实现非成员重载运算符

xslt - 输入 XML 的动态命名空间

javascript - Jquery 将值数组添加到 json 对象

javascript - 将密码存储在 Javascript localStorage 中

c++ - 嵌套命名空间没有看到使用 'using-directive' 嵌套在另一个命名空间中的类

c++ - 带有命名空间的编译器的有趣行为