1- import React , { useEffect , useRef } from 'react' ;
1+ import React , { useEffect , useRef , useCallback } from 'react' ;
22import { usePageVisibility } from 'react-page-visibility' ;
33import Handsontable from 'handsontable' ;
4- import { HotTable } from '@handsontable/react' ;
54import 'handsontable/dist/handsontable.full.css' ;
65import { useAsync } from 'react-use' ;
76import styled from '@emotion/styled' ;
@@ -19,6 +18,10 @@ import {
1918} from '~/src/js/spreadsheet/hooks' ;
2019import { Loader } from '~/src/js/spreadsheet/Loader' ;
2120
21+ type HotTable = HTMLDivElement & {
22+ hotInstance ?: Handsontable ;
23+ } ;
24+
2225type SpreadSheetProps = {
2326 saveAfterChange : Handsontable . Hooks [ 'afterChange' ] ;
2427 beforeRemoveRow : Handsontable . Hooks [ 'beforeRemoveRow' ] ;
@@ -27,23 +30,14 @@ type SpreadSheetProps = {
2730 dataSchema : Handsontable . GridSettings [ 'dataSchema' ] ;
2831 data : Handsontable . GridSettings [ 'data' ] ;
2932 hotRef : React . RefObject < HotTable > ;
33+ setHotRef : ( node : HotTable ) => void ;
3034} ;
3135
3236type Props = {
3337 isLoading : boolean ;
3438 errorMessages : string ;
3539} & SpreadSheetProps ;
3640
37- const ARRAY_FIELDS = [
38- 'CHECK_BOX' ,
39- 'MULTI_SELECT' ,
40- 'FILE' ,
41- 'USER_SELECT' ,
42- 'CATEGORY' ,
43- 'SUBTABLE' ,
44- 'ORGANIZATION_SELECT' ,
45- 'GROUP_SELECT' ,
46- ] ;
4741const NOT_ALLOWED_EDIT_FIELDS = [
4842 'RECORD_NUMBER' ,
4943 'CREATED_TIME' ,
@@ -79,6 +73,18 @@ declare type CheckBoxFieldProperty = {
7973 align : 'HORIZONTAL' | 'VERTICAL' ;
8074} ;
8175
76+ export const useHookWithRefCallback = < T extends HTMLElement > ( ) : [
77+ React . MutableRefObject < T | null > ,
78+ ( node : T ) => void ,
79+ ] => {
80+ const ref = useRef < T | null > ( null ) ;
81+ const setRef = useCallback ( ( node : T ) => {
82+ ref . current = node ;
83+ } , [ ] ) ;
84+
85+ return [ ref , setRef ] ;
86+ } ;
87+
8288const getColumnData = async ( config : Config , appId : number , onChange : any ) => {
8389 const resp = await client . app . getFormFields ( { app : appId } ) ;
8490 // ヘッダーの取得
@@ -174,7 +180,8 @@ export const useSpreadSheet = ({ config, query, appId }: { config: Config; query
174180 i18n . changeLanguage ( kintone . getLoginUser ( ) . language ) ;
175181 } , [ i18n ] ) ;
176182
177- const hotRef = useRef < HotTable > ( ) ;
183+ // const hotRef = useRef<HotTable>();
184+ const [ hotRef , setHotRef ] = useHookWithRefCallback < HotTable > ( ) ;
178185 const isPageVisible = usePageVisibility ( ) ;
179186
180187 const [ fetchedAndLoadDataState , fetchAndLoadData ] = useFetchRecords ( {
@@ -239,6 +246,7 @@ export const useSpreadSheet = ({ config, query, appId }: { config: Config; query
239246 data : [ ] , // 繰り返しデータは取得するので初期値としてのデータはあたえない
240247 dataSchema : fetchedAppDataState . value ?. columnData . dataSchema ?? { } ,
241248 hotRef : hotRef as React . MutableRefObject < HotTable > ,
249+ setHotRef : setHotRef ,
242250 isLoading :
243251 fetchedAndLoadDataState . loading ||
244252 afterChangeState . loading ||
@@ -255,22 +263,22 @@ export const useSpreadSheet = ({ config, query, appId }: { config: Config; query
255263} ;
256264
257265const MemoedHotTable = React . memo < SpreadSheetProps > (
258- ( { hotRef, beforeRemoveRow, saveAfterChange, colHeaders, columns, dataSchema, data } ) => (
259- < HotTable
260- ref = { hotRef }
261- data = { data }
262- rowHeaders
263- contextMenu = { [ 'remove_row' ] }
264- minSpareRows = { 1 }
265- // width="100%"
266- // height="100vh"
267- colHeaders = { colHeaders }
268- columns = { columns }
269- dataSchema = { dataSchema }
270- afterChange = { saveAfterChange }
271- beforeRemoveRow = { beforeRemoveRow }
272- />
273- ) ,
266+ ( { setHotRef , hotRef, beforeRemoveRow, saveAfterChange, colHeaders, columns, dataSchema, data } ) => {
267+ if ( hotRef . current ) {
268+ hotRef . current . hotInstance = new Handsontable ( hotRef . current , {
269+ data : data ,
270+ rowHeaders : true ,
271+ contextMenu : [ 'remove_row' ] ,
272+ minSpareRows : 1 ,
273+ colHeaders : colHeaders ,
274+ columns : columns ,
275+ dataSchema : dataSchema ,
276+ afterChange : saveAfterChange ,
277+ beforeRemoveRow : beforeRemoveRow ,
278+ } ) ;
279+ }
280+ return < div ref = { setHotRef } > </ div > ;
281+ } ,
274282 ( prev , next ) => prev . hotRef === next . hotRef && prev . columns ?. length === next . columns ?. length ,
275283) ;
276284
@@ -290,13 +298,15 @@ export const SpreadSheet: React.FC<Props> = ({
290298 data,
291299 isLoading,
292300 errorMessages,
301+ setHotRef,
293302} ) => {
294303 return (
295304 < Wrapper >
296305 { errorMessages && < Alert isVisible text = { errorMessages } /> }
297306 { isLoading && < Loader /> }
298307 < MemoedHotTable
299308 hotRef = { hotRef }
309+ setHotRef = { setHotRef }
300310 data = { data }
301311 colHeaders = { colHeaders }
302312 columns = { columns }
0 commit comments