Как передавать значение из дочернего компонента к родителю vue 3?

В Vue.js 3 есть несколько способов передачи данных из дочернего компонента в родительский компонент.

1. Через события:
Дочерний компонент может вызывать событие с помощью $emit, а родительский компонент может слушать это событие с помощью v-on или сокращённой записи @. Например, в дочернем компоненте:

   // Дочерний компонент
   <template>
     <button @click="emitValue">Отправить значение</button>
   </template>

   <script>
   export default {
     methods: {
       emitValue() {
         this.$emit('valueChanged', 'Some value');
       }
     }
   }
   </script>

В родительском компоненте можно прослушивать это событие и обрабатывать переданное значение:

   // Родительский компонент
   <template>
     <child-component @valueChanged="handleValueChanged"></child-component>
   </template>

   <script>
   import ChildComponent from './ChildComponent.vue';

   export default {
     components: {
       ChildComponent
     },
     methods: {
       handleValueChanged(value) {
         console.log(value); // 'Some value'
       }
     }
   }
   </script>

2. Через модель:
Дочерний компонент может определить свойство modelValue, которое будет представлять передаваемое значение, а родительский компонент будет использовать атрибут v-model для связывания этого значения с собственным свойством. Например, в дочернем компоненте:

   // Дочерний компонент
   <template>
     <input v-model="modelValue" />
   </template>

   <script>
   export default {
     props: {
       modelValue: {
         type: String,
         required: true
       }
     },
     emits: ['update:modelValue']
   }
   </script>

В родительском компоненте можно связать значение дочернего компонента с помощью v-model:

   // Родительский компонент
   <template>
     <child-component v-model="value"></child-component>
   </template>

   <script>
   import ChildComponent from './ChildComponent.vue';

   export default {
     components: {
       ChildComponent
     },
     data() {
       return {
         value: 'Initial value'
       }
     }
   }
   </script>

Теперь значения в родительском компоненте и дочернем компоненте будут всегда синхронизированы, и изменение значения в одном компоненте приведет к изменению значения в другом компоненте.

3. Через колбэки:
Дочерний компонент может принимать функцию-колбэк через свойство и вызывать эту функцию с передаваемым значением при необходимости. Например, в дочернем компоненте:

   // Дочерний компонент
   <template>
     <button @click="emitValue">Отправить значение</button>
   </template>

   <script>
   export default {
     props: {
       valueChangedCallback: {
         type: Function,
         required: true
       }
     },
     methods: {
       emitValue() {
         this.valueChangedCallback('Some value');
       }
     }
   }
   </script>

В родительском компоненте можно передать функцию-колбэк через свойство:

   // Родительский компонент
   <template>
     <child-component :valueChangedCallback="handleValueChanged"></child-component>
   </template>

   <script>
   import ChildComponent from './ChildComponent.vue';

   export default {
     components: {
       ChildComponent
     },
     methods: {
       handleValueChanged(value) {
         console.log(value); // 'Some value'
       }
     }
   }
   </script>

Теперь при клике на кнопку в дочернем компоненте вызовется переданная колбэк-функция с переданным значением.

В зависимости от конкретной ситуации один из этих способов может быть более подходящим. Выберите тот, который лучше всего соответствует вашим требованиям и организации вашего проекта.