mirror of
https://github.com/ianstormtaylor/slate.git
synced 2025-08-30 18:39:51 +02:00
fix to nudge selection outside of inline nodes, closes #349
This commit is contained in:
@@ -623,6 +623,31 @@ class Content extends React.Component {
|
|||||||
isBackward: null
|
isBackward: null
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// If the selection is at the end of a non-void inline node, and there is
|
||||||
|
// a node after it, put it in the node after instead.
|
||||||
|
const anchorText = document.getNode(anchor.key)
|
||||||
|
const focusText = document.getNode(focus.key)
|
||||||
|
const anchorInline = document.getClosestInline(anchor.key)
|
||||||
|
const focusInline = document.getClosestInline(focus.key)
|
||||||
|
|
||||||
|
if (anchorInline && anchor.offset == anchorText.length) {
|
||||||
|
const block = document.getClosestBlock(anchor.key)
|
||||||
|
const next = block.getNextText(anchor.key)
|
||||||
|
if (next) {
|
||||||
|
properties.anchorKey = next.key
|
||||||
|
properties.anchorOffset = 0
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (focusInline && focus.offset == focusText.length) {
|
||||||
|
const block = document.getClosestBlock(focus.key)
|
||||||
|
const next = block.getNextText(focus.key)
|
||||||
|
if (next) {
|
||||||
|
properties.focusKey = next.key
|
||||||
|
properties.focusOffset = 0
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
data.selection = selection
|
data.selection = selection
|
||||||
.merge(properties)
|
.merge(properties)
|
||||||
.normalize(document)
|
.normalize(document)
|
||||||
|
@@ -71,7 +71,11 @@ function Plugin(options = {}) {
|
|||||||
*/
|
*/
|
||||||
|
|
||||||
function onBeforeInput(e, data, state, editor) {
|
function onBeforeInput(e, data, state, editor) {
|
||||||
const { document, startKey, startOffset, startInline, startText } = state
|
const { document, startKey, startBlock, startOffset, startInline, startText } = state
|
||||||
|
const pText = startBlock.getPreviousText(startKey)
|
||||||
|
const pInline = pText && startBlock.getClosestInline(pText.key)
|
||||||
|
const nText = startBlock.getNextText(startKey)
|
||||||
|
const nInline = nText && startBlock.getClosestInline(nText.key)
|
||||||
|
|
||||||
// Determine what the characters would be if natively inserted.
|
// Determine what the characters would be if natively inserted.
|
||||||
const schema = editor.getSchema()
|
const schema = editor.getSchema()
|
||||||
@@ -103,15 +107,30 @@ function Plugin(options = {}) {
|
|||||||
|
|
||||||
// We do not have to re-render if the current selection is collapsed, the
|
// We do not have to re-render if the current selection is collapsed, the
|
||||||
// current node is not empty, there are no marks on the cursor, the cursor
|
// current node is not empty, there are no marks on the cursor, the cursor
|
||||||
// is not at the edge of an inline node, and the natively inserted
|
// is not at the edge of an inline node, the cursor isn't at the starting
|
||||||
|
// edge of a text node after an inline node, and the natively inserted
|
||||||
// characters would be the same as the non-native.
|
// characters would be the same as the non-native.
|
||||||
const isNative = (
|
const isNative = (
|
||||||
|
// If the selection is expanded, we don't know what the edit will look
|
||||||
|
// like so we can't let it happen natively.
|
||||||
(state.isCollapsed) &&
|
(state.isCollapsed) &&
|
||||||
(state.startText.text != '') &&
|
// If the selection has marks, then we need to render it non-natively
|
||||||
|
// because we need to create the new marks as well.
|
||||||
(state.selection.marks == null) &&
|
(state.selection.marks == null) &&
|
||||||
// Must not be, for example, at edge of an inline link
|
// If the text node in question has no content, browsers might do weird
|
||||||
|
// things so we need to insert it normally instead.
|
||||||
|
(state.startText.text != '') &&
|
||||||
|
// COMPAT: Browsers do weird things when typing at the edges of inline
|
||||||
|
// nodes, so we can't let them render natively. (?)
|
||||||
(!startInline || !state.selection.isAtStartOf(startInline)) &&
|
(!startInline || !state.selection.isAtStartOf(startInline)) &&
|
||||||
(!startInline || !state.selection.isAtEndOf(startInline)) &&
|
(!startInline || !state.selection.isAtEndOf(startInline)) &&
|
||||||
|
// COMPAT: In Chrome & Safari, it isn't possible to have a selection at
|
||||||
|
// the starting edge of a text node after another inline node. It will
|
||||||
|
// have been automatically changed. So we can't render natively because
|
||||||
|
// the cursor isn't technique in the right spot. (2016/12/01)
|
||||||
|
(!(pInline && !pInline.isVoid && startOffset == 0)) &&
|
||||||
|
(!(nInline && !nInline.isVoid && startOffset == startText.length)) &&
|
||||||
|
// If the
|
||||||
(chars.equals(nextChars))
|
(chars.equals(nextChars))
|
||||||
)
|
)
|
||||||
|
|
||||||
|
Reference in New Issue
Block a user