|
| 1 | +# useFormContext |
| 2 | + |
| 3 | +`useFormContext` is a composable to access all the exposed functionalities of `useFormHandler` in any descendant of the handlers subtree is used. By this we avoid drilling the things we need down. |
| 4 | + |
| 5 | +## How it works |
| 6 | + |
| 7 | +`useFormContext` makes use of the [Vue 3 Provide/Inject](https://vuejs.org/guide/components/provide-inject.html) feature to directly provide the exposed features of `useFormHandler` to all the subtree. |
| 8 | + |
| 9 | +As you can imagine, `useFormContext` and `useFormHandler` share the same return, nevertheless, the ancestor who consumes useFormHandler will rule things like `initialValues`, `validationMode`.... |
| 10 | + |
| 11 | +## Example: |
| 12 | + |
| 13 | +```vue |
| 14 | +<!-- Parent.vue component --> |
| 15 | +<template> |
| 16 | + <form @submit.prevent="handleSubmit(successFn)"> |
| 17 | + <input v-bind="register('firstName')" /> |
| 18 | + <input v-bind="register('lastName')" /> |
| 19 | + <Child></Child> |
| 20 | + <button type="submit">Submit</button> |
| 21 | + </form> |
| 22 | +</template> |
| 23 | +<script setup lang="ts"> |
| 24 | +import { useFormHandler } from 'vue-form-handler' |
| 25 | +import Child from './Child.vue' |
| 26 | +
|
| 27 | +const { handleSubmit, register } = useFormHandler(); |
| 28 | +const successFn = (form: Record<string, any>) => { |
| 29 | + console.log({ form }) |
| 30 | +} |
| 31 | +</script> |
| 32 | +``` |
| 33 | + |
| 34 | +```vue |
| 35 | +<!-- Child.vue component --> |
| 36 | +<template> |
| 37 | + <input v-bind="register('anotherField')" /> |
| 38 | + <GrandChild></GrandChild> |
| 39 | +</template> |
| 40 | +<script setup lang="ts"> |
| 41 | +import { useFormContext } from 'vue-form-handler' |
| 42 | +import GrandChild from './GrandChild.vue' |
| 43 | +
|
| 44 | +const { register } = useFormContext() |
| 45 | +</script> |
| 46 | +``` |
| 47 | + |
| 48 | +```vue |
| 49 | +<!-- GrandChild.vue component --> |
| 50 | +<template> |
| 51 | + <input v-bind="register('anotherField2')" /> |
| 52 | +</template> |
| 53 | +<script setup lang="ts"> |
| 54 | +import { useFormContext } from 'vue-form-handler' |
| 55 | +
|
| 56 | +const { register } = useFormContext() |
| 57 | +</script> |
| 58 | +``` |
| 59 | + |
| 60 | +Feel free to play with it, you can also combine `register` and `build` approaches for the same form, within the same and in different files |
| 61 | + |
| 62 | +::: warning |
| 63 | +Be aware that for a basic and usual functionality, We provide with a default key, If you have more than one `useFormHandler` usage in the same tree, the `injection keys` will collide, so you'll need to pass a specific one to `useFormHandler` and then to its consequent consumer, i.e: |
| 64 | + |
| 65 | +:::details |
| 66 | +```vue |
| 67 | +<!-- Parent.vue component --> |
| 68 | +<template> |
| 69 | + <div> |
| 70 | + <form @submit.prevent="handleSubmit(successFn)"> |
| 71 | + <input v-bind="register('firstName')" /> |
| 72 | + <input v-bind="register('lastName')" /> |
| 73 | + <Child></Child> |
| 74 | + <button type="submit">Submit</button> |
| 75 | + </form> |
| 76 | + <form @submit.prevent="handleSubmit2(successFn)"> |
| 77 | + <input v-bind="register2('firstName')" /> |
| 78 | + <input v-bind="register2('lastName')" /> |
| 79 | + <AnotherChild></AnotherChild> |
| 80 | + <button type="submit">Submit</button> |
| 81 | + </form> |
| 82 | + </div> |
| 83 | +</template> |
| 84 | +<script setup lang="ts"> |
| 85 | +import { useFormHandler } from 'vue-form-handler' |
| 86 | +import Child from './Child.vue' |
| 87 | +import AnotherChild from './AnotherChild.vue' |
| 88 | +
|
| 89 | +const { handleSubmit, register } = useFormHandler({ injectionKey: 'form1' }); |
| 90 | +const { handleSubmit: handleSubmit2, register: register2 } = useFormHandler({ injectionKey: 'form2' }); |
| 91 | +const successFn = (form: Record<string, any>) => { |
| 92 | + console.log({ form }) |
| 93 | +} |
| 94 | +</script> |
| 95 | +``` |
| 96 | + |
| 97 | +```vue |
| 98 | +<!-- Child.vue component --> |
| 99 | +<template> |
| 100 | + <input v-bind="register('anotherField')" /> |
| 101 | +</template> |
| 102 | +<script setup lang="ts"> |
| 103 | +import { useFormContext } from 'vue-form-handler' |
| 104 | +
|
| 105 | +const { register } = useFormContext('form1') |
| 106 | +</script> |
| 107 | +``` |
| 108 | + |
| 109 | +```vue |
| 110 | +<!-- AnotherChild.vue component --> |
| 111 | +<template> |
| 112 | + <input v-bind="register('anotherField')" /> |
| 113 | +</template> |
| 114 | +<script setup lang="ts"> |
| 115 | +import { useFormContext } from 'vue-form-handler' |
| 116 | +
|
| 117 | +const { register } = useFormContext('form2') |
| 118 | +</script> |
| 119 | +``` |
| 120 | +::: |
| 121 | + |
| 122 | +::: tip |
| 123 | +Please refer to [Working with Symbol Keys](https://vuejs.org/guide/components/provide-inject.html#working-with-symbol-keys) for a quick read and understanding how provide/inject is intended to be used, and a correct way of defining your keys, as passing plain strings might not be the best approach, but rather using `Symbol` |
| 124 | +::: |
0 commit comments