0

У меня проблема, аналогичная тем, о которых сообщалось как here, так и here, с несколькими изменениями в том, как загружаются мои данные формы.jQuery UI, AJAX и CKEditor - CKEditor загружает только первый раз

Решение, представленное во второй ссылке, по-видимому, устраняет мою проблему, но удаление эффектов масштабирования show/hide не требуется, чтобы CKEditor корректно создавал экземпляр. Там будет гораздо лучшая альтернатива разрешению этого конфликта.

Мой вопрос:

Когда я открываю страницу и нажмите на кнопку редактирования, jQueryUI Dialog выскакивает, загружает свои данные через AJAX, а затем я пытаюсь заменить текстовое поле добавляется в диалоговое окно с экземпляр CKEditor. При первом запуске страницы диалог работает без сбоев. Я могу изменить данные в редакторе, сохранить данные формы и продолжить жизнь. Однако, если я закрою диалог, а затем снова откроем его, редактор больше не будет включен. Кнопки все еще имеют эффекты зависания и доступны для кликов, но ничего не делают. Текстовая область редактора отключена и установлена ​​в "style: visibility: hidden; display: none;". Почти вся информация, которую я могу найти по этой проблеме, - это много лет назад, и исправления связаны с использованием функций/методов, которые больше не существуют или применимы.

Управление потоком

Я открываю страницу, содержащую текстовую ссылку 'Edit Update', который вызывает мою функцию Javascript openEditTicketUpdateDialog.

function openEditTicketUpdateDialog(tup_id, url) 
    { 
     simplePost(null, url, new Callback 
     (
      function onSuccess(data) 
      { 
       $('#editticketupdatedialog').dialog('option', 'buttons', 
       [ 
        { 
         text: 'Save Edits', 
         click: function() 
         { 
          // Save the Update info 
          var formData = { 
           tup_update: CKEDITOR.instances.tup_update_edit.getData(), 
           tup_internal: +$('#tup_internal_edit').is(":checked"), 
           tup_important: +$('#tup_important_edit').is(":checked") 
          }; 

          simplePost(formData, data['submitRoute'], new Callback 
          (
           function onSuccess(data) 
           { 
            $('#update-' + tup_id).html(data.input['tup_update']); 
            $('#updateflags-' + tup_id).html(data.flags); 
            $('#editticketupdatedialog').dialog('close'); 
           }, 
           function onFail(errors) 
           { 
            console.log(errors); 
           } 
          )); 
         } 
        }, 
        { 
         text: 'Cancel', 
         click: function() 
         { 
          $(this).dialog("close"); 
         } 
        } 
       ]); 

       $('#editticketupdatedialog').dialog('option', 'title', data['title']); 
       $('#editticketupdatedialog').html(data['view']); 
       $('#editticketupdatedialog').dialog('open'); 

       destroyEditor('tup_update_edit'); 

       console.log('CKEDITOR.status: ' + CKEDITOR.status); 
       createEditor('tup_update_edit'); 

      }, 
      function onFail(errors) 
      { 
       console.log(errors); 
      } 
     )); 
    } 

Эта функция использует три вспомогательные функции, simplePost, destroyEditor и createEditor.

function simplePost(data, url, callback) 
{ 
    post(data, url, true, false, callback); 
} 

function createEditor(name) 
{ 
    console.log('Create editor: ' + name); 
    console.log('Current Instance: '); 
    console.log(CKEDITOR.instances.name); 

    if (CKEDITOR.status == 'loaded') 
    { 
     CKEDITOR.replace(name, 
     { 
      customConfig: '/js/ckeditor/custom/configurations/standard_config.js' 
     }); 
    } 
    else 
    { 
     CKEDITOR.on('load', createEditor(name)); 
     CKEDITOR.loadFullCore && CKEDITOR.loadFullCore(); 
    } 

    console.log('After instance created: '); 
    var instance = CKEDITOR.instances.name; 
    console.log(instance); 
} 

function destroyEditor(name) 
{ 
    console.log('Destroy editor: ' + name); 
    console.log('Current Instance: '); 
    console.log(CKEDITOR.instances.name); 

    if (CKEDITOR.instances.name) 
    { 
     console.log('Instance exists - destroying...'); 
     CKEDITOR.instances.name.destroy(); 
     $('#' + name).off().remove(); 
    } 

    console.log('After instance removed: '); 
    var instance = CKEDITOR.instances.name; 
    console.log(instance); 
} 

