medium-editor-rails 2.3.2 → 2.3.3
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/README.md +1 -1
- data/Rakefile +1 -0
- data/lib/medium-editor-rails/version.rb +2 -2
- data/vendor/assets/javascripts/medium-editor.js +85 -33
- metadata +3 -3
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA1:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 9fbc5be5c8889b94516fe3d384de117a143a8f64
|
4
|
+
data.tar.gz: baa9b17e491b54932b130529bdc9c93a15bbd211
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 5731769e8b3c8bcf932c2bf7f5a06c9a1e9c6e1fec3ae28e301e19c701623f7661ea3353cf6212c49cc3270a5ffa0dbc17ec7303af013ea0b32cf62a0f1e67ac
|
7
|
+
data.tar.gz: 4c75128963d9cb4cbcfadf3de3023576e5759f8b03e14e979fd58c5b01aecb3069722f75316125206e5ae4fdcf2945d4aacf185d4d2a38f0507a1fb1cbf9528a
|
data/README.md
CHANGED
@@ -8,7 +8,7 @@ This gem integrates [Medium Editor](https://github.com/yabwe/medium-editor) with
|
|
8
8
|
|
9
9
|
## Version
|
10
10
|
|
11
|
-
The latest version of Medium Editor bundled by this gem is [5.
|
11
|
+
The latest version of Medium Editor bundled by this gem is [5.23.2](https://github.com/yabwe/medium-editor/releases)
|
12
12
|
|
13
13
|
## Installation
|
14
14
|
|
data/Rakefile
CHANGED
@@ -544,6 +544,9 @@ MediumEditor.extensions = {};
|
|
544
544
|
Util.moveTextRangeIntoElement(textNodes[0], textNodes[textNodes.length - 1], anchor);
|
545
545
|
anchor.setAttribute('href', href);
|
546
546
|
if (target) {
|
547
|
+
if (target === '_blank') {
|
548
|
+
anchor.setAttribute('rel', 'noopener noreferrer');
|
549
|
+
}
|
547
550
|
anchor.setAttribute('target', target);
|
548
551
|
}
|
549
552
|
return anchor;
|
@@ -629,11 +632,10 @@ MediumEditor.extensions = {};
|
|
629
632
|
splitEndNodeIfNeeded: function (currentNode, newNode, matchEndIndex, currentTextIndex) {
|
630
633
|
var textIndexOfEndOfFarthestNode,
|
631
634
|
endSplitPoint;
|
632
|
-
textIndexOfEndOfFarthestNode = currentTextIndex +
|
633
|
-
(newNode ?
|
634
|
-
|
635
|
-
|
636
|
-
(textIndexOfEndOfFarthestNode + 1 - matchEndIndex);
|
635
|
+
textIndexOfEndOfFarthestNode = currentTextIndex + currentNode.nodeValue.length +
|
636
|
+
(newNode ? newNode.nodeValue.length : 0) - 1;
|
637
|
+
endSplitPoint = matchEndIndex - currentTextIndex -
|
638
|
+
(newNode ? currentNode.nodeValue.length : 0);
|
637
639
|
if (textIndexOfEndOfFarthestNode >= matchEndIndex &&
|
638
640
|
currentTextIndex !== textIndexOfEndOfFarthestNode &&
|
639
641
|
endSplitPoint !== 0) {
|
@@ -990,12 +992,14 @@ MediumEditor.extensions = {};
|
|
990
992
|
var i, url = anchorUrl || false;
|
991
993
|
if (el.nodeName.toLowerCase() === 'a') {
|
992
994
|
el.target = '_blank';
|
995
|
+
el.rel = 'noopener noreferrer';
|
993
996
|
} else {
|
994
997
|
el = el.getElementsByTagName('a');
|
995
998
|
|
996
999
|
for (i = 0; i < el.length; i += 1) {
|
997
1000
|
if (false === url || url === el[i].attributes.href.value) {
|
998
1001
|
el[i].target = '_blank';
|
1002
|
+
el[i].rel = 'noopener noreferrer';
|
999
1003
|
}
|
1000
1004
|
}
|
1001
1005
|
}
|
@@ -1009,17 +1013,24 @@ MediumEditor.extensions = {};
|
|
1009
1013
|
var i;
|
1010
1014
|
if (el.nodeName.toLowerCase() === 'a') {
|
1011
1015
|
el.removeAttribute('target');
|
1016
|
+
el.removeAttribute('rel');
|
1012
1017
|
} else {
|
1013
1018
|
el = el.getElementsByTagName('a');
|
1014
1019
|
|
1015
1020
|
for (i = 0; i < el.length; i += 1) {
|
1016
1021
|
if (anchorUrl === el[i].attributes.href.value) {
|
1017
1022
|
el[i].removeAttribute('target');
|
1023
|
+
el[i].removeAttribute('rel');
|
1018
1024
|
}
|
1019
1025
|
}
|
1020
1026
|
}
|
1021
1027
|
},
|
1022
1028
|
|
1029
|
+
/*
|
1030
|
+
* this function adds one or several classes on an a element.
|
1031
|
+
* if el parameter is not an a, it will look for a children of el.
|
1032
|
+
* if no a children are found, it will look for the a parent.
|
1033
|
+
*/
|
1023
1034
|
addClassToAnchors: function (el, buttonClass) {
|
1024
1035
|
var classes = buttonClass.split(' '),
|
1025
1036
|
i,
|
@@ -1029,7 +1040,13 @@ MediumEditor.extensions = {};
|
|
1029
1040
|
el.classList.add(classes[j]);
|
1030
1041
|
}
|
1031
1042
|
} else {
|
1032
|
-
|
1043
|
+
var aChildren = el.getElementsByTagName('a');
|
1044
|
+
if (aChildren.length === 0) {
|
1045
|
+
var parentAnchor = Util.getClosestTag(el, 'a');
|
1046
|
+
el = parentAnchor ? [parentAnchor] : [];
|
1047
|
+
} else {
|
1048
|
+
el = aChildren;
|
1049
|
+
}
|
1033
1050
|
for (i = 0; i < el.length; i += 1) {
|
1034
1051
|
for (j = 0; j < classes.length; j += 1) {
|
1035
1052
|
el[i].classList.add(classes[j]);
|
@@ -2485,15 +2502,17 @@ MediumEditor.extensions = {};
|
|
2485
2502
|
win = this.base.options.contentWindow,
|
2486
2503
|
doc = this.base.options.ownerDocument;
|
2487
2504
|
|
2488
|
-
|
2505
|
+
if (targets !== null) {
|
2506
|
+
targets = MediumEditor.util.isElement(targets) || [win, doc].indexOf(targets) > -1 ? [targets] : targets;
|
2489
2507
|
|
2490
|
-
|
2491
|
-
|
2492
|
-
|
2493
|
-
|
2494
|
-
|
2495
|
-
|
2496
|
-
|
2508
|
+
Array.prototype.forEach.call(targets, function (target) {
|
2509
|
+
index = this.indexOfListener(target, event, listener, useCapture);
|
2510
|
+
if (index !== -1) {
|
2511
|
+
e = this.events.splice(index, 1)[0];
|
2512
|
+
e[0].removeEventListener(e[1], e[2], e[3]);
|
2513
|
+
}
|
2514
|
+
}.bind(this));
|
2515
|
+
}
|
2497
2516
|
},
|
2498
2517
|
|
2499
2518
|
indexOfListener: function (target, event, listener, useCapture) {
|
@@ -3350,6 +3369,14 @@ MediumEditor.extensions = {};
|
|
3350
3369
|
contentDefault: '<b>image</b>',
|
3351
3370
|
contentFA: '<i class="fa fa-picture-o"></i>'
|
3352
3371
|
},
|
3372
|
+
'html': {
|
3373
|
+
name: 'html',
|
3374
|
+
action: 'html',
|
3375
|
+
aria: 'evaluate html',
|
3376
|
+
tagNames: ['iframe', 'object'],
|
3377
|
+
contentDefault: '<b>html</b>',
|
3378
|
+
contentFA: '<i class="fa fa-code"></i>'
|
3379
|
+
},
|
3353
3380
|
'orderedlist': {
|
3354
3381
|
name: 'orderedlist',
|
3355
3382
|
action: 'insertorderedlist',
|
@@ -3511,6 +3538,7 @@ MediumEditor.extensions = {};
|
|
3511
3538
|
};
|
3512
3539
|
|
3513
3540
|
})();
|
3541
|
+
|
3514
3542
|
(function () {
|
3515
3543
|
'use strict';
|
3516
3544
|
|
@@ -3743,8 +3771,8 @@ MediumEditor.extensions = {};
|
|
3743
3771
|
// figure out how to deprecate? also consider `fa-` icon default implcations.
|
3744
3772
|
template.push(
|
3745
3773
|
'<div class="medium-editor-toolbar-form-row">',
|
3746
|
-
'<input type="checkbox" class="medium-editor-toolbar-anchor-target">',
|
3747
|
-
'<label>',
|
3774
|
+
'<input type="checkbox" class="medium-editor-toolbar-anchor-target" id="medium-editor-toolbar-anchor-target-field-' + this.getEditorId() + '">',
|
3775
|
+
'<label for="medium-editor-toolbar-anchor-target-field-' + this.getEditorId() + '">',
|
3748
3776
|
this.targetCheckboxText,
|
3749
3777
|
'</label>',
|
3750
3778
|
'</div>'
|
@@ -3890,22 +3918,35 @@ MediumEditor.extensions = {};
|
|
3890
3918
|
// Matches common external protocols "mailto:" "tel:" "maps:"
|
3891
3919
|
// Matches relative hash link, begins with "#"
|
3892
3920
|
var urlSchemeRegex = /^([a-z]+:)?\/\/|^(mailto|tel|maps):|^\#/i,
|
3921
|
+
hasScheme = urlSchemeRegex.test(value),
|
3922
|
+
scheme = '',
|
3893
3923
|
// telRegex is a regex for checking if the string is a telephone number
|
3894
3924
|
telRegex = /^\+?\s?\(?(?:\d\s?\-?\)?){3,20}$/,
|
3895
|
-
|
3896
|
-
path =
|
3897
|
-
query =
|
3925
|
+
urlParts = value.match(/^(.*?)(?:\?(.*?))?(?:#(.*))?$/),
|
3926
|
+
path = urlParts[1],
|
3927
|
+
query = urlParts[2],
|
3928
|
+
fragment = urlParts[3];
|
3898
3929
|
|
3899
3930
|
if (telRegex.test(value)) {
|
3900
3931
|
return 'tel:' + value;
|
3901
|
-
} else {
|
3902
|
-
// Check for URL scheme and default to http:// if none found
|
3903
|
-
return (urlSchemeRegex.test(value) ? '' : 'http://') +
|
3904
|
-
// Ensure path is encoded
|
3905
|
-
this.ensureEncodedUri(path) +
|
3906
|
-
// Ensure query is encoded
|
3907
|
-
(query === undefined ? '' : '?' + this.ensureEncodedQuery(query));
|
3908
3932
|
}
|
3933
|
+
|
3934
|
+
if (!hasScheme) {
|
3935
|
+
var host = path.split('/')[0];
|
3936
|
+
// if the host part of the path looks like a hostname
|
3937
|
+
if (host.match(/.+(\.|:).+/) || host === 'localhost') {
|
3938
|
+
scheme = 'http://';
|
3939
|
+
}
|
3940
|
+
}
|
3941
|
+
|
3942
|
+
return scheme +
|
3943
|
+
// Ensure path is encoded
|
3944
|
+
this.ensureEncodedUri(path) +
|
3945
|
+
// Ensure query is encoded
|
3946
|
+
(query === undefined ? '' : '?' + this.ensureEncodedQuery(query)) +
|
3947
|
+
// Include fragment unencoded as encodeUriComponent is too
|
3948
|
+
// heavy handed for the many characters allowed in a fragment
|
3949
|
+
(fragment === undefined ? '' : '#' + fragment);
|
3909
3950
|
},
|
3910
3951
|
|
3911
3952
|
doFormCancel: function () {
|
@@ -4067,7 +4108,9 @@ MediumEditor.extensions = {};
|
|
4067
4108
|
},
|
4068
4109
|
|
4069
4110
|
hidePreview: function () {
|
4070
|
-
this.anchorPreview
|
4111
|
+
if (this.anchorPreview) {
|
4112
|
+
this.anchorPreview.classList.remove('medium-editor-anchor-preview-active');
|
4113
|
+
}
|
4071
4114
|
this.activeAnchor = null;
|
4072
4115
|
},
|
4073
4116
|
|
@@ -4305,7 +4348,8 @@ MediumEditor.extensions = {};
|
|
4305
4348
|
var WHITESPACE_CHARS,
|
4306
4349
|
KNOWN_TLDS_FRAGMENT,
|
4307
4350
|
LINK_REGEXP_TEXT,
|
4308
|
-
KNOWN_TLDS_REGEXP
|
4351
|
+
KNOWN_TLDS_REGEXP,
|
4352
|
+
LINK_REGEXP;
|
4309
4353
|
|
4310
4354
|
WHITESPACE_CHARS = [' ', '\t', '\n', '\r', '\u00A0', '\u2000', '\u2001', '\u2002', '\u2003',
|
4311
4355
|
'\u2028', '\u2029'];
|
@@ -4327,6 +4371,8 @@ MediumEditor.extensions = {};
|
|
4327
4371
|
|
4328
4372
|
KNOWN_TLDS_REGEXP = new RegExp('^(' + KNOWN_TLDS_FRAGMENT + ')$', 'i');
|
4329
4373
|
|
4374
|
+
LINK_REGEXP = new RegExp(LINK_REGEXP_TEXT, 'gi');
|
4375
|
+
|
4330
4376
|
function nodeIsNotInsideAnchorTag(node) {
|
4331
4377
|
return !MediumEditor.util.getClosestTag(node, 'a');
|
4332
4378
|
}
|
@@ -4508,12 +4554,11 @@ MediumEditor.extensions = {};
|
|
4508
4554
|
},
|
4509
4555
|
|
4510
4556
|
findLinkableText: function (contenteditable) {
|
4511
|
-
var
|
4512
|
-
textContent = contenteditable.textContent,
|
4557
|
+
var textContent = contenteditable.textContent,
|
4513
4558
|
match = null,
|
4514
4559
|
matches = [];
|
4515
4560
|
|
4516
|
-
while ((match =
|
4561
|
+
while ((match = LINK_REGEXP.exec(textContent)) !== null) {
|
4517
4562
|
var matchOk = true,
|
4518
4563
|
matchEnd = match.index + match[0].length;
|
4519
4564
|
// If the regexp detected something as a link that has text immediately preceding/following it, bail out.
|
@@ -5392,8 +5437,10 @@ MediumEditor.extensions = {};
|
|
5392
5437
|
// on empty line, rects is empty so we grab information from the first container of the range
|
5393
5438
|
if (rects.length) {
|
5394
5439
|
top += rects[0].top;
|
5395
|
-
} else {
|
5440
|
+
} else if (range.startContainer.getBoundingClientRect !== undefined) {
|
5396
5441
|
top += range.startContainer.getBoundingClientRect().top;
|
5442
|
+
} else {
|
5443
|
+
top += range.getBoundingClientRect().top;
|
5397
5444
|
}
|
5398
5445
|
}
|
5399
5446
|
|
@@ -7111,6 +7158,11 @@ MediumEditor.extensions = {};
|
|
7111
7158
|
return this.options.ownerDocument.execCommand('insertImage', false, src);
|
7112
7159
|
}
|
7113
7160
|
|
7161
|
+
if (action === 'html') {
|
7162
|
+
var html = this.options.contentWindow.getSelection().toString().trim();
|
7163
|
+
return MediumEditor.util.insertHTMLCommand(this.options.ownerDocument, html);
|
7164
|
+
}
|
7165
|
+
|
7114
7166
|
/* Issue: https://github.com/yabwe/medium-editor/issues/595
|
7115
7167
|
* If the action is to justify the text */
|
7116
7168
|
if (justifyAction.exec(action)) {
|
@@ -7826,7 +7878,7 @@ MediumEditor.parseVersionString = function (release) {
|
|
7826
7878
|
|
7827
7879
|
MediumEditor.version = MediumEditor.parseVersionString.call(this, ({
|
7828
7880
|
// grunt-bump looks for this:
|
7829
|
-
'version': '5.
|
7881
|
+
'version': '5.23.2'
|
7830
7882
|
}).version);
|
7831
7883
|
|
7832
7884
|
return MediumEditor;
|
metadata
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: medium-editor-rails
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 2.3.
|
4
|
+
version: 2.3.3
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Ahmet Sezgin Duran
|
@@ -9,7 +9,7 @@ authors:
|
|
9
9
|
autorequire:
|
10
10
|
bindir: bin
|
11
11
|
cert_chain: []
|
12
|
-
date: 2017-
|
12
|
+
date: 2017-10-26 00:00:00.000000000 Z
|
13
13
|
dependencies:
|
14
14
|
- !ruby/object:Gem::Dependency
|
15
15
|
name: railties
|
@@ -94,7 +94,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
|
|
94
94
|
version: '0'
|
95
95
|
requirements: []
|
96
96
|
rubyforge_project:
|
97
|
-
rubygems_version: 2.
|
97
|
+
rubygems_version: 2.6.13
|
98
98
|
signing_key:
|
99
99
|
specification_version: 4
|
100
100
|
summary: Metdium Editor integrated in Rails asset pipeline
|