@@ -2,6 +2,7 @@ import React, { useContext, useEffect, useState } from "react";
22import { FieldContext } from "../contexts/field-context" ;
33import { GroupContext } from "../contexts/group-context" ;
44import { useForceUpdate } from "../force-update" ;
5+ import { GroupStore } from "../stores/group-store" ;
56
67export interface FieldValues {
78 defaultValue ?: string ;
@@ -13,55 +14,31 @@ export interface TextFieldProps extends FieldValues {
1314 name : string ;
1415}
1516
16- export const SEPARATOR = "." ;
17-
18- function useFieldId ( props : Pick < TextFieldProps , "name" > ) : string {
19- const { groupId } = useContext ( GroupContext ) ;
20- if ( groupId == null ) {
21- return props . name ;
22- }
23- return `${ groupId } ${ SEPARATOR } ${ props . name } ` ;
17+ interface FieldResult {
18+ store : GroupStore ;
19+ fieldId : string ;
20+ fieldProps : JSX . IntrinsicElements [ "input" ] ;
2421}
2522
26- function useRegisterField (
27- fieldId : string ,
28- props : TextFieldProps ,
29- updateHandler : ( ) => void
30- ) : void {
31- useEffect ( ( ) => {
32- const { store } = useContext ( GroupContext ) ;
23+ function useField ( props : TextFieldProps ) : FieldResult {
24+ const [ currentValue , setCurrentValue ] = useState ( "" ) ;
3325
34- let { defaultValue, initialValue } = props ;
35- if ( defaultValue == null ) {
36- defaultValue = "" ;
37- }
26+ const { store, groupId } = useContext ( GroupContext ) ;
3827
39- if ( initialValue == null ) {
40- initialValue = defaultValue ;
41- }
28+ if ( groupId == null ) {
29+ // TODO: Error message.
30+ throw new Error ( "groupId is not defined." ) ;
31+ }
4232
43- store . registerField ( fieldId , props . name , defaultValue , initialValue ) ;
33+ let { defaultValue, initialValue } = props ;
4434
45- store . addListener ( updateHandler ) ;
35+ const fieldId = store . generateFieldId ( props . name , groupId ) ;
4636
47- return ( ) => {
48- // First, remove listener to not get any more updates.
49- store . removeListener ( updateHandler ) ;
50- // Then, unregister field.
51- store . unregisterField ( fieldId ) ;
52- } ;
53- } , [ ] ) ;
54- }
55-
56- export const TextField = ( props : TextFieldProps ) => {
57- const { store } = useContext ( GroupContext ) ;
58- const [ currentValue , setCurrentValue ] = useState ( "" ) ;
59-
60- const fieldId = useFieldId ( props ) ;
37+ const onChange : React . ChangeEventHandler < HTMLInputElement > = event => {
38+ store . updateValue ( fieldId , event . target . value ) ;
39+ } ;
6140
6241 useEffect ( ( ) => {
63- let { defaultValue, initialValue } = props ;
64-
6542 if ( defaultValue == null ) {
6643 defaultValue = "" ;
6744 }
@@ -70,40 +47,38 @@ export const TextField = (props: TextFieldProps) => {
7047 initialValue = defaultValue ;
7148 }
7249
73- store . registerField ( fieldId , props . name , defaultValue , initialValue ) ;
50+ store . registerField ( props . name , groupId , defaultValue , initialValue ) ;
7451
75- const updateValue = ( ) => {
52+ const storeUpdated = ( ) => {
7653 const field = store . getField ( fieldId ) ;
7754 if ( field == null ) {
7855 return ;
7956 }
8057 setCurrentValue ( field . currentValue ) ;
8158 } ;
82- updateValue ( ) ;
59+ storeUpdated ( ) ;
8360
84- store . addListener ( updateValue ) ;
61+ store . addListener ( storeUpdated ) ;
8562
8663 return ( ) => {
87- store . removeListener ( updateValue ) ;
64+ // First, remove listener to not get any more updates.
65+ store . removeListener ( storeUpdated ) ;
66+ // Then, unregister field.
8867 store . unregisterField ( fieldId ) ;
8968 } ;
9069 } , [ ] ) ;
91-
92- const onChange = ( event : React . ChangeEvent < HTMLInputElement > ) => {
93- const value = event . target . value ;
94- store . updateValue ( fieldId , value ) ;
70+ return {
71+ fieldId : fieldId ,
72+ store : store ,
73+ fieldProps : {
74+ value : currentValue ,
75+ onChange : onChange
76+ }
9577 } ;
78+ }
9679
97- const onFocus = ( event : React . FocusEvent < HTMLInputElement > ) => {
98- console . debug ( event . target ) ;
99- } ;
80+ export const TextField = ( props : TextFieldProps ) => {
81+ const { fieldId, store, fieldProps } = useField ( props ) ;
10082
101- return (
102- < input
103- type = "text"
104- value = { currentValue }
105- onChange = { onChange }
106- onFocus = { onFocus }
107- />
108- ) ;
83+ return < input type = "text" { ...fieldProps } /> ;
10984} ;
0 commit comments