Этот метод создания экземпляра CKEditor была собрана из here. Этот метод уничтожения экземпляра CKEditor был собран с here.

Как вы можете видеть, openEditTicketUpdateDialog запускает вызов AJAX моей функции getEditUpdateForm через маршруты Laravel.

public function getEditUpdateForm($tup_id, $update_number) 
{ 
    $update = Update::find($tup_id); 

    $data = [ 
     'title' => 'Editing update #' . $update_number . ' of ticket #' . $update->tup_ticket, 
     'view' => View::make('tickets.ticketupdate-edit') 
      ->with('update', $update) 
      ->render(), 
     'submitRoute' => route('tickets/update/submit', $tup_id) 
    ]; 

    return Response::json(array('status' => 1, 'data' => $data)); 
} 

Отсюда, состояние 1, возвращается, и функция onSuccess называется. Я попытался добавить вызовы create/delete перед вызовом $('#editticketupdatedialog').dialog('open');, но безрезультатно. Я также попробовал несколько других решений, которые я нашел на поверхности, которые включают взломанные реализации функций и атрибутов jQueryUI: _allowInteraction и moveToTop. не я изначально был успешным в решении этого вопроса в первый раз, когда он возник, вызвав эту функцию перед выполнением CKEDITOR.replace:

function enableCKEditorInDialog() 
{ 
    $.widget("ui.dialog", $.ui.dialog, { 
    /** 
    * jQuery UI v1.11+ fix to accommodate CKEditor (and other iframed content) inside a dialog 
    * @see http://bugs.jqueryui.com/ticket/9087 
    * @see http://dev.ckeditor.com/ticket/10269 
    */ 
    _allowInteraction: function(event) { 
     return this._super(event) || 

     // addresses general interaction issues with iframes inside a dialog 
     event.target.ownerDocument !== this.document[ 0 ] || 

     // addresses interaction issues with CKEditor's dialog windows and iframe-based dropdowns in IE 
     !!$(event.target).closest(".cke_dialog, .cke_dialog_background_cover, .cke").length; 
    } 
    }); 
} 

После обновления Laravel 5, и сделать несколько других изменений ServerSide, это исправление не работает. Мне удалось решить проблему, удалив свойства show/hide из моего диалога. Я бы предпочел не удалять эти свойства, так как половина аргументов за наличие диалога - это эстетика анимации. Вот моя инициализация диалога.

$('#editticketupdatedialog').dialog({ 
    modal: true, 
    draggable: false, 
    minWidth: 722, 
    autoOpen: false, 
    show: 
    { 
     effect: "scale", 
     duration: 200 
    }, 
    hide: 
    { 
     effect: "scale", 
     duration: 200 
    }, 
    closeOnEscape: true 
}); 

Когда я включил эти анимации, в первый раз, когда я использую диалог, он отлично работает.Второй раз, я получаю ошибку TypeError: this.getWindow(...).$ is undefined - ckeditor.js:83:18 в консоли JS, которая относится к этой линии:

function(a) 
{ 
    var d = this.getWindow().$.getComputedStyle(this.$,null); 

    return d ? d.getPropertyValue(a) : "" 
} 

резюмировать

Моей главной цели здесь, чтобы найти решение этой проблемы, без необходимости удалите анимацию jQueryUI Dialog. Я не уверен, на кого указывать пальцы, поскольку я действительно не могу определить, находится ли проблема в CKEditor, jQueryUI или моей реализации.

ответ

0

Наконец-то я нашел решение, которое работает в моем случае. losnir обновил устаревшее решение до сообщения here и добавив открытую функцию в мою инициализацию диалога, разрешил мою проблему.

Моя инициализация выглядит следующим образом:

$('#editticketupdatedialog').dialog({ 
    modal: true, 
    draggable: false, 
    minWidth: 722, 
    autoOpen: false, 
    show: 
    { 
     effect: "scale", 
     duration: 200 
    }, 
    hide: 
    { 
     effect: "scale", 
     duration: 200 
    }, 
    closeOnEscape: true, 
    open: function() 
    { 
     $(this).parent().promise().done(function() 
     { 
      destroyEditor('tup_update_edit'); 

      console.log('CKEDITOR.status: ' + CKEDITOR.status); 
      createEditor('tup_update_edit'); 
     }); 
    } 
});