Web Dev/3. React 관련
React 관련 싹훑기(12) - React-ContentEditable관련 reference가업데이트가 안되는 문제 해결,
hYhY1234
2021. 5. 30. 16:35
728x90
이번에 에러처리를 하면서 JavaScript를 좀더 알게된 느낌이다.
React-ContentEditable의 알수없는 동작?
// const orderedList = useSelector((state) => getBlockOrder(state, pageId));
// 블럭id마다의 subBlock을 가져옴
<ContentEditable
innerRef={ref}
html={blockValue}
disabled={false}
onChange={(e) => setBlockValue(e.target.value)}
onKeyDown={(e) => {
onKeyDownHandler(e, pageId, blockId, depth);
}}
onBlur={(e) => onBlurHandler(e)}
className={`w-full p-2 rounded-md hover:bg-gray-200`}
tabIndex="-1"
/>
<span
{...forHandle}
className="w-8 block hover:bg-gray-400 flex justify-center align-center"
>
<img src={Dot} className="dot" alt="logo" width="10px" />
</span>
이런식으로 ContentEditable을 사용하고 있다. 그런데블럭 id당 subBlock을 매핑해놓은 객체(orderedList라는 변수로 선언)를 어떤 수를 써도 onKeyDown에 준 콜백함수에 넘겨줄수가 없었다. 아예 rerendering이 되도 계속 기존의 값만 참조했다.
// 해당 id의 하위 블럭들을 모아서 보내준다
const blockToSubBlock = {};
// 이 reference로 모든 애들이 접근할거라, 얘는 그대로 고정. react-contentEditable이 콜백을 한번 렌더링하고나면 안바꾸는것 같다
export const getBlockOrder = (state, pageId) => {
Object.getOwnPropertyNames(blockToSubBlock).forEach(function (prop) {
delete blockToSubBlock[prop];
});
const recursive = (blockList) => {
for (let i = 0; i < blockList.length; i++) {
const getSubBlock = getCurrentBlockInfo(state, blockList[i]).blocks;
blockToSubBlock[blockList[i]] = getSubBlock;
if (getSubBlock.length > 0) {
recursive(getSubBlock);
}
}
};
blockToSubBlock[-1] = getPageState(state).pageById[pageId].blocks;
recursive(blockToSubBlock[-1]);
return blockToSubBlock;
};
이건 내가 subBlock의 정보를 select해오는 함수인데, blockToSubBlock을 getBlockOrder함수내에서 선언하지않고, 밖에 선언해서 reference는 고정하고, 새로 state가 업데이트될때, onKeyDown에 넘겨준 콜백함수가 초반에 가져간 orderList의 reference가 업데이트 되지 않더라도 변경된 값을 읽을 수 있도록 했다.
한 두세시간 삽질을 했는데 해결해서 다행이다.
이제 블럭 재정렬되고, 엔터되고, 탭된다. focus쪽은 조금 미비한데, 정말 notion만든 사람들 많이 고생했겠구나 싶은 시간이다.