Merge branch 'MDL-74632-master' of https://github.com/HuongNV13/moodle
This commit is contained in:
@@ -82,3 +82,37 @@ Feature: Add links to Atto
|
||||
And I click on "Link" "button"
|
||||
And the field "Text to display" matches value "Moodle - Open-source learning platform"
|
||||
And the field "Enter a URL" matches value "https://moodle.org/"
|
||||
|
||||
@javascript
|
||||
Scenario: Insert a link for an image
|
||||
Given I log in as "admin"
|
||||
And I follow "Private files" in the user menu
|
||||
And I upload "lib/editor/atto/tests/fixtures/moodle-logo.png" file to "Files" filemanager
|
||||
And I click on "Save changes" "button"
|
||||
And I open my profile in edit mode
|
||||
And I click on "Insert or edit image" "button"
|
||||
And I click on "Browse repositories..." "button"
|
||||
And I click on "Private files" "link" in the ".fp-repo-area" "css_element"
|
||||
And I click on "moodle-logo.png" "link"
|
||||
And I click on "Select this file" "button"
|
||||
And I set the field "Describe this image for someone who cannot see it" to "It's the Moodle"
|
||||
And I press "Save image"
|
||||
And I select the text in the "Description" Atto editor
|
||||
And I press the right key
|
||||
And I press the shift left key
|
||||
And I click on "Link" "button"
|
||||
And I set the field "Enter a URL" to "https://moodle.org/"
|
||||
And I set the field "Text to display" to "Moodle - Open-source learning platform"
|
||||
And I click on "Create link" "button"
|
||||
When I click on "Show more buttons" "button"
|
||||
And I click on "HTML" "button"
|
||||
Then I should see "<a href=\"https://moodle.org/\" title=\"Moodle - Open-source learning platform\"><img"
|
||||
And I click on "HTML" "button"
|
||||
And I select the text in the "Description" Atto editor
|
||||
And I press the shift left key
|
||||
And I click on "Insert or edit image" "button"
|
||||
And the field "Describe this image for someone who cannot see it" matches value "It's the Moodle"
|
||||
And I click on "Close" "button" in the "Image properties" "dialogue"
|
||||
And I click on "Link" "button"
|
||||
And the field "Text to display" matches value "Moodle - Open-source learning platform"
|
||||
And the field "Enter a URL" matches value "https://moodle.org/"
|
||||
|
||||
Vendored
+48
-4
@@ -111,6 +111,14 @@ Y.namespace('M.atto_link').Button = Y.Base.create('button', Y.M.editor_atto.Edit
|
||||
*/
|
||||
_hasTextToDisplay: false,
|
||||
|
||||
/**
|
||||
* User has selected plain text or not.
|
||||
* @property _hasPlainTextSelected
|
||||
* @type Boolean
|
||||
* @private
|
||||
*/
|
||||
_hasPlainTextSelected: false,
|
||||
|
||||
initializer: function() {
|
||||
// Add the link button first.
|
||||
this.addButton({
|
||||
@@ -176,7 +184,8 @@ Y.namespace('M.atto_link').Button = Y.Base.create('button', Y.M.editor_atto.Edit
|
||||
anchornode,
|
||||
url,
|
||||
target,
|
||||
textToDisplay;
|
||||
textToDisplay,
|
||||
title;
|
||||
|
||||
// Note this is a document fragment and YUI doesn't like them.
|
||||
if (!selectednode) {
|
||||
@@ -190,11 +199,14 @@ Y.namespace('M.atto_link').Button = Y.Base.create('button', Y.M.editor_atto.Edit
|
||||
url = anchornode.getAttribute('href');
|
||||
target = anchornode.getAttribute('target');
|
||||
textToDisplay = anchornode.get('innerText');
|
||||
title = anchornode.getAttribute('title');
|
||||
if (url !== '') {
|
||||
this._content.one(SELECTORS.URLINPUT).setAttribute('value', url);
|
||||
}
|
||||
if (textToDisplay !== '') {
|
||||
this._content.one(SELECTORS.URLTEXT).set('value', textToDisplay);
|
||||
} else if (title !== '') {
|
||||
this._content.one(SELECTORS.URLTEXT).set('value', title);
|
||||
}
|
||||
if (target === '_blank') {
|
||||
this._content.one(SELECTORS.NEWWINDOW).setAttribute('checked', 'checked');
|
||||
@@ -203,9 +215,10 @@ Y.namespace('M.atto_link').Button = Y.Base.create('button', Y.M.editor_atto.Edit
|
||||
}
|
||||
} else {
|
||||
// User is selecting some text before clicking on the Link button.
|
||||
textToDisplay = window.getSelection().toString();
|
||||
textToDisplay = this._getTextSelection();
|
||||
if (textToDisplay !== '') {
|
||||
this._hasTextToDisplay = true;
|
||||
this._hasPlainTextSelected = true;
|
||||
this._content.one(SELECTORS.URLTEXT).set('value', textToDisplay);
|
||||
}
|
||||
}
|
||||
@@ -325,9 +338,16 @@ Y.namespace('M.atto_link').Button = Y.Base.create('button', Y.M.editor_atto.Edit
|
||||
} else {
|
||||
anchornode.removeAttribute('target');
|
||||
}
|
||||
if (isUpdating) {
|
||||
if (isUpdating && textToDisplay) {
|
||||
// The 'createLink' command do not allow to set the custom text to display. So we need to do it here.
|
||||
anchornode.set('innerText', textToDisplay);
|
||||
if (this._hasPlainTextSelected) {
|
||||
// Only replace the innerText if the user has not selected any element or just the plain text.
|
||||
anchornode.set('innerText', textToDisplay);
|
||||
} else {
|
||||
// The user has selected another element to add the hyperlink, like an image.
|
||||
// We should add the title attribute instead of replacing the innerText of the hyperlink.
|
||||
anchornode.setAttribute('title', textToDisplay);
|
||||
}
|
||||
}
|
||||
}, this);
|
||||
|
||||
@@ -387,6 +407,7 @@ Y.namespace('M.atto_link').Button = Y.Base.create('button', Y.M.editor_atto.Edit
|
||||
}));
|
||||
|
||||
this._content.one(SELECTORS.URLINPUT).on('keyup', this._updateTextToDisplay, this);
|
||||
this._content.one(SELECTORS.URLINPUT).on('change', this._updateTextToDisplay, this);
|
||||
this._content.one(SELECTORS.URLTEXT).on('keyup', this._setTextToDisplayState, this);
|
||||
this._content.one(SELECTORS.SUBMIT).on('click', this._setLink, this);
|
||||
if (canShowFilepicker) {
|
||||
@@ -479,6 +500,29 @@ Y.namespace('M.atto_link').Button = Y.Base.create('button', Y.M.editor_atto.Edit
|
||||
if (!this._hasTextToDisplay) {
|
||||
urlText.set('value', urlEntryVal);
|
||||
}
|
||||
},
|
||||
|
||||
/**
|
||||
* Get only the selected text.
|
||||
* In some cases, window.getSelection() is not run as expected. We should only get the text value
|
||||
* For ex: <img src="" alt="XYZ">Some text here
|
||||
* window.getSelection() will return XYZSome text here
|
||||
*
|
||||
* @returns {string} Selected text
|
||||
* @private
|
||||
*/
|
||||
_getTextSelection: function() {
|
||||
var selText = '';
|
||||
var sel = window.getSelection();
|
||||
var rangeCount = sel.rangeCount;
|
||||
if (rangeCount) {
|
||||
var rangeTexts = [];
|
||||
for (var i = 0; i < rangeCount; ++i) {
|
||||
rangeTexts.push('' + sel.getRangeAt(i));
|
||||
}
|
||||
selText = rangeTexts.join('');
|
||||
}
|
||||
return selText;
|
||||
}
|
||||
});
|
||||
|
||||
|
||||
Vendored
+1
-1
File diff suppressed because one or more lines are too long
+48
-4
@@ -111,6 +111,14 @@ Y.namespace('M.atto_link').Button = Y.Base.create('button', Y.M.editor_atto.Edit
|
||||
*/
|
||||
_hasTextToDisplay: false,
|
||||
|
||||
/**
|
||||
* User has selected plain text or not.
|
||||
* @property _hasPlainTextSelected
|
||||
* @type Boolean
|
||||
* @private
|
||||
*/
|
||||
_hasPlainTextSelected: false,
|
||||
|
||||
initializer: function() {
|
||||
// Add the link button first.
|
||||
this.addButton({
|
||||
@@ -176,7 +184,8 @@ Y.namespace('M.atto_link').Button = Y.Base.create('button', Y.M.editor_atto.Edit
|
||||
anchornode,
|
||||
url,
|
||||
target,
|
||||
textToDisplay;
|
||||
textToDisplay,
|
||||
title;
|
||||
|
||||
// Note this is a document fragment and YUI doesn't like them.
|
||||
if (!selectednode) {
|
||||
@@ -190,11 +199,14 @@ Y.namespace('M.atto_link').Button = Y.Base.create('button', Y.M.editor_atto.Edit
|
||||
url = anchornode.getAttribute('href');
|
||||
target = anchornode.getAttribute('target');
|
||||
textToDisplay = anchornode.get('innerText');
|
||||
title = anchornode.getAttribute('title');
|
||||
if (url !== '') {
|
||||
this._content.one(SELECTORS.URLINPUT).setAttribute('value', url);
|
||||
}
|
||||
if (textToDisplay !== '') {
|
||||
this._content.one(SELECTORS.URLTEXT).set('value', textToDisplay);
|
||||
} else if (title !== '') {
|
||||
this._content.one(SELECTORS.URLTEXT).set('value', title);
|
||||
}
|
||||
if (target === '_blank') {
|
||||
this._content.one(SELECTORS.NEWWINDOW).setAttribute('checked', 'checked');
|
||||
@@ -203,9 +215,10 @@ Y.namespace('M.atto_link').Button = Y.Base.create('button', Y.M.editor_atto.Edit
|
||||
}
|
||||
} else {
|
||||
// User is selecting some text before clicking on the Link button.
|
||||
textToDisplay = window.getSelection().toString();
|
||||
textToDisplay = this._getTextSelection();
|
||||
if (textToDisplay !== '') {
|
||||
this._hasTextToDisplay = true;
|
||||
this._hasPlainTextSelected = true;
|
||||
this._content.one(SELECTORS.URLTEXT).set('value', textToDisplay);
|
||||
}
|
||||
}
|
||||
@@ -325,9 +338,16 @@ Y.namespace('M.atto_link').Button = Y.Base.create('button', Y.M.editor_atto.Edit
|
||||
} else {
|
||||
anchornode.removeAttribute('target');
|
||||
}
|
||||
if (isUpdating) {
|
||||
if (isUpdating && textToDisplay) {
|
||||
// The 'createLink' command do not allow to set the custom text to display. So we need to do it here.
|
||||
anchornode.set('innerText', textToDisplay);
|
||||
if (this._hasPlainTextSelected) {
|
||||
// Only replace the innerText if the user has not selected any element or just the plain text.
|
||||
anchornode.set('innerText', textToDisplay);
|
||||
} else {
|
||||
// The user has selected another element to add the hyperlink, like an image.
|
||||
// We should add the title attribute instead of replacing the innerText of the hyperlink.
|
||||
anchornode.setAttribute('title', textToDisplay);
|
||||
}
|
||||
}
|
||||
}, this);
|
||||
|
||||
@@ -387,6 +407,7 @@ Y.namespace('M.atto_link').Button = Y.Base.create('button', Y.M.editor_atto.Edit
|
||||
}));
|
||||
|
||||
this._content.one(SELECTORS.URLINPUT).on('keyup', this._updateTextToDisplay, this);
|
||||
this._content.one(SELECTORS.URLINPUT).on('change', this._updateTextToDisplay, this);
|
||||
this._content.one(SELECTORS.URLTEXT).on('keyup', this._setTextToDisplayState, this);
|
||||
this._content.one(SELECTORS.SUBMIT).on('click', this._setLink, this);
|
||||
if (canShowFilepicker) {
|
||||
@@ -479,6 +500,29 @@ Y.namespace('M.atto_link').Button = Y.Base.create('button', Y.M.editor_atto.Edit
|
||||
if (!this._hasTextToDisplay) {
|
||||
urlText.set('value', urlEntryVal);
|
||||
}
|
||||
},
|
||||
|
||||
/**
|
||||
* Get only the selected text.
|
||||
* In some cases, window.getSelection() is not run as expected. We should only get the text value
|
||||
* For ex: <img src="" alt="XYZ">Some text here
|
||||
* window.getSelection() will return XYZSome text here
|
||||
*
|
||||
* @returns {string} Selected text
|
||||
* @private
|
||||
*/
|
||||
_getTextSelection: function() {
|
||||
var selText = '';
|
||||
var sel = window.getSelection();
|
||||
var rangeCount = sel.rangeCount;
|
||||
if (rangeCount) {
|
||||
var rangeTexts = [];
|
||||
for (var i = 0; i < rangeCount; ++i) {
|
||||
rangeTexts.push('' + sel.getRangeAt(i));
|
||||
}
|
||||
selText = rangeTexts.join('');
|
||||
}
|
||||
return selText;
|
||||
}
|
||||
});
|
||||
|
||||
|
||||
+48
-4
@@ -109,6 +109,14 @@ Y.namespace('M.atto_link').Button = Y.Base.create('button', Y.M.editor_atto.Edit
|
||||
*/
|
||||
_hasTextToDisplay: false,
|
||||
|
||||
/**
|
||||
* User has selected plain text or not.
|
||||
* @property _hasPlainTextSelected
|
||||
* @type Boolean
|
||||
* @private
|
||||
*/
|
||||
_hasPlainTextSelected: false,
|
||||
|
||||
initializer: function() {
|
||||
// Add the link button first.
|
||||
this.addButton({
|
||||
@@ -174,7 +182,8 @@ Y.namespace('M.atto_link').Button = Y.Base.create('button', Y.M.editor_atto.Edit
|
||||
anchornode,
|
||||
url,
|
||||
target,
|
||||
textToDisplay;
|
||||
textToDisplay,
|
||||
title;
|
||||
|
||||
// Note this is a document fragment and YUI doesn't like them.
|
||||
if (!selectednode) {
|
||||
@@ -188,11 +197,14 @@ Y.namespace('M.atto_link').Button = Y.Base.create('button', Y.M.editor_atto.Edit
|
||||
url = anchornode.getAttribute('href');
|
||||
target = anchornode.getAttribute('target');
|
||||
textToDisplay = anchornode.get('innerText');
|
||||
title = anchornode.getAttribute('title');
|
||||
if (url !== '') {
|
||||
this._content.one(SELECTORS.URLINPUT).setAttribute('value', url);
|
||||
}
|
||||
if (textToDisplay !== '') {
|
||||
this._content.one(SELECTORS.URLTEXT).set('value', textToDisplay);
|
||||
} else if (title !== '') {
|
||||
this._content.one(SELECTORS.URLTEXT).set('value', title);
|
||||
}
|
||||
if (target === '_blank') {
|
||||
this._content.one(SELECTORS.NEWWINDOW).setAttribute('checked', 'checked');
|
||||
@@ -201,9 +213,10 @@ Y.namespace('M.atto_link').Button = Y.Base.create('button', Y.M.editor_atto.Edit
|
||||
}
|
||||
} else {
|
||||
// User is selecting some text before clicking on the Link button.
|
||||
textToDisplay = window.getSelection().toString();
|
||||
textToDisplay = this._getTextSelection();
|
||||
if (textToDisplay !== '') {
|
||||
this._hasTextToDisplay = true;
|
||||
this._hasPlainTextSelected = true;
|
||||
this._content.one(SELECTORS.URLTEXT).set('value', textToDisplay);
|
||||
}
|
||||
}
|
||||
@@ -323,9 +336,16 @@ Y.namespace('M.atto_link').Button = Y.Base.create('button', Y.M.editor_atto.Edit
|
||||
} else {
|
||||
anchornode.removeAttribute('target');
|
||||
}
|
||||
if (isUpdating) {
|
||||
if (isUpdating && textToDisplay) {
|
||||
// The 'createLink' command do not allow to set the custom text to display. So we need to do it here.
|
||||
anchornode.set('innerText', textToDisplay);
|
||||
if (this._hasPlainTextSelected) {
|
||||
// Only replace the innerText if the user has not selected any element or just the plain text.
|
||||
anchornode.set('innerText', textToDisplay);
|
||||
} else {
|
||||
// The user has selected another element to add the hyperlink, like an image.
|
||||
// We should add the title attribute instead of replacing the innerText of the hyperlink.
|
||||
anchornode.setAttribute('title', textToDisplay);
|
||||
}
|
||||
}
|
||||
}, this);
|
||||
|
||||
@@ -385,6 +405,7 @@ Y.namespace('M.atto_link').Button = Y.Base.create('button', Y.M.editor_atto.Edit
|
||||
}));
|
||||
|
||||
this._content.one(SELECTORS.URLINPUT).on('keyup', this._updateTextToDisplay, this);
|
||||
this._content.one(SELECTORS.URLINPUT).on('change', this._updateTextToDisplay, this);
|
||||
this._content.one(SELECTORS.URLTEXT).on('keyup', this._setTextToDisplayState, this);
|
||||
this._content.one(SELECTORS.SUBMIT).on('click', this._setLink, this);
|
||||
if (canShowFilepicker) {
|
||||
@@ -477,5 +498,28 @@ Y.namespace('M.atto_link').Button = Y.Base.create('button', Y.M.editor_atto.Edit
|
||||
if (!this._hasTextToDisplay) {
|
||||
urlText.set('value', urlEntryVal);
|
||||
}
|
||||
},
|
||||
|
||||
/**
|
||||
* Get only the selected text.
|
||||
* In some cases, window.getSelection() is not run as expected. We should only get the text value
|
||||
* For ex: <img src="" alt="XYZ">Some text here
|
||||
* window.getSelection() will return XYZSome text here
|
||||
*
|
||||
* @returns {string} Selected text
|
||||
* @private
|
||||
*/
|
||||
_getTextSelection: function() {
|
||||
var selText = '';
|
||||
var sel = window.getSelection();
|
||||
var rangeCount = sel.rangeCount;
|
||||
if (rangeCount) {
|
||||
var rangeTexts = [];
|
||||
for (var i = 0; i < rangeCount; ++i) {
|
||||
rangeTexts.push('' + sel.getRangeAt(i));
|
||||
}
|
||||
selText = rangeTexts.join('');
|
||||
}
|
||||
return selText;
|
||||
}
|
||||
});
|
||||
|
||||
Reference in New Issue
Block a user