为vanilla javascript插件制作默认设置

Nor*_*orx 6 javascript plugins object

试图用普通的javascript构建一个简单的工具提示插件.

在我的代码中,我试图在我的代码中制作并设置bcolor为默认设置,我认为当我们想要放置多个默认值时,这不是一个好方法.

那么,我如何在我的vanilla javascript插件中进行默认设置?

的jsfiddle

var Tooltip = function(selector, bcolor) {
  this.targetElement = document.querySelectorAll(selector);
  this.bcolor = bcolor;
  if (this.bcolor == null || typeof this.bcolor !== "string") {
    this.bcolor = "#333";
  }

  if (this.targetElement == null) {
    console.log("Ooops, error!")
  }

  return this;
}

Tooltip.prototype.tooltip = function() {
  for (var i = 0; i < this.targetElement.length; i++) {

    var text = this.targetElement[i].getAttribute("data-tooltip");

    this.targetElement[i].style.position = "relative";

    var span = document.createElement("span");
    this.targetElement[i].appendChild(span);
    span.style.position = "absolute";
    span.style.top = "-25px";
    span.style.left = "-20px";
    span.style.padding = "4px"
    span.style.borderRadius = "5px";
    span.style.backgroundColor = this.bcolor;
    span.style.color = "#fff";
    span.innerHTML = text;
  }
}

var box = new Tooltip(".box", "red");
box.tooltip();
Run Code Online (Sandbox Code Playgroud)

Sea*_*ema 14

首先,让我们看看如何轻松支持多种选择.对此的一个常见解决方案是让构造函数接受"配置"对象而不是简单的字符串或数字参数.请考虑使用此表单:

var Tooltip = function(selector, options) {
    this.targetElement = document.querySelectorAll(selector);
    this.options = options;
    ...
};

var box = new Tooltip(".box", { color: "red" });
Run Code Online (Sandbox Code Playgroud)

请注意,我们不是传递单个值,而是传入包含该单个值的对象.但是该对象可能包含许多配置选项 - 而不仅仅是一个!例如,您可以传入:

var box = new Tooltip(".box", {
    backgroundColor: "red",
    textColor: "white",
    fontSize: 12,
    animated: true,
    animationSpeed: 1000
});
Run Code Online (Sandbox Code Playgroud)

当您需要访问任何这些选项时,您的代码可以简单地使用对options对象的引用:例如this.bcolor,您可以使用,而不是this.options.backgroundColor.这是上面的代码,扩展了一些选项:

Tooltip.prototype.tooltip = function() {
   for (var i = 0; i < this.targetElement.length; i++) {
       ...
       span.style.backgroundColor = this.options.backgroundColor;
       span.style.color = this.options.textColor;
       span.style.fontSize = this.options.fontSize + "px";
       ...
   }
}
Run Code Online (Sandbox Code Playgroud)

这就是你如何处理多种选择; 但每个的默认值呢?要做到这一点,您需要首先在某处定义默认值:

Tooltip.prototype.defaultOptions = {
    backgroundColor: "#FF9",
    textColor: "black",
    fontSize: 12,
    animated: false,
    animationSpeed: 1000
};
Run Code Online (Sandbox Code Playgroud)

然后你的构造函数可以旋转defaultOptions,使用它的值填充提供的options对象中任何缺少的"漏洞" :

var Tooltip = function(selector, options) {
    this.targetElement = document.querySelectorAll(selector);
    this.options = options;

    for (var optionName in this.defaultOptions) {
        if (typeof this.options[optionName] === 'undefined')
            this.options[optionName] = this.defaultOptions[optionName];
    }
    ...
};
Run Code Online (Sandbox Code Playgroud)

仅当值不存在时,针对a typeof的值的测试undefined才为真,因此这个for循环将任何值复制defaultOptionsoptions,只要它们尚不存在options.它很好且可扩展:只要你添加一个新值defaultOptions,循环就会将它复制到其中options,无论调用者之前传递的是什么.

并且,更重要的是,该for循环实际上jQuery.extend是在幕后进行的:将值从一个对象复制到另一个对象.(jQuery解决方案稍微优雅一点,但我在这里简化了一些事情,以便更明显地发生了什么.)


但是如果你想在某些地方使用默认行为呢?例如,如果您没有定义特定的字体大小,可能只是希望它从父元素或文档继承,而不是将其分配给某些东西defaultOptions.

如果你想要那种"不分配 - 除非提供"的行为,上面相同的基本模式可以工作,但你需要调整一下默认选项,然后在你申请时添加一个条件选项.考虑一下这个例子与我上面展示的不同之处:

// Notice that we specifically leave out fontSize here in the defaults.
Tooltip.prototype.defaultOptions = {
    backgroundColor: "#FF9",
    textColor: "black",
    animated: false,
    animationSpeed: 1000
};

Tooltip.prototype.tooltip = function() {
   for (var i = 0; i < this.targetElement.length; i++) {
       ...
       span.style.backgroundColor = this.options.backgroundColor;
       span.style.color = this.options.textColor;

       // Now, we only assign the fontSize if it was provided by the user.
       if (typeof this.options.fontSize !== 'undefined')
           span.style.fontSize = this.options.fontSize + "px";
       ...
   }
}
Run Code Online (Sandbox Code Playgroud)

希望这对你来说应该足够了.


对此的变化(Object.extend模式测试反对undefined)在JavaScript中被广泛使用,并且被jQuery和许多其他库大量使用.如果你遵循他们所做的相同基本设计,你将会处于非常好的公司.