Как вы можете интегрировать пользовательский файловый браузер / загрузчик с CKEditor?


официальная документация менее чем понятна - как правильно интегрировать пользовательский файловый браузер / загрузчик с CKEditor? (v3-не FCKEditor)

8 109

8 ответов:

начните с регистрации пользовательского браузера / загрузчика при создании экземпляра CKEditor. Вы можете назначить разные URL-адреса для браузера изображений и общего браузера файлов.

<script type="text/javascript">
CKEDITOR.replace('content', {
    filebrowserBrowseUrl : '/browser/browse/type/all',
    filebrowserUploadUrl : '/browser/upload/type/all',
    filebrowserImageBrowseUrl : '/browser/browse/type/image',
filebrowserImageUploadUrl : '/browser/upload/type/image',
    filebrowserWindowWidth  : 800,
    filebrowserWindowHeight : 500
});
</script>

ваш пользовательский код получит параметр GET с именем CKEditorFuncNum. Сохранить его - это ваша функция обратного вызова. Допустим, вы положили его в $callback.

когда кто-то выбирает файл, запустите этот JavaScript, чтобы сообщить CKEditor, какой файл был выбран:

window.opener.CKEDITOR.tools.callFunction(<?php echo $callback; ?>,url)

где" url" URL-адрес файла, который они выбрали. Необязательным третьим параметром может быть текст, который вы хотите отобразить в стандартном диалоговом окне предупреждения, например "незаконный файл" или что-то еще. Установите url-адрес в пустую строку, если третий параметр является сообщением об ошибке.

вкладка CKEditor "upload "отправит файл в поле" upload " - в PHP, который переходит в $_FILES['upload']. То, что CKEditor хочет, чтобы ваш сервер выводил полный блок JavaScript:

$output = '<html><body><script type="text/javascript">window.parent.CKEDITOR.tools.callFunction('.$callback.', "'.$url.'","'.$msg.'");</script></body></html>';
echo $output;

опять же, вам нужно дать ему этот обратный вызов параметр, URL-адрес файла и, возможно, сообщение. Если сообщение является пустой строкой, ничего не будет отображаться, если сообщение об ошибке, то URL должен быть пустой строкой.

официальная документация CKEditor является неполной по всему этому, но если вы будете следовать выше, это будет работать как чемпион.

Я опубликовал один небольшой учебник об интеграции FileBrowser доступны в старом FCKEditor в CKEditor.

http://www.mixedwaves.com/2010/02/integrating-fckeditor-filemanager-in-ckeditor/

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

Я просто прошел через процесс обучения сам. Я понял это, но я согласен, что документация написана таким образом, что это было немного пугающе для меня. Большой" ага " момент для меня было понимание того, что для просмотра, все CKeditor делает это открыть новое окно и предоставить несколько параметров в url. Это позволяет добавлять дополнительные параметры, но имейте в виду, что вам нужно будет использовать encodeURIComponent() на ваших значениях.

Я вызываю браузер и загрузчик с

