Skip to content

Commit

Permalink
fix(useCheckboxFieldProps): extend to support BooleanField as input
Browse files Browse the repository at this point in the history
fixes #33
  • Loading branch information
MiroslavPetrik committed Dec 5, 2023
1 parent 97d50b3 commit c3c59c0
Show file tree
Hide file tree
Showing 4 changed files with 70 additions and 5 deletions.
23 changes: 23 additions & 0 deletions src/fields/boolean-field/booleanField.stories.tsx
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
import { booleanField } from "./booleanField";
import { RadioGroupField } from "../../components/radio-group/RadioGroupField";
import { formStory, meta } from "../../scenarios/StoryForm";
import { CheckboxInput } from "../checkbox-field/CheckboxInput.mock";

export default {
...meta,
Expand Down Expand Up @@ -72,3 +73,25 @@ export const Optional = formStory({
},
},
});

export const OptionalCheckbox = formStory({
args: {
fields: {
approved: booleanField().optional(),
},
children: ({ fields }) => (
<CheckboxInput
field={fields.approved}
label="I preffer the digital form to the paper one"
/>
),
},
parameters: {
docs: {
description: {
story:
"Optional _booleanField_ can be submitted with the initial `undefined` value which indicates that the user didn't care to interact with the field.",
},
},
},
});
3 changes: 2 additions & 1 deletion src/fields/checkbox-field/CheckboxInput.mock.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -4,13 +4,14 @@ import { CheckboxField } from "./checkboxField";
import { FieldLabel } from "../../components";
import { FieldErrors } from "../../components/field-errors";
import { useCheckboxFieldProps, useRequiredProps } from "../../hooks";
import { BooleanField } from "../boolean-field";

export const CheckboxInput = ({
field,
label,
required,
}: {
field: CheckboxField;
field: BooleanField | CheckboxField;
label: ReactNode;
required?: boolean;
}) => {
Expand Down
38 changes: 38 additions & 0 deletions src/hooks/use-checkbox-field-props/useCheckboxFieldProps.test.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,38 @@
import { render, renderHook, screen } from "@testing-library/react";
import { userEvent } from "@testing-library/user-event";
import { describe, expect, test } from "vitest";

import { useCheckboxFieldProps } from "./useCheckboxFieldProps";
import { booleanField, checkboxField } from "../../fields";

describe("useCheckboxFieldProps()", () => {
describe("with booleanField()", () => {
test("initial value prop is false", () => {
const field = booleanField();

const checkboxProps = renderHook(() => useCheckboxFieldProps(field));

expect(checkboxProps.result.current.checked).toBe(false);
});
});

test("it reads the checked event property", async () => {
const field = checkboxField();

const checkboxProps = renderHook(() => useCheckboxFieldProps(field));

render(
<input
type="checkbox"
data-testid="input-checkbox"
{...checkboxProps.result.current}
/>,
);

expect(checkboxProps.result.current.checked).toBe(false);

await userEvent.click(screen.getByTestId("input-checkbox"));

expect(checkboxProps.result.current.checked).toBe(true);
});
});
11 changes: 7 additions & 4 deletions src/hooks/use-checkbox-field-props/useCheckboxFieldProps.ts
Original file line number Diff line number Diff line change
@@ -1,15 +1,18 @@
import { ChangeEvent, useMemo } from "react";

import { FieldProps, useFieldProps } from "../";
import { type CheckboxField } from "../../fields";
import { BooleanField, type CheckboxField } from "../../fields";

export type CheckboxFieldProps = FieldProps<CheckboxField>;
export type CheckboxFieldProps = FieldProps<CheckboxField | BooleanField>;

const getChecked = (event: ChangeEvent<HTMLInputElement>) =>
event.target.checked;

export function useCheckboxFieldProps(field: CheckboxField) {
const { value: checked, ...props } = useFieldProps(field, getChecked);
export function useCheckboxFieldProps(field: CheckboxField | BooleanField) {
// undefined (empty checkbox) is rendered as unchecked input
const { value: checked = false, ...props } = useFieldProps<
CheckboxField | BooleanField
>(field, getChecked);

return useMemo(
() => ({
Expand Down

0 comments on commit c3c59c0

Please sign in to comment.