mirror of
https://github.com/BookStackApp/BookStack.git
synced 2024-08-26 20:22:18 +00:00
Made WYSIWYG editor translatable
- Created new translation file for editor view. - Added simple logic to format for tinymce. - Aligned some of the custom labels we were using.
This commit is contained in:
parent
921131f999
commit
ef211a76ae
@ -10,6 +10,7 @@ class WysiwygEditor {
|
|||||||
this.isDarkMode = document.documentElement.classList.contains('dark-mode');
|
this.isDarkMode = document.documentElement.classList.contains('dark-mode');
|
||||||
|
|
||||||
this.tinyMceConfig = buildEditorConfig({
|
this.tinyMceConfig = buildEditorConfig({
|
||||||
|
language: this.$opts.language,
|
||||||
containerElement: this.elem,
|
containerElement: this.elem,
|
||||||
darkMode: this.isDarkMode,
|
darkMode: this.isDarkMode,
|
||||||
textDirection: this.textDirection,
|
textDirection: this.textDirection,
|
||||||
@ -18,7 +19,8 @@ class WysiwygEditor {
|
|||||||
translations: {
|
translations: {
|
||||||
imageUploadErrorText: this.$opts.imageUploadErrorText,
|
imageUploadErrorText: this.$opts.imageUploadErrorText,
|
||||||
serverUploadLimitText: this.$opts.serverUploadLimitText,
|
serverUploadLimitText: this.$opts.serverUploadLimitText,
|
||||||
}
|
},
|
||||||
|
translationMap: window.editor_translations,
|
||||||
});
|
});
|
||||||
|
|
||||||
window.$events.emitPublic(this.elem, 'editor-tinymce::pre-init', {config: this.tinyMceConfig});
|
window.$events.emitPublic(this.elem, 'editor-tinymce::pre-init', {config: this.tinyMceConfig});
|
||||||
|
@ -9,16 +9,16 @@ import {getPlugin as getCustomhrPlugin} from "./plugins-customhr";
|
|||||||
import {getPlugin as getImagemanagerPlugin} from "./plugins-imagemanager";
|
import {getPlugin as getImagemanagerPlugin} from "./plugins-imagemanager";
|
||||||
|
|
||||||
const style_formats = [
|
const style_formats = [
|
||||||
{title: "Header Large", format: "h2", preview: 'color: blue;'},
|
{title: "Large Header", format: "h2", preview: 'color: blue;'},
|
||||||
{title: "Header Medium", format: "h3"},
|
{title: "Medium Header", format: "h3"},
|
||||||
{title: "Header Small", format: "h4"},
|
{title: "Small Header", format: "h4"},
|
||||||
{title: "Header Tiny", format: "h5"},
|
{title: "Tiny Header", format: "h5"},
|
||||||
{title: "Paragraph", format: "p", exact: true, classes: ''},
|
{title: "Paragraph", format: "p", exact: true, classes: ''},
|
||||||
{title: "Blockquote", format: "blockquote"},
|
{title: "Blockquote", format: "blockquote"},
|
||||||
{title: "Inline Code", inline: "code"},
|
{title: "Inline Code", inline: "code"},
|
||||||
{
|
{
|
||||||
title: "Callouts", items: [
|
title: "Callouts", items: [
|
||||||
{title: "Info", format: 'calloutinfo'},
|
{title: "Information", format: 'calloutinfo'},
|
||||||
{title: "Success", format: 'calloutsuccess'},
|
{title: "Success", format: 'calloutsuccess'},
|
||||||
{title: "Warning", format: 'calloutwarning'},
|
{title: "Warning", format: 'calloutwarning'},
|
||||||
{title: "Danger", format: 'calloutdanger'}
|
{title: "Danger", format: 'calloutdanger'}
|
||||||
@ -174,6 +174,10 @@ function getSetupCallback(options) {
|
|||||||
*/
|
*/
|
||||||
export function build(options) {
|
export function build(options) {
|
||||||
|
|
||||||
|
// Set language
|
||||||
|
window.tinymce.addI18n(options.language, options.translationMap);
|
||||||
|
|
||||||
|
// Return config object
|
||||||
return {
|
return {
|
||||||
width: '100%',
|
width: '100%',
|
||||||
height: '100%',
|
height: '100%',
|
||||||
@ -186,6 +190,7 @@ export function build(options) {
|
|||||||
body_class: 'page-content',
|
body_class: 'page-content',
|
||||||
browser_spellcheck: true,
|
browser_spellcheck: true,
|
||||||
relative_urls: false,
|
relative_urls: false,
|
||||||
|
language: options.language,
|
||||||
directionality: options.textDirection,
|
directionality: options.textDirection,
|
||||||
remove_script_host: false,
|
remove_script_host: false,
|
||||||
document_base_url: window.baseUrl('/'),
|
document_base_url: window.baseUrl('/'),
|
||||||
@ -224,9 +229,11 @@ export function build(options) {
|
|||||||
/**
|
/**
|
||||||
* @typedef {Object} WysiwygConfigOptions
|
* @typedef {Object} WysiwygConfigOptions
|
||||||
* @property {Element} containerElement
|
* @property {Element} containerElement
|
||||||
|
* @property {string} language
|
||||||
* @property {boolean} darkMode
|
* @property {boolean} darkMode
|
||||||
* @property {string} textDirection
|
* @property {string} textDirection
|
||||||
* @property {string} drawioUrl
|
* @property {string} drawioUrl
|
||||||
* @property {int} pageId
|
* @property {int} pageId
|
||||||
* @property {Object} translations
|
* @property {Object} translations
|
||||||
|
* @property {Object} translationMap
|
||||||
*/
|
*/
|
@ -69,7 +69,7 @@ function register(editor, url) {
|
|||||||
editor.ui.registry.addIcon('codeblock', '<svg width="24" height="24"><path d="M4 3h16c.6 0 1 .4 1 1v16c0 .6-.4 1-1 1H4a1 1 0 0 1-1-1V4c0-.6.4-1 1-1Zm1 2v14h14V5Z"/><path d="M11.103 15.423c.277.277.277.738 0 .922a.692.692 0 0 1-1.106 0l-4.057-3.78a.738.738 0 0 1 0-1.107l4.057-3.872c.276-.277.83-.277 1.106 0a.724.724 0 0 1 0 1.014L7.6 12.012ZM12.897 8.577c-.245-.312-.2-.675.08-.955.28-.281.727-.27 1.027.033l4.057 3.78a.738.738 0 0 1 0 1.107l-4.057 3.872c-.277.277-.83.277-1.107 0a.724.724 0 0 1 0-1.014l3.504-3.412z"/></svg>')
|
editor.ui.registry.addIcon('codeblock', '<svg width="24" height="24"><path d="M4 3h16c.6 0 1 .4 1 1v16c0 .6-.4 1-1 1H4a1 1 0 0 1-1-1V4c0-.6.4-1 1-1Zm1 2v14h14V5Z"/><path d="M11.103 15.423c.277.277.277.738 0 .922a.692.692 0 0 1-1.106 0l-4.057-3.78a.738.738 0 0 1 0-1.107l4.057-3.872c.276-.277.83-.277 1.106 0a.724.724 0 0 1 0 1.014L7.6 12.012ZM12.897 8.577c-.245-.312-.2-.675.08-.955.28-.281.727-.27 1.027.033l4.057 3.78a.738.738 0 0 1 0 1.107l-4.057 3.872c-.277.277-.83.277-1.107 0a.724.724 0 0 1 0-1.014l3.504-3.412z"/></svg>')
|
||||||
|
|
||||||
editor.ui.registry.addButton('codeeditor', {
|
editor.ui.registry.addButton('codeeditor', {
|
||||||
title: 'Insert code block',
|
tooltip: 'Insert code block',
|
||||||
icon: 'codeblock',
|
icon: 'codeblock',
|
||||||
onAction() {
|
onAction() {
|
||||||
editor.execCommand('codeeditor');
|
editor.execCommand('codeeditor');
|
||||||
|
@ -102,7 +102,7 @@ export function getPlugin(providedOptions) {
|
|||||||
editor.ui.registry.addIcon('diagram', `<svg width="24" height="24" fill="${options.darkMode ? '#BBB' : '#000000'}" xmlns="http://www.w3.org/2000/svg"><path d="M20.716 7.639V2.845h-4.794v1.598h-7.99V2.845H3.138v4.794h1.598v7.99H3.138v4.794h4.794v-1.598h7.99v1.598h4.794v-4.794h-1.598v-7.99zM4.736 4.443h1.598V6.04H4.736zm1.598 14.382H4.736v-1.598h1.598zm9.588-1.598h-7.99v-1.598H6.334v-7.99h1.598V6.04h7.99v1.598h1.598v7.99h-1.598zm3.196 1.598H17.52v-1.598h1.598zM17.52 6.04V4.443h1.598V6.04zm-4.21 7.19h-2.79l-.582 1.599H8.643l2.717-7.191h1.119l2.724 7.19h-1.302zm-2.43-1.006h2.086l-1.039-3.06z"/></svg>`)
|
editor.ui.registry.addIcon('diagram', `<svg width="24" height="24" fill="${options.darkMode ? '#BBB' : '#000000'}" xmlns="http://www.w3.org/2000/svg"><path d="M20.716 7.639V2.845h-4.794v1.598h-7.99V2.845H3.138v4.794h1.598v7.99H3.138v4.794h4.794v-1.598h7.99v1.598h4.794v-4.794h-1.598v-7.99zM4.736 4.443h1.598V6.04H4.736zm1.598 14.382H4.736v-1.598h1.598zm9.588-1.598h-7.99v-1.598H6.334v-7.99h1.598V6.04h7.99v1.598h1.598v7.99h-1.598zm3.196 1.598H17.52v-1.598h1.598zM17.52 6.04V4.443h1.598V6.04zm-4.21 7.19h-2.79l-.582 1.599H8.643l2.717-7.191h1.119l2.724 7.19h-1.302zm-2.43-1.006h2.086l-1.039-3.06z"/></svg>`)
|
||||||
|
|
||||||
editor.ui.registry.addSplitButton('drawio', {
|
editor.ui.registry.addSplitButton('drawio', {
|
||||||
tooltip: 'Drawing',
|
tooltip: 'Insert/edit drawing',
|
||||||
icon: 'diagram',
|
icon: 'diagram',
|
||||||
onAction() {
|
onAction() {
|
||||||
editor.execCommand('drawio');
|
editor.execCommand('drawio');
|
||||||
@ -111,7 +111,7 @@ export function getPlugin(providedOptions) {
|
|||||||
callback([
|
callback([
|
||||||
{
|
{
|
||||||
type: 'choiceitem',
|
type: 'choiceitem',
|
||||||
text: 'Drawing Manager',
|
text: 'Drawing manager',
|
||||||
value: 'drawing-manager',
|
value: 'drawing-manager',
|
||||||
}
|
}
|
||||||
]);
|
]);
|
||||||
|
@ -12,16 +12,7 @@ function register(editor, url) {
|
|||||||
|
|
||||||
editor.ui.registry.addButton('hr', {
|
editor.ui.registry.addButton('hr', {
|
||||||
icon: 'horizontal-rule',
|
icon: 'horizontal-rule',
|
||||||
tooltip: 'Horizontal line',
|
tooltip: 'Insert horizontal line',
|
||||||
onAction() {
|
|
||||||
editor.execCommand('InsertHorizontalRule');
|
|
||||||
}
|
|
||||||
});
|
|
||||||
|
|
||||||
editor.ui.registry.addMenuItem('hr', {
|
|
||||||
icon: 'horizontal-rule',
|
|
||||||
text: 'Horizontal line',
|
|
||||||
context: 'insert',
|
|
||||||
onAction() {
|
onAction() {
|
||||||
editor.execCommand('InsertHorizontalRule');
|
editor.execCommand('InsertHorizontalRule');
|
||||||
}
|
}
|
||||||
|
@ -6,9 +6,9 @@ function register(editor, url) {
|
|||||||
|
|
||||||
// Custom Image picker button
|
// Custom Image picker button
|
||||||
editor.ui.registry.addButton('imagemanager-insert', {
|
editor.ui.registry.addButton('imagemanager-insert', {
|
||||||
title: 'Insert an image',
|
title: 'Insert image',
|
||||||
icon: 'image',
|
icon: 'image',
|
||||||
tooltip: 'Insert an image',
|
tooltip: 'Insert image',
|
||||||
onAction() {
|
onAction() {
|
||||||
window.ImageManager.show(function (image) {
|
window.ImageManager.show(function (image) {
|
||||||
const imageUrl = image.thumbs.display || image.url;
|
const imageUrl = image.thumbs.display || image.url;
|
||||||
|
133
resources/lang/en/editor.php
Normal file
133
resources/lang/en/editor.php
Normal file
@ -0,0 +1,133 @@
|
|||||||
|
<?php
|
||||||
|
/**
|
||||||
|
* Page Editor Lines
|
||||||
|
* Contains text strings used within the user interface of the
|
||||||
|
* WYSIWYG page editor. Some Markdown editor strings may still
|
||||||
|
* exist in the 'entities' file instead since this was added later.
|
||||||
|
*/
|
||||||
|
return [
|
||||||
|
// General editor terms
|
||||||
|
'general' => 'General',
|
||||||
|
'advanced' => 'Advanced',
|
||||||
|
'none' => 'None',
|
||||||
|
'cancel' => 'Cancel',
|
||||||
|
'save' => 'Save',
|
||||||
|
'close' => 'Close',
|
||||||
|
'undo' => 'Undo',
|
||||||
|
'redo' => 'Redo',
|
||||||
|
'left' => 'Left',
|
||||||
|
'center' => 'Center',
|
||||||
|
'right' => 'Right',
|
||||||
|
'top' => 'Top',
|
||||||
|
'middle' => 'Middle',
|
||||||
|
'bottom' => 'Bottom',
|
||||||
|
'width' => 'Width',
|
||||||
|
'height' => 'Height',
|
||||||
|
|
||||||
|
// Toolbar
|
||||||
|
'formats' => 'Formats',
|
||||||
|
'header_large' => 'Large Header',
|
||||||
|
'header_medium' => 'Medium Header',
|
||||||
|
'header_small' => 'Small Header',
|
||||||
|
'header_tiny' => 'Tiny Header',
|
||||||
|
'paragraph' => 'Paragraph',
|
||||||
|
'blockquote' => 'Blockquote',
|
||||||
|
'inline_code' => 'Inline Code',
|
||||||
|
'callouts' => 'Callouts',
|
||||||
|
'callout_information' => 'Information',
|
||||||
|
'callout_success' => 'Success',
|
||||||
|
'callout_warning' => 'Warning',
|
||||||
|
'callout_danger' => 'Danger',
|
||||||
|
'bold' => 'Bold',
|
||||||
|
'italic' => 'Italic',
|
||||||
|
'underline' => 'Underline',
|
||||||
|
'strikethrough' => 'Strikethrough',
|
||||||
|
'superscript' => 'Superscript',
|
||||||
|
'subscript' => 'Subscript',
|
||||||
|
'text_color' => 'Text color',
|
||||||
|
'custom_color' => 'Custom color',
|
||||||
|
'remove_color' => 'Remove color',
|
||||||
|
'background_color' => 'Background color',
|
||||||
|
'align_left' => 'Align left',
|
||||||
|
'align_center' => 'Align center',
|
||||||
|
'align_right' => 'Align right',
|
||||||
|
'align_justify' => 'Align justify',
|
||||||
|
'list_bullet' => 'Bullet list',
|
||||||
|
'list_numbered' => 'Numbered list',
|
||||||
|
'indent_increase' => 'Increase indent',
|
||||||
|
'indent_decrease' => 'Decrease indent',
|
||||||
|
'table' => 'Table',
|
||||||
|
'insert_image' => 'Insert image',
|
||||||
|
'insert_image_title' => 'Insert/Edit Image',
|
||||||
|
'insert_link' => 'Insert/edit link',
|
||||||
|
'insert_link_title' => 'Insert/Edit Link',
|
||||||
|
'insert_horizontal_line' => 'Insert horizontal line',
|
||||||
|
'insert_code_block' => 'Insert code block',
|
||||||
|
'insert_drawing' => 'Insert/edit drawing',
|
||||||
|
'drawing_manager' => 'Drawing manager',
|
||||||
|
'insert_media' => 'Insert/edit media',
|
||||||
|
'insert_media_title' => 'Insert/Edit Media',
|
||||||
|
'clear_formatting' => 'Clear formatting',
|
||||||
|
'source_code' => 'Source code',
|
||||||
|
'source_code_title' => 'Source Code',
|
||||||
|
'fullscreen' => 'Fullscreen',
|
||||||
|
'image_options' => 'Image options',
|
||||||
|
|
||||||
|
// Tables
|
||||||
|
'table_properties' => 'Table properties',
|
||||||
|
'table_properties_title' => 'Table Properties',
|
||||||
|
'delete_table' => 'Delete table',
|
||||||
|
'insert_row_before' => 'Insert row before',
|
||||||
|
'insert_row_after' => 'Insert row after',
|
||||||
|
'delete_row' => 'Delete row',
|
||||||
|
'insert_column_before' => 'Insert column before',
|
||||||
|
'insert_column_after' => 'Insert column after',
|
||||||
|
'delete_column' => 'Delete column',
|
||||||
|
'table_cell' => 'Cell',
|
||||||
|
'table_row' => 'Row',
|
||||||
|
'table_column' => 'Column',
|
||||||
|
'cell_properties' => 'Cell properties',
|
||||||
|
'cell_properties_title' => 'Cell Properties',
|
||||||
|
'cell_type' => 'Cell type',
|
||||||
|
'cell_type_cell' => 'Cell',
|
||||||
|
'cell_type_header' => 'Header cell',
|
||||||
|
'table_row_group' => 'Row Group',
|
||||||
|
'table_column_group' => 'Column Group',
|
||||||
|
'horizontal_align' => 'Horizontal align',
|
||||||
|
'vertical_align' => 'Vertical align',
|
||||||
|
'border_width' => 'Border width',
|
||||||
|
'border_style' => 'Border style',
|
||||||
|
'border_color' => 'Border color',
|
||||||
|
'row_properties' => 'Row properties',
|
||||||
|
'row_properties_title' => 'Row Properties',
|
||||||
|
'cut_row' => 'Cut row',
|
||||||
|
'copy_row' => 'Copy row',
|
||||||
|
'paste_row_before' => 'Paste row before',
|
||||||
|
'paste_row_after' => 'Paste row after',
|
||||||
|
'row_type' => 'Row type',
|
||||||
|
'row_type_header' => 'Header',
|
||||||
|
'row_type_body' => 'Body',
|
||||||
|
'row_type_footer' => 'Footer',
|
||||||
|
'alignment' => 'Alignment',
|
||||||
|
'cut_column' => 'Cut column',
|
||||||
|
'copy_column' => 'Copy column',
|
||||||
|
'paste_column_before' => 'Paste column before',
|
||||||
|
'paste_column_after' => 'Paste column after',
|
||||||
|
'cell_padding' => 'Cell padding',
|
||||||
|
'cell_spacing' => 'Cell spacing',
|
||||||
|
'caption' => 'Caption',
|
||||||
|
'show_caption' => 'Show caption',
|
||||||
|
'constrain' => 'Constrain proportions',
|
||||||
|
|
||||||
|
// Images, links & embed
|
||||||
|
'source' => 'Source',
|
||||||
|
'alt_desc' => 'Alternative description',
|
||||||
|
'embed' => 'Embed',
|
||||||
|
'paste_embed' => 'Paste your embed code below:',
|
||||||
|
'url' => 'URL',
|
||||||
|
'text_to_display' => 'Text to display',
|
||||||
|
'title' => 'Title',
|
||||||
|
'open_link' => 'Open link in...',
|
||||||
|
'open_link_current' => 'Current window',
|
||||||
|
'open_link_new' => 'New window',
|
||||||
|
];
|
11
resources/views/pages/parts/editor-translations.blade.php
Normal file
11
resources/views/pages/parts/editor-translations.blade.php
Normal file
@ -0,0 +1,11 @@
|
|||||||
|
@php
|
||||||
|
$en = trans('editor', [], 'en');
|
||||||
|
$lang = trans('editor');
|
||||||
|
$mergedText = [];
|
||||||
|
foreach ($en as $key => $value) {
|
||||||
|
$mergedText[$value] = $lang[$key] ?? $value;
|
||||||
|
}
|
||||||
|
@endphp
|
||||||
|
<script nonce="{{ $cspNonce }}">
|
||||||
|
window.editor_translations = @json($mergedText);
|
||||||
|
</script>
|
@ -1,4 +1,5 @@
|
|||||||
<div component="wysiwyg-editor"
|
<div component="wysiwyg-editor"
|
||||||
|
option:wysiwyg-editor:language="{{ config('app.lang') }}"
|
||||||
option:wysiwyg-editor:page-id="{{ $model->id ?? 0 }}"
|
option:wysiwyg-editor:page-id="{{ $model->id ?? 0 }}"
|
||||||
option:wysiwyg-editor:text-direction="{{ config('app.rtl') ? 'rtl' : 'ltr' }}"
|
option:wysiwyg-editor:text-direction="{{ config('app.rtl') ? 'rtl' : 'ltr' }}"
|
||||||
option:wysiwyg-editor:image-upload-error-text="{{ trans('errors.image_upload_error') }}"
|
option:wysiwyg-editor:image-upload-error-text="{{ trans('errors.image_upload_error') }}"
|
||||||
@ -12,3 +13,5 @@
|
|||||||
@if($errors->has('html'))
|
@if($errors->has('html'))
|
||||||
<div class="text-neg text-small">{{ $errors->first('html') }}</div>
|
<div class="text-neg text-small">{{ $errors->first('html') }}</div>
|
||||||
@endif
|
@endif
|
||||||
|
|
||||||
|
@include('pages.parts.editor-translations')
|
Loading…
Reference in New Issue
Block a user