3

内部にDOMノードを含み、追加の機能メソッドで拡張されたフォーム入力フィールドのカスタムクラスラッパーを作成しています。

私の質問は、追加のメソッドを呼び出す代わりに、オブジェクトをDOMに直接挿入したいので、DOMに追加するための.toString()と同様のメソッドがあるかどうかです。

他のワークドでは、これが私が持っているものの例です:

function A () {
  this.element = documenet.createElement('input');
  // blah blah logic
  this.toString = function () {
    return '<input type="'+this.element.type+'" value="'+this.element.value+'" />';
  }
  // a similar method to this i'ld like
  this.toString = function () {
    return this.element;
  }
}

私がそれを次のように使うことができるように:

var a = new A();

// this works as it calls .toString(), but it is a hack and it is not pretty
document.body.innerHTML += a;

// this is what i'd want to be able to do:
document.body.appendChild(a);

// this is what **I AM REALLY TRYING TO AVOID:**
document.body.appendCHild(a.toElement());

DOMノードはパブリッククラスではないため、単純に継承することはできません。

私は他の質問を見てみましたが、答えがないようです...どんなアイデアでも大歓迎です

4

3 に答える 3

3

ネイティブDOMコンストラクターから継承することはできませんが、jQueryからラッパークラスを継承することはできます。

function A () {
    if (!(this instanceof A)) return new A(); // fix wrong constructor invocations
    if (this.length) { // shouldn't be set yet, so another odd invocation:
        var empty = Object.create(A.prototype); // a new, but *empty* instance
        empty.length = 0; // explicitly set length
        return empty;
    }

    this[0] = document.createElement('input');
    …
    // or you might want to call $.fn.init
    this.context = undefined; // not sure whether
    this.selector = ""; // we need those two lines
    this.length = 1; // but the length is obligatory
}
A.prototype = Object.create($.fn, {constructor:{value:A,configurable:true}});
A.prototype.toString = function () {
    return '<input type="'+this[0].type+'" value="'+this[0].value+'" />';
}

それで、あなたはちょうど$(document.body).append(new A)またはnew A().appendTo(document.body)などすることができます。

于 2012-12-17T18:30:03.983 に答える
1

Aオブジェクトとして考える代わりに、ファクトリメソッドとして考えることができます:http: //jsfiddle.net/fnK56/2/

// We can modify ele however we like, even overriding the toString method.
function CustomElement() {
    var ele = document.createElement("input");
    ele.type = "button";
    ele.value = "Testing";
    // do stuff to ele
    ele.CustomProperty = {one:"two", three:"four"}; // we can even add custom properties that will persist with that DOM node. 

    ele.toString = function(){
        return '<input type="'+this.type+'" value="'+this.value+'" />';
    };

    return ele;
}

var tmp = CustomElement(); // get us a new CustomElement

document.body.innerHTML += tmp; // this works because of the overridden toString
tmp.id = "Test";
document.body.appendChild(tmp);​ // this works because tmp is still a DOM input node.

console.log(tmp.CustomProperty); // Object {one: "two", three: "four"} 
console.log(document.getElementById("Test").CustomProperty); // Object {one: "two", three: "four"} 
于 2012-12-17T18:17:53.443 に答える
1

オプションの詳細については、すべてのブラウザ(http://www.meekostuff.net/blog/Overriding-DOM-Methods/を参照)にあるわけではありませんが、次のようになります。

HTMLElement.prototype._appendChild = HTMLElement.prototype.appendChild;
HTMLElement.prototype.appendChild = function(target)
{
    if(target.toElement)
    {
        this._appendChild(target.toElement());
    }
    else
    {  
        //attempt to do it the old fashioned way
        this._appendChild(target);
    }


}

これにより、構文が有効になります。

// this is what i'd want to be able to do:
document.body.appendChild(a);

そして、「toElement()」が内部的に呼び出されるという事実を隠します。

このレベルの複雑さに到達し始めると、jQueryのようなフレームワークを使用することが理にかなっていることに注意してください。

于 2012-12-17T18:19:45.343 に答える