uiwjs / react-codemirror

CodeMirror 6 component for React. @codemirror https://uiwjs.github.io/react-codemirror/
https://uiwjs.github.io/react-codemirror/
MIT License
1.67k stars 132 forks source link

Multiple CodeMirrors in a List Breaks #309

Open fjur opened 2 years ago

fjur commented 2 years ago

I am trying to show a list of CodeMirrors, but when multiple of the component is loading in a list, it fails to properly handle state updates.

Steps to reproduce (When key={index})

  1. Click on codemirror instance 1, type in 1
  2. Click on codemirror instance 2, type in 2
  3. No text will appear in instance 2, and the text from type 1 will disappear.

When key={cuid()}, then you can properly type in instance 1 and 2, but it triggers a re-render every character and you cannot type multiple characters at a time, so this doesn't work.

If you use a normal input element, this example works, but with code mirrors, it fails.

How do I show codemirror in a list and have it properly update to the correct states?

https://codesandbox.io/s/uiwjs-react-codemirror-issues-294-forked-74fp81

jaywcjlove commented 2 years ago

@fjur

I see your code is a bit complicated. I wrote a simple example and it works fine. https://codesandbox.io/embed/react-codemirror-example-codemirror-6-forked-6u17wf?fontsize=14&hidenavigation=1&theme=dark

import React from "react";
import CodeMirror from "@uiw/react-codemirror";
import { javascript } from "@codemirror/lang-javascript";
import { oneDark } from "@codemirror/theme-one-dark";

export default function App() {
  return (
    <div>
      <CodeMirror
        value="console.log('hello world!');"
        height="200px"
        theme={oneDark}
        extensions={[javascript({ jsx: true })]}
        onChange={(value, viewUpdate) => {
          console.log("value:", value);
        }}
      />
      <CodeMirror
        value="console.log('hello world!');"
        height="200px"
        extensions={[javascript({ jsx: true })]}
        onChange={(value, viewUpdate) => {
          console.log("value:", value);
        }}
      />
      <CodeMirror
        value="console.log('hello world!');"
        height="200px"
        theme="dark"
        extensions={[javascript({ jsx: true })]}
        onChange={(value, viewUpdate) => {
          console.log("value:", value);
        }}
      />
      <CodeMirror
        value="console.log('hello world!');"
        height="200px"
        theme="light"
        extensions={[javascript({ jsx: true })]}
        onChange={(value, viewUpdate) => {
          console.log("value:", value);
        }}
      />
    </div>
  );
}