CKEDITOR.replace( 'body',  
{  
    filebrowserBrowseUrl: 'browse.php?type=Images&dir=' +  
        encodeURIComponent('content/images'),  
    filebrowserUploadUrl: 'upload.php?type=Files&dir=' +  
        encodeURIComponent('content/images')  
}

на обозреватель в открывшемся окне (обзор.php) вы используете php & js для предоставления списка вариантов, а затем на предоставленном обработчике onclick вы вызываете функцию CKeditor с двумя аргументами: url / путь к выбранному изображению и ckeditorfuncnum, предоставленный CKeditor в url:

function myOnclickHandler(){  
//..    
    window.opener.CKEDITOR.tools.callFunction(<?php echo $_GET['CKEditorFuncNum']; ?>, pathToImage);  
    window.close();
}       

Simarly, the uploader просто вызывает url, который вы предоставляете, например,загрузить.php и опять поставки $_GET ['CKEditorFuncNum']. Цель iframe Итак, после сохранения файла из $_FILES вы передаете свой отзыв CKeditor следующим образом:

$funcNum = $_GET['CKEditorFuncNum'];  
exit("<script>window.parent.CKEDITOR.tools.callFunction($funcNum, '$filePath', '$errorMessage');</script>");  

Ниже приведен простой для понимания пользовательский скрипт браузере. Хотя он не позволяет пользователям перемещаться по серверу, он позволяет указать, из какого каталога извлекать файлы изображений при вызове браузера.

это все довольно простое кодирование, поэтому оно должно работать во всех относительно современных браузерах.

CKeditor просто открывает новое окно с указанным url

/*          
    in CKeditor **use encodeURIComponent()** to add dir param to the filebrowserBrowseUrl property

    Replace content/images with directory where your images are housed.
*/          
        CKEDITOR.replace( 'editor1', {  
            filebrowserBrowseUrl: '**browse.php**?type=Images&dir=' + encodeURIComponent('content/images'),  
            filebrowserUploadUrl: 'upload.php?type=Files&dir=' + encodeURIComponent('content/images') 
        });   

// ========= полный код ниже обзор.php

<?php  
header("Content-Type: text/html; charset=utf-8\n");  
header("Cache-Control: no-cache, must-revalidate\n");  
header("Expires: Sat, 26 Jul 1997 05:00:00 GMT");  

// e-z params  
$dim = 150;         /* image displays proportionally within this square dimension ) */  
$cols = 4;          /* thumbnails per row */
$thumIndicator = '_th'; /* e.g., *image123_th.jpg*) -> if not using thumbNails then use empty string */  
?>  
<!DOCTYPE html>  
<html>  
<head>  
    <title>browse file</title>  
    <meta charset="utf-8">  

    <style>  
        html,  
        body {padding:0; margin:0; background:black; }  
        table {width:100%; border-spacing:15px; }  
        td {text-align:center; padding:5px; background:#181818; }  
        img {border:5px solid #303030; padding:0; verticle-align: middle;}  
        img:hover { border-color:blue; cursor:pointer; }  
    </style>  

</head>  


<body>  

<table>  

<?php  

$dir = $_GET['dir'];    

$dir = rtrim($dir, '/'); // the script will add the ending slash when appropriate  

$files = scandir($dir);  

$images = array();  

foreach($files as $file){  
    // filter for thumbNail image files (use an empty string for $thumIndicator if not using thumbnails )
    if( !preg_match('/'. $thumIndicator .'\.(jpg|jpeg|png|gif)$/i', $file) )  
        continue;  

    $thumbSrc = $dir . '/' . $file;  
    $fileBaseName = str_replace('_th.','.',$file);  

    $image_info = getimagesize($thumbSrc);  
    $_w = $image_info[0];  
    $_h = $image_info[1]; 

    if( $_w > $_h ) {       // $a is the longer side and $b is the shorter side
        $a = $_w;  
        $b = $_h;  
    } else {  
        $a = $_h;  
        $b = $_w;  
    }     

    $pct = $b / $a;     // the shorter sides relationship to the longer side

    if( $a > $dim )   
        $a = $dim;      // limit the longer side to the dimension specified

    $b = (int)($a * $pct);  // calculate the shorter side

    $width =    $_w > $_h ? $a : $b;  
    $height =   $_w > $_h ? $b : $a;  

    // produce an image tag
    $str = sprintf('<img src="%s" width="%d" height="%d" title="%s" alt="">',   
        $thumbSrc,  
        $width,  
        $height,  
        $fileBaseName  
    );  

    // save image tags in an array
    $images[] = str_replace("'", "\'", $str); // an unescaped apostrophe would break js  

}

$numRows = floor( count($images) / $cols );  

// if there are any images left over then add another row
if( count($images) % $cols != 0 )  
    $numRows++;  


// produce the correct number of table rows with empty cells
for($i=0; $i<$numRows; $i++)   
    echo "\t<tr>" . implode('', array_fill(0, $cols, '<td></td>')) . "</tr>\n\n";  

?>  
</table>  


<script>  

// make a js array from the php array
images = [  
<?php   

foreach( $images as $v)  
    echo sprintf("\t'%s',\n", $v);  

?>];  

tbl = document.getElementsByTagName('table')[0];  

td = tbl.getElementsByTagName('td');  

// fill the empty table cells with data
for(var i=0; i < images.length; i++)  
    td[i].innerHTML = images[i];  


// event handler to place clicked image into CKeditor
tbl.onclick =   

    function(e) {  

        var tgt = e.target || event.srcElement,  
            url;  

        if( tgt.nodeName != 'IMG' )  
            return;  

        url = '<?php echo $dir;?>' + '/' + tgt.title;  

        this.onclick = null;  

        window.opener.CKEDITOR.tools.callFunction(<?php echo $_GET['CKEditorFuncNum']; ?>, url);  

        window.close();  
    }  
</script>  
</body>  
</html>            

Я потратил некоторое время пыталась разобраться и вот что я сделал. Я сломал его очень просто, как это то, что мне нужно.

прямо под текстовой областью ckeditor введите файл загрузки следующим образом >>>>

<form action="welcomeeditupload.asp" method="post" name="deletechecked">
    <div align="center">
        <br />
        <br />
        <label></label>
        <textarea class="ckeditor" cols="80" id="editor1" name="editor1" rows="10"><%=(rslegschedule.Fields.Item("welcomevar").Value)%></textarea>
        <script type="text/javascript">
        //<![CDATA[
            CKEDITOR.replace( 'editor1',
            {
                filebrowserUploadUrl : 'updateimagedone.asp'
            });
        //]]>
        </script>
        <br />
        <br />
        <br />
        <input type="submit" value="Update">
    </div>
</form>

' а затем добавьте свой файл загрузки, вот мой, который написан на ASP. Если вы используете PHP и т. д. просто замените ASP на свой скрипт загрузки, но убедитесь, что страница выводит то же самое.

<%@LANGUAGE="VBSCRIPT" CODEPAGE="65001"%>
<%
    if Request("CKEditorFuncNum")=1 then
        Set Upload = Server.CreateObject("Persits.Upload")
        Upload.OverwriteFiles = False
        Upload.SetMaxSize 5000000, True
        Upload.CodePage = 65001

        On Error Resume Next
        Upload.Save "d:\hosting\belaullach\senate\legislation"

        Dim picture
        For Each File in Upload.Files
            Ext = UCase(Right(File.Path, 3))
            If Ext <> "JPG" Then
                    If Ext <> "BMP" Then
                    Response.Write "File " & File.Path & " is not a .jpg or .bmp file." & "<BR>"
                    Response.write "You can only upload .jpg or .bmp files." & "<BR>" & "<BR>"
                    End if
            Else
                File.SaveAs Server.MapPath(("/senate/legislation") & "/" & File.fileName)
                f1=File.fileName
            End If
        Next
    End if

    fnm="/senate/legislation/"&f1
    imgop = "<html><body><script type=""text/javascript"">window.parent.CKEDITOR.tools.callFunction('1','"&fnm&"');</script></body></html>;"
    'imgop="callFunction('1','"&fnm&"',"");"
    Response.write imgop
%>

это подход, который я использовал. Это довольно просто, и работает просто отлично.

в корневом каталоге редактора CK есть файл с именем config.js

я добавил Это (вам не нужен материал querystring, это только для нашего файлового менеджера). Я также включил некоторые скины и изменения кнопок по умолчанию показано:

CKEDITOR.editorConfig = function(config) {

    config.skin = 'v2';
    config.startupFocus = false;
    config.filebrowserBrowseUrl = '/admin/content/filemanager.aspx?path=Userfiles/File&editor=FCK';
    config.filebrowserImageBrowseUrl = '/admin/content/filemanager.aspx?type=Image&path=Userfiles/Image&editor=FCK';
    config.toolbar_Full =
    [
        ['Source', '-', 'Preview', '-'],
        ['Cut', 'Copy', 'Paste', 'PasteText', 'PasteFromWord', '-', 'Print', 'SpellChecker'], //, 'Scayt' 
        ['Undo', 'Redo', '-', 'Find', 'Replace', '-', 'SelectAll', 'RemoveFormat'],
        '/',
        ['Bold', 'Italic', 'Underline', 'Strike', '-', 'Subscript', 'Superscript'],
        ['NumberedList', 'BulletedList', '-', 'Outdent', 'Indent', 'Blockquote'],
        ['JustifyLeft', 'JustifyCenter', 'JustifyRight', 'JustifyBlock'],
        ['Link', 'Unlink', 'Anchor'],
        ['Image', 'Flash', 'Table', 'HorizontalRule', 'SpecialChar'],
        '/',
        ['Styles', 'Format', 'Templates'],
        ['Maximize', 'ShowBlocks']
    ];

};

затем наш файловый менеджер называет это:

opener.SetUrl('somefilename');

статья в zerokspot под названием пользовательские обратные вызовы filebrowser в CKEditor 3.0 обрабатывает это. Наиболее релевантный раздел приведен ниже:

поэтому все, что вам нужно сделать из файла браузер, когда у вас есть выбранный файл стоит вызвать этот код с правом номер обратного вызова (обычно 1) и URL-адрес выбранного файла:

window.opener.CKEDITOR.tools.callFunction(CKEditorFuncNum,url);

для быстрого загрузчика процесс является весьма похожий. Сначала я подумал, что редактор может быть, прислушиваясь 200 HTTP код возврата и возможно посмотреть в какое-то поле заголовка или что-то еще похоже, что для определения местоположения загруженный файл, но потом-через некоторые Firebug мониторинг-я заметил что все это происходит после загрузки это следующий код:

<script type="text/javascript">
window.parent.CKEDITOR.tools.callFunction(CKEditorFuncNum,url, errorMessage); </script>

если загрузка не удалась, установить errorMessage до некоторой ненулевой длины строка и пустой url, и вице наоборот на успех.

начните с регистрации пользовательского браузера / загрузчика при создании экземпляра CKEditor.

<script type="text/javascript">
CKEDITOR.replace('content', {
    filebrowserUploadUrl: "Upload File Url",//http://localhost/phpwork/test/ckFileUpload.php
    filebrowserWindowWidth  : 800,
    filebrowserWindowHeight : 500
});
</script>

код для загрузки файла(ckFileUpload.php) & поместите файл загрузки в корневой каталог вашего проекта.

// HERE SET THE PATH TO THE FOLDERS FOR IMAGES AND AUDIO ON YOUR SERVER (RELATIVE TO THE ROOT OF YOUR WEBSITE ON SERVER)

$upload_dir = array(
 'img'=> '/phpwork/test/uploads/editor-images/',
 'audio'=> '/phpwork/ezcore_v1/uploads/editor-images/'
);

// HERE PERMISSIONS FOR IMAGE
$imgset = array(
 'maxsize' => 2000,     // maximum file size, in KiloBytes (2 MB)
 'maxwidth' => 900,     // maximum allowed width, in pixels
 'maxheight' => 800,    // maximum allowed height, in pixels
 'minwidth' => 10,      // minimum allowed width, in pixels
 'minheight' => 10,     // minimum allowed height, in pixels
 'type' => array('bmp', 'gif', 'jpg', 'jpeg', 'png'),  // allowed extensions
);

// HERE PERMISSIONS FOR AUDIO
$audioset = array(
 'maxsize' => 20000,    // maximum file size, in KiloBytes (20 MB)
 'type' => array('mp3', 'ogg', 'wav'),  // allowed extensions
);

// If 1 and filename exists, RENAME file, adding "_NR" to the end of filename (name_1.ext, name_2.ext, ..)
// If 0, will OVERWRITE the existing file
define('RENAME_F', 1);

$re = '';
if(isset($_FILES['upload']) && strlen($_FILES['upload']['name']) >1) {
  define('F_NAME', preg_replace('/\.(.+?)$/i', '', basename($_FILES['upload']['name'])));  //get filename without extension

  // get protocol and host name to send the absolute image path to CKEditor
  $protocol = !empty($_SERVER['HTTPS']) ? 'https://' : 'http://';
  $site = $protocol. $_SERVER['SERVER_NAME'] .'/';
  $sepext = explode('.', strtolower($_FILES['upload']['name']));
  $type = end($sepext);    // gets extension
  $upload_dir = in_array($type, $imgset['type']) ? $upload_dir['img'] : $upload_dir['audio'];
  $upload_dir = trim($upload_dir, '/') .'/';

  //checkings for image or audio
  if(in_array($type, $imgset['type'])){
    list($width, $height) = getimagesize($_FILES['upload']['tmp_name']);  // image width and height
    if(isset($width) && isset($height)) {
      if($width > $imgset['maxwidth'] || $height > $imgset['maxheight']) $re .= '\n Width x Height = '. $width .' x '. $height .' \n The maximum Width x Height must be: '. $imgset['maxwidth']. ' x '. $imgset['maxheight'];
      if($width < $imgset['minwidth'] || $height < $imgset['minheight']) $re .= '\n Width x Height = '. $width .' x '. $height .'\n The minimum Width x Height must be: '. $imgset['minwidth']. ' x '. $imgset['minheight'];
      if($_FILES['upload']['size'] > $imgset['maxsize']*1000) $re .= '\n Maximum file size must be: '. $imgset['maxsize']. ' KB.';
    }
  }
  else if(in_array($type, $audioset['type'])){
    if($_FILES['upload']['size'] > $audioset['maxsize']*1000) $re .= '\n Maximum file size must be: '. $audioset['maxsize']. ' KB.';
  }
  else $re .= 'The file: '. $_FILES['upload']['name']. ' has not the allowed extension type.';

  //set filename; if file exists, and RENAME_F is 1, set "img_name_I"
  // $p = dir-path, $fn=filename to check, $ex=extension $i=index to rename
  function setFName($p, $fn, $ex, $i){
    if(RENAME_F ==1 && file_exists($p .$fn .$ex)) return setFName($p, F_NAME .'_'. ($i +1), $ex, ($i +1));
    else return $fn .$ex;
  }

  $f_name = setFName($_SERVER['DOCUMENT_ROOT'] .'/'. $upload_dir, F_NAME, ".$type", 0);
  $uploadpath = $_SERVER['DOCUMENT_ROOT'] .'/'. $upload_dir . $f_name;  // full file path

  // If no errors, upload the image, else, output the errors
  if($re == '') {
    if(move_uploaded_file($_FILES['upload']['tmp_name'], $uploadpath)) {
      $CKEditorFuncNum = $_GET['CKEditorFuncNum'];
      $url = $site. $upload_dir . $f_name;
      $msg = F_NAME .'.'. $type .' successfully uploaded: \n- Size: '. number_format($_FILES['upload']['size']/1024, 2, '.', '') .' KB';
      $re = in_array($type, $imgset['type']) ? "window.parent.CKEDITOR.tools.callFunction($CKEditorFuncNum, '$url', '$msg')"  //for img
       : 'var cke_ob = window.parent.CKEDITOR; for(var ckid in cke_ob.instances) { if(cke_ob.instances[ckid].focusManager.hasFocus) break;} cke_ob.instances[ckid].insertHtml(\'<audio src="'. $url .'" controls></audio>\', \'unfiltered_html\'); alert("'. $msg .'"); var dialog = cke_ob.dialog.getCurrent();  dialog.hide();';
    }
    else $re = 'alert("Unable to upload the file")';
  }
  else $re = 'alert("'. $re .'")';
}

@header('Content-type: text/html; charset=utf-8');
echo '<script>'. $re .';</script>';

документация Ck-editor не ясна после выполнения большого количества исследований и разработок для загрузки пользовательских файлов, наконец, я нашел это решение. Это работает для меня и я надеюсь, что это будет полезно для других.

для людей, интересующихся реализацией сервлета / JSP, вот как вы это делаете... Я буду объяснять uploadimage ниже.

1) Сначала убедитесь, что вы добавили filebrowser и uploadimage переменной конфиг.js файл. Сделать вас также есть uploadimage и filebrowser папка внутри папки плагинов тоже.

2) Эта часть, где он споткнулся меня вверх:

документация сайта Ckeditor говорит, что вам нужно использовать эти два метода:

function getUrlParam( paramName ) {
    var reParam = new RegExp( '(?:[\?&]|&)' + paramName + '=([^&]+)', 'i' );
    var match = window.location.search.match( reParam );
    return ( match && match.length > 1 ) ? match[1] : null;
}
function returnFileUrl() {
    var funcNum = getUrlParam( 'CKEditorFuncNum' );
    var fileUrl = 'https://patiliyo.com/wp-content/uploads/2017/07/ruyada-kedi-gormek.jpg';
    window.opener.CKEDITOR.tools.callFunction( funcNum, fileUrl );
    window.close();
}

они не упоминают, что эти методы должны быть на a другая страница, а не страница, на которой вы нажимаете обзор сервера из.

так что если у вас есть ckeditor инициализируется в Редакторе страниц.jsp тогда вам нужно создать файловый браузер (с базовым html/css/javascript) на странице файлообменник.jsp.

редактор.jsp (все, что вам нужно, это в вашем теге скрипта) эта страница откроет filebrowser.JSP в мини-окне при нажатии на кнопку Обзор сервера.

CKEDITOR.replace( 'editor', {
    filebrowserBrowseUrl: '../filebrowser.jsp', //jsp page with jquery to call servlet and get image files to view
    filebrowserUploadUrl: '../UploadImage', //servlet

});

filebrowser.jsp (это пользовательский браузер файлов, который вы создали, который будет содержать методы, упомянутые выше)

<head>
<script src="../../ckeditor/ckeditor.js"></script>
</head>
<body>
<script>


function getUrlParam( paramName ) {
    var reParam = new RegExp( '(?:[\?&]|&)' + paramName + '=([^&]+)', 'i' );
    var match = window.location.search.match( reParam );
    return ( match && match.length > 1 ) ? match[1] : null;
}

function returnFileUrl() {
    var funcNum = getUrlParam( 'CKEditorFuncNum' );
var fileUrl = 'https://patiliyo.com/wp-content/uploads/2017/07/ruyada-kedi-gormek.jpg';
    window.opener.CKEDITOR.tools.callFunction( funcNum, fileUrl );
    window.close();
}


//when this window opens it will load all the images which you send from the FileBrowser Servlet. 
getImages();
function getImages(){
    $.get("../FileBrowser", function(responseJson) {    
        //do something with responseJson (like create <img> tags and update the src attributes) 
    });
}

   //you call this function and pass 'fileUrl' when user clicks on an image that you loaded into this window from a servlet
returnFileUrl();
</script>
</body>

3) Сервлет FileBrowser

protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
    Images i = new Images();
    List<ImageObject> images = i.getImages(); //get images from your database or some cloud service or whatever (easier if they are in a url ready format)
    String json = new Gson().toJson(images);
    response.setContentType("application/json");
    response.setCharacterEncoding("UTF-8");
    response.getWriter().write(json);
}

4) UploadImage Сервлет

вернуться к конфигурации.js-файл для ckeditor и добавьте следующую строку:

//https://docs.ckeditor.com/ckeditor4/latest/guide/dev_file_upload.html
config.uploadUrl = '/UploadImage';

затем вы можете перетаскивать файлы также:

   protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {


                Images i = new Images();

   //do whatever you usually do to upload your image to your server (in my case i uploaded to google cloud storage and saved the url in a database. 

   //Now this part is important. You need to return the response in json format. And it has to look like this:

//      https://docs.ckeditor.com/ckeditor4/latest/guide/dev_file_upload.html
//      response must be in this format:
//      {
//          "uploaded": 1,
//          "fileName": "example.png",
//          "url": "https://www.cats.com/example.png"
//      }

                    String image = "https://www.cats.com/example.png";
                        ImageObject objResponse = i.getCkEditorObjectResponse(image);
                        String json = new Gson().toJson(objResponse);
                        response.setContentType("application/json");
                        response.setCharacterEncoding("UTF-8");
                        response.getWriter().write(json);
                    }
                }

и это все люди. Надеюсь, это кому-то поможет.