﻿(function ($) {
    var isControl = false;
    var dialogAdded = false;
    var durl = '';
    var uurl = '';
    var ftoken = '';
    var purl = '';
    $.fn.initEditor = function (uploadUrl, downloadUrl, previewUrl, forgeryToken) {
        durl = downloadUrl;
        uurl = uploadUrl;
        ftoken = forgeryToken;
        purl = previewUrl;
    };
    $.fn.editor = function () {
        $(this).each(function () {
            var textArea = $(this);
            var editorContainer = $('<div></div>');
            editorContainer.insertBefore(textArea);
            var newTextArea = $('<textarea></textarea>');
            newTextArea.attr('id', textArea.attr('id'));
            newTextArea.attr('name', textArea.attr('name'));
            newTextArea.attr('class', textArea.attr('class'));
            newTextArea.attr('style', textArea.attr('style'));
            newTextArea.attr('rows', textArea.attr('rows'));
            newTextArea.attr('cols', textArea.attr('cols'));
            newTextArea.blur(function () {
                isControl = false;
            });
            newTextArea[0].value = textArea[0].value;
            textArea.remove();
            newTextArea.keydown(function (e) {
                if (e.keyCode === 17) {
                    isControl = true;
                }
                if (!isControl)
                    return true;
                switch (e.keyCode) {
                    case 66:
                        wrapSelection($(this)[0], '*');
                        return false;
                    case 73:
                        wrapSelection($(this)[0], '/');
                        return false;
                    case 72:
                        doLineStyle($(this)[0], '-', 2, false);
                        return false;
                    case 68:
                        wrapSelection($(this)[0], '_');
                        return false;
                    case 85:
                        doLineStyle($(this)[0], '*', 1);
                        return false;
                    case 79:
                        doLineStyle($(this)[0], '#', 1);
                        return false;
                    case 76:
                        doLink($(this)[0]);
                        return false;
                    case 75:
                        doCode($(this)[0]);
                        return false;
                    case 71:
                        doImage($(this)[0]);
                        return false;
                    case 80:
                        doPreview($(this)[0]);
                        return false;
                    case 49:
                    case 50:
                    case 51:
                    case 52:
                    case 53:
                    case 54:
                        doLineStyle($(this)[0], '!', parseInt(String.fromCharCode(e.keyCode)));
                        return false;
                }
                return true;
            });
            newTextArea.keyup(function (e) {
                if (e.keyCode === 17)
                    isControl = false;
            });
            if (!dialogAdded) {
                $('body').append($('<div id="EditorDialog"><div id="EditorDialogContent"></div><div class="sepLine"></div><div class="buttonBar"><button class="button greenButton" id="EditorDialogAcceptButton">تائید</button></div></div>'));
                $('#EditorDialog').dialog();
                dialogAdded = true;
            }
            var buttonsBar = $('<div class="editor_buttons"></div>');
            buttonsBar.append(addTag($('<a tabindex="-1" href="" class="iconLink_15 editor_bold" title="برجسته (Ctrl+B)"></a>'), '*'));
            buttonsBar.append(addTag($('<a tabindex="-1" href="" class="iconLink_15 editor_italic" title="ایتالیک (Ctrl+I)"></a>'), '/'));
            buttonsBar.append(addTag($('<a tabindex="-1" href="" class="iconLink_15 editor_underline" title="زیر خط (Ctrl+D)"></a>'), '_'));
            buttonsBar.append(addLineStyle($('<a tabindex="-1" href="" class="iconLink_15 editor_number" title="لیست عددی (Ctrl+O)"></a>'), 1, '#'));
            buttonsBar.append(addLineStyle($('<a tabindex="-1" href="" class="iconLink_15 editor_bullet" title="لیست نمادی (Ctrl+U)"></a>'), 1, '*'));
            var hrButton = $('<a tabindex="-1" href="" class="iconLink_15 editor_hline" title="خط عمودی (Ctrl+H)"></a>');
            hrButton.click(function (e) {
                e.preventDefault();
                doLineStyle($(this).parent().parent().find('textarea')[0], '-', 2, true);
            });
            buttonsBar.append(hrButton);
            var linkButton = $('<a tabindex="-1" href="#" class="iconLink_15 editor_link" title="لینک (Ctrl+L)"></a>');
            linkButton.click(function (e) {
                e.preventDefault();
                doLink($(this).parent().parent().find('textarea')[0]);
            });
            buttonsBar.append(linkButton);
            var imageButton = $('<a tabindex="-1" href="" class="iconLink_15 editor_image" title="تصویر (Ctrl+G)"></a>');
            imageButton.click(function (e) {
                e.preventDefault();
                doImage($(this).parent().parent().find('textarea')[0]);
            });
            buttonsBar.append(imageButton);
            var codeButton = $('<a tabindex="-1" href="" class="iconLink_15 editor_code" title="کد (Ctrl+K)"></a>');
            codeButton.click(function (e) {
                e.preventDefault();
                doCode($(this).parent().parent().find('textarea')[0]);
            });
            buttonsBar.append(codeButton);
            buttonsBar.append(addLineStyle($('<a tabindex="-1" href="" class="iconLink_15 editor_head1" title="هد 1 (Ctrl+1)"></a>'), 1, '!'));
            buttonsBar.append(addLineStyle($('<a tabindex="-1" href="" class="iconLink_15 editor_head2" title="هد 2 (Ctrl+2)"></a>'), 2, '!'));
            buttonsBar.append(addLineStyle($('<a tabindex="-1" href="" class="iconLink_15 editor_head3" title="هد 3 (Ctrl+3)"></a>'), 3, '!'));
            buttonsBar.append(addLineStyle($('<a tabindex="-1" href="" class="iconLink_15 editor_head4" title="هد 4 (Ctrl+4)"></a>'), 4, '!'));
            buttonsBar.append(addLineStyle($('<a tabindex="-1" href="" class="iconLink_15 editor_head5" title="هد 5 (Ctrl+5)"></a>'), 5, '!'));
            buttonsBar.append(addLineStyle($('<a tabindex="-1" href="" class="iconLink_15 editor_head6" title="هد 6 (Ctrl+6)"></a>'), 6, '!'));
            var previewButton = $('<a tabindex="-1" href="" class="iconLink_15 editor_preview" title="پیش نمایش (Ctrl+P)"></a>');
            previewButton.click(function (e) {
                e.preventDefault();
                doPreview($(this).parent().parent().find('textarea')[0]);
            });
            buttonsBar.append(previewButton);
            editorContainer.append(buttonsBar);
            editorContainer.append(newTextArea);
        });
    };

    function addTag(button, type) {
        button.click(function (e) {
            e.preventDefault();
            wrapSelection($(this).parent().parent().find('textarea')[0], type);
        });
        return button;
    }

    function doPreview(ta) {
        $('#EditorDialogContent').html('<h4>در حال بارگذاری</h4>');
        $.ajax({
            url: purl,
            data: { content: ta.value },
            type: 'post',
            cache: false,
            success: function (result) {
                if (result != null && result.accessDenied) {
                    alert('امکان انجام درخواست شما وجود ندارد.');
                } else {
                    $('#EditorDialog').dialog({
                        title: 'پیش نمایش',
                        open: true,
                        width: 700,
                        afterDisplay: function () {
                            var paneContent = $('<div class="paneContent content"></div>');
                            paneContent.html(result);
                            $('#EditorDialogContent').html(paneContent);
                            $('#EditorDialogContent').find('pre').each(function () {
                                SyntaxHighlighter.highlight($(this)[0]);
                            });
                            $('#EditorDialogAcceptButton').click(function () {
                                $('#EditorDialog').dialogclose();
                            });
                        },
                        onClose: function () {
                            ta.focus();
                        }
                    });
                }
            },
            error: function (err) {
                alert(err);
                alert('مشکل در انجام عملیات');
            }
        });
    }

    function addLineStyle(button, size, type) {
        button.click(function (e) {
            e.preventDefault();
            doLineStyle($(this).parent().parent().find('textarea')[0], type, size);
        });
        return button;
    }

    function doLink(ta) {
        var selection = new Selection(ta);
        var s = selection.create();
        var substring = '';
        if (s.end > s.start) {
            substring = ta.value.substring(s.start, s.end);
        }
        var linkEditor = $('<div class="paneContent"></div>');
        linkEditor.append($('<input type="hidden" id="LinkEditorStartIndex" value="' + s.start + '" />'));
        linkEditor.append($('<input type="hidden" id="LinkEditorEndIndex" value="' + s.end + '" />'));
        var editorTable = $('<table style="width: 100%;"><tr><td>عنوان لینک</td><td><input type="textbox" style="width: 100%;" class="textBox" id="LinkEditorTitleInput" value="' + substring + '" /></td></tr><tr><td>آدرس لینک</td><td><input type="textbox" class="textBox" id="LinkEditorAddressInput" style="width: 100%; direction: ltr;" /></td></tr></table>');
        linkEditor.append(editorTable);
        var linkEditorContainer = $('<div></div>');
        linkEditorContainer.append(linkEditor);
        $('#EditorDialog').dialog({
            title: 'درج لینک',
            open: true,
            afterDisplay: function () {
                $('#EditorDialogContent').html(linkEditorContainer);
                $('#EditorDialogAcceptButton').click(function () {
                    var start = $('#LinkEditorStartIndex').attr('value');
                    var end = $('#LinkEditorEndIndex').attr('value');
                    var title = $('#LinkEditorTitleInput').val();
                    var address = $('#LinkEditorAddressInput').val();
                    var result = '|';
                    if (title != '')
                        result += title + '::';
                    result += address + "|";
                    ta.value = ta.value.substring(0, start) + result + ta.value.substring(end);
                    ta.focus();
                    setCaretPosition(ta, s.start + result.length);
                    $('#EditorDialog').dialogclose();
                    ta.focus();
                });
                if (substring != '')
                    $('#LinkEditorAddressInput').focus();
                else
                    $('#LinkEditorTitleInput').focus();
            },
            onClose: function () {
                ta.focus();
            }
        });
    }

    function doCode(ta) {
        var selection = new Selection(ta);
        var s = selection.create();
        var substring = '';
        if (s.end > s.start) {
            substring = ta.value.substring(s.start, s.end);
        }
        var codeEditor = $('<div class="paneContent"></div>');
        codeEditor.append($('<input type="hidden" id="LinkEditorStartIndex" value="' + s.start + '" />'));
        codeEditor.append($('<input type="hidden" id="LinkEditorEndIndex" value="' + s.end + '" />'));
        var select = '<select style="direction: ltr;" id="EditorCodeLanguage"><option value="c#">CSharp</option><option value="vb">Visual Basic</option><option value="xml">XML</option><option value="sql">SQL</option><option value="js">Java Script</option><option value="htm">HTML</option><option value="powershell">Powershell</option><option value="css">CSS</option><option value="ruby">Ruby</option><option value="python">Python</option><option value="cpp">C++</option><option value="php">PHP</option><option value="java">Java</option><option value="text">Plain Text</option></select>';
        var editorTable = $('<table style="width: 100%;"><tr><td style="width: 70px;">انتخاب زبان</td><td>' + select + '</td></tr></table>');
        codeEditor.append(editorTable);
        codeEditor.append($('<textarea rows="20" cols="50" style="width: 99%; direction: ltr;" id="EditorCodeContent" class="textArea">' + substring + '</textarea>'));
        var codeEditorContainer = $('<div></div>');
        codeEditorContainer.append(codeEditor);
        $('#EditorDialog').dialog({
            title: 'درج کد',
            open: true,
            width: 500,
            afterDisplay: function () {
                $('#EditorDialogContent').html(codeEditorContainer);
                $('#EditorDialogAcceptButton').click(function () {
                    var start = $('#LinkEditorStartIndex').attr('value');
                    var end = $('#LinkEditorEndIndex').attr('value');
                    var language = $('#EditorCodeLanguage').val();
                    var content = $('#EditorCodeContent').val();
                    var result = '<' + language + '>\n' + content + '\n<' + language + '>';
                    ta.value = ta.value.substring(0, start) + result + ta.value.substring(end);
                    ta.focus();
                    setCaretPosition(ta, s.start + result.length);
                    $('#EditorDialog').dialogclose();
                    ta.focus();
                });
                $('#EditorCodeContent').focus();
            },
            onClose: function () {
                ta.focus();
            }
        });
    }

    function doImage(ta) {
        var selection = new Selection(ta);
        var s = selection.create();
        var substring = '';
        if (s.end > s.start) {
            substring = ta.value.substring(s.start, s.end);
        }
        var imageEditor = $('<div class="paneContent" style="text-align: center;"></div>');
        imageEditor.append($('<input type="hidden" id="LinkEditorStartIndex" value="' + s.start + '" />'));
        imageEditor.append($('<input type="hidden" id="LinkEditorEndIndex" value="' + s.end + '" />'));
        imageEditor.append($('<input type="hidden" id="ImageEditorSelectedImage" value="" />'));
        var imageUploadForm = $('<form action="' + durl + '" method="post" id="EditorImageForm" enctype="multipart/form-data"></form>');
        imageUploadForm.append($(ftoken));
        imageUploadForm.append($('<button type="button" class="editor_choosebutton ui-corner-all selected" disabled="disabled" id="EditorImageFromUrlButton">از آدرس وب</button><button type="button" class="editor_choosebutton ui-corner-all" id="EditorImageFromFileButton">از فایل</button>'));
        imageUploadForm.append($('<div id="EditorImageFromUrl"><table style="width: 100%;"><tr><td style="width: 70px;">آدرس تصویر</td><td><input type="textbox" class="textBox" style="width: 100%; direction: ltr;" id="EditorImageUrlInput" name="url" /></td></tr></table></div>'));
        imageUploadForm.append($('<div id="EditorImageFromFile"><input type="file" style="border: 1px solid gray; padding: 2px; width: 80%; direction: ltr;" id="EditorImageFileInput" name="file" /></div>'));
        imageUploadForm.append($('<img src="" alt="" style="margin-top: 4px; width: 100px; height: 100px;" id="EditorImageEditorPreview" />'));
        imageUploadForm.append($('<div><button type="submit" style="border: 1px solid gray; padding: 4px; margin-top: 4px;" id="EditorImageSubmitButton">ارسال عکس</button></div>'));
        imageUploadForm.append($('<div><a class="iconLink_15 ajax_icon" style="cursor: default; margin-top: 4px;" id="EditorImageAjax" /></div>'));
        imageUploadForm.append($('<div style="margin-top: 4px;" id="EditorImageSuccess"><span style="color: green;">فایل با موفقیت بر روی سرور قرار گرفت</span></div>'));
        imageUploadForm.append($('<div style="margin-top: 4px;" id="EditorImageError"><span style="color: red;">فرمت فایل یا آدرس انتخابی صحیح نمی باشد</span></div>'));
        imageEditor.append(imageUploadForm);
        var imageEditorContainer = $('<div></div>');
        imageEditorContainer.append(imageEditor);
        imageEditorContainer.append($('<div class="sepLine"></div>'));
        imageEditorContainer.append($('<div class="paneContent" style="margin-bottom: 4px;"><table style="width: 100%;"><tr><td style="width: 90px;">توضیحات عکس</td><td><input type="textbox" class="textBox" style="width: 100%;" id="EditorImageAltInput" value="' + substring + '" /></td></tr></table></div>'));
        $('#EditorDialog').dialog({
            title: 'درج عکس',
            open: true,
            width: 500,
            afterDisplay: function () {
                $('#EditorDialogContent').html(imageEditorContainer);
                $('#EditorImageFromFile').hide();
                $('#EditorImageAjax').hide();
                $('#EditorImageSuccess').hide();
                $('#EditorImageError').hide();
                $('#EditorImageUrlInput').focus();
                $('#EditorImageForm').ajaxForm({
                    iframe: true,
                    dataType: 'json',
                    beforeSubmit: function () {
                        $('#EditorImageError').hide();
                        $('#EditorImageSuccess').hide();
                        $('#EditorImageAjax').show();
                        $('#EditorImageSubmitButton').attr('disabled', 'disabled');
                    },
                    success: function (result) {
                        $('#EditorImageAjax').hide();
                        $('#EditorImageSubmitButton').removeAttr('disabled');
                        if (result == null || result.status == undefined || result.status === false) {
                            $('#EditorImageError').show();
                            return;
                        }
                        $('#EditorImageSuccess').show();
                        $('#ImageEditorSelectedImage').attr('value', result.url);
                        $('#EditorImageEditorPreview').attr('src', result.url);
                    },
                    error: function () {
                        $('#EditorImageError').show();
                        $('#EditorImageSubmitButton').removeAttr('disabled');
                        $('#EditorImageAjax').hide();
                    }
                });
                $('#EditorImageFromUrlButton').click(function (e) {
                    e.preventDefault();
                    $('#EditorImageFromFileButton').removeAttr('disabled');
                    $('#EditorImageFromFileButton').removeClass('selected');
                    $('#EditorImageForm').attr('action', durl);
                    $(this).attr('disabled', 'disabled');
                    $(this).addClass('selected');
                    $('#EditorImageFromUrl').show();
                    $('#EditorImageFromFile').hide();
                    $('#EditorImageUrlInput').focus();
                });
                $('#EditorImageFromFileButton').click(function (e) {
                    e.preventDefault();
                    $('#EditorImageForm').attr('action', uurl);
                    $('#EditorImageFromUrlButton').removeAttr('disabled');
                    $('#EditorImageFromUrlButton').removeClass('selected');
                    $(this).attr('disabled', 'disabled');
                    $(this).addClass('selected');
                    $('#EditorImageFromUrl').hide();
                    $('#EditorImageFromFile').show();
                    $('#EditorImageFileInput').focus();
                });
                $('#EditorDialogAcceptButton').click(function () {
                    var start = $('#LinkEditorStartIndex').attr('value');
                    var end = $('#LinkEditorEndIndex').attr('value');
                    var title = $('#EditorImageAltInput').val();
                    var address = $('#ImageEditorSelectedImage').attr('value');
                    var result = '||';
                    if (title != '')
                        result += title + '::';
                    result += address + "||";
                    ta.value = ta.value.substring(0, start) + result + ta.value.substring(end);
                    ta.focus();
                    setCaretPosition(ta, s.start + result.length);
                    $('#EditorDialog').dialogclose();
                    ta.focus();
                });
                $('#EditorCodeContent').focus();
            },
            onClose: function () {
                ta.focus();
            }
        });
    }

    function wrapSelection(ta, type) {
        var selection = new Selection(ta);
        var s = selection.create();
        var substring = ta.value.substring(s.start, s.end);
        var textSelected = true;
        if (substring === '') {
            textSelected = false;
            substring = 'متن';
        }
        ta.value = ta.value.substring(0, s.start) + type + substring + type + ta.value.substring(s.end);
        if (textSelected) {
            setCaretPosition(ta, s.start + substring.length + 2);
        }
        else {
            selectText(ta, s.start + 1, substring.length);
        }
        ta.focus();
    }

    function doLineStyle(ta, type, size, dontSpaceEnd) {
        var selection = new Selection(ta);
        var s = selection.create();
        var index;
        for (index = s.start; index >= 0; index--) {
            if (ta.value[index] == '\n') {
                break;
            }
        }
        if (index > 0)
            index += 1;
        else if (index == -1)
            index = 0;
        var result = '';
        for (var counter = 1; counter <= size; counter++) {
            result += type;
        }
        if (ta.value.substring(index, index + size + 1) != result + ' ') {
            if (dontSpaceEnd == undefined)
                result += ' ';
            ta.value = ta.value.substring(0, index) + result + ta.value.substring(index);
        }
        else {
            ta.value = ta.value.substring(0, index) + ta.value.substring(index + size + 1);
        }
        ta.focus();
        setCaretPosition(ta, s.start + size + 1);
    }

    function selectText(ta, startIndex, length) {
        if (ta.createTextRange) {
            var textRange = ta.createTextRange();
            textRange.move('character', startIndex);
            textRange.moveEnd('character', length);
            textRange.select();
        }
        else {
            ta.selectionStart = startIndex;
            ta.selectionEnd = startIndex + length;
        }
    }

    function setCaretPosition(ta, pos) {
        if (ta.createTextRange) {
            var textRange = ta.createTextRange();
            textRange.move('character', pos);
            textRange.select();
        }
        else {
            ta.selectionStart = pos;
            ta.selectionEnd = pos;
        }
    }

    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() + "##";
    };
})(jQuery)
