React Adminで郵便番号から住所を取得するTextInputを作りたい
React Adminで郵便番号TextInputに入力すると、別のTextInputを作りたかったのだが、useFormとgetValues、setValueを使っても上手くいかず、途方に暮れていた。
結論としては、useFormContextをSimpleFormの内部で呼び出せば、getValues、setValueが使用できることがわかった。
//Zipcode.tsx
import { TextInput, useInput } from 'react-admin';
import { TextField } from '@mui/material';
import { useFormContext } from 'react-hook-form';
export default (props:{zip:string, add1:string, add2:string}) => {
const add1Input = useInput({source:props.add1});
const add2Input = useInput({source:props.add2});
const fc = useFormContext();
return (
<>
<TextInput source={props.zip} label="郵便番号" onChange={(ev:any)=>{
//7文字に達したら郵便番号APIへ検索
let postalCode:string = ev.target.value;
const m= postalCode.match(/^([0-9]{3})([0-9]{4})$/);
if(postalCode.length !== 7 || m === null )
{
return;
}
const code = m[1]+"-"+m[2];
//Google日本語入力から住所情報を取得
fetch("https://www.google.com/transliterate?langpair=ja-Hira|ja&jsonp=jsonp1670934291792&text="+code)
.then(
(r)=> {
return r.text();
})
.then(data => {
const result = data.replace(/^json.+\(+(.+)\)$/, "$1");
const address = JSON.parse(result);
//取得した情報をセット
fc.setValue(props.add1, address[0][1][0]);
});
}}/>
<TextField {...add1Input.field} label="住所" sx={{width:500}} />
<TextField {...add2Input.field} label="ビル等" sx={{width:500}} />
</>
);
};
const CustomerCreate = () => {
return (
<Create>
<SimpleForm>
<CustomerInput />
<ZipcodeInput zip="zipCode" add1="address1" add2="address2" />
</SimpleForm>
</Create>
);
};
export default (<ResourceGuesser name="customers" create={CustomerCreate} />);