// Cross Browser selectionStart/selectionEnd
// Version 0.2
// Copyright (c) 2005-2007 KOSEKI Kengo
//
// This script is distributed under the MIT licence.
// http://www.opensource.org/licenses/mit-license.php
function Selection(textareaElement) {
    this.element = textareaElement;
}

Selection.prototype.create = function() {
    if (document.selection != null && this.element.selectionStart == null) {
        return this._ieGetSelection();
    } else {
        return this._mozillaGetSelection();
    }
}

Selection.prototype._mozillaGetSelection = function() {
    return {
        start: this.element.selectionStart,
        end: this.element.selectionEnd
    };
}

Selection.prototype._ieGetSelection = function() {
    this.element.focus();

    var range = document.selection.createRange();
    var bookmark = range.getBookmark();

    var contents = this.element.value;
    var originalContents = contents;
    var marker = this._createSelectionMarker();
    while(contents.indexOf(marker) != -1) {
        marker = this._createSelectionMarker();
    }

    var parent = range.parentElement();
    if (parent == null || parent.type != "textarea") {
        return { start: 0, end: 0 };
    }
    range.text = marker + range.text + marker;
    contents = this.element.value;

    var result = {};
    result.start = contents.indexOf(marker);
    contents = contents.replace(marker, "");
    result.end = contents.indexOf(marker);

    this.element.value = originalContents;
    range.moveToBookmark(bookmark);
    range.select();

    return result;
}

Selection.prototype._createSelectionMarker = function() {
    return "##SELECTION_MARKER_" + Math.random() + "##";
}

var cElement = function (tag, kon, data) {
    data = data||{"type":"in", "attribute":{}};
    kon = typeof kon == 'object' ? kon : $(kon);
    var _BODY = document.getElementsByTagName("body").item(0);
    if (!kon) kon = _BODY;
    var ob = document.createElement(tag);
    var type = data["type"]||"in";
    var attrib = data["attribute"]||{};
    for (var k in attrib) {
        ob.setAttribute(k, attrib[k]);
    }
    switch (type) {
       case "first":
           _BODY.insertBefore(ob, _BODY.firstChild)
           break;
       case "before":
           kon.parentNode.insertBefore(ob, kon.nextSibling);
           break;
       default:
           kon.appendChild(ob);
           break;
    }
    return ob;
}
var addFormElement = function(oBut, oKon, inputName, deleteButton) {
    var form;
    var oInput;
    deleteButton = deleteButton||false;
    form = oBut;
    do {
        form = form.parentNode;
    } while (form.tagName.toLowerCase() != "form" && form.tagName.toLowerCase() != "body");
    var fEl = form.getElementsByTagName("input");
    for (var k = fEl.length - 1; k >= 0; k--) {
        try {
        if (fEl[k].name.match(new RegExp('^' + inputName + '\\['))) {
            oInput = fEl[k];
            break;
        }
        } catch (e) {
        }
    }
    if (!oInput) return false
    oKon = oKon||oInput.parentNode;
    var id = oInput.getAttribute("id").split("-");
    if (parseInt(id[id.length - 1]) == id[id.length - 1]) {
        id[id.length - 1] = id[id.length - 1] + 1;
    } else {
        oInput.id = id.join("-") + "-1";
        id.push(2);
    }
    cElement("br", oKon);
    var input = cElement("input", oKon, {"type":"in", "attribute":{"type": oInput.getAttribute("type"), "id":id.join("-"), "name":oInput.getAttribute("name"), "value":"", "class":oInput.className}});
    if(deleteButton) {
        cElement("input", oKon, {"type":"in", "attribute":{"type": "button", "name":"delBut-"+oInput.getAttribute("name"), "value":deleteButton}}).onclick = function() {
            dElement(input); dElement(this); return false;
        };
    }
    return false;
}
var dElement = function(oid) {
    oid = $(oid);
    if (oid) {
        oid.parentNode.removeChild(oid);
    }
    return null;
}

