@ckeditor/ckeditor5-ckbox 34.2.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/LICENSE.md ADDED
@@ -0,0 +1,17 @@
1
+ Software License Agreement
2
+ ==========================
3
+
4
+ **CKEditor 5 CKBox feature** – https://github.com/ckeditor/ckeditor5-ckbox <br>
5
+ Copyright (c) 2003-2022, [CKSource Holding sp. z o.o.](http://cksource.com) All rights reserved.
6
+
7
+ Licensed under the terms of [GNU General Public License Version 2 or later](http://www.gnu.org/licenses/gpl.html).
8
+
9
+ Sources of Intellectual Property Included in CKEditor
10
+ -----------------------------------------------------
11
+
12
+ Where not otherwise indicated, all CKEditor content is authored by CKSource engineers and consists of CKSource-owned intellectual property. In some specific instances, CKEditor will incorporate work done by developers outside of CKSource with their express permission.
13
+
14
+ Trademarks
15
+ ----------
16
+
17
+ **CKEditor** is a trademark of [CKSource Holding sp. z o.o.](http://cksource.com) All other brand and product names are trademarks, registered trademarks or service marks of their respective holders.
package/README.md ADDED
@@ -0,0 +1,19 @@
1
+ CKEditor 5 CKBox integration
2
+ =========================================
3
+
4
+ [![npm version](https://badge.fury.io/js/%40ckeditor%2Fckeditor5-ckbox.svg)](https://www.npmjs.com/package/@ckeditor/ckeditor5-ckbox)
5
+ [![Coverage Status](https://coveralls.io/repos/github/ckeditor/ckeditor5/badge.svg?branch=master)](https://coveralls.io/github/ckeditor/ckeditor5?branch=master)
6
+ [![Build Status](https://travis-ci.com/ckeditor/ckeditor5.svg?branch=master)](https://app.travis-ci.com/github/ckeditor/ckeditor5)
7
+ ![Dependency Status](https://img.shields.io/librariesio/release/npm/@ckeditor/ckeditor5-ckbox)
8
+
9
+ This package implements the [CKBox feature](https://ckeditor.com/docs/ckeditor5/latest/features/ckbox.html). This feature allows you to easily insert images as well as links to files into the editor content. It is a bridge between CKEditor 5 WYSIWYG editor and CKBox file manager and uploader.
10
+
11
+ ## Documentation
12
+
13
+ See the [CKBox integration guide](https://ckeditor.com/docs/ckeditor5/latest/features/ckbox.html) and the [plugin documentation](https://ckeditor.com/docs/ckeditor5/latest/api/ckbox.html) to learn more about the integration.
14
+
15
+ Check out the [comprehensive Image upload guide](https://ckeditor.com/docs/ckeditor5/latest/features/image-upload.html) to learn about other ways to upload images into CKEditor 5.
16
+
17
+ ## License
18
+
19
+ Licensed under the terms of [GNU General Public License Version 2 or later](http://www.gnu.org/licenses/gpl.html). For full details about the license, please check the `LICENSE.md` file or [https://ckeditor.com/legal/ckeditor-oss-license](https://ckeditor.com/legal/ckeditor-oss-license).
package/build/ckbox.js ADDED
@@ -0,0 +1,5 @@
1
+ !function(e){const t=e.en=e.en||{};t.dictionary=Object.assign(t.dictionary||{},{"Cannot determine a category for the uploaded file.":"Cannot determine a category for the uploaded file.","Open file manager":"Open file manager"})}(window.CKEDITOR_TRANSLATIONS||(window.CKEDITOR_TRANSLATIONS={})),
2
+ /*!
3
+ * @license Copyright (c) 2003-2022, CKSource Holding sp. z o.o. All rights reserved.
4
+ * For licensing, see LICENSE.md.
5
+ */(()=>{var e={704:(e,t,i)=>{e.exports=i(79)("./src/core.js")},492:(e,t,i)=>{e.exports=i(79)("./src/engine.js")},273:(e,t,i)=>{e.exports=i(79)("./src/ui.js")},448:(e,t,i)=>{e.exports=i(79)("./src/upload.js")},209:(e,t,i)=>{e.exports=i(79)("./src/utils.js")},79:e=>{"use strict";e.exports=CKEditor5.dll}},t={};function i(n){var o=t[n];if(void 0!==o)return o.exports;var r=t[n]={exports:{}};return e[n](r,r.exports,i),r.exports}i.d=(e,t)=>{for(var n in t)i.o(t,n)&&!i.o(e,n)&&Object.defineProperty(e,n,{enumerable:!0,get:t[n]})},i.o=(e,t)=>Object.prototype.hasOwnProperty.call(e,t),i.r=e=>{"undefined"!=typeof Symbol&&Symbol.toStringTag&&Object.defineProperty(e,Symbol.toStringTag,{value:"Module"}),Object.defineProperty(e,"__esModule",{value:!0})};var n={};(()=>{"use strict";i.r(n),i.d(n,{CKBox:()=>I,CKBoxEditing:()=>f,CKBoxUI:()=>o});var e=i(704),t=i(273);class o extends e.Plugin{static get pluginName(){return"CKBoxUI"}afterInit(){const e=this.editor;if(!e.commands.get("ckbox"))return;const i=e.t;e.ui.componentFactory.add("ckbox",(n=>{const o=e.commands.get("ckbox"),r=new t.ButtonView(n);return r.set({label:i("Open file manager"),icon:'<svg viewBox="0 0 20 20" xmlns="http://www.w3.org/2000/svg"><path d="M11.627 16.5zm5.873-.196zm0-7.001V8h-13v8.5h4.341c.191.54.457 1.044.785 1.5H2a1.5 1.5 0 0 1-1.5-1.5v-13A1.5 1.5 0 0 1 2 2h4.5a1.5 1.5 0 0 1 1.06.44L9.122 4H16a1.5 1.5 0 0 1 1.5 1.5v1A1.5 1.5 0 0 1 19 8v2.531a6.027 6.027 0 0 0-1.5-1.228zM16 6.5v-1H8.5l-2-2H2v13h1V8a1.5 1.5 0 0 1 1.5-1.5H16z"/><path d="M14.5 19.5a5 5 0 1 1 0-10 5 5 0 0 1 0 10zM15 14v-2h-1v2h-2v1h2v2h1v-2h2v-1h-2z"/></svg>',tooltip:!0}),r.bind("isOn","isEnabled").to(o,"value","isEnabled"),r.on("execute",(()=>{e.execute("ckbox")})),r}))}}var r=i(492),s=i(209);function a({token:e,id:t,origin:i,width:n,extension:o}){const r=c(e),s=function(e){const t=[10*e/100,80],i=Math.floor(Math.max(...t)),n=[Math.min(e,4e3)];let o=n[0];for(;o-i>=i;)o-=i,n.unshift(o);return n}(n),a=function(e){if("bmp"===e||"tiff"===e||"jpg"===e)return"jpeg";return e}(o);return{imageFallbackUrl:d({environmentId:r,id:t,origin:i,width:n,extension:a}),imageSources:[{srcset:s.map((e=>`${d({environmentId:r,id:t,origin:i,width:e,extension:"webp"})} ${e}w`)).join(","),sizes:`(max-width: ${n}px) 100vw, ${n}px`,type:"image/webp"}]}}function c(e){const[,t]=e.value.split(".");return JSON.parse(atob(t)).aud}function d({environmentId:e,id:t,origin:i,width:n,extension:o}){return new URL(`${e}/assets/${t}/images/${n}.${o}`,i).toString()}class l extends e.Command{constructor(e){super(e),this._chosenAssets=new Set,this._wrapper=null,this._initListeners()}refresh(){this.value=this._getValue(),this.isEnabled=this._checkEnabled()}execute(){this.fire("ckbox:open")}_getValue(){return null!==this._wrapper}_checkEnabled(){const e=this.editor.commands.get("insertImage"),t=this.editor.commands.get("link");return!(!e.isEnabled&&!t.isEnabled)}_prepareOptions(){const e=this.editor.config.get("ckbox");return{theme:e.theme,language:e.language,tokenUrl:e.tokenUrl,serviceOrigin:e.serviceOrigin,assetsOrigin:e.assetsOrigin,dialog:{onClose:()=>this.fire("ckbox:close")},assets:{onChoose:e=>this.fire("ckbox:choose",e)}}}_initListeners(){const e=this.editor,t=e.model,i=!e.config.get("ckbox.ignoreDataId");this.on("ckbox",(()=>{this.refresh()}),{priority:"low"}),this.on("ckbox:open",(()=>{this.isEnabled&&!this.value&&(this._wrapper=(0,s.createElement)(document,"div",{class:"ck ckbox-wrapper"}),document.body.appendChild(this._wrapper),window.CKBox.mount(this._wrapper,this._prepareOptions()))})),this.on("ckbox:close",(()=>{this.value&&(this._wrapper.remove(),this._wrapper=null)})),this.on("ckbox:choose",((n,o)=>{if(!this.isEnabled)return;const r=e.commands.get("insertImage"),s=e.commands.get("link"),a=e.plugins.get("CKBoxEditing"),c=function({assets:e,origin:t,token:i,isImageAllowed:n,isLinkAllowed:o}){return e.map((e=>({id:e.data.id,type:g(e)?"image":"link",attributes:u(e,i,t)}))).filter((e=>"image"===e.type?n:o))}({assets:o,origin:e.config.get("ckbox.assetsOrigin"),token:a.getToken(),isImageAllowed:r.isEnabled,isLinkAllowed:s.isEnabled});0!==c.length&&t.change((e=>{for(const t of c){const n=t===c[c.length-1];this._insertAsset(t,n,e),i&&(setTimeout((()=>this._chosenAssets.delete(t)),1e3),this._chosenAssets.add(t))}}))})),this.listenTo(e,"destroy",(()=>{this.fire("ckbox:close"),this._chosenAssets.clear()}))}_insertAsset(e,t,i){const n=this.editor.model.document.selection;i.removeSelectionAttribute("linkHref"),"image"===e.type?this._insertImage(e):this._insertLink(e,i),t||i.setSelection(n.getLastPosition())}_insertImage(e){const t=this.editor,{imageFallbackUrl:i,imageSources:n,imageTextAlternative:o}=e.attributes;t.execute("insertImage",{source:{src:i,sources:n,alt:o}})}_insertLink(e,t){const i=this.editor,n=i.model,o=n.document.selection,{linkName:r,linkHref:a}=e.attributes;if(o.isCollapsed){const e=(0,s.toMap)(o.getAttributes()),i=t.createText(r,e),a=n.insertContent(i);t.setSelection(a)}i.execute("link",a)}}function u(e,t,i){if(g(e)){const{imageFallbackUrl:n,imageSources:o}=a({token:t,origin:i,id:e.data.id,width:e.data.metadata.width,extension:e.data.extension});return{imageFallbackUrl:n,imageSources:o,imageTextAlternative:e.data.metadata.description||""}}return{linkName:e.data.name,linkHref:m(e,t,i)}}function g(e){const t=e.data.metadata;return!!t&&(t.width&&t.height)}function m(e,t,i){const n=c(t),o=new URL(`${n}/assets/${e.data.id}/file`,i);return o.searchParams.set("download","true"),o.toString()}var h=i(448);class b extends e.Plugin{static get requires(){return["ImageUploadEditing","ImageUploadProgress",h.FileRepository,f]}static get pluginName(){return"CKBoxUploadAdapter"}async afterInit(){const e=this.editor,t=!!e.config.get("ckbox"),i=!!window.CKBox;if(!t&&!i)return;const n=e.plugins.get(h.FileRepository),o=e.plugins.get(f);n.createUploadAdapter=t=>new p(t,o.getToken(),e);const r=!e.config.get("ckbox.ignoreDataId"),s=e.plugins.get("ImageUploadEditing");r&&s.on("uploadComplete",((t,{imageElement:i,data:n})=>{e.model.change((e=>{e.setAttribute("ckboxImageId",n.ckboxImageId,i)}))}))}}class p{constructor(e,t,i){this.loader=e,this.token=t,this.editor=i,this.controller=new AbortController,this.serviceOrigin=i.config.get("ckbox.serviceOrigin"),this.assetsOrigin=i.config.get("ckbox.assetsOrigin")}async getAvailableCategories(e=0){const t=new URL("categories",this.serviceOrigin);return t.searchParams.set("limit",50..toString()),t.searchParams.set("offset",e.toString()),this._sendHttpRequest({url:t}).then((async t=>{if(t.totalCount-(e+50)>0){const i=await this.getAvailableCategories(e+50);return[...t.items,...i]}return t.items})).catch((()=>{this.controller.signal.throwIfAborted(),(0,s.logError)("ckbox-fetch-category-http-error")}))}async getCategoryIdForFile(e){const t=k(e.name),i=await this.getAvailableCategories();if(!i)return null;const n=this.editor.config.get("ckbox.defaultUploadCategories");if(n){const e=Object.keys(n).find((e=>n[e].includes(t)));if(e){const t=i.find((t=>t.id===e||t.name===e));return t?t.id:null}}const o=i.find((e=>e.extensions.includes(t)));return o?o.id:null}async upload(){const e=this.editor.t,t=e("Cannot determine a category for the uploaded file."),i=await this.loader.file,n=await this.getCategoryIdForFile(i);if(!n)return Promise.reject(t);const o=new URL("assets",this.serviceOrigin),r=new FormData;r.append("categoryId",n),r.append("file",i);const s={method:"POST",url:o,data:r,onUploadProgress:e=>{e.lengthComputable&&(this.loader.uploadTotal=e.total,this.loader.uploaded=e.loaded)}};return this._sendHttpRequest(s).then((async e=>{const t=await this._getImageWidth(),n=k(i.name),o=a({token:this.token,id:e.id,origin:this.assetsOrigin,width:t,extension:n});return{ckboxImageId:e.id,default:o.imageFallbackUrl,sources:o.imageSources}})).catch((()=>{const t=e("Cannot upload file:")+` ${i.name}.`;return Promise.reject(t)}))}abort(){this.controller.abort()}_sendHttpRequest(e){const{url:t,data:i,onUploadProgress:n}=e,o=e.method||"GET",r=this.controller.signal,s=new XMLHttpRequest;s.open(o,t.toString(),!0),s.setRequestHeader("Authorization",this.token.value),s.setRequestHeader("CKBox-Version","CKEditor 5"),s.responseType="json";const a=()=>{s.abort()};return new Promise(((e,t)=>{r.addEventListener("abort",a),s.addEventListener("loadstart",(()=>{r.addEventListener("abort",a)})),s.addEventListener("loadend",(()=>{r.removeEventListener("abort",a)})),s.addEventListener("error",(()=>{t()})),s.addEventListener("abort",(()=>{t()})),s.addEventListener("load",(async()=>{const i=s.response;return!i||i.statusCode>=400?t(i&&i.message):e(i)})),n&&s.upload.addEventListener("progress",(e=>{n(e)})),s.send(i)}))}_getImageWidth(){return new Promise((e=>{const t=new Image;t.onload=()=>{URL.revokeObjectURL(t.src),e(t.width)},t.src=this.loader.data}))}}function k(e){return e.match(/\.(?<ext>[^.]+)$/).groups.ext}class f extends e.Plugin{static get pluginName(){return"CKBoxEditing"}static get requires(){return["CloudServicesCore","LinkEditing","PictureEditing",b]}async init(){const e=this.editor,t=!!e.config.get("ckbox"),i=!!window.CKBox;if(!t&&!i)return;this._initConfig();const n=e.plugins.get("CloudServicesCore"),o=e.config.get("ckbox.tokenUrl"),r=e.config.get("cloudServices.tokenUrl");this._token=o===r?e.plugins.get("CloudServices").token:await n.createToken(o).init(),e.config.get("ckbox.ignoreDataId")||(this._initSchema(),this._initConversion(),this._initFixers()),i&&e.commands.add("ckbox",new l(e))}getToken(){return this._token}_initConfig(){const e=this.editor;e.config.define("ckbox",{serviceOrigin:"https://api.ckbox.io",assetsOrigin:"https://ckbox.cloud",defaultUploadCategories:null,ignoreDataId:!1,language:e.locale.uiLanguage,theme:"default",tokenUrl:e.config.get("cloudServices.tokenUrl")});if(!e.config.get("ckbox.tokenUrl"))throw new s.CKEditorError("ckbox-plugin-missing-token-url",this);e.plugins.has("ImageBlockEditing")||e.plugins.has("ImageInlineEditing")||(0,s.logError)("ckbox-plugin-image-feature-missing",e)}_initSchema(){const e=this.editor.model.schema;e.extend("$text",{allowAttributes:"ckboxLinkId"}),e.isRegistered("imageBlock")&&e.extend("imageBlock",{allowAttributes:["ckboxImageId","ckboxLinkId"]}),e.isRegistered("imageInline")&&e.extend("imageInline",{allowAttributes:["ckboxImageId","ckboxLinkId"]}),e.addAttributeCheck(((e,t)=>{if(!!!e.last.getAttribute("linkHref")&&"ckboxLinkId"===t)return!1}))}_initConversion(){const e=this.editor;e.conversion.for("downcast").add((e=>{e.on("attribute:ckboxLinkId:imageBlock",((e,t,i)=>{const{writer:n,mapper:o,consumable:r}=i;if(!r.consume(t.item,e.name))return;const s=[...o.toViewElement(t.item).getChildren()].find((e=>"a"===e.name));s&&(t.item.hasAttribute("ckboxLinkId")?n.setAttribute("data-ckbox-resource-id",t.item.getAttribute("ckboxLinkId"),s):n.removeAttribute("data-ckbox-resource-id",s))}),{priority:"low"}),e.on("attribute:ckboxLinkId",((e,t,i)=>{const{writer:n,mapper:o,consumable:r}=i;if(r.consume(t.item,e.name)){if(t.attributeOldValue){const e=w(n,t.attributeOldValue);n.unwrap(o.toViewRange(t.range),e)}if(t.attributeNewValue){const e=w(n,t.attributeNewValue);if(t.item.is("selection")){const t=n.document.selection;n.wrap(t.getFirstRange(),e)}else n.wrap(o.toViewRange(t.range),e)}}}),{priority:"low"})})),e.conversion.for("upcast").add((e=>{e.on("element:a",((e,t,i)=>{const{writer:n,consumable:o}=i;if(!t.viewItem.getAttribute("href"))return;if(!o.consume(t.viewItem,{attributes:["data-ckbox-resource-id"]}))return;const r=t.viewItem.getAttribute("data-ckbox-resource-id");if(r)if(t.modelRange)for(let e of t.modelRange.getItems())e.is("$textProxy")&&(e=e.textNode),v(e)&&n.setAttribute("ckboxLinkId",r,e);else{const e=t.modelCursor.nodeBefore||t.modelCursor.parent;n.setAttribute("ckboxLinkId",r,e)}}),{priority:"low"})})),e.conversion.for("downcast").attributeToAttribute({model:"ckboxImageId",view:"data-ckbox-resource-id"}),e.conversion.for("upcast").elementToAttribute({model:{key:"ckboxImageId",value:e=>e.getAttribute("data-ckbox-resource-id")},view:{attributes:{"data-ckbox-resource-id":/[\s\S]+/}}})}_initFixers(){const e=this.editor,t=e.model,i=t.document.selection;t.document.registerPostFixer(function(e){return t=>{let i=!1;const n=e.model,o=e.commands.get("ckbox");if(!o)return i;for(const e of n.document.differ.getChanges()){if("insert"!==e.type&&"attribute"!==e.type)continue;const n="insert"===e.type?new r.Range(e.position,e.position.getShiftedBy(e.length)):e.range,s="attribute"===e.type&&"linkHref"===e.attributeKey&&null===e.attributeNewValue;for(const e of n.getItems()){if(s&&e.hasAttribute("ckboxLinkId")){t.removeAttribute("ckboxLinkId",e),i=!0;continue}const n=x(e,o._chosenAssets);for(const o of n){const n="image"===o.type?"ckboxImageId":"ckboxLinkId";o.id!==e.getAttribute(n)&&(t.setAttribute(n,o.id,e),i=!0)}}}return i}}(e)),t.document.registerPostFixer(function(e){return t=>{!e.hasAttribute("linkHref")&&e.hasAttribute("ckboxLinkId")&&t.removeSelectionAttribute("ckboxLinkId")}}(i))}}function x(e,t){const i=e.is("element","imageInline")||e.is("element","imageBlock"),n=e.hasAttribute("linkHref");return[...t].filter((t=>"image"===t.type&&i?t.attributes.imageFallbackUrl===e.getAttribute("src"):"link"===t.type&&n?t.attributes.linkHref===e.getAttribute("linkHref"):void 0))}function w(e,t){const i=e.createAttributeElement("a",{"data-ckbox-resource-id":t},{priority:5});return e.setCustomProperty("link",!0,i),i}function v(e){return!!e.is("$text")||!(!e.is("element","imageInline")&&!e.is("element","imageBlock"))}class I extends e.Plugin{static get pluginName(){return"CKBox"}static get requires(){return[f,o]}}})(),(window.CKEditor5=window.CKEditor5||{}).ckbox=n})();
@@ -0,0 +1,38 @@
1
+ {
2
+ "plugins": [
3
+ {
4
+ "name": "CKBox",
5
+ "className": "CKBox",
6
+ "description": "Allows inserting images as well as links to files into the rich-text editor content.",
7
+ "docs": "features/images/image-upload/ckbox.html",
8
+ "path": "src/ckbox.js",
9
+ "requires": [
10
+ "CloudServices",
11
+ "Link",
12
+ "Image",
13
+ "ImageUpload",
14
+ "PictureEditing"
15
+ ],
16
+ "uiComponents": [
17
+ {
18
+ "name": "ckbox",
19
+ "type": "Button",
20
+ "iconPath": "theme/icons/browse-files.svg"
21
+ }
22
+ ],
23
+ "htmlOutput": [
24
+ {
25
+ "elements": [
26
+ "a",
27
+ "figure",
28
+ "img"
29
+ ],
30
+ "attributes": [
31
+ "data-ckbox-resource-id"
32
+ ],
33
+ "_comment": "If `config.ckbox.ignoreDataId` is set to false (off), the asset ID as the `data-ckbox-resource-id` attribute is added on the inserted elements (by default)."
34
+ }
35
+ ]
36
+ }
37
+ ]
38
+ }
@@ -0,0 +1,4 @@
1
+ {
2
+ "Open file manager": "Toolbar button tooltip for opening a file browser that allows inserting an image or a file to the editor.",
3
+ "Cannot determine a category for the uploaded file.": "A message is displayed when CKEditor 5 cannot associate an image with any of the categories defined in CKBox while uploading an asset."
4
+ }
@@ -0,0 +1,25 @@
1
+ # Copyright (c) 2003-2022, CKSource Holding sp. z o.o. All rights reserved.
2
+ #
3
+ # !!! IMPORTANT !!!
4
+ #
5
+ # Before you edit this file, please keep in mind that contributing to the project
6
+ # translations is possible ONLY via the Transifex online service.
7
+ #
8
+ # To submit your translations, visit https://www.transifex.com/ckeditor/ckeditor5.
9
+ #
10
+ # To learn more, check out the official contributor's guide:
11
+ # https://ckeditor.com/docs/ckeditor5/latest/framework/guides/contributing/contributing.html
12
+ #
13
+ msgid ""
14
+ msgstr ""
15
+ "Language: \n"
16
+ "Language-Team: \n"
17
+ "Plural-Forms: \n"
18
+
19
+ msgctxt "Toolbar button tooltip for opening a file browser that allows inserting an image or a file to the editor."
20
+ msgid "Open file manager"
21
+ msgstr "Open file manager"
22
+
23
+ msgctxt "A message is displayed when CKEditor 5 cannot associate an image with any of the categories defined in CKBox while uploading an asset."
24
+ msgid "Cannot determine a category for the uploaded file."
25
+ msgstr "Cannot determine a category for the uploaded file."
package/package.json ADDED
@@ -0,0 +1,58 @@
1
+ {
2
+ "name": "@ckeditor/ckeditor5-ckbox",
3
+ "version": "34.2.0",
4
+ "description": "CKBox integration for CKEditor 5.",
5
+ "keywords": [
6
+ "ckeditor",
7
+ "ckeditor5",
8
+ "ckeditor 5",
9
+ "ckeditor5-feature",
10
+ "ckeditor5-plugin",
11
+ "ckeditor5-dll"
12
+ ],
13
+ "main": "src/index.js",
14
+ "dependencies": {
15
+ "ckeditor5": "^34.2.0"
16
+ },
17
+ "devDependencies": {
18
+ "@ckeditor/ckeditor5-basic-styles": "^34.2.0",
19
+ "@ckeditor/ckeditor5-core": "^34.2.0",
20
+ "@ckeditor/ckeditor5-clipboard": "^34.2.0",
21
+ "@ckeditor/ckeditor5-cloud-services": "^34.2.0",
22
+ "@ckeditor/ckeditor5-dev-utils": "^30.1.0",
23
+ "@ckeditor/ckeditor5-editor-classic": "^34.2.0",
24
+ "@ckeditor/ckeditor5-engine": "^34.2.0",
25
+ "@ckeditor/ckeditor5-image": "^34.2.0",
26
+ "@ckeditor/ckeditor5-link": "^34.2.0",
27
+ "@ckeditor/ckeditor5-paragraph": "^34.2.0",
28
+ "@ckeditor/ckeditor5-theme-lark": "^34.2.0",
29
+ "@ckeditor/ckeditor5-ui": "^34.2.0",
30
+ "@ckeditor/ckeditor5-upload": "^34.2.0",
31
+ "@ckeditor/ckeditor5-utils": "^34.2.0",
32
+ "webpack": "^5.58.1",
33
+ "webpack-cli": "^4.9.0"
34
+ },
35
+ "engines": {
36
+ "node": ">=14.0.0",
37
+ "npm": ">=5.7.1"
38
+ },
39
+ "author": "CKSource (http://cksource.com/)",
40
+ "license": "GPL-2.0-or-later",
41
+ "homepage": "https://ckeditor.com/ckeditor-5",
42
+ "bugs": "https://github.com/ckeditor/ckeditor5/issues",
43
+ "repository": {
44
+ "type": "git",
45
+ "url": "https://github.com/ckeditor/ckeditor5.git",
46
+ "directory": "packages/ckeditor5-ckbox"
47
+ },
48
+ "files": [
49
+ "lang",
50
+ "src",
51
+ "theme",
52
+ "build",
53
+ "ckeditor5-metadata.json"
54
+ ],
55
+ "scripts": {
56
+ "dll:build": "webpack"
57
+ }
58
+ }
package/src/ckbox.js ADDED
@@ -0,0 +1,243 @@
1
+ /**
2
+ * @license Copyright (c) 2003-2022, CKSource Holding sp. z o.o. All rights reserved.
3
+ * For licensing, see LICENSE.md or https://ckeditor.com/legal/ckeditor-oss-license
4
+ */
5
+
6
+ /**
7
+ * @module ckbox/ckbox
8
+ */
9
+
10
+ import { Plugin } from 'ckeditor5/src/core';
11
+
12
+ import CKBoxUI from './ckboxui';
13
+ import CKBoxEditing from './ckboxediting';
14
+
15
+ /**
16
+ * The CKBox feature, a bridge between the CKEditor 5 WYSIWYG editor and the CKBox file manager and uploader.
17
+ *
18
+ * This is a "glue" plugin which enables:
19
+ *
20
+ * * {@link module:ckbox/ckboxediting~CKBoxEditing},
21
+ * * {@link module:ckbox/ckboxui~CKBoxUI},
22
+ *
23
+ * See the {@glink features/images/image-upload/ckbox CKBox integration} guide to learn how to configure and use this feature.
24
+ *
25
+ * Check out the {@glink features/images/image-upload/image-upload Image upload} guide to learn about other ways to upload
26
+ * images into CKEditor 5.
27
+ *
28
+ * @extends module:core/plugin~Plugin
29
+ */
30
+ export default class CKBox extends Plugin {
31
+ /**
32
+ * @inheritDoc
33
+ */
34
+ static get pluginName() {
35
+ return 'CKBox';
36
+ }
37
+
38
+ /**
39
+ * @inheritDoc
40
+ */
41
+ static get requires() {
42
+ return [ CKBoxEditing, CKBoxUI ];
43
+ }
44
+ }
45
+
46
+ /**
47
+ * The configuration of the {@link module:ckbox/ckbox~CKBox CKBox feature}.
48
+ *
49
+ * Read more in {@link module:ckbox/ckbox~CKBoxConfig}.
50
+ *
51
+ * @member {module:ckbox/ckbox~CKBoxConfig} module:core/editor/editorconfig~EditorConfig#ckbox
52
+ */
53
+
54
+ /**
55
+ * The configuration of the {@link module:ckbox/ckbox~CKBox CKBox feature}.
56
+ *
57
+ * The minimal configuration for the CKBox feature requires providing the
58
+ * {@link module:ckbox/ckbox~CKBoxConfig#tokenUrl `config.ckbox.tokenUrl`}:
59
+ *
60
+ * ClassicEditor
61
+ * .create( editorElement, {
62
+ * ckbox: {
63
+ * tokenUrl: 'https://example.com/cs-token-endpoint'
64
+ * }
65
+ * } )
66
+ * .then( ... )
67
+ * .catch( ... );
68
+ *
69
+ * Hovewer, you can also adjust the feature to fit your needs:
70
+ *
71
+ * ClassicEditor
72
+ * .create( editorElement, {
73
+ * ckbox: {
74
+ * defaultUploadCategories: {
75
+ * Bitmaps: [ 'bmp' ],
76
+ * Pictures: [ 'jpg', 'jpeg' ],
77
+ * Scans: [ 'png', 'tiff' ]
78
+ * },
79
+ * ignoreDataId: true,
80
+ * serviceOrigin: 'https://example.com/',
81
+ * assetsOrigin: 'https://example.cloud/',
82
+ * tokenUrl: 'https://example.com/cs-token-endpoint'
83
+ * }
84
+ * } )
85
+ * .then( ... )
86
+ * .catch( ... );
87
+ *
88
+ * See {@link module:core/editor/editorconfig~EditorConfig all editor options}.
89
+ *
90
+ * @interface CKBoxConfig
91
+ */
92
+
93
+ /**
94
+ * The authentication token URL for CKBox feature.
95
+ *
96
+ * Defaults to {@link module:cloud-services/cloudservices~CloudServicesConfig#tokenUrl `config.cloudServices.tokenUrl`}
97
+ *
98
+ * @member {String} module:ckbox/ckbox~CKBoxConfig#tokenUrl
99
+ */
100
+
101
+ /**
102
+ * Defines the categories to which the uploaded images will be assigned. If configured, it overrides the category mappings defined on the
103
+ * cloud service. The value of this option should be an object, where the keys define categories and their values are the types of images
104
+ * that will be uploaded to these categories. The categories might be referenced by their name or ID.
105
+ *
106
+ * Example:
107
+ *
108
+ * const ckboxConfig = {
109
+ * defaultUploadCategories: {
110
+ * Bitmaps: [ 'bmp' ],
111
+ * Pictures: [ 'jpg', 'jpeg' ],
112
+ * Scans: [ 'png', 'tiff' ],
113
+ * // The category below is referenced by its ID.
114
+ * 'fdf2a647-b67f-4a6c-b692-5ba1dc1ed87b': [ 'gif' ]
115
+ * }
116
+ * };
117
+ *
118
+ * @default null
119
+ * @member {Object} [module:ckbox/ckbox~CKBoxConfig#defaultUploadCategories]
120
+ */
121
+
122
+ /**
123
+ * Inserts the unique asset ID as the `data-ckbox-resource-id` attribute. To disable this behavior, set it to `true`.
124
+ *
125
+ * @default false
126
+ * @member {Boolean} [module:ckbox/ckbox~CKBoxConfig#ignoreDataId]
127
+ */
128
+
129
+ /**
130
+ * Configures the base URL of the API service. Required only in on-premises installations.
131
+ *
132
+ * @default 'https://api.ckbox.io'
133
+ * @member {String} [module:ckbox/ckbox~CKBoxConfig#serviceOrigin]
134
+ */
135
+
136
+ /**
137
+ * Configures the base URL for assets inserted into the editor. Required only in on-premises installations.
138
+ *
139
+ * @default 'https://ckbox.cloud'
140
+ * @member {String} [module:ckbox/ckbox~CKBoxConfig#assetsOrigin]
141
+ */
142
+
143
+ /**
144
+ * Configures the language for the CKBox dialog.
145
+ *
146
+ * Defaults to {@link module:utils/locale~Locale#uiLanguage `Locale#uiLanguage`}
147
+ *
148
+ * @member {String} [module:ckbox/ckbox~CKBoxConfig#language]
149
+ */
150
+
151
+ /**
152
+ * Asset definition.
153
+ *
154
+ * The definition contains the unique `id`, asset `type` and an `attributes` definition.
155
+ *
156
+ * @typedef {Object} module:ckbox/ckbox~CKBoxAssetDefinition
157
+ *
158
+ * @property {String} id An unique asset id.
159
+ * @property {'image'|'link'} type Asset type.
160
+ * @property {module:ckbox/ckbox~CKBoxAssetImageAttributesDefinition|
161
+ * module:ckbox/ckbox~CKBoxAssetLinkAttributesDefinition} attributes Asset attributes.
162
+ */
163
+
164
+ /**
165
+ * Asset attributes definition for an image.
166
+ *
167
+ * The definition contains the `imageFallbackUrl`, an `imageSources` array with one image source definition object and the
168
+ * `imageTextAlternative`.
169
+ *
170
+ * {
171
+ * imageFallbackUrl: 'https://example.com/assets/asset-id/images/1000.png',
172
+ * imageSources: [
173
+ * {
174
+ * sizes: '1000px',
175
+ * srcset:
176
+ * 'https://example.com/assets/asset-id/images/100.webp 100w,' +
177
+ * 'https://example.com/assets/asset-id/images/200.webp 200w,' +
178
+ * 'https://example.com/assets/asset-id/images/300.webp 300w,' +
179
+ * 'https://example.com/assets/asset-id/images/400.webp 400w,' +
180
+ * 'https://example.com/assets/asset-id/images/500.webp 500w,' +
181
+ * 'https://example.com/assets/asset-id/images/600.webp 600w,' +
182
+ * 'https://example.com/assets/asset-id/images/700.webp 700w,' +
183
+ * 'https://example.com/assets/asset-id/images/800.webp 800w,' +
184
+ * 'https://example.com/assets/asset-id/images/900.webp 900w,' +
185
+ * 'https://example.com/assets/asset-id/images/1000.webp 1000w',
186
+ * type: 'image/webp'
187
+ * }
188
+ * ],
189
+ * imageTextAlternative: 'An alternative text for the image'
190
+ * }
191
+ *
192
+ * @typedef {Object} module:ckbox/ckbox~CKBoxAssetImageAttributesDefinition
193
+ *
194
+ * @property {String} imageFallbackUrl A fallback URL for browsers that do not support the "webp" format.
195
+ * @property {Array.<Object>} imageSources An array containing one image source definition object.
196
+ * @property {String} imageTextAlternative An alternative text for an image.
197
+ */
198
+
199
+ /**
200
+ * Asset attributes definition for a link.
201
+ *
202
+ * The definition contains the `linkName` and `linkHref` strings.
203
+ *
204
+ * {
205
+ * linkName: 'File name',
206
+ * linkHref: 'https://example.com/assets/asset-id/file.pdf'
207
+ * }
208
+ *
209
+ * @typedef {Object} module:ckbox/ckbox~CKBoxAssetLinkAttributesDefinition
210
+ *
211
+ * @property {String} linkName A link name.
212
+ * @property {String} linkHref An URL for the asset.
213
+ */
214
+
215
+ /**
216
+ * Raw asset definition that is received from the CKBox feature.
217
+ *
218
+ * @typedef {Object} module:ckbox/ckbox~CKBoxRawAssetDefinition
219
+ *
220
+ * @property {module:ckbox/ckbox~CKBoxRawAssetDataDefinition} data A raw asset data definition.
221
+ * @property {String} origin An asset origin URL.
222
+ */
223
+
224
+ /**
225
+ * Part of raw asset data that is received from the CKBox feature.
226
+ *
227
+ * @typedef {Object} module:ckbox/ckbox~CKBoxRawAssetDataDefinition
228
+ *
229
+ * @property {String} id An unique asset id.
230
+ * @property {String} extension An asset extension.
231
+ * @property {String} name An asset name.
232
+ * @property {module:ckbox/ckbox~CKBoxRawAssetMetadataDefinition} metadata A raw asset metadata definition.
233
+ */
234
+
235
+ /**
236
+ * Part of raw asset data that is received from the CKBox feature. Properties are set only if the chosen asset is an image.
237
+ *
238
+ * @typedef {Object} module:ckbox/ckbox~CKBoxRawAssetMetadataDefinition
239
+ *
240
+ * @property {String} [description] Image description.
241
+ * @property {Number} [width] Image width.
242
+ * @property {Number} [height] Image height.
243
+ */