Skip to content

Instantly share code, notes, and snippets.

@PranavSK
Created January 18, 2024 05:37
Show Gist options
  • Save PranavSK/25e52ed1c21c35c0171d7900b316d2b8 to your computer and use it in GitHub Desktop.
Save PranavSK/25e52ed1c21c35c0171d7900b316d2b8 to your computer and use it in GitHub Desktop.
import { type WritableStore, action, onNotify } from 'nanostores'
export function createHistory<Value>(store: WritableStore<Value>): {
clearHistory: () => void
redo: () => void
undo: () => void
} {
let historyIndex = -1
let history: Value[] = [store.get()]
let isInternalChange = false
onNotify(store, () => {
// The store value can be undefined if there are no subscribers
// Do not update the history if there are no subscribers
if (isInternalChange || store.lc <= 0) return
const newHistory = history.slice(0, historyIndex + 1)
newHistory.push(store.value!)
history = newHistory
historyIndex = history.length - 1
})
const undo = action(store, 'undo', (store) => {
if (historyIndex <= 0) return
historyIndex--
isInternalChange = true
store.set(history[historyIndex])
isInternalChange = false
})
const redo = action(store, 'redo', (store) => {
if (historyIndex === history.length - 1) return
historyIndex++
isInternalChange = true
store.set(history[historyIndex])
isInternalChange = false
})
const clearHistory = () => {
history = [store.get()]
historyIndex = 0
}
return { clearHistory, redo, undo }
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment