Skip to content

Commit

Permalink
Field component added
Browse files Browse the repository at this point in the history
  • Loading branch information
soumak-witbybit committed Aug 10, 2022
1 parent 927f66e commit f67ced2
Show file tree
Hide file tree
Showing 4 changed files with 138 additions and 0 deletions.
58 changes: 58 additions & 0 deletions example/forms/FieldForm.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,58 @@
import * as React from 'react';
import { Field, useForm, withFormProvider } from '../../src';
import { FileField, InputField } from './components/Fields';
import { Results } from '..';

function ExtraInfoForm(props) {
const { handleSubmit, resetInitialValues } = useForm({
onSubmit: props.onSubmit,
onError: props.onError,
});
return (
<React.Fragment>
<form onSubmit={handleSubmit}>
<div
style={{
display: 'flex',
flexDirection: 'column',
gap: '10px',
alignItems: 'flex-start',
}}
>
<Field name="username">
<input type="text" placeholder="Username" />
</Field>

<Field name="email">
<input type="text" placeholder="Email" />
</Field>

<Field
name="accept"
render={({ value, onChange }) => (
<label>
<input
checked={!!value}
onChange={(e) => onChange(!value)}
type="checkbox"
/>
Do you accept?
</label>
)}
></Field>
</div>

<br />
<div>
<button type="submit">Submit</button>
<button type="button" onClick={() => resetInitialValues({})}>
Reset
</button>
</div>
</form>
<Results />
</React.Fragment>
);
}

export default withFormProvider(ExtraInfoForm);
6 changes: 6 additions & 0 deletions example/index.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@ import * as ReactDOM from 'react-dom';
import { RecoilRoot } from 'recoil';
import { useFormValues, useIsDirty } from '../src';
import DirtyCheckForm from './forms/DirtyCheckForm';
import FieldForm from './forms/FieldForm';
import ExtraInfoForm from './forms/FileUploadForm';
import FormContext from './forms/FormContext';
import MultipleSimpleForms from './forms/MultipleSimpleForms';
Expand Down Expand Up @@ -47,6 +48,11 @@ const formExamples = [
title: 'Is Dirty Prop',
getComponent: (props) => <DirtyCheckForm {...props} />,
},
{
id: 'fields-form',
title: 'Fields',
getComponent: (props) => <FieldForm {...props} />,
},
];

function App() {
Expand Down
73 changes: 73 additions & 0 deletions src/Field.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,73 @@
import React, { Fragment } from 'react';
import { useField } from './FormProvider';
import { IAncestorInput } from './types';

interface IRenderProps {
value: any;
onChange: (data: any, extraInfo?: any) => void;
error: string | null | undefined;
}

interface IField {
children?: any;
name: string;
required?: boolean;
defaultValue?: any;
handleChange?: (value?: any) => void;
ancestors?: IAncestorInput[];
render?: (props: IRenderProps) => void;
validate?: (value?: any, otherParams?: any) => string | undefined;
}

export const Field = (props: IField) => {
const {
children,
name,
required,
handleChange,
defaultValue,
ancestors,
render,
validate,
} = props;
const { fieldValue, setFieldValue, error } = useField({
name,
ancestors,
defaultValue,
validate: validate
? validate
: (value) => {
if (required) {
if (!value) {
return 'Required';
}
}
return null;
},
});

const fieldProps: any = {
value: fieldValue ?? '',
onChange: (e: any) => {
const val = e?.target?.value;
handleChange?.(val);
setFieldValue(val);
},
error,
// touched,
};

if (render) {
return (
<>{render({ value: fieldValue ?? '', onChange: setFieldValue, error })}</>
);
}

const childrenWithProps = React.Children.map(children, (child) => {
if (React.isValidElement(child)) {
return React.cloneElement(child, fieldProps);
}
return child;
});
return <Fragment>{childrenWithProps}</Fragment>;
};
1 change: 1 addition & 0 deletions src/index.tsx
Original file line number Diff line number Diff line change
@@ -1 +1,2 @@
export * from './FormProvider';
export * from './Field';

0 comments on commit f67ced2

Please sign in to comment.