From e86add851fce50eef1ca82da441416e040dbd76f Mon Sep 17 00:00:00 2001 From: Ian Storm Taylor Date: Thu, 6 Oct 2016 11:29:12 -0700 Subject: [PATCH] handle removing text nodes when removing all characters --- src/transforms/apply-operation.js | 1 - src/transforms/by-key.js | 27 +++++++++++++++++-- .../adjacent-non-void-inlines/index.js | 10 +++++++ .../adjacent-non-void-inlines/input.yaml | 17 ++++++++++++ .../adjacent-non-void-inlines/output.yaml | 15 +++++++++++ .../remove-text-by-key/inline-void/index.js | 10 +++++++ .../remove-text-by-key/inline-void/input.yaml | 12 +++++++++ .../inline-void/output.yaml | 12 +++++++++ .../by-key/remove-text-by-key/inline/index.js | 10 +++++++ .../remove-text-by-key/inline/input.yaml | 10 +++++++ .../remove-text-by-key/inline/output.yaml | 10 +++++++ .../next-void-inline/index.js | 10 +++++++ .../next-void-inline/input.yaml | 17 ++++++++++++ .../next-void-inline/output.yaml | 15 +++++++++++ .../previous-void-inline/index.js | 10 +++++++ .../previous-void-inline/input.yaml | 17 ++++++++++++ .../previous-void-inline/output.yaml | 15 +++++++++++ .../by-key/remove-text-by-key/text/index.js | 10 +++++++ .../by-key/remove-text-by-key/text/input.yaml | 7 +++++ .../remove-text-by-key/text/output.yaml | 7 +++++ 20 files changed, 239 insertions(+), 3 deletions(-) create mode 100644 test/transforms/fixtures/by-key/remove-text-by-key/adjacent-non-void-inlines/index.js create mode 100644 test/transforms/fixtures/by-key/remove-text-by-key/adjacent-non-void-inlines/input.yaml create mode 100644 test/transforms/fixtures/by-key/remove-text-by-key/adjacent-non-void-inlines/output.yaml create mode 100644 test/transforms/fixtures/by-key/remove-text-by-key/inline-void/index.js create mode 100644 test/transforms/fixtures/by-key/remove-text-by-key/inline-void/input.yaml create mode 100644 test/transforms/fixtures/by-key/remove-text-by-key/inline-void/output.yaml create mode 100644 test/transforms/fixtures/by-key/remove-text-by-key/inline/index.js create mode 100644 test/transforms/fixtures/by-key/remove-text-by-key/inline/input.yaml create mode 100644 test/transforms/fixtures/by-key/remove-text-by-key/inline/output.yaml create mode 100644 test/transforms/fixtures/by-key/remove-text-by-key/next-void-inline/index.js create mode 100644 test/transforms/fixtures/by-key/remove-text-by-key/next-void-inline/input.yaml create mode 100644 test/transforms/fixtures/by-key/remove-text-by-key/next-void-inline/output.yaml create mode 100644 test/transforms/fixtures/by-key/remove-text-by-key/previous-void-inline/index.js create mode 100644 test/transforms/fixtures/by-key/remove-text-by-key/previous-void-inline/input.yaml create mode 100644 test/transforms/fixtures/by-key/remove-text-by-key/previous-void-inline/output.yaml create mode 100644 test/transforms/fixtures/by-key/remove-text-by-key/text/index.js create mode 100644 test/transforms/fixtures/by-key/remove-text-by-key/text/input.yaml create mode 100644 test/transforms/fixtures/by-key/remove-text-by-key/text/output.yaml diff --git a/src/transforms/apply-operation.js b/src/transforms/apply-operation.js index 1dccee47e..5410913a5 100644 --- a/src/transforms/apply-operation.js +++ b/src/transforms/apply-operation.js @@ -211,7 +211,6 @@ function removeText(state, operation) { let node = document.assertPath(path) node = node.removeText(offset, length) document = document.updateDescendant(node) - document = document.normalize() state = state.merge({ document }) return state } diff --git a/src/transforms/by-key.js b/src/transforms/by-key.js index caa80189d..b3397d083 100644 --- a/src/transforms/by-key.js +++ b/src/transforms/by-key.js @@ -154,9 +154,32 @@ export function removeNodeByKey(transform, key) { export function removeTextByKey(transform, key, offset, length) { const { state } = transform - const { document } = state + let { document } = state const path = document.getPath(key) - return transform.removeTextOperation(path, offset, length) + transform.removeTextOperation(path, offset, length) + + // If the text node is now empty, and not needed in the tree, remove it. + document = transform.state.document + const node = document.getDescendant(key) + const parent = document.getParent(key) + + if (node.text != '') { + return transform + } + + // If the text node is now empty, and not needed in the tree, remove it. + const previous = document.getPreviousSibling(key) + const next = document.getNextSibling(key) + + if ( + (parent.nodes.size == 1) || + (previous && previous.isVoid == false) || + (next && next.isVoid == false) + ) { + transform.removeNodeByKey(key) + } + + return transform } /** diff --git a/test/transforms/fixtures/by-key/remove-text-by-key/adjacent-non-void-inlines/index.js b/test/transforms/fixtures/by-key/remove-text-by-key/adjacent-non-void-inlines/index.js new file mode 100644 index 000000000..c5deeb445 --- /dev/null +++ b/test/transforms/fixtures/by-key/remove-text-by-key/adjacent-non-void-inlines/index.js @@ -0,0 +1,10 @@ + +export default function (state) { + const { document, selection } = state + const second = document.getTexts().get(1) + + return state + .transform() + .removeTextByKey(second.key, 0, 1) + .apply() +} diff --git a/test/transforms/fixtures/by-key/remove-text-by-key/adjacent-non-void-inlines/input.yaml b/test/transforms/fixtures/by-key/remove-text-by-key/adjacent-non-void-inlines/input.yaml new file mode 100644 index 000000000..a78b31f17 --- /dev/null +++ b/test/transforms/fixtures/by-key/remove-text-by-key/adjacent-non-void-inlines/input.yaml @@ -0,0 +1,17 @@ + +nodes: + - kind: block + type: paragraph + nodes: + - kind: inline + type: link + nodes: + - kind: text + text: one + - kind: text + text: a + - kind: inline + type: link + nodes: + - kind: text + text: two diff --git a/test/transforms/fixtures/by-key/remove-text-by-key/adjacent-non-void-inlines/output.yaml b/test/transforms/fixtures/by-key/remove-text-by-key/adjacent-non-void-inlines/output.yaml new file mode 100644 index 000000000..496aeb02a --- /dev/null +++ b/test/transforms/fixtures/by-key/remove-text-by-key/adjacent-non-void-inlines/output.yaml @@ -0,0 +1,15 @@ + +nodes: + - kind: block + type: paragraph + nodes: + - kind: inline + type: link + nodes: + - kind: text + text: one + - kind: inline + type: link + nodes: + - kind: text + text: two diff --git a/test/transforms/fixtures/by-key/remove-text-by-key/inline-void/index.js b/test/transforms/fixtures/by-key/remove-text-by-key/inline-void/index.js new file mode 100644 index 000000000..c38e1667f --- /dev/null +++ b/test/transforms/fixtures/by-key/remove-text-by-key/inline-void/index.js @@ -0,0 +1,10 @@ + +export default function (state) { + const { document, selection } = state + const last = document.getTexts().last() + + return state + .transform() + .removeTextByKey(last.key, 0, 4) + .apply() +} diff --git a/test/transforms/fixtures/by-key/remove-text-by-key/inline-void/input.yaml b/test/transforms/fixtures/by-key/remove-text-by-key/inline-void/input.yaml new file mode 100644 index 000000000..fbfc98018 --- /dev/null +++ b/test/transforms/fixtures/by-key/remove-text-by-key/inline-void/input.yaml @@ -0,0 +1,12 @@ + +nodes: + - kind: block + type: paragraph + nodes: + - kind: text + text: "" + - kind: inline + type: image + isVoid: true + - kind: text + text: word diff --git a/test/transforms/fixtures/by-key/remove-text-by-key/inline-void/output.yaml b/test/transforms/fixtures/by-key/remove-text-by-key/inline-void/output.yaml new file mode 100644 index 000000000..e19de93d6 --- /dev/null +++ b/test/transforms/fixtures/by-key/remove-text-by-key/inline-void/output.yaml @@ -0,0 +1,12 @@ + +nodes: + - kind: block + type: paragraph + nodes: + - kind: text + text: "" + - kind: inline + type: image + isVoid: true + - kind: text + text: "" diff --git a/test/transforms/fixtures/by-key/remove-text-by-key/inline/index.js b/test/transforms/fixtures/by-key/remove-text-by-key/inline/index.js new file mode 100644 index 000000000..b99ee839d --- /dev/null +++ b/test/transforms/fixtures/by-key/remove-text-by-key/inline/index.js @@ -0,0 +1,10 @@ + +export default function (state) { + const { document, selection } = state + const first = document.getTexts().first() + + return state + .transform() + .removeTextByKey(first.key, 3, 1) + .apply() +} diff --git a/test/transforms/fixtures/by-key/remove-text-by-key/inline/input.yaml b/test/transforms/fixtures/by-key/remove-text-by-key/inline/input.yaml new file mode 100644 index 000000000..f752cee89 --- /dev/null +++ b/test/transforms/fixtures/by-key/remove-text-by-key/inline/input.yaml @@ -0,0 +1,10 @@ + +nodes: + - kind: block + type: paragraph + nodes: + - kind: inline + type: link + nodes: + - kind: text + text: word diff --git a/test/transforms/fixtures/by-key/remove-text-by-key/inline/output.yaml b/test/transforms/fixtures/by-key/remove-text-by-key/inline/output.yaml new file mode 100644 index 000000000..e0e015d73 --- /dev/null +++ b/test/transforms/fixtures/by-key/remove-text-by-key/inline/output.yaml @@ -0,0 +1,10 @@ + +nodes: + - kind: block + type: paragraph + nodes: + - kind: inline + type: link + nodes: + - kind: text + text: wor diff --git a/test/transforms/fixtures/by-key/remove-text-by-key/next-void-inline/index.js b/test/transforms/fixtures/by-key/remove-text-by-key/next-void-inline/index.js new file mode 100644 index 000000000..c5deeb445 --- /dev/null +++ b/test/transforms/fixtures/by-key/remove-text-by-key/next-void-inline/index.js @@ -0,0 +1,10 @@ + +export default function (state) { + const { document, selection } = state + const second = document.getTexts().get(1) + + return state + .transform() + .removeTextByKey(second.key, 0, 1) + .apply() +} diff --git a/test/transforms/fixtures/by-key/remove-text-by-key/next-void-inline/input.yaml b/test/transforms/fixtures/by-key/remove-text-by-key/next-void-inline/input.yaml new file mode 100644 index 000000000..739e5c59f --- /dev/null +++ b/test/transforms/fixtures/by-key/remove-text-by-key/next-void-inline/input.yaml @@ -0,0 +1,17 @@ + +nodes: + - kind: block + type: paragraph + nodes: + - kind: inline + type: link + nodes: + - kind: text + text: one + - kind: text + text: a + - kind: inline + type: image + isVoid: true + - kind: text + text: "" diff --git a/test/transforms/fixtures/by-key/remove-text-by-key/next-void-inline/output.yaml b/test/transforms/fixtures/by-key/remove-text-by-key/next-void-inline/output.yaml new file mode 100644 index 000000000..ebb1fd4d6 --- /dev/null +++ b/test/transforms/fixtures/by-key/remove-text-by-key/next-void-inline/output.yaml @@ -0,0 +1,15 @@ + +nodes: + - kind: block + type: paragraph + nodes: + - kind: inline + type: link + nodes: + - kind: text + text: one + - kind: inline + type: image + isVoid: true + - kind: text + text: "" diff --git a/test/transforms/fixtures/by-key/remove-text-by-key/previous-void-inline/index.js b/test/transforms/fixtures/by-key/remove-text-by-key/previous-void-inline/index.js new file mode 100644 index 000000000..af62d3422 --- /dev/null +++ b/test/transforms/fixtures/by-key/remove-text-by-key/previous-void-inline/index.js @@ -0,0 +1,10 @@ + +export default function (state) { + const { document, selection } = state + const third = document.getTexts().get(2) + + return state + .transform() + .removeTextByKey(third.key, 0, 1) + .apply() +} diff --git a/test/transforms/fixtures/by-key/remove-text-by-key/previous-void-inline/input.yaml b/test/transforms/fixtures/by-key/remove-text-by-key/previous-void-inline/input.yaml new file mode 100644 index 000000000..d468b8878 --- /dev/null +++ b/test/transforms/fixtures/by-key/remove-text-by-key/previous-void-inline/input.yaml @@ -0,0 +1,17 @@ + +nodes: + - kind: block + type: paragraph + nodes: + - kind: text + text: "" + - kind: inline + type: image + isVoid: true + - kind: text + text: a + - kind: inline + type: link + nodes: + - kind: text + text: two diff --git a/test/transforms/fixtures/by-key/remove-text-by-key/previous-void-inline/output.yaml b/test/transforms/fixtures/by-key/remove-text-by-key/previous-void-inline/output.yaml new file mode 100644 index 000000000..2a4137d88 --- /dev/null +++ b/test/transforms/fixtures/by-key/remove-text-by-key/previous-void-inline/output.yaml @@ -0,0 +1,15 @@ + +nodes: + - kind: block + type: paragraph + nodes: + - kind: text + text: "" + - kind: inline + type: image + isVoid: true + - kind: inline + type: link + nodes: + - kind: text + text: two diff --git a/test/transforms/fixtures/by-key/remove-text-by-key/text/index.js b/test/transforms/fixtures/by-key/remove-text-by-key/text/index.js new file mode 100644 index 000000000..b99ee839d --- /dev/null +++ b/test/transforms/fixtures/by-key/remove-text-by-key/text/index.js @@ -0,0 +1,10 @@ + +export default function (state) { + const { document, selection } = state + const first = document.getTexts().first() + + return state + .transform() + .removeTextByKey(first.key, 3, 1) + .apply() +} diff --git a/test/transforms/fixtures/by-key/remove-text-by-key/text/input.yaml b/test/transforms/fixtures/by-key/remove-text-by-key/text/input.yaml new file mode 100644 index 000000000..27f668fe2 --- /dev/null +++ b/test/transforms/fixtures/by-key/remove-text-by-key/text/input.yaml @@ -0,0 +1,7 @@ + +nodes: + - kind: block + type: paragraph + nodes: + - kind: text + text: word diff --git a/test/transforms/fixtures/by-key/remove-text-by-key/text/output.yaml b/test/transforms/fixtures/by-key/remove-text-by-key/text/output.yaml new file mode 100644 index 000000000..2ee7c9598 --- /dev/null +++ b/test/transforms/fixtures/by-key/remove-text-by-key/text/output.yaml @@ -0,0 +1,7 @@ + +nodes: + - kind: block + type: paragraph + nodes: + - kind: text + text: wor