Tiptap: How to clear history?

Created on 14 Oct 2019  路  11Comments  路  Source: ueberdosis/tiptap

Is it possible to clear the history?

The problem is that I'm changing the content in the editor dynamically when user selects a new "file", but then the history from the last file will still be available.
Basically, when a user changes file, and hit undo, the content from the last file will be put into the editor. So I want to clear history every time the user changes files.

I've tried recreating the component using the "hack" :key="componentKey" - but it just gave an error TypeError: Cannot read property 'matchesNode' of null

Anyone know how?

wontfix

Most helpful comment

As per the suggestion of the author we should set brand new state when loading new document. I am doing it in this way if anyone needs:

this.editor.options.content = jsonDocOrHTML
this.editor.view.updateState(this.editor.createState())

All 11 comments

Did you find out how to clear the history?

I ended up doing my custom history. Not ideal but I couldn't find any other way.

Just destroy your editor and create a new one seems to do the trick.

  private editor = new Editor(this.editorOptions);

  private get editorOptions() {
    return {
       ...
    };
  }

  clearHistory() {
    this.editor.destroy();
    this.editor = new Editor(this.editorOptions);
  }

And I didn't notice any stuttering by recreating the editor (yet)

There is not such a feature in prosemirror-history. Related: https://discuss.prosemirror.net/t/reset-history-plugin-state/1883

Feel free to create a PR for prosemirror.

When loading a new file, you should create a fresh ProseMirror state. I don't intend to merge that PR until someone comes up with a more compelling use case.

@marijnh Thanks for the quick response. That makes sense. Actually, I added it according to your suggestion here https://discuss.prosemirror.net/t/reset-history-plugin-state/1883

Ah right, seems I did suggest that last year. But there's other weird effects you'll get when trying to start a new document without starting a new state (decorations might stick around, other plugins might still drag around irrelevant state), so unless someone has a more solid reason for needing this, I think providing it just steers people in the wrong direction.

As per the suggestion of the author we should set brand new state when loading new document. I am doing it in this way if anyone needs:

this.editor.options.content = jsonDocOrHTML
this.editor.view.updateState(this.editor.createState())

It would be good to encapsulate this functionality, preferably also handling the collaboration plugin state (#691). How about Editor.loadDocument(doc, version)?

this.editor.options.content = jsonDocOrHTML
this.editor.view.updateState(this.editor.createState())

So updating current editor state is not the best solution in my case. It breaks menu positioning so menu.left and menu.bottom always return 0. I believe that I found the right-way solution:

const { doc, tr } = this.editor.state;
const document = this.editor.createDocument(yourHTMLOrJSONContentHere);
const selection = TextSelection.create(doc, 0, doc.content.size);
const transaction = tr
  .setSelection(selection)
  .replaceSelectionWith(document, false)
  .setMeta('preventUpdate', true) // true by default but you can set it to false
  .setMeta('addToHistory', false); // Finally we prevent pushing content to the history

this.editor.view.dispatch(transaction);

TextSelection should be imported from 'tiptap' as well.

Note: this code only prevents pushing new content to the history stack but NOT clears the entire history. It can be useful when you need to replace content after fetching it from API.

Was this page helpful?
0 / 5 - 0 ratings

Related issues

jetacpp picture jetacpp  路  3Comments

afwn90cj93201nixr2e1re picture afwn90cj93201nixr2e1re  路  3Comments

pk-pressf1 picture pk-pressf1  路  3Comments

santicros picture santicros  路  3Comments

klaasgeldof picture klaasgeldof  路  3Comments