Skip to content
This repository has been archived by the owner on Jun 26, 2020. It is now read-only.

Added defaultValue to ManualDecorators. #258

Merged
merged 6 commits into from
Apr 7, 2020
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
11 changes: 10 additions & 1 deletion docs/features/link.md
Original file line number Diff line number Diff line change
Expand Up @@ -132,7 +132,7 @@ ClassicEditor
// ...
link: {
decorators: {
addTargetToExternalLinks: {
openInNewTab: {
mode: 'manual',
label: 'Open in a new tab',
attributes: {
Expand Down Expand Up @@ -195,6 +195,15 @@ ClassicEditor
attributes: {
download: 'file'
}
},
openInNewTab: {
mode: 'manual',
label: 'Open in a new tab',
defaultValue: true, // This option will be selected by default.
attributes: {
target: '_blank',
rel: 'noopener noreferrer'
}
}
}
}
Expand Down
11 changes: 9 additions & 2 deletions src/link.js
Original file line number Diff line number Diff line change
Expand Up @@ -147,8 +147,13 @@ export default class Link extends Plugin {
*/

/**
* Represents a link decorator definition ({@link module:link/link~LinkDecoratorManualDefinition `'manual'`}
* or {@link module:link/link~LinkDecoratorAutomaticDefinition `'automatic'`}).
* A link decorator definition. Two types implement this defition:
*
* * {@link module:link/link~LinkDecoratorManualDefinition}
* * {@link module:link/link~LinkDecoratorAutomaticDefinition}
*
* Refer to their document for more information about available options or to the
* {@glink features/link#custom-link-attributes-decorators link feature guide} for general information.
*
* @interface LinkDecoratorDefinition
*/
Expand Down Expand Up @@ -203,6 +208,7 @@ export default class Link extends Plugin {
* {
* mode: 'manual',
* label: 'Open in a new tab',
* defaultValue: true,
* attributes: {
* target: '_blank',
* rel: 'noopener noreferrer'
Expand All @@ -215,4 +221,5 @@ export default class Link extends Plugin {
* @property {Object} attributes Key-value pairs used as link attributes added to the output during the
* {@glink framework/guides/architecture/editing-engine#conversion downcasting}.
* Attributes should follow the {@link module:engine/view/elementdefinition~ElementDefinition} syntax.
* @property {Boolean} [defaultValue] Controls whether the decorator is "on" by default.
*/
2 changes: 1 addition & 1 deletion src/linkcommand.js
Original file line number Diff line number Diff line change
Expand Up @@ -214,6 +214,6 @@ export default class LinkCommand extends Command {
*/
_getDecoratorStateFromModel( decoratorName ) {
const doc = this.editor.model.document;
return doc.selection.getAttribute( decoratorName ) || false;
return doc.selection.getAttribute( decoratorName );
}
}
2 changes: 1 addition & 1 deletion src/linkui.js
Original file line number Diff line number Diff line change
Expand Up @@ -144,7 +144,7 @@ export default class LinkUI extends Plugin {
const editor = this.editor;
const linkCommand = editor.commands.get( 'link' );

const formView = new LinkFormView( editor.locale, linkCommand.manualDecorators );
const formView = new LinkFormView( editor.locale, linkCommand );

formView.urlInputView.fieldView.bind( 'value' ).to( linkCommand, 'value' );

Expand Down
22 changes: 11 additions & 11 deletions src/ui/linkformview.js
Original file line number Diff line number Diff line change
Expand Up @@ -39,10 +39,9 @@ export default class LinkFormView extends View {
* Also see {@link #render}.
*
* @param {module:utils/locale~Locale} [locale] The localization services instance.
* @param {module:utils/collection~Collection} [manualDecorators] Reference to manual decorators in
* {@link module:link/linkcommand~LinkCommand#manualDecorators}.
* @param {module:link/linkcommand~LinkCommand} linkCommand Reference to {@link module:link/linkcommand~LinkCommand}.
*/
constructor( locale, manualDecorators = [] ) {
constructor( locale, linkCommand ) {
super( locale );

const t = locale.t;
Expand Down Expand Up @@ -94,15 +93,15 @@ export default class LinkFormView extends View {
* @readonly
* @type {module:ui/viewcollection~ViewCollection}
*/
this._manualDecoratorSwitches = this._createManualDecoratorSwitches( manualDecorators );
this._manualDecoratorSwitches = this._createManualDecoratorSwitches( linkCommand );

/**
* A collection of child views in the form.
*
* @readonly
* @type {module:ui/viewcollection~ViewCollection}
*/
this.children = this._createFormChildren( manualDecorators );
this.children = this._createFormChildren( linkCommand.manualDecorators );

/**
* A collection of views that can be focused in the form.
Expand Down Expand Up @@ -135,7 +134,7 @@ export default class LinkFormView extends View {

const classList = [ 'ck', 'ck-link-form' ];

if ( manualDecorators.length ) {
if ( linkCommand.manualDecorators.length ) {
classList.push( 'ck-link-form_layout-vertical' );
}

Expand Down Expand Up @@ -258,14 +257,13 @@ export default class LinkFormView extends View {
* made based on {@link module:link/linkcommand~LinkCommand#manualDecorators}.
*
* @private
* @param {module:utils/collection~Collection} manualDecorators A reference to the
* collection of manual decorators stored in the link command.
* @param {module:link/linkcommand~LinkCommand} linkCommand A reference to the link command.
* @returns {module:ui/viewcollection~ViewCollection} of switch buttons.
*/
_createManualDecoratorSwitches( manualDecorators ) {
_createManualDecoratorSwitches( linkCommand ) {
const switches = this.createCollection();

for ( const manualDecorator of manualDecorators ) {
for ( const manualDecorator of linkCommand.manualDecorators ) {
const switchButton = new SwitchButtonView( this.locale );

switchButton.set( {
Expand All @@ -274,7 +272,9 @@ export default class LinkFormView extends View {
withText: true
} );

switchButton.bind( 'isOn' ).to( manualDecorator, 'value' );
switchButton.bind( 'isOn' ).toMany( [ manualDecorator, linkCommand ], 'value', ( decoratorValue, commandValue ) => {
return commandValue === undefined && decoratorValue === undefined ? manualDecorator.defaultValue : decoratorValue;
} );

switchButton.on( 'execute', () => {
manualDecorator.set( 'value', !switchButton.isOn );
Expand Down
10 changes: 9 additions & 1 deletion src/utils/manualdecorator.js
Original file line number Diff line number Diff line change
Expand Up @@ -27,8 +27,9 @@ export default class ManualDecorator {
* @param {String} config.label The label used in the user interface to toggle the manual decorator.
* @param {Object} config.attributes A set of attributes added to output data when the decorator is active for a specific link.
* Attributes should keep the format of attributes defined in {@link module:engine/view/elementdefinition~ElementDefinition}.
* @param {Boolean} [config.defaultValue] Controls whether the decorator is "on" by default.
*/
constructor( { id, label, attributes } ) {
constructor( { id, label, attributes, defaultValue } ) {
/**
* An ID of a manual decorator which is the name of the attribute in the model, for example: 'linkManualDecorator0'.
*
Expand All @@ -44,6 +45,13 @@ export default class ManualDecorator {
*/
this.set( 'value' );

/**
* The default value of manual decorator.
*
* @type {Boolean}
*/
this.defaultValue = defaultValue;

/**
* The label used in the user interface to toggle the manual decorator.
*
Expand Down
65 changes: 51 additions & 14 deletions tests/linkcommand.js
Original file line number Diff line number Diff line change
Expand Up @@ -284,10 +284,18 @@ describe( 'LinkCommand', () => {
target: '_blank'
}
} ) );
command.manualDecorators.add( new ManualDecorator( {
id: 'linkIsSth',
label: 'Sth',
attributes: {
class: 'sth'
},
defaultValue: true
} ) );

model.schema.extend( '$text', {
allowIn: '$root',
allowAttributes: [ 'linkHref', 'linkIsFoo', 'linkIsBar' ]
allowAttributes: [ 'linkHref', 'linkIsFoo', 'linkIsBar', 'linkIsSth' ]
} );

model.schema.register( 'p', { inheritAllFrom: '$block' } );
Expand All @@ -302,19 +310,19 @@ describe( 'LinkCommand', () => {
it( 'should insert additional attributes to link when it is created', () => {
setData( model, 'foo[]bar' );

command.execute( 'url', { linkIsFoo: true, linkIsBar: true } );
command.execute( 'url', { linkIsFoo: true, linkIsBar: true, linkIsSth: true } );

expect( getData( model ) ).to
.equal( 'foo[<$text linkHref="url" linkIsBar="true" linkIsFoo="true">url</$text>]bar' );
.equal( 'foo[<$text linkHref="url" linkIsBar="true" linkIsFoo="true" linkIsSth="true">url</$text>]bar' );
} );

it( 'should add additional attributes to link when link is modified', () => {
setData( model, 'f<$text linkHref="url">o[]oba</$text>r' );

command.execute( 'url', { linkIsFoo: true, linkIsBar: true } );
command.execute( 'url', { linkIsFoo: true, linkIsBar: true, linkIsSth: true } );

expect( getData( model ) ).to
.equal( 'f[<$text linkHref="url" linkIsBar="true" linkIsFoo="true">ooba</$text>]r' );
.equal( 'f[<$text linkHref="url" linkIsBar="true" linkIsFoo="true" linkIsSth="true">ooba</$text>]r' );
} );

it( 'should remove additional attributes to link if those are falsy', () => {
Expand All @@ -330,19 +338,19 @@ describe( 'LinkCommand', () => {
it( 'should insert additional attributes to link when it is created', () => {
setData( model, 'f[ooba]r' );

command.execute( 'url', { linkIsFoo: true, linkIsBar: true } );
command.execute( 'url', { linkIsFoo: true, linkIsBar: true, linkIsSth: true } );

expect( getData( model ) ).to
.equal( 'f[<$text linkHref="url" linkIsBar="true" linkIsFoo="true">ooba</$text>]r' );
.equal( 'f[<$text linkHref="url" linkIsBar="true" linkIsFoo="true" linkIsSth="true">ooba</$text>]r' );
} );

it( 'should add additional attributes to link when link is modified', () => {
setData( model, 'f[<$text linkHref="foo">ooba</$text>]r' );

command.execute( 'url', { linkIsFoo: true, linkIsBar: true } );
command.execute( 'url', { linkIsFoo: true, linkIsBar: true, linkIsSth: true } );

expect( getData( model ) ).to
.equal( 'f[<$text linkHref="url" linkIsBar="true" linkIsFoo="true">ooba</$text>]r' );
.equal( 'f[<$text linkHref="url" linkIsBar="true" linkIsFoo="true" linkIsSth="true">ooba</$text>]r' );
} );

it( 'should remove additional attributes to link if those are falsy', () => {
Expand All @@ -356,25 +364,54 @@ describe( 'LinkCommand', () => {

describe( 'restoreManualDecoratorStates()', () => {
it( 'synchronize values with current model state', () => {
setData( model, 'foo<$text linkHref="url" linkIsBar="true" linkIsFoo="true">u[]rl</$text>bar' );
setData( model, 'foo<$text linkHref="url" linkIsBar="true" linkIsFoo="true" linkIsSth="true">u[]rl</$text>bar' );

expect( decoratorStates( command.manualDecorators ) ).to.deep.equal( {
linkIsFoo: true,
linkIsBar: true
linkIsBar: true,
linkIsSth: true
} );

command.manualDecorators.first.value = false;

expect( decoratorStates( command.manualDecorators ) ).to.deep.equal( {
linkIsFoo: false,
linkIsBar: true
linkIsBar: true,
linkIsSth: true
} );

command.restoreManualDecoratorStates();

expect( decoratorStates( command.manualDecorators ) ).to.deep.equal( {
linkIsFoo: true,
linkIsBar: true,
linkIsSth: true
} );
} );

it( 'synchronize values with current model state when the decorator that is "on" default is "off"', () => {
setData( model, 'foo<$text linkHref="url" linkIsBar="true" linkIsFoo="true" linkIsSth="false">u[]rl</$text>bar' );

expect( decoratorStates( command.manualDecorators ) ).to.deep.equal( {
linkIsFoo: true,
linkIsBar: true,
linkIsSth: false
} );

command.manualDecorators.last.value = true;

expect( decoratorStates( command.manualDecorators ) ).to.deep.equal( {
linkIsFoo: true,
linkIsBar: true,
linkIsSth: true
} );

command.restoreManualDecoratorStates();

expect( decoratorStates( command.manualDecorators ) ).to.deep.equal( {
linkIsFoo: true,
linkIsBar: true
linkIsBar: true,
linkIsSth: false
} );
} );
} );
Expand All @@ -383,7 +420,7 @@ describe( 'LinkCommand', () => {
it( 'obtain current values from the model', () => {
setData( model, 'foo[<$text linkHref="url" linkIsBar="true">url</$text>]bar' );

expect( command._getDecoratorStateFromModel( 'linkIsFoo' ) ).to.be.false;
expect( command._getDecoratorStateFromModel( 'linkIsFoo' ) ).to.be.undefined;
expect( command._getDecoratorStateFromModel( 'linkIsBar' ) ).to.be.true;
} );
} );
Expand Down
Loading