1
0
mirror of https://github.com/ianstormtaylor/slate.git synced 2025-04-21 22:02:05 +02:00

fix to not create snapshot history for selection changes, closes #94

This commit is contained in:
Ian Storm Taylor 2016-07-18 16:52:11 -07:00
parent 826956c2c9
commit a50ec42d67

View File

@ -68,25 +68,16 @@ const SELECTION_TRANSFORMS = [
]
/**
* State transforms, that act on both the document and selection.
* State-level document transforms.
*/
const STATE_TRANSFORMS = [
'collapseToEndOfNextBlock',
'collapseToEndOfNextText',
'collapseToEndOfPreviousBlock',
'collapseToEndOfPreviousText',
'collapseToStartOfNextBlock',
'collapseToStartOfNextText',
'collapseToStartOfPreviousBlock',
'collapseToStartOfPreviousText',
const STATE_DOCUMENT_TRANSFORMS = [
'delete',
'deleteBackward',
'deleteForward',
'insertFragment',
'insertText',
'addMark',
'moveTo',
'setBlock',
'setInline',
'splitBlock',
@ -98,6 +89,30 @@ const STATE_TRANSFORMS = [
'wrapInline'
]
/**
* State selection transforms.
*/
const STATE_SELECTION_TRANSFORMS = [
'collapseToEndOfNextBlock',
'collapseToEndOfNextText',
'collapseToEndOfPreviousBlock',
'collapseToEndOfPreviousText',
'collapseToStartOfNextBlock',
'collapseToStartOfNextText',
'collapseToStartOfPreviousBlock',
'collapseToStartOfPreviousText',
'moveTo',
]
/**
* All state-level transforms.
*/
const STATE_TRANSFORMS = []
.concat(STATE_DOCUMENT_TRANSFORMS)
.concat(STATE_SELECTION_TRANSFORMS)
/**
* All transforms.
*/
@ -122,23 +137,12 @@ const DEFAULT_PROPERTIES = {
class Transform extends new Record(DEFAULT_PROPERTIES) {
/**
* Create a history-ready snapshot of the current state.
*
* @return {Snapshot} snapshot
*/
snapshot() {
let { state, steps } = this
let { document, selection } = state
return new Snapshot({ document, selection, steps })
}
/**
* Apply the transform and return the new state.
*
* @param {Object} options
* @property {Boolean} isNative
* @property {Boolean} snapshot
* @return {State} state
*/
@ -149,29 +153,9 @@ class Transform extends new Record(DEFAULT_PROPERTIES) {
let { undos, redos } = history
// Determine whether we need to create a new snapshot.
let shouldSnapshot = false
const previous = undos.peek()
// If there isn't a previous state, snapshot.
if (!previous) shouldSnapshot = true
// If there is a previous state but the steps are different, snapshot.
if (!shouldSnapshot && previous) {
const types = steps.map(step => step.type)
const prevTypes = previous.steps.map(step => step.type)
const diff = xor(types.toArray(), prevTypes.toArray())
if (diff.length) shouldSnapshot = true
}
// If the current steps aren't one of the "combinale" types, snapshot.
if (!shouldSnapshot) {
const allCombinable = (
steps.every(step => step.type == 'insertText') ||
steps.every(step => step.type == 'deleteForward') ||
steps.every(step => step.type == 'deleteBackward')
)
if (!allCombinable) shouldSnapshot = true
}
const shouldSnapshot = options.snapshot == null
? this.shouldSnapshot()
: options.snapshot
// If we should, save a snapshot into the history before transforming.
if (shouldSnapshot) {
@ -237,6 +221,63 @@ class Transform extends new Record(DEFAULT_PROPERTIES) {
}
}
/**
* Check whether the current transform steps should create a snapshot.
*
* @return {Boolean}
*/
shouldSnapshot() {
const transform = this
const { state, steps } = transform
const { cursorMarks, history, selection } = state
const { undos, redos } = history
const previous = undos.peek()
// If the only steps applied are selection transforms, don't snapshot.
const onlySelections = steps.every((step) => {
return (
includes(SELECTION_TRANSFORMS, step.type) ||
includes(STATE_SELECTION_TRANSFORMS, step.type)
)
})
if (onlySelections) return false
// If there isn't a previous state, snapshot.
if (!previous) return true
// If there is a previous state but the steps are different, snapshot.
const types = steps.map(step => step.type)
const prevTypes = previous.steps.map(step => step.type)
const diff = xor(types.toArray(), prevTypes.toArray())
if (diff.length) return true
// If the current steps aren't one of the "combinable" types, snapshot.
const allCombinable = (
steps.every(step => step.type == 'insertText') ||
steps.every(step => step.type == 'deleteForward') ||
steps.every(step => step.type == 'deleteBackward')
)
if (!allCombinable) return true
// Otherwise, don't snapshot.
return false
}
/**
* Create a history-ready snapshot of the current state.
*
* @return {Snapshot} snapshot
*/
snapshot() {
let { state, steps } = this
let { document, selection } = state
return new Snapshot({ document, selection, steps })
}
/**
* Undo to the previous state in the history.
*