lexxy 0.9.20 → 0.9.22
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.
- checksums.yaml +4 -4
- data/README.md +2 -19
- data/app/assets/javascript/lexxy.js +69 -17
- data/app/assets/javascript/lexxy.js.br +0 -0
- data/app/assets/javascript/lexxy.js.gz +0 -0
- data/app/assets/javascript/lexxy.js.map +1 -1
- data/app/assets/javascript/lexxy.min.js +1 -1
- data/app/assets/javascript/lexxy.min.js.br +0 -0
- data/app/assets/javascript/lexxy.min.js.gz +0 -0
- data/lib/lexxy/version.rb +1 -1
- metadata +1 -1
checksums.yaml
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
---
|
|
2
2
|
SHA256:
|
|
3
|
-
metadata.gz:
|
|
4
|
-
data.tar.gz:
|
|
3
|
+
metadata.gz: 3dd84ec12b2544306275e4c55775e2ef95770e6e9de65adb028663f51bd099e6
|
|
4
|
+
data.tar.gz: c3bc7b9f5834a80f1e40de9e2c82fec32ce590aba1cb2022eb13c320303dd92d
|
|
5
5
|
SHA512:
|
|
6
|
-
metadata.gz:
|
|
7
|
-
data.tar.gz:
|
|
6
|
+
metadata.gz: 3a29b71559385f62b6b084731cc77baea92c67ebe10b0f588610de8d5d9cecba54403f7201c8bbc1143a0122402195b356d7c0b45bac6d176136dbefcb016b02
|
|
7
|
+
data.tar.gz: 05cac4466fc4374f1cfbe3e547a462e2cdceed094b2eb043e6a713ff165ff852ec39f08d8f15aed0ae4e24634376243cced2ca36e37e5657bb87faaac4991f8b
|
data/README.md
CHANGED
|
@@ -2,7 +2,7 @@
|
|
|
2
2
|
|
|
3
3
|
A modern rich text editor for Rails.
|
|
4
4
|
|
|
5
|
-
|
|
5
|
+
[Documentation](https://basecamp.github.io/lexxy/docs/) | <mark>[Try it out!](https://basecamp.github.io/lexxy/sandbox/)</mark>
|
|
6
6
|
|
|
7
7
|
## Features
|
|
8
8
|
|
|
@@ -15,24 +15,7 @@ A modern rich text editor for Rails.
|
|
|
15
15
|
- Preview attachments like PDFs and Videos in the editor.
|
|
16
16
|
- Works seamlessly with Action Text, generating the same canonical HTML format it expects for attachments.
|
|
17
17
|
|
|
18
|
-

|
|
19
|
-
|
|
20
|
-
## Documentation
|
|
21
|
-
|
|
22
|
-
Visit the **[documentation site](https://basecamp.github.io/lexxy)**.
|
|
23
|
-
|
|
24
|
-
## Roadmap
|
|
25
|
-
|
|
26
|
-
This is a beta. Here's what's coming next:
|
|
27
|
-
|
|
28
|
-
- [x] Configurable editors in Action Text: Choose your editor like you choose your database.
|
|
29
|
-
- [x] More editing features:
|
|
30
|
-
- [x] Tables
|
|
31
|
-
- [x] Text highlighting
|
|
32
|
-
- [x] Configuration hooks.
|
|
33
|
-
- [x] Standalone JS package: to use in non-Rails environments.
|
|
34
|
-
- [x] Image galleries: The only remaining feature for full Action Text compatibility
|
|
35
|
-
- [ ] Install task that generates the necessary JS and adds stylesheets.
|
|
18
|
+

|
|
36
19
|
|
|
37
20
|
## Contributing
|
|
38
21
|
|
|
@@ -12884,7 +12884,7 @@ class Clipboard {
|
|
|
12884
12884
|
}
|
|
12885
12885
|
|
|
12886
12886
|
if (this.#isPlainTextOrURLPasted(clipboardData)) {
|
|
12887
|
-
this.#
|
|
12887
|
+
this.#pastePlainTextOrURL(clipboardData);
|
|
12888
12888
|
event.preventDefault();
|
|
12889
12889
|
return true
|
|
12890
12890
|
}
|
|
@@ -12922,14 +12922,34 @@ class Clipboard {
|
|
|
12922
12922
|
return types.length === 1 && types[0] === "text/plain"
|
|
12923
12923
|
}
|
|
12924
12924
|
|
|
12925
|
+
// Browsers expose a copied URL in several shapes:
|
|
12926
|
+
// Safari [ text/plain, text/uri-list ]
|
|
12927
|
+
// App ShareSheet [ text/uri-list ]
|
|
12928
|
+
// Chromium macOS [ text/plain, text/html, (?:text/link-preview) ]
|
|
12925
12929
|
#isOnlyURLPasted(clipboardData) {
|
|
12926
|
-
|
|
12927
|
-
|
|
12930
|
+
if (this.#isLexicalClipboardData(clipboardData)) return false
|
|
12931
|
+
|
|
12928
12932
|
const types = Array.from(clipboardData.types);
|
|
12929
|
-
|
|
12930
|
-
|
|
12931
|
-
|
|
12932
|
-
|
|
12933
|
+
if (types.includes("text/uri-list")) {
|
|
12934
|
+
return types.every(type => type === "text/plain" || type === "text/uri-list")
|
|
12935
|
+
}
|
|
12936
|
+
|
|
12937
|
+
if (clipboardData.files.length) return false
|
|
12938
|
+
|
|
12939
|
+
const text = clipboardData.getData("text/plain").trim();
|
|
12940
|
+
if (!isAutolinkableURL(text)) return false
|
|
12941
|
+
|
|
12942
|
+
const html = clipboardData.getData("text/html");
|
|
12943
|
+
return !html || this.#htmlIsBareLinkToURL(html, text)
|
|
12944
|
+
}
|
|
12945
|
+
|
|
12946
|
+
#htmlIsBareLinkToURL(html, url) {
|
|
12947
|
+
const doc = parseHtml(html);
|
|
12948
|
+
if (doc.body.textContent.trim() !== url) return false
|
|
12949
|
+
|
|
12950
|
+
const links = doc.body.querySelectorAll("a");
|
|
12951
|
+
if (links.length === 0) return true
|
|
12952
|
+
return links.length === 1 && links[0].getAttribute("href") === url
|
|
12933
12953
|
}
|
|
12934
12954
|
|
|
12935
12955
|
#isPastingIntoCodeBlock() {
|
|
@@ -12963,14 +12983,12 @@ class Clipboard {
|
|
|
12963
12983
|
}, { tag: jn });
|
|
12964
12984
|
}
|
|
12965
12985
|
|
|
12966
|
-
#
|
|
12967
|
-
const item = clipboardData
|
|
12986
|
+
#pastePlainTextOrURL(clipboardData) {
|
|
12987
|
+
const item = this.#plainTextOrURLItem(clipboardData);
|
|
12968
12988
|
item.getAsString((text) => {
|
|
12969
|
-
|
|
12970
|
-
|
|
12971
|
-
|
|
12972
|
-
const nodeKey = this.contents.createLink(text);
|
|
12973
|
-
this.#dispatchLinkInsertEvent(nodeKey, { url: text });
|
|
12989
|
+
const url = text.trim();
|
|
12990
|
+
if (isAutolinkableURL(url)) {
|
|
12991
|
+
this.#pasteURL(url);
|
|
12974
12992
|
} else if (this.editorElement.supportsMarkdown) {
|
|
12975
12993
|
this.#pasteMarkdown(text);
|
|
12976
12994
|
} else {
|
|
@@ -12979,6 +12997,20 @@ class Clipboard {
|
|
|
12979
12997
|
});
|
|
12980
12998
|
}
|
|
12981
12999
|
|
|
13000
|
+
#plainTextOrURLItem(clipboardData) {
|
|
13001
|
+
const items = Array.from(clipboardData.items);
|
|
13002
|
+
return items.find((item) => item.type === "text/plain") || items.find((item) => item.type === "text/uri-list")
|
|
13003
|
+
}
|
|
13004
|
+
|
|
13005
|
+
#pasteURL(url) {
|
|
13006
|
+
if (this.contents.hasSelectedText()) {
|
|
13007
|
+
this.contents.createLinkWithSelectedText(url);
|
|
13008
|
+
} else {
|
|
13009
|
+
const nodeKey = this.contents.createLink(url);
|
|
13010
|
+
this.#dispatchLinkInsertEvent(nodeKey, { url });
|
|
13011
|
+
}
|
|
13012
|
+
}
|
|
13013
|
+
|
|
12982
13014
|
#insertSingleLinkAt(selection, url) {
|
|
12983
13015
|
if (!Fr(selection)) return
|
|
12984
13016
|
|
|
@@ -13437,6 +13469,26 @@ function $getAllProvisionalParagraphs(rootNode = Zo()) {
|
|
|
13437
13469
|
return Ht$3(rootNode.getChildren(), $isProvisionalParagraphNode)
|
|
13438
13470
|
}
|
|
13439
13471
|
|
|
13472
|
+
// Registers code highlighting through the extension system so its node
|
|
13473
|
+
// transforms exist before the initial editor state is applied. Registering
|
|
13474
|
+
// after editor creation misses code blocks loaded from the initial value:
|
|
13475
|
+
// their transform pass has already run, and Lexical's catch-up dirtying
|
|
13476
|
+
// only sees the committed (still empty) state.
|
|
13477
|
+
class CodeHighlightingExtension extends LexxyExtension {
|
|
13478
|
+
get enabled() {
|
|
13479
|
+
return this.editorElement.supportsRichText
|
|
13480
|
+
}
|
|
13481
|
+
|
|
13482
|
+
get lexicalExtension() {
|
|
13483
|
+
return dc({
|
|
13484
|
+
name: "lexxy/code-highlighting",
|
|
13485
|
+
register(editor) {
|
|
13486
|
+
return L$1(editor)
|
|
13487
|
+
}
|
|
13488
|
+
})
|
|
13489
|
+
}
|
|
13490
|
+
}
|
|
13491
|
+
|
|
13440
13492
|
const TRIX_LANGUAGE_ATTR = "language";
|
|
13441
13493
|
|
|
13442
13494
|
class TrixContentExtension extends LexxyExtension {
|
|
@@ -14957,6 +15009,7 @@ class LexicalEditorElement extends HTMLElement {
|
|
|
14957
15009
|
get baseExtensions() {
|
|
14958
15010
|
return [
|
|
14959
15011
|
ProvisionalParagraphExtension,
|
|
15012
|
+
CodeHighlightingExtension,
|
|
14960
15013
|
HighlightExtension,
|
|
14961
15014
|
TrixContentExtension,
|
|
14962
15015
|
TablesExtension,
|
|
@@ -15364,7 +15417,7 @@ class LexicalEditorElement extends HTMLElement {
|
|
|
15364
15417
|
Ie$2(this.editor)
|
|
15365
15418
|
);
|
|
15366
15419
|
this.#registerTableComponents();
|
|
15367
|
-
this.#
|
|
15420
|
+
this.#registerCodeLanguagePicker();
|
|
15368
15421
|
if (this.supportsMarkdown) {
|
|
15369
15422
|
const transformers = [ ...te, HORIZONTAL_DIVIDER ];
|
|
15370
15423
|
registered.push(
|
|
@@ -15386,8 +15439,7 @@ class LexicalEditorElement extends HTMLElement {
|
|
|
15386
15439
|
this.#disposables.push(tableTools);
|
|
15387
15440
|
}
|
|
15388
15441
|
|
|
15389
|
-
#
|
|
15390
|
-
L$1(this.editor);
|
|
15442
|
+
#registerCodeLanguagePicker() {
|
|
15391
15443
|
let codeLanguagePicker = this.querySelector("lexxy-code-language-picker");
|
|
15392
15444
|
codeLanguagePicker ??= createElement("lexxy-code-language-picker");
|
|
15393
15445
|
this.append(codeLanguagePicker);
|
|
Binary file
|
|
Binary file
|